カスタム投稿のパーマリンク

カスタム投稿のパーマリンク

企業系ホームページを作っていると、固定ページのURLにぶら下げる形で投稿を追加したいことがある。

固定ページで簡単な説明を書いて、その下に記事一覧を表示する。

その場合、固定ページのスラッグと投稿のスラッグを同じにするのだが、そう単純には行かない。

特にカスタム投稿の場合。

標準の「投稿」を「お知らせ」記事、カスタム投稿を追加して「ブログ」記事。

その逆の場合もある。

 

やりたいこと

今回は、「投稿」を「お知らせ」、カスタム投稿を「ブログ」として作る。

固定ページ
http://sample.com/blog

個別記事ページ
http://sample.com/blog/123 (「123」は記事ID)

タクソノミー(カテゴリー)ページ
http://sample.com/blog/category/abc (「abc」はタクソノミーのスラッグ)

アーカイブページ
http://sample.com/blog/date/2018/5 (「2018」は年、「5」が月)

こんな感じの仕上がりにする。

なお、「投稿」を「お知らせ」とするため、パーマリンク設定は

http://sample.com/information/%post_id%

としている。

また、固定ページとして

http://sample.com/information と http://sample.com/blog

を作っている。

カスタム投稿を追加する

カスタム投稿を追加する場合、functions.php に以下のコードを追加する。

	function register_post_type_and_taxonomy() {
	// カスタム投稿
	register_post_type(
		'blog_item',
		array(
			'labels' => array(
                            'name' => __('ブログ'),
                            'all_items'=> __('ブログ一覧'),
                            'add_new' => __('ブログを追加する'),
                            'add_new_item' => __('ブログの追加'),
                            'edit_item' => __('ブログの編集'),
                            'singular_name' => __('ブログタイプ'),
                            'new_item' => __('新しいブログ'),
                            'view_item' => __('ブログを見る'),
                            'search_items' => __('ブログを探す'),
                            'not_found' =>  __('ブログはありません'),
                            'not_found_in_trash' => __('ゴミ箱にブログはありません'),
                            'parent_item_colon' => ''
						),
			'public' => true,
			'hierarchical' => false,
            'has_archive' => true,
            'menu_position' => 4,
			'supports' => array(
							'title',
							'editor',
							'excerpt',
							'custom-fields',
							'thumbnail',
							'page-attributes'
						),
            'rewrite' => array('slug'=>'blog', 'with_front' => false ),
		)
	);

	// カスタムタクソノミー
	register_taxonomy(
		'blog_type',
		'blog_item',
		array(
			'labels' => array(
							'name' => 'ブログカテゴリー',
							'add_new_item' => 'ブログカテゴリーを追加',
							'edit_item' => 'ブログカテゴリーの編集',
						),
			'public'=>true,
			'hierarchical' => true,
			'show_admin_column' => true,
            'rewrite' => array('slug'=>'blog/category', 'with_front' => false ),
		)
	);

}
add_action('init','register_post_type_and_taxonomy');

ここでポイントになるのは、カスタム投稿のスラッグを「blog_item」(4行目)としているところ。

固定ページのスラッグと重複しないように名付ける必要がる。

もう1つのポイントが

'rewrite' => array('slug'=>'blog', 'with_front' => false )

だ。(32行目)

rewiteでスラッグを「blog」にする。

with_fronはをtrueにすると

http://sample.com/information/blog/

となってしまうので、falseにする。

with_fronをかんたんに説明すると「ベースとなるパーマリンクを引き継ぐかどうか」ということ。

URLを変更する

上記の「カスタム投稿を追加する」で設定した内容は、あくまでもルール決めをしただけで、実際に動作はしない。

そこで、URLをリライトする必要がある。

function prefix_movie_rewrite_rule() {

    // ブログカテゴリー
    add_rewrite_rule('blog/category/([^/]+)/?$', 'index.php?blog_type=$matches[1]', 'top');

    // ブログ年別
    add_rewrite_rule('blog/date/([0-9]{4})/?$', 'index.php?post_type=blog_item&year=$matches[1]', 'top');

    // ブログ月別
    add_rewrite_rule('blog/date/([0-9]{4})/([0-9]{2})/?$', 'index.php?post_type=blog_item&year=$matches[1]&month=$matches[2]', 'top');

    // ブログ(個別記事)
    add_rewrite_rule('blog/([0-9]+)/?$', 'index.php?post_type=blog_item&p=$matches[1]', 'top');

    // ブログ(固定ページ)
    add_rewrite_rule('blog/?$', 'index.php?pagename=blog', 'top');

}
add_action( 'init', 'prefix_movie_rewrite_rule' );

これをfunctions.php に追加することで、目標としていたURLで動作するようになる。

忘れていけないのは、上記コードを追加したあとに、パーマリンク設定を保存すること。

何も変更していなくても、「変更を保存」ボタンを押すこと。

 

プラグインの力を借りる

基本的にプラグインは使いたくないのだが、ここから先は面倒なのでプラグインの力をお借りします。

と言うのも、wp_get_archivesで日別アーカイブの一覧を出力すると、カスタム投稿のパーマリンクが

http://sample.com/information/date/2018/5?post_type=blog_item

となるのだ。

これを回避するには、日別アーカイブを自力で作るしかない。面倒だ。

そこで登場するのが「Custom Post Type Permalinks」プラグイン。

こいつをインストールすることで、wp_get_archivesが出力するパーマリンクを

http://sample.com/blog/date/2018/5

にすることができる。

日本語翻訳済でわかりやす。ありがとう。

 

どのテンプレートが使われる?

固定ページ(http://sample.com/blog)

固定ページなので当然、page.phpが摘要される。

固定ページのコンテンツ+記事一覧とすることが一般的なので、page-blog.phpを使用するのが常套手段であろう。

個別記事ページ(http://sample.com/blog/123)

個別記事なので、single.phpが摘要される。

標準の「投稿」を「お知らせ」と使用しているので、「カスタム投稿」の「ブログ」とデザインを変えたい時はsingle-blog_item.phpとする。

注意したいのは、single_information.phpではなくsingle.phpである。あくまでも「お知らせ」は標準の投稿だからだ。

そして「カスタム投稿」はsingle-blogphpではなく、single-blog_item.phpだ。

register_post_type_and_taxonomyでカスタム投稿を追加したときのスラッグになることに注意。

タクソノミーページ(http://sample.com/blog/category/abc)

タクソノミーのテンプレートはtaxonomy-blog_type.phpになる。

これもregister_post_type_and_taxonomyでカスタム投稿タイプを追加した時のスラッグになる。

ちなみに標準の投稿のカテゴリーページはcategory.phpが摘要される。

アーカイブページ(http://sample.com/blog/date/2018/5)

標準のアーカイブはarchive.phpなので、カスタム投稿のアーカイブはarchive-information_item.phpとなる。

ここもregister_post_type_and_taxonomyでカスタム投稿を追加したときのスラッグになることに注意。

アーカイブページで「年」「年月」を判別するには、is_year() (年)、is_month()(年月)を使用する。

また、get_query_var(‘year’)で年の値、get_query_var(‘monthnum’)で月の値を取得できる。

 

最後のこだわり

以上で、目的は達成したが、現状ではダッシュボードの記事編集画面に表示されるパーマリンクが

http://sample.com/information/123

となってします。

ユーザーには見えない部分だが、どうせならここも

http://sample.com/blog/123

としたい。

function my_post_type_link( $link, $post ){

    if ('information_item' == $post->post_type ) {
        return home_url( '/information/' . $post->ID );
    } else {
        return $link;
    }
}
add_filter('post_type_link', 'my_post_type_link', 1, 2 );

これをfunctions.php に追加することで、編集画面でも目標のURLとなる。

 

おしまし。

 

WordPressカテゴリの最新記事