Metadata-Version: 2.4
Name: skillsaw-runbooks
Version: 0.1.0
Summary: skillsaw plugin: lint operational runbooks as agent content
Author: Stephen Benjamin
License-Expression: Apache-2.0
Project-URL: Homepage, https://github.com/stbenjam/skillsaw-runbooks
Project-URL: Issues, https://github.com/stbenjam/skillsaw-runbooks/issues
Keywords: skillsaw,lint,runbook,agents
Classifier: Development Status :: 4 - Beta
Classifier: Intended Audience :: Developers
Classifier: Programming Language :: Python :: 3
Classifier: Topic :: Software Development :: Quality Assurance
Requires-Python: >=3.9
Description-Content-Type: text/markdown
License-File: LICENSE
Requires-Dist: skillsaw>=0.14.1
Provides-Extra: dev
Requires-Dist: pytest>=7.0; extra == "dev"
Dynamic: license-file

# skillsaw-runbooks

A [skillsaw](https://skillsaw.org) plugin that lints operational runbooks
as agent content. Runbooks are step-by-step procedures executed under
pressure — increasingly by AI agents as well as on-call engineers — so
they deserve the same lint coverage as any other instruction file.

This plugin also serves as a complete, published example of every skillsaw
plugin extension point: rules, a custom repository type with content
paths, a lint tree contributor, and a plugin CLI.

## What it does

When a repository has markdown files under `runbooks/`, the plugin:

- detects the **`runbook` repository type**, which activates the rules
  below and pulls `runbooks/**/*.md` into skillsaw's content linting (so
  every builtin `content-*` rule covers your runbooks too);
- attaches `runbooks/catalog.json` (if present) to the lint tree so the
  catalog rule can check it.

### Rules

| Rule | Default severity | Checks |
|---|---|---|
| `runbook-required-sections` | warning | Every runbook has the required headings (default: `Steps`, `Rollback`) |
| `runbook-frontmatter` | warning | Every runbook has YAML frontmatter with the required fields (default: `title`, `owner`) |
| `runbook-catalog` | warning | `runbooks/catalog.json`, when present, lists every runbook and only runbooks that exist |

A passing runbook:

```markdown
---
title: Database failover to the replica
owner: storage-team
---

# Database failover

## Steps

1. Freeze writes ...

## Rollback

Repeat with the old primary as the candidate ...
```

A failing one — no `owner`, no `Rollback` section:

```markdown
---
title: Flush the Redis cache
---

# Cache flush

## Steps

1. redis-cli --scan --pattern 'rates:*' | xargs redis-cli del
```

```console
$ skillsaw lint
⚠ WARNING (runbook-required-sections) [runbooks/cache-flush.md]: Runbook is missing a 'Rollback' section
⚠ WARNING (runbook-frontmatter) [runbooks/cache-flush.md]: Runbook frontmatter is missing 'owner'
```

### Catalog

Optionally keep an index of your runbooks in `runbooks/catalog.json`:

```json
{
    "runbooks": [
        "db-failover.md",
        "cache-flush.md"
    ]
}
```

Paths are relative to `runbooks/`. The `runbook-catalog` rule warns when a
runbook on disk is missing from the catalog or a catalog entry has no
file. Without a catalog file the rule stays quiet — it is opt-in by
presence.

## Install

```console
$ pip install skillsaw-runbooks
$ skillsaw lint
```

That's it — skillsaw discovers the plugin automatically. Requires a
skillsaw new enough to support plugins (>= 0.15).

## CLI

The plugin ships a small companion CLI, dispatched through skillsaw:

```console
$ skillsaw runbooks list
runbooks/db-failover.md: Database failover to the replica — storage-team
runbooks/cache-flush.md: Flush the Redis cache — (no owner)

$ skillsaw runbooks rules
runbook-required-sections — Runbooks must contain the required sections (default: Steps, Rollback)
...
```

## Configuration

Configure rules by ID in `.skillsaw.yaml`, like any builtin rule:

```yaml
rules:
  runbook-required-sections:
    severity: error
    sections: ["Steps", "Rollback", "Verification"]
  runbook-frontmatter:
    fields: ["title", "owner", "last-reviewed"]
```

Disable a single rule, the whole plugin, or all plugins:

```yaml
rules:
  runbook-catalog:
    enabled: false
```

```yaml
plugins:
  disable: [runbooks]
```

```console
$ skillsaw lint --no-plugins
```

## Development

```console
$ python -m venv .venv
$ .venv/bin/pip install -e '.[dev]'
$ .venv/bin/pytest
```

To develop against an unreleased skillsaw, install it first:
`.venv/bin/pip install -e ../skillsaw`.

## License

Apache-2.0
