การอัปเดตบางส่วนแบบประกาศ

เผยแพร่: 19 พฤษภาคม 2026, อัปเดตล่าสุด: 8 กันยายน 2026

เว็บได้พัฒนาไปไกลจากสื่อแบบคงที่ที่เน้นเอกสารซึ่งเป็นจุดเริ่มต้น ทุกคนใช้เว็บแอปที่ทันสมัยและมีฟีเจอร์มากมายด้วยเหตุผลหลายประการ ตั้งแต่การสื่อสาร การซื้อ การรับชมข้อมูลอย่างละเอียด ไปจนถึงการจัดการชีวิตที่ซับซ้อน

แม้ว่า HTML จะมีความก้าวหน้ามากมาย แต่ก็ยังคงแสดงผลตามลำดับจากบนลงล่างโดยไม่คำนึงถึงเวลาที่เนื้อหาพร้อมหรือเวลาที่ผู้ใช้บริโภคเนื้อหา CSS ช่วยให้คุณเปลี่ยนลำดับเนื้อหาได้ แต่ก็มักจะส่งผลข้างเคียงต่อการช่วยเหลือพิเศษอย่างมาก JavaScript ช่วยให้คุณจัดการ DOM ผ่าน API ต่างๆ เพื่อหลุดพ้นจากข้อจำกัดนี้ได้ แต่ API เหล่านั้นมักต้องใช้ไวยากรณ์ที่ยาว หรือต้องสร้างแผนผัง DOM เพื่อเสียบเข้ากับ HTML

ประสิทธิภาพมีความสำคัญอย่างยิ่งต่อเว็บ เนื่องจากลักษณะของสื่อที่เป็นแบบไคลเอ็นต์-เซิร์ฟเวอร์ อย่างไรก็ตาม มักมีการเลือกตัวเลือกที่ไม่เหมาะสมเพื่อหลีกเลี่ยงลักษณะการทำงานตามลำดับของ HTML ซึ่งจะทำให้ประสิทธิภาพช้าลง ซึ่งรวมถึงการรอจนกว่าหน้าเว็บทั้งหมดจะพร้อม หรือการใช้เฟรมเวิร์กที่มีขนาดใหญ่เพื่อแสดงคอมโพเนนต์แบบไม่พร้อมกัน ความนิยมของเฟรมเวิร์ก JavaScript แสดงให้เห็นว่านักพัฒนาเว็บชอบโมเดลที่อิงตามคอมโพเนนต์มากกว่าโมเดลเอกสารที่ยืดหยุ่นของต้นกำเนิดของเว็บ

ทีม Chrome ได้พิจารณาปัญหานี้และได้พัฒนาฟีเจอร์ใหม่ๆ เพิ่มเติมในแพลตฟอร์มเว็บภายใต้ชื่อ Declarative Partial Updates

API ชุดใหม่ 2 ชุดแรกช่วยให้ส่ง HTML ได้ง่ายขึ้นในลักษณะที่ไม่เป็นเส้นตรง ไม่ว่าจะเป็นในเอกสาร HTML เองหรือผ่านวิธีที่ง่ายขึ้นในการแทรก HTML ลงในเอกสารที่มีอยู่แบบไดนามิกโดยใช้ JavaScript API ใหม่ นอกจากนี้ยังมี Polyfill ที่ช่วยให้คุณใช้ API ใหม่เหล่านี้ได้ทันที แม้ในเบราว์เซอร์ที่ยังไม่รองรับ

การสตรีมแบบไม่อยู่ในลำดับ

Browser Support

  • Chrome: 150.
  • Edge: 150.
  • Firefox: not supported.
  • Safari: not supported.

Source

การเปลี่ยนแปลงชุดแรกคือ API การสตรีมแบบไม่อยู่ในลำดับใหม่ที่ใช้ตัวยึดตำแหน่งคำสั่งการประมวลผลและองค์ประกอบ HTML <template> ที่มีแอตทริบิวต์ for เช่น

<div>
  <?marker name="placeholder">
</div>

...

<template for="placeholder">
  Here is some <em>HTML content</em>!
</template>

วิธีการประมวลผลมีอยู่ใน XML มาเป็นเวลานานแล้ว แต่ได้รับการถือว่าเป็นความคิดเห็นใน HTML และถูกละเว้น API ใหม่นี้จะเปลี่ยนแปลงการทำงานดังกล่าวและนำวิธีการประมวลผลมาไว้ใน HTML ตัวอย่างเช่น เมื่อเบราว์เซอร์เห็นคำสั่งการประมวลผล <?marker name="placeholder"> เบราว์เซอร์จะไม่ทำอะไรในทันที ซึ่งก็เหมือนกับก่อนหน้านี้ แต่สามารถอ้างอิงได้ในภายหลัง

องค์ประกอบ <template> ที่มีแอตทริบิวต์ for จะค้นหาคำสั่งในการประมวลผลที่เกี่ยวข้องซึ่งมีแอตทริบิวต์ name และแทนที่เนื้อหา ในกรณีนี้ หลังจากแยกวิเคราะห์แล้ว DOM จะมีลักษณะดังนี้ (ไม่สนใจความแตกต่างของช่องว่างบางส่วน)

<div>
  Here is some <em>HTML content</em>!
</div>

นอกจากแอตทริบิวต์ <?marker> สำหรับการแทนที่แล้ว ยังมีเครื่องหมายช่วง <?start> และ <?end> ซึ่งอนุญาตให้แสดงเนื้อหาตัวยึดตำแหน่งชั่วคราวก่อนที่จะประมวลผลเทมเพลต

<div>
  <?start name="another-placeholder">
  Loading…
  <?end>
</div>

...

<template for="another-placeholder">
  Here is some <em>HTML content</em>!
</template>

ในกรณีนี้ Loading…สตริงจะแสดงจนกว่าจะเห็น <template> จากนั้นระบบจะแทนที่ด้วยเนื้อหาใหม่

นอกจากนี้ คุณยังใส่วิธีการประมวลผลในเทมเพลตเพื่อให้ทำการอัปเดตได้หลายรายการได้ด้วย

<ul id="results">
  <?start name="results">
  Loading…
  <?end>
</ul>

...

<template for="results">
  <li>Result One</li>
  <?marker name="results">
</template>

...

<template for="results">
  <li>Result Two</li>
  <?marker name="results">
</template>

...

ซึ่งจะส่งผลให้ได้ HTML ต่อไปนี้หลังจากแยกวิเคราะห์และประมวลผลแล้ว

<ul id="results">
  <li>Result One</li>
  <li>Result Two</li>
  <?marker name="results">
</ul>

โดยมีคำสั่งการประมวลผลสุดท้ายที่ส่วนท้าย ในกรณีที่มีการเพิ่ม<template for="results">ตัวยึดตำแหน่งลงในเอกสารในภายหลัง

เหตุใดจึงใช้คำสั่งในการประมวลผลแทนองค์ประกอบ HTML มาตรฐาน

นี่เป็นคำถามที่พบบ่อยสำหรับผู้ที่ใช้ API นี้เป็นครั้งแรก โดยมีคำแนะนำให้ใช้องค์ประกอบ <slot> หรือแม้แต่ <template> เอง ข้อเสนอเวอร์ชันเริ่มต้นนี้ทำงานร่วมกับองค์ประกอบ HTML มาตรฐาน แต่มีการเปลี่ยนวิธีการประมวลผลเมื่อมีการออกแบบซ้ำ วิธีการประมวลผลช่วยให้การแก้ไขเกิดขึ้นได้โดยไม่ส่งผลกระทบต่อ DOM ซึ่งจะช่วยให้ใช้ใน <head> ได้ เช่น สำหรับการอัปเดต <title> หรือแม้แต่ภายในองค์ประกอบอื่นๆ เช่น <table> (เช่น เพื่อเพิ่มแถวเพิ่มเติมที่ไม่บังคับ)

แม้ว่าไวยากรณ์จะไม่คุ้นเคยสำหรับนักพัฒนาเว็บหลายๆ คน แต่คำสั่งการประมวลผลก็มีความยืดหยุ่นมากกว่ามากและมีโอกาสเกิดปัญหาความเข้ากันได้แบบย้อนหลังน้อยกว่า ซึ่งใช้ใน XML อยู่แล้ว และตอนนี้เป็นส่วนหนึ่งของมาตรฐาน HTML ด้วยข้อเสนอนี้

สาธิต

ในวิดีโอนี้ เราจะติดตั้งใช้งานแอปพลิเคชันอัลบั้มรูปภาพพื้นฐานด้วย HTML แบบสตรีมมิง

การสาธิตอัลบั้มรูปภาพที่ใช้การสตรีมแบบไม่อิงตามลำดับ (แหล่งที่มา)

ทั้งสถานะและรูปภาพจะสตรีมลงใน HTML หลังจากเลย์เอาต์เริ่มต้น

กรณีการใช้งาน

มีกรณีการใช้งานมากมายสำหรับการแก้ไข HTML ที่ไม่อยู่ในลำดับนี้เมื่อใช้ร่วมกับ HTML การสตรีม

  • สถาปัตยกรรมแบบไอส์แลนด์ รูปแบบทั่วไปที่ได้รับความนิยมจากเฟรมเวิร์กอย่าง Astro คือสถาปัตยกรรมแบบไอส์แลนด์ ซึ่งคอมโพเนนต์จะได้รับการไฮเดรตอย่างอิสระบน HTML แบบคงที่ <template for> API ช่วยให้จัดการเนื้อหาแบบคงที่ในลักษณะที่คล้ายกันได้โดยตรงใน HTML เฟรมเวิร์ก JavaScript ยังใช้สิ่งนี้เพื่อสร้างไอส์แลนด์แบบอินเทอร์แอกทีฟมากขึ้นหรือเพื่อจัดการคอมโพเนนต์ได้ด้วย
  • ส่งเนื้อหาเมื่อพร้อม สถาปัตยกรรมแบบไอส์แลนด์นี้ช่วยให้สตรีมเนื้อหาได้เมื่อพร้อม แทนที่จะต้องรอเนื้อหาที่ต้องมีการประมวลผลเพิ่มเติม เช่น การค้นหาฐานข้อมูล แม้ว่าหลายแพลตฟอร์มจะอนุญาตให้สตรีม HTML แต่ลักษณะการทำงานตามลำดับของ HTML หมายความว่าเนื้อหามักจะถูกหน่วงไว้ หรือต้องใช้การจัดการ DOM ของ JavaScript ที่ซับซ้อน ตอนนี้คุณสามารถแสดงเนื้อหาแบบคงที่ขณะรอ แล้วเสียบเนื้อหาแบบไดนามิกที่มีราคาแพงกว่าที่ส่วนท้ายของสตรีม HTML
  • ส่ง HTML ในลำดับที่เหมาะสมเพื่อประสิทธิภาพการโหลดหน้าเว็บ และคุณยังเปลี่ยนลำดับได้แม้ว่าคำสั่งซื้อจะพร้อมจัดส่งแล้วก็ตาม ตัวอย่างเช่น เมกะเมนูเป็นฟีเจอร์การนำทางทั่วไปที่มี HTML จำนวนมากซึ่งผู้ใช้จะไม่เห็นจนกว่าหน้าเว็บจะโต้ตอบได้ สามารถส่ง HTML ขนาดใหญ่นี้ในภายหลังในเอกสาร HTML เพื่อจัดลําดับความสําคัญของ HTML ที่สําคัญกว่าซึ่งจําเป็นสําหรับการโหลดหน้าเว็บครั้งแรก HTML ทำให้ลำดับไม่ใช่ข้อจำกัดอีกต่อไป

นี่เป็นเพียง Use Case บางส่วน และเราตื่นเต้นที่จะได้เห็นสิ่งที่นักพัฒนาแอปใช้ API ใหม่นี้

ข้อจำกัดและความซับซ้อน

API มีข้อจำกัดและรายละเอียดบางอย่างที่ควรทราบ ดังนี้

  • <template for> อัปเดตวิธีการประมวลผลได้เฉพาะภายในองค์ประกอบระดับบนสุดเดียวกันเท่านั้นด้วยเหตุผลด้านความปลอดภัย การเพิ่ม <template for> ลงในองค์ประกอบ <body> โดยตรงจะทำให้องค์ประกอบดังกล่าวเข้าถึงทั้งเอกสาร (รวมถึง <head>) ได้
  • <?end> คำสั่งการประมวลผลเป็นตัวเลือก และหากไม่มี ระบบจะแทนที่เนื้อหาระหว่างองค์ประกอบ <?start> กับจุดสิ้นสุดขององค์ประกอบที่มี
  • การย้ายวิธีการประมวลผลหลังจากที่ <template for> เริ่มสตรีมแล้วอาจส่งผลที่ไม่คาดคิด โดยเนื้อหาใหม่จะยังคงสตรีมไปยังตำแหน่งเก่า
  • โปรดทราบว่าเมื่อแทรก <template for> แบบไดนามิกด้วยเมธอด เช่น setHTML หรือพร็อพเพอร์ตี้ innerHTML "องค์ประกอบหลัก" ของเทมเพลตเมื่อมีการแยกวิเคราะห์จะเป็น DocumentFragment ระดับกลาง ซึ่งหมายความว่าการแทรก HTML ด้วยวิธีเหล่านี้จะไม่สามารถแก้ไข DOM ที่มีอยู่ได้ และการแก้ไขจะเกิดขึ้น "ในตำแหน่ง" ภายใน Fragment อย่างไรก็ตาม เมื่อสตรีมโดยใช้วิธีการต่างๆ เช่น streamHTMLUnsafe (จะกล่าวถึงในเร็วๆ นี้) จะไม่มี Fragment ระหว่างกลาง ดังนั้นเทมเพลตจึงสามารถแทนที่เนื้อหาที่มีอยู่ได้

สถานะการกำหนดมาตรฐาน

แอตทริบิวต์ <template for> เป็นส่วนหนึ่งของมาตรฐาน HTML แต่ยังไม่รองรับในบางเบราว์เซอร์

การเพิ่มศักยภาพในอนาคต

เรากำลังพิจารณาเพิ่มฟีเจอร์ต่อไปนี้ในอนาคต

  • ฝั่งไคลเอ็นต์ประกอบด้วย เช่น <template for="footer" src="/partials/footer.html"> หรือแม้แต่ไม่ได้แพตช์ <template src="/partials/footer.html"> ดูรายละเอียดเพิ่มเติมได้ที่วิดีโออธิบาย โดยฟีเจอร์นี้จะอยู่หลังฟีเจอร์แฟล็ก chrome://flags/#enable-experimental-web-platform-features
  • ป้องกันการเขียนทับเนื้อหาที่จะไม่มีการเปลี่ยนแปลง ซึ่งทำได้โดยใช้หมายเลขการแก้ไขเนื้อหาหรือการกำหนดเวอร์ชัน ซึ่งจะช่วยให้สถานะยังคงอยู่ระหว่างการเปลี่ยนเส้นทางหรือการอัปเดตอื่นๆ แทนที่จะรีเซ็ตเนื้อหา
  • การล้างข้อมูลขณะแก้ไข เช่น <template for=icon safe><svg id="from-untrusted-source">...</svg></template>

Polyfill

ทีม Chrome ได้เปิดตัวtemplate-for-polyfill ซึ่งพร้อมใช้งานใน npm เพื่อให้เว็บไซต์ใช้ฟังก์ชันใหม่นี้ได้ทันทีแม้ว่าฟังก์ชันนี้จะยังไม่พร้อมใช้งานในเบราว์เซอร์อื่นๆ

ข้อจำกัดบางอย่างเนื่องจากอัปเดตตัวแยกวิเคราะห์ HTML ของเบราว์เซอร์โดยตรงไม่ได้ แต่ครอบคลุมกรณีการใช้งานที่พบบ่อยที่สุด เว็บไซต์ยังคงควรทดสอบในเบราว์เซอร์อื่นๆ

วิธีการแทรก HTML และการสตรีมแบบใหม่

เนื้อหาบางอย่างอาจนำส่งเป็น HTML ไม่ได้ ส่วนที่ 2 ของงานที่ Chrome ทำในส่วนนี้มีเป้าหมายเพื่อให้อัปเดตเนื้อหาด้วย JavaScript ได้ง่ายขึ้น

ปัจจุบันมีหลายวิธีในการแทรก HTML ลงในเอกสารที่มีอยู่แบบไดนามิกโดยใช้ JavaScript ดังนี้

  • setHTML
  • setHTMLUnsafe
  • innerHTML และ outerHTML
  • createContextualFragment
  • insertAdjacentHTML

อย่างไรก็ตาม ทั้งหมดนี้ทำงานแตกต่างกันเล็กน้อย โดยมีรายละเอียดและความแตกต่างที่นักพัฒนาแอปอาจไม่ได้พิจารณาเสมอไป ดังนี้

  • เนื้อหาใหม่จะเขียนทับหรือต่อท้าย
  • มีการล้าง HTML ที่อาจเป็นอันตรายหรือไม่ เช่น โดยการหลีกเลี่ยงแท็ก <script>
  • หากไม่ควร <script> ทำงานหรือไม่
  • และทำงานร่วมกับ Trusted Types อย่างไร

นักพัฒนาแอปไม่กี่รายที่สามารถดู API เหล่านั้นและตอบคำถามเกี่ยวกับ API แต่ละรายการได้อย่างมั่นใจ

ข้อจำกัดที่สำคัญคือใช้ได้เฉพาะกับชุด HTML ที่สมบูรณ์ซึ่งทราบล่วงหน้าเท่านั้น เมื่อมีการเรียกใช้เพื่ออนุญาตให้สตรีม HTML ในทางปฏิบัติแล้ว หมายความว่าคุณต้องดาวน์โหลดเนื้อหาทั้งหมดก่อนแทรก เนื่องจากจุดแข็งอย่างหนึ่งของ HTML คือความสามารถในการสตรีมเนื้อหาได้ทันที คุณอาจหลีกเลี่ยงข้อจำกัดนี้ได้ในขอบเขตที่จำกัดโดยการแยกเพย์โหลดหรือใช้วิธีการที่ล้าสมัยและไม่แนะนำ เช่น document.write แต่ก็อาจทำให้เกิดปัญหาอื่นๆ ตามมา

ชุด API แบบคงที่และสตรีมมิงชุดใหม่

Browser Support

  • Chrome: behind a flag.
  • Edge: behind a flag.
  • Firefox: not supported.
  • Safari: not supported.

Chrome ได้พัฒนาชุด API ใหม่และส่วนขยายสำหรับ setHTML และ setHTMLUnsafe ที่มีอยู่เพื่อจัดการปัญหานี้ รวมถึงเปิดตัวฟังก์ชันการสตรีม

ฟีเจอร์เหล่านี้พร้อมให้นักพัฒนาซอฟต์แวร์ทดสอบได้ตั้งแต่ Chrome 148 โดยใช้chrome://flags/#enable-experimental-web-platform-features Flag และมีกำหนดเปิดตัวใน Chrome 155

มีวิธีการตั้งค่าหรือแทนที่ รวมถึงวิธีการแทรกเนื้อหาก่อนหรือหลัง HTML ที่มีอยู่ แต่ละเมธอดมีสตรีมที่เทียบเท่าดังนี้

การดำเนินการ คงที่ สตรีมมิง
ตั้งค่าเนื้อหา HTML ขององค์ประกอบ setHTML(html, options); streamHTML(options);
แทนที่ทั้งองค์ประกอบด้วย HTML นี้ replaceWithHTML(html, options); streamReplaceWithHTML(options);
เพิ่ม HTML ก่อนองค์ประกอบ beforeHTML(html, options); streamBeforeHTML(options);
เพิ่ม HTML เป็นองค์ประกอบย่อยแรกขององค์ประกอบ prependHTML(html, options); streamPrependHTML(options);
เพิ่ม HTML เป็นองค์ประกอบย่อยสุดท้ายขององค์ประกอบ appendHTML(html, options); streamAppendHTML(options);
เพิ่ม HTML หลังองค์ประกอบ afterHTML(html, options); streamAfterHTML(options);
วิธีการแทรกและสตรีมแบบใหม่

นอกจากนี้ ยังมีเวอร์ชัน Unsafe ซึ่งเราจะกล่าวถึงในเร็วๆ นี้ แม้ว่าจะมีพร็อพเพอร์ตี้จำนวนมาก (โดยเฉพาะเมื่อคุณเพิ่มUnsafeเทียบเท่า) แต่รูปแบบการตั้งชื่อที่สอดคล้องกันจะช่วยให้เห็นได้ชัดเจนยิ่งขึ้นว่าแต่ละพร็อพเพอร์ตี้ทำอะไรได้บ้างเมื่อเทียบกับเมธอดที่ไม่เกี่ยวข้องที่กล่าวถึงก่อนหน้านี้

เวอร์ชันแบบคงที่จะใช้ HTML ใหม่เป็นอาร์กิวเมนต์สตริง DOM พร้อมกับตัวเลือกที่ไม่บังคับ ดังนี้

const newHTML = "<p>This is a new paragraph</p>";
const contentElement = document.querySelector('#content-to-update');

contentElement.setHTML(newHTML);

เวอร์ชันการสตรีมจะทำงานร่วมกับ Streams API เช่น getWriter()

const contentElement = document.querySelector('#content-to-update');
const writer = contentElement.streamHTMLUnsafe().getWriter();

// Example stream of updating content
while (true) {
  await writer.write(`<p>${++i}</p>`);
  await new Promise((resolve) => setTimeout(resolve, 1000));
}

writer.close();

หรืออีกวิธีหนึ่งคือจากคำตอบของการดึงข้อมูลโดยใช้การเชื่อมต่อแบบไปป์

const contentElement = document.querySelector('#content-to-update');
const response = await fetch('/api/content.html');

response.body
  .pipeThrough(new TextDecoderStream())
  .pipeTo(contentElement.streamHTMLUnsafe());

textStream() วิธีที่สะดวก

Browser Support

  • Chrome: 151.
  • Edge: 151.
  • Firefox: not supported.
  • Safari: not supported.

นอกจากนี้ เรายังได้เพิ่มtextStreamวิธีการที่สะดวก ซึ่งคุณสามารถสตรีมได้โดยตรงโดยไม่ต้องมีขั้นตอนTextDecoderStream()ขั้นกลาง

const contentElement = document.querySelector('#content-to-update');
const response = await fetch('/api/content.html');

response.textStream().pipeTo(contentElement.streamHTMLUnsafe());

options

อาร์กิวเมนต์ options ช่วยให้คุณระบุ sanitizer ที่กำหนดเองได้ ซึ่งค่าเริ่มต้นคือ default หมายถึงการกำหนดค่า Sanitizer เริ่มต้น โดยมีวิธีใช้ดังนี้

const newHTML = '<p>This is a new paragraph</p>';
const contentElement = document.querySelector('#content-to-update');

// Only allows basic formatting
const basicFormattingSanitzer = new Sanitizer({ elements: ['em', 'i', 'b', 'strong'] });

contentElement.setHTML(newHTML, {sanitizer: basicFormattingSanitzer});

เมธอด "ไม่ปลอดภัย"

นอกจากนี้ยังมี API แต่ละรายการในเวอร์ชัน "ไม่ปลอดภัย" ด้วย

การดำเนินการ คงที่ สตรีมมิง
ตั้งค่าเนื้อหา HTML ขององค์ประกอบ setHTMLUnsafe(html,options); streamHTMLUnsafe(options);
แทนที่ทั้งองค์ประกอบด้วย HTML นี้ replaceWithHTMLUnsafe(html, options); streamReplaceWithHTMLUnsafe(options);
เพิ่ม HTML ก่อนองค์ประกอบ beforeHTMLUnsafe(html, options); streamBeforeHTMLUnsafe(options);
เพิ่ม HTML เป็นองค์ประกอบย่อยแรกขององค์ประกอบ prependHTMLUnsafe(html, options); streamPrependHTMLUnsafe(options);
เพิ่ม HTML เป็นองค์ประกอบย่อยสุดท้ายขององค์ประกอบ appendHTMLUnsafe(html, options); streamAppendHTMLUnsafe(options);
เพิ่ม HTML หลังองค์ประกอบ afterHTMLUnsafe(html, options); streamAfterHTMLUnsafe(options);
วิธีการแทรกและสตรีมที่ "ไม่ปลอดภัย"

เมธอด "ไม่ปลอดภัย" เหล่านี้จะปิดตัวฆ่าเชื้อโดยค่าเริ่มต้น และคุณสามารถระบุตัวฆ่าเชื้อที่กำหนดเองได้หากต้องการ นอกจากนี้ วิธีการเหล่านี้ยังช่วยให้เรียกใช้สคริปต์ด้วยตัวเลือก runScripts (ไม่บังคับ) ได้ด้วย ซึ่งค่าเริ่มต้นจะเป็น false

เช่น setHTML setHTMLUnsafe เป็นเมธอดที่มีอยู่ แต่ได้เพิ่มพารามิเตอร์ตัวเลือก runScripts ลงในเมธอดนี้เพื่อให้ใช้กับการเรียกใช้สคริปต์ได้

const newHTML = `<p>This is a new paragraph</p>
                 <script src=script.js></script>`;
const contentElement = document.querySelector('#content-to-update');

contentElement.setHTMLUnsafe(newHTML, {runScripts: true});

คำว่า "ไม่ปลอดภัย" ในวิธีการนี้มีไว้เพื่อเตือนให้นักพัฒนาซอฟต์แวร์ทราบถึงความเสี่ยงที่อาจเกิดขึ้นและวิธีที่อาจต้องใช้ในการล้างข้อมูลหรือจำกัดสคริปต์ ไม่ได้หมายความว่าไม่ควรใช้วิธีการเหล่านี้

ระดับความ "ไม่ปลอดภัย" จะขึ้นอยู่กับความน่าเชื่อถือของอินพุต Unsafeเมธอดแบบคงที่ทั้งหมดใช้ได้ทั้งกับ DOM String หรือ TrustedHTML เป็นอาร์กิวเมนต์ html และยังอนุญาตให้ใช้ Sanitizer ได้ด้วย แม้ว่า runScript จะมีจุดประสงค์ทั้งหมดเพื่ออนุญาตสคริปต์ จึงเป็นเหตุผลที่ไม่มีการใช้โปรแกรมล้างข้อมูลโดยค่าเริ่มต้น

กรณีการใช้งาน

API ใหม่เหล่านี้ช่วยให้นักพัฒนาแอปเพิ่ม HTML ลงในหน้าเว็บที่มีอยู่ได้ง่ายขึ้น โดยการเพิ่ม API ใหม่ที่มีชื่อและตัวเลือกที่สอดคล้องกัน API การสตรีมช่วยให้ได้รับประโยชน์ด้านประสิทธิภาพโดยไม่ต้องรอจนกว่าเนื้อหาใหม่ทั้งหมดจะพร้อมใช้งานบนแพลตฟอร์ม

ตัวอย่างกรณีการใช้งานมีดังนี้

  • การสตรีมแบบไดนามิกของการอัปเดตเนื้อหาขนาดใหญ่ในแอปหน้าเว็บเดียว ดังที่ได้กล่าวไปก่อนหน้านี้ ข้อเสียที่สำคัญของสถาปัตยกรรม SPA ปัจจุบันคือไม่ได้รับประโยชน์จากลักษณะการสตรีมของการโหลด HTML เริ่มต้น ซึ่งตอนนี้เราได้แก้ไขปัญหานี้แล้ว
  • การแทรกเนื้อหาทั่วไป เช่น ส่วนท้าย HTML การใช้ JavaScript API ช่วยให้คุณดึงข้อมูลบางส่วนและแทรกลงในหน้าเว็บได้ ซึ่งจะได้รับประโยชน์จากการแคชแทนที่จะต้องทำซ้ำในทุกหน้าเว็บที่ส่ง อย่างไรก็ตาม เนื่องจากต้องใช้ JavaScript ในการเรียกใช้ จึงควรใช้วิธีนี้กับเนื้อหาที่จะไม่แสดงในการโหลดครั้งแรกเท่านั้น

อีกครั้งว่านี่เป็นเพียงตัวอย่างบางส่วนเท่านั้น และเราก็ตื่นเต้นที่จะได้เห็นผลงานของคุณ

ข้อจำกัดและความซับซ้อน

นอกจากนี้ API ใหม่เหล่านี้ยังมีข้อจำกัดและรายละเอียดเล็กๆ น้อยๆ ที่ควรทราบดังนี้

  • การผสานรวมการสตรีมกับ Trusted Types API ต้องใช้createParserOptionsเมธอดใหม่ซึ่งช่วยให้แทรกตัวกรองไปยังการดำเนินการตั้งค่า HTML ใดก็ได้ ดูวิดีโออธิบายเพื่อดูรายละเอียดเพิ่มเติมเกี่ยวกับการผสานรวมประเภทที่เชื่อถือได้
  • การย้ายองค์ประกอบที่กำลังสตรีมอยู่จะทำให้เกิดผลลัพธ์ที่ไม่คาดคิดหรือข้อผิดพลาดในการสตรีมได้ ซึ่งคล้ายกับ <template for>
  • streamHTMLUnsafe ทำงานคล้ายกับตัวแยกวิเคราะห์หลักในหลายๆ ด้าน รวมถึงการประมวลผลคำสั่ง <template for> เมื่อมีการเพิ่มลงในเอกสารหลัก และการเลื่อนสคริปต์ defer จนกว่าจะสิ้นสุดสตรีม

สถานะการกำหนดมาตรฐาน

วิธีการแทรกและสตรีมแบบใหม่อยู่ระหว่างการเพิ่มลงในมาตรฐาน HTML แต่ยังไม่รองรับในบางเบราว์เซอร์

Polyfill

ทีม Chrome ได้เปิดตัวhtml-setters-polyfill ซึ่งพร้อมใช้งานใน npm เพื่อให้เว็บไซต์ใช้ฟังก์ชันใหม่นี้ได้ทันทีแม้ว่าฟังก์ชันนี้จะยังไม่พร้อมใช้งานในเบราว์เซอร์อื่นๆ

โปรดทราบว่า Polyfill นี้ไม่ได้สตรีม แต่จะบัฟเฟอร์และใช้เมื่อเสร็จสมบูรณ์ ซึ่งเป็น Polyfill สำหรับรูปร่างของ API มากกว่าฟังก์ชันการทำงาน

นอกจากนี้ การตั้งค่าเนื้อหาที่ปลอดภัยยังขึ้นอยู่กับ setHTML และ Sanitizer API ซึ่งไม่รองรับใน Safari

ใช้ทั้ง 2 อย่างร่วมกัน

แม้ว่าจะเป็น API 2 รายการที่แยกกัน แต่ประสิทธิภาพที่แท้จริงมาจากการรวม API ทั้ง 2 รายการนี้ การสตรีมองค์ประกอบ <template for> ใหม่ลงใน HTML ช่วยให้คุณอัปเดตเนื้อหาส่วนต่างๆ แบบไดนามิกได้โดยไม่ต้องกำหนดเป้าหมายแต่ละส่วนโดยตรงด้วยการอ้างอิง JavaScript แยกต่างหากไปยัง DOM

คุณสามารถใช้การโหลดหน้าเว็บสไตล์ SPA ขั้นพื้นฐานได้โดยการโหลดหน้าโครงร่างพร้อมวิธีการประมวลผล แล้วสตรีมเทมเพลตของแต่ละหน้าใหม่ลงในส่วนล่างของ HTML เพื่อให้สอดคล้องกับวิธีการประมวลผลเหล่านั้น

แน่นอนว่า API ทั้ง 2 รายการนี้ยังมีศักยภาพและกรณีการใช้งานอีกมาก ดังนั้นอย่าปล่อยให้จินตนาการ (ที่จำกัด) ของเรามาฉุดรั้งคุณไว้ การจัดการการอัปเดตบางส่วนที่ง่ายขึ้นจะช่วยลดโค้ด Boilerplate บางส่วน ทำให้การอัปเดตง่ายขึ้น และปลดล็อกศักยภาพใหม่ๆ สำหรับเว็บ

Chrome กำลังพัฒนา API อีก 2-3 รายการภายใต้โปรเจ็กต์การอัปเดตบางส่วนแบบประกาศ แต่เราก็ตื่นเต้นที่จะได้ส่งมอบ API 2 รายการแรกนี้ให้คุณ เราจะคอยอัปเดตข้อมูลให้คุณทราบและแจ้งให้ทราบเมื่อมีข้อมูลเพิ่มเติมในส่วนนี้