Deep linking 🔗 in React Native

stanleyugwu

Stanley Ugwu

Posted on December 19, 2022

Deep linking 🔗 in React Native

Hello Dev 👋 trust you're hacking good. Let's talk about setting up deep linking for react native projects. Grab your laptop and let's grab some knowledge .

So what is deep linking?

Deep linking is a way to move directly to a particular screen in a particular mobile app through URLs.

You know the way you click a link for e.g dev.to/stanleyugwu and it takes you to a particular page within a website, with mobile deep linking, you'll be able to achieve the same result for mobile apps. In short you'll be able to navigate to a particular screen/view of a mobile app by clicking a link.

Without deep linking

The traditional way of getting to where you want in any mobile app without deep linking is to launch the app, and then follow whichever route the app puts you through, till you get to where you want.

Consider below diagram as the UI flow of an example mobile app. Each box represents a screen within the app.

App UI flow

Say you want to edit your profile from the Profile screen, you have to move from Home to Settings then to Profile screen.

With deep linking

With deep linking setup for our example app, we'll be able to move directly to the Profile screen without going through the intermediate screens (Home, Settings).
App UI flow

A common use-case scenario of deep linking is when slack sends you an email with a magic link which you click on and it takes you to slack app if you have it installed. That's deep linking at work there 😎

Benefits of deep links

There are numerous advantages of setting up deep links for your mobile app:

  • Improves app discoverability
  • Improves user engagement
  • Enhances the user experience
  • Re-Engages users to your app fast
  • Campaign opportunity (campaign can be run for individual screen)
  • e.t.c

Configuring deep links

Deep links are regular links, it's just the underlying operating system and the mobile app been deep-linked into that makes them powerful.

Configuring your mobile app to support deep linking is just about informing the operating system that the app can handle certain URLs and/or URL schemes. So that when the user clicks on a URL matching the specifications, your app can take over, and handle the user's request.

A typical URL has different parts or segments as denoted by the image below:
URL segments

You can configure your app to handle each segment or combination of segments. What that means is you can configure your app to handle URLs with certain scheme, second-level domain, top-level domain, subdirectory, or a combination of them.

In this tutorial, we will be setting up our React Native app to handle the scheme myapp:// so that URLs having myapp:// scheme would be handled by our app.

I think I've said enough 🤐, let's get to work 💻.

1. Create a new React Native app (let's call it deepLinkApp 😉)



npx react-native init deepLinkApp


Enter fullscreen mode Exit fullscreen mode

Move into the app's directory



cd ./deepLinkApp


Enter fullscreen mode Exit fullscreen mode

Click here to learn how to setup your environment for React Native.

2. Configure deep links for android

On Android, deep links works through intents. The Android OS broadcasts an intent when a link is clicked, and apps that can handle the intent and link shows up for user to choose. Now let's tell Android that our app can handle myapp:// scheme.
The easiest way to do this is with the uri-scheme package:



npx uri-scheme add myapp --android


Enter fullscreen mode Exit fullscreen mode

If you want to set it up manually, open up deepLinkApp/android/app/src/main/AndroidManifest.xml, and make the following adjustments:

  1. Set launchMode of MainActivity to singleTask in order to receive intent on existing MainActivity.

  2. Create a new intent-filter inside the MainActivity entry with a VIEW type action

Below is how your .MainActivity activity tag should look like with the intent-filter and launchMode set, so you can just copy and paste it:



...
<activity
    android:name=".MainActivity"
    android:launchMode="singleTask">
    <intent-filter>
        <action android:name="android.intent.action.MAIN" />
        <category android:name="android.intent.category.LAUNCHER" />
    </intent-filter>
    <intent-filter>
        <action android:name="android.intent.action.VIEW" />
        <category android:name="android.intent.category.DEFAULT" />
        <category android:name="android.intent.category.BROWSABLE" />
        <data android:scheme="myapp" />
    </intent-filter>
</activity>
...


Enter fullscreen mode Exit fullscreen mode

3. Configure deep links for iOS

Include the following lines in your project's AppDelegate.m file in order to be able to listen to incoming app links:

Copy/paste below code at the top of the file
#import <React/RCTLinkingManager.h>

Copy/paste below code inside @implementation AppDelegate above @end:



- (BOOL)application:(UIApplication *)application
   openURL:(NSURL *)url
   options:(NSDictionary<UIApplicationOpenURLOptionsKey,id> *)options
{
  return [RCTLinkingManager application:application openURL:url options:options];
}


Enter fullscreen mode Exit fullscreen mode

Now let's add the scheme to our iOS project configuration.
The easiest way to do this is again with the uri-scheme package. Run the following command:



npx uri-scheme add myapp --ios


Enter fullscreen mode Exit fullscreen mode

Again, if you want to do it manually, open up the project deepLinkApp/ios/deepLinkApp.xcworkspace in Xcode. Select the project in sidebar and navigate to the info tab. Scroll down to "URL Types" and add one. In the new URL type, set the identifier and the URL scheme to myapp.

This is how it should look in Xcode:

Xcode scheme configuration interface
Imge Source: react-navigation

4. Rebuild and install the app

We have made changes on the native side of our app, so you need to rebuild and install the app in your emulator, simulator, or device.

For iOS, run:



npx react-native run-ios


Enter fullscreen mode Exit fullscreen mode

For Android, run:



npx react-native run-android


Enter fullscreen mode Exit fullscreen mode

5. Test out the deep link (the moment of truth 😆)

Now we're going to use our handy uri-scheme command line package to test out the deep link we just set up for both Android and iOS.

For iOS run:



npx uri-scheme open "myapp://any/host/and/path" --ios


Enter fullscreen mode Exit fullscreen mode

For Android run:



npx uri-scheme open "myapp://any/host/and/path" --android


Enter fullscreen mode Exit fullscreen mode

Running above command will launch/start-up our app on the emulator/simulator/device if it's not already running, otherwise nothing really happens. Yes nothing 😎.
The reason is because we didn't specify what happens next after our app is granted permission to handle the deep link.

6. Handle the deep link

We need to handle the deep link on the Javascript side of our app so that we can specify what happens next after our app is launched or foregrounded as a result of running above command, or user clicking on URL with myapp:// scheme. Fortunately, React Native provides us with a Linking module which we can call from JavaScript to handle deep linking easily 😇👌.

There are two ways to handle deep links that open your app:

  1. If the app is already open/launched, the app is foregrounded and a Linking 'url' event is fired
    You can handle these events with Linking.addEventListener('url', callback) - it calls callback({ url }) with the URL which was used to open the app.

  2. If the app is not already open/launched, it is opened and the url which was used to open the app is passed in as the initialURL
    You can handle these events with Linking.getInitialURL() - it returns a Promise that resolves to the URL, if there is one.

To handle these cases in our app, open up App.js and add the following code to it:



useEffect(() => {
      // handles deep link when app is already open
      Linking.addEventListener('url', evt => {
        console.log(evt.url);
      });

      // handles deep link when app is not already open
      Linking.getInitialURL()
        .then(url => console.log('Initial URL:', url))
        .catch(console.warn);

    return () => {
      // clears listener when component unmounts
      Linking.removeAllListeners('url');
    };
  }, []);


Enter fullscreen mode Exit fullscreen mode

Now lets' run the uri-scheme test command one more time:

For iOS run:



npx uri-scheme open "myapp://any/host/and/path" --ios


Enter fullscreen mode Exit fullscreen mode

For Android run:



npx uri-scheme open "myapp://any/host/and/path" --android


Enter fullscreen mode Exit fullscreen mode

Now you should see your app opened, and "myapp://any/host/and/path" logged to the console. Bravo!! 💃🕺 your deep link setup is working.

Note that we're just logging the URL (which opened our app) to the console, in real apps however, you might need to parse the URL and perform further operations such as navigating the user to the appropriate screen. Luckily if you use react-navigation package for your app navigation, there's an easy way to bind certain deep link URLs to certain screens in your app. You can read more on that here.

Summary

We've just learnt how to setup deep links for our React Native (Android and iOS) app. If you've not been doing this for your apps, you really need to consider it as it comes with so many benefits.

The technicalities involved in setting up deep links are not really that much, the lengthiness of this article can be attributed to the stretch in explanations (I was more concerned with how it worked, sorry 😉).

Phew! 😌 that was a long one 😅. I hope you learnt something?. happy hacking 💻 ✌🖖

💖 💪 🙅 🚩
stanleyugwu
Stanley Ugwu

Posted on December 19, 2022

Join Our Newsletter. No Spam, Only the good stuff.

Sign up to receive the latest update from our blog.

Related

File download in React Native and Expo
Deep linking 🔗 in React Native
reactnative Deep linking 🔗 in React Native

December 19, 2022