ComponentDidMount 被多次调用
我构建了一个 HOC,用于在我的应用中受保护的路由.它接收应该在路由上呈现的组件,检查用户是否通过身份验证,然后如果通过,则呈现该组件.它可以工作,但会导致组件多次挂载/卸载(与调用 app.js 文件中的渲染函数的次数一样).
I built a HOC to use on protected routes in my app. It takes in the component that should be rendered at the route, checks if the user is authenticated, and then renders that component if they are. It works, but it causes the component to mount/unmount several times (as many times as the render function in my app.js file is called).
来自我的 app.js 的路由
routes from my app.js
<Switch>
<Route path='/groups/show/:id'
component={ RequireAuth(Group) } />
<Route path='/groups/create'
component={ RequireAuth(CreateGroup) } />
<Route path='/groups'
component={ RequireAuth(GroupsMenu) } />
<Route path='/tutorials/:id' component={ Tutorial } />
<Route path='/tutorials' component={ TutorialMenu } />
<Route path='/ranked' component={ RankedPlay } />
<Route path='/casual' component={ CasualPlay } />
<Route path='/offline' component={ OfflinePlay } />
<Route path='/signup' component={ Signup } />
<Route path='/' component={ Menu } />
</Switch>
require_auth.js
require_auth.js
import React, { Component } from 'react';
import { connect } from 'react-redux';
import { withRouter } from 'react-router-dom';
import { store } from '../../index';
import { AUTH_ERROR } from '../../actions';
import PropTypes from 'prop-types';
import Display from './display';
export default function(ComposedComponent) {
class Authentication extends Component {
static propTypes = {
history: PropTypes.object.isRequired
};
componentWillMount() {
const { history } = this.props;
const error = 'You must be logged in to do this. Please login';
if (!this.props.authenticated) {
store.dispatch({ type: AUTH_ERROR, payload: error });
history.push('/');
}
}
componentWillUpdate(nextProps) {
const { history } = this.props;
const error = 'You must be logged in to do this. Please login';
if (!nextProps.authenticated) {
store.dispatch({ type: AUTH_ERROR, payload: error });
history.push('/');
}
}
render() {
return (
<Display if={ this.props.authenticated } >
<ComposedComponent { ...this.props } />
</Display>
);
}
}
function mapStateToProps(state) {
return {
authenticated: state.auth.authenticated
};
}
return withRouter(connect(mapStateToProps)(Authentication));
}
如果您从任何路由中删除 RequireAuth(),则该组件只会在您点击该路由时安装一次.但是添加它会导致组件在每次 app.js render() 触发时挂载.有没有办法设置这个组件只安装一次?
If you remove RequireAuth() from any of the routes, the component only mounts once when you hit the route. But adding it causes the component to mount every time app.js render() fires. Is there a way I can set this up so the component only mounts once?
通过在渲染中调用 RequireAuth(Component)
,您在每次渲染中都使用 HOC 装饰 Component
调用,使每个渲染返回一个新组件.
By calling RequireAuth(Component)
in render, you are decorating Component
with your HOC in every render call, making that each render returns a new Component each render.
在导出它们之前,您应该使用 RequireAuth
修饰 Group
、CreateGroup
和 GroupsMenu
.就像使用 react-redux
的 connect
一样.
You should decorate Group
, CreateGroup
and GroupsMenu
with RequireAuth
, before exporting them. Just as you would with react-redux
's connect
.