Chrome Uzantıları: Eyeo' hizmet çalışanı askıya alma testi

Aga Czyżewska
Aga Czyżewska
Rowan Deysel
Rowan Deysel

Bu neyle ilgili?

Manifest v2'den Manifest v3'e geçiş, temel bir değişiklikle birlikte gelir. Manifest V2'de uzantılar arka plan sayfasında yer alıyordu. Arka plan sayfaları, uzantılar ile web sayfaları arasındaki iletişimi yönetiyordu. Manifest V3 bunun yerine hizmet işçilerini kullanır.

Bu yayında, genişletilmiş çalışma süresi kapsamındaki hizmet çalışanlarını test etme sorununu ayrıntılı olarak ele alıyoruz. Özellikle, bir hizmet çalışanının askıya alınması durumunda ürünümüzün düzgün şekilde çalıştığından nasıl emin olabileceğimize bakıyoruz.

Biz kimleriz?

eyeo, kullanıcılar, tarayıcılar, reklamverenler ve yayıncılar için dengeli ve sürdürülebilir bir online değer alışverişi sağlamaya odaklanmış bir şirkettir. Bir reklamın kabul edilebilir ve müdahaleci olup olmadığını belirleyen bağımsız olarak türetilmiş bir reklam standardı olan Kabul Edilebilir Reklamlar'ın gösterilmesine izin veren 300 milyondan fazla küresel reklam filtreleme kullanıcımız var.

Uzantı Motoru ekibimiz, dünya genelinde 110 milyondan fazla kullanıcısı olan AdBlock ve Adblock Plus gibi pazardaki en popüler reklam engelleyici tarayıcı uzantılarından bazılarını destekleyen reklam filtreleme teknolojisi sağlar. Ayrıca bu teknolojiyi açık kaynak kitaplık olarak sunarak diğer reklam filtreleyen tarayıcı uzantılarının kullanımına sunuyoruz.

Hizmet çalışanı nedir?

Uzantı hizmet işçileri, tarayıcı uzantısının merkezi etkinlik işleyicisidir. Bu işlemler arka planda bağımsız olarak çalışır. Genel olarak bu sorun değil. Yapmamız gerekenlerin çoğunu yeni hizmet çalışanında arka plan sayfasında yapabiliriz. Ancak arka plan sayfalarına kıyasla birkaç değişiklik vardır:

  • Hizmet çalışanları kullanımda değilken sonlandırılır. Bu nedenle, genel değişkenleri kullanmak yerine uygulama durumlarını korumamız gerekir. Bu nedenle, sistemimiz için giriş noktaları, sistem başlatılmadan önce çağrılmaya hazır olmalıdır.
  • Etkinlik işleyiciler, herhangi bir ayarsız geri çağırma işlevi beklenmeden önce eklenmelidir. Askıya alınmış hizmet işçileri, abone oldukları etkinlikleri almaya devam edebilir. Etkinliğin dinleyicisi, etkinlik döngüsünün ilk turunda kaydedilmemişse bu etkinlik hizmet çalışanını uyandırırsa etkinliği almaz.
  • Boş zaman sonlandırma işlemi, tamamlanmadan önce zamanlayıcıları kesintiye uğratabilir.

Hizmet çalışanları ne zaman askıya alınır?

Chrome 119'da, hizmet işçilerinin askıya alındığını tespit ettik:

  • 30 saniye boyunca etkinlik alınmadığında veya uzantı API'leri çağrıldığında.
  • Geliştirici araçları açıksa veya ChromeDriver tabanlı bir test kitaplığı kullanıyorsanız hiçbir zaman (özellik isteğine bakın).
  • chrome://serviceworker-internals adresinde Durdur'u tıklarsanız.

Daha güncel bilgiler için Hizmet Çalışanlarının Yaşam Döngüsü başlıklı makaleyi inceleyin.

Bunu test etmek neden sorundur?

İdeal olarak, "hizmet işçilerinin verimli bir şekilde nasıl test edileceği" hakkında resmi bir kılavuz veya çalışan test örnekleri olması yararlı olurdu. Hizmet işçilerini test etme maceralarımız sırasında birkaç zorlukla karşılaştık:

  • Test uzantımızda durum bilgisi var. Hizmet çalışanı durduğunda durumunu ve kayıtlı etkinliklerini kaybederiz. Verileri test akışımızda nasıl tutarız?
  • Hizmet işçileri herhangi bir zamanda askıya alınabiliyorsa kesinti olması durumunda tüm özelliklerin çalıştığını test etmemiz gerekir.
  • Testlerimize, hizmet işçilerini rastgele askıya alacak bir mekanizma eklesek bile tarayıcıda kolayca askıya alacak bir API yoktur. W3C ekibinden bu özelliği eklemesini istedik ancak bu konudaki görüşmelerimiz devam ediyor.

Hizmet Çalışanı Askıya Alınmasını Test Etme

Testler sırasında hizmet çalışanının askıya alınmasını tetiklemek için çeşitli yaklaşımlar denedik:

Yaklaşım Yaklaşımla ilgili sorunlar
İstediğiniz kadar bekleyin (ör. 30 saniye) Bu durum, özellikle birden fazla test çalıştırırken testin yavaş ve güvenilir olmamasına neden olur. WebDriver, Chrome'un DevTools API'sini kullandığından ve DevTools açıkken hizmet çalışanı askıya alınmadığından bu yöntem WebDriver kullanılırken çalışmaz. Bu sorunu atlayabilsek bile hizmet çalışanının askıya alınıp alınmadığını kontrol etmemiz gerekir. Bunu yapmanın bir yolu yoktur.
Hizmet çalışanında sonsuz döngü çalıştırma Spesifikasyona göre, bu durum tarayıcının bu işlevi nasıl uyguladığına bağlı olarak feshe neden olabilir. Chrome bu durumda hizmet çalışanını sonlandırmaz. Bu nedenle, hizmet çalışanının askıya alındığı senaryoyu test edemeyiz.
Hizmet çalışanında, askıya alınıp alınmadığını kontrol etmek için bir mesaj bulunması Bir mesaj göndermek, hizmet çalışanını uyandırır. Bu yöntem, hizmet işçisinin uykuda olup olmadığını kontrol etmek için kullanılabilir ancak hizmet işçisi askıya alındıktan hemen sonra kontrol yapması gereken testlerin sonuçlarını bozar.
chrome.processes.terminate() işlevini kullanarak hizmet çalışanı işlemini sonlandırın Uzantı için hizmet çalışanı, uzantının diğer bölümleriyle bir işlem paylaşır. Bu nedenle, chrome.process.terminate() veya Chrome'un işlem yöneticisi kullanıcı arayüzü kullanılarak bu işlem sonlandırılırsa yalnızca hizmet çalışanı değil, tüm uzantı sayfaları da sonlandırılır.

Selenium WebDriver'ın chrome://serviceworker-internals/ adresini açmasını ve hizmet çalışanı için "durdur" düğmesini tıklamasını sağlayarak kodumuzun hizmet çalışanının askıya alınmasına nasıl yanıt verdiğini kontrol eden bir test oluşturduk.

Bu, şimdiye kadarki en iyi seçenektir ancak Mocha testlerimiz (bir uzantı sayfasında çalıştırılır) bunu kendileri yapamadığından WebDriver düğüm programımızla geri iletişim kurmaları gerektiği için ideal değildir. Bu, bu testlerin yalnızca uzantı kullanılarak çalıştırılamayacağını, Selenium WebDriver kullanılarak tetiklenmesi gerektiğini gösterir.

Aşağıda, farklı akışlar üzerinden tarayıcı API'siyle nasıl iletişim kurduğumuz ve "askıya alınan hizmet işçileri" mekanizmasının bunu nasıl etkilediğini gösteren bir şema verilmiştir.

Test akışını gösteren şema
Hizmet çalışanının askıya alınmasıyla akışı test etme.

Hizmet işçilerini askıya alan yeni bir akışta (mavi), kullanıcı arayüzü üzerinden askıya alma işlemini "tıklamak" için Selenium WebDriver'ı ekledik. Bu işlem, tarayıcı API'sinde bir işlem tetikler.

Selenium WebDriver ile bu işlemin yapılmasının, hizmet çalışanının tekrar başlatılamamasına neden olduğu bir Chrome hatası olduğunu belirtmek isteriz. Bu sorun Chrome 116'da düzeltildi ve bu sorun için bir geçici çözüm de var: Chrome'u her sekmede DevTools'u otomatik olarak açacak şekilde ayarlamak, hizmet çalışanının doğru şekilde başlatılmasını sağlar.

Düğmeyi tıklamak kararlı bir API olmayabileceği ve DevTools'un (eski tarayıcılar için) açılmasının performans maliyeti olduğu için ideal olmasa da test yaparken bu yaklaşımı kullanıyoruz.

İşlevin tamamını nasıl ele alabiliriz? Fuzz Testleri

Askıya alma işlemini test etmek için bir mekanizma oluşturduktan sonra, bu mekanizmayı otomasyon test paketlerimize nasıl ekleyeceğimize karar vermemiz gerekiyordu. Standart testlerimizi, arka plan sayfasıyla her etkileşimden önce WebDriver'ın chrome://serviceworker-internals/ sayfasında Durdur'u tıklayarak hizmet çalışanının askıya alındığı bir ortamda çalıştırdık.

Örnek bir fuzz testi çalıştırma
Testlerin mevcut kurulumunu gösteren resim.

Askıya alma mekanizması tam olarak kararlı olmadığı ve bazen kararsızlığa neden olduğu için testlerin tamamını değil, çoğunu çalıştırırız. Ayrıca, tüm test paketlerini fuzz modunda çalıştırmak çok zaman alır. Bu nedenle, tüm "benzer" durumları kapsamak yerine, bulanıklık modunda test için en kritik yolları seçtik. İşlevsel testleri "fuzz" modunda çalıştırmanın, hizmet işçilerinin askıya alınması ve yeniden başlatılmasının ek zaman aldığı için testlerin zaman aşımlarını artırmamız gerektiği anlamına geldiğini belirtmek isteriz.

Bu testler, kodun başarısız olduğu birçok yeri vurgulayan kaba bir ilk geçiş olarak değerlidir ancak hizmet işçisinin askıya alınmasının bazı şeylerin bozulmasına neden olabileceği tüm ince yolları her zaman ortaya çıkarmayabilir.

Şirket içinde bu tür testlere "Fuzz testleri" diyoruz. Geleneksel olarak, fuzz testi, programınıza geçersiz girişler gönderip makul bir yanıt aldığınızdan veya en azından kilitlenmediğinden emin olduğunuzda yapılır. Bizim durumumuzda "geçersiz giriş", hizmet çalışanının herhangi bir zamanda askıya alınmasıdır ve beklediğimiz "makul davranış", reklam filtreleme işlevimizin eskisi gibi çalışmaya devam etmesidir. Manifest V3'te beklenen bir davranış olduğu için bu aslında geçersiz bir giriş değildir. Ancak Manifest V2'de geçersiz olurdu. Bu nedenle, makul bir terminoloji gibi görünüyor.

Özet

Hizmet çalışanları, Manifest V3'teki en büyük değişikliklerden biridir (declarativeNetRequest kurallarının yanı sıra). Manifest V3'e geçiş, tarayıcı uzantılarında birçok kod değişikliği ve teste yeni yaklaşımlar gerektirebilir. Ayrıca, kalıcı duruma sahip uzantıların geliştiricilerinin, uzantılarını beklenmedik servis çalışanı askıya alma işlemlerini sorunsuz bir şekilde ele almaya hazırlamaları gerekir.

Maalesef askıya alma işlemini kullanım alanımıza uygun, kolay bir şekilde gerçekleştirmek için kullanabileceğiniz bir API yok. Uzantı kod tabanımızın askıya alma mekanizmalarına karşı sağlamlığını erken bir aşamada test etmek istediğimizden bu sorunun üstesinden gelmek zorunda kaldık. Benzer zorluklarla karşılaşan diğer uzantı geliştiricileri bu geçici çözümü kullanabilir. Geliştirme ve bakım aşamasında zaman alıcı olsa da bu çözüm, uzantılarımızın hizmet işçilerinin düzenli olarak askıya alındığı bir ortamda başarılı bir şekilde çalışabilmesini sağlayabileceğimiz için buna değer.

Hizmet çalışanlarının askıya alınmasını test etmek için temel destek mevcut olsa da test yürütme sürelerimizi ve bakım çalışmalarımızı büyük ölçüde azaltabileceği için gelecekte uzantılardan hizmet çalışanlarını test etmek için daha iyi platform desteği görmek isteriz.