DEV Community

Cover image for Teaching GitHub Copilot About Your Codebase: What Custom Instructions, Skills, and MCP Servers Reveal About Agent Context Management
mech.app
mech.app

Posted on Originally published at mech.app

Teaching GitHub Copilot About Your Codebase: What Custom Instructions, Skills, and MCP Servers Reveal About Agent Context Management

GitHub's official guidance on teaching Copilot about your codebase reveals three distinct context management strategies: custom instructions, repository-specific skills, and MCP server connections. Each operates at a different layer of the agent stack, with different injection points, execution boundaries, and failure modes.

This is not about making Copilot "smarter." It's about understanding how context gets into the agent's working memory, where tool boundaries are drawn, and what happens when your codebase exceeds the context window.

Custom Instructions: System Message Injection

Custom instructions are prepended to every conversation as system-level context. They live in a .github/copilot-instructions.md file at the repository root.

Injection mechanism:

  • Loaded at conversation start
  • Treated as system messages, not user messages
  • Persist across turns within a session
  • Do not consume user-facing context window quota (they sit in the system prompt budget)

What to put here:

  • Coding standards (naming conventions, file structure)
  • Framework-specific patterns (React hooks rules, FastAPI dependency injection)
  • Security boundaries (never log PII, always validate input)
  • Deployment constraints (serverless cold start limits, container memory caps)

What not to put here:

  • Dynamic data (API keys, environment-specific config)
  • Large code samples (these blow the system prompt budget)
  • Frequently changing information (instructions are static per session)

Custom instructions are best for stable, repository-wide rules that apply to every interaction. They are not retrieval-augmented. If your instruction references a specific file, Copilot will not automatically fetch that file unless you explicitly open it or reference it in the conversation.

Repository Skills: In-Process Tool Calls

Skills are lightweight, repository-scoped functions that Copilot can invoke during a conversation. They run in the same process as the Copilot agent, not as external services.

Execution boundary:

  • Skills are JavaScript/TypeScript functions defined in .github/copilot-skills/
  • They execute synchronously within the agent's runtime
  • They have access to the local filesystem (read-only by default)
  • They can call external APIs, but latency blocks the agent

Example skill structure:

// .github/copilot-skills/get-api-schema.ts
export async function getApiSchema(endpoint: string): Promise<string> {
  const schemaPath = `./api/schemas/${endpoint}.json`;
  const schema = await fs.readFile(schemaPath, 'utf-8');
  return schema;
}

export const metadata = {
  name: "get-api-schema",
  description: "Fetches the OpenAPI schema for a given endpoint",
  parameters: {
    endpoint: { type: "string", description: "API endpoint name" }
  }
};
Enter fullscreen mode Exit fullscreen mode

When the agent decides to call a skill:

  1. User asks a question that matches the skill description
  2. Agent generates a tool call (function name + arguments)
  3. Skill executes, returns result as a string
  4. Result is injected into the conversation context
  5. Agent generates a response using the skill output

Failure modes:

  • Skill throws an exception: agent receives error message, may retry or apologize
  • Skill times out: agent waits (blocking), then fails
  • Skill returns too much data: context window overflow, truncation, or out-of-memory error

Skills are best for structured lookups (schema files, config templates, dependency graphs) that fit in memory and execute quickly. They are not sandboxed. A poorly written skill can crash the agent or leak secrets.

MCP Servers: External Tool Boundaries

Model Context Protocol (MCP) servers are external processes that expose tools, resources, and prompts over stdio or HTTP. Copilot connects to them as separate services.

Execution boundary:

  • MCP servers run as independent processes (local or remote)
  • Communication happens over JSON-RPC (stdio transport or SSE over HTTP)
  • Servers can expose multiple tools, each with its own schema
  • Copilot serializes tool calls, sends them to the server, waits for responses

Example: Playwright MCP server

GitHub's blog post mentions connecting a Playwright MCP server to Copilot. This server exposes browser automation tools (navigate, click, screenshot) as callable functions.

Connection flow:

  1. User configures MCP server in Copilot settings (server command, transport type)
  2. Copilot spawns the server process on startup
  3. Server sends tools/list response with available tools
  4. Agent sees tools in its function registry
  5. User asks Copilot to "take a screenshot of the login page"
  6. Agent calls playwright.screenshot tool
  7. MCP server executes Playwright script, returns base64 image
  8. Agent injects image into conversation, generates response

Security boundaries:

  • MCP servers can be sandboxed (Docker, VM, separate user)
  • Tool calls are explicit (agent must choose to invoke them)
  • Servers can reject calls (authentication, rate limiting)
  • Stdout/stderr are isolated from the agent's logs

Failure modes:

  • Server crashes: agent loses access to tools, may not notice until next call
  • Server hangs: agent waits indefinitely (no built-in timeout in MCP spec)
  • Server returns malformed JSON: agent fails to parse, treats as error
  • Server returns too much data: same context window overflow as skills

MCP servers are best for heavyweight operations (browser automation, database queries, external API calls) that need isolation, long-running execution, or access to resources the agent cannot reach directly.

Context Window Management: What Gets Included

When your codebase is too large to fit in the context window, Copilot uses a retrieval strategy to decide what to include.

Retrieval triggers:

  • User opens a file: file content is added to context
  • User references a symbol: definition and related code are fetched
  • User asks a question: semantic search over indexed codebase

Indexing strategy (inferred from behavior):

  • Copilot indexes repository content on clone or pull
  • Index includes file paths, symbol definitions, import graphs
  • Semantic embeddings are generated for code chunks (likely 512-1024 token chunks)
  • Retrieval uses cosine similarity between query embedding and chunk embeddings

What gets prioritized:

  1. Currently open files (always included)
  2. Recently edited files (recency bias)
  3. Files imported by open files (dependency graph)
  4. Semantically similar files (embedding search)
  5. Files mentioned in custom instructions (if explicitly referenced)

What gets excluded:

  • Binary files (images, compiled code)
  • Large generated files (lockfiles, build artifacts)
  • Files in .gitignore (usually, but not always)
  • Files outside the current workspace

Context window budget allocation (estimated):

Component Token Budget Refresh Rate
System prompt + custom instructions 2,000-4,000 Per session
Open files 8,000-16,000 Per edit
Retrieved context 4,000-8,000 Per query
Conversation history 4,000-8,000 Per turn
Tool call results 2,000-4,000 Per call

Total context window is likely 32k-64k tokens (GPT-4 Turbo range). When the budget is exceeded, older conversation turns are dropped first, then retrieved context, then open files are truncated.

Custom Agents: Multi-Agent Orchestration

GitHub's post mentions "custom agents" as a feature for creating specialized Copilot instances. This is multi-agent orchestration within the Copilot app.

Architecture (inferred):

  • Each custom agent has its own system prompt (custom instructions)
  • Each agent has access to a subset of skills and MCP servers
  • Agents can be invoked by name in the conversation (@agent-name do something)
  • Agents share the same conversation history (no isolated contexts)

Use cases:

  • Code review agent: has access to linting tools, test coverage reports
  • Deployment agent: has access to CI/CD APIs, infrastructure state
  • Documentation agent: has access to Markdown files, API schemas

Orchestration flow:

  1. User invokes agent by name
  2. Copilot switches system prompt to agent's custom instructions
  3. Agent has access to its configured tools (skills + MCP servers)
  4. Agent generates response, returns control to main conversation
  5. Conversation history includes agent's response (visible to all agents)

Failure modes:

  • Agent invoked with wrong context: generates irrelevant response
  • Agent lacks necessary tools: apologizes or asks user to switch agents
  • Agent conflicts with previous agent's advice: user must resolve manually

Custom agents are best for workflows that require different expertise or tool access at different stages (design, implementation, review, deployment). They are not isolated. All agents see the same conversation history, so context leakage is possible.

Observability Gaps

GitHub's guidance does not mention:

  • How to inspect which context was included in a given response
  • How to debug skill or MCP server failures (no error logs exposed)
  • How to measure token usage per component (system prompt, retrieval, tools)
  • How to trace tool call latency (skills vs. MCP servers)

What you can infer:

  • If Copilot references a file you didn't open, retrieval happened
  • If Copilot apologizes for not knowing something, retrieval failed or context was excluded
  • If Copilot takes a long time to respond, a tool call is likely blocking
  • If Copilot's response is truncated, context window overflow occurred

What you cannot infer:

  • Which files were retrieved and why
  • How much of the context window each component consumed
  • Whether a skill or MCP server was called (unless the response explicitly mentions it)
  • Why a particular tool was chosen over another

Technical Verdict

Use GitHub Copilot's context management features when:

  • Your codebase has stable, repository-wide conventions (custom instructions)
  • You need structured lookups that fit in memory (skills)
  • You need heavyweight operations with isolation (MCP servers)
  • You have multiple workflows that require different tool access (custom agents)

Avoid or supplement when:

  • Your codebase changes frequently (custom instructions lag behind)
  • You need fine-grained control over retrieval (no API for this)
  • You need observability into context window usage (no telemetry exposed)
  • You need guaranteed tool execution order (orchestration is opaque)
  • You need to debug why a particular file was or wasn't included (no trace logs)

The plumbing is pragmatic but opaque. Custom instructions and skills are easy to set up but hard to debug. MCP servers add isolation but introduce latency and failure modes. Custom agents enable multi-agent workflows but share context in ways that may surprise you.

If you need full control over context management, retrieval strategy, or tool orchestration, you will need to build your own agent layer on top of the LLM API. Copilot's abstractions are useful for common cases but do not expose the knobs required for advanced tuning.

Source Links

Top comments (0)