Is was wondering if its possible to deploy a React Native app to Heroku? The reason I ask is because then I can retrieve the url and place it in an iframe to mimic an iPhone where the user can then tryout the app without actually having to install it on to the iPhone via iTunes.
Your React app should now be deployed to Heroku! You can open it directly from the terminal by running heroku open .
Heroku lets you deploy, run and manage applications written in Ruby, Node. js, Java, Python, Clojure, Scala, Go and PHP.
Can React Native be used for web and mobile? Yes! With React Native for Web, developers can write a single React Native application that can run natively on Android and iOS, as well as on a web browser using standard web technologies.
This is possible using react-native-web (sources). There are few things that you have to do to set this up on heroku:
heroku/nodejs
,package.json
set the build
script to build your web version from RN sources, for example, if you are using expo: expo build:web
,web-build
and therfore the command should be npx serve web-build
,Additionally, if you use expo, make sure to add the expo-cli
as a dev dependency: npm install -D expo-cli
.
You will then simply need to push to heroku the usual way. By default, heroku will run yarn build
(or npm run build
depending on wether you used one or the other to generate your lock file).
In the end, here is what the package.json
file might look like (using expo again):
{
"main": "node_modules/expo/AppEntry.js",
"scripts": {
"start": "expo start",
"android": "expo start --android",
"ios": "expo start --ios",
"web": "expo start --web",
"eject": "expo eject",
"test": "jest --watchAll",
"build": "expo build:web"
},
"jest": {
"preset": "jest-expo"
},
"dependencies": {
"@expo/vector-icons": "^12.0.0",
"@react-native-community/masked-view": "0.1.10",
"@react-navigation/bottom-tabs": "^5.11.1",
"@react-navigation/native": "^5.8.9",
"@react-navigation/stack": "^5.12.6",
"expo": "~40.0.0",
"expo-asset": "~8.2.1",
"expo-constants": "~9.3.0",
"expo-font": "~8.4.0",
"expo-linking": "~2.0.0",
"expo-splash-screen": "~0.8.0",
"expo-status-bar": "~1.0.3",
"expo-web-browser": "~8.6.0",
"react": "16.13.1",
"react-dom": "16.13.1",
"react-native": "https://github.com/expo/react-native/archive/sdk-40.0.1.tar.gz",
"react-native-gesture-handler": "~1.8.0",
"react-native-safe-area-context": "3.1.9",
"react-native-screens": "~2.15.0",
"react-native-web": "~0.13.12"
},
"devDependencies": {
"expo-cli": "^4.0.16",
"@babel/core": "~7.9.0",
"@types/react": "~16.9.35",
"@types/react-native": "~0.63.2",
"jest-expo": "~40.0.0",
"typescript": "~4.0.0"
},
"private": true
}
And the Procfile
simply consists of a single line:
web: npx serve web-build
You could probably achieve similar results using reactxp instead of reac-native-web, but I never tried it myself.
If you use client side routing (react navigation for example), you will have to setup a few more things to make sure linking works. With the previous build alone, client side routing will fail (404 errors) because heroku will try to route requests on its own, but your app needs everything to end up at index.html
so it can perform routing tasks on its own (client side routing).
We will thus prevent any Heroku routing by adding a second buildpack heroku-community/static next to heroku/nodejs
. This second buildpack is configured via a /static.json
file (default values):
{
"root": "web-build/",
"clean_urls": false,
"routes": {
"/**": "index.html"
}
}
You probably already have this part setup because otherwise you would have 404 errors even locally. To allow client side routing it seems like we also need to configure webpack (output.publicPath
and devServer.historyApiFallback
), with expo this can be done by running expo customize:web
and then editing /webpack.config.js
with:
const createExpoWebpackConfigAsync = require('@expo/webpack-config');
module.exports = async function (env, argv) {
const config = await createExpoWebpackConfigAsync(env, argv);
config.output.publicPath = '/';
config.devServer = {
...config.devServer,
historyApiFallback: true,
};
return config;
};
There is a nice article about these routing issues you might have here: Fixing the 'cannot GET /URL'
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With