【问题标题】:PHP and htaccess | Redirect to "page not found" if user try to directly access parameter value inside urlPHP 和 htaccess |如果用户尝试直接访问 url 中的参数值,则重定向到“找不到页面”
【发布时间】:2021-01-11 09:50:42
【问题描述】:

我在我的网站上使用了这个友好的网址:

https://myexample.com/post/10/post-title

我正在尝试做一些拒绝用户直接访问参数值的事情。例如,如果用户尝试在上面的 url 中放置另一个 id,htaccess 会将他重定向到 404 页面。

下面是我的 htaccess 代码,它将我的 url 获取参数转换为友好的 url,并且像一个魅力一样工作:

RewriteEngine On
RewriteRule ^post/([^/]*)/([^/]*)$ /news?id=$1&title=$2 [L]

在这种情况下,我该如何改进我的 htaccess 来做到这一点?

感谢任何帮助。

【问题讨论】:

  • 在这个级别上,无法检查 ID 10 是否存在,或者是否属于带有 slug post-title 的帖子。你应该在你的脚本中处理这个,这会产生实际的数据库请求(?)。
  • 感谢您的反馈@04FS。知道了。实际上,当我尝试在 url 中清空 id 参数时,我得到 500 内部服务器错误,即使我有 GET 规则来重定向,如果 id 为空。如果某些参数不存在或 GET 值发生更改,我将尝试在 php 中实现一些规则以重定向到 404 页面。
  • 仅供参考,外部重定向到 404 文档是错误的做法。所有依赖状态代码信息的客户端(例如搜索引擎机器人),将无法再将 404 状态代码与最初请求的 URL 相关联 - 因为您重定向到其他地方,并且只有然后第二个请求得到了 404 响应。如果您确定您的 PHP 脚本中有“404 案例”,那么该脚本应该直接以 404 响应,重定向到不同的 404 文档 URL。
  • 我明白了。但在这种情况下,如果我想在 url 不正确的情况下重定向用户?例如,如果我尝试编辑或尝试删除此问题页面的此参数 /64057693/,SO 会给我一个 Page not found。在这种情况下,这与我的疑问有关吗?
  • “如果我尝试编辑或尝试删除此问题页面的此参数 /64057693/,SO 将给我一个未找到的页面。” - 那就是适当的回应,不是吗?

标签: php .htaccess friendly-url


【解决方案1】:

我找到了解决问题的方法并且工作正常:

我的 .htaccess:

RewriteEngine On
RewriteRule ^post/?(.*)/([^/]*)$ /news?id=$1&title=$2 [L]

首先,我在news.php的title参数上实现了一个替换空格和特殊字符的函数:

function sanitizeString($str) {
    $str = preg_replace('/[áàãâä]/ui', 'a', $str);
    $str = preg_replace('/[éèêë]/ui', 'e', $str);
    $str = preg_replace('/[íìîï]/ui', 'i', $str);
    $str = preg_replace('/[óòõôö]/ui', 'o', $str);
    $str = preg_replace('/[úùûü]/ui', 'u', $str);
    $str = preg_replace('/[ç]/ui', 'c', $str);
    $str = preg_replace('/[^a-z0-9]/i', '-', $str);
    $str = preg_replace('/_+/', '-', $str);
    return $str;
}

然后我在 news.php 上创建了一个脚本来检查 idtitle 参数是否在 MySql 上正确关联:

include 'connection.php';

$stmt = $db -> prepare('SELECT id, title FROM posts WHERE id = ?');

$id = $_GET['id'];

$stmt -> bind_param('i', $id);
$stmt -> execute();
$stmt -> store_result();
$stmt -> bind_result($postID, $title);
$stmt -> fetch();
$stmt -> close();
$db -> close();

$postTitle = sanitizeString(trim(strtolower($title)));

if($_GET['id'] != $postID || $_GET['title'] != $postTitle){
    
    header('location: /404.html');
    exit();
    
}else{
    
    echo 'Everything Fine';
    
}

基本上,根据上面的代码,如果用户尝试操作 URL 中的参数,例如 id /10/ 和 title /post-title:

https://myexample.com/post/10/post-title

例如,脚本会将用户重定向到 404 错误页面或找不到页面或某些自定义页面。

如果有人有更好的方法来改进这一点,请在这里告诉。

希望这个问题可以帮助其他人。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2012-10-09
    • 2013-04-07
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多