ReactNative——fetch封装新姿势

Posted TaoLee-

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了ReactNative——fetch封装新姿势相关的知识,希望对你有一定的参考价值。

React和ReactNative 的网络请求使用的是fetch

关于基本的POST和GET请求以及异步变同步就不再描述,看看API的介绍。

网络请求封装要完成的内容有:

1、基本功能(网络请求)

2、统一处理

异常处理
不同错误码处理

3、可定制loading弹窗提示

4 、可定制Header

5、超时处理

6、登陆验证token处理

7、url 特殊字符处理

8、网络请求日志打印

超级方便的调试技巧

const WrapFetch = (url, req, config) => 
  //默认参数
  let request = 
    method: 'GET',
    headers: 
      'Accept': 'application/json',
      'Content-Type': 'application/json',
      'Authorization': 'Bearer ' + (window.token || '')
    
  ;

  //配置参数
  //默认不显示进度条,如果需要显示config传参 showLoading: true
  const cnf = Object.assign(, 
    showLoading: false,
    showLoginView: true
  , config);

   //默认header,如果需要特殊处理可通过传参改变
  if (req && req.headers) 
    const mergeHeader =  Object.assign(, request.headers, req.headers);
    request.headers = mergeHeader;
    delete req.headers;
  

  //merge
  const merge = Object.assign(, request, req);


  //去掉url中可能存在的//
  url = url.replace(/([^:])\\/\\//, '$1/');

  if (__DEV__) 
    console.log('请求->', url, '\\n', JSON.stringify(merge, null, 2));
  

  return new Promise((resolve, reject) => 
    let isServerOk = true;
    let httpStatus = 200;

    //超时优化
    let httpTimeout = setTimeout(() => 
      const err = 
        code: 'S-000002',
        message: '网络超时'
      ;
      //计时开始,显示弹窗
      if (cnf.showLoading) 
        msg.emit('ModalLoading:hide');
      
      msg.emit('app:tip', err.code + '-' + err.message);
      reject(err);
    , 5000);


    //如果配置showLoading为true,显示modalloading
    if (cnf.showLoading) 
      msg.emit('ModalLoading:show');
    


    fetch(url, merge)
      .then(res => 
        //清除网络超时
        clearTimeout(httpTimeout);
        //当前的http的状态
        httpStatus = res.status;
        //判断server是不是异常状态404500等
        isServerOk = !!(res.status >= 200 && res.status < 300);
        //promise
        return res.json();
      )
      .then((res) => 
        //hide
        if (cnf.showLoading) 
          msg.emit('ModalLoading:hide');
        
        if (isServerOk&&res.code===1000) 
          if (__DEV__) 
            console.info('响应->', httpStatus, url, '\\n', res);
          
          //数据正确返回
          resolve(res);
         else 
          if (__DEV__) 
            console.info('响应->', url, httpStatus, '\\n', res);
          
          if (httpStatus == 401) 
            if(cnf.showLoginView)
              msg.emit('tokenInvalid');
            
            //token过期或者校验错误,将token清除
            AsyncStorage.setItem('token', '');
            window.token = '';
           else 
            if (res.code === 'N-000001') 
              // 系统异常隐藏
              msg.emit('app:tip', '您的网络不给力:(');
             else 
              msg.emit('app:tip', res.message);
            
          
          reject(res);
        
      )
      .catch((err) => 
        //清除网络超时
        clearTimeout(httpTimeout);

        if (cnf.showLoading) 
          msg.emit('ModalLoading:hide');
        

        if (__DEV__) 
          console.info('WrapFetchError:', err);
        

        msg.emit('app:tip', '您的网络不给力:(');
        reject(
          code: 'N-000001',
          message: '网络错误'
        );
      )
      .done();
  );
;


export default WrapFetch;

msg.emit()是iflux-native框架的事件方法,用于调用相关方法

具体实现需要根据后端定义的接口状态码,使其符合你的项目。

以上是关于ReactNative——fetch封装新姿势的主要内容,如果未能解决你的问题,请参考以下文章

fetch获取json的正确姿势

fetch网络请求 get 和 post

React Native / Expo:Fetch 抛出“网络请求失败”

React Native探索使用fetch进行网络请求

TypeScript开发ReactNative之fetch函数的提示问题

react-native——fetch