web-dev-qa-db-ja.com

投稿から保護者カテゴリーリマークを削除する方法

簡単に言えば、私はこのようなことをしたいのです。

http://example.com/parent-category/child-category/post-name

着替える

http://example.com/child-category/post-name

いくつかの解決策を見つけましたが、それらは完璧ではありません。例えば、私はこのコードを見つけました。

add_filter( 'post_link', 'remove_parent_category', 10, 3 );
function remove_parent_category( $permalink, $post, $leavename )
{
$cats = get_the_category( $post->ID );
if ( $cats ) {
    usort( $cats, '_usort_terms_by_ID' );
    $category = $cats[0]->slug;
    if ( $parent = $cats[0]->parent ) {
        // Find parent categories and replace them in the link
        $parentcats = get_category_parents( $parent, false, '/', true );
        $permalink = str_replace( $parentcats, '', $permalink );
    }
}
return $permalink;
}

Str_replaceのため、カテゴリの名前が似ているとリンクが切れます。好き

http://example.com/myhouse/house/post-title

それは両方のカテゴリーから家を削除します。誰かがこのコードを修正して任意の名前で機能するようにできますか?

1
Recofa

str_replaceまたはpreg_replaceのいずれかを使用すると、ユーザー側での命名規則やメソッドのディレクティブへの強力な作業なしで(リンクされ、ここでパターンについて読むことができます )、あなたはとの問題に遭遇するつもりです

House | My House | New Houseのシナリオ。特に一度スラグを扱っているとき、そしてそれらのナメクジがmyhousenewhouseのようなものであれば。

それから質問は「孫の何?」になり、「投稿が異なる親を持つ複数の子カテゴリにあり、間違った親がその$cats配列の最初の位置にある場合はどうなりますか?」


考えられる解決策:パーマリンクをフィルタリングして親カテゴリを削除します。

以下は、私が上で述べたシナリオのために私の目的のために働くように思われました、そしてそれはstr_-とpreg_ - を完全に置き換えることを避けます。

私はあなたのリンクの例で仮定します:

http://example.com/myhouse/house/post-title

あなたのパーマリンク構造は/%category%/%postname%/です。そしてここでの目標は、パーマリンクをカテゴリファミリーの最も若いメンバーと投稿タイトルに制限することです。そのため、example.com/child-cat/post-title/またはexample.com/grandchild-cat/post-title

最後の2つの値だけを残して、パーマリンクがあることを知っているので、それを解析し、パス部分を配列に展開し、配列エントリを数え、最後と最後から2番目のエントリを保持し、パーマリンクして返してください。

もちろん、子カテゴリを持つ投稿も扱っていることを確認した後に。

このようなものかもしれません:

    add_filter( 'post_link', 'remove_parent_category', 10, 3 );
    function remove_parent_category( $permalink, $post, $leavename ) {

         $cats = get_the_category( $post->ID );

         if ( $cats ) {

             foreach ($cats as $cat => $parent) {

               $cat_parent_values[] = $parent->parent; 
             }

             if( array_sum( $cat_parent_values ) > 0 )  {

                 $url_array      = parse_url( $permalink );
                 $url_path       = array_filter( explode( '/', $url_array['path'] ) );
                 $url_path      = array_values($url_path);
                 $url_path_count = count( $url_path );

                 $name_slot      = $url_path_count - 1;  
                 $child_cat_slot = $name_slot - 1;

                 $new_url_path[] = '/'. $url_path[ $child_cat_slot ];
                 $new_url_path[] = '/'. $url_path[ $name_slot ] .'/';

                 $new_permalink  = $url_array['scheme'] .'://'. $url_array['Host'] . $new_url_path[0] . $new_url_path[1];

             }//end if sum > 0
         }//end if $cats

        return $new_permalink;
    }  

それの予備テストは私の側ではフレッシュインストールでうまくいくようで、str_replaceなしでHouse | MyHouseテストに合格します。私はそれが改善されることができると確信しています、そしてあなたはそれを本当にテストし、それを壊すような他の問題やシナリオがないことを確かめなければならないでしょう。パーマリンクをフィルタリングすることを含まない、より良いアプローチが完全にあるかもしれませんが、私は手にすることが確実ではありません。

説明:

最初に get_the_category を使います。あなたはすでにカテゴリオブジェクトの配列を取得しなければなりません。いくつかあることを確認したら、次にarray as $key => $valueのforeachループを実行して、各値を新しい配列にキャストします。

Wordpressはカテゴリのparentの値をidとして格納し、そのidは(int)です。親がいない場合は0を取得します。したがって、新しい配列のすべての値の合計が0よりも大きい場合、その中に少なくとも1つの親カテゴリがあります。そしてそれは、削除したいパーマリンクの中に少なくとも1つのパス部分があることを意味するので、続けます。

phpの parse_url'scheme' => 'http', 'Host' => 'example.com', 'path' => '/category/child-cat/postname/'の配列()を返します。

we explode() that、$url_array、それぞれの/はそれぞれのセクションの配列を与えます。空の配列値もあるので、array_filterでラップし、うまくいけばそれをクリーンアップして$url_pathに設定します。 [array_values()][5]を使って、array_filterによって削除された欠けている数字キーをきれいにし、3つの項目の配列の中のキーに[0],[1],[2]を与えることができます。

前述したように、投稿の名前は最後であると仮定しているので、フィルタリングされ再評価された配列ではcount()を使用してこの配列に含まれるキーの数を調べます。これは、配列が[0]から始まるためです。それからthatから1を引くと私たちの "最年少カテゴリー"ができます。

それから、私たちの$ url_arrayと、保持したい投稿名とカテゴリーのパス部分を使って、パーマリンクを元に戻します。

そしてそれをpost_linkフィルタに返します。


あなたの例で気づいた他の可能な問題:

get_the_category()はカテゴリオブジェクトの配列を返しますが、そのusort()がそれらをIDで並べることを目的としている場合、次に既存のカテゴリの親になるカテゴリを作成する場合は最初にその配列の位置$cats[0]は、必ずしも親カテゴリとは限りません。 (_usort_terms_by_idの性質を誤解していない限り)。

if($parent = $cats[0]->parent)$parent変数に何を設定しようとしているのかも不明です。

1
hwl