php 使用add_permastruct的多个自定义post_type URL的自定义永久链接结构返回常规post错误/ 404

20jt8wwn  于 2022-12-17  发布在  PHP
关注(0)|答案(1)|浏览(102)

在我的WP v6.1,我有两个自定义端口类型:companyproduct和自定义分类country
所需的URL结构分别为%country%/%company_postname%%country%/%product_postname%,下面是$wp_rewrite的代码:

add_action('init', 'custom_init');

function custom_init() {

global $wp_rewrite;
$company_url = '/%country%/%company_postname%';
$product_url = '/%country%/%product_postname%';

$wp_rewrite->add_permastruct('company', $company_url, false);
$wp_rewrite->add_permastruct('product', $product_url, false);

$wp_rewrite->add_rewrite_tag("%company_postname%", '([^/]+)', "company=");
$wp_rewrite->add_rewrite_tag("%product_postname%", '([^/]+)', "product=");
}

使用上面的代码和另一个post_type_link过滤函数,我可以生成我的自定义URL。但是问题是常规的postpage帖子没有返回error_404
常规帖子/页面标准URL结构:x1米10英寸1x
我试过add_permastruct的职位和网页,但没有工作。我如何显示网页和职位,同时有我的自定义职位的自定义网址。

更新1自定义帖子和分类是通过代码创建的。

company代码示例

function company_post_type() {

    $labels = array(
        'name' => _x('Company', 'Post Type General Name', 'text'),
    );
    $args = array(
        'labels' => $labels,
        'supports' => array('title', 'editor', 'custom-fields'),
        'taxonomies' => array('country'),
        'query_var' => true,
        'rewrite' => false
    );
    register_post_type('company', $args);
}

add_action('init', 'company_post_type', 0);

更新2

我的post_type_link函数是:

function post_type_link_function($url, $post) {

    // only if post is published
    if ('' != $url && !in_array($post->post_status, array('draft', 'pending', 'auto-draft'))) {

        // get country terms
        $terms = wp_get_object_terms($post->ID, 'country');

        // country
        if (strpos($url, '%country%') !== FALSE) {
            if (!is_wp_error($terms) && !empty($terms) && is_object($terms[0])) {
                $country = urlencode($terms[0]->slug);
                $url = str_replace('%country%', $country, $url);
            }
        }

        // post names
        $postnames = array('%company_postname%', '%product_postname%', '%postname%');
        foreach ($postnames as $postname) {
            $postname = $post->post_name;
            $url = str_replace($postnames, $postname, $url);
        }

        return $url;
    }

    return $url;
}

更新3

当固定链接设置为普通www.example.com/?p=123时,所有帖子、页面和自定义帖子都可以正常加载。

更新4

我注意到帖子和页面没有使用single.phppage.php模板。它使用的是index.php。然而,我没有附加任何模板到这些页面或帖子。

更新5 -已解决

这是由于country自定义分类中的'rewrite' => array('slug' => '/', 'with_front' => FALSE)。如果没有这个rewrite,现在页面和帖子都很好。

xwbd5t1u

xwbd5t1u1#

您可以使用post_type_link挂钩。
使用自定义重写添加自定义帖子类型和分类:

function company_post_type() {
    
    $labels = array(
        'name' => _x('Company', 'Post Type General Name', 'text'),
    );
    
    $args = array(
        'labels' => $labels,
        'show_ui' => true,
        'public' => true,
        'publicly_queryable' => true,
        'supports' => array('title', 'editor', 'custom-fields'),
        'taxonomies' => array('country'),
        'query_var' => true,
        'rewrite' => array( 'slug' => '%country%', 'with_front' => false ),
    );
    
    register_post_type('company', $args);
    
    
    $tax_args = array(
        'hierarchical'      => true,
        'public'            => true,
        'show_ui'           => true,
        'show_admin_column' => true,
        'query_var'         => true,
        'show_in_rest'      => true,
    );

    register_taxonomy( 'country', 'company', $tax_args );

}
    
add_action('init', 'company_post_type', 0);

然后我们通过钩子在固定链接上运行一个替换:

function replace_post_link( $post_link, $id = 0 ){
    $post = get_post($id);
    $post_type = get_post_type( $id );
    if ( is_object( $post ) && $post_type == 'company'){
        
        $cat = 'country';
        
        $terms = wp_get_object_terms( $post->ID, $cat );
        if( $terms && !is_wp_error($terms) ){
            return str_replace( '%country%' , $terms[0]->slug , $post_link );
        }
    }
    return $post_link;  
}
add_filter( 'post_type_link', 'replace_post_link', 1, 3 );

更新日期:

在使用这种语法进行重写时,wordpress似乎有一个怪癖,所以你需要在这个术语前面加上一个前缀。

'rewrite' => array( 'slug' => 'country/%country%', 'with_front' => false )

在替换帖子链接中:

return str_replace( 'country/%country%', $terms[0]->slug , $post_link );

那么您的URL将是:

country/%country%/%company_postname%

确保在完成后刷新重写规则,方法是转到:设置〉永久链接并单击“保存更改”

相关问题