如何将 prepare() 与动态列名一起使用?
Posted
技术标签:
【中文标题】如何将 prepare() 与动态列名一起使用?【英文标题】:How to use prepare() with dynamic column names? 【发布时间】:2015-06-19 13:28:57 【问题描述】:我有一个函数,它以一个 sql 表列名字符串作为参数,返回 1 个字符串结果:
function myFunction($column_name)
return $wpdb->get_var($wpdb->prepare("SELECT %s FROM myTable WHERE user_id=%s", $column_name, $current_user->user_login));
但是,此代码不起作用,因为由于准备的性质,我不能将变量用于列名(和表名)。
这可行,但我认为它会带来安全问题:
return $wpdb->get_var('SELECT ' . $column_name . ' FROM myTable WHERE user_id=' . $current_user->user_login);
我需要做什么才能在我的准备语句中使用动态列名?
【问题讨论】:
【参考方案1】:您可以改用“已批准”值的列表,这样您就不会真正在查询中使用用户数据。像这样的:
$Approved = array ('firstname', 'lastname', 'birthdate') ;
$Location = array_search($ColumnName, $Approved) // Returns approved column location as int
if($Location !== FALSE)
// Use the value from Approved using $Location as a key
$Query = $wpdb->Prepare('SELECT ' . $Approved[$Location] . ' FROM myTable WHERE user_id=:userid');
$Query->Execute(array(
:userid => $current_user->user_login
));
return $Query;
else
return false;
也许只获取所有(SELECT * 或 SELECT a、b、c、d)用户数据并将其保存到会话以供以后使用可能更容易?
【讨论】:
这行得通。但是,prepare() 中的 $Approved[$Location] 被篡改有多“安全”?谢谢! @Rollor 该代码不使用任何真正的动态值,仅使用 $Approved 数组中的值。只要您不允许以任何方式更改该数组,它将是安全的。它基本上是根据您手动设置的已批准值列表验证 $ColumnName 。如果我不验证,那么它将不会运行查询。在 Execute 中发送的值受到保护以防注入,因此无需验证/清除这些值。 ...既然$ColumnName别无选择,只能“通过”$Approved,我认为这是有道理的。sanitize_text_field()
是否足以保证数据安全而不是列入白名单?以上是关于如何将 prepare() 与动态列名一起使用?的主要内容,如果未能解决你的问题,请参考以下文章
将列名作为参数传递给 Redshift 中的“PREPARE”的问题
QSqlQuery 与列名 Sqlite 的 prepare 和 bindValue
C#如何将.OrderBy与多列一起使用并将列号解码为列名?
当列名包含特殊字符时,如何将 Convert 函数与 RowFilter/CustomFilter 一起使用?