当前位置

PHP生成的网站地图sitemap.xml改为gz压缩格式文件

James Qi 在 2021年6月18日 - 15:11 提交

好些年前,我们的网站就用PHP程序来动态生成robots.txtsitemap.xml,其中网站地图用php来动态生成而没有保存成文件,因为有些站网址太多,怕sitemap文件过多、过大而占用磁盘空间。虽然动态生成会对数据量很大的数据库有一定影响,但经过一些优化还是可以承受的。但URL很多的网站还存在另外一个问题,就是sitemap被大量爬取,占用带宽,这个问题因为不是很普遍、很迫切,所以就一直放着没有动,只是把有一个站的php程序中添加了延时来让爬虫慢一点。

前几天在为新改版的邮编库添加网站地图的时候,用MediaWiki自带的maintenance/generateSitemap.php生成地图文件,发现默认compress参数是yes,生成的网站地图都是.xml.gz的文件,除了sitemap.xml这个index页以外,观察了一下,正常的单个xml文件是10M字节,压缩后的xml.gz文件大约是200多K字节,只有以前的几十分之一。对于数百万URL,以前近200个xml文件需要上G的空间,现在只要几十M,不仅空间占用少得多,爬虫下载也会快很多倍。

于是想到把以前php生成的sitemap.xml也改为.xml.gz格式,修改以前的sitemap.php中的部分代码

......

# 准备输出内容

$output = '';
if ($query_string == NULL) { //index file or single file, example: https://cidian.18dao.net/sitemap_cidian.xml or https://cidian.18dao.net/sitemap_bihua.xml

	$result_count = mysqli_query($link,$sql_count);
	while ($row = $result_count->fetch_array()) {
		$num_rows = $row[0];
	}
	$pages = ceil($num_rows / $url_per_page);
	if ($pages == 1) {//single file, example: https://cidian.18dao.net/sitemap_bihua.xml
		$sql_page = "$sql LIMIT 10000 OFFSET 0";
		$result_page = mysqli_query($link,$sql_page);
		$output .= map_start();
		while ($row = $result_page->fetch_array()) {
			$value = $row[0];
			if ($value != '') {
				if (isset($row[1])) {
					$value1 = $row[1];
				}
				$value_urlencode = urlencode($value);
				if (strpos($value,'&') == FALSE) {
					$output .= "";
					if (isset($row[1]) && !is_date_time($value1)) {
						$output .= "https://$http_host/$path/$value_urlencode/".urlencode($row[1])."";
					} else {
						$output .= "https://$http_host/$path/$value_urlencode";
					}
					if (isset($row[1]) && is_date_time($value1)) {
						$output .= "".str_replace(' ','T',$value1)."Z";
					} else {
						$output .= "$lastmod";
					}
					$output .= "$changefreq";
					$output .= "$priority";
					$output .= "\n";
				}
			}
		}
		$output .= map_end();
	} else {//index file, example: https://cidian.18dao.net/sitemap_cidian.xml
		$output .= index_start();
		if (is_date_time($lastmod)) {
			$lastmod_index = $lastmod;
		} else {
			$lastmod_index = $lastmod_default;
		}
		for ($i=1; $i<=$pages; $i++) {
			$output .= "\t\n";
			//2021-6-16//$output .= "\t\thttps://$http_host$request_uri?page=$i\n";//2021-6-16
			$output .= "\t\thttps://$http_host$request_uri.gz?page=$i\n";//2021-6-16
			$output .= "\t\t$lastmod_index\n";
			$output .= "\t\n";
		}
		$output .= index_end();
	}
	header("Content-Type: application/xml");
	print $output;
} else {//paged file, example: https://cidian.18dao.net/sitemap_cidian.xml?page=2
	$page = substr($query_string, 5); //example: 2
	$offset = ($page - 1) * $url_per_page;
	$limit = $url_per_page;
	//$sql = "SELECT DISTINCT $field FROM $table WHERE not $field like '%gif%' and not $field like '%jpg%' and not $field = '' LIMIT $limit OFFSET $offset";
	//$sql = "SELECT DISTINCT $field FROM $table WHERE not $field = '' LIMIT $limit OFFSET $offset";
	$sql_pages = "$sql LIMIT $limit OFFSET $offset";//jamesqi 2018-5-6
	$result_pages = mysqli_query($link,$sql_pages);
	$output .= map_start();
	while ($row = $result_pages->fetch_array()) {
		$value = $row[0];
		if ($value != '') {
			if (isset($row[1])) {
				$value1 = $row[1];
			}
			$value_urlencode = urlencode($value);
			if (strpos($value,'&') == FALSE) {
				$output .= "";
				if (isset($row[1]) && !is_date_time($value1)) {
					$output .= "https://$http_host/$path/$value_urlencode/".urlencode($row[1])."";
				} else {
					$output .= "https://$http_host/$path/$value_urlencode";
				}
				if (isset($row[1]) && is_date_time($value1)) {
					$output .= "".str_replace(' ','T',$value1)."Z";
				} else {
					$output .= "$lastmod";
				}
				$output .= "$changefreq";
				$output .= "$priority";
				$output .= "\n";
			}
		}
	}
	$output .= map_end();
	header('content-type: application/x-gzip');
	$output = gzencode($output, 9);//2021-6-16
	print $output;
}

......

上面代码中红色部分是这次修改或者新增的。

这样对于索引型页面和只有一页长度的网站地图页面是不采用gz压缩的,只对索引页指向的多个页面采用gz压缩。

一个索引页的例子,里面指向的多个网站地图页都是.xml.gz的。

添加新评论

Plain text

  • 不允许使用HTML标签。
  • 自动将网址与电子邮件地址转变为链接。
  • 自动断行和分段。