copytree [path] [options]Arguments:
path- Directory path or GitHub URL to copy (defaults to current directory)
Use a specific profile for file selection. If omitted, CopyTree uses the default profile.
Examples:
copytree --profile mycustom
copytree -p mycustomNote: The default profile is automatically used when no profile is specified. Create custom profiles in ~/.copytree/profiles/ or .copytree/ for project-specific needs.
Include files matching glob patterns. Can be used multiple times.
copytree --filter "*.js" --filter "*.ts"
copytree -f "src/**/*.php" -f "tests/**/*.php"Only include files modified since the last Git commit.
copytree --modified
copytree -mInclude files changed since a specific Git reference (commit, branch, or tag).
copytree --changed HEAD~5
copytree -c main
copytree --changed v1.0.0Exclude files matching glob patterns. Can be used multiple times.
copytree --exclude "**/*.test.js" --exclude "fixtures/**"Copy only these paths. Literal paths, not globs — a directory named src/[draft] is just a
path, and there is nothing to escape.
Ignore rules still resolve from the project root: the root .gitignore, the root
.copytreeignore, and every nested ignore file between the root and the selection all apply. A
scoped run selects exactly the files a filtered full run would. Output paths stay relative to the
project root, so @-references handed to an agent still resolve.
Traversal starts at the selection rather than the root, so the cost scales with what you asked for instead of with the size of the repository.
# One folder, repository rules
copytree --scope src/panels/file-browser
# Several entries, files as well as directories
copytree --scope src/panels package.json
# Compose with a filter: TypeScript files under src
copytree --scope src --filter "**/*.ts"Let --scope entries override the ignore rules that would otherwise exclude them. Off by default,
so a scoped run keeps the "same set as a full run" guarantee. Use it for the deliberate gesture:
you navigated into a gitignored folder and want it anyway.
copytree --scope build/generated --scope-include-ignoredLet --scope entries override the config exclusions blocking them (node_modules, and anything
in copytree.globalExcludedDirectories / globalExcludedFiles).
Separate from --scope-include-ignored because the two answer different questions: one is "yes, I
know it's gitignored", the other is "yes, I really do mean node_modules". A path excluded by both
layers needs both flags, which scoping into node_modules normally does, since most repositories
also gitignore it.
.git is excluded by a layer neither flag lifts.
copytree --scope node_modules/some-package --scope-include-ignored --scope-include-config-excludedSave output to a file.
copytree --output output.xml
copytree -o output.xmlPrint the output to the terminal instead of writing a file reference.
copytree --display
copytree -iStream output without buffering (useful for piping).
copytree --stream | less
copytree -S > project.xmlSee --clipboard under Content Options for copying the output text itself. The default is a file
reference: CopyTree writes the output to a temp file and puts that path on the clipboard.
Output format: xml, markdown|md, json, ndjson, sarif, or tree.
Default: xml
copytree --format json
copytree --format ndjson
copytree --format sarif
copytree --format tree
copytree --format xml # default
copytree --format markdownLimit to first N files processed.
copytree --head 50
copytree -l 100Character budget across all file content.
Truncation happens at a line boundary and is marked inline
(… [truncated 4,213 of 9,001 lines]), so an agent cannot conclude the file simply ends there.
When a single line is longer than the remaining budget — a minified bundle, say — the cut is
mid-line and labelled as such rather than dropping the file. Chunks never end on an unpaired
UTF-16 surrogate.
copytree --char-limit 100000
copytree -C 50000Budgets are applied after sorting, so which files survive follows --sort. Truncation is
always reported, never silent: a silently truncated context is worse than an error, because the
agent answers confidently from a partial repository.
Hard per-file size gate, applied from stat() before anything is opened. Default: 256KB.
This is not the same as maxFileSize (a 10MB memory-safety ceiling) or --char-limit (which
truncates after reading). No single 256KB+ file belongs in an agent's context window, and the
gate exists whether or not truncation is enabled.
Only --always and .copytreeinclude lift the gate, and the override is reported.
copytree --size-gate 64KB
copytree --no-size-gate # include large files
copytree --size-gate 64KB --always "docs/spec.md"Total size budget across all selected files.
copytree --max-total-size 5MBMaximum number of files to include.
Budgets keep the head of the sorted list and drop the tail, and --sort is ascending by default.
--sort modified therefore keeps the oldest files; pair it with --sort-order desc to keep the
recently-touched ones.
copytree --max-files 500 --sort modified --sort-order desc # keep the newest 500
copytree --max-files 500 --sort size # keep the 500 smallestSort direction (default: asc). Decides which end of the list a budget keeps.
Show only directory structure, no file contents.
copytree --only-tree
copytree -tSort files by: path, size, modified, name, or extension.
copytree --sort modified
copytree --sort size
copytree -s nameInclude Git status indicators for each file.
copytree --with-git-statusAlways include these patterns (force-include), even if excluded by profile.
copytree --always "*.config.js" --always "config.example.js"Include line numbers in output.
copytree --with-line-numbersShow file sizes in output.
copytree --show-sizeShow information table with project statistics.
copytree --infoInclude binary files in output (normally excluded).
copytree --include-binaryRemove duplicate files from output.
copytree --dedupeCopy the output text itself to the clipboard, rather than a reference to a file containing it.
The default is a file reference: CopyTree writes the output to a temp file and puts that path on the clipboard, so pasting into an agent hands over a file to read instead of a few hundred kilobytes of inline context. Use this when you want the text itself, for example to paste into a chat box directly.
copytree --clipboard
copytree -yNo-op. Writing a file reference is the default, so this flag selects the behaviour you would get anyway. Accepted so existing scripts and habits keep working.
Skip auto-discovery of a .copytree.yml (or .copytree.yaml / .copytree.json)
profile in the project being copied. Discovery is on by default; a profile named
explicitly with -p takes precedence over a discovered one.
copytree --no-folder-profileInclude external sources (GitHub URLs or local paths).
copytree --external https://github.com/user/repoNote: Transformers are configured in profiles, not via CLI flags. Built-in transformers include file-loader, binary, and streaming-file-loader.
Plan the run without reading or formatting content.
A dry run is a strict prefix of the real run: the same file set, in the same order, under the same budgets. It reports the file count, total size, an approximate token count, and what was excluded.
copytree --dry-runDry run - nothing was read or written.
Base path: /repo
221 file(s), 1.42 MB, ~406k tokens
25 excluded: 19 copytreeignore, 4 gitignore, 1 configExclude, 1 sizeGate
Report which rule excluded each file, with the ignore file and line it came from. Turns "why isn't my file here?" from a bisect into a glance.
copytree --dry-run --explainLargest exclusions:
package-lock.json — 351.44 KB — sizeGate [sizeGate:262144]
CHANGELOG.md — 14.78 KB — copytreeignore [CHANGELOG.md] (/repo/.copytreeignore:20)
sub/nested.txt — 2 B — gitignore [nested.txt] (/repo/sub/.gitignore:1)
Aggregate counts are always collected and cost nothing extra. --explain adds the per-file detail.
Validate profile syntax without processing files.
copytree --validate --profile myprofileDisable caching for AI operations and external sources.
copytree --no-cacheDisable configuration validation (for testing/debugging).
copytree --no-validateDisable including instructions in output.
copytree --no-instructionsUse custom instructions set (default: default).
copytree --instructions custom
copytree --instructions default0- Success1- Profile validation or loading errors2- Invalid option combination3- File system or Git errors
# Copy current directory; the clipboard gets a path to the output file
copytree
# Copy the output text itself instead
copytree --clipboard
# Copy specific directory
copytree /path/to/project
# Copy from GitHub
copytree https://github.com/facebook/react# Uses default profile automatically
copytree
# Use custom profile
copytree --profile mycustom
# Preview profile selection
copytree --profile mycustom --dry-run# Pattern matching
copytree --filter "src/**/*.js" --filter "*.json"
# Git integration
copytree --modified
copytree --changed HEAD~5# Save to file (Markdown by default)
copytree --output project-snapshot.md
# Save as XML
copytree --output project-snapshot.xml --format xml
# Display in console
copytree --display
# Different formats
copytree --format json
copytree --format tree# Combine multiple options
copytree --profile myproject --modified --output snapshot.md
# Dry run with validation
copytree --dry-run --validate
# Limit output
copytree --head 50 --char-limit 100000
# Stream large projects
copytree --stream | gzip > project.md.gz- The
--validateoption cannot be combined with output options or filters - External sources (GitHub URLs) are cached by default in
~/.copytree/repos/ - Use
DEBUG=copytree:*environment variable for detailed debugging