238 votes

Comment détecter si l'URL a changé après un hachage en JavaScript ?

Comment puis-je vérifier si une URL a changé en JavaScript ? Par exemple, des sites Web comme GitHub, qui utilisent AJAX, ajouteront des informations sur la page après un symbole # pour créer une URL unique sans recharger la page. Quel est le meilleur moyen de détecter si cette URL a changé ?

  • Est-ce que le onload L'événement est rappelé ?
  • Y a-t-il un gestionnaire d'événement pour l'URL ?
  • Ou faut-il vérifier l'URL toutes les secondes pour détecter un changement ?

1 votes

Pour les futurs visiteurs, une nouvelle réponse de @aljgom de 2018 est la meilleure solution : stackoverflow.com/a/52809105/151503

27voto

Trev14 Points 916

Ajoutez un écouteur d'événement de changement de hachage !

window.addEventListener('hashchange', function(e){console.log('hash changed')});

Ou, pour écouter tous les changements d'URL :

window.addEventListener('popstate', function(e){console.log('url changed')});

C'est mieux que quelque chose comme le code ci-dessous car une seule chose peut exister dans window.onhashchange et vous pourriez écraser le code de quelqu'un d'autre.

// Bad code example

window.onhashchange = function() { 
     // Code that overwrites whatever was previously in window.onhashchange  
}

14voto

leoneckert Points 155

Cette solution a fonctionné pour moi :

var oldURL = "";
var currentURL = window.location.href;
function checkURLchange(currentURL){
    if(currentURL != oldURL){
        alert("url changed!");
        oldURL = currentURL;
    }

    oldURL = window.location.href;
    setTimeout(function() {
        checkURLchange(window.location.href);
    }, 1000);
}

checkURLchange();

6voto

Si aucun des événements de la fenêtre ne fonctionne pour vous (comme c'est le cas pour moi), vous pouvez également utiliser un fichier de type MutationObserver qui examine l'élément Root (de manière non récursive).

// capture the location at page load
let currentLocation = document.location.href;

const observer = new MutationObserver((mutationList) => {
  if (currentLocation !== document.location.href) {
    // location changed!
    currentLocation = document.location.href;

    // (do your event logic here)
  }
});

observer.observe(
  document.getElementById('root'),
  {
    childList: true,

    // important for performance
    subtree: false
  });

Ce n'est pas toujours possible, mais en général, si l'URL change, le contenu de l'élément racine change aussi.

Je n'ai pas fait de profilage, mais théoriquement cela a moins d'overhead qu'un timer parce que le pattern Observer est typiquement implémenté de telle sorte qu'il boucle juste à travers les souscriptions quand un changement se produit. Nous n'avons ajouté qu'un seul abonnement ici. Le timer d'autre part devrait vérifier très fréquemment afin de s'assurer que l'événement a été déclenché immédiatement après le changement d'URL.

De plus, cette méthode a de bonnes chances d'être plus fiable qu'une minuterie puisqu'elle élimine les problèmes de timing.

4voto

Ray Booysen Points 10606

Bien qu'il s'agisse d'une vieille question, le Barre de localisation Le projet est très utile.

var LocationBar = require("location-bar");
var locationBar = new LocationBar();

// listen to all changes to the location bar
locationBar.onChange(function (path) {
  console.log("the current url is", path);
});

// listen to a specific change to location bar
// e.g. Backbone builds on top of this method to implement
// it's simple parametrized Backbone.Router
locationBar.route(/some\-regex/, function () {
  // only called when the current url matches the regex
});

locationBar.start({
  pushState: true
});

// update the address bar and add a new entry in browsers history
locationBar.update("/some/url?param=123");

// update the address bar but don't add the entry in history
locationBar.update("/some/url", {replace: true});

// update the address bar and call the `change` callback
locationBar.update("/some/url", {trigger: true});

4voto

John Kennedy Points 2490

Pour écouter les changements d'url, voir ci-dessous :

window.onpopstate = function(event) {
  console.log("location: " + document.location + ", state: " + JSON.stringify(event.state));
};

Utilisez ce style si vous avez l'intention d'arrêter/supprimer l'auditeur après une certaine condition.

window.addEventListener('popstate', function(e) {
   console.log('url changed')
});

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X