the future of progressive web apps - google for indonesia
TRANSCRIPT
I'm from Sweden
Credit: https://www.flickr.com/photos/stephenbove/184201987
Service workers allow for offline caching
and instant loading.
Smooth animations, scrolling and
navigations keep the experience silky
smooth.
Push notifications and add to
homescreen help users re-engage.
HTTPS secures the connection between you
and your users.
Reliable Fast Engaging Secure
Progressive Web Apps, today
What about the future?
Credit: https://www.flickr.com/photos/mssarakelly/9422242223
Things we'll talk about today
Knowing who the user is
Credentials Management
Paying for things on the web
Connecting with hardware
Physical Web
Knowing who the user is
Credit: https://commons.wikimedia.org/wiki/File:Steal_password.jpg
Title Text
Password
Forgot password?
Login
LOGIN
Don’t have an account? Sign up!
Did I use that?
$%&§”%$?!
Hm?
Most likely!
Yes, but which one?Email address
Sign Up Form
<form id="signup" action="signup.php" method="post"> <input name="display-name" type="text"> <input name="phone" type="text"> <input name="email" type="text"> <input name="password" type="password"> <input type="submit" value="Sign Up!"> </form>
Friendly name? Identifier? Idunno?
Sign Up Form
<form id="signup" action="signup.php" method="post"> <input name="display-name" type="text" autocomplete="name"> <input name="phone" type="text" autocomplete="home tel"> <input name="email" type="text" autocomplete="username"> <input name="password" type="password"> <input type="submit" value="Sign Up!"> </form>
Aha!
Sign In Form
<form id="login" action="login.php" method="post"> <input name="username" type="text" autocomplete="username"> <input name="password" type="password" autocomplete="current-password"> <input type="submit" value="Sign In!"> </form>
Sign Up Form
<form id="signup" action="signup.php" method="post"> <input name="display-name" type="text" autocomplete="name"> <input name="phone" type="text" autocomplete="home tel"> <input name="email" type="text" autocomplete="username"> <input name="password" type="password" autocomplete="new-password"> <input type="submit" value="Sign Up!"> </form>
the Credentials Management API
Credit: https://commons.wikimedia.org/wiki/File:Michael_de_la_Force_Leaders_Magazine_Press_Credentials_2013.jpg
navigator.credentials.get({ "password": true, "unmediated": true }).then(c => { if (!c) return; // Hooray, we have a credential! signInToYourApplication(c); });
Automatic Sign-in
Chrome will offer automatic sign-in if and only if:
✓Automatic sign-in is enabled
✓Only one credential is saved for the site
Automatic Sign-in
✓navigator.credentials is restricted to secure contexts
✓Passwords are not directly exposed to JavaScript
✓fetch() will only submit credentials to same-site endpoint
function signInToYourApplication(c) { fetch("/signin", { "method": "POST", "credentials": c }).then(r => { if (r.status == 200) renderSignedInExperience(r); else renderUsefulErrorMessage(); });}
navigator.credentials.get({ "password": true }).then(c => { if (!c) return; // Hooray, we have a credential! signInToYourApplication(c); });
var f = document.querySelector("#form");var c = new PasswordCredential(f);navigator.credentials.store(c) .then(_ => { // ... });
var c = new FederatedCredential({ "id": "username", "provider": "https://accounts.google.com"});navigator.credentials.store(c) .then(_ => { // ... });
Paying for things on the web
Credit: http://www.publicdomainpictures.net/view-image.php?image=149197
Card and address saved to Chrome
Automatic form detection
95+ ACCURACY
Form filled automatically
How Autofill works
XYZ
PaymentRequest A W3C API to eliminate checkout forms for users and standardize payment collection for sites
new PaymentRequest( [“visa“, “mastercard“, “amex“, “discover“], { items: [ { id: "basket", label: "Sub-total", amount: { currencyCode: "USD", value: "55.00" }, // $55.00 }, { id: "tax", label: "Sales Tax", amount: { currencyCode: "USD", value: "5.00" }, // $5.00 }, { id: "total", label: "Total excluding shipping", amount: { currencyCode: "USD", value: "60.00" }, // $60.00 } ] }, { requestShipping: true } ).show().then(response => { /* process payment */ }).catch(error => { /* handle */ });
new PaymentRequest( [“visa“, “mastercard“, “amex“, “discover“], { items: [ { id: "basket", label: "Sub-total", amount: { currencyCode: "USD", value: "55.00" }, // $55.00 }, { id: "tax", label: "Sales Tax", amount: { currencyCode: "USD", value: "5.00" }, // $5.00 }, { id: "total", label: "Total excluding shipping", amount: { currencyCode: "USD", value: "60.00" }, // $60.00 } ] }, { requestShipping: true } ).show().then(response => { /* process payment */ }).catch(error => { /* handle */ });
var request = new PaymentRequest( [“visa”, ..., “https://android.com/pay”], // add Android Pay as supported { items: [...] }, { requestShipping: true }, { // add Android Pay application specific parameters "https://android.com/pay": { "gateway": "stripe", "stripe:publishableKey": "put_your_stripe_publishable_key_here", "stripe:version": "2015-10-16 (latest)" } } );
PaymentRequest with Autofill cards in
Chrome Dev Android
PaymentRequest available in Chrome
Beta on mobile; Android Pay
Support for all platforms & 3rd party
payment apps
May 2016 Aug 2016 Early 2017
When can I use PaymentRequest?
Connecting with hardware
Credit: https://en.wikipedia.org/wiki/Open-source_hardware
The evolution of transfer rates
Wi-Fi (Mbps)
802.11: 2802.11b: 11802.11g: 54802.11n: 135
Ethernet (Mbps)
802.3i: 10802.3u: 100802.3ab: 1000802.3an: 10000
Bluetooth (Mbps)
1.1: 12.0: 33.0: 544.0: 0.3
Basic BTLE terms to know...
“Central” device (my phone) “Peripheral” device (candle) GATT (Generic ATTribute profile)
var options = { filters: [{ services: [’battery_service’] }] };
navigator.bluetooth.requestDevice(options).then(device => { console.log(device.name); ...}).catch(error => { console.log(error); });
var options = { filters: [{ services: [’battery_service’] }] };
navigator.bluetooth.requestDevice(options).then(device => device.gatt.connect()).then(server => { ... }).catch(error => { console.log(error); });
var options = { filters: [{ services: [’battery_service'] }] };
navigator.bluetooth.requestDevice(options).then(device => device.gatt.connect()).then(server => server.getPrimaryService(’battery_service’)).then(service => service.getCharacteristic(’battery_level’)).then(characteristic => characteristic.readValue()).then(value => { console.log(’Battery percentage is ’ + value.getUint8(0));}).catch(error => { console.log(error); });
var options = { filters: [{ services: [CANDLE_SERVICE_UUID] }], optionalServices: ['battery_service'] };navigator.bluetooth.requestDevice(options).then(device => device.gatt.connect()).then(server => server.getPrimaryService(CANDLE_SERVICE_UUID)).then(service => service.getCharacteristic(CANDLE_COLOR_UUID)).then(characteristic => { let data = [0x00, r, g, b, 0x05, 0x00, 0x01, 0x00]; return characteristic.writeValue(new Uint8Array(data));}).catch(error => { console.log(error); });
var options = { filters: [{ services: [CANDLE_SERVICE_UUID] }] };
navigator.bluetooth.requestDevice(options).then(device => device.gatt.connect()).then(server => server.getPrimaryService(CANDLE_SERVICE_UUID)).then(service => service.getCharacteristic(CANDLE_BLOW_NOTIFICATIONS_UUID)).then(characteristic => { characteristic.addEventListener(’characteristicvaluechanged’, blow); return characteristic.startNotifications(); }).catch(error => { console.log(error); });
function blow(event) { console.log(event.target.value); }
The Physical Web
http://www.physical-web.org
Credit: https://en.wikipedia.org/wiki/Spider_web
/* Awesomeness to come */
var referringDevice = navigator.bluetooth.referringDevice;
if (referringDevice) { referringDevice.gatt.connect() .then(server => { ... }) .catch(error => { console.log(error); });}
Tell us what you needReport bug https://crbug.com
Feature statushttps://chromestatus.com
Slackhttps://goo.gl/jCWx5m
Videos https://www.youtube.com/user/ChromeDevelopers
@ChromiumDev