Получите конкретный субдомен от URL-адреса в foo.bar.car.com
Учитывая URL-адрес следующим образом:
foo.bar.car.com.au
Мне нужно извлечь foo.bar
.
Я наткнулся на следующий код:
private static string GetSubDomain(Uri url)
{
if (url.HostNameType == UriHostNameType.Dns)
{
string host = url.Host;
if (host.Split('.').Length > 2)
{
int lastIndex = host.LastIndexOf(".");
int index = host.LastIndexOf(".", lastIndex - 1);
return host.Substring(0, index);
}
}
return null;
}
Мне это нравится foo.bar.car
. Я хочу foo.bar. Должен ли я просто использовать split и принимать 0 и 1?
Но тогда существует возможность wwww.
Есть ли простой способ для этого?
Ответы
Ответ 1
Учитывая ваше требование (вы хотите, чтобы 1-й два уровня, не включая "www." ), я подошел бы к нему примерно так:
private static string GetSubDomain(Uri url)
{
if (url.HostNameType == UriHostNameType.Dns)
{
string host = url.Host;
var nodes = host.Split('.');
int startNode = 0;
if(nodes[0] == "www") startNode = 1;
return string.Format("{0}.{1}", nodes[startNode], nodes[startNode + 1]);
}
return null;
}
Ответ 2
Вы можете использовать следующий пакет nuget Nager.PublicSuffix. Он использует PUBLIC SUFFIX LIST
от Mozilla для разделения домена.
PM> Install-Package Nager.PublicSuffix
пример
var domainParser = new DomainParser();
var data = await domainParser.LoadDataAsync();
var tldRules = domainParser.ParseRules(data);
domainParser.AddRules(tldRules);
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";
Ответ 3
Я столкнулся с аналогичной проблемой и, основываясь на предыдущих ответах, написал этот метод расширения. Самое главное, что он принимает параметр, определяющий "корневой" домен, т.е. Какой бы потребитель этого метода не считал корнем. В случае OP вызов будет
Uri uri = "foo.bar.car.com.au";
uri.DnsSafeHost.GetSubdomain("car.com.au"); // returns foo.bar
uri.DnsSafeHost.GetSubdomain(); // returns foo.bar.car
Здесь метод расширения:
/// <summary>Gets the subdomain portion of a url, given a known "root" domain</summary>
public static string GetSubdomain(this string url, string domain = null)
{
var subdomain = url;
if(subdomain != null)
{
if(domain == null)
{
// Since we were not provided with a known domain, assume that second-to-last period divides the subdomain from the domain.
var nodes = url.Split('.');
var lastNodeIndex = nodes.Length - 1;
if(lastNodeIndex > 0)
domain = nodes[lastNodeIndex-1] + "." + nodes[lastNodeIndex];
}
// Verify that what we think is the domain is truly the ending of the hostname... otherwise we're hooped.
if (!subdomain.EndsWith(domain))
throw new ArgumentException("Site was not loaded from the expected domain");
// Quash the domain portion, which should leave us with the subdomain and a trailing dot IF there is a subdomain.
subdomain = subdomain.Replace(domain, "");
// Check if we have anything left. If we don't, there was no subdomain, the request was directly to the root domain:
if (string.IsNullOrWhiteSpace(subdomain))
return null;
// Quash any trailing periods
subdomain = subdomain.TrimEnd(new[] {'.'});
}
return subdomain;
}
Ответ 4
ОК, сначала. Вы конкретно смотрите в "com.au", или это общие имена доменов в Интернете? Потому что, если это последнее, просто нет автоматического способа определить, какая часть домена является "сайтом" или "зоной" или что-то еще, и сколько это отдельный "хост" или другая запись в этой зоне.
Если вам нужно понять это из произвольного имени домена, вам нужно будет захватить список TLD из проекта Mozilla Public Suffix (http://publicsuffix.org) и используйте их алгоритм для поиска TLD в вашем доменном имени. Тогда вы можете предположить, что часть, которую вы хотите, заканчивается последней меткой непосредственно перед TLD.
Ответ 5
private static string GetSubDomain(Uri url)
{
if (url.HostNameType == UriHostNameType.Dns)
{
string host = url.Host;
String[] subDomains = host.Split('.');
return subDomains[0] + "." + subDomains[1];
}
return null;
}
Ответ 6
Я бы рекомендовал использовать регулярное выражение. Следующий фрагмент кода должен извлекать то, что вы ищете...
string input = "foo.bar.car.com.au";
var match = Regex.Match(input, @"^\w*\.\w*\.\w*");
var output = match.Value;
Ответ 7
В дополнение к пакету NuGet Nager.PubilcSuffix, указанному в этом ответе, есть также пакет NuGet Louw.PublicSuffix, который согласно Страница проекта GitHub - это .Net Core Library, которая анализирует Public Suffix и основана на Проект Nager.PublicSuffix со следующими изменениями:
- Портировано в .NET Core Library.
- Исправлена библиотека, чтобы она проходила ВСЕ всесторонние тесты.
- Реализованные классы для разделения функциональности на более мелкие сфокусированные классы.
- Сделал классы неизменными. Таким образом,
DomainParser
может использоваться как одноэлементный и является потокобезопасным.
- Добавлены
WebTldRuleProvider
и FileTldRuleProvider
.
- Добавлена возможность знать, является ли правило правилом ICANN или частного домена.
- Использовать модель асинхронного программирования
На странице также указано, что многие из вышеперечисленных изменений были возвращены в оригинальный проект Nager.PublicSuffix.