1

我有一个简单的用例,在 React-Router 4 和 Redux 环境中似乎很难实现。

当用户登录时,会触发一个 redux 承诺操作,该操作会返回一个 API 令牌、到期日期和一些其他信息。何时以及如果实现了承诺,我将希望将用户重定向到另一个页面。

我无法弄清楚如何使用上述架构以编程方式重定向用户。想在Action.js里面做,但是感觉只能在Reducers.js里面做。即使我不确定如何开始。

到目前为止我发现的最好的方法是在我的视图中有一个 Redirect 组件,并让 Promise 将loggedIn 状态设置为true,如果loggedIn 道具在视图上为true,它将返回重定向道具,然后重定向用户到所需的页面。不知何故,对于一个简单的用例来说,这感觉像是很多额外的代码。

任何意见将是有益的。谢谢你。

动作.js:

import axios from 'axios';

export function login(email, password) {
  return {
    type: 'LOGIN_USER',
    payload: axios.post('http://localhost:3114/api/users/authenticate', 
    {
      email,
      password,
    }),
  };
}

减速器.js

// Promise
// pending
// fulfilled
// rejected
const initalState = {
  token: null,
  expiryDate: '',
  loading: false,
  error: null,
};

// REDCUER
function loginReducer(state = initalState, action) {
  switch (action.type) {
    case 'LOGIN_USER_PENDING':
      return { ...state, loading: true };
    case 'LOGIN_USER_FULFILLED':
      return {
        ...state,
        loading: false,
        token: action.payload.data.token,
        expiryDate: action.payload.data.expires,
        loggedIn: true,
      };
    case 'LOGIN_USER_REJECTED':
      return { ...state, loading: false, error: `${action.payload}` };
    default:
      return state;
  }
}

export default loginReducer;

登录视图.js

render() {
        const { data, login, loggedIn } = this.props;
        if (data.loggedIn) {
          return <Redirect to="/users" push />;
        }
        return (
          ...
        )
       }

问候,埃米尔

4

1 回答 1

0

我可以看到isLoggedIn处于 Redux 状态的 a 在以后可能有用(例如,您可以将所有应该只对登录用户可见的路由/页面包装在一个组件中,该组件会检查它isLoggedIn并可能重定向到登录页面) ,所以我不一定会在那里改变任何东西。

但是,如果您仍然想找到解决此问题的另一种方法,则可以使用history.push(newUrl)orhistory.replace(newUrl)以编程方式重定向(不呈现 Redirect 组件) 。但我不确定你会在哪里称呼它。与在减速器中相比,在动作创建器中出现副作用对我来说似乎稍微不那么奇怪,所以一种可能性可能是做类似的事情

import axios from 'axios';

// pushOnResolve would be something like () => push('mynew/url')
export function login(email, password, pushOnResolve) {
  const promise = axios.post('http://localhost:3114/api/users/authenticate';
  // it's possible to have several .then on a promise
  // so this shouldn't interfere with
  // the Redux-promise or the LOGIN_USER_FULFILLED reducer
  promise.then(pushOnResolve);

  return {
    type: 'LOGIN_USER',
    payload: promise, 
    {
      email,
      password,
    }),
  };
}
于 2017-09-10T11:13:52.400 回答