NKSSG
NakaKen Static Site Generator

defaultテーマを見てみよう

😐

ここでは、デフォルトテーマの構成を見ていきます。テーマの修正や作成を行うときに、参考にしましょう。

defaultテーマの大まかな構成

default テーマには、いろいろな役割のファイルが含まれています。いつ使われるファイルか、という観点で分けると、おおまかには次の3つに分かれます。

  • ファイル出力のために使うもの
  • new コマンドで使うもの
  • draft コマンドで使うもの

それぞれに使うファイルが異なるので、順番に見ていきます。また、デフォルトで有効となっている子テーマ child についても見ていきます。

ファイル出力のために使うもの

nkssg build などを実行するとき、HTML ファイルを作成するためのテンプレートが必要です。default テーマには、次のようなテンプレートファイルが含まれています。

base

まず、base.html を見てみましょう。これが各テンプレートの最もベースとなるものです(名前の通りです)。

ざっと眺めてみると、html タグがあって、headタグと bodyタグがあります。headタグには、いくつか meta タグがあります。bodyタグには、header、main、footerがあり、ページの大まかな構成が書かれています。

【ざっくりとした構成】
<html>
  <head>
    <meta charset="utf-8" />
  </head>
  <body>
    <header> ~ </header>
    <main> ~ </main>
    <footer> ~ </footer>
  </body>
</html>

ただ、普通の HTMLタグにはないものもたくさんあります。波かっこで囲まれている部分がたくさんありますね。これらの波かっこで囲まれた部分は、Jinja2 の構文です。Jinja2 とは、Python でよく使われるテンプレートエンジンのことです。

まず、import と書かれた部分があります。これは、後に出てくる import フォルダのところで説明します。

block と書かれた部分がいくつか見つかります。この block は、範囲に名前をつけるために使います。block のすぐ後にあるものが、ブロック名です。block は後でまた出てきます。

include もたくさんありますね。これは、他のファイルの中身をひっぱってくるためのものです。例えば、次のように書いている場所があります。

{% include "partials/head/description.html" %}

このように書くと、partials/head/description.html にある内容を持ってくることができます。HTML ファイルの中身を分割して、部品化して使っているわけです。

次のように書かれている部分もあります。

{{ config.site.language }}

これは、値を表示するためのものです。波かっこ2つで囲むと、値の表示を行います。波かっことパーセントで囲むと、制御文となります。

このように、base.htmlでは、他のいろんなところから内容を引っ張ってきて、1つのファイルを作ろうとしています。

ところで、コンテンツのメイン部分であるarticleタグがどうなっているかを見てみましょう。

<article>
  {% block content -%}
  {%- endblock %}
</article>

content という名前の block があるだけで、中身は何もないですね。これでなぜいろんなページでコンテンツが表示されるのかは、おいおいわかってきます。

main

次に、main.htmlを見てみましょう。次のようになっています。

{% extends "base.html" %}

1行だけです。これは、「base.htmlの内容を引き継ぎます」という意味です。main.htmlはこれで終わりです。このファイルの存在意義は後でわかります。

メモ

NKSSG は、特に指定がなければ、この main.html を基準として HTML ページを作ります。そのため、少なくともこのファイルは用意しましょう。

single

次に、single.htmlを見てみます。これは、個別ページ用のテンプレートです。

次の1行から始まっています。

{% extends "main.html" %}

これは、「main.htmlの内容を引き継ぎます」という意味です。main.htmlbase.htmlを引き継いでいたので、結局base.htmlから引き継いだものが反映されます。main.htmlをはさむ意味がないように思うかもしれませんが、このようにしている理由は後でわかります。

ファイルの後半には、次のように書かれている部分があります。

{% block content %}
~
{% endblock %}

base.htmlにもありましたね。blockを後で定義すると、その部分を差し替えることができます。つまり、base.htmlの中の content には何もなかったけれど、single.htmlではここで定義した内容が反映されます。しかも、他の部分はbase.htmlの内容が引き継がれるわけです。

このように、基準となるbase.htmlを作り、それを引き継ぎつつ、差し替えたい場所を定義していく、というやり方でテンプレートを作っていきます。

archive

次に、archive.htmlarchive-section.html です。これらは、アーカイブページ用のテンプレートです。後者がセクションアーカイブ用で、それ以外のアーカイブページは前者が使われます。

これらのファイルを見てみると、single.html と同じように、content block の設定などが入っています。

sitemapと404

defaultテーマには、次の3つのファイルも含まれています。

  • 404.html
  • sitemap.html
  • sitemap.xml

どれも名前から目的はわかるでしょう。1つ目と2つ目は、single.html などと同じように、main.html を拡張して使っています。

3つ目からもわかる通り、xml ファイルも作ることができます。これは、他のファイルの拡張ではなく、一から出力内容の設定を書いています。

メモ

Jinja2 は、HTML に限らず、テキスト形式のファイルであれば、なんでも作れます。default テーマには入っていませんが、csv とか json でデータを書き出すことも可能です。

partialsフォルダ

今までのテンプレートに、たくさん include が出てきていました。今までは呼び出す側でしたが、呼び出される側を見てみましょう。

例えば、base.htmlheadタグ内には、partials/head/description.htmlinclude するという記述がありました。この description.html の中は、次のようになっています。

{% if mypage and mypage.summary -%}
<meta name="description" content="{{ mypage.summary }}" />
{%- elif config.site.site_desc -%}
<meta name="description" content="{{ config.site.site_desc }}" />
{%- endif %}

これは、summary があればそれを使い、なければサイトの詳細を使って、meta タグを書く、という意味です。このように、各パーツごとに部分ファイルを作成しています。もちろん、こんなことはせずに、base.html に全部書いてしまう方法もあります。

Jinja2 は Python で書かれていますが、上の if文を見てもわかる通り、少し文法が異なります。似ていますが違うところも多いので、その都度覚えていきましょう。

importフォルダ

single.htmlには、次のような記述があります。

<p class="top-thumbnail">{{ sc.get_thumb(mypage) }}</p>

このscとは、short-code の略です。import/short-code.htmlに処理内容が定義されています。

このファイルに書いてあるものは、Jinja2 ではマクロと呼ばれます。処理をまとめ、名前を付けて呼び出すことができます。

メモ

WordPress のショートコードと Jinja2 のマクロはまったく別物ですが、default テーマではショートコードと似たような使い方をしようとしています。

マクロの入ったファイルを読み込むには、次のように import しておく必要があります。

{% import "import/short-code.html" as sc %}

もし別の場所に書いたマクロを読み込みたい場合は、次のように書く必要があります。

{% import "ファイル名" as 呼び出し名 %}

こうすると、「呼び出し名.マクロ名()」でマクロを呼び出せるようになります。

newコマンドで使うもの

defaultテーマには、new コマンドで新規記事を作るときに使うテンプレートも入っています。new/new_post.html です。

このファイルの修正の仕方、新しいひな型の追加方法は、次の記事にまとめています。

🐤 新規記事のひな型を作ろう

draftコマンドで使うもの

defaultテーマには、draft コマンドで使うテンプレートも入っています。 draft.html です。

nkssg draft は、指定したファイルだけをプレビューために使います。このとき、他のファイルは更新されません。そのため、サイドバーにあるようなページ一覧やアーカイブ一覧は更新できません。そのため、draft モードでは、更新されないものを省いたテンプレートを適用したほうがいいです。

更新されないものがあってもエラーにならない箇所もありますが、エラーになる場合には draft.html を使いましょう。

子テーマ

子テーマを使うと、親テーマの内容を上書きすることができます。デフォルトでは、child テーマを子テーマにするように設定されています。

child テーマには、すでにmain.htmlが入っています。これはdefaultテーマと同じく、中身は1行だけです。

子テーマと親テーマに同じ名前のファイルがあると、子テーマのほうが優先されます。そこで、例えば子テーマにあるmain.htmlで、次のように書いたとしましょう。

{% block sidebar %}
{% endblock %}

サイドバーの内容を削除してみました。

この状態で、single.html を呼び出したときに何が起こるかを考えてみます。まず、single.htmlは、main.htmlの内容を引き継ぐのでした。このとき、子テーマにmain.htmlがあるので、親テーマにあるものは無視してこちらが読み込まれます。このとき、サイドバーは新しく定義した内容です。さらに、main.htmlbase.htmlを引き継ぎます。これは子テーマにはないので、親テーマのファイルが使われます。サイドバー以外は、親テーマの定義したものが使われます。

つまり、次のように上から順番に処理されていきます。

  • single.html を呼び出す
    • 子テーマにはないので、親テーマのテンプレートを呼び出す
    • テンプレート内で、main.htmlinclude している
  • main.html を呼び出す
    • 子テーマにはあるので、子テーマのテンプレートを呼び出す
    • (サイドバーはなくなっている)
    • テンプレート内で、base.htmlinclude している
  • base.html を呼び出す
    • 子テーマにはないので、親テーマのテンプレートを呼び出す
    • (サイドバー以外はそのまま)

こうすると、親テーマの内容はそのままで、子テーマをいじるだけで中身を変えることができます。もちろん、親テーマをそのままいじることもできますが、親テーマはいじらないもの、子テーマはいじるもの、という分け方をしたほうがきれいだと思います。

次に何をする?

使えるもの Jinjaの文法