
投稿の際には必ずスラッグをつけてスラッグをURLの一部として表示するように設定しています。そのスラッグは重複しないように付けないといけないことになっています。もし重複してもWordPressではそんなときに自動的にスラッグに数字を付けてダブらないようにしてくれるということですが、そうならない場合もあるようでした。
そのため絶対にスラッグの重複は避けたいと思います。もし同じスラッグが存在しているとわかったらその投稿はすぐに別の名前にして、元の投稿を生かすようにとかをする必要があります。
ということでスラッグが重複していたら投稿画面にメッセージを出したり、スラッグを付け忘れていたらそれも教えてくれるようにしてみました。
子テーマのfunctions.phpに書きました
いつものように使っている子テーマのfunctions.phpに書きました。
追加したコードは、
function ryus_slug_check_message() {
global $pagenow;
global $post;
global $wpdb;
$statusName = array();
$statusName['publish'] = '公開済み';
$statusName['pending'] = 'レビュー待ち';
$statusName['draft'] = '下書き';
$statusName['future'] = 'スケジュール済み';
$statusName['private'] = '非公開';
if ($pagenow == 'post.php'){
$slug = _get_post_name($post->ID);
if($slug != ''){
// 同じslugが存在しているかチェックする
$sql = "SELECT * FROM $wpdb->posts WHERE (post_type = 'post' OR post_type = 'page') AND ID != ".$post->ID. " AND post_status != 'trash' AND post_name = '%s'";
$duplicatePosts = array();
$results = $wpdb->get_results(sprintf($sql, $slug));
$link = '<a href="'.site_url().'/post.php?p=%s&preview=true" target="_blank">%s(%s)</a>';
foreach ($results as $value) {
if($value->post_title == ''){
$value->post_title = '(タイトル無し)';
}
$duplicatePosts[] = sprintf($link, $value->ID, $value->post_title, $statusName[$value->post_status]);
}
if (count($duplicatePosts) > 0){
$message = implode('<br />', $duplicatePosts);
echo '<div class="message error"><p>スラッグ「'.$slug.'」が重複しています</p><p>'.$message.'</p></div>';
}
} else {
echo '<div class="message error"><p>スラッグが入っていません!</p></div>';
}
}
}
function _get_post_name($id){
// ページIDからslugを取得
$page = get_page($id);
return $page->post_name;
}
add_action( 'admin_notices','ryus_slug_check_message' );
こんな感じです。
内容をざっくり説明すると、
ryus_slug_check_message という関数で、投稿画面だったときはそのときのスラッグが他の投稿で使われていないかどうかをチェックします。もし使われていたら重複したスラッグを使っている投稿の一覧を表示します。スラッグが空の時はスラッグの入力を促すように、スラッグが入っていません! と表示します。
add_action( 'admin_notices','ryus_slug_check_message' )
admin_noticesというactionで管理画面の上部にメッセージを表示します。
スラッグが重複していたら表示するメッセージ
このコードを入れて、実際にスラッグを重複させて表示してみました。

こんな感じで、重複したスラッグの投稿一覧が表示されます。クリックすると別画面が開いてそれぞれの投稿を確認することができます。
スラッグが入っていなかったら表示するメッセージ

このように表示されるので、スラッグを必ず入れるつもりでblogを書いている場合は便利かと思います(^^)/
まとめ:というか書き込まれないようにしたい(^_^;
このblogを書く前にローカルでテストしていたときは特に問題なく、重複投稿の場合でも後から投稿したものに別の名前が自動的に付いたりしていたので「メッセージが出ればいいや」と思ってました。
しかし、この本番のblogで試してみたところ 既存のblog投稿がテスト投稿に置き換わって しまい、、超焦りました。
本番なのであまり思い切ったテストができないので、どういう場合に重複投稿が名前が変更されずに保存されちゃうのかが分かりません。ということはそもそも「重複したスラッグを指定したときは書き込まれないようにしたい」と思いました。
この関数をさらに進化させて書き込まれないような関数にしていきたいと思っていますm(_ _)m



コメント