claude-code - 💡(How to fix) Fix claude plugin install silently strips fields from .claude.json

Official PRs (…)
ON THIS PAGE

Recommended Tools

×6

Utilities matched from this issue’s tags and category — try them while you read without losing context.

GitHub issue graph ai analysis

Paste a GitHub issue URL. We fetch that issue, discover linked issues from bodies/comments/timeline, collect linked pull requests, and produce a structured English report.

The report is written in English Markdown for sharing and archival.

Helpful · Quick feedback

Loading…

claude plugin install <name> rewrites ~/.claude/.claude.json using a deserialize-modify-serialize cycle that silently drops any field outside the CLI's internal struct. Re-running it (even with a plugin that is already installed) shrinks the file from ~75 KB / ~60 keys to ~1.5 KB / 8 keys.

The dropped fields include subscription state, causing Claude Code to prompt for OAuth re-authentication on every session even though credentials in .credentials.json are intact.

Root Cause

claude plugin install <name> rewrites ~/.claude/.claude.json using a deserialize-modify-serialize cycle that silently drops any field outside the CLI's internal struct. Re-running it (even with a plugin that is already installed) shrinks the file from ~75 KB / ~60 keys to ~1.5 KB / 8 keys.

The dropped fields include subscription state, causing Claude Code to prompt for OAuth re-authentication on every session even though credentials in .credentials.json are intact.

Fix Action

Workaround

Backups under ~/.claude/backups/.claude.json.backup.<epoch_ms> preserve the pre-truncation state and allow full recovery via cp.

Idempotence guard in automation that calls the CLI: cache claude plugin list once, skip already-installed plugins. Avoids re-triggering the write entirely.

RAW_BUFFERClick to expand / collapse

Summary

claude plugin install <name> rewrites ~/.claude/.claude.json using a deserialize-modify-serialize cycle that silently drops any field outside the CLI's internal struct. Re-running it (even with a plugin that is already installed) shrinks the file from ~75 KB / ~60 keys to ~1.5 KB / 8 keys.

The dropped fields include subscription state, causing Claude Code to prompt for OAuth re-authentication on every session even though credentials in .credentials.json are intact.

Reproduction

  1. Healthy state: wc -c ~/.claude/.claude.json → ~75 KB
  2. claude plugin install <any-already-installed-plugin> (exits 0, no warning)
  3. wc -c ~/.claude/.claude.json → ~1.5 KB

Observed vs expected

Lost fields include:

  • oauthAccount.organizationType (e.g. "claude_max")
  • oauthAccount.organizationRateLimitTier (e.g. "default_claude_max_5x")
  • projects.* per-project state map (entire map dropped)
  • ~50 onboarding / UI flags
  • All install metadata not present in the CLI's plugin struct

Effect: without organizationType, the CLI treats the account as un-subscribed and re-prompts for OAuth on next session, despite valid accessToken / refreshToken in .credentials.json.

Expected: unknown fields should round-trip through claude plugin install untouched (standard pattern: deserialize into a typed struct + retain unknown fields, or operate at the JSON-value level).

Scope

  • Confirmed: claude plugin install
  • Likely (untested): any claude CLI subcommand that writes to .claude.jsonmcp add, mcp remove, plugin uninstall, etc. The bug is in the read/write layer, not the install path.

Workaround

Backups under ~/.claude/backups/.claude.json.backup.<epoch_ms> preserve the pre-truncation state and allow full recovery via cp.

Idempotence guard in automation that calls the CLI: cache claude plugin list once, skip already-installed plugins. Avoids re-triggering the write entirely.

Suggested fix

Either (a) deserialize into a struct that preserves unknown fields (Go: use json.RawMessage for the catch-all; Rust: #[serde(flatten)] extra: Map<...>), or (b) operate at the JSON-value level (load → mutate one key → save) without round-tripping through a typed schema.

Version

claude --version: 2.1.144 (Claude Code)

Vote matrix · Quick signals

Works
Did the solution work? Tap to confirm.
Easy Fix
Was it a quick fix?
Time Saver
Did it save you time?
Blocking
Was it severely blocking?
Common Issue
Are others likely hitting this too?
Flaky / Intermittent
Is it intermittent?
Verified / Reproducible
Can you reproduce it reliably?
Loading…

Still need to ship something?

×6

Another batch ranked right after the header list — different links, same matching logic.

Back to top recommendations

TRENDING

claude-code - 💡(How to fix) Fix claude plugin install silently strips fields from .claude.json