Thiết kế hệ thống quản lý danh mục sản phẩm trong hệ thống Ecommerce.

  • 15665
Lê Minh Nghĩa 2017-11-16 18:37:13

Vừa rồi anh em Tiki có design lại phần quản lý sản phẩm. Có một số phân tích và practise tốt share lại. Bài gốc được đăng tải Blog Engineer của Tiki.

Quản lý danh mục sản phẩm là một trong các thành phần quan trọng nhất của một hệ thống E-Commerce. Cùng với quản lý đơn hàng và giao vận tạo thành ba trụ cột chính của một hệ thống E-Commerce. Chính vì vậy xây dựng hệ thống quản lý danh mục sản phẩm có vai trò quan trọng trong kiến trúc tổng thể. Nó phải đáp ứng các mục tiêu sau:

  • Quản lý thuộc tính đa dạng của sản phẩm
  • Dễ dàng bảo trì, mở rộng về nghiệp vụ và hệ thống
  • Có thể đáp ứng yêu cầu cao về hiệu năng
  • Giải quyết được các vấn đề tích hợp hệ thống.

1.Product Model.

Sản phẩm là đối tượng hiển thị các thông tin để người dùng thực hiện việc mua bán. Một sản phẩm có các thuộc tính đa dạng về số lượng, loại thuộc tính, kiểu dữ liệu. Mỗi thuộc tính có các yêu cầu khác nhau tính chất dữ liệu: độ dài, kiểu kí tự, các yêu cầu về nghiệp vụ… Do đó model product là một model không có cấu trúc cố định (schemaless structure).

Cách tiếp cận phổ biến để giải quyết vấn đề này là sử dụng model dạng EAV — Entity Attribute Value. Đây là model được Magento, Word Press sử dụng để lưu trữ các cấu trúc đa dạng không định trước. Đặc điểm của cấu trúc EAV là tách phần lưu trữ giá trị thuộc tính (attribute value) khỏi phần cấu trúc các attribute của model. Nhờ đó có thể định nghĩa đa dạng các loại cấu trúc attribute khác nhau của product.

 

Một attribute set là một tập hợp các thuộc tính. Mỗi thuộc tính phân biệt nhau bởi mã thuộc tính, loại kiểu dữ liệu. Một thuộc tính có thể thuộc nhiều bộ thuộc tính khác nhau. Một product thuộc một bộ thuộc tính. Các giá trị thuộc tính của product tương ứng với các thuộc tính, đặc trưng bởi kiểu dữ liệu và mã thuộc tính. Giá trị thuộc tính có kiểu dữ liệu được định nghĩa bởi thuộc tính. Bằng cách tổ chức như vậy, hệ thống có thể thêm các bộ thuộc tính mới dễ dàng, cũng như bổ sung các thuộc tính vào các bộ thuộc tính đã có.

Ngoài ra một product còn có nhiều hỉnh ảnh, thuộc nhiều category và có nhiều biến thể khác nhau (có quan hệ liên hệ với nhiều product khác, vd điện thoại iphone còn có các sản phẩm biến thể theo màu sắc; hay một chiếc váy có nhiều size khác nhau, tức product váy có mối quan hệ với các product váy có màu sắc khác nhau, phân biệt bởi thuộc tính kích cỡ).

2.Thiết kế tầng nghiệp vụ.

Các nghiệp vụ sẽ được phát triển xoay quanh model đã được xây dựng. Đây là layer phức tạp nhất, chiếm phần lớn khối lượng công việc. Nghiệp vụ quản lý sản phẩm tập trung vào việc thay đổi các thuộc tính đa dạng của sản phẩm. Các mục tiêu thiết kế:

  • Đảm bảo nguyên lý Don’t Repeat Yourself tốt nhất. Các nghiệp vụ được phân tách rõ ràng, cô đọng và tập trung cao.
  • Có thể mở rộng, sửa đổi các thành phần độc lập.
  • Linh hoạt trong việc phát triển.
  • Có khả năng dễ dàng test và bảo trì

Các mục tiêu đó sẽ ảnh hưởng tới các cách thiết kế mô hình ứng dụng khác nhau. Phần dưới đây sẽ phân tích từng mô hình thiết kế phần mềm để đưa ra sự lựa chọn phù hợp nhất.

2.1. Mô hình MVC.

Mô hình MVC là mô hình phổ biến trong việc lựa chọn để xây dựng ứng dụng. Đó là mô hình đơn giản, dễ tiếp cận và nhanh chóng đưa ra các tính năng. Theo mô hình MVC, thì phần quản lý catalog sẽ có kiến trúc như sau:

 

Với mô hình mvc, product model sẽ chứa tất cả các định nghĩa thuộc tính của product, truy xuất database, thực thi các nghiệp vụ. Thông thường mô hình MVC sẽ sử dụng pattern Active Record để mapping với database. Đây là cách làm đơn giản, nhưng có các hạn chế sau:

  • Model product trở nên quá nặng khi chứa quá nhiều các logic từ định nghĩa thuộc tính, truy xuất dữ liệu, thực thi nghiệp vụ…
  • Do không phân tách được các tầng nghiệp vụ và dữ liệu nên khó thực hiện unit test các thành phần riêng biệt.
  • Việc thay đổi logic truy xuất dữ liệu và logic nghiệp vụ khó khăn. Do các thành phần bị phụ thuộc vào nhau.
  • Tính đóng gói của nghiệp vụ không đảm bảo. Các nghiệp vụ sẽ chỉ được cài đặt theo mô hình CRUD. Vì vậy càng về sau sự trùng lặp các logic càng cao.

Do các hạn chế đó nên đây không phải mô hình phù hợp với các ứng dụng logic phức tạp như ecommerce. Nó sẽ dẫn tới chi phí maintain về sau cao.

2.2. Mô hình ba lớp.

Hướng tiếp cận tiếp theo là phân tích và thiết kế theo phương pháp Domain Driven Design. Đặc trưng của mô hình này là:

  • Phân tách tầng nghiệp vụ khỏi tầng ứng dụng và tầng truy xuất cơ sở dữ liệu. Gọi là Domain Layer. Đây là nơi trung tâm chứa tất cả các logic nghiệp vụ.
  • Trong tầng nghiệp vụ, tập trung vào design model sao cho model phản ánh đầy đủ nhất tính chất nhất quán của nghiệp vụ. Chia tầng nghiệp vụ thành hai thành phần riêng biệt: Domain Model và Domain Service. Domain service có vai trò cung cấp các nghiệp vụ ra bên ngoài xoay quanh các domain model của hệ thống.
  • Thiết kế riêng tầng infrastructure chứa các logic về truy xuất dữ liệu, thao tác với database, messeage queue.
 

Với việc tổ chức như này các tầng ứng dụng, nghiệp vụ và data access sẽ chia tách riêng biệt, và chỉ tương tác thông qua interface. Các nghiệp vụ sẽ xoay quanh model product. Tầng data acccess sẽ truy xuất hoặc lưu trữ các object products.

Nhưng việc áp dụng mô hình ba lớp xoay quanh model product cũng dẫn tới một khó khăn khác là việc model cho các nghiệp vụ đọc dữ liệu. Các nghiệp vụ này rất đa dạng và cách làm hiệu quả nhất là sử dụng các raw sql. Nhưng nếu các việc truy xuất bị thắt chắt vào các mô hình ORM sẽ ảnh hưởng tới hiệu năng, cũng như khó cho việc thay đổi các logic truy xuất dữ liệu. Đồng thời nó cũng ảnh hưởng tới tốc độ phát triển, khi việc cài đặt các nghiệp vụ query đa dạng phục vụ client bị cản trở và phụ thuộc vào việc thiết kế model và tầng Repository.

2.3. Mô hình CQRS.

Mô hình CQRS (Command Query Responsibility Segregation) là sử mở rộng của mô hình trong ba lớp trong DDD. Đặc trưng quan trọng của CQRS là việc tách hai phần logic đọc và ghi dữ liệu ra hai phần riêng biệt:

  • Phần ghi dữ liệu: được thực hiện qua việc send các command tới các handler thông qua command bus. Comand hanlder đóng vai trò tương tự domain service sẽ tương tác với các model để thực hiện các nghiệp vụ thay đổi dữ liệu.
  • Phần đọc dữ liệu: được thiết kế riêng không lệ thuộc vào các model của phần ghi dữ liệu. Do đó có thể linh hoạt trong việc truy xuất database, cũng như sử dụng các data source khác nhau để tối ưu về tốc độ truy xuất.
 

Mô hình CQRS đã khắc phục các hạn chế đã nêu ở mục 2 bên trên. CQRS mang lại các lợi thế lớn:

  • Cho phép phát triển và tối ưu phần đọc dữ liệu riêng biệt với phần ghi dữ liệu.
  • Việc mô hình hoá các nghiệp vụ ghi dữ liệu dưới các command cho phép che đậy tốt các logic nghiệp vụ, giúp việc mở rộng dễ dàng hơn. Đồng thời các comand đó có thể dễ dàng chuyển đổi giữa xử lý đồng bộ và bất đồng bộ thông qua lớp abstract là command bus mà không thay đổi mô hình. Giúp cung cấp một mô hình nhất quán, xuyên suốt trong bộ kiến trúc.

Cả ba mô hình trên đều có ưu nhược điểm riêng:

  • Mô hình MVC đơn giản, nhưng hạn chế khi giải quyết nghiệp vụ phức tạp và testing, mở rộng
  • Mô hình ba lớp phù hợp cho việc xử lý nghiệp vụ phức tạp, nhưng có nhiều hạn chế khi tối ưu phần đọc ra.
  • Mô hình CQRS mở rộng từ mô hình ba lớp, giải quyết tốt việc chia tách đọc ghi, nhưng cũng đòi hỏi phải thiết kế phức tạp hơn.

Đối với các hệ thống ecommerce lớn thì mô hình CQRS là mô hình phù hợp nhất. Vì nó giúp giải quyết cả hai đòi hỏi lớn là xử lý nghiệp vụ phức tạp và phải đáp ứng hiệu năng cao. Phân tiếp theo sẽ phân tích sâu hơn về mặt hệ thống và một biến thở mở rộng của CQRS là CQRS — ES (Command Query Responsibility Segregation — Event Sourcing).

3. Thiết kế về hệ thống.

Một trong các đòi hỏi lớn của việc quản lý danh mục sản phẩm là phải thiết kế để đáp ứng các nhu cầu về hiệu năng và tích hợp với các hệ thống khác. Để đáp ứng các yêu cầu tốt, thì phải được thiết kế từ tổng thể ngay từ đầu. Có vậy mới tạo ra sự phát triển liền mạch, nhất quán giúp đảm bảo tính ổn định, cũng như tiến độ làm việc.

3.1. Mô hình CQRS — ES.

Mô hình Event Sourcing — ES, là mô hình thiết kế mà trạng thái của object sẽ được lưu trữ dưới dạng chuỗi các sự kiện thay đổi. Nó khác với mô hình thiết kế thông thường, khi mà chỉ lưu trữ trạng thái cuối cùng của object.

 

Khi object bị thay đổi, sẽ tương ứng với một versioned event lưu trữ dữ liệu thay đổi của object. Các event sẽ được lưu trữ dạng appending only vào một cấu trúc table gọi là event store. Việc lưu trữ các event thay đổi này giúp mang lại các lợi ích:

  • Lưu trữ được lịch sử thay đổi của các đối tượng.
  • Nếu các event được gửi tới các hệ thống khác, các hệ thống đó có thể sinh ra trạng thái cuối cùng chính xác của đốc tượng gốc. Do đó dễ dàng tích hợp với các hệ thống khác.

Dựa trên các event được published đi có thể xây dựng phần lưu trữ riêng cho read side, để tối ưu cho tốc độ truy xuất dữ liệu.

3.2. Event Bus — Kafka — MySql Binlog.

Các versioned event của đối tượng nếu được gửi đi sẽ giúp hệ thống dễ dàng tích hợp với nhiều hệ thống khác. Event Bus là tên gọi logic của một đường truyền chứa tất cả các versioned event dưới dạng stream. Các consumer chỉ việc subscribe event bus là có thể nhận được các event để xử lý.

Các event được lưu trữ trong mysql database. Tất cả các thay đổi trong database đều được MySql lưu vào một log file, gọi là binlog. Bằng việc extra binlog của mysql, thì hệ thống có thể bắt được mọi event phát sinh để gửi đi.

Kafka là một message broker theo mô hình log based, cho phép lưu trữ và gửi đi các event đúng với thứ tự gửi vào. Vì vậy nó là lựa chọn tốt nhất để làm tầng lưu trữ cho event bus.

 

3.3. Kiến trúc tổng thể.

Đên đây bức tranh của hệ thống đã trở nên rõ ràng. Từng mảnh ghép từ model, nghiệp vụ tới tích hợp đã đầy đủ. Có thể tóm tắt lại: hệ thống sẽ xây dựng nghiệp vụ quanh model product; cấu trúc theo mô hình CQRS — ES; sử dụng MySql Binlog; Kafka để publish các event thay đổi một cách ổn định; dựa trên event bus sẽ xây dựng các cấu trúc lữu trữ có tốc độ truy xuất cao như Elastic, MongoDb, cũng như tích hợp với các hệ thống khác.

 

4. Kết luận.

Thiết kế hệ thống quản lý danh mục sản phẩm trong ecommerce đòi hỏi phải đạt được cùng lúc nhiều mục tiêu, với một tầm nhìn xuyên suốt và nhất quán. Từ mức ứng dụng cho tới mức hệ thống đều phải có sự gắn kết liền mạch. Tất cả hướng tới hai mục tiêu quan trọng phải đạt được:

  • Xử lý được các nghiệp vụ phức tạp
  • Đảm bộ hiệu năng và độ ổn định của hệ thống.

Phương pháp phân tích thiết kế Domain Driven Desing, mô hình CQRS — ES, cơ chế replicate ổn định của MySql, sự đảm bảo thứ tự message của Kafka, cũng như các database tối ưu cho read như Elastic, Mongo… là các nhân tố chính đảm bảo chất lượng của hệ thống.

0 Bình luận

Cùng một tác giả