Using Makefile in Jekyll

Github Pages is a great “it just works” resource.

Except for what it does not do.

The Problem

For safety reasons, Github Pages, which is powered by Jekyll,

disables any custom plugins.

However, Jekyll is really intended to be a framework for expansion

into larger degrees of customization and sophistication,

and thankfully it has a very powerful plugin model1.

If you want to automatically generate

categroies and tags

by using plugins, you have to generate the site locally and push the raw pages.

Besides, there are a lot of other tools that we can use

to help generate a powerful site. For example,

the Visual Git Reference

is generated by pdflatex, pdf2svg and convert;

the Learn Vimscript the Hard Way

is generated by Bookmarkdown.

You can generate and deploy the site with a single command2, by using a

Rakefile.

But if you also want to use some tools other than Jekyll in some of the generating phase,

writing a Makefile could be a better solution.

The Solution

1. Directory Structure

Let the basic directory structure like this:

.
├── .site
├── jekyll
|   └── _posts
├── posts
└── shell

The jekyll source code is in the ‘jekyll’ directory and

your posts are under ‘posts’ directory.

Create a simble link from “jekyll/_posts’ to ‘../posts’.

In this structure you can seperate your ‘source code – jekyll’ and your ‘data – posts’.

And it can also be more well couped with other tools, such as latex.

2. Makefile and Script

Write this into your Makefile:

SITE= .site
RM= rm -rf

all : site

site:
    jekyll build --source jekyll --destination $(SITE)

server:
    jekyll server --source jekyll --destination $(SITE) --watch

publish: site gh-pages

gh-pages:
    shell/publish gh-pages

clean :
    $(RM) $(SITE)

Create shell script shell/publish:

#!/bin/bash

HEAD=`git symbolic-ref --short HEAD`
SHA=`git rev-parse HEAD`
SITE=.site

if [ $# -eq 0 ]; then
echo "USAGE: $0 <files>" >&2
    exit 1
fi
if ! git diff --quiet; then
echo >&2
    echo "ERROR: working tree is dirty; aborting..." >&2
    echo >&2
    exit 2
fi
if ! git diff --quiet --cached; then
echo >&2
    echo "ERROR: index is dirty; aborting..." >&2
    echo >&2
    exit 2
fi

gh-pages(){
    git checkout gh-pages
    rm * -rf
    mv $SITE/* .
    git add -A
    git commit -m "$HEAD $SHA"
    mv * $SITE
    git checkout $HEAD
}

$*

3. Creating Git Branch gh-pages

Ctreate a new empty branch:

$ git checkout --orphan gh-pages
$ rm -rf *
$ touch .gitignore
$ git add -A
$ git commit -m init
$ git checkout master

4. Generate Your Site

Build and publish with single commands:

$ make publish
  • Jekyll is really intended to be a framework for expansion into larger degrees
    of customization and sophistication, and thankfully it has a very powerful
    plugin model.
    Realjenius.com 
  • Project Build Requires Only One Step:
    Check out and then build with a single command.
    Clean Code Cheat Sheet  </fn></footnotes>