Jam*_*een 12 javascript reactjs react-native redux react-redux
我想在使用Redux的React应用程序中显示一些新闻.
问题是我想显示个别日期的新闻,我想分页新闻.
在我的API我打印
{
pagination: {
count: 1000,
size: 10,
page: 1,
pages: 100
},
news: [
..
]
}
Run Code Online (Sandbox Code Playgroud)
我知道如何进行简单的分页,但如果我希望能够在我的应用程序中显示不同日期的新闻,我不知道API应该如何工作.
到目前为止(没有日期),我刚刚保留了一个状态news并pagination在我的Redux reducer中,然后检查页码是否等于总页数以确定是否应该尝试加载更多新闻.
但现在我可能有很多不同的日期,我想在Redux商店保留所有新闻,我不知道如何构建它.
我可以按原样保留我的API,因为使用GET参数进行过滤?date=15-09-2017只会减少API结果中的新闻数量.
但是仍然可以将所有新闻保存news在我的reducer 中的变量数组中,或者我是否必须将其构造成类似的东西
news: {
'15-09-2017': {
news: [...],
pagination: {}
},
...
}
Run Code Online (Sandbox Code Playgroud)
为了跟踪每个日期的分页?
认为一个结构,你按照id和id存储你的新闻每个日期将是良好和灵活的结构:
{
"byId": {
"10": { /* News */ },
"14": { /* News */ },
/* ... */
},
"listsByDate": {
"2017-08-24": {
"total": 100,
"pageSize": 10,
"page": 2,
"items": [
10,
14,
/* ... */
]
}
}
}
Run Code Online (Sandbox Code Playgroud)
您可以为此结构实现简单的选择器:
const getNewsById = (state, id) => state.byId[id];
const getListByDate = (state, date) => state.listByDate[date];
const getPageOfList = (state, data) => getListByDate(state, date).page
/* ... */
const getNewsByDate = (state, date) => {
return getListByDate(state, data).items.map((id) => {
return getNewsById(state, id);
});
}
Run Code Online (Sandbox Code Playgroud)
我建议将所有新闻存储在一个位置(news在您的减速器中),并使用选择器来计算派生数据。
为了实现这一点,您需要将当前日期(我想它是您应用程序中的某种过滤器)存储在 Redux 存储中,以便可以在您的选择器中使用。
所以你的减速器将如下所示:
{
news: [], // you can keep all the news here
date: '15-09-2017', // selected date
page: 1, // current page
pagination: {
'15-09-2017': { ... }, // pagination info by date.
// You will need this only if you use the classic pager (with page numbers in UI)
// it's not needed in case of infinite scroll
}
}
Run Code Online (Sandbox Code Playgroud)
和选择器:
import { createSelector } from 'reselect';
// select all news
const newsSelector = () => (state) => state.get('news');
// select date
const dateSelector = () => (state) => state.get('date');
// select page
const pageSelector = () => (state) => state.get('page');
// select news by date
const newsByDateSelector = () => createSelector(
newsSelector(),
dateSelector(),
(news, date, page) => news.filter((newsItem) => newsItem.get('date') === date)
);
const pageSize = 10;
const newsByDatePagedSelector = () => createSelector(
newsByDateSelector(),
pageSelector(),
(news, page) => news.slice(pageSize * (page - 1), pageSize * page)
);
Run Code Online (Sandbox Code Playgroud)
然后你可以使用newsByDatePagedSelector选择器来获取容器中所需的新闻:
import React from 'react';
import { connect } from 'react-redux';
import { createStructuredSelector } from 'reselect';
export class NewsContainer extends React.PureComponent {
componentDidMount() {
// news by selected date are not loaded yet
if (!this.props.news) {
this.loadNews();
}
}
componentWillReceiveProps(nextProps) {
// user navigated to the next page
if (this.props.news && !nextProps.news) {
this.loadNews();
}
}
loadNews() {
// fetch next 10 news from server
}
render() {
return (
<div>
this.props.news.map((newsItem) => ...)
</div>
);
}
}
const mapStateToProps = createStructuredSelector({
news: newsByDatePagedSelector(),
});
export default connect(mapStateToProps)(NewsContainer);
Run Code Online (Sandbox Code Playgroud)
当用户在某个日期到达最后一条新闻时,您可以像往常一样使用过滤器从 API 请求接下来的 10 条新闻?date=15-09-2017,并将它们放入您的商店。Redux 和 reselect 会将它们作为NewsContainerprop newsByDate。
| 归档时间: |
|
| 查看次数: |
677 次 |
| 最近记录: |