SlideShare una empresa de Scribd logo
1 de 100
Descargar para leer sin conexión
Host your own
Over-the-air update service
Roadmap
Buggy Valley App
Glorified cURLing App
Designing an OTA Service
Hosting Your Own Service
OTA Assets
Announcements
Pillar Valley
Pillar Valley
Pillar Valley
My Awesome App
Standing on the shoulders
of giants
Pillar Valley
Buggy Valley
Buggy Valley
$
p = 0.5
$$
Nothingp = 0.5
Buggy Valley
p = 0.5
p = 0.5
Android Java Implementation
String redScreenPath = “file:///red-screen.js”;
String pillarValleyPath = “file:///pillar-valley.js”;
Android Java Implementation
String redScreenPath = “file:///red-screen.js”;
String pillarValleyPath = “file:///pillar-valley.js”;
int randNum = getRandom();
if (isEven(randNum)){
loadApp(redScreenPath);
} else {
loadApp(pillarValleyPath);
}
Android Java Implementation
String redScreenPath = “file:///red-screen.js”;
String pillarValleyPath = “file:///pillar-valley.js”;
int randNum = getRandom();
if (isEven(randNum)){
loadApp(redScreenPath);
} else {
loadApp(pillarValleyPath);**
}
** how does loadApp work?
Quick Recap
String redScreenPath = “file:///red-screen.js”;
String pillarValleyPath = “file:///pillar-valley.js”;
int randNum = getRandom();
if (isEven(randNum)){
loadApp(redScreenPath);
} else {
loadApp(pillarValleyPath);**
}
** how does loadApp work?
Roadmap
Buggy Valley App
Glorified cURLing App
Designing an OTA Service
Hosting Your Own Service
OTA Assets
Announcements
Buggy Valley fits in perfectly with my use case.
Your MVP was just what I needed!
One small suggestion tho...
Original Buggy Valley
String redScreenPath = “file:///red-screen.js”;
String pillarValleyPath = “file:///pillar-valley.js”;
int randNum = getRandom();
if (isEven(randNum)){
loadApp(redScreenPath);
} else {
loadApp(pillarValleyPath);
}
Modified Buggy Valley
String redScreenPath = “file:///red-screen.js”;
String aliceAppPath = “file:///alice-app.js”;
int randNum = getRandom();
if (isEven(randNum)){
loadApp(redScreenPath);
} else {
loadApp(aliceAppPath);
}
Modified Buggy Valley
String redScreenPath = “file:///red-screen.js”;
String aliceAppPath = “file:///alice-app.js”;
int randNum = getRandom();
if (isEven(randNum)){
loadApp(redScreenPath);
} else {
loadApp(aliceAppPath);
}
Modified Buggy Valley
String newAliceAppPath
String aliceAppPath = “file:///alice-app.js”;
int randNum = getRandom();
if (isEven(randNum)){
loadApp(newAliceAppPath);
} else {
loadApp(aliceAppPath);
}
Modified Buggy Valley
String newAliceAppPath = cURLToDisk(“https://expo.io/@alice/app”);
String aliceAppPath = “file:///alice-app.js”;
int randNum = getRandom();
if (isEven(randNum)){
loadApp(newAliceAppPath);
} else {
loadApp(aliceAppPath);
}
Modified Buggy Valley
String newAliceAppPath = cURLToDisk(“https://expo.io/@alice/app”);
String aliceAppPath = “file:///alice-app.js”;
int randNum = getRandom();
if (isEven(randNum)){
loadApp(newAliceAppPath);
} else {
loadApp(aliceAppPath);
}
Glorified cURL
String newAliceAppPath = cURLToDisk(“https://expo.io/@alice/app”);
String aliceAppPath = “file:///alice-app.js”;
if (newAliceAppPath != null){
loadApp(newAliceAppPath);
} else {
loadApp(aliceAppPath);
}
Wait but how does this benefit me?
JS Bundle
Native Modules
Currently on disk:
JS Bundle
Native Modules
Currently on disk:
Traditional update
New JS Bundle
New Native Modules
JS Bundle
Native Modules
Currently on disk:
Traditional update
New JS Bundle
New Native Modules
Avg binary size ~30Mb
JS Bundle
Native Modules
Currently on disk:
JS Bundle
Native Modules
Currently on disk:
Glorified cURL update
New JS Bundle
Native Modules
Roadmap
Buggy Valley App
Glorified cURLing App
Designing an OTA Service
Hosting Your Own Service
OTA Assets
Announcements
Glorified cURL fits in perfectly with my use case.
Your MVP was just what I needed!
It’s not very performant tho...
Glorified cURL
String newBobAppPath = cURLToDisk(“https://expo.io/@bob/app”);
String bobAppPath = “file:///bob-app.js”;
if (newBobAppPath != null){
loadApp(newBobAppPath);
} else {
loadApp(bobAppPath);
}
Glorified cURL
String newBobAppPath = cURLToDisk(“https://expo.io/@bob/app”);
String bobAppPath = “file:///bob-app.js”;
if (newBobAppPath != null){
loadApp(newBobAppPath);
} else {
loadApp(bobAppPath);
}
JS Bundle
We don’t want to load the JS bundle unnecessarily.
We only want to load the JS bundle if there’s a new change available.
Let’s take a step back
And think about how the web
works for a sec
The Web
<script src=“bundle.js” />
Big JS bundle
bundle.js
index.html
Taking a page out of the web book
{bundleUrl: ‘bundle.js’}
Big JS bundle
bundle.js
index.json
Taking a page out of the web book
{bundleUrl: ‘ios-1a2b3c.js’}
Big JS bundle
ios-1a2b3c.js
index.json
Bundle name is based off its md5 hash
Taking a page out of the web book
{bundleUrl: ‘ios-7a8b9c’}
Big JS bundle
ios-7a8b9c.js
index.json
Cache the bundleUrl
Only download bundleUrl
if we don’t have it cached
How do I use an OTA service in my app?
^ these are my app files
^ this is what my app looks like
How do I use an OTA service in my app?
dev tools GUI
^ push this button to upload app to expo server
How do I use an OTA service in my app?
Or use the cli if you prefer
> expo publish
Run this command in your project directory to upload to expo servers
How often is the server polled for updates?
The default behavior is to poll the server when the app starts up
What if I don’t like the default behavior?
You can use the Updates module to customize when you’d to update your app
^ from the docs page
Roadmap
Buggy Valley App
Glorified cURLing App
Designing an OTA Service
Hosting Your Own Service
OTA Assets
Announcements
I’m in a country where network latency
to your CDNs are really high
I’m in a country where network latency
to your CDNs are really high
How about hosting your own app then?
I’m in a country where network latency
to your CDNs are really high
How about hosting your own app then?*
* in our upcoming SDK release
How do I host my own app?
^ these are my app files
^ this is what my app looks like
> expo export
Run this command in your project directory
to dump your app to disk
How do I host my own app?
This is what gets dumped to disk
How do I host my own app?
.
├── android-index.json
├── ios-index.json
├── assets
│   └── 1ecc2
└── bundles
      ├── android-01ee6.js
      └── ios-ee820.js
How do I host my own app?
.
├── android-index.json
├── ios-index.json
├── assets
│   └── 1ecc2
└── bundles
      ├── android-01ee6.js
      └── ios-ee820.js
How do I host my own app?
.
├── android-index.json
├── ios-index.json
├── assets
│   └── 1ecc2
└── bundles
      ├── android-01ee6.js
      └── ios-ee820.js
{bundleUrl: ‘ios-ee820.js’}
Big JS bundle
ios-ee820.js
ios-index.json
How do I host my own app?
.
├── android-index.json
├── ios-index.json
├── assets
│   └── 1ecc2
└── bundles
      ├── android-01ee6.js
      └── ios-ee820.js
git push master
I pushed to GitHub because it has free static hosting.
You can host your app from any server.
How do I build my app binary?
> expo build:ios
Run this command in your project directory
How do I build my app binary?
> expo build:ios —public-url https://quinlanj.github.io/self-hosting/ios-index.json
Run this command in your project directory
How do I build my app binary?
> expo build:ios —public-url https://quinlanj.github.io/self-hosting/ios-index.json
{bundleUrl: ‘ios-ee820.js’}
Big JS bundle
ios-ee820.js
ios-index.json
^ This file is served first
Press this button
To download
How do I use this in development?
https://quinlanj.github.io/selfhost/ios-index.json
Convert to QR code
How do I use this in development?
Scan the QR code into the expo dev app
How do I use this in development?
http://localhost:8000/ios-index.json
Convert to QR code
How do I use this in development?
Scan the QR code into the expo dev app
Roadmap
Buggy Valley App
Glorified cURLing App
Designing an OTA Service
Hosting Your Own Service
OTA Assets
Announcements
This is what my app looks like.
I’ve installed it on my phone.
In development, let’s make a change by adding another pic
Push changes to GitHub
This is what my app looks like.
I’ve installed it on my phone.
This is what my app looks like.
I’ve installed it on my phone.
Currently on filesystem:
JS Bundle
This is what my app looks like.
I’ve installed it on my phone.
Currently on filesystem:
JS Bundle
quinlanj.github.io
Here is the server hosting my app
This is what my app looks like.
I’ve installed it on my phone.
Currently on filesystem:
JS Bundle
quinlanj.github.io
An update is ready!
This is what my app looks like.
I’ve installed it on my phone.
Currently on filesystem:
JS Bundle
quinlanj.github.io
An update is ready!
Files to be served:
New
JS Bundle
This is what my app looks like.
I’ve installed it on my phone.
Currently on filesystem:
JS Bundle
quinlanj.github.io
An update is ready!
Files to be served:
New
JS Bundle
JS Bundle
This is what my app looks like.
I’ve installed it on my phone.
Currently on filesystem:
quinlanj.github.io
An update is ready!
Files to be served:
New
JS Bundle
New
JS Bundle
<Image source={require(‘cat.png’} />
<Image source={require(‘dog.png’} />
This is what my app looks like.
I’ve installed it on my phone.
Currently on filesystem:
quinlanj.github.io
An update is ready!
Files to be served:
New
JS Bundle
?
dog.png is pulled down to filesystem?
New
JS Bundle
<Image source={require(‘cat.png’} />
<Image source={require(‘dog.png’} />
But how? It looks like these assets are fetched from filesystem
New
JS Bundle
<Image source={require(‘cat.png’} />
<Image source={require(‘dog.png’} />
We wrote a module to override asset resolution
New
JS Bundle
<Image source={require(‘cat.png’} />
<Image source={require(‘dog.png’} />
Module Logic:
Look for asset in the filesystem
If it’s not there, look for it from the server
This is what my app looks like.
I’ve installed it on my phone.
Currently on filesystem:
quinlanj.github.io
An update is ready!
Files to be served:
New
JS Bundle
?
dog.png is pulled down to filesystem?
This is what my app looks like.
I’ve installed it on my phone.
Currently on filesystem:
quinlanj.github.io
An update is ready!
Files to be served:
New
JS Bundle
?
dog.png is not on the filesystem
This is what my app looks like.
I’ve installed it on my phone.
Currently on filesystem:
quinlanj.github.io
An update is ready!
Files to be served:
New
JS Bundle
?
Let’s grab dog.png from server then!
This is what my app looks like.
I’ve installed it on my phone.
Currently on filesystem:
quinlanj.github.io
An update is ready!
Files to be served:
New
JS Bundle
This is what my app looks like.
I’ve installed it on my phone.
Currently on filesystem:
quinlanj.github.io
An update is ready!
Files to be served:
New
JS Bundle
Cached for future use
How come assets are stored by hash?
.
├── android-index.json
├── ios-index.json
├── assets
│   └── 1ecc2
└── bundles
      ├── android-01ee6.js
      └── ios-ee820.js
JS Bundle
<Image source={require(‘cat.png’)} />
We are requiring assets by their name, not by their hash
JS Bundle
require(‘cat.png’)
React native packager
{assetName: ‘cat.png’, hash:’1ecc2’}
App packaging
App.js
JS Bundle
<Image source={require(‘cat.png’} />
Module Logic:
Look for cat.png in the filesystem
If it’s not there, look for cat.png from the server
Recall
JS Bundle
Module Logic:
Look for 1ecc2 in the filesystem
If it’s not there, look for 1ecc2 from the server
Actual Implementation
{assetName: ‘cat.png’, hash:’1ecc2’}
How does this benefit me?
<Image source={require(‘cat1.png’} />
<Image source={require(‘crazy-cat.png’} />
<Image source={require(‘lime-cat.png’} />
…
This app displays the same cat picture
These cat pictures are all named something different
{assetName: ‘cat1.png’, hash:’1ecc2’}
{assetName: ‘crazy-cat.png’, hash:’1ecc2’}
{assetName: ‘lime-cat.png’, hash:’1ecc2’}
…
They all resolve to the same file on disk: 1ecc2
Roadmap
Buggy Valley App
Glorified cURLing App
Designing an OTA Service
Hosting Your Own Service
OTA Assets
Announcements
Announcements
We made a web application called Snack
Snack is like a JS Fiddle for react native apps
Snack is now open source, check it out at https://github.com/expo/snack-web

Más contenido relacionado

La actualidad más candente

Webinar presentation on AUTOSAR Multicore Systems
Webinar presentation on AUTOSAR Multicore SystemsWebinar presentation on AUTOSAR Multicore Systems
Webinar presentation on AUTOSAR Multicore SystemsKPIT
 
What is AUTOSAR MCAL? Learn about the software module architecture and device...
What is AUTOSAR MCAL? Learn about the software module architecture and device...What is AUTOSAR MCAL? Learn about the software module architecture and device...
What is AUTOSAR MCAL? Learn about the software module architecture and device...Embitel Technologies (I) PVT LTD
 
Automotive embedded systems part7 v1
Automotive embedded systems part7 v1Automotive embedded systems part7 v1
Automotive embedded systems part7 v1Keroles karam khalil
 
Diagnostic in Adaptive AUTOSAR
Diagnostic in Adaptive AUTOSARDiagnostic in Adaptive AUTOSAR
Diagnostic in Adaptive AUTOSARBernhard Wagner
 
Automotive Cybersecurity: Test Like a Hacker
Automotive Cybersecurity: Test Like a HackerAutomotive Cybersecurity: Test Like a Hacker
Automotive Cybersecurity: Test Like a HackerForAllSecure
 
What is AUTOSAR Communication Stack (ComStack)?Get introduced to CAN ComStack
What is AUTOSAR Communication Stack (ComStack)?Get introduced to CAN ComStackWhat is AUTOSAR Communication Stack (ComStack)?Get introduced to CAN ComStack
What is AUTOSAR Communication Stack (ComStack)?Get introduced to CAN ComStackEmbitel Technologies (I) PVT LTD
 
Vector red bend_webinar_flashing_over_the_air_and_delta_technology_20140121_en
Vector red bend_webinar_flashing_over_the_air_and_delta_technology_20140121_enVector red bend_webinar_flashing_over_the_air_and_delta_technology_20140121_en
Vector red bend_webinar_flashing_over_the_air_and_delta_technology_20140121_enRed Bend Software
 
Ids sdd-jlr manual 02 02-12 (1)
Ids sdd-jlr manual 02 02-12 (1)Ids sdd-jlr manual 02 02-12 (1)
Ids sdd-jlr manual 02 02-12 (1)Boualam Mohammed
 
What is AUTOSAR Memory Stack | Software modules and device drivers
What is AUTOSAR Memory Stack | Software modules and device driversWhat is AUTOSAR Memory Stack | Software modules and device drivers
What is AUTOSAR Memory Stack | Software modules and device driversEmbitel Technologies (I) PVT LTD
 
Automotive embedded systems part8 v1
Automotive embedded systems part8 v1Automotive embedded systems part8 v1
Automotive embedded systems part8 v1Keroles karam khalil
 
Automotive embedded systems part5 v1
Automotive embedded systems part5 v1Automotive embedded systems part5 v1
Automotive embedded systems part5 v1Keroles karam khalil
 

La actualidad más candente (20)

FOTA Upgrade on Automotive and IoT Industry
FOTA Upgrade on Automotive and IoT IndustryFOTA Upgrade on Automotive and IoT Industry
FOTA Upgrade on Automotive and IoT Industry
 
What is AUTOSAR Communiation Stack
What is AUTOSAR Communiation StackWhat is AUTOSAR Communiation Stack
What is AUTOSAR Communiation Stack
 
Webinar presentation on AUTOSAR Multicore Systems
Webinar presentation on AUTOSAR Multicore SystemsWebinar presentation on AUTOSAR Multicore Systems
Webinar presentation on AUTOSAR Multicore Systems
 
What is AUTOSAR MCAL? Learn about the software module architecture and device...
What is AUTOSAR MCAL? Learn about the software module architecture and device...What is AUTOSAR MCAL? Learn about the software module architecture and device...
What is AUTOSAR MCAL? Learn about the software module architecture and device...
 
Automotive embedded systems part7 v1
Automotive embedded systems part7 v1Automotive embedded systems part7 v1
Automotive embedded systems part7 v1
 
Automotive telematics
Automotive telematicsAutomotive telematics
Automotive telematics
 
Diagnostic in Adaptive AUTOSAR
Diagnostic in Adaptive AUTOSARDiagnostic in Adaptive AUTOSAR
Diagnostic in Adaptive AUTOSAR
 
Automotive Cybersecurity: Test Like a Hacker
Automotive Cybersecurity: Test Like a HackerAutomotive Cybersecurity: Test Like a Hacker
Automotive Cybersecurity: Test Like a Hacker
 
What is AUTOSAR Communication Stack (ComStack)?Get introduced to CAN ComStack
What is AUTOSAR Communication Stack (ComStack)?Get introduced to CAN ComStackWhat is AUTOSAR Communication Stack (ComStack)?Get introduced to CAN ComStack
What is AUTOSAR Communication Stack (ComStack)?Get introduced to CAN ComStack
 
Flash Bootloader Development for ECU programming
Flash Bootloader Development for ECU programmingFlash Bootloader Development for ECU programming
Flash Bootloader Development for ECU programming
 
Autosar MCAL (Microcontroller Abstraction Layer)
Autosar MCAL (Microcontroller Abstraction Layer)Autosar MCAL (Microcontroller Abstraction Layer)
Autosar MCAL (Microcontroller Abstraction Layer)
 
Vector red bend_webinar_flashing_over_the_air_and_delta_technology_20140121_en
Vector red bend_webinar_flashing_over_the_air_and_delta_technology_20140121_enVector red bend_webinar_flashing_over_the_air_and_delta_technology_20140121_en
Vector red bend_webinar_flashing_over_the_air_and_delta_technology_20140121_en
 
Ids sdd-jlr manual 02 02-12 (1)
Ids sdd-jlr manual 02 02-12 (1)Ids sdd-jlr manual 02 02-12 (1)
Ids sdd-jlr manual 02 02-12 (1)
 
What is AUTOSAR Memory Stack | Software modules and device drivers
What is AUTOSAR Memory Stack | Software modules and device driversWhat is AUTOSAR Memory Stack | Software modules and device drivers
What is AUTOSAR Memory Stack | Software modules and device drivers
 
What is IVI (In Vehicle Infotainment)?
What is IVI (In Vehicle Infotainment)?What is IVI (In Vehicle Infotainment)?
What is IVI (In Vehicle Infotainment)?
 
Automotive Telematics
Automotive TelematicsAutomotive Telematics
Automotive Telematics
 
Automotive embedded systems part8 v1
Automotive embedded systems part8 v1Automotive embedded systems part8 v1
Automotive embedded systems part8 v1
 
AUTOSAR Memory Stcak (MemStack).
AUTOSAR Memory Stcak (MemStack). AUTOSAR Memory Stcak (MemStack).
AUTOSAR Memory Stcak (MemStack).
 
Automotive embedded systems part5 v1
Automotive embedded systems part5 v1Automotive embedded systems part5 v1
Automotive embedded systems part5 v1
 
Autosar Basics hand book_v1
Autosar Basics  hand book_v1Autosar Basics  hand book_v1
Autosar Basics hand book_v1
 

Similar a Hosting Your Own OTA Update Service

Deploying Symfony | symfony.cat
Deploying Symfony | symfony.catDeploying Symfony | symfony.cat
Deploying Symfony | symfony.catPablo Godel
 
TLS303 How to Deploy Python Applications on AWS Elastic Beanstalk - AWS re:In...
TLS303 How to Deploy Python Applications on AWS Elastic Beanstalk - AWS re:In...TLS303 How to Deploy Python Applications on AWS Elastic Beanstalk - AWS re:In...
TLS303 How to Deploy Python Applications on AWS Elastic Beanstalk - AWS re:In...Amazon Web Services
 
AWS CodeDeploy - basic intro
AWS CodeDeploy - basic introAWS CodeDeploy - basic intro
AWS CodeDeploy - basic introAnton Babenko
 
Обход проверки безопасности в магазинах мобильных приложений при помощи платф...
Обход проверки безопасности в магазинах мобильных приложений при помощи платф...Обход проверки безопасности в магазинах мобильных приложений при помощи платф...
Обход проверки безопасности в магазинах мобильных приложений при помощи платф...Positive Hack Days
 
Appium workship, Mobile Web+Dev Conference
Appium workship,  Mobile Web+Dev ConferenceAppium workship,  Mobile Web+Dev Conference
Appium workship, Mobile Web+Dev ConferenceIsaac Murchie
 
Appium mobile web+dev conference
Appium   mobile web+dev conferenceAppium   mobile web+dev conference
Appium mobile web+dev conferenceIsaac Murchie
 
Cannibalising The Google App Engine
Cannibalising The  Google  App  EngineCannibalising The  Google  App  Engine
Cannibalising The Google App Enginecatherinewall
 
(ARC402) Deployment Automation: From Developers' Keyboards to End Users' Scre...
(ARC402) Deployment Automation: From Developers' Keyboards to End Users' Scre...(ARC402) Deployment Automation: From Developers' Keyboards to End Users' Scre...
(ARC402) Deployment Automation: From Developers' Keyboards to End Users' Scre...Amazon Web Services
 
Torquebox @ Raleigh.rb - April 2011
Torquebox @ Raleigh.rb - April 2011Torquebox @ Raleigh.rb - April 2011
Torquebox @ Raleigh.rb - April 2011tobiascrawley
 
[QE 2018] Adam Stasiak – Nadchodzi React Native – czyli o testowaniu mobilnyc...
[QE 2018] Adam Stasiak – Nadchodzi React Native – czyli o testowaniu mobilnyc...[QE 2018] Adam Stasiak – Nadchodzi React Native – czyli o testowaniu mobilnyc...
[QE 2018] Adam Stasiak – Nadchodzi React Native – czyli o testowaniu mobilnyc...Future Processing
 
Symfony Deployments on Heroku
Symfony Deployments on HerokuSymfony Deployments on Heroku
Symfony Deployments on HerokuStefan Adolf
 
Node Summit 2018: Cloud Native Node.js
Node Summit 2018: Cloud Native Node.jsNode Summit 2018: Cloud Native Node.js
Node Summit 2018: Cloud Native Node.jsChris Bailey
 
Silicon Valley Code Camp 2019 - Reaching the Cloud Native World
Silicon Valley Code Camp 2019 - Reaching the Cloud Native WorldSilicon Valley Code Camp 2019 - Reaching the Cloud Native World
Silicon Valley Code Camp 2019 - Reaching the Cloud Native WorldChris Bailey
 
Torquebox Asheville.rb April 2011
Torquebox Asheville.rb April 2011Torquebox Asheville.rb April 2011
Torquebox Asheville.rb April 2011Lance Ball
 
Running Microservices and Docker on AWS Elastic Beanstalk - August 2016 Month...
Running Microservices and Docker on AWS Elastic Beanstalk - August 2016 Month...Running Microservices and Docker on AWS Elastic Beanstalk - August 2016 Month...
Running Microservices and Docker on AWS Elastic Beanstalk - August 2016 Month...Amazon Web Services
 
Running Microservices on AWS Elastic Beanstalk
Running Microservices on AWS Elastic BeanstalkRunning Microservices on AWS Elastic Beanstalk
Running Microservices on AWS Elastic BeanstalkAmazon Web Services
 
Nodejs Intro - Part2 Introduction to Web Applications
Nodejs Intro - Part2 Introduction to Web ApplicationsNodejs Intro - Part2 Introduction to Web Applications
Nodejs Intro - Part2 Introduction to Web ApplicationsBudh Ram Gurung
 
Can I Contain This?
Can I Contain This?Can I Contain This?
Can I Contain This?Eficode
 
Modern Web Application Development Workflow - EclipseCon France 2014
Modern Web Application Development Workflow - EclipseCon France 2014Modern Web Application Development Workflow - EclipseCon France 2014
Modern Web Application Development Workflow - EclipseCon France 2014Stéphane Bégaudeau
 

Similar a Hosting Your Own OTA Update Service (20)

Deploying Symfony | symfony.cat
Deploying Symfony | symfony.catDeploying Symfony | symfony.cat
Deploying Symfony | symfony.cat
 
TLS303 How to Deploy Python Applications on AWS Elastic Beanstalk - AWS re:In...
TLS303 How to Deploy Python Applications on AWS Elastic Beanstalk - AWS re:In...TLS303 How to Deploy Python Applications on AWS Elastic Beanstalk - AWS re:In...
TLS303 How to Deploy Python Applications on AWS Elastic Beanstalk - AWS re:In...
 
AWS CodeDeploy - basic intro
AWS CodeDeploy - basic introAWS CodeDeploy - basic intro
AWS CodeDeploy - basic intro
 
Обход проверки безопасности в магазинах мобильных приложений при помощи платф...
Обход проверки безопасности в магазинах мобильных приложений при помощи платф...Обход проверки безопасности в магазинах мобильных приложений при помощи платф...
Обход проверки безопасности в магазинах мобильных приложений при помощи платф...
 
Appium workship, Mobile Web+Dev Conference
Appium workship,  Mobile Web+Dev ConferenceAppium workship,  Mobile Web+Dev Conference
Appium workship, Mobile Web+Dev Conference
 
Appium mobile web+dev conference
Appium   mobile web+dev conferenceAppium   mobile web+dev conference
Appium mobile web+dev conference
 
Cannibalising The Google App Engine
Cannibalising The  Google  App  EngineCannibalising The  Google  App  Engine
Cannibalising The Google App Engine
 
(ARC402) Deployment Automation: From Developers' Keyboards to End Users' Scre...
(ARC402) Deployment Automation: From Developers' Keyboards to End Users' Scre...(ARC402) Deployment Automation: From Developers' Keyboards to End Users' Scre...
(ARC402) Deployment Automation: From Developers' Keyboards to End Users' Scre...
 
Mojolicious
MojoliciousMojolicious
Mojolicious
 
Torquebox @ Raleigh.rb - April 2011
Torquebox @ Raleigh.rb - April 2011Torquebox @ Raleigh.rb - April 2011
Torquebox @ Raleigh.rb - April 2011
 
[QE 2018] Adam Stasiak – Nadchodzi React Native – czyli o testowaniu mobilnyc...
[QE 2018] Adam Stasiak – Nadchodzi React Native – czyli o testowaniu mobilnyc...[QE 2018] Adam Stasiak – Nadchodzi React Native – czyli o testowaniu mobilnyc...
[QE 2018] Adam Stasiak – Nadchodzi React Native – czyli o testowaniu mobilnyc...
 
Symfony Deployments on Heroku
Symfony Deployments on HerokuSymfony Deployments on Heroku
Symfony Deployments on Heroku
 
Node Summit 2018: Cloud Native Node.js
Node Summit 2018: Cloud Native Node.jsNode Summit 2018: Cloud Native Node.js
Node Summit 2018: Cloud Native Node.js
 
Silicon Valley Code Camp 2019 - Reaching the Cloud Native World
Silicon Valley Code Camp 2019 - Reaching the Cloud Native WorldSilicon Valley Code Camp 2019 - Reaching the Cloud Native World
Silicon Valley Code Camp 2019 - Reaching the Cloud Native World
 
Torquebox Asheville.rb April 2011
Torquebox Asheville.rb April 2011Torquebox Asheville.rb April 2011
Torquebox Asheville.rb April 2011
 
Running Microservices and Docker on AWS Elastic Beanstalk - August 2016 Month...
Running Microservices and Docker on AWS Elastic Beanstalk - August 2016 Month...Running Microservices and Docker on AWS Elastic Beanstalk - August 2016 Month...
Running Microservices and Docker on AWS Elastic Beanstalk - August 2016 Month...
 
Running Microservices on AWS Elastic Beanstalk
Running Microservices on AWS Elastic BeanstalkRunning Microservices on AWS Elastic Beanstalk
Running Microservices on AWS Elastic Beanstalk
 
Nodejs Intro - Part2 Introduction to Web Applications
Nodejs Intro - Part2 Introduction to Web ApplicationsNodejs Intro - Part2 Introduction to Web Applications
Nodejs Intro - Part2 Introduction to Web Applications
 
Can I Contain This?
Can I Contain This?Can I Contain This?
Can I Contain This?
 
Modern Web Application Development Workflow - EclipseCon France 2014
Modern Web Application Development Workflow - EclipseCon France 2014Modern Web Application Development Workflow - EclipseCon France 2014
Modern Web Application Development Workflow - EclipseCon France 2014
 

Último

Kotlin Multiplatform & Compose Multiplatform - Starter kit for pragmatics
Kotlin Multiplatform & Compose Multiplatform - Starter kit for pragmaticsKotlin Multiplatform & Compose Multiplatform - Starter kit for pragmatics
Kotlin Multiplatform & Compose Multiplatform - Starter kit for pragmaticscarlostorres15106
 
Scaling API-first – The story of a global engineering organization
Scaling API-first – The story of a global engineering organizationScaling API-first – The story of a global engineering organization
Scaling API-first – The story of a global engineering organizationRadu Cotescu
 
From Event to Action: Accelerate Your Decision Making with Real-Time Automation
From Event to Action: Accelerate Your Decision Making with Real-Time AutomationFrom Event to Action: Accelerate Your Decision Making with Real-Time Automation
From Event to Action: Accelerate Your Decision Making with Real-Time AutomationSafe Software
 
Automating Business Process via MuleSoft Composer | Bangalore MuleSoft Meetup...
Automating Business Process via MuleSoft Composer | Bangalore MuleSoft Meetup...Automating Business Process via MuleSoft Composer | Bangalore MuleSoft Meetup...
Automating Business Process via MuleSoft Composer | Bangalore MuleSoft Meetup...shyamraj55
 
08448380779 Call Girls In Friends Colony Women Seeking Men
08448380779 Call Girls In Friends Colony Women Seeking Men08448380779 Call Girls In Friends Colony Women Seeking Men
08448380779 Call Girls In Friends Colony Women Seeking MenDelhi Call girls
 
SQL Database Design For Developers at php[tek] 2024
SQL Database Design For Developers at php[tek] 2024SQL Database Design For Developers at php[tek] 2024
SQL Database Design For Developers at php[tek] 2024Scott Keck-Warren
 
Tech-Forward - Achieving Business Readiness For Copilot in Microsoft 365
Tech-Forward - Achieving Business Readiness For Copilot in Microsoft 365Tech-Forward - Achieving Business Readiness For Copilot in Microsoft 365
Tech-Forward - Achieving Business Readiness For Copilot in Microsoft 3652toLead Limited
 
Presentation on how to chat with PDF using ChatGPT code interpreter
Presentation on how to chat with PDF using ChatGPT code interpreterPresentation on how to chat with PDF using ChatGPT code interpreter
Presentation on how to chat with PDF using ChatGPT code interpreternaman860154
 
04-2024-HHUG-Sales-and-Marketing-Alignment.pptx
04-2024-HHUG-Sales-and-Marketing-Alignment.pptx04-2024-HHUG-Sales-and-Marketing-Alignment.pptx
04-2024-HHUG-Sales-and-Marketing-Alignment.pptxHampshireHUG
 
Pigging Solutions in Pet Food Manufacturing
Pigging Solutions in Pet Food ManufacturingPigging Solutions in Pet Food Manufacturing
Pigging Solutions in Pet Food ManufacturingPigging Solutions
 
Swan(sea) Song – personal research during my six years at Swansea ... and bey...
Swan(sea) Song – personal research during my six years at Swansea ... and bey...Swan(sea) Song – personal research during my six years at Swansea ... and bey...
Swan(sea) Song – personal research during my six years at Swansea ... and bey...Alan Dix
 
Breaking the Kubernetes Kill Chain: Host Path Mount
Breaking the Kubernetes Kill Chain: Host Path MountBreaking the Kubernetes Kill Chain: Host Path Mount
Breaking the Kubernetes Kill Chain: Host Path MountPuma Security, LLC
 
Transforming Data Streams with Kafka Connect: An Introduction to Single Messa...
Transforming Data Streams with Kafka Connect: An Introduction to Single Messa...Transforming Data Streams with Kafka Connect: An Introduction to Single Messa...
Transforming Data Streams with Kafka Connect: An Introduction to Single Messa...HostedbyConfluent
 
Factors to Consider When Choosing Accounts Payable Services Providers.pptx
Factors to Consider When Choosing Accounts Payable Services Providers.pptxFactors to Consider When Choosing Accounts Payable Services Providers.pptx
Factors to Consider When Choosing Accounts Payable Services Providers.pptxKatpro Technologies
 
Neo4j - How KGs are shaping the future of Generative AI at AWS Summit London ...
Neo4j - How KGs are shaping the future of Generative AI at AWS Summit London ...Neo4j - How KGs are shaping the future of Generative AI at AWS Summit London ...
Neo4j - How KGs are shaping the future of Generative AI at AWS Summit London ...Neo4j
 
Install Stable Diffusion in windows machine
Install Stable Diffusion in windows machineInstall Stable Diffusion in windows machine
Install Stable Diffusion in windows machinePadma Pradeep
 
08448380779 Call Girls In Diplomatic Enclave Women Seeking Men
08448380779 Call Girls In Diplomatic Enclave Women Seeking Men08448380779 Call Girls In Diplomatic Enclave Women Seeking Men
08448380779 Call Girls In Diplomatic Enclave Women Seeking MenDelhi Call girls
 
How to Troubleshoot Apps for the Modern Connected Worker
How to Troubleshoot Apps for the Modern Connected WorkerHow to Troubleshoot Apps for the Modern Connected Worker
How to Troubleshoot Apps for the Modern Connected WorkerThousandEyes
 
Key Features Of Token Development (1).pptx
Key  Features Of Token  Development (1).pptxKey  Features Of Token  Development (1).pptx
Key Features Of Token Development (1).pptxLBM Solutions
 
Unblocking The Main Thread Solving ANRs and Frozen Frames
Unblocking The Main Thread Solving ANRs and Frozen FramesUnblocking The Main Thread Solving ANRs and Frozen Frames
Unblocking The Main Thread Solving ANRs and Frozen FramesSinan KOZAK
 

Último (20)

Kotlin Multiplatform & Compose Multiplatform - Starter kit for pragmatics
Kotlin Multiplatform & Compose Multiplatform - Starter kit for pragmaticsKotlin Multiplatform & Compose Multiplatform - Starter kit for pragmatics
Kotlin Multiplatform & Compose Multiplatform - Starter kit for pragmatics
 
Scaling API-first – The story of a global engineering organization
Scaling API-first – The story of a global engineering organizationScaling API-first – The story of a global engineering organization
Scaling API-first – The story of a global engineering organization
 
From Event to Action: Accelerate Your Decision Making with Real-Time Automation
From Event to Action: Accelerate Your Decision Making with Real-Time AutomationFrom Event to Action: Accelerate Your Decision Making with Real-Time Automation
From Event to Action: Accelerate Your Decision Making with Real-Time Automation
 
Automating Business Process via MuleSoft Composer | Bangalore MuleSoft Meetup...
Automating Business Process via MuleSoft Composer | Bangalore MuleSoft Meetup...Automating Business Process via MuleSoft Composer | Bangalore MuleSoft Meetup...
Automating Business Process via MuleSoft Composer | Bangalore MuleSoft Meetup...
 
08448380779 Call Girls In Friends Colony Women Seeking Men
08448380779 Call Girls In Friends Colony Women Seeking Men08448380779 Call Girls In Friends Colony Women Seeking Men
08448380779 Call Girls In Friends Colony Women Seeking Men
 
SQL Database Design For Developers at php[tek] 2024
SQL Database Design For Developers at php[tek] 2024SQL Database Design For Developers at php[tek] 2024
SQL Database Design For Developers at php[tek] 2024
 
Tech-Forward - Achieving Business Readiness For Copilot in Microsoft 365
Tech-Forward - Achieving Business Readiness For Copilot in Microsoft 365Tech-Forward - Achieving Business Readiness For Copilot in Microsoft 365
Tech-Forward - Achieving Business Readiness For Copilot in Microsoft 365
 
Presentation on how to chat with PDF using ChatGPT code interpreter
Presentation on how to chat with PDF using ChatGPT code interpreterPresentation on how to chat with PDF using ChatGPT code interpreter
Presentation on how to chat with PDF using ChatGPT code interpreter
 
04-2024-HHUG-Sales-and-Marketing-Alignment.pptx
04-2024-HHUG-Sales-and-Marketing-Alignment.pptx04-2024-HHUG-Sales-and-Marketing-Alignment.pptx
04-2024-HHUG-Sales-and-Marketing-Alignment.pptx
 
Pigging Solutions in Pet Food Manufacturing
Pigging Solutions in Pet Food ManufacturingPigging Solutions in Pet Food Manufacturing
Pigging Solutions in Pet Food Manufacturing
 
Swan(sea) Song – personal research during my six years at Swansea ... and bey...
Swan(sea) Song – personal research during my six years at Swansea ... and bey...Swan(sea) Song – personal research during my six years at Swansea ... and bey...
Swan(sea) Song – personal research during my six years at Swansea ... and bey...
 
Breaking the Kubernetes Kill Chain: Host Path Mount
Breaking the Kubernetes Kill Chain: Host Path MountBreaking the Kubernetes Kill Chain: Host Path Mount
Breaking the Kubernetes Kill Chain: Host Path Mount
 
Transforming Data Streams with Kafka Connect: An Introduction to Single Messa...
Transforming Data Streams with Kafka Connect: An Introduction to Single Messa...Transforming Data Streams with Kafka Connect: An Introduction to Single Messa...
Transforming Data Streams with Kafka Connect: An Introduction to Single Messa...
 
Factors to Consider When Choosing Accounts Payable Services Providers.pptx
Factors to Consider When Choosing Accounts Payable Services Providers.pptxFactors to Consider When Choosing Accounts Payable Services Providers.pptx
Factors to Consider When Choosing Accounts Payable Services Providers.pptx
 
Neo4j - How KGs are shaping the future of Generative AI at AWS Summit London ...
Neo4j - How KGs are shaping the future of Generative AI at AWS Summit London ...Neo4j - How KGs are shaping the future of Generative AI at AWS Summit London ...
Neo4j - How KGs are shaping the future of Generative AI at AWS Summit London ...
 
Install Stable Diffusion in windows machine
Install Stable Diffusion in windows machineInstall Stable Diffusion in windows machine
Install Stable Diffusion in windows machine
 
08448380779 Call Girls In Diplomatic Enclave Women Seeking Men
08448380779 Call Girls In Diplomatic Enclave Women Seeking Men08448380779 Call Girls In Diplomatic Enclave Women Seeking Men
08448380779 Call Girls In Diplomatic Enclave Women Seeking Men
 
How to Troubleshoot Apps for the Modern Connected Worker
How to Troubleshoot Apps for the Modern Connected WorkerHow to Troubleshoot Apps for the Modern Connected Worker
How to Troubleshoot Apps for the Modern Connected Worker
 
Key Features Of Token Development (1).pptx
Key  Features Of Token  Development (1).pptxKey  Features Of Token  Development (1).pptx
Key Features Of Token Development (1).pptx
 
Unblocking The Main Thread Solving ANRs and Frozen Frames
Unblocking The Main Thread Solving ANRs and Frozen FramesUnblocking The Main Thread Solving ANRs and Frozen Frames
Unblocking The Main Thread Solving ANRs and Frozen Frames
 

Hosting Your Own OTA Update Service

  • 1. Host your own Over-the-air update service
  • 2. Roadmap Buggy Valley App Glorified cURLing App Designing an OTA Service Hosting Your Own Service OTA Assets Announcements
  • 7. Standing on the shoulders of giants
  • 10. Buggy Valley $ p = 0.5 $$ Nothingp = 0.5
  • 11. Buggy Valley p = 0.5 p = 0.5
  • 12. Android Java Implementation String redScreenPath = “file:///red-screen.js”; String pillarValleyPath = “file:///pillar-valley.js”;
  • 13. Android Java Implementation String redScreenPath = “file:///red-screen.js”; String pillarValleyPath = “file:///pillar-valley.js”; int randNum = getRandom(); if (isEven(randNum)){ loadApp(redScreenPath); } else { loadApp(pillarValleyPath); }
  • 14. Android Java Implementation String redScreenPath = “file:///red-screen.js”; String pillarValleyPath = “file:///pillar-valley.js”; int randNum = getRandom(); if (isEven(randNum)){ loadApp(redScreenPath); } else { loadApp(pillarValleyPath);** } ** how does loadApp work?
  • 15.
  • 16.
  • 17. Quick Recap String redScreenPath = “file:///red-screen.js”; String pillarValleyPath = “file:///pillar-valley.js”; int randNum = getRandom(); if (isEven(randNum)){ loadApp(redScreenPath); } else { loadApp(pillarValleyPath);** } ** how does loadApp work?
  • 18. Roadmap Buggy Valley App Glorified cURLing App Designing an OTA Service Hosting Your Own Service OTA Assets Announcements
  • 19.
  • 20. Buggy Valley fits in perfectly with my use case. Your MVP was just what I needed!
  • 22. Original Buggy Valley String redScreenPath = “file:///red-screen.js”; String pillarValleyPath = “file:///pillar-valley.js”; int randNum = getRandom(); if (isEven(randNum)){ loadApp(redScreenPath); } else { loadApp(pillarValleyPath); }
  • 23. Modified Buggy Valley String redScreenPath = “file:///red-screen.js”; String aliceAppPath = “file:///alice-app.js”; int randNum = getRandom(); if (isEven(randNum)){ loadApp(redScreenPath); } else { loadApp(aliceAppPath); }
  • 24. Modified Buggy Valley String redScreenPath = “file:///red-screen.js”; String aliceAppPath = “file:///alice-app.js”; int randNum = getRandom(); if (isEven(randNum)){ loadApp(redScreenPath); } else { loadApp(aliceAppPath); }
  • 25. Modified Buggy Valley String newAliceAppPath String aliceAppPath = “file:///alice-app.js”; int randNum = getRandom(); if (isEven(randNum)){ loadApp(newAliceAppPath); } else { loadApp(aliceAppPath); }
  • 26. Modified Buggy Valley String newAliceAppPath = cURLToDisk(“https://expo.io/@alice/app”); String aliceAppPath = “file:///alice-app.js”; int randNum = getRandom(); if (isEven(randNum)){ loadApp(newAliceAppPath); } else { loadApp(aliceAppPath); }
  • 27. Modified Buggy Valley String newAliceAppPath = cURLToDisk(“https://expo.io/@alice/app”); String aliceAppPath = “file:///alice-app.js”; int randNum = getRandom(); if (isEven(randNum)){ loadApp(newAliceAppPath); } else { loadApp(aliceAppPath); }
  • 28. Glorified cURL String newAliceAppPath = cURLToDisk(“https://expo.io/@alice/app”); String aliceAppPath = “file:///alice-app.js”; if (newAliceAppPath != null){ loadApp(newAliceAppPath); } else { loadApp(aliceAppPath); }
  • 29. Wait but how does this benefit me?
  • 31. JS Bundle Native Modules Currently on disk: Traditional update New JS Bundle New Native Modules
  • 32. JS Bundle Native Modules Currently on disk: Traditional update New JS Bundle New Native Modules Avg binary size ~30Mb
  • 34. JS Bundle Native Modules Currently on disk: Glorified cURL update New JS Bundle Native Modules
  • 35. Roadmap Buggy Valley App Glorified cURLing App Designing an OTA Service Hosting Your Own Service OTA Assets Announcements
  • 36.
  • 37. Glorified cURL fits in perfectly with my use case. Your MVP was just what I needed!
  • 38. It’s not very performant tho...
  • 39. Glorified cURL String newBobAppPath = cURLToDisk(“https://expo.io/@bob/app”); String bobAppPath = “file:///bob-app.js”; if (newBobAppPath != null){ loadApp(newBobAppPath); } else { loadApp(bobAppPath); }
  • 40. Glorified cURL String newBobAppPath = cURLToDisk(“https://expo.io/@bob/app”); String bobAppPath = “file:///bob-app.js”; if (newBobAppPath != null){ loadApp(newBobAppPath); } else { loadApp(bobAppPath); } JS Bundle We don’t want to load the JS bundle unnecessarily. We only want to load the JS bundle if there’s a new change available.
  • 41. Let’s take a step back And think about how the web works for a sec
  • 42. The Web <script src=“bundle.js” /> Big JS bundle bundle.js index.html
  • 43. Taking a page out of the web book {bundleUrl: ‘bundle.js’} Big JS bundle bundle.js index.json
  • 44. Taking a page out of the web book {bundleUrl: ‘ios-1a2b3c.js’} Big JS bundle ios-1a2b3c.js index.json Bundle name is based off its md5 hash
  • 45. Taking a page out of the web book {bundleUrl: ‘ios-7a8b9c’} Big JS bundle ios-7a8b9c.js index.json Cache the bundleUrl Only download bundleUrl if we don’t have it cached
  • 46. How do I use an OTA service in my app? ^ these are my app files ^ this is what my app looks like
  • 47. How do I use an OTA service in my app? dev tools GUI ^ push this button to upload app to expo server
  • 48. How do I use an OTA service in my app? Or use the cli if you prefer > expo publish Run this command in your project directory to upload to expo servers
  • 49. How often is the server polled for updates? The default behavior is to poll the server when the app starts up
  • 50. What if I don’t like the default behavior? You can use the Updates module to customize when you’d to update your app ^ from the docs page
  • 51. Roadmap Buggy Valley App Glorified cURLing App Designing an OTA Service Hosting Your Own Service OTA Assets Announcements
  • 52. I’m in a country where network latency to your CDNs are really high
  • 53. I’m in a country where network latency to your CDNs are really high How about hosting your own app then?
  • 54. I’m in a country where network latency to your CDNs are really high How about hosting your own app then?* * in our upcoming SDK release
  • 55. How do I host my own app? ^ these are my app files ^ this is what my app looks like
  • 56. > expo export Run this command in your project directory to dump your app to disk How do I host my own app?
  • 57. This is what gets dumped to disk How do I host my own app? . ├── android-index.json ├── ios-index.json ├── assets │   └── 1ecc2 └── bundles       ├── android-01ee6.js       └── ios-ee820.js
  • 58. How do I host my own app? . ├── android-index.json ├── ios-index.json ├── assets │   └── 1ecc2 └── bundles       ├── android-01ee6.js       └── ios-ee820.js
  • 59. How do I host my own app? . ├── android-index.json ├── ios-index.json ├── assets │   └── 1ecc2 └── bundles       ├── android-01ee6.js       └── ios-ee820.js {bundleUrl: ‘ios-ee820.js’} Big JS bundle ios-ee820.js ios-index.json
  • 60. How do I host my own app? . ├── android-index.json ├── ios-index.json ├── assets │   └── 1ecc2 └── bundles       ├── android-01ee6.js       └── ios-ee820.js git push master
  • 61. I pushed to GitHub because it has free static hosting. You can host your app from any server.
  • 62. How do I build my app binary? > expo build:ios Run this command in your project directory
  • 63. How do I build my app binary? > expo build:ios —public-url https://quinlanj.github.io/self-hosting/ios-index.json Run this command in your project directory
  • 64. How do I build my app binary? > expo build:ios —public-url https://quinlanj.github.io/self-hosting/ios-index.json {bundleUrl: ‘ios-ee820.js’} Big JS bundle ios-ee820.js ios-index.json ^ This file is served first
  • 66. How do I use this in development? https://quinlanj.github.io/selfhost/ios-index.json Convert to QR code
  • 67. How do I use this in development? Scan the QR code into the expo dev app
  • 68. How do I use this in development? http://localhost:8000/ios-index.json Convert to QR code
  • 69. How do I use this in development? Scan the QR code into the expo dev app
  • 70. Roadmap Buggy Valley App Glorified cURLing App Designing an OTA Service Hosting Your Own Service OTA Assets Announcements
  • 71. This is what my app looks like. I’ve installed it on my phone.
  • 72. In development, let’s make a change by adding another pic
  • 73. Push changes to GitHub
  • 74. This is what my app looks like. I’ve installed it on my phone.
  • 75. This is what my app looks like. I’ve installed it on my phone. Currently on filesystem: JS Bundle
  • 76. This is what my app looks like. I’ve installed it on my phone. Currently on filesystem: JS Bundle quinlanj.github.io Here is the server hosting my app
  • 77. This is what my app looks like. I’ve installed it on my phone. Currently on filesystem: JS Bundle quinlanj.github.io An update is ready!
  • 78. This is what my app looks like. I’ve installed it on my phone. Currently on filesystem: JS Bundle quinlanj.github.io An update is ready! Files to be served: New JS Bundle
  • 79. This is what my app looks like. I’ve installed it on my phone. Currently on filesystem: JS Bundle quinlanj.github.io An update is ready! Files to be served: New JS Bundle JS Bundle
  • 80. This is what my app looks like. I’ve installed it on my phone. Currently on filesystem: quinlanj.github.io An update is ready! Files to be served: New JS Bundle
  • 81. New JS Bundle <Image source={require(‘cat.png’} /> <Image source={require(‘dog.png’} />
  • 82. This is what my app looks like. I’ve installed it on my phone. Currently on filesystem: quinlanj.github.io An update is ready! Files to be served: New JS Bundle ? dog.png is pulled down to filesystem?
  • 83. New JS Bundle <Image source={require(‘cat.png’} /> <Image source={require(‘dog.png’} /> But how? It looks like these assets are fetched from filesystem
  • 84. New JS Bundle <Image source={require(‘cat.png’} /> <Image source={require(‘dog.png’} /> We wrote a module to override asset resolution
  • 85. New JS Bundle <Image source={require(‘cat.png’} /> <Image source={require(‘dog.png’} /> Module Logic: Look for asset in the filesystem If it’s not there, look for it from the server
  • 86. This is what my app looks like. I’ve installed it on my phone. Currently on filesystem: quinlanj.github.io An update is ready! Files to be served: New JS Bundle ? dog.png is pulled down to filesystem?
  • 87. This is what my app looks like. I’ve installed it on my phone. Currently on filesystem: quinlanj.github.io An update is ready! Files to be served: New JS Bundle ? dog.png is not on the filesystem
  • 88. This is what my app looks like. I’ve installed it on my phone. Currently on filesystem: quinlanj.github.io An update is ready! Files to be served: New JS Bundle ? Let’s grab dog.png from server then!
  • 89. This is what my app looks like. I’ve installed it on my phone. Currently on filesystem: quinlanj.github.io An update is ready! Files to be served: New JS Bundle
  • 90. This is what my app looks like. I’ve installed it on my phone. Currently on filesystem: quinlanj.github.io An update is ready! Files to be served: New JS Bundle Cached for future use
  • 91. How come assets are stored by hash? . ├── android-index.json ├── ios-index.json ├── assets │   └── 1ecc2 └── bundles       ├── android-01ee6.js       └── ios-ee820.js
  • 92. JS Bundle <Image source={require(‘cat.png’)} /> We are requiring assets by their name, not by their hash
  • 93. JS Bundle require(‘cat.png’) React native packager {assetName: ‘cat.png’, hash:’1ecc2’} App packaging App.js
  • 94. JS Bundle <Image source={require(‘cat.png’} /> Module Logic: Look for cat.png in the filesystem If it’s not there, look for cat.png from the server Recall
  • 95. JS Bundle Module Logic: Look for 1ecc2 in the filesystem If it’s not there, look for 1ecc2 from the server Actual Implementation {assetName: ‘cat.png’, hash:’1ecc2’}
  • 96. How does this benefit me?
  • 97. <Image source={require(‘cat1.png’} /> <Image source={require(‘crazy-cat.png’} /> <Image source={require(‘lime-cat.png’} /> … This app displays the same cat picture These cat pictures are all named something different
  • 98. {assetName: ‘cat1.png’, hash:’1ecc2’} {assetName: ‘crazy-cat.png’, hash:’1ecc2’} {assetName: ‘lime-cat.png’, hash:’1ecc2’} … They all resolve to the same file on disk: 1ecc2
  • 99. Roadmap Buggy Valley App Glorified cURLing App Designing an OTA Service Hosting Your Own Service OTA Assets Announcements
  • 100. Announcements We made a web application called Snack Snack is like a JS Fiddle for react native apps Snack is now open source, check it out at https://github.com/expo/snack-web