React + axios + redux 拦截器

Posted

技术标签:

【中文标题】React + axios + redux 拦截器【英文标题】:React + axios + redux interceptors 【发布时间】:2018-11-27 09:28:51 【问题描述】:

我有一个 React + redux + axios 应用程序,白色 jwt 身份验证。因此,我需要拦截对服务器的每个请求并使用令牌设置标头。问题是我必须在哪里设置此标头或实施拦截器。 (另外,我需要范围内的 redux 存储,以从存储中获取令牌)。我的想法 - 在 Index 组件中实现它。方法对吗?

【问题讨论】:

【参考方案1】:

为什么一定要手动设置header。您不能将 JWT 存储在 cookie 中,然后浏览器会自动为您转发。只需确保在 HTTP 选项中传递 credentials: 'include'

【讨论】:

【参考方案2】:

我建议你设置标题axios.defaults.headers.common.authorization。看看这里Global axios defaults。如果您需要一个工作示例,this public repo 可以帮助您。

【讨论】:

【参考方案3】:

创建一个redux-middleware 来做这些事情。

除了表现得像interceptoradd header token, 你也可以request/response transformation

另外,如果你不想返回promise和result,你可以提到你想要dispatch结果的next action

Middleware 给你一个机会to get the store statefetch & dispatch other action

const apiInterceptor = store => next => action => 

      if(action.type !== 'ajax') return next(action)

      const state = store.getState();

      state.token // get token here

      //add this api check part in some other module.
      if(action.api=='UPDATE_CLIENT') 
        
          method = 'post';
          url  = 'some url';
        
      else
      
        method = 'get';
        url  = 'other url';
      


      fetch(url, 
        method: method,
        headers : 'add token here',
        body: JSON.stringify(action.body())
      )
      .then(response => response.json())
      .then(json => json)//either return result
      //OR dispatch the result
       .then(json => 

         dispatch(type:action.next_action,payload : json)        
       )
    

将中间件与商店集成。

import customMiddleware from './customMiddleware'
const store = createStore(
  reducer,
  applyMiddleware(customMiddleware)
)

【讨论】:

这会破坏 SRP,您可以将其分解为请求/响应拦截器,让您的 api 客户端只执行 api 调用,不需要中间件,如果您不这样做,它会更简单、更清洁和更可测试的解决方案使用中间件【参考方案4】:

我建议您推荐redux-thunk。

您必须创建 api-wrapper-helper 以将 extra argument 注入 redux-thunk,然后从 redux 操作访问 api-wrapper-helper。

api-wrapper-helper 是一个获取 url 和方法作为参数并将请求发送到 api-server 然后返回结果的函数。 (您可以在此文件中设置标题)

例如你可以看到ApiClient.js 的react-redux-universal-hot-example boilerplate。

【讨论】:

【参考方案5】:

这是一篇旧帖子,但它获得了一些浏览量,所以这样的东西可以很好地工作并且很容易测试。

apiclient.js

import axios from 'axios';

import  setRequestHeadersInterceptor  from './interceptors';

const apiClient = axios.create(

  baseUrl: 'https://my.api.com',
  timeout: 3000
);

apiClient.interceptors.request.use(setRequestHeadersInterceptor);

export default apiClient;

interceptors.js

export const setRequestHeadersInterceptor = config =>

   // have each interceptor do one thing - Single Responsibility Principle
;

您应该将您的身份验证详细信息存储在 httpOnly 安全 cookie 中,然后与服务器之间的传输将是自动的

【讨论】:

以上是关于React + axios + redux 拦截器的主要内容,如果未能解决你的问题,请参考以下文章

处理 axios react-redux 应用程序中的 401 未授权错误

将错误响应拦截器放在 redux-axios-middleware 上

在 axios 拦截器中使用时,redux 调度不起作用

使用带有 JWT 令牌的 Axios 对 Redux saga 产生调用的无限循环

取消路由更改请求 (React/Redux/Axios)

在 React 中无效时自动刷新令牌