個人ブログをWordPressからHugo+Netlifyへ移行した際の知見をまとめる


 これまでは、WordPress+Xserverで個人ブログを運用していました。投稿頻度、アクセス数に対して、年間1万円近くのサーバ運用代はオーバースペックな感じがしたため、ブログをWordPressからGO製の静的サイトジェネレータHugo+Netlifyへと移行しました。 移行の際に得られた知見をまとめておきます。

技術選定

 最近Goばかり書いてるので、Go製って所が結構響きました。テーマ数はWordPressと比較すると多くはないですが、シンプルでかっこいいデザインが多い印象をうけました。他の静的サイトジェネレータを使用したことがないため、実感はないのですが、生成速度が速いという特徴があります。他のエディタを使って、マークダウンでブログ記述できる点も強みです。

 ホスティングサイトの選定に関しては、NetlifyとGithubPages、FirebaseHostingの三者で悩みました。正直どのサービスも素晴らしく、その上無料枠に収まりそうでしたので、選ぶに選びきれないのですが、こちらのサイトを参考にして、Netlifyを使用することにしました。検索流入数を下げたくないので、スピード優先でFirebaseHostingにしようかと迷ったのですが、アフィリエイトを目的としたサイトでもないので、兼ねてから使ってみたいと思っていたNetlifyを採用しました。

Hugoの導入

Mac本体にhugoをインストールします。

$ brew install hugo

プロジェクトを作成したいディレクトリ上で、コマンドを打ち込んでサイトを作成します。

$ hugo new site プロジェクト名

テーマを追加します。 今回はシンプルでかっこいいtaleというテーマを使っています。

$ cd プロジェクト名
$ git init
$ git submodule add https://github.com/EmielH/tale-hugo.git themes/tale

これだけで、サーバは起動します。

$ hugo server -D

テーマのカスタム

 フォントやデザインなど、カスタマイズしたい点が少なからずあると思います。Hugoでは、thems以下を書き換えることなく、見た目を調整できます。

HTMLのカスタム

 themes以下のHTMLファイルを直接編集することはありません。上書きしたいファイルをオーバライドすることでHTMLファイルをカスタムすることができます。例えば、次のような/themes/tale/layouts/partials/single/post-info.htmlから著者情報を取り除きたいとします。

<div class="post-info">
    <span>{{ i18n "writtenBy" }}</span>
    {{- if .Params.Author }}
        {{ .Params.Author }}
    {{- else }}
        {{ .Site.Params.Author }}
    {{- end }}

    {{- if .PublishDate }}
        <br>
        <span>{{ i18n "on" }}&nbsp;</span><time datetime="{{ .PublishDate }}">{{ i18n "publishdate" . }}</time>
    {{- end }}
</div>

layouts以下のディレクトリ構造が同じになるように気をつけながら、/layouts/partials/single/post-info.htmlを作成し次のように編集することで、上書きできます。

<div class="post-info">
  {{- if .PublishDate }}
      <br>
      <time datetime="{{ .PublishDate }}">{{ i18n "publishdate" . }}</time>
  {{- end }}
</div>

CSSのカスタム

 CSSを上書きする際には、/static/css以下に配置します。 例えば,/static/css/costom.cssというファイルを作成し、CSSを上書きしたとします。すると、配置したCSSをHTMLからスタイルシートとして呼び出さなくてはなりません。したがって、同様に/layouts/single/header.htmlを作成して、以下を追記することで、スタイルシートを呼び出すことが可能です。

  <link rel="stylesheet" href="{{ .Site.BaseURL }}css/custom.css" type="text/css" media="all" />

触ったプロパティによっては、トップページにだけCSSが反映されないことがあります。 その時は、/layouts/partials/head.htmlを作成して、直にリンクを書き込むと反映されました。

i18nのカスタム

 標準で日本語対応のja.ymlやja.tomlは用意されていないかもしれません。en.toml等を参考にしてja.yamlを作成したら、/i18n/を作成して配置することで、反映することができます。

CodeSyntax のカスタム

  技術ブログを執筆するなら、Syntax Highlight欲しいですよね! Hugoには、標準でハイライト機能が備わっています。しかし、テーマは自分で設定しないと反映されません。せっかくなら自分のコードをかっこよく表示したいですよね?

まずは、config.tomlに以下を追記します。

  ygmentsCodefences  = true
  pygmentsUseClasses = true

これで、コードをマークダウン記法にしたがって、```で囲うことで、ハイライトが適用されます。

続いて、Syntaxテーマをカスタムしていきます。 私は、長年Monokaiを愛用してるため、Styleをmonokaiとしていますが、選べるテーマは他にたくさん存在します。 次のコマンドを打ち込んでください。

  $ hugo gen chromastyles --style=monokai > syntax.css

ルートディレクトリ以下にsyntax.cssが生成されたはずです。 これを/static/css/に配置します。 CSSのカスタムで触れたのと同様に、ヘッダーにリンクを貼ります。 /layouts/single/header.htmlに以下を追記しておきます。

  <link rel="stylesheet" href="{{ .Site.BaseURL }}css/syntax.css" type="text/css" media="all" />

これで、monokaiが反映されたはずですが、BackgroundColorをQitaと同じ色にしたいので、syntax.cssのbackground-colorを以下のように修正します.

/* Background */ .chroma { color: #f8f8f2; background-color: #364449 }
/* Error */ .chroma .err { color: #960050; background-color: #364449 }

あとは、エディタで以下のように記述すると、うまくテーマが反映されているのがわかるはずです。

```Go
func main(){
fmt.Println(“hello world”)
} ```

ブラウザでは、このように表示されるはずです。

func main(){
  fmt.Println("hello world")
}

```の後に使用している言語を描き忘れないようにしましょう。

ソーシャルアイコン

 ブログ下部にソーシャルアイコンつけたいですよね? FooterをカスタムしてGithubとTwitterアイコンを付与します。 SVG形式のアイコンをフッターに貼り付けます。

layouts/partials/footer.html

<footer>
  <ul class="social-icon">
      <li>
        <a href="https://github.com/takeru56" target="_blank" rel="noopener noreferrer" class="github-icon-link color no-god no-god-prefetch no-dios" title="github-icon">
          <svg class="" role="img" viewBox="0 0 24 24" xmlns="http://www.w3.org/2000/svg"><title>GitHub icon</title><path d="M12 .297c-6.63 0-12 5.373-12 12 0 5.303 3.438 9.8 8.205 11.385.6.113.82-.258.82-.577 0-.285-.01-1.04-.015-2.04-3.338.724-4.042-1.61-4.042-1.61C4.422 18.07 3.633 17.7 3.633 17.7c-1.087-.744.084-.729.084-.729 1.205.084 1.838 1.236 1.838 1.236 1.07 1.835 2.809 1.305 3.495.998.108-.776.417-1.305.76-1.605-2.665-.3-5.466-1.332-5.466-5.93 0-1.31.465-2.38 1.235-3.22-.135-.303-.54-1.523.105-3.176 0 0 1.005-.322 3.3 1.23.96-.267 1.98-.399 3-.405 1.02.006 2.04.138 3 .405 2.28-1.552 3.285-1.23 3.285-1.23.645 1.653.24 2.873.12 3.176.765.84 1.23 1.91 1.23 3.22 0 4.61-2.805 5.625-5.475 5.92.42.36.81 1.096.81 2.22 0 1.606-.015 2.896-.015 3.286 0 .315.21.69.825.57C20.565 22.092 24 17.592 24 12.297c0-6.627-5.373-12-12-12"></path></svg>
      </a>
      </li>
      <li>
        <a href="https://twitter.com/tanaken56" target="_blank" rel="noopener noreferrer" class="twitter-icon-link color no-god no-god-prefetch no-dios" title="twitter-icon">
          <svg class="" role="img" viewBox="0 0 24 24" xmlns="http://www.w3.org/2000/svg"><title>Twitter icon</title><path d="M23.954 4.569c-.885.389-1.83.654-2.825.775 1.014-.611 1.794-1.574 2.163-2.723-.951.555-2.005.959-3.127 1.184-.896-.959-2.173-1.559-3.591-1.559-2.717 0-4.92 2.203-4.92 4.917 0 .39.045.765.127 1.124C7.691 8.094 4.066 6.13 1.64 3.161c-.427.722-.666 1.561-.666 2.475 0 1.71.87 3.213 2.188 4.096-.807-.026-1.566-.248-2.228-.616v.061c0 2.385 1.693 4.374 3.946 4.827-.413.111-.849.171-1.296.171-.314 0-.615-.03-.916-.086.631 1.953 2.445 3.377 4.604 3.417-1.68 1.319-3.809 2.105-6.102 2.105-.39 0-.779-.023-1.17-.067 2.189 1.394 4.768 2.209 7.557 2.209 9.054 0 13.999-7.496 13.999-13.986 0-.209 0-.42-.015-.63.961-.689 1.8-1.56 2.46-2.548l-.047-.02z"></path></svg>
        </a>
    </li>
  </ul>
  <span>
  &copy; <time datetime="{{ now }}">{{ now.Format "2006" }}</time> {{ .Site.Author.name }}.me{{ i18n "generator" | safeHTML }}
  </span>
</footer>

/static/css/custom.css

/*================================*
               footer
=================================*/
.social-icon {
  padding: 0 5px;
  list-style-type: none;
  text-align: center;
}

.social-icon > li {
  width: 0px;
  display: inline-block;
  width: 50px;
}

li > a > svg {
  height: 30px;
  cursor: pointer;
}

こんな感じになります。

Netlifyへデプロイ

 Netlifyへのデプロイは本当にあっという間でした。プロジェクトをリモートリポジトリにプッシュしてNetlifyと連携するだけです。会員登録の5分後にはデプロイが完了していました。NetlifyのUIが洗練されているため、指示に従えば、迷うことはないでしょう。ただ一つ注意するとしたら、Hugoのバージョンを指定する箇所です。デプロイの際にバージョンを指定する箇所があるのですが、デフォルトだと少し古いバージョンをさしているため、ローカルのバージョンを確認した上で、手動で一致させる必要がありそうです。

WordPressのデータを移行

 WordPressのコンテンツをMarkDownに変換してくれるツールをオープンソースで作成してくれていく方がいたので、ありがたく使わせていただきました。これです→ SchumacherFM/wordpress-to-hugo-exporter

まずGithubからzip形式でダウンロードします。 これをWordPressのプラグイン > プラグインの追加 からzip形式でアップロードします。

完了したら、ツールタブ > Export to Hugoを選択すると、これまで投稿したWordPressのコンテンツがマークダウン形式に変換されてzip形式でダウンロードされます。

あとは、これらをcontent以下に配置すれば、苦労することなく記事を引き継ぐことが可能です。写真のサイズなど少し修正すべき箇所は見当たります。

ひとまずアクセス数の多かった10記事を修正てアップしました。

ドメインの移行

 お名前.comにドメインを登録します。 Custom domainsのCheck DNS configurationの欄にしたがってDNSの設定をしていきます。 私は、お名前.comを利用してドメインを取得しました。以下の記事が参考になりました。

【Netlify】カスタムドメインを設定する

NetlifyとGithubで独自ドメインのサイトをHTTPS化したメモ

反映まで、数十分かかります。

SEOについて

 SEOについては、あまり詳しくありませんが、WordPressから移行してきた記事のURL構造が変わらないように意識しました。アクセス数の推移は今後注目していきます。

まとめ

 移行で週末を丸々使ってしまいましたが、引き締まっていてカッコいいブログになったので、かなり満足度が高いです。個人ブログの所有は記事執筆のモチベーションにもなるのでかなり良いですね!!また、Qitaとブログの使い分けが未だ自分の中で確立されていませんが、2019年は、Qitaには簡単なメモ書き、ブログにはそれなりのボリュームになりそうな記事を執筆するという使い分けでひとまず進めていきたいと考えています。皆さんもHugoとNetlifyでブログを始めてみてはいかがでしょうか!

comments powered by Disqus