使用 jwt 授权反应 js 在标头中添加授权时遇到问题?

Posted

技术标签:

【中文标题】使用 jwt 授权反应 js 在标头中添加授权时遇到问题?【英文标题】:trouble adding athorization in headers using jwt authoriation react js? 【发布时间】:2021-04-16 00:32:27 【问题描述】:

我试图用不记名令牌从我的前面到我的 api 进行授权,在我的 api 中所有它的工作我都用 insmonia 测试,当我尝试以这种方式在标题中添加授权时,问题就在前面,我使用 react-redux 存储所以和 redux-persist 持久化数据持久化,当我尝试添加这个

     export function setToken( payload ) 
      if (!payload) return;
    
      const  token  = payload.auth;
    
      if (token) 
        api.defaults.headers.authorization = `Bearer $token`;
      
    
   export default all([
    takeLatest('@auth/persist/REHYDRATE', setToken),
    takeLatest('@auth/SIGN_IN_REQUEST', signIn),
    takeLatest('@auth/SIGN_UP_REQUEST', signUp),
  ]);

但是当我重新加载我的管理页面时,我在浏览器中进行 httprequests(post/get etc),它没有在标题中接收授权并说 createError.js:16 Uncaught (in promise) 错误:请求失败,状态码为 401

    Request URL: http://localhost:3333/notifications
Request Method: GET
Status Code: 401 Unauthorized
Remote Address: [::1]:3333
Referrer Policy: strict-origin-when-cross-origin

RESPONSE HEADERS
Access-Control-Allow-Origin: *
Connection: keep-alive
Content-Length: 23
Content-Type: application/json; charset=utf-8
Date: Mon, 11 Jan 2021 00:52:14 GMT
ETag: W/"17-IQ4NhR9c983ggGeU6wL1lrE99jM"
Keep-Alive: timeout=5
X-Powered-By: Express


REQUEST HEADERS
Accept: application/json, text/plain, */
Accept-Encoding: gzip, deflate, br
Accept-Language: en-US,en;q=0.9
Cache-Control: no-cache
Connection: keep-alive
Host: localhost:3333
Origin: http://localhost:3000
Pragma: no-cache
Referer: http://localhost:3000/
Sec-Fetch-Dest: empty
Sec-Fetch-Mode: cors
Sec-Fetch-Site: same-site
Sec-GPC: 1
User-Agent: Mozilla/5.0 (Linux; android 6.0; Nexus 5 Build/MRA58N) AppleWebKit/537.36 (Khtml, like Gecko) Chrome/87.0.4280.101 Mobile Safari/537.36

我做错了什么?如何添加不记名和令牌的授权?

如果有助于理解问题,这是我的项目存储库 https://github.com/dariocoroneldev/Error

【问题讨论】:

我尝试导入 axios 并以这种方式制作。 axios.defaults.headers.common.Authorization = Bearer $token;但即使这样仍然无法正常工作 我没有专门使用redux-persist,所以我不能说是否存在与此相关的问题,但我假设它会重新加载状态,但它会在不调用的情况下这样做您的任何操作,因此永远不会调用setToken,因此永远不会设置身份验证。我个人有一个类似的设置,除了我在我的应用程序的顶层获取我保存的令牌并确保在加载时设置它。我还会跟踪是否设置了身份验证,并且通常在使用“useEffects”进行许多 API 调用之前等待它被应用。 作为个人经验的附注,我还使用 redux-thunk 进行 API 调用,我可以轻松访问状态并将标头插入所有 fetch 调用,而无需将其传递到行动。我还为每个 API 调用提供了一个状态变量,因此我可以轻松跟踪正在加载或完成的内容或有一些错误等。 非常感谢您的建议,我要去研究redux-thunk,我从来没有听说过,可以帮助我谢谢 redux-thunk 本身并不能解决这个问题,但可以让生活更轻松,尤其是根据我的经验,对于身份验证和 API 调用。 【参考方案1】:

当我将授权添加到我的函数 setToken() 之外的标头时 应用程序中的任何位置,然后它都可以工作,但是如果我这样做,我会像手动那样手动进行测试,因为我不知道如何在 setToken() 之外获取我的令牌

const tokentest =
  'eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJpZCI6MiwiaWF0IjoxNjEwMzE3NDcwLCJleHAiOjE2OTY2MzEwNzB9.TikP-RQknI5YMVZmirTH69agd2P0zsW5jIHFcK27kO8';

api.defaults.headers.Authorization = `Bearer $tokentest`;

现在问题不再是发送授权,现在我不知道如何使用我由 react-perssit 库生成的操作在 setToken 函数之外获取我的令牌,所以这里是我的代码

 import  takeLatest, call, put, all  from 'redux-saga/effects';
    import  toast  from 'react-toastify';
    import history from '~/services/history';
    import api from '~/services/api';
    import  signInSuccess, signFailure  from './actions';
    
    // const test = api.defaults.headers.Authorization;
    // console.log(test);

      //here it work, but how can i get my token from here?
      //why just working here and not inside my fucntion?

      const tokentest =
  'eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJpZCI6MiwiaWF0IjoxNjEwMzE3NDcwLCJleHAiOjE2OTY2MzEwNzB9.TikP-RQknI5YMVZmirTH69agd2P0zsW5jIHFcK27kO8';

api.defaults.headers.Authorization = `Bearer $tokentest`;
    
    export function* signIn( payload ) 
      try 
        const  email, password  = payload;
    
        const response = yield call(api.post, 'session', 
          email,
          password,
        );
        const  token, user  = response.data;
    
        if (!user.provider) 
          toast.error('usario no es porveedor');
        

         //but here doe'snt work nothing when i do this
    
         api.defaults.headers.Authorization = `Bearer $token`;
    
        yield put(signInSuccess(token, user));
    
        history.push('/admin');
       catch (err) 
        toast.error('error de autenticacion, verifique sus datos');
        yield put(signFailure());
      
    
    
    export function* signUp( payload ) 
      try 
        const  name, email, password, whatsapp, repeatPassword  = payload;
        yield call(api.post, 'users', 
          name,
          email,
          password,
          whatsapp,
          repeatPassword,
          provider: true,
        );
    
        history.push('/sesion');
       catch (err) 
        toast.error('error al registarse');
        yield put(signFailure());
      
    
       //here not working too
    export function setToken( payload ) 
      if (!payload) return;
      const  token  = payload.auth;
      console.log(token);
      if (token) 
        api.defaults.headers.Authorization = `Bearer $token`;
      
    
    
    export default all([
      takeLatest('@auth/persist/REHYDRATE', setToken),
      takeLatest('@auth/SIGN_IN_REQUEST', signIn),
      takeLatest('@auth/SIGN_UP_REQUEST', signUp),
    ]);

为什么只在这里工作而不是在我的职能范围内工作?

【讨论】:

以上是关于使用 jwt 授权反应 js 在标头中添加授权时遇到问题?的主要内容,如果未能解决你的问题,请参考以下文章

添加 JWT 授权标头后,CORS 无法工作

simple-auth-token JWT 授权未设置授权标头

使用节点 js 获取授权标头令牌

JwtModule 不添加授权标头

在 Volley 请求中添加 JWT 令牌

JWT:如何在标头中发送授权?