0

我正在尝试创建一个每分钟都会发出 API 请求以刷新会话的 cron 作业。在我refreshToken作为请求正文发送的请求中。刷新令牌,我从商店获得。贝娄是我的要求。

api.actions.js

export const getAccessToken = () => {
  const { refreshToken } = store.getState(); // getting refreshToken from store
  return apiDefaultAction({
    url: ACCESS_TOKEN_URL,
    method: 'POST',
    data: {
      refresh_token: refreshToken,
    },
    onSuccess: apiData => {
      return {
        type: ACCESS_TOKEN_SUCCESS,
        payload: { ...apiData },
      };
    },
  });
};

请求响应是一个新的accessTokenrefreshToken。reducer 用新的accessTokenand更新 store refreshToken

export default (state = initialState, action) => {
  switch (action.type) {
    ...
    case ACCESS_TOKEN_SUCCESS:
      return {
        ...state,
        accessToken: action.payload.accessToken,
        refreshToken: action.payload.refreshToken,
      };
  }
};

我在组件内启动了调用此方法的 cron 作业:

import schedule from 'node-schedule';

const RUN_EVERY_MINUTE = '0 * * * * *';

export const initiateAccessToken = () => {
  schedule.scheduleJob(RUN_EVERY_MINUTE, () => {
    store.dispatch(getAccessToken());
  });
};

但是,当请求每分钟都发生时refreshToken,从第一个状态开始,它总是相同的。第一个请求收到 200,其余请求没有通过,因为refreshToken它没有来自存储的更新值并且它已过期。

我检查了请求之前和之后的状态,redux 在请求refreshToken之后更新了值,但是在 cron 作业中始终具有相同的令牌。任何想法为什么会发生这种情况?

更新

我尝试了下面的示例,按钮值也没有改变:|

import React from 'react';
import schedule from 'node-schedule';

const RUN_EVERY_10_SEC = '0,10 * * * * *';

const TestComponent = () => {
  let value = 0;
  schedule.scheduleJob(RUN_EVERY_10_SEC, () => {
    value += 1;
  });
  const Button = <button>{value}</button>;
  return <div>{Button}</div>;
};

export default TestComponent;
4

1 回答 1

1

我相信原因是你的node-schedule代码在你第一次运行它时保存了对你的任意函数的引用。这意味着它将始终在初始状态下保留对商店的引用,并解释为什么您没有看到更新。

可能最好的解决方案是将 store 作为函数的依赖项传递:

import schedule from 'node-schedule';

const RUN_EVERY_MINUTE = '0 * * * * *';

export const initiateAccessToken = (store) => {
  schedule.scheduleJob(RUN_EVERY_MINUTE, () => {
    store.dispatch(getAccessToken());
  });
};

这样,您的函数将始终对您的商店有一个新的和更新的引用。

于 2020-03-25T10:47:44.227 回答