Chuyển đến nội dung
MINH VO Ghi chép từ công việc
của một kỹ sư tại Việt Nam
Cơ bản11 phút đọc

Học backend bằng cách theo một yêu cầu

Theo mã yêu cầu, công việc, lần xử lý và đối tượng để điều tra một lần xuất ảnh mà không đưa nội dung nhạy cảm vào log.

Tranh màu nước vẽ những cuốn sổ, một quyển sổ mở và bút chì trên nền màu kem

Hãy theo một yêu cầu qua backend trước khi cố hiểu mọi mô-đun. Với lập trình viên học dịch vụ chưa quen, việc lần theo một thao tác cụ thể có thể nối endpoint, công việc nền và kết quả người dùng thấy. Tôi thích đường này vì mỗi tệp có mục đích: nó tham gia thao tác quan sát được, thay vì chỉ nằm trong cây thư mục.

Dùng dịch vụ xuất ảnh giả định. Trình duyệt gửi yêu cầu, API tạo công việc, tiến trình nền kết xuất ảnh và nơi lưu giữ kết quả. Câu hỏi đầu tiên là thời gian hoặc lỗi có thể phát sinh ở đâu trên đường đi, không phải thư viện log nào có nhiều tính năng nhất.

Định nghĩa thao tác muốn theo dõi

Chọn một lần xuất giả định và gán mã nối các sự kiện. Mã yêu cầu có thể khác mã công việc vì một yêu cầu HTTP tạo việc tồn tại lâu hơn kết nối. Giữ quan hệ giữa chúng thay vì ép mọi tầng vào cùng vòng đời dễ gây hiểu nhầm.

Bản ghi sự kiện nhỏ có thể chứa tên sự kiện, thời điểm, mã yêu cầu, mã công việc, thành phần và nhóm kết quả. Giữ trường đủ ổn định để so hai lần chạy. Tránh đưa toàn bộ nội dung yêu cầu vào log chỉ vì tiện lúc phát triển.

Bài tổng quan khả năng quan sát của OpenTelemetry giải thích log, metric và trace là các tín hiệu khác nhau. Log ghi sự kiện; trace nối công việc qua các thao tác; metric tổng hợp phép đo. Trong bài này, bước đầu quan trọng là xác định tín hiệu nào trả lời câu hỏi bạn đặt ra.

Đọc chuỗi sự kiện nhỏ

Xét các sự kiện giả định sau theo thứ tự mong đợi. Mã chỉ để minh họa, bảng không chứa kết quả đo độ trễ.

Sự kiệnCác mãĐiều xác lập được
Yêu cầu được chấp nhậnyêu cầu R1, công việc J1API chấp nhận thao tác theo hợp đồng
Bắt đầu công việccông việc J1, lần xử lý A1Tiến trình nền bắt đầu một lần xử lý
Kết xuất xongcông việc J1, lần xử lý A1Kết xuất tới điểm hoàn tất
Đối tượng đã lưucông việc J1, đối tượng O1Thao tác lưu báo thành công
Công việc hoàn tấtcông việc J1, đối tượng O1Trạng thái công việc trỏ tới kết quả đã lưu

Mỗi sự kiện cần nghĩa chính xác. “Xuất thành công” mơ hồ nếu xuất hiện trước khi lưu xong. Tiến trình nền có thể kết xuất được nhưng không công bố được kết quả tải xuống. Đặt tên sự kiện theo ranh giới nó thực sự vượt qua.

Yêu cầu R1 tạo công việc J1; lần xử lý A1 kết xuất và đối tượng O1 trở thành kết quả tải xuống, với các mã nối từng sự kiệnMở ảnh kích thước đầy đủ ↗

Hình tách lần xử lý khỏi công việc. Thử lại có thể tạo lần xử lý khác trong khi người dùng vẫn mong một lần xuất. Thiếu phân biệt đó, người đọc log có thể hiểu hoạt động lặp của tiến trình nền thành nhiều yêu cầu người dùng riêng.

Thận trọng khi suy từ sự kiện thiếu

Giả sử chuỗi dừng sau kết xuất. Nơi lưu có thể lỗi, tiến trình có thể thoát hoặc hệ thống log có thể mất sự kiện. Thiếu một dòng là manh mối, chưa phải bằng chứng cho một cách giải thích.

Chọn kiểm tra tiếp theo tách được các khả năng. Xem đối tượng kết quả có tồn tại dưới mã dự định không. Xem trạng thái công việc. Tìm dấu tiến trình dừng hoặc lỗi lưu với cùng mã công việc. Nếu có trace, xem ranh giới thao tác và lỗi đã ghi.

Cách này tạo vòng học hữu ích: nêu giả thuyết, chọn quan sát phân biệt được nó và ghi kết quả. Đọc thêm mã có thể giúp, nhưng nên trả lời câu hỏi nảy sinh từ chuỗi sự kiện. Nếu không, kho mã lạ có thể thành chuỗi tệp bất tận mà mô hình hành vi không rõ hơn.

Giữ nội dung nhạy cảm ngoài dòng sự kiện

Yêu cầu xuất có thể chứa văn bản tài liệu, token truy cập hoặc URL tải có chữ ký. Sao chép chúng vào log có thể lộ dữ liệu hoặc thông tin xác thực. Dùng mã và nhóm giá trị có giới hạn khi đủ trả lời câu hỏi vận hành; giới hạn quyền đọc log phù hợp với thông tin chúng chứa.

Bộ quy tắc đạo đức ACM nêu trách nhiệm tôn trọng riêng tư và bảo vệ thông tin mật. Trong sổ học tập, dùng mã giả định và tóm tắt sự kiện thay vì dán dữ liệu sản xuất riêng tư.

Có đánh đổi: bỏ quá nhiều ngữ cảnh làm lỗi khó điều tra. Chọn trường cần cho một nhiệm vụ chẩn đoán cụ thể, thời gian giữ và người được đọc. Mã gián tiếp làm lộ danh tính một người vẫn cần được cân nhắc.

Kết thúc bằng bản đồ yêu cầu

Sau khi theo lần xuất, vẽ các thành phần đã đi qua và gắn bằng chứng tại mỗi ranh giới. Ghi phần nào còn suy luận. Chẳng hạn, API có thể ghi đã đưa công việc vào hàng đợi trong khi việc hàng đợi thực sự giao nó chưa được kiểm tra.

Lời giải thích cuối hữu ích nêu thao tác bắt đầu đâu, điều gì làm nó hoàn tất và cách điều tra kết quả thiếu. Chưa cần liệt kê mọi lớp trong kho mã. Yêu cầu tiếp theo có thể khác một điểm có ý nghĩa như thử lại hoặc lỗi lưu, để bản đồ lớn lên nhờ bằng chứng thay vì số tệp.

Phân biệt mã yêu cầu với ngữ cảnh trace

R1, J1 và A1 trả lời câu hỏi ứng dụng. Trace ID cùng các span ID mô tả quan hệ giữa phần việc đã được gắn công cụ theo dõi. Giữ riêng hai khái niệm: một công việc có thể được thử lại trong lần xử lý khác, còn yêu cầu xem trạng thái về sau có mã HTTP riêng dù vẫn nói tới cùng công việc.

Hướng dẫn truyền ngữ cảnh của OpenTelemetry giải thích cách dịch vụ gửi chuyển ngữ cảnh trace và span để dịch vụ nhận nối phần việc với bên gọi. Thư viện đo đạc có thể tự làm việc đó tại ranh giới được hỗ trợ. Qua hàng đợi nền, kiểm tra cách gắn công cụ theo dõi bên gửi, bên nhận và nơi mang ngữ cảnh thực tế; đừng cho rằng chuyển mã công việc cũng tự truyền trace.

Trong bài xuất, giữ J1 trong bản ghi ứng dụng để tìm được công việc dù trace không được lưu lại. Quan hệ trace có thể thêm cấu trúc nhân quả nhưng không thay bản ghi công việc bền. Trace ID chung cũng không phải thông tin cấp quyền truy cập. Ngữ cảnh từ bên gọi không đáng tin cần được xử lý phù hợp với hệ thống tracing; tài liệu nêu rõ header giả từ bên ngoài và ngữ cảnh không nên gửi ra ngoài.

Điều tra hai lần xử lý mà không gộp chúng

Mở rộng lần xuất giả định. A1 kết xuất xong rồi thoát trước khi ứng dụng ghi công việc hoàn tất. A2 bắt đầu sau. Nó có thể tìm thấy đối tượng đã có, dùng lại theo chính sách công việc hoặc tạo ứng viên kết quả khác. Chỉ mã công việc chưa cho biết lần xử lý nào tạo đối tượng nào.

Bằng chứngQuan sátCâu hỏi tiếp theo
Sự kiện kết xuất A1Kết xuất đã xongĐã lưu đối tượng nào chưa?
O1 tồn tạiNơi lưu có đối tượng đóLần xử lý nào tạo nó, đã có bản ghi trỏ tới chưa?
A2 bắt đầuLần xử lý nền khác đã chạyQuy tắc khôi phục nào chọn phần việc của nó?
J1 trỏ O2Kết quả công việc hiện tại là O2O1 có cần dọn theo chính sách lưu giữ không?

Có đối tượng trong nơi lưu chưa chứng minh công việc hoàn tất. Dòng công việc hoàn tất chưa chứng minh tải vẫn thành công sau khi hết hạn hay bị xóa. Dùng chuỗi sự kiện để chọn quan sát trạng thái tiếp theo, rồi so với hợp đồng ứng dụng.

Công việc J1 nối lần xử lý A1 và A2, có thể tạo các đối tượng khác nhau; kết quả hiện tại và lịch sử sự kiện trả lời câu hỏi riêngMở ảnh kích thước đầy đủ ↗

Điều đó cũng giải thích vì sao sự kiện lặp cần nghĩa ổn định. Nếu bộ xuất telemetry gửi lại cùng sự kiện sau khi kết nối lại, hai dòng thu thập có thể nói về một lần xảy ra. Nếu hai tiến trình thực sự xử lý công việc, mã lần xử lý phải khác. Thêm mã sự kiện hoặc số thứ tự khi đường log cần loại bản trùng; đừng suy ra thao tác nghiệp vụ bị nhân đôi chỉ từ số dòng.

Đừng sắp xếp thành một dòng thời gian sai

Dấu thời gian hữu ích, nhưng đồng hồ các máy có thể lệch. Giả sử sự kiện API mang giờ 10:00:00.100 còn sự kiện tiến trình nền là 10:00:00.095. Đồng hồ bên xử lý có thể chậm. Sắp hai thời điểm theo đồng hồ thực không xác lập rằng tiến trình nền đã chạy trước yêu cầu tạo công việc.

Giữ các mã liên hệ nhân quả và thành phần tạo sự kiện. Thời điểm bộ thu nhận được telemetry cho biết khi dữ liệu tới nơi, có thể khác lúc sự kiện ứng dụng xảy ra. Đo khoảng thời gian trong một tiến trình nên dùng phép đo đơn điệu thích hợp của môi trường chạy, thay vì trừ giờ đồng hồ có thể bị chỉnh. Định thời giữa dịch vụ cần thêm giả định về đồng hồ và cách gắn công cụ theo dõi.

Hướng dẫn log của OWASP khuyến nghị đồng bộ thời gian và ghi độ không chắc chắn khi không kiểm soát được đồng hồ. Trong báo cáo học tập, nêu đã so thời điểm nào và chúng hỗ trợ kết luận gì. Bảng năm sự kiện ban đầu chỉ cho thứ tự logic mong đợi, không cung cấp phép đo thời lượng.

Chọn cấu trúc sự kiện có thể kiểm tra an toàn

Bắt đầu bằng các trường được cho phép rõ ràng: tên sự kiện, thành phần, mã yêu cầu/công việc/lần xử lý và nhóm kết quả có giới hạn. Chỉ thêm mã đối tượng khi giúp tìm kết quả liên quan và người đọc log được phép thấy nó. Coi tiêu đề, chuỗi truy vấn hay thông báo ngoại lệ do người dùng ảnh hưởng là đầu vào không đáng tin, dù nằm trong sự kiện có cấu trúc.

Hướng dẫn OWASP bao quát loại dữ liệu nhạy cảm và chèn nội dung vào log bằng ký tự điều khiển hoặc dấu phân cách. Chuyển dữ liệu theo định dạng có cấu trúc giúp giữ thông điệp trong một trường, nhưng không khiến nội dung tự phù hợp để lưu hoặc an toàn với mọi công cụ xem phía sau. Tránh đưa token truy cập và URL tải có chữ ký vào cấu trúc sự kiện; chọn cách biểu đạt lỗi không sao chép cả yêu cầu.

Thực hành ba ca chẩn đoán: ngắt nơi lưu sau khi kết xuất, tạm dừng bộ thu telemetry và để thử lại tạo lần xử lý thứ hai theo hợp đồng công việc. So trạng thái bền của ứng dụng với sự kiện đến nơi. Đây là bài cục bộ được đề xuất; chỉ nói đã thử bộ thu ngừng hoạt động khi thực sự quan sát cách đệm và xử lý lỗi của nó.

Kết quả học là bản đồ vẫn dùng được khi bằng chứng chưa đầy đủ. Với mỗi kết quả thiếu, xác định riêng trạng thái công việc, lịch sử lần xử lý và đối tượng lưu. Sau đó giải thích quan sát nào sẽ đổi giả thuyết hiện tại. Nhờ vậy, tệp mã tiếp theo được mở có một câu hỏi cụ thể để trả lời.

Nguồn tham khảo & đọc thêm

  1. OpenTelemetry: observability primer
  2. ACM Code of Ethics
  3. OpenTelemetry: context propagation
  4. OWASP: logging cheat sheet
← Về trang bài viết

Hình minh họa

100%