PHP 5.4内置网络服务器是否有任何关于相对路径的错误或限制?或者是否需要正确(和另外)配置?
当我以前主动编程时,我在 .htaccess 文件中使用这些行在URI路由下工作:
RewriteEngine On
RewriteRule !\.(js|ico|gif|jpg|png|css)$ index.php [L]
FrontController接收到Request,在SQLITE数据库中找到来自给定URI的正确路由,Dispatcher调用Action Controller。
它与Apache非常合作。今天,几个月后,我决定使用PHP 5.4内置的webserver运行我的测试应用程序。
我注意到的第一件事,显然, .htaccess 不起作用所以我使用了代码文件:
<?php
if( preg_match( '/\.(?:png|jpg|jpeg|gif)$/', $_SERVER["REQUEST_URI"] ) ) {
return false;
}
include __DIR__ . '/index.php';
并启动了这样的网络服务器:
php.exe -c "php.ini" -S "localhost:8080" "path\to\testfolder\routing.php"
到目前为止,这么好。我的应用程序需要引导的所有内容都可以通过修改 include_path 来完成:
set_include_path(
'.' . PATH_SEPARATOR . realpath( '../common/next' )
);
下一个文件夹中所有模块的核心文件夹,包含我拥有的所有应用程序的所有内容。并且它不需要为此目的做任何进一步的解释。
我见过的 AutoLoader 技术都没有能够自动加载,因此手动需要的唯一类是我的Autoloader。但运行测试应用程序后,我收到错误,因为找不到我的AutoLoader。 o.O
我一直对realpath()非常怀疑,所以我决定用这个 next 目录的完整和绝对路径来改变它,并且它有效。不应该像我一样做,但它确实有效。
我的自动加载器已加载并由spl_autoload_register()成功注册。作为参考,这是自动加载功能(当然只有Closure):
function( $classname ) {
$classname = stream_resolve_include_path(
str_replace( '\\', DIRECTORY_SEPARATOR, $classname ) . '.php'
);
if( $classname !== FALSE ) {
include $classname;
}
};
但是,无法找到位于 index.php 路径中的资源,如MVC类。所以我做了一些我也不应该做的事情,并将工作目录添加到 include_path 。再次,手动,而不依赖于realpath():
set_include_path(
'.' . PATH_SEPARATOR . 'path/to/common/next'
. PATH_SEPARATOR . 'path/to/htdocs/testfolder/'
);
它再次起作用......几乎! &GT;。&LT;
我可以使用此系统创建的大多数应用程序与基于SQLITE数据库的标准路由器配合得很好。为了使事情更容易,这个路由器在工作目录中查找预定义的SQLITE文件。
当然,我还提供了一种更改此默认条目的方法以防万一,因此我检查此文件是否存在,如果不存在则触发错误。
这是我看到的具体错误。检查程序是这样的:
if( ! file_exists( $this -> options -> dbPath ) ) {
throw RouterException::connectionFailure(
'Routes Database File %s doesn\'t exist in Data Directory',
array( $this -> options -> dbPath )
);
}
dbPath 条目(如果未更改)使用相对于工作目录的常量值 Data / Routes.sqlite 。
如果再次,我再次手动设置绝对路径,一切(真的)工作,请求流成功到达动作控制器。
发生了什么事?
答案 0 :(得分:1)
这是PHP内置Web服务器中的一个错误,自PHP版本5.6.30起,仍然没有修复。
简而言之,如果请求www.foo.com/bar/
并且恰好是目录,则Web服务器不会重定向到www.foo./bar
。作为服务器www.foo.com/bar
的客户端假设它是一个文件(因为末尾缺少斜杠),因此所有后续相对链接将相对于www.foo.com/
而不是www.foo.com/bar/
获取。< / p>
A bug ticket was opened早在2013年就被错误地设置为“不是错误”。
我在2017年遇到类似的问题,所以我对错误罚单留下了评论。
编辑:注意到@ jens-a-koch打开了我链接的机票。我并不是对原始问题的评论。