Домен верхнего уровня из URL в C#

Я использую C# и ASP.NET за это.

мы получаем много "странных" запросов на наших серверах IIS 6.0, и я хочу регистрировать и каталогизировать их по домену.

например. мы получаем некоторые странные запросы, такие как эти:

http://www.poker.winner4ever.example.com/

http://www.hotgirls.example.com/

http://santaclaus.example.com/

http://m.example.com/

http://wap.example.com/

http://iphone.example.com/

последние три типа очевидны, но я хотел бы отсортировать их все в один, как "example.com" размещается на наших серверах. Остальное нет, извините : -)

поэтому я ищу некоторые хорошие идеи для того, как получить example.com сверху. Во-вторых, я хотел бы соответствовать m., wap., iphone и т. д. В группу, но это, вероятно, просто быстрый поиск в списке мобильных ярлыков.Я мог handcode этот список для начала.

но является ли regexp ответом здесь или чистая манипуляция строкой самым простым способом? Я думал о "разбиении" строки URL на "." и поиск элемента[0] и элемента[1]...

какие идеи?

8 ответов


мне нужно было то же самое, поэтому я написал класс, который вы можете скопировать и вставить в свое решение. Он использует жесткий кодированный строковый массив tld. http://pastebin.com/raw.php?i=VY3DCNhp

Console.WriteLine(GetDomain.GetDomainFromUrl("http://www.beta.microsoft.com/path/page.htm"));

выходы microsoft.com

и

Console.WriteLine(GetDomain.GetDomainFromUrl("http://www.beta.microsoft.co.uk/path/page.htm"));

выходы microsoft.co.uk


следующий код использует Uri класс для получения имени хоста, а затем получает хост второго уровня (examplecompany.com) от Uri.Host путем разделения имени хоста на периоды.

var uri = new Uri("http://www.poker.winner4ever.examplecompany.com/");
var splitHostName = uri.Host.Split('.');
if (splitHostName.Length >= 2)
{
    var secondLevelHostName = splitHostName[splitHostName.Length - 2] + "." +
                              splitHostName[splitHostName.Length - 1];
}

это невозможно без обновленной базы данных различных уровней домена.

считаем:

s1.moh.gov.cn
moh.gov.cn
s1.google.com
google.com

тогда на каком уровне вы хотите приобрести домен? Это полностью зависит от TLD, SLD, ccTLD... потому что ccTLD в подконтрольных странах, они могут определить особенный SLD что вам неизвестно.


могут быть некоторые примеры, когда это возвращает что-то другое, чем требуется, но коды стран являются единственными, которые являются 2 символами, и они могут или не могут иметь короткий второй уровень (2 или 3 символа) обычно используется. Поэтому это даст вам то, что вы хотите в большинстве случаев:

String GetRootDomain(String host)
    {
        String[] domains = host.Split('.');

        if (domains.Length >= 3)
        {
            int c = domains.Length;
            // handle international country code TLDs 
            // www.amazon.co.uk => amazon.co.uk
            if (domains[c - 1].Length < 3 && domains[c - 2].Length <= 3)
                return String.Join(".", domains, c - 3, 3);
            else
                return String.Join(".", domains, c - 2, 2);
        }
        else
            return host;
    }

использовать регулярное выражение:

^https?://([\w./]+[^.])?\.?(\w+\.(com)|(co.uk)|(com.au))$

Это будет соответствовать любому URL, заканчивающемуся TLD, в котором вы заинтересованы. Расширьте список на столько, сколько хотите. Кроме того, группы захвата будут содержать поддомен, имя хоста и TLD соответственно.


Я написал библиотека для использования в .NET 2+, чтобы помочь выбрать компоненты домена URL.

больше деталей на github но одно преимущество над предыдущими вариантами что оно может загрузить самые последние данные отhttp://publicsuffix.org автоматически (один раз в месяц), поэтому выход из библиотеки должен быть более или менее на одном уровне с выходом, используемым веб-браузерами для установления границ безопасности домена (т. е. довольно хорошо).

Это еще не идеально, но подходит для моих нужд и не должно занять много работы, чтобы приспособиться к другим случаям использования, поэтому, пожалуйста, вилка и отправить запрос тяги, если вы хотите.


вы можете использовать следующий nuget Nager.PublicSuffix пакета.

NuGet для

PM> Install-Package Nager.PublicSuffix

пример

var domainParser = new DomainParser(new WebTldRuleProvider());

var domainName = domainParser.Get("sub.test.co.uk");
//domainName.Domain = "test";
//domainName.Hostname = "sub.test.co.uk";
//domainName.RegistrableDomain = "test.co.uk";
//domainName.SubDomain = "sub";
//domainName.TLD = "co.uk";

uri.Host.ToLower().Replace("www.","").Substring(uri.Host.ToLower().Replace("www.","").IndexOf('.'))
  • returns".com " для

    Uri uri = new Uri("http://stackoverflow.com/questions/4643227/top-level-domain-from-url-in-c");

  • returns".co.jp " для Uri uri = new Uri("http://stackoverflow.co.jp");

  • returns".s1.МО.gov.cn " для Uri uri = new Uri("http://stackoverflow.s1.moh.gov.cn");

etc.