Product Management
Đăng nhập
ESC

Nhập từ khóa để tìm kiếm

↑↓ Di chuyển
Enter Mở
ESC Đóng

Event tracking (khái niệm)

Technical Basics

Không track = không bao giờ có số — và đây là kỹ năng duy nhất mà sai lầm không sửa được bằng cách làm lại.

Bạn đang ở đâu với kỹ năng này?

Làm bài Đánh giá Nền tảng Kỹ thuật cho PM/BA — 3 người đã làm. Một lần làm chấm điểm cho tất cả kỹ năng trong nhóm Technical Basics, không chỉ kỹ năng này.

Làm bài đánh giá

Hai mức độ

Baseline — bạn hiểu

Hành động chỉ đo được nếu nó bắn một event kèm properties (màn hình, sản phẩm, giá trị) — không track = không bao giờ có số.

Mọi người làm sản phẩm, từ ngày đầu.
Working — bạn làm được

Suy ra danh sách tracking từ những câu hỏi sẽ phải trả lời sau launch; review tracking plan trước khi dev code; giữ tracking trong ticket từ ngày đầu — event không đo ngược quá khứ.

Product Analyst và Product Owner.

Roadmap — Cách học và đạt kỹ năng

Event tracking là gì?

Hệ thống không tự biết người dùng vừa làm gì. Nó chỉ ghi lại đúng những gì có người viết code ra để ghi. Một cú bấm nút mà không có dòng lệnh "gửi event" đi kèm thì không để lại dấu vết ở bất kỳ đâu — không trong database, không trong log, không trong công cụ analytics.

Một event gồm hai phần:

  • Tên event — chuyện gì vừa xảy ra. Ví dụ add_to_cart, order_placed.
  • Properties — chuyện đó xảy ra với cái gì, ở đâu, giá trị bao nhiêu. Ví dụ product_id, price, source_screen, city.

Hệ quả quan trọng nhất với BA/PO: event không đo ngược được quá khứ. Mọi thứ khác trong khung kỹ thuật này đều sửa được — cache sai thì xoá cache, job hỏng thì chạy lại, API chậm thì tối ưu. Riêng tracking thiếu thì thứ duy nhất mua lại được dữ liệu là thời gian: bạn sửa hôm nay và bắt đầu có số từ hôm nay.

Bốn bước nối tiếp: hành động của người dùng, event kèm properties, funnel và biểu đồ, rồi dashboard — với ghi chú không track bằng không có số đặt ngay ở bước đầu tiên
Bước 1 là dòng duy nhất phải nằm trong ticket trước khi dev code. Thiếu nó thì ba bước sau không chậm — chúng không tồn tại.

Baseline — bạn hiểu

  • Hành động chỉ đo được nếu nó bắn một event kèm properties (màn hình, sản phẩm, giá trị) — không track = không bao giờ có số.
  • Thiếu một property cũng nghiêm trọng như thiếu cả event: có số tổng nhưng không cắt được theo chiều mình cần.
  • Dữ liệu chỉ có từ ngày event được deploy trở đi; không có cách nào tính bù cho quá khứ.

Working — bạn làm được

  • Suy ra danh sách tracking từ những câu hỏi sẽ phải trả lời sau launch, thay vì từ danh sách nút bấm trên màn hình.
  • Review tracking plan trước khi dev code, cùng với người sẽ đọc số sau này.
  • Giữ tracking trong cùng ticket với tính năng từ ngày đầu — và đưa nó vào acceptance criteria.

Cơ chế hoạt động

Khái niệmNghĩa là gìDấu hiệu bạn đã hiểu
EventMột chuyện đã xảy ra, có tên, gửi lên đúng lúc nó xảy ra.Bạn đặt tên theo sự kiện nghiệp vụ, không theo màu nút.
PropertyThông tin đi kèm event: sản phẩm nào, giá bao nhiêu, từ màn hình nào.Bạn biết mỗi property tương ứng với một câu hỏi sẽ được hỏi sau này.
Tracking planBảng liệt kê event và property cần có, viết trước khi code.Bạn viết nó từ câu hỏi đi ngược lại, không từ giao diện đi ra.
Property mặc địnhBộ property gắn tự động vào mọi event (nền tảng, phiên bản, khu vực).Bạn quyết định bộ này một lần cho cả sản phẩm.
Định danh người dùngCách nối các event của cùng một người trước và sau khi đăng nhập.Bạn hỏi về nó trước khi tin vào bất kỳ con số "số người" nào.
Số lần và số ngườiHai cách đếm khác nhau trên cùng một event.Bạn luôn nói rõ mình đang đọc cái nào.
Dữ liệu hồi tốViệc tính lại số cho quá khứ.Bạn biết với event thì điều này không tồn tại.

Ví dụ theo cấp độ

Cơ bản — Nút "Thêm vào giỏ" chỉ đếm được nếu nó bắn một event

Tình huống: bạn vừa cho lên nút "Thêm vào giỏ" ở trang chi tiết sản phẩm. Một tuần sau bạn muốn biết nút đó được dùng bao nhiêu lần, và mọi người trong đội đều tưởng rằng "chắc chắn hệ thống có ghi lại".

Điều thực sự xảy ra: nếu không ai viết dòng gửi event, cú bấm đó biến mất ngay khi xảy ra. Database có bản ghi "giỏ hàng có sản phẩm X" — nhưng nó không nói ai đã thêm từ màn hình nào, và hoàn toàn không nói gì về những người bấm mà không thành công.

Dòng viết vào ticket, copy được nguyên văn:

Khi người dùng bấm "Thêm vào giỏ" và sản phẩm đã thực sự vào giỏ,
gửi event `add_to_cart` với các property:
  product_id      (chuỗi, bắt buộc)  — mã sản phẩm
  product_name    (chuỗi)            — tên hiển thị
  price           (số nguyên, VND)   — giá đang hiển thị tại thời điểm bấm
  quantity        (số nguyên)        — số lượng thêm vào giỏ
  source_screen   (chuỗi: "product_detail" | "search_results" | "category_list")

Nếu bấm mà không thêm được (hết hàng, lỗi mạng), gửi event
`add_to_cart_failed` với cùng bộ property và thêm error_reason.

Vì sao có source_screen: mười hai chữ trong ticket này là thứ sau đó cho bạn trả lời câu "khách thêm vào giỏ từ đâu nhiều nhất — trang chi tiết, kết quả tìm kiếm hay danh mục?". Không có nó, bạn vẫn biết tổng số, nhưng vĩnh viễn không biết nên đầu tư vào màn hình nào.

Vì sao có add_to_cart_failed: nếu chỉ track lần thành công, một sự cố khiến 30% cú bấm thất bại sẽ hiện ra dưới dạng "số lượt thêm giỏ giảm nhẹ" — trông y như nhu cầu giảm, và không ai đi tìm nguyên nhân.

Học được: "đếm số lượt bấm" không phải chuyện hiển nhiên của hệ thống; nó là một dòng yêu cầu mà ai đó phải viết ra trước khi tính năng lên. Và mỗi property bạn thêm vào dòng đó chính là một câu hỏi mà bạn sẽ trả lời được sau này.

Trung bình — Từ câu hỏi của sếp suy ngược ra danh sách event

Tình huống: bạn sắp làm lại luồng thanh toán. Phản xạ thông thường là đi từ màn hình: liệt kê các nút rồi track hết. Cách đúng thì ngược lại — bắt đầu bằng câu hỏi: "Một tháng sau khi chạy, tôi sẽ phải trả lời những câu nào?"

Bốn câu hỏi bạn viết ra trước, cùng với trưởng nhóm vận hành:

  1. Bao nhiêu người bỏ giữa chừng, và bỏ ở bước nào?
  2. Cách thanh toán nào bị bỏ nhiều nhất?
  3. Khách mua lần đầu hay khách cũ bỏ nhiều hơn?
  4. Có phải nhiều người bỏ vì mã giảm giá không dùng được không?

Bốn câu hỏi đó dịch thẳng thành tracking plan:

Câu hỏi sẽ phải trả lờiEvent cần cóProperty bắt buộc
Bỏ ở bước nàocheckout_started, shipping_info_submitted, payment_method_selected, order_placedcheckout_id, step_index
Cách thanh toán nào bị bỏpayment_method_selectedpayment_method ("momo" | "vnpay" | "cod" | "the_ngan_hang")
Khách mới hay khách cũtất cả các event trênuser_id, is_first_order (đúng/sai)
Mã giảm giápromo_code_applied, promo_code_rejectedpromo_code, reject_reason

Bốn quy tắc đặt tên, thống nhất một lần cho cả sản phẩm:

  • Động từ ở thì đã xảy ra: order_placed, không phải place_order. Event mô tả chuyện đã rồi, không mô tả ý định.
  • Chữ thường, nối bằng gạch dưới, thống nhất tuyệt đối. Add_To_Cartadd_to_cart là hai event khác nhau trong mọi công cụ, và bạn sẽ mất một buổi để phát hiện ra điều đó.
  • Đặt tên theo sự kiện nghiệp vụ, không theo giao diện: checkout_started chứ không phải blue_button_clicked. Nút sẽ đổi màu, đổi chữ, đổi vị trí; sự kiện nghiệp vụ thì không.
  • Dùng property thay vì đẻ thêm event: một event payment_method_selected kèm property payment_method tốt hơn ba event momo_selected, vnpay_selected, cod_selected. Vì thêm một cách thanh toán mới khi đó chỉ là thêm một giá trị, không phải sửa lại mọi biểu đồ đã dựng.

Dòng acceptance criteria đưa vào ticket, nằm ngay cạnh các AC chức năng:

AC-7 (tracking): Trên môi trường test, đi hết luồng thanh toán và đặt hàng
thành công thì trong công cụ analytics phải thấy đủ 4 event theo đúng thứ tự,
mỗi event có đủ property bắt buộc, không property nào rỗng.
Ticket chỉ được chuyển sang Done khi kiểm tra này đạt.

Học được: tracking plan viết từ câu hỏi đi ngược lại, không phải từ màn hình đi ra. Và nó phải nằm trong cùng ticket với tính năng — tách thành ticket riêng thì nó luôn là thứ bị cắt đầu tiên khi sprint hết chỗ, và không ai nhớ ra cho tới lúc cần số.

Nâng cao — "Tỷ lệ theo từng thành phố là bao nhiêu?"

Tình huống: luồng thanh toán mới đã chạy được một tháng, số liệu nhìn khá đẹp. Trong buổi review, giám đốc vận hành hỏi: "Tỷ lệ đặt hàng thành công ở Hà Nội so với Đà Nẵng thế nào? Tôi cần con số này để chốt ngân sách giao hàng quý tới." Bạn mở công cụ analytics: event order_placedproduct_id, có payment_method, không có thành phố.

Cái bẫy, gọi tên thẳng: đừng bao giờ giả định có thể tính bù dữ liệu về sau. Event là một ảnh chụp tại đúng thời điểm hành động xảy ra. Suốt một tháng qua, mỗi lần một khách đặt hàng, thông tin thành phố có nằm ngay trên màn hình đó — và đã đi qua mà không được ghi lại. Nó không nằm chờ ở đâu cả.

"Nhưng địa chỉ giao hàng có trong database đơn hàng mà?" Đúng, và đó chính là cái bẫy phụ khiến người ta tưởng cứu được. Bạn có thể lấy được tử số: bao nhiêu đơn thành công ở mỗi thành phố. Nhưng câu hỏi là tỷ lệ, và mẫu số là "bao nhiêu người ở Đà Nẵng đã bắt đầu thanh toán". Những người bỏ giữa chừng không tạo ra đơn hàng nào, nên họ không tồn tại trong database đơn hàng. Mẫu số đó vĩnh viễn không có.

Cái giá, tính bằng con số cụ thể:

  • Thêm property city vào các event: khoảng nửa ngày công của một dev. Rẻ.
  • Nhưng dữ liệu chỉ bắt đầu có từ ngày deploy. Muốn một tháng dữ liệu đủ để tin được thì phải chờ thêm một tháng nữa.
  • Quyết định phân bổ ngân sách giao hàng bị lùi một tháng — hoặc, phổ biến hơn, vẫn được ra đúng hạn nhưng dựa trên cảm tính, và không ai gọi tên điều đó ra trong biên bản họp.
  • Nếu ngân sách phải chốt trong hai tuần thì cái giá thật không phải nửa ngày công dev, mà là cả một quyết định ngân sách quý ra mà không có số.

Ba việc để lần sau không lặp lại:

  1. Một bộ property mặc định gắn vào mọi event, quyết định một lần cho cả sản phẩm: user_id, is_logged_in, platform (web/ios/android), app_version, city (suy ra từ hồ sơ hoặc địa chỉ mặc định), utm_source. Chi phí gần như bằng không vì chỉ làm một lần; đổi lại bạn cắt được mọi số liệu theo các chiều này mà không phải sửa từng event.
  2. Thêm một mục bắt buộc vào mẫu ticket: "Sau khi tính năng này chạy một tháng, những câu hỏi nào sẽ được hỏi?" Câu trả lời của mục đó chính là danh sách property.
  3. Một buổi review tracking plan 30 phút trước khi dev bắt đầu code, có mặt người sẽ phải đọc số sau này. Nửa giờ ở đây mua lại được một tháng chờ đợi ở phía sau.

Học được: event tracking là kỹ năng duy nhất trong khung này mà sai lầm không sửa được bằng cách làm lại. Với mọi thứ khác, sửa xong là có ngay kết quả đúng. Với tracking, sửa xong bạn mới bắt đầu đếm từ số không — nên giá trị của BA nằm hoàn toàn ở nửa giờ trước khi dev code, không phải ở lúc đi tìm cách cứu.

Áp dụng khi viết spec

Với mỗi tính năng bạn spec, ticket phải trả lời được bốn câu trước khi dev bắt đầu:

  1. Một tháng sau khi chạy, những câu hỏi nào sẽ được hỏi về tính năng này?
  2. Mỗi câu hỏi đó cần event nào và property nào? Property nào là bắt buộc, property nào có thể rỗng?
  3. Trường hợp thất bại có được track không, hay chỉ track lần thành công?
  4. Kiểm tra tracking nằm ở đâu trong acceptance criteria, và ai xác nhận nó đạt?

Câu hỏi nên hỏi dev

  • "Hành động này hiện đã bắn event nào chưa? Tên chính xác là gì?"
  • "Những property nào được gắn tự động vào mọi event, mình không cần khai lại?"
  • "Event được gửi từ phía trình duyệt hay từ phía máy chủ? Nếu từ trình duyệt thì người chặn quảng cáo có làm mất event không?"
  • "Trước và sau khi đăng nhập, các event của cùng một người có được nối lại với nhau không?"
  • "Mình có môi trường test riêng để kiểm tra event trước khi lên thật không?"
  • "Nếu bây giờ mình thêm một property, dữ liệu của những tháng trước có được tính lại không?" — câu trả lời gần như luôn là không, và đó là điều cần nghe tận tai một lần.

Sai lầm thường gặp

  • Tưởng hệ thống tự ghi lại mọi hành động, nên không viết gì vào ticket.
  • Viết tracking plan từ danh sách nút bấm trên màn hình thay vì từ câu hỏi sẽ được hỏi.
  • Tách tracking thành ticket riêng "làm sau" — và nó không bao giờ được làm.
  • Chỉ track trường hợp thành công, nên mọi sự cố hiện ra dưới dạng "nhu cầu giảm".
  • Đặt tên event theo giao diện (blue_button_clicked), rồi mất hết lịch sử khi giao diện đổi.
  • Đẻ một event mới cho mỗi lựa chọn thay vì dùng một property.
  • Nhầm số lần với số người khi báo cáo, khiến hai người đọc cùng một biểu đồ ra hai kết luận.
  • Hứa với stakeholder rằng "để tôi lấy số đó" trước khi kiểm tra event có tồn tại hay không.

Definition of done — dấu hiệu bạn đã đạt

  • Mọi tính năng bạn spec đều có tracking plan nằm trong cùng ticket, viết từ câu hỏi đi ngược lại.
  • Bạn kiểm tra event có tồn tại hay không trước khi hứa sẽ lấy được một con số.
  • Đội của bạn có một bộ property mặc định và một quy ước đặt tên được viết ra ở một chỗ ai cũng đọc được.
  • Có ít nhất một acceptance criteria về tracking trong mỗi ticket tính năng.

Đi sâu hơn

Khóa học liên quan (2)

Sử dụng trong vai trò

Thảo luận & tài liệu thêm 0

Chia sẻ kinh nghiệm, đặt câu hỏi, hoặc đính kèm tài liệu/YouTube giúp người khác học kỹ năng này.

Hãy là người đầu tiên chia sẻ kinh nghiệm cho kỹ năng này.

Nên làm bài đánh giá nào

Bắt đầu từ bài chẩn đoán
1 Chẩn đoán

Đánh giá mức sẵn sàng làm Business Analyst

Chấm từng chiều kỹ năng và cho ra hồ sơ — biết mình đứng ở đâu trước.

13 người đã làm
Làm bài này

Học kỹ năng này ở đâu?

Có 2 khóa dạy đúng phần này, miễn phí và bằng tiếng Việt.

Bắt đầu học