Yêu cầu thg 7 4, 2019 10:14 SA 453 0 4
  • 453 0 4
+3

Hỏi về cách làm hệ thống comment như viblo

Chia sẻ
  • 453 0 4

Chào mọi người,

Mình đang làm một trang mạng xã hội như một cách để luyện kĩ năng. Trong project này mình sử dụng Django cho phía Backend và Angular 7 cho phía Frontend. Hiện tại mình đang cần tìm cách để tạo ra mội hệ thống comment giống như viblo, có thể reply comment liên tục và hiển thị dưới dạng hình cây.

Mình có nghĩ ra ý tưởng là có thể tạo ra một bảng với 2 column là parent và content, ví dụ như bảng dưới đây:

id parent content
1 null First comment
2 1 Child of first comment

Tuy nhiên khi dùng cách này thì việc query khi lấy content rất chậm, vì cứ phải lặp đi lặp lại để tìm child của parent. Mình đã thử search trên mạng xem có thuật toán nào ứng dụng cho hệ thống comment này không tuy nhiên chưa đúng keyword nên chưa tìm được. Vì vậy mình post câu hỏi này mong được mọi người giúp đỡ và chỉ giúp mình thuật toán hoặc keywords để giải quyết vấn đề này.

Mọi người xem giúp mình với ạ. Mình cảm ơn!

Avatar Quý Đinh @quyctd
thg 7 4, 2019 5:28 CH

4 CÂU TRẢ LỜI


Đã trả lời thg 7 9, 2019 2:11 SA
Đã được chấp nhận
+8

Không biết bạn đang dùng DBMS nào nhỉ? Như bạn nói, mấu chốt của bạn là gặp vấn đề khi query comments ra bị chậm. Bạn có thể thử như sau:

  • Mỗi comment mình sẽ lưu id của bài viết được comment (mình gọi là commentable_id nha). Khi try vấn chỉ cần thêm ràng buộc where('commentable_id', postID) là lấy được tất cả các comments của một bài viết.
  • Nếu làm kiểu comment đa cấp, bạn có thể lưu thêm parent_id, sau khi truy vấn xong ở bước 1 lấy được tất cả comments, mình xử lý gộp chúng bằng code Python cũng được. Làm kiểu này nếu hệ thống có ít comment. Còn như facebook thì họ chỉ làm 2 cấp. Ở cấp thứ 2 họ chỉ select ra mấy cái mới nhất mà thôi.
  • Nếu bạn muốn tiện truy vấn trong khi làm comment đa cấp, có thể thêm một trường path, có format: child_path = parent_path + child_id VD: Comment 0003 reply cho comment 0002, comment 0002 thì lại reply cho comment 0001 tạo thành 3 cấp độ. Cái path tương ứng của các comment là:
    • 0001 => 0001
    • 0002 => 0001.0002
    • 0003 => 0001.0002.0003

Lúc này mình có thể query theo regex: comments.path ^= 0001 thì sẽ lấy được tất cả comments của 0001.

Làm nested comment như trang xem bài viết của Viblo cũng được nhưng chắc bạn nên cải tiến việc hiển thị comments theo một cách khác. Hiển thị như Viblo không phải là một cách hay, khi mà có quá nhiều cấp độ dẫn tới việc hiển thị theo dạng cây rất tệ về UI/UX. Giống như Callback Hell trong javascript vậy.

callback-hell.png

Chia sẻ
Avatar Quý Đinh @quyctd
thg 7 9, 2019 4:21 SA

Bài viết rất chi tiết, đúng cái mình cần, cảm ơn bác ạ 😄

thg 7 22, 2019 11:49 SA
thg 7 22, 2019 11:49 SA
Đã trả lời thg 7 5, 2019 1:22 SA
+2

Bạn cần lưu thêm path cho mỗi comment nữa Bạn tham khảo link này nhé: https://dba.stackexchange.com/questions/191160/list-parent-then-nested-child-items-in-a-single-table

Chia sẻ
Đã trả lời thg 7 5, 2019 4:10 SA
+2

nếu như viblo thì chả cần nested set đâu, cứ thêm cái trường parent, thêm trường path, path thì gen ra khi insert comment

Chia sẻ
Đã trả lời thg 7 9, 2019 3:28 SA
Chia sẻ
Viblo
Hãy đăng ký một tài khoản Viblo để nhận được nhiều bài viết thú vị hơn.
Đăng kí