钩子中的React类组件的this.props.history.push('/ some_route')等效于什么?

时间:2020-06-13 18:32:56

标签: reactjs routes react-hooks

我正在努力实现

import {isAuthorized} from '../somewhere'
async componentDidMount() {
   const authorized = await isAuthorized()
   if(!authorized){
   this.props.history.push('/login')
  }
}

在react hooks中,我如何实现这一确切功能,谢谢

5 个答案:

答案 0 :(得分:1)

您将需要使用useEffect钩子:

useEffect(async () => {
  const authorized = await isAuthorized()
   if(!authorized){
   props.history.push('/login') // note: not this.props but simply props
  }
},[]) // empty array to call effect in mounted period.

但是react不允许直接在useEffect挂钩中执行异步操作。您可以在其中包装一个异步函数:

useEffect(() => {
  (async () => {
   //...
  })()
},[])

有关更多详细信息,您可以查看我的another post

答案 1 :(得分:1)

useEffect(() => {
const apiCall = async () => {
  const authorized = await isAuthorized()
   if(!authorized){
   props.history.push('/login');
  }
}

apiCall()
},[]) 

您需要将await包装在一个异步函数中,并在useEffect函数的主体中调用该异步函数apiCall。

答案 2 :(得分:1)

我认为在这种情况下,您可以使用useHistory钩子,如下所示:

import React from 'react'
import { useHistory } from 'react-router-dom'

export default props => {
    const history = useHistory()

    React.useEffect(() => {
        const isLogged = async () => {
            const authorized = await isAuthorized()
            return authorized
        }
        const authorized = isLogged()
        if(!authorized)
            history.replace('/login') // to replace the route , in order to push : history.push('/login')
    },[])
}

编辑:

是的,它不能设为异步,我更改了答案。抱歉。

答案 3 :(得分:1)

您可以使用useHistory钩子来访问history实例,并在history.push内部调用useEffect以导航到所需的路线。

import {isAuthorized} from '../somewhere';
import { useHistory } from "react-router-dom";

function SomeComponent(props) {
  const history = useHistory()

  useEffect(() => {
    const navigate = async () => {
       const authorized = await isAuthorized();

       if(!authorized){
          history.push('/login')
       }
    }

    // call the async function 
    navigate()

  }, [])
}

请记住,由于可能的竞争条件,React不允许将useEffect的回调用作async函数。因此,您必须在async挂钩中定义一个新的useEffect函数并调用它。

答案 4 :(得分:0)

还有一种替代方案来自 redux-react-hooks 库的 useDispatch() 钩子。它通常用于调用 store 操作,然后调用 store reducer,但您也可以通过 react-router-redux 中定义的 push 方法来传递路由/路径名数据。

import {isAuthorized} from '../somewhere';
import {useDispatch} from "redux-react-hook";
import {push} from "react-router-redux";
async componentDidMount() {
   const authorized = await isAuthorized();
   const dispatch = useDispatch();
   if(!authorized){
      dispatch(push('/login'));
  }
}