Giới thiệu
Trong các ứng dụng phần mềm, việc quản lý và đọc cấu hình là một nhu cầu thiết yếu. Thông thường, các giá trị cấu hình này được lưu trữ trong các file cấu hình, chẳng hạn như appsettings.json
trong môi trường .NET.
Đọc Cấu Hình Qua IConfiguration
Chúng ta có thể sử dụng IConfiguration
để đọc thông tin cấu hình một cách trực tiếp. Ví dụ, hãy tưởng tượng rằng chúng ta có cấu hình kết nối đến cơ sở dữ liệu MySQL trong Entity Framework Core được khai báo trong appsettings.json
như sau:
json
{
"DatabaseMysqlOptions": {
"ConnectionString": "your_connection_string",
"CommandTimeout": 30
}
}
Chúng ta có thể sử dụng một Controller với một API để lấy ra danh sách các cấu hình này.
Những Hạn Chế Khi Sử Dụng IConfiguration
Tuy nhiên, việc đọc cấu hình bằng IConfiguration
có thể gặp một số hạn chế:
- Thiếu kiểm tra giá trị: Các giá trị trong file cấu hình không được validation tự động, và chúng ta phải kiểm tra từng giá trị trong runtime.
- Loại không rõ ràng: Các giá trị không được chỉ định loại cụ thể, có thể gây ra lỗi trong quá trình phát triển.
- Khó khăn với giá trị mặc định: Thiếu giá trị mặc định cho các cấu hình, yêu cầu phải kiểm tra và gán trong mỗi lần gọi.
Để khắc phục những vấn đề này, bài viết này sẽ giới thiệu về Options Pattern.
Giới Thiệu Về Options Pattern
Options Pattern là một phương pháp phổ biến trong phát triển ứng dụng .NET, cho phép chúng ta định nghĩa các lớp chứa các cấu hình ứng dụng. Nhờ vào đây, chúng ta có thể tạo ra các Options hoặc Configuration classes, giúp quản lý cấu hình một cách linh hoạt.
Lợi Ích Khi Sử Dụng Options Pattern
- Kiểm tra (Validation): Cho phép kiểm tra giá trị ngay khi khai báo.
- Giá trị mặc định: Cho phép dễ dàng thiết lập giá trị mặc định cho toàn bộ ứng dụng.
- Reload cấu hình: Có khả năng tải lại giá trị cấu hình mà không cần khởi động lại ứng dụng.
Bước Đầu Với Options Pattern
Chúng ta sẽ tạo một lớp có tên DatabaseOptions để đại diện cho cấu hình kết nối cơ sở dữ liệu, bao gồm các thuộc tính công khai cho từng giá trị cấu hình.
Cách Đọc Cấu Hình Với Options Pattern
Có hai cách để chúng ta có thể đọc cấu hình từ file JSON là bằng phương thức Bind(object) và Get
Đăng Ký Options Trong Dịch Vụ
Chúng ta sẽ tạo một lớp ServiceExtensions để mở rộng việc đăng ký dịch vụ trong IServiceCollection
. Trong đó, chúng ta sẽ định nghĩa phương thức AddOptionsService() và đăng ký nó trong program.cs
để sử dụng IOptions
trong toàn bộ ứng dụng.
Sử Dụng Dependency Injection
Chúng ta có thể inject IOptions
Kiểm Tra Giá Trị Cấu Hình
Để đảm bảo tính chính xác của các giá trị, Options Pattern cho phép dùng Data Annotations để thực hiện các quy tắc kiểm tra. Ví dụ:
- ConnectionString: không được rỗng hoặc null.
- CommandTimeout: phải nằm trong khoảng từ 10 đến 50.
Kích Hoạt Kiểm Tra Giá Trị
Sau khi bổ sung các quy tắc kiểm tra bằng Data Annotations, chúng ta sẽ gọi thêm phương thức ValidateDataAnnotations trong phần đăng ký dịch vụ để kích hoạt kiểm tra.
Reload Cấu Hình Với Options Interfaces
Trong môi trường Production, chúng ta cần cấu hình cho phép ứng dụng đọc giá trị mới mà không cần khởi động lại. Để đạt được điều đó, .NET cung cấp hai interface: IOptionsSnapshot và IOptionsMonitor.
So Sánh Các Interfaces
- IOptions: Được đăng ký dưới dạng Singleton và không có khả năng phản ánh các thay đổi trong cấu hình sau khi khởi động.
- IOptionsSnapshot: Được đăng ký dưới dạng Scoped, chụp nhanh giá trị và không bị ảnh hưởng bởi thời gian chạy.
- IOptionsMonitor: Có thể lấy giá trị mới nhất ngay cả khi ứng dụng đang chạy, đăng ký dưới dạng Singleton.
Minh Họa Sử Dụng Các Interface
Chúng ta sẽ thêm vào Controller ba API khác nhau để lấy cấu hình từ IOptions
, IOptionsSnapshot
, và IOptionsMonitor
để cho thấy sự khác biệt giữa chúng.
Kết Luận
Bài viết đã giới thiệu tổng quan về Options Pattern và cách thức áp dụng hiệu quả trong các dự án .NET Core. Qua đó, bạn có thể dễ dàng quản lý cấu hình ứng dụng của mình hơn. Hy vọng thông tin trong bài viết hữu ích đối với bạn. Nếu trò chuyện này hấp dẫn, hãy theo dõi thêm nội dung từ kênh của tôi!
Mã Nguồn
Tài liệu tham khảo:
- Options Pattern in ASP.NET Core
source: viblo