Updated on 2021-12-08
The pages on this site are written in Markdown and converted to HTML using a custom Makefile to orchestrate the conversion. I don't see why the actual Makefile would be of use to other people, but maybe it can serve as an example for others in building their own site generators using a Makefile. In what follows, I will explain my requirements, solution and the actual code used.
I have very modest requirements for my site generator.
To prevent feature creep I have also create a list of non-requirements.
I decided to go with a Makefile using one recipe per file type. Another option
would have been to use a bash script, but make is trivial to parallelize the
build with the -j
flag and I think easier to write.
For converting Markdown files into HTML I will use cmark-gfm
, but I may switch
to md4c
in the future. To strip the meta data from binary files I will use
mat2
. Both cmark-gfm
and mat2
are available in Debian 11, so easy for me
to install. I will add the header and footer to pages using cat
. So far I do
not have support for LaTeX equations, but I will worry about that later.
The entire Makefile file is less than 50 lines of code. Time will tell if builds are fast, but so far it seems fast to me.
The next three sections include contents of Makefile
, header
and footer
.
SRC_DIR := src
DST_DIR := site
MD2HTML := cmark-gfm -e table -e strikethrough -e autolink
HTML_HEADER := header
HTML_FOOTER := footer
REMOVE_META := mat2 --inplace
SRV_SYNC := rsync -rcize ssh --delay-updates --delete-after --force
SRV_USERNAME := username
SRV_HOST := example.com
SRV_DIR := /var/www/example.com
.DEFAULT_GOAL := all
SRC_MD_FILES := $(shell find $(SRC_DIR) -type f -name '*.md')
DST_HTML_FILES := $(patsubst $(SRC_DIR)/%.md,$(DST_DIR)/%.html,$(SRC_MD_FILES))
DST_FILES += $(DST_HTML_FILES)
$(DST_DIR)/%.html: $(SRC_DIR)/%.md $(HTML_HEADER) $(HTML_FOOTER)
@mkdir -p "$(dir $@)"
$(MD2HTML) "$<" | cat $(HTML_HEADER) - $(HTML_FOOTER) > "$@"
SRC_JPG_FILES := $(shell find $(SRC_DIR) -type f -name '*.jpg')
DST_JPG_FILES := $(patsubst $(SRC_DIR)/%,$(DST_DIR)/%,$(SRC_JPG_FILES))
DST_FILES += $(DST_JPG_FILES)
$(DST_DIR)/%.jpg: $(SRC_DIR)/%.jpg
@mkdir -p "$(dir $@)"
cp "$<" "$@"
$(REMOVE_META) "$@"
SRC_PNG_FILES := $(shell find $(SRC_DIR) -type f -name '*.png')
DST_PNG_FILES := $(patsubst $(SRC_DIR)/%,$(DST_DIR)/%,$(SRC_PNG_FILES))
DST_FILES += $(DST_PNG_FILES)
$(DST_DIR)/%.png: $(SRC_DIR)/%.png
@mkdir -p "$(dir $@)"
cp "$<" "$@"
$(REMOVE_META) "$@"
DST_FILES += $(DST_DIR)/favicon.ico
$(DST_DIR)/favicon.ico: $(DST_DIR)/favicon.png
cp "$<" "$@"
.PHONY: all
all: $(DST_FILES)
.PHONY: clean
clean:
rm -r $(DST_DIR)
.PHONY: serve
serve: all
python -m http.server --directory $(DST_DIR)
.PHONY: deploy
deploy: all
$(SRV_SYNC) $(DST_DIR)/ $(SRV_USERNAME)@$(SRV_HOST):$(SRV_DIR)
<!DOCTYPE html>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<style>
html {
font-size: 20px;
background: mintcream;
font-family: "Comic Sans MS", "Comic Neue", sans-serif;
}
body {
margin: 1rem;
}
p {
line-height: 1.4;
}
code, pre {
font-family: "Fantasque Sans Mono", monospace;
}
pre {
overflow: auto;
}
img {
max-width: 100%;
}
</style>
<title>The Stuff I Do...</title>
<a href="/">The Stuff I Do...</a>
<hr>
<hr>
<p>Copyright © 2020-2021 thestuffido.xyz All Rights Reserved</p>
I have been making personal webpages for myself since the 1990s. Over the years I have tried WYSIWYG editors, Jekyll, Hugo, 11ty, ssg, a convoluted JavaScript program using Markdown-it and of course just writing HTML in HTML. I am hoping this Makefile will workout, but odds are I will switch to something else at some point.
Copyright © 2020-2021 thestuffido.xyz All Rights Reserved