Skip to main content

Limberer: Flexible document generation based on WeasyPrint, mustache templates, and Pandoc.

limberer is a utility for assembling markdown into documents.

Usage

$ limberer create projname
$ cd projname
$ limberer build report.toml
$ open projname.pdf

Features

  • Markdown-based
  • Consistent builds
  • Automatic table of contents generation
  • Mustache template hardening (disable __ access and lambda evaluation)
  • WeasyPrint hardening (restricts file access)
  • Source code snippet syntax highlighting
  • 2-column layouts
  • Footnote support
  • Image/figure support
  • Markdown within HTML tables
  • Flexible

Installation

Prerequisites

$ sudo apt-get install pandoc highlight

Note: If your distro has an older version of pandoc (e.g. 2.9.x), get it from https://github.com/jgm/pandoc/releases/.

$ wget https://github.com/jgm/pandoc/releases/download/<ver>/pandoc-<...>.deb
$ sudo dpkg -i ./pandoc-*.deb

Install

$ pip3 install --user limberer

From Source

$ git clone https://github.com/ChaosData/limberer && cd limberer
$ python3 -m pip install --user --upgrade pip setuptools
$ python3 -m pip install --user .

Packaging

$ python3 -m pip install --user wheel build
$ python3 -m build --sdist --wheel .
$ python3 -m pip install --user dist/limberer-*.whl

Cleaning

$ rm -rf ./build ./dist ./src/limberer.egg-info ./src/limberer/__pycache__

Guide

limberer is primarily about structuring documents through the use of "sections," which are ordered in a document's <project>.toml file.

These sections are based on HTML Mustache templates. For the most part, the section template will be used to write document content. For such type = "section" sections, the content will be sourced from a (currently) Markdown file based on the section name value (sections/<name>.md). By default, sections will be rendered against the template/section.html template, but the template used can be changed via an alt = "othertemplate" section list setting.

Project TOML

title = "Example Document"
subheading = "..."
#globaloption=value
#...

authors = [
  { name = "Example Person", email = "example@example.com" },
  ...
]

sections = [
  { type = "cover" },
  { type = "toc" },
  { name = "example", type = "section", title = "Example" },
  { name = "example2", type = "section", title = "Example2", sectionoption = "value" },
  ...
]

Sections

Sections are a mix of Markdown (and, in some cases, HTML), where most document content is written. A section can begin with a block of Markdown metadata:

---
toc_header_level: 2
columns: true
title: Example3
classes: foo bar baz
---

The metadata options are merged with the section entry options. Currently supported options are the following:

  • toc_header_level: Header level limit to use for table of contents entry generation.
  • columns: Whether or not to use the 2-column format for the section.
  • title: Section title for 2-column format.
  • classes: List of HTML class names to apply to the section (<article>)

Tables

Tables can be written using the pipe-delimited GitHub-flavored Markdown convention, or with HTML tables.

| First Header  | Second Header |
| ------------- | ------------- |
| Content Cell  | Content Cell  |
| Content Cell  | Content Cell  |
<table>
  <thead>
    <tr>
      <th style="width: 20%">a</th>
      <th style="width: 40%">b</th>
      <th>c</th>
      <th>d</th>
    </tr>
  </thead>
  <tbody>
    <tr><td>**Bold**</td><td>_italic_</td>
<td>
```
code block
```
</td>
<td>
* list
* of
* things
</td>
    </tr>
    <tr><td></td><td></td><td></td><td></td></tr>
    <tr><td></td><td></td><td></td><td></td></tr>
    <tr><td></td><td></td><td></td><td></td></tr>
  </tbody>
</table>

Images

A simple image can be embedded with custom CSS to place/style it:

![](./images/test1.jpg){style="width: 30%; margin: auto; display: block;"}

However, for the most part, figures are a better way to embed images:

![An example image](./images/test1.jpg){style="width: 30%; border: 1px solid red;"}

The figures themselves can be styled with the figstyle and figclass options:

![Another example image](./images/test1.jpg){style="width: 1.5in" figstyle="color: red; width: 35%;" figclass="aaa bbb"}

Additionally, there is support for a side-by-side image-and-text in the default layout/theme using a little HTML:

<div class="two-col-fig">
![This is on the left](./images/test1.jpg)
<div style="width: 40%">
## A Header

Lorem ipsum dolor sit amet...
</div>
</div>

The order of these can also be swapped:

<div class="two-col-fig">
<div style="width: 40%">
## A Header

Lorem ipsum dolor sit amet...
</div>
![This is on the right](./images/test1.jpg){style="width: 1.5in"}
</div>

Cross-References

Xrefs can be made through links to an element's id. By default, headings have autogenerated IDs based on the heading text (e.g. # Examplely Example will have an id of {section}-examplely-example. However, this can be overridden as follows:

## AAA{#aaah2}

Note: The {section}- prefix will be applied to all id values other than of the sections themselves.

To xref, any link to #<id> will suffice, but to style xrefs, a few options are available in the default style/layout.

  • .xref: A simple unstyled segment of text.

    * [xref to Example2.AAA](#example2-aaah2){.xref}
    * <a class="xref" href="#example2-aaah2">xref to Example2.AAA</a>
    
  • .xrefn: This will autopopulate the target's text content.
    Note: Be careful not to use this on elements containing large quantities of text via child nodes.

    * <a class="xrefn" href="#example2-aaah2"></a>
    * [](#example2-aaah2){.xrefn}
    
  • .xrefpg: This will add a " on page XX".

    * <a class="xrefn xrefpg" href="#example2-aaah2"></a>
    * [](#example2-aaah2){.xrefn .xrefpg}
    

Breaks

The following can be added to force a break.

<div class="pagebreak"></div>
<div class="columnbreak"></div>

Footnotes

Footnotes should mostly work as expected, but can fit poorly and may be better shifted to another page.

Hello world.[^test]

[^test]: <https://github.com/ChaosData/limberer>

Theming/Styling

By default, limberer comes with some core styling and section templates. It is expected that users will customize their document templates beyond what is provided. As such, the limberer create command supports a -t <path> option to generate a new project from a given template project directory.

Generally speaking, the styling you want to use is up to you. However, for convenience, the CSS is organized as core, style, and custom. The intent is for the assets/core.css to cover the main layout and functioning of the document, the assets/style.css to cover group theming for consistency, and custom/custom.css to be for any per-document/project styling.

Todo List

  • Draft builds
  • Partial builds of individual sections
  • Support for non-Markdown sections

FAQ

Why?

For a litany of reasons, but if I had to go out on a limb and pick one, it would be that LaTeX is a great typesetter, but a terrible build system.

What!?

Greetz to asch, tanner, agrant, jblatz, and dthiel. <3

Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

limberer-0.3.2.tar.gz (77.2 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

limberer-0.3.2-py3-none-any.whl (75.5 kB view details)

Uploaded Python 3

File details

Details for the file limberer-0.3.2.tar.gz.

File metadata

  • Download URL: limberer-0.3.2.tar.gz
  • Upload date:
  • Size: 77.2 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/4.0.2 CPython/3.10.6

File hashes

Hashes for limberer-0.3.2.tar.gz
Algorithm Hash digest
SHA256 e721f59d90a084d89a7782984dc0556585d7df21df500d6d182e027a0aeaaf82
MD5 7939435ba361d5f7ba3ad2e6b23cf593
BLAKE2b-256 1f4da84a20e1a36238919e40bc4c99982a9b34906da2bd1551510d2a1807df4b

See more details on using hashes here.

File details

Details for the file limberer-0.3.2-py3-none-any.whl.

File metadata

  • Download URL: limberer-0.3.2-py3-none-any.whl
  • Upload date:
  • Size: 75.5 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/4.0.2 CPython/3.10.6

File hashes

Hashes for limberer-0.3.2-py3-none-any.whl
Algorithm Hash digest
SHA256 f9a434e02bcb0aac3c2911f4813ec1550dc961da020a11c717318f116445e9ba
MD5 b25c70195a89eb54a50bc7db2034c213
BLAKE2b-256 caad847a13c95aa5aeaa94346579db4e5c16bf57578cd6b945b099dff3e26a21

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page