API to open app settings

Hi folks,

Is there a way to open OS app settings on iOS? (On Android it looks like we have Opening Device Settings on Android using Linking)

Non-expo example of what I’d like to be able to do:


I would use this to take users who have denied push notification settings to the settings page, should they choose to re-enable them.

Native code:

if let appSettings = NSURL(string: UIApplicationOpenSettingsURLString) {
            UIApplication.sharedApplication().openURL(appSettings)
}

Thank you!

1 Like

@aje do you mean Linking.openURL('app-settings:'); doesnt work for you in iOS?

https://snack.expo.io/@quinlanj/os-settings <-- (ie) does this snack redirect you to the settings page (it does for me on an iphone 7 plus)?

8 Likes

Hi @quinlanj, thanks for the response. You’re right, that works perfectly. I should have read the post I linked to better :slight_smile:

Thanks again!

I’d like to link to notifications settings. I found this:

https://stackoverflow.com/questions/44582694/react-native-open-settings-through-linking-openurl-in-ios#comment76271660_44582884 (comment)

It works for Expo client, like this: Linking.openURL("app-settings://notification/expo")

What should be the last part for a stand alone app? Is it expo.ios.bundleIdentifier from app.json, expo.slug, or something else?

2 Likes

To answer @lazurski’s question, you use expo.ios.bundleIdentifier

Linking.openURL('app-settings://notification/<bundleIdentifier>')

6 Likes

Thanks for this snack demo, it works perfectly for me as well! :smiley:

what is the equivalent on Android?

https://docs.expo.io/versions/latest/sdk/intent-launcher/

1 Like

thanks. im in managed mode, and tried this but still not opening :frowning:

IntentLauncher.startActivityAsync(IntentLauncher.ACTION_APP_NOTIFICATION_SETTINGS);

even with package name still not working:

IntentLauncher.startActivityAsync(IntentLauncher.ACTION_APP_NOTIFICATION_SETTINGS, { data: 'package:' + pkg  });
1 Like

not sure what is going on with that particular intent type but here’s an example of using it for application details: https://snack.expo.io/@notbrent/launch. notice that in expo client you need to use host.exp.exponent as the package name

1 Like

looks like this is different depending on the operating system version: https://stackoverflow.com/a/45192258/659988

you can use the extra field instead of putExtra

1 Like

Yup that one works. I mean its not ideal but at least takes me to the app’s settings screen. Do you think this one at least is not version dependent?

1 Like

it does seem to work on all versions yeah, i’m not very familiar with these details. you could handle it so on android 8+ you open notifs directly easily with this: https://snack.expo.io/@notbrent/suspicious-milkshake

not sure if we expose the uid for the android 5-7 approach

1 Like

actually a better way to get the package name is with expo-application:

import * as Application from 'expo-application';

export default class App extends React.Component {
  render() {
    return (
      <View style={styles.container}>
        <Button
          title="Open settings"
          onPress={() => {
            IntentLauncher.startActivityAsync(
              IntentLauncher.ACTION_APPLICATION_DETAILS_SETTINGS,
              {
                data: `package:${Application.applicationId}`,
              }
            );
          }}
        />
      </View>
    );
  }
}
4 Likes

Ah nice!
But yeah not sure what’s the best way to get Android version, to know if I should do one thing for v > 8 and for those before v8 …

import { Platform } from 'react-native';

// assuming this code is just running on android..
if (Platform.Version >= 26) {
  // do something for android 8+ (api 26 and higher)
} else {
  // do other thing
}

gotcha. didnt know 26 is for v8.
Thanks so much!

you can check out the mappings here: https://en.wikipedia.org/wiki/Android_version_history

1 Like

The following url scheme not open notification settings screen only the app settings, any way to open app notification settings directly?

you could use app-settings: and produces the same effect

Here working unified example:

import { Linking } from 'expo';
import * as Application from 'expo-application';
import * as IntentLauncher from 'expo-intent-launcher';

const open_settings = () => {
  // TODO: it might work on SDK 37?
  // Linking.openSettings();
  if (Platform.OS === 'ios') {
    Linking.openURL(`app-settings:`);
  } else {
    const bundleIdentifier = Application.applicationId;
    IntentLauncher.startActivityAsync(IntentLauncher.ACTION_APPLICATION_DETAILS_SETTINGS, {
      data: `package:${bundleIdentifier}`,
    });
  }
}

has @notbrent say, you must render open_settings button when the following conditon:

import { Platform } from 'react-native';

(Platform.OS === 'android' && Platform.Version >= 26) || Platform.OS === 'ios';  
9 Likes