loading...
Cover image for Jekyll Do's and Don'ts

Jekyll Do's and Don'ts

jmau111 profile image Julien Maury Updated on ・3 min read

Jekyll is a clever generator. Unfortunately, there are bad practices and you should avoid them.

Use inheritance

Jekyll comes with a layout feature. To create a custom layout create a file, e.g custom-layout.html in the _layouts folder and call it in the front matter of your markdown file :

---
title: "My post"
layout: custom-layout
lang: en
---
Enter fullscreen mode Exit fullscreen mode

The front matter is everything set between triple-dashed lines at the beginning of your markdown file.

However, it's a good practice to inherit from a default layout in your custom layout.

In the _layouts folder create a default.html file:

<!DOCTYPE html>
<html lang="{{ page.lang }}">
  <body>
    <div class="container">
      {{ content }}
    </div>
  </body>
</html>
Enter fullscreen mode Exit fullscreen mode

This way, you can inherit this global structure in all custom layouts:

---
layout: default
---
<h1>{{ page.title }}</h1>
<!-- other code here e.g custom loops -->
Enter fullscreen mode Exit fullscreen mode

Besides, I recommend you not make specific includes for header and footer in default.html.

Even if some CMS such as WordPress use includes for header and footer, this is not the best pattern in the world.

Inheritance prevents bad code duplication and allows for easy maintenance. It is kinda the same logic in other high-level templating languages such as Twig.

"Where" is better than "if"

Most of the time, using loops and if conditions is totally palatable, but there are tricky situations.

For example, the following code is bad:

{% for post in site.posts %}
  {% if page.lang == post.lang %}
  <!-- custom code for each row -->
  {% endif %}
{% endfor %}
Enter fullscreen mode Exit fullscreen mode

Here is a better one:

{% assign posts = site.posts | where: "lang", page.lang %}
{% for post in posts %}
  <!-- custom code for each row -->
{% endfor %}
Enter fullscreen mode Exit fullscreen mode

In both cases, we display posts in the same lang. The first approach makes you loop through all posts whereas the second approach allows for fine selecting posts even before iterating.

Indeed, you can combine multiple where conditions.

Don't put everything in _config.yml

The _config.yml file is used for global settings such as:

  • the list of plugins
  • the declaration of custom collections
  • the name of main folders (layouts, includes, sass, plugins, data, etc)

Everything you set in this file is globally accessible so it's pretty tempting to put all the things here.

For example, you can set foo this way:

foo: bar
Enter fullscreen mode Exit fullscreen mode

and then call foo in templates to display bar:

<!-- displays "bar" -->
{{ site.foo }}
Enter fullscreen mode Exit fullscreen mode

However, there are some caveats with this approach:

  • everytime you need to change/add data, you have to stop/relaunch jekyll
  • the config file becomes fat and less readable

Instead of doing that, create a _data folder and start organizing things (you can even define subfolders).

For example, in _data/social.yml:

linkedin_username: julienmaury73
github_username: jmau111
Enter fullscreen mode Exit fullscreen mode

And in your template:

<!-- displays "julienmaury73" -->
{{ site.data.social.linkedin_username }}
Enter fullscreen mode Exit fullscreen mode

Don't use posts or pages for everything and anything

The built-in collection posts is great for blog posts, news, or contents that must be chronologically ordered.

The built-in collection pages is great for individual and unrelated pages e.g your contact page.

What if you want to group non-chronological contents, use custom collections.

Wrap up

To make the most of Jekyll, just follow the right patterns.

Posted on by:

jmau111 profile

Julien Maury

@jmau111

Practise what you preach.

Discussion

pic
Editor guide