此解决方案通过应用仅匹配常用和拉丁Unicode脚本中的字符的正则表达式来过滤搜索字符串。
用正则表达式匹配拉丁字符had my mind blown over at Stack Overflow. 事实证明,正则表达式a mechanism 匹配整个Unicode类别,包括指定整个Unicode "scripts", 每个对应于不同书写系统中使用的字符组。
这是通过使用\\p
在大括号中后跟Unicode类别标识符的元字符-so[\\p{Common}\\p{Latin}]
匹配Latin or Common scripts - 这包括标点符号、数字和其他符号。
像@Paul \'Sparrow Hawk\' Biron points out, 这个u
pattern modifier flag 应在正则表达式的末尾设置,以便PHP的PCRE函数将主题字符串视为UTF-8
Unicode编码。
那么,所有这些模式
/^[\\p{Latin}\\p{Common}]+$/u
将匹配由拉丁语和通用Unicode脚本中的一个或多个字符组成的整个字符串。
过滤搜索字符串的好地方是the pre_get_posts
action 在WordPress执行查询之前立即触发。具有more care, 这也可以通过使用a request
filter.
function wpse261038_validate_search_characters( $query ) {
// Leave admin, non-main query, and non-search queries alone
if( is_admin() || !$query->is_main_query() || !$query->is_seach() )
return;
// Check if the search string contains only Latin/Common Unicode characters
$match_result = preg_match( \'/^[\\p{Latin}\\p{Common}]+$/u\', $query->get( \'s\' ) );
// If the search string only contains Latin/Common characters, let it continue
if( 1 === $match_result )
return;
// If execution reaches this point, the search string contains non-Latin characters
//TODO: Handle non-Latin search strings
//TODO: Set up logic to display error message
}
add_action( \'pre_get_posts\', \'wpse261038_validate_search_characters\' );
响应不允许的搜索一旦确定搜索字符串包含非拉丁字符,您可以使用
WP_Query::set()
通过更改查询的名称来修改查询
query vars - 因此会影响SQL查询WordPress随后的组合和执行。
最相关的查询变量可能如下所示:
考虑到上述情况,您可以通过加载
search.php
没有结果的模板:
function wpse261038_validate_search_characters( $query ) {
// Leave admin, non-main query, and non-search queries alone
if( is_admin() || !$query->is_main_query() || !$query->is_seach() )
return;
// Check if the search string contains only Latin/Common Unicode characters
$match_result = preg_match( \'/^[\\p{Latin}\\p{Common}]+$/u\', $query->get( \'s\' ) );
// If the search string only contains Latin/Common characters, let it continue
if( 1 === $match_result )
return;
$query->set( \'s\', \' \' ); // Replace the non-latin search with an empty one
$query->set( \'post__in\', array(0) ); // Make sure no post is ever returned
//TODO: Set up logic to display error message
}
add_action( \'pre_get_posts\', \'wpse261038_validate_search_characters\' );
显示错误的方式实际上显示错误消息的方式在很大程度上取决于您的应用程序和主题的能力,可以通过多种方式来实现。如果主题调用
get_search_form()
在它的搜索模板中,最简单的解决方案可能是使用
pre_get_search_form
action 钩住以在搜索表单的正上方输出错误:
function wpse261038_validate_search_characters( $query ) {
// Leave admin, non-main query, and non-search queries alone
if( is_admin() || !$query->is_main_query() || !$query->is_seach() )
return;
// Check if the search string contains only Latin/Common Unicode characters
$match_result = preg_match( \'/^[\\p{Latin}\\p{Common}]+$/u\', $query->get( \'s\' ) );
// If the search string only contains Latin/Common characters, let it continue
if( 1 === $match_result )
return;
$query->set( \'s\', \' \' ); // Replace the non-latin search with an empty one
$query->set( \'post__in\', array(0) ); // Make sure no post is ever returned
add_action( \'pre_get_search_form\', \'wpse261038_display_search_error\' );
}
add_action( \'pre_get_posts\', \'wpse261038_validate_search_characters\' );
function wpse261038_display_search_error() {
echo \'<div class="notice notice-error"><p>Your search could not be completed as it contains characters from non-Latin alphabets.<p></div>\';
}
显示错误消息的其他一些可能性包括:
如果您的网站使用JavaScript,可以显示;闪光灯“;或“或”;“模态”;消息(或您自己添加此类功能),添加在设置特定变量时显示页面加载消息的逻辑,然后添加wp_enqueue_script
用钩子钩住$priority
大于将该JavaScript排队并使用wp_localize_script()
将该变量设置为包含错误消息使用wp_redirect()
将用户发送到您选择的URL(此方法需要额外的页面加载)设置一个PHP变量或调用一个方法,该方法将通知主题/插件错误,以便在适当的地方显示设置s
查询变量至\'\'
而不是\' \'
和使用page_id
代替post__in
以便返回您选择的页面使用loop_start
hook 注射假药WP_Post
对象将您的错误包含到查询结果中-这无疑是一个丑陋的黑客行为,可能与您的特定主题不符,但它具有潜在的令人满意的副作用,即抑制;“无结果”;消息使用template_include
过滤挂钩,将搜索模板与主题或插件中显示错误的自定义模板交换如果不研究所讨论的主题,就很难决定你应该走哪条路。