我正在使用React 15.0.1和react-router 2.2.1 . 我正在使用App作为父组件,它呈现从路由器处理程序传递的子组件 .
var App = React.createClass({
getInitialState(){
return {
auth : false
}
},
checkAuth(){
var self = this;
$.ajax({
type : 'GET',
url : '/auth',
success : function(res){
if(res){
self.setState({
auth : true
});
}else{
self.setState({ auth : false});
}
}
});
},
render() {
return(
<div className="appWrapper">
<Navbar auth={this.state.auth}/>
<div className="container">
{this.props.children}
</div>
</div>
);
}
});
这是我的Navbar组件 .
var Navbar = React.createClass({
getInitialState(){
return{
user_actions : '' ,
auth : this.props.auth
}
},
componentDidMount(){
this.checkAuth();
},
componentWillReceiveProps(nextProps){
this.setState({
auth : nextProps.auth
}, function(){
this.checkAuthState();
});
console.log(nextProps.auth);
},
checkAuth(){
var self = this;
$.ajax({
type : 'GET',
url : '/auth',
success : function(res){
if(res){
self.setState({
auth : true
});
}else{
self.setState({ auth : false});
}
self.checkAuthState();
console.log(self.state);
}
});
},
checkAuthState(){
if(!this.state.auth){
this.state.user_actions = <ul className="nav navbar-nav navbar-right">
<li><a href="/login">Login</a></li>
<li><a href="/register">Register</a></li>
</ul>;
this.setState({
user_actions : this.state.user_actions
});
}
if(this.state.auth){
this.state.user_actions = <ul className="nav navbar-nav navbar-right">
<li><a href="/logout">Logout</a></li>
</ul>;
this.setState({
user_actions : this.state.user_actions
});
}
},
render : function(){
return (
<nav className="navbar navbar-default">
<div className="container">
<a href="/" className="navbar-brand">Reactor</a>
{this.state.user_actions}
</div>
</nav>
);
}
});
这些是我的路线处理程序 . 当用户登陆路线时,将检查他们的身份验证 . 如果验证失败,它们将被重定向到登录路由 .
var routes = (
<Router history={browserHistory}>
<Route path="/" component={require('./components/app')}>
<IndexRoute component={require('./components/dashboard/index')} onEnter={Auth.isAuthenticated}/>
<Route path="/register"
component={require('./components/authentication/register')}
onEnter={Auth.isNotAuthenticated} />
<Route path="/login"
component={require('./components/authentication/login')}
onEnter={Auth.isNotAuthenticated}/>
<Route path="*"
component={require('./components/404/404')}/>
</Route>
</Router>
);
当应用程序组件首次使用Navbar和子组件安装时,它会检查身份验证并相应地添加指向导航栏的链接 . 当用户在成功登录后从登录路由重定向到索引路由时,子组件将替换为其他组件,并且会调用该组件的生命周期方法,但Navbar不会重新渲染 . 如何重新渲染Navbar组件,以便它可以再次检查身份验证并更改为导航栏链接?
2 回答
我想通了,我从App组件传递了一个方法到子组件 .
当子组件,例如Login验证用户时,它调用作为prop传递的更新方法,将重新检查身份验证,并更改为App组件auth状态,这将触发Navbar组件上的componentWillReceiveProps方法,其中包含将更改状态和重新渲染Navbar组件 . 这就是我想要实现的目标 .
现在我可以通过调用
this.props.update()
从路由处理程序传递的任何子组件更新我的Navbar组件链接 .您需要在单独的服务中抽象auth逻辑,例如
然后在你
App
组件中你可以做到并且在您需要检查身份验证的每个路由中添加
onEnter={auth.check}
或者您可以将数据存储在localstorage中以避免每次都调用api .见basic example of auth flow with react-router