web-dev-qa-db-fra.com

Suppression du lien entre les navigateurs mobiles et l'application native - Problèmes avec Chrome lorsque l'application n'est pas installée

J'ai une page Web, appelons-la entry.html.

Lorsqu'un utilisateur entre sur cette page, un code javascript (voir ci-dessous) tente de lier en profondeur l'utilisateur à l'application iOS/Android Android native).

Si le lien profond échoue (probablement si l'application n'est pas installée sur l'appareil), l'utilisateur doit "se replier" sur une autre page - appelons-le fallback.html.

voici le code javascript qui s'exécute sur entry.html:

$(function(){
    window.location = 'myapp://';
    setTimeout(function(){
        window.location = 'fallback.html';
    }, 500);
});

il s'agit d'une méthode de lien profond standard recommandée sur tout le réseau; essayez de créer un lien profond, et si le délai d'expiration se déclenche, cela signifie que le lien profond ne s'est pas produit - donc repli.

cela fonctionne très bien, tant que l'application est installée sur l'appareil.

mais si l'application n'est pas installée, c'est le comportement lors de la tentative de lien profond:

Mobile Safari: Je vois un message d'alerte disant "Safari ne peut pas ouvrir cette page ..." pendant un moment, puis il revient correctement à fallback.html- qui est le comportement attendu.

Chrome mobile est mon problème.

lorsque l'application n'est pas installée, le navigateur est en fait redirigé vers le myapp:// url, qui est bien sûr invalide, donc j'obtiens une page "non trouvée" et le repli ne se produit pas.

Enfin - ma question est:

Comment puis-je corriger mon code afin que le RETOUR se produise sur mobile Chrome également? Tout comme Mobile Safari?

Remarque: je vois que le site Web mobile de LinkedIn le fait correctement, avec Safari Chrome, avec ou sans l'application installée, mais je n'ai pas pu retrouver le code responsable: (

note2: j'ai essayé d'ajouter un iframe au lieu de window.location = url, cela ne fonctionne que sur Safari, mobile Chrome ne crée pas de lien profond lors de l'ajout d'un iFrame même si l'application est installée.

Merci a tous!


MISE À JOUR:

j'ai trouvé une solution décente et j'ai répondu à ma propre question. voir la réponse acceptée pour ma solution.

24
geevee

pour celui qui est intéressé, j'ai réussi à trouver une solution décente pour résoudre ces problèmes avec deeplinking Chrome sur Android.

j'ai abandonné le myapp:// approche, je l'ai laissé fonctionner uniquement dans le cas d'un appareil iOS.

pour Android, j'utilise maintenant intents qui sont conceptuellement différents que les myapp:// protocole.

Je suis principalement un développeur Web, pas un développeur Android, il m'a donc fallu un certain temps pour comprendre le concept, mais c'est assez simple. J'essaierai d'expliquer et de démontrer MA solution ici ( notez qu'il existe d'autres approches qui pourraient être implémentées avec intents, mais celle-ci a parfaitement fonctionné pour moi).

voici la partie pertinente du manifeste de l'application Android, enregistrant les règles d'intention (notez le Android:scheme="http" - nous en parlerons sous peu):

<receiver Android:name=".DeepLinkReceiver">
    <intent-filter >
        <data Android:scheme="http" Android:Host="www.myapp.com" />
        <action Android:name="Android.intent.action.VIEW" />
        <category Android:name="Android.intent.category.BROWSABLE"/>
        <category Android:name="Android.intent.category.DEFAULT"/>
    </intent-filter>
</receiver>

maintenant, après que cela soit déclaré dans le manifeste de l'application, je m'envoie un e-mail avec " http://www.myapp.com " dans le message.

lorsque le lien est exploité avec le Android, une boîte de dialogue "sélecteur" apparaît, demandant avec quelle application je veux ouvrir ce qui suit? [chrome, myapp ]

la raison pour laquelle cette boîte de dialogue est apparue en tapant sur une URL "régulière", c'est parce que nous avons enregistré l'intention avec le schéma http .

avec cette approche, le lien profond n'est même pas géré dans la page Web, il est géré par le périphérique lui-même, lorsque vous appuyez sur un lien correspondant à une règle d'intention existante défini dans le manifeste de l'application Android.

et oui, comme je l'ai dit, cette approche est conceptuellement différente de l'approche iOS, qui invoque le lien profond depuis la page Web, mais elle résout le problème et fait la magie.

Remarque: lorsque l'application n'est pas installée, aucune boîte de dialogue de sélection n'apparaît, vous accédez simplement à la page Web réelle avec l'adresse donnée ( sauf si vous avez plus d'un navigateur, vous devrez donc en choisir un ... mais ne soyons pas mesquins).

j'espère vraiment que cela pourrait aider quelqu'un qui fait face à la même chose .. j'aurais aimé avoir une telle explication ;-)

à votre santé.

13
geevee

Il est très important de vous assurer que lorsque vous essayez d'ouvrir une URL de lien profond avec JavaScript, l'URL est correctement formatée pour l'appareil et le navigateur . (Si vous n'utilisez pas l'URL de lien profond appropriée pour le navigateur/la plate-forme, un utilisateur peut être redirigé vers une "Page non trouvée", ce que vous ressentez.)

Maintenant, vous devez noter que Chrome sur Android a un format d'URL différent de l'ancien standard Android navigateur  1! Vous devez annoter les liens profonds à l'aide de href="Android-app://" dans le balisage HTML de vos pages Web. Vous pouvez le faire dans la section de chaque page Web en ajoutant une balise et en spécifiant le lien profond en tant qu'URI alternatif.

Par exemple, l'extrait HTML suivant montre comment vous pouvez spécifier le lien profond correspondant dans une page Web contenant l'exemple d'URL: // gizmos.

<html>
<head>
    <link rel="alternate"
          href="Android-app://com.example.Android/example/gizmos" />
    ...
</head>
<body> ... </body>

Pour plus de détails, voir les références ici:
https://developer.chrome.com/multidevice/Android/intents
https://developers.google.com/app-indexing/webmasters/server
https://developer.Android.com/training/app-indexing/enabling-app-indexing.html#webpages

Et voici un outil de test de liens profonds pour Android: https://developers.google.com/app-indexing/webmasters/test.html

J'espère que ça t'as aidé.

1 Étant donné que l'ancien navigateur AOSP a été remplacé par chrome, c'est maintenant la façon par défaut de gérer les liens profonds pour les versions récentes Android. Néanmoins, Android nécessite toujours une conditionnelle) solution, car les anciennes versions du système d'exploitation utilisent toujours le navigateur AOSP.

8
eyecatchUp

J'ai créé un plugin Javascript, qui prend en charge la plupart des navigateurs modernes sur mobile. Mais cela nécessite d'avoir des pages de destination de liens profonds hébergées sur un domaine croisé (différent de l'URL du lien universel) pour fonctionner sur ios9 Facebook en utilisant la liaison universelle. Il existe également différentes manières de le faire fonctionner sur Facebook iOS9 à l'aide du SDK Facebook. Je partage ceci si quelqu'un peut trouver cela utile. Actuellement, il ne propose pas d'option de repli, mais s'il revient à l'App Store.

https://github.com/prabeengiri/DeepLinkingToNativeApp

1
prabeen giri

J'utilise ce code pour pour deeplinking. Si l'application est installée, l'application s'ouvrira. Si l'application n'est pas installée, cela reste tel quel. Si vous souhaitez ajouter une autre condition pour l'application sans installation, décommentez simplement le code setTimeout.

<script>

var deeplinking_url = scootsy://vendor/1;
$(document).ready(function(){
    call_me_new(deeplinking_url);
});

var call_me_new = function(deeplinking_url){

    if(deeplinking_url!=''){
        var fallbackUrl ='http://scootsy.com/';
        var iframe = document.createElement("iframe");
        var nativeSchemaUrl = deeplinking_url;
        console.log(nativeSchemaUrl);

        iframe.id = "app_call_frame";
        iframe.style.border = "none";
        iframe.style.width = "1px";
        iframe.style.height = "1px";
        iframe.onload = function () {
            document.location = nativeSchemaUrl;
        };
        iframe.src = nativeSchemaUrl; //iOS app schema url
        window.onload = function(){
            document.body.appendChild(iframe);
        }

        //IF the App is not install then it will remain on the same page.If you wish to send the use to other page then uncomment the below code and send a time interval for the redirect.
        /*
        setTimeout(function(){
            console.log('Iframe Removed...');
            document.getElementById("app_call_frame").remove();

        window.location = fallbackUrl; //fallback url
        },5000);*/
    }
};
</script>
1
Stephen Salve