htaccessにて
Redirect permanent /tag/ http://example.com/taxonomy/
とかそんな感じ?
あう;;
書いてるうちにかぶった。ごめんなさい>jim912さん
トピック投稿者
poem
(@poem)
素晴らしいです。さっそく試してみます。jim912さん、kvexさん、ありがとうございました!
トピック投稿者
poem
(@poem)
これをRedirectMatchでhtaccessに反映させようと悩んでいたところで、うっかり最初の相談内容を間違えていたことに気づいてしまったのですが、
今回の状況は、正しくはタグで管理していた「一部を」カスタムタクソノミーで管理に変更、でした。ですのでまるごと無条件にリダイレクトではありません。それと個別のシングルページではなくタグアーカイブとタクソノミーアーカイブの話でした。つまり
旧URL /tag/abc/
↓
新URL /(taxonomy)/abc/ または /tag/abc/
をどうリダイレクトすればよいか?でした。具体的には
旧URL /tag/芥川龍之介/
↓
新URL /writer/芥川龍之介/ であったり(writer部分は複数種類)
旧URL /tag/小説/
↓
新URL /tag/小説/
とそのまま残っているものがあります。
ですので、前者の場合に限りリダイレクト、後者の場合にはそのままというようにしたいのですが可能でしょうか。
- URL に /tag/ が含まれる場合 /tag/ 以下のスラッグ部分を抜き出す
- 抜き出したスラッグの term_id を調べる
- 調べた term_id のタクソノミを調べる
- 調べたタクソノミが、タグ(post_tag)以外の場合
- タクソノミの rewrite slug を調べる
- URLに、/page/2 やクエリ(?***=*** など)が含まれていないか調べる
- URLを整形してリダイレクト
という順序で行えば可能かと思います。
/tag/ が含まれる全ての URL に対して検証を行うので、リダイレクトの必要がないタグ(post_tag)で管理しているものも含め、その都度 WP を起動して、データベースに問い合わせをする必要があります。
カスタムタクソノミー管理に変更したものが数百個に及ぶ場合は別として、変更したものを抽出し、jim912さん、kvexさんが提示した方法(.htaccess)での制御の方がいいのではないかと思います。(面倒ですが)
get_terms() で .htaccess 用に書き出し、それをコピペすれば手間が省ける気がします。
Redirect permanent /tag/aaa/ http://example.com/writer/aaa/
これを変更した分だけ繰り返す。
トピック投稿者
poem
(@poem)
LVP8さん、ありがとうございます。
しかしわたしのレベル的についていけてないです…
タグ管理からカスタムタクソノミー管理に変更したものは確実に百以上はあるので、大変な作業になりそうです。
ちなみにこれらはその都度データベースに問い合わせとありますが、サイトのパフォーマンスに影響はあるのでしょうか?
タグのアーカイブページは、質問の最初で /tag/abc/xxx.html と記述されて、その後 /tag/abc/ になっていますがどちらが正しいですか?
例えば「aaa」というタグの場合、アーカイブページのURL はどんな形式になっていますか?
example.com/tag/aaa/
ですか? また、最後にスラッシュは付けてますか? あるいは、
example.com/archive/tag/aaa/
のように何らかの接続語がつきますか? それとも、最後に .html がつく(?)のですか?
example.com/tag/abc/xxx.html
トピック投稿者
poem
(@poem)
LVP8様、
タグのアーカイブは、
/tag/abc
が正しいです。
aaaというタグの場合、アーカイブページは
/tag/aaa
となります。最後にスラッシュは付きません。
また、仮に「publisher」というタクソノミーも
/publisher/新潮社
のようになります。
「小説」「新潮社」「芥川龍之介」をタグで管理していたのを、小説はそのままタグで、新潮社をpublisher、芥川龍之介をwriterという名称のカスタムタクソノミーにそれぞれ変更したということになります。
functions.php に以下のコードを
function new_taxonomy_redirect() {
if ( strpos($_SERVER['REQUEST_URI'], '/tag/') === false )
return;
global $wpdb;
$slug = explode( '/', parse_url($_SERVER['REQUEST_URI'], PHP_URL_PATH) );
$tid = $wpdb->get_var("SELECT term_id FROM $wpdb->terms WHERE slug = '$slug[2]'");
if ( $tid ) {
$tax = $wpdb->get_var("SELECT taxonomy FROM $wpdb->term_taxonomy WHERE term_id = $tid");
if ( $tax != 'post_tag' ) {
$red = get_option('siteurl') . '/';
$red .= get_taxonomy($tax)->rewrite['slug'] . '/' . $slug[2];
$red .= ( isset($slug[3]) ) ? str_replace('/tag/' . $slug[2], '', $_SERVER['REQUEST_URI']) : '';
wp_redirect( $red, 301 );
}
}
}
add_filter('wp', 'new_taxonomy_redirect');
簡単な検証はしていますが…
- 必要のない余分な処理をしている可能性があります。
- もっと単純にWPの関数を利用して実現できるかもしれません。
- wp にフックさせていますが、これが適切かどうかは疑問です。
- 少なからずサイトのパフォーマンスに影響(悪い)を及ぼします。
というのをご理解ください。
なお、もしこれでpoemさんの希望通りになったとしても、コードに対する修正など、他の方からの意見を数日程度待って上で「解決済み」にしていただければと思います。
トピック投稿者
poem
(@poem)
LVP8様、わざわざありがとうございます。
今同時にサイトのパフォーマンス最適化も行おうと考えています。ですので、少しでも悪影響を及ぼすことについては慎重になっています。
もう少し考えますが、場合によっては旧URLはすべてトップページにリダイレクトさせるか、あるいはもうそのまま404にしておくかにしようと思います。
このトピックがほかのどなたかの参考になれば幸いです。
ありがとうございました。