Tester si les liens sont externes avec jQuery / javascript?
Comment tester pour voir si les liens sont externes ou internes? Veuillez noter:
- Je ne peux pas coder le domaine local.
- Je ne peux pas tester pour"http". Je pourrais tout aussi bien me connecter à mon propre site avec un lien absolu http.
- je veux utiliser jQuery / javascript, pas css.
je soupçonne que la réponse se trouve quelque part dans l'emplacement.href, mais la solution m'échappe.
Merci!
12 réponses
var comp = new RegExp(location.host);
$('a').each(function(){
if(comp.test($(this).attr('href'))){
// a link that contains the current host
$(this).addClass('local');
}
else{
// a link that does not contain the current host
$(this).addClass('external');
}
});
Note: Ceci est juste un exemple rapide et sale. Il correspondrait à tous les liens href="#anchor" comme externe. Il pourrait être amélioré en faisant une vérification supplémentaire de RegExp.
mise à jour 2016-11-17
cette question a encore beaucoup de circulation et j'ai été dit par une tonne de personnes que cette solution acceptée échouera à plusieurs reprises. Comme je l'ai dit, c'était un très rapide et sale réponse à montrer la voie principale comment résoudre ce problème. Une solution plus sophistiquée consiste à utiliser les propriétés accessibles sur un élément <a>
(ancre). Comme @Daved l'a déjà souligné dans cette réponse, la clé est de comparer le hostname
avec le window.location.hostname
actuel . Je préférerais comparer les propriétés hostname
, car elles n'incluent jamais la propriété port
qui est incluse à la propriété host
si elle diffère de 80.
So nous y voilà:
$( 'a' ).each(function() {
if( location.hostname === this.hostname || !this.hostname.length ) {
$(this).addClass('local');
} else {
$(this).addClass('external');
}
});
Etat de l'art:
Array.from( document.querySelectorAll( 'a' ) ).forEach( a => {
a.classList.add( location.hostname === a.hostname || !a.hostname.length ? 'local' : 'external' );
});
je sais que ce post est vieux mais il montre toujours au sommet des résultats donc je voulais offrir une autre approche. Je vois tous les contrôles regex sur un élément d'ancrage, mais pourquoi ne pas simplement utiliser window.location.host
et vérifier la propriété host
de l'élément?
function link_is_external(link_element) {
return (link_element.host !== window.location.host);
}
avec jQuery:
$('a').each(function() {
if (link_is_external(this)) {
// External
}
});
et avec javascript simple:
var links = document.getElementsByTagName('a');
for (var i = 0; i < links.length; i++) {
if (link_is_external(links[i])) {
// External
}
}
Et la non-jQuery façon
var nodes = document.getElementsByTagName("a"), i = nodes.length;
var regExp = new RegExp("//" + location.host + "($|/)");
while(i--){
var href = nodes[i].href;
var isLocal = (href.substring(0,4) === "http") ? regExp.test(href) : true;
alert(href + " is " + (isLocal ? "local" : "not local"));
}
tous les href ne commençant pas par http
(http://, https://) sont automatiquement traités comme locaux
var external = RegExp('^((f|ht)tps?:)?//(?!' + location.host + ')');
Utilisation:
external.test('some url'); // => true or false
voici un sélecteur jQuery pour Liens externes seulement:
$('a[href^="(http:|https:)?//"])')
un sélecteur jQuery uniquement pour les liens internes (à l'exclusion des liens de hachage dans la même page) doit être un peu plus compliqué:
$('a:not([href^="(http:|https:)?//"],[href^="#"],[href^="mailto:"])')
Les filtres supplémentaires peuvent être placés à l'intérieur de la condition :not()
et séparés par des virgules supplémentaires si nécessaire.
http://jsfiddle.net/mblase75/Pavg2 /
alternativement, nous pouvons filtrer les liens internes en utilisant la propriété JavaScript vanilla href
, qui est toujours une URL absolue:
$('a').filter( function(i,el) {
return el.href.indexOf(location.protocol+'//'+location.hostname)===0;
})
vous en avez oublié un, et si vous utilisez un chemin relatif.
parexemple: /test
hostname = new RegExp(location.host);
// Act on each link
$('a').each(function(){
// Store current link's url
var url = $(this).attr("href");
// Test if current host (domain) is in it
if(hostname.test(url)){
// If it's local...
$(this).addClass('local');
}
else if(url.slice(0, 1) == "/"){
$(this).addClass('local');
}
else if(url.slice(0, 1) == "#"){
// It's an anchor link
$(this).addClass('anchor');
}
else {
// a link that does not contain the current host
$(this).addClass('external');
}
});
il y a aussi la question des téléchargements de fichiers .zip locaux (en externe), qui pourrait utiliser les classes locales "télécharger" ou "externe"télécharger". Mais n'ai pas trouvé de solution pour l'instant.
Vous pouvez utiliser url externe module.
var isExternal = require('is-url-external');
isExternal('http://stackoverflow.com/questions/2910946'); // true | false
/**
* All DOM url
* [links description]
* @type {[type]}
*/
var links = document.querySelectorAll('a');
/**
* Home Page Url
* [HomeUrl description]
* @type {[type]}
*/
var HomeUrl = 'https://stackoverflow.com/'; // Current Page url by-> window.location.href
links.forEach(function(link) {
link.addEventListener('click', function(e) {
e.preventDefault();
// Make lowercase of urls
var url = link.href.toLowerCase();
var isExternalLink = !url.includes(HomeUrl);
// Check if external or internal
if (isExternalLink) {
if (confirm('it\'s an external link. Are you sure to go?')) {
window.location = link.href;
}
} else {
window.location = link.href;
}
})
})
<a href="https://stackoverflow.com/users/3705299/king-rayhan">Internal Link</a>
<a href="https://wordpress.stackexchange.com/">External Link</a>
Oui, je crois que vous pouvez récupérer le nom de domaine actuel emplacement.href. Une autre possibilité est de créer un élément de lien, de définir le src à / puis de récupérer l'URL canonique (ceci récupérera L'URL de base si vous en utilisez un, et pas nécessairement le nom de domaine).
Voir Aussi ce post: obtenir L'URI complet de la propriété href d'un lien
pour les personnes intéressées, j'ai fait une version ternaire du bloc if avec un check pour voir quelles classes l'élément a et quelle classe est attachée.
$(document).ready(function () {
$("a").click(function (e) {
var hostname = new RegExp(location.host);
var url = $(this).attr("href");
hostname.test(url) ?
$(this).addClass('local') :
url.slice(0, 1) == "/" && url.slice(-1) == "/" ?
$(this).addClass('localpage') :
url.slice(0, 1) == "#" ?
$(this).addClass('anchor') :
$(this).addClass('external');
var classes = $(this).attr("class");
console.log("Link classes: " + classes);
$(this).hasClass("external") ? googleAnalytics(url) :
$(this).hasClass("anchor") ? console.log("Handle anchor") : console.log("Handle local");
});
});
le bit Google analytics peut être ignoré, mais c'est là que vous aimeriez probablement faire quelque chose avec l'url maintenant que vous savez quel type de lien il s'agit. Il suffit d'ajouter du code dans le bloc ternaire. Si vous voulez seulement vérifier 1 Type de lien, remplacez les ternaires par une instruction if à la place.
édité pour ajouter dans un numéro que je suis tombé sur. Certains de mes href étaient "/Courses/" comme ça. J'ai vérifié s'il y avait un slash au début et à la fin du href. Bien que le simple fait de vérifier Un " / " Au début soit probablement suffisant.
j'utilise cette fonction pour jQuery:
$.fn.isExternal = function() {
var host = window.location.host;
var link = $('<a>', {
href: this.attr('href')
})[0].hostname;
return (link !== host);
};
utilisation est: $('a').isExternal();
cela devrait fonctionner pour tout type de lien sur chaque navigateur sauf IE.
// check if link points outside of app - not working in IE
try {
const href = $linkElement.attr('href'),
link = new URL(href, window.location);
if (window.location.host === link.host) {
// same app
} else {
// points outside
}
} catch (e) { // in case IE happens}