raidlock 0.1.0__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- raidlock-0.1.0/.claude-plugin/marketplace.json +24 -0
- raidlock-0.1.0/.claude-plugin/plugin.json +13 -0
- raidlock-0.1.0/.dockerignore +7 -0
- raidlock-0.1.0/.github/CODEOWNERS +1 -0
- raidlock-0.1.0/.github/ISSUE_TEMPLATE/bug_report.yml +49 -0
- raidlock-0.1.0/.github/ISSUE_TEMPLATE/config.yml +5 -0
- raidlock-0.1.0/.github/ISSUE_TEMPLATE/feature_request.yml +22 -0
- raidlock-0.1.0/.github/ISSUE_TEMPLATE/runner_adapter.yml +43 -0
- raidlock-0.1.0/.github/dependabot.yml +16 -0
- raidlock-0.1.0/.github/pull_request_template.md +13 -0
- raidlock-0.1.0/.github/workflows/ci.yml +175 -0
- raidlock-0.1.0/.github/workflows/docker-publish.yml +63 -0
- raidlock-0.1.0/.github/workflows/pr-title.yml +28 -0
- raidlock-0.1.0/.github/workflows/release-please.yml +19 -0
- raidlock-0.1.0/.github/workflows/release.yml +118 -0
- raidlock-0.1.0/.gitignore +10 -0
- raidlock-0.1.0/.gitleaks.toml +74 -0
- raidlock-0.1.0/.release-please-manifest.json +3 -0
- raidlock-0.1.0/CHANGELOG.md +124 -0
- raidlock-0.1.0/CODE_OF_CONDUCT.md +9 -0
- raidlock-0.1.0/CONTRIBUTING.md +144 -0
- raidlock-0.1.0/Dockerfile +27 -0
- raidlock-0.1.0/LICENSE +21 -0
- raidlock-0.1.0/PKG-INFO +186 -0
- raidlock-0.1.0/PROTOCOL.md +149 -0
- raidlock-0.1.0/README.md +153 -0
- raidlock-0.1.0/SECURITY.md +77 -0
- raidlock-0.1.0/agents/raid-worker.md +19 -0
- raidlock-0.1.0/bin/raid +52 -0
- raidlock-0.1.0/bin/raidlock +52 -0
- raidlock-0.1.0/docs/ARCHITECTURE.md +494 -0
- raidlock-0.1.0/docs/RELEASING.md +120 -0
- raidlock-0.1.0/docs/assets/README.md +48 -0
- raidlock-0.1.0/docs/assets/brand/README.md +54 -0
- raidlock-0.1.0/docs/assets/brand/raidlock-lockup-dark.svg +1 -0
- raidlock-0.1.0/docs/assets/brand/raidlock-lockup.svg +1 -0
- raidlock-0.1.0/docs/assets/brand/raidlock-mark-dark.svg +1 -0
- raidlock-0.1.0/docs/assets/brand/raidlock-mark-mono.svg +1 -0
- raidlock-0.1.0/docs/assets/brand/raidlock-mark.svg +1 -0
- raidlock-0.1.0/docs/assets/brand/raidlock-wordmark-dark.svg +1 -0
- raidlock-0.1.0/docs/assets/brand/raidlock-wordmark.svg +1 -0
- raidlock-0.1.0/docs/assets/brand/social-preview.png +0 -0
- raidlock-0.1.0/docs/assets/brand/social-preview.svg +1 -0
- raidlock-0.1.0/docs/assets/demo-60s.cast +32 -0
- raidlock-0.1.0/docs/assets/demo.gif +0 -0
- raidlock-0.1.0/docs/assets/hero.gif +0 -0
- raidlock-0.1.0/docs/assets/hero.mp4 +0 -0
- raidlock-0.1.0/docs/assets/ui-plain-desktop.png +0 -0
- raidlock-0.1.0/docs/assets/ui-plain-mobile.png +0 -0
- raidlock-0.1.0/docs/assets/ui-plain-overview-desktop.png +0 -0
- raidlock-0.1.0/docs/assets/ui-plain-overview-mobile.png +0 -0
- raidlock-0.1.0/docs/assets/ui-raid-achievements-desktop.png +0 -0
- raidlock-0.1.0/docs/assets/ui-raid-desktop.png +0 -0
- raidlock-0.1.0/docs/assets/ui-raid-frames-desktop.png +0 -0
- raidlock-0.1.0/docs/assets/ui-raid-graph-desktop.png +0 -0
- raidlock-0.1.0/docs/assets/ui-raid-map-desktop.png +0 -0
- raidlock-0.1.0/docs/assets/ui-raid-mobile.png +0 -0
- raidlock-0.1.0/docs/assets/ui-raid-overview-desktop.png +0 -0
- raidlock-0.1.0/docs/assets/ui-raid-overview-mobile.png +0 -0
- raidlock-0.1.0/docs/assets/ui-raid-replay-desktop.png +0 -0
- raidlock-0.1.0/docs/guides/benchmark.md +95 -0
- raidlock-0.1.0/docs/guides/commands.md +176 -0
- raidlock-0.1.0/docs/guides/concepts.md +43 -0
- raidlock-0.1.0/docs/guides/docker.md +128 -0
- raidlock-0.1.0/docs/guides/foresight.md +35 -0
- raidlock-0.1.0/docs/guides/getting-started.md +102 -0
- raidlock-0.1.0/docs/guides/hooks.md +102 -0
- raidlock-0.1.0/docs/guides/install.md +184 -0
- raidlock-0.1.0/docs/guides/lead-playbook.md +48 -0
- raidlock-0.1.0/docs/guides/limits.md +57 -0
- raidlock-0.1.0/docs/guides/lore.md +150 -0
- raidlock-0.1.0/docs/guides/mcp.md +89 -0
- raidlock-0.1.0/docs/guides/multi-provider.md +68 -0
- raidlock-0.1.0/docs/guides/native.md +111 -0
- raidlock-0.1.0/docs/guides/operations.md +178 -0
- raidlock-0.1.0/docs/guides/orchestration.md +274 -0
- raidlock-0.1.0/docs/guides/overview.md +108 -0
- raidlock-0.1.0/docs/guides/planning.md +78 -0
- raidlock-0.1.0/docs/guides/pr.md +104 -0
- raidlock-0.1.0/docs/guides/ui.md +237 -0
- raidlock-0.1.0/docs/guides/verification.md +75 -0
- raidlock-0.1.0/docs/guides/worker-rules.md +50 -0
- raidlock-0.1.0/examples/README.md +9 -0
- raidlock-0.1.0/examples/claude-only/README.md +25 -0
- raidlock-0.1.0/examples/claude-plus-codex/README.md +20 -0
- raidlock-0.1.0/examples/demo/README.md +27 -0
- raidlock-0.1.0/examples/demo/builder.py +54 -0
- raidlock-0.1.0/examples/demo/record.py +169 -0
- raidlock-0.1.0/examples/demo/run.sh +270 -0
- raidlock-0.1.0/examples/docker/compose.yaml +37 -0
- raidlock-0.1.0/examples/multi-workspace/README.md +13 -0
- raidlock-0.1.0/examples/playground/README.md +115 -0
- raidlock-0.1.0/examples/playground/setup.sh +116 -0
- raidlock-0.1.0/hooks/hooks.json +94 -0
- raidlock-0.1.0/pyproject.toml +112 -0
- raidlock-0.1.0/release-please-config.json +22 -0
- raidlock-0.1.0/scripts/bench_overhead.py +11 -0
- raidlock-0.1.0/scripts/curate-public.sh +115 -0
- raidlock-0.1.0/scripts/demo-60s.sh +192 -0
- raidlock-0.1.0/scripts/demo-tape-setup.sh +80 -0
- raidlock-0.1.0/scripts/demo.tape +78 -0
- raidlock-0.1.0/scripts/docker-smoke.sh +57 -0
- raidlock-0.1.0/scripts/overhead_ab.sh +45 -0
- raidlock-0.1.0/scripts/render-hero.sh +24 -0
- raidlock-0.1.0/skills/raid/SKILL.md +11 -0
- raidlock-0.1.0/skills/raidlock/SKILL.md +57 -0
- raidlock-0.1.0/skills/raidlock/reference/commands.md +67 -0
- raidlock-0.1.0/skills/raidlock/reference/hooks.md +20 -0
- raidlock-0.1.0/skills/raidlock/reference/lead.md +30 -0
- raidlock-0.1.0/src/raidlock/__init__.py +11 -0
- raidlock-0.1.0/src/raidlock/__main__.py +5 -0
- raidlock-0.1.0/src/raidlock/_python.py +58 -0
- raidlock-0.1.0/src/raidlock/achievements.py +156 -0
- raidlock-0.1.0/src/raidlock/approvals.py +237 -0
- raidlock-0.1.0/src/raidlock/bench.py +286 -0
- raidlock-0.1.0/src/raidlock/bridge/__init__.py +186 -0
- raidlock-0.1.0/src/raidlock/budgets.py +178 -0
- raidlock-0.1.0/src/raidlock/cli.py +2153 -0
- raidlock-0.1.0/src/raidlock/commands_install.py +114 -0
- raidlock-0.1.0/src/raidlock/core/__init__.py +26 -0
- raidlock-0.1.0/src/raidlock/core/advisories.py +16 -0
- raidlock-0.1.0/src/raidlock/core/billing.py +54 -0
- raidlock-0.1.0/src/raidlock/core/board.py +2251 -0
- raidlock-0.1.0/src/raidlock/core/brief.py +111 -0
- raidlock-0.1.0/src/raidlock/core/clock.py +40 -0
- raidlock-0.1.0/src/raidlock/core/cost.py +198 -0
- raidlock-0.1.0/src/raidlock/core/db.py +608 -0
- raidlock-0.1.0/src/raidlock/core/errors.py +52 -0
- raidlock-0.1.0/src/raidlock/core/exe.py +6 -0
- raidlock-0.1.0/src/raidlock/core/hints.py +32 -0
- raidlock-0.1.0/src/raidlock/core/identity.py +285 -0
- raidlock-0.1.0/src/raidlock/core/lead.py +758 -0
- raidlock-0.1.0/src/raidlock/core/lead_env.py +23 -0
- raidlock-0.1.0/src/raidlock/core/lead_hook.py +42 -0
- raidlock-0.1.0/src/raidlock/core/leases.py +19 -0
- raidlock-0.1.0/src/raidlock/core/lock.py +99 -0
- raidlock-0.1.0/src/raidlock/core/messages.py +98 -0
- raidlock-0.1.0/src/raidlock/core/migrate.py +579 -0
- raidlock-0.1.0/src/raidlock/core/model.py +126 -0
- raidlock-0.1.0/src/raidlock/core/models.py +109 -0
- raidlock-0.1.0/src/raidlock/core/paths.py +61 -0
- raidlock-0.1.0/src/raidlock/core/portable.py +53 -0
- raidlock-0.1.0/src/raidlock/core/receipts.py +73 -0
- raidlock-0.1.0/src/raidlock/core/registry.py +39 -0
- raidlock-0.1.0/src/raidlock/core/repos.py +250 -0
- raidlock-0.1.0/src/raidlock/core/safeio.py +201 -0
- raidlock-0.1.0/src/raidlock/core/status.py +52 -0
- raidlock-0.1.0/src/raidlock/core/store.py +107 -0
- raidlock-0.1.0/src/raidlock/core/tokens.py +77 -0
- raidlock-0.1.0/src/raidlock/core/transcript.py +208 -0
- raidlock-0.1.0/src/raidlock/duel.py +371 -0
- raidlock-0.1.0/src/raidlock/foresight.py +191 -0
- raidlock-0.1.0/src/raidlock/frames.py +162 -0
- raidlock-0.1.0/src/raidlock/gitguard.py +753 -0
- raidlock-0.1.0/src/raidlock/guard.py +239 -0
- raidlock-0.1.0/src/raidlock/hooks.py +1526 -0
- raidlock-0.1.0/src/raidlock/infer.py +205 -0
- raidlock-0.1.0/src/raidlock/limits.py +685 -0
- raidlock-0.1.0/src/raidlock/lore/__init__.py +22 -0
- raidlock-0.1.0/src/raidlock/lore/approval.py +145 -0
- raidlock-0.1.0/src/raidlock/lore/capture.py +146 -0
- raidlock-0.1.0/src/raidlock/lore/cli.py +109 -0
- raidlock-0.1.0/src/raidlock/lore/distill.py +17 -0
- raidlock-0.1.0/src/raidlock/lore/frontmatter.py +56 -0
- raidlock-0.1.0/src/raidlock/lore/inject.py +127 -0
- raidlock-0.1.0/src/raidlock/lore/vault.py +264 -0
- raidlock-0.1.0/src/raidlock/mcp/__init__.py +34 -0
- raidlock-0.1.0/src/raidlock/mcp/resources.py +72 -0
- raidlock-0.1.0/src/raidlock/mcp/server.py +184 -0
- raidlock-0.1.0/src/raidlock/mcp/tools.py +178 -0
- raidlock-0.1.0/src/raidlock/notify.py +144 -0
- raidlock-0.1.0/src/raidlock/party.py +239 -0
- raidlock-0.1.0/src/raidlock/pr.py +575 -0
- raidlock-0.1.0/src/raidlock/prsync.py +318 -0
- raidlock-0.1.0/src/raidlock/recipes/README.md +34 -0
- raidlock-0.1.0/src/raidlock/recipes/__init__.py +105 -0
- raidlock-0.1.0/src/raidlock/recipes/docs-refresh.md +15 -0
- raidlock-0.1.0/src/raidlock/recipes/multi-repo-refactor.md +15 -0
- raidlock-0.1.0/src/raidlock/recipes/security-audit.md +27 -0
- raidlock-0.1.0/src/raidlock/recipes/upgrade-deps.md +15 -0
- raidlock-0.1.0/src/raidlock/reputation.py +194 -0
- raidlock-0.1.0/src/raidlock/resume.py +329 -0
- raidlock-0.1.0/src/raidlock/resurrect.py +419 -0
- raidlock-0.1.0/src/raidlock/routing.py +419 -0
- raidlock-0.1.0/src/raidlock/runners/__init__.py +16 -0
- raidlock-0.1.0/src/raidlock/runners/base.py +341 -0
- raidlock-0.1.0/src/raidlock/runners/brief.py +176 -0
- raidlock-0.1.0/src/raidlock/runners/claude_code.py +121 -0
- raidlock-0.1.0/src/raidlock/runners/cli.py +110 -0
- raidlock-0.1.0/src/raidlock/runners/codex.py +114 -0
- raidlock-0.1.0/src/raidlock/runners/gemini.py +64 -0
- raidlock-0.1.0/src/raidlock/runners/isolation.py +391 -0
- raidlock-0.1.0/src/raidlock/runners/policy.py +123 -0
- raidlock-0.1.0/src/raidlock/runners/runner.py +921 -0
- raidlock-0.1.0/src/raidlock/runners/shell.py +35 -0
- raidlock-0.1.0/src/raidlock/runners/verifycache.py +93 -0
- raidlock-0.1.0/src/raidlock/runners/workspace.py +376 -0
- raidlock-0.1.0/src/raidlock/scan.py +357 -0
- raidlock-0.1.0/src/raidlock/snapshot.py +151 -0
- raidlock-0.1.0/src/raidlock/treasury.py +210 -0
- raidlock-0.1.0/src/raidlock/tui.py +223 -0
- raidlock-0.1.0/src/raidlock/web/__init__.py +5 -0
- raidlock-0.1.0/src/raidlock/web/achievements/view.css +19 -0
- raidlock-0.1.0/src/raidlock/web/achievements/view.js +58 -0
- raidlock-0.1.0/src/raidlock/web/bosses/view.css +19 -0
- raidlock-0.1.0/src/raidlock/web/bosses/view.js +46 -0
- raidlock-0.1.0/src/raidlock/web/cli.py +90 -0
- raidlock-0.1.0/src/raidlock/web/data.py +687 -0
- raidlock-0.1.0/src/raidlock/web/export.py +153 -0
- raidlock-0.1.0/src/raidlock/web/frames/view.css +25 -0
- raidlock-0.1.0/src/raidlock/web/frames/view.js +63 -0
- raidlock-0.1.0/src/raidlock/web/graph/__init__.py +142 -0
- raidlock-0.1.0/src/raidlock/web/graph/view.css +33 -0
- raidlock-0.1.0/src/raidlock/web/graph/view.js +136 -0
- raidlock-0.1.0/src/raidlock/web/raidmap/__init__.py +205 -0
- raidlock-0.1.0/src/raidlock/web/raidmap/view.css +15 -0
- raidlock-0.1.0/src/raidlock/web/raidmap/view.js +47 -0
- raidlock-0.1.0/src/raidlock/web/replay/__init__.py +258 -0
- raidlock-0.1.0/src/raidlock/web/replay/view.css +13 -0
- raidlock-0.1.0/src/raidlock/web/replay/view.js +127 -0
- raidlock-0.1.0/src/raidlock/web/server.py +292 -0
- raidlock-0.1.0/src/raidlock/web/static/app.css +851 -0
- raidlock-0.1.0/src/raidlock/web/static/app.js +2102 -0
- raidlock-0.1.0/src/raidlock/web/static/fonts/OFL.txt +93 -0
- raidlock-0.1.0/src/raidlock/web/static/fonts/cinzel-600.woff2 +0 -0
- raidlock-0.1.0/src/raidlock/web/static/fonts/cinzel-700.woff2 +0 -0
- raidlock-0.1.0/src/raidlock/web/static/icon-32.png +0 -0
- raidlock-0.1.0/src/raidlock/web/static/icon-raid.svg +1 -0
- raidlock-0.1.0/src/raidlock/web/static/icon.svg +1 -0
- raidlock-0.1.0/src/raidlock/web/static/index.html +122 -0
- raidlock-0.1.0/tests/achievements/conftest.py +9 -0
- raidlock-0.1.0/tests/achievements/test_achievements.py +204 -0
- raidlock-0.1.0/tests/approvals/conftest.py +33 -0
- raidlock-0.1.0/tests/approvals/test_approvals.py +172 -0
- raidlock-0.1.0/tests/bench/budget.json +106 -0
- raidlock-0.1.0/tests/bench/test_overhead.py +88 -0
- raidlock-0.1.0/tests/budgets/test_budgets.py +195 -0
- raidlock-0.1.0/tests/conftest.py +9 -0
- raidlock-0.1.0/tests/core/conftest.py +86 -0
- raidlock-0.1.0/tests/core/corehelpers.py +59 -0
- raidlock-0.1.0/tests/core/test_advisories.py +43 -0
- raidlock-0.1.0/tests/core/test_brief_untrusted.py +25 -0
- raidlock-0.1.0/tests/core/test_bug_sweep.py +197 -0
- raidlock-0.1.0/tests/core/test_cli.py +349 -0
- raidlock-0.1.0/tests/core/test_cli_extensions.py +72 -0
- raidlock-0.1.0/tests/core/test_cli_safe_credentials.py +21 -0
- raidlock-0.1.0/tests/core/test_cli_team.py +262 -0
- raidlock-0.1.0/tests/core/test_cli_ux.py +241 -0
- raidlock-0.1.0/tests/core/test_concurrency.py +98 -0
- raidlock-0.1.0/tests/core/test_cost.py +184 -0
- raidlock-0.1.0/tests/core/test_db_initialization.py +32 -0
- raidlock-0.1.0/tests/core/test_handover_security.py +208 -0
- raidlock-0.1.0/tests/core/test_identity.py +145 -0
- raidlock-0.1.0/tests/core/test_lead_token.py +117 -0
- raidlock-0.1.0/tests/core/test_leases.py +235 -0
- raidlock-0.1.0/tests/core/test_long_loops.py +36 -0
- raidlock-0.1.0/tests/core/test_messages.py +127 -0
- raidlock-0.1.0/tests/core/test_migration.py +658 -0
- raidlock-0.1.0/tests/core/test_model.py +269 -0
- raidlock-0.1.0/tests/core/test_multi_agent_collaboration.py +340 -0
- raidlock-0.1.0/tests/core/test_paths.py +134 -0
- raidlock-0.1.0/tests/core/test_portable.py +71 -0
- raidlock-0.1.0/tests/core/test_process_anchor.py +207 -0
- raidlock-0.1.0/tests/core/test_release_audit.py +310 -0
- raidlock-0.1.0/tests/core/test_safeio.py +82 -0
- raidlock-0.1.0/tests/core/test_scale.py +237 -0
- raidlock-0.1.0/tests/core/test_status_registry.py +120 -0
- raidlock-0.1.0/tests/core/test_store_lock.py +111 -0
- raidlock-0.1.0/tests/core/test_transcript.py +150 -0
- raidlock-0.1.0/tests/core/test_transcript_events.py +37 -0
- raidlock-0.1.0/tests/core/test_ui_host.py +66 -0
- raidlock-0.1.0/tests/core/test_verification_membership.py +110 -0
- raidlock-0.1.0/tests/core/test_verify_cache.py +216 -0
- raidlock-0.1.0/tests/core/test_verify_receipts.py +290 -0
- raidlock-0.1.0/tests/duel/conftest.py +33 -0
- raidlock-0.1.0/tests/duel/test_duel.py +242 -0
- raidlock-0.1.0/tests/e2e/test_demo.py +70 -0
- raidlock-0.1.0/tests/enforce/README.md +44 -0
- raidlock-0.1.0/tests/enforce/conftest.py +51 -0
- raidlock-0.1.0/tests/enforce/test_must_not.py +316 -0
- raidlock-0.1.0/tests/examples/test_demo_60s.py +77 -0
- raidlock-0.1.0/tests/examples/test_playground.py +76 -0
- raidlock-0.1.0/tests/extras/test_notify_snapshot.py +328 -0
- raidlock-0.1.0/tests/fixtures/.gitattributes +1 -0
- raidlock-0.1.0/tests/fixtures/v1-board/LOG.md +16 -0
- raidlock-0.1.0/tests/fixtures/v1-board/agents.json +27 -0
- raidlock-0.1.0/tests/fixtures/v1-board/cards/active.md +14 -0
- raidlock-0.1.0/tests/fixtures/v1-board/cards/checking.md +14 -0
- raidlock-0.1.0/tests/fixtures/v1-board/cards/finished.md +14 -0
- raidlock-0.1.0/tests/fixtures/v1-board/cards/first.md +24 -0
- raidlock-0.1.0/tests/fixtures/v1-board/cards/queued.md +14 -0
- raidlock-0.1.0/tests/fixtures/v1-board/cards/second.md +21 -0
- raidlock-0.1.0/tests/fixtures/v1-board/cards/waiting.md +14 -0
- raidlock-0.1.0/tests/fixtures/v1-board/inbox/w-one.jsonl +1 -0
- raidlock-0.1.0/tests/fixtures/v1-board/inbox/worker.jsonl +1 -0
- raidlock-0.1.0/tests/fixtures/v1-board/leases.json +34 -0
- raidlock-0.1.0/tests/fixtures/v1-board/settings.json +7 -0
- raidlock-0.1.0/tests/fixtures/v1-board/teams.json +12 -0
- raidlock-0.1.0/tests/foresight/test_foresight.py +210 -0
- raidlock-0.1.0/tests/frames/conftest.py +9 -0
- raidlock-0.1.0/tests/frames/test_frames.py +119 -0
- raidlock-0.1.0/tests/guard/test_guard.py +331 -0
- raidlock-0.1.0/tests/guard/test_guard_security.py +91 -0
- raidlock-0.1.0/tests/hooks/conftest.py +168 -0
- raidlock-0.1.0/tests/hooks/fixtures/post_claim.json +1 -0
- raidlock-0.1.0/tests/hooks/fixtures/pre_bash_board_write.json +1 -0
- raidlock-0.1.0/tests/hooks/fixtures/pre_bash_plain.json +1 -0
- raidlock-0.1.0/tests/hooks/fixtures/pre_bash_subagent_done.json +1 -0
- raidlock-0.1.0/tests/hooks/fixtures/pre_write_allow.json +1 -0
- raidlock-0.1.0/tests/hooks/fixtures/pre_write_board_file.json +1 -0
- raidlock-0.1.0/tests/hooks/fixtures/pre_write_main_free.json +1 -0
- raidlock-0.1.0/tests/hooks/fixtures/pre_write_main_held.json +1 -0
- raidlock-0.1.0/tests/hooks/fixtures/pre_write_no_task.json +1 -0
- raidlock-0.1.0/tests/hooks/fixtures/pre_write_notebook.json +1 -0
- raidlock-0.1.0/tests/hooks/fixtures/pre_write_other_fence.json +1 -0
- raidlock-0.1.0/tests/hooks/fixtures/session_start.json +1 -0
- raidlock-0.1.0/tests/hooks/fixtures/subagent_stop.json +1 -0
- raidlock-0.1.0/tests/hooks/test_compound_targets.py +74 -0
- raidlock-0.1.0/tests/hooks/test_git_guard.py +343 -0
- raidlock-0.1.0/tests/hooks/test_hook_interpreter.py +147 -0
- raidlock-0.1.0/tests/hooks/test_hook_security.py +358 -0
- raidlock-0.1.0/tests/hooks/test_hooks.py +396 -0
- raidlock-0.1.0/tests/hooks/test_install_commands.py +133 -0
- raidlock-0.1.0/tests/hooks/test_native_bridge.py +781 -0
- raidlock-0.1.0/tests/hooks/test_separate_session_worker.py +103 -0
- raidlock-0.1.0/tests/infer/test_infer.py +241 -0
- raidlock-0.1.0/tests/limits/conftest.py +14 -0
- raidlock-0.1.0/tests/limits/test_limits.py +345 -0
- raidlock-0.1.0/tests/lore/conftest.py +28 -0
- raidlock-0.1.0/tests/lore/lorehelpers.py +115 -0
- raidlock-0.1.0/tests/lore/test_lore_approval.py +188 -0
- raidlock-0.1.0/tests/lore/test_lore_capture.py +105 -0
- raidlock-0.1.0/tests/lore/test_lore_inject.py +95 -0
- raidlock-0.1.0/tests/lore/test_lore_vault.py +168 -0
- raidlock-0.1.0/tests/mcp/conftest.py +56 -0
- raidlock-0.1.0/tests/mcp/mcphelpers.py +32 -0
- raidlock-0.1.0/tests/mcp/test_mcp_protocol.py +238 -0
- raidlock-0.1.0/tests/mcp/test_mcp_resources.py +41 -0
- raidlock-0.1.0/tests/mcp/test_mcp_tools.py +141 -0
- raidlock-0.1.0/tests/mcp/test_mcp_workspace.py +63 -0
- raidlock-0.1.0/tests/party/conftest.py +9 -0
- raidlock-0.1.0/tests/party/test_party.py +210 -0
- raidlock-0.1.0/tests/portable.py +14 -0
- raidlock-0.1.0/tests/pr/conftest.py +26 -0
- raidlock-0.1.0/tests/pr/prhelpers.py +128 -0
- raidlock-0.1.0/tests/pr/test_pr.py +516 -0
- raidlock-0.1.0/tests/prsync/conftest.py +34 -0
- raidlock-0.1.0/tests/prsync/test_prsync.py +399 -0
- raidlock-0.1.0/tests/recipes/test_recipes.py +142 -0
- raidlock-0.1.0/tests/reputation/test_reputation.py +268 -0
- raidlock-0.1.0/tests/resume/conftest.py +33 -0
- raidlock-0.1.0/tests/resume/test_resume.py +291 -0
- raidlock-0.1.0/tests/resurrect/conftest.py +33 -0
- raidlock-0.1.0/tests/resurrect/fake_claude.py +42 -0
- raidlock-0.1.0/tests/resurrect/test_resurrect.py +363 -0
- raidlock-0.1.0/tests/routing/conftest.py +33 -0
- raidlock-0.1.0/tests/routing/test_routing.py +195 -0
- raidlock-0.1.0/tests/runners/conftest.py +24 -0
- raidlock-0.1.0/tests/runners/fake_agent.py +51 -0
- raidlock-0.1.0/tests/runners/fixtures/claude_read_only.jsonl +7 -0
- raidlock-0.1.0/tests/runners/fixtures/codex_read_only.jsonl +9 -0
- raidlock-0.1.0/tests/runners/fixtures/codex_workspace_write.jsonl +7 -0
- raidlock-0.1.0/tests/runners/runhelpers.py +103 -0
- raidlock-0.1.0/tests/runners/test_recovery_integration.py +72 -0
- raidlock-0.1.0/tests/runners/test_runner_adapters.py +232 -0
- raidlock-0.1.0/tests/runners/test_runner_brief.py +86 -0
- raidlock-0.1.0/tests/runners/test_runner_delegate.py +438 -0
- raidlock-0.1.0/tests/runners/test_runner_live.py +43 -0
- raidlock-0.1.0/tests/runners/test_runner_policy.py +76 -0
- raidlock-0.1.0/tests/runners/test_runner_security.py +597 -0
- raidlock-0.1.0/tests/runners/test_sensitive_disposal.py +76 -0
- raidlock-0.1.0/tests/runners/test_verify_cleanup.py +66 -0
- raidlock-0.1.0/tests/scan/fixtures/paths.patch +10 -0
- raidlock-0.1.0/tests/scan/fixtures/secrets.patch +12 -0
- raidlock-0.1.0/tests/scan/test_scan.py +199 -0
- raidlock-0.1.0/tests/treasury/conftest.py +9 -0
- raidlock-0.1.0/tests/treasury/test_nonfinite.py +22 -0
- raidlock-0.1.0/tests/treasury/test_treasury.py +138 -0
- raidlock-0.1.0/tests/tui/empty.txt +21 -0
- raidlock-0.1.0/tests/tui/populated.txt +26 -0
- raidlock-0.1.0/tests/tui/test_tui.py +198 -0
- raidlock-0.1.0/tests/web/browser.py +110 -0
- raidlock-0.1.0/tests/web/conftest.py +9 -0
- raidlock-0.1.0/tests/web/demo.py +398 -0
- raidlock-0.1.0/tests/web/fxfeed.py +105 -0
- raidlock-0.1.0/tests/web/graph/test_graph.py +253 -0
- raidlock-0.1.0/tests/web/layout_states.py +55 -0
- raidlock-0.1.0/tests/web/party/test_party_web.py +85 -0
- raidlock-0.1.0/tests/web/raidmap/test_raidmap.py +143 -0
- raidlock-0.1.0/tests/web/replay/test_replay.py +248 -0
- raidlock-0.1.0/tests/web/serving.py +105 -0
- raidlock-0.1.0/tests/web/test_approvals_web.py +28 -0
- raidlock-0.1.0/tests/web/test_focus_view.py +529 -0
- raidlock-0.1.0/tests/web/test_fx.py +163 -0
- raidlock-0.1.0/tests/web/test_layout_browser.py +136 -0
- raidlock-0.1.0/tests/web/test_layout_logic.py +145 -0
- raidlock-0.1.0/tests/web/test_pr_pill.py +39 -0
- raidlock-0.1.0/tests/web/test_web_browser.py +685 -0
- raidlock-0.1.0/tests/web/test_web_fds.py +61 -0
- raidlock-0.1.0/tests/web/test_web_features.py +166 -0
- raidlock-0.1.0/tests/web/test_web_server.py +428 -0
- raidlock-0.1.0/uv.lock +372 -0
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "raidlock",
|
|
3
|
+
"owner": {
|
|
4
|
+
"name": "agi1clj",
|
|
5
|
+
"url": "https://github.com/agi1clj"
|
|
6
|
+
},
|
|
7
|
+
"metadata": {
|
|
8
|
+
"description": "raidlock plugin for Claude Code"
|
|
9
|
+
},
|
|
10
|
+
"plugins": [
|
|
11
|
+
{
|
|
12
|
+
"name": "raidlock",
|
|
13
|
+
"source": "./",
|
|
14
|
+
"description": "Lease-and-review board for coding agents: path locks enforced by hooks, a lead-only done gate, heartbeats and handbacks.",
|
|
15
|
+
"version": "0.1.0",
|
|
16
|
+
"author": {
|
|
17
|
+
"name": "agi1clj"
|
|
18
|
+
},
|
|
19
|
+
"homepage": "https://github.com/agi1clj/raidlock",
|
|
20
|
+
"repository": "https://github.com/agi1clj/raidlock",
|
|
21
|
+
"license": "MIT"
|
|
22
|
+
}
|
|
23
|
+
]
|
|
24
|
+
}
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "raidlock",
|
|
3
|
+
"version": "0.1.0",
|
|
4
|
+
"description": "Lease-and-review board for coding agents: path locks enforced by hooks, a lead-only done gate, heartbeats and handbacks.",
|
|
5
|
+
"author": {
|
|
6
|
+
"name": "agi1clj",
|
|
7
|
+
"url": "https://github.com/agi1clj"
|
|
8
|
+
},
|
|
9
|
+
"homepage": "https://github.com/agi1clj/raidlock",
|
|
10
|
+
"repository": "https://github.com/agi1clj/raidlock",
|
|
11
|
+
"license": "MIT",
|
|
12
|
+
"keywords": ["agents", "coordination", "leases", "locks", "review"]
|
|
13
|
+
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
* @agi1clj
|
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
name: Bug report
|
|
2
|
+
description: Something does not work as documented.
|
|
3
|
+
labels: [bug]
|
|
4
|
+
body:
|
|
5
|
+
- type: textarea
|
|
6
|
+
id: what
|
|
7
|
+
attributes:
|
|
8
|
+
label: What happened
|
|
9
|
+
description: What you did, what you expected and what happened instead.
|
|
10
|
+
validations:
|
|
11
|
+
required: true
|
|
12
|
+
- type: textarea
|
|
13
|
+
id: repro
|
|
14
|
+
attributes:
|
|
15
|
+
label: Steps to reproduce
|
|
16
|
+
description: Commands, from a fresh board if possible. Do not paste secrets or private transcript content.
|
|
17
|
+
render: shell
|
|
18
|
+
validations:
|
|
19
|
+
required: true
|
|
20
|
+
- type: input
|
|
21
|
+
id: version
|
|
22
|
+
attributes:
|
|
23
|
+
label: raidlock version
|
|
24
|
+
placeholder: raidlock --version
|
|
25
|
+
validations:
|
|
26
|
+
required: true
|
|
27
|
+
- type: dropdown
|
|
28
|
+
id: os
|
|
29
|
+
attributes:
|
|
30
|
+
label: OS
|
|
31
|
+
options: [Linux, macOS, Windows, Other]
|
|
32
|
+
validations:
|
|
33
|
+
required: true
|
|
34
|
+
- type: input
|
|
35
|
+
id: python
|
|
36
|
+
attributes:
|
|
37
|
+
label: Python version
|
|
38
|
+
- type: dropdown
|
|
39
|
+
id: runtime
|
|
40
|
+
attributes:
|
|
41
|
+
label: Runtime involved
|
|
42
|
+
multiple: true
|
|
43
|
+
options: [Claude Code, Codex CLI, Gemini CLI, shell, web UI, none]
|
|
44
|
+
- type: textarea
|
|
45
|
+
id: logs
|
|
46
|
+
attributes:
|
|
47
|
+
label: Output
|
|
48
|
+
description: Error output or `--json` output.
|
|
49
|
+
render: text
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
name: Feature request
|
|
2
|
+
description: Suggest a change or new feature.
|
|
3
|
+
labels: [enhancement]
|
|
4
|
+
body:
|
|
5
|
+
- type: textarea
|
|
6
|
+
id: problem
|
|
7
|
+
attributes:
|
|
8
|
+
label: Problem
|
|
9
|
+
description: What are you trying to do, and what gets in the way today?
|
|
10
|
+
validations:
|
|
11
|
+
required: true
|
|
12
|
+
- type: textarea
|
|
13
|
+
id: proposal
|
|
14
|
+
attributes:
|
|
15
|
+
label: Proposal
|
|
16
|
+
description: What should raidlock do? Note any change to PROTOCOL.md.
|
|
17
|
+
validations:
|
|
18
|
+
required: true
|
|
19
|
+
- type: textarea
|
|
20
|
+
id: alternatives
|
|
21
|
+
attributes:
|
|
22
|
+
label: Alternatives considered
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
name: Runner adapter request
|
|
2
|
+
description: Ask for raidlock to delegate quests to another agent CLI.
|
|
3
|
+
labels: [runner-adapter]
|
|
4
|
+
body:
|
|
5
|
+
- type: input
|
|
6
|
+
id: cli
|
|
7
|
+
attributes:
|
|
8
|
+
label: Agent CLI
|
|
9
|
+
placeholder: name and link
|
|
10
|
+
validations:
|
|
11
|
+
required: true
|
|
12
|
+
- type: input
|
|
13
|
+
id: version
|
|
14
|
+
attributes:
|
|
15
|
+
label: CLI version tested
|
|
16
|
+
validations:
|
|
17
|
+
required: true
|
|
18
|
+
- type: textarea
|
|
19
|
+
id: headless
|
|
20
|
+
attributes:
|
|
21
|
+
label: Headless invocation
|
|
22
|
+
description: How to run it non-interactively with a prompt on stdin, a working directory and a model.
|
|
23
|
+
render: shell
|
|
24
|
+
validations:
|
|
25
|
+
required: true
|
|
26
|
+
- type: textarea
|
|
27
|
+
id: sandbox
|
|
28
|
+
attributes:
|
|
29
|
+
label: Sandbox and approval modes
|
|
30
|
+
description: Read-only and write modes, and how to keep approvals on. Links to the CLI's docs.
|
|
31
|
+
validations:
|
|
32
|
+
required: true
|
|
33
|
+
- type: textarea
|
|
34
|
+
id: events
|
|
35
|
+
attributes:
|
|
36
|
+
label: Machine-readable output
|
|
37
|
+
description: Event stream or JSON output format, structured output support, and where usage (tokens, cost) is reported.
|
|
38
|
+
- type: checkboxes
|
|
39
|
+
id: willing
|
|
40
|
+
attributes:
|
|
41
|
+
label: Contribution
|
|
42
|
+
options:
|
|
43
|
+
- label: I can open a pull request with the adapter and recorded-event tests
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
version: 2
|
|
2
|
+
updates:
|
|
3
|
+
- package-ecosystem: github-actions
|
|
4
|
+
directory: /
|
|
5
|
+
schedule:
|
|
6
|
+
interval: weekly
|
|
7
|
+
groups:
|
|
8
|
+
github-actions:
|
|
9
|
+
patterns: ["*"]
|
|
10
|
+
- package-ecosystem: pip
|
|
11
|
+
directory: /
|
|
12
|
+
schedule:
|
|
13
|
+
interval: weekly
|
|
14
|
+
groups:
|
|
15
|
+
python:
|
|
16
|
+
patterns: ["*"]
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
## What and why
|
|
2
|
+
|
|
3
|
+
## How it was tested
|
|
4
|
+
|
|
5
|
+
## Checklist
|
|
6
|
+
|
|
7
|
+
- [ ] Every commit is signed off (`git commit -s`)
|
|
8
|
+
- [ ] Tests added or updated; the suite passes locally
|
|
9
|
+
- [ ] `CHANGELOG.md` updated under Unreleased (if users would notice)
|
|
10
|
+
- [ ] Docs updated (README, PROTOCOL.md, docs/guides) if behavior changed
|
|
11
|
+
- [ ] PROTOCOL.md changes called out above
|
|
12
|
+
- [ ] No code comments, no new runtime dependency, no secrets or real board data in fixtures
|
|
13
|
+
- [ ] Workflow changes pass actionlint and pin actions to commit SHAs
|
|
@@ -0,0 +1,175 @@
|
|
|
1
|
+
name: CI
|
|
2
|
+
|
|
3
|
+
on:
|
|
4
|
+
push:
|
|
5
|
+
branches: [main]
|
|
6
|
+
pull_request:
|
|
7
|
+
workflow_dispatch:
|
|
8
|
+
|
|
9
|
+
permissions:
|
|
10
|
+
contents: read
|
|
11
|
+
|
|
12
|
+
concurrency:
|
|
13
|
+
group: ci-${{ github.ref }}
|
|
14
|
+
cancel-in-progress: true
|
|
15
|
+
|
|
16
|
+
env:
|
|
17
|
+
PYTHONUTF8: "1"
|
|
18
|
+
UV_NO_PROGRESS: "1"
|
|
19
|
+
|
|
20
|
+
jobs:
|
|
21
|
+
actionlint:
|
|
22
|
+
name: actionlint
|
|
23
|
+
runs-on: ubuntu-latest
|
|
24
|
+
timeout-minutes: 5
|
|
25
|
+
env:
|
|
26
|
+
ACTIONLINT_VERSION: 1.7.12
|
|
27
|
+
ACTIONLINT_SHA256: 8aca8db96f1b94770f1b0d72b6dddcb1ebb8123cb3712530b08cc387b349a3d8
|
|
28
|
+
steps:
|
|
29
|
+
- uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1
|
|
30
|
+
with:
|
|
31
|
+
persist-credentials: false
|
|
32
|
+
- name: Install actionlint
|
|
33
|
+
run: |
|
|
34
|
+
archive="actionlint_${ACTIONLINT_VERSION}_linux_amd64.tar.gz"
|
|
35
|
+
curl -fsSLo "$archive" "https://github.com/rhysd/actionlint/releases/download/v${ACTIONLINT_VERSION}/${archive}"
|
|
36
|
+
echo "${ACTIONLINT_SHA256} ${archive}" | sha256sum -c -
|
|
37
|
+
tar -xzf "$archive" actionlint
|
|
38
|
+
- name: Run actionlint
|
|
39
|
+
run: ./actionlint -color
|
|
40
|
+
|
|
41
|
+
test:
|
|
42
|
+
name: test (${{ matrix.os }}, py${{ matrix.python }})
|
|
43
|
+
runs-on: ${{ matrix.os }}
|
|
44
|
+
timeout-minutes: 30
|
|
45
|
+
continue-on-error: ${{ matrix.os == 'windows-latest' }}
|
|
46
|
+
strategy:
|
|
47
|
+
fail-fast: false
|
|
48
|
+
matrix:
|
|
49
|
+
os: [ubuntu-latest, macos-latest]
|
|
50
|
+
python: ["3.11", "3.12", "3.13", "3.14", "3.15"]
|
|
51
|
+
include:
|
|
52
|
+
- os: windows-latest
|
|
53
|
+
python: "3.11"
|
|
54
|
+
defaults:
|
|
55
|
+
run:
|
|
56
|
+
shell: bash
|
|
57
|
+
steps:
|
|
58
|
+
- uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1
|
|
59
|
+
with:
|
|
60
|
+
persist-credentials: false
|
|
61
|
+
- uses: astral-sh/setup-uv@07a047e608db84b3d8c06cd9a7c7dcc9c355c18e
|
|
62
|
+
with:
|
|
63
|
+
python-version: ${{ matrix.python }}
|
|
64
|
+
- name: Run tests
|
|
65
|
+
run: uv run --locked pytest --ignore=tests/web
|
|
66
|
+
|
|
67
|
+
playwright:
|
|
68
|
+
name: web UI (Playwright)
|
|
69
|
+
runs-on: ubuntu-latest
|
|
70
|
+
timeout-minutes: 20
|
|
71
|
+
steps:
|
|
72
|
+
- uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1
|
|
73
|
+
with:
|
|
74
|
+
persist-credentials: false
|
|
75
|
+
- uses: astral-sh/setup-uv@07a047e608db84b3d8c06cd9a7c7dcc9c355c18e
|
|
76
|
+
with:
|
|
77
|
+
python-version: "3.13"
|
|
78
|
+
- name: Install browser
|
|
79
|
+
run: |
|
|
80
|
+
uv sync --locked --extra ui-test
|
|
81
|
+
uv run --locked playwright install --with-deps chromium
|
|
82
|
+
- name: Run web tests
|
|
83
|
+
run: uv run --locked pytest tests/web
|
|
84
|
+
- name: Upload traces on failure
|
|
85
|
+
if: failure()
|
|
86
|
+
uses: actions/upload-artifact@cf430e030ddbb5b0abf93d22962f4752f3646cd9
|
|
87
|
+
with:
|
|
88
|
+
name: playwright-results
|
|
89
|
+
path: test-results/
|
|
90
|
+
if-no-files-found: ignore
|
|
91
|
+
retention-days: 7
|
|
92
|
+
|
|
93
|
+
lint:
|
|
94
|
+
runs-on: ubuntu-latest
|
|
95
|
+
timeout-minutes: 10
|
|
96
|
+
steps:
|
|
97
|
+
- uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1
|
|
98
|
+
with:
|
|
99
|
+
persist-credentials: false
|
|
100
|
+
- uses: astral-sh/setup-uv@07a047e608db84b3d8c06cd9a7c7dcc9c355c18e
|
|
101
|
+
with:
|
|
102
|
+
python-version: "3.11"
|
|
103
|
+
- name: Ruff lint
|
|
104
|
+
run: uv run --locked --with ruff==0.15.14 ruff check
|
|
105
|
+
- name: Ruff format
|
|
106
|
+
if: always()
|
|
107
|
+
run: uv run --locked --with ruff==0.15.14 ruff format --check
|
|
108
|
+
|
|
109
|
+
overhead:
|
|
110
|
+
name: idle overhead
|
|
111
|
+
runs-on: ubuntu-latest
|
|
112
|
+
timeout-minutes: 10
|
|
113
|
+
steps:
|
|
114
|
+
- uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1
|
|
115
|
+
with:
|
|
116
|
+
persist-credentials: false
|
|
117
|
+
- uses: astral-sh/setup-uv@07a047e608db84b3d8c06cd9a7c7dcc9c355c18e
|
|
118
|
+
with:
|
|
119
|
+
python-version: "3.11"
|
|
120
|
+
- name: Measure idle overhead
|
|
121
|
+
run: |
|
|
122
|
+
uv run --locked python scripts/bench_overhead.py --runs 5 --tokenizer estimate > overhead.json 2> overhead.md
|
|
123
|
+
head -n 1 overhead.md
|
|
124
|
+
cat overhead.md >> "$GITHUB_STEP_SUMMARY"
|
|
125
|
+
|
|
126
|
+
types:
|
|
127
|
+
runs-on: ubuntu-latest
|
|
128
|
+
timeout-minutes: 10
|
|
129
|
+
steps:
|
|
130
|
+
- uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1
|
|
131
|
+
with:
|
|
132
|
+
persist-credentials: false
|
|
133
|
+
- uses: astral-sh/setup-uv@07a047e608db84b3d8c06cd9a7c7dcc9c355c18e
|
|
134
|
+
with:
|
|
135
|
+
python-version: "3.11"
|
|
136
|
+
- name: Pyright
|
|
137
|
+
run: uv run --locked --with pyright==1.1.408 pyright src/raidlock
|
|
138
|
+
|
|
139
|
+
docker:
|
|
140
|
+
name: docker image
|
|
141
|
+
continue-on-error: true
|
|
142
|
+
runs-on: ubuntu-latest
|
|
143
|
+
timeout-minutes: 20
|
|
144
|
+
env:
|
|
145
|
+
IMAGE: raidlock:ci
|
|
146
|
+
TRIVY_VERSION: 0.75.0
|
|
147
|
+
TRIVY_SHA256: c6e65abddb348e25f10549df887045629cf28cc72453cd1c63acb717316b3f3f
|
|
148
|
+
steps:
|
|
149
|
+
- uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1
|
|
150
|
+
with:
|
|
151
|
+
persist-credentials: false
|
|
152
|
+
- name: Build image
|
|
153
|
+
run: docker build --platform linux/amd64 -t "$IMAGE" .
|
|
154
|
+
- name: Allow unprivileged user namespaces
|
|
155
|
+
run: |
|
|
156
|
+
if [ -e /proc/sys/kernel/apparmor_restrict_unprivileged_userns ]; then
|
|
157
|
+
sudo sysctl -w kernel.apparmor_restrict_unprivileged_userns=0
|
|
158
|
+
fi
|
|
159
|
+
- name: Smoke test in a hardened container
|
|
160
|
+
run: |
|
|
161
|
+
docker run --rm --read-only --cap-drop ALL --security-opt no-new-privileges \
|
|
162
|
+
--security-opt apparmor=unconfined --network none \
|
|
163
|
+
--tmpfs /tmp:uid=10001,gid=10001,mode=1777 \
|
|
164
|
+
--tmpfs /home/raid:uid=10001,gid=10001,mode=0700 \
|
|
165
|
+
--tmpfs /workspace:uid=10001,gid=10001,mode=0700 \
|
|
166
|
+
-v "$PWD/scripts/docker-smoke.sh:/smoke.sh:ro" \
|
|
167
|
+
--entrypoint sh "$IMAGE" /smoke.sh
|
|
168
|
+
- name: Install Trivy
|
|
169
|
+
run: |
|
|
170
|
+
archive="trivy_${TRIVY_VERSION}_Linux-64bit.tar.gz"
|
|
171
|
+
curl -fsSLo "$archive" "https://github.com/aquasecurity/trivy/releases/download/v${TRIVY_VERSION}/${archive}"
|
|
172
|
+
echo "${TRIVY_SHA256} ${archive}" | sha256sum -c -
|
|
173
|
+
tar -xzf "$archive" trivy
|
|
174
|
+
- name: Trivy image scan
|
|
175
|
+
run: ./trivy image --exit-code 1 --severity HIGH,CRITICAL --ignore-unfixed --no-progress "$IMAGE"
|
|
@@ -0,0 +1,63 @@
|
|
|
1
|
+
name: Docker publish
|
|
2
|
+
|
|
3
|
+
on:
|
|
4
|
+
push:
|
|
5
|
+
tags: ["v*"]
|
|
6
|
+
|
|
7
|
+
permissions:
|
|
8
|
+
contents: read
|
|
9
|
+
|
|
10
|
+
concurrency:
|
|
11
|
+
group: docker-publish-${{ github.ref }}
|
|
12
|
+
cancel-in-progress: false
|
|
13
|
+
|
|
14
|
+
env:
|
|
15
|
+
IMAGE: ghcr.io/agi1clj/raidlock
|
|
16
|
+
|
|
17
|
+
jobs:
|
|
18
|
+
publish:
|
|
19
|
+
name: Build, sign and push
|
|
20
|
+
runs-on: ubuntu-latest
|
|
21
|
+
timeout-minutes: 45
|
|
22
|
+
permissions:
|
|
23
|
+
contents: read
|
|
24
|
+
packages: write
|
|
25
|
+
id-token: write
|
|
26
|
+
steps:
|
|
27
|
+
- uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1
|
|
28
|
+
with:
|
|
29
|
+
persist-credentials: false
|
|
30
|
+
- name: Check tag matches project version
|
|
31
|
+
run: |
|
|
32
|
+
version="$(python3 -c 'import runpy; print(runpy.run_path("src/raidlock/__init__.py")["__version__"])')"
|
|
33
|
+
if [ "${GITHUB_REF_NAME#v}" != "$version" ]; then
|
|
34
|
+
echo "::error::tag ${GITHUB_REF_NAME} does not match project version ${version}"
|
|
35
|
+
exit 1
|
|
36
|
+
fi
|
|
37
|
+
echo "VERSION=${version}" >> "$GITHUB_ENV"
|
|
38
|
+
- uses: docker/setup-qemu-action@99012661954931238ded8c8b007157a8430204e1
|
|
39
|
+
- uses: docker/setup-buildx-action@f87e5991a6d7451dcb8d9637bfbc97413f497069
|
|
40
|
+
- uses: docker/login-action@dbcb813823bdd20940b903addbd779551569679f
|
|
41
|
+
with:
|
|
42
|
+
registry: ghcr.io
|
|
43
|
+
username: ${{ github.actor }}
|
|
44
|
+
password: ${{ github.token }}
|
|
45
|
+
- name: Build and push
|
|
46
|
+
id: build
|
|
47
|
+
uses: docker/build-push-action@c3c9e263c25d99ce0380d002d59b67737d91b0dc
|
|
48
|
+
with:
|
|
49
|
+
context: .
|
|
50
|
+
platforms: linux/amd64,linux/arm64
|
|
51
|
+
push: true
|
|
52
|
+
sbom: true
|
|
53
|
+
provenance: mode=max
|
|
54
|
+
tags: |
|
|
55
|
+
${{ env.IMAGE }}:${{ env.VERSION }}
|
|
56
|
+
${{ env.IMAGE }}:latest
|
|
57
|
+
- uses: sigstore/cosign-installer@6f9f17788090df1f26f669e9d70d6ae9567deba6
|
|
58
|
+
with:
|
|
59
|
+
cosign-release: v3.1.3
|
|
60
|
+
- name: Sign image
|
|
61
|
+
env:
|
|
62
|
+
DIGEST: ${{ steps.build.outputs.digest }}
|
|
63
|
+
run: cosign sign --yes "${IMAGE}@${DIGEST}"
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
name: PR title
|
|
2
|
+
|
|
3
|
+
on:
|
|
4
|
+
pull_request_target:
|
|
5
|
+
types: [opened, edited, synchronize, reopened, ready_for_review]
|
|
6
|
+
|
|
7
|
+
permissions:
|
|
8
|
+
pull-requests: read
|
|
9
|
+
|
|
10
|
+
jobs:
|
|
11
|
+
title:
|
|
12
|
+
runs-on: ubuntu-latest
|
|
13
|
+
steps:
|
|
14
|
+
- uses: amannn/action-semantic-pull-request@48f256284bd46cdaab1048c3721360e808335d50
|
|
15
|
+
env:
|
|
16
|
+
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
|
17
|
+
with:
|
|
18
|
+
types: |
|
|
19
|
+
feat
|
|
20
|
+
fix
|
|
21
|
+
docs
|
|
22
|
+
test
|
|
23
|
+
refactor
|
|
24
|
+
perf
|
|
25
|
+
ci
|
|
26
|
+
build
|
|
27
|
+
chore
|
|
28
|
+
revert
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
name: Release please
|
|
2
|
+
|
|
3
|
+
on:
|
|
4
|
+
push:
|
|
5
|
+
branches: [main]
|
|
6
|
+
|
|
7
|
+
permissions:
|
|
8
|
+
contents: write
|
|
9
|
+
pull-requests: write
|
|
10
|
+
|
|
11
|
+
jobs:
|
|
12
|
+
release-please:
|
|
13
|
+
runs-on: ubuntu-latest
|
|
14
|
+
steps:
|
|
15
|
+
- uses: googleapis/release-please-action@45996ed1f6d02564a971a2fa1b5860e934307cf7
|
|
16
|
+
with:
|
|
17
|
+
token: ${{ secrets.RELEASE_PLEASE_TOKEN || github.token }}
|
|
18
|
+
config-file: release-please-config.json
|
|
19
|
+
manifest-file: .release-please-manifest.json
|
|
@@ -0,0 +1,118 @@
|
|
|
1
|
+
name: Release
|
|
2
|
+
|
|
3
|
+
on:
|
|
4
|
+
push:
|
|
5
|
+
tags: ["v*"]
|
|
6
|
+
|
|
7
|
+
permissions:
|
|
8
|
+
contents: read
|
|
9
|
+
|
|
10
|
+
concurrency:
|
|
11
|
+
group: release-${{ github.ref }}
|
|
12
|
+
cancel-in-progress: false
|
|
13
|
+
|
|
14
|
+
jobs:
|
|
15
|
+
build:
|
|
16
|
+
name: Build sdist and wheel
|
|
17
|
+
runs-on: ubuntu-latest
|
|
18
|
+
timeout-minutes: 10
|
|
19
|
+
steps:
|
|
20
|
+
- uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1
|
|
21
|
+
with:
|
|
22
|
+
persist-credentials: false
|
|
23
|
+
- uses: astral-sh/setup-uv@07a047e608db84b3d8c06cd9a7c7dcc9c355c18e
|
|
24
|
+
with:
|
|
25
|
+
python-version: "3.13"
|
|
26
|
+
- name: Check tag matches project version
|
|
27
|
+
run: |
|
|
28
|
+
version="$(python -c 'import runpy; print(runpy.run_path("src/raidlock/__init__.py")["__version__"])')"
|
|
29
|
+
if [ "${GITHUB_REF_NAME#v}" != "$version" ]; then
|
|
30
|
+
echo "::error::tag ${GITHUB_REF_NAME} does not match project version ${version}"
|
|
31
|
+
exit 1
|
|
32
|
+
fi
|
|
33
|
+
- name: Check distribution metadata versions
|
|
34
|
+
run: |
|
|
35
|
+
python - <<'PYTHON'
|
|
36
|
+
import json
|
|
37
|
+
import runpy
|
|
38
|
+
import tomllib
|
|
39
|
+
from pathlib import Path
|
|
40
|
+
version = runpy.run_path("src/raidlock/__init__.py")["__version__"]
|
|
41
|
+
plugin = json.loads(Path(".claude-plugin/plugin.json").read_text())
|
|
42
|
+
marketplace = json.loads(Path(".claude-plugin/marketplace.json").read_text())
|
|
43
|
+
lock = tomllib.loads(Path("uv.lock").read_text())
|
|
44
|
+
project = tomllib.loads(Path("pyproject.toml").read_text())
|
|
45
|
+
assert project["project"]["version"] == version
|
|
46
|
+
assert plugin["version"] == version
|
|
47
|
+
assert all(p["version"] == version for p in marketplace["plugins"])
|
|
48
|
+
assert next(p["version"] for p in lock["package"] if p["name"] == "raidlock") == version
|
|
49
|
+
PYTHON
|
|
50
|
+
- name: Build
|
|
51
|
+
run: uv build
|
|
52
|
+
- name: Extract release notes from CHANGELOG
|
|
53
|
+
run: |
|
|
54
|
+
version="${GITHUB_REF_NAME#v}"
|
|
55
|
+
awk -v v="$version" '
|
|
56
|
+
index($0, "## [" v "]") == 1 { found = 1; next }
|
|
57
|
+
found && /^## \[/ { exit }
|
|
58
|
+
found && /^\[[^]]+\]: / { exit }
|
|
59
|
+
found { print }
|
|
60
|
+
' CHANGELOG.md > dist/RELEASE_NOTES.md
|
|
61
|
+
if [ ! -s dist/RELEASE_NOTES.md ]; then
|
|
62
|
+
echo "::error::no CHANGELOG.md section for ${version}"
|
|
63
|
+
exit 1
|
|
64
|
+
fi
|
|
65
|
+
- uses: actions/upload-artifact@cf430e030ddbb5b0abf93d22962f4752f3646cd9
|
|
66
|
+
with:
|
|
67
|
+
name: dist
|
|
68
|
+
path: dist/
|
|
69
|
+
if-no-files-found: error
|
|
70
|
+
retention-days: 7
|
|
71
|
+
|
|
72
|
+
pypi:
|
|
73
|
+
name: Publish to PyPI
|
|
74
|
+
needs: build
|
|
75
|
+
runs-on: ubuntu-latest
|
|
76
|
+
timeout-minutes: 10
|
|
77
|
+
environment:
|
|
78
|
+
name: pypi
|
|
79
|
+
url: https://pypi.org/p/raidlock
|
|
80
|
+
permissions:
|
|
81
|
+
id-token: write
|
|
82
|
+
steps:
|
|
83
|
+
- uses: actions/download-artifact@9000827ccba6bdab643e8b6fd33ac0654aef8333
|
|
84
|
+
with:
|
|
85
|
+
name: dist
|
|
86
|
+
path: dist/
|
|
87
|
+
- name: Keep only distributions
|
|
88
|
+
run: rm -f dist/RELEASE_NOTES.md
|
|
89
|
+
- uses: pypa/gh-action-pypi-publish@7245906fb61fa33a13554f9d5fb856fe61758086
|
|
90
|
+
with:
|
|
91
|
+
attestations: true
|
|
92
|
+
|
|
93
|
+
github-release:
|
|
94
|
+
name: GitHub release
|
|
95
|
+
needs: pypi
|
|
96
|
+
runs-on: ubuntu-latest
|
|
97
|
+
timeout-minutes: 10
|
|
98
|
+
permissions:
|
|
99
|
+
contents: write
|
|
100
|
+
steps:
|
|
101
|
+
- uses: actions/download-artifact@9000827ccba6bdab643e8b6fd33ac0654aef8333
|
|
102
|
+
with:
|
|
103
|
+
name: dist
|
|
104
|
+
path: dist/
|
|
105
|
+
- name: Create release
|
|
106
|
+
env:
|
|
107
|
+
GH_TOKEN: ${{ github.token }}
|
|
108
|
+
GH_REPO: ${{ github.repository }}
|
|
109
|
+
run: |
|
|
110
|
+
if gh release view "$GITHUB_REF_NAME" >/dev/null 2>&1; then
|
|
111
|
+
gh release upload "$GITHUB_REF_NAME" dist/*.tar.gz dist/*.whl
|
|
112
|
+
exit 0
|
|
113
|
+
fi
|
|
114
|
+
gh release create "$GITHUB_REF_NAME" \
|
|
115
|
+
--title "$GITHUB_REF_NAME" \
|
|
116
|
+
--notes-file dist/RELEASE_NOTES.md \
|
|
117
|
+
--verify-tag \
|
|
118
|
+
dist/*.tar.gz dist/*.whl
|