Two real defects, plus the CLI reference claims that go with them. ## 1. ECDSA P-384 login instructions cannot work Every "ECDSA P-384" tab ran the *identical* command to the Ed25519 tab. Since `--algorithm` defaults to ed25519 ([login.go:100](https://github.com/modelcontextprotocol/registry/blob/main/cmd/publisher/commands/login.go#L100)), a 96-hex key is rejected outright. Verified against a freshly generated P-384 key: ``` $ mcp-publisher login dns --domain=example.com --private-key=$KEY Signing in process using key algorithm ed25519 Error: failed to get token: failed to sign timestamp: invalid seed length: expected 32 bytes, got 48 $ mcp-publisher login dns --algorithm ecdsap384 --domain=example.com --private-key=$KEY Signing in process using key algorithm ecdsap384 Expected proof record: # works ``` `--algorithm` is registered at [login.go:129](https://github.com/modelcontextprotocol/registry/blob/main/cmd/publisher/commands/login.go#L129) and described correctly by the CLI's own help, but `grep -rn algorithm docs/` had **zero** hits for it. Anyone following the ECDSA path in the docs hit that error with nothing to tell them why. Fixed at all four in-process ECDSA sites (2 in `authentication.mdx`, 2 in `cli/commands.md`), with a note that cloud signing providers derive the algorithm from the key itself so the flag does not apply to them. ## 2. `mcp-publisher validate --help` was broken ``` $ mcp-publisher validate --help Unknown command: validate ... Use 'mcp-publisher <command> --help' for more information about a command. ``` It printed the very instruction that had just failed. `main.go` intercepted `--help` for all subcommands and called `printCommandHelp`, whose switch had no `validate` case — making `ValidateCommand`'s own help block ([validate.go:120-129](https://github.com/modelcontextprotocol/registry/blob/main/cmd/publisher/commands/validate.go#L120)) unreachable. Rather than paste a third copy of the help text, `printCommandHelp` now returns whether it handled the command, and the caller falls through to normal dispatch when it did not. Commands own their own `--help`, and any future command with this shape works automatically. | Command | Before | After | |---|---|---| | `validate --help` | `Unknown command`, exit 0 | prints its help, exit 0 | | `publish --help` | works | works | | `init -h` | works | works | | `bogus --help` | `Unknown command`, exit 0 | `Unknown command`, **exit 1** | ## 3. CLI reference corrections - **`--registry` is not global.** It exists only on `login`; other commands read the URL from the stored token. `publish --registry=URL` silently treats the flag as the `server.json` path. `cmd/publisher/README.md` had exactly this broken example. - **`--token` was undocumented** despite `github-actions.mdx:123` depending on it. Now documented, noting it is `login github` only. - **`init` takes no flags** and does not prompt; it writes `TODO:` placeholders. The reference said `init [options]` and "Prompts for missing required fields". - **Refreshed the `--help` transcript** in `quickstart.mdx`, which listed only 4 of 6 commands. Now byte-for-byte identical to real output (diffed). - **Added `validate`** to the command list in `cmd/publisher/README.md`. ## Verification `go build` and `go test ./cmd/...` pass. All four help paths exercised with exit codes checked. The 23 `goconst` findings in `validate_test.go` are pre-existing — identical count on pristine `main`, none in `main.go`. Quickstart transcript diffed against real output. 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-authored-by: Claude Opus 5 <noreply@anthropic.com>
1.7 KiB
1.7 KiB
MCP Publisher Tool - Development
CLI tool for publishing MCP servers to the registry.
These docs are for contributors. See the Publisher User Guide for end-user documentation.
Quick Development Setup
# Build the tool
make publisher
# Test locally
make dev-compose # Start local registry
./bin/mcp-publisher init
./bin/mcp-publisher login none --registry=http://localhost:8080
./bin/mcp-publisher publish
publish takes the registry URL from the token saved by login, so it accepts no --registry
flag — passing one would be read as the server.json path.
Architecture
Commands
init- Generate server.json templates with auto-detectionlogin- Handle authentication (github, dns, http, none)publish- Validate and upload servers to registrystatus- Update server lifecycle status (active, deprecated, deleted)validate- Validate server.json without publishinglogout- Clear stored credentials
Authentication Providers
github- Interactive OAuth flowgithub-oidc- CI/CD with GitHub Actionsdns- Domain verification via DNS TXT recordshttp- Domain verification via HTTPS endpointsnone- No auth (testing only)
Signing Providers
Optional: enables dns and http methods to sign out-of-process without direct access to the private key.
google-kms- Google KMS signingazure-key-vault- Azure Key Vault signing
Key Files
main.go- CLI setup and command routingcommands/- Command implementations with auto-detection logicauth/- Authentication provider implementations