Build websites with R and nanoc or Jekyll

Build websites with R and nanoc or Jekyll

Workflow for static site generators

Using static website generators (SSG) like nanoc, Jekyll, or Hugo to automatically build a website based on R markdown documents currently requires dealing with a couple of technical details.

  • The first step of the workflow requires knitr to turn the R markdown documents into regular markdown. I use an R script that gets called from a Makefile.
  • The plain markdown files are then processed into regular HTML by the SSG. This is done by a markdown engine - popular choices are pandoc and Redcarpet. Unfortunately, not all engines are supported out-of-the-box by nanoc and Jekyll. Also unfortunately, the engines have slightly different behavior and feature sets when it comes to markdown extensions.
  • SSGs require markdown files with YAML front matter that describes the type of layout, post title, categories and tags. knitr ignores YAML front matter in R markdown files, so this is fine.

Setup for nanoc

This website is currently (2024) built with nanoc (version 4.12.5, compatibility options for working with nanoc3 config), using Ruby (version 3.0.2). The design uses the Bootstrap framework (version 5.3.3). As a markdown engine, I use pandoc (version 2.9) because it provides

  • automatical creation of a table-of-contents
  • MathJax support for great math rendering based on () syntax
  • support for “fenced code blocks” in GitHub flavor (code stands between backticks) - the knitr default
  • built-in fast syntax highlighting for R code

The build-process is automatically managed with a Makefile that calls an R-script for knitting R markdown files to plain markdown. To build this website yourself:

  • You need R with the knitr package. Set a permanent R option which CRAN mirror to use by creating a file .Rprofile in your home directory, containing the line options(repos=c(CRAN="https://cran.rstudio.com/")). Also install pandoc, Ruby, as well as the Ruby gems nanoc and pandoc-ruby.
  • Clone the RExRepos GitHub repository at https://github.com/dwoll/RExRepos.git.
  • In the RExRepos directory, just run nanoc to build the already present markdown files. To build from R markdown, run make clean and make. Doing this under Windows has not been tested since 2013. In theory, it requires editing the Makefiles first, commenting the Linux rm commands, und un-commenting the Windows del commands. On Windows, you need to have make and sed installed, and in your path.

Setup for Jekyll

The following description is based on my experience in 2013, and has not been validated since.

A website like this could also be built with Jekyll. However, Jekyll is less suited for building a navigation structure as it does not let you use embedded Ruby in templates (like nanoc does). The best choice for a markdown engine currently seems to be kramdown. Using Jekyll with kramdown has some extra requirements:

  • Call knitr::render_jekyll() before you knit an R markdown file to plain markdown. This embeds code snippets in curly braces - kramdown doesn’t support fenced code blocks with backticks (knitr’s default).
  • kramdown natively supports MathJax. However, it needs double dollar signs as inline math delimiters instead of single dollar signs. Double dollar signs are normally reserved for display math. If you use single dollar signs with kramdown, inline math underscores are erroneously interpreted as markdown emphasis syntax (and not subscripts).
  • kramdown supports automatical generation of a table-of-contents, but needs a toc-placeholder.
  • Jekyll can also use Redcarpet which supports fenced code blocks, inline math with single dollar signs and has an option to turn off inline emphasis. Redcarpet supports automatical creation of a table of contents, but Jekyll - in 2013 - did not implement the two necessary rendering passes.
  • Posts cannot contain double braces as these are delimiters for Jekyll’s template engine Liquid. Unfortunately, double braces are valid R output, e.g., from package sets. You have to replace them before running Jekyll.
  • The post filenames have to conform to Jekyll standards (start with the date), i.e., have the format “YYYY-MM-DD-title.md”.

Other solutions

knitr-based online publication is possible with the R package blogdown which supports Hugo.

A new package for building entire websites based on files in syntax very similar to R markdown files is Quarto