You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

WordPress通过自定义分类法获取自定义文章仅init钩子生效,如何获取文章数组?

问题原因

你的判断是对的,WordPress 中自定义文章类型、自定义分类法的标准注册时机都是挂载在 init 钩子下执行,默认优先级为10。如果在 init 钩子触发前就调用 get_portfolio_posts(),此时分类法、自定义文章类型还未被注册到 WordPress 系统中,tax_query 会被判定为无效,自然返回空数组。


解决方案

根据你使用场景的不同,可选以下任意一种方案:

1. 模板文件中直接调用

如果你是在主题/子主题的模板文件(如 page.php、archive-portfolio.php 或自定义页面模板)中需要使用该文章数组,直接调用即可:

// 直接写在模板代码对应位置即可正常拿到返回值
$portfolio_posts = get_portfolio_posts();

模板文件的加载时机远晚于 init 钩子,此时所有自定义内容类型都已注册完成,不会返回空。

2. 全局作用域/非模板场景下缓存结果

如果你需要在 functions.php、插件文件的全局作用域中提前声明该变量,可以写一个带静态缓存的获取方法,确保查询在 init 钩子之后执行:

// 先保留你原有查询方法
function get_portfolio_posts()
{
    $tax_query = 
        [
            'relation' => 'AND',
            [
                'taxonomy' => 'project-type',
                'field' => 'slug',
                'terms' => 'mobile',
            ],
            [
                'taxonomy' => 'project-industry',
                'field' => 'slug',
                'terms' => 'health-fitness',
            ],
        ];

    $posts = get_posts([
        'post_type' => 'portfolio',
        'posts_per_page' => -1,
        'tax_query' => $tax_query,
    ]);

    return $posts;
}

// 新增带缓存的获取方法
function get_cached_portfolio_posts() {
    static $posts_cache = null;
    if (null === $posts_cache) {
        // 已过init钩子时机,直接查询
        if (did_action('init')) {
            $posts_cache = get_portfolio_posts();
        } else {
            // 未到时机,挂载到init钩子后执行查询,优先级设为20(晚于默认的分类法/文章类型注册优先级10)
            add_action('init', function() use (&$posts_cache) {
                $posts_cache = get_portfolio_posts();
            }, 20);
        }
    }
    return $posts_cache;
}

后续所有需要用到文章数组的位置,统一调用 get_cached_portfolio_posts() 即可拿到非空结果:

// 全局声明变量
$portfolio_posts = get_cached_portfolio_posts();

// 任意init之后的执行场景下都可以直接使用该变量,比如其他钩子回调、模板文件中
add_action('wp_head', function() {
    global $portfolio_posts;
    // 这里就可以正常操作$portfolio_posts
});

3. 挂载到晚于init的钩子中调用

如果你是在自定义逻辑中使用,只需要将调用逻辑挂载到 init 之后触发的钩子即可,常用的可选钩子有 wp_loaded、template_redirect 等:

add_action('wp_loaded', function() {
    $posts = get_portfolio_posts();
    // 在这里写你的业务逻辑即可正常拿到返回值
});

内容的提问来源于stack exchange,提问作者forever_young

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.06 18:09:01