configure-plugin/skills/configure-claude-plugins/SKILL.md
Claude plugins marketplace setup: .claude/settings.json, GitHub Actions, plugin sets. Use when onboarding to claude-plugins, setting up claude.yml, or pinning plugins.
npx skillsauth add laurigates/claude-plugins configure-claude-pluginsInstall this skill globally with one command. Works with Claude Code, Cursor, and Windsurf.
3 of 9 scanners reported clean
Some scanners were skipped, did not run, or reported a non-clean status. Review each row below.
Configure a project to use the laurigates/claude-plugins Claude Code plugin marketplace. Sets up .claude/settings.json with permissions, marketplace enrollment, and enabledPlugins; and GitHub Actions workflows (claude.yml, claude-code-review.yml) with the marketplace pre-configured.
| Use this skill when... | Use another approach when... |
|------------------------|------------------------------|
| Onboarding a new project to use Claude Code plugins | Configuring Claude Code settings unrelated to plugins |
| Setting up claude.yml and claude-code-review.yml workflows | Creating general GitHub Actions workflows (/configure:workflows) |
| Adding the laurigates/claude-plugins marketplace to a repo | Installing individual plugins manually |
| Merging plugin permissions into existing .claude/settings.json | Debugging Claude Code action failures (check GitHub Actions logs) |
| Selecting recommended plugins based on project type | Developing new plugins (see CLAUDE.md plugin lifecycle) |
find . -maxdepth 3 -name 'settings.json' -path '*/.claude/*'find .github/workflows -maxdepth 1 -name 'claude*.yml'git remote -vfind . -maxdepth 1 \( -name 'package.json' -o -name 'pyproject.toml' -o -name 'Cargo.toml' -o -name 'go.mod' -o -name 'Dockerfile' -o -name 'justfile' -o -name 'Justfile' \)find . -maxdepth 2 \( -name 'idf_component.yml' -o -name 'sdkconfig' -o -name 'CMakeLists.txt' \)find . -maxdepth 2 -name '*.yaml' -path '*/esphome/*'Parse from command arguments:
| Parameter | Description |
|-----------|-------------|
| --check-only | Report current configuration status without changes |
| --fix | Apply configuration automatically |
| --plugins | Comma-separated list of plugins to install (default: all recommended) |
| --exhaustive | Enumerate every marketplace plugin in enabledPlugins — recommended ones as true, the rest as false. Pins the project's plugin set against global toggles. |
| --workflows | Force-scaffold the claude.yml / claude-code-review.yml workflows even when no git remote is detected (default: scaffold only when a remote exists). |
| --no-workflows | Skip workflow scaffolding even when a git remote is present. Useful for local-only or vendored projects. |
Execute this Claude plugins configuration workflow:
.claude/settings.json.github/workflows/claude.yml.github/workflows/claude-code-review.ymlgit remote -v. Capture has_remote = true when the output is non-empty, has_remote = false otherwise. This gates workflow scaffolding in Steps 4 and 5 — workflows that cannot run (no remote → no GitHub Actions) should not be scaffolded by default.If --plugins is not specified, select recommended plugins based on detected project type:
| Project Indicator | Recommended Plugins |
|-------------------|---------------------|
| package.json | git-plugin, typescript-plugin, testing-plugin, code-quality-plugin |
| pyproject.toml / setup.py | git-plugin, python-plugin, testing-plugin, code-quality-plugin |
| Cargo.toml | git-plugin, rust-plugin, testing-plugin, code-quality-plugin |
| Dockerfile | Above + container-plugin |
| .github/workflows/ | Above + github-actions-plugin |
| idf_component.yml / sdkconfig | git-plugin, code-quality-plugin, testing-plugin, container-plugin |
| ESPHome yaml | git-plugin, python-plugin, code-quality-plugin |
| CMakeLists.txt (without Dockerfile / ESP-IDF / ESPHome indicators) | git-plugin, code-quality-plugin, testing-plugin, tools-plugin + clangd@claude-plugins-official (LSP) |
| Default (any) | git-plugin, code-quality-plugin, testing-plugin, tools-plugin |
Always include: configure-plugin, health-plugin, hooks-plugin.
Create or merge into .claude/settings.json. The permissions baseline includes common entries plus stack-aware expansions. The stanza also enrolls the marketplace so web sessions retain plugin access.
Suffix forms — read this before copy-pasting. The two suffix forms below are not interchangeable. Using the wrong one silently breaks the config:
| Where | Suffix | Source of the suffix | |---|---|---| |
.claude/settings.json→enabledPlugins(Step 3) |<plugin>@claude-plugins| TheextraKnownMarketplaceskey in the same stanza | |.github/workflows/claude*.yml→plugins:(Steps 4–5) |<plugin>@laurigates-claude-plugins| Thenamefield inlaurigates/claude-plugins/.claude-plugin/marketplace.json|Wrong suffix in
enabledPlugins→ entry silently ignored (marketplace key does not match). Wrong suffix in the workflowplugins:block → action rejects the run.
enabledPlugins merge semantics matterenabledPlugins is a per-key merging map across the settings hierarchy: a project entry overrides the matching global entry, but global entries the project does not mention still take effect. There is no enabledPluginsExclusive flag. So if a user has accidentally toggled an unwanted plugin globally (easy to do via the plugins UI), it leaks into every repo that does not explicitly set it to false.
| Mode | Project enabledPlugins contents | Behaviour vs global toggles |
|------|------------------------------------|------------------------------|
| Default (no flag) | Recommended plugins as true only | Lean. Vulnerable to global drift — any plugin the user toggled on globally is also active here. |
| --exhaustive | Every marketplace plugin enumerated as true or false | Deterministic. Project pin overrides every global toggle. Re-run when the marketplace adds plugins. |
Pick --exhaustive for repos that need a self-documenting, drift-resistant plugin set (infrastructure repos, repos shared with teammates / CI, repos sensitive to context tax from unrelated plugins). Use the default for personal scratch repos where global toggles are intentional.
permissions.allow baselineAlways include these common entries:
"Bash(git:*)", "Bash(gh:*)", "Bash(pre-commit:*)", "Bash(gitleaks:*)", "Bash(python3:*)"
Add stack-specific entries based on detected project type:
| Stack | Additional allow entries |
|---|---|
| Python (uv + ruff + ty) | "Bash(uv:*)", "Bash(uvx:*)", "Bash(ruff:*)", "Bash(ty:*)", "Bash(pytest:*)" |
| Node / TypeScript | "Bash(npm:*)", "Bash(pnpm:*)", "Bash(bun:*)", "Bash(tsc:*)", "Bash(eslint:*)", "Bash(prettier:*)", "Bash(vitest:*)" |
| Go | "Bash(go:*)", "Bash(gofmt:*)", "Bash(golangci-lint:*)" |
| Rust | "Bash(cargo:*)", "Bash(rustc:*)", "Bash(clippy:*)", "Bash(rustfmt:*)" |
| C / C++ (CMake) | "Bash(cmake:*)", "Bash(ctest:*)", "Bash(clang-format:*)", "Bash(clang-tidy:*)", "Bash(cppcheck:*)", "Bash(make:*)", "Bash(ninja:*)" |
| ESP-IDF / embedded | "Bash(idf.py:*)", "Bash(esptool:*)", "Bash(clang-format:*)", "Bash(cppcheck:*)", "Bash(docker:*)", "Bash(docker compose:*)", "Bash(just:*)", "Bash(make:*)" |
| ESPHome | "Bash(esphome:*)", "Bash(uv:*)", "Bash(uvx:*)" |
Use granular patterns only — do not add Bash(bash *) for CLI tools.
--exhaustive is set)Build the full enabledPlugins map by reading every plugin name from the two relevant marketplaces, then writing each one with the appropriate boolean. The recommended set from Step 2 becomes true; everything else becomes false.
Read the laurigates marketplace in priority order:
.claude-plugin/marketplace.json:
jq -r '.plugins[].name' .claude-plugin/marketplace.json
gh api repos/laurigates/claude-plugins/contents/.claude-plugin/marketplace.json --jq '.content' | base64 -d | jq -r '.plugins[].name'
@claude-plugins to match the existing stanza format.Add the official LSP plugins (@claude-plugins-official). The currently shipped names are: pyright, typescript-language-server, rust-analyzer, gopls, swift-language-server, clangd. Mark the LSP that matches the detected stack as true, the rest as false. If none match (no detectable stack), leave them all false.
Compose the map with all entries, alphabetised within each marketplace block. Suffix @claude-plugins matches the extraKnownMarketplaces key (not the marketplace name used in workflows):
{
"enabledPlugins": {
"accessibility-plugin@claude-plugins": false,
"agent-patterns-plugin@claude-plugins": false,
"agents-plugin@claude-plugins": false,
"...": "...",
"code-quality-plugin@claude-plugins": true,
"configure-plugin@claude-plugins": true,
"git-plugin@claude-plugins": true,
"health-plugin@claude-plugins": true,
"hooks-plugin@claude-plugins": true,
"testing-plugin@claude-plugins": true,
"typescript-plugin@claude-plugins": true,
"...": "...",
"clangd@claude-plugins-official": false,
"gopls@claude-plugins-official": false,
"pyright@claude-plugins-official": false,
"rust-analyzer@claude-plugins-official": false,
"swift-language-server@claude-plugins-official": false,
"typescript-language-server@claude-plugins-official": true
}
}
enabledPlugins (or a merged-in copy of the user's global file) contains plugin names that are not in either marketplace listing, surface them in the report and ask whether to keep them. They may belong to a third marketplace the user has enrolled.The extraKnownMarketplaces key (claude-plugins) is what each enabledPlugins entry's @claude-plugins suffix must match. The two stanzas are coupled — changing the key without also changing every suffix silently disables every plugin in enabledPlugins.
{
"permissions": {
"allow": [
"Bash(git:*)",
"Bash(gh:*)",
"Bash(pre-commit:*)",
"Bash(gitleaks:*)",
"Bash(python3:*)"
// ... plus stack-specific entries from the table above
]
},
"extraKnownMarketplaces": {
"claude-plugins": { // marketplace KEY (used by enabledPlugins suffix below)
"source": { "source": "github", "repo": "laurigates/claude-plugins" },
"autoUpdate": true
}
},
"enabledPlugins": {
"<selected-plugin-1>@claude-plugins": true, // suffix == extraKnownMarketplaces key, NOT marketplace name
"<selected-plugin-2>@claude-plugins": true
}
}
Replace <selected-plugin-N> with the plugin names selected in Step 2.
If .claude/settings.json already exists, MERGE without duplicating entries. Preserve any existing hooks, env, or other fields.
Gate this step on a git remote being present. Decide whether to scaffold using this table:
| has_remote (from Step 1) | Flag | Behaviour |
|---|---|---|
| true | (default) or --workflows | Scaffold claude.yml |
| true | --no-workflows | Skip; record STATUS=SKIPPED (--no-workflows) |
| false | (default) | Default-skip — prompt the user via AskUserQuestion: "No git remote detected. claude.yml cannot run without GitHub Actions. Scaffold anyway (will sit dormant until a remote is added), or skip?" Default to skip on --check-only (no prompt). |
| false | --workflows | Force-scaffold anyway (e.g. the user plans to add a remote later) |
| false | --no-workflows | Skip without prompting |
When the decision is skip, do not write the file, and surface STATUS=SKIPPED (no git remote) in the Step 6 report so the omission is visible.
When the decision is scaffold, create .github/workflows/claude.yml with the Claude Code action configured to use the plugin marketplace. Workflow plugins: entries use the @laurigates-claude-plugins suffix — the marketplace name from marketplace.json, NOT the extraKnownMarketplaces key used in Step 3:
name: Claude Code
on:
issue_comment:
types: [created]
pull_request_review_comment:
types: [created]
issues:
types: [opened, assigned]
permissions:
contents: write
pull-requests: write
issues: write
id-token: write
jobs:
claude:
if: |
(github.event_name == 'issue_comment' && contains(github.event.comment.body, '@claude')) ||
(github.event_name == 'pull_request_review_comment' && contains(github.event.comment.body, '@claude')) ||
(github.event_name == 'issues' && contains(github.event.issue.body, '@claude'))
runs-on: ubuntu-latest
steps:
- name: Checkout repository
uses: actions/checkout@v6
with:
fetch-depth: 0
- name: Run Claude Code
uses: anthropics/claude-code-action@v1
with:
claude_code_oauth_token: ${{ secrets.CLAUDE_CODE_OAUTH_TOKEN }}
plugin_marketplaces: |
https://github.com/laurigates/claude-plugins.git
plugins: |
# suffix matches marketplace `name` in marketplace.json (NOT extraKnownMarketplaces key)
PLUGINS_LIST
Replace PLUGINS_LIST with the selected plugins in the format plugin-name@laurigates-claude-plugins, one per line. The suffix is the marketplace name field from laurigates/claude-plugins/.claude-plugin/marketplace.json — distinct from the @claude-plugins suffix used in .claude/settings.json (Step 3).
Apply the same git-remote gate from Step 4. Reuse the user's answer (or the --workflows / --no-workflows flag) — do not re-prompt. If Step 4 skipped, skip Step 5 as well and record STATUS=SKIPPED (no git remote).
When the decision is scaffold, create .github/workflows/claude-code-review.yml for automatic PR reviews:
name: Claude Code Review
on:
pull_request:
types: [opened, synchronize, reopened]
permissions:
contents: read
pull-requests: write
issues: write
jobs:
review:
runs-on: ubuntu-latest
steps:
- name: Checkout repository
uses: actions/checkout@v6
with:
fetch-depth: 0
- name: Claude Code Review
uses: anthropics/claude-code-action@v1
with:
claude_code_oauth_token: ${{ secrets.CLAUDE_CODE_OAUTH_TOKEN }}
prompt: |
Review this pull request. Focus on:
- Code quality and best practices
- Potential bugs or security issues
- Test coverage gaps
- Documentation needs
claude_args: "--max-turns 5"
plugin_marketplaces: |
https://github.com/laurigates/claude-plugins.git
plugins: |
# suffix matches marketplace `name` in marketplace.json (NOT extraKnownMarketplaces key)
code-quality-plugin@laurigates-claude-plugins
testing-plugin@laurigates-claude-plugins
Print a status report:
Claude Plugins Configuration Report
=====================================
Repository: <repo-name>
.claude/settings.json:
Status: <CREATED|UPDATED|EXISTS>
Mode: <DEFAULT|EXHAUSTIVE>
Permissions: <N> allowed patterns configured
Marketplace: laurigates/claude-plugins (extraKnownMarketplaces)
Plugins pinned: <N> total (<E> enabled, <D> disabled) # exhaustive only
Enabled plugins: <list>
Git remote: <PRESENT|MISSING>
.github/workflows/claude.yml:
Status: <CREATED|UPDATED|EXISTS|SKIPPED (no git remote)|SKIPPED (--no-workflows)>
Marketplace: laurigates/claude-plugins
Plugins: <list>
.github/workflows/claude-code-review.yml:
Status: <CREATED|UPDATED|EXISTS|SKIPPED (no git remote)|SKIPPED (--no-workflows)>
Trigger: PR opened/synchronize/reopened
Next Steps:
1. Add CLAUDE_CODE_OAUTH_TOKEN to repository secrets
Settings > Secrets and variables > Actions > New repository secret
2. Commit and push the new/updated files
3. Test by mentioning @claude in a PR comment
4. (exhaustive mode) Re-run when the marketplace adds new plugins so they
get an explicit `false` rather than inheriting the global toggle
5. (no remote) When you add a GitHub remote later, re-run with `--workflows`
to scaffold the workflows that were skipped
| Context | Command |
|---------|---------|
| Quick status check | /configure:claude-plugins --check-only |
| Auto-configure all | /configure:claude-plugins --fix |
| Specific plugins only | /configure:claude-plugins --fix --plugins git-plugin,testing-plugin |
| Pin against global drift | /configure:claude-plugins --fix --exhaustive |
| Settings only (local-only repo) | /configure:claude-plugins --fix --no-workflows |
| Pre-stage workflows before remote exists | /configure:claude-plugins --fix --workflows |
| List marketplace plugin names | jq -r '.plugins[].name' .claude-plugin/marketplace.json |
| Verify settings exist | find .claude -maxdepth 1 -name 'settings.json' |
| List Claude workflows | find .github/workflows -name 'claude*.yml' |
| Check for git remote | git remote -v |
| Flag | Description |
|------|-------------|
| --check-only | Report current status without making changes |
| --fix | Apply all configuration automatically |
| --plugins | Override automatic plugin selection |
| --exhaustive | Enumerate every marketplace plugin (recommended ones true, the rest false). Pins the project's plugin set deterministically against global toggles. |
| --workflows | Force-scaffold the claude.yml / claude-code-review.yml workflows even when no git remote is detected. By default, workflow scaffolding is skipped on remote-less repos to avoid dormant files. |
| --no-workflows | Skip workflow scaffolding even when a git remote is present. Useful for local-only or vendored projects where settings should be configured but Actions should not. |
CLAUDE_CODE_OAUTH_TOKEN secret must be added manually to the repositoryextraKnownMarketplaces in .claude/settings.json is the key to surviving ephemeral web sessions — without it, the marketplace is only enrolled via CIclaude.yml and claude-code-review.yml are skipped by default — writing them would create dormant files that confuse future readers. Override with --workflows to pre-stage them before adding a remote.enabledPlugins entries use <plugin>@claude-plugins — the extraKnownMarketplaces keyplugins: blocks use <plugin>@laurigates-claude-plugins — the marketplace name field from marketplace.jsonenabledPlugins entries with the wrong suffix are ignored; workflow plugins: entries with the wrong suffix are rejected by the action/configure:repo - Full end-to-end driver (runs this skill + web-session + health check)/configure:web-session - SessionStart hook for infrastructure tools/configure:all - Run all compliance checksclaude-security-settings skill - Claude Code security settingstools
Scaffold a new ComfyUI custom-node repo (pyproject, CI, release-please, vitest+pytest, JS extension skeleton) in the picker/gesture vein. Use when bootstrapping or init-ing a comfyui node pack.
tools
Orchestrate a ComfyUI node pack from idea to registry: scaffold, create + seed the repo, open the gitops adoption PR. Use when releasing or spinning up a new comfyui node pack.
testing
macOS EndpointSecurity/EDR high CPU & battery drain. Use when Kandji ESF / XProtect pegs a core; trace the exec storm via powermetrics + eslogger.
development
odiff pixel-by-pixel image diffing. Use when comparing screenshots, detecting visual regressions, diffing before/after PNGs, asserting golden images.