Claude Code
Deep dive into Claude Code β CLI, CLAUDE.md, hooks, permissions, MCP, and IDE integrations
Deep dive into Claude Code β CLI, CLAUDE.md, hooks, permissions, MCP, and IDE integrations
Claude Code is Anthropic's agentic AI coding assistant that operates directly in your terminal. Unlike chat-based AI tools where you copy-paste code, Claude Code reads your codebase, writes code, executes shell commands, and iterates autonomously until the task is complete.
At its core it runs a single-threaded agent loop: think β act β observe β repeat. Each iteration, Claude selects from ~26 built-in tools (Bash, Read, Write, Edit, Glob, Grep, Agent, WebFetch, WebSearch, and more) to make progress toward the goal. It stops only when the task is done or it gets stuck.
Available as: CLI (primary), VS Code extension, JetBrains extension, Desktop app (Mac/Windows), and Web app (claude.ai/code).
CLAUDE CODE AGENT LOOP (SINGLE-THREADED)
Install globally via npm or Homebrew, then run claude in any project directory to start an interactive session.
# Install via npm (recommended)
npm install -g @anthropic-ai/claude-code
# Or via Homebrew
brew install claude-code
# Verify installation
claude --version
# Start interactive session in current directory
claude# Model selection
claude --model claude-sonnet-4-20250514
# Permission modes
claude --permission-mode plan # read-only until plan approved
claude --permission-mode auto # auto-approve most tools
claude --permission-mode default # ask for risky ops (default)
# Tool restrictions
claude --allowedTools "Read,Write,Edit,Glob,Grep"
claude --disallowedTools "Bash,Agent"
# Non-interactive mode (for scripting / CI)
claude -p "explain this codebase"
claude -p "review this PR" --output-format json
claude -p "fix the bug in auth.ts" --max-turns 20
# System prompt injection
claude --system-prompt "You are a security reviewer"
claude --append-system-prompt "Always write tests"
# Session management
claude --resume # resume last conversation
claude --continue # continue last conversation with new input
# Piping input
cat src/auth.ts | claude -p "review this file for vulnerabilities"
git diff HEAD~3 | claude -p "summarize these changes"Both Python and TypeScript SDKs allow you to embed Claude Code as a subprocess in your own tooling β useful for custom IDE integrations, CI bots, or multi-agent orchestration.
import { claude } from "@anthropic-ai/claude-code";
const result = await claude({
prompt: "Add input validation to the login form",
options: {
model: "claude-sonnet-4-20250514",
maxTurns: 10,
allowedTools: ["Read", "Write", "Edit", "Bash"],
},
});
console.log(result.output);from claude_code import claude
result = claude(
prompt="Add input validation to the login form",
model="claude-sonnet-4-20250514",
max_turns=10,
allowed_tools=["Read", "Write", "Edit", "Bash"],
)
print(result.output)CLAUDE.mdis the project's βtech leadβ β a persistent instruction file that tells Claude Code how to work in your codebase. Unlike chat context that gets compacted, CLAUDE.md instructions survive context compaction and are always visible to the model.
CLAUDE.MD / SETTINGS HIERARCHY (LATER OVERRIDES EARLIER)
Files are loaded in hierarchy order: ~/.claude/CLAUDE.md β ./CLAUDE.md β ./subdir/CLAUDE.md β .claude/settings.json β .claude/settings.local.json. Later files override earlier ones. Subdirectory CLAUDE.md files are only loaded when Claude is working in that directory.
DO include:
DO NOT include:
# Project: MyApp
## Build & Test
- Build: `npm run build`
- Test all: `npm test`
- Test single: `npm test -- --grep "test name"`
- Lint: `npm run lint`
## Code Style
- Use TypeScript strict mode
- Prefer named exports over default exports
- Use `const` arrow functions for React components
- CSS: Tailwind utility classes, never inline styles
## Architecture
- Next.js App Router (not Pages Router)
- Server Components by default; "use client" only when needed
- State management: Zustand (not Redux)
- Database: Prisma ORM with PostgreSQL
## Important Rules
- NEVER use `any` type β use `unknown` + type guards
- ALWAYS run `npm run lint` before committing
- Tests required for all API routes
- Do not modify files in /generated/ β they are auto-generatedAGENTS.md works exactly like CLAUDE.md but is specifically targeted at subagents spawned via the Agent tool. When a subagent is created, it reads AGENTS.md in addition to CLAUDE.md. This is useful for giving subagents different instructions than the main agent β for example, restricting subagents to read-only operations or pointing them to specific documentation.
Beyond CLAUDE.md, Claude Code uses JSON settings files for structured configuration like permissions, tool restrictions, hooks, and model preferences.
~/.claude/settings.json
Global user settings. Applies to all projects. Set your default model, theme, global permissions, and tools you always want allowed/disallowed.
.claude/settings.json
Project-shared settings. Checked into the repo so the whole team shares the same Claude Code configuration. Contains project-specific permissions, hooks, MCP servers, and tool restrictions.
.claude/settings.local.json
Personal overrides. Gitignored. Your local preferences that override both global and project settings. This file wins in any conflict.
{
"model": "claude-sonnet-4-20250514",
"permissions": {
"allow": [
"Read",
"Write",
"Edit",
"Glob",
"Grep",
"Bash(npm run *)",
"Bash(npx prettier *)"
],
"deny": [
"Bash(rm -rf *)",
"Bash(git push *)"
]
},
"allowedTools": ["Read", "Write", "Edit", "Bash", "Glob", "Grep"],
"customInstructions": "Always run tests after modifying code"
}global β project β local. Local always wins. This means an individual developer can override project-wide settings without affecting the team. For arrays like allowedTools, the most specific file takes precedence entirely (not merged).
Hooks let you run custom commands before or after Claude Code uses tools. They are configured in settings.json under the "hooks" key. Hook output is injected back into the conversation as <system-reminder> tags.
Runs before a tool is called. Can block the call or inject context.
Runs after a tool completes. Use for auto-formatting, linting, notifications.
Fires when Claude sends a notification (e.g., task done).
Fires when Claude finishes its turn. Use for final validation.
Each hook has a matcher (tool name pattern to match) and a command to execute. The matcher can be an exact tool name or a regex pattern.
{
"hooks": {
"PreToolUse": [
{
"matcher": "Write",
"command": "echo 'About to write a file...'"
}
],
"PostToolUse": [
{
"matcher": "Write",
"command": "npx prettier --write $CLAUDE_FILE_PATH"
},
{
"matcher": "Edit",
"command": "npx eslint --fix $CLAUDE_FILE_PATH"
}
],
"Notification": [
{
"matcher": "",
"command": "notify-send 'Claude Code' '$CLAUDE_NOTIFICATION'"
}
],
"Stop": [
{
"matcher": "",
"command": "echo 'Claude finished its turn'"
}
]
}
}Claude Code implements a layered permission system that controls which tools the agent can use and whether it needs user approval for specific operations.
PERMISSION MODES
Asks for risky ops (write, bash), auto-approves reads
Read-only until a plan is approved; then executes
Auto-approves most tool calls; only asks for very risky ones
Approves everything without asking β no guardrails
Beyond the mode, you can restrict individual tools using allowedTools and disallowedTools. These can include patterns: Bash(npm run *) allows only npm run commands, while Bash(rm -rf *) in deny blocks destructive removals.
# CLI: restrict tools for this session
claude --allowedTools "Read,Write,Edit,Glob,Grep"
claude --disallowedTools "Bash,Agent"
# In settings.json:
{
"permissions": {
"allow": [
"Read", "Write", "Edit", "Glob", "Grep",
"Bash(npm run *)",
"Bash(npx *)"
],
"deny": [
"Bash(rm -rf *)",
"Bash(git push --force *)",
"Bash(curl *)"
]
}
}When the main agent spawns a subagent via the Agenttool, the subagent inherits the parent's permission settings by default. You can further restrict subagents by passing allowedTools to the Agent tool call. Subagents cannot escalatebeyond the parent's permissions β they can only be more restrictive, never less.
Claude Code can connect to Model Context Protocol (MCP) servers, extending its capabilities with external tools. MCP tools appear alongside built-in tools and can be used in the same agent loop.
# Add a server for the current project only
claude mcp add github-server --scope project -- \
npx -y @modelcontextprotocol/server-github
# Add a server globally (available in all projects)
claude mcp add filesystem-server --scope user -- \
npx -y @modelcontextprotocol/server-filesystem /path/to/dir
# List configured servers
claude mcp list
# Remove a server
claude mcp remove github-server{
"mcpServers": {
"github": {
"command": "npx",
"args": ["-y", "@modelcontextprotocol/server-github"],
"env": {
"GITHUB_TOKEN": "env:GITHUB_TOKEN"
}
},
"postgres": {
"command": "npx",
"args": ["-y", "@modelcontextprotocol/server-postgres"],
"env": {
"DATABASE_URL": "env:DATABASE_URL"
}
}
}
}--scope user: stored in ~/.claude/settings.json, available in all projects. --scope project: stored in .claude/settings.json, only available in this repo. Popular MCP servers include filesystem, GitHub, PostgreSQL, browser automation, and memory/knowledge servers.
Create reusable prompt templates by adding .md files to the .claude/commands/ directory. Each file becomes a slash command (e.g., review.md β /review).
Review the following code for:
1. Security vulnerabilities
2. Performance issues
3. Code style violations
4. Missing error handling
5. Test coverage gaps
Focus on: $ARGUMENTS
Be specific β cite line numbers and suggest fixes.Run a pre-deployment checklist:
1. Run all tests: npm test
2. Run linter: npm run lint
3. Check for console.log statements
4. Verify no TODO/FIXME in changed files
5. Ensure all env vars are documented
Report status for each check. $ARGUMENTSUse in a session: /review auth module or /deploy-check staging. The $ARGUMENTS placeholder is replaced with whatever follows the command name. Commands can also be placed in ~/.claude/commands/ for global availability across all projects.
Claude Code operates within a finite context window. As conversations grow, the system must manage what stays in context and what gets evicted.
Automatic Compaction
When context fills up, Claude Code automatically compacts: older tool outputs are cleared, and the conversation is summarized. The model retains the summary but loses verbatim details from earlier turns.
/compact
Manually trigger compaction to free up context space. Useful when you're about to start a complex task and want maximum room.
/context
Inspect current context usage β see how much space is consumed by conversation history, tool outputs, and system prompts.
Extended Thinking
For complex reasoning tasks, Claude Code can use extended thinking to allocate additional compute before responding. This is especially useful for architecture decisions and multi-step debugging.
Instructions in CLAUDE.md are re-injected after every compaction. This is why critical project rules, build commands, and style conventions belong in CLAUDE.md β they persist even as conversation history is pruned. Chat messages do not have this guarantee.
A production-grade workflow pattern tested in CCA scenarios. Instead of a single pass, use multiple specialized passes for higher quality output.
Main agent writes the code, creating or modifying files
Spawn a code-reviewer subagent (read-only) to critique the changes
Run the test suite; fix any failures in a feedback loop
This pattern keeps authoring and review as separate passes. The reviewer subagent is intentionally given only read access so it cannot modify the code β it can only report issues for the main agent to fix. This mirrors real code review workflows and prevents the reviewer from βfixingβ issues in ways that introduce new problems.
Claude Code's -p flag enables non-interactive mode, making it suitable for CI/CD pipelines. Combined with --output-format json, you get structured output for automated decision-making.
name: Claude Code Review
on: [pull_request]
jobs:
review:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
with:
fetch-depth: 0
- name: Install Claude Code
run: npm install -g @anthropic-ai/claude-code
- name: Review PR
env:
ANTHROPIC_API_KEY: ${{ secrets.ANTHROPIC_API_KEY }}
run: |
git diff origin/main...HEAD | \
claude -p "Review this diff for bugs, security issues, \
and style violations. Output JSON with severity levels." \
--output-format json \
--max-turns 5 > review.json
- name: Check results
run: |
# Parse review.json and fail if critical issues found
cat review.json | jq '.result'The Agent tool spawns independent subagents that run in their own context. This enables parallel execution, task isolation, and specialized workflows.
Fresh Context
Each subagent starts with a clean context window. It loads CLAUDE.md and AGENTS.md but does not inherit the parent's conversation history.
run_in_background: true
Run subagents in the background for parallel execution. The parent continues working and is notified when the subagent completes.
isolation: "worktree"
Creates a git worktree for the subagent so it works on an isolated copy of the codebase. Prevents file conflicts when multiple agents edit the same repository concurrently.
allowedTools restriction
Restrict which tools the subagent can use. A reviewer subagent might only get Read, Glob, Grep while an executor subagent gets full access.
# Conceptual: how the Agent tool is invoked internally
# 1. Background subagent with tool restrictions
Agent({
prompt: "Review src/auth/ for security issues",
allowedTools: ["Read", "Glob", "Grep"],
run_in_background: true
})
# 2. Worktree-isolated subagent for parallel dev
Agent({
prompt: "Implement the new dashboard feature",
isolation: "worktree",
run_in_background: true
})
# 3. Specialized subagent type
Agent({
prompt: "Write unit tests for the auth module",
subagent_type: "test-writer",
allowedTools: ["Read", "Write", "Edit", "Bash", "Glob", "Grep"]
})Claude Code has approximately 26 built-in tools. These are the core tools you need to know for the CCA exam β understand what each does and when it's appropriate.
KEY BUILT-IN TOOLS (~26 TOTAL)
| Tool | Description |
|---|---|
| Read | Read file contents (with line range support) |
| Write | Create or overwrite files |
| Edit | Surgical string replacements in existing files |
| Bash | Execute shell commands |
| Glob | Find files by glob pattern (fast) |
| Grep | Search file contents via ripgrep |
| Agent | Spawn subagents for parallel/isolated work |
| WebFetch | Fetch web page content |
| WebSearch | Search the web |
| NotebookEdit | Edit Jupyter notebook cells |
| TodoWrite | Manage internal task lists |
| ToolSearch | Discover deferred/MCP tools by query |
CLAUDE.md Hierarchy (memorize this order)
1. ~/.claude/CLAUDE.md (global) β 2. ./CLAUDE.md (project) β 3. ./subdir/CLAUDE.md (subdir) β 4. .claude/settings.json (project settings) β 5. .claude/settings.local.json (local overrides). Later wins.
Permission Modes
default (asks for risky ops) β plan (read-only until approved) β auto (auto-approve most) β bypassPermissions (approve all). Know which to recommend for each scenario.
Hook Events (4 types)
PreToolUse (before tool call) β’ PostToolUse (after tool call) β’ Notification (on notification) β’ Stop (on turn end). Configured in settings.json under "hooks". Output injected as <system-reminder> tags.
MCP Scope
--scope user β global (~/.claude/settings.json). --scope project β repo-local (.claude/settings.json). Know the difference and which file each modifies.
Non-Interactive Mode
claude -p "prompt" is the key flag for CI/CD and scripting. Combine with --output-format json for machine-readable output and --max-turns N to control cost.
Context Compaction
CLAUDE.md instructions survive compaction. Chat messages do not. This is why persistent rules go in CLAUDE.md, not in the chat. /compact triggers manual compaction; /context shows usage.
Subagent Permissions
Subagents inherit parent permissions but cannot escalate. They can only be more restrictive. Subagents start with fresh context and load CLAUDE.md + AGENTS.md.
Custom Slash Commands
.claude/commands/*.md for project commands, ~/.claude/commands/*.md for global. File name = command name. $ARGUMENTS is the only placeholder.
The CCA exam tests application of knowledge, not just recall. Practice these scenario patterns: