בדרך כלל, כשמשתמש סוגר דף או אפליקציה, יש נתונים שלא נשלחו לניתוח או נתונים אחרים. כדי למנוע אובדן נתונים, חלק מהאתרים משתמשים בקריאה סינכרונית ל-XMLHttpRequest() כדי להשאיר את הדף או האפליקציה פתוחים עד שהנתונים שלהם מועברים לשרת. יש דרכים טובות יותר לשמירת נתונים, והטכניקה הזו יוצרת חוויית משתמש גרועה כי היא מעכבת את סגירת הדף למשך כמה שניות.
השיטה הזו צריכה להשתנות, והדפדפנים מגיבים. המפרט של XMLHttpRequest() כבר עומד לצאת משימוש ולהימחק. ב-Chrome 80 נעשה הצעד הראשון בכיוון הזה, והשימוש בקריאות סינכרוניות בתוך כמה מטפלי אירועים נאסר, במיוחד beforeunload, unload, pagehide ו-visibilitychange כשהם מופעלים בביטול. בנוסף, לאחרונה בוצע ב-WebKit commit שמטמיע את אותו שינוי בהתנהגות.
אני אציג בקצרה אפשרויות למי שצריך זמן לעדכן את האתרים שלו, ואפרט את החלופות ל-XMLHttpRequest().
ביטולים זמניים של הסכמה
צוות Chrome רוצה להציע למפתחים זמן להסרת התלות ב-XMLHttpRequest(), ולכן הצענו אפשרויות זמניות לביטול ההסכמה.
הצטרפות לתקופת ניסיון של תכונה חדשה כך מוסיפים טוקן ספציפי למקור לכותרות הדפים, שמאפשר קריאות סינכרוניות XMLHttpRequest(). האפשרות הזו תוסר זמן קצר לפני השקת Chrome 89, במהלך מרץ 2021. לקוחות Chrome Enterprise יכולים גם להשתמש בדגל המדיניות AllowSyncXHRInPageDismissal, שתוקפו יפוג באותו הזמן.
אפשרויות אחרות
לא משנה איך שולחים את הנתונים בחזרה לשרת, מומלץ לא לחכות עד שהדף יוסר כדי לשלוח את כל הנתונים בבת אחת. בנוסף ליצירת חוויית משתמש גרועה, השימוש ב-unload בדפדפנים מודרניים לא אמין ועלול לגרום לאובדן נתונים אם משהו ישתבש. ספציפית, אירועי הסרת הנתונים שנטענו לרוב לא מופעלים בדפדפנים לנייד כי יש דרכים רבות לסגור כרטיסייה או דפדפן במערכות הפעלה לנייד בלי שהאירוע unload יופעל.
ב-XMLHttpRequest(), השימוש במטענים ייעודיים (payloads) קטנים היה בחירה. עכשיו זו דרישה. לשתי החלופות יש מגבלת העלאה של 64 KB לכל הקשר, כפי שנדרש במפרט.
אחזור הודעת keep-alive
Fetch API מספק אמצעי אמין להתמודדות עם אינטראקציות עם שרתים וממשק עקבי לשימוש בממשקי API שונים של פלטפורמות. אחת מהאפשרויות היא keepalive, שמבטיחה שהבקשה תמשיך גם אם הדף שממנו היא נשלחה יישאר פתוח וגם אם לא:
window.addEventListener('unload', {
fetch('/siteAnalytics', {
method: 'POST',
body: getStatistics(),
keepalive: true
});
}
היתרון של השיטה fetch() הוא שליטה רבה יותר על מה שנשלח לשרת. בדוגמה לא רואים ש-fetch() מחזירה גם הבטחה שמושלמת עם אובייקט Response. מכיוון שאני מנסה לא להפריע לתהליך הסרת הנתונים שנטענו של הדף, בחרתי לא לעשות איתו כלום.
SendBeacon()
SendBeacon() בעצם משתמש ב-Fetch API מתחת לפני השטח, ולכן יש לו את אותה מגבלת מטען ייעודי (payload) של 64 KB, והוא גם מבטיח שהבקשה תימשך אחרי טעינת הדף. היתרון העיקרי שלה הוא הפשטות שלה. הוא מאפשר לכם לשלוח את הנתונים באמצעות שורת קוד אחת:
window.addEventListener('unload', {
navigator.sendBeacon('/siteAnalytics', getStatistics());
}
סיכום
עם הזמינות המוגברת של
fetch()
בדפדפנים, יש סיכוי ש-XMLHttpRequest() יוסר מפלטפורמת האינטרנט. ספקי הדפדפנים מסכימים שצריך להסיר אותו, אבל זה ייקח זמן. הוצאה משימוש של אחד מתרחישי השימוש הגרועים ביותר היא צעד ראשון לשיפור חוויית המשתמש לכולם.