it-swarm.com.de

Rufen Sie den Domainnamen von der angegebenen URL ab

Angesichts einer URL möchte ich den Domänennamen extrahieren (er sollte keinen "www" -Teil enthalten). URL kann http/https enthalten. Hier ist der Java-Code, den ich geschrieben habe. Obwohl es gut zu funktionieren scheint, gibt es einen besseren Ansatz oder gibt es einige Edge-Fälle, die scheitern könnten.

public static String getDomainName(String url) throws MalformedURLException{
    if(!url.startsWith("http") && !url.startsWith("https")){
         url = "http://" + url;
    }        
    URL netUrl = new URL(url);
    String Host = netUrl.getHost();
    if(Host.startsWith("www")){
        Host = Host.substring("www".length()+1);
    }
    return Host;
}

Eingabe: http://google.com/blah

Ausgabe: google.com

102
RandomQuestion

Wenn Sie eine URL analysieren möchten, verwenden Sie Java.net.URI . Java.net.URL hat eine Reihe von Problemen - seine equals-Methode führt eine DNS-Suche durch, was bedeutet, dass der Code, der sie verwendet, anfällig für Denial-of-Service-Angriffe sein kann, wenn er mit nicht vertrauenswürdigen Eingaben verwendet wird.

"Mr. Gosling - warum haben Sie URL gleich saugen lassen?" erklärt ein solches Problem. Gewöhnen Sie sich einfach an, stattdessen Java.net.URI zu verwenden.

public static String getDomainName(String url) throws URISyntaxException {
    URI uri = new URI(url);
    String domain = uri.getHost();
    return domain.startsWith("www.") ? domain.substring(4) : domain;
}

soll tun was du willst.


Obwohl es gut zu funktionieren scheint, gibt es einen besseren Ansatz oder gibt es einige Edge-Fälle, die scheitern könnten.

Ihr Code, wie geschrieben, schlägt für die gültigen URLs fehl:

  • httpfoo/bar - relative URL mit einer Pfadkomponente, die mit http beginnt.
  • HTTP://example.com/ - Protokoll unterscheidet nicht zwischen Groß- und Kleinschreibung.
  • //example.com/ - Protokollrelative URL mit einem Host
  • www/foo - eine relative URL mit einer Pfadkomponente, die mit www beginnt
  • wwwexample.com - Domänenname, der nicht mit www. beginnt, sondern mit www beginnt.

Hierarchische URLs haben eine komplexe Grammatik. Wenn Sie versuchen, Ihren eigenen Parser zu rollen, ohne RFC 3986 sorgfältig zu lesen, werden Sie es wahrscheinlich falsch verstehen. Verwenden Sie einfach diejenige, die in die Kernbibliotheken integriert ist.

Wenn Sie wirklich mit unordentlichen Eingaben umgehen müssen, die Java.net.URI ablehnen, siehe RFC 3986 Anhang B:

Anhang B. Analysieren einer URI-Referenz mit einem regulären Ausdruck

Da der "first-match-wins" -Algorithmus mit dem "gierigen" .__ identisch ist. Disambiguierungsmethode, die von regulären POSIX-Ausdrücken verwendet wird, ist natürlich und alltäglich, um einen regulären Ausdruck für die Analyse des mögliche fünf Komponenten einer URI-Referenz.

Die folgende Zeile ist der reguläre Ausdruck für die Aufgliederung von a wohlgeformte URI-Referenz in ihre Komponenten.

  ^(([^:/?#]+):)?(//([^/?#]*))?([^?#]*)(\?([^#]*))?(#(.*))?
   12            3  4          5       6  7        8 9

Die Zahlen in der zweiten Zeile dienen nur zur besseren Lesbarkeit; Sie geben die Bezugspunkte für jeden Unterausdruck an (d. h. jede gepaarte Klammer).

238
Mike Samuel
import Java.net.*;
import Java.io.*;

public class ParseURL {
  public static void main(String[] args) throws Exception {

    URL aURL = new URL("http://example.com:80/docs/books/tutorial"
                       + "/index.html?name=networking#DOWNLOADING");

    System.out.println("protocol = " + aURL.getProtocol()); //http
    System.out.println("authority = " + aURL.getAuthority()); //example.com:80
    System.out.println("Host = " + aURL.getHost()); //example.com
    System.out.println("port = " + aURL.getPort()); //80
    System.out.println("path = " + aURL.getPath()); //  /docs/books/tutorial/index.html
    System.out.println("query = " + aURL.getQuery()); //name=networking
    System.out.println("filename = " + aURL.getFile()); ///docs/books/tutorial/index.html?name=networking
    System.out.println("ref = " + aURL.getRef()); //DOWNLOADING
  }
}

Weiterlesen

63
Michael Tarimo

Hier ist eine kurze und einfache Zeile, die InternetDomainName.topPrivateDomain() in Guava verwendet: InternetDomainName.from(new URL(url).getHost()).topPrivateDomain().toString()

Bei http://www.google.com/blah erhalten Sie google.com. Bei Angabe von http://www.google.co.mx erhalten Sie google.co.mx.

Da Sa Qada in eine weitere Antwort zu diesem Beitrag kommentierte , wurde diese Frage zuvor gestellt: Extrahieren Sie den Hauptdomänennamen aus einer angegebenen URL . Die beste Antwort auf diese Frage ist von Satya , die Guavas InternetDomainName.topPrivateDomain () vorschlägt.

public boolean isTopPrivateDomain ()

Gibt an, ob dieser Domänenname genau aus einem .__ besteht. Subdomain-Komponente gefolgt von einem öffentlichen Suffix. Zum Beispiel wird .__ zurückgegeben. trifft für google.com und foo.co.uk zu, aber nicht für www.google.com oder co.uk. 

Warnung: Ein wahres Ergebnis dieser Methode bedeutet nicht, dass die Domäne ist auf der höchsten Ebene, die als Host angesprochen werden kann, ebenso viele Öffentliche Suffixe sind auch adressierbare Hosts. Zum Beispiel die Domäne bar.uk.com hat ein öffentliches Suffix von uk.com, also würde es von .__ zurückkehren. diese Methode. Aber uk.com ist selbst ein ansprechbarer Gastgeber.

Diese Methode kann verwendet werden, um festzustellen, ob eine Domäne wahrscheinlich die .__ ist. höchste Stufe, für die Cookies gesetzt werden können, auch wenn dies von __ abhängig ist. auf die Implementierung von Cookie-Steuerelementen einzelner Browser. Siehe RFC 2109 für Einzelheiten.

Wenn Sie das mit URL.getHost() zusammenstellen, das der ursprüngliche Beitrag bereits enthält, erhalten Sie: 

import com.google.common.net.InternetDomainName;

import Java.net.URL;

public class DomainNameMain {

  public static void main(final String... args) throws Exception {
    final String urlString = "http://www.google.com/blah";
    final URL url = new URL(urlString);
    final String Host = url.getHost();
    final InternetDomainName name = InternetDomainName.from(Host).topPrivateDomain();
    System.out.println(urlString);
    System.out.println(Host);
    System.out.println(name);
  }
}
8
Kirby

Ich habe eine Methode geschrieben (siehe unten), die den Domänennamen einer URL extrahiert und die einfache Zeichenfolge verwendet. Was es tatsächlich tut, ist das Bit zwischen dem ersten "://" (oder dem Index 0, wenn kein "://" enthalten ist) und dem ersten nachfolgenden "/" (oder dem Index String.length(), wenn es keinen nachfolgenden "/" gibt) zu extrahieren. Das verbleibende "www(_)*."-Bit wird abgehackt. Ich bin mir sicher, dass es Fälle geben wird, in denen das nicht gut genug ist, aber in den meisten Fällen sollte es gut genug sein!

Der Beitrag von Mike Samuel oben sagt, dass die Java.net.URI-Klasse dies tun könnte (und wurde der Java.net.URL-Klasse vorgezogen), aber ich hatte Probleme mit der URI-Klasse. Insbesondere gibt URI.getHost() einen Nullwert an, wenn die URL das Schema nicht enthält, d. H. Das "http(s)"-Bit.

/**
 * Extracts the domain name from {@code url}
 * by means of String manipulation
 * rather than using the {@link URI} or {@link URL} class.
 *
 * @param url is non-null.
 * @return the domain name within {@code url}.
 */
public String getUrlDomainName(String url) {
  String domainName = new String(url);

  int index = domainName.indexOf("://");

  if (index != -1) {
    // keep everything after the "://"
    domainName = domainName.substring(index + 3);
  }

  index = domainName.indexOf('/');

  if (index != -1) {
    // keep everything before the '/'
    domainName = domainName.substring(0, index);
  }

  // check for and remove a preceding 'www'
  // followed by any sequence of characters (non-greedy)
  // followed by a '.'
  // from the beginning of the string
  domainName = domainName.replaceFirst("^www.*?\\.", "");

  return domainName;
}
3
Adil Hussain

Ich habe nach der Erstellung des URI-Objekts eine kleine Behandlung vorgenommen

 if (url.startsWith("http:/")) {
        if (!url.contains("http://")) {
            url = url.replaceAll("http:/", "http://");
        }
    } else {
        url = "http://" + url;
    }
    URI uri = new URI(url);
    String domain = uri.getHost();
    return domain.startsWith("www.") ? domain.substring(4) : domain;
2
migueloop

Es gibt eine ähnliche Frage Extrahieren Sie den Hauptdomänennamen aus einer angegebenen URL . Wenn Sie sich diese answer ansehen, werden Sie feststellen, dass dies sehr einfach ist. Sie müssen nur Java.net.URL und String verwenden - Split

1
Sa Qada
private static final String hostExtractorRegexString = "(?:https?://)?(?:www\\.)?(.+\\.)(com|au\\.uk|co\\.in|be|in|uk|org\\.in|org|net|edu|gov|mil)";
private static final Pattern hostExtractorRegexPattern = Pattern.compile(hostExtractorRegexString);

public static String getDomainName(String url){
    if (url == null) return null;
    url = url.trim();
    Matcher m = hostExtractorRegexPattern.matcher(url);
    if(m.find() && m.groupCount() == 2) {
        return m.group(1) + m.group(2);
    }
    else {
        return null;
    }
}

Erläuterung: Der Regex hat 4 Gruppen. Die ersten beiden sind nicht übereinstimmende Gruppen und die nächsten zwei sind übereinstimmende Gruppen.

Die erste nicht übereinstimmende Gruppe ist "http" oder "https" oder "".

Die zweite nicht übereinstimmende Gruppe ist "www." oder ""

Die zweite übereinstimmende Gruppe ist die Top-Level-Domain

Die erste übereinstimmende Gruppe steht nach den nicht übereinstimmenden Gruppen und vor der Domäne der obersten Ebene

Die Verkettung der zwei übereinstimmenden Gruppen gibt uns den Domänen-/Hostnamen.

PS: Beachten Sie, dass Sie dem regulären Ausdruck eine beliebige Anzahl unterstützter Domänen hinzufügen können.

1
cegprakash

versuchen Sie es hier mit: Java.net.URL;
JOptionPane.showMessageDialog (null, getDomainName (neue URL (" https://en.wikipedia.org/wiki/List_of_Internet_top-level_domains ")));

public String getDomainName(URL url){
String strDomain;
String[] strhost = url.getHost().split(Pattern.quote("."));
String[] strTLD = {"com","org","net","int","edu","gov","mil","arpa"};

if(Arrays.asList(strTLD).indexOf(strhost[strhost.length-1])>=0)
    strDomain = strhost[strhost.length-2]+"."+strhost[strhost.length-1];
else if(strhost.length>2)
    strDomain = strhost[strhost.length-3]+"."+strhost[strhost.length-2]+"."+strhost[strhost.length-1];
else
    strDomain = strhost[strhost.length-2]+"."+strhost[strhost.length-1];
return strDomain;}
1
Eko Didik

Wenn die Eingabe-URL eine Benutzereingabe ist. Diese Methode gibt den am besten geeigneten Hostnamen an. Wenn nicht gefunden, wird die Eingabe-URL zurückgegeben.

private String getHostName(String urlInput) {
        urlInput = urlInput.toLowerCase();
        String hostName=urlInput;
        if(!urlInput.equals("")){
            if(urlInput.startsWith("http") || urlInput.startsWith("https")){
                try{
                    URL netUrl = new URL(urlInput);
                    String Host= netUrl.getHost();
                    if(Host.startsWith("www")){
                        hostName = Host.substring("www".length()+1);
                    }else{
                        hostName=Host;
                    }
                }catch (MalformedURLException e){
                    hostName=urlInput;
                }
            }else if(urlInput.startsWith("www")){
                hostName=urlInput.substring("www".length()+1);
            }
            return  hostName;
        }else{
            return  "";
        }
    }
0
spaceMonkey

Alle oben genannten sind gut. Dieser scheint mir wirklich einfach und leicht zu verstehen. Entschuldigen Sie die Anführungszeichen. Ich habe es für Groovy in einer Klasse namens DataCenter geschrieben.

static String extractDomainName(String url) {
    int start = url.indexOf('://')
    if (start < 0) {
        start = 0
    } else {
        start += 3
    }
    int end = url.indexOf('/', start)
    if (end < 0) {
        end = url.length()
    }
    String domainName = url.substring(start, end)

    int port = domainName.indexOf(':')
    if (port >= 0) {
        domainName = domainName.substring(0, port)
    }
    domainName
}

Und hier sind einige junit4-Tests:

@Test
void shouldFindDomainName() {
    assert DataCenter.extractDomainName('http://example.com/path/') == 'example.com'
    assert DataCenter.extractDomainName('http://subpart.example.com/path/') == 'subpart.example.com'
    assert DataCenter.extractDomainName('http://example.com') == 'example.com'
    assert DataCenter.extractDomainName('http://example.com:18445/path/') == 'example.com'
    assert DataCenter.extractDomainName('example.com/path/') == 'example.com'
    assert DataCenter.extractDomainName('example.com') == 'example.com'
}
0
Lee Meador

In meinem Fall brauchte ich nur die Hauptdomain und nicht die Subdomain (kein "www" oder was auch immer die Subdomain ist):

public static String getUrlDomain(String url) throws URISyntaxException {
    URI uri = new URI(url);
    String domain = uri.getHost();
    String[] domainArray = domain.split("\\.");
    if (domainArray.length == 1) {
        return domainArray[0];
    }
    else {
        return domainArray[domainArray.length - 2] + "." + domainArray[domainArray.length - 1];
    }
}

Bei dieser Methode hat die URL " https://rest.webtoapp.io/llSlider?lg=de&t=8 " für die Domäne "webtoapp.io".

0
Laurent