使用 react-router-v4 对路由执行身份验证

Posted

技术标签:

【中文标题】使用 react-router-v4 对路由执行身份验证【英文标题】:Performing Authentication on Routes with react-router-v4 【发布时间】:2018-05-17 14:11:20 【问题描述】:

我正在尝试写 Authentication 检查我的 DashBoard。但是函数本身没有被调用。谁能给我一些解决方案?我正在使用 ReactJs 进行开发。

这是路线部分:

 <Router>
            <div>
              <Route exact path="/" component=Home />
              <Route path="/SignUp" component=SignUp />
              <Route path="/SignIn" component=SignIn />
              <Route path="/Dashboard" component=Dashboard onEnter=this.requireAuth />
            </div>
          </Router>

这是函数:

  requireAuth (nextState, replace) 
    console.log("?????????????",this.state.getToken);
    if(!this.state.getToken) 
      replace(pathname: '/');
    
  

【问题讨论】:

如果您使用的是 React-router v4,请查看***.com/questions/45429963/… 我已经改变了:" requireAuth(); return / >” 但我收到“bundle.js:6004 警告:您不应在同一路由中使用 将被忽略”错误。 因为错误表明您不应该同时是组件和渲染,请按照链接答案中的建议从渲染道具渲染组件仪表板 requireAuth(); return /> 这个错误显示为“requireAuth is not defined” 不会是this.requireAuth() 【参考方案1】:

react-router v4 中,您可以使用render propRoute 以及生命周期方法来替换react-router v3 中现有的onEnter 功能。

查看此答案了解更多详情:

onEnter prop in react-router v4

但是,由于您要做的只是在 onEnter 属性中进行身份验证,因此您可以轻松创建一个执行此操作的 HOC

const RequireAuth = (Component) =>  

    return class App extends Component  
    
        componentWillMount()  
            const getToken = localStorage.getItem('token'); 
            if(!getToken)  
               this.props.history.replace(pathname: '/'); 
             
         
        render()  
           return <Component ...this.props /> 
        
     

 

export  RequireAuth 

并像使用它

<Route path="/Dashboard" component=RequireAuth(Dashboard)/>

编辑:如果您需要进行网络调用以查找是否已通过身份验证使用,您可以编写 HOC 之类的

 const RequireAuth = (Component) =>  

    return class App extends Component  
        state = 
            isAuthenticated: false,
            isLoading: true
        
    
        componentDidMount() 
            AuthCall().then(() => 
                this.setState(isAuthenticated: true, isLoading: false);
            ).catch(() => 
                this.setState(isLoading: false);
            )
         
        render()  
           const  isAuthenticated, isLoading  = this.state;
           if(isLoading) 
               return <div>Loading...</div>
           
           if(!isAuthenticated) 
               return <Redirect to="/login" />
           
           return <Component ...this.props /> 
        
     

 

export  RequireAuth 

更新:

除了HOC,你还可以去PrivateRoute这样的组件

const PrivateRoute = (component: Component, isAuthenticated, isLoading, ...rest ) =>  
           if(isLoading) 
               return <div>Loading...</div>
           
           if(!isAuthenticated) 
               return <Redirect to="/login" />
           
           return <Component ...this.props /> 
        
     
 

 export  PrivateRoute ;

你可以像这样使用它

  class App extends Component  
        state = 
            isAuthenticated: false,
            isLoading: true
        
    
        componentDidMount() 
            AuthCall().then(() => 
                this.setState(isAuthenticated: true, isLoading: false);
            ).catch(() => 
                this.setState(isLoading: false);
            )
         
        render()  
           <Router>
              <div>
                  <Route exact path="/" component=Home />
                  <Route path="/SignUp" component=SignUp />
                  <Route path="/SignIn" component=SignIn />
                  <PrivateRoute path="/Dashboard" component=Dashboard isAuthenticated=this.state.isAuthenticated isLoading=this.isLoading/>
               </div>
           </Router>
        
     

   

【讨论】:

难道有人不能通过反应开发工具编辑反应状态来制作isAuthenticated: trueisLoading: false吗?然后他们就可以访问受保护的路由 @JL9 如果他们这样做,他们将进入视图,但如果他们向后端发送无效请求,服务器应以 401 响应,然后用户界面将重定向到登录

以上是关于使用 react-router-v4 对路由执行身份验证的主要内容,如果未能解决你的问题,请参考以下文章

React-router-v6 嵌套路由只渲染主路由

react-router-v4 没有正确重定向

使用 react-router-v5 和 redux-toolkit 登录时重定向页面

《树莓派开发笔记 - 第1部分 基础篇》第7章 树莓派变身路由器

《树莓派开发笔记 - 第1部分 基础篇》第7章 树莓派变身路由器

Dora.Interception, 为.NET Core度身打造的AOP框架[4]:演示几个典型应用