如何从请求 URI 中删除版本前缀并使用正确的文档根目录


How to remove version prefix from request URI and use correct document root?

我们需要支持几个主要和次要版本的Web服务,所以我们决定在URL中使用这样的版本:

http://service/# 上次部署的服务版本http://service/1/# 符号链接,指向上次部署的主要版本 1.xhttp://service/1.2/# 指向上次部署的次要版本 1.2.x 的符号链接

我们将所有标签存储在文件夹中,并制作指向正确版本的符号链接:

这里是 apache 的根目录:lrwxr-xr-x 1 xxxx xxxx 28五月23 15:21 1 ->/首页/站点/标签/20120523084844-HEADlrwxr-xr-x 1 xxxx xxxx 28 四月 27 15:21 1.1 ->/首页/站点/标签/20120427152123-HEADlrwxr-xr-x 1 xxxx xxxx 28五月23 08:48 1.2 ->/首页/站点/标签/20120523084844-HEADlrwxr-xr-x 1 xxxx xxxx 28五月24 16:12 2 ->/首页/网站/标签/20120524161232-HEAD(此处为上次部署版本的源代码).....

这里有一个问题,因为我们在PHP的REQUEST_URI中会有版本前缀,而Symfony路由器不会将其与模式匹配。我们如何才能删除该版本前缀,但仍使用特定目录作为文档根目录?

例如,当我们向http://service/1.2/some/handler/pattern发出请求时,将使用 1.2 目录中的代码,PHP 中的REQUEST_URI将是/some/handler/pattern

试试这个:

RewriteEngine On
RewriteBase /
RewriteCond $1 !^[0-9.]+/
RewriteRule ^(.*) /1.2/$1 [L]

唯一的想法是你一次只能测试版本,如果你想要一个不同的版本,必须更改htaccess。

我可以建议使用子域进行版本控制吗?

这是一个有趣的问题。

我不认为它只能用htaccess来完成,至少不能没有丑陋的黑客。REQUEST_URI始终保存原始请求,据我所知,无法对其进行编辑(如果我们尝试通过 E=REQUEST_URI="something" 将内容分配给变量REQUEST_URI,则将创建一个名为"REDIRECT_REQUEST_URI"的环境变量)。

我不熟悉Symfony,所以我不知道编辑处理路由的脚本有多容易。如果这很容易,你可以做一些类似的事情

RewriteRule ^[1-9.]/(.*)$ - [R,QSA,NC,E=HANDLER:$1]

然后在 PHP 中,您可以将处理程序复制到request_uri:

$_SERVER['REQUEST_URI'] = $_SERVER['REDIRECT_HANDLER'];

除了像这样更改 PHP 之外,我只能想到这一点:首先硬重定向到处理程序,将版本信息放在查询字符串中。然后捕获该请求,并软重定向到版本/处理程序。Request_uri将正确设置,但它很丑陋且非常容易出错。

也就是说,我完全同意 Gerben 关于使用子域进行版本控制的观点。