Setting up DeployPulse with the new React Native architecture

DeployPulse initially extended support for the new React Native architecture by leveraging the existing CodePush SDK before the default enablement of this architecture in React Native version 0.76. This guide provides a step-by-step approach to configuring DeployPulse with the new React Native architecture, utilizing a compatible SDK.

Most steps remain unchanged, ensuring a smooth and straightforward transition.

Prerequisites

Your app must be using:

  • React Native version 0.77 or higher.
  • iOS minimum target version of 15.5.

Install the new CodePush client

npm install --save @code-push-next/react-native-code-push

Configure environment

Update your app to point to the DeployPulse server and use CodePushDeploymentKey generated from your DeployPulse account For your iOS app you will need to update the Info.plist file with the following

	<key>CodePushDeploymentKey</key>
	<string>{{DEPLOYMENT_KEY_HERE}}</string>
	<key>CodePushServerURL</key>
    <string>https://apps.deploypulse.io/</string>

For your Android app you will need to update the strings.xml file with the following

 <resources>
     <string name="app_name">AppName</string>
     <string moduleConfig="true" name="CodePushDeploymentKey">{{DEPLOYMENT_KEY_HERE}}</string>
     <string moduleConfig="true" name="CodePushServerUrl">https://apps.deploypulse.io/</string>
 </resources>

iOS Setup

Once you've acquired the CodePush plugin, you need to integrate it into the Xcode project of your React Native app and configure it correctly. To do this, take the following steps:

Plugin Installation and Configuration for React Native 0.76 version and above (iOS)

  1. Run cd ios && pod install && cd .. to install all the necessary CocoaPods dependencies.

  2. Change bundleUrl on AppDelegate file.

    If you're using objective-c:

    1. Open up the AppDelegate.m file, and add an import statement for the CodePush headers:

      #import <CodePush/CodePush.h>
      
    2. Find the following line of code, which sets the source URL for bridge for production releases:

      return [[NSBundle mainBundle] URLForResource:@"main" withExtension:@"jsbundle"];
      
    3. Replace it with this line:

      return [CodePush bundleURL];
      

      This change configures your app to always load the most recent version of your app's JS bundle. On the first launch, this will correspond to the file that was compiled with the app. However, after an update has been pushed via CodePush, this will return the location of the most recently installed update.

      NOTE: The bundleURL method assumes your app's JS bundle is named main.jsbundle. If you have configured your app to use a different file name, simply call the bundleURLForResource: method (which assumes you're using the .jsbundle extension) or bundleURLForResource:withExtension: method instead, in order to overwrite that default behavior

      Typically, you're only going to want to use CodePush to resolve your JS bundle location within release builds, and therefore, we recommend using the DEBUG pre-processor macro to dynamically switch between using the packager server and CodePush, depending on whether you are debugging or not. This will make it much simpler to ensure you get the right behavior you want in production, while still being able to use the Chrome Dev Tools, live reload, etc. at debug-time.

      Your sourceURLForBridge method should look like this:

      - (NSURL *)sourceURLForBridge:(RCTBridge *)bridge
      {
        #if DEBUG
          return [[RCTBundleURLProvider sharedSettings] jsBundleURLForBundleRoot:@"index"];
        #else
          return [CodePush bundleURL];
        #endif
      }
      

    If you're using Swift:

    1. Open up the AppDelegate.swift file, and add an import statement for the CodePush headers:

      import CodePush
      
    2. Find the following line of code, which sets the source URL for bridge for production release:

      Bundle.main.url(forResource: "main", withExtension: "jsbundle")
      
    3. Replace it with this line:

      CodePush.bundleURL()
      

      Your bundleUrl method should look like this:

      override func bundleURL() -> URL? {
      #if DEBUG
         RCTBundleURLProvider.sharedSettings().jsBundleURL(forBundleRoot: "index")
      #else
         CodePush.bundleURL()
      #endif
      }
      

Android Setup

In order to integrate CodePush into your Android project, please perform the following steps:

Plugin Installation and Configuration for React Native 0.76 version and above (Android)

  1. In your android/app/build.gradle file, add the codepush.gradle file as an additional build task definition to the end of the file:

    ...
    apply from: "../../node_modules/@code-push-next/react-native-code-push/android/codepush.gradle"
    ...
    
  2. Update the MainApplication file to use CodePush via the following changes:

    For React Native 0.76 and above: update the MainApplication.kt

    Important! : PackageList must be instantiated only one in application lifetime.

    ...
    // 1. Import the plugin class.
    import com.microsoft.codepush.react.CodePush
    
    class MainApplication : Application(), ReactApplication {
       override val reactNativeHost: ReactNativeHost =
           object : DefaultReactNativeHost(this) {
               override fun getPackages(): List<ReactPackage> = PackageList(this).packages.apply {
                 // Packages that cannot be autolinked yet can be added manually here, for example:
                 // add(MyReactNativePackage())
                }
    
               // 2. Override the getJSBundleFile method in order to let
               // the CodePush runtime determine where to get the JS
               // bundle location from on each app start
               override fun getJSBundleFile(): String {
                 return CodePush.getJSBundleFile()
               }
        };
    }
    

Usage

There are many ways to use CodePush in your app. The most common way is to wrap your root component with the codePush higher order component.

import codePush from '@code-push-next/react-native-code-push';

class MyApp extends Component {
}

MyApp = codePush(MyApp);

For more examples, check the plugin usage here.