Navigation Menu

Skip to content

Instantly share code, notes, and snippets.

@davidwkeith
Last active April 10, 2024 12:01
Show Gist options
  • Save davidwkeith/2662899 to your computer and use it in GitHub Desktop.
Save davidwkeith/2662899 to your computer and use it in GitHub Desktop.
NOTE: This was a great hack in days gone by, but now both Apple and Google have improved their support for custom protocol handlers. Licensed under the WFTPL http://www.wtfpl.net/txt/copying/
<!doctype html>
<html>
<head>
<meta charset="utf-8">
<title>App Redirection</title>
</head>
<body>
<!--
NOTE: This was a great hack in days gone by, but now both Apple and Google have improved their support for custom
protocol handlers.
# References
* Handle Open URL: http://handleopenurl.com/
* iOS Smart App Banners: https://developer.apple.com/library/content/documentation/AppleApplications/Reference/SafariWebContent/PromotingAppswithAppBanners/PromotingAppswithAppBanners.html
* Android Intents: https://developer.android.com/reference/android/content/Intent.html
* On the desktop you still need to make a custom plugin to do the right thing, or save some sort of user prefernce.
-->
<!-- iframe used for attempting to load a custom protocol -->
<iframe style="display:none" height="0" width="0" id="loader"></iframe>
<script>(function(){
// For desktop browser, remember to pass though any metadata on the link for deep linking
var fallbackLink = 'http://example.com/my-web-app/'+window.location.search+window.location.hash;
// Simple device detection
var isiOS = navigator.userAgent.match('iPad') || navigator.userAgent.match('iPhone') || navigator.userAgent.match('iPod'),
isAndroid = navigator.userAgent.match('Android');
// Mobile
if (isiOS || isAndroid) {
// Load our custom protocol in the iframe, for Chrome and Opera this burys the error dialog (which is actually HTML)
// for iOS we will get a popup error if this protocol is not supported, but it won't block javascript
document.getElementById('loader').src = 'custom-protocol://my-app'+window.location.search+window.location.hash;
// The fallback link for Android needs to be https:// rather than market:// or the device will try to
// load both URLs and only the last one will win. (Especially FireFox, where an "Are You Sure" dialog will appear)
// on iOS we can link directly to the App Store as our app switch will fire prior to the switch
// If you have a mobile web app, your fallback could be that instead.
fallbackLink = isAndroid ? 'https://play.google.com/store/apps/details?id=com.mycompany.myapp' :
'itms-apps://itunes.apple.com/app/my-app/idxxxxxxxx?mt=8' ;
}
// Now we just wait for everything to execute, if the user is redirected to your custom app
// the timeout below will never fire, if a custom app is not present (or the user is on the Desktop)
// we will replace the current URL with the fallbackLink (store URL or desktop URL as appropriate)
window.setTimeout(function (){ window.location.replace(fallbackLink); }, 1);
/*
Q&A
I have a native desktop app as well, how do I link to a custom protocol handler on the desktop?
IE Only: http://msdn.microsoft.com/en-us/library/ms537512.aspx#Version_Vectors
All Other Browsers: Use a custom plugin like iTunes does: http://ax.itunes.apple.com/detection/itmsCheck.js
*/
})();</script>
</body>
</html>
@curbsaleem
Copy link

doesn't work with iOS9

@ebsaral
Copy link

ebsaral commented Oct 27, 2015

document.getElementById('loader').src = '{{ url }}';

this does not work in iOS 9

@jonesmac
Copy link

jonesmac commented Jun 9, 2017

This mostly worked for me...major gotcha for iOS is that you cannot start your custom protocol with a number. Evidently that get's url encoded and the redirect will fail since it would find that registered with an app. Specifically, I noticed that 9 gets reencoded as %39

@maquannene
Copy link

Safair has already not support call up app by iframe after iOS9.

@yashwanthkumar1796
Copy link

Safair has already not support call up app by iframe after iOS9.

@maquannene did you find any solution for this ??

@yashwanthkumar1796
Copy link

document.getElementById('loader').src = '{{ url }}';

this does not work in iOS 9

Hi, Did you find any solution for this ??

@quantumpotato
Copy link

How do you pass data to the appstore - to the itms link?

@davidwkeith
Copy link
Author

@quantumpotato You really shouldn't be using this hack anymore. Use Smart App Banners on iOS and Intents on Android.

@quantumpotato
Copy link

@davidwkeith can you pass data to be loaded by the app when it boots up with smart banners?

@davidwkeith
Copy link
Author

yes, just provided an app-argument in the content parameters of the Smart App Banner meta tag.

See the official documentation here https://developer.apple.com/documentation/webkit/promoting_apps_with_smart_app_banners

@quantumpotato
Copy link

Thank you

@jjj201200
Copy link

Thank you

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment