htaccess:从缺少值的查询字符串中删除 URL 参数?

Posted

技术标签:

【中文标题】htaccess:从缺少值的查询字符串中删除 URL 参数?【英文标题】:htaccess: remove URL parameter from query string with missing value? 【发布时间】:2021-03-14 12:16:14 【问题描述】:

我要重定向:

https://www.example.com/?p2https://www.example.com/

https://www.example.com/?p1=v1&p2&p3=v3https://www.example.com/?p1=v1&p3=v3

https://www.example.com/page.php?p4=v4&p2https://www.example.com/page.php?p4=v4

您可以假设缺少值的查询字符串始终为p2,如果这样更容易回答问题。

p2 查询字符串不会总是缺少该值,在这些情况下我不希望它被删除。

【问题讨论】:

如果它为空,在应用程序逻辑中忽略该参数可能会容易得多。 这是一个公平的问题:+1。请阅读 Steven 的回复,如果您觉得有用,请“点赞”和“接受”。 arkascha:“您需要将代码添加到问题中。”参考? 【参考方案1】:

修复.htaccess

您可以在.htaccess 中以多种不同的方式进行大量重写...

示例 1:

RewriteCond %QUERY_STRING ^p2$
RewriteRule . / [QSD,L]

RewriteCond %QUERY_STRING ^(.+)&p2$
RewriteRule . /?%1 [L]

RewriteCond %QUERY_STRING ^p2&(.+)$
RewriteRule . /?%1 [L]

RewriteCond %QUERY_STRING ^(.+)&p2(&.+)$
RewriteRule . /?%1%2 [L]

示例 2:

RewriteCond %QUERY_STRING (^|.*&)p2(&.*|$)
RewriteRule . /?%1%2 [L]

// This doesn't give particularly clean query strings (not that they need to
// be for the server to understand it).
// e.g. 
//    ?p1=v1&p2&p3=v3 -> ?p1=v1&&p3=v3

示例 3:

RewriteCond %QUERY_STRING (^|.*&)p2(?:&(.*)|$)
RewriteRule . /test.php?%1%2 [L]

// ?p2&p3=v3       -> ?p3=v3
// ?p1=v1&p2       -> ?p1=v1
// ?p1=v1&p2&p3=v3 -> ?p1=v1&p3=v3

“这也利用了 mod_rewrite “功能”,其中结果查询字符串上的尾随 & 在分配给 Location HTTP 响应标头之前被自动截断/删除。” @MrWhite

正如 @MrWhite 指出尾随 & 被截断,所以考虑到这一点,您可以使用上述作为单行条件来捕捉所有可能性(示例输入和输出在注释行//...)。

在脚本中修复它

虽然您可以如上所示更改查询字符串,但当您可以在脚本中轻松处理它时,这样做真的没有意义(例如PHP):

if(empty($_GET["p2"]))
    unset($_GET["p2"]);

无论如何你必须做什么来处理你页面上的查询字符串?!


补充说明

上面的规则会默默地删除查询字符串。如果您想让用户知道,那么您应该按照 @MrWhite's 的回答重定向,使用适当的 HTTP 响应代码设置标志 [R=30X]

https://developer.mozilla.org/en-US/docs/Web/HTTP/Status

【讨论】:

【参考方案2】:

.htaccess...中执行此操作的另一种方法...

RewriteCond %QUERY_STRING ^&?p2(?:&|$)(.*) [OR]
RewriteCond %QUERY_STRING (.+)&p2(&.*|$)
RewriteRule ^ %REQUEST_URI?%1%2 [R=302,L]

这应该在你的.htaccess文件的顶部附近,在其他重写之前。

这会处理p2 URL 参数(没有值)的所有 查询字符串变体,并产生一个“干净”的查询字符串。该 URL 已通过外部重定向“更正”。 (首先使用 302 - 临时 - 重定向进行测试,然后再更改为 301 - 永久 - 如果这是故意的,以避免潜在的缓存问题。)

两个 OR 条件中只有一个会匹配。第一个条件处理p2 出现在查询字符串开头的情况。第二个条件处理p2 稍后出现或出现在查询字符串末尾的情况。这样我们就不会在结果替换中得到不匹配或重复的&(URL 参数分隔符)。

%1%2 反向引用包含最后匹配 CondPattern(无论是哪个)中的第一个和第二个捕获组。基本上是p2 参数前后的字符串。

这还利用了 mod_rewrite “功能”,其中在结果查询字符串上的尾随 & 会在分配给 Location HTTP 响应标头之前自动截断/删除

但是,正如已经提到的,取决于这个“错误”p2 URL 的普遍程度以及它出现的位置,那么最好简单地“忽略”它并确保您已设置适当的 rel="canonical" html 中的元素。

【讨论】:

以上是关于htaccess:从缺少值的查询字符串中删除 URL 参数?的主要内容,如果未能解决你的问题,请参考以下文章

.htaccess URL 重写挑战

htaccess 301 重定向 - 删除查询字符串 (QSA)

.htaccess 获取整个查询字符串到一个变量

HTACCESS-重定向并删除所有查询字符串

htaccess 帮助,从 URL 中删除一个字符串

通过 .htaccess 替换查询字符串中的字符