网易云音乐的评论回帖是怎么存的?

网易云音乐" title="网易云音乐">网易云音乐的评论回帖是怎么存的?关系性数据库还是给非关系性数据库,又或者是两者同时使用?一首歌的回帖就30多万了,感觉用关系性数据库的话,效率很低?求大神解答

图片描述

回答:

效率低? MySQL 毕竟是个久经考验的数据库,它没你想得那么脆弱。

再一个,讨论问题要考虑场景:

  1. 是不是所有歌曲都有几十万的评论量?
  2. 网易云音乐歌曲的 评论 看起来只有 赞数 这个字段会在记录生成后被修改,这意味着大多数时间它都是只读的,因此对于热门评论可以做热缓放在前面抗压。
  3. 并不是一次性拉取几十万条评论到客户端,如前面所说,热评可以放热缓分压,客户端方面即使拉取不那么热的评论,也可以一次十条/百条去拉。
  4. 其实这种大量只读的情况下,热缓做得好,命中率高的话,数据库方面本身就不会承受特别多的压力。

以上仅是个人想法,有错误还请指正 :)

回答:

仅从MongoDB的角度说明这种东西可以怎么存。至于别人到底是怎么存,我们是不知道的。

关系模型存法

不多介绍,可以按照范式设计成跟关系数据库一样的表结构来存储,大概是:

{

_id: ObjectId(...),

comment: "...",

time: ISODate(...),

user: "...",

musicId: "...",

...

}

如果用惯关系数据库的用户,这样的做法简单自然。在现在讨论的场景下,这样没有太大的问题,在数据量大时可以使用分片来达到水平扩展以应对数据量的增长。
不过仍有可以改进的地方。这要从MongoDB的模型设计来讲起。简单地说,MongoDB是实用主义,怎么方便怎么来,怎么快怎么来,完全不应该受范式的约束。但这也意味着你的模型要从应用的需求出发。仅从上面截图的信息,可能有2个不同的需求:

  1. 评论
  2. 点赞

考虑到评论和点赞都有可能上万甚至上十万百万,它们以单独的集合来存放会比较合适。但是为了读取和存储效率,我会考虑把多条评论压缩到一起,这种方式通常称为分桶(bucket)。

非关系模型存法

{

_id: ObjectId(...),

musicId: "...",

// 根据需要可能将音乐本身的一些数据冗余进来

musicName: "...",

comments: [

{content: "...", time: ISODate(...), user: "..."},

{content: "...", time: ISODate(...), user: "..."},

{content: "...", time: ISODate(...), user: "..."},

...

],

count: 10, // 该桶内已有10条comments

}

comments的数据量我会考虑一页会展示多少评论(比如30条),那么在添加评论时可以有:

db.comments.updateOne({

musicId: "...",

count: {$lt: 30}

}, {

$push: {

comments: {content: "...", time: ISODate(...), user: "..."}

},

$inc: { count: 1 }

}, {

upsert: true

});

// 优化查询速度会使用到索引:

db.comments.createIndex({

musicId: 1,

count: 1

});

在查询时总是只需要最多取最新的2条记录就可以查到第一页:

db.comments.find({

musicId: "..."

}).sort({_id: -1}).limit(2)

// 这个查询需要索引

db.comments.createIndex({

musicId: 1,

_id: -1

});

注意_id的高4位是时间,所以是可以排序的,其顺序就是时间顺序。
点赞的问题可以通过类似的方式实现,就留给你自己思考了。

以上是 网易云音乐的评论回帖是怎么存的? 的全部内容, 来源链接: utcz.com/p/196666.html

回到顶部