プラグインなしで多言語サイト(英語サイトなど)の作り方

WordPressを利用して日本語サイトと同様の内容で英語版サイト(多言語サイト)も作る場合の良い方法、注意点などをお伝えします。プラグインは重くなりバグが生じやすいので使わないほうがよいでしょう。
ディレクトリで分ける場合の注意点
プラグインを利用するかどうかに関わらず、まず決めるべきなのが、日本語サイトと英語サイトのどちらをトップページにするかです。
どちらもトップページがあるんですけど、と思うかもしれませんが、Googleはどちらかしかトップページとして見てくれません。
https://www.example.com/
https://www.example.com/jp/
こうすれば、英語サイトがトップページです。
日本語サイトのトップページは、英語サイトの直下にある1ページとして見られてしまいます。それで何が問題かというと、会社名で検索して1位に表示されたときに、最近はGoogleで直下の階層のページが表示されるようになっていると思います。これが、日本語サイト側ではそうならなくなる、ということがあります。特にこれを問題視しないのならばそれほど気にする必要もありません。
英語用のテンプレートファイルを作る
以下3種類のテンプレートファイルを作ります(カスタム投稿タイプ利用の場合は後述します)。header.phpとfooter.phpはそもそも日本語でも存在しない、ということがもしあれば必要ないです(そんなことはないかと思いますが一応)。
- header-en.php
- page-en.php
- footer-en.php
header-en.phpでは、<html lang="en">
とすることをお忘れなく。
そして、page-en.phpのファイルの先頭に、
<?php /* Template Name: page-en */ ?>
と記述してください。functions.php内に記述しても問題はありません。
この記述により、WordPressの機能で、後述する箇所でテンプレートとして選べるようになります。
また、header-en.phpとfooter-en.phpを以下記述によりpage-en.phpから読み込みます(このあたりは説明なしでもできるくらいのWordPressに対する知識がないと、さすがに厳しいかもしれませんが)。
<?php get_header('en'); ?>
<?php get_footer('en'); ?>
英語サイトのトップページの位置づけのページを作る
「固定ページ」で、スラッグ名「en」(※)としてページを作ります。
また、テンプレートのところで先述のpage-en.phpのファイルの記述により「page-en」というテンプレートが選べるようになっているので、それを選びます。
※ ディレクトリは「en」が良い、ということはありませんがHTMLの言語宣言の記述方法も「en」ですし、「en」が一般的だと思います。日本は「ja」も見ますが、「jp」の方が一般的だと思われます。

英語のトップページ以外のページを作る
例えば日本語のサイトで
https://www.example.com/about/
というページがあるとします。
この場合、英語サイトでは
https://www.example.com/en/about/
とする、というのは先に述べた通りですが、このページの作り方を例に説明します。
テンプレートを先ほどと同じように「page-en」を選択、さらに親ページについて、英語のトップページの位置づけのページを選択します。
そして、スラッグ名を「about」にします。
通常、固定ページで他に使われているスラッグ名はURLが同じになってしまうので当然使えないのですが、テンプレートのところで、先ほどと同じように「page-en」を選ぶことでディレクトリが
となり、それに続くスラッグ名を「about」とできるようになります。
通常、固定ページで他に使われているスラッグ名はURLが同じになってしまうので当然使えないのですが、テンプレートのところで、先ほどと同じように「page-en」を選ぶことでディレクトリが
となり、それに続くスラッグ名を「about」とできるようになります。

カスタム投稿タイプの場合
news
というカスタム投稿タイプの場合を例に、カスタム投稿タイプの場合を説明します。
この場合、single-news-en.php
というテンプレートファイルを作成します。
固定ページの場合は、次のようにファイルの先頭に記述しました。
<?php /* Template Name: page-en */ ?>
カスタム投稿タイプの場合は次のように記述します。
<?php
/*
Template Name: single-news-en
Template Post Type: news
*/
?>
固定ページの場合と同様、functions.php内への記述でも問題ありません。この記述により、投稿ページ編集画面でテンプレートとして選べるようになります。固定ページの場合と同様に、ヘッダーとフッターは次の記述により英語用のファイルをsingle-news-en.php
の中で読み込みます。
<?php get_header('en'); ?>
<?php get_footer('en'); ?>
また、newsのカスタム投稿タイプについて、次の記述により'hierarchical'
をtrue
にし、'supports'
に'page-attributes'
を設定することで親階層が作れるようにします。
'hierarchical' => true,
'supports' => array('title', 'editor', 'page-attributes'),
これで、enというスラッグ名の投稿を1つ作り、その投稿を親ページに設定すれば次のように、同一のカスタム投稿タイプを利用して、/en/をディレクトリとして持たせつつ、同一のスラッグ名で投稿ができるようになります。
https://www.example.com/news/news-01/
https://www.example.com/news/en/news-01/
なお、newsとは別にnews-enのように英語投稿用のカスタム投稿タイプを作るという手もあります。
https://www.example.com/news/news-01/
https://www.example.com/news-en/news-01/
次の記述によりnews-enの前に/en/のディレクトリを設けることも可能です。
'rewrite' => array( 'slug' => 'en/news-en' ),
https://www.example.com/en/news-en/news-01/
こうする場合、同一投稿内ではなくなるので、記事の複製がしづらくなるというデメリットがあります。
さらに、後述する言語切替スイッチのプログラミングは、/en/
を取るということに加えて、-en
を取るという内容にする必要があります。/en/というディレクトリを意図せず設けてしまうリスクはないですが、-enという文字列は生まれやすいので、推奨はしないのですが、一応選択肢としてお示ししました。
hreflang属性の設定
hreflang属性は、そのページと同等の別言語のページのURLを検索エンジンに伝える役割があり、次のように書きます。
<link rel="alternate" hreflang="ja" href="https://www/example.com/ja/">
<link rel="alternate" hreflang="en" href="https://www.example.com/en/">
<link rel="alternate" hreflang="x-default" href="https://www.example.com/ja/">
そのページの言語とURLの記載と、デフォルトの言語とそのURLも記載する必要があるため、例えば日英の2言語あるサイトの場合は上記のように3つの記述が必要となり、日英中の3種類の言語があるサイトの場合は4つの記述が必要となります。
x-default
で指定したサイトは、どの言語にも属さない国のユーザーが検索したときに表示されるページとなります。
言語切替スイッチの設け方
言語切替スイッチには、JavaScritptを使います。
let url = location.href;
const dir = url.split("/").filter( e =>; Boolean(e)); //URLを/で分割して配列に格納
const lastDir = dir.pop(); //分割したURLの最後の部分を取り出し
const beforeDomain = 'http://ドメイン名/';
const afterDomain = url.replace( beforeDomain , '' );
//スイッチの見た目について、スイッチ押下前に変更が必要な場合の記述(不要なら消す)
if ( url.match(new RegExp('/en/')) ) {
//英語サイトでの見た目のための処理
} else {
//日本語サイトでの見た目のための処理
}
document.getElementById('lang-sw').addEventListener('click', function() {
//ページ内にページ内リンクが設けられている場合を考慮して、URLに#から始まる記述がある場合にその部分を削除
if (url.match('#')) {
url.substring(0, url.indexOf('#'));
}
//スタイルの見た目について、スイッチ押下後、リンク先に飛ぶ前に変更が必要な場合の処理
// URLに「/en/」が含まれる場合に、「/en/」を取ることで日本語サイトを表示
if ( url.match(new RegExp('/en/')) ){
const url_ja = url.replace('/en/', '/');
location.href = url_ja;
// URLに「/en/」が含まれない場合は日本語サイトのため、
//トップページと、そうでない場合で条件分岐してURLを英語サイトのものに変更
} else {
if ( url == beforeDomain ) {
location.href = url + 'en/';
} else {
url = url.replace(lastDir + '/' , '')
location.href = url + 'en/' + lastDir + '/';
}
}
}, false);
この記述はこちらの記事で解説しておりますので、よろしければご参照ください。
まとめ
英語サイトの作り方は以上です。ページ数がものすごく多いサイトの場合は、多少面倒な部分もあるかもしれませんが、そうであったとしても、プラグインを用いるデメリットを考えると、私はこうやって作る方が良いのではないかと思っています。