Liberale URL Regex di aiuto Hacking Gruber
Domanda
Mi sono preso la liberale URL Regex da Daring Fireball , fusa con alcuni dei miglioramenti Alan tempesta e hacked la mia strada nel fissare alcuni bug come il supporto per i caratteri IDN all'interno delle parentesi. Questo è quello che ho:
/(?:[\w-]+:\/\/?|www[.])[^\s()<>]+(?:(?:\([^\s()<>]*\)[^\s()<>]*)+|[^[:punct:]\s]|\/)/
Comunque ho incontrato un bug che non sto essendo in grado di risolvere:
'www.dsd(sd)sdsd.com' // can also be the valid 'www.dsd.com/whatever(whatever)'
L'URL di cui sopra è stato riconosciuto come www.dsd(sd)sdsd.com'
(o www.dsd.com/whatever(whatever)'
) al posto di www.dsd(sd)sdsd.com
(o www.dsd.com/whatever(whatever)
). Questo sembra accadere solo quando l'URL è parentesi, dal momento che il seguente URL:
'www.sampleurl.com'
è correttamente essere riconosciuto come www.sampleurl.com
.
Credo che la parte [^[:punct:]\s]|\/
del regex non viene eseguita quando l'URL ha parentesi , ho cercato per qualche tempo, ma io non riesco a trovare una soluzione. Qualcuno mi può aiutare?
Per merce, ho creato una Rubular permalink con l'espressione regolare e alcuni dati di test (l'ultimo URL fallisce).
Credo che regex di Gruber era un po 'affrettata, per esempio, non corrisponde del URL del tipo:
http://en.wikipedia.org/wiki/Something_(Special)_For_You
Sono ancora più colpito nel vedere che entrambi Gruber e Alan perso questo molto semplice errore di battitura:
\([\w\d]+\)
Non sarebbe \(\w+\)
essere sufficiente? : S
Soluzione
Gruber ha rivisto la sua espressione regolare :
\b((?:[a-z][\w-]+:(?:\/{1,3}|[a-z0-9%])|www\d{0,3}[.])(?:[^\s()<>]+|\([^\s()<>]+\))+(?:\([^\s()<>]+\)|[^`!()\[\]{};:'".,<>?«»“”‘’\s]))
Altri suggerimenti
www.dsd (sd) sdsd.com non è un nome di dominio valido.
Se avessi 'www.dsd.com/whatever(whatever)'
, sarebbe stato riconosciuto correttamente. (O almeno è nelle mie prove)
/(?:[\w-]+:\/\/?|www[.])[^\s()<>]+(?:(?:\([^\s()<>]*\)[^\s()<>]*)+|[^[:punct:]\s]|\/)/
www. | | |
dsd | |
(sd) |
sdsd.com'
Ecco come credo che questo si rompe ... la punta del regex sopra (sd)
inizia con un sfuggiti parentesi aperta, poi un Stared char classe corrispondente sd
, poi un sfuggiti paren di chiusura, e la prossima cosa è [^\s()<>]*
che corrisponde sdsd.com'
.