Skip to content
RemoteRabbitPublic

About

A documentation generator for Terraform/OpenTofu modules, built on open-inspector.

Topics

Resources

Stars

2 stars

Watchers

0 watching

Forks

Repository files navigation

open-docs

A documentation generator for Terraform/OpenTofu modules, built on open-inspector.

The goal: a modern alternative to terraform-docs that matches its day-to-day workflow, then goes further using data the inspector captures that terraform-docs discards (source ranges, schema findings, reference graphs, structured types).

Status: early / proof-of-concept. Today open-docs emits a verbose, debug-oriented dump of everything the inspector parses. The curated, reader-facing output and the workflow features below are planned. See the feature checklist for what works now vs. what is coming.

Why open-docs

terraform-docs renders the fields it understands and throws the rest away. open-inspector keeps the parts that make docs actionable, and open-docs turns them into output:

  • Source permalinks. Every block carries filename + start/end line:column:byte, so docs can deep-link to the exact source lines on GitHub/GitLab/Bitbucket.
  • Health, not just a field dump. Schema findings (deprecated, unknown, missing-required attributes) and missing descriptions become an actionable checklist with severities.
  • Diagrams. The inspector's module graph (tree/DOT/Mermaid) becomes inline dependency and resource diagrams; GitHub renders Mermaid natively.
  • Richer data. Leading # ... doc-comments, structured variable types (object({ ... }) with optional), decoded default values, and expression-level references (var.x, module.y.z, aws_s3_bucket.b).
  • Fuller block coverage than terraform-docs: moved, import, removed, check, ephemeral, and OpenTofu encryption.

Features

Core rendering

  • Inspect a module directory and render Markdown for every block type (providers, inputs, outputs, locals, managed/data/ephemeral resources, module calls, moved/import/removed, checks, schema findings, diagnostics).
  • Full source position per row (`file.tf` [L:C:B -> L:C:B]).
  • Doc-comments, structured types, decoded defaults, and expression references surfaced in the table view.
  • [~] Curated, reader-facing default layout. Today the output is the verbose all-columns debug view; a clean default with --verbose as the opt-in debug mode is planned.
  • [~ ] Section toggles (show/hide) and sort order (by name or source position).
  • [~ ] Deterministic, diff-stable output across runs and platforms.

Workflow / terraform-docs parity (table stakes)

  • Write to stdout or a file (-o).
  • README injection between <!-- BEGIN_OPEN_DOC --> / <!-- END_OPEN_DOC --> markers instead of overwriting the file (output { mode = "inject" }).
  • [~] Config file (.open-docs.hcl): output { file, mode } works today; formatter, sections, sort, and header/footer source are planned.
  • prek hooks for file hygiene, gofmt, go vet, and go test.
  • GitHub Action wrapper.
  • CI gate: --check (fail if on-disk docs are stale) and --fail-on warning|error.

Differentiators (the wedge)

  • Schema-aware inspection via -schema (shells out to tofu/terraform).
  • [~] Health section: render schema findings + missing descriptions as a severity checklist. Findings render as a table today; the curated health view is planned.
  • Source permalinks: ranges -> host links at the right ref/line, with git remote/ref detection and config override.
  • Inline Mermaid graph: module dependency and resource-relationship diagrams.
  • Cross-references ("used by"): drive from expression references (e.g. which outputs/resources consume var.x).
  • Lint/quality: unused variables, unreferenced outputs, undocumented inputs/outputs, doc-completeness score.

Power features (later)

  • Dynamic config (HCL eval context): build section lists with for/conditionals that react to the inspected module.
  • Templates / custom content: arrange generated sections and interleave prose or included files.
  • More formats: Markdown document, json, mdx, asciidoc.
  • Recursive / multi-module docs via the module graph.
  • Examples extraction: include examples/*/main.tf snippets.
  • Optional static HTML/MDX site output.

Usage

go build -o open-docs .

# print to stdout
./open-docs ./examples/vpc

# write to a file (replace mode)
./open-docs -o ./examples/vpc/README.md ./examples/vpc

# enrich with provider schema (deprecated / missing-required findings)
# requires `tofu` or `terraform` available and the module initialized
./open-docs -schema ./examples/vpc

Configuration (.open-docs.hcl)

# Built-in defaults for open-docs. A user's .open-docs.hcl is decoded on top
# of these values, so any attribute set there overrides the one here.
main {
  docsfile = "README.md"
  mode     = "stdout"
  # mode = "replace"
  header   = true
}

required {
  render = true
  name = true
  source = true
  version = true
  alias = false
  position = true
}

providers {
  render = true
  name = true
  alias = true
  for_each = false
  position = true
}

variables {
  render = true
  name = true
  type = true
  default = true
  required = true
  description = true
  comment = true
  sensitive = true
  nullable = true
  ephemeral = true
  validation = true
  position = true
}

outputs {
  render = true
  name = true
  value = true
  references = true
  description = true
  comment = true
  sensitive = true
  ephemeral = true
  depends_on = true
  position = true
}

locals {
  render = true
  name = true
  value = true
  references = true
  position = true
}

resources {
  render    = true
	name      = true
	mode      = false
	type      = true
	provider  = false
	count     = true
	for_each   = true
	depends_on = true
	nested_body= true
	lifecycle = true
	comment   = true
	position  = true
}

Drop a .open-docs.hcl in the module directory or the repository root (or pass -config <file>) to control output. open-docs uses the nearest one, searching from the module directory up to the repository root.

main {
  docsfile = "README.md"  # relative to the module directory
  mode = "inject"     # "stdout" (default) | "replace" | "inject"
  header = false      # omit the module title and path lines (default: true)
}

In inject mode, open-docs replaces the text between the markers and leaves the rest of the file untouched (creating the region if it is missing):

# My Module

Hand-written intro.

<!-- BEGIN_OPEN_DOC -->
<!-- END_OPEN_DOC -->

The -o <file> flag is a shortcut for replace mode to that path and takes precedence over the config file.

Example

Each directory under examples/ is a module with its generated README.md, used to check how output renders:

  • vpc: a realistic multi-file AWS VPC module with a local child module.
  • complete: every block type open-inspector understands (including ephemeral, check, OpenTofu encryption and provider for_each, and a .tf.json file), plus table edge cases such as pipes, heredocs, Unicode, and long values.
  • invalid: deliberately broken configuration for the diagnostics table.

Development

The project uses devenv for a pinned Go, OpenTofu, and prek toolchain. Enter it directly or allow direnv once:

devenv shell
# or
direnv allow

The shell installs the prek Git shim. Common commands are:

build                 # compile ./open-docs
format                # format all Go files
verify                # format check, build, vet, test, and smoke test
prek run --all-files  # run every repository hook
devenv test           # run the complete devenv verification

How it works

open-docs calls inspector.Inspect(dir) to parse the module into a *model.Module, then walks that struct in markdown.go to render Markdown tables. All HCL parsing lives in open-inspector; open-docs owns presentation only.

Project layout

  • main.go: CLI flag parsing, calls inspector.Inspect, writes output.
  • markdown.go: renders a *model.Module to Markdown.
  • examples/: sample modules and their generated README.md.

Related

About

A documentation generator for Terraform/OpenTofu modules, built on open-inspector.

Topics

Resources

Stars

2 stars

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages