WordPress:如何在init钩子获取完整路径?非管理员重定向如何排除REST API路径?
解决非管理员用户重定向但排除自定义REST API请求的问题
问题背景
你想要实现非管理员用户访问站点时自动重定向,但需要排除/wp-json/v1/这类自定义REST API路径的请求,同时有两个核心疑问:
- 如何正确获取并判断请求URL?
- 是否应该在
init钩子中实现这个逻辑?
现有代码的不足
你当前基于init钩子的代码缺少请求路径判断逻辑,而且init并不是处理这类请求判断的最佳时机:
function redirect_users() { global $wp; // $url = get_url(); // if ($url === 'whatever') { // return; // } if (get_current_user_id()) { $user = get_userdata(get_current_user_id()); $user_roles = $user->roles; if (!in_array('administrator', (array) $user_roles)) { wp_logout(); wp_redirect($url); exit; } } } add_action('init', '\kw_signup\redirect_non_admin_users', 15);
最优解决方案
推荐使用parse_request钩子(或template_redirect钩子)来实现,这两个钩子能更早且更准确地获取请求路径信息,其中parse_request会自动传入$wp对象,无需全局调用。下面是完善后的代码:
function redirect_non_admin_users($wp) { // 排除所有wp-json开头的REST API请求(包含/wp-json/v1/这类自定义路径) if (!preg_match('/^wp-json\//', $wp->request)) { // 未登录用户直接重定向 if (!get_current_user_id()) { $redirect_url = '你的重定向目标URL'; // 替换为实际的重定向地址 wp_redirect($redirect_url); exit(); } // 已登录但非管理员用户重定向 $user = get_userdata(get_current_user_id()); $user_roles = $user->roles; if (!in_array('administrator', (array) $user_roles)) { $redirect_url = '你的重定向目标URL'; // 替换为实际的重定向地址 wp_redirect($redirect_url); exit(); } } } add_action('parse_request', '\kw_signup\redirect_non_admin_users', 15);
关键细节说明
- 请求路径判断:通过
$wp->request获取当前请求的相对路径,用正则/^wp-json\//匹配所有以wp-json/开头的请求,匹配到就跳过重定向逻辑,完美排除自定义REST API路径。 - 钩子选择:
parse_request:WP处理请求的早期钩子,能准确获取路由信息,适合做这类路由级别的判断。template_redirect:稍晚的钩子,在模板加载前触发,同样可以实现需求。
- 代码优化:合并了重复的登录判断逻辑,同时确保
wp_redirect后必须调用exit()终止后续执行,避免重定向失效。
内容的提问来源于stack exchange,提问作者GWorking
相关产品推荐
相关产品推荐

