Slide 1

Slide 1 text

以 實現 網站開發: 離線、推播、Service Worker Jecelyn Yeen

Slide 2

Slide 2 text

@JecelynYeen ⼟土⽣生⼟土⻑⾧長的吉隆隆坡,⾺馬來來⻄西亞⼈人 • ⾕谷歌開發技術專家 • Web technologies • Angular • 部落客 @ scotch.io, medium.com • 軟件架構師 @ Randstad • 社群發起⼈人 • Women Who Code KL • The Frontend Malaysia

Slide 3

Slide 3 text

概覽 何謂 ? 以 實現 開發 設定 Service Worker + 離線 實現網絡推播 Web Push Notification 剖解 PWA 的 P (progressive) ⼯工具箱 和 資源

Slide 4

Slide 4 text

Quiz

Slide 5

Slide 5 text

PWA Quiz It is just a normal website It can be talk to your phone’s native api - e.g. camera, sensor, spawn notification It can work offline / semi offline It is installable / can be add to home screen (icon) It is fast / performant It can work cross platform + cross browsers Install update on the fly / refresh It is safe

Slide 6

Slide 6 text

What is Progressive Web App? It is just a normal website It can be talk to your phone’s native api - e.g. camera, sensor, spawn notification It can work offline / semi offline It is installable / can be add to home screen (icon) It is fast / performant It can work cross platforms + cross browsers Cross platform yes - as long as it’s browser, Cross browser… no, most modern browsers support* Yes, it should, but… you know Install update on the fly / refresh It is safe Definitely safer than https, but…

Slide 7

Slide 7 text

Biggest myth about PWA It is all about adding to home screen

Slide 8

Slide 8 text

It is about Bringing better web experience to the users

Slide 9

Slide 9 text

+

Slide 10

Slide 10 text

How to Start ? • npm install @angular/cli • ng new my-app-name Run in command line / terminal:

Slide 11

Slide 11 text

How to Start + • ng add @angular/pwa Run in command line / terminal: Build & Deploy it: • ng build --prod • deploy /dist/[project] folder to hosting • ng serve do not support service worker

Slide 12

Slide 12 text

Mobile View test pwa

Slide 13

Slide 13 text

test pwa test-pwa test pwa

Slide 14

Slide 14 text

test pwa test-pwa test pwa It’s work!

Slide 15

Slide 15 text

How does it works? Magic?

Slide 16

Slide 16 text

Minimum PWA • Have manifest.json • Register service worker

Slide 17

Slide 17 text

Behind the scene, … • Creating manifest.json • Creating set of icons • Register service worker • Creating ngsw-config.json

Slide 18

Slide 18 text

manifest.json { "name": "test-pwa", "short_name": "test-pwa", "theme_color": "#1976d2", "background_color": "#fafafa", "display": "standalone", "scope": "/", "start_url": "/", "icons": [ { "src": "assets/icons/icon-72x72.png", "sizes": "72x72", "type": "image/png" }, … ] }

Slide 19

Slide 19 text

Service Worker The Middle Man

Slide 20

Slide 20 text

How Service Worker works? Browser App Service Worker Cache

Slide 21

Slide 21 text

Service Worker & Cache APIs support Browsers Mobile Desktop

Slide 22

Slide 22 text

NGSW configuration file { "assetGroups": [ Smart defaults for the app shell ], "dataGroups": [ Settings for your API, etc ], ... } ngsw-config.json

Slide 23

Slide 23 text

NGSW configuration file { "index": "/index.html", "assetGroups": [{ "name": "app", "installMode": "prefetch", "resources": { "files": [ "/favicon.ico", "/index.html", "/*.css", "/*.js" ] } }] } ngsw-config.json / assetGroups • prefetch: fetch eagerly • lazy: fetch when we need

Slide 24

Slide 24 text

NGSW configuration file { "name": "myApi", "urls": [ "/api/archive/**" ], "cacheConfig": { "strategy": "performance", "maxSize": 100, "maxAge": "365d" } } ngsw-config.json / dataGroups • performance: cache first • freshness: network-first

Slide 25

Slide 25 text

SwUpdate Service constructor(updates: SwUpdate) { // force check for sw update updates.checkForUpdate(); // when sw update available updates.available.subscribe(event => { console.log('current version is', event.current); console.log('available version is', event.available); }); } https://angular.io/guide/service-worker-communications

Slide 26

Slide 26 text

Web Push Notification

Slide 27

Slide 27 text

Why push notifications? • Allow users to opt-in for timely updates • Re-engage users with customised content

Slide 28

Slide 28 text

Push Notifications is… • Notification API - allow pwa display system notification to user • Push API - allow service worker to handle Push Messages from a server, even while the pwa is not active • Both APIs are built on top of Service Worker API.

Slide 29

Slide 29 text

Not all browsers support web push notification yet OS Browsers Android iOS Mac Windows

Slide 30

Slide 30 text

Push Notification Banner Fields https://webengage.com/blog/web-push-notification-guide/

Slide 31

Slide 31 text

SwPush Service constructor(push: SwPush) { push.messages.subscribe(x => { // subscribe & display messages to user console.log('push', x); }); const key = 'VAPID server public key'; // ask for permission push.requestSubscription({ serverPublicKey: key }).then(ps => { // normally these info are save in database console.log(ps.toJSON()); }); }

Slide 32

Slide 32 text

Push Subscription - should be stored in database { endpoint: "https://fcm.googleapis.com/fcm/send/f2WhAQ..", expirationTime: null, keys: { auth: "t1kTHJn_wemTVrA7hq2...", p256dh: "BNeD7NIDj29w9P0q1..." } }

Slide 33

Slide 33 text

Generate VAPID key • Easiest way https://github.com/web-push-libs/web-push • npm install web-push -g • web-push generate-vapid-keys

Slide 34

Slide 34 text

SwPush Service constructor(push: SwPush) { push.messages.subscribe(x => { // subscribe & display messages to user console.log('push', x); }); const key = 'VAPID server public key'; // ask for permission push.requestSubscription({ serverPublicKey: key }).then(ps => { // normally these info are save in database console.log(ps.toJSON()); }); }

Slide 35

Slide 35 text

Example Push Notification object { "notification": { "title": "hello", "body": "blah blah blah" } } • banner info must put under notification property

Slide 36

Slide 36 text

Let’s talk about Progressive? What does it mean?

Slide 37

Slide 37 text

http://www.dictionary.com/browse/progressive

Slide 38

Slide 38 text

+ progressive performance

Slide 39

Slide 39 text

Build the app using prod • Run ng build --prod • Using Ahead of Time compilation • Using Build Optimizer

Slide 40

Slide 40 text

Use Lazy Loading / Preloading • Download the only the code needed to start the app • Preload all the modules by using PreloadAllModules strategy • 100% flexibility with your custom PreloadingStrategy

Slide 41

Slide 41 text

Preloading Strategy @NgModule({ imports: [RouterModule.forRoot(appRoutes, { preloadingStrategy: PreloadAllModules })], exports: [RouterModule] }) app-routing.module.ts

Slide 42

Slide 42 text

Consider Server Side Rendering (SSR) No SSR Load HTML SSR Load HTML Boostrap Boostrap First meaningful Paint Loading First meaningful Paint Loading • Better first load experience

Slide 43

Slide 43 text

How to • ng generate universal --client-project=ssr Long way • ng add @ng-toolkit/universal • npm run build:prod • npm run server Short way Follow the guide here: https://angular.io/guide/universal https://medium.com/@maciejtreder/angular-server-side-rendering-with-ng-toolkit-universal-c08479ca688

Slide 44

Slide 44 text

Tooling & Resources • /ngsw/state - current state of the service worker & log • Workbox - Need more control & flexibility on service worker configuration https://developers.google.com/web/tools/workbox/ • PWA audit tools - lighthouse or page speed insight • Learn service worker by playing games https://serviceworkies.com/

Slide 45

Slide 45 text

No content

Slide 46

Slide 46 text

No content

Slide 47

Slide 47 text

謝謝 https://speakerdeck.com/chybie/angular-pwa-ngtw