Reactjs 为cookie管理创建单独的react组件
我有一个组件,如果它的prop.paramA与存储在cookie中的paramA值不同,它就会进行渲染 下面是我将cookie管理逻辑移动到单独组件中的尝试。问题是,当showQuestion为false时,问题组件只呈现一次,因此我永远看不到问题 目前,我的代码如下所示Reactjs 为cookie管理创建单独的react组件,reactjs,cookies,react-cookie,Reactjs,Cookies,React Cookie,我有一个组件,如果它的prop.paramA与存储在cookie中的paramA值不同,它就会进行渲染 下面是我将cookie管理逻辑移动到单独组件中的尝试。问题是,当showQuestion为false时,问题组件只呈现一次,因此我永远看不到问题 目前,我的代码如下所示 // question.js import React from 'react'; import ToggleDisplay from 'react-toggle-display'; import {withCookies,
// question.js
import React from 'react';
import ToggleDisplay from 'react-toggle-display';
import {withCookies, Cookies} from 'react-cookie';
class Question extends React.Component {
static get propTypes() {
return {
cookies: instanceOf(Cookies).isRequired
}
}
constructor(props) {
super(props);
this.state = {
paramA: props.paramA,
showQuestion: props.showQuestion
};
}
componentDidMount() {
if (this.state.showQuestion) {
// do some ajax calls etc.
}
}
render() {
return (
<div id="simplequestion">
<ToggleDisplay show={this.state.showQuestion}>
<div>What is your SO profile?</div>
</ToggleDisplay>
</div>
);
}
}
export default withCookies(Question);
//question.js
从“React”导入React;
从“反应切换显示”导入切换显示;
从“react cookie”导入{withCookies,Cookies};
类问题扩展了React.Component{
静态get propTypes(){
返回{
cookies:instanceOf(cookies)。需要
}
}
建造师(道具){
超级(道具);
此.state={
帕拉玛:道具,帕拉玛,
showQuestion:props.showQuestion
};
}
componentDidMount(){
if(this.state.showQuestion){
//做一些ajax调用等。
}
}
render(){
返回(
你的个人资料是什么?
);
}
}
导出带有cookies的默认值(问题);
我编写了以下CookieManager组件-
// cookiemanager.js
import React from 'react';
import {withCookies, Cookies} from 'react-cookie';
class CookieManager extends React.Component {
static get propTypes() {
return {
cookies: instanceOf(Cookies).isRequired
}
}
constructor(props) {
super(props);
let propA = props.cookies.get('propA');
if (!propA || propA !== props.propA) {
props.cookies.set('propA', props.propA, { path: '/', maxAge: 604800});
console.log('changed', propA, props.propA);
props.propAChanged(true);
} else if (propA === props.propA) {
console.log('unchanged', propA, props.propA);
props.propAChanged(false);
}
}
render() {
return <div id="cookieManager"></div>;
}
}
export default withCookies(CookieManager);
//cookiemanager.js
从“React”导入React;
从“react cookie”导入{withCookies,Cookies};
类CookieManager扩展了React.Component{
静态get propTypes(){
返回{
cookies:instanceOf(cookies)。需要
}
}
建造师(道具){
超级(道具);
让propA=props.cookies.get('propA');
如果(!propA | | propA!==props.propA){
set('propA',props.propA,{path:'/',maxAge:604800});
console.log('changed',propA,props.propA);
props.propa已更改(true);
}否则如果(propA==props.propA){
console.log('unchanged',propA,props.propA);
道具。更改道具(错误);
}
}
render(){
返回;
}
}
导出带有cookies的默认值(CookieManager);
以下是顶级应用程序
// app.js
import React from 'react';
import Question from './question';
import CookieManager from './cookiemanager';
import { CookiesProvider } from 'react-cookie';
class App extends React.Component {
constructor(props) {
super(props);
this.state = {
paramA: props.paramA,
showQuestion: false,
avoidUpdate: false
};
this.updateShowQuestion = this.updateShowQuestion.bind(this);
}
updateShowQuestion(x) {
if (this.state.avoidUpdate) {
return;
}
this.setState({
paramA: this.state.paramA,
showQuestion: x,
avoidUpdate: !this.state.avoidUpdate
});
}
componentWillUpdate(nextProps, nextState) {
if (!nextState.avoidUpdate && nextState.paramA === this.state.paramA) {
this.setState({
paramA: this.state.paramA,
showQuestion: this.state.showQuestion,
avoidUpdate: true
});
}
}
render() {
return (
<CookiesProvider>
<CookieManager paramA={this.state.paramA} ridChanged={this.updateShowQuestion}>
<Question
paramA={this.state.paramA}
showQuestion={this.state.showQuestion}/>
</CookieManager>
</CookiesProvider>
);
}
}
export default App;
//app.js
从“React”导入React;
从“./问题”导入问题;
从“/CookieManager”导入CookieManager;
从“react cookie”导入{CookiesProvider};
类应用程序扩展了React.Component{
建造师(道具){
超级(道具);
此.state={
帕拉玛:道具,帕拉玛,
问题:错,
避免更新:false
};
this.updateShowQuestion=this.updateShowQuestion.bind(this);
}
更新show问题(x){
if(this.state.avoidUpdate){
返回;
}
这是我的国家({
帕拉玛:这个州,帕拉玛,
问题:x,,
avoidUpdate:!this.state.avoidUpdate
});
}
组件将更新(下一步,下一步状态){
如果(!nextState.avoidUpdate&&nextState.paramA===this.state.paramA){
这是我的国家({
帕拉玛:这个州,帕拉玛,
showQuestion:this.state.showQuestion,
避免更新:正确
});
}
}
render(){
返回(
);
}
}
导出默认应用程序;
您正在从这里的州政府阅读:
但是showQuestion
仅在构造函数中设置一次:
this.state={
帕拉玛:道具,帕拉玛,
showQuestion:props.showQuestion
};
当this.props
更改时,将呈现组件,但您仍在读取未更新的this.state
,因此可见输出是相同的
我认为有两种方法可以解决这个问题:
- 每当道具更改时,更新
:this.state.showQuestion
静态getDerivedStateFromProps(下一步,上一步){ if(nextrops.showQuestion!==prevState.showQuestion) 返回{showQuestion}; }
- 在
中,阅读render()
:this.props.showQuestion
这种方法看起来更容易,但使用另一种方法,您可以获得对状态更改的更细粒度控制
您还遗漏了另一件事:
组件将更新(下一步,下一步状态){
如果(!nextState.avoidUpdate&&nextState.paramA===this.state.paramA){
这是我的国家({
帕拉玛:这个州,帕拉玛,
showQuestion:this.state.showQuestion,//此行
避免更新:正确
});
}
}
您正在接收新道具,但您正在设置旧状态:showQuestion:this.state.showQuestion
。相反,从新道具-nextrops
设置新的showQuestion
值,方法如下:
组件将更新(下一步,下一步状态){
如果(!nextState.avoidUpdate&&nextState.paramA===this.state.paramA){
这是我的国家({
帕拉玛:这个州,帕拉玛,
showQuestion:nextrops.showQuestion,//此行
避免更新:正确
});
}
}
换句话说:当Cookie更改时,您希望再次呈现您的CookieManager
吗?我希望在CookieManager更改时再次呈现问题showQuestionBtw,无需在componentWillUpdate()
:paramA:this.state.paramA,
中写入setState()
。您可以省略它-旧状态保持原样,只有新传递的对象被分配到状态
。呈现条件是:如果参数与其在cookie中的值相比发生变化,则显示问题,否则不显示问题。我设法让cookiemanager只渲染了一次,但当showQuestion更改时,应用程序的渲染方法仍然没有被再次调用。您的建议在问题中很有用,但在决定渲染的父组件中却没有Question@comiventor我发现你错在哪里了。编辑