Giao diện
Database - Collection & Repository
1) Database - lớp trung tâm ORM/meta
Trong constructor:
| Bước | Mô tả |
|---|---|
| Validate dialect | Database.getDialect(...) - hỗ trợ postgres, mysql, sqlite, mariadb |
| Setup logger | Logger riêng cho DB queries |
| Chuẩn hóa timezone | Postgres/MySQL/SQLite behavior khác nhau |
| Khởi tạo Sequelize | Connection pool + query interface custom |
| Đăng ký built-in | Field types, interfaces, value parsers, operators |
| Gắn listener | afterDefineCollection → bind pending relation fields |
2) Đăng ký collection
collection(options)
extendCollection(collectionOptions)
- Nếu collection đã tồn tại: merge trực tiếp vào collection hiện tại.
- Nếu chưa tồn tại: lưu vào
delayCollectionExtend, sẽ apply sau khi collection được define.
Khi nào dùng extend?
Plugin thường dùng extendCollection để thêm field vào collection của plugin khác mà không cần sửa source gốc. Ví dụ: plugin audit thêm field lastAuditAt vào collection users.
import({ directory, from, extensions })
- Đọc module collection từ thư mục.
- Module kiểu
extend→ gọiextendCollection. - Module thường → gọi
collection(...)và setorigin.
3) Hooks và event model
Database.on(...) override để auto bind Sequelize hook:
- Khi event name match model hook type → DB sẽ
sequelize.addHookmột lần. - Plugin có thể nghe event qua
db.on(...)mà không cần gắn trực tiếp vào model Sequelize.
Model hooks vs DB events
Model hooks (beforeCreate, afterUpdate...) fire cho mọi collection. Nếu chỉ cần hook cho một collection cụ thể, dùng pattern db.on('users.afterCreate', handler) thay vì db.on('afterCreate', handler).
4) Sync, clean, reconnect
| Method | Hành vi |
|---|---|
sync(options) | MySQL: tắt FOREIGN_KEY_CHECKS trước sync, bật lại sau. Postgres: tạo schema nếu chưa có. |
clean({ drop: true }) | Postgres có schema: drop từng table. Còn lại: queryInterface.dropAll. |
auth() | Retry kết nối theo exponential backoff. |
prepare() | MySQL: kiểm tra lower_case_table_names. |
reconnect() | Recreate connection manager (không áp dụng sqlite memory). |
close() | Emit beforeClose → gọi custom hook afterClose nếu có. |
5) Filter parser (FilterParser)
FilterParser chuyển JSON filter sang Sequelize where + include.
Các điểm đáng chú ý:
prepareFilter()tự rewrite key...$existsvà...$notExistscho relation path.- Hỗ trợ operator custom dạng function - operator tự build expression theo context.
- Filter Digiforce không chỉ map
where, mà còn can thiệp include tree theo relation path.
Ví dụ filter qua relation
json
{
"createdBy.department.name": { "$eq": "Engineering" }
}FilterParser sẽ tự sinh include chain: users → departments và đặt where condition trên departments.name.
6) Options parser (OptionsParser)
OptionsParser gom và chuyển đổi tất cả query options:
| Input | Output Sequelize | Parser |
|---|---|---|
filter | where + include | Qua FilterParser |
filterByTargetKey | Merge vào where (Op.and) | Trực tiếp |
fields / appends / except | attributes + include | Tính toán select list |
sort | order | Fallback PK hoặc filter target key |
Method quan trọng: toSequelizeParams({ parseSort = true }).
7) Repository workflow
Repository chính cung cấp:
Read operations
| Method | Mô tả |
|---|---|
find(options) | Query chính, hỗ trợ filter/fields/sort/pagination |
findOne(options) | Tìm một record |
findAndCount(options) | Find + count cho pagination |
count(options) | Đếm records |
query(options) | Aggregate query (measure/dimension) |
aggregate(options) | Aggregate functions |
Write operations
| Method | Mô tả |
|---|---|
create(options) | Tạo record + association values |
createMany(records) | Batch create |
update(options) | Update record + UpdateGuard validation |
destroy(options) | Xóa record |
firstOrCreate(options) | Tìm hoặc tạo mới |
updateOrCreate(options) | Tìm để update hoặc tạo mới |
Batch streaming
| Method | Mô tả |
|---|---|
chunk(options) | Đọc theo batch, callback mỗi chunk |
chunkWithCursor(options) | Dùng cursor-based pagination |
find() chi tiết
Performance
list action mặc định có thể chuyển sang simple pagination nếu row count lớn (getEstimatedRowCount). Với bảng > 100k rows, hệ thống tự bỏ qua count query để tăng tốc.
create() / update() chi tiết
- Đi qua
UpdateGuard- validate và xử lý association values. - Hỗ trợ
whitelist/blacklistđể kiểm soát field nào được ghi. updateAssociationValuescho phép update nested relation trong cùng transaction.
8) runSQL trong Database
runSQL(sql, options) cho SQL thủ công:
| Feature | Mô tả |
|---|---|
| Auto filter | Nhận filter → wrap SQL thành subquery + append WHERE |
| Bind params | Hỗ trợ parameterized query |
| Transaction | Chạy trong transaction nếu cung cấp |
| Return modes | selectVar, selectRow, selectRows |
| Postgres schema | Set search_path local trước khi chạy |
Đọc tiếp
- Resourcer & Actions - action handler gọi tới repository
- DataSourceManager - quản lý nhiều database