npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

claudecode-linter

v2.1.101

Published

Standalone linter for Claude Code plugins and configuration files

Downloads

2,833

Readme

claudecode-linter

CI npm version license Known Vulnerabilities Socket Badge

Standalone linter for Claude Code plugins and configuration files.

Validates plugin.json, SKILL.md, agent/command markdown, hooks.json, mcp.json, settings.json, and CLAUDE.md files with 90 rules across 8 artifact types.

demo

Install

npm install -g claudecode-linter

Or run directly:

npx claudecode-linter ~/projects/my-plugin/

Usage

Lint

Check plugin artifacts for errors without modifying files. This is the default mode — --lint is optional:

# Lint a plugin directory
claudecode-linter --lint path/to/plugin/
claudecode-linter path/to/plugin/  # same thing

# Lint multiple paths
claudecode-linter plugin-a/ plugin-b/

# JSON output
claudecode-linter --output json path/to/plugin/

# Errors only
claudecode-linter --quiet path/to/plugin/

# Filter by rule
claudecode-linter --rule plugin-json/name-kebab-case path/to/plugin/

# Enable/disable specific rules
claudecode-linter --enable skill-md/word-count --disable claude-md/no-todos path/to/plugin/

# List all available rules
claudecode-linter --list-rules

Format

Reformat all artifacts for consistent style (sorted keys, normalized indentation, trailing whitespace, kebab-case names, quoted YAML values). No lint output — just formats and reports what changed:

# Format all artifacts in place
claudecode-linter --format path/to/plugin/

Fix

Fix lint violations in place, then lint the result — output shows only issues that remain after fixing:

# Fix issues in place
claudecode-linter --fix path/to/plugin/

# Preview fixes without writing (shows diff)
claudecode-linter --fix-dry-run path/to/plugin/

Example Output

$ claudecode-linter my-plugin/

my-plugin/skills/example/SKILL.md
  warn   Body has 117 words (recommended: 500-5000)  skill-md/body-word-count:5

my-plugin/.claude/settings.json
  error  "settings.json" should only exist at user level (~/.claude/).
         Use "settings.local.json" for project-level settings  settings-json/scope-file-name
  warn   "env" is a user-level field — it has no effect in
         project-level settings.local.json  settings-json/scope-field:9:3

1 error, 2 warnings
$ claudecode-linter --fix-dry-run my-plugin/

--- my-plugin/skills/deploy/SKILL.md
+++ my-plugin/skills/deploy/SKILL.md (fixed)
-name: My Deploy Skill
+name: my-deploy-skill
-description: Use when the user asks to "deploy": handles both cases.
+description: "Use when the user asks to \"deploy\": handles both cases."
$ claudecode-linter my-plugin/
No issues found.

Artifact Types

| Type | Files | Rules | |------|-------|-------| | plugin-json | .claude-plugin/plugin.json | 12 | | skill-md | skills/*/SKILL.md | 11 | | agent-md | agents/*.md | 13 | | command-md | commands/*.md | 5 | | hooks-json | hooks/hooks.json | 9 | | settings-json | .claude-plugin/settings.json | 14 | | mcp-json | .claude-plugin/mcp.json | 16 | | claude-md | CLAUDE.md | 10 |

Configuration

Generate a config file with all rules and their default severities:

# Create .claudecode-lint.yaml in current directory
claudecode-linter --init

# Create in a specific directory
claudecode-linter --init ~/projects/my-plugin/

# Create in home directory (applies globally)
claudecode-linter --init ~

claudecode-linter looks for config in this order:

  1. .claudecode-lint.yaml or .claudecode-lint.yml in the current directory
  2. .claudecode-lint.yaml or .claudecode-lint.yml in $HOME
  3. Bundled defaults (all rules enabled at their default severity)

Example config:

rules:
  plugin-json/name-kebab-case: true
  skill-md/word-count:
    severity: warning
    min: 50
  claude-md/no-todos: false

Fixers

Both --format and --fix run the same fixers. The difference: --format only formats and reports changes, --fix also lints the result afterwards.

Formatting is powered by prettier for consistent JSON and markdown output. Custom logic handles domain-specific transformations that prettier can't (key sorting, YAML fixes, kebab-case normalization).

| Artifact | Prettier | Custom logic | |----------|----------|--------------| | plugin-json | Tab-indented JSON | Canonical key ordering | | hooks-json | 2-space JSON | Alphabetical key sorting | | mcp-json | 2-space JSON | Server name sorting, canonical field ordering | | settings-json | 2-space JSON | Canonical key ordering, permission array sorting | | skill-md / agent-md / command-md | Markdown body | Frontmatter YAML normalization, kebab-case names, pre-parse quoting | | claude-md | Markdown | Blank line before headings |

Exit Codes

| Code | Meaning | |------|---------| | 0 | No errors | | 1 | Lint errors found | | 2 | Fatal error |

Versioning

This linter's version tracks the Claude Code version it was extracted from:

  • Contract sync: version matches Claude Code exactly (e.g., 2.1.69 for Claude Code v2.1.69)
  • Linter-only bugfix: pre-release suffix 2.1.69-patch.1, 2.1.69-patch.2, etc.

Pre-release versions sort below the base version in npm (2.1.69-patch.1 < 2.1.69), but ^2.1.68 will still resolve them. When the next Claude Code version is released (e.g., 2.1.70), it supersedes all patches.

Development

npm install
npm run build
npm test

Updating contracts

When a new Claude Code version is released:

# 1. Extract contracts from latest Claude Code
npm run extract-contracts

# Or extract from a specific version
npm run extract-contracts -- --version 2.1.58

# 2. Generate src/contracts.ts from the JSON
npm run generate-contracts

# 3. Build and test
npm run build && npm test

The --version flag is useful for testing the CI pipeline: extract an older version, commit it, then let CI detect the newer latest version and run the full release flow.

Use --changelog to also write a CHANGELOG_ENTRY.md file with a markdown drift report (used by CI):

npm run extract-contracts -- --changelog

This is automated in CI via .github/workflows/release.yml.

License

MIT