Sau khi đã nắm từng phần riêng lẻ — kết nối GCP MCP, viết query BigQuery, kiểm tra Cloud Run — bài này ghép mọi thứ lại thành một workflow đầu-cuối hoàn chỉnh, mô phỏng một tình huống rất thường gặp trong công việc thật: nhận báo cáo "số liệu bị lệch" từ team business, phải tìm ra nguyên nhân trong một data pipeline chạy trên GCP, sửa lỗi, và backfill lại dữ liệu đã sai — toàn bộ thực hiện với sự hỗ trợ của agent qua GCP MCP. Đây là dạng bài tổng hợp, phù hợp để bạn luyện lại toàn bộ kỹ năng đã học trong module này theo một case study cụ thể, có số liệu, có bước debug thật.
Tổng Quan Workflow: Từ Báo Cáo Lệch Số Liệu Đến Bản Fix Đã Được Xác Minh
Tình huống giả định nhưng rất thực tế: team Finance báo rằng dashboard doanh thu (revenue_daily) cho thấy doanh thu ngày 14/07/2026 giảm bất thường 40% so với các ngày xung quanh, trong khi theo họ biết, hôm đó không có sự kiện gì đặc biệt (không phải ngày lễ, không có outage được ghi nhận). Bạn được giao nhiệm vụ xác minh: đây là vấn đề thật của business, hay là lỗi trong data pipeline.
Workflow tổng thể gồm 3 bước chính, mỗi bước tương ứng với một phần dưới đây:
- Profiling và xác định điểm bất thường — dùng BigQuery để xác nhận con số lệch có thật không, và khoanh vùng chính xác nó nằm ở đâu trong luồng dữ liệu.
- Truy vết qua pipeline — dùng Cloud Run logs và GCS artifact để tìm ra bước xử lý nào trong pipeline gây ra lỗi.
- Sửa lỗi và backfill — sửa code transform, chạy lại (backfill) dữ liệu bị sai, và verify bằng query so sánh trước/sau.
Nguyên tắc xuyên suốt cả ba bước: luôn để agent chứng minh bằng dữ liệu thật (query, log thật) trước khi đưa ra kết luận, không chấp nhận agent "đoán" nguyên nhân dựa trên pattern lỗi phổ biến. Đây cũng là lý do bạn cần một agent có quyền truy cập GCP MCP thật, thay vì chỉ hỏi một chatbot không thấy dữ liệu.
Mẹo: Trước khi bắt đầu bất kỳ session debug nào, viết rõ ràng giả thuyết ban đầu và yêu cầu agent xác nhận hoặc bác bỏ bằng data — ví dụ "giả thuyết: lỗi nằm ở bước aggregation, không phải ở nguồn raw data" — điều này giữ cho agent tập trung đúng hướng, tránh lan man khám phá không mục tiêu.
Bước 1: Profiling Dataset Và Xác Định Điểm Bất Thường Với BigQuery
Bước đầu tiên luôn là xác nhận con số bất thường có thật, và khoanh vùng nó xuất phát từ đâu trong chuỗi transform (raw → staging → warehouse).
Prompt mở đầu:
Dùng GCP MCP, lấy schema của table `warehouse.revenue_daily`. Viết query
so sánh doanh thu ngày 14/07/2026 với trung bình 7 ngày trước và sau ngày đó
(loại trừ chính ngày 14/07). Dry-run trước, chạy nếu dưới 1GB scanned.
Giả sử kết quả xác nhận: doanh thu ngày 14/07 là 420 triệu, trung bình các ngày xung quanh là 700 triệu — giảm khoảng 40%, đúng như Finance báo cáo. Bước tiếp theo là khoanh vùng: lỗi nằm ở tầng nguồn (ít order thật) hay tầng transform (order có thật nhưng bị tính sai/thiếu khi lên warehouse)?
Table warehouse.revenue_daily được build từ table raw `raw.orders` qua một
pipeline transform. Viết query đếm số order thật trong raw.orders ngày 14/07/2026
(theo created_at), so sánh với số order được aggregate trong warehouse.revenue_daily
cùng ngày. Cho tôi biết chênh lệch số lượng order giữa hai tầng.
Đây là bước quan trọng nhất của toàn bộ quá trình debug: nếu số order ở raw.orders bình thường (không giảm) nhưng số order phản ánh trong warehouse.revenue_daily giảm, bạn đã xác nhận được vấn đề nằm ở transform, không phải ở business thật — tức khách hàng vẫn đặt hàng bình thường, nhưng pipeline tính sai. Trong case thực tế tương tự tôi từng xử lý, kết quả cho thấy raw.orders có 1,240 order ngày đó (bình thường), nhưng warehouse.revenue_daily chỉ aggregate được 740 order — tức khoảng 500 order "biến mất" trong quá trình transform.
Bước khoanh vùng tiếp theo là kiểm tra xem 500 order bị thiếu có đặc điểm chung gì không:
Trong raw.orders ngày 14/07/2026, tìm các order KHÔNG xuất hiện trong
warehouse.revenue_daily (dùng order_id để so sánh, tự viết LEFT JOIN
hoặc NOT EXISTS phù hợp). Lấy 20 order mẫu và cho tôi biết chúng có
điểm chung gì về status, currency, hoặc region không.
Đây là lúc agent phát huy giá trị thật: tự viết SQL so sánh chính xác (không phải bạn tự nhớ cú pháp NOT EXISTS hay LEFT JOIN ... WHERE ... IS NULL), và quan trọng hơn — tự phân tích pattern trong kết quả. Ví dụ nếu agent phát hiện toàn bộ 500 order thiếu đều có currency = 'USD' (khác với phần lớn order khác là VND), đây là một đầu mối cực mạnh để bước 2 tiếp tục truy vết.
Mẹo: Luôn so sánh số liệu ở nhiều tầng của pipeline (raw → staging → warehouse) theo cùng một khóa duy nhất (
order_id), không chỉ so sánh tổng số tiền — tổng số tiền có thể "trùng khớp giả" do bù trừ lỗi (một số order bị tính thiếu, một số khác bị tính trùng, tổng vẫn ra số gần đúng nhưng chi tiết sai hoàn toàn).
Bước 2: Truy Vết Pipeline Qua Cloud Run Logs Và GCS Artifacts
Đã xác định pattern nghi vấn (order currency = 'USD' bị thiếu), bước tiếp theo là tìm đúng đoạn code/job nào trong pipeline gây ra việc bỏ sót này. Giả sử pipeline chạy dạng: một Cloud Run job đọc file JSON export từ GCS (do hệ thống order upstream đẩy vào), transform, rồi load vào BigQuery.
Dùng GCP MCP, describe Cloud Run job (hoặc service) `orders-etl-job` chạy
cho ngày 14/07/2026. Lấy log của lần chạy đó, tìm các dòng log có chứa
"USD", "currency", "error", hoặc "skip" — tôi nghi ngờ có order bị filter
nhầm trong bước transform.
Trong tình huống thực tế, log thường sẽ lộ ra nguyên nhân qua một dòng cụ thể, ví dụ:
WARN: Skipping order with unsupported currency format: USD (expected: VND)
Đây chính là nguyên nhân gốc: code transform có một bước validate currency chỉ chấp nhận format VND, và một đợt cập nhật gần đây từ hệ thống upstream (có thể do một team khác thêm tính năng thanh toán quốc tế) đã bắt đầu gửi order với currency = USD, nhưng bước transform coi đây là dữ liệu không hợp lệ và silently skip — không throw lỗi, không alert, chỉ log WARN và bỏ qua, khiến vấn đề âm thầm tồn tại nhiều ngày trước khi Finance phát hiện qua dashboard.
Bước tiếp theo là xác nhận đúng đoạn code gây ra hành vi này, nếu bạn có source code pipeline trong repo đang mở (kết hợp với agent trong Cursor hoặc Claude Code VS Code):
Tìm trong codebase đoạn xử lý validate currency trong pipeline orders-etl.
Cho tôi xem logic hiện tại đang filter currency như thế nào, và giải thích
vì sao order USD bị skip thay vì được convert hoặc xử lý riêng.
Cũng nên kiểm tra artifact gốc trên GCS để xác nhận dữ liệu USD thực sự có trong file export gốc (chứ không phải lỗi từ hệ thống upstream):
List các object trong bucket orders-export với prefix exports/2026-07-14/.
Đọc nội dung file export gần trưa ngày đó (khoảng thời điểm nghi vấn),
cho tôi biết có bao nhiêu record có currency USD trong file gốc này.
Việc kiểm tra artifact gốc là bước xác minh quan trọng, giúp bạn loại trừ khả năng lỗi nằm ở phía trước pipeline (hệ thống upstream) — nếu dữ liệu gốc trên GCS đã đúng và có currency USD, bạn khẳng định chắc chắn lỗi nằm trong logic transform của chính pipeline này, không phải lỗi từ team khác.
Mẹo: Khi log chỉ ghi WARN mà không throw exception, đây thường là dấu hiệu của một "silent failure" — loại lỗi nguy hiểm nhất vì hệ thống vẫn chạy "thành công" theo giám sát thông thường (không có alert, không crash) trong khi dữ liệu đang sai. Luôn rà log WARN định kỳ, không chỉ log ERROR, khi audit độ tin cậy của một pipeline quan trọng.
Bước 3: Sửa Transform Và Backfill Với Các Query Đã Được Xác Minh
Sau khi xác định nguyên nhân gốc, bước cuối là sửa code, sau đó backfill lại đúng phần dữ liệu bị ảnh hưởng — không phải chạy lại toàn bộ pipeline từ đầu (tốn thời gian và tiền không cần thiết), mà chỉ backfill đúng phạm vi bị lỗi.
Yêu cầu agent đề xuất fix code (bạn luôn tự review trước khi merge, đây không phải bước tự động approve):
Sửa logic validate currency trong pipeline orders-etl để chấp nhận cả USD
và VND, convert USD sang VND theo tỷ giá tại thời điểm order (giả sử có
table exchange_rates.daily_rates), thay vì skip order như hiện tại.
Viết lại hàm, kèm log rõ ràng (không phải silent skip) nếu gặp currency
không được hỗ trợ khác.
Sau khi code fix đã được review và merge, bước backfill cần làm rất cẩn thận để không tạo duplicate hoặc double-count dữ liệu đã đúng:
Viết query backfill cho warehouse.revenue_daily: chỉ xử lý lại các order
có currency = USD trong khoảng 01/07/2026 đến 21/08/2026 (từ ngày bắt đầu
lỗi đến hôm nay) mà chưa từng được aggregate (dùng order_id để kiểm tra
NOT EXISTS trong warehouse hiện tại). Dùng câu MERGE, không dùng INSERT
trực tiếp, để tránh tạo duplicate nếu chạy lại nhiều lần.
Việc yêu cầu dùng MERGE thay vì INSERT là một nguyên tắc an toàn quan trọng cho mọi job backfill — MERGE cho phép bạn chạy lại nhiều lần một cách an toàn (idempotent), trong khi INSERT trực tiếp nếu chạy nhầm hai lần sẽ tạo dữ liệu trùng, gây ra một lỗi mới trong khi đang sửa lỗi cũ.
Bước cuối cùng, không thể thiếu: verify lại bằng chính query đã dùng ở Bước 1, để xác nhận số liệu đã về đúng và không tạo lệch mới ở nơi khác:
Chạy lại query so sánh doanh thu ngày 14/07/2026 với trung bình 7 ngày
xung quanh (giống query ở bước đầu). Đồng thời kiểm tra tổng số order
trong warehouse.revenue_daily từ 01/07 đến hôm nay có tăng đúng bằng
số order USD đã backfill không, không tăng nhiều hơn (dấu hiệu duplicate).
Nếu kết quả verify khớp — doanh thu ngày 14/07 giờ gần với mức trung bình, và số order tăng đúng bằng số lượng order USD được backfill, không hơn không kém — bạn có thể tự tin báo cáo lại cho Finance kèm bằng chứng số liệu cụ thể, đồng thời đề xuất thêm một alert giám sát (ví dụ Cloud Monitoring alert khi log WARN "Skipping order" xuất hiện) để phát hiện sớm hơn nếu tình huống tương tự xảy ra lần sau.
Mẹo: Luôn dùng lại chính xác query đã dùng để phát hiện vấn đề ở Bước 1 làm query verify ở Bước 3 — đây là cách đảm bảo bạn đang đo đúng cùng một thước đo trước/sau, tránh trường hợp verify bằng một query khác vô tình "che" mất phần lỗi chưa được sửa hết.
Tips
- Luôn khoanh vùng theo tầng dữ liệu (raw → staging → warehouse) bằng khóa chính (
order_id) trước khi kết luận nguyên nhân, đừng chỉ nhìn tổng số tiền hay tổng số lượng. - Rà cả log WARN, không chỉ log ERROR — silent failure (skip âm thầm không throw lỗi) là nguyên nhân phổ biến nhất của các vụ lệch số liệu khó phát hiện.
- Luôn dùng
MERGE(không phảiINSERTtrực tiếp) cho mọi job backfill để đảm bảo idempotent, có thể chạy lại an toàn nếu cần. - Verify bằng chính query đã dùng để phát hiện vấn đề ban đầu, để đảm bảo đo đúng cùng thước đo trước và sau khi fix.