Domanda

Qualcuno ha a portata di mano un'espressione regolare che corrisponderà a qualsiasi nome host DNS o indirizzo IP legale?

È facile scriverne uno che funziona il 95% delle volte, ma spero di ottenere qualcosa che sia ben testato per abbinare esattamente le ultime specifiche RFC per i nomi host DNS.

È stato utile?

Soluzione

Puoi usare le seguenti espressioni regolari separatamente o combinandole in un'espressione OR congiunta.

ValidIpAddressRegex = "^(([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])\.){3}([0-9]|[1-9][0-9]|1[0-9]{2}|2[0-4][0-9]|25[0-5])$";

ValidHostnameRegex = "^(([a-zA-Z0-9]|[a-zA-Z0-9][a-zA-Z0-9\-]*[a-zA-Z0-9])\.)*([A-Za-z0-9]|[A-Za-z0-9][A-Za-z0-9\-]*[A-Za-z0-9])$";

ValidIpAddressRegex corrisponde a indirizzi IP validi e ValidHostnameRegex nomi host validi. A seconda della lingua che usi \ potrebbe essere necessario scappare con \.


ValidHostnameRegex è valido secondo RFC 1123 . Inizialmente, RFC 952 specificava che i segmenti del nome host non potevano iniziare con una cifra.

http://en.wikipedia.org/wiki/Hostname

  

Le specifiche originali di   nomi host in RFC   952 ,   imposto che le etichette non potevano iniziare   con una cifra o con un trattino e   non deve terminare con un trattino. Tuttavia, a   specifica successiva ( RFC   1123 )   consentire l'avvio delle etichette dei nomi host   con cifre.

Valid952HostnameRegex = "^(([a-zA-Z]|[a-zA-Z][a-zA-Z0-9\-]*[a-zA-Z0-9])\.)*([A-Za-z]|[A-Za-z][A-Za-z0-9\-]*[A-Za-z0-9])$";

Altri suggerimenti

La regex del nome host di smink non osserva la limitazione sulla lunghezza delle singole etichette all'interno di un nome host. Ogni etichetta con un nome host valido non può superare i 63 ottetti.

ValidHostnameRegex="^([a-zA-Z0-9]|[a-zA-Z0-9][a-zA-Z0-9\-]{0,61}[a-zA-Z0-9])\
(\.([a-zA-Z0-9]|[a-zA-Z0-9][a-zA-Z0-9\-]{0,61}[a-zA-Z0-9]))*$"

Nota che la barra rovesciata alla fine della prima riga (sopra) è la sintassi della shell Unix per dividere la linea lunga. Non fa parte dell'espressione regolare stessa.

Ecco solo l'espressione regolare su una sola riga:

^([a-zA-Z0-9]|[a-zA-Z0-9][a-zA-Z0-9\-]{0,61}[a-zA-Z0-9])(\.([a-zA-Z0-9]|[a-zA-Z0-9][a-zA-Z0-9\-]{0,61}[a-zA-Z0-9]))*$

Dovresti anche controllare separatamente che la lunghezza totale del nome host non deve superare 255 caratteri . Per ulteriori informazioni, consultare RFC-952 e RFC-1123.

Per abbinare un indirizzo IP valido usa la seguente regex:

(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)(\.(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)){3}

anziché:

([01]?[0-9][0-9]?|2[0-4][0-9]|25[0-5])(\.([01]?[0-9][0-9]?|2[0-4][0-9]|25[0-5])){3}

Spiegazione

Molti motori regex corrispondono alla prima possibilità nella sequenza OR. Ad esempio, prova la seguente regex:

10.48.0.200

test

Prova la differenza tra good vs bad

Non riesco a modificare il primo post, quindi aggiungerò la mia risposta qui.

Per nome host - risposta semplice, ad esempio qui esempio - http: //www.linuxinsight.com/how_to_grep_for_ip_addresses_using_the_gnu_egrep_utility.html

egrep '([[:digit:]]{1,3}\.){3}[[:digit:]]{1,3}'

Anche se il caso non tiene conto di valori come 0 nell'ottetto del pugno e valori maggiori di 254 (indirizzo IP) o 255 (maschera di rete). Forse un'ulteriore dichiarazione if sarebbe di aiuto.

Per quanto riguarda il nome host DNS legale, a condizione che si stia verificando solo i nomi host Internet (e non Intranet), ho scritto il seguente frammento, un mix di shell / php ma dovrebbe essere applicabile come qualsiasi espressione regolare.

prima vai sul sito web ietf, scarica e analizza un elenco di nomi di dominio legali di livello 1:

tld=$(curl -s http://data.iana.org/TLD/tlds-alpha-by-domain.txt |  sed 1d  | cut -f1 -d'-' | tr '\n' '|' | sed 's/\(.*\)./\1/')
echo "($tld)"

Questo dovrebbe darti un bel codice di re che controlla la legalità del nome di dominio principale, come .com .org o .ca

Quindi aggiungi la prima parte dell'espressione secondo le linee guida trovate qui - http: //www.domainit.com/support/faq.mhtml?category=Domain_FAQ&question=9 (qualsiasi combinazione alfanumerica e ' - "simbolo, trattino non dovrebbe essere all'inizio o alla fine di un ottetto.

(([a-z0-9]+|([a-z0-9]+[-]+[a-z0-9]+))[.])+

Quindi metti tutto insieme (esempio PHP preg_match):

$pattern = '/^(([a-z0-9]+|([a-z0-9]+[-]+[a-z0-9]+))[.])+(AC|AD|AE|AERO|AF|AG|AI|AL|AM|AN|AO|AQ|AR|ARPA|AS|ASIA|AT|AU|AW|AX|AZ|BA|BB|BD|BE|BF|BG|BH|BI|BIZ|BJ|BM|BN|BO|BR|BS|BT|BV|BW|BY|BZ|CA|CAT|CC|CD|CF|CG|CH|CI|CK|CL|CM|CN|CO|COM|COOP|CR|CU|CV|CX|CY|CZ|DE|DJ|DK|DM|DO|DZ|EC|EDU|EE|EG|ER|ES|ET|EU|FI|FJ|FK|FM|FO|FR|GA|GB|GD|GE|GF|GG|GH|GI|GL|GM|GN|GOV|GP|GQ|GR|GS|GT|GU|GW|GY|HK|HM|HN|HR|HT|HU|ID|IE|IL|IM|IN|INFO|INT|IO|IQ|IR|IS|IT|JE|JM|JO|JOBS|JP|KE|KG|KH|KI|KM|KN|KP|KR|KW|KY|KZ|LA|LB|LC|LI|LK|LR|LS|LT|LU|LV|LY|MA|MC|MD|ME|MG|MH|MIL|MK|ML|MM|MN|MO|MOBI|MP|MQ|MR|MS|MT|MU|MUSEUM|MV|MW|MX|MY|MZ|NA|NAME|NC|NE|NET|NF|NG|NI|NL|NO|NP|NR|NU|NZ|OM|ORG|PA|PE|PF|PG|PH|PK|PL|PM|PN|PR|PRO|PS|PT|PW|PY|QA|RE|RO|RS|RU|RW|SA|SB|SC|SD|SE|SG|SH|SI|SJ|SK|SL|SM|SN|SO|SR|ST|SU|SV|SY|SZ|TC|TD|TEL|TF|TG|TH|TJ|TK|TL|TM|TN|TO|TP|TR|TRAVEL|TT|TV|TW|TZ|UA|UG|UK|US|UY|UZ|VA|VC|VE|VG|VI|VN|VU|WF|WS|XN|XN|XN|XN|XN|XN|XN|XN|XN|XN|XN|YE|YT|YU|ZA|ZM|ZW)[.]?$/i';

    if (preg_match, $pattern, $matching_string){
    ... do stuff
    }

Puoi anche aggiungere un'istruzione if per verificare che la stringa che controlli sia più corta di 256 caratteri - http://www.ops.ietf.org/lists/namedroppers/namedroppers.2003/msg00964.html

def isValidHostname(hostname):

    if len(hostname) > 255:
        return False
    if hostname[-1:] == ".":
        hostname = hostname[:-1]   # strip exactly one dot from the right,
                                   #  if present
    allowed = re.compile("(?!-)[A-Z\d-]{1,63}(?<!-)$", re.IGNORECASE)
    return all(allowed.match(x) for x in hostname.split("."))

Vale la pena notare che ci sono librerie per la maggior parte delle lingue che lo fanno per te, spesso integrate nella libreria standard. E è probabile che quelle librerie vengano aggiornate molto più spesso del codice che hai copiato da una risposta Stack Overflow quattro anni fa e che hai dimenticato. E ovviamente analizzeranno anche l'indirizzo in una forma utilizzabile, piuttosto che darti una corrispondenza con un gruppo di gruppi.

Ad esempio, il rilevamento e l'analisi di IPv4 in (POSIX) C:

#include <arpa/inet.h>
#include <stdio.h>

int main(int argc, char *argv[]) {
  for (int i=1; i!=argc; ++i) {
    struct in_addr addr = {0};
    printf("%s: ", argv[i]);
    if (inet_pton(AF_INET, argv[i], &addr) != 1)
      printf("invalid\n");
    else
      printf("%u\n", addr.s_addr);
  }
  return 0;
}

Ovviamente, tali funzioni non funzioneranno se stai provando, ad esempio, a trovare tutti gli indirizzi validi in un messaggio di chat & # 8212; ma anche lì, potrebbe essere più facile usare una regex semplice ma troppo zelante per trova potenziali corrispondenze, quindi utilizza la libreria per analizzarle.

Ad esempio, in Python:

>>> import ipaddress
>>> import re
>>> msg = "My address is 192.168.0.42; 192.168.0.420 is not an address"
>>> for maybeip in re.findall(r'\d{1,3}\.\d{1,3}\.\d{1,3}\.\d{1,3}', msg):
...     try:
...         print(ipaddress.ip_address(maybeip))
...     except ValueError:
...         pass

Penso che questa sia la migliore regex di validazione IP. per favore controlla una volta !!!

^(([01]?[0-9]?[0-9]|2([0-4][0-9]|5[0-5]))\.){3}([01]?[0-9]?[0-9]|2([0-4][0-9]|5[0-5]))$
/^(?:[a-zA-Z0-9]+|[a-zA-Z0-9][-a-zA-Z0-9]+[a-zA-Z0-9])(?:\.[a-zA-Z0-9]+|[a-zA-Z0-9][-a-zA-Z0-9]+[a-zA-Z0-9])?$/

localhost & # 1078; & # 1077; # 1077 &; # 1089 &; # 1090 &; & # 1100;

"^((\\d{1,2}|1\\d{2}|2[0-4]\\d|25[0-5])\.){3}(\\d{1,2}|1\\d{2}|2[0-4]\\d|25[0-5])$"

Funziona con indirizzi IP validi:

regex = '^([0-9]|[1-9][0-9]|[1][0-9][0-9]|[2][0-5][0-5])[.]([0-9]|[1-9][0-9]|[1][0-9][0-9]|[2][0-5][0-5])[.]([0-9]|[1-9][0-9]|[1][0-9][0-9]|[2][0-5][0-5])[.]([0-9]|[1-9][0-9]|[1][0-9][0-9]|[2][0-5][0-5])$'

Ecco un regex che ho usato in Ant per ottenere un IP host proxy o un nome host da ANT_OPTS. Questo è stato usato per ottenere l'IP proxy in modo da poter eseguire un quot & Ant; quot & Isreachable; test prima di configurare un proxy per una JVM biforcuta.

^.*-Dhttp\.proxyHost=(\w{1,}\.\w{1,}\.\w{1,}\.*\w{0,})\s.*$

Ho trovato che funziona abbastanza bene per gli indirizzi IP. Si convalida come la risposta migliore ma si assicura anche che l'ip sia isolato, quindi nessun testo o più numeri / decimali sono dopo o prima dell'ip.

  
    
      ??

(? &! Lt; \ S) (: (: \ d | [1-9] \ D | 1 \ d \ d | 2 [0-4] \ d | 25 [0- 5]) \ b |.?! \ b) {7} (\ S)

    
  
AddressRegex = "^(ftp|http|https):\/\/([0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}:[0-9]{1,5})$";

HostnameRegex =  /^(ftp|http|https):\/\/([a-z0-9]+\.)?[a-z0-9][a-z0-9-]*((\.[a-z]{2,6})|(\.[a-z]{2,6})(\.[a-z]{2,6}))$/i

questo re è usato solo per questo tipo di validazione

funziona solo se http://www.kk.com http://www.kk.co.in

non funziona per

http://www.kk.com/ http: //www.kk.co.in.kk

http://www.kk.com/dfas http://www.kk.co.in/

prova questo:

((2[0-4]\d|25[0-5]|[01]?\d\d?)\.){3}(2[0-4]\d|25[0-5]|[01]?\d\d?)

funziona nel mio caso.

Per quanto riguarda gli indirizzi IP, sembra che ci sia un dibattito sull'opportunità di includere zeri iniziali. Una volta era una pratica comune ed è generalmente accettata, quindi direi che dovrebbero essere contrassegnati come validi indipendentemente dalla preferenza corrente. C'è anche una certa ambiguità sul fatto che il testo prima e dopo la stringa debba essere convalidato e, di nuovo, penso che dovrebbe. 1.2.3.4 è un IP valido ma 1.2.3.4.5 non lo è e né la parte 1.2.3.4 né la parte 2.3.4.5 devono tradursi in una corrispondenza. Alcune delle preoccupazioni possono essere gestite con questa espressione:

grep -E '(^|[^[:alnum:]+)(([0-1]?[0-9]{1,2}|2[0-4][0-9]|25[0-5])\.){3}([0-1]?[0-9]{1,2}|2[0-4][0-9]|25[0-5])([^[:alnum:]]|$)' 

La parte sfortunata qui è il fatto che la parte regex che convalida un ottetto si ripete come è vero in molte soluzioni offerte. Sebbene ciò sia migliore che per le istanze del pattern, la ripetizione può essere eliminata del tutto se sono supportate subroutine nel regex in uso. L'esempio seguente abilita tali funzioni con l'opzione -P di grep e sfrutta anche la funzionalità lookahead e lookbehind. (Il nome della funzione che ho selezionato è 'o' per ottetto. Avrei potuto usare 'ottetto' come nome ma volevo essere conciso.)

grep -P '(?<![\d\w\.])(?<o>([0-1]?[0-9]{1,2}|2[0-4][0-9]|25[0-5]))(\.\g<o>){3}(?![\d\w\.])'

La gestione del punto potrebbe effettivamente creare falsi negativi se gli indirizzi IP si trovano in un file con testo sotto forma di frasi poiché il punto potrebbe seguire senza che fosse parte della notazione punteggiata. Una variante di quanto sopra risolverebbe questo:

grep -P '(?<![\d\w\.])(?<x>([0-1]?[0-9]{1,2}|2[0-4][0-9]|25[0-5]))(\.\g<x>){3}(?!([\d\w]|\.\d))'
>>> my_hostname = "testhostn.ame"
>>> print bool(re.match("^(([a-zA-Z]|[a-zA-Z][a-zA-Z0-9\-]*[a-zA-Z0-9])\.)*([A-Za-z]|[A-Za-z][A-Za-z0-9\-]*[A-Za-z0-9])$", my_hostname))
True
>>> my_hostname = "testhostn....ame"
>>> print bool(re.match("^(([a-zA-Z]|[a-zA-Z][a-zA-Z0-9\-]*[a-zA-Z0-9])\.)*([A-Za-z]|[A-Za-z][A-Za-z0-9\-]*[A-Za-z0-9])$", my_hostname))
False
>>> my_hostname = "testhostn.A.ame"
>>> print bool(re.match("^(([a-zA-Z]|[a-zA-Z][a-zA-Z0-9\-]*[a-zA-Z0-9])\.)*([A-Za-z]|[A-Za-z][A-Za-z0-9\-]*[A-Za-z0-9])$", my_hostname))
True

Il nuovo framework di rete ha inizializzatori disponibili per struct IPv4Address e struct IPv6Address che gestiscono molto facilmente la parte dell'indirizzo IP. Fare questo in IPv6 con un regex è difficile con tutte le regole di accorciamento.

Sfortunatamente non ho una risposta elegante per il nome host.

Si noti che il framework di rete è recente, quindi potrebbe costringerti a compilare per le versioni recenti del sistema operativo.

import Network
let tests = ["192.168.4.4","fkjhwojfw","192.168.4.4.4","2620:3","2620::33"]

for test in tests {
    if let _ = IPv4Address(test) {
        debugPrint("\(test) is valid ipv4 address")
    } else if let _ = IPv6Address(test) {
        debugPrint("\(test) is valid ipv6 address")
    } else {
        debugPrint("\(test) is not a valid IP address")
    }
}

output:
"192.168.4.4 is valid ipv4 address"
"fkjhwojfw is not a valid IP address"
"192.168.4.4.4 is not a valid IP address"
"2620:3 is not a valid IP address"
"2620::33 is valid ipv6 address"

che ne dici di questo?

([0-9]{1,3}\.){3}[0-9]{1,3}

su php: filter_var(gethostbyname($dns), FILTER_VALIDATE_IP) == true ? 'ip' : 'not ip'

Verifica dei nomi host come ... mywebsite.co.in, thangaraj.name, 18thangaraj.in, thangaraj106.in ecc.,

[a-z\d+].*?\\.\w{2,4}$

Ho pensato a questo semplice schema di corrispondenza regex per la corrispondenza dell'indirizzo IP \ D + [.] \ D + [.] \ D + [.] \ D +

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top