Web İşaretçisi API'si ile Etkinliği Günlüğe Kaydetme
Yayınlanan: 2022-03-10 Beacon API, yanıt beklemeden tarayıcıdan web sunucusuna küçük miktarlarda veri göndermek için JavaScript tabanlı bir Web API'sidir. Bu makalede, bunun ne için yararlı olabileceğine, onu XMLHTTPRequest
('Ajax') gibi bilinen tekniklerden farklı kılanın ne olduğuna ve onu nasıl kullanmaya başlayabileceğinize bakacağız.
Beacon'u neden kullanmak istediğinizi zaten biliyorsanız, doğrudan Başlarken bölümüne geçmekten çekinmeyin.
Beacon API Ne İçin?
Beacon API, yanıt beklemeden bir sunucuya az miktarda veri göndermek için kullanılır. Bu son kısım kritiktir ve Beacon'ın neden bu kadar yararlı olduğunun anahtarıdır - sunucu bir yanıt gönderse bile kodumuz hiçbir zaman bir yanıt göremez. İşaretçiler özellikle veri göndermek ve sonra onu unutmak içindir. Bir yanıt beklemiyoruz ve yanıt da alamıyoruz.
Tatildeyken eve gönderilen bir kartpostal gibi düşünün. Üzerine az miktarda veri koyarsınız (biraz “Keşke burada olsaydınız” ve “Hava güzeldi”), posta kutusuna atarsınız ve bir yanıt beklemezsiniz. Hiç kimse “Evet, keşke orada olsaydım, çok teşekkür ederim!” diye bir iade kartpostal göndermiyor.
Modern web siteleri ve uygulamalar için, bu gönder ve unut modeline çok uygun bir şekilde giren bir dizi kullanım durumu vardır.
İzleme İstatistikleri ve Analiz Verileri
Çoğu insan için akla gelen ilk kullanım durumu analitiktir. Google Analytics gibi büyük çözümler, sayfa ziyaretleri gibi şeylere iyi bir genel bakış sağlayabilir, ancak ya daha özelleştirilmiş bir şey istiyorsak? Bir sayfada neler olduğunu (belki bir kullanıcının bir bileşenle nasıl etkileşime girdiğini, ne kadar ilerlediğini veya bir CTA'yı izlemeden önce hangi makalelerin görüntülendiğini) izlemek için biraz JavaScript yazabiliriz, ancak daha sonra bu verileri göndermemiz gerekir. kullanıcı sayfadan ayrıldığında sunucuya. Beacon bunun için mükemmel, çünkü biz sadece verileri günlüğe kaydediyoruz ve bir yanıta ihtiyacımız yok.
Ayrıca, genellikle Google Analytics tarafından gerçekleştirilen sıradan görevleri, kullanıcının kendisi ve cihazının ve tarayıcısının kapasitesi hakkında rapor vermememiz için hiçbir neden yok. Kullanıcının oturum açmış bir oturumu varsa, bu istatistikleri bilinen bir kişiye bile bağlayabilirsiniz. Hangi verileri toplarsanız toplayın, Beacon ile sunucuya geri gönderebilirsiniz.
Hata Ayıklama ve Günlüğe Kaydetme
Bu davranış için başka bir yararlı uygulama, JavaScript kodunuzdaki bilgileri günlüğe kaydetmektir. Sayfanızda tüm testleriniz için mükemmel çalışan, ancak bazen üretimde başarısız olan karmaşık bir etkileşimli bileşeniniz olduğunu hayal edin. Başarısız olduğunu biliyorsunuz, ancak hata ayıklamaya başlamak için hatayı göremezsiniz. Kodun kendisinde bir arıza tespit edebiliyorsanız, teşhisleri toplayabilir ve günlük kaydı için hepsini geri göndermek için Beacon'ı kullanabilirsiniz.
Aslında, ister bir oyunda kaydetme noktaları oluşturma, ister özellik kullanımı hakkında bilgi toplama veya çok değişkenli bir testin sonuçlarını kaydetme olsun, herhangi bir günlük kaydı görevi, Beacon kullanılarak yararlı bir şekilde gerçekleştirilebilir. Sunucunun bilmesini istediğiniz tarayıcıda olan bir şeyse, Beacon muhtemelen bir rakiptir.
Bunu Zaten Yapamaz mıyız?
Ne düşündüğünü biliyorum. Bunların hiçbiri yeni değil, değil mi? On yıldan fazla bir süredir XMLHTTPRequest
kullanarak tarayıcıdan sunucuya iletişim kurabiliyoruz. Daha yakın zamanlarda, aynı şeyi daha modern bir vaat tabanlı arayüzle yapan Fetch API'ye de sahibiz. Buna göre, neden Beacon API'sine ihtiyacımız var?
Buradaki anahtar, bir yanıt alamadığımız için, tarayıcının isteği kuyruğa alıp başka herhangi bir kodun yürütülmesini engellemeden gönderebilmesidir. Tarayıcı söz konusu olduğunda, kodumuzun hala çalışıp çalışmadığı veya komut dosyası yürütmesinin nerede olması gerektiği önemli değildir, döndürülecek hiçbir şey olmadığından, uygun olana kadar HTTP isteğinin gönderilmesini arka planda tutabilir. gönder.
Bu, CPU yükü düşene kadar veya ağ boş olana kadar beklemek veya hatta mümkünse hemen göndermek anlamına gelebilir. Önemli olan, tarayıcının beacon'ı kuyruğa alması ve kontrolü hemen geri vermesidir. İşaret gönderirken işleri tutmaz.
Bunun neden bu kadar önemli olduğunu anlamak için, kodumuzdan bu tür isteklerin nasıl ve ne zaman verildiğine bakmamız gerekiyor. Analiz günlüğü komut dosyası örneğimizi alın. Kodumuz, kullanıcıların bir sayfada ne kadar zaman harcadıklarının zamanlaması olabilir, bu nedenle verilerin mümkün olan en son anda sunucuya geri gönderilmesi kritik hale gelir. Kullanıcı bir sayfadan ayrılmaya gittiğinde, zamanlamayı durdurmak ve verileri eve geri göndermek istiyoruz.
Tipik olarak, günlüğe kaydetmeyi yürütmek için ya unload
ya da boşaltmadan beforeunload
olayını kullanırsınız. Bunlar, kullanıcı sayfadan uzaklaşmak için bir bağlantıyı takip etmek gibi bir şey yaptığında tetiklenir. Buradaki sorun, unload
olaylarından birinde çalışan kodun, yürütmeyi engelleyebilmesi ve sayfanın boşaltılmasını geciktirebilmesidir. Sayfanın boşaltılması gecikirse, sonraki sayfanın yüklenmesi de gecikir ve bu nedenle deneyim gerçekten ağır gelir.
HTTP isteklerinin ne kadar yavaş olabileceğini unutmayın. Performansı düşünüyorsanız, tipik olarak azaltmaya çalıştığınız ana faktörlerden biri fazladan HTTP istekleridir çünkü ağa çıkmak ve yanıt almak çok yavaş olabilir. Yapmak isteyeceğiniz en son şey, bir bağlantının etkinleştirilmesi ile bir sonraki sayfa için talebin başlaması arasındaki o yavaşlığı koymaktır.
Beacon, isteği engellemeden kuyruğa alarak ve kontrolü hemen komut dosyanıza geri döndürerek bu sorunu çözer. Tarayıcı daha sonra bu isteği engellemeden arka planda göndermeye özen gösterir. Bu, her şeyi çok daha hızlı hale getirir, bu da kullanıcıları daha mutlu eder ve hepimizin işimizi sürdürmemizi sağlar.
Başlarken
Beacon'ın ne olduğunu ve neden kullanabileceğimizi anlıyoruz, o yüzden biraz kodla başlayalım. Temel bilgiler daha basit olamazdı:
let result = navigator.sendBeacon(url, data);
Sonuç boolean, tarayıcı isteği kabul edip sıraya aldıysa true
ve bunu yaparken bir sorun varsa false
olur.
navigator.sendBeacon()
kullanma
navigator.sendBeacon
iki parametre alır. Birincisi, istekte bulunulacak URL'dir. İstek, ikinci parametrede sağlanan tüm verileri göndererek bir HTTP POST olarak gerçekleştirilir.
Veri parametresi, tümü doğrudan Getirme API'sinden alınmışsa, birkaç biçimden birinde olabilir. Bu bir Blob
, bir BufferSource
, FormData
veya URLSearchParams
- temel olarak Fetch ile istekte bulunurken kullanılan gövde türlerinden herhangi biri.
Basit ve okunması kolay olduğu için temel anahtar/değer verileri için FormData
kullanmayı seviyorum.
// URL to send the data to let url = '/api/my-endpoint'; // Create a new FormData and add a key/value pair let data = new FormData(); data.append('hello', 'world'); let result = navigator.sendBeacon(url, data); if (result) { console.log('Successfully queued!'); } else { console.log('Failure.'); }
Tarayıcı Desteği
Tarayıcılarda Beacon desteği çok iyidir, dikkate değer istisnalar yalnızca Internet Explorer (Edge'de çalışır) ve Opera Mini'dir. Çoğu kullanım için bu iyi olabilir, ancak navigator.sendBeacon
kullanmayı denemeden önce destek için test etmeye değer.
Bunu yapmak çok kolay:
if (navigator.sendBeacon) { // Beacon code } else { // No Beacon. Maybe fall back to XHR? }
Beacon mevcut değilse ve talebiniz önemliyse, XHR gibi bir engelleme yöntemine geri dönebilirsiniz. Hedef kitlenize ve amacınıza bağlı olarak, aynı şekilde rahatsız etmemeyi de seçebilirsiniz.
Bir Örnek: Bir Sayfada Kayıt Süresi
Bunu pratikte görmek için, bir kullanıcının bir sayfada ne kadar kaldığını zamanlamak için temel bir sistem oluşturalım. Sayfa yüklendiğinde saati not edeceğiz ve kullanıcı sayfadan ayrıldığında başlangıç saatini ve geçerli saati sunucuya göndereceğiz.
Yalnızca harcanan süreyi önemsediğimiz için (günün gerçek saati değil), sayfa yüklenirken temel bir zaman damgası almak için performance.now()
işlevini kullanabiliriz:
let startTime = performance.now();
Bir fonksiyona girişimizi tamamlarsak, sayfa boşaldığında onu çağırabiliriz.
let logVisit = function() { // Test that we have support if (!navigator.sendBeacon) return true; // URL to send the data to, eg let url = '/api/log-visit'; // Data to send let data = new FormData(); data.append('start', startTime); data.append('end', performance.now()); data.append('url', document.URL); // Let's go! navigator.sendBeacon(url, data); };
Son olarak kullanıcı sayfadan ayrıldığında bu fonksiyonu çağırmamız gerekiyor. İlk beforeunload
, unload
olayını kullanmaktı, ancak Mac'te Safari, isteği bir güvenlik uyarısıyla engelliyor gibi görünüyor, bu nedenle, boşaltmadan önce burada bizim için gayet iyi çalışıyor.
window.addEventListener('beforeunload', logVisit);
Sayfa kaldırıldığında (veya hemen öncesinde) logVisit()
işlevimiz çağrılır ve tarayıcının Beacon API'sini desteklemesi koşuluyla işaretimiz gönderilir.
(Beacon desteği yoksa, true
değerini döndürürüz ve her şey harika çalışıyormuş gibi davranırız. false
döndürmek etkinliği iptal eder ve sayfanın yüklenmesini durdurur. Bu talihsizlik olur.)
İzleme Sırasında Dikkat Edilmesi Gereken Hususlar
Beacon'ın potansiyel kullanımlarının çoğu, aktivite takibi etrafında döndüğünden, geliştiriciler olarak, kullanıcılara bağlı olabilecek aktiviteyi kaydederken ve takip ederken sahip olduğumuz sosyal ve yasal sorumluluklardan bahsetmemek yanlış olur.
GDPR
Son Avrupa GDPR yasalarını e-postayla ilgili olarak düşünebiliriz, ancak elbette mevzuat her türlü kişisel veriyi depolamakla ilgilidir. Kullanıcılarınızın kim olduğunu biliyorsanız ve oturumlarını tanımlayabiliyorsanız, hangi etkinliği günlüğe kaydettiğinizi ve bunun belirtilen politikalarla nasıl ilişkili olduğunu kontrol etmelisiniz.
Çoğu zaman, geliştiricilerin bize yapmamız gerektiğini söylediği gibi, içgüdülerimiz kadar çok veri izlememize gerek yoktur. Bir kullanıcıyı tanımlayacak bilgileri kasten saklamamak daha iyi olabilir ve ardından yanlış anlama olasılığınızı azaltırsınız.
DNT: Takip Etme
Yasal gerekliliklere ek olarak, çoğu tarayıcının, kullanıcının izlenmeme isteğini ifade etmesine olanak tanıyan bir ayarı vardır. Do Not Track, şuna benzeyen istekle bir HTTP başlığı gönderir:
DNT: 1
Belirli bir kullanıcıyı izleyebilecek verileri günlüğe kaydediyorsanız ve kullanıcı pozitif bir DNT
başlığı gönderirse, kullanıcının isteklerini takip etmek ve bu verileri anonim hale getirmek veya hiç izlememek en iyisi olacaktır.
Örneğin PHP'de bu başlık için çok kolay bir şekilde şu şekilde test edebilirsiniz:
if (!empty($_SERVER['HTTP_DNT'])) { // User does not wish to be tracked ... }
Sonuç olarak
Beacon API, özellikle günlük kaydı bağlamında, bir sayfadan sunucuya veri göndermenin gerçekten kullanışlı bir yoludur. Tarayıcı desteği çok geniştir ve kullanıcının göz atma deneyimini ve sitenizin performansını olumsuz etkilemeden verileri sorunsuz bir şekilde günlüğe kaydetmenizi sağlar. İsteklerin engellenmeyen doğası, performansın XHR ve Fetch gibi alternatiflerden çok daha hızlı olduğu anlamına gelir.
Beacon API hakkında daha fazla bilgi edinmek isterseniz, aşağıdaki sitelere göz atmaya değer.
- “W3C Beacon spesifikasyonu,” W3C Aday Önerisi
- "MDN Beacon belgeleri", MDN web belgeleri, Mozilla
- "Tarayıcı destek bilgileri," caniuse.com