Các script của plugin WordPress phổ biến bị thay đổi để cài cắm Backdoor ẩn trên các trang web

Kẻ tấn công đã can thiệp vào các tệp JavaScript đáng tin cậy được sử dụng bởi các trang web WordPress chạy PushEngage, OptinMonster và TrustPulse, biến những tệp đó thành phương thức để xâm nhập vào trang web. Khi quản trị viên trang web đăng nhập vào lúc tệp đang tải, mã độc sẽ tạo một tài khoản admin dưới quyền kiểm soát của kẻ tấn công và cài đặt một plugin ẩn để duy trì quyền truy cập. Khách truy cập thông thường sẽ không kích hoạt mã độc này.
WordPress Plugin Security

Một kẻ tấn công đã can thiệp vào các tệp JavaScript đáng tin cậy được sử dụng bởi các trang web WordPress đang chạy PushEngage, OptinMonsterTrustPulse, biến những tệp này thành phương thức để xâm nhập trái phép vào hệ thống.

Khi quản trị viên trang web đăng nhập vào thời điểm tệp được tải, mã độc sẽ tự động tạo một tài khoản admin dưới quyền kiểm soát của kẻ tấn công và cài đặt một plugin ẩn để duy trì con đường truy cập trở lại. Những khách truy cập thông thường sẽ không kích hoạt mã độc này.

Bất kỳ trang web nào bị ảnh hưởng đều nên được coi là đã bị xâm nhập hoàn toàn. Cả ba plugin này đều được vận hành bởi cùng một công ty là Awesome Motive. Tính đến ngày 15 tháng 6, công ty này vẫn chưa đưa ra bình luận nào về hai plugin lớn nhất của mình.

Công ty bảo mật Sansec đã tiết lộ chiến dịch quy mô lớn này vào ngày 13 tháng 6, sau khi phát hiện cùng một đoạn mã độc trong các tệp JavaScript được cung cấp cho cả ba plugin.

PushEngage đã nối gót một ngày sau đó với thông báo sự cố riêng, xác nhận rằng kẻ tấn công đã cung cấp các bản sao script bị can thiệp và các trang web tải chúng có thể bị chiếm quyền điều khiển.

PushEngage, được Awesome Motive mua lại cách đây nhiều năm, cho đến nay là đơn vị duy nhất trong số ba đơn vị đưa ra hướng dẫn; người dùng OptinMonster và TrustPulse vẫn chưa nhận được thông báo chính thức nào.

Khoảng thời gian bị tấn công không giống nhau cho mỗi plugin. Sansec nhận thấy mã độc trong OptinMonster và TrustPulse chỉ xuất hiện trong khoảng 25 phút vào ngày 12 tháng 6, bắt đầu từ khoảng 22:17 UTC và kết thúc lúc 22:42. Thời gian tiếp xúc của PushEngage kéo dài hơn: vài giờ vào ngày 12 tháng 6, và script độc hại vẫn tiếp tục được phân phối từ một số máy chủ CDN cho đến tận ngày 14 tháng 6.

Vì vậy, hai plugin có lượng trang web sử dụng lớn nhất lại có cửa sổ tấn công nhỏ nhất, trong khi PushEngage có cửa sổ lớn nhất.

Sansec ước tính rằng ba plugin này tiếp cận hơn 1,2 triệu trang web, phần lớn là OptinMonster với hơn một triệu lượt cài đặt đang hoạt động. Plugin WordPress của PushEngage có hơn 9.000 lượt. Những con số này thể hiện phạm vi tiếp cận, không phải mức độ thiệt hại: nó tính các trang web chạy plugin, không phải số trang web chắc chắn đã bị xâm nhập.

Cách thức cuộc tấn công diễn ra

Script độc hại không thực hiện bất kỳ hành động nào khi một trang web được xem bình thường. Nó chỉ hoạt động khi một quản trị viên WordPress đã đăng nhập tải nó, sau đó sử dụng phiên làm việc (session) của admin đó để chiếm quyền kiểm soát.

Thiết kế này cũng là lý do tại sao bảng điều khiển WordPress dashboard không thể cho bạn biết liệu bạn có bị tấn công hay không: Backdoor được xây dựng để ẩn khỏi các màn hình quản trị, vì vậy cách kiểm tra đáng tin cậy duy nhất là thực hiện trực tiếp trên máy chủ.

Trong trường hợp của PushEngage, các tệp bị can thiệp là các bản nhúng thông thường, pushengage-web-sdk.js và pushengage-subscription.js, được phân phối từ clientcdn.pushengage.com, mạng phân phối nội dung (CDN) đẩy script của PushEngage đến các trang web khách hàng. OptinMonster và TrustPulse bị tấn công thông qua các điểm cuối CDN riêng biệt của Awesome Motive.

Cơ chế tấn công CDN

PushEngage cho biết các hệ thống còn lại của họ không bị ảnh hưởng: họ không tìm thấy dấu hiệu nào cho thấy ứng dụng chính hoặc các máy chủ lưu trữ dữ liệu khách hàng bị xâm nhập.

Theo tài liệu của PushEngage, một khi script chạy với tư cách quản trị viên đã đăng nhập, nó sẽ:

  • Sử dụng phiên làm việc của admin đó để hành động với đầy đủ quyền hạn.
  • Tạo một tài khoản admin mới dưới quyền kiểm soát của kẻ tấn công.
  • Cài đặt một plugin không hiển thị trong dashboard.
  • Gửi thông tin đăng nhập mới và thông tin trang web đến tidio[.]cc, một tên miền giả mạo được tạo ra để trông giống với trang tidio.com thật.

Sansec đã tìm thấy quy trình tương tự trên cả ba plugin. Tên miền tidio[.]cc đã được đăng ký vào ngày 28 tháng 4, nhiều tuần trước cuộc tấn công, điều này cho thấy đây là một hoạt động có kế hoạch rõ ràng thay vì một vụ tấn công chớp nhoáng.

Plugin ẩn chính là mục tiêu thực sự. Nó mở ra một thứ gọi là web shell, một kênh điều khiển từ xa: bất kỳ ai biết URL chính xác đều có thể chạy mã trên máy chủ mà không cần đăng nhập. Từ đó, kẻ tấn công có thể đọc hoặc thay đổi bất kỳ tệp nào, sao chép cơ sở dữ liệu, cài đặt thêm các Backdoor khác, chèn mã đánh cắp thông tin thẻ (card-skimming), chuyển hướng khách truy cập hoặc đánh cắp dữ liệu.

Tài khoản admin bổ sung là một cách đơn giản để quay lại nếu bạn xóa plugin nhưng bỏ sót tài khoản. Và vì kẻ tấn công có thể chạy mã tự do, việc xóa plugin và tài khoản đã nêu có thể là chưa đủ; cả Sansec và PushEngage đều khuyến cáo nên giả định rằng các Backdoor khác vẫn có thể tồn tại.

Cách kẻ tấn công xâm nhập

Đây là phần mà hai báo cáo có sự mâu thuẫn. PushEngage nói rằng kẻ tấn công ban đầu đã xâm nhập vào máy chủ chạy trang web marketing của họ thông qua một lỗ hổng đã biết trong UpdraftPlus, một plugin sao lưu WordPress. Máy chủ đó tách biệt với các hệ thống vận hành sản phẩm và lưu trữ dữ liệu khách hàng.

Điều quan trọng không phải là bản thân máy chủ mà là một khóa (key) nằm trên đó: một CDN API key. Với khóa đó, kẻ tấn công không cần phải xâm nhập vào hệ thống chính của PushEngage. Chúng có thể đơn giản là thay đổi các tệp mà CDN đang phân phối đến các trang web của khách hàng.

Sansec không thuyết phục rằng điểm xâm nhập đã được xác định rõ ràng. Họ cho rằng hệ thống bị vi phạm vẫn chưa rõ danh tính, trong đó các máy chủ của chính Awesome Motive là nơi có khả năng cao nhất, tài khoản CDN là có thể, và nhà cung cấp CDN BunnyNet là ít khả năng nhất.

Phân tích công khai của Sansec không xem xét hoặc xác nhận giả thuyết về UpdraftPlus; thông tin đó chỉ đến từ phía PushEngage về môi trường của chính họ. UpdraftPlus có một lỗ hổng bỏ qua xác thực riêng biệt, CVE-2026-10795, mà Wordfence xếp hạng 8.1 (mức độ nghiêm trọng cao); hiện nó đã được vá và Wordfence đã báo cáo các cuộc tấn công nhắm vào lỗ hổng này, vì vậy bất kỳ ai đang chạy UpdraftPlus nên cập nhật ngay lập tức.

Liệu lỗ hổng đó có liên quan gì đến vụ xâm nhập này hay không vẫn chưa được xác nhận. Hãy coi điểm xâm nhập hiện vẫn là một ẩn số.

Những điều cần kiểm tra và thực hiện

Theo dòng thời gian của Sansec, các tệp của OptinMonster và TrustPulse đã sạch vào ngày 13 tháng 6, trong khi script của PushEngage vẫn còn tồn tại trên một số máy chủ CDN cho đến ngày 14 tháng 6. PushEngage cho biết họ vẫn đang xác định khung thời gian chính xác và đã thay thế các tệp độc hại, xóa bộ nhớ đệm CDN, thay đổi CDN key cùng tất cả các thông tin xác thực liên quan, đồng thời chuyển trang web marketing sang cơ sở hạ tầng mới.

Tuy nhiên, không có bước nào ở trên có thể làm sạch một trang web đã bị chiếm quyền điều khiển trước đó.

Các chỉ số thỏa hiệp (IoCs) từ Sansec
Các chỉ số thỏa hiệp (IoCs) từ Sansec

Bởi vì Backdoor ẩn mình khỏi bảng điều khiển, bạn không thể loại trừ khả năng bị xâm nhập chỉ bằng cách nhìn vào WordPress. Nếu trang web của bạn đã chạy bất kỳ plugin nào trong số ba plugin này trong khoảng thời gian bị đe dọa, câu trả lời đáng tin cậy duy nhất là quét trực tiếp trên máy chủ.

Đừng cố gắng quyết định dựa trên việc phỏng đoán liệu bạn có đang đăng nhập hay không; hầu hết chủ sở hữu trang web không thể chứng minh điều đó một cách chắc chắn. Hãy thực hiện các bước dưới đây như một tiêu chuẩn tối thiểu:

  1. Chạy quét phía máy chủ (server-side scan): Bất kỳ ai đã kích hoạt PushEngage, OptinMonster hoặc TrustPulse trong khung thời gian trên nên quét máy chủ trực tiếp. Việc kiểm tra qua trình duyệt hoặc dashboard sẽ bỏ lỡ các mã độc vốn chỉ chạy đối với các admin đã đăng nhập.
  2. Kiểm tra hệ thống tệp (filesystem), không phải bảng điều khiển: Trong thư mục wp-content/plugins, hãy tìm các thư mục có tên content-delivery-helper ("Content Delivery Helper") hoặc database-optimizer ("Database Optimizer"). Hãy tin vào những gì có trên ổ đĩa. Xóa mọi tài khoản admin mà bạn không tự tạo, đặc biệt là developer_api1 hoặc bất kỳ tài khoản nào khớp với định dạng dev_xxxxxx.
  3. Kiểm tra nhật ký (logs): Xem lại nhật ký truy cập máy chủ web từ ngày 12 đến 14 tháng 6 UTC để tìm lưu lượng truy cập ra ngoài đến tidio.cc (bao gồm các đường dẫn /cdn-cgi/) và đến máy chủ của kẻ tấn công tại địa chỉ IP 84.201.6.54.
  4. Nếu phát hiện bất cứ điều gì, hãy giả định tình huống xấu nhất: Thay đổi toàn bộ: mật khẩu admin, API keys, thông tin đăng nhập cơ sở dữ liệu và các khóa bí mật (salts) trong tệp wp-config.php. Với khả năng thực thi mã trên máy chủ, các cơ chế duy trì sự hiện diện khác có thể vẫn còn sót lại.