40 điểm bởi GN⁺ 20 ngày trước | 5 bình luận | Chia sẻ qua WhatsApp
  • Codebase Drag là trạng thái codebase khiến mọi công việc mất nhiều thời gian hơn mức cần thiết, nhưng lại không lộ ra trên dashboard hay báo cáo sprint, khiến lãnh đạo hiểu nhầm đây là "vấn đề con người" và tiếp tục lặp lại vòng luẩn quẩn đó
  • Qua nhiều năm audit codebase, cùng một bộ 5 tín hiệu liên tục lặp lại, và từ đó tác giả đưa ra một rubric chẩn đoán định lượng mang tên "kiểm toán độ kéo của codebase" với thang điểm 0~2
  • 5 tín hiệu gồm ước lượng kiểu xin lỗi, nỗi sợ deploy, file "đừng động vào", lời nói dối của coverage, và thời gian đến commit đầu tiên đều bắt nguồn từ vấn đề chất lượng codebase, khác với việc năng lực con người kém
  • Kỹ sư càng dày dạn càng nhận ra rủi ro trong codebase tốt hơn nên di chuyển thận trọng hơn, vì thế lại tạo ra nghịch lý là trông còn chậm hơn; nếu hiểu nhầm đây là vấn đề nhân sự thì tác dụng ngược là chỉ làm quy trình thêm nặng nề
  • Từ 4 điểm trở lên là cần đầu tư trực tiếp vào codebase, còn từ 7 điểm trở lên là mức cần can thiệp cấu trúc ngay lập tức

Codebase Drag là gì

  • Codebase Drag là hiện tượng codebase khiến mọi công việc mất nhiều thời gian hơn mức cần thiết, và điều này không xuất hiện trong báo cáo sprint hay dashboard
    • Ví dụ: một đội client mất 1 tuần với 2 kỹ sư để thêm tính năng xuất CSV vào admin panel — phần việc thực tế chỉ đáng 1 ngày, còn thời gian còn lại là để hiểu cách sửa mã hiện có cho an toàn
  • Khi việc chậm lại của đội lặp đi lặp lại, lãnh đạo thường kết luận đó là vấn đề nhân sự và phản ứng bằng tái cơ cấu tổ chức, thêm quy trình, thay người, nhưng đội kế tiếp vẫn va vào đúng bức tường đó
  • Căn nguyên của vấn đề không phải bug, không phải tính năng còn thiếu, cũng không phải technical debt theo nghĩa thông thường, mà là chính bản thân codebase

5 tín hiệu của Codebase Drag

1. Ước lượng kiểu xin lỗi (Apology Estimate)

  • Đây là tình huống kỹ sư đưa ra estimate 2 tuần cho một tính năng thực tế chỉ mất 3 ngày, và phía lãnh đạo hiểu nhầm đó là thổi phồng lịch trình
  • Lý do thật sự là độ kết dính giữa các module: sửa module billing có thể kéo theo notification system, và cấu trúc hiện tại khiến không thể biết thay đổi sẽ lan ra đến đâu
    • Với hidden default scope hay callback lồng sâu, gần như không thể dự đoán blast radius của thay đổi nếu chưa đọc qua một nửa codebase
  • Nếu estimate liên tục mất thời gian gấp 2~3 lần dự đoán ban đầu, thì đó không phải vấn đề estimate mà là chi phí do codebase gây ra

2. Nỗi sợ deploy (Deploy Fear)

  • Đội ngũ có xu hướng né deploy vào thứ Sáu, hoặc gom deploy thành những đợt lớn và release thưa hơn
  • Một đội client từng vận hành một quy tắc ngầm là cấm deploy sau thứ Tư — hình thành sau khi 3 lần deploy vào thứ Năm đều dẫn đến sự cố cuối tuần
    • Nguyên nhân là không có chiến lược rollback, test không đáng tin cậy, và pipeline deploy dài 45 phút
  • Theo chuẩn DORA, các đội elite có tỷ lệ thất bại khi thay đổi dưới 5% và có thể deploy ngay khi cần, còn đội này thì chỉ deploy mỗi tuần một lần rồi thấp thỏm chờ đợi

3. File "đừng động vào đó" (Don't Touch That File)

  • Ở gần như mọi nơi, câu "đừng động vào file đó" đều xuất hiện trong vòng 2 ngày đầu
    • Ví dụ như billing controller có 30 before_action, hay một model đứng đầu git log nhưng về mặt cấu trúc thì đã nhiều năm không được đụng đến đúng nghĩa
  • Khi chạy git log --oneline --since="2 years ago", file được sửa nhiều nhất luôn là đúng file từng bị cảnh báo — nếu chỉ có các bản vá nhỏ lặp đi lặp lại mà không có cải tổ cấu trúc, thì nghĩa là chỉ đang chữa triệu chứng mà bỏ mặc căn bệnh
  • Chi phí thật sự là các chức năng lẽ ra phải nằm trong module đó lại bị triển khai ở chỗ khác, và người mới vào thường học được cách tránh file đó ngay trong tuần đầu — codebase phát triển méo mó quanh những vùng chết

4. Lời nói dối của coverage (Coverage Lie)

  • Con số 80% test coverage trông có vẻ khỏe mạnh, nhưng trên thực tế thường được chống đỡ bởi các test cho serializer, helper, utility vốn hầu như không bao giờ vỡ, trong khi 3 model cốt lõi xử lý tiền lại hoàn toàn không có test
  • Bộ test tồn tại không phải để bắt regression mà là để làm cho metric trông đẹp hơn — test pass nhưng production vẫn hỏng
  • Thời gian CI lên tới 40 phút khiến lập trình viên ngừng chạy test local → con số coverage nói dối theo hai nghĩa: vừa không cover được chỗ quan trọng, vừa đến cả test hiện có cũng không được chạy
  • Câu hỏi thật sự không phải là số coverage, mà là "Lần gần nhất test bắt được bug trước khi lên production là khi nào?"

5. Thời gian đến commit đầu tiên (Time to First Commit)

  • Đây là thời gian từ lúc giao laptop cho một kỹ sư mới đến khi họ mở được một PR chứa sửa bug thực tế hoặc một tính năng nhỏ
    • Codebase khỏe mạnh: 1~2 ngày
    • Codebase đang bị drag: hơn 2 tuần
  • Có một khách hàng mà việc set up môi trường phát triển từng mất nhiều tuần, nhưng sau khi được chỉnh sửa, một lập trình viên mới có thể hoàn tất cấu hình môi trường chỉ trong 15~20 phút
  • Nguyên nhân cốt lõi là setup rot — script bin/setup không được cập nhật sau lần thay đổi môi trường gần nhất, dữ liệu seed tham chiếu đến các bảng/cột đã không còn tồn tại, và có 3 biến môi trường không được tài liệu hóa mà chỉ khi chạy app mới biết là thiếu
  • Các kỹ sư cũ đã nội hóa quy trình không được ghi chép đó, nên chỉ người mới mới phơi bày chính xác quy mô của lượng tri thức ngầm mà codebase đang đòi hỏi

Vì sao kỹ sư giỏi lại trông chậm đi trong một codebase tệ

  • 5 tín hiệu này tác động chồng lấn lên nhau và cộng thêm overhead vào mọi công việc theo cách không thể chỉ ra trong buổi standup
    • Một kỹ sư từng làm xong tính năng trong 2 ngày ở công ty trước, nhưng ở codebase này lại mất 1 tuần, và dù có cố giải thích lý do thì cũng nghe như đang viện cớ
  • Nghiên cứu METR năm 2025 cho thấy các lập trình viên lành nghề khi dùng công cụ AI lại chậm hơn 19% — bằng chứng rằng nút thắt không nằm ở tốc độ gõ code
  • Kỹ sư giỏi nhất càng nhận ra rủi ro tốt hơn nên càng hành động cẩn trọng và đưa ra estimate rộng hơn — trong khi kỹ sư ít kinh nghiệm hơn không nhìn thấy rủi ro nên deploy nhanh hơn rồi gây sự cố production, khiến cả đội lại càng dè dặt hơn về sau
  • Một khách hàng đã thay 6 đội trong 10 năm (bao gồm 2 lần mua lại hoàn toàn) — mô thức lặp lại là lãnh đạo đòi tính năng → bỏ qua xử lý debt → code rơi vào trạng thái không thể cứu vãn → đề xuất rewrite hoặc tách microservice → hệ thống phình ra gấp đôi và còn tệ hơn
  • Nếu lãnh đạo đọc sự chậm lại như một vấn đề nhân sự thì họ sẽ chỉ thêm quy trình cho một đội vốn đã bị bào mòn bởi ma sát, khiến tình hình xấu hơn — can thiệp thực sự hữu ích duy nhất là sửa chính con đường đó

Kiểm toán Codebase Drag: cách chẩn đoán

  • Chấm điểm từng tín hiệu trong 5 tín hiệu theo thang 0~2:
    • 0 điểm: không có vấn đề
    • 1 điểm: có vấn đề một phần
    • 2 điểm: vấn đề nghiêm trọng
  • Nếu từ 4 điểm trở lên thì cần ưu tiên đầu tư trực tiếp vào codebase trước mọi biện pháp khác

Cách ứng phó khi technical debt đang kéo cả đội lại

  • Bắt đầu từ tín hiệu có điểm cao nhất — đừng cố sửa mọi thứ cùng lúc
    • Nỗi sợ deploy 2 điểm: ưu tiên cải thiện tốc độ CI, tự động hóa rollback, và chia nhỏ đơn vị deploy
    • Ước lượng kiểu xin lỗi đứng đầu: ưu tiên gỡ kết dính module có blast radius rộng nhất
    • Thời gian đến commit đầu tiên 2 điểm: đầu tư 1 ngày để sửa bin/setup và tài liệu hóa môi trường có thể thu hồi vốn ở mọi đợt tuyển mới sau đó
  • Nếu phiên bản Rails đang tụt lại nhiều phiên bản, thì nâng cấp phiên bản có thể trở thành một forcing function đủ mạnh để hợp thức hóa khoản đầu tư
  • Đo lường theo chu kỳ 2 tuần: chọn tín hiệu điểm cao nhất → sprint tập trung → đo bằng số liệu cụ thể (tần suất deploy, độ chính xác estimate, thời gian tới PR đầu tiên, v.v.)
  • Lý do khó được duyệt đầu tư là vì chi phí của việc không làm thì vô hình — nói "có technical debt" kém thuyết phục hơn rất nhiều so với nói "độ kết dính giữa 3 module này khiến mọi tính năng đều mất gần gấp đôi thời gian"
  • Từ 7 điểm trở lên thường là mức nên bắt đầu bằng một đợt audit codebase kéo dài 1 tuần

5 bình luận

 

Chuẩn luôn, dự án legacy đúng là sự tồn tại như ung nhọt
Có những thứ thà làm lại từ đầu còn hơn

 
hanje3765 19 ngày trước

Là đang nói về mình à ..?

 

Có vẻ đây là một bài viết thực sự quan trọng để giảm chi phí bảo trì.

 

Vì thế nên cũng có những trường hợp viết lại từ đầu còn nhanh hơn.

 

Ai cũng biết rằng dọn dẹp codebase là con đường giúp tăng tốc về lâu dài,
nhưng nó cũng chỉ giống như kiểu lời khuyên rằng ăn uống đầy đủ, tập thể dục và ngủ ngon thì sẽ khỏe mạnh thôi.