这是一个非常不可靠的插件,我的朋友。
在我们真正开始之前,扔掉这个条件-它完全不起作用:
if($_REQUEST[\'s\'] != \'\') {
}
但事实上,最有可能的是,最初的插件开发人员打算通过退出函数来实现这个条件,如果
$_REQUEST[\'s\']
未设置(请参见,在这种情况下,此函数的作用很小):
function getApplications( $_REQUEST ) {
if( empty( $_REQUEST[\'s\'] ) ) {
return false;
}
global $wpdb;
$sql = "SELECT * FROM employment_applications";
...
return $applications;
}
致命错误首先:致命错误。
$_REQUEST
在PHP中,是一个自动填充的超全局,PHP用HTTP请求数据填充它。因此,它可以被视为
reserved word (更具体地说,a
predefined variable). 指定
$_REQUEST
作为
getApplications()
函数告诉PHP将第一个参数引用为
$_REQUEST
, 但是,在PHP5中,超全局变量不能在本地范围内,这意味着PHP将代码解释为试图重新分配超全局变量,因此出现了错误(不确定更改的具体版本,但可以在PHP4中使用超全局变量作为参数)。
If the getApplications()
function is called with arguments, 更改参数的名称以保持适当的流,并避免重新分配$_REQUEST
超级全球:
function getApplications( $request ) {
if( empty( $request[\'s\'] ) )
return false;
global $wpdb;
$sql = "SELECT * FROM employment_applications";
$sql .= " WHERE applicant_name LIKE \'%" . $request[\'s\'] . "%\'";
$applications = $wpdb->get_results( $sql );
$wpdb->show_errors();
$error = $wpdb->last_error;
if($error != \'\') {
echo \'<div class="alert alert-error">\' . $error . \'</div>\';
}
return $applications;
}
If the getApplications()
function called without arguments (or is always called with $_REQUEST
as the argument, i.e. getApplications( $_REQUEST )
), 完全删除参数并直接使用
$_REQUEST
超级全球:
function getApplications() {
if( empty( $_REQUEST[\'s\'] ) )
return false;
global $wpdb;
$sql = "SELECT * FROM employment_applications";
$sql .= " WHERE applicant_name LIKE \'%" . $_REQUEST[\'s\'] . "%\'";
$applications = $wpdb->get_results( $sql );
$wpdb->show_errors();
$error = $wpdb->last_error;
if($error != \'\') {
echo \'<div class="alert alert-error">\' . $error . \'</div>\';
}
return $applications;
}
更有可能的是,您的解决方案将是两者中的后者。
禁用仪表板外的插件有很多方法,但以下是最常见的几种方法:
更改active_plugins
选项(永久)
Database:
在wp_options
表查找其option_name
字段为active_plugins
并修改它的option_value
领域请注意this is a serialized
value, 因此,如果您不确定如何手动修改序列化数据,则需要取消序列化值,进行修改,然后在将其放回字段之前重新序列化。或者,删除option_value
将禁用所有插件(尽管其停用挂钩可能不会触发,具体取决于插件的实现)。或者你可以利用serialization-aware search and replace tool.
PHP:
利用the deactivate_plugins()
function 或者Options API 在a中must-use plugin. 必须使用的插件始终被视为“已激活”,并在加载所有其他插件之前加载;这为执行代码提供了一个方便的入口点,即使站点的大部分无法访问。无效active_plugins
(“可撤销”)
这与重命名(根)插件文件夹的技巧基本相同。在里面active_plugins
, WordPress记录每个插件的主文件相对于插件根的位置(the constant
WP_PLUGIN_DIR
). 通过更改WP_PLUGIN_DIR
您可以强制WordPress松开插件的跟踪,从而无法加载它们,从而有效地处理请求,就像没有插件一样,并离开active_plugins
选项在数据库中未触及。在里面wp-config.php: define( \'WP_PLUGIN_DIR\', \'thisPathDoesNotExist\' );
. 删除此行将使插件路径恢复为其默认设置。
“更好的故障排除方法”请参阅Codex条目Debugging in WordPress WordPress提供的调试工具入门,以及一些帮助调试的优秀插件的简短列表。第一步是始终启用WP_DEBUG
常量inwp-config.php
(尽管尽可能避免在生产环境中进行此操作):
define( \'WP_DEBUG\', true );
如果WP_DEBUG
是false
(默认情况下),WordPress会抑制绝大多数警告和错误。我还强烈建议使用Xdebug 在开发机器上快速访问非常有用的堆栈跟踪,格式化var_dump()
s、 远程调试和漂亮的颜色(等等)。
关于安全的注意事项让我们花点时间检查一下这条线:
$sql .= " WHERE applicant_name LIKE \'%" . $_REQUEST[\'s\'] . "%\'";
作为$_REQUEST
填充了HTTP请求数据,这一行所做的是获取数据键s
直接从请求中删除,并将其放入SQL查询中。This is a major security hole and likely exposes your site to SQL injections. 任何可以访问网站任何部分并导致getApplications()
执行的函数可以简单地附加?s=whatever
到URL以执行自己设计的查询。缺少正确的转义意味着攻击者甚至可能使用此查询访问employment_applications
桌子如果未进行抽象和/或验证,则应转义用户提供的所有数据,至少:
$sql = "SELECT * FROM employment_applications";
$sql .= " WHERE applicant_name LIKE \'%" . esc_sql( like_escape( $_REQUEST[\'s\'] ) ) . "%\'";
$applications = $wpdb->get_results( $sql );
或$querystring = "SELECT * FROM employment_applications WHERE applicant_name LIKE \'%%%s%%\'";
$applications = $wpdb->get_results( $wpdb->prepare( $querystring, $_REQUEST[\'s\'] ) );
你应该在Data Validation 和Protecting Queries Against SQL Injection Attacks WordPress中的数据安全简介。综上所述,我觉得您修改后的代码应该与以下代码类似:
function getApplications() {
if( empty( $_REQUEST[\'s\'] ) )
return false;
global $wpdb;
$querystring = "SELECT * FROM employment_applications WHERE applicant_name LIKE \'%%%s%%\'";
$applications = $wpdb->get_results( $wpdb->prepare( $querystring, $_REQUEST[\'s\'] ) );
$wpdb->show_errors();
$error = $wpdb->last_error;
if( ! empty( $error ) ) {
echo \'<div class="alert alert-error">\' . $error . \'</div>\';
}
return $applications;
}