WordPressのナビゲーションメニューで非公開の記事を自動的に非表示にする方法

WordPressのナビゲーションメニューは、管理画面上からドラッグ&ドロップで設定できて便利なのですが、非公開設定となっている投稿や固定ページなどが含まれている場合でも、表示の調整は行ってくれず全てが表示されてしまいます。このため、閲覧権限がないユーザーが非公開記事のメニューをクリックした場合「リンク切れか?」と思われてしまうことになります。

これでは、ユーザーエクスペリエンスもだだ下がりになってしまうので、メニューの記事が非公開の場合、自動的に表示されないようにしてみましょう。

ナビゲーションメニューには、wp_nav_menu_objects という、登録されたメニューをフィルタリングできるフックが存在しています。

今回は、ここで

  • メニューが投稿タイプかどうかをチェック
  • メニューの記事が非公開で、なおかつユーザーの閲覧権限がない場合、メニューを削除し、削除済みリストにメニューのIDを保持
  • 子メニューだけが表示されることを防ぐため、メニューの親ID(menu_item_parent)が、削除済みリストに含まれていた場合も、メニューを削除

という処理を行います。
具体的なコードが、CODE 1

CODE 1

function remove_private_post_menu( $sorted_menu_items ) {
	$unset_ids = array();
	foreach ( $sorted_menu_items as $key => $item ) {
		if ( $item->type == 'post_type' ) {
			$post = get_post( $item->object_id );
			$post_type = get_post_type_object( $post->post_type );
			if ( $post->post_status == 'private' && ! current_user_can( $post_type->cap->read_private_posts ) ) {
				unset( $sorted_menu_items[$key] );
				$unset_ids[] = $item->ID;
				continue;
			}
		}
		if ( in_array( $item->menu_item_parent, $unset_ids ) ) {
			unset( $sorted_menu_items[$key] );
			$unset_ids[] = $item->ID;
		}
	}
	return $sorted_menu_items;
}
add_filter( 'wp_nav_menu_objects', 'remove_private_post_menu' );

テーマの functions.php や プラグインに記述していただければ、閲覧権限がないユーザーの場合、メニューが子メニューごとキレイさっぱり表示されなくなります。

ログイン機構を持ったサイトなどで、ユーザーの状況次第でメニューの表示を変えることにも応用が利くのではないでしょうか。

コメントを残す

メールアドレスが公開されることはありません。 * が付いている欄は必須項目です