如何在ImmutableJS中存储和更新深层嵌套结构

时间:2016-02-03 17:13:43

标签: javascript reactjs immutability redux immutable.js

我正在使用react + redux构建一个小博客,我无法弄清楚如何回复博客帖子下的评论。 我正在获得一篇博文的评论结构,看起来像这样。

"[
{"_id":"5676ed8b9104691f3b85b687",
"content":"Lorem",
"creator":"Admin",
"replies":[
  {
    "_id":"5676ede4b7a9044c3c1d9641",
    "content":"Ipsum",
    "creator":"Admin",
    "replies":[
      {
        "_id":"5676eec224ab8fe23c7ce4c6",
        "content":"Dolor",
        "creator":"Admin",
        "replies":[]
      },
      {
        "_id":"5676eeda1c0e3d093d1f90a0",
        "content":"Sit",
        "creator":"Admin",
        "replies":[]
      }
    ]
  },
  {
    "_id":"5676ee5b4b03bbac3c1f7544",
    "content":"Amet",
    "creator":"Admin",
    "replies":[]
  },
  {
    "_id":"5676ee91c43c05c63c319ace",
    "content":"Sup",
    "creator":"Admin",
    "replies":[]
  }
]},
{...}
]

如何将它存储在ImmutableJS状态,以便我可以根据_id轻松添加对评论的回复?此外,注释必须是可迭代的,因为我之后将它们渲染到注释树中,但我认为只要使用ImmutableJS数据结构,这应该是一个问题。基本上我不知道如何在我的reducer中实现这个功能。

[REPLY_COMMENT]: (state, { payload }) => {
  const { _id, comment } = payload
  let newState = ???
  return newState
}

修改

这是jsbin显示我想要实现的目标。我只想回复所有

的评论

1 个答案:

答案 0 :(得分:0)

你必须稍微打破这一点。

首先让我们将评论添加到Immutable.Map

state = state.update('coolPostId', post => Immutable.fromJS(comments));

const replyToPostComment = {
  _id: '1234',
  content: 'Hello',
  creator: 'RandomUser',
  replies: []
};

您现在Immutable.List下有coolPostId,因此您希望update列出push新评论:

state = state.update('coolPostId', comment => comment.push(Immutable.fromJS(replyToPostComment)));

那将通过你的第一次测试:

const expected = state.get('coolPostId').last();
expect(expected.toJS()).to.deep.equal(replyToPostComment);

第二部分同样简单,但您需要映射覆盖您的评论并检查_id是否与您的元数据匹配。

这是您的设置:

const replyComment = {
  _id: '5678',
  content: 'Wellcome',
  creator: 'RandomUser2',
  replies: []
};

const reply = {
  postId: 'coolPostId',
  commentId: '1234',
  comment: replyComment
};

下一行取决于将执行_id检查的功能

state = state.get(reply.postId)
  .map(comment => addReply(comment)(reply));

最后一点是addReply谓词:

const addReply = c => cr => c.get('_id') === cr.commentId ? c
  .update('replies', replies => replies.push(Immutable.fromJS(cr.comment)) ) : c;

以下是完整的jsbin供审核

相关问题