Create a new project

Run the following commands to setup a new project:

$ mkdir my-website
$ cd my-website
$ npm init
$ npm install --save-dev linkdd/gin#v0.2.1
$ npx gin init .

This should create the following tree:


Website content

In the content/ folder, we will find for example:

Every Markdown file will have a frontmatter header:

---
title: Page title
weight: 0
layout: _default # optional

foo: bar
---

Page content (in markdown)

The content can contain HTML:

---
title: Example
---

<div class="foo">

# Hello in a div

</div>

As well as Twing template directives:

---
title: Example

items:
  - foo
  - bar
  - baz
---

{% for item in page.params.items %}
- {{ item }}
{% endfor %}

NB: Includes are resolved from the templates/shortcodes/ folder, the following example will render the template templates/shortcodes/hello.html in your document:

---
title: Example
---

{% include "hello.html" %}

Website layouts

In a document's frontmatter, if the key layout is specified, Gin will look for templates in the templates/layout/{layout}/ folder. If not specified, the layout _default is assumed.

In the following example, Gin will look for templates in the templates/layout/foo/ folder:

---
title: Example
layout: foo
---

# Hello

There are 3 kinds of documents:

Document type Location in content directory Template
The homepage content/_index.md templates/layouts/{layout}/home.html
A section content/**/_index.md templates/layouts/{layout}/section.html
A single page content/**/*.md templates/layouts/{layout}/single.html

Each document AND template have access to the following data:

classDiagram direction LR class PageTemplateData { +url: string +title: string +params: Object +isHome: boolean +isSection: boolean +children: PageTemplateData[] } class PagesTemplateData { [url: string]: PageTemplateData } class SiteTemplateData { +title: string +description?: string +languageCode?: string +pages: PagesTemplateData +params: Object +data: any } class TemplateData { +content: string +page: PageTemplateData +site: SiteTemplateData } PageTemplateData --> PageTemplateData : children TemplateData --> PageTemplateData : page TemplateData --> SiteTemplateData : site SiteTemplateData --> PagesTemplateData : pages

For example, a section template could look like this:

<html>
  <head>
    <title>{{ site.title }} - {{ page.title }}</title>
  </head>

  <body>
    <nav>
      {% for child in page.children %}
        <a href="{{ child.url }}">{{ child.title }}</a>
      {% endfor %}
    </nav>

    <main>
      {{ content|raw }}
    </main>
  </body>
</html>

NB: Layout templates will resolve templates from the templates/ folder.

One common use case is to have a root template templates/base.html and have your layout templates inherit from it:

templates/base.html

<html>
  <head>
    <title>{{ site.title }} - {{ page.title }}</title>
  </head>
  <body>
    {% block content %}
    {% endblock %}
  </body>
</html>

templates/layouts/_default/home.html

{% extends "base.html" %}

{% block content %}
  <h1>Welcome on my website</h1>

  <main>
    {{ content|raw }}
  </main>
{% endblock %}