Я пытаюсь создать блог в React. В моем основном компоненте ReactBlog я делаю вызов AJAX на сервер узлов, чтобы возвращать массив сообщений. Я хочу передать эти данные сообщения различным компонентам в качестве реквизита.Передача результатов AJAX в качестве реквизита для дочернего компонента
В частности, у меня есть компонент, называемый PostViewer, который будет отображать информацию о сообщении. Я хочу, чтобы он по умолчанию показывал сообщение, переданное от родителя через реквизит, и в противном случае показывал данные, которые устанавливаются с помощью государственного вызова.
В настоящее время соответствующие части моего кода выглядят так.
var ReactBlog = React.createClass({
getInitialState: function() {
return {
posts: []
};
},
componentDidMount: function() {
$.get(this.props.url, function(data) {
if (this.isMounted()) {
this.setState({
posts: data
});
}
}.bind(this));
},
render: function() {
var latestPost = this.state.posts[0];
return (
<div className="layout">
<div className="layout layout-sidebar">
<PostList posts={this.state.posts}/>
</div>
<div className="layout layout-content">
<PostViewer post={latestPost}/>
</div>
</div>
)
}
});
и нижестоящий компонент:
var PostViewer = React.createClass({
getInitialState: function() {
return {
post: this.props.post
}
},
render: function() {
/* handle check for initial load which doesn't include prop data yet */
if (this.state.post) {
return (
<div>
{this.state.post.title}
</div>
)
}
return (
<div/>
)
}
});
Вышеуказанных работы, если я поменять, если заявление и содержание в моем ребенке вынести на this.props * Тем не менее, это будет означать, что я не мог. t изменить содержимое позже через состояние, правильно?
TLDR: Я хочу установить пост по умолчанию для просмотра через реквизит в дочернем компоненте (результаты вызова AJAX), и я хочу, чтобы иметь возможность изменять, что сообщение просматривается, добавляя события onClick (другого компонент), который будет обновлять состояние.
Правильно ли это?
Текущая иерархия компонентов моего приложения являются:
React Blog
- Post List
- Post Snippet (click will callback on React Blog and update Post Viewer)
- Post Viewer (default post passed in via props)
Спасибо!
EDIT:
Так что я в конечном итоге делает была прикрепление реквизита в ReactBlog, используя значение, основанное на this.state. Это гарантировало, что он обновляется, когда я меняю состояние и правильно рисую дочерние компоненты. Однако для этого мне пришлось подключать callback-запросы onClick через все дочерние компоненты. Это верно? Похоже, он может стать ОЧЕНЬ беспорядочным. Вот мой полный примерный код:
var ReactBlog = React.createClass({
getInitialState: function() {
return {
posts: [],
};
},
componentDidMount: function() {
$.get(this.props.url, function(data) {
if (this.isMounted()) {
this.setState({
posts: data,
post: data[0]
});
}
}.bind(this));
},
focusPost: function(slug) {
$.get('/api/posts/' + slug, function(data) {
this.setState({
post: data
})
}.bind(this));
},
render: function() {
return (
<div className="layout">
<div className="layout layout-sidebar">
<PostList handleTitleClick={this.focusPost} posts={this.state.posts}/>
</div>
<div className="layout layout-content">
<PostViewer post={this.state.post}/>
</div>
</div>
)
}
});
var PostList = React.createClass({
handleTitleClick: function(slug) {
this.props.handleTitleClick(slug);
},
render: function() {
var posts = this.props.posts;
var postSnippets = posts.map(function(post, i) {
return <PostSnippet data={post} key={i} handleTitleClick={this.handleTitleClick}/>;
}, this);
return (
<div className="posts-list">
<ul>
{postSnippets}
</ul>
</div>
)
}
});
var PostSnippet = React.createClass({
handleTitleClick: function(slug) {
this.props.handleTitleClick(slug);
},
render: function() {
var post = this.props.data;
return (
<li>
<h1 onClick={this.handleTitleClick.bind(this, post.slug)}>{post.title}</h1>
</li>
)
}
});
var PostViewer = React.createClass({
getInitialState: function() {
return {
post: this.props.post
}
},
render: function() {
/* handle check for initial load which doesn't include prop data yet */
if (this.props.post) {
return (
<div>
{this.props.post.title}
</div>
)
}
return (
<div/>
)
}
});
Все еще надеемся получить некоторые отзывы/надеюсь, что это поможет!
Вы делаете все сразу после издания. Использование состояния в родительском компоненте для предоставления реквизита для детей - это путь. Ваша проблема заключалась в том, что «getInitialState» выполняется только один раз для каждого компонента (если он не размонтирован), поэтому, когда вы изменили родительское состояние, даже если дочерние реквизиты тоже изменились, его состояние не будет. – GonArrivi