javascript - saber - ¿Cómo probar si una cadena de URL es absoluta o relativa?
como saber si es plata o alpaca (11)
¿Cómo puedo probar una URL si es una ruta relativa o absoluta en Javascript o jQuery? Quiero manejar en consecuencia, dependiendo de si la URL pasada es una ruta local o externa.
if (urlString starts with http:// or https://)
//do this
Un enfoque aún más universal URI compatible con RFC:
(?:^[az][a-z0-9+.-]*:|////)
explicación de la expresión regular
Las otras soluciones enumeradas aquí fallarían para enlaces como mailto:[email protected]
RFC 3986 define un Esquema como:
scheme = ALPHA *( ALPHA / DIGIT / "+" / "-" / "." )
3.1. Esquema https://tools.ietf.org/html/rfc3986#section-3.1
Si bien la URL relativa al protocolo es técnicamente válida según la sección 4.2, Paul Irish ha cambiado hacia atrás y lo considera un antipatrón. Ver http://www.paulirish.com/2010/the-protocol-relative-url/
4.2. Referencia relativa http://tools.ietf.org/html/rfc3986#section-4.2
Si desea la expresión regular sin el uso de url relativa al protocolo:
^[az][a-z0-9+.-]*:
Para ver una lista completa de otros tipos de casos de borde de uri válidos, consulte la lista aquí: https://en.wikipedia.org/wiki/URI_scheme
RÁPIDO
Si solo necesita probar http://
o https://
, la forma más eficiente es:
if (urlString.indexOf(''http://'') === 0 || urlString.indexOf(''https://'') === 0)
UNIVERSAL
Sin embargo, sugeriría un enfoque más universal, que no distinga entre mayúsculas y minúsculas, compatible con el protocolo :
var r = new RegExp(''^(?:[a-z]+:)?//'', ''i'');
r.test(''http://example.com''); // true - regular http absolute URL
r.test(''HTTP://EXAMPLE.COM''); // true - HTTP upper-case absolute URL
r.test(''https://www.exmaple.com''); // true - secure http absolute URL
r.test(''ftp://example.com/file.txt''); // true - file transfer absolute URL
r.test(''//cdn.example.com/lib.js''); // true - protocol-relative absolute URL
r.test(''/myfolder/test.txt''); // false - relative URL
r.test(''test''); // false - also relative URL
Explica el RegExp
^(?:[a-z]+:)?//
^
- comienzo de la cadena
(?:
- comienzo de un grupo no capturado
[az]+
- cualquier caracter de ''a'' a ''z'' 1 o más veces
:
- cadena (carácter de dos puntos)
)?
- fin del grupo no capturado Grupo que aparece 0 o 1 veces
//
- cadena (dos caracteres de barra inclinada)
''i''
: indicador que no distingue entre mayúsculas y minúsculas
Hoy en día, cuando muchos servicios usan una URL relativa al protocolo (por ejemplo, //cdn.example.com/libary.js ), este método es más seguro:
var isAbsolute = new RegExp(''^([a-z]+://|//)'', ''i'');
if (isAbsolute.test(urlString)) {
// go crazy here
}
No use cosas de bajo nivel como regexp, etc. Estas cosas han sido resueltas por muchas otras personas. Especialmente los casos extremos.
Eche un vistazo a URI.js , debería hacer el trabajo: http://medialize.github.io/URI.js/docs.html#is
var uri = new URI("http://example.org/");
uri.is("absolute") === true;
Se llamará a la siguiente función cuando se produzca un clic en un hipervínculo, es decir, una etiqueta ''a'' si la etiqueta contiene url será relativa o contiene el mismo host, luego esa nueva página se cargará en la misma pestaña si contiene una URL diferente y la página cargará nueva pestaña del navegador
jQuery(document).ready(function() {
$(''a'').click(function(){
var a = this;
var a_href = $(this).attr(''href'');
var regex = new RegExp(''^(?:[a-z]+:)?//'', ''i'');
if(a.host == location.host || regex.test(a_href) == false){
a.target = ''_self'';
}else{
a.target = ''_blank'';
}
});
});
Un control muy rápido y muy flexible es:
if (url.indexOf(''://'') > 0 || url.indexOf(''//'') === 0 ) {
// URL is absolute; either "http://example.com" or "//example.com"
} else {
// URL is relative
}
Esto reconocerá una URL absoluta, si:
- La URL contiene ": //" en cualquier lugar después del primer carácter, o
- La URL comienza con "//" (relativo al protocolo)
- Sin expresiones regulares
- Sin jQuery u otra dependencia.
- No hay nombres de protocolo codificados que hagan que la condición sea sensible a mayúsculas y minúsculas.
- Sin manipulación de cadenas (por ej. ToLowerCase o similar).
- Solo las verificaciones de "relativo o absoluto" pero no hacen ninguna otra verificación de cordura, se pueden usar para URL web o cualquier protocolo interno.
Actualizar
Aquí hay una función rápida que devuelve verdadero / falso para la URL dada:
function isUrlAbsolute(url) {
return (url.indexOf(''://'') > 0 || url.indexOf(''//'') === 0);
}
Y lo mismo en ES6:
const isUrlAbsolute = (url) => (url.indexOf(''://'') > 0 || url.indexOf(''//'') === 0)
Actualización 2
Para abordar direcciones URL en formato /redirect?target=http://example.org
, recomiendo usar este código:
function isUrlAbsolute(url) {
if (url.indexOf(''//'') === 0) {return true;} // URL is protocol-relative (= absolute)
if (url.indexOf(''://'') === -1) {return false;} // URL has no protocol (= relative)
if (url.indexOf(''.'') === -1) {return false;} // URL does not contain a dot, i.e. no TLD (= relative, possibly REST)
if (url.indexOf(''/'') === -1) {return false;} // URL does not contain a single slash (= relative)
if (url.indexOf('':'') > url.indexOf(''/'')) {return false;} // The first colon comes after the first slash (= relative)
if (url.indexOf(''://'') < url.indexOf(''.'')) {return true;} // Protocol is defined before first dot (= absolute)
return false; // Anything else must be relative
}
Y lo mismo en forma corta y ES 6
// Traditional JS, shortened
function isUrlAbsolute(url) {
return url.indexOf(''//'') === 0 ? true : url.indexOf(''://'') === -1 ? false : url.indexOf(''.'') === -1 ? false : url.indexOf(''/'') === -1 ? false : url.indexOf('':'') > url.indexOf(''/'') ? false : url.indexOf(''://'') < url.indexOf(''.'') ? true : false;
}
// ES 6
const isUrlAbsolute = (url) => (url.indexOf(''//'') === 0 ? true : url.indexOf(''://'') === -1 ? false : url.indexOf(''.'') === -1 ? false : url.indexOf(''/'') === -1 ? false : url.indexOf('':'') > url.indexOf(''/'') ? false : url.indexOf(''://'') < url.indexOf(''.'') ? true : false)
Aquí hay algunos casos de prueba:
// Test
console.log( isUrlAbsolute(''http://.com'') ) // -> true
console.log( isUrlAbsolute(''//.com'') ) // -> true
console.log( isUrlAbsolute(''.com'') ) // -> false
console.log( isUrlAbsolute(''Ftp://example.net'') ) // -> true
console.log( isUrlAbsolute(''/redirect?target=http://example.org'') ) // -> false
Usa una expresión regular:
if (/^(?:[a-z]+:)?/////i.test(url))
var adress = ''http://roflmao.com'';
if (adress.substr(0,7) == ''http://'' || adress.substr(0,8) == ''https://'') {
//
}
var external = RegExp(''^(https?:)?//'');
if(external.test(el)){
// do something
}
EDITAR:
Con la siguiente expresión regular, incluso puede verificar si el enlace va al mismo dominio o a uno externo:
var external = RegExp(''^((f|ht)tps?:)?//(?!'' + location.host + '')'');
if(external.test(el)){
// do something
}
var isExternalURL = url.toLowerCase().indexOf(''http://'') === 0 || url.toLowerCase().indexOf(''https://'') === 0 ;
var pat = /^https?://///i;
if (pat.test(urlString))
{
//do stuff
}
Para las URL relativas al protocolo, use esta expresión regular:
/^https?:////|^/////i