Hugo のテーマを作ってみます 2(Base Templates and Blocks)

前回の記事では、サイトとテーマの骨組みを作成しました。 今回は、 Base Templates and Blocks を使ってみます。

最初に、この記事の通り、サイトとテーマの骨組みを作成しておきます。

環境

  • Hugo Static Site Generator v0.31.1

Base Templates and Blocks

以前はなかったと思うのですが、 Base Templates and Blocks というものがあるみたいです。

Base Template Lookup Order

The lookup order for base templates is as follows:

  1. /layouts/section/<TYPE>-baseof.html
  2. /themes/<THEME>/layouts/section/<TYPE>-baseof.html
  3. /layouts/<TYPE>/baseof.html
  4. /themes/<THEME>/layouts/<TYPE>/baseof.html
  5. /layouts/section/baseof.html
  6. /themes/<THEME>/layouts/section/baseof.html
  7. /layouts/_default/<TYPE>-baseof.html
  8. /themes/<THEME>/layouts/_default/<TYPE>-baseof.html
  9. /layouts/_default/baseof.html
  10. /themes/<THEME>/layouts/_default/baseof.html

Base Templates and Blocks | Hugo

レイアウトの適用の優先度があって、上の方が優先度が高くて、下の方が優先度が低いようです。 サイトのレイアウトが優先されて、テーマのレイアウトは優先されないようです。

Content Sections

Hugo generates a section tree that matches your content.

A Section is a collection of pages that gets defined based on the organization structure under the content/ directory.

By default, all the first-level directories under content/ form their own sections (root sections).

Content Sections | Hugo

section は、記事を保存するディレクトリー (content/) の直下のディレクトリーのことのようです。 content/blog/ というディレクトリーは、 blog セクションになるようです。 section ごとにレイアウトを適用することができるようです。

Content Types

Hugo supports sites with multiple content types and assumes your site will be organized into sections, where each section represents the corresponding type.

Content Types | Hugo

Type は、記事の front matter で指定する Type のようです。 type = "event" (TOML の例) と記述すると、 event という Type になるようです。 Type ごとにもレイアウトを適用することができるようです。

baseof.html

一番優先度の低いレイアウト (themes/<THEME>/layouts/_default/baseof.html) を作成してみます。 テーマとして、このファイルを作成しておけば、記事のページにアクセスしても、記事のリストのページにアクセスしても、トップのページにアクセスしても、他に優先されるレイアウトがなければこのレイアウトで表示してくれることになるようです。

次のような HTML ファイルを作成しました。

<!DOCTYPE html>
<html>
  <head>
    <meta charset="utf-8">
    <title>
      {{ block "title" . }}
        {{/* <!-- Blocks may include default content. --> */}}
        {{ .Site.Title }}
      {{ end }}
    </title>
  </head>
  <body>
    <!-- Code that all your templates share, like a header -->
    {{ block "main" . }}
      <!-- The part of the page that begins to differ between templates -->
    {{ end }}
    {{ block "footer" . }}
      <!-- More shared code, perhaps a footer but that can be overridden if need be in  -->
    {{ end }}
  </body>
</html>

list.html

What is a List Page Template?

A list page template is a template used to render multiple pieces of content in a single HTML page. The exception to this rule is the homepage, which is still a list but has its own dedicated template.

Lists of Content in Hugo | Hugo

記事の一覧を表示するページのレイアウト (themes/<THEME>/layouts/_default/list.html) です。

ベースとなるレイアウト (baseof.html) の {{ block }} を実装(オーバーライド)してみます。

{{ define "main" }}
  <h1>Posts</h1>
  {{ range .Data.Pages }}
    <article>
      <h2>{{ .Title }}</h2>
      {{ .Content }}
    </article>
  {{ end }}
{{ end }}

{{ define }}{{ block }} を実装できるようです。 実装すると、 baseof.html の {{ block }} の部分が list.html の {{ define }} に置き換わって HTML が生成されるようです。

list.html では {{ block "main" }} しか実装していないため、 {{ block "title" }}{{ block "footer" }} は baseof.html の内容がそのまま HTML として生成されるようです。

single.html

Single Page Templates The primary view of content in Hugo is the single view. Hugo will render every Markdown file provided with a corresponding single template.

Single Page Templates | Hugo

記事を表示するページのレイアウト (themes/<THEME>/layouts/_default/single.html) です。

{{ define "title" }}
  {{/* <!-- This will override the default value set in baseof.html; i.e., "{{.Site.Title}}" in the original example--> */}}
  {{ .Title }} &ndash; {{ .Site.Title }}
{{ end }}
{{ define "main" }}
  <h1>{{ .Title }}</h1>
  {{ .Content }}
{{ end }}

こちらは {{ define "title" }} も実装してみました。

content

content/post ディレクトリーに次の 2 つの examples の記事を作成しました。

次のコマンドでダウンロードしました。

$ install -d content/post
$ curl -L -o content/post/hello-hugo.md 'https://raw.githubusercontent.com/gohugoio/hugo/master/examples/blog/content/post/hello-hugo.md'
$ curl -L -o content/post/another-post.md 'https://raw.githubusercontent.com/gohugoio/hugo/master/examples/blog/content/post/another-post.md'

Hugo のサーバーで確認

Hugo のサーバーで確認するために次のコマンドを入力します。

$ hugo -t <THEMENAME> server

記事の一覧を表示するページ

http://localhost:1313/post/ にアクセスします。

すると、テーマで作成した、 baseof.html と list.html のレイアウトが適用されたものが表示されます。

この例だと、記事の内容をすべて一覧に表示してしまっていて、一覧という感じじゃないかもしれません。

記事を表示するページ

次に、 http://localhost:1313/post/hello-hugo/ にアクセスします。

すると、テーマで作成した、 baseof.html と single.html のレイアウトが適用されたものが表示されます。

Ctrl + C で Hugo のサーバーを終了します。

終わり

以前は、 Base Templates はなかったと思います。 そのため、 Partial Templates で、ヘッダーのレイアウトのファイルは <div> タグで終了して、フッターのレイアウトのファイルは </div> タグで開始するような、気持ちの悪い区切り方をしていました。 Base Templates はタグの単位でレイアウトのファイルを区切ることができるので、良さそうに感じました。

今回は、ここまでにします。

参考

7 April 2018 追記

次の記事を書きました。