How to implement my very own URI scheme on Android

189,369

Solution 1

This is very possible; you define the URI scheme in your AndroidManifest.xml, using the <data> element. You setup an intent filter with the <data> element filled out, and you'll be able to create your own scheme. (More on intent filters and intent resolution here.)

Here's a short example:

<activity android:name=".MyUriActivity">
    <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" android:host="path" />
    </intent-filter>
</activity>

As per how implicit intents work, you need to define at least one action and one category as well; here I picked VIEW as the action (though it could be anything), and made sure to add the DEFAULT category (as this is required for all implicit intents). Also notice how I added the category BROWSABLE - this is not necessary, but it will allow your URIs to be openable from the browser (a nifty feature).

Solution 2

Complementing the @DanielLew answer, to get the values of the parameteres you have to do this:

URI example: myapp://path/to/what/i/want?keyOne=valueOne&keyTwo=valueTwo

in your activity:

Intent intent = getIntent();
if (Intent.ACTION_VIEW.equals(intent.getAction())) {
  Uri uri = intent.getData();
  String valueOne = uri.getQueryParameter("keyOne");
  String valueTwo = uri.getQueryParameter("keyTwo");
}

Solution 3

I strongly recommend that you not define your own scheme. This goes against the web standards for URI schemes, which attempts to rigidly control those names for good reason -- to avoid name conflicts between different entities. Once you put a link to your scheme on a web site, you have put that little name into entire the entire Internet's namespace, and should be following those standards.

If you just want to be able to have a link to your own app, I recommend you follow the approach I described here:

How to register some URL namespace (myapp://app.start/) for accessing your program by calling a URL in browser in Android OS?

Solution 4

Another alternate approach to Diego's is to use a library:

https://github.com/airbnb/DeepLinkDispatch

You can easily declare the URIs you'd like to handle and the parameters you'd like to extract through annotations on the Activity, like:

@DeepLink("path/to/what/i/want")
public class SomeActivity extends Activity {
  ...
}

As a plus, the query parameters will also be passed along to the Activity as well.

Solution 5

As the question is asked years ago, and Android is evolved a lot on this URI scheme.
From original URI scheme, to deep link, and now Android App Links.

Android now recommends to use HTTP URLs, not define your own URI scheme. Because Android App Links use HTTP URLs that link to a website domain you own, so no other app can use your links. You can check the comparison of deep link and Android App links from here

Now you can easily add a URI scheme by using Android Studio option: Tools > App Links Assistant. Please refer the detail to Android document: https://developer.android.com/studio/write/app-link-indexing.html

Share:
189,369

Related videos on Youtube

punnie
Author by

punnie

Site Reliability Engineer with 10 years of experience in both Software Engineering and System Operations roles, owning a strong Software Engineering technical background and good business acumen. I've worked for companies such as the Fraunhofer Research Institute, Gruvi and Talkdesk, besides having done contract work for several international companies.

Updated on June 07, 2020

Comments

  • punnie
    punnie about 4 years

    Say I want to define that an URI such as:

    myapp://path/to/what/i/want?d=This%20is%20a%20test
    

    must be handled by my own application, or service. Notice that the scheme is "myapp" and not "http", or "ftp". That is precisely what I intend: to define my own URI schema globally for the Android OS. Is this possible?

    This is somewhat analogous to what some programs already do on, e.g., Windows systems, such as Skype (skype://) or any torrent downloader program (torrent://).

  • punnie
    punnie over 14 years
    Thanks for the heads up, but I'll be only using this to try to prove a concept, in a closed environment. Should this experiment ever leave its testing phase, I'll definitely consider ratifying the whole deal.
  • hackbod
    hackbod over 14 years
    Okay... but why not just do the right thing? It's not any significant more work.
  • Casebash
    Casebash about 14 years
    It took me a while to figure out that to link to a specific path that the "android:path" variable has to specify everything after the protocol, ie. it must be of the form "youtube.com/myvideo"
  • AlikElzin-kilaka
    AlikElzin-kilaka about 12 years
    Youtube do what @hackbod is suggesting, but opening Youtube links from facebook opens the browser and not the Youtube app. Is this mechanism too "delicate"?
  • Timo Ernst
    Timo Ernst about 11 years
    Works great but how can I read the value of the GET parameter "d" given in the url from MyUriActivity?
  • Chicowitz
    Chicowitz over 10 years
    I'm leaning towards defining my own scheme so that I can use the same web logic to launch either my iOS app OR my Android app. Just my 2 cents
  • mohitum
    mohitum almost 10 years
    not working for me I have multiple Intent filters for the same activity. One for main launcher. second for opening a particular file third as above First two are working perfectly but not the third.
  • Salmaan
    Salmaan over 9 years
    can you please look at the question here stackoverflow.com/q/29116574/3828908
  • Bugs Happen
    Bugs Happen over 8 years
    what if the link is like http://www.host.com/directory/value? How can we get this value?
  • Bugs Happen
    Bugs Happen over 8 years
    Never mind, got the SO answer here.
  • Zensaburou
    Zensaburou over 8 years
    English language version of the above link just in case someone needs it.
  • Pradeep Chakravarti Gudipati
    Pradeep Chakravarti Gudipati about 7 years
    How to read the data tags in AndroidManifest.xml in code without using meta data. I need that to send the exact scheme,path & host to the server also in the oauth call. I do not want to duplicate the call back declaration !
  • bob
    bob about 7 years
    This won't work if sending a URI such as "<a href="myApp://path> Here</a> (path being any fully formed com.app.packagename) using GMAIL. GMAIL receives the link in the message body but does not recognize it as a link. The same email received in MS Outlook will show the link and when clicked, try to open an application. I'm stuck trying to email a link to my phone with an embedded link to open my app.
  • Muhammad Muazzam
    Muhammad Muazzam over 6 years
    @Daniel I am passing url like this iptv2://cityofworks.com/1510126973.m3u but file is not being accessible while I have intent filter in file here 1drv.ms/u/s!AmLTh4MRccdmimQx6rkwCz7MzS7e
  • Martin
    Martin about 6 years
    @BugsHappen it's last URI path segment. Use uri.getLastPathSegment();
  • icyerasor
    icyerasor over 5 years
    @hackbod I do not think they had android in mind when they wrote that rfc. While I'm 100% with you that it is not necessary to create a new scheme, I think the reason is exactly this: that it's not even necessary to accomplish the goal. And now.. when you're like facebook, whatsapp or other big, established tec tools - the "don't create a new URI-Scheme"-Rule does not apply to you anymore of course. There will be no collision on scheme names when your name is already tied to a company on a global scale.
  • Hashim Akhtar
    Hashim Akhtar over 5 years
    I had to remove the android:host="path" to make it work. Now it works with Gmail.