This post aims to provide a quick sum-up for anyone who is unfamiliar with Jekyll. To learn more about Jekyll, check the doc & source out.

1st minute: General Overview 267 words

Jekyll is a tool to build static website that exists as merely a directory of files. That said, you can only use it to create websites that don’t have run-time logic in the backend. (such as a simple content-based website or a blog) In other words, it is a web-pages generator.

With a Github acc, anyone can set up his or her Github Page for free with ease. A Github Page is a static website hosted by Github. GitHub Pages™ has built-in support of Jekyll (So just push the code and you’ll have a website).

That doesn’t mean you have to use Jekyll for a Github Page. You can always use some other static site generator to generate the site (e.g. Hakyll) before pushing the repo of generated files (aka static files ready for access).

Keep in mind GitHub Pages™ supports only Jekyll 2.4.0 as of June 2015. To have a local environment for making GitHub Pages™ supporting Jekyll website, you are advised to install Jekyll via The GitHub Pages™ Gem (instead of installing Jekyll separately by yourself). The GitHub Pages™ Gem also includes Jekyll-coffeescript, Jekyll-sass-converter, Liquid, etc. That is to say, GitHub Pages™ will generate a site for you with these components.

To sum up, GitHub Pages™ does not execute server-side code. It helps you generate static website (using Jekyll) if you give it the source code. That is as much as it does, aside from also hosting the static website for you and giving you a super cool github.io subdomain. (You can still use your own domain if you want.)

● ● ●

2nd minute: What you need to know when working with Jekyll 314 words

Jekyll is made in Ruby (with Cucumber). Since all it does is generate static website, there is no Rails in it.Jekyll puts all the pieces (of html, md, textile) you give it together, and that’s all. The way Jekyll works relies mainly on Liquid (a templating language) and YAML Front Matter Block, or Front Matter for short.

Front Matter is the starting session of each file where you put down meta-information in YAML format.

---
layout: default
title: "0a: About "
permalink: /about/
extraClasses: ['aboutPage']
---
<!-- The session on top is Front Matter -->
<div class="archywrap">
<h2> {{site.data.author.bioTitle}}</h2>
{{site.data.author.bio}}
</div>

YAML is like a sister of JSON. YAML to JSON is, syntax-wise, like what Less is to Sass.

For every HTML file you’d be dealing with in Jekyll, it’d either be

  1. an Include File,

  2. a Layout File

  3. a serving file.

Include Files, as its name suggested, are to be included in other files with this one-liner:

{% include includeFileName.html %}

while Layout Files, obvious enough, are the layouts, to be used by other files:

---
layout: layoutFileName
---

Every file can contain multiple Include Files but can use only one Layout File. Each Layout File is located in _layouts/ folder while each Include File is located in _includes/ folder.

A serving file on the other hand can be in any folder except the reserved ones (e.g. _includes/). Normally people put them in the root directory. A serving file will be served by its name (e.g. about.html will be served at http://domainName/about.html) unless you specify the url in Front Matter.

---
permalink: /about
---
#this file would be served at http://domainName/about

Lastly, I would like to introduce 2 very special types of files: Post file and Data file. Post files are located in _posts/ while Data Files in _data/. All Post files of a site can be accessed as an array using the variable site.posts in your Liquid html files, while all Data Files can be accessed as site.data.filename.

You can define your own kinds of Collections files similar to Post files. (E.g. Blogpost files accessed as site.blogpost located in the _blogpost/ folder after you’ve declared it in _config.yml).

● ● ●

3rd minute: on the Liquid templating language 336 words

Liquid is a Templating languages written in Ruby and can be easily extended by exporting methods from your modules to the list of “filters”. If you would like to stick to the Jekyll that is supported by GitHub Pages™, you can’t extend Liquid (or Jekyll) by yourself . That is to say, there would be some limitation on the Liquid that you are working with, data-manipulation-wise. This is why if the website you want to build consists of a lot of data-manipulating, you are advices to use frameworks like Angular to have a better architecture (e.g. MVC) and it would make your life easier too.

There are basically 3 things in Liquid: Variable, Logic Blocks and Filter. Variables defined in Front Matter is accessed as page.variableName, while in /_config.yml it is as site.variableName. A variable can be either a primitive (e.g. an integer), an array, or a object. Pretty standard. Variables can be printed/echoed out as string, much the same way as Handlebar & mustache:

{{site.title}}

Or it can also be assigned using this one-liner:

{% assign catName = "Nyanchan" %}
<p>The cat name is {{catName}}!</p>

You can check if some statement is true before deciding what to do with Conditions Blocks.

{% if site.name == "0a: Arch Here" %}
   This is 0a.io
{% else %}
   You are on some other site.
{% endif %}

There is also a For loop block for going though an array.

{% for post in site.posts %}
{{ post.title }}
{% endfor %}

Every logic block starts and ends with a corresponding start/end tag. To learn more about logic blocks you can read the doc here.

The last thing to introduce is Filter. It is the only thing you can use for data-manipulation. Let’s say you have a variable x = 1 and you want to add 10 to it, you can’t just write x + 10, the only way to do it is to use the plus Filter:

{% assign x = 1 %}
{% assign x = x | plus: 10 %}
{{x}}

You can also apply filter before it is printed/echoed.

{{x | plus: 10}}

You can also apply filter after filter

{% assign x = 2 | plus: 3 | times: 100 %}

The flow of operations moves from left to right, so you would expect the x above to be 500 (instead of 302 or 203).

Aside from the default Liquid Filters, here is a list of filters (came along with Jekyll) that you can use.

● ● ●

End Note 500-600 words

Hope it didn’t take you longer than 3 minutes to read through this article! If you still have a bit more time to spare, here are a few tips you may find useful:

  1. Liquid works in every file except for data files. So you can have Liquid in your .md files too, and it'd work!

  2. The Jekyll server reads _config.yml only once (when it is starting). Changes you made in _config.yml would only be reflected after the server is restarted.

  3. There seems to no way to create array or object declaratively on the fly. {% assign %} is only capable of assigning primitive values to variables unless things are done in this way:

    {% assign x = b %}

    where b is an array or object already defined in Front Matter. So the line below would not work at all:

    {% assign x = [1,2,3] %}
  4. Apparently, every variable can be overwritten locally with {%assign%}.

    {{site.url}}
    {% assign site = 2 %}
    {{site}}

    Initially site is an object, after the {%assign%} tag, site is 2. This only has effect in a local scope.

  5. Having a Rake file is a good way to define tasks to run in CLI. Tasks such as the ones in this Jekyll Bootstrap Repo for creating posts. For that, an alternative is to use jekyll-compose. (But Jekyll compose only works for Jekyll 2.5 & GitHub Pages™ supports 2.4 .)

  6. Jekyll has built in support for syntax highlighting! (though it is actually done through Python)

  7. This is added on 19th June If you are working with custom url for Collection files, remember to always end the permalink with / (e.g. myCat/ instead of myCat) or the file would be served raw.

  8. This is added on 7th July When working with angular in your Jekyll site, remember that liquid and Angular both uses the {{}} syntax for templating and any {{}} in your .html will be evaluated before it is servered. So you'd need to do it like this

    <div>
    {% raw %}
    {{ angular.stuff }}
    {% endraw %}
    </div>
    in order for {{}} to show up when the broswer downloads the html. Also, consider using ng-bind instead of {{}}. It's a lot neater this way. (If necessary, ng-bind-html).

  9. Lastly, you don't really need to stick to the GitHub Pages™ Jekyll (the Jekyll that GitHub Pages™ has built-in support for) for your GitHub Page if you prefer something else. Or something more advanced - Try out Jekyll 3.0, it's got hooks. (If you want to use Jekyll 3.0 for production, you'd just need to build locally & push the _site/ dir as the repo.) This way you can fully customize your Jekyll with plugins as well.

If you are interested in server architecture, you can learn about the new infrastructure used by GitHub Pages™ in production (since Jan 2015) here.

Despite advocating for Jekyll 3.0 & Angular, I built this site of mine using Jekyll 2.4, without any JS framework or heavy library (jQuery is used only by 2 articles because they rely on a small jQuery widget I wrote some time ago). I just want to keep things lightweight & simple (although I do have some really messy code in my templating files as a consequence of a pointless challenge I gave myself to hack around under the limitation imposed by the GitHub Pages™ Jekyll). So I’m considering using Angular.

Update (early July): a part of the home page now uses angular.