'league/commonmark ข้ามตัวกรอง XSS — GHSA-f8fg-pg57-v4j8'
'เว็บที่เปิด AttributesExtension ให้เนื้อหาจากผู้ใช้และยังใช้รุ่นที่ได้รับผลกระทบควรเร่งติดตั้งแพตช์'
1-minute summary
- Symptom / problem
- อักขระ form feed ทำให้ชื่อแอตทริบิวต์ผ่านตัวกรองและกลายเป็น JavaScript ที่ทำงานในเบราว์เซอร์ได้
- Who should read
- แอปที่ใช้ league/commonmark รุ่น >=2.7.0,<2.9.1 เปิด AttributesExtension และใช้ attributes.allow ค่าเริ่มต้น []
- Fix in short
- อัปเดตเป็น 2.9.1 หรือใหม่กว่า ระหว่างรอใช้ allow list ที่ระบุชื่อแอตทริบิวต์ที่อนุญาตอย่างชัดเจน
พอดีไล่ฟีด Packagist เจอประกาศของ league/commonmark ไลบรารี PHP สำหรับแปลง Markdown เป็น HTML ที่เว็บแอปนำไปใช้แสดงเนื้อหา ช่องโหว่ GHSA-f8fg-pg57-v4j8 อยู่ใน AttributesExtension ซึ่งเปิดให้กำหนดแอตทริบิวต์ของ HTML ผ่าน Markdown ได้ อักขระ form feed ที่มองไม่เห็นทำให้ชื่อแอตทริบิวต์อันตรายผ่านตัวกรองได้ ผลคือ Stored XSS ในหน้าที่แสดงเนื้อหานั้น
เกิดอะไรขึ้น
ประกาศผู้พัฒนาเผยแพร่วันที่ 9 สิงหาคม 2026 ส่วนรายการใน GitHub Advisory Database เข้าฐานวันที่ 1 กันยายน 2026 เวลา UTC ซึ่งตรงกับ 2 กันยายน 2026 ตามเวลาไทย
ตามปกติส่วนขยายนี้จะกรองแอตทริบิวต์ที่ขึ้นต้นด้วย on เช่น onclick และ onerror เพราะใช้เรียก JavaScript ได้ แต่เมื่อมี U+000C FORM FEED นำหน้าชื่อ ตัว parser ยอมรับอักขระดังกล่าว ขณะที่ trim() ของ PHP ตามค่าเริ่มต้นไม่ได้ตัดมันออก ชื่อที่ส่งไปตรวจเลยไม่ตรงกับคำที่ตัวกรองต้องการบล็อก
เมื่อแปลงเป็น HTML เบราว์เซอร์มอง form feed เป็นช่องว่าง แล้วอ่านชื่อที่เหลือเป็น event handler ได้ ปัญหานี้ยังข้ามการตรวจ href หรือ src ทำให้ javascript: URI ผ่านได้ แม้ตั้ง allow_unsafe_links เป็น false เป็นการข้ามตัวกรองที่เพิ่มไว้ในรุ่น 2.7.0 ตาม ประกาศของผู้พัฒนา
ผลกระทบคือสคริปต์จากเนื้อหาที่ผู้โจมตีฝากไว้ทำงานในบริบทของเว็บ ผู้เปิดอ่านอาจถูกขโมยข้อมูลเซสชันหรือคุกกี้ที่สคริปต์เข้าถึงได้ หรือถูกสั่งทำรายการด้วยสิทธิ์ของตน ขึ้นอยู่กับการป้องกันของแอป กรณี event handler บนรูปภาพอาจทำงานทันทีที่หน้าโหลดโดยไม่ต้องคลิก การตั้ง html_input เป็น escape และปิด unsafe links เลยยังไม่พอสำหรับช่องโหว่นี้
ใครโดนและรุ่นที่แก้
เงื่อนไขที่ประกาศระบุคือแอปรับ Markdown ที่ไม่น่าเชื่อถือ เปิด AttributesExtension และปล่อย attributes.allow เป็นค่าเริ่มต้น [] ค่าว่างตรงนี้ไม่ได้หมายความว่าจะปฏิเสธทุกแอตทริบิวต์ ส่วนแอปที่ใช้แพ็กเกจนี้ควรตรวจการลงทะเบียนส่วนขยายและค่าคอนฟิกจริงก่อนประเมินความเสี่ยง
| แพ็กเกจ | รุ่นที่ได้รับผลกระทบ | รุ่นที่แก้ไข |
|---|---|---|
league/commonmark ผ่าน Composer |
>=2.7.0,<2.9.1 |
2.9.1 |
บันทึกการออกรุ่น 2.9.1 ยืนยันการแก้ช่องโหว่นี้ ส่วน GitHub Advisory Database จัดความรุนแรงเป็น High คะแนน CVSS 3.1 เท่ากับ 7.2 และยังไม่ระบุ CVE ให้ใช้อ้างอิงด้วย GHSA ข้างต้น ช่องโหว่นี้ยังไม่อยู่ใน KEV ฉบับ 4 พฤศจิกายน 2026
ต้องทำอะไร
ตรวจรุ่นที่ติดตั้งและอัปเดต dependency ในสภาพแวดล้อมทดสอบก่อนนำขึ้นใช้งานจริง สำรองไฟล์กำหนด dependency และ lock file เพื่อให้ย้อนกลับได้ ตัวอย่างคำสั่งในโฟลเดอร์โปรเจกต์ที่ใช้ Composer:
composer show league/commonmark
composer update league/commonmark --with-all-dependencies
composer show league/commonmark
ตรวจผลให้ได้ 2.9.1 หรือใหม่กว่า หากข้อกำหนดใน composer.json หรือ dependency อื่นขวางการอัปเดต ต้องแก้ข้อจำกัดนั้นก่อน อย่าถือว่ารันคำสั่งสำเร็จแล้วแปลว่าได้รุ่นที่แก้เสมอ ทดสอบหน้าที่แสดง Markdown รวมถึงลิงก์ รูปภาพ และแอตทริบิวต์ที่แอปใช้งาน แล้วนำ lock file ที่ตรวจแล้วไปใช้ในขั้นตอน deploy ตามปกติ
ประกาศแนะนำให้กำหนด attributes.allow เป็น allow list อย่างชัดเจน เช่น ['id', 'class', 'align'] เพื่อให้ชื่อที่มี form feed ถูกปฏิเสธ เลือกเฉพาะแอตทริบิวต์ที่แอปจำเป็นต้องใช้และทดสอบผลการแสดงเนื้อหาด้วย
ส่วนตัวผมแนะนำให้เร่งแพตช์หากเปิดรับ Markdown จากผู้ใช้พร้อมส่วนขยายนี้ เพราะเนื้อหาที่ถูกเปิดอ่านอาจทำให้สคริปต์ทำงานได้โดยไม่ต้องคลิก ที่มา: GHSA-f8fg-pg57-v4j8 (GitHub Advisory Database) หากมีรายละเอียดจากผู้พัฒนาเพิ่มเติม เดี๋ยวกลับมาแก้เพิ่มให้ภายหลังครับ
Want us to set this up?
Get help with server setup, configuration, migration, or troubleshooting. Save time for the work that matters.
Hit something like this? Stuck somewhere?
Come trade notes on the LinuxThai board



Comments 0
No comments yet — be the first