如何使用isomorphic-fetch在异常处理promise之后解析json

seo*_*han 8 javascript ecmascript-6 reactjs es6-promise redux

在使用React,Redux,isomorphic-fetch,ES6 Babel实现登录功能期间.

问题

我不知道如何在checkstatus承诺之后正确组合promises以便从我的服务器获取解析的JSON数据.
我在这做错了什么?

另外,我需要isomorphic-fetch用其他更方便的包替换包吗?
欢迎任何其他包装的建议!

loginAction.js

import * as API from '../middleware/api';
import * as ActionTypes from '../actionTypes/authActionTypes';
import 'isomorphic-fetch';

function encodeCredentials(id, pwd) {
  return btoa(`${id}{GS}${pwd}`);
}

function checkStatus(response) {
  if (response.status >= 200 && response.status < 300) {
    response;
  } else {
    const error = new Error(response.statusText);
    error.response = response;
    throw error;
  }
}

function parseJSON(response) {
  return response.json();
}

export function loginFailure(error) {
  return { error, type: ActionTypes.LOGIN_FAILURE };
}

export function loginSuccess(response) {
  return dispatch => {
    dispatch({ response, type: ActionTypes.LOGIN_SUCCESS });
  };
}

export function loginRequest(id, pwd) {
  return {
    type: ActionTypes.LOGIN_REQUEST,
    command: 'login',
    lang: 'en',
    str: encodeCredentials(id, pwd),
    ip: '',
    device_id: '',
    install_ver: '',
  };
}


export function login(id, pwd) {
  const credentials = loginRequest(id, pwd);

  return dispatch => {
    fetch(`${API.ROOT_PATH}${API.END_POINT.LOGIN}`, {
      method: 'post',
      headers: {
        'Accept': 'application/json',
        'Content-Type': 'application/json',
      },
      body: JSON.stringify(credentials),
    })
    .then(checkStatus)
    .then(parseJSON)
    .then(data => {
      console.log(`parsed data ${data}`);
      dispatch(loginSuccess(data));
    })
    .catch(error => {
      console.log(`request failed ${error}`);
    });
  };

}
Run Code Online (Sandbox Code Playgroud)

jus*_*ris 7

在我的项目中,我有一个辅助函数fetchJSON,可以执行所有实用程序逻辑,例如JSON解析和状态检查.

这里是:

import fetch from 'isomorphic-fetch';

function checkStatus(response) {
  if(response.ok) {
    return response;
  } else {
    const error = new Error(response.statusText);
    error.response = response;
    throw error;
  }
}

function parseJSON(response) {
  return response.json();
}

export default function enhancedFetch(url, options) {
  options.headers = Object.assign({
    'Accept': 'application/json',
    'Content-Type': 'application/json'
  }, options.headers);
  if(typeof options.body !== 'string') {
    options.body = JSON.stringify(options.body);
  }
  return fetch(url, options)
    .then(checkStatus)
    .then(parseJSON);
}
Run Code Online (Sandbox Code Playgroud)

然后你可以在动作中使用它:

import fetchJSON from '../utils/fetchJSON'; // this is the enhanced method from utilities

export function login(id, pwd) {
    const credentials = loginRequest(id, pwd);

    return dispatch => {
       fetchJSON(`${API.ROOT_PATH}${API.END_POINT.LOGIN}`, {
           method: 'post',
           body: credentials
       }).then(data => {
           console.log(`parsed data ${data}`);
           dispatch(loginSuccess(data));
       }).catch(error => {
           console.log(`request failed ${error}`);
       });
   };
}
Run Code Online (Sandbox Code Playgroud)

它可以帮助您从一些样板代码中保持操作代码的清洁.在有大量类似fetch电话的大项目中,这是一件非常必要的事情.