ทำความเข้าใจวิสัยทัศน์เบื้องหลังคอมโพเนนต์สคริปต์ของ Next.js ซึ่งมีโซลูชันในตัวเพื่อเพิ่มประสิทธิภาพการโหลดสคริปต์ของบุคคลที่สาม
ประมาณ 45% ของคำขอจากเว็บไซต์ที่แสดงในอุปกรณ์เคลื่อนที่และเดสก์ท็อปเป็นคำขอของบุคคลที่สาม ซึ่ง 33% เป็นสคริปต์ ขนาด เวลาในการตอบสนอง และการโหลดสคริปต์ของบุคคลที่สามอาจส่งผลต่อประสิทธิภาพของเว็บไซต์อย่างมาก คอมโพเนนต์สคริปต์ Next.js มาพร้อมกับแนวทางปฏิบัติแนะนำและค่าเริ่มต้นที่ช่วยให้นักพัฒนาซอฟต์แวร์แนะนำสคริปต์ของบุคคลที่สามในแอปพลิเคชันของตนได้ พร้อมกับแก้ไขปัญหาด้านประสิทธิภาพที่อาจเกิดขึ้นได้ทันที
สคริปต์ของบุคคลที่สามและผลกระทบต่อประสิทธิภาพ
สคริปต์ของบุคคลที่สามช่วยให้นักพัฒนาเว็บใช้ประโยชน์จากโซลูชันที่มีอยู่เพื่อติดตั้งใช้งานฟีเจอร์ทั่วไปและลดเวลาในการพัฒนาได้ แต่ผู้สร้างสคริปต์เหล่านี้มักจะไม่มีสิ่งจูงใจในการพิจารณาผลกระทบด้านประสิทธิภาพที่มีต่อเว็บไซต์ที่กำลังเข้าชม สคริปต์เหล่านี้ยังเป็นกล่องดำของนักพัฒนาซอฟต์แวร์ที่ใช้สคริปต์ด้วย
สคริปต์พิจารณาไบต์ของบุคคลที่สามเป็นจำนวนมากที่เว็บไซต์ดาวน์โหลดจากคำขอของบุคคลที่สามในหมวดหมู่ต่างๆ โดยค่าเริ่มต้น เบราว์เซอร์จะจัดลำดับความสำคัญของสคริปต์ตามตำแหน่งในเอกสาร ซึ่งอาจทำให้การค้นหาหรือการดำเนินการสคริปต์ที่มีความสำคัญต่อประสบการณ์ของผู้ใช้ล่าช้า
ควรโหลดไลบรารีของบุคคลที่สามที่จำเป็นสำหรับเลย์เอาต์ก่อนเพื่อแสดงผลหน้าเว็บ ควรเลื่อนของบุคคลที่สามที่ไม่จำเป็นสำหรับการแสดงผลครั้งแรกออกไป เพื่อไม่ให้บล็อกการประมวลผลอื่นๆ ในเทรดหลัก Lighthouse มีการตรวจสอบ 2 แบบเพื่อระบุว่าสคริปต์การบล็อกการแสดงผลหรือการบล็อกเทรดหลัก
![การตรวจสอบ Lighthouse เพื่อกำจัดทรัพยากรที่บล็อกการแสดงผลและลดการใช้งานของบุคคลที่สาม](https://developer.chrome.google.cn/static/blog/script-component/image/lighthouse-audits-elimin-fd1156fda5643.png?authuser=9&hl=th)
คุณต้องพิจารณาลำดับการโหลดทรัพยากรของหน้าเว็บ เพื่อไม่ให้ทรัพยากรที่สำคัญไม่ล่าช้าและทรัพยากรที่ไม่สำคัญไม่บล็อกทรัพยากรที่สำคัญ
แม้ว่าจะมีแนวทางปฏิบัติแนะนำในการลดผลกระทบจากบุคคลที่สาม แต่ก็อาจมีบางคนที่ยังไม่ทราบวิธีนำไปใช้กับบุคคลที่สามทุกราย ซึ่งอาจซับซ้อนเนื่องด้วยเหตุผลต่อไปนี้
- โดยเฉลี่ยแล้ว เว็บไซต์จะใช้บุคคลที่สาม 21-23 ราย (รวมถึงสคริปต์) บนอุปกรณ์เคลื่อนที่และเดสก์ท็อป การใช้งานและคำแนะนำอาจแตกต่างกันไปในแต่ละฟีเจอร์
- การใช้งานระบบของบุคคลที่สามจำนวนมากอาจแตกต่างกันไป ขึ้นอยู่กับว่ามีการใช้เฟรมเวิร์กหรือไลบรารี UI ใดโดยเฉพาะ
- จะมีการนำไลบรารีใหม่ๆ ของบุคคลที่สามมาใช้เป็นประจำ
- ข้อกำหนดทางธุรกิจที่แตกต่างกันเกี่ยวกับบุคคลที่สามรายเดียวกันทำให้นักพัฒนาแอปกำหนดการใช้งานให้เป็นมาตรฐานได้ยาก
Aurora มุ่งเน้นสคริปต์ของบุคคลที่สาม
หนึ่งในการทำงานร่วมกันของ Aurora กับเฟรมเวิร์กและเครื่องมือเว็บโอเพนซอร์สคือการมอบเครื่องมือเริ่มต้นที่มีประสิทธิภาพและมีเครื่องมือแสดงความคิดเห็น เพื่อช่วยให้นักพัฒนาซอฟต์แวร์ปรับปรุงประสบการณ์ของผู้ใช้ในด้านต่างๆ เช่น ประสิทธิภาพ การช่วยเหลือพิเศษ การรักษาความปลอดภัย และความพร้อมของอุปกรณ์เคลื่อนที่ ในปี 2021 เรามุ่งเน้นที่การช่วยให้สแต็กเฟรมเวิร์กปรับปรุงประสบการณ์ของผู้ใช้และเมตริก Core Web Vitals
ขั้นตอนที่สำคัญที่สุดขั้นตอนหนึ่งในการบรรลุเป้าหมายในการปรับปรุงประสิทธิภาพของเฟรมเวิร์ก คือการค้นหาลำดับการโหลดสคริปต์ของบุคคลที่สามที่เหมาะสมใน Next.js เฟรมเวิร์กอย่าง Next.js จัดตำแหน่งขึ้นมาโดยเฉพาะเพื่อมอบค่าเริ่มต้นที่มีประโยชน์และฟีเจอร์ที่จะช่วยให้นักพัฒนาซอฟต์แวร์โหลดทรัพยากรได้อย่างมีประสิทธิภาพ ซึ่งรวมถึงบริการของบุคคลที่สามด้วย เราได้ศึกษา HTTP Archive และ ข้อมูล ของ Lighthouse อย่างครอบคลุมเพื่อค้นหาบุคคลที่สามที่บล็อกการแสดงผลมากที่สุดในเฟรมเวิร์กที่แตกต่างกัน
เราได้สร้างคอมโพเนนต์สคริปต์เพื่อแก้ไขปัญหาการที่เทรดหลักบล็อกสคริปต์ของบุคคลที่สามที่ใช้ในแอปพลิเคชัน คอมโพเนนต์สรุปฟีเจอร์การเรียงลำดับเพื่อให้นักพัฒนาซอฟต์แวร์ควบคุมการโหลดสคริปต์ของบุคคลที่สามได้ดียิ่งขึ้น
การจัดลำดับสคริปต์ของบุคคลที่สามที่ไม่มีคอมโพเนนต์เฟรมเวิร์ก
คำแนะนำที่มีให้ในการลดผลกระทบของสคริปต์ที่บล็อกการแสดงผลจะช่วยให้การโหลดและการจัดลำดับสคริปต์ของบุคคลที่สามอย่างมีประสิทธิภาพมีดังต่อไปนี้
ใช้แอตทริบิวต์
async
หรือdefer
กับแท็ก<script>
ที่บอกให้เบราว์เซอร์โหลดสคริปต์ของบุคคลที่สามที่ไม่สำคัญโดยไม่ต้องบล็อกโปรแกรมแยกวิเคราะห์เอกสาร สคริปต์ที่ไม่จำเป็นสำหรับการโหลดหน้าเว็บเริ่มต้นหรือการโต้ตอบของผู้ใช้ครั้งแรกอาจถือว่าไม่สำคัญ<script src="https://example.com/script1.js" defer></script> <script src="https://example.com/script2.js" async></script>
สร้างการเชื่อมต่อกับต้นทางที่จำเป็นล่วงหน้าโดยใช้การเชื่อมต่อล่วงหน้าและการดึงข้อมูล DNS ล่วงหน้า ซึ่งจะทำให้สคริปต์ที่สำคัญเริ่มดาวน์โหลดได้เร็วขึ้น
<head> <link rel="preconnect" href="http://PreconnThis.com"> <link rel="dns-prefetch" href="http://PrefetchThis.com"> </head>
การโหลดแบบ Lazy Loading สำหรับทรัพยากรของบุคคลที่สามและการฝังหลังจากเนื้อหาหลักในหน้าโหลดเสร็จแล้ว หรือเมื่อผู้ใช้เลื่อนลงไปที่ส่วนของหน้าเว็บที่มีทรัพยากรดังกล่าวอยู่
คอมโพเนนต์สคริปต์ Next.js
คอมโพเนนต์สคริปต์ Next.js ใช้วิธีการข้างต้นสำหรับการจัดลำดับสคริปต์ และให้เทมเพลตสำหรับนักพัฒนาซอฟต์แวร์เพื่อกำหนดกลยุทธ์การโหลด เมื่อระบุกลยุทธ์ที่เหมาะสมแล้ว กลยุทธ์ดังกล่าวจะโหลดได้อย่างดีที่สุดโดยไม่บล็อกทรัพยากรที่สำคัญอื่นๆ
คอมโพเนนต์สคริปต์สร้างจาก HTML <script> แท็กและมีตัวเลือกให้กำหนดลำดับความสำคัญในการโหลดสำหรับสคริปต์ของบุคคลที่สามโดยใช้แอตทริบิวต์กลยุทธ์
// Example for beforeInteractive:
<Script src="https://cdnjs.cloudflare.com/polyfill/v3/polyfill.min.js?features=IntersectionObserverEntry%2CIntersectionObserver" strategy="beforeInteractive" />
// Example for afterInteractive (default):
<Script src="https://example.com/samplescript.js" />
// Example for lazyonload:
<Script src="https://connect.facebook.net/en_US/sdk.js" strategy="lazyOnload" />
แอตทริบิวต์กลยุทธ์มีได้ 3 ค่า
beforeInteractive
: ใช้ตัวเลือกนี้กับสคริปต์สำคัญที่ควรทำงานก่อนที่หน้าเว็บจะมีการโต้ตอบ Next.js ช่วยให้แน่ใจว่ามีการแทรกสคริปต์ดังกล่าวลงใน HTML เริ่มต้นของเซิร์ฟเวอร์ และทำงานก่อน JavaScript อื่นๆ ที่จัดแพ็กเกจตัวเอง การจัดการความยินยอม สคริปต์ตรวจจับบ็อต หรือไลบรารีตัวช่วยที่จำเป็นในการแสดงเนื้อหาที่สำคัญเป็นตัวเลือกที่ดีสำหรับกลยุทธ์นี้afterInteractive
: กลยุทธ์นี้เป็นกลยุทธ์เริ่มต้นและเทียบเท่ากับการโหลดสคริปต์ที่มีแอตทริบิวต์ที่เลื่อนเวลาออกไป ควรใช้สำหรับสคริปต์ที่เบราว์เซอร์สามารถเรียกใช้หลังจากที่หน้าเว็บมีการโต้ตอบ เช่น สคริปต์การวิเคราะห์ Next.js จะแทรกสคริปต์เหล่านี้ในฝั่งไคลเอ็นต์และจะทำงานหลังจากที่หน้าเว็บได้รับการเติมน้ำแล้ว ดังนั้น Next.js จะเลื่อนเวลาสคริปต์ของบุคคลที่สามทั้งหมดที่กำหนดโดยใช้คอมโพเนนต์สคริปต์ออกไป ด้วยเหตุนี้จึงให้ค่าเริ่มต้นที่แข็งแกร่งlazyOnload
: คุณอาจใช้ตัวเลือกนี้เพื่อโหลดสคริปต์ที่มีลำดับความสำคัญต่ำแบบ Lazy Loading เมื่อไม่มีการใช้งานเบราว์เซอร์ ฟังก์ชันการทำงานของสคริปต์ดังกล่าวไม่จำเป็นในทันทีหลังจากที่หน้าเว็บมีการโต้ตอบ เช่น แชทหรือปลั๊กอินโซเชียลมีเดีย
นักพัฒนาซอฟต์แวร์สามารถบอก Next.js ว่าแอปพลิเคชันของตนใช้สคริปต์อย่างไรโดยระบุกลยุทธ์ วิธีนี้จะช่วยให้เฟรมเวิร์กใช้การเพิ่มประสิทธิภาพและแนวทางปฏิบัติแนะนำเพื่อโหลดสคริปต์ขณะที่คงลำดับการโหลดที่ดีที่สุดได้
เมื่อใช้คอมโพเนนต์สคริปต์ นักพัฒนาซอฟต์แวร์สามารถวางสคริปต์ของบุคคลที่สามไว้ที่ใดก็ได้ในแอปพลิเคชันสำหรับบุคคลที่สามที่โหลดล่าช้า และในระดับเอกสารสำหรับสคริปต์ที่สำคัญ ซึ่งหมายความว่าคอมโพเนนต์ของสคริปต์อาจอยู่ร่วมกับคอมโพเนนต์โดยใช้สคริปต์ หลังเติมน้ำแล้ว ระบบจะแทรกสคริปต์เข้าไปในส่วนหัวของเอกสารที่แสดงผลครั้งแรกหรือบริเวณด้านล่างของร่างกาย ขึ้นอยู่กับกลยุทธ์ที่ใช้
การวัดผลกระทบ
เราใช้เทมเพลตสำหรับแอปการค้าและบล็อกเริ่มต้นของ Next.js เพื่อสร้างแอปเดโม 2 แอปที่ช่วยวัดผลลัพธ์ของการรวมสคริปต์ของบุคคลที่สาม บุคคลที่สามที่ใช้กันโดยทั่วไปสำหรับ Google Tag Manager และการฝังโซเชียลมีเดียจะมีอยู่ในหน้าของแอปเหล่านี้โดยตรงในตอนแรก จากนั้นจึงผ่านคอมโพเนนต์สคริปต์ จากนั้นเราได้เปรียบเทียบประสิทธิภาพของหน้าเว็บเหล่านี้ใน WebPageTest
สคริปต์ของบุคคลที่สามในแอปการค้า Next.js
มีการเพิ่มสคริปต์ของบุคคลที่สามลงในเทมเพลตแอปเชิงพาณิชย์สำหรับการสาธิตตามที่ระบุไว้ด้านล่าง
การเปรียบเทียบต่อไปนี้แสดงความคืบหน้าของภาพสำหรับ Next.js commerce starter-kit ทั้ง 2 เวอร์ชัน ตามที่เห็นคือ LCP เกิดขึ้นก่อนหน้าเกือบ 1 วินาทีโดยเปิดใช้คอมโพเนนต์สคริปต์โดยมีกลยุทธ์การโหลดที่ถูกต้อง
![การเปรียบเทียบแถบฟิล์มที่แสดงการด้นสดใน LCP](https://developer.chrome.google.cn/static/blog/script-component/image/film-strip-comparison-sho-e0d0929f7666e.png?authuser=9&hl=th)
สคริปต์ของบุคคลที่สามในบล็อก Next.js
มีการเพิ่มสคริปต์ของบุคคลที่สามลงในแอปบล็อกเดโมตามที่ระบุไว้ด้านล่าง
ก่อน | หลัง |
---|---|
Google Tag Manager แบบไม่พร้อมกัน | คอมโพเนนต์สคริปต์ที่มีกลยุทธ์ = lazyonload สำหรับแต่ละสคริปต์จากทั้งหมด 4 สคริปต์ |
ปุ่มติดตาม Twitter ที่ไม่พร้อมกัน | |
ปุ่มติดตาม YouTube แบบไม่ซิงค์หรือเลื่อนเวลา | |
ปุ่มติดตามของ LinkedIn แบบไม่ซิงค์หรือเลื่อนเวลา |
![วิดีโอแสดงความคืบหน้าในการโหลดหน้าดัชนีที่มีและไม่มีคอมโพเนนต์สคริปต์ FCP ได้รับการปรับปรุง 0.5 วินาทีด้วยคอมโพเนนต์สคริปต์](https://developer.chrome.google.cn/static/blog/script-component/image/video-showing-loading-pr-6cc1f9330829c.gif?authuser=9&hl=th)
ตามที่เห็นในวิดีโอ First Contentful Paint (FCP) จะเกิดที่วินาทีที่ 0.9 ในหน้าเว็บโดยไม่มีคอมโพเนนต์ของสคริปต์ และ 0.4 วินาทีเมื่อคอมโพเนนต์สคริปต์
ขั้นตอนถัดไปสำหรับคอมโพเนนต์สคริปต์
แม้ว่าตัวเลือกกลยุทธ์สำหรับ afterInteractive
และ lazyOnload
จะให้การควบคุมสคริปต์ที่บล็อกการแสดงผลได้อย่างมาก แต่เราก็ยังสำรวจตัวเลือกอื่นๆ ที่อาจเพิ่มประโยชน์ของคอมโพเนนต์สคริปต์ด้วย
การใช้ Web Worker
สามารถใช้ผู้ปฏิบัติงานบนเว็บเพื่อเรียกใช้สคริปต์อิสระบนเทรดพื้นหลังได้ ซึ่งจะช่วยให้เทรดหลักว่างมากขึ้นในการจัดการกับงานด้านอินเทอร์เฟซผู้ใช้และปรับปรุงประสิทธิภาพ Web Worker เหมาะกับการลดการประมวลผล JavaScript มากกว่าการทำงาน UI นอกเทรดหลัก สคริปต์ที่ใช้สำหรับการสนับสนุนลูกค้าหรือการตลาด ซึ่งโดยทั่วไปแล้วจะไม่โต้ตอบกับ UI อาจเหมาะสำหรับการดำเนินการกับเทรดเบื้องหลัง คุณสามารถใช้ไลบรารีของบุคคลที่สามขนาดเล็ก PartyTown เพื่อแยกสคริปต์ดังกล่าวให้เป็น Web Worker
เมื่อใช้คอมโพเนนต์สคริปต์ Next.js ในปัจจุบัน เราขอแนะนำให้เลื่อนเวลาสคริปต์เหล่านี้ในเทรดหลักโดยตั้งค่ากลยุทธ์เป็น afterInteractive
หรือ lazyOnload
ในอนาคตเราขอเสนอตัวเลือกกลยุทธ์ใหม่ชื่อ 'worker'
ซึ่งจะทำให้ Next.js ใช้ PartyTown หรือโซลูชันที่กำหนดเองเพื่อเรียกใช้สคริปต์ในผู้ปฏิบัติงานบนเว็บได้ เรายินดีรับฟังความคิดเห็นจากนักพัฒนาซอฟต์แวร์ใน RFC นี้
การลด CLS
การฝังของบุคคลที่สาม เช่น โฆษณา วิดีโอ หรือการฝังฟีดโซเชียลมีเดียอาจทำให้เลย์เอาต์เกิดการเปลี่ยนแปลงเมื่อโหลดแบบ Lazy Loading ซึ่งจะส่งผลต่อประสบการณ์ของผู้ใช้และเมตริก Cumulative Layout Shift (CLS) ของหน้าเว็บ คุณย่อ CLS ได้โดยระบุขนาดของคอนเทนเนอร์ที่จะโหลดการฝัง
อาจมีการใช้คอมโพเนนต์สคริปต์เพื่อโหลดการฝังที่อาจทำให้เกิดการเปลี่ยนเลย์เอาต์ โดยเรากำลังพิจารณาที่จะเพิ่มประสิทธิภาพดังกล่าวเพื่อมอบตัวเลือกการกำหนดค่าที่จะช่วยลด CLS ซึ่งสามารถพร้อมใช้งานภายในคอมโพเนนต์สคริปต์เองหรือเป็นคอมโพเนนต์ที่ใช้ร่วมกันก็ได้
คอมโพเนนต์ Wrapper
โดยทั่วไปแล้ว กลยุทธ์ด้านไวยากรณ์และการโหลดสำหรับการรวมสคริปต์ของบุคคลที่สามที่ได้รับความนิยม เช่น Google Analytics หรือ Google Tag Manager (GTM) มักจะได้รับการแก้ไข คุณจะรวมสิ่งเหล่านี้เพิ่มเติมไว้ในคอมโพเนนต์ Wrapper แต่ละรายการสำหรับสคริปต์แต่ละประเภทได้ นักพัฒนาซอฟต์แวร์จะใช้ชุดแอตทริบิวต์เฉพาะแอปพลิเคชันได้เพียงเล็กน้อยเท่านั้น (เช่น รหัสติดตาม) คอมโพเนนต์ Wrapper จะช่วยนักพัฒนาซอฟต์แวร์ได้โดยทำดังนี้
- ทำให้รวมแท็กสคริปต์ยอดนิยมได้ง่ายขึ้น
- ทำให้แน่ใจว่าเฟรมเวิร์กจะใช้กลยุทธ์ที่มีประสิทธิภาพสูงสุดภายใต้การทำงาน
บทสรุป
โดยปกติแล้วสคริปต์ของบุคคลที่สามจะสร้างขึ้นเพื่อรวมฟีเจอร์ที่เฉพาะเจาะจงไว้ในเว็บไซต์ที่ใช้งานอยู่ เพื่อลดผลกระทบของสคริปต์ที่ไม่สำคัญ เราขอแนะนำให้เลื่อนเวลาการทำงานออกไป ซึ่งคอมโพเนนต์สคริปต์ Next.js จะทำโดยค่าเริ่มต้น นักพัฒนาแอปมั่นใจว่าสคริปต์ที่รวมไว้จะไม่ทำให้ฟังก์ชันการทำงานที่สำคัญล่าช้าลง เว้นแต่จะใช้กลยุทธ์ beforeInteractive
อย่างชัดแจ้ง นักพัฒนาเฟรมเวิร์กยังสามารถพิจารณาสร้างคุณลักษณะเหล่านี้ในเฟรมเวิร์กอื่นๆ เช่นเดียวกับคอมโพเนนต์สคริปต์ Next.js เรากำลังสำรวจองค์ประกอบที่คล้ายกันนี้ร่วมกับทีม Nuxt.js เรายังหวังที่จะปรับปรุงคอมโพเนนต์สคริปต์ให้ครอบคลุมกรณีการใช้งานอื่นๆ อีกโดยอิงจากความคิดเห็นของคุณ
บริการรับรองคำให้การ
ขอขอบคุณ Kara Erickson, Janicklas Ralph, Katie Hempenius, Philip Walton, Jeremy Wagner และ Addy Osmani สำหรับความคิดเห็นเกี่ยวกับโพสต์นี้