# GitHub tối ưu hóa hiệu suất: Chuyển đổi sang CSS Modules giúp giảm 55% thời gian SSR

- Nguồn: GitHub Blog
- Thời gian phát hành: 2026-09-25 22:00 (giờ Việt Nam)
- Điểm AI: 64/100
- Nhãn AIHOT: Tinh chọn
- Link AIHOT.vn: https://aihot.vn/items/617af14b21353df1
- Nguồn dữ liệu AI HOT: https://aihot.news/items/cmuh3oryg07vcrolz1nd3fov6
- Link gốc: https://github.blog/engineering/architecture-optimization/improving-site-performance-by-shipping-more-css

## Lý do tinh chọn

Bài viết cung cấp lộ trình hoàn chỉnh và lợi ích định lượng khi các tập đoàn lớn chuyển đổi từ CSS-in-JS sang CSS Modules, có thể áp dụng cho các dự án cải tiến kiến trúc frontend tương tự.

## Tóm tắt AI

Kỹ sư GitHub chia sẻ hành trình chuyển đổi hệ thống thiết kế Primer từ CSS-in-JS sang CSS Modules, giúp giảm 55% thời gian render phía máy chủ và 25% thời gian khởi tạo thành phần.

## Thân bài

Góc nhìn về cách một hệ thống thiết kế thực hiện những thay đổi lớn mà không gây ảnh hưởng đến toàn bộ hệ thống.

25 tháng 9, 2026

8 phút

- Chia sẻ:

[Primer Design System](https://primer.style/) là nền tảng cho nhiều trải nghiệm mà bạn thấy trên GitHub ngày nay. Từ các nút bấm, biểu ngữ cho đến thanh điều hướng (breadcrumbs), những thành phần nền tảng này đòi hỏi phải có tính truy cập, linh hoạt và hiệu năng cao trong nhiều tình huống khác nhau.

Quay lại năm 2023, số lượng thành phần trên một số trang bắt đầu tăng vọt. Điều này dẫn đến nhiều thách thức về hiệu năng với giải pháp CSS-in-JS hiện tại của chúng tôi:

- Thời gian tải trang ban đầu lâu hơn do các kiểu (styles) được khởi tạo trên trình duyệt khách (client)
- Hiệu năng kết xuất phía máy chủ (server-side rendering) giảm sút do việc thu thập kiểu được chuyển từ phía khách
- Việc cập nhật các kiểu trở nên mất kiểm soát khi số lượng thành phần trên một trang tăng lên

Rõ ràng là đội ngũ Primer cần giải quyết vấn đề từ gốc rễ. Chúng tôi cần tìm một giải pháp thay thế giúp loại bỏ hoàn toàn các chi phí về phía khách và máy chủ mà chúng tôi đang gặp phải với giải pháp hiện tại. Quan trọng nhất, bất kỳ giải pháp thay thế nào được chọn cũng cần phải hoạt động theo cách tránh gây ra bất kỳ sự cố nào cho GitHub trong quá trình chuyển đổi.

### Giới thiệu CSS (Modules)

Đội ngũ Primer đã tìm ra một giải pháp đáp ứng tất cả các tiêu chí của chúng tôi: [CSS Modules](https://github.com/css-modules/css-modules). Định dạng này cho phép chúng tôi thực hiện một trong những điều mình yêu thích nhất: viết và sử dụng các tính năng CSS gốc, đồng thời vẫn giữ được khả năng đặt chung (colocation) và đóng gói (encapsulation) mà chúng tôi mong đợi từ CSS-in-JS.

Với CSS Modules, các kiểu sẽ được viết trong một tệp CSS nằm cùng với mã nguồn JavaScript của thành phần đó. Nó cũng cho phép chúng tôi coi tất cả tên lớp (class names) là cục bộ theo mặc định, ngăn chặn một số xung đột và thách thức có thể phát sinh từ các bộ chọn toàn cục (global selectors). Định dạng này cũng loại bỏ nhu cầu về bất kỳ hành vi runtime nào ở phía khách hoặc máy chủ. Thay vào đó, các kiểu sẽ được tổng hợp thành các tệp CSS được gửi kèm như một phần của HTML cho trang web.

Tuy nhiên, giải pháp này khác biệt hoàn toàn so với giải pháp CSS-in-JS mà chúng tôi đang sử dụng vào thời điểm đó. Thay đổi này đòi hỏi phải cập nhật mọi thành phần Primer và mọi thành phần tại GitHub được viết bằng kỹ thuật này. Rất may, các hệ thống thiết kế là phương tiện hoàn hảo để thực hiện loại thay đổi này trên quy mô lớn.

### Hành trình dần chuyển sang CSS Modules

Tình hình chuyển đổi sang CSS Modules đã rất rõ ràng. Đội ngũ Primer cần thực hiện cập nhật cho từng thành phần, chuyển chúng từ CSS-in-JS sang CSS Modules. Đồng thời, các bản cập nhật mà chúng tôi thực hiện cho các thành phần này không được làm gián đoạn bất kỳ cách sử dụng nào trên GitHub. Cuối cùng, kỹ thuật nền tảng mà chúng tôi đã sử dụng cho CSS-in-JS cũng phải tiếp tục hoạt động cho bất kỳ thành phần nào trên GitHub đang sử dụng nó.

Với tất cả những ràng buộc này, chúng tôi đã quyết định áp dụng chiến lược chuyển đổi dần dần để có thể triển khai các bản cập nhật thành phần một cách an toàn mà không gây ảnh hưởng đến hệ thống. Đối với mỗi thành phần, kế hoạch của chúng tôi là:

- Thêm một tệp mới để chuyển đổi các kiểu hiện có sang CSS Modules
- Thêm thành phần đó vào một cờ tính năng (feature flag) để chuyển đổi giữa kiểu mới và kiểu cũ
- Sử dụng các bài kiểm tra hồi quy hình ảnh (visual regression tests) hiện có để xác minh rằng các bản chụp (snapshots) là giống hệt nhau giữa giải pháp CSS-in-JS và CSS Modules
- Dần dần triển khai cờ tính năng cho đội ngũ của chúng tôi, sau đó đến nhân viên GitHub, và cuối cùng là tất cả người dùng GitHub để phát hiện bất kỳ vấn đề nào trong quá trình thực hiện

Quy trình này tạo ra một vòng lặp phản hồi mạnh mẽ, nơi các vấn đề được gắn cờ sớm trong quá trình khi Primer liên tục chuyển giao các thay đổi này cho GitHub. Việc sử dụng cờ tính năng cho phép chúng tôi thực hiện chuyển đổi này một cách an toàn, đồng thời cung cấp các tín hiệu rõ ràng về lợi ích hiệu năng của CSS Modules.

Đến tháng 12 năm 2024, tất cả các thành phần trong Primer đã được chuyển đổi sang CSS Modules bằng quy trình này. Chúng tôi đã thấy hiệu năng được cải thiện trên diện rộng, cụ thể là:

- Giảm 55% thời gian kết xuất trang phía máy chủ
- Giảm 25% thời gian khởi tạo các thành phần trên một trang

Với những cải thiện hiệu năng rõ ràng từ công việc này trong Primer, chúng tôi bắt đầu tự hỏi liệu có thể đạt được kết quả tương tự bằng cách thực hiện chuyển đổi này ở các phần khác của GitHub hay không. Tương tự, bao lâu nữa chúng ta mới có thể chấm dứt hoàn toàn việc hỗ trợ CSS-in-JS trên toàn công ty?

### Loại bỏ CSS-in-JS tại GitHub

Một trong những phần khó khăn nhất khi loại bỏ giải pháp CSS-in-JS khỏi Primer là do việc sử dụng thuộc tính sx. Thuộc tính này là cách để tạo kiểu và tùy chỉnh các thành phần từ Primer. Các đội ngũ có thể cung cấp một đối tượng nội dòng (inline object) để tùy chỉnh mọi thứ về thành phần. Nó đại diện cho cả điểm tốt nhất và tệ nhất của CSS-in-JS:

- Hỗ trợ TypeScript tuyệt vời với khả năng tích hợp Design Tokens của chúng tôi
- Đặt cùng vị trí với thành phần để mọi thứ nằm ở một nơi
- Chi phí runtime cao do tính chất động của các đối tượng nội dòng được sử dụng cho sx
- Khó khăn trong việc mở rộng khi số lượng thành phần sử dụng sx trên một trang tăng lên

Kết quả là, phần đầu tiên trong hành trình rời bỏ CSS-in-JS của chúng tôi là giảm việc sử dụng sx trên toàn GitHub. Điều này cho phép chúng tôi cải thiện hiệu năng ngay lập tức tương tự như những gì đã thấy khi chuyển đổi các thành phần Primer. Nó cũng tạo tiền đề hoàn hảo để chúng tôi loại bỏ hoàn toàn CSS-in-JS khỏi sản phẩm.

### Tính hai mặt của Primer

Cần lưu ý rằng, trong khi bản thân hệ thống thiết kế đã chính thức loại bỏ styled-components, thì một phần lớn cơ sở mã của GitHub vẫn chưa làm được điều đó. Với việc các thuộc tính sx đã trở thành tiêu chuẩn tạo kiểu thực tế tại GitHub trong nhiều năm, chúng tôi đang đối mặt với hàng nghìn thuộc tính sx cần được chuyển đổi trước khi có thể nghĩ đến việc đưa GitHub lên phiên bản @primer/react mới mượt mà hơn mà không phụ thuộc vào styled-components.

Vậy… làm thế nào chúng tôi thực hiện khối lượng công việc khổng lồ này trong khi vẫn tăng sự tự tin và giảm thiểu rủi ro? Câu trả lời là: không làm tất cả cùng một lúc.

Quá trình chuyển đổi CSS ban đầu có sự tinh tế hơn một chút so với những gì chúng tôi đã đề cập: ngoài việc chuyển đổi các thành phần sang CSS modules, sử dụng cờ tính năng để kiểm thử trong môi trường thực tế và triển khai dần dần, chúng tôi còn tạo ra các thành phần "bao bọc" (wrapper) trong một thư viện trung gian mà chúng tôi gọi là [@primer/styled-react](https://github.com/primer/react/blob/main/packages/styled-react/README.md). Mục đích duy nhất của gói này là cho phép sử dụng sx trong các thành phần mới được chuyển đổi. Bằng cách này, các phần của cơ sở mã giao diện GitHub đang sử dụng thuộc tính này có thể tiếp tục sử dụng chúng bằng cách nhập cùng một thành phần thông qua @primer/styled-react, trong khi chúng tôi vẫn đạt được hiệu năng tối ưu khi nhập trực tiếp từ @primer/react cho các trường hợp còn lại.

### Styled Box Zero

Giai đoạn tiếp theo của quy trình chuyển đổi như sau:

- Trên cơ sở từng gói:
- – Chuyển đổi tất cả việc sử dụng sx sang các tệp CSS modules tương đương. Điều này bao gồm cả việc tham chiếu chéo (Xem [chuyển đổi sang biến CSS](https://primer.style/product/primitives/migrating/))
- – Thay thế các lệnh nhập @primer/styled-react bằng @primer/react
- – Kiểm thử trong môi trường tiền sản xuất
- – Triển khai

Thật thú vị, trong khi chúng tôi đang chuẩn bị thực hiện nỗ lực to lớn này, [chế độ bảo trì](https://opencollective.com/styled-components/updates/thank-you) của styled-components đã được công bố, như một sự xác nhận thêm rằng chúng tôi đang đi đúng hướng.

Công việc bắt đầu từ tháng 4 năm 2025 với đỉnh điểm là khoảng 7.760 sxprops cần được di chuyển; chúng tôi phải đợi đến tháng 5 năm 2026 mới hoàn thành. Ban đầu, một trong những lập trình viên nội bộ xuất sắc của chúng tôi, [Ian Sanders,](https://github.com/iansan5653) đã tạo ra một [VS Code plugin](https://marketplace.visualstudio.com/items?itemName=ian-sanders.sx-to-css) để hỗ trợ việc di chuyển từng thuộc tính. Một codemod tương tự cũng được phát triển nội bộ và sử dụng để di chuyển toàn bộ tệp trong cơ sở mã nguồn của GitHub. Công việc này, dù đòi hỏi một chút giám sát thủ công và kiểm chứng cẩn thận, phần lớn đã được tự động hóa. Một nhóm luân phiên gồm 8 kỹ sư đã di chuyển 6.419 thuộc tính trong vòng 6 tháng, ghi nhận hiệu suất thời gian Server-Side Rendering tăng từ 1% lên đến 22% ở một số trang.

![Table titled “Server Side Rendering” with a search field and columns for CATALOG_SERVICE, CONTROLLER, and IMPROVEMENT. It lists GitHub services and controllers with improvement percentages ranging fro](https://github.blog/wp-content/uploads/2026/09/625328348-91f668f6-2565-492d-aa76-632d429fb4ba.png?resize=1024%2C966)

Ở một khía cạnh khác của GitHub, khả năng của Copilot đang tăng theo cấp số nhân. AI ngày càng thông minh và mạnh mẽ hơn; chúng tôi đã ra mắt Copilot coding agent và Copilot code review trong khi công việc này vẫn đang được tiến hành.

Đến khi chúng tôi quay lại với công việc này vào tháng 4 năm 2026, bức tranh toàn cảnh đã khác; chúng tôi đã có thể giảm từ 895 xuống còn 0 sxprops chỉ trong vòng ba tuần với một đội ngũ gồm hai kỹ sư, sự quyết tâm không ngừng nghỉ và rất nhiều Copilot coding agent.

![Area chart titled “Total SX props” showing values declining from about 7,300 in May to near zero by June–July of the following year, with several short-lived spikes. Two highlighted points are labeled](https://github.blog/wp-content/uploads/2026/09/623314819-82999b6e-c79e-4163-8ec5-a4a36e439c6c.png?resize=1024%2C232)

### Cuộc chiến của các chủ đề

Đó là một ngày trọng đại: chúng tôi cuối cùng đã hoàn thành việc di chuyển sx vốn là rào cản ngăn chúng tôi loại bỏ hoàn toàn styled-components, một quá trình kéo dài nhiều năm… chúng tôi cuối cùng có thể dọn dẹp các phụ thuộc này và chuyển sang những công việc khác thú vị hơn, phải không? Sai lầm!

GitHub hỗ trợ [bảy chủ đề khác nhau,](https://docs.github.com/en/get-started/accessibility/managing-your-theme-settings) tất cả đều cung cấp biến thể chế độ độ tương phản cao. Tất cả đều được kích hoạt thông qua, bạn đoán đúng rồi đấy, styled-components. Trước khi có thể nghĩ đến việc loại bỏ các phụ thuộc này, chúng tôi cần tách rời hệ thống chủ đề của mình.

_Bài gốc còn tiếp._ Xem tiếp tại: <https://github.blog/engineering/architecture-optimization/improving-site-performance-by-shipping-more-css>
