Hướng dẫn này nhằm mục đích trang bị cho bạn những hiểu biết và phương pháp thực hành cơ bản để đảm bảo bạn có thể giám sát và khắc phục sự cố dịch vụ của mình hiệu quả hơn.
Trong quá trình phát triển ứng dụng, việc ghi nhật ký thường bị bỏ qua nhưng đây là một thành phần quan trọng trong việc xây dựng một hệ thống mạnh mẽ và có thể quan sát được. Thực hành ghi nhật ký phù hợp có thể nâng cao khả năng hiển thị của ứng dụng, giúp bạn hiểu sâu hơn về hoạt động bên trong của ứng dụng và cải thiện tình trạng tổng thể của ứng dụng.
Việc kết hợp các cơ chế ghi nhật ký mặc định tại các điểm vào ứng dụng của bạn rất có lợi. Việc ghi nhật ký tự động này có thể nắm bắt các tương tác thiết yếu và có khả năng bao gồm các đối số của điểm nhập. Tuy nhiên, điều quan trọng là phải thận trọng vì việc ghi lại thông tin nhạy cảm như mật khẩu có thể gây ra rủi ro về quyền riêng tư và bảo mật.
Mọi hành động quan trọng mà ứng dụng của bạn thực hiện phải tạo ra một mục nhật ký, đặc biệt là những hành động làm thay đổi trạng thái của nó. Phương pháp ghi nhật ký toàn diện này là chìa khóa để nhanh chóng xác định và giải quyết các vấn đề khi chúng phát sinh, mang lại cái nhìn minh bạch về tình trạng và chức năng của ứng dụng của bạn. Sự siêng năng như vậy trong việc ghi nhật ký đảm bảo việc chẩn đoán và bảo trì dễ dàng hơn.
Việc áp dụng các cấp độ nhật ký phù hợp là rất quan trọng để quản lý và diễn giải lượng dữ liệu khổng lồ do ứng dụng của bạn tạo ra. Bằng cách phân loại nhật ký dựa trên mức độ nghiêm trọng và mức độ liên quan của chúng, bạn đảm bảo các vấn đề quan trọng được xác định và giải quyết kịp thời, trong khi những thông tin ít khẩn cấp hơn vẫn có thể truy cập được mà không làm quá tải nỗ lực giám sát của bạn.
Dưới đây là hướng dẫn sử dụng cấp độ nhật ký một cách hiệu quả:
Mức độ | Mô tả & Ví dụ | Chấp nhận sử dụng | Không được chấp nhận |
---|---|---|---|
| Các sự kiện nghiêm trọng làm ngừng hoạt động của hệ thống. ví dụ: Mất kết nối cơ sở dữ liệu | Lỗi hệ thống nghiêm trọng | Các lỗi không nghiêm trọng, như lần đăng nhập không thành công của người dùng |
| Xảy ra sự cố nhưng hệ thống có thể tiếp tục thực thi và hoàn thành thao tác được yêu cầu | Các vấn đề tiềm ẩn dẫn đến vấn đề | Thay đổi trạng thái thường lệ |
| Hiểu biết sâu sắc về các chức năng ứng dụng thông thường, như tạo tài khoản người dùng hoặc ghi dữ liệu | Thay đổi trạng thái | Hoạt động chỉ đọc mà không thay đổi |
| Thông tin chẩn đoán chi tiết, chẳng hạn như quá trình bắt đầu/kết thúc | Các bước của quá trình ghi nhật ký không làm thay đổi trạng thái hệ thống | Thay đổi trạng thái thường xuyên hoặc hoạt động tần số cao |
| Cấp độ chi tiết nhất, bao gồm các mục nhập/thoát phương thức | Hiểu dòng chảy và chi tiết của một quy trình | Ghi nhật ký thông tin nhạy cảm |
Khi ghi nhật ký các hành động trong ứng dụng của bạn, việc bao gồm ID của các thực thể có liên quan trực tiếp là rất quan trọng để liên kết thông tin nhật ký với dữ liệu cơ sở dữ liệu. Cách tiếp cận theo cấp bậc giúp bạn nhanh chóng tìm thấy tất cả nhật ký được kết nối với một phần cụ thể trong ứng dụng của bạn bằng cách liên kết các mục với nhóm hoặc danh mục chính của chúng.
Ví dụ: thay vì chỉ ghi lại ID của cuộc trò chuyện khi tin nhắn không gửi được, bạn cũng nên ghi lại ID của phòng trò chuyện và công ty mà nó thuộc về. Bằng cách này, bạn có được nhiều bối cảnh hơn và có thể thấy tác động rộng hơn của vấn đề.
Failed to send the message - chat=$roomId, chatRoomId=chatRoomId, company=$companyId
Dưới đây là ví dụ về cách nhật ký sản xuất có thể trông như thế nào khi sử dụng phương pháp phân cấp:
Việc chuẩn hóa định dạng nhật ký giữa tất cả các nhóm có thể giúp nhật ký của bạn dễ đọc và dễ hiểu hơn nhiều. Dưới đây là một số tiền tố tiêu chuẩn cần xem xét:
Việc tách tên và giá trị biến khỏi nội dung của thông điệp tường trình mang lại một số lợi ích:
Log message - valueName=value
Dưới đây là ví dụ về các mục nhật ký có cấu trúc tốt tuân theo các phương pháp hay nhất đã được thảo luận:
2023-10-05 14:32:01 [INFO] Successful login attempt - userId=24543, teamId=1321312 2023-10-05 14:33:17 [WARN] Failed login attempt - userId=536435, teamId=1321312
Những ví dụ này chứng minh:
Dưới đây là ví dụ về cách nhật ký sản xuất có thể trông như thế nào khi sử dụng các phương pháp được đề xuất:
Để liên kết hiệu quả nhật ký với một hành động cụ thể của người dùng, điều quan trọng là phải bao gồm traceId
hoặc vì nó còn được gọi là correlationId
trong nhật ký của bạn. ID phải nhất quán trên tất cả nhật ký được tạo bởi logic được kích hoạt bởi điểm nhập đó, cung cấp cái nhìn rõ ràng về chuỗi sự kiện.
Mặc dù một số dịch vụ giám sát như Datadog cung cấp tính năng nhóm nhật ký ngay lập tức nhưng việc này cũng có thể được triển khai theo cách thủ công. Trong ứng dụng Kotlin sử dụng Spring, bạn có thể triển khai ID theo dõi cho các yêu cầu REST bằng HandlerInterceptor.
@Component class TraceIdInterceptor : HandlerInterceptor { companion object { private const val TRACE_ID = "traceId" } override fun preHandle(request: HttpServletRequest, response: HttpServletResponse, handler: Any): Boolean { val traceId = UUID.randomUUID().toString() MDC.put(TRACE_ID, traceId) return true } override fun afterCompletion(request: HttpServletRequest, response: HttpServletResponse, handler: Any, ex: Exception?) { MDC.remove(TRACE_ID) } }
Thiết bị chặn này tạo ra một traceId
duy nhất cho mỗi yêu cầu, thêm nó vào MDC khi bắt đầu yêu cầu và xóa nó sau khi yêu cầu hoàn thành.
Việc triển khai tính năng tổng hợp nhật ký như vậy sẽ cho phép bạn lọc nhật ký tương tự như ví dụ bên dưới
Trong nhiều hệ thống, các thực thể có thể sử dụng UUID
hoặc ID Long
làm mã định danh chính, trong khi một số hệ thống có thể sử dụng cả hai loại ID cho các mục đích khác nhau. Hiểu được ý nghĩa của từng loại đối với mục đích ghi nhật ký là rất quan trọng để đưa ra lựa chọn sáng suốt.
Dưới đây là bảng phân tích những điều cần xem xét:
Khả năng đọc: ID Long
dễ đọc hơn và ngắn hơn đáng kể, đặc biệt nếu chúng không ở mức cao nhất trong phạm vi Long
.
Giá trị duy nhất: ID UUID
cung cấp tính duy nhất trên toàn hệ thống, cho phép bạn tìm kiếm nhật ký bằng ID mà không gặp phải vấn đề xung đột ID. Xung đột ở đây có nghĩa là có khả năng 2 thực thể từ các bảng DB không liên quan sẽ có cùng ID Long
.
Giới hạn hệ thống : Trong các hệ thống sử dụng khóa chính Dài làm ID thực thể, việc thêm ID UUID
ngẫu nhiên thường đơn giản, trong hệ thống phân tán có ID thực thể UUID
việc có ID Long
đặc biệt để ghi nhật ký có thể là một thách thức hoặc tốn kém.
Nhật ký hiện có: Tính nhất quán về loại ID được sử dụng trong nhật ký là rất quan trọng, ít nhất là đối với mỗi thực thể. Nếu hệ thống đã tạo nhật ký cho một số thực thể và bạn không cân nhắc việc thay đổi tất cả chúng, tốt hơn hết bạn nên sử dụng loại đã được sử dụng để xác định thực thể đó. Việc ghi nhật ký cả hai ID có thể được xem xét trong giai đoạn chuyển tiếp, nhưng việc có nhiều ID vĩnh viễn sẽ làm lộn xộn nhật ký một cách không cần thiết.
Thực hành ghi nhật ký thích hợp là điều cần thiết để có thể quan sát dịch vụ hiệu quả. Bằng cách kết hợp tính năng ghi nhật ký toàn diện, cấp độ nhật ký phù hợp, ID theo dõi và định dạng nhật ký được chuẩn hóa, bạn có thể nâng cao đáng kể khả năng giám sát và khắc phục sự cố ứng dụng của mình. Những phương pháp này cải thiện tính rõ ràng và nhất quán của nhật ký, giúp chẩn đoán và giải quyết vấn đề nhanh chóng dễ dàng hơn.
Cảm ơn bạn đã dành thời gian để đọc bài viết này!