我来自一个C# MVC背景,但我目前正在从事一个PHP项目。
在C#中,你可以设置装饰器来指定请求URL,使用沿着下面这样的代码:
[HttpGet]
[Route("/ControllerName/ActionName")]
public string MyAction() {
// ...
}
我想在PHP中设置一些类似的东西,所以我设置了如下的文件结构:
+ assets
+ css
+ javascript
+ images
+ server
+ api
+ controllers
- index.php
+ ui
+ area1
- view1.html
- view2.html
+ area2
- etc.html
- .htaccess
- index.html
其中index.html是我的登录页面,其他html页面位于它们各自的/ui/area
目录中,我的restful API页面位于/server/api/controllers
中。/server/api/index.php
遵循与堆栈溢出答案非常相似的模式:https://stackoverflow.com/a/1737903/1920035
在我的.htaccess
文件中,我设置了以下重定向规则:
# Redirect traffic starting with /api to the /server/api/index.php file
Redirect 301 ^(api/.*)$ /server/api/index.php [L,QSA]
这个想法是,如果我点击/api/account/get
,它将重定向到/server/api/index.php
文件,并运行其魔术运行相应的控制器/动作。
问题是,当我启动服务器并点击漂亮的URL时,它总是返回一个500的响应,而没有任何有用的响应文本。
更复杂的是,我正在使用php:8.2.2-apache运行Windows版Docker。
我在这里做错了什么?我没有太多的经验设置.htaccess文件和一个模糊的500响应,我没有太多的去小康。
1条答案
按热度按时间ffscu2ro1#
您需要检查Apache的错误日志以获取500错误的详细信息。
这在语法上是无效的(这 * 可能 * 解释了500错误),并且此处使用了错误的指令。
Redirect
是触发外部重定向的mod_alias指令。[L,QSA]
是与mod_rewriteRewriteRule
指令一起使用的“标志”。Redirect
指令不将正则表达式作为参数(它使用简单的前缀匹配)。但是您不应该在这里触发HTTP外部(301)重定向,您需要在内部重写请求(用户不应该知道底层的
/server
子目录)。为此(URL重写),您需要使用mod_rewrite(如果尚未安装,则需要安装)。例如:
对
/api/<anything>
的请求将被 * 内部重写 * 为/server/api/index.php
。原始正则表达式不需要捕获组和
.*
后缀。因此,^api/
本质上与^(api/.*)$
相同,但更有效。内部重写不需要 substitution 字符串(第二个参数)上的斜杠前缀(最好省略-因此它被视为文件系统路径,而不是URL路径)。mod_rewrite(
RewriteRule
/RewriteCond
指令)能够发出(复杂的)外部重定向以及内部重写。mod_alias(Redirect
/RedirectMatch
指令)仅用于 * 简单的 * 外部重定向。参考: