23	al	27	de	Octubre	2017.NET	Conf	UY v2017
Progressive	Web	Apps
Nicolás Bello	Camilletti
Lead	Developer
SOUTHWORKS
23	al	27	de	Octubre	2017.NET	Conf	UY v2017
PROGRESSIVEWEBAPP
Es un conjunto de conceptos/herramientas/etc.
WEBCOMONATIVO
No es un concepto nuevo
native web
native web
WEBAPPSENWINDOWS
Pinned Sites
Windows 7
WEBAPPSENWINDOWS
Pinned Sites
Windows 7
Packaged Web Apps
Windows 8
WEBAPPSENWINDOWS
Pinned Sites
Windows 7
Packaged Web Apps
Windows 8
Hosted Web Apps
Windows 10
WEBAPPSENWINDOWS
Pinned Sites
Windows 7
Packaged Web Apps
Windows 8
Progressive Web Apps
Windows 10
Hosted Web Apps
Windows 10
PROGRESSIVEWEBAPP
a.k.a. “PWA”
PWA&ANDROID
Lyft
ride.lyft.com
Lyft
ride.lyft.com
BENEFICIOSDEWEBAPPS
WEBAPPSANDAN
ENCUALQUIERLUGAR!
ONECODEBASETORULETHEMALL…
PWAS=MENORCOSTO(&TIEMPO)
App core
iPhone iPad Publicar en App Store
Android
Phone
Android
Tablet Publicar en Play Store
Windows Publicar en Windows Store
MacOS Publicar en Mac App Store
Web Host
Nativa
Es requerido publicar en los App store
PWAS=MENORCOSTO(&TIEMPO)
PWA
Publicar en los App store es opcional (o por única vez)
Host
Free
Nativa
Es requerido publicar en los App store
App core
iPhone iPad Publicar en App Store
Android
Phone
Android
Tablet Publicar en Play Store
Windows Publicar en Windows Store
MacOS Publicar en Mac App Store
Web Host
App core
iPhone iPad
Android
Phone
Android
Tablet
Windows
MacOS
Web
Other PWA-capable
PRINCIPIOSDEPWA
PWASSONSIMPLEMENTEWEBAPPS…
PWASSONSIMPLEMENTEWEBAPPS…
¡QUEPROVEENDEUNAEXCELENTE
EXPERIENCIADEUSUARIO!
PWAES
PWAES
Progressive
PROGRESSIVE
¿QUÉESPROGRESSIVEENHANCEMENT?
Mono
¿QUÉESPROGRESSIVEENHANCEMENT?
Stereo
¿QUÉESPROGRESSIVEENHANCEMENT?
Surround Sound
¿QUÉESPROGRESSIVEENHANCEMENT?
5.1 Channel
Surround Sound
¿QUÉESPROGRESSIVEENHANCEMENT?
7.1 Channel
Surround Sound
¿QUÉESPROGRESSIVEENHANCEMENT?
16.2 Channel Surround Sound
¿QUÉESPROGRESSIVEENHANCEMENT?
A veces, mono es
la única opción
¿QUÉESPROGRESSIVEENHANCEMENT?
Objectivo &
tareas principales
¿QUÉESPROGRESSIVEENHANCEMENT?
Capacidades
Experiencia
PESEASEGURADEQUELOSUSUARIOS
PUEDANUSARTUPRODUCTO
SINIMPORTARELCONTEXTO.
PROGRESSIVEENHANCEMENTWEB
PROGRESSIVEENHANCEMENTWEB
type="email"
Deltas	de	experiencia
1. ¿Soporta input para email?
2. ¿Algoritmo de	validación implementado?
3. ¿Teclado virtual?
PROGRESSIVEENHANCEMENTWEB
required
Deltas	de	experiencia
1. ¿Soporta validación HTML?
PROGRESSIVEENHANCEMENTWEB
aria-required="true"
Deltas	de	experiencia
1. ¿El navegador expone la propiedad aria-required ?
2. Assistive tech implementation of aria-required?
required validation
email validation
dedicated keyboard
PROGRESSIVEENHANCEMENTWEB
Capabilities
Experience
text input required notification
PESEASEGURADEQUELOSUSUARIOS
PUEDANUSARTUPRODUCTO
SINIMPORTARELCONTEXTO.
PWAES
Progressive Responsive
PWAES
Network
Independent
Progressive Responsive
PWAES
Network
Independent
Progressive Responsive App-Like
PWAOAPPNATIVA?
PWAES
Network
Independent
Progressive Responsive App-Like Fresh
PWAES
Network
Independent
Segura
Progressive Responsive App-Like Fresh
PWAES
Discoverable
Network
Independent
Segura
Progressive Responsive App-Like Fresh
PWAES
Discoverable
Network
Independent
Segura Re-engageable
Progressive Responsive App-Like Fresh
PWAES
Discoverable Instalable
Network
Independent
Segura Re-engageable
Progressive Responsive App-Like Fresh
LAAPPVAASEGUIRANDANDOENEL
BROWSER.SÓLOPODRÍAHACERMÁSCOSAS
CUANDOSE“INSTALE”.
WHATWEBCANDO.TODAY
PWAES
Discoverable Instalable Linkeable
Network
Independent
Segura Re-engageable
Progressive Responsive App-Like Fresh
{
"lang": "en",
"short_name": "My App",
"name": "My Totally Awesome App",
"icons": [
{
"src": "img/launcher-icon-2x.png",
"sizes": "96x96",
"type": "image/png"
}, {
"src": "img/launcher-icon-4x.png",
"sizes": "192x192",
"type": "image/png"
}
],
"start_url": "/pwa/?utm_source=homescreen",
"display": "standalone",
"orientation": "portrait",
"background_color": "black"
}
WEBAPPMANIFEST
Meta Tags 2.0
SERVICEWORKER
Actua como servidor proxy entre la web
app, el browser y la conexión (cuando
está disponible)
Solo HTTPS
No tiene acceso al DOM
Solo se aceptan request asyncronicos
Ejecuta separado del sitio
Un solo service worker por alcance
SERVICE WORKERS
PROPIEDADES
PERO…PUEDOUSARLO?
1. if ('serviceWorker' in navigator) {
2. navigator.serviceWorker.register('/service-worker.js')
3. .then(registration => {
4. console.log('Registered:', registration);
5. })
6. .catch(error => {
7. console.log('Registration failed: ', error);
8. });
9. }
index.html
CICLODEVIDA
Service Worker Lifecycle
Inicia la registraciónInstalling
1. self.addEventListener('install', event => {
2. event.waitUntil(
3. caches.open('static-v1').then(cache => {
4. return cache.addAll([
5. '/',
6. '/index.html',
7. '/styles.css',
8. '/main.js',
9. '/fallback.html'
10. ]);
11. })
12. );
13. }
sw.js
Service Worker Lifecycle
Inicia la registraciónInstalling
Service Worker Lifecycle
Inicia la registraciónInstalling
Se completó la registraciónInstalled
Service Worker Lifecycle
Inicia la registraciónActivating
Inicia la registraciónInstalling
Se completó la registraciónInstalled
1. self.addEventListener('activate', event => {
2. var keepList = ['assets-v1'];
3.
4. event.waitUntil(
5. caches.keys().then(function(cacheNameList) {
6. return Promise.all(cacheNameList.map(function(cacheName) {
7. if (keepList.indexOf(cacheName) === -1) {
8. return caches.delete(cacheName);
9. }
10. }));
11. })
12. );
13. }
sw.js
Service Worker Lifecycle
Inicia la registraciónActivating
Ya se pueden escuchar eventosActivated
Inicia la registraciónInstalling
Se completó la registraciónInstalled
Service Worker Lifecycle
Inicia la registraciónActivating
Ya se pueden escuchar eventosActivated
Inicia la registraciónInstalling
Se completó la registraciónInstalled
El SW se está reemplazando por otroRedundant
1. self.addEventListener('fetch', event => {
2. event.respondWith(
3. caches.match(event.request).then(response => {
4. return response || fetch(event.request).catch(() => {
5. return caches.match('/fallback.htm1');
6. });
7. })
8. );
9. }
sw.js
FETCH!
EXPUESTOAJAVASCRIPT
FETCH(),REQUESTYRESPONSE
1. fetch('weather.json')
2. .then(function(response) {
3. if (response.headers.get('content-type') == 'application/json') {
4. return response.json();
5. } else {
6. throw new TypeError();
7. }
8. })
9. .then(processJSON);
index.html
1. self.addEventListener('fetch', event => {
2. event.respondWith(
3. fetch(event.request)
4. );
5. }
sw.js
1. self.addEventListener('fetch', event => {
2. event.respondWith(
3. fetch(event.request)
4. );
5. }
sw.js
1. self.addEventListener('fetch', event => {
2. event.respondWith(
3. fetch(event.request)
4. );
5. }
sw.js
1. self.addEventListener('fetch', event => {
2. event.respondWith(
3. fetch(event.request)
4. );
5. }
sw.js
CACHEAPIS
CACHES API
ANATOMY
REQUEST	(URL) RESPONSE
https://weather.app/index.html <!doctype html>
https://weather.app/script.js console.log('test')
.	.	.	
key / value storage
Cache API
URL-addressable resources
-----or -----
Indexed DB
Other data
PUSHNOTIFICATIONS
1. navigator.serviceWorker.register('sw.js')
2. .then(reg => {
3. return reg.pushManager.getSubscription().then(subscription => {
4. if (subscription) return subscription;
5. return registration.pushManager.subscribe({
6. userVisibleOnly: true, applicationServerKey: appPubkey
7. });
8. });
9. })
index.html
1. self.addEventListener('push', event => {
2. var payload = event.data ? event.data.text() : 'no payload';
3. event.waitUntil(
4. registration.showNotification('WEATHER ADVISORY', {
5. body: payload,
6. icon: 'icon.png'
7. })
8. );
9. }
sw.js
1. self.addEventListener('notificationclick', event => {
2. event.notification.close();
3. event.waitUntil(clients.openWindow('https://weather.app/advisory'));
4. }
sw.js
PROGRESSIVEWEBAPPS
ENWINDOWS
¿COMOHACEUNUSUARIOPARAENCONTRAR
UNAPROGRESSIVEWEBAPP?
AHORAMISMO:STORE&BING
PROGRESSIVEWEBAPPS
¿¡¿ENWINDOWSSTORE?!?
PWASENWINDOWSSTORE
• Presentación activa
PWASENWINDOWSSTORE
• Presentación activa
• Ingestión Pasiva
No hacer nada y Microsoft va a agregar tu PWA automaticamente *
* Se puede no hacerlo usando robots.txt
PWAINGESTIONPROCESS(PASSIVE)
ANULANDOLAINGESTIÓNCONROBOTS.TXT
PWASIN
THESTORE
app.manifest
popula la entrada:
1. name
2. description
3. icons
4. screenshots
DESDELAPERSPECTIVADELUSUARIO,
UNAPWAVAASERUNAAPP.
¡ANUESTROSUSUARIOSNOLES
INTERESAQUETECNOLOGIAUSAMOS!
Quieren usar nuestra app
UNAPWAESSUPERSIMPLEDEHACERY
LOSBENEFICIOSSONIMPORTANTES.
BIT.LY/PWA-WORKSHOP-NETCONF
Github: https://github.com/PWA-espanol/workshop
¡MUCHASGRACIAS!
@nbellocam
10/26/17 11423	al	27	de	Octubre	2017.NET	Conf	UY v2017

Progressive Web Apps