Khi WordPress 6.7 chính thức ra mắt, hàng loạt quản trị viên và kỹ sư frontend đã phát hiện hiện tượng bất thường: mã nguồn HTML xuất hiện đoạn CSS nội dòng lạ trong thẻ head. Cụ thể, bộ chọn img:is([sizes=”auto” i], [sizes^=”auto,” i]) đi kèm thuộc tính contain-intrinsic-size: 3000px 1500px được tự động chèn vào trang web mà không qua cài đặt của người dùng, tạo nên làn sóng tranh luận lớn.

Đoạn mã này không phải mã độc hay do plugin, mà là tính năng cốt lõi hỗ trợ chuẩn ảnh tải chậm. Tuy nhiên, việc ép giá trị kích thước 3000px 1500px dẫn đến thảm họa: hình ảnh bị méo mó, khung hình kéo giãn bất thường và điểm số Core Web Vitals lao dốc do chỉ số dịch chuyển bố cục (CLS) tăng vọt. Trong bài viết này, Cypher sẽ cùng bạn mổ xẻ bản chất của lỗi WordPress 6.7, phân tích nguồn gốc contain-intrinsic-size và cung cấp 3 giải pháp xử lý triệt để.

1. Bản chất sự cố: Đoạn mã CSS contain-intrinsic-size từ đâu xuất hiện trên WordPress 6.7?

Để hiểu rõ căn nguyên vấn đề, chúng ta cần truy cập thông báo phát hành chính thức trên WordPress Core Make Blog để xem xét các cải tiến liên quan đến xử lý media. Trong phiên bản này, đội ngũ phát triển nhân lõi muốn đón đầu đặc tả kỹ thuật web mới nhất về hình ảnh tự động co giãn bằng cách tích hợp sâu thuộc tính contain-intrinsic-size vào mã nguồn.

Khi kiểm tra mã nguồn trang web (View Page Source) để tìm mã contain-intrinsic-size trên bản mới, bạn sẽ dễ dàng bắt gặp một khối thẻ style nội dòng được hệ thống tự động sinh ra trong phần header:

/* Doan ma CSS duoc WordPress 6.7 tu dong chen vao wp_head */
img:is([sizes="auto" i], [sizes^="auto," i]) {
    contain-intrinsic-size: 3000px 1500px;
}

Khi đưa quy tắc contain-intrinsic-size vào nhân, mục tiêu ban đầu của các kỹ sư là giải quyết bài toán của kỹ thuật bách khoa toàn thư Wikipedia về thiết kế web tương thích Responsive Web Design: làm thế nào để trình duyệt biết được kích thước tương đối của một bức ảnh khi nó đang ở trạng thái tải chậm (Lazy Loading) nhằm chuẩn bị sẵn không gian hiển thị trước khi tệp ảnh thực tế được tải về qua mạng.

Thế nhưng, ý định tối ưu hóa tốt đẹp này lại trở thành một lỗi WordPress 6.7 nghiêm trọng do cách triển khai thiếu linh hoạt. Việc ép buộc thuộc tính contain-intrinsic-size nhận giá trị chiều rộng 3000px và chiều cao 1500px đã vô tình áp đặt một tỷ lệ khung hình giả định 2:1 lên toàn bộ các hình ảnh có thuộc tính tải chậm, gây ra hàng loạt lỗi hiển thị tai hại trên môi trường sản xuất.

2. Phân tích kỹ thuật: Thuộc tính sizes auto trong chuẩn WHATWG và cơ chế wp_calculate_image_sizes

Để đánh giá vì sao contain-intrinsic-size xuất hiện, chúng ta phải đối chiếu với các quy chuẩn mạng quốc tế. Theo đặc tả kỹ thuật hình ảnh HTML Living Standard của WHATWG, thuộc tính sizes=”auto” cho phép các nhà phát triển thông báo với trình duyệt rằng: “Hãy tự động tính toán kích thước chiều rộng hiển thị của phần tử hình ảnh này dựa trên bố cục thực tế của trang web thay vì phải khai báo cứng một danh sách media queries dài dòng.”

Cơ chế tự động can thiệp của hàm wp_calculate_image_sizes

Liên quan mật thiết đến cơ chế sinh contain-intrinsic-size, trong mã nguồn tại kho mã nguồn WordPress chính thức trên GitHub, hàm cốt lõi wp_calculate_image_sizes đã được bổ sung một logic tự động mới. Khi hệ điều hành phân tích nội dung bài viết, nếu một thẻ img có thuộc tính loading=”lazy”, WordPress 6.7 sẽ tự động gắn thêm giá trị auto vào đầu thuộc tính sizes (chẳng hạn biến thành sizes=”auto, (max-width: 800px) 100vw, 800px”).

Đi kèm với việc thêm thuộc tính sizes auto, WordPress cần một cơ chế để ngăn chặn hiện tượng giật cục bố cục khi trình duyệt chưa nạp xong ảnh. Và giải pháp mà đội ngũ Core lựa chọn chính là chèn đoạn mã CSS sử dụng thuộc tính contain-intrinsic-size để tạo ra một kích thước giữ chỗ tự nhiên (Placeholder Size).

Hàm wp_img_tag_add_auto_sizes() trong luồng xử lý nội dung

Tiến trình này được điều khiển bởi một bộ lọc nội dung mới mang tên wp_img_tag_add_auto_sizes(). Hàm này quét qua toàn bộ thẻ hình ảnh bên trong nội dung bài viết (the_content), trích xuất tệp ảnh đính kèm và tự động bổ sung thuộc tính sizes auto vào thẻ HTML trước khi xuất ra trình duyệt. Đây chính là mắt xích kích hoạt quy tắc CSS contain-intrinsic-size hoạt động trên giao diện người dùng.

3. Giải phẫu thuộc tính CSS contain-intrinsic-size và con số giả định 3000px 1500px

Để hiểu vì sao đoạn mã lại gây họa, chúng ta cần tìm hiểu bản chất của thuộc tính contain-intrinsic-size trong cấu trúc CSS hiện đại theo chuẩn W3C.

Theo tài liệu thuộc tính contain-intrinsic-size trên MDN Web Docs, thuộc tính này quy định kích thước tự nhiên giả định của một phần tử khi phần tử đó đang được áp dụng cơ chế cô lập kích thước (Size Containment, chẳng hạn khi dùng contain: size hoặc content-visibility: auto). Nó giúp trình duyệt xác định được phần tử đó sẽ chiếm khoảng bao nhiêu diện tích trên màn hình mà không cần phải chờ đợi dữ liệu con bên trong được tải xong hoàn toàn.

Nghịch lý từ con số cố định 3000px 1500px

Tại sao giá trị của contain-intrinsic-size lại là con số 3000px 1500px? Trong các cuộc thảo luận kỹ thuật trên diễn đàn phát triển, đội ngũ Core giải thích rằng họ muốn cung cấp một tỷ lệ khung hình mặc định là 2:1 (chiều rộng gấp đôi chiều cao) với kích thước đủ lớn để bao quát hầu hết các kích cỡ màn hình hiện đại. Ý đồ là trình duyệt sẽ sử dụng tỷ lệ này làm tham chiếu trước khi ảnh tải xong.

Thế nhưng, trong thế giới thực của công việc tối ưu hình ảnh WordPress, hình ảnh hiển thị trên trang web có muôn hình vạn trạng: ảnh chân dung khổ dọc (tỷ lệ 3:4 hoặc 9:16), ảnh đại diện vuông vắn (tỷ lệ 1:1), biểu trưng logo dài ngoằng, hay các biểu tượng icon nhỏ gọn chỉ vài chục pixel. Khi tất cả các định dạng đa dạng đó đều bị ép chung một quy tắc contain-intrinsic-size: 3000px 1500px, hàng loạt xung đột không gian hiển thị bắt đầu bùng nổ.

4. Những hệ lụy nghiêm trọng: Vỡ layout, biến dạng hình ảnh và tụt điểm Core Web Vitals

Hậu quả thực tế mà đoạn mã contain-intrinsic-size gây ra trên các website đang hoạt động không dừng lại ở mức độ cảnh báo lý thuyết, mà trực tiếp phá vỡ giao diện người dùng theo nhiều cách khác nhau.

Hình ảnh bị kéo giãn méo mó và phình to bất thường

Trên nhiều giao diện sử dụng các khung chứa linh hoạt (Flexbox hoặc CSS Grid) nhưng không khai báo tường minh thuộc tính height: auto hoặc aspect-ratio, trình duyệt sẽ sử dụng trực tiếp giá trị của contain-intrinsic-size làm kích thước tính toán ban đầu. Kết quả là những bức ảnh vuông hoặc ảnh dọc bỗng nhiên bị kéo bè sang hai bên, hoặc các biểu tượng icon nhỏ xíu bị phóng to khổng lồ chiếm trọn màn hình trước khi kịp thu nhỏ lại khi ảnh tải xong.

Gia tăng chỉ số Cumulative Layout Shift (CLS)

Mục tiêu ban đầu của tính năng là chống giật khung hình, nhưng trong thực tế nó lại phản tác dụng hoàn toàn. Khi người dùng cuộn trang tới vị trí có ảnh tải chậm, trình duyệt ban đầu dành sẵn một khoảng không gian theo tỷ lệ của contain-intrinsic-size (3000px x 1500px). Ngay sau khi bức ảnh thực tế (chẳng hạn ảnh dọc 600px x 800px) được tải xong, khoảng không gian đó đột ngột co lại, đẩy toàn bộ nội dung văn bản bên dưới nhảy lên phía trên.

Tác dụng phụ từ contain-intrinsic-size khiến chỉ số Cumulative Layout Shift (CLS) tăng vọt, phá hỏng trải nghiệm đọc của khách hàng và khiến điểm số hiệu năng lao dốc không phanh khi bạn tiến hành kiểm tra và tối ưu chỉ số tốc độ trên Google PageSpeed.

Xung đột với các trình dựng trang (Page Builders) và Slider

Hầu hết các công cụ dựng trang phổ biến như Elementor, Divi, WPBakery hay các plugin trình chiếu ảnh (Slider Revolution, Swiper) đều tự quản lý việc tính toán kích thước khung hình bằng mã JavaScript riêng biệt. Sự can thiệp đột ngột của quy tắc CSS contain-intrinsic-size từ WordPress 6.7 đã gây ra xung đột trực tiếp với các kịch bản tính toán này, khiến các slider bị đứng hình, các cột lưới hiển thị lệch hàng và khoảng cách trắng xuất hiện dày đặc.

5. Hướng dẫn 3 phương pháp xử lý triệt để lỗi contain-intrinsic-size

Trước những phản hồi gay gắt từ cộng đồng phát triển, các chuyên gia WordPress đã đúc kết được 3 phương pháp giải quyết tối ưu nhất. Tùy thuộc vào hạ tầng kỹ thuật và mức độ tùy biến của trang web, bạn có thể lựa chọn giải pháp phù hợp nhất dưới đây.

Phương pháp 1 (Khuyên dùng): Tắt tính năng tự động thêm sizes auto qua Filter Hook

Để triệt tiêu lỗi contain-intrinsic-size, đây là giải pháp triệt để và sạch sẽ nhất về mặt kiến trúc. Thay vì để hệ thống tự động chèn thuộc tính sizes auto vào thẻ img rồi phải vất vả đi dọn dẹp mã CSS phát sinh, chúng ta sẽ can thiệp trực tiếp vào bộ lọc của WordPress để tắt hoàn toàn tính năng này từ gốc rễ.

Để loại bỏ quy tắc contain-intrinsic-size, bạn chỉ cần mở tệp functions.php trong thư mục giao diện con của mình theo đúng chuẩn hướng dẫn tại bài viết tạo child theme WordPress tùy biến và bổ sung đoạn mã ngắn gọn sau:

// Vo hieu hoa tinh nang tu dong them sizes="auto" trong WordPress 6.7
add_filter('wp_img_tag_add_auto_sizes', '__return_false');

Khi hàm wp_img_tag_add_auto_sizes() trả về giá trị false, WordPress sẽ ngừng gắn thêm giá trị auto vào thuộc tính sizes của các thẻ hình ảnh. Đồng thời, hàm wp_calculate_image_sizes sẽ quay trở lại hoạt động theo cơ chế tính toán truyền thống ổn định, và đoạn mã CSS contain-intrinsic-size sẽ tự động biến mất hoàn toàn khỏi phần header của trang web.

Phương pháp 2: Gỡ bỏ đoạn mã inline style tự sinh trong wp_head

Nếu muốn giữ thuộc tính sizes auto nhưng cần gỡ bỏ contain-intrinsic-size, nhưng chỉ muốn loại bỏ đoạn mã định kiểu CSS có hại, bạn có thể ngắt kết nối hàm in mã CSS ra đầu trang. Tương tự như cách chúng ta loại bỏ các đoạn mã kiểu dáng thừa trong WordPress, hãy thêm đoạn mã sau vào functions.php:

// Go bo doan ma inline style chua contain-intrinsic-size khoi wp_head
add_action('wp_enqueue_scripts', 'cypher_remove_auto_sizes_inline_css', 100);

function cypher_remove_auto_sizes_inline_css() {
    wp_dequeue_style('wp-img-auto-sizes');
    wp_deregister_style('wp-img-auto-sizes');
}

Phương pháp này cho phép thuộc tính sizes=”auto” vẫn hiện diện trên DOM để các trình duyệt hỗ trợ tự động tính toán kích thước hiển thị, trong khi đoạn mã ép buộc contain-intrinsic-size: 3000px 1500px bị loại bỏ hoàn toàn, trả lại sự tự do định kiểu cho tệp CSS chính của theme.

Phương pháp 3: Ghi đè thuộc tính bằng CSS tùy biến an toàn

Trong trường hợp bạn không có quyền truy cập để can thiệp vào tệp mã nguồn PHP hoặc đang sử dụng một nền tảng quản trị bị giới hạn, bạn có thể áp dụng giải pháp trung hòa bằng chính CSS. Hãy thêm đoạn mã sau vào phần Tùy biến CSS (Customizer CSS) hoặc tệp style.css của Child Theme:

/* Ghi de dua thuoc tinh contain-intrinsic-size ve trang thai an toan */
img:is([sizes="auto" i], [sizes^="auto," i]) {
    contain-intrinsic-size: unset !important;
}

Bằng cách đưa contain-intrinsic-size về giá trị unset đi kèm chỉ thị !important, chúng ta đã hủy bỏ hoàn toàn giá trị giả định 3000px 1500px, ép trình duyệt phải quay về sử dụng kích thước nội tại thực tế của hình ảnh mà không gây biến dạng khung hình.

6. Hướng dẫn kiểm tra và debug hình ảnh trên Chrome DevTools sau khi vá lỗi

Sau khi xử lý contain-intrinsic-size, công đoạn kiểm chứng thực tế là bắt buộc để đảm bảo sự cố đã được triệt tiêu hoàn toàn.

Kiểm tra thẻ style trong phần tử DOM

Hãy mở trang web của bạn trên cửa sổ ẩn danh của trình duyệt Google Chrome hoặc Mozilla Firefox, bấm phím F12 để mở bảng điều khiển nhà phát triển (Chrome DevTools). Chuyển sang tab Elements và mở thẻ <head>. Hãy bấm tổ hợp phím Ctrl + F và tìm kiếm từ khóa contain-intrinsic-size.

Nếu bạn áp dụng Phương pháp 1 hoặc Phương pháp 2, kết quả tìm kiếm sẽ trả về 0 kết quả, khẳng định đoạn mã CSS nội dòng độc hại đã được loại bỏ thành công khỏi mã nguồn.

Mô phỏng mạng chậm để phát hiện hiện tượng nhảy layout

Để đảm bảo tác động xấu từ contain-intrinsic-size đã hết, hãy kiểm tra bố cục trang: hãy chuyển sang tab Network trong DevTools, tại mục Throttling hãy chọn cấu hình Fast 3G hoặc Slow 3G. Sau đó, tiến hành làm mới trang (Reload) và cuộn trang dọc từ trên xuống dưới.

Quan sát kỹ các vị trí có ảnh tải chậm: nếu các khung hình không còn bị phình to rồi giật cục co lại khi tệp ảnh nạp xong, hệ thống của bạn đã phục hồi trạng thái hiển thị mượt mà nguyên bản. Nếu bạn đang quản lý số lượng media đồ sộ, hãy kết hợp thêm giải pháp tối ưu hình ảnh WordPress qua file server để giảm tải băng thông lưu trữ cho máy chủ.

7. Bài học kinh nghiệm cho DevOps và lập trình viên khi nâng cấp các bản phát hành WordPress lớn

Sự cố liên quan đến contain-intrinsic-size trên bản cập nhật này để lại nhiều bài học đắt giá cho bất kỳ ai làm nghề quản trị website và kỹ sư vận hành hệ thống.

Tuyệt đối không cập nhật phiên bản lớn (Major Release) ngay ngày đầu tiên

Sự cố contain-intrinsic-size nhắc nhở một nguyên tắc sống còn: không nâng cấp bản lớn một bản phát hành lớn (như từ 6.6 lên 6.7) trực tiếp trên máy chủ sản xuất (Production Server) ngay trong tuần đầu tiên ra mắt. Các tính năng mới luôn tiềm ẩn lỗi phát sinh chưa lường trước hết trên hàng triệu cấu hình giao diện khác nhau.

Hãy duy trì một môi trường thử nghiệm (Staging Environment) có dữ liệu tương đồng, thực hiện nâng cấp thử nghiệm trên đó trước, chạy qua toàn bộ quy trình kiểm thử giao diện và kiểm tra bảng điều khiển lỗi (Console Log) trước khi đưa ra quyết định nâng cấp chính thức.

Cảnh giác với các tính năng tự động can thiệp vào tầng hiển thị Frontend

Xu hướng đưa các tính năng tối ưu hóa tự động vào nhân Core là điều đáng hoan nghênh, nhưng nó cũng mang lại rủi ro phá vỡ tính tương thích ngược (Backward Compatibility). Các kỹ sư cần chủ động theo dõi các hàm can thiệp như wp_calculate_image_sizes để nắm bắt kịp thời các thay đổi trong cách hệ thống biên dịch thẻ HTML ra màn hình.

8. Bảng tổng hợp đối chiếu 3 giải pháp khắc phục sự cố

Để giúp bạn dễ dàng đưa ra quyết định kỹ thuật chính xác cho dự án của mình, Cypher đã tổng hợp bảng đối chiếu chi tiết 3 giải pháp xử lý sự cố contain-intrinsic-size dưới đây:

Tiêu chí so sánhPhương pháp 1: Filter tắt auto sizesPhương pháp 2: Dequeue inline CSSPhương pháp 3: Ghi đè CSS unset
Vị trí can thiệpTệp functions.php của Child ThemeTệp functions.php của Child ThemeCustomizer CSS hoặc style.css
Độ triệt đểCao nhất (Ngăn chặn từ gốc rễ)Rất cao (Xóa sạch mã CSS)Trung bình (Vẫn còn mã dư trong DOM)
Tính an toàn giao diệnTuyệt đối (Quay về cơ chế chuẩn)Tuyệt đối (Bảo toàn layout theme)Tốt (Cần chỉ thị !important)
Giữ lại chuẩn HTML sizes autoKhông (Quay lại sizes truyền thống)Có (Vẫn giữ sizes=”auto” trên thẻ img)Có (Vẫn giữ sizes=”auto” trên thẻ img)
Mức độ phức tạpCực kỳ đơn giản (Chỉ 1 dòng mã)Đơn giản (Một hàm hook nhỏ)Cực kỳ đơn giản (Vài dòng CSS)
Khuyến nghị của CypherLựa chọn tối ưu số 1 cho mọi dự ánDành cho dự án cần giữ sizes=”auto”Giải pháp tạm thời khi không sửa được PHP

Bảng phân tích xử lý contain-intrinsic-size trên khẳng định rằng Phương pháp 1 sử dụng bộ lọc wp_img_tag_add_auto_sizes là con đường ngắn nhất, an toàn nhất và loại bỏ hoàn toàn mọi rủi ro tiềm ẩn cho website của bạn.

9. Tổng kết và lời khuyên từ Cypher

Sự cố xuất hiện đoạn mã contain-intrinsic-size: 3000px 1500px trên WordPress 6.7 là một minh chứng rõ nét cho thấy ranh giới mong manh giữa việc đón đầu công nghệ hiện đại và sự ổn định của hệ thống đang vận hành thực tế. Việc hiểu sâu bản chất kỹ thuật giúp chúng ta không bị bối rối trước những thay đổi đột ngột từ mã nguồn mở.

Lời khuyên thực chiến từ Cypher: Trong công nghệ web, mọi giải pháp tự động hóa áp đặt chung một khuôn mẫu lên toàn bộ nội dung đều tiềm ẩn rủi ro phá vỡ tính đa dạng của thiết kế. Hãy luôn là người làm chủ mã nguồn, kiểm soát chặt chẽ các thẻ được nạp vào phần header và sẵn sàng sử dụng các bộ lọc hook để vô hiệu hóa những tính năng không phù hợp với dự án của mình.

Chỉ với một dòng mã filter, bạn đã có thể dẹp bỏ hoàn toàn lỗi contain-intrinsic-size, bạn đã có thể dẹp bỏ hoàn toàn nỗi lo vỡ giao diện, khôi phục lại sự ổn định cho các khối hình ảnh và bảo toàn điểm số hiệu năng quý giá cho website của mình.

Website của bạn có gặp phải sự cố biến dạng hình ảnh do thuộc tính contain-intrinsic-size sau khi nâng cấp lên phiên bản mới không? Bạn đã lựa chọn phương pháp nào trong 3 cách trên để giải quyết? Hãy chia sẻ trải nghiệm thực tế hoặc để lại thắc mắc ở phần bình luận bên dưới để cùng Cypher và cộng đồng lập trình viên trao đổi thêm nhé!