I'm having an issue with my vote score on comments. I can see in Redux Devtool that the value has changed but I need to force reload to update the UI.
Not sure why this is. I get my comments as an object with a key of the parent elements id as a key and an array inside of it.
This is then converted inside of mapStateToProps.
Heres an image showing different stages of comments.
Anyone have any idea why this is.
Cheers, Petter
export function pushVoteComment(option, postId) {
const request = API.commentPostVote(option, postId)
return dispatch => {
request.then(({ data }) => {
dispatch({ type: COMMENTS_POST_VOTE, payload: data, meta: postId })
})
}
}
const comments = (state = {}, action) => {
switch (action.type) {
case COMMENTS_GET_COMMENTS:
return {
...state,
[action.meta]: action.payload,
}
case COMMENTS_POST_VOTE:
console.log('An vote request was sent returning ', action.payload)
return { ...state, [action.payload.id]: action.payload }
default:
return state
}
}
renderComments() {
const { comments, post } = this.props
console.log('This post has these comments: ', comments)
return _.map(comments, comment => {
return (
<div key={comment.id} className="post-container">
{post ? (
<PostComment
key={comment.id}
postId={comment.id}
body={comment.body}
author={comment.author}
voteScore={comment.voteScore}
timestamp={comment.timestamp}
/>
) : (
''
)}
</div>
)
})
}
const mapStateToProps = (state, ownProps) => {
const { posts, comments } = state
return {
comments: comments[ownProps.match.params.postId],
post: posts.filter(
item => item.id === ownProps.match.params.postId && item.deleted !== true
)[0],
}
}
<i
className="fa fa-chevron-up"
aria-hidden="true"
onClick={() => pushVoteComment('upVote', postId)}
/>
<span className="vote-amount">{voteScore}</span>
<i
className="fa fa-chevron-down"
onClick={() => pushVoteComment('downVote', postId)}
/>
export default connect(null, { pushVoteComment })(PostComment)
The reason it is built with a {parentId: [{comment1}, {comment2}]}
Is that I use it when showing all posts to see a number of comments.
return ({comments.length})
const mapStateToProps = (state, ownProps) => {
return {
comments: state.comments[ownProps.postId]
? state.comments[ownProps.postId]
: [],
}
}
Looks like this when I press the votebutton for the first time:
Then when I press again I get this:
The issue here is that it's changing the state, not thinking about the fact that I have my comment stored as
{
[postId]: [array of comments]
}
So in order to resolve it, I ended up rewriting my reducer doing it like this.
case COMMENTS_POST_VOTE:
const { parentId } = action.payload // get commentId
const commentList = [...state[parentId]] // get array of comments, but copy it
const commentIndex = commentList.findIndex(el => (el.id === payload.id)) // get index of comment
commentList[commentIndex] = action.payload // update the commentList
const updatedPost = {...state, [parentId]: commentList} // return new state
return updatedPost
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.