如何使用 apache 403 错误作为带有 htaccess 的路由技术
Posted
技术标签:
【中文标题】如何使用 apache 403 错误作为带有 htaccess 的路由技术【英文标题】:How to use apache 403 error as routing technique with htacess 【发布时间】:2019-09-22 18:56:51 【问题描述】:我有一个具有这种目录结构的简单 php web 应用程序
.
├── custom_403.html
├── custom_404.html
├── home
│ └── home.php
├── .htaccess
├── index.php
├── login
│ └── login.php
├── public
│ ├── bootstrap
│ ├── css
│ ├── error_pages
│ ├── fontawesome
│ ├── .htaccess
│ └── js
├── signup
│ └── signup.php
├── test.php
我制作了一个.htacess
文件,基本上看起来像这样
ErrorDocument 404 /public/error_pages/404.php
ErrorDocument 500 /public/error_pages/500.php
ErrorDocument 403 /index.php
当我输入类似http://localhost/login/
的内容时,它应该给我一个403 Forbidden
错误,因为目录login
存在但没有文件index.php
。根据我的.htacess
,它应该提供默认的index.php
文件。我利用index.php
上的这一点,使用jquery 从地址栏加载指定路径中的文件。
我搜索window.location.pathname
以使用resolveUrl()
函数从该路径加载相应的文件。
这是一个例子
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>Document</title>
<!-- Boostrap 4.3 -->
<link rel="stylesheet" href="/public/bootstrap/css/bootstrap.css">
<!-- Fontawesome 5 Free -->
<link rel="stylesheet" href="/public/fontawesome/css/all.css">
<link rel="stylesheet" href="/public/css/style.css">
<script src="/public/js/jquery.js"></script>
<script src="/public/bootstrap/js/bootstrap.js"></script>
</head>
<body>
<nav class="navbar navbar-expand-lg r-shadow">
<a class="navbar-brand" href="#"><img class="d-inline-block align-top" src="https://seeklogo.com/images/M/marvel-comics-logo-31D9B4C7FB-seeklogo.com.png" srcset=""></a>
<button class="navbar-toggler" type="button" data-toggle="collapse" data-target="#navbarText" aria-controls="navbarText" aria-expanded="false" aria-label="Toggle navigation">
<span class="navbar-toggler-icon"></span>
</button>
<div class="collapse navbar-collapse justify-content-end" id="navbarText">
<ul class="navbar-nav">
<li class="nav-item active">
<a class="nav-link" href="home">Home</span></a>
</li>
<li class="nav-item">
<a class="nav-link" href="login">Login</a>
</li>
<li class="nav-item">
<a class="nav-link" href="signup">Sign Up</a>
</li>
</ul>
</nav>
<div class="root">
<div class="container mt-3 rounded" style="background-color: rgba(255, 255, 255, 0.1); ">dcfdcf</div>
<div id="loader">
<div class="spinner"><i class="fas fa-spinner fa-spin"></i></div>
</div>
</div>
</body>
<script>
function resolveUrl(url)
if (url)
var path = url.replace(/\//gi, '').trim();
$(".container").load("/" + path + "/" + path + ".php");
return path;
else
$(".container").load("/home/home.php");
console.log(path)
function resolveActiveTab(pathName)
$(".nav-item").removeClass("active");
if (pathName)
$("li > a[href='" + pathName + "']").parent().addClass("active");
else
$("li > a").first().parent().addClass("active");
$(document).ready(function ()
console.log(window.location.pathname)
var currentPath = resolveUrl(window.location.pathname);
resolveActiveTab(currentPath)
$(document).ajaxStart(function ()
$("#loader").css(
"display": "block"
);
)
$(document).ajaxStop(function ()
$("#loader").css(
"display": "none"
);
)
$('.nav-link').click(function (e)
e.preventDefault();
var path = $(this).attr("href");
$(".container").load("/" + path + "/" + path + ".php");
resolveActiveTab(path)
window.history.pushState("", "", "/" + path);
)
)
</script>
</html>
这意味着如果使用http://localhost/login/
之类的路径刷新页面,jquery 将加载login.php
。
这工作正常,除了我在 apache 日志上得到一个看起来像这样的错误
AH01276: 无法提供目录 /var/www/html/test/login/: 找不到匹配的 DirectoryIndex (index.php,index.html,index.cgi,index.pl,index.xhtml,index.htm),和选项指令禁止的服务器生成的目录索引
当我尝试通过将文件名从 login.php signup.php etc
更改为 index.php
来解决此问题时,我会返回这些文件,因为它们确实存在,这意味着我不会收到 403
错误。我尝试在我的.htaccess
中拒绝访问这些特定文件,但随后它们被拒绝访问包括 jquery .load()
函数在内的所有内容。我的问题是如何在没有 apache 错误的情况下有效地做我正在做的事情。
【问题讨论】:
【参考方案1】:您的.htaccess
错误,您正在使用ErrorDocument
403
加载文件index.php
,(ErrorDocument
通常用于自定义错误页面而不是加载正常资源)您希望有一个@ 987654328@ 尝试加载 login/
时,因为此文件夹没有 index.php
文件,但我怀疑您在 VirtualHost
中有选项 Indexes
,此指令加载文件夹内容但不提供403
错误。
我的VirtualHost
用于测试目的是:
<VirtualHost localhost-test:80>
ServerName localhost-test
ServerAlias localhost-test
ErrorLog "logs/localhost-test-error.log"
TransferLog "logs/localhost-test-access.log"
DocumentRoot "D:/Web/test"
<Directory />
Require all granted
Options FollowSymLinks Includes ExecCGI
AllowOverride All
</Directory>
</VirtualHost>
如果您从VirtualHost
中删除Indexes
,您会看到Forbidden
错误自定义页面。你应该有:
ErrorDocument 404 /public/error_pages/404.php
ErrorDocument 500 /public/error_pages/500.php
ErrorDocument 403 /public/error_pages/403.php
现在,如果您尝试在没有 index.php
文件的情况下加载文件夹 /login/
,您应该有一个带有自定义页面错误的 Forbidden
403
,但同时使用 JQuery 您可以加载 login.php
文件而是。
我希望这会有所帮助。
【讨论】:
我对你所说的一切都很熟悉,但我的问题是我想在我的应用程序中使用文件夹名称作为路径/路由。因此,当有人加载http://localhost/login
时,它不会尝试访问登录文件夹,但我的 jquery 会从 login/login.php
加载内容
看这个:***.com/questions/5301776/…
看这个:***.com/questions/21346486/…
您是否尝试在文件夹 login
中放入一个文件 index.php
并将其命名为 index.php?option=login
和 index.php?option=signup
和 index.php?option=home
?然后使用switch
执行一些操作,例如case 'login': header("Location: login.php"); break; case 'signup': header("Location: signup.php"); break; case 'home': header("Location: ../index.php"); break;
等等。我的只是想法。
你觉得改用referer
检查怎么样?例如,如果login.php
文件有www/login/index.php
作为referer,则可以,而如果referer
为空,则意味着用户可以直接访问login.php
文件,在这种情况下,在检查后放置一个漂亮exit();
if (!isset($_SERVER['HTTP_REFERER'])) exit("Direct Access to this File not Allowed");
以上是关于如何使用 apache 403 错误作为带有 htaccess 的路由技术的主要内容,如果未能解决你的问题,请参考以下文章
apache在发布请求时返回403错误,输入变量计数保持不变,值发生变化
启用永久链接后,Wordpress 在 wamp apache 上抛出 403 禁止错误?