PWA (Progressive Web App) — je webová aplikace, která využívá moderní možnosti prohlížeče k tomu, aby fungovala jako nativní aplikace: rychle se načítá, pracuje offline, odesílá push oznámení a instaluje se na domovskou obrazovku. V základu PWA leží tři technologie: Service Worker, manifest a HTTPS. Service Worker — je skript, který prohlížeč spouští na pozadí, odděleně od webové stránky, a otevírá možnosti nedostupné běžným webům: zachycování síťových požadavků, ukládání zdrojů do mezipaměti, synchronizace na pozadí a push oznámení. Manifest — je JSON soubor, který prohlížeči sděluje, jak má aplikace vypadat při instalaci na zařízení: název, ikony, barva motivu, orientace obrazovky. Bez HTTPS Service Worker nefunguje — to je povinný bezpečnostní požadavek. PWA je kompatibilní s jakýmkoli moderním prohlížečem a nevyžaduje publikování v obchodu s aplikacemi. Uživatel otevře web, uvidí nabídku k instalaci aplikace, klikne na «Přidat na domovskou obrazovku» — a aplikace je hotová. Pro podnikání PWA znamená pokrytí jakéhokoli publika bez nákladů na vývoj zvlášť pro iOS a Android, vysokou rychlost načítání i na pomalých sítích a zapojení prostřednictvím push oznámení. V článku si rozebereme, jak funguje Service Worker, jak sestavit manifest, jaké strategie ukládání do mezipaměti používat a jak zajistit offline přístup.
Hlavní
Hlavní
Progressive Web App (PWA) — je přístup k vývoji webových aplikací, který kombinuje nejlepší vlastnosti webu a nativních aplikací. Termín zavedl Francesco Berriman v roce 2015 a Google aktivně propaguje PWA jako náhradu jednoduchých mobilních aplikací. Hlavní myšlenka: webová stránka se postupně zlepšuje v závislosti na možnostech prohlížeče a zařízení. Pokud prohlížeč podporuje Service Worker — připojí se offline režim. Pokud podporuje manifest — objeví se tlačítko «Instalovat». Pokud existuje API oznámení — aplikace může posílat push. Uživatel na slabém zařízení s pomalým internetem dostane základní verzi webu, zatímco na moderním smartphonu — plnohodnotnou aplikaci s ikonou na ploše.
PWA není třeba instalovat přes obchod s aplikacemi. Stačí odkaz. To řeší hlavní problém mobilních aplikací — vysokou vstupní bariéru. Uživatel nejde do Google Play nebo App Store, nečeká na stažení 100 MB, neuděluje desítky oprávnění. Jednoduše otevře web a prohlížeč nabídne instalaci aplikace. Pokud uživatel odmítne — stále používá web. A pokud souhlasí — ikona se objeví na domovské obrazovce a aplikace se otevře jako nativní: bez adresního řádku prohlížeče, v režimu celé obrazovky a s rychlým spuštěním.
Technicky musí PWA splňovat tři kritéria: pracovat přes HTTPS (bezpečné připojení), mít Service Worker (skript pro zpracování na pozadí) a obsahovat manifest (Web App Manifest). Tyto tři komponenty mění běžný web na instalovatelnou aplikaci.
Service Worker — je JavaScriptový skript, který prohlížeč spouští v samostatném vlákně, nezávisle na webové stránce. Nemá přístup k DOM, nemůže přímo interagovat s rozhraním, ale může zachycovat a upravovat síťové požadavky, spravovat mezipaměť, zpracovávat push oznámení a provádět synchronizaci na pozadí. Service Worker funguje jako proxy server mezi prohlížečem a sítí: každý požadavek ze stránky prochází přes Service Worker, který rozhoduje — vrátit data z mezipaměti, vyžádat ze serveru nebo udělat obojí.
Service Worker žije podle vlastního životního cyklu, nezávislého na otevřené stránce. Instaluje se, aktivuje se a pracuje na pozadí i po zavření všech karet webu. To umožňuje PWA přijímat push oznámení a aktualizovat mezipaměť na pozadí, bez účasti uživatele.
Service Worker prochází čtyřmi fázemi: registrace, instalace, aktivace a nečinnost/ukončení.
Registrace. Prohlížeč obdrží odkaz na JS soubor Service Worker a zahájí stahování. Registrace se provádí z běžného JavaScriptu na stránce:
if ('serviceWorker' in navigator) {
navigator.serviceWorker.register('/sw.js')
.then(registration => {
console.log('SW registrován:', registration.scope);
})
.catch(error => {
console.log('Registrace SW selhala:', error);
});
}Instalace. Po úspěšném stažení prohlížeč spustí událost install. V této fázi je obvyklé ukládat do mezipaměti klíčové zdroje (HTML kostru, CSS, hlavní obrázky), aby aplikace mohla fungovat offline. Pokud instalace proběhne úspěšně, Service Worker přejde do další fáze. Pokud skript vyvolá chybu — instalace se zruší a starý Service Worker pokračuje v činnosti.
self.addEventListener('install', event => {
event.waitUntil(
caches.open('pwa-cache-v1').then(cache => {
return cache.addAll([
'/',
'/index.html',
'/styles/main.css',
'/scripts/app.js',
'/images/logo.png'
]);
})
);
});Aktivace. Když jsou všechny karty webu zavřeny, starý Service Worker se ukončí a nový se aktivuje. Událost activate se používá k čištění starých mezipamětí a migraci dat:
self.addEventListener('activate', event => {
const cacheWhitelist = ['pwa-cache-v2'];
event.waitUntil(
caches.keys().then(cacheNames => {
return Promise.all(
cacheNames.map(cacheName => {
if (!cacheWhitelist.includes(cacheName)) {
return caches.delete(cacheName);
}
})
);
})
);
});Nečinnost. Aktivovaný Service Worker zachycuje požadavky a zpracovává události. Může být zastaven prohlížečem za účelem úspory zdrojů a znovu spuštěn při dalším požadavku. Service Worker je událostmi řízený: žije pouze dokud zpracovává události.
Service Worker podporuje několik strategií ukládání do mezipaměti. Volba závisí na typu zdroje a požadavcích na aktuálnost dat.
Cache First (nejprve mezipaměť). Nejprve se zkontroluje mezipaměť. Pokud je zdroj nalezen — vrátí se z mezipaměti. Pokud ne — požadavek jde na server, odpověď se uloží do mezipaměti. Strategie je vhodná pro statické zdroje: obrázky, písma, CSS, JS. Zajišťuje maximální rychlost a plnohodnotnou práci offline.
self.addEventListener('fetch', event => {
event.respondWith(
caches.match(event.request).then(response => {
return response || fetch(event.request).then(fetchResponse => {
return caches.open('pwa-cache-v1').then(cache => {
cache.put(event.request, fetchResponse.clone());
return fetchResponse;
});
});
})
);
});Network First (nejprve síť). Požadavek jde nejprve na server. Pokud server odpoví — data se vrátí uživateli a uloží se do mezipaměti. Pokud server není dostupný — vrátí se kopie z mezipaměti. Strategie je vhodná pro API požadavky, zprávy, obsah, který musí být aktuální, ale může fungovat i offline.
self.addEventListener('fetch', event => {
event.respondWith(
fetch(event.request).then(response => {
return caches.open('pwa-dynamic-v1').then(cache => {
cache.put(event.request, response.clone());
return response;
});
}).catch(() => {
return caches.match(event.request);
})
);
});Stale While Revalidate (zastaralé s obnovením). Odpověď je okamžitě vrácena z mezipaměti, zatímco na pozadí je odeslán požadavek na server pro aktualizaci mezipaměti. Uživatel vidí obsah okamžitě a další požadavek již obdrží čerstvá data. Ideální pro obsah, který se mění, ale není kritické, pokud uživatel uvidí verzi o pár minut starší.
self.addEventListener('fetch', event => {
event.respondWith(
caches.match(event.request).then(cached => {
const fetchPromise = fetch(event.request).then(response => {
return caches.open('pwa-dynamic-v1').then(cache => {
cache.put(event.request, response.clone());
return response;
});
});
return cached || fetchPromise;
})
);
});Manifest — je JSON soubor, obvykle manifest.json, který se připojuje přes tag <link> v hlavičce HTML stránky. Sděluje prohlížeči, jak má být aplikace zobrazena při instalaci na zařízení: název, ikony různých velikostí, barva pozadí, barva motivu, orientace a režim zobrazení (prohlížeč, minimální UI, celá obrazovka).
{
"name": "PWA Demo App",
"short_name": "PWA Demo",
"description": "Demo PWA aplikace",
"start_url": "/",
"display": "standalone",
"background_color": "#ffffff",
"theme_color": "#3f51b5",
"orientation": "portrait",
"icons": [
{
"src": "/icons/icon-192x192.png",
"sizes": "192x192",
"type": "image/png"
},
{
"src": "/icons/icon-512x512.png",
"sizes": "512x512",
"type": "image/png",
"purpose": "any maskable"
}
]
}Parametr display určuje, jak bude aplikace vypadat po instalaci. standalone skrývá adresní řádek prohlížeče a navigační panel — aplikace vypadá jako nativní. fullscreen využívá celou obrazovku bez jakýchkoli prvků prohlížeče. minimal-ui ponechává minimální prvky prohlížeče (tlačítka zpět a obnovení).
Ikony by měly být připraveny nejméně ve dvou velikostech: 192x192 a 512x512 pixelů. Formát PNG s podporou parametru purpose (například maskable) umožňuje prohlížeči přizpůsobit ikonu tvaru krytu zařízení — na Androidu může být ikona oříznuta na zaoblený čtverec. Po připojení manifestu začne prohlížeč Chrome na Androidu zobrazovat banner «Přidat na domovskou obrazovku» při splnění podmínek: HTTPS, registrovaný Service Worker, správný manifest a nejméně dvě návštěvy s intervalem 5 minut.
PWA může odesílat push oznámení jako nativní aplikace. K tomu se používají dvě API: Push API (odesílání ze serveru) a Notification API (zobrazení na zařízení). Service Worker obdrží push událost, i když aplikace není otevřena, a může zobrazit oznámení s názvem, textem a ikonou.
Pro příjem push oznámení musí uživatel udělit povolení:
Notification.requestPermission().then(permission => {
if (permission === 'granted') {
console.log('Push povolen');
}
});Service Worker se přihlásí k odběru push události a zobrazí oznámení:
self.addEventListener('push', event => {
const data = event.data.json();
self.registration.showNotification(data.title, {
body: data.body,
icon: '/icons/icon-192x192.png',
badge: '/icons/badge-72x72.png',
actions: [
{ action: 'open', title: 'Otevřít' },
{ action: 'close', title: 'Zavřít' }
]
});
});
self.addEventListener('notificationclick', event => {
event.notification.close();
if (event.action === 'open') {
clients.openWindow('/');
}
});Pro odesílání push ze serveru se používá protokol Web Push (VAPID). Server zašifruje zprávu a odešle ji prostřednictvím push služby prohlížeče (Firebase Cloud Messaging pro Chrome, Mozilla Autopush pro Firefox). Odběr uživatele (objekt PushSubscription) musí být uložen na serveru při registraci.
PWA musí být rychlé. Google Lighthouse — je nástroj pro audit, který kontroluje PWA podle kontrolního seznamu: registrace Service Worker, odpověď 200 při offline přístupu, správný manifest, HTTPS, správná velikost ikon, rychlé načítání na pomalých sítích. Minimální skóre pro úspěch PWA — 80 ze 100 na stupnici Lighthouse. Aplikace se skóre pod 80 nezískají banner pro instalaci v Chrome.
Klíčové metriky výkonu pro PWA — First Contentful Paint (FCP) do 1,8 sekundy, Largest Contentful Paint (LCP) do 2,5 sekundy, Time to Interactive (TTI) do 3,5 sekundy. Service Worker může výrazně zlepšit FCP a LCP, pokud ukládá do mezipaměti kritické HTML a CSS při instalaci. Strategie Cache First pro statiku a Stale While Revalidate pro API poskytuje nejlepší uživatelský zážitek.
Jednou z hlavních možností PWA — práce bez internetu. Service Worker zachycuje požadavky a vrací verze stránek uložené v mezipaměti. Pokud se uživatel pokusí otevřít stránku, která není v mezipaměti, lze zobrazit vlastní záložní stránku:
self.addEventListener('fetch', event => {
event.respondWith(
caches.match(event.request).then(response => {
return response || fetch(event.request);
}).catch(() => {
return caches.match('/offline.html');
})
);
});Synchronizace na pozadí (Background Sync) umožňuje odložit odesílání dat na server, pokud je zařízení offline. Service Worker uloží požadavek a automaticky jej odešle, když je připojení obnoveno:
self.addEventListener('sync', event => {
if (event.tag === 'sync-messages') {
event.waitUntil(sendMessages());
}
});
function sendMessages() {
return caches.open('pwa-pending-v1').then(cache => {
return cache.keys().then(requests => {
return Promise.all(requests.map(request => {
return fetch(request).then(() => cache.delete(request));
}));
});
});
}Chrome DevTools poskytuje panel Application, kde lze ladit Service Worker (registrace, stav, mezipaměť, push), kontrolovat manifest, čistit mezipaměť a vytvářet vlastní push oznámení pro testování. Záložka Network s emulací offline režimu pomáhá kontrolovat činnost mezipaměti. Lighthouse v panelu Audits poskytuje úplný audit PWA s doporučeními.
Workbox — knihovna od Google, která zjednodušuje vytváření Service Worker. Místo ručního psaní strategií ukládání do mezipaměti nabízí Workbox hotové moduly:
import { precacheAndRoute } from 'workbox-precaching';
import { registerRoute } from 'workbox-routing';
import { StaleWhileRevalidate } from 'workbox-strategies';
precacheAndRoute(self.__WB_MANIFEST);
registerRoute(
/\.(?:png|jpg|jpeg|svg|gif)$/,
new StaleWhileRevalidate()
);Workbox se integruje s bundlery (Webpack, Vite) a automaticky generuje manifest předběžného ukládání do mezipaměti. PWA Builder (pwabuilder.com) od Microsoftu generuje všechny soubory PWA online: Service Worker, manifest, ikony, HTML šablonu.
FAQ
PWA — je web, který po instalaci do telefonu funguje jako běžná aplikace: ikona na ploše, offline přístup, push oznámení, režim celé obrazovky bez adresního řádku prohlížeče. Přitom není třeba chodit do App Store nebo Google Play — instalace probíhá jedním kliknutím z prohlížeče.
Nativní aplikace se píše pro konkrétní platformu (Swift pro iOS, Kotlin pro Android), vyžaduje publikování v obchodě a ruční instalaci. PWA — je webová stránka napsaná v HTML, CSS a JavaScriptu, kterou lze nainstalovat na zařízení prostřednictvím prohlížeče. PWA nezabírá mnoho místa (pouze mezipaměť), aktualizuje se automaticky a je podporována všemi moderními prohlížeči.
Chrome, Firefox, Safari (od iOS 11.3), Edge, Samsung Internet, Opera. Service Worker je podporován všemi moderními prohlížeči kromě Internet Exploreru. Safari má omezenou podporu push oznámení, ale základní možnosti PWA (instalace na domovskou obrazovku, offline přístup) fungují.
Ano. K tomu je třeba přidat manifest (manifest.json), vytvořit a zaregistrovat Service Worker (sw.js), převést web na HTTPS, přidat meta tagy a ikony. Samotný web nevyžaduje přepisování, pokud funguje na JavaScriptu a vrací HTML. Pokud je web plně serverový (MPA), lze Service Worker přidat jako vrstvu pro ukládání do mezipaměti bez změny architektury.
Když uživatel otevře PWA, prohlížeč zkontroluje, zda se soubor Service Worker na serveru změnil. Pokud se soubor liší alespoň o jeden bajt, prohlížeč stáhne nový Service Worker a spustí jeho instalaci. Starý Service Worker pokračuje v činnosti, dokud nejsou zavřeny všechny karty aplikace. Po zavření karet se nový Service Worker aktivuje a nahradí starý. Uživatel může vynutit aktualizaci aplikace opětovným načtením stránky.
PWA je opodstatněné, pokud je cílem pokrýt maximální publikum bez nákladů na vývoj pro dvě platformy, pokud aplikace nevyžaduje hluboký přístup k hardwaru (Bluetooth, NFC, kamera na pozadí), pokud se obsah často mění. Pro složité aplikace (hry, video editory) zůstává nativní aplikace preferovaná. PWA se často používá jako doplňkový kanál nebo jako MVP před plnohodnotnou aplikací.
Shrnutí
Vyvineme mobilní aplikaci na klíč
IT Sectr vytváří aplikace pro iOS a Android pro startupy a podniky od roku 2017. Poradíme vám a navrhneme nejlepší řešení.
Přečtěte si také