这实际上是个好问题。当然,用户输入不可信,但也会对同一值进行两次清理”;以防万一”;不是解决问题的最佳方案。
这个问题的唯一真正答案可以通过查看代码并遵循所发生的事情来给出。
读了几个小时后,我可以说:
WP Query清理这些值,但并不是在一个地方完成所有操作。值在实际使用之前正在清理。这是一种非常有机的、随时可用的方法。此外,并不是所有的值都会被清理,但在这些情况下,SQL查询会使用一条准备好的语句。
让我们详细了解一下,当我们这样做时会发生什么:
$query = new WP_Query($args);
WP\\u查询类构造函数检查
$args
是否为空数组。如果不是,它将运行
query()
方法通过
$args
数组(此时称为
$query
阵列)。
$this->query($query);
The
query()
方法调用
init()
方法,该方法可取消设置以前可能的值并设置新的默认值。
然后它运行wp_parse_args() 在$args
大堆此函数不清理任何内容,它充当默认数据和输入数据之间的桥梁。
下一个电话是get_posts()
方法,该方法负责根据给定的查询变量检索帖子。
在get_posts()
方法是parse_query()
方法,该方法首先调用fill_query_vars()
方法(此方法确保设置了默认键的列表。未设置的键将根据具体情况使用空字符串或空数组进行设置)。
然后,仍然在parse_query()
方法,进行第一次santization。
p
对照检查is_scalar() 并用intval()
而且absint() 用于以下值:
page_id
year
monthnum
day
w
paged
hour
minute
second
attachment_id
此外,a
preg_replace(\'|[^0-9]|\'...)
正在运行
m
,
cat
,
author
仅允许在这些上使用逗号分隔的正整数或负整数列表。
对于此时的其他值,仅使用trim()函数。以下情况如下:
pagename
name
title
之后,该方法开始检查我们正在运行的查询类型。是搜索吗?附件?一页?一个帖子。。。
如果apagename
设置,然后调用(不清理值)get_page_by_path($qv[\'pagename\'])
. 但通过检查函数源,我们可以看到该值已用esc_sql() before it\'s used for a database request.
之后,我们可以看到post_type
或post_status
使用时,它们都经过消毒sanitize_key() (只允许使用小写字母数字字符、破折号和下划线)。
对于与分类相关的参数parse_tax_query()
方法被调用。
category__and
, category__in
, category__not_in
, tag_id
, tag__in
, tag__not_in
, tag__and
使用absint()
tag_slug__in
和tag_slug__and
使用sanitize_title_for_query()
此时parse_query()
方法已结束,但我们仍在get_posts()
方法
posts_per_page
已消毒。
title
使用时未初始化,但带有prepared statement. 您可能会发现这个问题很有趣:Are prepared statements enough to prevent SQL injection?
那么我们有post__in
和post__not_in
正在用absint().
如果您继续阅读代码并加以注意,您将看到所有键在接触SQL语句或使用准备好的语句之前实际上都已被清理。
因此,要回答您最初的问题:
Does WordPress sanitize arguments to WP_Query?
它确实净化了大部分,但不是全部。例如
pagename
,
name
和
title
仅为“;“已清理”;使用
trim() 函数(不返回SQL安全值!)。但对于未清理的值,将使用prepared语句来执行数据库请求。
你应该相信这个吗
好吧,在这种特殊情况下,我更倾向于
redundant 只需在将所有方法放入查询之前对其进行预先组织即可。
我也是,作为一名工科学生,我希望得到一个肯定或否定的答案。但请注意,WordPress的代码库是以一种自然的方式进化而来的,所以它就像大自然一样:凌乱。这并不意味着它不好。但混乱意味着可能存在一个看不见的边缘案例,有人可能携带炸弹潜入。你可以通过加倍守卫来防止这种情况!