This feature allows you to use a Git repository to host your bundle files. The mobile application will pull only the changes from the Git repository instead of downloading the entire bundle file from a server. This reduces data usage and improves update speed.
iOS GIF | Android GIF |
---|---|
Can see the demo video here:
https://drive.google.com/file/d/1P3usN7cbBlboJ5pH211m9BKZyVusMQw5/view?usp=sharing
Currently, this feature supports the following Git hosting platforms:
- GitHub
- GitLab
- Bitbucket
I strongly recommend you to self hosted git into your server, don't use free git hosting if you really run you application. Some guideline: https://git-scm.com/book/en/v2/Git-on-the-Server-Getting-Git-on-a-Server
If you want to use git control, you may need install react-native-fs
yarn add react-native-fs
- Log in to your Git hosting service (e.g., GitHub, GitLab, Bitbucket).
- Create a new repository to host your bundle files. For example, name it
OTA-bundle
. - Clone the repository to your local machine:
git clone https://github.com/<your-username>/OTA-bundle.git
- Generate your bundle files using the React Native CLI or Expo.
- For react native CLI:
"scripts": {
"export-android": "mkdir -p android/output && react-native bundle --platform android --dev false --entry-file index.js --bundle-output android/output/index.android.bundle --assets-dest android/output",
"export-ios": "mkdir -p ios/output && react-native bundle --platform ios --dev false --entry-file index.js --bundle-output ios/output/main.jsbundle --assets-dest ios/output"
}
- For expo / expo bare project:
"scripts": {
"export-android": "mkdir -p android/output && npx expo export:embed --platform android --entry-file node_modules/expo/AppEntry.js --bundle-output android/output/index.android.bundle --dev false --assets-dest android/output",
"export-ios": "mkdir -p ios/output && npx expo export:embed --platform ios --entry-file node_modules/expo/AppEntry.js --bundle-output ios/output/main.jsbundle --dev false --assets-dest ios/output"
}
For expo you might need check path of --entry-file node_modules/expo/AppEntry.js
, get it from package.json / main
- Copy
android/output
/ios/output
folder into the cloned repository directory. - Commit and push the changes to your Git repository:
git add . git commit -m "Initial commit with bundle files" git push origin main
- Create separate branches for iOS and Android updates (optional but recommended):
git checkout -b iOS git push origin iOS git checkout -b android git push origin android
- Maintain platform-specific bundle files in their respective branches.
Here is a complete example of how to implement the hot update via Git:
const onCheckGitVersion = () => {
hotUpdate.git.checkForGitUpdate({
branch: Platform.OS === 'ios' ? 'iOS' : 'android',
bundlePath:
Platform.OS === 'ios'
? 'output/main.jsbundle'
: 'output/index.android.bundle',
url: 'https://github.com/<your-username>/OTA-bundle.git',
onCloneFailed(msg: string) {
Alert.alert('Clone project failed!', msg, [
{
text: 'Cancel',
onPress: () => {},
style: 'cancel',
},
]);
},
onCloneSuccess() {
Alert.alert('Clone project success!', 'Restart to apply the changes', [
{
text: 'OK',
onPress: () => hotUpdate.resetApp(),
},
{
text: 'Cancel',
onPress: () => {},
style: 'cancel',
},
]);
},
onPullFailed(msg: string) {
Alert.alert('Pull project failed!', msg, [
{
text: 'Cancel',
onPress: () => {},
style: 'cancel',
},
]);
},
onPullSuccess() {
Alert.alert('Pull project success!', 'Restart to apply the changes', [
{
text: 'OK',
onPress: () => hotUpdate.resetApp(),
},
{
text: 'Cancel',
onPress: () => {},
style: 'cancel',
},
]);
},
onProgress(received: number, total: number) {
const percent = (+received / +total) * 100;
LayoutAnimation.configureNext(LayoutAnimation.Presets.easeInEaseOut);
setProgress(percent);
},
onFinishProgress() {
setLoading(false);
},
});
};
Key | Required | Type | Description |
---|---|---|---|
restartAfterInstall |
No | boolean |
Default is false . If true , the app will restart automatically after applying the changes. |
branch |
Yes | string |
The Git branch to pull updates from (e.g., iOS or android ). |
bundlePath |
Yes | string |
The relative path to the bundle file within the repository. |
url |
Yes | string |
The URL of the Git repository hosting the bundle files. |
onCloneFailed |
No | Callback |
Triggered if the cloning process fails. Receives an error message as an argument. |
onCloneSuccess |
No | Callback |
Triggered when the cloning process is successful. |
onPullFailed |
No | Callback |
Triggered if the pull process fails. Receives an error message as an argument. |
onPullSuccess |
No | Callback |
Triggered when the pull process is successful. |
onProgress |
No | Callback |
A callback that provides download progress updates (received bytes and total bytes). |
onFinishProgress |
No | Callback |
Triggered when the download progress is complete. |
- Clone in the first time: The app will check if repository in local not exist, app will clone repo in the first time, this may take time depend on your project size.
- Check for Updates: Next time you call
checkForGitUpdate
method, it will just pull the latest commit. - Handle Clone/Pull Success: If the operation is successful, you can notify the user and restart the app to apply the updates.
- Handle Failures: If cloning or pulling fails, the user is notified with an appropriate error message.
- Track Progress: The
onProgress
callback is used to update a progress bar or indicator to inform the user of the download status.
- Ensure the Git repository is publicly accessible or configured with the appropriate credentials if private.
- The
bundlePath
should match the location of the bundle file within your Git repository. - This feature is designed to work seamlessly with both iOS and Android platforms.
- There are noway to check whether have new updating, need pull first and notify user or restart the app to apply the changes, if you want check new version before pull the changes, you should design an api for that.
- Git for client we are using
isomorphic-git
, a lightweight git engine for js. - Finally, i am not recommend to use this way to control your hot update if your application is really big and has a lot of users, i would like to recommend you to use custom server.