我需要构建一个函数来解析URL中的域名。从PHP解析域名在PHP中
所以,用
http://google.com/dhasjkdas/sadsdds/sdda/sdads.html
或
http://www.google.com/dhasjkdas/sadsdds/sdda/sdads.html
它应该返回google.com
与
http://google.co.uk/dhasjkdas/sadsdds/sdda/sdads.html
它应该返回google.co.uk
。
我需要构建一个函数来解析URL中的域名。从PHP解析域名在PHP中
所以,用
http://google.com/dhasjkdas/sadsdds/sdda/sdads.html
或
http://www.google.com/dhasjkdas/sadsdds/sdda/sdads.html
它应该返回google.com
与
http://google.co.uk/dhasjkdas/sadsdds/sdda/sdads.html
它应该返回google.co.uk
。
退房parse_url()
:
$url = 'http://google.com/dhasjkdas/sadsdds/sdda/sdads.html';
$parse = parse_url($url);
echo $parse['host']; // prints 'google.com'
parse_url
不处理实在太差了错位的网址非常好,但是是好的,如果你普遍预期体面的URL。
parse_url()不做的一件事是只返回域。如果您添加www.google.com或www.google.co.uk,它也会返回主机。对此有何建议? – 2008-12-30 00:40:49
@Crad,http://stackoverflow.com/questions/8272805/how-to-handle-mozillas-top-domain-name-list-with-php – ilhan 2011-11-25 21:22:22
`parse_url`不处理子域,但是Purl的确如下:https: //github.com/jwage/purl – Damien 2013-01-18 11:48:40
从http://us3.php.net/manual/en/function.parse-url.php#93983
一些奇怪的原因,parse_url 返回主机(例如:example.com)作为 当没有方案中 输入URL提供的路径。所以我写了一个快速 函数来获得真正的主机:
function getHost($Address) {
$parseUrl = parse_url(trim($Address));
return trim($parseUrl['host'] ? $parseUrl['host'] : array_shift(explode('/', $parseUrl['path'], 2)));
}
getHost("example.com"); // Gives example.com
getHost("http://example.com"); // Gives example.com
getHost("www.example.com"); // Gives www.example.com
getHost("http://example.com/xyz"); // Gives example.com
$domain = str_ireplace('www.', '', parse_url($url, PHP_URL_HOST));
这将返回google.com
两个http://google.com/ ...和... http://www.google.com/
这里是我所做的代码,100%只找到域名,因为它需要mozilla子域来解释。只有你必须检查的是你如何缓存该文件,所以你不要每次都查询mozilla。
由于一些奇怪的原因,像co.uk这样的域名不在列表中,所以你必须做一些黑客攻击并手动添加它们。它不是最干净的解决方案,但我希望它可以帮助某人。
//=====================================================
static function domain($url)
{
$slds = "";
$url = strtolower($url);
$address = 'http://mxr.mozilla.org/mozilla-central/source/netwerk/dns/effective_tld_names.dat?raw=1';
if(!$subtlds = @kohana::cache('subtlds', null, 60))
{
$content = file($address);
foreach($content as $num => $line)
{
$line = trim($line);
if($line == '') continue;
if(@substr($line[0], 0, 2) == '/') continue;
$line = @preg_replace("/[^a-zA-Z0-9\.]/", '', $line);
if($line == '') continue; //$line = '.'.$line;
if(@$line[0] == '.') $line = substr($line, 1);
if(!strstr($line, '.')) continue;
$subtlds[] = $line;
//echo "{$num}: '{$line}'"; echo "<br>";
}
$subtlds = array_merge(Array(
'co.uk', 'me.uk', 'net.uk', 'org.uk', 'sch.uk', 'ac.uk',
'gov.uk', 'nhs.uk', 'police.uk', 'mod.uk', 'asn.au', 'com.au',
'net.au', 'id.au', 'org.au', 'edu.au', 'gov.au', 'csiro.au',
),$subtlds);
$subtlds = array_unique($subtlds);
//echo var_dump($subtlds);
@kohana::cache('subtlds', $subtlds);
}
preg_match('/^(http:[\/]{2,})?([^\/]+)/i', $url, $matches);
//preg_match("/^(http:\/\/|https:\/\/|)[a-zA-Z-]([^\/]+)/i", $url, $matches);
$host = @$matches[2];
//echo var_dump($matches);
preg_match("/[^\.\/]+\.[^\.\/]+$/", $host, $matches);
foreach($subtlds as $sub)
{
if (preg_match("/{$sub}$/", $host, $xyz))
preg_match("/[^\.\/]+\.[^\.\/]+\.[^\.\/]+$/", $host, $matches);
}
return @$matches[0];
}
这是为了工作,100%似乎没有削减对我的代码,我没有打补丁的例子一点点,但发现这是没有帮助的代码,并与它的问题。所以我将它改为了几个函数(为了节省从mozilla始终询问的列表,并删除了cahce系统)。这已经通过一组1000个URL进行了测试,似乎工作。
function domain($url)
{
global $subtlds;
$slds = "";
$url = strtolower($url);
$host = parse_url('http://'.$url,PHP_URL_HOST);
preg_match("/[^\.\/]+\.[^\.\/]+$/", $host, $matches);
foreach($subtlds as $sub){
if (preg_match('/\.'.preg_quote($sub).'$/', $host, $xyz)){
preg_match("/[^\.\/]+\.[^\.\/]+\.[^\.\/]+$/", $host, $matches);
}
}
return @$matches[0];
}
function get_tlds(){
$address = 'http://mxr.mozilla.org/mozilla-central/source/netwerk/dns/effective_tld_names.dat?raw=1';
$content = file($address);
foreach($content as $num => $line){
$line = trim($line);
if($line == '') continue;
if(@substr($line[0], 0, 2) == '/') continue;
$line = @preg_replace("/[^a-zA-Z0-9\.]/", '', $line);
if($line == '') continue; //$line = '.'.$line;
if(@$line[0] == '.') $line = substr($line, 1);
if(!strstr($line, '.')) continue;
$subtlds[] = $line;
//echo "{$num}: '{$line}'"; echo "<br>";
}
$subtlds = array_merge(array(
'co.uk', 'me.uk', 'net.uk', 'org.uk', 'sch.uk', 'ac.uk',
'gov.uk', 'nhs.uk', 'police.uk', 'mod.uk', 'asn.au', 'com.au',
'net.au', 'id.au', 'org.au', 'edu.au', 'gov.au', 'csiro.au'
),$subtlds);
$subtlds = array_unique($subtlds);
return $subtlds;
}
然后使用它像
$subtlds = get_tlds();
echo domain('www.example.com') //outputs: exmaple.com
echo domain('www.example.uk.com') //outputs: exmaple.uk.com
echo domain('www.example.fr') //outputs: exmaple.fr
我知道我应该把这个变成一个类,但没有时间。
parse_url不适合我。它只返回了路径。切换到基本使用php5.3 +:
$url = str_replace('http://', '', strtolower($s->website));
if (strpos($url, '/')) $url = strstr($url, '/', true);
如果输入的URL不是全部垃圾,这通常会工作得很好。它删除子域。
$host = parse_url($Row->url, PHP_URL_HOST);
$parts = explode('.', $host);
$parts = array_reverse($parts);
$domain = $parts[1].'.'.$parts[0];
例
输入:http://www2.website.com:8080/some/file/structure?some=parameters
输出:website.com
这里我的基于上述答案检索器。
Curl
所以我们可以使用需要HTTP认证爬行类代码
class crawler
{
protected $_url;
protected $_depth;
protected $_host;
public function __construct($url, $depth = 5)
{
$this->_url = $url;
$this->_depth = $depth;
$parse = parse_url($url);
$this->_host = $parse['host'];
}
public function run()
{
$this->crawl_page($this->_url, $this->_depth = 5);
}
public function crawl_page($url, $depth = 5)
{
static $seen = array();
if (isset($seen[$url]) || $depth === 0) {
return;
}
$seen[$url] = true;
list($content, $httpcode) = $this->getContent($url);
$dom = new DOMDocument('1.0');
@$dom->loadHTML($content);
$this->processAnchors($dom, $url, $depth);
ob_end_flush();
echo "CODE::$httpcode, URL::$url <br>";
ob_start();
flush();
// echo "URL:", $url, PHP_EOL, "CONTENT:", PHP_EOL, $dom->saveHTML(), PHP_EOL, PHP_EOL;
}
public function processAnchors($dom, $url, $depth)
{
$anchors = $dom->getElementsByTagName('a');
foreach ($anchors as $element) {
$href = $element->getAttribute('href');
if (0 !== strpos($href, 'http')) {
$path = '/' . ltrim($href, '/');
if (extension_loaded('http')) {
$href = http_build_url($url, array('path' => $path));
} else {
$parts = parse_url($url);
$href = $parts['scheme'] . '://';
if (isset($parts['user']) && isset($parts['pass'])) {
$href .= $parts['user'] . ':' . $parts['pass'] . '@';
}
$href .= $parts['host'];
if (isset($parts['port'])) {
$href .= ':' . $parts['port'];
}
$href .= $path;
}
}
// Crawl only link that belongs to the start domain
if (strpos($href, $this->_host) !== false)
$this->crawl_page($href, $depth - 1);
}
}
public function getContent($url)
{
$handle = curl_init($url);
curl_setopt($handle, CURLOPT_RETURNTRANSFER, TRUE);
/* Get the HTML or whatever is linked in $url. */
$response = curl_exec($handle);
/* Check for 404 (file not found). */
$httpCode = curl_getinfo($handle, CURLINFO_HTTP_CODE);
if ($httpCode == 404) {
/* Handle 404 here. */
}
curl_close($handle);
return array($response, $httpCode);
}
}
// USAGE
$startURL = 'http://YOUR_START_ULR';
$depth = 2;
$crawler = new crawler($startURL, $depth);
$crawler->run();
您可以通过PHP_URL_HOST到parse_url功能作为第二个参数
$url = 'http://google.com/dhasjkdas/sadsdds/sdda/sdads.html';
$host = parse_url($url, PHP_URL_HOST);
print $host; // prints 'google.com'
我已经编辑为你:
function getHost($Address) {
$parseUrl = parse_url(trim($Address));
$host = trim($parseUrl['host'] ? $parseUrl['host'] : array_shift(explode('/', $parseUrl['path'], 2)));
$parts = explode('.', $host);
$num_parts = count($parts);
if ($parts[0] == "www") {
for ($i=1; $i < $num_parts; $i++) {
$h .= $parts[$i] . '.';
}
}else {
for ($i=0; $i < $num_parts; $i++) {
$h .= $parts[$i] . '.';
}
}
return substr($h,0,-1);
}
所有类型的网址(www.domain.ltd,sub1.subn.domain.ltd将导致:domain.ltd。
$domain = parse_url($url, PHP_URL_HOST);
echo implode('.', array_slice(explode('.', $domain), -2, 2))
function get_domain($url = SITE_URL)
{
preg_match("/[a-z0-9\-]{1,63}\.[a-z\.]{2,6}$/", parse_url($url, PHP_URL_HOST), $_domain_tld);
return $_domain_tld[0];
}
get_domain('http://www.cdl.gr'); //cdl.gr
get_domain('http://cdl.gr'); //cdl.gr
get_domain('http://www2.cdl.gr'); //cdl.gr
像下面只需使用...
<?php
echo $_SERVER['SERVER_NAME'];
?>
结合worldofjr和阿利克斯阿克塞尔成一个小的功能,将处理大多数使用情况的答案:
function get_url_hostname($url) {
$parse = parse_url($url);
return str_ireplace('www.', '', $parse['host']);
}
get_url_hostname('http://www.google.com/example/path/file.html'); // google.com
如果你想从字符串http://google.com/dhasjkdas/sadsdds/sdda/sdads.html
中提取主机,使用parse_url()是可以接受的解决方案。
但是,如果你想提取域或其部分,你需要使用Public Suffix List包。是的,你可以使用字符串函数arround parse_url(),但它有时会产生不正确的结果。
我建议TLDExtract域解析,这里是显示DIFF示例代码:
$extract = new LayerShifter\TLDExtract\Extract();
# For 'http://google.com/dhasjkdas/sadsdds/sdda/sdads.html'
$url = 'http://google.com/dhasjkdas/sadsdds/sdda/sdads.html';
parse_url($url, PHP_URL_HOST); // will return google.com
$result = $extract->parse($url);
$result->getFullHost(); // will return 'google.com'
$result->getRegistrableDomain(); // will return 'google.com'
$result->getSuffix(); // will return 'com'
# For 'http://search.google.com/dhasjkdas/sadsdds/sdda/sdads.html'
$url = 'http://search.google.com/dhasjkdas/sadsdds/sdda/sdads.html';
parse_url($url, PHP_URL_HOST); // will return 'search.google.com'
$result = $extract->parse($url);
$result->getFullHost(); // will return 'search.google.com'
$result->getRegistrableDomain(); // will return 'google.com'
我加入这个答案晚,因为这是弹出在谷歌大部分的答案...
您可以使用PHP来...
$url = "www.google.co.uk";
$host = parse_url($url, PHP_URL_HOST);
// $host == "www.google.co.uk"
抢主机但不是私人领域到主机指的是哪个。 (例www.google.co.uk
是主机,但google.co.uk
是私人领域)
抢私人领域,你必须需要知道公共后缀的列表中哪一个可以注册的私人领地。这个列表恰好由Mozilla在https://publicsuffix.org/
策划当下面的代码在公共后缀数组已经创建时工作。只需拨打
$domain = get_private_domain("www.google.co.uk");
与其余代码...
// find some way to parse the above list of public suffix
// then add them to a PHP array
$suffix = [... all valid public suffix ...];
function get_public_suffix($host) {
$parts = split("\.", $host);
while (count($parts) > 0) {
if (is_public_suffix(join(".", $parts)))
return join(".", $parts);
array_shift($parts);
}
return false;
}
function is_public_suffix($host) {
global $suffix;
return isset($suffix[$host]);
}
function get_private_domain($host) {
$public = get_public_suffix($host);
$public_parts = split("\.", $public);
$all_parts = split("\.", $host);
$private = [];
for ($x = 0; $x < count($public_parts); ++$x)
$private[] = array_pop($all_parts);
if (count($all_parts) > 0)
$private[] = array_pop($all_parts);
return join(".", array_reverse($private));
}
我发现,@ philfreo的解决方案(从php.net引用)是颇能获得良好的效果,但在某些情况下,显示php的“通知”和“严格标准”消息。这里是这个代码的固定版本。
function getHost($url) {
$parseUrl = parse_url(trim($url));
if(isset($parseUrl['host']))
{
$host = $parseUrl['host'];
}
else
{
$path = explode('/', $parseUrl['path']);
$host = $path[0];
}
return trim($host);
}
echo getHost("http://example.com/anything.html"); // example.com
echo getHost("http://www.example.net/directory/post.php"); // www.example.net
echo getHost("https://example.co.uk"); // example.co.uk
echo getHost("www.example.net"); // example.net
echo getHost("subdomain.example.net/anything"); // subdomain.example.net
echo getHost("example.net"); // example.net
-1:没有打扰看手册。 – 2012-01-11 10:25:10
看到这一个:http://stackoverflow.com/questions/288810/get-the-subdomain-from-a-url/14688913#14688913 – 2013-02-04 14:41:05
@LightnessRacesinOrbit这不仅仅是“看手册”。 PHP的`parse_url()`返回_host_,而不是_domain_。 – MrWhite 2016-04-25 14:45:00