# How the `/caveman-commit` Command Generates Commit Messages: An LLM-Driven Approach to Conventional Commits

> Discover how caveman-commit uses an LLM to generate concise Conventional Commits with strict formatting, imperative mood, and short subject lines.

- Repository: [Julius Brussee/caveman](https://github.com/JuliusBrussee/caveman)
- Tags: how-to-guide
- Published: 2026-07-11

---

**The `/caveman-commit` command generates terse Conventional Commits by passing a diff and strict formatting rules to an LLM, enforcing 50-character subject lines, imperative mood, and minimal body content.**

The JuliusBrussee/caveman repository provides an LLM-driven skill that transforms staged diffs into compact, specification-compliant commit messages. Unlike traditional commit helpers that rely on templates or heuristics, this command uses a detailed rule contract to constrain the language model into generating terse, conventional output that follows precise formatting standards.

## Core Mechanism of the caveman-commit Command

The command operates as a specialized skill that intercepts git diffs and user prompts, routing them through a constrained LLM pipeline designed specifically for commit message generation.

### Command Detection and Routing

In [`src/plugins/opencode/plugin.js`](https://github.com/JuliusBrussee/caveman/blob/main/src/plugins/opencode/plugin.js), the system detects the `/caveman-commit` slash command and routes execution to the "commit" mode. The [`src/hooks/caveman-mode-tracker.js`](https://github.com/JuliusBrussee/caveman/blob/main/src/hooks/caveman-mode-tracker.js) module manages this mode's lifecycle, ensuring the skill remains active only during the commit generation interaction and preventing interference with other operations.

### The SKILL.md Rule Contract

The actual intelligence resides in [`skills/caveman-commit/SKILL.md`](https://github.com/JuliusBrussee/caveman/blob/main/skills/caveman-commit/SKILL.md), which functions as a strict contract between the user and the LLM. This file enumerates non-negotiable formatting rules that the model must follow, effectively constraining the otherwise open-ended language generation process into deterministic, specification-compliant output.

## Strict Formatting Rules Enforced by the LLM

The skill mandates specific constraints that guarantee Conventional Commits compliance while maximizing brevity and clarity.

### Subject Line Constraints

According to [`skills/caveman-commit/SKILL.md`](https://github.com/JuliusBrussee/caveman/blob/main/skills/caveman-commit/SKILL.md) (lines 14-20), the subject line must follow the format `<type>(<scope>): <imperative summary>`, where valid types include `feat`, `fix`, and other Conventional Commits categories. The length is capped at **50 characters** where possible, with a hard limit of **72 characters**. The specification explicitly requires:
- **Imperative mood** (e.g., "add" not "added")
- **No trailing period**
- **No fluff phrases** such as "This commit does..."

### Body Content Guidelines

The body is **omitted entirely** unless the change requires explanation of "why", breaking changes, migration notes, or issue references (lines 22-25). When present, the body must:
- Wrap at **72 characters**
- Use dashes for bullet points
- End with issue trailers such as `Closes #42` (lines 26-28)

### Explicit Prohibitions

Lines 30-33 of the SKILL.md explicitly forbid:
- First-person pronouns and phrases like "As requested by..."
- AI attribution (e.g., "Generated with Claude Code")
- Emojis, unless project-specific conventions require them

## Architectural Flow from Slash Command to Output

The execution follows a deterministic five-stage pipeline:

1. **Command Parsing**: [`src/plugins/opencode/plugin.js`](https://github.com/JuliusBrussee/caveman/blob/main/src/plugins/opencode/plugin.js) detects `/caveman-commit` and activates commit mode
2. **Mode Management**: [`src/hooks/caveman-mode-tracker.js`](https://github.com/JuliusBrussee/caveman/blob/main/src/hooks/caveman-mode-tracker.js) maintains the skill context during interaction
3. **Rule Injection**: The skill engine loads [`skills/caveman-commit/SKILL.md`](https://github.com/JuliusBrussee/caveman/blob/main/skills/caveman-commit/SKILL.md) into the LLM prompt
4. **Generation**: The LLM (Claude, Gemini, etc.) produces output constrained by the rule set
5. **Formatting**: The result formatter returns the message as a plain text code block without execution

## Practical Usage Examples

### Standard Invocation

```bash
/caveman-commit

```

The skill automatically reads the staged diff and returns a compact commit message:

```text
feat(api): add GET /users/:id/profile

Mobile client needs profile data without the full user payload
to reduce LTE bandwidth on cold‑launch screens.

Closes #128

```

### Prompt-Based Usage

```text
User: "Please write a commit for the new endpoint that returns user profiles."

```

The command returns:

```text
feat(api): add GET /users/:id/profile

Mobile client needs profile data without the full user payload
to reduce LTE bandwidth on cold‑launch screens.

Closes #128

```

### Handling Breaking Changes

```text
User: "Rename /v1/orders to /v1/checkout – update the docs as well."

```

Result:

```text
feat(api)!: rename /v1/orders to /v1/checkout

BREAKING CHANGE: clients on /v1/orders must migrate to /v1/checkout
before 2026-06-01. Old route returns 410 after that date.

```

## Summary

- The `/caveman-commit` command uses an LLM-driven skill defined in [`skills/caveman-commit/SKILL.md`](https://github.com/JuliusBrussee/caveman/blob/main/skills/caveman-commit/SKILL.md) to generate messages
- Subject lines must follow Conventional Commits format with a 50-character soft limit and 72-character hard limit
- Body content is suppressed unless necessary for explaining breaking changes, migration steps, or context
- The architecture routes commands through [`src/plugins/opencode/plugin.js`](https://github.com/JuliusBrussee/caveman/blob/main/src/plugins/opencode/plugin.js) and manages state via [`src/hooks/caveman-mode-tracker.js`](https://github.com/JuliusBrussee/caveman/blob/main/src/hooks/caveman-mode-tracker.js)
- Output is pure text ready for manual commit, not automated git execution

## Frequently Asked Questions

### Does caveman-commit automatically execute git commit?

No. The command returns only the formatted commit message as plain text in a code block. You must manually paste the output into your git workflow or editor. This design prevents unintended commits and allows for final human review before applying the message.

### What is the maximum length for commit messages generated by caveman-commit?

The subject line has a soft limit of 50 characters and a hard limit of 72 characters. When the skill includes a body section, those lines must wrap at 72 characters. These constraints align with the Conventional Commits specification and ensure compatibility with git log displays and GitHub's interface.

### Can I customize the rules for commit message generation?

The rules are hardcoded in [`skills/caveman-commit/SKILL.md`](https://github.com/JuliusBrussee/caveman/blob/main/skills/caveman-commit/SKILL.md). To customize behavior, you would need to modify this file in the JuliusBrussee/caveman repository. The system does not currently support runtime rule overrides, as the strict constraints ensure consistent, terse output across different LLM providers.

### Which LLM providers work with caveman-commit?

The skill is provider-agnostic and works with Claude, Gemini, and other LLM backends supported by the caveman framework. The [`SKILL.md`](https://github.com/JuliusBrussee/caveman/blob/main/SKILL.md) file acts as a universal prompt that constrains any compatible model to produce the same terse, conventional format regardless of the underlying architecture.