小程序商品留言楼中楼的实现

一个商品下是否可以有多个独立的顶级留言,每个顶级留言下面都有自己的楼中楼?

答案:是的!完全可以! 每个商品下可以有多个独立的顶级留言,每个顶级留言都是一个独立的楼中楼树。

一、数据库示例(多个顶级留言)

-- 商品1下面有3个独立的顶级留言,每个都有自己的楼中楼对话链
INSERT INTO product_comments (id, product_id, user_id, user_name, parent_id, content) VALUES
-- ===== 第1个顶级留言(关于拍照)=====
(1, 1, 1, '用户A', NULL, '这个手机拍照怎么样?'),      -- 顶级留言1
(2, 1, 2, '用户B', 1, '拍照很清晰!'),                 -- 回复留言1
(3, 1, 3, '用户C', 2, '夜间拍照呢?'),                 -- 回复留言2
(4, 1, 4, '用户D', 3, '夜间也不错'),                  -- 回复留言3

-- ===== 第2个顶级留言(关于电池)=====
(5, 1, 5, '用户E', NULL, '电池续航多久?'),            -- 顶级留言2
(6, 1, 6, '用户F', 5, '能用一整天'),                  -- 回复留言5
(7, 1, 7, '用户G', 6, '玩游戏呢?'),                  -- 回复留言6
(8, 1, 8, '用户H', 7, '玩游戏也够用'),                -- 回复留言7

-- ===== 第3个顶级留言(关于价格)=====
(9, 1, 9, '用户I', NULL, '价格太贵了吧?'),            -- 顶级留言3
(10, 1, 10, '用户J', 9, '但性能好呀'),                -- 回复留言9
(11, 1, 11, '用户K', 10, '确实值这个价');              -- 回复留言10

二、构建的树形结构

// 查询商品1的所有留言后,会构建出这样的结构:
const commentTree = [
  {
    id: 1,
    content: '这个手机拍照怎么样?',
    parent_id: null,  // 顶级留言
    replies: [        // 第1个楼中楼对话链
      {
        id: 2,
        content: '拍照很清晰!',
        parent_id: 1,
        replies: [
          {
            id: 3,
            content: '夜间拍照呢?',
            parent_id: 2,
            replies: [
              {
                id: 4,
                content: '夜间也不错',
                parent_id: 3,
                replies: []
              }
            ]
          }
        ]
      }
    ]
  },
  {
    id: 5,
    content: '电池续航多久?',
    parent_id: null,  // 顶级留言
    replies: [        // 第2个楼中楼对话链
      {
        id: 6,
        content: '能用一整天',
        parent_id: 5,
        replies: [
          {
            id: 7,
            content: '玩游戏呢?',
            parent_id: 6,
            replies: [
              {
                id: 8,
                content: '玩游戏也够用',
                parent_id: 7,
                replies: []
              }
            ]
          }
        ]
      }
    ]
  },
  {
    id: 9,
    content: '价格太贵了吧?',
    parent_id: null,  // 顶级留言
    replies: [        // 第3个楼中楼对话链
      {
        id: 10,
        content: '但性能好呀',
        parent_id: 9,
        replies: [
          {
            id: 11,
            content: '确实值这个价',
            parent_id: 10,
            replies: []
          }
        ]
      }
    ]
  }
];

三、前端显示效果

=== 商品:iPhone 15 Pro ===

【楼层1】用户A: 这个手机拍照怎么样?
├── 用户B: 拍照很清晰!
│   └── 用户C: 夜间拍照呢?
│       └── 用户D: 夜间也不错

【楼层2】用户E: 电池续航多久?
├── 用户F: 能用一整天
│   └── 用户G: 玩游戏呢?
│       └── 用户H: 玩游戏也够用

【楼层3】用户I: 价格太贵了吧?
├── 用户J: 但性能好呀
│   └── 用户K: 确实值这个价

【楼层4】用户L: 系统流畅吗?
└── 用户M: 非常流畅
    └── 用户N: 打游戏卡吗?
        └── 用户O: 完全不卡

四、关键查询代码

// 获取商品的所有留言(包含多个顶级留言)
static async getProductCommentTree(productId, page = 1, limit = 20) {
  // 1. 分页查询顶级留言
  const topLevelSql = `
    SELECT * FROM product_comments 
    WHERE product_id = ? 
      AND parent_id IS NULL  -- 只查顶级留言
      AND status = 1
    ORDER BY created_at DESC
    LIMIT ? OFFSET ?
  `;

  const [topLevelComments] = await db.execute(topLevelSql, [productId, limit, offset]);

  // 2. 获取所有相关留言
  const allCommentsSql = `
    SELECT * FROM product_comments 
    WHERE product_id = ? AND status = 1
    ORDER BY created_at ASC
  `;
  const [allComments] = await db.execute(allCommentsSql, [productId]);

  // 3. 为每个顶级留言构建自己的楼中楼树
  const commentTree = this.buildCommentTree(topLevelComments, allComments);

  return commentTree;
}

五、创建新顶级留言的示例

用户想发起一个新的话题:

// API调用:创建新的顶级留言
POST /api/comments
{
  "product_id": 1,
  "user_id": 12,
  "user_name": "用户L",
  "parent_id": null,  // 关键:parent_id为null表示是顶级留言
  "content": "系统流畅吗?"
}

// 数据库插入:
// id: 12, product_id: 1, user_id: 12, parent_id: NULL, content: "系统流畅吗?"

然后其他人可以回复这个新话题:

// 回复这个新话题
POST /api/comments
{
  "product_id": 1,
  "user_id": 13,
  "user_name": "用户M",
  "parent_id": 12,  // 回复id=12的留言
  "content": "非常流畅"
}

// 再回复这个回复
POST /api/comments
{
  "product_id": 1,
  "user_id": 14,
  "user_name": "用户N",
  "parent_id": 13,  // 回复id=13的留言
  "content": "打游戏卡吗?"
}

六、总结

一个商品下的留言结构就像这样:

商品1
├── 顶级留言1(楼中楼树1)
│   ├── 回复1-1
│   │   └── 回复1-1-1
│   │       └── 回复1-1-1-1
│   └── 回复1-2
│       └── 回复1-2-1
├── 顶级留言2(楼中楼树2)
│   ├── 回复2-1
│   │   └── 回复2-1-1
│   └── 回复2-2
└── 顶级留言3(楼中楼树3)
    ├── 回复3-1
    │   └── 回复3-1-1
    └── 回复3-2
        └── 回复3-2-1
            └── 回复3-2-1-1

核心特点:

  1. 一个商品可以有多个顶级留言(每个都是独立的话题)
  2. 每个顶级留言下面可以有自己的楼中楼对话树
  3. 楼中楼可以无限层级嵌套
  4. 每个顶级留言和它的所有回复构成一个独立的树

所以您完全可以实现:在一个商品页面下,显示多个独立的楼中楼对话,每个对话讨论不同的话题。这就是典型的论坛/商品留言板模式!

《 “小程序商品留言楼中楼的实现” 》 有 2 条评论

  1. rensheng

    parent id就是上一个留言的id。然后遍历每一个父节点null,把他对应的那个子的那些全都拉到一块,一层一层的树形结构返回前端然后渲染。

    1. hello world 的头像
      hello world

      666

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注