【发布时间】:2016-12-30 12:20:43
【问题描述】:
我正在使用 Meteor + React。 问题是关于在客户端本地存储持久数据的正确方法。
假设我有一个组件List,其中包含 5 篇文章:
export default class List extends Component {
render() {
return(
<ul>
<li><a href='/article1'>Article 1</li>
<li><a href='/article2'>Article 2</li>
<li><a href='/article3'>Article 3</li>
<li><a href='/article4'>Article 4</li>
<li><a href='/article5'>Article 5</li>
</ul>
);
}
}
那么假设Article 组件应该为/articleN 之类的路由渲染。
export default class Article extends Component {
render() {
return(
<main>
..
</main>
);
}
}
我的目标是构建一个VisitedList 组件,其中包含已访问文章的列表。
我的解决方案使用 persistent-session 包 (link)。有几个像 persistent-minimongo 这样的包,但我需要一个 stable 解决方案。 u2622:persistent-session 超过 27k 的下载量让我觉得它相当稳定。但同样 - 我不确定。现在谈谈我的解决方案。
在ComponentDidMount 部分的Article 组件中,我正在处理持久会话变量,例如数组元素。让我解释。首先,我检查是否存在带有key historyLength 的Session 变量。如果不是(这意味着用户第一次访问文章页面),我设置了一个名为historyLength 的新持久变量,并且等于 0。我使用这个变量来存储我的历史自制“数组”的长度。
然后我检查当前文章是否在历史记录中,如果没有 - 我将其添加到历史记录。实际上添加到历史记录 - 使用key historyN 设置一个新的持久变量,其中N = historyLength。
看代码更简单,而不是我试图用文字来解释它。
所以Article 组件的代码:
export default class Article extends Component {
componentDidMount() {
if (Session.get('historyLength')) {
console.log('history exists');
} else {
Session.setPersistent('historyLength', 0);
console.log('first history init');
}
var articleInHistory = false;
for(i = 0; i < Session.get('historyLength'); i++) {
var key = 'history' + i;
if(Session.equals(key, this.props.articleName)) {
articleInHistory = true;
console.log('already in history:', i);
} else {
console.log(i, 'product is not in history');
}
}
if(!articleInHistory) {
var newHistoryKey = 'history' + (Session.get('historyLength'));
Session.setPersistent(newHistoryKey, this.props.articleName);
var curHistoryLength = Session.get('historyLength');
Session.setPersistent('historyLength', curHistoryLength + 1);
}
}
render() {
return(
<main>
..
</main>
);
}
}
此代码工作正常。我可以在任何组件中访问Session.get('historyLength'),然后使用for 循环获取访问文章的名称:
for(i = 0; i < Session.get(historyLength); i++) {
let key = "history" + i;
console.log(key, Session.get(key));
}
最后是VisitedList 组件:
export default class VisitedList extends Component {
renderVisited() {
var visitedArticles = [];
for(i = 0; i < Session.get(historyLength); i++) {
let key = "history" + i;
visitedArticles.push(Session.get(key));
}
return visistedArticles.map((each) => {
return <li> {each} </li>
}
}
render() {
return(
<ul>
{ this.renderVisited() }
</ul>
);
}
}
我的问题是:我的解决方案是存储和使用本地持久数据的正确方法吗? 这个例子很简单,不是来自真实的项目,但它显示了问题和问题的解决方案。
我将在我的项目和购物车中构建这样的历史块。因此,如果有更有效、更快速、更正确的方法来解决这个问题,那么在我开始之前我想知道它。感谢您的回答!
【问题讨论】:
标签: session meteor reactjs local-storage persistent-storage