Skip to main content

Program Enhanced Text — documentation automation tool

Project description

🐾 PET — Program Enhanced Text

Write docs once. Automate the rest. Never copy-paste again.

Python License Version


PET turns your documentation into a living document. Instead of manually copying version numbers, pasting code samples, and updating chapter headings by hand, you write a .md.pet template and let PET generate the final Markdown. When your source changes, regenerate — done.

pet  README.md.pet  README.md

Not just Markdown. PET works with any text-based format — AsciiDoc, reStructuredText, LaTeX, HTML, plain text, or anything else. The template extension and output format are entirely up to you. Markdown is the most common use case, which is why the examples here use it.


1 The Idea in 30 Seconds

A .md.pet file is regular Markdown with Python code blocks between {% and %}. PET executes the blocks and splices their output into the document.

Template (docs.md.pet):

{%
use('number')
use('snippet')
n = number(fmt="{:3d}  ")
src = snippet("src")
%}

The core loop:

{% doc | n(src('main_loop')) %}

Output (docs.md):

The core loop:

  1  for item in queue:
  2      process(item)
  3      log(item)

PET replaces every {% ... %} block with whatever that Python code prints. Everything else passes through untouched.


2 Installation

pip install pet-doc

Initialise a project (copies the macro library into .pet/):

cd my-project
pet init

Process a template once, or watch it for changes:

pet  my-doc.md.pet  my-doc.md          # one-shot
pet watch my-doc.md.pet my-doc.md      # live reload on every save

3 Built-in Macro Library

Text & Structure

Macro What it does
chapter(header_prefix="#", sep=" ") Hierarchical section counter — # 1, ## 1.1, ### 1.1.1
number(start=1, step=1, fmt="{} ") Prefix each line of a text block with a sequential number
include(filename) Read any file and return its content as a string
snippet(directory) Scan source files for named snippet / end snippet markers
dedent(text) Strip common leading indentation from included code

Data Readers

All data macros expose get("dot.separated.path") for deep value access. Lists support integer indices: get("dependencies.0.name").

Macro Format
toml(file) TOML — great for pyproject.toml, config files
yaml(file) YAML — nested keys, lists, indexed access
json(file) JSON — identical API to yaml
xml(file) XML — xpath queries, attribute access via attr()
properties(file) Java .properties — flat key=value, dotted keys preserved
env(file) .env files — strips surrounding quotes, skips comments

Pipelines

pipe is an identity transformer. Compose steps with |:

use('pipe')
use('dedent')
use('number')

n      = number(fmt="{:3d}  ")
clean  = pipe | dedent | n   # dedent first, then add line numbers

doc | clean(include("src/core.py"))

Apply a transformation line by line with .on_lines():

shout = pipe | str.upper
doc | shout.on_lines()(include("words.txt"))

4 Worked Example — This README

This very document is generated by PET 1.0.0. The version badge above is not hardcoded — it is read live from pyproject.toml:

 1 | use('data/toml')
 2 | proj = toml("pyproject.toml")
 3 | VERSION = proj.get('project.version')

The section headings are auto-numbered by chapter:

 4 | ch = chapter()
 5 | # becomes  ->  # 1 The Idea in 30 Seconds
 6 | # becomes  ->  # 2 Installation
 7 | # etc.

Change the order, add a section, remove one — the numbers update on the next pet README.md.pet README.md.


5 Why PET?

Documentation rots. Code evolves, but the docs that reference it often don't. Copy-pasted version numbers fall behind. Pasted code samples go stale. Chapter numbers break the moment you reorder sections.

PET's answer is deliberately small:

  • No new language — your macros are plain Python classes
  • No build framework — one command, one output file
  • No lock-in — the output is standard Markdown; stop using PET any time
  • Self-documenting — the template is the documentation intent

If information already exists somewhere in your project, humans shouldn't maintain a second copy of it. PET makes the automated copy the only copy.

For the full theory — single-source-of-truth, consistency checks as document unit tests, and why correct docs matter more than ever in the age of LLM RAG — see RATIONALE.md.

To learn how to write your own macros, with every built-in macro explained pattern by pattern, see MACROGUIDE.md.


Generated from README.md.pet by PET 1.0.0 · pet README.md.pet README.md

Project details


Download files

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

Source Distribution

pet_doc-1.0.0.tar.gz (48.2 kB view details)

Uploaded Source

Built Distribution

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

pet_doc-1.0.0-py3-none-any.whl (15.1 kB view details)

Uploaded Python 3

File details

Details for the file pet_doc-1.0.0.tar.gz.

File metadata

  • Download URL: pet_doc-1.0.0.tar.gz
  • Upload date:
  • Size: 48.2 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.13.7

File hashes

Hashes for pet_doc-1.0.0.tar.gz
Algorithm Hash digest
SHA256 6faabc9b151349c3d2db3c20334b565030101a42fa721d606458ef2af720e308
MD5 ff491b7dd8bc83a5f580951fe3de2cd8
BLAKE2b-256 2ca18ffef1183d093c76bc730372db1799943644c59ad067bad37516f47334b0

See more details on using hashes here.

File details

Details for the file pet_doc-1.0.0-py3-none-any.whl.

File metadata

  • Download URL: pet_doc-1.0.0-py3-none-any.whl
  • Upload date:
  • Size: 15.1 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.13.7

File hashes

Hashes for pet_doc-1.0.0-py3-none-any.whl
Algorithm Hash digest
SHA256 993e126422f01f332e0fb8d1882518b11dc9c1a1dd684207ff2da3db1740c62e
MD5 d964045fad6b1c6c4877f889076b2a04
BLAKE2b-256 864c56dda5923f645f690445276dc391260ad79e1f73d6781f3704fc9fcdcee6

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