Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
31 changes: 31 additions & 0 deletions .agents/plugins/marketplace.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
{
"name": "filip-podstavec",
"interface": {
"displayName": "Filip Podstavec"
},
"plugins": [
{
"name": "claude-leverage",
"version": "1.12.0",
"description": "Personal Claude Code + Codex dev stack: security hooks, AI-first code conventions, 14 on-demand skills (incl. /repo-doctor — AI-readiness audit with code↔docs drift detection — and /refresh-context-map for the v1.8.0 smart-context-surfacing hook), ADR + session-log conventions, portable statusline. Complements other skills-based plugins, not a replacement.",
"source": {
"source": "url",
"url": "https://github.com/Filip-Podstavec/claude-leverage.git"
},
"policy": {
"installation": "AVAILABLE"
},
"category": "workflow",
"keywords": [
"ai-first",
"security-review",
"codex",
"claude-code",
"agents-md",
"repo-map",
"statusline",
"stack-freshness"
]
}
]
}
2 changes: 1 addition & 1 deletion .claude-plugin/marketplace.json
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@
"url": "https://github.com/Filip-Podstavec/claude-leverage.git"
},
"description": "Personal Claude Code + Codex dev stack: security hooks, AI-first code conventions, 14 on-demand skills (incl. /repo-doctor — AI-readiness audit with code↔docs drift detection — and /refresh-context-map for the v1.8.0 smart-context-surfacing hook), ADR + session-log conventions, portable statusline. Complements other skills-based plugins, not a replacement.",
"version": "1.11.0",
"version": "1.12.0",
"category": "workflow",
"keywords": [
"ai-first",
Expand Down
2 changes: 1 addition & 1 deletion .claude-plugin/plugin.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "claude-leverage",
"version": "1.11.0",
"version": "1.12.0",
"description": "Personal Claude Code + Codex dev stack: security hooks, AI-first code conventions, /security-review, /repo-map, /stack-check, portable statusline. Designed to complement other skills-based plugins, not replace them.",
"author": {
"name": "Filip Podstavec",
Expand Down
24 changes: 24 additions & 0 deletions .codex-plugin/plugin.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
{
"name": "claude-leverage",
"version": "1.12.0",
"description": "Personal Claude Code + Codex dev stack: security hooks, AI-first code conventions, /security-review, /repo-map, /stack-check, portable statusline. Designed to complement other skills-based plugins, not replace them.",
"author": {
"name": "Filip Podstavec",
"url": "https://github.com/Filip-Podstavec"
},
"homepage": "https://github.com/Filip-Podstavec/claude-leverage",
"repository": "https://github.com/Filip-Podstavec/claude-leverage",
"license": "MIT",
"keywords": [
"ai-first",
"security-review",
"codex",
"claude-code",
"agents-md",
"repo-map",
"statusline",
"stack-freshness"
],
"skills": "./skills/",
"hooks": "./hooks/hooks.json"
}
11 changes: 11 additions & 0 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -77,3 +77,14 @@ jobs:
python-version: "3.11"
- name: Check generator parity (gen-codex-agents.py --check)
run: python scripts/gen-codex-agents.py --check

codex-plugin-parity:
name: Codex plugin artifacts match Claude manifest
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- uses: actions/setup-python@v5
with:
python-version: "3.11"
- name: Check generator parity (gen-codex-plugin.py --check)
run: python scripts/gen-codex-plugin.py --check
15 changes: 14 additions & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,19 @@ All notable changes to `claude-leverage` are recorded here.
Format: [Keep a Changelog](https://keepachangelog.com/en/1.1.0/) +
[SemVer](https://semver.org/spec/v2.0.0.html).

## [1.12.0] — 2026-06-04

### Added

- **Codex plugin distribution path** — `.codex-plugin/plugin.json` and
`.agents/plugins/marketplace.json` are now **generated from the canonical
Claude manifest** by `scripts/gen-codex-plugin.py`, so Codex installs the same
plugin via its marketplace path without a hand-maintained second source of
truth. CI enforces artifact parity (`gen-codex-plugin.py --check`) and the
pre-push smoke run regenerates on drift. Rationale in
[ADR 0011](docs/adr/0011-codex-plugin-marketplace-third-distribution-path.md);
`docs/maintaining.md` gains the regenerate-on-change step.

## [1.11.0] — 2026-06-03

### Added
Expand Down Expand Up @@ -484,7 +497,7 @@ Format: [Keep a Changelog](https://keepachangelog.com/en/1.1.0/) +
### Fixed (field-feedback bundle)

- **`ai-first-nudge.sh`** split basename-only vs path ignore patterns
so directories named e.g. `slevomat_test_api/` no longer silently
so directories named e.g. `acme_test_api/` no longer silently
swallow nudges for production files inside them. Added Windows
backslash → forward slash normalization before pattern matching so
`node_modules` and friends still match on Git Bash.
Expand Down
20 changes: 19 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -129,7 +129,25 @@ current session) to pick up all 15 skills and 2 subagents.

### Codex CLI

Codex has no plugin marketplace, so installation is via a script:
Two ways to use the stack with Codex — they're complementary, not either/or.

**A. Plugin marketplace (skills + hooks).** Codex now has a plugin marketplace;
add this repo as a marketplace source and install it from `/plugins`:

```bash
npm i -g @openai/codex # one time
```
Then in a Codex session, open `/plugins`, add the marketplace from GitHub
shorthand `Filip-Podstavec/claude-leverage`, open the `claude-leverage` plugin,
and select **Install plugin**.

This delivers the **skills** and the **security/nudge hooks** (Codex sets
`CLAUDE_PLUGIN_ROOT` for compatibility, so the same `hooks/hooks.json` works).
It does **not** deliver the subagents or the `/flaky-test` command — Codex
plugins don't load those — nor the global `@AGENTS.md` import. For the full
stack, use option B.

**B. Install script (full stack: + subagents + global AGENTS.md import).**

```bash
# 1. Install Codex CLI itself (one time)
Expand Down
92 changes: 92 additions & 0 deletions docs/adr/0011-codex-plugin-marketplace-third-distribution-path.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,92 @@
---
status: accepted
date: 2026-06-03
deciders: Filip Podstavec
consulted: Claude Opus 4.8 (brainstorming session)
informed: stack users
---

# 0011. Codex plugin marketplace as a third distribution path

## Context and Problem Statement

OpenAI Codex shipped a plugin marketplace (installable from GitHub shorthand, a
Git URL, or a local marketplace root). Its format is close to Claude Code's:
skills as `skills/<name>/SKILL.md`, hooks as `hooks/hooks.json`, a plugin
manifest, and a marketplace root — and Codex even sets `CLAUDE_PLUGIN_ROOT` for
hook compatibility. Until now this repo reached Codex two ways: Codex reads
`AGENTS.md` natively, and `scripts/install-codex.sh` copies skills/hooks/agents
into `~/.codex` + `~/.agents`. The question: should the stack also ship as an
installable Codex plugin, and if so, how do we keep yet another manifest from
drifting?

Two format gaps block a drop-in install: Codex reads the plugin manifest ONLY
from `.codex-plugin/plugin.json` (no legacy fallback), and its marketplace
schema differs from Claude's (`interface.displayName` not `owner`; per-plugin
`policy`).

## Decision

We ship a Codex plugin distribution path via **generated** tool-native
artifacts. `scripts/gen-codex-plugin.py` derives `.codex-plugin/plugin.json` and
`.agents/plugins/marketplace.json` from the Claude manifest pair, which stays
the single source of truth. A `--check` mode runs in CI and `smoke-plugin.sh`.
The plugin path is **complementary** to the install script: it carries skills +
hooks only; subagents, the `/flaky-test` command, and the global `@AGENTS.md`
import remain on the script path.

## Decision Drivers

- The repo already treats Codex parity as a generated-and-`--check`ed artifact
(`gen-codex-agents.py`); a second generator is the idiomatic fit.
- Three manifests bumped by hand drift silently — exactly the failure
`check_version_sync.py` exists to stop.
- Codex plugins can't carry slash commands or subagents, so the plugin path
cannot fully replace the install script; framing them as complementary is
honest and avoids a regression.

## Considered Options

1. **Generated tool-native artifacts (selected).** New generator emits
`.codex-plugin/plugin.json` + `.agents/plugins/marketplace.json` from the
Claude source, `--check` in CI. Clean schema separation, no drift.
2. **Augment the shared `.claude-plugin/marketplace.json`** with Codex fields
(Codex reads it via the legacy path). Rejected: mixes two schemas in one
file and still needs a hand-written `.codex-plugin/plugin.json`.
3. **Hand-write both Codex files + extend `check_version_sync.py`.** Rejected:
more manual upkeep per change and weaker than generation against structural
drift.

## Decision Outcome

**Chosen: Option 1.** `.claude-plugin/` is the source of truth; the Codex
artifacts are generated and committed, guarded by `gen-codex-plugin.py --check`
in CI (`codex-plugin-parity` job) and `smoke-plugin.sh` (gate 3b). README
documents the plugin path (option A) alongside the install script (option B),
explicitly noting the skills+hooks-only scope.

### Consequences

**Positive:**
- One source of truth; Codex artifacts can't silently drift from the Claude
manifest.
- Codex users get a one-command marketplace install for skills + hooks.

**Negative / costs:**
- A third manifest to regenerate (automated; `--check` catches a forgotten
run).
- `policy.authentication` for an app-less plugin is assumed absent pending a
real Codex test-install (tracked as an AIDEV-NOTE in the generator).

## Alternatives considered

- See "Considered Options" above (options 2 and 3, both rejected).

## References

- `docs/superpowers/specs/2026-06-03-codex-plugin-distribution-design.md` — the
design this ADR records.
- <https://developers.openai.com/codex/plugins> and
<https://developers.openai.com/codex/plugins/build> — the Codex plugin spec.
- [ADR 0002](0002-agents-md-canonical-claude-md-import.md) — AGENTS.md as the
cross-tool canonical surface (the native Codex path).
1 change: 1 addition & 0 deletions docs/adr/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,7 @@ the original choice.
- [0008 — Smart context surfacing via PreToolUse hook (cuts per-session token tax)](0008-smart-context-surfacing-via-pretooluse-hook.md)
- [0009 — AGENTS.md lean budget (8 KiB target / 32 KiB hard cap) and stack-check vs repo-doctor severity split](0009-agents-md-lean-budget-and-size-tiers.md)
- [0010 — Naming: detect-and-conform over a prescribed house style](0010-naming-detect-and-conform-over-house-style.md)
- [0011 — Codex plugin marketplace as a third distribution path](0011-codex-plugin-marketplace-third-distribution-path.md)

(Keep this index in sync with the files in this directory; `/adr-new` will
append to it automatically.)
15 changes: 12 additions & 3 deletions docs/maintaining.md
Original file line number Diff line number Diff line change
Expand Up @@ -24,9 +24,17 @@ When you change version or hook configuration:
1. Bump `version` in BOTH `.claude-plugin/plugin.json` and
`.claude-plugin/marketplace.json`. They must match — CI fails on drift via
`scripts/check_version_sync.py`.
2. Hook scripts use `${CLAUDE_PLUGIN_ROOT}/scripts/hooks/...` in `hooks/hooks.json`.
Never `~` or `$HOME`.
3. `.codex/hooks.json` is a template using `__CLAUDE_LEVERAGE_DIR__` placeholder.
2. Regenerate the Codex plugin artifacts from the Claude source:
```bash
python scripts/gen-codex-plugin.py
```
This rewrites `.codex-plugin/plugin.json` and `.agents/plugins/marketplace.json`.
CI (`codex-plugin-parity`) and `smoke-plugin.sh` fail if they drift. Never
hand-edit the generated files — change `.claude-plugin/` and regenerate.
3. Hook scripts use `${CLAUDE_PLUGIN_ROOT}/scripts/hooks/...` in `hooks/hooks.json`.
Never `~` or `$HOME`. Codex sets `CLAUDE_PLUGIN_ROOT` for compatibility, so
the same file works in both tools.
4. `.codex/hooks.json` is a template using `__CLAUDE_LEVERAGE_DIR__` placeholder.
`scripts/install-codex.sh` resolves it at install time when writing to
`~/.codex/hooks.json`.

Expand All @@ -48,6 +56,7 @@ pytest tests/ -v # plugin integrity + frontmatter tests
python scripts/check_version_sync.py # plugin.json == marketplace.json
shellcheck scripts/hooks/*.sh # CI runs this; install locally to match
python scripts/gen-codex-agents.py --check # ensure .codex/agents/*.toml matches agents/
python scripts/gen-codex-plugin.py --check # ensure .codex-plugin/ + .agents/ match Claude manifest
bash scripts/smoke-plugin.sh # single-shot pre-push: all of the above + install-codex e2e
```

Expand Down
Loading
Loading