anthropics / anthropics/claude-code

[BUG] plugin install copies gitignored files, including a root .env, from a directory marketplace

Aperta
#93,423 0 commenti 0 reazioni 0 assegnatari Vedi su GitHub
area:plugins area:security bug has repro platform:macos
Lingua principale
Python
Stelle
145k
Fork
23.1k
Metriche di merge delle PR
Metriche PR in attesa

Descrizione

### Preflight

- Searched open issues for plugin cache and gitignore reports; found none matching.
- Single bug report.
- Running the latest version (2.1.266).

### What's Wrong?

`claude plugin install` and `claude plugin update` copy the marketplace root into `~/.claude/plugins/cache////`. When the marketplace source is a `directory`, which is the local plugin development path, the copy includes files git ignores.

Measured on my checkout (github.com/bostonaholic/team, 90 skills and 13 agents):

- cache copy: 128M
- content tracked by git: 4.5M
- `node_modules/` accounts for 51M of that difference. The rest is local scratch: `.playwright-mcp/`, `.claude/worktrees/`, `.agents/friction-log/`.

The copy already excludes `.git`, so some filtering happens, but it does not read `.gitignore`.

`.gitignore` is also where local secrets go by convention. My repo reserves a root `.env` for the API key its eval suite reads. I confirmed that file gets copied by writing a probe value to it and reinstalling:

```
$ cat ~/.claude/plugins/cache/team-dev/team/0.97.0-claude.20260910173552/.env
TEAM_DEV_COPY_PROBE=not-a-real-secret
```

The install prints no warning, and the copied file stays until the install is replaced.

### What Should Happen?

When the marketplace source is a directory, skip files git ignores, honoring global excludes and `core.excludesFile`. An explicit exclude list in `marketplace.json` or `plugin.json` would work too.

### Steps to Reproduce

1. Clone a plugin repo whose `.gitignore` covers `node_modules/` and a root `.env`.
2. `bun install` (or `npm install`), and write any value to `.env`.
3. `claude plugin marketplace add --scope user`
4. `claude plugin install @ --scope user`
5. `ls -A ~/.claude/plugins/cache////` shows both `node_modules/` and `.env` in the copy.

### Is this a regression?

Unknown. This is the first version I have measured.

### Claude Code Version

2.1.266

### Platform

macOS (arm64)

### Operating System

macOS 26.6.2

### Terminal/Shell

zsh

### Additional Information

`--plugin-dir` skips the copy for a session, and I use it while iterating. My dev install script goes through `plugin install` so the install I test is the one users get, and that path is where the ignored files come along.

Guida per i contributori

Nessuna guida per i contributori indicizzata per questo repository

Direzione di ricerca

Start with the implementation behind `claude plugin install` and `claude plugin update` for directory marketplaces, then reproduce the copy using the listed marketplace and cache commands. Trace the directory-copy step and identify how `.gitignore`, global excludes, and `core.excludesFile` could be honored. Done means ignored paths such as `node_modules/` and a root `.env` are absent from the cache while tracked plugin files remain.

Scritto dal modello di indicizzazione a partire dal testo della issue.

Valutazione

Stack tecnologico
git
Ambito
cli, security, tooling
Tipo di issue
Bug
Difficoltà
4/5
Tempo stimato
3-5 giorni
Stato di attività
Attiva
Chiarezza
Abbastanza chiara
Idoneità per principianti
55/100

Ricevi le nuove issue nella tua casella

Un breve riepilogo di issue GitHub adatte ai principianti.