5

apache RewriteMap MapSource自定义规则使用手记

 4 years ago
source link: https://www.cnxct.com/apache-rewritemap-%e4%bd%bf%e7%94%a8%e6%89%8b%e8%ae%b0/
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.
neoserver,ios ssh client

apache RewriteMap MapSource自定义规则使用手记

10.1期间,一位朋友问我一个apache的 Rewrite规则中一个高级语法RewriteMap的用法问题。其想要实现的是这个功能,有个多用户的blog,用户访问的时候,是用三级域名访问的。比如http://cfc4n1.blog.cnxct.com,http://cfc4n2.blog.cnxct.com这种三级域名。在服务器上,是对三级域名做泛解析。每个三级域名都生成了一个静态的html主页文件。由于用户数量较多,linux ext硬盘格式上同一目录文件太多,检索文件的速度会有折扣,遂将文件打散到不同的目录下。打散方式是以用户名【三级域名中的cfc4n1,cfc4n2等】的MD5值的每隔两位作为一个目录。MD5的默认长度是32位,每隔两位分一次目录的话,那就有16级目录。每级目录的目录名是2个字符,每个字符的有16种可能【0-9a-f】,那么每级目录的目录数为256个目录,16级的话就有4096个目录。每个目录存1000个文件的话,可以存放4096000个文件,这样做,即可以把文件均匀打散到各个小目录中,同时,每个目录下的文件数又不是很多。当用户访问的时候,取目录里的用户名,计算MD5hash,做字符分割,重写到对应的目录下的文件中,如果文件不存在,则重写到生成这个文件的动态页面中。

到apache手册里找了下RewriteMap的用法

RewriteMap MapName MapType:MapSource

遂顺手在.htaccess里这么写了

RewriteMap cfc prg:/var/www/1.php
RewriteRule ^([a-f0-9-]+)\.blog\.cnxct\.com ${cfc:$1} [L,PT]

然后访问一个三级域名试试。结果提示500 http 错误。到apache日志里看到如下

/var/www/.htaccess: RewriteMap not allowed here

搜了半天,不知道是什么错误,只好再次看手册,这时候,才发现rewritemap的作用域却是server config, virtual host,真汗了一下。自己没认真看手册。
改到virtual host里之后,重启apache,结果,还是http 500。再到错误日志里查个究竟。里面记录的确实(13)Permission denied: mod_rewrite: could not start RewriteMap program /var/www/1.php。呃,权限,权限。。赶紧chmod了一下。再次启动,却提示404。。。 /0a/c1/…./…html那种MD5字符串切割之后的文件找不到。但目录里确实是存在的啊。又到日志里查看,原来却是/0a/c1/…../…html\r 文件无法找到了。为什么地址后面多个\r呢?打开MapSource的脚本文件,才看到里面PHP操作流的结束字符里是“\r\n”了,去掉\r 才可以。

总结一下使用APACHE URL REwrite的RewriteMap方法要注意以下几点:

  • 作用域-server config, virtual host,其他配置里无效。
  • 自定义规则MapSource中流的结束符要跟操作系统符合,linux的要用“\n”,同时,切记在win平台编辑脚本传到linux上的时候,文件换行符要用linux格式的,不然,同样会出现问题。
  • 要给apache赋予对脚本的读权限。
  • apache会在启动的时候,将自定义规则的脚本读取到内存中,之后,再次修改脚本时,不会立刻生效,需要重启 apache
  • apache 的error.log中会记录[warn] mod_rewrite: Running external rewrite maps without defining a RewriteLock is DANGEROUS!这样的错误日志,在apache2.conf【我的系统是ubuntu,其他linux在httpd.conf中】中添加RewriteLock /etc/apache2/script/cfc.lock来指定RewriteLock的文件位置。记得给apache对script目录下有读写权限。

自定义脚本的代码格式如下:

<?php
while($in = trim(fgets(STDIN)))
fputs(STDOUT, getfile($in)."\n");
function getfile($str)
{
//函数判断文件是否存在等逻辑
}

莿鸟栖草堂 由 CFC4N 创作,采用 知识共享 署名-非商业性使用-相同方式共享(3.0未本地化版本)许可协议进行许可。基于http://www.cnxct.com上的作品创作。转载请注明转自:apache RewriteMap MapSource自定义规则使用手记

No related posts.


About Joyk


Aggregate valuable and interesting links.
Joyk means Joy of geeK