- android - 多次调用 OnPrimaryClipChangedListener
- android - 无法更新 RecyclerView 中的 TextView 字段
- android.database.CursorIndexOutOfBoundsException : Index 0 requested, 光标大小为 0
- android - 使用 AppCompat 时,我们是否需要明确指定其 UI 组件(Spinner、EditText)颜色
我正在使用 MERN 堆栈,但似乎无法弄清楚为什么会发生这种情况。我有一个显示得很好的帖子列表。当我单击帖子时,我在控制台内收到 Cannot read property 'email' undefined
。但是,如果我点击刷新,一切都会正常工作,并且该帖子会显示所有工作问题。
我能够查明我的 renderComments()
函数的错误。这就是所有内容都显示为未定义的地方。
编辑:我想我发现发生了什么,但我不确定为什么会发生。在渲染发生之前,在 array.map 函数中创建的注释只是注释 ID。仅当组件呈现时,注释才是具有其所有属性的实际完整对象。我将发布后端来展示我如何获取帖子上的评论以提供帮助。
要求在 array.map 函数之前显示 post 的 console.log。由于这确实指出了我在编辑中所说的内容,因此我将继续并在下面显示以提供帮助。
发布带有评论的 Controller :
exports.getOnePost = function(req, res, next) {
Posts.findById(req.params.id).populate("comments").exec(function(err, foundPost) {
if(err) {
return next(err);
} else {
res.json(foundPost);
}
});
}
发帖和评论模型:
var mongoose = require("mongoose");
const Schema = mongoose.Schema;
var postsSchema = new Schema({
title: String,
createdAt: {type: Date, default: Date.now},
content: String,
author: {
id: {
type: mongoose.Schema.Types.ObjectId,
ref: "user"
},
email: String
},
comments: [
{
type: mongoose.Schema.Types.ObjectId,
ref: "comments"
}
]
});
var Posts = mongoose.model("posts", postsSchema);
module.exports = Posts;
<小时/>
var mongoose = require("mongoose");
const Schema = mongoose.Schema;
var commentSchema = new Schema({
text: String,
createdAt: {type: Date, default: Date.now },
author: {
id: {
type: mongoose.Schema.Types.ObjectId,
ref: "User"
},
email: String
}
});
module.exports = mongoose.model("comments", commentSchema);
Post_show页面:
import React, { Component } from 'react';
import { connect } from 'react-redux';
import { Link } from 'react-router-dom';
import { bindActionCreators } from 'redux';
import * as actions from '../../actions/posts_actions';
import * as actionsIndex from '../../actions/index';
import * as actionsComments from '../../actions/comments_actions';
class ShowPosts extends Component {
constructor(props) {
super(props);
this.onDeleteClick = this.onDeleteClick.bind(this);
this.deleteComment = this.deleteComment.bind(this);
}
componentDidMount() {
const {id} = this.props.match.params;
this.props.getOnePost(id);
if(this.props.auth) {
this.props.getUser();
}
}
renderButtons() {
const { post } = this.props;
if(!this.props.user) {
return ( <div></div> );
}
if(this.props.auth) {
if(this.props.user._id === post.author.id) {
return (
<div>
<button
onClick={this.onDeleteClick}
className="btn btn-danger"
>
Delete
</button>
<Link
to={`/posts/${post._id}/edit`}
className="btn btn-success"
>
Edit
</Link>
</div>
)
}
} else {
return (
<div></div>
)
}
}
renderCommentsButtons(comment) {
const { post, user, auth } = this.props;
if(!user) {
return (<div></div>);
}
if(auth) {
if(user._id === comment.author.id) {
return (
<div>
<button
onClick={() => this.deleteComment(comment)}
className="btn btn-xs btn-danger">
Delete
</button>
<Link
to={`/posts/${post._id}/comments/${comment._id}/edit`}
className="btn btn-xs btn-warning">
Edit
</Link>
</div>
)
}
}
}
renderComments() {
const { post } = this.props;
return post.comments.map((comment) => {
return (
<li className="list-group-item" key={comment._id}>
<div>
{comment.text} : {comment.author.email}
</div>
{this.renderCommentsButtons(comment)}
</li>
);
});
}
deleteComment(comment) {
const {id} = this.props.match.params;
const {user, post, auth} = this.props;
if(!user) {
return (<div></div>);
}
if(auth) {
if(user._id === comment.author.id){
console.log(comment._id, '-', post._id);
// this.props.deleteComments(id, comment._id, () => {
// this.props.history.push(`/posts/${post._id}`);
// });
}
}
}
onDeleteClick() {
const {id} = this.props.match.params;
if(!this.props.user) {
return (<div></div>);
}
if(this.props.auth) {
if(this.props.user._id === this.props.post.author.id) {
this.props.deletePost(id, () => {
this.props.history.push("/posts");
});
}
}
}
render() {
const { post } = this.props;
if (!post) {
return <div> Loading...No Post</div>;
}
return (
<div>
<Link className="btn btn-primary" to="/posts">Back To Post</Link>
<h3>{post.title}</h3>
<p>{post.content}</p>
<p>created by: {post.author.email}</p>
<ul className="list-group">
{this.renderComments()}
</ul>
{this.renderButtons()}
<Link
className="btn btn-warning"
to={`/posts/${post._id}/comments/new`}>
Comment
</Link>
</div>
);
}
}
function mapStateToProps({ posts, auth, user }, ownProps) {
return {
post: posts[ownProps.match.params.id],
user: user,
auth: auth.authenticated
};
}
function mapDispatchToProps(dispatch) {
return bindActionCreators({...actions, ...actionsIndex, ...actionsComments}, dispatch);
}
export default connect(mapStateToProps, mapDispatchToProps)(ShowPosts);
发布
import React , { Component } from 'react';
import * as actions from '../../actions/posts_actions';
import {connect} from 'react-redux';
import {Link} from 'react-router-dom';
import _ from 'lodash';
class Posts extends Component {
componentDidMount() {
this.props.getAllPosts();
}
renderPosts() {
return _.map(this.props.posts, post => {
return (
<Link to={`/posts/${post._id}`} key={post._id}>
<li className="list-group-item">
{post.title}
</li>
</Link>
)
});
}
render() {
return (
<div>
<div className="text-xs-right">
<Link className="btn btn-primary" to="/posts/new">
Add a Post
</Link>
</div>
<h3>Posts</h3>
<ul className="list-group">
{this.renderPosts()}
</ul>
</div>
);
}
}
function mapStateToProps(state) {
return {
posts: state.posts
};
}
export default connect(mapStateToProps, actions)(Posts);
最佳答案
这是一个后端问题。正如编辑中所述,首先呈现的帖子只有评论的评论 ID,而不是完整的评论对象。我相信发生的事情是,最初的帖子来自 posts[ownProps.match.params.id]
,它所做的就是从客户端的帖子中获取单个帖子。
如果您查看后端,我会将评论存储为 objectID,然后在调用 getOnePost
时填充它们。
我需要做的是在所有帖子被调用之前填充评论,这样评论就已经填充了,而不仅仅是 ID。因此,为了解决这个问题,我执行了以下操作(我还将发布所需的所有其他代码)。
导出到后端路由器的函数:
旧:
exports.getAllPosts = function(req, res, next) {
Posts.find({}, function(err, posts) {
if(err) {
return next(err);
} else {
res.json(posts);
}
});
}
新:
exports.getAllPosts = function(req, res, next) {
Posts.find({}).populate("comments").exec(function(err, posts) {
if(err) {
return next(err);
} else {
res.json(posts);
}
});
}
这是帖子模型:
var mongoose = require("mongoose");
const Schema = mongoose.Schema;
var postsSchema = new Schema({
title: String,
createdAt: {type: Date, default: Date.now},
content: String,
author: {
id: {
type: mongoose.Schema.Types.ObjectId,
ref: "user"
},
email: String
},
comments: [
{
type: mongoose.Schema.Types.ObjectId,
ref: "comments"
}
]
});
var Posts = mongoose.model("posts", postsSchema);
module.exports = Posts;
这两个模型已在上面发布。
关于javascript - 收到错误bundle.js :39454 Uncaught TypeError: Cannot read property 'email' of undefined using MERN stack,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/44909013/
我是一名优秀的程序员,十分优秀!