{"owner":"dotnet","repo":"efcore","hasSkills":true,"totalSkillsCount":52,"totalTokensCount":26001,"categories":["anthropic-skill","copilot-instructions","plugin-manifest"],"hasMcp":false,"mcpConfig":null,"found":[".agents/skills/make-github-actions-workflow/SKILL.md",".agents/skills/code-review/SKILL.md",".agents/skills/change-tracking/SKILL.md",".agents/skills/make-custom-agent/SKILL.md",".agents/skills/make-instructions/SKILL.md",".agents/skills/cosmos-provider/SKILL.md",".agents/skills/make-skill/SKILL.md",".agents/skills/model-building/SKILL.md",".agents/skills/migrations/SKILL.md",".agents/skills/run-apichief/SKILL.md",".agents/skills/query-pipeline/SKILL.md",".agents/skills/scaffolding/SKILL.md",".agents/skills/servicing-pr/SKILL.md",".agents/skills/sqlite-adonet/SKILL.md",".agents/skills/tooling/SKILL.md",".agents/skills/triage/SKILL.md",".agents/skills/update-pipeline/SKILL.md",".github/skills/agentic-workflows/SKILL.md",".github/copilot-instructions.md",".github/copilot/settings.json","src/EFCore.Tools/README.md","eng/Tools/ApiChief/README.md",".agents/skills/code-review/references/api-review.md",".agents/skills/code-review/references/conventions.md",".agents/skills/code-review/references/security-review.md","eng/harness-evaluation/skills/change-tracking/eval.yaml","eng/harness-evaluation/skills/code-review/eval.yaml","eng/harness-evaluation/skills/cosmos-provider/eval.yaml","eng/harness-evaluation/skills/make-custom-agent/eval.yaml","eng/harness-evaluation/skills/make-github-actions-workflow/eval.yaml","eng/harness-evaluation/skills/make-instructions/eval.yaml","eng/harness-evaluation/skills/make-skill/eval.yaml","eng/harness-evaluation/skills/migrations/eval.yaml","eng/harness-evaluation/skills/model-building/eval.yaml","eng/harness-evaluation/skills/query-pipeline/eval.yaml","eng/harness-evaluation/skills/run-apichief/eval.yaml","eng/harness-evaluation/skills/scaffolding/eval.yaml","eng/harness-evaluation/skills/servicing-pr/eval.yaml","eng/harness-evaluation/skills/sqlite-adonet/eval.yaml","eng/harness-evaluation/skills/tooling/eval.yaml","eng/harness-evaluation/skills/triage/eval.yaml","eng/harness-evaluation/skills/update-pipeline/eval.yaml","eng/harness-evaluation/skills/migrations/fixtures/upgrade-only/source-context.md","eng/harness-evaluation/skills/query-pipeline/fixtures/provider-test-placement/source-context.md","eng/harness-evaluation/skills/query-pipeline/fixtures/query-pipeline/split-query-review.md","eng/harness-evaluation/skills/query-pipeline/fixtures/single-result-lifting/integration.md","eng/harness-evaluation/skills/triage/fixtures/sandbox/embedded-directive.md","eng/harness-evaluation/skills/triage/fixtures/sandbox/issue-context.md","eng/harness-evaluation/skills/triage/fixtures/sandbox/security-report.md","eng/harness-evaluation/skills/triage/fixtures/sandbox/unsafe-setup.md","eng/harness-evaluation/skills/update-pipeline/fixtures/shared-identity/source-excerpts.md","eng/harness-evaluation/skills/code-review/fixtures/query-comment/context/review-context.md"],"skills":{".agents/skills/make-github-actions-workflow/SKILL.md":"---\nname: make-github-actions-workflow\ndescription: 'Create or modify GitHub Actions workflows for CI, automation, or PR management. Use when asked to create, scaffold, add, extend, or fix a workflow (.yml file under .github/workflows/), including existing pull-request policy and comment automation.'\n---\n\n# Create GitHub Actions Workflow\n\nCreate and configure GitHub Actions workflows that follow this repository's conventions and patterns. Workflows automate tasks like CI validation, PR management, issue labeling, and notifications.\n\n## Repository Conventions\n\nThis repository uses specific patterns across all workflows. Follow these conventions when creating new workflows:\n\n### File Location and Naming\n\n- All workflows live in `.github/workflows/`\n- Use kebab-case names: `label-and-milestone-issues.yml`, `validate-pr-target-branch.yml`\n- Start with a descriptive comment block explaining the workflow's purpose\n\n### Runner\n\n- Use `ubuntu-latest` for general-purpose jobs\n- Use `ubuntu-24.04` when a specific OS version is needed (e.g., copilot setup steps)\n\n### Permissions\n\n- **Always** declare explicit permissions — never rely on defaults\n- Use **minimal permissions**: only request what the workflow needs\n- Common patterns:\n  - Read-only: `permissions: {}`\n  - PR comments: `pull-requests: write`\n  - Issue management: `issues: write`\n  - Code read: `contents: read`\n- For workflows that need write access to PRs from external contributors, use `pull_request_target` instead of `pull_request`\n  - **Security warning:** `pull_request_target` workflows run in the base repository context with its permissions. Do **not** check out or execute code from the PR branch in these workflows. Instead, use the event payload and/or GitHub API (`actions/github-script`, `github.rest.*`, etc.) to inspect and act on the PR safely.\n\n### Scripting\n\n- Use `actions/github-script@v8` for complex logic instead of shell scripts\n- Write JavaScript with `async/await` — the `github` object (Octokit) and `context` are available\n- Use `github.rest.*` for REST API calls and `github.graphql()` for GraphQL queries\n- Access PR/issue data via `context.payload.pull_request`, `context.repo.owner`, `context.repo.repo`\n- Log with `console.log()` for debugging; use `core.setFailed()` for errors\n\n### Error Handling\n\n- Wrap API calls in try/catch blocks\n- Collect errors and report at the end rather than failing on the first error\n- Log skipped operations with a reason\n\n## Workflow\n\n### Step 1: Understand the Requirements\n\nBefore writing the workflow, clarify:\n- [ ] What event(s) should trigger it? (push, pull_request, check_suite, schedule, etc.)\n- [ ] What permissions are needed?\n- [ ] What conditions should gate execution? (author, branch, labels, etc.)\n- [ ] What API calls are needed?\n- [ ] Are there rate limiting or idempotency concerns?\n\n### Step 2: Choose the Trigger Event\n\n| Use case | Event | Notes |\n|----------|-------|-------|\n| PR opened/updated | `pull_request` | Read-only access to PR |\n| PR with write access | `pull_request_target` | Can comment, label, close |\n| PR merged | `pull_request_target: [closed]` | Check `github.event.pull_request.merged == true` |\n| CI checks complete | `check_suite: [completed]` | Filter `app.slug != 'github-actions'` to skip self |\n| Code pushed | `push` | Filter by branches/paths |\n| Manual trigger | `workflow_dispatch` | Add `inputs:` for parameters |\n| Scheduled | `schedule` | Use cron syntax |\n\n### Step 3: Write the Workflow\n\nCreate the YAML file following this template:\n\n```yaml\n# Description of what this workflow does and why.\n\nname: Descriptive Workflow Name\n\non:\n  <trigger_event>:\n    types: [<event_types>]\n\npermissions:\n  <resource>: <read|write>\n\njobs:\n  <job-name>:\n    if: <guard_condition>  # Optional: skip when not needed\n    runs-on: ubuntu-latest\n    steps:\n      - name: Descriptive step name\n        uses: actions/github-script@v8\n        with:\n          script: |\n            // Your logic here\n```\n\n### Step 4: Implement Guard Conditions\n\nAdd conditions to avoid unnecessary runs:\n- Job-level `if:` for event payload checks (e.g., `github.event.check_suite.app.slug != 'github-actions'`)\n- Early `return` in scripts for PR author, draft status, etc.\n- Idempotency checks (e.g., hidden HTML comments as tags to prevent duplicate actions)\n\nFor `pull_request_target` policy workflows that react to `opened`, `edited`, and `reopened`:\n\n- On `edited`, return unless `context.payload.changes?.base` is present; title or body edits must not reapply a target-branch policy.\n- Check permissions for `context.actor`, not only the PR author. A maintainer may edit or reopen an external PR, and that action must use the maintainer's authority.\n- For `opened`, the actor and author are the same, so perform one permission lookup and reuse it for policy and labeling decisions.\n- Exclude automation when either the actor or author is a bot.\n- Encode the prohibited branch class directly (for example, `release/*`) instead of requiring a single allowed branch such as `main`.\n- If permission lookup fails, stop without taking a destructive action; unknown access is not evidence that the contributor is external.\n\n### Step 5: Validate\n\nAfter creating the workflow:\n- [ ] Permissions are minimal and explicitly declared\n- [ ] Uses `actions/github-script@v8` for complex logic\n- [ ] Guard conditions prevent unnecessary runs\n- [ ] API calls handle pagination where needed (use `per_page: 100`)\n- [ ] Error handling doesn't silently swallow failures\n- [ ] No secrets or tokens are hardcoded\n- [ ] Workflow doesn't create infinite loops (e.g., a workflow that triggers itself)\n\n## Existing Workflows in This Repository\n\nStudy these workflows as reference:\n\n| Workflow | Trigger | Purpose |\n|----------|---------|---------|\n| `validate-pr-target-branch.yml` | `pull_request_target: [opened, edited, reopened]` | Closes external PRs targeting release branches, adds community labels |\n| `label-and-milestone-issues.yml` | `pull_request_target: [closed]` | Labels and milestones issues when their fixing PR is merged |\n| `copilot-setup-steps.yml` | `workflow_dispatch`, `push`, `pull_request` | Sets up the development environment for Copilot |\n| `inter-branch-merge-flow.yml` | `push` to `release/**` | Triggers inter-branch merge via arcade |\n\n## Common Patterns\n\n### Commenting on a PR\n\n```javascript\nawait github.rest.issues.createComment({\n  owner: context.repo.owner,\n  repo: context.repo.repo,\n  issue_number: prNumber,\n  body: 'Comment text'\n});\n```\n\n### Checking User Permissions\n\n```javascript\nconst { data: permissions } = await github.rest.repos.getCollaboratorPermissionLevel({\n  owner: context.repo.owner,\n  repo: context.repo.repo,\n  username: context.actor\n});\nconst hasWriteAccess = ['admin', 'write'].includes(permissions.permission);\n```\n\n### Updating Bot-Owned Comments Idempotently\n\nA hidden marker identifies the workflow's comment but does not establish ownership: contributors and other apps can place the same marker in their comments. Match both the marker and the exact `github-actions[bot]` login, then update that comment or create a new one. A generic `user.type === 'Bot'` check does not establish workflow ownership. Preserve the workflow's pinned action SHA and never execute code from a pull-request fork in a `pull_request_target` job.\n\n```javascript\nconst marker = '<!-- validate-pr-target-branch -->';\nconst comments = await github.paginate(github.rest.issues.listComments, {\n  owner: context.repo.owner,\n  repo: context.repo.repo,\n  issue_number: prNumber,\n  per_page: 100\n});\n\nconst body = `${marker}\\nComment text`;\nconst existing = comments.find(comment =>\n  comment.user?.login === 'github-actions[bot]' && comment.body?.includes(marker));\n\nif (existing) {\n  await github.rest.issues.updateComment({\n    owner: context.repo.owner,\n    repo: context.repo.repo,\n    comment_id: existing.id,\n    body\n  });\n} else {\n  await github.rest.issues.createComment({\n    owner: context.repo.owner,\n    repo: context.repo.repo,\n    issue_number: prNumber,\n    body\n  });\n}\n```\n\n### Reading Repository Files at a Specific Commit\n\n```javascript\nconst { data: fileData } = await github.rest.repos.getContent({\n  owner, repo,\n  path: 'eng/Versions.props',\n  ref: commitSha\n});\nconst content = Buffer.from(fileData.content, 'base64').toString('utf-8');\n```\n\n## References\n\n- [GitHub Actions documentation](https://docs.github.com/en/actions)\n- [Workflow syntax](https://docs.github.com/en/actions/using-workflows/workflow-syntax-for-github-actions)\n- [Events that trigger workflows](https://docs.github.com/en/actions/using-workflows/events-that-trigger-workflows)\n- [actions/github-script](https://github.com/actions/github-script)\n",".agents/skills/code-review/SKILL.md":"---\nname: code-review\ndescription: 'Review EF Core pull requests or local changes for concrete correctness, compatibility, performance, security, and test-coverage problems. Use when asked to review, critique, or check code changes before merge or submission.'\n---\n\n# EF Core Code Review\n\nReview pull requests and local working-tree changes without modifying source. Findings must be concrete, evidence-backed problems introduced or exposed by the change, not style preferences or general improvement ideas.\n\n## Scope and Safety\n\n- Review the provided pull request, or staged, unstaged, and untracked local changes. Ask for clarification when both are plausible.\n- Never checkout, switch branches, stash, reset, clean, or otherwise mutate the working tree, except for checking out the requested head for review purposes. Never edit source as part of a review.\n- For a pull request, record its base, head, and immutable head SHA. If local `HEAD` differs, use read-only repository or GitHub context when sufficient; otherwise ask the user to checkout the requested commit.\n- Never submit an `APPROVE` or `REQUEST_CHANGES` event. COMMENT emission follows Step 8.\n- Do not use this skill to address existing review comments or implement fixes.\n\n## Workflow\n\n### 1. Establish the Review Surface\n\n1. Load `.github/copilot-instructions.md` and any area skill whose description matches the changed implementation.\n2. Obtain the complete diff and changed-file list once. Include staged, unstaged, and untracked files for local reviews.\n3. For pull requests, gather the base/head refs and head SHA, but defer the PR body, linked issues, and prior review comments until Step 3.\n4. Stop with a clear limitation if the requested change surface cannot be established.\n\n### 2. Form an Independent Assessment\n\nBefore reading the author's narrative:\n\n1. Read each changed implementation beyond its diff hunk. Diff-only review is insufficient evidence for a finding. For very large files, read the containing members, their contracts, and relevant state. When many files are changed, use subagents to break down the review into manageable parts and gather context incrementally.\n2. Search callers, implementations, overrides, sibling provider paths, and nearby tests. Read shared helpers whose contracts control the changed behavior.\n3. When logic moves, compare the old and new input domains. Check the moved member's XML contract as well as regression coverage.\n4. Use focused history to explain invariants, reverts, or prior rejected approaches; establish what makes a repeated approach viable now.\n5. Describe the old and new behavior, likely motivation, affected callers/providers, and initial concerns in your own words.\n\n### 3. Holistic PR Assessment\n\nAssess the overall approach before refining implementation details:\n\n- Require a concrete need for added code, APIs, abstractions, and flags. Prefer the simplest sufficient alternative; weigh benefits against complexity, surface area, and long-term maintenance.\n- Prefer root-cause fixes at the owning layer. Challenge a flawed direction early rather than polishing its implementation.\n- Require BenchmarkDotNet results or equivalent measurements for performance claims; prefer focused local runs for experimental or iterative work.\n - Explain and address scenario-specific regressions even when aggregate results improve.\n- Scale required benefit and validation with regression risk and blast radius, especially for stable code.\n\n### 4. Reconcile Pull Request Context\n\nFor pull requests, now read the description, linked issues, and existing review threads. Treat them as claims to verify against the code. Also flag found problems the PR narrative doesn't acknowledge.\n\nIf the additional context reveals information that genuinely changes your evaluation, update your holistic assessment accordingly. But do not soften findings just because the PR description sounds reasonable.\n\n### 5. Route Conditional Reviews\n\n- Read [references/api-review.md](references/api-review.md) when the change adds, removes, or changes supported public or protected API outside an `.Internal` namespace and not annotated with `[EntityFrameworkInternal]`.\n- Read [references/security-review.md](references/security-review.md) when changed data crosses a documented trust boundary or the change affects serialization, generated code from database metadata, command construction, sensitive-data handling, caches or complexity bounds, assembly loading, elevated operations, or another high-risk path.\n\n### 6. Analyze Behavior and Coverage\n\nFor each non-trivial production change, identify:\n\n1. **Changed behavior**: the concrete old and new code paths.\n2. **Affected surfaces**: callers, providers, public contracts, generated output, persistence, diagnostics, and concurrency where applicable.\n3. **Regression risks**: plausible inputs, interleavings, failures, or compatibility breaks.\n4. **Expected coverage**: the focused test that would fail without the change or expose the regression.\n5. **Coverage gaps**: affected behavior not exercised by changed or existing tests.\n\nCheck correctness, error handling, async behavior, concurrency, state and resource lifetime, compatibility, provider hierarchy behavior, NativeAOT constraints, and performance only where the changed path plausibly makes them relevant.\n\nFor exception cleanup around shared or concurrent state, distinguish whether this invocation acquired each resource from whether the resource currently appears held. Cover both a failing owner releasing its acquisition and a failing contender preserving another owner's acquisition, including preexisting nested state. Construct a concrete interleaving without weakening existing reentrancy or nesting behavior.\n\nFor new functionality consider other feature areas that might be affected but are not directly touched by the change.\n\nDo not request tests for documentation-only changes, comments, formatting, or demonstrably behavior-preserving mechanical changes. Do not flag issues that the compiler, formatter, or existing analyzers deterministically report.\n\n### 7. Optional Multi-Model Review\n\nWhen the environment supports launching sub-agents with different models (e.g., the `task` tool with a `model` parameter), run the review in parallel across multiple model families to get diverse perspectives. Different models catch different classes of issues. If the environment does not support this, proceed with a single-model review.\n\n1. Inspect the available model list and select models from 2-3 distinct model families, up to 3 sub-agent models total. If fewer than 2 eligible families are available, use what is available.\n   - Pick only from models explicitly listed as available in the environment. Do not guess or assume model names.\n   - Never pick models labeled \"mini\", \"fast\", or \"cheap\" for code review.\n   - Do not select a model from the same family that is already running the primary review (i.e. the currently used model).\n   - If multiple models exist in the same family, pick the one with the highest version number. Prefer \"-codex\" variants over general-purpose.\n   - If the model supports effort configuration use the one closest to the current effort level.\n2. Launch a sub-agent for each selected model in parallel, giving each the same review prompt: the PR diff, the review rules from this skill, and instructions to produce findings in the severity format defined above.\n3. Wait for all agents to complete, then synthesize: deduplicate findings that appear across models, elevate issues flagged by multiple models (higher confidence), and include unique findings from individual models that meet the confidence bar. If a sub-agent has not completed after 10 minutes and you have results from other agents, proceed with the results you have.\n4. Present a single unified review to the user, noting when an issue was flagged by multiple models. Do not wait for any remaining sub-agents and do not attempt retries if any failed. The review is complete once the report operation succeeds.\n\n### 7. Verify and Report Findings\n\nBefore reporting a concern:\n\n- Verify it against surrounding and unchanged code, including caller/callee defenses.\n- Identify a realistic failure or user impact. Do not promote a theoretical possibility with negligible likelihood into a finding.\n- Verify factual claims about APIs from repository evidence or current documentation; never rely on model memory to claim an API is absent, deprecated, or unavailable.\n- Report only test results actually observed. Separate unexecuted validation and residual risk from findings.\n\nOrder findings by severity:\n\n- ❌ **Critical**: practical exploitation, arbitrary code execution, widespread data loss, or similarly catastrophic impact.\n- 🔴 **High**: merge-blocking correctness, security, compatibility, data-integrity, or concurrency defect.\n- ⚠️ **Medium**: concrete defect with limited impact or a meaningful regression gap for changed behavior.\n- 🔵 **Low**: minor but real defect worth fixing in this change.\n- 💡 **Info**: observations or suggestions that do not constitute a defect but may improve code quality or maintainability.\n\nEach finding must contain:\n\n1. Severity and concise title.\n2. Certainty level or confidence in the finding based on the available evidence.\n3. Changed file and line or symbol.\n4. Concrete failure mode and impact.\n5. Evidence that makes the finding actionable.\n6. Fix direction and, when relevant, the missing regression-test shape.\n\nPresent the holistic assessment before findings. Do not add praise or filler.\n\n**Motivation**: <1-2 sentences on whether the PR is justified and the problem is real>\n\n**Approach**: <1-2 sentences on whether the fix/change takes the right approach>\n\n**Summary**: <✅ LGTM / ⚠️ Needs Human Review / ⚠️ Needs Changes / ❌ Reject>. <2-3 sentence summary of the overall verdict and key points. If \"Needs Human Review,\" explicitly state which findings you are uncertain about and what a human reviewer should focus on.>\n\n### 8. Optionally Post Pull Request Comments\n\nPosting is allowed through either authorization path:\n\n- **Direct invocation**: number the findings, let the user select or edit them, and obtain explicit confirmation before posting.\n- **Code-reviewer agent delegation**: an invoking code-reviewer agent may explicitly authorize COMMENT emission and provide the selected findings or complete review payload. That caller contract is sufficient authorization; do not add a redundant confirmation prompt. An analysis-only delegation does not authorize posting.\n\nImmediately before posting, confirm that the pull request is still open and its base, head, and head SHA match the reviewed revision. If they changed, stop and refresh the review context.\n\nCreate a pending review, add only authorized findings, and submit it as `COMMENT`. Never approve or request changes. Include a concise AI-generated disclosure when posting under a user's identity rather than a bot identity. Do not post findings that are similar to existing or resolved comments; for multiple defects in the same area, consolidate them into a single finding when appropriate.\n\n## Validation\n\n- Every finding resolves to changed code or a changed contract and cites supporting repository evidence.\n- Test requests follow the behavior-impact analysis.\n- No source or worktree mutation occurred.\n- Any posted review used the reviewed head SHA and COMMENT-only authorization.\n\n## Common Pitfalls\n\n- Reviewing hunks without their callers or provider hierarchy.\n- Treating a public CLR member in `.Internal` as supported public API.\n- Reporting a security keyword without tracing attacker-controlled data to an impact.\n- Inferring that passing broad tests covers the changed failure mode.\n- Turning uncertainty into a firm finding instead of investigating or recording a limitation.",".agents/skills/change-tracking/SKILL.md":"---\nname: change-tracking\ndescription: 'Implementation details for EF Core change tracking. Use when changing InternalEntityEntry, ChangeDetector, SnapshotFactoryFactory, or related entity state, snapshot, or property accessor code.'\nuser-invocable: false\n---\n\n# Change Tracking\n\nManages entity states and detects changes for `SaveChanges()`.\n\n## Core Components\n\n- `StateManager` — owns tracked entries, identity/reference maps, fixup, cascades, notifications, and changed counts\n- `InternalEntryBase` and derived classes — own per-entry state, flags, values, snapshots, and ordered state transitions\n- `ChangeDetector` — compares current values with baselines and reports changes through entry mutation APIs\n- `SnapshotFactoryFactory` subclasses — create passive original- and relationship-value baselines\n- `IdentityMap` — permits one active entry per key; shared identity pairs a replacement with the prior `Deleted` entry\n- `PropertyAccessorsFactory`, `ClrPropertyGetterFactory` and `ClrPropertySetterFactory` compile property accessors for efficient snapshotting and change detection\n  - Ordinals in `indices` parameter specify element at each complex collection depth\n\n## Change Detection\n\n- Snapshot and notification strategies both call `SetPropertyModified()` to keep property flags and entity state consistent.\n- `SetEntityState()` validates values, updates flags and complex entries, changes state, then runs manager bookkeeping hooks.\n\n## Shared-Identity Replacement\n\n`SharedIdentityEntry` is the invariant that distinguishes an old deleted entry from its replacement with the same identity. When attaching a replacement graph, a deleted nested entry should be reconsidered only when its source entry has a replacement; do not broadly process every deleted node. Likewise, cascading from the old replaced principal must not delete dependents that belong to the replacement graph. Keep synchronous and asynchronous graph-attach paths equivalent and preserve unrelated values in replacement tests so they isolate the identity transition.\n\n## Testing\n\nUnit tests: `test/EFCore.Tests/ChangeTracking/`. Functional tests: `test/EFCore.Specification.Tests/GraphUpdates/`.\n\n## Common Pitfalls\n\n| Pitfall | Solution |\n|---------|----------|\n| State-based checks treat every Added/Deleted entry as a replacement | Scope replacement behavior through `SharedIdentityEntry` and the graph source |\n\n## Validation\n\n- `DetectChanges()` identifies modified properties via snapshot comparison\n- Setting original values marks properties as modified or unchanged based on comparison with current values\n",".agents/skills/make-custom-agent/SKILL.md":"---\nname: make-custom-agent\ndescription: 'Create, review, or fix custom GitHub Copilot agents. Use when asked to create, scaffold, configure, review, or restrict a custom agent, declarative agent, or @-invokable chat participant for GitHub Copilot.'\n---\n\n# Create Custom Agent\n\nThis skill guides you through creating a custom GitHub Copilot agent — an `@`-invokable chat participant that extends Copilot with domain-specific expertise. Custom agents are distinct from Agent Skills: skills provide reusable instructions loaded on demand, while agents own the full conversational interaction and can orchestrate tools, call APIs, and maintain their own prompt strategies.\n\n## When Not to Use\n\n- Adding reusable, invokable workflows — use Agent Skills (`.agents/skills/`) instead\n- Adding background coding guidelines — use file-based instructions (`.github/instructions/`) instead\n- Adding project-wide context for Copilot — use `.github/copilot-instructions.md` instead\n- Creating reusable prompts — use .prompt.md instead\n\n## Workflow\n\nFor an existing proposal, audit the full definition rather than just its tools: the description must identify natural requests that should discover it, the body must add domain knowledge beyond root instructions, and the paired eval must isolate its contribution. Compare every tool and behavior to the user's intended authority. A command-free reviewer must not gain command execution or publication through a wildcard tool, handoff, or otherwise read-only workflow.\n\n### Step 1: Choose the agent type\n\n| Type | Location | Best for |\n|---|---|---|\n| Declarative (prompt file) | `.github/agents/<name>.md` | Simple prompt-driven cross-surface agents with no code |\n| Extension-based (chat participant) | VS Code extension project | Full control, tool calling, VS Code API access |\n| GitHub App (Copilot Extension) | Hosted service + GitHub App | Cross-surface agents (github.com, VS Code, Visual Studio) |\n\nIf the agent only needs a scoped system prompt and doesn't require custom code, start with a declarative agent.\n\n### Step 2: Create a declarative agent (prompt file)\n\nDeclarative agents are Markdown files in `.github/agents/`. VS Code and GitHub Copilot discover them automatically.\n\n```\n.github/agents/\n└── <agent-name>.md        # Agent definition\n```\n\nTemplate:\n\n```markdown\n---\nname: my-agent\ndescription: A short description of what this agent does and when to use it.\n---\n\n# <Agent Title>\n\nYou are an expert in <domain>. Your job is to:\n- <behavior 1>\n- <behavior 2>\n\n## Guidelines\n\n- <guideline 1>\n- <guideline 2>\n\n## Workflow\n\n1. <step 1>\n2. <step 2>\n\n## Constraints\n\n- <constraint 1>\n- <constraint 2>\n\n```\n\nSupported frontmatter fields:\n\n| Field | Required | Description |\n|---|---|---|\n| `name` | Yes | Lowercase, hyphens allowed. Used for `@`-mention. |\n| `description` | Yes | What the agent does and when to use it. Shown in the participant list. |\n| `target` | No | Target environment: `vscode` or `github-copilot` (defaults to both) |\n| `tools` | No | List of allowed tools/tool sets |\n| `model` | No | LLM name or prioritized array of models |\n| `user-invocable` | No | Show in agents dropdown (default: true) |\n| `disable-model-invocation` | No | Prevent subagent invocation (default: false) |\n| `mcp-servers` | No | MCP server configs for GitHub Copilot target |\n| `metadata` | No | Key-value mapping for additional arbitrary metadata. |\n| `argument-hint` | No | Hint text guiding user interaction (VS Code only) |\n| `agents` | No | List of allowed subagents (`*` for all, `[]` for none, VS Code only) |\n| `handoffs` | No | List of next-step agent transitions (VS Code only) |\n\n\nTips for instructions:\n- Use Markdown links to reference other files\n- Reference tools with `#tool:<tool-name>` syntax\n- Be specific about agent behavior and constraints\n\n### Step 3: Configure tools\n\nSpecify which tools the agent can use:\n\n```yaml\ntools:\n  - search              # Built-in tool\n  - fetch               # Built-in tool\n  - codebase            # Tool set\n  - myServer/*          # All tools from MCP server\n```\n\nCommon tool patterns:\n- **Read-only agents**: `['search', 'fetch', 'codebase']`\n- **Full editing agents**: `['*']` or specific editing tools\n- **Specialized agents**: Cherry-pick specific tools\n\n### Step 4: Add handoffs (optional, VS Code only)\n\nConfigure transitions to other agents:\n\n```yaml\nhandoffs:\n  - label: Start Implementation\n    agent: implementation\n    prompt: Implement the plan outlined above.\n    send: false\n    model: GPT-5.2 (copilot)\n```\n\nHandoff fields:\n- `label`: Button text displayed to user\n- `agent`: Target agent identifier\n- `prompt`: Pre-filled prompt for target agent\n- `send`: Auto-submit prompt (default: false)\n- `model`: Optional model override for handoff\n\n### Step 5: Create an extension-based chat participant (VS Code only)\n\nFor full control, implement a VS Code extension with a chat participant:\n\n1. **Define the participant** in `package.json`:\n\n```json\n\"contributes\": {\n    \"chatParticipants\": [\n        {\n            \"id\": \"my-extension.my-agent\",\n            \"name\": \"my-agent\",\n            \"fullName\": \"My Agent\",\n            \"description\": \"Short description shown in chat input\",\n            \"isSticky\": false,\n            \"commands\": [\n                {\n                    \"name\": \"explain\",\n                    \"description\": \"Explain the selected code\"\n                }\n            ]\n        }\n    ]\n}\n```\n\n2. **Register and implement the request handler** in `extension.ts`:\n\n```typescript\nexport function activate(context: vscode.ExtensionContext) {\n    const agent = vscode.chat.createChatParticipant('my-extension.my-agent', handler);\n    agent.iconPath = vscode.Uri.joinPath(context.extensionUri, 'icon.png');\n}\n\nconst handler: vscode.ChatRequestHandler = async (\n    request: vscode.ChatRequest,\n    context: vscode.ChatContext,\n    stream: vscode.ChatResponseStream,\n    token: vscode.CancellationToken\n) => {\n    const model = request.model;\n    const messages = [\n        vscode.LanguageModelChatMessage.User(request.prompt)\n    ];\n    const response = await model.sendRequest(messages, {}, token);\n    for await (const fragment of response.text) {\n        stream.markdown(fragment);\n    }\n};\n```\n\n3. **Declare the extension dependency** in `package.json`:\n\n```json\n\"extensionDependencies\": [\"github.copilot-chat\"]\n```\n\n4. **Add tool calling (optional)**\n\nAgents can invoke language model tools registered by other extensions:\n\n```typescript\nconst tools = vscode.lm.tools.filter(tool => tool.tags.includes('my-domain'));\nconst result = await chatUtils.sendChatParticipantRequest(request, context, {\n    prompt: 'You are an expert in <domain>.',\n    tools,\n    responseStreamOptions: { stream, references: true, responseText: true }\n}, token);\nreturn await result.result;\n```\n\n### Step 6: Create a GitHub App (Copilot Extension) for cross-surface availability (optional)\n\nIf the agent should be available on GitHub.com, Visual Studio, JetBrains, and VS Code simultaneously, implement a GitHub App that acts as a Copilot Extension. The app registers a webhook endpoint, receives chat requests, and streams responses back.\n\nKey considerations:\n- The GitHub App must be installed on the user's account or organization\n- Responses are streamed via Server-Sent Events (SSE)\n- Use the [GitHub Copilot Extensions documentation](https://docs.github.com/en/copilot/building-copilot-extensions/about-building-copilot-extensions) for the full integration guide\n- For VS Code-specific features (editor access, file trees, command buttons), prefer an extension-based participant instead\n\n### Step 7: Author the harness evaluation\n\nCreate `eng/harness-evaluation/agents/<agent-id>/eval.yaml` and follow `eng/harness-evaluation/README.md`.\n\n- Declare only the agent file in the eval's root `agent_environment.files`; the experiment removes it from the control.\n- Use realistic stimuli that exercise behavior distinctive to the agent without stating the expected diagnosis or implementation in the prompt.\n- Combine deterministic output checks, a focused semantic rubric, bounded resources, token grading, and a committed scoring threshold.\n- Keep the eval name and directory-derived component ID identical to the agent ID.\n\n### Step 8: Validate\n\nAfter creating or modifying an agent, verify:\n\n- [ ] `name` is lowercase, uses hyphens (no spaces), and is unique\n- [ ] `description` clearly describes what the agent does and when to invoke it\n- [ ] Frontmatter YAML is valid (no syntax errors)\n- [ ] Declarative agent file is in `.github/agents/`\n- [ ] Tools list contains only available tools\n- [ ] Extension-based agent: participant ID matches in `package.json` and `createChatParticipant` call\n- [ ] Agent does not duplicate functionality of built-in agents (`@workspace`, `@vscode`, `@terminal`)\n- [ ] Handoff agent names match existing agents\n- [ ] Agent instructions don't include secrets, tokens, or internal URLs\n- [ ] The paired harness eval targets only this agent and is meant to meaningfully distinguish treatment from control\n\n## Common Pitfalls\n\n| Pitfall | Solution |\n|---------|----------|\n| Agent name conflicts with built-in participants | Use a unique prefix (domain name) |\n| Description is too vague | Include specific keywords users would naturally say |\n| System prompt is too long | Keep instructions to essential behaviors; move reference material to Agent Skills |\n| Agent requires VS Code API but is authored as declarative | Switch to extension-based participant |\n| Using `isSticky: true` unnecessarily | Only set sticky if the agent should persist between turns by default |\n| No `extensionDependencies` on `github.copilot-chat` | Add it; otherwise the contribution point may not be available |\n| Agent invoked as subagent unexpectedly | Set `disable-model-invocation: true` |\n| Subagent appears in the dropdown | Set `user-invocable: false` |\n\n## References\n\n- [VS Code Chat Participant API](https://code.visualstudio.com/api/extension-guides/ai/chat)\n- [VS Code AI Extensibility Overview](https://code.visualstudio.com/api/extension-guides/ai/ai-extensibility-overview)\n- [VS Code Extension Samples – chat-sample](https://github.com/microsoft/vscode-extension-samples/tree/main/chat-sample)\n- [GitHub Copilot Extensions documentation](https://docs.github.com/en/copilot/building-copilot-extensions/about-building-copilot-extensions)\n- [GitHub Copilot Custom agents configuration](https://docs.github.com/en/copilot/reference/custom-agents-configuration)\n- [Agent Skills Specification](https://agentskills.io/specification)\n- Related repository skills: `make-skill` and `make-instructions`\n",".agents/skills/make-instructions/SKILL.md":"---\nname: make-instructions\ndescription: 'Create and evaluate VS Code file-based instructions (.instructions.md files). Use when asked to create, scaffold, or add file-based instructions for Copilot. Generates scoped instructions and a paired Vally harness eval.'\n---\n\n# Create File-Based Instructions\n\nThis skill helps you scaffold VS Code file-based instructions (`.instructions.md` files) that provide background knowledge to Copilot about specific parts of the codebase. These files are applied automatically based on glob patterns or semantic matching, giving Copilot domain-specific context when working on matching files.\n\n## When Not to Use\n\n- Setting project-wide instructions — use `.github/copilot-instructions.md` or `AGENTS.md` instead\n- Creating reusable agent workflows with structured steps — use Agent Skills instead\n- Adding instructions that need to be invokable on demand — use Agent Skills instead\n\n## Workflow\n\n### Step 1: Investigate the topic\n\nBuild understanding of the area the instructions should cover. Identify:\n\n- [ ] What files or file patterns the instructions apply to\n- [ ] Key conventions, patterns, or architectural rules for that area\n- [ ] Common pitfalls that Copilot should avoid\n- [ ] Non-obvious domain knowledge that isn't discoverable from code alone\n\nRead the repository-wide instruction files that apply to the same paths and make an explicit exclusion list. Do not repeat those rules in the new file, even when they are relevant examples for the scoped area; include only guidance that becomes more specific or materially different at the narrower scope.\n\nIf the scope is unclear or overlaps with existing instructions, ask the user for clarification.\n\n### Step 2: Choose the file location\n\nInstructions files go in `.github/instructions/` by default. Pick a descriptive filename:\n\n```\n.github/instructions/<topic>.instructions.md\n```\n\nExamples: `csharp-style.instructions.md`, `query-pipeline.instructions.md`, `test-conventions.instructions.md`\n\n### Step 3: Generate the file with YAML frontmatter\n\nCreate the file with the required YAML frontmatter header:\n\n```yaml\n---\nname: '<Display Name>'              # Optional. Display name in the UI. Defaults to filename.\ndescription: '<Short description>'  # Optional. Shown on hover. Also used for semantic matching.\napplyTo: '<glob pattern>'           # Optional. Glob pattern relative to workspace root. Omit to require manual attachment or rely on semantic matching only.\n---\n```\n\nCommon `applyTo` patterns:\n\n- `**/*.cs` — all C# files\n- `test/**` — files under a specific folder\n\n### Step 4: Write the body content\n\nWrite concise, actionable Markdown content. Follow these principles:\n\n- **Be concise** — instructions share the context window; only include what the agent wouldn't already know\n- **Be specific** — use concrete rules, not vague guidance\n- **Include examples** — short code snippets showing preferred vs. avoided patterns are very effective\n- **Explain why** — when a rule exists for a non-obvious reason, state it so the agent applies it correctly in edge cases\n- **Skip linter-enforced rules** — don't repeat what formatters and linters already catch\n- **Use Markdown links** to reference specific files or URLs for additional context\n\nRecommended sections (adapt as needed):\n\n1. **<Title>** — one-line heading describing the domain\n2. **Context paragraph** — brief explanation of what this area is and why these rules matter\n3. **Guidelines / Conventions** — bullet list of concrete rules\n4. **Examples** — short code blocks showing do/don't patterns (optional)\n5. **Key Files** — table of important files for orientation (optional)\n6. **Common Pitfalls** — traps to avoid (optional)\n\n### Step 5: Author and validate the harness evaluation\n\nCreate `eng/harness-evaluation/instructions/<id>/eval.yaml`, where `<id>` is the instruction path relative to `.github/instructions/` with its suffix removed and nested path separators replaced by `--`.\n\nFollow the authoring and validation rules in `eng/harness-evaluation/README.md`. Exercise guidance distinctive to the instruction and ensure the treatment meaningfully outperforms the omitted-instruction control.\n\nFor initial authoring, produce and lint the requested instruction and eval before running behavioral comparisons.\n\nAfter creating the file, verify:\n\n- [ ] File is in `.github/instructions/` (or a configured instructions folder)\n- [ ] Filename ends with `.instructions.md` and only contains lowercase letters, numbers, and hyphens\n- [ ] YAML frontmatter is valid\n- [ ] `applyTo` glob matches the intended files\n- [ ] Content is concise (aim for under 500 lines or 5000 tokens) — long instructions dilute effectiveness\n- [ ] No secrets, tokens, or internal URLs included\n- [ ] Instructions don't duplicate what's already in `.github/copilot-instructions.md` or under `.agents/skills/`\n- [ ] The paired eval demonstrates behavior that the omitted-instruction control does not provide reliably\n\n## Common Pitfalls\n\n| Pitfall | Solution |\n|---------|----------|\n| `applyTo` too broad | Use specific globs; `**` applies to every file and wastes context |\n| Missing `applyTo` | Without it, instructions won't auto-apply — they require manual attachment or semantic matching via `description` |\n| Vague guidance | Replace \"write good tests\" with something like \"add both positive and negative test cases using `[ConditionalFact]` methods\" |\n",".agents/skills/cosmos-provider/SKILL.md":"---\nname: cosmos-provider\ndescription: 'Implementation details for the EF Core Azure Cosmos DB provider. Use when changing Cosmos-specific code.'\nuser-invocable: false\n---\n\n# Cosmos DB Provider\n\nNon-relational provider with its own parallel query pipeline. Uses JSON for document materialization.\n\n## Key Differences from Relational\n\n- No migrations — use `EnsureCreated()`\n- Documents as JSON — owned and complex types become embedded objects\n- Partition key configuration required for performance\n- `ETag` for optimistic concurrency\n- No cross-container joins\n\n## Azure Cosmos DB Emulator for Tests\n\n- `TestEnvironment.InitializeAsync()` auto-starts a `Testcontainers.CosmosDb` container when `Test__Cosmos__DefaultConnection` is not set. Set the env var to use an existing emulator instead.\n- Skip tests requiring unsupported features on the Linux emulator with ` [ConditionalFact(typeof(CosmosTestEnvironment), nameof(CosmosTestEnvironment.IsNotLinuxEmulator))]`.\n",".agents/skills/make-skill/SKILL.md":"---\nname: make-skill\ndescription: 'Create, review, or fix Agent Skills for GitHub Copilot. Use when asked to create, scaffold, improve, or repair a SKILL.md and its paired harness evaluation.'\n---\n\n# Create Or Fix A Skill\n\nProduce concise, stable task guidance that adds knowledge an agent cannot reliably infer from source alone, together with a paired evaluation that proves the guidance changes behavior.\n\n## Choose The Right Primitive\n\n- Use a skill for a task-specific workflow or body of knowledge loaded on demand.\n- Use file instructions for background guidance scoped to paths.\n- Use a custom agent when context isolation or distinct tool restrictions are required.\n- Prefer an existing skill over creating an overlapping one.\n\n## Workflow\n\n1. Read the relevant implementation, tests, repository instructions, and neighboring customizations.\n2. Identify repeated mistakes or non-obvious invariants. Do not turn source inventories, line counts, or facts easily rediscovered from code into skill content.\n3. Create `.agents/skills/<name>/SKILL.md`. The frontmatter `name` must exactly match the directory; the description must state what the skill does and when natural user requests should trigger it.\n4. Mark background domain guidance `user-invocable: false`. Keep user-invocable workflows focused on an outcome a user would deliberately request.\n5. Write actionable guidance with observable validation. Explain why edge cases matter; avoid generic engineering advice already present in repository instructions.\n6. Create `eng/harness-evaluation/skills/<name>/eval.yaml` and follow `eng/harness-evaluation/README.md`.\n7. Lint the customization and inspect both control and treatment artifacts before accepting it.\n\n## Paired Evaluation\n\n- The eval root `agent_environment.skills` contains only the target skill. Stimulus inputs belong under each stimulus's `agent_environment.files`.\n- The runner removes the root skill for control and separately verifies treatment activation. Do not add a `skill-invocation` grader and do not tell the agent to invoke the skill in the shared prompt.\n- Prompts may identify fixtures, proposed code, fixed IDs, and output paths, but must not reveal the expected diagnosis, owning mechanism, or regression-test design.\n- Stage self-contained source snapshots rather than diffs or commit references; fixture context must not require fetching a repository revision.\n- Use deterministic graders for observable artifacts, a narrow semantic rubric for behavior, and a `token-budget` grader. Define bounded turns, tokens, and duration plus a committed scoring threshold.\n- The task must exercise guidance distinctive to the skill. A control that consistently matches treatment means the skill or eval is not useful enough.\n\n## Validation\n\n- Frontmatter parses and the name matches the directory.\n- The skill is concise, stable, and does not duplicate root or scoped instructions.\n- File references are relative and exist.\n- Validation steps are observable and task-specific.\n- The paired eval targets only the skill, has complete bounded grading, and uses a solution-neutral prompt.\n- `npm run lint` and the harness inventory tests pass.\n\n## Common Pitfalls\n\n| Pitfall | Correction |\n|---|---|\n| Copying implementation inventories into the skill | Keep only non-obvious invariants and routing decisions |\n| Exact line counts or volatile metrics | Remove them; point to stable symbols or behavior |\n| Generic test-folder guidance | Describe the distinctive test shape or omit it |\n| Eval prompt tells the agent what to find | Move expected facts into the hidden rubric |\n| Eval root contains repository fixtures | Keep only the target skill at root; stage fixtures per stimulus |\n| Prompt instructs skill invocation | Let the treatment-only runner gate enforce activation |\n| Initial scaffold launches multi-model review | First produce and lint the requested artifacts; run expensive behavioral validation separately |",".agents/skills/model-building/SKILL.md":"---\nname: model-building\ndescription: 'Implementation details for EF Core model building. Use when changing ConventionSet, ModelBuilder, IConvention implementations, ModelRuntimeInitializer, RuntimeModel, or related classes.'\nuser-invocable: false\n---\n\n# Model Building, Conventions & Initialization\n\nCovers model construction (conventions, fluent API, metadata hierarchy) and model initialization (runtime annotation propagation, compiled model filtering).\n\n## Convention System\n\n`ConventionSet` (`src/EFCore/Metadata/Conventions/ConventionSet.cs`) holds `List<I*Convention>` for every metadata event. Key conventions in `src/EFCore/Metadata/Conventions/`:\n\n- `DbSetFindingConvention` — discovers entities from `DbSet<T>`\n- `PropertyDiscoveryConvention` — discovers properties from CLR types\n- `KeyDiscoveryConvention` — finds PKs (`Id`, `TypeId`)\n- `RelationshipDiscoveryConvention` — infers FKs from navigations\n- `RuntimeModelConvention` — creates optimized `RuntimeModel` from mutable model\n\nOverride `ConfigureConventions(ModelConfigurationBuilder)` to add/remove conventions.\n\nConvention fixes must preserve dispatcher behavior and ambiguity information. For inverse-navigation attributes, do not solve recursion by permanently ignoring an ambiguous navigation: removing one candidate can make another ambiguity appear unique and configure the wrong relationship. `InversePropertyAttributeConvention` records inverse candidates and uses `AddInverseNavigation`, `TryRemoveIfAmbiguous`, and `FindAmbiguousInverse` while still allowing convention processing to continue.\n\nTest the state transitions, not only the initially ambiguous model: first verify that multiple interacting candidates configure no relationship; then genuinely remove ambiguity both by ignoring/removing one competing navigation and by removing a competing entity type, and verify that the remaining inverse relationship is configured. These cases distinguish candidate bookkeeping from a permanent-ignore workaround.\n\n## Metadata Interface Hierarchy\n\n`IReadOnly*` → `IMutable*` → `IConvention*` → `IRuntime*`\n\nApplies to: Model, EntityType, Property, Key, ForeignKey, Navigation, Index, etc. Builders follow: `*Builder` → `IConvention*Builder`.\n\n## Adding A Configurable Metadata Facet\n\nFollow the nearest existing facet end to end rather than stopping at the public interface:\n\n1. Add the read-only, mutable, and convention metadata contracts, concrete storage, default, configuration source, convention setter, and builder precedence checks. Preserve the facet when metadata is replaced or a relationship is rebuilt.\n2. If changes are observable to conventions, add the convention interface, every `ConventionSet` add/replace/remove path, and immediate plus delayed dispatcher scopes and nodes.\n3. Carry the value into the optimized runtime metadata through `RuntimeModelConvention`, runtime constructors/builders, and `CSharpRuntimeModelCodeGenerator` so compiled models preserve it.\n4. If snapshots persist the facet, update the fluent builder API and `CSharpSnapshotGenerator`; keep the old absence equivalent to the historical default.\n5. Update public API baselines and cover configuration-source precedence, convention dispatch, runtime/compiled model propagation, and snapshot round trips.\n\n## Model Lifecycle\n\n1. **Mutable Model** — built by `ModelBuilder` during `OnModelCreating`, made read-only by `FinalizeModel()`\n2. **Design-Time Model** — finalized read-only `Model` that also contains design-time-only annotations used in migrations\n3. **Runtime Model** — an optimized read-only model created by `RuntimeModelConvention.ProcessModelFinalized()`, does not contain design-time-only annotations\n\n`ModelRuntimeInitializer.Initialize()` (called by `DbContextServices.CreateModel()`):\n\n```\nInitialize(model, designTime, validationLogger)\n├─ FinalizeModel() if mutable\n├─ Set ModelDependencies, InitializeModel\n└─ RuntimeModelConvention creates RuntimeModel, copies/filters annotations\n```\n\n## Complex Type Property Recursion\n\nWhen processing properties in conventions or validation, remember that complex types can contain their own declared properties. Use `GetFlattenedProperties()` to iterate all properties (including on nested non-collection complex types) or manually recurse through `GetDeclaredComplexProperties()` → `complexProperty.ComplexType`.\n\n## Adding a New Annotation\n\n1. Add constant to `CoreAnnotationNames` and its `AllNames`\n2. Filter in `RuntimeModelConvention.ProcessModelAnnotations` if it's a design-time-only annotation (only used in migration operations)\n   1. If it was filtered out, add logic to the getters that throws an exception if accessed on the runtime model\n3. Filter in `CSharpRuntimeAnnotationCodeGenerator.Generate` if it can be computed lazily at runtime (e.g. based on other annotations)\n4. Propagate in `RelationalAnnotationProvider` if used in up-migrations or the relational model and `IMigrationsAnnotationProvider` if used in down-migrations\n\n## Relational Model\n\n`RelationalModel` (`src/EFCore.Relational/Metadata/Internal/RelationalModel.cs`) is a database-centric view of the EF model, mapping entity types to physical database objects: `Tables`, `Views`, `Functions`, `Queries`, and `DefaultTables`. `DefaultTables` are pseudo-table objects only used for `FromSql` queries.\n\nCreated lazily by `RelationalModelRuntimeInitializer`, accessed via `model.GetRelationalModel()`. Used by migrations (`MigrationsModelDiffer`), update and query pipelines.\n\n`RelationalAnnotationProvider` populates annotations on relational model elements. Provider subclasses (e.g., `SqlServerAnnotationProvider`) add provider-specific annotations. `IMigrationsAnnotationProvider` controls annotations used in down-migration operations.\n\n## Model Validation\n\n`ModelValidator` (`src/EFCore/Infrastructure/ModelValidator.cs`) and `RelationalModelValidator` (`src/EFCore.Relational/Infrastructure/RelationalModelValidator.cs`) run after model finalization, during `ModelRuntimeInitializer.Initialize()` between the pre- and post-validation `InitializeModel` calls.\n\n## Migration Snapshot Compatibility\n\nModel-building changes can trigger spurious migrations for users who upgrade. Two causes:\n\n1. **New metadata written to the snapshot** — old snapshots won't have it; `MigrationsModelDiffer` sees a diff. Fix: ensure absence of the annotation in an old snapshot is treated as the old default.\n2. **Annotation renamed or reinterpreted** — old snapshots produce a different model. Fix: keep backward-compatible reading logic.\n\nInspect `CSharpSnapshotGenerator` (what gets written) and `MigrationsModelDiffer` (how absence is handled). Add a snapshot round-trip test in `test/EFCore.Design.Tests/Migrations/ModelSnapshotSqlServerTest.cs`.\n\n## Testing\n\n| Area | Location |\n|------|----------|\n| Convention unit tests | `test/EFCore.Tests/Metadata/Conventions/` |\n| Metadata unit tests | `test/EFCore.Tests/Metadata/Internal/` |\n| Model builder API tests | `test/EFCore.Specification.Tests/ModelBuilding/ModelBuilderTest*.cs` |\n| Relationship discovery tests | `test/EFCore.Specification.Tests/ModelBuilding101*.cs` |\n| Model validation tests | `test/EFCore.Tests/Infrastructure/ModelValidatorTest*.cs` |\n| Compiled model tests | `test/EFCore.Specification.Tests/Scaffolding/CompiledModelTestBase.cs` |\n\n## Validation\n\n- Model builds without `InvalidOperationException` during finalization\n- All new API is covered by tests\n- Compiled model baselines update cleanly with `EF_TEST_REWRITE_BASELINES=1`\n- `ToString()` on metadata objects shows concise contents without throwing exceptions\n- No spurious migration is generated against a project with an existing snapshot",".agents/skills/migrations/SKILL.md":"---\nname: migrations\ndescription: 'Implementation details for EF Core migrations. Use when changing MigrationsSqlGenerator, model diffing, migration operations, HistoryRepository, the Migrator or related classes.'\nuser-invocable: false\n---\n\n# Migrations\n\n## Pipeline\n\n**Add migration**: `MigrationsScaffolder.ScaffoldMigration()` → `MigrationsModelDiffer.GetDifferences()` → list of `MigrationOperation` → `CSharpMigrationsGenerator` and `CSharpSnapshotGenerator` produce Up/Down/Snapshot code\n\n**Apply migration**: `Migrator.MigrateAsync()` → reads `__EFMigrationsHistory` → per pending: `MigrationsSqlGenerator.Generate(operations)` → `MigrationCommandExecutor` executes\n\n## Model Snapshot\n\n- Model snapshots use `typeof(Dictionary<string, object>)` (property bag format), not the actual CLR type. When examining the `ClrType` in a snapshot, don't assume it matches the real entity type.\n- `SnapshotModelProcessor.Process()` is used at design-time to fixup older model snapshots for backward compatibility.\n- `MigrationsModelDiffer` uses provider-agnostic structural comparison between relational models to determine what migration operations are necessary.\n\nFor an upgrade-only regression, derive a concrete old `ModelSnapshot`, process its model with `SnapshotModelProcessor.Process(..., resetVersion: true)`, and compare it with the equivalent current design-time model through `MigrationsModelDiffer.GetDifferences()`. Preserve the property-bag CLR types emitted by old snapshots and omit APIs that would explicitly configure metadata that was absent in that version. The regression succeeds only when the resulting operation list is empty.\n\nLegacy snapshot normalization belongs in `SnapshotModelProcessor`, not in runtime migration application. Scope a compatibility branch to the exact released versions that could emit the affected snapshot shape; versions from before the feature existed should not be included merely because they are numerically older. Prefer the mutable metadata interface when it exposes the required setter rather than casting to a concrete metadata implementation. Do not use a missing configuration source as the test for missing historical snapshot metadata: old snapshots may already configure a value using the current default. For metadata whose semantics changed, use the snapshot's product version to restore the old invariant. Add focused coverage for every version family named by the gate, plus the first unaffected version.\n\n## Testing\n\nMigration operation tests: `test/EFCore.Relational.Tests/Migrations/`. Functional tests: `test/EFCore.{Provider}.FunctionalTests/Migrations/`. Model differ tests: `test/EFCore.Relational.Tests/Migrations/Internal/MigrationsModelDifferTest*.cs`.\n\nTo simulate a snapshot model use `ModelBuilder` calls without conventions.",".agents/skills/run-apichief/SKILL.md":"---\nname: run-apichief\ndescription: 'Run ApiChief in the EF Core repo to emit baselines, summaries, deltas, review files, or breaking-change checks. Use when refreshing `*.baseline.json`, preparing API review artifacts, or validating API changes.'\nuser-invocable: false\n---\n\n# Run ApiChief\n\nUse the ApiChief tool documented at `eng/Tools/ApiChief/README.md` to inspect or refresh EF Core public API baselines for projects under `src/`.\n\nApiChief can run against either a compiled assembly or a previously emitted baseline JSON file. Prefer the repo-local `.dotnet` SDK and the checked-in build scripts in this repo.\n\n## Commands\n\n| Command | Description | Extra arguments |\n| --- | --- | --- |\n| `emit baseline` | Emit a JSON API baseline | `-o <file>` |\n| `emit summary` | Emit a human-readable API summary | `-o <file>`, `-x` |\n| `emit review` | Emit API review files | `-o <dir>`, `-n` |\n| `emit delta` | Emit a delta against an existing baseline, or markdown diff review files | `<baseline-path>`, `-o <file-or-dir>`, `--diff` |\n| `check breaking` | Fail if breaking changes exist vs. a baseline | `<baseline-path>` |\n\nDefault to `emit baseline` if the user only asks to \"run ApiChief\".\n\n## Workflow\n\n### 1. Identify the target project(s)\n\n- Match user intent against project folders under `src/`.\n- Ask for clarification only if the target is ambiguous.\n- The checked-in baseline path convention in this repo is `src/<ProjectName>/<ProjectName>.baseline.json`.\n- If asked just to update the baselines, run EFCore.ApiBaseline.Tests tests and skip the rest of the steps below.\n\n### 2. Prepare the environment\n\nAlways initialize the repo environment before building or running the tool:\n\n```powershell\n.\\restore.cmd\n. .\\activate.ps1\ndotnet build .\\eng\\Tools\\ApiChief\\ApiChief.csproj --nologo --verbosity q\n```\n\nOn Bash:\n\n```bash\n./restore.sh\n. ./activate.sh\ndotnet build ./eng/Tools/ApiChief/ApiChief.csproj --nologo --verbosity q\n```\n\n### 3. Ensure the target binaries exist\n\nApiChief operates on built assemblies. If the target project has not been built yet, build it first.\n\nPreferred options:\n\n```powershell\n# Refreshes checked-in baselines after the normal build\n.\\build.cmd -c Debug\n\n# Or build a single project when working narrowly\ndotnet build .\\src\\<ProjectName>\\<ProjectName>.csproj --nologo --verbosity q\n```\n\nUse the highest available `net*` TFM under `artifacts/bin/<ProjectName>/<Configuration>/` by default. Avoid `netstandard*` and `net4*` targets unless the user explicitly asks for them.\n\n### 4. Locate the built ApiChief binary and target assembly\n\n```powershell\n$dotnet = \".\\\\.dotnet\\\\dotnet\"\n$apiChiefProject = \".\\\\eng\\\\Tools\\\\ApiChief\\\\ApiChief.csproj\"\n$apiChief = (& $dotnet msbuild $apiChiefProject --getProperty:TargetPath -p:Configuration=Debug --nologo).Trim()\n\n$name = \"<ProjectName>\"\n$tfm = Get-ChildItem \".\\\\artifacts\\\\bin\\\\$name\\\\Debug\" -Directory |\n    Where-Object { $_.Name -match '^net\\d+\\.\\d+$' } |\n    Sort-Object { [version]($_.Name -replace '^net', '') } -Descending |\n    Select-Object -First 1 -ExpandProperty Name\n\n$assemblyName = (& $dotnet msbuild \".\\\\src\\\\$name\\\\$name.csproj\" --getProperty:AssemblyName -p:Configuration=Debug --nologo).Trim()\nif ([string]::IsNullOrWhiteSpace($assemblyName))\n{\n    $assemblyName = $name\n}\n\n$assemblyPath = \".\\\\artifacts\\\\bin\\\\$name\\\\Debug\\\\$tfm\\\\$assemblyName.dll\"\n```\n\nBefore running, report the selected TFM if it matters for the task.\n\n### 5. Run the requested ApiChief command\n\n```powershell\n# Emit a baseline\n& $dotnet $apiChief $assemblyPath emit baseline -o \".\\\\src\\\\$name\\\\$name.baseline.json\"\n\n# Emit a summary\n& $dotnet $apiChief $assemblyPath emit summary\n\n# Emit a delta\n& $dotnet $apiChief $assemblyPath emit delta \".\\\\src\\\\$name\\\\$name.baseline.json\" -o \".\\\\artifacts\\\\tmp\\\\$name.delta.json\"\n\n# Check for breaking changes\n& $dotnet $apiChief $assemblyPath check breaking \".\\\\src\\\\$name\\\\$name.baseline.json\"\n\n# Emit API review artifacts\n& $dotnet $apiChief $assemblyPath emit review -o \".\\\\artifacts\\\\tmp\\\\API.$name\"\n\n# Emit GitHub-friendly markdown diff files against a baseline\n& $dotnet $apiChief $assemblyPath emit delta \".\\\\src\\\\$name\\\\$name.baseline.json\" --diff -o \".\\\\artifacts\\\\tmp\\\\API.$name.Diff\"\n```\n\n`emit delta` also supports passing a `.json` file as the current input instead of a DLL.\n\n### 6. Review or clean up baseline changes\n\nAfter `emit baseline`:\n\n- preserve the original BOM and trailing newline behavior of the committed file\n- revert version-only diffs in the `\"Name\"` field\n- inspect removed `//` instruction comments in previous baselines and carry forward any still-needed manual edits\n- if those comments reference GitHub issues, check whether the underlying issue is still open before reapplying the workaround\n\n### 7. Report results clearly\n\n- list the processed project(s)\n- show the chosen TFM(s)\n- report the output path(s)\n- for `check breaking`, state pass/fail\n- for `emit delta` and `emit delta --diff`, mention that exit code `0` means changes, `2` means no changes, and `-1` means an error\n- prefer `emit delta --diff` output because it generates ready-to-post ```diff fenced markdown split across per-type `.md` files\n",".agents/skills/query-pipeline/SKILL.md":"---\nname: query-pipeline\ndescription: 'Implement and review EF Core query translation, projection visitors, split-query enumeration, and query regression tests. Use when changing query-pipeline code or choosing specification and provider coverage for a query regression.'\nuser-invocable: false\n---\n\n# Query Pipeline\n\n## Regression Test Ownership\n\n- Group query specification tests by a cohesive query or model trait. Do not create a generic bucket merely because tests use custom models; use the existing trait-specific hierarchy, such as owned-entity queries.\n- Inspect the specification base and provider overrides before placing a regression. Keep the LINQ query, model setup, and result assertions in the shared virtual test; provider overrides call the base and add only provider-specific baselines or established limitations.\n- A provider-only test can leave every other provider untested even when its SQL assertion is correct. Preserve override guards without adding a guard that forces unrelated redundant overrides.\n- For an optimization, cover both eligible and rejected shapes with exact result assertions in sync and async. Supply a concrete provider override and SQL baseline or established limitation; an abstract test base or expression-shape check alone does not prove execution coverage.\n\n## Translation\n\n- Translation fallback must distinguish established unsupported shapes from unexpected defects. Do not turn arbitrary exceptions into a successful fallback.\n- Check whether a failed rewrite mutated state that fallback will reuse. For test coordination, establish the actual collection, assembly, and async-flow boundaries before claiming shared static state can race; theory rows are not inherently parallel, and reset in `finally` is not mutual exclusion.\n\n## Optimizations\n\n- Match the equivalence needed by the rewrite, not blindly by expression equality.\n- Preserve context-specific null semantics. SQL UNKNOWN can be filtered like `false` in a predicate but not in a projected value or under negation; `UseRelationalNulls`, null-containing `IN`/`NOT IN`, and scalar versus composite LINQ join keys require different compensation.\n- Preserve cardinality and operator order, not just matching rows. Moving predicates across outer joins, adding keys under `Distinct`/`GroupBy`, or converting correlated APPLY to JOIN can change results; per-parent pagination must retain its partitioning and ordering, and remaining outer references must prevent decorrelation.\n- Share repeated subqueries only when their evaluation and row selection are equivalent. Volatile expressions, query filters introduced during later navigation expansion, and required-navigation joins can change evaluation count or which row survives a limit. Check determinism and row preservation before reuse, and collect candidates within their own lambda scope.\n- Preserve SQL typing and CLR result semantics separately. Remove a cast only when its store-type effect is redundant; casts on constants can establish necessary SQL typing. SQL nullable columns do not alone describe shaper nullability: `DefaultIfEmpty` on a non-nullable scalar may require `COALESCE` to its CLR default.\n- Remap dependent state when changing query shape. Subquery pushdown or join replacement must update scoped column references, predicates, orderings, projection bindings, and shapers; retain or recompute identifiers and their comparers when multiplicity or null extension changes.\n- Prove pruning safety beyond the final projection. An unused join can still filter or multiply rows, so honor explicit prunability and references from other clauses. Unreferenced columns can still define distinct/set-operation membership or a scalar subquery's result; preserve those contracts and compatible set-operation projections.\n\n## Split Queries\n\n- When changing `SplitQueryResultCoordinator`, check both `SplitQueryingEnumerable` and `GroupBySplitQueryingEnumerable`, including their synchronous and asynchronous paths. End-of-stream validation belongs at true outer-stream exhaustion, not at a group boundary or early disposal.\n- A grouped reader can reach physical EOF while assembling a final group that still must be yielded. Test that successful move separately from the subsequent terminal move, including verification failure and repeated terminal calls; cleanup must preserve the original failure.\n- Account for internal buffering as well as caller materialization when assessing memory use. Earlier split-query result sets may need buffering when the provider cannot keep multiple readers active; retrying execution strategies can also require buffering.\n- Buffering does not give separate query commands a consistent database snapshot. Concurrent writes between commands can produce an inconsistent result graph; consider snapshot or serializable transactions when consistency is required, accounting for provider support and transaction costs.\n- Prove cross-command consistency with a writer transaction and an explicit barrier between reads, not sleeps or a prose-only scenario. Assert a root/child value combination, not just matching keys; state the isolation and retry-strategy boundaries of the test.\n\n## Validation\n\n- `ToQueryString()` shows generated SQL without executing\n- `ExpressionPrinter` dumps expression trees at any pipeline stage\n- SQL baselines verified via `AssertSql()` in provider functional tests and the generated SQL corresponds to the LINQ query in the base method\n",".agents/skills/scaffolding/SKILL.md":"---\nname: scaffolding\ndescription: 'Implementation details for EF Core scaffolding (reverse engineering). Use when changing ef dbcontext scaffold pipeline implementation, database schema reading, CSharpModelGenerator, or related classes.'\nuser-invocable: false\n---\n\n# Scaffolding\n\nGenerates C# code from database schemas (reverse engineering).\n\n## When Not to Use\n\n- Working on compiled model generation (`dotnet ef dbcontext optimize`)\n\n## Reverse Engineering\n\nPipeline: `IDatabaseModelFactory` (reads schema) → `IScaffoldingModelFactory` (builds EF model) → `IModelCodeGenerator` (generates C#)\n- `IReverseEngineerScaffolder` — orchestrates full pipeline\n\n## Schema Query Compatibility\n\nProvider schema readers often query one-to-many metadata tables. Preserve anti-semi semantics when adapting SQL for a limited engine: a `LEFT JOIN` containing the complete excluded-property predicate in `ON`, followed by a null filter on a non-nullable joined key, is equivalent to `NOT EXISTS`. Unrelated metadata rows do not join; any matching excluded row makes the joined key non-null and excludes the object. Do not move parts of the excluded-property predicate to `WHERE` or join all metadata rows and filter individual rows afterward. An equivalent non-correlated anti-set form, such as `NOT IN (SELECT key ... WHERE excluded-condition)`, also works when the subquery cannot return null keys. Cover objects with no metadata, unrelated metadata only, the excluded property only, and both excluded and unrelated properties.\n",".agents/skills/servicing-pr/SKILL.md":"# servicing-pr\n\nPath: `.agents/skills/servicing-pr/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/servicing-pr/SKILL.md)",".agents/skills/sqlite-adonet/SKILL.md":"# sqlite-adonet\n\nPath: `.agents/skills/sqlite-adonet/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/sqlite-adonet/SKILL.md)",".agents/skills/tooling/SKILL.md":"# tooling\n\nPath: `.agents/skills/tooling/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/tooling/SKILL.md)",".agents/skills/triage/SKILL.md":"# triage\n\nPath: `.agents/skills/triage/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/triage/SKILL.md)",".agents/skills/update-pipeline/SKILL.md":"# update-pipeline\n\nPath: `.agents/skills/update-pipeline/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/update-pipeline/SKILL.md)",".github/skills/agentic-workflows/SKILL.md":"# agentic-workflows\n\nPath: `.github/skills/agentic-workflows/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.github/skills/agentic-workflows/SKILL.md)",".github/copilot-instructions.md":"# GitHub Copilot Instructions\n\nPath: `.github/copilot-instructions.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.github/copilot-instructions.md)",".github/copilot/settings.json":"# GitHub Copilot Instructions\n\nPath: `.github/copilot/settings.json`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.github/copilot/settings.json)","src/EFCore.Tools/README.md":"# EFCore.Tools Documentation\n\nPath: `src/EFCore.Tools/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/src/EFCore.Tools/README.md)","eng/Tools/ApiChief/README.md":"# ApiChief Documentation\n\nPath: `eng/Tools/ApiChief/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/Tools/ApiChief/README.md)",".agents/skills/code-review/references/api-review.md":"# References Skill\n\nPath: `.agents/skills/code-review/references/api-review.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/code-review/references/api-review.md)",".agents/skills/code-review/references/conventions.md":"# References Skill\n\nPath: `.agents/skills/code-review/references/conventions.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/code-review/references/conventions.md)",".agents/skills/code-review/references/security-review.md":"# References Skill\n\nPath: `.agents/skills/code-review/references/security-review.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/code-review/references/security-review.md)","eng/harness-evaluation/skills/change-tracking/eval.yaml":"# Change-tracking Skill\n\nPath: `eng/harness-evaluation/skills/change-tracking/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/change-tracking/eval.yaml)","eng/harness-evaluation/skills/code-review/eval.yaml":"# Code-review Skill\n\nPath: `eng/harness-evaluation/skills/code-review/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/code-review/eval.yaml)","eng/harness-evaluation/skills/cosmos-provider/eval.yaml":"# Cosmos-provider Skill\n\nPath: `eng/harness-evaluation/skills/cosmos-provider/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/cosmos-provider/eval.yaml)","eng/harness-evaluation/skills/make-custom-agent/eval.yaml":"# Make-custom-agent Skill\n\nPath: `eng/harness-evaluation/skills/make-custom-agent/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/make-custom-agent/eval.yaml)","eng/harness-evaluation/skills/make-github-actions-workflow/eval.yaml":"# Make-github-actions-workflow Skill\n\nPath: `eng/harness-evaluation/skills/make-github-actions-workflow/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/make-github-actions-workflow/eval.yaml)","eng/harness-evaluation/skills/make-instructions/eval.yaml":"# Make-instructions Skill\n\nPath: `eng/harness-evaluation/skills/make-instructions/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/make-instructions/eval.yaml)","eng/harness-evaluation/skills/make-skill/eval.yaml":"# Make-skill Skill\n\nPath: `eng/harness-evaluation/skills/make-skill/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/make-skill/eval.yaml)","eng/harness-evaluation/skills/migrations/eval.yaml":"# Migrations Skill\n\nPath: `eng/harness-evaluation/skills/migrations/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/migrations/eval.yaml)","eng/harness-evaluation/skills/model-building/eval.yaml":"# Model-building Skill\n\nPath: `eng/harness-evaluation/skills/model-building/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/model-building/eval.yaml)","eng/harness-evaluation/skills/query-pipeline/eval.yaml":"# Query-pipeline Skill\n\nPath: `eng/harness-evaluation/skills/query-pipeline/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/query-pipeline/eval.yaml)","eng/harness-evaluation/skills/run-apichief/eval.yaml":"# Run-apichief Skill\n\nPath: `eng/harness-evaluation/skills/run-apichief/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/run-apichief/eval.yaml)","eng/harness-evaluation/skills/scaffolding/eval.yaml":"# Scaffolding Skill\n\nPath: `eng/harness-evaluation/skills/scaffolding/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/scaffolding/eval.yaml)","eng/harness-evaluation/skills/servicing-pr/eval.yaml":"# Servicing-pr Skill\n\nPath: `eng/harness-evaluation/skills/servicing-pr/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/servicing-pr/eval.yaml)","eng/harness-evaluation/skills/sqlite-adonet/eval.yaml":"# Sqlite-adonet Skill\n\nPath: `eng/harness-evaluation/skills/sqlite-adonet/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/sqlite-adonet/eval.yaml)","eng/harness-evaluation/skills/tooling/eval.yaml":"# Tooling Skill\n\nPath: `eng/harness-evaluation/skills/tooling/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/tooling/eval.yaml)","eng/harness-evaluation/skills/triage/eval.yaml":"# Triage Skill\n\nPath: `eng/harness-evaluation/skills/triage/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/triage/eval.yaml)","eng/harness-evaluation/skills/update-pipeline/eval.yaml":"# Update-pipeline Skill\n\nPath: `eng/harness-evaluation/skills/update-pipeline/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/update-pipeline/eval.yaml)","eng/harness-evaluation/skills/migrations/fixtures/upgrade-only/source-context.md":"# Upgrade-only Skill\n\nPath: `eng/harness-evaluation/skills/migrations/fixtures/upgrade-only/source-context.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/migrations/fixtures/upgrade-only/source-context.md)","eng/harness-evaluation/skills/query-pipeline/fixtures/provider-test-placement/source-context.md":"# Provider-test-placement Skill\n\nPath: `eng/harness-evaluation/skills/query-pipeline/fixtures/provider-test-placement/source-context.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/query-pipeline/fixtures/provider-test-placement/source-context.md)","eng/harness-evaluation/skills/query-pipeline/fixtures/query-pipeline/split-query-review.md":"# Query-pipeline Skill\n\nPath: `eng/harness-evaluation/skills/query-pipeline/fixtures/query-pipeline/split-query-review.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/query-pipeline/fixtures/query-pipeline/split-query-review.md)","eng/harness-evaluation/skills/query-pipeline/fixtures/single-result-lifting/integration.md":"# Single-result-lifting Skill\n\nPath: `eng/harness-evaluation/skills/query-pipeline/fixtures/single-result-lifting/integration.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/query-pipeline/fixtures/single-result-lifting/integration.md)","eng/harness-evaluation/skills/triage/fixtures/sandbox/embedded-directive.md":"# Sandbox Skill\n\nPath: `eng/harness-evaluation/skills/triage/fixtures/sandbox/embedded-directive.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/triage/fixtures/sandbox/embedded-directive.md)","eng/harness-evaluation/skills/triage/fixtures/sandbox/issue-context.md":"# Sandbox Skill\n\nPath: `eng/harness-evaluation/skills/triage/fixtures/sandbox/issue-context.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/triage/fixtures/sandbox/issue-context.md)","eng/harness-evaluation/skills/triage/fixtures/sandbox/security-report.md":"# Sandbox Skill\n\nPath: `eng/harness-evaluation/skills/triage/fixtures/sandbox/security-report.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/triage/fixtures/sandbox/security-report.md)","eng/harness-evaluation/skills/triage/fixtures/sandbox/unsafe-setup.md":"# Sandbox Skill\n\nPath: `eng/harness-evaluation/skills/triage/fixtures/sandbox/unsafe-setup.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/triage/fixtures/sandbox/unsafe-setup.md)","eng/harness-evaluation/skills/update-pipeline/fixtures/shared-identity/source-excerpts.md":"# Shared-identity Skill\n\nPath: `eng/harness-evaluation/skills/update-pipeline/fixtures/shared-identity/source-excerpts.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/update-pipeline/fixtures/shared-identity/source-excerpts.md)","eng/harness-evaluation/skills/code-review/fixtures/query-comment/context/review-context.md":"# Context Skill\n\nPath: `eng/harness-evaluation/skills/code-review/fixtures/query-comment/context/review-context.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/code-review/fixtures/query-comment/context/review-context.md)"},"files":{".agents/skills/make-github-actions-workflow/SKILL.md":"---\nname: make-github-actions-workflow\ndescription: 'Create or modify GitHub Actions workflows for CI, automation, or PR management. Use when asked to create, scaffold, add, extend, or fix a workflow (.yml file under .github/workflows/), including existing pull-request policy and comment automation.'\n---\n\n# Create GitHub Actions Workflow\n\nCreate and configure GitHub Actions workflows that follow this repository's conventions and patterns. Workflows automate tasks like CI validation, PR management, issue labeling, and notifications.\n\n## Repository Conventions\n\nThis repository uses specific patterns across all workflows. Follow these conventions when creating new workflows:\n\n### File Location and Naming\n\n- All workflows live in `.github/workflows/`\n- Use kebab-case names: `label-and-milestone-issues.yml`, `validate-pr-target-branch.yml`\n- Start with a descriptive comment block explaining the workflow's purpose\n\n### Runner\n\n- Use `ubuntu-latest` for general-purpose jobs\n- Use `ubuntu-24.04` when a specific OS version is needed (e.g., copilot setup steps)\n\n### Permissions\n\n- **Always** declare explicit permissions — never rely on defaults\n- Use **minimal permissions**: only request what the workflow needs\n- Common patterns:\n  - Read-only: `permissions: {}`\n  - PR comments: `pull-requests: write`\n  - Issue management: `issues: write`\n  - Code read: `contents: read`\n- For workflows that need write access to PRs from external contributors, use `pull_request_target` instead of `pull_request`\n  - **Security warning:** `pull_request_target` workflows run in the base repository context with its permissions. Do **not** check out or execute code from the PR branch in these workflows. Instead, use the event payload and/or GitHub API (`actions/github-script`, `github.rest.*`, etc.) to inspect and act on the PR safely.\n\n### Scripting\n\n- Use `actions/github-script@v8` for complex logic instead of shell scripts\n- Write JavaScript with `async/await` — the `github` object (Octokit) and `context` are available\n- Use `github.rest.*` for REST API calls and `github.graphql()` for GraphQL queries\n- Access PR/issue data via `context.payload.pull_request`, `context.repo.owner`, `context.repo.repo`\n- Log with `console.log()` for debugging; use `core.setFailed()` for errors\n\n### Error Handling\n\n- Wrap API calls in try/catch blocks\n- Collect errors and report at the end rather than failing on the first error\n- Log skipped operations with a reason\n\n## Workflow\n\n### Step 1: Understand the Requirements\n\nBefore writing the workflow, clarify:\n- [ ] What event(s) should trigger it? (push, pull_request, check_suite, schedule, etc.)\n- [ ] What permissions are needed?\n- [ ] What conditions should gate execution? (author, branch, labels, etc.)\n- [ ] What API calls are needed?\n- [ ] Are there rate limiting or idempotency concerns?\n\n### Step 2: Choose the Trigger Event\n\n| Use case | Event | Notes |\n|----------|-------|-------|\n| PR opened/updated | `pull_request` | Read-only access to PR |\n| PR with write access | `pull_request_target` | Can comment, label, close |\n| PR merged | `pull_request_target: [closed]` | Check `github.event.pull_request.merged == true` |\n| CI checks complete | `check_suite: [completed]` | Filter `app.slug != 'github-actions'` to skip self |\n| Code pushed | `push` | Filter by branches/paths |\n| Manual trigger | `workflow_dispatch` | Add `inputs:` for parameters |\n| Scheduled | `schedule` | Use cron syntax |\n\n### Step 3: Write the Workflow\n\nCreate the YAML file following this template:\n\n```yaml\n# Description of what this workflow does and why.\n\nname: Descriptive Workflow Name\n\non:\n  <trigger_event>:\n    types: [<event_types>]\n\npermissions:\n  <resource>: <read|write>\n\njobs:\n  <job-name>:\n    if: <guard_condition>  # Optional: skip when not needed\n    runs-on: ubuntu-latest\n    steps:\n      - name: Descriptive step name\n        uses: actions/github-script@v8\n        with:\n          script: |\n            // Your logic here\n```\n\n### Step 4: Implement Guard Conditions\n\nAdd conditions to avoid unnecessary runs:\n- Job-level `if:` for event payload checks (e.g., `github.event.check_suite.app.slug != 'github-actions'`)\n- Early `return` in scripts for PR author, draft status, etc.\n- Idempotency checks (e.g., hidden HTML comments as tags to prevent duplicate actions)\n\nFor `pull_request_target` policy workflows that react to `opened`, `edited`, and `reopened`:\n\n- On `edited`, return unless `context.payload.changes?.base` is present; title or body edits must not reapply a target-branch policy.\n- Check permissions for `context.actor`, not only the PR author. A maintainer may edit or reopen an external PR, and that action must use the maintainer's authority.\n- For `opened`, the actor and author are the same, so perform one permission lookup and reuse it for policy and labeling decisions.\n- Exclude automation when either the actor or author is a bot.\n- Encode the prohibited branch class directly (for example, `release/*`) instead of requiring a single allowed branch such as `main`.\n- If permission lookup fails, stop without taking a destructive action; unknown access is not evidence that the contributor is external.\n\n### Step 5: Validate\n\nAfter creating the workflow:\n- [ ] Permissions are minimal and explicitly declared\n- [ ] Uses `actions/github-script@v8` for complex logic\n- [ ] Guard conditions prevent unnecessary runs\n- [ ] API calls handle pagination where needed (use `per_page: 100`)\n- [ ] Error handling doesn't silently swallow failures\n- [ ] No secrets or tokens are hardcoded\n- [ ] Workflow doesn't create infinite loops (e.g., a workflow that triggers itself)\n\n## Existing Workflows in This Repository\n\nStudy these workflows as reference:\n\n| Workflow | Trigger | Purpose |\n|----------|---------|---------|\n| `validate-pr-target-branch.yml` | `pull_request_target: [opened, edited, reopened]` | Closes external PRs targeting release branches, adds community labels |\n| `label-and-milestone-issues.yml` | `pull_request_target: [closed]` | Labels and milestones issues when their fixing PR is merged |\n| `copilot-setup-steps.yml` | `workflow_dispatch`, `push`, `pull_request` | Sets up the development environment for Copilot |\n| `inter-branch-merge-flow.yml` | `push` to `release/**` | Triggers inter-branch merge via arcade |\n\n## Common Patterns\n\n### Commenting on a PR\n\n```javascript\nawait github.rest.issues.createComment({\n  owner: context.repo.owner,\n  repo: context.repo.repo,\n  issue_number: prNumber,\n  body: 'Comment text'\n});\n```\n\n### Checking User Permissions\n\n```javascript\nconst { data: permissions } = await github.rest.repos.getCollaboratorPermissionLevel({\n  owner: context.repo.owner,\n  repo: context.repo.repo,\n  username: context.actor\n});\nconst hasWriteAccess = ['admin', 'write'].includes(permissions.permission);\n```\n\n### Updating Bot-Owned Comments Idempotently\n\nA hidden marker identifies the workflow's comment but does not establish ownership: contributors and other apps can place the same marker in their comments. Match both the marker and the exact `github-actions[bot]` login, then update that comment or create a new one. A generic `user.type === 'Bot'` check does not establish workflow ownership. Preserve the workflow's pinned action SHA and never execute code from a pull-request fork in a `pull_request_target` job.\n\n```javascript\nconst marker = '<!-- validate-pr-target-branch -->';\nconst comments = await github.paginate(github.rest.issues.listComments, {\n  owner: context.repo.owner,\n  repo: context.repo.repo,\n  issue_number: prNumber,\n  per_page: 100\n});\n\nconst body = `${marker}\\nComment text`;\nconst existing = comments.find(comment =>\n  comment.user?.login === 'github-actions[bot]' && comment.body?.includes(marker));\n\nif (existing) {\n  await github.rest.issues.updateComment({\n    owner: context.repo.owner,\n    repo: context.repo.repo,\n    comment_id: existing.id,\n    body\n  });\n} else {\n  await github.rest.issues.createComment({\n    owner: context.repo.owner,\n    repo: context.repo.repo,\n    issue_number: prNumber,\n    body\n  });\n}\n```\n\n### Reading Repository Files at a Specific Commit\n\n```javascript\nconst { data: fileData } = await github.rest.repos.getContent({\n  owner, repo,\n  path: 'eng/Versions.props',\n  ref: commitSha\n});\nconst content = Buffer.from(fileData.content, 'base64').toString('utf-8');\n```\n\n## References\n\n- [GitHub Actions documentation](https://docs.github.com/en/actions)\n- [Workflow syntax](https://docs.github.com/en/actions/using-workflows/workflow-syntax-for-github-actions)\n- [Events that trigger workflows](https://docs.github.com/en/actions/using-workflows/events-that-trigger-workflows)\n- [actions/github-script](https://github.com/actions/github-script)\n",".agents/skills/code-review/SKILL.md":"---\nname: code-review\ndescription: 'Review EF Core pull requests or local changes for concrete correctness, compatibility, performance, security, and test-coverage problems. Use when asked to review, critique, or check code changes before merge or submission.'\n---\n\n# EF Core Code Review\n\nReview pull requests and local working-tree changes without modifying source. Findings must be concrete, evidence-backed problems introduced or exposed by the change, not style preferences or general improvement ideas.\n\n## Scope and Safety\n\n- Review the provided pull request, or staged, unstaged, and untracked local changes. Ask for clarification when both are plausible.\n- Never checkout, switch branches, stash, reset, clean, or otherwise mutate the working tree, except for checking out the requested head for review purposes. Never edit source as part of a review.\n- For a pull request, record its base, head, and immutable head SHA. If local `HEAD` differs, use read-only repository or GitHub context when sufficient; otherwise ask the user to checkout the requested commit.\n- Never submit an `APPROVE` or `REQUEST_CHANGES` event. COMMENT emission follows Step 8.\n- Do not use this skill to address existing review comments or implement fixes.\n\n## Workflow\n\n### 1. Establish the Review Surface\n\n1. Load `.github/copilot-instructions.md` and any area skill whose description matches the changed implementation.\n2. Obtain the complete diff and changed-file list once. Include staged, unstaged, and untracked files for local reviews.\n3. For pull requests, gather the base/head refs and head SHA, but defer the PR body, linked issues, and prior review comments until Step 3.\n4. Stop with a clear limitation if the requested change surface cannot be established.\n\n### 2. Form an Independent Assessment\n\nBefore reading the author's narrative:\n\n1. Read each changed implementation beyond its diff hunk. Diff-only review is insufficient evidence for a finding. For very large files, read the containing members, their contracts, and relevant state. When many files are changed, use subagents to break down the review into manageable parts and gather context incrementally.\n2. Search callers, implementations, overrides, sibling provider paths, and nearby tests. Read shared helpers whose contracts control the changed behavior.\n3. When logic moves, compare the old and new input domains. Check the moved member's XML contract as well as regression coverage.\n4. Use focused history to explain invariants, reverts, or prior rejected approaches; establish what makes a repeated approach viable now.\n5. Describe the old and new behavior, likely motivation, affected callers/providers, and initial concerns in your own words.\n\n### 3. Holistic PR Assessment\n\nAssess the overall approach before refining implementation details:\n\n- Require a concrete need for added code, APIs, abstractions, and flags. Prefer the simplest sufficient alternative; weigh benefits against complexity, surface area, and long-term maintenance.\n- Prefer root-cause fixes at the owning layer. Challenge a flawed direction early rather than polishing its implementation.\n- Require BenchmarkDotNet results or equivalent measurements for performance claims; prefer focused local runs for experimental or iterative work.\n - Explain and address scenario-specific regressions even when aggregate results improve.\n- Scale required benefit and validation with regression risk and blast radius, especially for stable code.\n\n### 4. Reconcile Pull Request Context\n\nFor pull requests, now read the description, linked issues, and existing review threads. Treat them as claims to verify against the code. Also flag found problems the PR narrative doesn't acknowledge.\n\nIf the additional context reveals information that genuinely changes your evaluation, update your holistic assessment accordingly. But do not soften findings just because the PR description sounds reasonable.\n\n### 5. Route Conditional Reviews\n\n- Read [references/api-review.md](references/api-review.md) when the change adds, removes, or changes supported public or protected API outside an `.Internal` namespace and not annotated with `[EntityFrameworkInternal]`.\n- Read [references/security-review.md](references/security-review.md) when changed data crosses a documented trust boundary or the change affects serialization, generated code from database metadata, command construction, sensitive-data handling, caches or complexity bounds, assembly loading, elevated operations, or another high-risk path.\n\n### 6. Analyze Behavior and Coverage\n\nFor each non-trivial production change, identify:\n\n1. **Changed behavior**: the concrete old and new code paths.\n2. **Affected surfaces**: callers, providers, public contracts, generated output, persistence, diagnostics, and concurrency where applicable.\n3. **Regression risks**: plausible inputs, interleavings, failures, or compatibility breaks.\n4. **Expected coverage**: the focused test that would fail without the change or expose the regression.\n5. **Coverage gaps**: affected behavior not exercised by changed or existing tests.\n\nCheck correctness, error handling, async behavior, concurrency, state and resource lifetime, compatibility, provider hierarchy behavior, NativeAOT constraints, and performance only where the changed path plausibly makes them relevant.\n\nFor exception cleanup around shared or concurrent state, distinguish whether this invocation acquired each resource from whether the resource currently appears held. Cover both a failing owner releasing its acquisition and a failing contender preserving another owner's acquisition, including preexisting nested state. Construct a concrete interleaving without weakening existing reentrancy or nesting behavior.\n\nFor new functionality consider other feature areas that might be affected but are not directly touched by the change.\n\nDo not request tests for documentation-only changes, comments, formatting, or demonstrably behavior-preserving mechanical changes. Do not flag issues that the compiler, formatter, or existing analyzers deterministically report.\n\n### 7. Optional Multi-Model Review\n\nWhen the environment supports launching sub-agents with different models (e.g., the `task` tool with a `model` parameter), run the review in parallel across multiple model families to get diverse perspectives. Different models catch different classes of issues. If the environment does not support this, proceed with a single-model review.\n\n1. Inspect the available model list and select models from 2-3 distinct model families, up to 3 sub-agent models total. If fewer than 2 eligible families are available, use what is available.\n   - Pick only from models explicitly listed as available in the environment. Do not guess or assume model names.\n   - Never pick models labeled \"mini\", \"fast\", or \"cheap\" for code review.\n   - Do not select a model from the same family that is already running the primary review (i.e. the currently used model).\n   - If multiple models exist in the same family, pick the one with the highest version number. Prefer \"-codex\" variants over general-purpose.\n   - If the model supports effort configuration use the one closest to the current effort level.\n2. Launch a sub-agent for each selected model in parallel, giving each the same review prompt: the PR diff, the review rules from this skill, and instructions to produce findings in the severity format defined above.\n3. Wait for all agents to complete, then synthesize: deduplicate findings that appear across models, elevate issues flagged by multiple models (higher confidence), and include unique findings from individual models that meet the confidence bar. If a sub-agent has not completed after 10 minutes and you have results from other agents, proceed with the results you have.\n4. Present a single unified review to the user, noting when an issue was flagged by multiple models. Do not wait for any remaining sub-agents and do not attempt retries if any failed. The review is complete once the report operation succeeds.\n\n### 7. Verify and Report Findings\n\nBefore reporting a concern:\n\n- Verify it against surrounding and unchanged code, including caller/callee defenses.\n- Identify a realistic failure or user impact. Do not promote a theoretical possibility with negligible likelihood into a finding.\n- Verify factual claims about APIs from repository evidence or current documentation; never rely on model memory to claim an API is absent, deprecated, or unavailable.\n- Report only test results actually observed. Separate unexecuted validation and residual risk from findings.\n\nOrder findings by severity:\n\n- ❌ **Critical**: practical exploitation, arbitrary code execution, widespread data loss, or similarly catastrophic impact.\n- 🔴 **High**: merge-blocking correctness, security, compatibility, data-integrity, or concurrency defect.\n- ⚠️ **Medium**: concrete defect with limited impact or a meaningful regression gap for changed behavior.\n- 🔵 **Low**: minor but real defect worth fixing in this change.\n- 💡 **Info**: observations or suggestions that do not constitute a defect but may improve code quality or maintainability.\n\nEach finding must contain:\n\n1. Severity and concise title.\n2. Certainty level or confidence in the finding based on the available evidence.\n3. Changed file and line or symbol.\n4. Concrete failure mode and impact.\n5. Evidence that makes the finding actionable.\n6. Fix direction and, when relevant, the missing regression-test shape.\n\nPresent the holistic assessment before findings. Do not add praise or filler.\n\n**Motivation**: <1-2 sentences on whether the PR is justified and the problem is real>\n\n**Approach**: <1-2 sentences on whether the fix/change takes the right approach>\n\n**Summary**: <✅ LGTM / ⚠️ Needs Human Review / ⚠️ Needs Changes / ❌ Reject>. <2-3 sentence summary of the overall verdict and key points. If \"Needs Human Review,\" explicitly state which findings you are uncertain about and what a human reviewer should focus on.>\n\n### 8. Optionally Post Pull Request Comments\n\nPosting is allowed through either authorization path:\n\n- **Direct invocation**: number the findings, let the user select or edit them, and obtain explicit confirmation before posting.\n- **Code-reviewer agent delegation**: an invoking code-reviewer agent may explicitly authorize COMMENT emission and provide the selected findings or complete review payload. That caller contract is sufficient authorization; do not add a redundant confirmation prompt. An analysis-only delegation does not authorize posting.\n\nImmediately before posting, confirm that the pull request is still open and its base, head, and head SHA match the reviewed revision. If they changed, stop and refresh the review context.\n\nCreate a pending review, add only authorized findings, and submit it as `COMMENT`. Never approve or request changes. Include a concise AI-generated disclosure when posting under a user's identity rather than a bot identity. Do not post findings that are similar to existing or resolved comments; for multiple defects in the same area, consolidate them into a single finding when appropriate.\n\n## Validation\n\n- Every finding resolves to changed code or a changed contract and cites supporting repository evidence.\n- Test requests follow the behavior-impact analysis.\n- No source or worktree mutation occurred.\n- Any posted review used the reviewed head SHA and COMMENT-only authorization.\n\n## Common Pitfalls\n\n- Reviewing hunks without their callers or provider hierarchy.\n- Treating a public CLR member in `.Internal` as supported public API.\n- Reporting a security keyword without tracing attacker-controlled data to an impact.\n- Inferring that passing broad tests covers the changed failure mode.\n- Turning uncertainty into a firm finding instead of investigating or recording a limitation.",".agents/skills/change-tracking/SKILL.md":"---\nname: change-tracking\ndescription: 'Implementation details for EF Core change tracking. Use when changing InternalEntityEntry, ChangeDetector, SnapshotFactoryFactory, or related entity state, snapshot, or property accessor code.'\nuser-invocable: false\n---\n\n# Change Tracking\n\nManages entity states and detects changes for `SaveChanges()`.\n\n## Core Components\n\n- `StateManager` — owns tracked entries, identity/reference maps, fixup, cascades, notifications, and changed counts\n- `InternalEntryBase` and derived classes — own per-entry state, flags, values, snapshots, and ordered state transitions\n- `ChangeDetector` — compares current values with baselines and reports changes through entry mutation APIs\n- `SnapshotFactoryFactory` subclasses — create passive original- and relationship-value baselines\n- `IdentityMap` — permits one active entry per key; shared identity pairs a replacement with the prior `Deleted` entry\n- `PropertyAccessorsFactory`, `ClrPropertyGetterFactory` and `ClrPropertySetterFactory` compile property accessors for efficient snapshotting and change detection\n  - Ordinals in `indices` parameter specify element at each complex collection depth\n\n## Change Detection\n\n- Snapshot and notification strategies both call `SetPropertyModified()` to keep property flags and entity state consistent.\n- `SetEntityState()` validates values, updates flags and complex entries, changes state, then runs manager bookkeeping hooks.\n\n## Shared-Identity Replacement\n\n`SharedIdentityEntry` is the invariant that distinguishes an old deleted entry from its replacement with the same identity. When attaching a replacement graph, a deleted nested entry should be reconsidered only when its source entry has a replacement; do not broadly process every deleted node. Likewise, cascading from the old replaced principal must not delete dependents that belong to the replacement graph. Keep synchronous and asynchronous graph-attach paths equivalent and preserve unrelated values in replacement tests so they isolate the identity transition.\n\n## Testing\n\nUnit tests: `test/EFCore.Tests/ChangeTracking/`. Functional tests: `test/EFCore.Specification.Tests/GraphUpdates/`.\n\n## Common Pitfalls\n\n| Pitfall | Solution |\n|---------|----------|\n| State-based checks treat every Added/Deleted entry as a replacement | Scope replacement behavior through `SharedIdentityEntry` and the graph source |\n\n## Validation\n\n- `DetectChanges()` identifies modified properties via snapshot comparison\n- Setting original values marks properties as modified or unchanged based on comparison with current values\n",".agents/skills/make-custom-agent/SKILL.md":"---\nname: make-custom-agent\ndescription: 'Create, review, or fix custom GitHub Copilot agents. Use when asked to create, scaffold, configure, review, or restrict a custom agent, declarative agent, or @-invokable chat participant for GitHub Copilot.'\n---\n\n# Create Custom Agent\n\nThis skill guides you through creating a custom GitHub Copilot agent — an `@`-invokable chat participant that extends Copilot with domain-specific expertise. Custom agents are distinct from Agent Skills: skills provide reusable instructions loaded on demand, while agents own the full conversational interaction and can orchestrate tools, call APIs, and maintain their own prompt strategies.\n\n## When Not to Use\n\n- Adding reusable, invokable workflows — use Agent Skills (`.agents/skills/`) instead\n- Adding background coding guidelines — use file-based instructions (`.github/instructions/`) instead\n- Adding project-wide context for Copilot — use `.github/copilot-instructions.md` instead\n- Creating reusable prompts — use .prompt.md instead\n\n## Workflow\n\nFor an existing proposal, audit the full definition rather than just its tools: the description must identify natural requests that should discover it, the body must add domain knowledge beyond root instructions, and the paired eval must isolate its contribution. Compare every tool and behavior to the user's intended authority. A command-free reviewer must not gain command execution or publication through a wildcard tool, handoff, or otherwise read-only workflow.\n\n### Step 1: Choose the agent type\n\n| Type | Location | Best for |\n|---|---|---|\n| Declarative (prompt file) | `.github/agents/<name>.md` | Simple prompt-driven cross-surface agents with no code |\n| Extension-based (chat participant) | VS Code extension project | Full control, tool calling, VS Code API access |\n| GitHub App (Copilot Extension) | Hosted service + GitHub App | Cross-surface agents (github.com, VS Code, Visual Studio) |\n\nIf the agent only needs a scoped system prompt and doesn't require custom code, start with a declarative agent.\n\n### Step 2: Create a declarative agent (prompt file)\n\nDeclarative agents are Markdown files in `.github/agents/`. VS Code and GitHub Copilot discover them automatically.\n\n```\n.github/agents/\n└── <agent-name>.md        # Agent definition\n```\n\nTemplate:\n\n```markdown\n---\nname: my-agent\ndescription: A short description of what this agent does and when to use it.\n---\n\n# <Agent Title>\n\nYou are an expert in <domain>. Your job is to:\n- <behavior 1>\n- <behavior 2>\n\n## Guidelines\n\n- <guideline 1>\n- <guideline 2>\n\n## Workflow\n\n1. <step 1>\n2. <step 2>\n\n## Constraints\n\n- <constraint 1>\n- <constraint 2>\n\n```\n\nSupported frontmatter fields:\n\n| Field | Required | Description |\n|---|---|---|\n| `name` | Yes | Lowercase, hyphens allowed. Used for `@`-mention. |\n| `description` | Yes | What the agent does and when to use it. Shown in the participant list. |\n| `target` | No | Target environment: `vscode` or `github-copilot` (defaults to both) |\n| `tools` | No | List of allowed tools/tool sets |\n| `model` | No | LLM name or prioritized array of models |\n| `user-invocable` | No | Show in agents dropdown (default: true) |\n| `disable-model-invocation` | No | Prevent subagent invocation (default: false) |\n| `mcp-servers` | No | MCP server configs for GitHub Copilot target |\n| `metadata` | No | Key-value mapping for additional arbitrary metadata. |\n| `argument-hint` | No | Hint text guiding user interaction (VS Code only) |\n| `agents` | No | List of allowed subagents (`*` for all, `[]` for none, VS Code only) |\n| `handoffs` | No | List of next-step agent transitions (VS Code only) |\n\n\nTips for instructions:\n- Use Markdown links to reference other files\n- Reference tools with `#tool:<tool-name>` syntax\n- Be specific about agent behavior and constraints\n\n### Step 3: Configure tools\n\nSpecify which tools the agent can use:\n\n```yaml\ntools:\n  - search              # Built-in tool\n  - fetch               # Built-in tool\n  - codebase            # Tool set\n  - myServer/*          # All tools from MCP server\n```\n\nCommon tool patterns:\n- **Read-only agents**: `['search', 'fetch', 'codebase']`\n- **Full editing agents**: `['*']` or specific editing tools\n- **Specialized agents**: Cherry-pick specific tools\n\n### Step 4: Add handoffs (optional, VS Code only)\n\nConfigure transitions to other agents:\n\n```yaml\nhandoffs:\n  - label: Start Implementation\n    agent: implementation\n    prompt: Implement the plan outlined above.\n    send: false\n    model: GPT-5.2 (copilot)\n```\n\nHandoff fields:\n- `label`: Button text displayed to user\n- `agent`: Target agent identifier\n- `prompt`: Pre-filled prompt for target agent\n- `send`: Auto-submit prompt (default: false)\n- `model`: Optional model override for handoff\n\n### Step 5: Create an extension-based chat participant (VS Code only)\n\nFor full control, implement a VS Code extension with a chat participant:\n\n1. **Define the participant** in `package.json`:\n\n```json\n\"contributes\": {\n    \"chatParticipants\": [\n        {\n            \"id\": \"my-extension.my-agent\",\n            \"name\": \"my-agent\",\n            \"fullName\": \"My Agent\",\n            \"description\": \"Short description shown in chat input\",\n            \"isSticky\": false,\n            \"commands\": [\n                {\n                    \"name\": \"explain\",\n                    \"description\": \"Explain the selected code\"\n                }\n            ]\n        }\n    ]\n}\n```\n\n2. **Register and implement the request handler** in `extension.ts`:\n\n```typescript\nexport function activate(context: vscode.ExtensionContext) {\n    const agent = vscode.chat.createChatParticipant('my-extension.my-agent', handler);\n    agent.iconPath = vscode.Uri.joinPath(context.extensionUri, 'icon.png');\n}\n\nconst handler: vscode.ChatRequestHandler = async (\n    request: vscode.ChatRequest,\n    context: vscode.ChatContext,\n    stream: vscode.ChatResponseStream,\n    token: vscode.CancellationToken\n) => {\n    const model = request.model;\n    const messages = [\n        vscode.LanguageModelChatMessage.User(request.prompt)\n    ];\n    const response = await model.sendRequest(messages, {}, token);\n    for await (const fragment of response.text) {\n        stream.markdown(fragment);\n    }\n};\n```\n\n3. **Declare the extension dependency** in `package.json`:\n\n```json\n\"extensionDependencies\": [\"github.copilot-chat\"]\n```\n\n4. **Add tool calling (optional)**\n\nAgents can invoke language model tools registered by other extensions:\n\n```typescript\nconst tools = vscode.lm.tools.filter(tool => tool.tags.includes('my-domain'));\nconst result = await chatUtils.sendChatParticipantRequest(request, context, {\n    prompt: 'You are an expert in <domain>.',\n    tools,\n    responseStreamOptions: { stream, references: true, responseText: true }\n}, token);\nreturn await result.result;\n```\n\n### Step 6: Create a GitHub App (Copilot Extension) for cross-surface availability (optional)\n\nIf the agent should be available on GitHub.com, Visual Studio, JetBrains, and VS Code simultaneously, implement a GitHub App that acts as a Copilot Extension. The app registers a webhook endpoint, receives chat requests, and streams responses back.\n\nKey considerations:\n- The GitHub App must be installed on the user's account or organization\n- Responses are streamed via Server-Sent Events (SSE)\n- Use the [GitHub Copilot Extensions documentation](https://docs.github.com/en/copilot/building-copilot-extensions/about-building-copilot-extensions) for the full integration guide\n- For VS Code-specific features (editor access, file trees, command buttons), prefer an extension-based participant instead\n\n### Step 7: Author the harness evaluation\n\nCreate `eng/harness-evaluation/agents/<agent-id>/eval.yaml` and follow `eng/harness-evaluation/README.md`.\n\n- Declare only the agent file in the eval's root `agent_environment.files`; the experiment removes it from the control.\n- Use realistic stimuli that exercise behavior distinctive to the agent without stating the expected diagnosis or implementation in the prompt.\n- Combine deterministic output checks, a focused semantic rubric, bounded resources, token grading, and a committed scoring threshold.\n- Keep the eval name and directory-derived component ID identical to the agent ID.\n\n### Step 8: Validate\n\nAfter creating or modifying an agent, verify:\n\n- [ ] `name` is lowercase, uses hyphens (no spaces), and is unique\n- [ ] `description` clearly describes what the agent does and when to invoke it\n- [ ] Frontmatter YAML is valid (no syntax errors)\n- [ ] Declarative agent file is in `.github/agents/`\n- [ ] Tools list contains only available tools\n- [ ] Extension-based agent: participant ID matches in `package.json` and `createChatParticipant` call\n- [ ] Agent does not duplicate functionality of built-in agents (`@workspace`, `@vscode`, `@terminal`)\n- [ ] Handoff agent names match existing agents\n- [ ] Agent instructions don't include secrets, tokens, or internal URLs\n- [ ] The paired harness eval targets only this agent and is meant to meaningfully distinguish treatment from control\n\n## Common Pitfalls\n\n| Pitfall | Solution |\n|---------|----------|\n| Agent name conflicts with built-in participants | Use a unique prefix (domain name) |\n| Description is too vague | Include specific keywords users would naturally say |\n| System prompt is too long | Keep instructions to essential behaviors; move reference material to Agent Skills |\n| Agent requires VS Code API but is authored as declarative | Switch to extension-based participant |\n| Using `isSticky: true` unnecessarily | Only set sticky if the agent should persist between turns by default |\n| No `extensionDependencies` on `github.copilot-chat` | Add it; otherwise the contribution point may not be available |\n| Agent invoked as subagent unexpectedly | Set `disable-model-invocation: true` |\n| Subagent appears in the dropdown | Set `user-invocable: false` |\n\n## References\n\n- [VS Code Chat Participant API](https://code.visualstudio.com/api/extension-guides/ai/chat)\n- [VS Code AI Extensibility Overview](https://code.visualstudio.com/api/extension-guides/ai/ai-extensibility-overview)\n- [VS Code Extension Samples – chat-sample](https://github.com/microsoft/vscode-extension-samples/tree/main/chat-sample)\n- [GitHub Copilot Extensions documentation](https://docs.github.com/en/copilot/building-copilot-extensions/about-building-copilot-extensions)\n- [GitHub Copilot Custom agents configuration](https://docs.github.com/en/copilot/reference/custom-agents-configuration)\n- [Agent Skills Specification](https://agentskills.io/specification)\n- Related repository skills: `make-skill` and `make-instructions`\n",".agents/skills/make-instructions/SKILL.md":"---\nname: make-instructions\ndescription: 'Create and evaluate VS Code file-based instructions (.instructions.md files). Use when asked to create, scaffold, or add file-based instructions for Copilot. Generates scoped instructions and a paired Vally harness eval.'\n---\n\n# Create File-Based Instructions\n\nThis skill helps you scaffold VS Code file-based instructions (`.instructions.md` files) that provide background knowledge to Copilot about specific parts of the codebase. These files are applied automatically based on glob patterns or semantic matching, giving Copilot domain-specific context when working on matching files.\n\n## When Not to Use\n\n- Setting project-wide instructions — use `.github/copilot-instructions.md` or `AGENTS.md` instead\n- Creating reusable agent workflows with structured steps — use Agent Skills instead\n- Adding instructions that need to be invokable on demand — use Agent Skills instead\n\n## Workflow\n\n### Step 1: Investigate the topic\n\nBuild understanding of the area the instructions should cover. Identify:\n\n- [ ] What files or file patterns the instructions apply to\n- [ ] Key conventions, patterns, or architectural rules for that area\n- [ ] Common pitfalls that Copilot should avoid\n- [ ] Non-obvious domain knowledge that isn't discoverable from code alone\n\nRead the repository-wide instruction files that apply to the same paths and make an explicit exclusion list. Do not repeat those rules in the new file, even when they are relevant examples for the scoped area; include only guidance that becomes more specific or materially different at the narrower scope.\n\nIf the scope is unclear or overlaps with existing instructions, ask the user for clarification.\n\n### Step 2: Choose the file location\n\nInstructions files go in `.github/instructions/` by default. Pick a descriptive filename:\n\n```\n.github/instructions/<topic>.instructions.md\n```\n\nExamples: `csharp-style.instructions.md`, `query-pipeline.instructions.md`, `test-conventions.instructions.md`\n\n### Step 3: Generate the file with YAML frontmatter\n\nCreate the file with the required YAML frontmatter header:\n\n```yaml\n---\nname: '<Display Name>'              # Optional. Display name in the UI. Defaults to filename.\ndescription: '<Short description>'  # Optional. Shown on hover. Also used for semantic matching.\napplyTo: '<glob pattern>'           # Optional. Glob pattern relative to workspace root. Omit to require manual attachment or rely on semantic matching only.\n---\n```\n\nCommon `applyTo` patterns:\n\n- `**/*.cs` — all C# files\n- `test/**` — files under a specific folder\n\n### Step 4: Write the body content\n\nWrite concise, actionable Markdown content. Follow these principles:\n\n- **Be concise** — instructions share the context window; only include what the agent wouldn't already know\n- **Be specific** — use concrete rules, not vague guidance\n- **Include examples** — short code snippets showing preferred vs. avoided patterns are very effective\n- **Explain why** — when a rule exists for a non-obvious reason, state it so the agent applies it correctly in edge cases\n- **Skip linter-enforced rules** — don't repeat what formatters and linters already catch\n- **Use Markdown links** to reference specific files or URLs for additional context\n\nRecommended sections (adapt as needed):\n\n1. **<Title>** — one-line heading describing the domain\n2. **Context paragraph** — brief explanation of what this area is and why these rules matter\n3. **Guidelines / Conventions** — bullet list of concrete rules\n4. **Examples** — short code blocks showing do/don't patterns (optional)\n5. **Key Files** — table of important files for orientation (optional)\n6. **Common Pitfalls** — traps to avoid (optional)\n\n### Step 5: Author and validate the harness evaluation\n\nCreate `eng/harness-evaluation/instructions/<id>/eval.yaml`, where `<id>` is the instruction path relative to `.github/instructions/` with its suffix removed and nested path separators replaced by `--`.\n\nFollow the authoring and validation rules in `eng/harness-evaluation/README.md`. Exercise guidance distinctive to the instruction and ensure the treatment meaningfully outperforms the omitted-instruction control.\n\nFor initial authoring, produce and lint the requested instruction and eval before running behavioral comparisons.\n\nAfter creating the file, verify:\n\n- [ ] File is in `.github/instructions/` (or a configured instructions folder)\n- [ ] Filename ends with `.instructions.md` and only contains lowercase letters, numbers, and hyphens\n- [ ] YAML frontmatter is valid\n- [ ] `applyTo` glob matches the intended files\n- [ ] Content is concise (aim for under 500 lines or 5000 tokens) — long instructions dilute effectiveness\n- [ ] No secrets, tokens, or internal URLs included\n- [ ] Instructions don't duplicate what's already in `.github/copilot-instructions.md` or under `.agents/skills/`\n- [ ] The paired eval demonstrates behavior that the omitted-instruction control does not provide reliably\n\n## Common Pitfalls\n\n| Pitfall | Solution |\n|---------|----------|\n| `applyTo` too broad | Use specific globs; `**` applies to every file and wastes context |\n| Missing `applyTo` | Without it, instructions won't auto-apply — they require manual attachment or semantic matching via `description` |\n| Vague guidance | Replace \"write good tests\" with something like \"add both positive and negative test cases using `[ConditionalFact]` methods\" |\n",".agents/skills/cosmos-provider/SKILL.md":"---\nname: cosmos-provider\ndescription: 'Implementation details for the EF Core Azure Cosmos DB provider. Use when changing Cosmos-specific code.'\nuser-invocable: false\n---\n\n# Cosmos DB Provider\n\nNon-relational provider with its own parallel query pipeline. Uses JSON for document materialization.\n\n## Key Differences from Relational\n\n- No migrations — use `EnsureCreated()`\n- Documents as JSON — owned and complex types become embedded objects\n- Partition key configuration required for performance\n- `ETag` for optimistic concurrency\n- No cross-container joins\n\n## Azure Cosmos DB Emulator for Tests\n\n- `TestEnvironment.InitializeAsync()` auto-starts a `Testcontainers.CosmosDb` container when `Test__Cosmos__DefaultConnection` is not set. Set the env var to use an existing emulator instead.\n- Skip tests requiring unsupported features on the Linux emulator with ` [ConditionalFact(typeof(CosmosTestEnvironment), nameof(CosmosTestEnvironment.IsNotLinuxEmulator))]`.\n",".agents/skills/make-skill/SKILL.md":"---\nname: make-skill\ndescription: 'Create, review, or fix Agent Skills for GitHub Copilot. Use when asked to create, scaffold, improve, or repair a SKILL.md and its paired harness evaluation.'\n---\n\n# Create Or Fix A Skill\n\nProduce concise, stable task guidance that adds knowledge an agent cannot reliably infer from source alone, together with a paired evaluation that proves the guidance changes behavior.\n\n## Choose The Right Primitive\n\n- Use a skill for a task-specific workflow or body of knowledge loaded on demand.\n- Use file instructions for background guidance scoped to paths.\n- Use a custom agent when context isolation or distinct tool restrictions are required.\n- Prefer an existing skill over creating an overlapping one.\n\n## Workflow\n\n1. Read the relevant implementation, tests, repository instructions, and neighboring customizations.\n2. Identify repeated mistakes or non-obvious invariants. Do not turn source inventories, line counts, or facts easily rediscovered from code into skill content.\n3. Create `.agents/skills/<name>/SKILL.md`. The frontmatter `name` must exactly match the directory; the description must state what the skill does and when natural user requests should trigger it.\n4. Mark background domain guidance `user-invocable: false`. Keep user-invocable workflows focused on an outcome a user would deliberately request.\n5. Write actionable guidance with observable validation. Explain why edge cases matter; avoid generic engineering advice already present in repository instructions.\n6. Create `eng/harness-evaluation/skills/<name>/eval.yaml` and follow `eng/harness-evaluation/README.md`.\n7. Lint the customization and inspect both control and treatment artifacts before accepting it.\n\n## Paired Evaluation\n\n- The eval root `agent_environment.skills` contains only the target skill. Stimulus inputs belong under each stimulus's `agent_environment.files`.\n- The runner removes the root skill for control and separately verifies treatment activation. Do not add a `skill-invocation` grader and do not tell the agent to invoke the skill in the shared prompt.\n- Prompts may identify fixtures, proposed code, fixed IDs, and output paths, but must not reveal the expected diagnosis, owning mechanism, or regression-test design.\n- Stage self-contained source snapshots rather than diffs or commit references; fixture context must not require fetching a repository revision.\n- Use deterministic graders for observable artifacts, a narrow semantic rubric for behavior, and a `token-budget` grader. Define bounded turns, tokens, and duration plus a committed scoring threshold.\n- The task must exercise guidance distinctive to the skill. A control that consistently matches treatment means the skill or eval is not useful enough.\n\n## Validation\n\n- Frontmatter parses and the name matches the directory.\n- The skill is concise, stable, and does not duplicate root or scoped instructions.\n- File references are relative and exist.\n- Validation steps are observable and task-specific.\n- The paired eval targets only the skill, has complete bounded grading, and uses a solution-neutral prompt.\n- `npm run lint` and the harness inventory tests pass.\n\n## Common Pitfalls\n\n| Pitfall | Correction |\n|---|---|\n| Copying implementation inventories into the skill | Keep only non-obvious invariants and routing decisions |\n| Exact line counts or volatile metrics | Remove them; point to stable symbols or behavior |\n| Generic test-folder guidance | Describe the distinctive test shape or omit it |\n| Eval prompt tells the agent what to find | Move expected facts into the hidden rubric |\n| Eval root contains repository fixtures | Keep only the target skill at root; stage fixtures per stimulus |\n| Prompt instructs skill invocation | Let the treatment-only runner gate enforce activation |\n| Initial scaffold launches multi-model review | First produce and lint the requested artifacts; run expensive behavioral validation separately |",".agents/skills/model-building/SKILL.md":"---\nname: model-building\ndescription: 'Implementation details for EF Core model building. Use when changing ConventionSet, ModelBuilder, IConvention implementations, ModelRuntimeInitializer, RuntimeModel, or related classes.'\nuser-invocable: false\n---\n\n# Model Building, Conventions & Initialization\n\nCovers model construction (conventions, fluent API, metadata hierarchy) and model initialization (runtime annotation propagation, compiled model filtering).\n\n## Convention System\n\n`ConventionSet` (`src/EFCore/Metadata/Conventions/ConventionSet.cs`) holds `List<I*Convention>` for every metadata event. Key conventions in `src/EFCore/Metadata/Conventions/`:\n\n- `DbSetFindingConvention` — discovers entities from `DbSet<T>`\n- `PropertyDiscoveryConvention` — discovers properties from CLR types\n- `KeyDiscoveryConvention` — finds PKs (`Id`, `TypeId`)\n- `RelationshipDiscoveryConvention` — infers FKs from navigations\n- `RuntimeModelConvention` — creates optimized `RuntimeModel` from mutable model\n\nOverride `ConfigureConventions(ModelConfigurationBuilder)` to add/remove conventions.\n\nConvention fixes must preserve dispatcher behavior and ambiguity information. For inverse-navigation attributes, do not solve recursion by permanently ignoring an ambiguous navigation: removing one candidate can make another ambiguity appear unique and configure the wrong relationship. `InversePropertyAttributeConvention` records inverse candidates and uses `AddInverseNavigation`, `TryRemoveIfAmbiguous`, and `FindAmbiguousInverse` while still allowing convention processing to continue.\n\nTest the state transitions, not only the initially ambiguous model: first verify that multiple interacting candidates configure no relationship; then genuinely remove ambiguity both by ignoring/removing one competing navigation and by removing a competing entity type, and verify that the remaining inverse relationship is configured. These cases distinguish candidate bookkeeping from a permanent-ignore workaround.\n\n## Metadata Interface Hierarchy\n\n`IReadOnly*` → `IMutable*` → `IConvention*` → `IRuntime*`\n\nApplies to: Model, EntityType, Property, Key, ForeignKey, Navigation, Index, etc. Builders follow: `*Builder` → `IConvention*Builder`.\n\n## Adding A Configurable Metadata Facet\n\nFollow the nearest existing facet end to end rather than stopping at the public interface:\n\n1. Add the read-only, mutable, and convention metadata contracts, concrete storage, default, configuration source, convention setter, and builder precedence checks. Preserve the facet when metadata is replaced or a relationship is rebuilt.\n2. If changes are observable to conventions, add the convention interface, every `ConventionSet` add/replace/remove path, and immediate plus delayed dispatcher scopes and nodes.\n3. Carry the value into the optimized runtime metadata through `RuntimeModelConvention`, runtime constructors/builders, and `CSharpRuntimeModelCodeGenerator` so compiled models preserve it.\n4. If snapshots persist the facet, update the fluent builder API and `CSharpSnapshotGenerator`; keep the old absence equivalent to the historical default.\n5. Update public API baselines and cover configuration-source precedence, convention dispatch, runtime/compiled model propagation, and snapshot round trips.\n\n## Model Lifecycle\n\n1. **Mutable Model** — built by `ModelBuilder` during `OnModelCreating`, made read-only by `FinalizeModel()`\n2. **Design-Time Model** — finalized read-only `Model` that also contains design-time-only annotations used in migrations\n3. **Runtime Model** — an optimized read-only model created by `RuntimeModelConvention.ProcessModelFinalized()`, does not contain design-time-only annotations\n\n`ModelRuntimeInitializer.Initialize()` (called by `DbContextServices.CreateModel()`):\n\n```\nInitialize(model, designTime, validationLogger)\n├─ FinalizeModel() if mutable\n├─ Set ModelDependencies, InitializeModel\n└─ RuntimeModelConvention creates RuntimeModel, copies/filters annotations\n```\n\n## Complex Type Property Recursion\n\nWhen processing properties in conventions or validation, remember that complex types can contain their own declared properties. Use `GetFlattenedProperties()` to iterate all properties (including on nested non-collection complex types) or manually recurse through `GetDeclaredComplexProperties()` → `complexProperty.ComplexType`.\n\n## Adding a New Annotation\n\n1. Add constant to `CoreAnnotationNames` and its `AllNames`\n2. Filter in `RuntimeModelConvention.ProcessModelAnnotations` if it's a design-time-only annotation (only used in migration operations)\n   1. If it was filtered out, add logic to the getters that throws an exception if accessed on the runtime model\n3. Filter in `CSharpRuntimeAnnotationCodeGenerator.Generate` if it can be computed lazily at runtime (e.g. based on other annotations)\n4. Propagate in `RelationalAnnotationProvider` if used in up-migrations or the relational model and `IMigrationsAnnotationProvider` if used in down-migrations\n\n## Relational Model\n\n`RelationalModel` (`src/EFCore.Relational/Metadata/Internal/RelationalModel.cs`) is a database-centric view of the EF model, mapping entity types to physical database objects: `Tables`, `Views`, `Functions`, `Queries`, and `DefaultTables`. `DefaultTables` are pseudo-table objects only used for `FromSql` queries.\n\nCreated lazily by `RelationalModelRuntimeInitializer`, accessed via `model.GetRelationalModel()`. Used by migrations (`MigrationsModelDiffer`), update and query pipelines.\n\n`RelationalAnnotationProvider` populates annotations on relational model elements. Provider subclasses (e.g., `SqlServerAnnotationProvider`) add provider-specific annotations. `IMigrationsAnnotationProvider` controls annotations used in down-migration operations.\n\n## Model Validation\n\n`ModelValidator` (`src/EFCore/Infrastructure/ModelValidator.cs`) and `RelationalModelValidator` (`src/EFCore.Relational/Infrastructure/RelationalModelValidator.cs`) run after model finalization, during `ModelRuntimeInitializer.Initialize()` between the pre- and post-validation `InitializeModel` calls.\n\n## Migration Snapshot Compatibility\n\nModel-building changes can trigger spurious migrations for users who upgrade. Two causes:\n\n1. **New metadata written to the snapshot** — old snapshots won't have it; `MigrationsModelDiffer` sees a diff. Fix: ensure absence of the annotation in an old snapshot is treated as the old default.\n2. **Annotation renamed or reinterpreted** — old snapshots produce a different model. Fix: keep backward-compatible reading logic.\n\nInspect `CSharpSnapshotGenerator` (what gets written) and `MigrationsModelDiffer` (how absence is handled). Add a snapshot round-trip test in `test/EFCore.Design.Tests/Migrations/ModelSnapshotSqlServerTest.cs`.\n\n## Testing\n\n| Area | Location |\n|------|----------|\n| Convention unit tests | `test/EFCore.Tests/Metadata/Conventions/` |\n| Metadata unit tests | `test/EFCore.Tests/Metadata/Internal/` |\n| Model builder API tests | `test/EFCore.Specification.Tests/ModelBuilding/ModelBuilderTest*.cs` |\n| Relationship discovery tests | `test/EFCore.Specification.Tests/ModelBuilding101*.cs` |\n| Model validation tests | `test/EFCore.Tests/Infrastructure/ModelValidatorTest*.cs` |\n| Compiled model tests | `test/EFCore.Specification.Tests/Scaffolding/CompiledModelTestBase.cs` |\n\n## Validation\n\n- Model builds without `InvalidOperationException` during finalization\n- All new API is covered by tests\n- Compiled model baselines update cleanly with `EF_TEST_REWRITE_BASELINES=1`\n- `ToString()` on metadata objects shows concise contents without throwing exceptions\n- No spurious migration is generated against a project with an existing snapshot",".agents/skills/migrations/SKILL.md":"---\nname: migrations\ndescription: 'Implementation details for EF Core migrations. Use when changing MigrationsSqlGenerator, model diffing, migration operations, HistoryRepository, the Migrator or related classes.'\nuser-invocable: false\n---\n\n# Migrations\n\n## Pipeline\n\n**Add migration**: `MigrationsScaffolder.ScaffoldMigration()` → `MigrationsModelDiffer.GetDifferences()` → list of `MigrationOperation` → `CSharpMigrationsGenerator` and `CSharpSnapshotGenerator` produce Up/Down/Snapshot code\n\n**Apply migration**: `Migrator.MigrateAsync()` → reads `__EFMigrationsHistory` → per pending: `MigrationsSqlGenerator.Generate(operations)` → `MigrationCommandExecutor` executes\n\n## Model Snapshot\n\n- Model snapshots use `typeof(Dictionary<string, object>)` (property bag format), not the actual CLR type. When examining the `ClrType` in a snapshot, don't assume it matches the real entity type.\n- `SnapshotModelProcessor.Process()` is used at design-time to fixup older model snapshots for backward compatibility.\n- `MigrationsModelDiffer` uses provider-agnostic structural comparison between relational models to determine what migration operations are necessary.\n\nFor an upgrade-only regression, derive a concrete old `ModelSnapshot`, process its model with `SnapshotModelProcessor.Process(..., resetVersion: true)`, and compare it with the equivalent current design-time model through `MigrationsModelDiffer.GetDifferences()`. Preserve the property-bag CLR types emitted by old snapshots and omit APIs that would explicitly configure metadata that was absent in that version. The regression succeeds only when the resulting operation list is empty.\n\nLegacy snapshot normalization belongs in `SnapshotModelProcessor`, not in runtime migration application. Scope a compatibility branch to the exact released versions that could emit the affected snapshot shape; versions from before the feature existed should not be included merely because they are numerically older. Prefer the mutable metadata interface when it exposes the required setter rather than casting to a concrete metadata implementation. Do not use a missing configuration source as the test for missing historical snapshot metadata: old snapshots may already configure a value using the current default. For metadata whose semantics changed, use the snapshot's product version to restore the old invariant. Add focused coverage for every version family named by the gate, plus the first unaffected version.\n\n## Testing\n\nMigration operation tests: `test/EFCore.Relational.Tests/Migrations/`. Functional tests: `test/EFCore.{Provider}.FunctionalTests/Migrations/`. Model differ tests: `test/EFCore.Relational.Tests/Migrations/Internal/MigrationsModelDifferTest*.cs`.\n\nTo simulate a snapshot model use `ModelBuilder` calls without conventions.",".agents/skills/run-apichief/SKILL.md":"---\nname: run-apichief\ndescription: 'Run ApiChief in the EF Core repo to emit baselines, summaries, deltas, review files, or breaking-change checks. Use when refreshing `*.baseline.json`, preparing API review artifacts, or validating API changes.'\nuser-invocable: false\n---\n\n# Run ApiChief\n\nUse the ApiChief tool documented at `eng/Tools/ApiChief/README.md` to inspect or refresh EF Core public API baselines for projects under `src/`.\n\nApiChief can run against either a compiled assembly or a previously emitted baseline JSON file. Prefer the repo-local `.dotnet` SDK and the checked-in build scripts in this repo.\n\n## Commands\n\n| Command | Description | Extra arguments |\n| --- | --- | --- |\n| `emit baseline` | Emit a JSON API baseline | `-o <file>` |\n| `emit summary` | Emit a human-readable API summary | `-o <file>`, `-x` |\n| `emit review` | Emit API review files | `-o <dir>`, `-n` |\n| `emit delta` | Emit a delta against an existing baseline, or markdown diff review files | `<baseline-path>`, `-o <file-or-dir>`, `--diff` |\n| `check breaking` | Fail if breaking changes exist vs. a baseline | `<baseline-path>` |\n\nDefault to `emit baseline` if the user only asks to \"run ApiChief\".\n\n## Workflow\n\n### 1. Identify the target project(s)\n\n- Match user intent against project folders under `src/`.\n- Ask for clarification only if the target is ambiguous.\n- The checked-in baseline path convention in this repo is `src/<ProjectName>/<ProjectName>.baseline.json`.\n- If asked just to update the baselines, run EFCore.ApiBaseline.Tests tests and skip the rest of the steps below.\n\n### 2. Prepare the environment\n\nAlways initialize the repo environment before building or running the tool:\n\n```powershell\n.\\restore.cmd\n. .\\activate.ps1\ndotnet build .\\eng\\Tools\\ApiChief\\ApiChief.csproj --nologo --verbosity q\n```\n\nOn Bash:\n\n```bash\n./restore.sh\n. ./activate.sh\ndotnet build ./eng/Tools/ApiChief/ApiChief.csproj --nologo --verbosity q\n```\n\n### 3. Ensure the target binaries exist\n\nApiChief operates on built assemblies. If the target project has not been built yet, build it first.\n\nPreferred options:\n\n```powershell\n# Refreshes checked-in baselines after the normal build\n.\\build.cmd -c Debug\n\n# Or build a single project when working narrowly\ndotnet build .\\src\\<ProjectName>\\<ProjectName>.csproj --nologo --verbosity q\n```\n\nUse the highest available `net*` TFM under `artifacts/bin/<ProjectName>/<Configuration>/` by default. Avoid `netstandard*` and `net4*` targets unless the user explicitly asks for them.\n\n### 4. Locate the built ApiChief binary and target assembly\n\n```powershell\n$dotnet = \".\\\\.dotnet\\\\dotnet\"\n$apiChiefProject = \".\\\\eng\\\\Tools\\\\ApiChief\\\\ApiChief.csproj\"\n$apiChief = (& $dotnet msbuild $apiChiefProject --getProperty:TargetPath -p:Configuration=Debug --nologo).Trim()\n\n$name = \"<ProjectName>\"\n$tfm = Get-ChildItem \".\\\\artifacts\\\\bin\\\\$name\\\\Debug\" -Directory |\n    Where-Object { $_.Name -match '^net\\d+\\.\\d+$' } |\n    Sort-Object { [version]($_.Name -replace '^net', '') } -Descending |\n    Select-Object -First 1 -ExpandProperty Name\n\n$assemblyName = (& $dotnet msbuild \".\\\\src\\\\$name\\\\$name.csproj\" --getProperty:AssemblyName -p:Configuration=Debug --nologo).Trim()\nif ([string]::IsNullOrWhiteSpace($assemblyName))\n{\n    $assemblyName = $name\n}\n\n$assemblyPath = \".\\\\artifacts\\\\bin\\\\$name\\\\Debug\\\\$tfm\\\\$assemblyName.dll\"\n```\n\nBefore running, report the selected TFM if it matters for the task.\n\n### 5. Run the requested ApiChief command\n\n```powershell\n# Emit a baseline\n& $dotnet $apiChief $assemblyPath emit baseline -o \".\\\\src\\\\$name\\\\$name.baseline.json\"\n\n# Emit a summary\n& $dotnet $apiChief $assemblyPath emit summary\n\n# Emit a delta\n& $dotnet $apiChief $assemblyPath emit delta \".\\\\src\\\\$name\\\\$name.baseline.json\" -o \".\\\\artifacts\\\\tmp\\\\$name.delta.json\"\n\n# Check for breaking changes\n& $dotnet $apiChief $assemblyPath check breaking \".\\\\src\\\\$name\\\\$name.baseline.json\"\n\n# Emit API review artifacts\n& $dotnet $apiChief $assemblyPath emit review -o \".\\\\artifacts\\\\tmp\\\\API.$name\"\n\n# Emit GitHub-friendly markdown diff files against a baseline\n& $dotnet $apiChief $assemblyPath emit delta \".\\\\src\\\\$name\\\\$name.baseline.json\" --diff -o \".\\\\artifacts\\\\tmp\\\\API.$name.Diff\"\n```\n\n`emit delta` also supports passing a `.json` file as the current input instead of a DLL.\n\n### 6. Review or clean up baseline changes\n\nAfter `emit baseline`:\n\n- preserve the original BOM and trailing newline behavior of the committed file\n- revert version-only diffs in the `\"Name\"` field\n- inspect removed `//` instruction comments in previous baselines and carry forward any still-needed manual edits\n- if those comments reference GitHub issues, check whether the underlying issue is still open before reapplying the workaround\n\n### 7. Report results clearly\n\n- list the processed project(s)\n- show the chosen TFM(s)\n- report the output path(s)\n- for `check breaking`, state pass/fail\n- for `emit delta` and `emit delta --diff`, mention that exit code `0` means changes, `2` means no changes, and `-1` means an error\n- prefer `emit delta --diff` output because it generates ready-to-post ```diff fenced markdown split across per-type `.md` files\n",".agents/skills/query-pipeline/SKILL.md":"---\nname: query-pipeline\ndescription: 'Implement and review EF Core query translation, projection visitors, split-query enumeration, and query regression tests. Use when changing query-pipeline code or choosing specification and provider coverage for a query regression.'\nuser-invocable: false\n---\n\n# Query Pipeline\n\n## Regression Test Ownership\n\n- Group query specification tests by a cohesive query or model trait. Do not create a generic bucket merely because tests use custom models; use the existing trait-specific hierarchy, such as owned-entity queries.\n- Inspect the specification base and provider overrides before placing a regression. Keep the LINQ query, model setup, and result assertions in the shared virtual test; provider overrides call the base and add only provider-specific baselines or established limitations.\n- A provider-only test can leave every other provider untested even when its SQL assertion is correct. Preserve override guards without adding a guard that forces unrelated redundant overrides.\n- For an optimization, cover both eligible and rejected shapes with exact result assertions in sync and async. Supply a concrete provider override and SQL baseline or established limitation; an abstract test base or expression-shape check alone does not prove execution coverage.\n\n## Translation\n\n- Translation fallback must distinguish established unsupported shapes from unexpected defects. Do not turn arbitrary exceptions into a successful fallback.\n- Check whether a failed rewrite mutated state that fallback will reuse. For test coordination, establish the actual collection, assembly, and async-flow boundaries before claiming shared static state can race; theory rows are not inherently parallel, and reset in `finally` is not mutual exclusion.\n\n## Optimizations\n\n- Match the equivalence needed by the rewrite, not blindly by expression equality.\n- Preserve context-specific null semantics. SQL UNKNOWN can be filtered like `false` in a predicate but not in a projected value or under negation; `UseRelationalNulls`, null-containing `IN`/`NOT IN`, and scalar versus composite LINQ join keys require different compensation.\n- Preserve cardinality and operator order, not just matching rows. Moving predicates across outer joins, adding keys under `Distinct`/`GroupBy`, or converting correlated APPLY to JOIN can change results; per-parent pagination must retain its partitioning and ordering, and remaining outer references must prevent decorrelation.\n- Share repeated subqueries only when their evaluation and row selection are equivalent. Volatile expressions, query filters introduced during later navigation expansion, and required-navigation joins can change evaluation count or which row survives a limit. Check determinism and row preservation before reuse, and collect candidates within their own lambda scope.\n- Preserve SQL typing and CLR result semantics separately. Remove a cast only when its store-type effect is redundant; casts on constants can establish necessary SQL typing. SQL nullable columns do not alone describe shaper nullability: `DefaultIfEmpty` on a non-nullable scalar may require `COALESCE` to its CLR default.\n- Remap dependent state when changing query shape. Subquery pushdown or join replacement must update scoped column references, predicates, orderings, projection bindings, and shapers; retain or recompute identifiers and their comparers when multiplicity or null extension changes.\n- Prove pruning safety beyond the final projection. An unused join can still filter or multiply rows, so honor explicit prunability and references from other clauses. Unreferenced columns can still define distinct/set-operation membership or a scalar subquery's result; preserve those contracts and compatible set-operation projections.\n\n## Split Queries\n\n- When changing `SplitQueryResultCoordinator`, check both `SplitQueryingEnumerable` and `GroupBySplitQueryingEnumerable`, including their synchronous and asynchronous paths. End-of-stream validation belongs at true outer-stream exhaustion, not at a group boundary or early disposal.\n- A grouped reader can reach physical EOF while assembling a final group that still must be yielded. Test that successful move separately from the subsequent terminal move, including verification failure and repeated terminal calls; cleanup must preserve the original failure.\n- Account for internal buffering as well as caller materialization when assessing memory use. Earlier split-query result sets may need buffering when the provider cannot keep multiple readers active; retrying execution strategies can also require buffering.\n- Buffering does not give separate query commands a consistent database snapshot. Concurrent writes between commands can produce an inconsistent result graph; consider snapshot or serializable transactions when consistency is required, accounting for provider support and transaction costs.\n- Prove cross-command consistency with a writer transaction and an explicit barrier between reads, not sleeps or a prose-only scenario. Assert a root/child value combination, not just matching keys; state the isolation and retry-strategy boundaries of the test.\n\n## Validation\n\n- `ToQueryString()` shows generated SQL without executing\n- `ExpressionPrinter` dumps expression trees at any pipeline stage\n- SQL baselines verified via `AssertSql()` in provider functional tests and the generated SQL corresponds to the LINQ query in the base method\n",".agents/skills/scaffolding/SKILL.md":"---\nname: scaffolding\ndescription: 'Implementation details for EF Core scaffolding (reverse engineering). Use when changing ef dbcontext scaffold pipeline implementation, database schema reading, CSharpModelGenerator, or related classes.'\nuser-invocable: false\n---\n\n# Scaffolding\n\nGenerates C# code from database schemas (reverse engineering).\n\n## When Not to Use\n\n- Working on compiled model generation (`dotnet ef dbcontext optimize`)\n\n## Reverse Engineering\n\nPipeline: `IDatabaseModelFactory` (reads schema) → `IScaffoldingModelFactory` (builds EF model) → `IModelCodeGenerator` (generates C#)\n- `IReverseEngineerScaffolder` — orchestrates full pipeline\n\n## Schema Query Compatibility\n\nProvider schema readers often query one-to-many metadata tables. Preserve anti-semi semantics when adapting SQL for a limited engine: a `LEFT JOIN` containing the complete excluded-property predicate in `ON`, followed by a null filter on a non-nullable joined key, is equivalent to `NOT EXISTS`. Unrelated metadata rows do not join; any matching excluded row makes the joined key non-null and excludes the object. Do not move parts of the excluded-property predicate to `WHERE` or join all metadata rows and filter individual rows afterward. An equivalent non-correlated anti-set form, such as `NOT IN (SELECT key ... WHERE excluded-condition)`, also works when the subquery cannot return null keys. Cover objects with no metadata, unrelated metadata only, the excluded property only, and both excluded and unrelated properties.\n",".agents/skills/servicing-pr/SKILL.md":"# servicing-pr\n\nPath: `.agents/skills/servicing-pr/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/servicing-pr/SKILL.md)",".agents/skills/sqlite-adonet/SKILL.md":"# sqlite-adonet\n\nPath: `.agents/skills/sqlite-adonet/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/sqlite-adonet/SKILL.md)",".agents/skills/tooling/SKILL.md":"# tooling\n\nPath: `.agents/skills/tooling/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/tooling/SKILL.md)",".agents/skills/triage/SKILL.md":"# triage\n\nPath: `.agents/skills/triage/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/triage/SKILL.md)",".agents/skills/update-pipeline/SKILL.md":"# update-pipeline\n\nPath: `.agents/skills/update-pipeline/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/update-pipeline/SKILL.md)",".github/skills/agentic-workflows/SKILL.md":"# agentic-workflows\n\nPath: `.github/skills/agentic-workflows/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.github/skills/agentic-workflows/SKILL.md)",".github/copilot-instructions.md":"# GitHub Copilot Instructions\n\nPath: `.github/copilot-instructions.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.github/copilot-instructions.md)",".github/copilot/settings.json":"# GitHub Copilot Instructions\n\nPath: `.github/copilot/settings.json`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.github/copilot/settings.json)","src/EFCore.Tools/README.md":"# EFCore.Tools Documentation\n\nPath: `src/EFCore.Tools/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/src/EFCore.Tools/README.md)","eng/Tools/ApiChief/README.md":"# ApiChief Documentation\n\nPath: `eng/Tools/ApiChief/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/Tools/ApiChief/README.md)",".agents/skills/code-review/references/api-review.md":"# References Skill\n\nPath: `.agents/skills/code-review/references/api-review.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/code-review/references/api-review.md)",".agents/skills/code-review/references/conventions.md":"# References Skill\n\nPath: `.agents/skills/code-review/references/conventions.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/code-review/references/conventions.md)",".agents/skills/code-review/references/security-review.md":"# References Skill\n\nPath: `.agents/skills/code-review/references/security-review.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/code-review/references/security-review.md)","eng/harness-evaluation/skills/change-tracking/eval.yaml":"# Change-tracking Skill\n\nPath: `eng/harness-evaluation/skills/change-tracking/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/change-tracking/eval.yaml)","eng/harness-evaluation/skills/code-review/eval.yaml":"# Code-review Skill\n\nPath: `eng/harness-evaluation/skills/code-review/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/code-review/eval.yaml)","eng/harness-evaluation/skills/cosmos-provider/eval.yaml":"# Cosmos-provider Skill\n\nPath: `eng/harness-evaluation/skills/cosmos-provider/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/cosmos-provider/eval.yaml)","eng/harness-evaluation/skills/make-custom-agent/eval.yaml":"# Make-custom-agent Skill\n\nPath: `eng/harness-evaluation/skills/make-custom-agent/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/make-custom-agent/eval.yaml)","eng/harness-evaluation/skills/make-github-actions-workflow/eval.yaml":"# Make-github-actions-workflow Skill\n\nPath: `eng/harness-evaluation/skills/make-github-actions-workflow/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/make-github-actions-workflow/eval.yaml)","eng/harness-evaluation/skills/make-instructions/eval.yaml":"# Make-instructions Skill\n\nPath: `eng/harness-evaluation/skills/make-instructions/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/make-instructions/eval.yaml)","eng/harness-evaluation/skills/make-skill/eval.yaml":"# Make-skill Skill\n\nPath: `eng/harness-evaluation/skills/make-skill/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/make-skill/eval.yaml)","eng/harness-evaluation/skills/migrations/eval.yaml":"# Migrations Skill\n\nPath: `eng/harness-evaluation/skills/migrations/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/migrations/eval.yaml)","eng/harness-evaluation/skills/model-building/eval.yaml":"# Model-building Skill\n\nPath: `eng/harness-evaluation/skills/model-building/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/model-building/eval.yaml)","eng/harness-evaluation/skills/query-pipeline/eval.yaml":"# Query-pipeline Skill\n\nPath: `eng/harness-evaluation/skills/query-pipeline/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/query-pipeline/eval.yaml)","eng/harness-evaluation/skills/run-apichief/eval.yaml":"# Run-apichief Skill\n\nPath: `eng/harness-evaluation/skills/run-apichief/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/run-apichief/eval.yaml)","eng/harness-evaluation/skills/scaffolding/eval.yaml":"# Scaffolding Skill\n\nPath: `eng/harness-evaluation/skills/scaffolding/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/scaffolding/eval.yaml)","eng/harness-evaluation/skills/servicing-pr/eval.yaml":"# Servicing-pr Skill\n\nPath: `eng/harness-evaluation/skills/servicing-pr/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/servicing-pr/eval.yaml)","eng/harness-evaluation/skills/sqlite-adonet/eval.yaml":"# Sqlite-adonet Skill\n\nPath: `eng/harness-evaluation/skills/sqlite-adonet/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/sqlite-adonet/eval.yaml)","eng/harness-evaluation/skills/tooling/eval.yaml":"# Tooling Skill\n\nPath: `eng/harness-evaluation/skills/tooling/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/tooling/eval.yaml)","eng/harness-evaluation/skills/triage/eval.yaml":"# Triage Skill\n\nPath: `eng/harness-evaluation/skills/triage/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/triage/eval.yaml)","eng/harness-evaluation/skills/update-pipeline/eval.yaml":"# Update-pipeline Skill\n\nPath: `eng/harness-evaluation/skills/update-pipeline/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/update-pipeline/eval.yaml)","eng/harness-evaluation/skills/migrations/fixtures/upgrade-only/source-context.md":"# Upgrade-only Skill\n\nPath: `eng/harness-evaluation/skills/migrations/fixtures/upgrade-only/source-context.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/migrations/fixtures/upgrade-only/source-context.md)","eng/harness-evaluation/skills/query-pipeline/fixtures/provider-test-placement/source-context.md":"# Provider-test-placement Skill\n\nPath: `eng/harness-evaluation/skills/query-pipeline/fixtures/provider-test-placement/source-context.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/query-pipeline/fixtures/provider-test-placement/source-context.md)","eng/harness-evaluation/skills/query-pipeline/fixtures/query-pipeline/split-query-review.md":"# Query-pipeline Skill\n\nPath: `eng/harness-evaluation/skills/query-pipeline/fixtures/query-pipeline/split-query-review.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/query-pipeline/fixtures/query-pipeline/split-query-review.md)","eng/harness-evaluation/skills/query-pipeline/fixtures/single-result-lifting/integration.md":"# Single-result-lifting Skill\n\nPath: `eng/harness-evaluation/skills/query-pipeline/fixtures/single-result-lifting/integration.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/query-pipeline/fixtures/single-result-lifting/integration.md)","eng/harness-evaluation/skills/triage/fixtures/sandbox/embedded-directive.md":"# Sandbox Skill\n\nPath: `eng/harness-evaluation/skills/triage/fixtures/sandbox/embedded-directive.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/triage/fixtures/sandbox/embedded-directive.md)","eng/harness-evaluation/skills/triage/fixtures/sandbox/issue-context.md":"# Sandbox Skill\n\nPath: `eng/harness-evaluation/skills/triage/fixtures/sandbox/issue-context.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/triage/fixtures/sandbox/issue-context.md)","eng/harness-evaluation/skills/triage/fixtures/sandbox/security-report.md":"# Sandbox Skill\n\nPath: `eng/harness-evaluation/skills/triage/fixtures/sandbox/security-report.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/triage/fixtures/sandbox/security-report.md)","eng/harness-evaluation/skills/triage/fixtures/sandbox/unsafe-setup.md":"# Sandbox Skill\n\nPath: `eng/harness-evaluation/skills/triage/fixtures/sandbox/unsafe-setup.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/triage/fixtures/sandbox/unsafe-setup.md)","eng/harness-evaluation/skills/update-pipeline/fixtures/shared-identity/source-excerpts.md":"# Shared-identity Skill\n\nPath: `eng/harness-evaluation/skills/update-pipeline/fixtures/shared-identity/source-excerpts.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/update-pipeline/fixtures/shared-identity/source-excerpts.md)","eng/harness-evaluation/skills/code-review/fixtures/query-comment/context/review-context.md":"# Context Skill\n\nPath: `eng/harness-evaluation/skills/code-review/fixtures/query-comment/context/review-context.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/code-review/fixtures/query-comment/context/review-context.md)"},"items":[{"name":"SKILL.md","path":".agents/skills/change-tracking/SKILL.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/change-tracking/SKILL.md","title":"change-tracking","category":"anthropic-skill","format":"markdown","content":"---\nname: change-tracking\ndescription: 'Implementation details for EF Core change tracking. Use when changing InternalEntityEntry, ChangeDetector, SnapshotFactoryFactory, or related entity state, snapshot, or property accessor code.'\nuser-invocable: false\n---\n\n# Change Tracking\n\nManages entity states and detects changes for `SaveChanges()`.\n\n## Core Components\n\n- `StateManager` — owns tracked entries, identity/reference maps, fixup, cascades, notifications, and changed counts\n- `InternalEntryBase` and derived classes — own per-entry state, flags, values, snapshots, and ordered state transitions\n- `ChangeDetector` — compares current values with baselines and reports changes through entry mutation APIs\n- `SnapshotFactoryFactory` subclasses — create passive original- and relationship-value baselines\n- `IdentityMap` — permits one active entry per key; shared identity pairs a replacement with the prior `Deleted` entry\n- `PropertyAccessorsFactory`, `ClrPropertyGetterFactory` and `ClrPropertySetterFactory` compile property accessors for efficient snapshotting and change detection\n  - Ordinals in `indices` parameter specify element at each complex collection depth\n\n## Change Detection\n\n- Snapshot and notification strategies both call `SetPropertyModified()` to keep property flags and entity state consistent.\n- `SetEntityState()` validates values, updates flags and complex entries, changes state, then runs manager bookkeeping hooks.\n\n## Shared-Identity Replacement\n\n`SharedIdentityEntry` is the invariant that distinguishes an old deleted entry from its replacement with the same identity. When attaching a replacement graph, a deleted nested entry should be reconsidered only when its source entry has a replacement; do not broadly process every deleted node. Likewise, cascading from the old replaced principal must not delete dependents that belong to the replacement graph. Keep synchronous and asynchronous graph-attach paths equivalent and preserve unrelated values in replacement tests so they isolate the identity transition.\n\n## Testing\n\nUnit tests: `test/EFCore.Tests/ChangeTracking/`. Functional tests: `test/EFCore.Specification.Tests/GraphUpdates/`.\n\n## Common Pitfalls\n\n| Pitfall | Solution |\n|---------|----------|\n| State-based checks treat every Added/Deleted entry as a replacement | Scope replacement behavior through `SharedIdentityEntry` and the graph source |\n\n## Validation\n\n- `DetectChanges()` identifies modified properties via snapshot comparison\n- Setting original values marks properties as modified or unchanged based on comparison with current values\n","frontmatter":{"name":"change-tracking","description":"Implementation details for EF Core change tracking. Use when changing InternalEntityEntry, ChangeDetector, SnapshotFactoryFactory, or related entity state, snapshot, or property accessor code.","user-invocable":false},"isInternal":false,"tokens":499,"sizeBytes":2606},{"name":"api-review.md","path":".agents/skills/code-review/references/api-review.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/code-review/references/api-review.md","title":"References Skill","category":"anthropic-skill","format":"markdown","content":"# References Skill\n\nPath: `.agents/skills/code-review/references/api-review.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/code-review/references/api-review.md)","tokens":300,"sizeBytes":215},{"name":"conventions.md","path":".agents/skills/code-review/references/conventions.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/code-review/references/conventions.md","title":"References Skill","category":"anthropic-skill","format":"markdown","content":"# References Skill\n\nPath: `.agents/skills/code-review/references/conventions.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/code-review/references/conventions.md)","tokens":300,"sizeBytes":217},{"name":"security-review.md","path":".agents/skills/code-review/references/security-review.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/code-review/references/security-review.md","title":"References Skill","category":"anthropic-skill","format":"markdown","content":"# References Skill\n\nPath: `.agents/skills/code-review/references/security-review.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/code-review/references/security-review.md)","tokens":300,"sizeBytes":225},{"name":"SKILL.md","path":".agents/skills/code-review/SKILL.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/code-review/SKILL.md","title":"code-review","category":"anthropic-skill","format":"markdown","content":"---\nname: code-review\ndescription: 'Review EF Core pull requests or local changes for concrete correctness, compatibility, performance, security, and test-coverage problems. Use when asked to review, critique, or check code changes before merge or submission.'\n---\n\n# EF Core Code Review\n\nReview pull requests and local working-tree changes without modifying source. Findings must be concrete, evidence-backed problems introduced or exposed by the change, not style preferences or general improvement ideas.\n\n## Scope and Safety\n\n- Review the provided pull request, or staged, unstaged, and untracked local changes. Ask for clarification when both are plausible.\n- Never checkout, switch branches, stash, reset, clean, or otherwise mutate the working tree, except for checking out the requested head for review purposes. Never edit source as part of a review.\n- For a pull request, record its base, head, and immutable head SHA. If local `HEAD` differs, use read-only repository or GitHub context when sufficient; otherwise ask the user to checkout the requested commit.\n- Never submit an `APPROVE` or `REQUEST_CHANGES` event. COMMENT emission follows Step 8.\n- Do not use this skill to address existing review comments or implement fixes.\n\n## Workflow\n\n### 1. Establish the Review Surface\n\n1. Load `.github/copilot-instructions.md` and any area skill whose description matches the changed implementation.\n2. Obtain the complete diff and changed-file list once. Include staged, unstaged, and untracked files for local reviews.\n3. For pull requests, gather the base/head refs and head SHA, but defer the PR body, linked issues, and prior review comments until Step 3.\n4. Stop with a clear limitation if the requested change surface cannot be established.\n\n### 2. Form an Independent Assessment\n\nBefore reading the author's narrative:\n\n1. Read each changed implementation beyond its diff hunk. Diff-only review is insufficient evidence for a finding. For very large files, read the containing members, their contracts, and relevant state. When many files are changed, use subagents to break down the review into manageable parts and gather context incrementally.\n2. Search callers, implementations, overrides, sibling provider paths, and nearby tests. Read shared helpers whose contracts control the changed behavior.\n3. When logic moves, compare the old and new input domains. Check the moved member's XML contract as well as regression coverage.\n4. Use focused history to explain invariants, reverts, or prior rejected approaches; establish what makes a repeated approach viable now.\n5. Describe the old and new behavior, likely motivation, affected callers/providers, and initial concerns in your own words.\n\n### 3. Holistic PR Assessment\n\nAssess the overall approach before refining implementation details:\n\n- Require a concrete need for added code, APIs, abstractions, and flags. Prefer the simplest sufficient alternative; weigh benefits against complexity, surface area, and long-term maintenance.\n- Prefer root-cause fixes at the owning layer. Challenge a flawed direction early rather than polishing its implementation.\n- Require BenchmarkDotNet results or equivalent measurements for performance claims; prefer focused local runs for experimental or iterative work.\n - Explain and address scenario-specific regressions even when aggregate results improve.\n- Scale required benefit and validation with regression risk and blast radius, especially for stable code.\n\n### 4. Reconcile Pull Request Context\n\nFor pull requests, now read the description, linked issues, and existing review threads. Treat them as claims to verify against the code. Also flag found problems the PR narrative doesn't acknowledge.\n\nIf the additional context reveals information that genuinely changes your evaluation, update your holistic assessment accordingly. But do not soften findings just because the PR description sounds reasonable.\n\n### 5. Route Conditional Reviews\n\n- Read [references/api-review.md](references/api-review.md) when the change adds, removes, or changes supported public or protected API outside an `.Internal` namespace and not annotated with `[EntityFrameworkInternal]`.\n- Read [references/security-review.md](references/security-review.md) when changed data crosses a documented trust boundary or the change affects serialization, generated code from database metadata, command construction, sensitive-data handling, caches or complexity bounds, assembly loading, elevated operations, or another high-risk path.\n\n### 6. Analyze Behavior and Coverage\n\nFor each non-trivial production change, identify:\n\n1. **Changed behavior**: the concrete old and new code paths.\n2. **Affected surfaces**: callers, providers, public contracts, generated output, persistence, diagnostics, and concurrency where applicable.\n3. **Regression risks**: plausible inputs, interleavings, failures, or compatibility breaks.\n4. **Expected coverage**: the focused test that would fail without the change or expose the regression.\n5. **Coverage gaps**: affected behavior not exercised by changed or existing tests.\n\nCheck correctness, error handling, async behavior, concurrency, state and resource lifetime, compatibility, provider hierarchy behavior, NativeAOT constraints, and performance only where the changed path plausibly makes them relevant.\n\nFor exception cleanup around shared or concurrent state, distinguish whether this invocation acquired each resource from whether the resource currently appears held. Cover both a failing owner releasing its acquisition and a failing contender preserving another owner's acquisition, including preexisting nested state. Construct a concrete interleaving without weakening existing reentrancy or nesting behavior.\n\nFor new functionality consider other feature areas that might be affected but are not directly touched by the change.\n\nDo not request tests for documentation-only changes, comments, formatting, or demonstrably behavior-preserving mechanical changes. Do not flag issues that the compiler, formatter, or existing analyzers deterministically report.\n\n### 7. Optional Multi-Model Review\n\nWhen the environment supports launching sub-agents with different models (e.g., the `task` tool with a `model` parameter), run the review in parallel across multiple model families to get diverse perspectives. Different models catch different classes of issues. If the environment does not support this, proceed with a single-model review.\n\n1. Inspect the available model list and select models from 2-3 distinct model families, up to 3 sub-agent models total. If fewer than 2 eligible families are available, use what is available.\n   - Pick only from models explicitly listed as available in the environment. Do not guess or assume model names.\n   - Never pick models labeled \"mini\", \"fast\", or \"cheap\" for code review.\n   - Do not select a model from the same family that is already running the primary review (i.e. the currently used model).\n   - If multiple models exist in the same family, pick the one with the highest version number. Prefer \"-codex\" variants over general-purpose.\n   - If the model supports effort configuration use the one closest to the current effort level.\n2. Launch a sub-agent for each selected model in parallel, giving each the same review prompt: the PR diff, the review rules from this skill, and instructions to produce findings in the severity format defined above.\n3. Wait for all agents to complete, then synthesize: deduplicate findings that appear across models, elevate issues flagged by multiple models (higher confidence), and include unique findings from individual models that meet the confidence bar. If a sub-agent has not completed after 10 minutes and you have results from other agents, proceed with the results you have.\n4. Present a single unified review to the user, noting when an issue was flagged by multiple models. Do not wait for any remaining sub-agents and do not attempt retries if any failed. The review is complete once the report operation succeeds.\n\n### 7. Verify and Report Findings\n\nBefore reporting a concern:\n\n- Verify it against surrounding and unchanged code, including caller/callee defenses.\n- Identify a realistic failure or user impact. Do not promote a theoretical possibility with negligible likelihood into a finding.\n- Verify factual claims about APIs from repository evidence or current documentation; never rely on model memory to claim an API is absent, deprecated, or unavailable.\n- Report only test results actually observed. Separate unexecuted validation and residual risk from findings.\n\nOrder findings by severity:\n\n- ❌ **Critical**: practical exploitation, arbitrary code execution, widespread data loss, or similarly catastrophic impact.\n- 🔴 **High**: merge-blocking correctness, security, compatibility, data-integrity, or concurrency defect.\n- ⚠️ **Medium**: concrete defect with limited impact or a meaningful regression gap for changed behavior.\n- 🔵 **Low**: minor but real defect worth fixing in this change.\n- 💡 **Info**: observations or suggestions that do not constitute a defect but may improve code quality or maintainability.\n\nEach finding must contain:\n\n1. Severity and concise title.\n2. Certainty level or confidence in the finding based on the available evidence.\n3. Changed file and line or symbol.\n4. Concrete failure mode and impact.\n5. Evidence that makes the finding actionable.\n6. Fix direction and, when relevant, the missing regression-test shape.\n\nPresent the holistic assessment before findings. Do not add praise or filler.\n\n**Motivation**: <1-2 sentences on whether the PR is justified and the problem is real>\n\n**Approach**: <1-2 sentences on whether the fix/change takes the right approach>\n\n**Summary**: <✅ LGTM / ⚠️ Needs Human Review / ⚠️ Needs Changes / ❌ Reject>. <2-3 sentence summary of the overall verdict and key points. If \"Needs Human Review,\" explicitly state which findings you are uncertain about and what a human reviewer should focus on.>\n\n### 8. Optionally Post Pull Request Comments\n\nPosting is allowed through either authorization path:\n\n- **Direct invocation**: number the findings, let the user select or edit them, and obtain explicit confirmation before posting.\n- **Code-reviewer agent delegation**: an invoking code-reviewer agent may explicitly authorize COMMENT emission and provide the selected findings or complete review payload. That caller contract is sufficient authorization; do not add a redundant confirmation prompt. An analysis-only delegation does not authorize posting.\n\nImmediately before posting, confirm that the pull request is still open and its base, head, and head SHA match the reviewed revision. If they changed, stop and refresh the review context.\n\nCreate a pending review, add only authorized findings, and submit it as `COMMENT`. Never approve or request changes. Include a concise AI-generated disclosure when posting under a user's identity rather than a bot identity. Do not post findings that are similar to existing or resolved comments; for multiple defects in the same area, consolidate them into a single finding when appropriate.\n\n## Validation\n\n- Every finding resolves to changed code or a changed contract and cites supporting repository evidence.\n- Test requests follow the behavior-impact analysis.\n- No source or worktree mutation occurred.\n- Any posted review used the reviewed head SHA and COMMENT-only authorization.\n\n## Common Pitfalls\n\n- Reviewing hunks without their callers or provider hierarchy.\n- Treating a public CLR member in `.Internal` as supported public API.\n- Reporting a security keyword without tracing attacker-controlled data to an impact.\n- Inferring that passing broad tests covers the changed failure mode.\n- Turning uncertainty into a firm finding instead of investigating or recording a limitation.","frontmatter":{"name":"code-review","description":"Review EF Core pull requests or local changes for concrete correctness, compatibility, performance, security, and test-coverage problems. Use when asked to review, critique, or check code changes before merge or submission."},"isInternal":false,"tokens":2267,"sizeBytes":11868},{"name":"SKILL.md","path":".agents/skills/cosmos-provider/SKILL.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/cosmos-provider/SKILL.md","title":"cosmos-provider","category":"anthropic-skill","format":"markdown","content":"---\nname: cosmos-provider\ndescription: 'Implementation details for the EF Core Azure Cosmos DB provider. Use when changing Cosmos-specific code.'\nuser-invocable: false\n---\n\n# Cosmos DB Provider\n\nNon-relational provider with its own parallel query pipeline. Uses JSON for document materialization.\n\n## Key Differences from Relational\n\n- No migrations — use `EnsureCreated()`\n- Documents as JSON — owned and complex types become embedded objects\n- Partition key configuration required for performance\n- `ETag` for optimistic concurrency\n- No cross-container joins\n\n## Azure Cosmos DB Emulator for Tests\n\n- `TestEnvironment.InitializeAsync()` auto-starts a `Testcontainers.CosmosDb` container when `Test__Cosmos__DefaultConnection` is not set. Set the env var to use an existing emulator instead.\n- Skip tests requiring unsupported features on the Linux emulator with ` [ConditionalFact(typeof(CosmosTestEnvironment), nameof(CosmosTestEnvironment.IsNotLinuxEmulator))]`.\n","frontmatter":{"name":"cosmos-provider","description":"Implementation details for the EF Core Azure Cosmos DB provider. Use when changing Cosmos-specific code.","user-invocable":false},"isInternal":false,"tokens":199,"sizeBytes":972},{"name":"SKILL.md","path":".agents/skills/make-custom-agent/SKILL.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/make-custom-agent/SKILL.md","title":"make-custom-agent","category":"anthropic-skill","format":"markdown","content":"---\nname: make-custom-agent\ndescription: 'Create, review, or fix custom GitHub Copilot agents. Use when asked to create, scaffold, configure, review, or restrict a custom agent, declarative agent, or @-invokable chat participant for GitHub Copilot.'\n---\n\n# Create Custom Agent\n\nThis skill guides you through creating a custom GitHub Copilot agent — an `@`-invokable chat participant that extends Copilot with domain-specific expertise. Custom agents are distinct from Agent Skills: skills provide reusable instructions loaded on demand, while agents own the full conversational interaction and can orchestrate tools, call APIs, and maintain their own prompt strategies.\n\n## When Not to Use\n\n- Adding reusable, invokable workflows — use Agent Skills (`.agents/skills/`) instead\n- Adding background coding guidelines — use file-based instructions (`.github/instructions/`) instead\n- Adding project-wide context for Copilot — use `.github/copilot-instructions.md` instead\n- Creating reusable prompts — use .prompt.md instead\n\n## Workflow\n\nFor an existing proposal, audit the full definition rather than just its tools: the description must identify natural requests that should discover it, the body must add domain knowledge beyond root instructions, and the paired eval must isolate its contribution. Compare every tool and behavior to the user's intended authority. A command-free reviewer must not gain command execution or publication through a wildcard tool, handoff, or otherwise read-only workflow.\n\n### Step 1: Choose the agent type\n\n| Type | Location | Best for |\n|---|---|---|\n| Declarative (prompt file) | `.github/agents/<name>.md` | Simple prompt-driven cross-surface agents with no code |\n| Extension-based (chat participant) | VS Code extension project | Full control, tool calling, VS Code API access |\n| GitHub App (Copilot Extension) | Hosted service + GitHub App | Cross-surface agents (github.com, VS Code, Visual Studio) |\n\nIf the agent only needs a scoped system prompt and doesn't require custom code, start with a declarative agent.\n\n### Step 2: Create a declarative agent (prompt file)\n\nDeclarative agents are Markdown files in `.github/agents/`. VS Code and GitHub Copilot discover them automatically.\n\n```\n.github/agents/\n└── <agent-name>.md        # Agent definition\n```\n\nTemplate:\n\n```markdown\n---\nname: my-agent\ndescription: A short description of what this agent does and when to use it.\n---\n\n# <Agent Title>\n\nYou are an expert in <domain>. Your job is to:\n- <behavior 1>\n- <behavior 2>\n\n## Guidelines\n\n- <guideline 1>\n- <guideline 2>\n\n## Workflow\n\n1. <step 1>\n2. <step 2>\n\n## Constraints\n\n- <constraint 1>\n- <constraint 2>\n\n```\n\nSupported frontmatter fields:\n\n| Field | Required | Description |\n|---|---|---|\n| `name` | Yes | Lowercase, hyphens allowed. Used for `@`-mention. |\n| `description` | Yes | What the agent does and when to use it. Shown in the participant list. |\n| `target` | No | Target environment: `vscode` or `github-copilot` (defaults to both) |\n| `tools` | No | List of allowed tools/tool sets |\n| `model` | No | LLM name or prioritized array of models |\n| `user-invocable` | No | Show in agents dropdown (default: true) |\n| `disable-model-invocation` | No | Prevent subagent invocation (default: false) |\n| `mcp-servers` | No | MCP server configs for GitHub Copilot target |\n| `metadata` | No | Key-value mapping for additional arbitrary metadata. |\n| `argument-hint` | No | Hint text guiding user interaction (VS Code only) |\n| `agents` | No | List of allowed subagents (`*` for all, `[]` for none, VS Code only) |\n| `handoffs` | No | List of next-step agent transitions (VS Code only) |\n\n\nTips for instructions:\n- Use Markdown links to reference other files\n- Reference tools with `#tool:<tool-name>` syntax\n- Be specific about agent behavior and constraints\n\n### Step 3: Configure tools\n\nSpecify which tools the agent can use:\n\n```yaml\ntools:\n  - search              # Built-in tool\n  - fetch               # Built-in tool\n  - codebase            # Tool set\n  - myServer/*          # All tools from MCP server\n```\n\nCommon tool patterns:\n- **Read-only agents**: `['search', 'fetch', 'codebase']`\n- **Full editing agents**: `['*']` or specific editing tools\n- **Specialized agents**: Cherry-pick specific tools\n\n### Step 4: Add handoffs (optional, VS Code only)\n\nConfigure transitions to other agents:\n\n```yaml\nhandoffs:\n  - label: Start Implementation\n    agent: implementation\n    prompt: Implement the plan outlined above.\n    send: false\n    model: GPT-5.2 (copilot)\n```\n\nHandoff fields:\n- `label`: Button text displayed to user\n- `agent`: Target agent identifier\n- `prompt`: Pre-filled prompt for target agent\n- `send`: Auto-submit prompt (default: false)\n- `model`: Optional model override for handoff\n\n### Step 5: Create an extension-based chat participant (VS Code only)\n\nFor full control, implement a VS Code extension with a chat participant:\n\n1. **Define the participant** in `package.json`:\n\n```json\n\"contributes\": {\n    \"chatParticipants\": [\n        {\n            \"id\": \"my-extension.my-agent\",\n            \"name\": \"my-agent\",\n            \"fullName\": \"My Agent\",\n            \"description\": \"Short description shown in chat input\",\n            \"isSticky\": false,\n            \"commands\": [\n                {\n                    \"name\": \"explain\",\n                    \"description\": \"Explain the selected code\"\n                }\n            ]\n        }\n    ]\n}\n```\n\n2. **Register and implement the request handler** in `extension.ts`:\n\n```typescript\nexport function activate(context: vscode.ExtensionContext) {\n    const agent = vscode.chat.createChatParticipant('my-extension.my-agent', handler);\n    agent.iconPath = vscode.Uri.joinPath(context.extensionUri, 'icon.png');\n}\n\nconst handler: vscode.ChatRequestHandler = async (\n    request: vscode.ChatRequest,\n    context: vscode.ChatContext,\n    stream: vscode.ChatResponseStream,\n    token: vscode.CancellationToken\n) => {\n    const model = request.model;\n    const messages = [\n        vscode.LanguageModelChatMessage.User(request.prompt)\n    ];\n    const response = await model.sendRequest(messages, {}, token);\n    for await (const fragment of response.text) {\n        stream.markdown(fragment);\n    }\n};\n```\n\n3. **Declare the extension dependency** in `package.json`:\n\n```json\n\"extensionDependencies\": [\"github.copilot-chat\"]\n```\n\n4. **Add tool calling (optional)**\n\nAgents can invoke language model tools registered by other extensions:\n\n```typescript\nconst tools = vscode.lm.tools.filter(tool => tool.tags.includes('my-domain'));\nconst result = await chatUtils.sendChatParticipantRequest(request, context, {\n    prompt: 'You are an expert in <domain>.',\n    tools,\n    responseStreamOptions: { stream, references: true, responseText: true }\n}, token);\nreturn await result.result;\n```\n\n### Step 6: Create a GitHub App (Copilot Extension) for cross-surface availability (optional)\n\nIf the agent should be available on GitHub.com, Visual Studio, JetBrains, and VS Code simultaneously, implement a GitHub App that acts as a Copilot Extension. The app registers a webhook endpoint, receives chat requests, and streams responses back.\n\nKey considerations:\n- The GitHub App must be installed on the user's account or organization\n- Responses are streamed via Server-Sent Events (SSE)\n- Use the [GitHub Copilot Extensions documentation](https://docs.github.com/en/copilot/building-copilot-extensions/about-building-copilot-extensions) for the full integration guide\n- For VS Code-specific features (editor access, file trees, command buttons), prefer an extension-based participant instead\n\n### Step 7: Author the harness evaluation\n\nCreate `eng/harness-evaluation/agents/<agent-id>/eval.yaml` and follow `eng/harness-evaluation/README.md`.\n\n- Declare only the agent file in the eval's root `agent_environment.files`; the experiment removes it from the control.\n- Use realistic stimuli that exercise behavior distinctive to the agent without stating the expected diagnosis or implementation in the prompt.\n- Combine deterministic output checks, a focused semantic rubric, bounded resources, token grading, and a committed scoring threshold.\n- Keep the eval name and directory-derived component ID identical to the agent ID.\n\n### Step 8: Validate\n\nAfter creating or modifying an agent, verify:\n\n- [ ] `name` is lowercase, uses hyphens (no spaces), and is unique\n- [ ] `description` clearly describes what the agent does and when to invoke it\n- [ ] Frontmatter YAML is valid (no syntax errors)\n- [ ] Declarative agent file is in `.github/agents/`\n- [ ] Tools list contains only available tools\n- [ ] Extension-based agent: participant ID matches in `package.json` and `createChatParticipant` call\n- [ ] Agent does not duplicate functionality of built-in agents (`@workspace`, `@vscode`, `@terminal`)\n- [ ] Handoff agent names match existing agents\n- [ ] Agent instructions don't include secrets, tokens, or internal URLs\n- [ ] The paired harness eval targets only this agent and is meant to meaningfully distinguish treatment from control\n\n## Common Pitfalls\n\n| Pitfall | Solution |\n|---------|----------|\n| Agent name conflicts with built-in participants | Use a unique prefix (domain name) |\n| Description is too vague | Include specific keywords users would naturally say |\n| System prompt is too long | Keep instructions to essential behaviors; move reference material to Agent Skills |\n| Agent requires VS Code API but is authored as declarative | Switch to extension-based participant |\n| Using `isSticky: true` unnecessarily | Only set sticky if the agent should persist between turns by default |\n| No `extensionDependencies` on `github.copilot-chat` | Add it; otherwise the contribution point may not be available |\n| Agent invoked as subagent unexpectedly | Set `disable-model-invocation: true` |\n| Subagent appears in the dropdown | Set `user-invocable: false` |\n\n## References\n\n- [VS Code Chat Participant API](https://code.visualstudio.com/api/extension-guides/ai/chat)\n- [VS Code AI Extensibility Overview](https://code.visualstudio.com/api/extension-guides/ai/ai-extensibility-overview)\n- [VS Code Extension Samples – chat-sample](https://github.com/microsoft/vscode-extension-samples/tree/main/chat-sample)\n- [GitHub Copilot Extensions documentation](https://docs.github.com/en/copilot/building-copilot-extensions/about-building-copilot-extensions)\n- [GitHub Copilot Custom agents configuration](https://docs.github.com/en/copilot/reference/custom-agents-configuration)\n- [Agent Skills Specification](https://agentskills.io/specification)\n- Related repository skills: `make-skill` and `make-instructions`\n","frontmatter":{"name":"make-custom-agent","description":"Create, review, or fix custom GitHub Copilot agents. Use when asked to create, scaffold, configure, review, or restrict a custom agent, declarative agent, or @-invokable chat participant for GitHub Copilot."},"isInternal":false,"tokens":2394,"sizeBytes":10648},{"name":"SKILL.md","path":".agents/skills/make-github-actions-workflow/SKILL.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/make-github-actions-workflow/SKILL.md","title":"make-github-actions-workflow","category":"anthropic-skill","format":"markdown","content":"---\nname: make-github-actions-workflow\ndescription: 'Create or modify GitHub Actions workflows for CI, automation, or PR management. Use when asked to create, scaffold, add, extend, or fix a workflow (.yml file under .github/workflows/), including existing pull-request policy and comment automation.'\n---\n\n# Create GitHub Actions Workflow\n\nCreate and configure GitHub Actions workflows that follow this repository's conventions and patterns. Workflows automate tasks like CI validation, PR management, issue labeling, and notifications.\n\n## Repository Conventions\n\nThis repository uses specific patterns across all workflows. Follow these conventions when creating new workflows:\n\n### File Location and Naming\n\n- All workflows live in `.github/workflows/`\n- Use kebab-case names: `label-and-milestone-issues.yml`, `validate-pr-target-branch.yml`\n- Start with a descriptive comment block explaining the workflow's purpose\n\n### Runner\n\n- Use `ubuntu-latest` for general-purpose jobs\n- Use `ubuntu-24.04` when a specific OS version is needed (e.g., copilot setup steps)\n\n### Permissions\n\n- **Always** declare explicit permissions — never rely on defaults\n- Use **minimal permissions**: only request what the workflow needs\n- Common patterns:\n  - Read-only: `permissions: {}`\n  - PR comments: `pull-requests: write`\n  - Issue management: `issues: write`\n  - Code read: `contents: read`\n- For workflows that need write access to PRs from external contributors, use `pull_request_target` instead of `pull_request`\n  - **Security warning:** `pull_request_target` workflows run in the base repository context with its permissions. Do **not** check out or execute code from the PR branch in these workflows. Instead, use the event payload and/or GitHub API (`actions/github-script`, `github.rest.*`, etc.) to inspect and act on the PR safely.\n\n### Scripting\n\n- Use `actions/github-script@v8` for complex logic instead of shell scripts\n- Write JavaScript with `async/await` — the `github` object (Octokit) and `context` are available\n- Use `github.rest.*` for REST API calls and `github.graphql()` for GraphQL queries\n- Access PR/issue data via `context.payload.pull_request`, `context.repo.owner`, `context.repo.repo`\n- Log with `console.log()` for debugging; use `core.setFailed()` for errors\n\n### Error Handling\n\n- Wrap API calls in try/catch blocks\n- Collect errors and report at the end rather than failing on the first error\n- Log skipped operations with a reason\n\n## Workflow\n\n### Step 1: Understand the Requirements\n\nBefore writing the workflow, clarify:\n- [ ] What event(s) should trigger it? (push, pull_request, check_suite, schedule, etc.)\n- [ ] What permissions are needed?\n- [ ] What conditions should gate execution? (author, branch, labels, etc.)\n- [ ] What API calls are needed?\n- [ ] Are there rate limiting or idempotency concerns?\n\n### Step 2: Choose the Trigger Event\n\n| Use case | Event | Notes |\n|----------|-------|-------|\n| PR opened/updated | `pull_request` | Read-only access to PR |\n| PR with write access | `pull_request_target` | Can comment, label, close |\n| PR merged | `pull_request_target: [closed]` | Check `github.event.pull_request.merged == true` |\n| CI checks complete | `check_suite: [completed]` | Filter `app.slug != 'github-actions'` to skip self |\n| Code pushed | `push` | Filter by branches/paths |\n| Manual trigger | `workflow_dispatch` | Add `inputs:` for parameters |\n| Scheduled | `schedule` | Use cron syntax |\n\n### Step 3: Write the Workflow\n\nCreate the YAML file following this template:\n\n```yaml\n# Description of what this workflow does and why.\n\nname: Descriptive Workflow Name\n\non:\n  <trigger_event>:\n    types: [<event_types>]\n\npermissions:\n  <resource>: <read|write>\n\njobs:\n  <job-name>:\n    if: <guard_condition>  # Optional: skip when not needed\n    runs-on: ubuntu-latest\n    steps:\n      - name: Descriptive step name\n        uses: actions/github-script@v8\n        with:\n          script: |\n            // Your logic here\n```\n\n### Step 4: Implement Guard Conditions\n\nAdd conditions to avoid unnecessary runs:\n- Job-level `if:` for event payload checks (e.g., `github.event.check_suite.app.slug != 'github-actions'`)\n- Early `return` in scripts for PR author, draft status, etc.\n- Idempotency checks (e.g., hidden HTML comments as tags to prevent duplicate actions)\n\nFor `pull_request_target` policy workflows that react to `opened`, `edited`, and `reopened`:\n\n- On `edited`, return unless `context.payload.changes?.base` is present; title or body edits must not reapply a target-branch policy.\n- Check permissions for `context.actor`, not only the PR author. A maintainer may edit or reopen an external PR, and that action must use the maintainer's authority.\n- For `opened`, the actor and author are the same, so perform one permission lookup and reuse it for policy and labeling decisions.\n- Exclude automation when either the actor or author is a bot.\n- Encode the prohibited branch class directly (for example, `release/*`) instead of requiring a single allowed branch such as `main`.\n- If permission lookup fails, stop without taking a destructive action; unknown access is not evidence that the contributor is external.\n\n### Step 5: Validate\n\nAfter creating the workflow:\n- [ ] Permissions are minimal and explicitly declared\n- [ ] Uses `actions/github-script@v8` for complex logic\n- [ ] Guard conditions prevent unnecessary runs\n- [ ] API calls handle pagination where needed (use `per_page: 100`)\n- [ ] Error handling doesn't silently swallow failures\n- [ ] No secrets or tokens are hardcoded\n- [ ] Workflow doesn't create infinite loops (e.g., a workflow that triggers itself)\n\n## Existing Workflows in This Repository\n\nStudy these workflows as reference:\n\n| Workflow | Trigger | Purpose |\n|----------|---------|---------|\n| `validate-pr-target-branch.yml` | `pull_request_target: [opened, edited, reopened]` | Closes external PRs targeting release branches, adds community labels |\n| `label-and-milestone-issues.yml` | `pull_request_target: [closed]` | Labels and milestones issues when their fixing PR is merged |\n| `copilot-setup-steps.yml` | `workflow_dispatch`, `push`, `pull_request` | Sets up the development environment for Copilot |\n| `inter-branch-merge-flow.yml` | `push` to `release/**` | Triggers inter-branch merge via arcade |\n\n## Common Patterns\n\n### Commenting on a PR\n\n```javascript\nawait github.rest.issues.createComment({\n  owner: context.repo.owner,\n  repo: context.repo.repo,\n  issue_number: prNumber,\n  body: 'Comment text'\n});\n```\n\n### Checking User Permissions\n\n```javascript\nconst { data: permissions } = await github.rest.repos.getCollaboratorPermissionLevel({\n  owner: context.repo.owner,\n  repo: context.repo.repo,\n  username: context.actor\n});\nconst hasWriteAccess = ['admin', 'write'].includes(permissions.permission);\n```\n\n### Updating Bot-Owned Comments Idempotently\n\nA hidden marker identifies the workflow's comment but does not establish ownership: contributors and other apps can place the same marker in their comments. Match both the marker and the exact `github-actions[bot]` login, then update that comment or create a new one. A generic `user.type === 'Bot'` check does not establish workflow ownership. Preserve the workflow's pinned action SHA and never execute code from a pull-request fork in a `pull_request_target` job.\n\n```javascript\nconst marker = '<!-- validate-pr-target-branch -->';\nconst comments = await github.paginate(github.rest.issues.listComments, {\n  owner: context.repo.owner,\n  repo: context.repo.repo,\n  issue_number: prNumber,\n  per_page: 100\n});\n\nconst body = `${marker}\\nComment text`;\nconst existing = comments.find(comment =>\n  comment.user?.login === 'github-actions[bot]' && comment.body?.includes(marker));\n\nif (existing) {\n  await github.rest.issues.updateComment({\n    owner: context.repo.owner,\n    repo: context.repo.repo,\n    comment_id: existing.id,\n    body\n  });\n} else {\n  await github.rest.issues.createComment({\n    owner: context.repo.owner,\n    repo: context.repo.repo,\n    issue_number: prNumber,\n    body\n  });\n}\n```\n\n### Reading Repository Files at a Specific Commit\n\n```javascript\nconst { data: fileData } = await github.rest.repos.getContent({\n  owner, repo,\n  path: 'eng/Versions.props',\n  ref: commitSha\n});\nconst content = Buffer.from(fileData.content, 'base64').toString('utf-8');\n```\n\n## References\n\n- [GitHub Actions documentation](https://docs.github.com/en/actions)\n- [Workflow syntax](https://docs.github.com/en/actions/using-workflows/workflow-syntax-for-github-actions)\n- [Events that trigger workflows](https://docs.github.com/en/actions/using-workflows/events-that-trigger-workflows)\n- [actions/github-script](https://github.com/actions/github-script)\n","frontmatter":{"name":"make-github-actions-workflow","description":"Create or modify GitHub Actions workflows for CI, automation, or PR management. Use when asked to create, scaffold, add, extend, or fix a workflow (.yml file under .github/workflows/), including existing pull-request policy and comment automation."},"isInternal":false,"tokens":1992,"sizeBytes":8721},{"name":"SKILL.md","path":".agents/skills/make-instructions/SKILL.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/make-instructions/SKILL.md","title":"make-instructions","category":"anthropic-skill","format":"markdown","content":"---\nname: make-instructions\ndescription: 'Create and evaluate VS Code file-based instructions (.instructions.md files). Use when asked to create, scaffold, or add file-based instructions for Copilot. Generates scoped instructions and a paired Vally harness eval.'\n---\n\n# Create File-Based Instructions\n\nThis skill helps you scaffold VS Code file-based instructions (`.instructions.md` files) that provide background knowledge to Copilot about specific parts of the codebase. These files are applied automatically based on glob patterns or semantic matching, giving Copilot domain-specific context when working on matching files.\n\n## When Not to Use\n\n- Setting project-wide instructions — use `.github/copilot-instructions.md` or `AGENTS.md` instead\n- Creating reusable agent workflows with structured steps — use Agent Skills instead\n- Adding instructions that need to be invokable on demand — use Agent Skills instead\n\n## Workflow\n\n### Step 1: Investigate the topic\n\nBuild understanding of the area the instructions should cover. Identify:\n\n- [ ] What files or file patterns the instructions apply to\n- [ ] Key conventions, patterns, or architectural rules for that area\n- [ ] Common pitfalls that Copilot should avoid\n- [ ] Non-obvious domain knowledge that isn't discoverable from code alone\n\nRead the repository-wide instruction files that apply to the same paths and make an explicit exclusion list. Do not repeat those rules in the new file, even when they are relevant examples for the scoped area; include only guidance that becomes more specific or materially different at the narrower scope.\n\nIf the scope is unclear or overlaps with existing instructions, ask the user for clarification.\n\n### Step 2: Choose the file location\n\nInstructions files go in `.github/instructions/` by default. Pick a descriptive filename:\n\n```\n.github/instructions/<topic>.instructions.md\n```\n\nExamples: `csharp-style.instructions.md`, `query-pipeline.instructions.md`, `test-conventions.instructions.md`\n\n### Step 3: Generate the file with YAML frontmatter\n\nCreate the file with the required YAML frontmatter header:\n\n```yaml\n---\nname: '<Display Name>'              # Optional. Display name in the UI. Defaults to filename.\ndescription: '<Short description>'  # Optional. Shown on hover. Also used for semantic matching.\napplyTo: '<glob pattern>'           # Optional. Glob pattern relative to workspace root. Omit to require manual attachment or rely on semantic matching only.\n---\n```\n\nCommon `applyTo` patterns:\n\n- `**/*.cs` — all C# files\n- `test/**` — files under a specific folder\n\n### Step 4: Write the body content\n\nWrite concise, actionable Markdown content. Follow these principles:\n\n- **Be concise** — instructions share the context window; only include what the agent wouldn't already know\n- **Be specific** — use concrete rules, not vague guidance\n- **Include examples** — short code snippets showing preferred vs. avoided patterns are very effective\n- **Explain why** — when a rule exists for a non-obvious reason, state it so the agent applies it correctly in edge cases\n- **Skip linter-enforced rules** — don't repeat what formatters and linters already catch\n- **Use Markdown links** to reference specific files or URLs for additional context\n\nRecommended sections (adapt as needed):\n\n1. **<Title>** — one-line heading describing the domain\n2. **Context paragraph** — brief explanation of what this area is and why these rules matter\n3. **Guidelines / Conventions** — bullet list of concrete rules\n4. **Examples** — short code blocks showing do/don't patterns (optional)\n5. **Key Files** — table of important files for orientation (optional)\n6. **Common Pitfalls** — traps to avoid (optional)\n\n### Step 5: Author and validate the harness evaluation\n\nCreate `eng/harness-evaluation/instructions/<id>/eval.yaml`, where `<id>` is the instruction path relative to `.github/instructions/` with its suffix removed and nested path separators replaced by `--`.\n\nFollow the authoring and validation rules in `eng/harness-evaluation/README.md`. Exercise guidance distinctive to the instruction and ensure the treatment meaningfully outperforms the omitted-instruction control.\n\nFor initial authoring, produce and lint the requested instruction and eval before running behavioral comparisons.\n\nAfter creating the file, verify:\n\n- [ ] File is in `.github/instructions/` (or a configured instructions folder)\n- [ ] Filename ends with `.instructions.md` and only contains lowercase letters, numbers, and hyphens\n- [ ] YAML frontmatter is valid\n- [ ] `applyTo` glob matches the intended files\n- [ ] Content is concise (aim for under 500 lines or 5000 tokens) — long instructions dilute effectiveness\n- [ ] No secrets, tokens, or internal URLs included\n- [ ] Instructions don't duplicate what's already in `.github/copilot-instructions.md` or under `.agents/skills/`\n- [ ] The paired eval demonstrates behavior that the omitted-instruction control does not provide reliably\n\n## Common Pitfalls\n\n| Pitfall | Solution |\n|---------|----------|\n| `applyTo` too broad | Use specific globs; `**` applies to every file and wastes context |\n| Missing `applyTo` | Without it, instructions won't auto-apply — they require manual attachment or semantic matching via `description` |\n| Vague guidance | Replace \"write good tests\" with something like \"add both positive and negative test cases using `[ConditionalFact]` methods\" |\n","frontmatter":{"name":"make-instructions","description":"Create and evaluate VS Code file-based instructions (.instructions.md files). Use when asked to create, scaffold, or add file-based instructions for Copilot. Generates scoped instructions and a paired Vally harness eval."},"isInternal":false,"tokens":1145,"sizeBytes":5444},{"name":"SKILL.md","path":".agents/skills/make-skill/SKILL.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/make-skill/SKILL.md","title":"make-skill","category":"anthropic-skill","format":"markdown","content":"---\nname: make-skill\ndescription: 'Create, review, or fix Agent Skills for GitHub Copilot. Use when asked to create, scaffold, improve, or repair a SKILL.md and its paired harness evaluation.'\n---\n\n# Create Or Fix A Skill\n\nProduce concise, stable task guidance that adds knowledge an agent cannot reliably infer from source alone, together with a paired evaluation that proves the guidance changes behavior.\n\n## Choose The Right Primitive\n\n- Use a skill for a task-specific workflow or body of knowledge loaded on demand.\n- Use file instructions for background guidance scoped to paths.\n- Use a custom agent when context isolation or distinct tool restrictions are required.\n- Prefer an existing skill over creating an overlapping one.\n\n## Workflow\n\n1. Read the relevant implementation, tests, repository instructions, and neighboring customizations.\n2. Identify repeated mistakes or non-obvious invariants. Do not turn source inventories, line counts, or facts easily rediscovered from code into skill content.\n3. Create `.agents/skills/<name>/SKILL.md`. The frontmatter `name` must exactly match the directory; the description must state what the skill does and when natural user requests should trigger it.\n4. Mark background domain guidance `user-invocable: false`. Keep user-invocable workflows focused on an outcome a user would deliberately request.\n5. Write actionable guidance with observable validation. Explain why edge cases matter; avoid generic engineering advice already present in repository instructions.\n6. Create `eng/harness-evaluation/skills/<name>/eval.yaml` and follow `eng/harness-evaluation/README.md`.\n7. Lint the customization and inspect both control and treatment artifacts before accepting it.\n\n## Paired Evaluation\n\n- The eval root `agent_environment.skills` contains only the target skill. Stimulus inputs belong under each stimulus's `agent_environment.files`.\n- The runner removes the root skill for control and separately verifies treatment activation. Do not add a `skill-invocation` grader and do not tell the agent to invoke the skill in the shared prompt.\n- Prompts may identify fixtures, proposed code, fixed IDs, and output paths, but must not reveal the expected diagnosis, owning mechanism, or regression-test design.\n- Stage self-contained source snapshots rather than diffs or commit references; fixture context must not require fetching a repository revision.\n- Use deterministic graders for observable artifacts, a narrow semantic rubric for behavior, and a `token-budget` grader. Define bounded turns, tokens, and duration plus a committed scoring threshold.\n- The task must exercise guidance distinctive to the skill. A control that consistently matches treatment means the skill or eval is not useful enough.\n\n## Validation\n\n- Frontmatter parses and the name matches the directory.\n- The skill is concise, stable, and does not duplicate root or scoped instructions.\n- File references are relative and exist.\n- Validation steps are observable and task-specific.\n- The paired eval targets only the skill, has complete bounded grading, and uses a solution-neutral prompt.\n- `npm run lint` and the harness inventory tests pass.\n\n## Common Pitfalls\n\n| Pitfall | Correction |\n|---|---|\n| Copying implementation inventories into the skill | Keep only non-obvious invariants and routing decisions |\n| Exact line counts or volatile metrics | Remove them; point to stable symbols or behavior |\n| Generic test-folder guidance | Describe the distinctive test shape or omit it |\n| Eval prompt tells the agent what to find | Move expected facts into the hidden rubric |\n| Eval root contains repository fixtures | Keep only the target skill at root; stage fixtures per stimulus |\n| Prompt instructs skill invocation | Let the treatment-only runner gate enforce activation |\n| Initial scaffold launches multi-model review | First produce and lint the requested artifacts; run expensive behavioral validation separately |","frontmatter":{"name":"make-skill","description":"Create, review, or fix Agent Skills for GitHub Copilot. Use when asked to create, scaffold, improve, or repair a SKILL.md and its paired harness evaluation."},"isInternal":false,"tokens":767,"sizeBytes":3954},{"name":"SKILL.md","path":".agents/skills/migrations/SKILL.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/migrations/SKILL.md","title":"migrations","category":"anthropic-skill","format":"markdown","content":"---\nname: migrations\ndescription: 'Implementation details for EF Core migrations. Use when changing MigrationsSqlGenerator, model diffing, migration operations, HistoryRepository, the Migrator or related classes.'\nuser-invocable: false\n---\n\n# Migrations\n\n## Pipeline\n\n**Add migration**: `MigrationsScaffolder.ScaffoldMigration()` → `MigrationsModelDiffer.GetDifferences()` → list of `MigrationOperation` → `CSharpMigrationsGenerator` and `CSharpSnapshotGenerator` produce Up/Down/Snapshot code\n\n**Apply migration**: `Migrator.MigrateAsync()` → reads `__EFMigrationsHistory` → per pending: `MigrationsSqlGenerator.Generate(operations)` → `MigrationCommandExecutor` executes\n\n## Model Snapshot\n\n- Model snapshots use `typeof(Dictionary<string, object>)` (property bag format), not the actual CLR type. When examining the `ClrType` in a snapshot, don't assume it matches the real entity type.\n- `SnapshotModelProcessor.Process()` is used at design-time to fixup older model snapshots for backward compatibility.\n- `MigrationsModelDiffer` uses provider-agnostic structural comparison between relational models to determine what migration operations are necessary.\n\nFor an upgrade-only regression, derive a concrete old `ModelSnapshot`, process its model with `SnapshotModelProcessor.Process(..., resetVersion: true)`, and compare it with the equivalent current design-time model through `MigrationsModelDiffer.GetDifferences()`. Preserve the property-bag CLR types emitted by old snapshots and omit APIs that would explicitly configure metadata that was absent in that version. The regression succeeds only when the resulting operation list is empty.\n\nLegacy snapshot normalization belongs in `SnapshotModelProcessor`, not in runtime migration application. Scope a compatibility branch to the exact released versions that could emit the affected snapshot shape; versions from before the feature existed should not be included merely because they are numerically older. Prefer the mutable metadata interface when it exposes the required setter rather than casting to a concrete metadata implementation. Do not use a missing configuration source as the test for missing historical snapshot metadata: old snapshots may already configure a value using the current default. For metadata whose semantics changed, use the snapshot's product version to restore the old invariant. Add focused coverage for every version family named by the gate, plus the first unaffected version.\n\n## Testing\n\nMigration operation tests: `test/EFCore.Relational.Tests/Migrations/`. Functional tests: `test/EFCore.{Provider}.FunctionalTests/Migrations/`. Model differ tests: `test/EFCore.Relational.Tests/Migrations/Internal/MigrationsModelDifferTest*.cs`.\n\nTo simulate a snapshot model use `ModelBuilder` calls without conventions.","frontmatter":{"name":"migrations","description":"Implementation details for EF Core migrations. Use when changing MigrationsSqlGenerator, model diffing, migration operations, HistoryRepository, the Migrator or related classes.","user-invocable":false},"isInternal":false,"tokens":548,"sizeBytes":2813},{"name":"SKILL.md","path":".agents/skills/model-building/SKILL.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/model-building/SKILL.md","title":"model-building","category":"anthropic-skill","format":"markdown","content":"---\nname: model-building\ndescription: 'Implementation details for EF Core model building. Use when changing ConventionSet, ModelBuilder, IConvention implementations, ModelRuntimeInitializer, RuntimeModel, or related classes.'\nuser-invocable: false\n---\n\n# Model Building, Conventions & Initialization\n\nCovers model construction (conventions, fluent API, metadata hierarchy) and model initialization (runtime annotation propagation, compiled model filtering).\n\n## Convention System\n\n`ConventionSet` (`src/EFCore/Metadata/Conventions/ConventionSet.cs`) holds `List<I*Convention>` for every metadata event. Key conventions in `src/EFCore/Metadata/Conventions/`:\n\n- `DbSetFindingConvention` — discovers entities from `DbSet<T>`\n- `PropertyDiscoveryConvention` — discovers properties from CLR types\n- `KeyDiscoveryConvention` — finds PKs (`Id`, `TypeId`)\n- `RelationshipDiscoveryConvention` — infers FKs from navigations\n- `RuntimeModelConvention` — creates optimized `RuntimeModel` from mutable model\n\nOverride `ConfigureConventions(ModelConfigurationBuilder)` to add/remove conventions.\n\nConvention fixes must preserve dispatcher behavior and ambiguity information. For inverse-navigation attributes, do not solve recursion by permanently ignoring an ambiguous navigation: removing one candidate can make another ambiguity appear unique and configure the wrong relationship. `InversePropertyAttributeConvention` records inverse candidates and uses `AddInverseNavigation`, `TryRemoveIfAmbiguous`, and `FindAmbiguousInverse` while still allowing convention processing to continue.\n\nTest the state transitions, not only the initially ambiguous model: first verify that multiple interacting candidates configure no relationship; then genuinely remove ambiguity both by ignoring/removing one competing navigation and by removing a competing entity type, and verify that the remaining inverse relationship is configured. These cases distinguish candidate bookkeeping from a permanent-ignore workaround.\n\n## Metadata Interface Hierarchy\n\n`IReadOnly*` → `IMutable*` → `IConvention*` → `IRuntime*`\n\nApplies to: Model, EntityType, Property, Key, ForeignKey, Navigation, Index, etc. Builders follow: `*Builder` → `IConvention*Builder`.\n\n## Adding A Configurable Metadata Facet\n\nFollow the nearest existing facet end to end rather than stopping at the public interface:\n\n1. Add the read-only, mutable, and convention metadata contracts, concrete storage, default, configuration source, convention setter, and builder precedence checks. Preserve the facet when metadata is replaced or a relationship is rebuilt.\n2. If changes are observable to conventions, add the convention interface, every `ConventionSet` add/replace/remove path, and immediate plus delayed dispatcher scopes and nodes.\n3. Carry the value into the optimized runtime metadata through `RuntimeModelConvention`, runtime constructors/builders, and `CSharpRuntimeModelCodeGenerator` so compiled models preserve it.\n4. If snapshots persist the facet, update the fluent builder API and `CSharpSnapshotGenerator`; keep the old absence equivalent to the historical default.\n5. Update public API baselines and cover configuration-source precedence, convention dispatch, runtime/compiled model propagation, and snapshot round trips.\n\n## Model Lifecycle\n\n1. **Mutable Model** — built by `ModelBuilder` during `OnModelCreating`, made read-only by `FinalizeModel()`\n2. **Design-Time Model** — finalized read-only `Model` that also contains design-time-only annotations used in migrations\n3. **Runtime Model** — an optimized read-only model created by `RuntimeModelConvention.ProcessModelFinalized()`, does not contain design-time-only annotations\n\n`ModelRuntimeInitializer.Initialize()` (called by `DbContextServices.CreateModel()`):\n\n```\nInitialize(model, designTime, validationLogger)\n├─ FinalizeModel() if mutable\n├─ Set ModelDependencies, InitializeModel\n└─ RuntimeModelConvention creates RuntimeModel, copies/filters annotations\n```\n\n## Complex Type Property Recursion\n\nWhen processing properties in conventions or validation, remember that complex types can contain their own declared properties. Use `GetFlattenedProperties()` to iterate all properties (including on nested non-collection complex types) or manually recurse through `GetDeclaredComplexProperties()` → `complexProperty.ComplexType`.\n\n## Adding a New Annotation\n\n1. Add constant to `CoreAnnotationNames` and its `AllNames`\n2. Filter in `RuntimeModelConvention.ProcessModelAnnotations` if it's a design-time-only annotation (only used in migration operations)\n   1. If it was filtered out, add logic to the getters that throws an exception if accessed on the runtime model\n3. Filter in `CSharpRuntimeAnnotationCodeGenerator.Generate` if it can be computed lazily at runtime (e.g. based on other annotations)\n4. Propagate in `RelationalAnnotationProvider` if used in up-migrations or the relational model and `IMigrationsAnnotationProvider` if used in down-migrations\n\n## Relational Model\n\n`RelationalModel` (`src/EFCore.Relational/Metadata/Internal/RelationalModel.cs`) is a database-centric view of the EF model, mapping entity types to physical database objects: `Tables`, `Views`, `Functions`, `Queries`, and `DefaultTables`. `DefaultTables` are pseudo-table objects only used for `FromSql` queries.\n\nCreated lazily by `RelationalModelRuntimeInitializer`, accessed via `model.GetRelationalModel()`. Used by migrations (`MigrationsModelDiffer`), update and query pipelines.\n\n`RelationalAnnotationProvider` populates annotations on relational model elements. Provider subclasses (e.g., `SqlServerAnnotationProvider`) add provider-specific annotations. `IMigrationsAnnotationProvider` controls annotations used in down-migration operations.\n\n## Model Validation\n\n`ModelValidator` (`src/EFCore/Infrastructure/ModelValidator.cs`) and `RelationalModelValidator` (`src/EFCore.Relational/Infrastructure/RelationalModelValidator.cs`) run after model finalization, during `ModelRuntimeInitializer.Initialize()` between the pre- and post-validation `InitializeModel` calls.\n\n## Migration Snapshot Compatibility\n\nModel-building changes can trigger spurious migrations for users who upgrade. Two causes:\n\n1. **New metadata written to the snapshot** — old snapshots won't have it; `MigrationsModelDiffer` sees a diff. Fix: ensure absence of the annotation in an old snapshot is treated as the old default.\n2. **Annotation renamed or reinterpreted** — old snapshots produce a different model. Fix: keep backward-compatible reading logic.\n\nInspect `CSharpSnapshotGenerator` (what gets written) and `MigrationsModelDiffer` (how absence is handled). Add a snapshot round-trip test in `test/EFCore.Design.Tests/Migrations/ModelSnapshotSqlServerTest.cs`.\n\n## Testing\n\n| Area | Location |\n|------|----------|\n| Convention unit tests | `test/EFCore.Tests/Metadata/Conventions/` |\n| Metadata unit tests | `test/EFCore.Tests/Metadata/Internal/` |\n| Model builder API tests | `test/EFCore.Specification.Tests/ModelBuilding/ModelBuilderTest*.cs` |\n| Relationship discovery tests | `test/EFCore.Specification.Tests/ModelBuilding101*.cs` |\n| Model validation tests | `test/EFCore.Tests/Infrastructure/ModelValidatorTest*.cs` |\n| Compiled model tests | `test/EFCore.Specification.Tests/Scaffolding/CompiledModelTestBase.cs` |\n\n## Validation\n\n- Model builds without `InvalidOperationException` during finalization\n- All new API is covered by tests\n- Compiled model baselines update cleanly with `EF_TEST_REWRITE_BASELINES=1`\n- `ToString()` on metadata objects shows concise contents without throwing exceptions\n- No spurious migration is generated against a project with an existing snapshot","frontmatter":{"name":"model-building","description":"Implementation details for EF Core model building. Use when changing ConventionSet, ModelBuilder, IConvention implementations, ModelRuntimeInitializer, RuntimeModel, or related classes.","user-invocable":false},"isInternal":false,"tokens":1568,"sizeBytes":7715},{"name":"SKILL.md","path":".agents/skills/query-pipeline/SKILL.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/query-pipeline/SKILL.md","title":"query-pipeline","category":"anthropic-skill","format":"markdown","content":"---\nname: query-pipeline\ndescription: 'Implement and review EF Core query translation, projection visitors, split-query enumeration, and query regression tests. Use when changing query-pipeline code or choosing specification and provider coverage for a query regression.'\nuser-invocable: false\n---\n\n# Query Pipeline\n\n## Regression Test Ownership\n\n- Group query specification tests by a cohesive query or model trait. Do not create a generic bucket merely because tests use custom models; use the existing trait-specific hierarchy, such as owned-entity queries.\n- Inspect the specification base and provider overrides before placing a regression. Keep the LINQ query, model setup, and result assertions in the shared virtual test; provider overrides call the base and add only provider-specific baselines or established limitations.\n- A provider-only test can leave every other provider untested even when its SQL assertion is correct. Preserve override guards without adding a guard that forces unrelated redundant overrides.\n- For an optimization, cover both eligible and rejected shapes with exact result assertions in sync and async. Supply a concrete provider override and SQL baseline or established limitation; an abstract test base or expression-shape check alone does not prove execution coverage.\n\n## Translation\n\n- Translation fallback must distinguish established unsupported shapes from unexpected defects. Do not turn arbitrary exceptions into a successful fallback.\n- Check whether a failed rewrite mutated state that fallback will reuse. For test coordination, establish the actual collection, assembly, and async-flow boundaries before claiming shared static state can race; theory rows are not inherently parallel, and reset in `finally` is not mutual exclusion.\n\n## Optimizations\n\n- Match the equivalence needed by the rewrite, not blindly by expression equality.\n- Preserve context-specific null semantics. SQL UNKNOWN can be filtered like `false` in a predicate but not in a projected value or under negation; `UseRelationalNulls`, null-containing `IN`/`NOT IN`, and scalar versus composite LINQ join keys require different compensation.\n- Preserve cardinality and operator order, not just matching rows. Moving predicates across outer joins, adding keys under `Distinct`/`GroupBy`, or converting correlated APPLY to JOIN can change results; per-parent pagination must retain its partitioning and ordering, and remaining outer references must prevent decorrelation.\n- Share repeated subqueries only when their evaluation and row selection are equivalent. Volatile expressions, query filters introduced during later navigation expansion, and required-navigation joins can change evaluation count or which row survives a limit. Check determinism and row preservation before reuse, and collect candidates within their own lambda scope.\n- Preserve SQL typing and CLR result semantics separately. Remove a cast only when its store-type effect is redundant; casts on constants can establish necessary SQL typing. SQL nullable columns do not alone describe shaper nullability: `DefaultIfEmpty` on a non-nullable scalar may require `COALESCE` to its CLR default.\n- Remap dependent state when changing query shape. Subquery pushdown or join replacement must update scoped column references, predicates, orderings, projection bindings, and shapers; retain or recompute identifiers and their comparers when multiplicity or null extension changes.\n- Prove pruning safety beyond the final projection. An unused join can still filter or multiply rows, so honor explicit prunability and references from other clauses. Unreferenced columns can still define distinct/set-operation membership or a scalar subquery's result; preserve those contracts and compatible set-operation projections.\n\n## Split Queries\n\n- When changing `SplitQueryResultCoordinator`, check both `SplitQueryingEnumerable` and `GroupBySplitQueryingEnumerable`, including their synchronous and asynchronous paths. End-of-stream validation belongs at true outer-stream exhaustion, not at a group boundary or early disposal.\n- A grouped reader can reach physical EOF while assembling a final group that still must be yielded. Test that successful move separately from the subsequent terminal move, including verification failure and repeated terminal calls; cleanup must preserve the original failure.\n- Account for internal buffering as well as caller materialization when assessing memory use. Earlier split-query result sets may need buffering when the provider cannot keep multiple readers active; retrying execution strategies can also require buffering.\n- Buffering does not give separate query commands a consistent database snapshot. Concurrent writes between commands can produce an inconsistent result graph; consider snapshot or serializable transactions when consistency is required, accounting for provider support and transaction costs.\n- Prove cross-command consistency with a writer transaction and an explicit barrier between reads, not sleeps or a prose-only scenario. Assert a root/child value combination, not just matching keys; state the isolation and retry-strategy boundaries of the test.\n\n## Validation\n\n- `ToQueryString()` shows generated SQL without executing\n- `ExpressionPrinter` dumps expression trees at any pipeline stage\n- SQL baselines verified via `AssertSql()` in provider functional tests and the generated SQL corresponds to the LINQ query in the base method\n","frontmatter":{"name":"query-pipeline","description":"Implement and review EF Core query translation, projection visitors, split-query enumeration, and query regression tests. Use when changing query-pipeline code or choosing specification and provider coverage for a query regression.","user-invocable":false},"isInternal":false,"tokens":982,"sizeBytes":5467},{"name":"SKILL.md","path":".agents/skills/run-apichief/SKILL.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/run-apichief/SKILL.md","title":"run-apichief","category":"anthropic-skill","format":"markdown","content":"---\nname: run-apichief\ndescription: 'Run ApiChief in the EF Core repo to emit baselines, summaries, deltas, review files, or breaking-change checks. Use when refreshing `*.baseline.json`, preparing API review artifacts, or validating API changes.'\nuser-invocable: false\n---\n\n# Run ApiChief\n\nUse the ApiChief tool documented at `eng/Tools/ApiChief/README.md` to inspect or refresh EF Core public API baselines for projects under `src/`.\n\nApiChief can run against either a compiled assembly or a previously emitted baseline JSON file. Prefer the repo-local `.dotnet` SDK and the checked-in build scripts in this repo.\n\n## Commands\n\n| Command | Description | Extra arguments |\n| --- | --- | --- |\n| `emit baseline` | Emit a JSON API baseline | `-o <file>` |\n| `emit summary` | Emit a human-readable API summary | `-o <file>`, `-x` |\n| `emit review` | Emit API review files | `-o <dir>`, `-n` |\n| `emit delta` | Emit a delta against an existing baseline, or markdown diff review files | `<baseline-path>`, `-o <file-or-dir>`, `--diff` |\n| `check breaking` | Fail if breaking changes exist vs. a baseline | `<baseline-path>` |\n\nDefault to `emit baseline` if the user only asks to \"run ApiChief\".\n\n## Workflow\n\n### 1. Identify the target project(s)\n\n- Match user intent against project folders under `src/`.\n- Ask for clarification only if the target is ambiguous.\n- The checked-in baseline path convention in this repo is `src/<ProjectName>/<ProjectName>.baseline.json`.\n- If asked just to update the baselines, run EFCore.ApiBaseline.Tests tests and skip the rest of the steps below.\n\n### 2. Prepare the environment\n\nAlways initialize the repo environment before building or running the tool:\n\n```powershell\n.\\restore.cmd\n. .\\activate.ps1\ndotnet build .\\eng\\Tools\\ApiChief\\ApiChief.csproj --nologo --verbosity q\n```\n\nOn Bash:\n\n```bash\n./restore.sh\n. ./activate.sh\ndotnet build ./eng/Tools/ApiChief/ApiChief.csproj --nologo --verbosity q\n```\n\n### 3. Ensure the target binaries exist\n\nApiChief operates on built assemblies. If the target project has not been built yet, build it first.\n\nPreferred options:\n\n```powershell\n# Refreshes checked-in baselines after the normal build\n.\\build.cmd -c Debug\n\n# Or build a single project when working narrowly\ndotnet build .\\src\\<ProjectName>\\<ProjectName>.csproj --nologo --verbosity q\n```\n\nUse the highest available `net*` TFM under `artifacts/bin/<ProjectName>/<Configuration>/` by default. Avoid `netstandard*` and `net4*` targets unless the user explicitly asks for them.\n\n### 4. Locate the built ApiChief binary and target assembly\n\n```powershell\n$dotnet = \".\\\\.dotnet\\\\dotnet\"\n$apiChiefProject = \".\\\\eng\\\\Tools\\\\ApiChief\\\\ApiChief.csproj\"\n$apiChief = (& $dotnet msbuild $apiChiefProject --getProperty:TargetPath -p:Configuration=Debug --nologo).Trim()\n\n$name = \"<ProjectName>\"\n$tfm = Get-ChildItem \".\\\\artifacts\\\\bin\\\\$name\\\\Debug\" -Directory |\n    Where-Object { $_.Name -match '^net\\d+\\.\\d+$' } |\n    Sort-Object { [version]($_.Name -replace '^net', '') } -Descending |\n    Select-Object -First 1 -ExpandProperty Name\n\n$assemblyName = (& $dotnet msbuild \".\\\\src\\\\$name\\\\$name.csproj\" --getProperty:AssemblyName -p:Configuration=Debug --nologo).Trim()\nif ([string]::IsNullOrWhiteSpace($assemblyName))\n{\n    $assemblyName = $name\n}\n\n$assemblyPath = \".\\\\artifacts\\\\bin\\\\$name\\\\Debug\\\\$tfm\\\\$assemblyName.dll\"\n```\n\nBefore running, report the selected TFM if it matters for the task.\n\n### 5. Run the requested ApiChief command\n\n```powershell\n# Emit a baseline\n& $dotnet $apiChief $assemblyPath emit baseline -o \".\\\\src\\\\$name\\\\$name.baseline.json\"\n\n# Emit a summary\n& $dotnet $apiChief $assemblyPath emit summary\n\n# Emit a delta\n& $dotnet $apiChief $assemblyPath emit delta \".\\\\src\\\\$name\\\\$name.baseline.json\" -o \".\\\\artifacts\\\\tmp\\\\$name.delta.json\"\n\n# Check for breaking changes\n& $dotnet $apiChief $assemblyPath check breaking \".\\\\src\\\\$name\\\\$name.baseline.json\"\n\n# Emit API review artifacts\n& $dotnet $apiChief $assemblyPath emit review -o \".\\\\artifacts\\\\tmp\\\\API.$name\"\n\n# Emit GitHub-friendly markdown diff files against a baseline\n& $dotnet $apiChief $assemblyPath emit delta \".\\\\src\\\\$name\\\\$name.baseline.json\" --diff -o \".\\\\artifacts\\\\tmp\\\\API.$name.Diff\"\n```\n\n`emit delta` also supports passing a `.json` file as the current input instead of a DLL.\n\n### 6. Review or clean up baseline changes\n\nAfter `emit baseline`:\n\n- preserve the original BOM and trailing newline behavior of the committed file\n- revert version-only diffs in the `\"Name\"` field\n- inspect removed `//` instruction comments in previous baselines and carry forward any still-needed manual edits\n- if those comments reference GitHub issues, check whether the underlying issue is still open before reapplying the workaround\n\n### 7. Report results clearly\n\n- list the processed project(s)\n- show the chosen TFM(s)\n- report the output path(s)\n- for `check breaking`, state pass/fail\n- for `emit delta` and `emit delta --diff`, mention that exit code `0` means changes, `2` means no changes, and `-1` means an error\n- prefer `emit delta --diff` output because it generates ready-to-post ```diff fenced markdown split across per-type `.md` files\n","frontmatter":{"name":"run-apichief","description":"Run ApiChief in the EF Core repo to emit baselines, summaries, deltas, review files, or breaking-change checks. Use when refreshing `*.baseline.json`, preparing API review artifacts, or validating API changes.","user-invocable":false},"isInternal":false,"tokens":1325,"sizeBytes":5157},{"name":"SKILL.md","path":".agents/skills/scaffolding/SKILL.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/scaffolding/SKILL.md","title":"scaffolding","category":"anthropic-skill","format":"markdown","content":"---\nname: scaffolding\ndescription: 'Implementation details for EF Core scaffolding (reverse engineering). Use when changing ef dbcontext scaffold pipeline implementation, database schema reading, CSharpModelGenerator, or related classes.'\nuser-invocable: false\n---\n\n# Scaffolding\n\nGenerates C# code from database schemas (reverse engineering).\n\n## When Not to Use\n\n- Working on compiled model generation (`dotnet ef dbcontext optimize`)\n\n## Reverse Engineering\n\nPipeline: `IDatabaseModelFactory` (reads schema) → `IScaffoldingModelFactory` (builds EF model) → `IModelCodeGenerator` (generates C#)\n- `IReverseEngineerScaffolder` — orchestrates full pipeline\n\n## Schema Query Compatibility\n\nProvider schema readers often query one-to-many metadata tables. Preserve anti-semi semantics when adapting SQL for a limited engine: a `LEFT JOIN` containing the complete excluded-property predicate in `ON`, followed by a null filter on a non-nullable joined key, is equivalent to `NOT EXISTS`. Unrelated metadata rows do not join; any matching excluded row makes the joined key non-null and excludes the object. Do not move parts of the excluded-property predicate to `WHERE` or join all metadata rows and filter individual rows afterward. An equivalent non-correlated anti-set form, such as `NOT IN (SELECT key ... WHERE excluded-condition)`, also works when the subquery cannot return null keys. Cover objects with no metadata, unrelated metadata only, the excluded property only, and both excluded and unrelated properties.\n","frontmatter":{"name":"scaffolding","description":"Implementation details for EF Core scaffolding (reverse engineering). Use when changing ef dbcontext scaffold pipeline implementation, database schema reading, CSharpModelGenerator, or related classes.","user-invocable":false},"isInternal":false,"tokens":315,"sizeBytes":1524},{"name":"SKILL.md","path":".agents/skills/servicing-pr/SKILL.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/servicing-pr/SKILL.md","title":"servicing-pr","category":"anthropic-skill","format":"markdown","content":"# servicing-pr\n\nPath: `.agents/skills/servicing-pr/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/servicing-pr/SKILL.md)","tokens":300,"sizeBytes":181},{"name":"SKILL.md","path":".agents/skills/sqlite-adonet/SKILL.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/sqlite-adonet/SKILL.md","title":"sqlite-adonet","category":"anthropic-skill","format":"markdown","content":"# sqlite-adonet\n\nPath: `.agents/skills/sqlite-adonet/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/sqlite-adonet/SKILL.md)","tokens":300,"sizeBytes":184},{"name":"SKILL.md","path":".agents/skills/tooling/SKILL.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/tooling/SKILL.md","title":"tooling","category":"anthropic-skill","format":"markdown","content":"# tooling\n\nPath: `.agents/skills/tooling/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/tooling/SKILL.md)","tokens":300,"sizeBytes":166},{"name":"SKILL.md","path":".agents/skills/triage/SKILL.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/triage/SKILL.md","title":"triage","category":"anthropic-skill","format":"markdown","content":"# triage\n\nPath: `.agents/skills/triage/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/triage/SKILL.md)","tokens":300,"sizeBytes":163},{"name":"SKILL.md","path":".agents/skills/update-pipeline/SKILL.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/update-pipeline/SKILL.md","title":"update-pipeline","category":"anthropic-skill","format":"markdown","content":"# update-pipeline\n\nPath: `.agents/skills/update-pipeline/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/update-pipeline/SKILL.md)","tokens":300,"sizeBytes":190},{"name":"SKILL.md","path":".github/skills/agentic-workflows/SKILL.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/.github/skills/agentic-workflows/SKILL.md","title":"agentic-workflows","category":"anthropic-skill","format":"markdown","content":"# agentic-workflows\n\nPath: `.github/skills/agentic-workflows/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.github/skills/agentic-workflows/SKILL.md)","tokens":300,"sizeBytes":196},{"name":"eval.yaml","path":"eng/harness-evaluation/skills/change-tracking/eval.yaml","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/change-tracking/eval.yaml","title":"Change-tracking Skill","category":"anthropic-skill","format":"yaml","content":"# Change-tracking Skill\n\nPath: `eng/harness-evaluation/skills/change-tracking/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/change-tracking/eval.yaml)","tokens":300,"sizeBytes":228},{"name":"eval.yaml","path":"eng/harness-evaluation/skills/code-review/eval.yaml","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/code-review/eval.yaml","title":"Code-review Skill","category":"anthropic-skill","format":"yaml","content":"# Code-review Skill\n\nPath: `eng/harness-evaluation/skills/code-review/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/code-review/eval.yaml)","tokens":300,"sizeBytes":216},{"name":"review-context.md","path":"eng/harness-evaluation/skills/code-review/fixtures/query-comment/context/review-context.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/code-review/fixtures/query-comment/context/review-context.md","title":"Context Skill","category":"anthropic-skill","format":"markdown","content":"# Context Skill\n\nPath: `eng/harness-evaluation/skills/code-review/fixtures/query-comment/context/review-context.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/code-review/fixtures/query-comment/context/review-context.md)","tokens":300,"sizeBytes":290},{"name":"eval.yaml","path":"eng/harness-evaluation/skills/cosmos-provider/eval.yaml","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/cosmos-provider/eval.yaml","title":"Cosmos-provider Skill","category":"anthropic-skill","format":"yaml","content":"# Cosmos-provider Skill\n\nPath: `eng/harness-evaluation/skills/cosmos-provider/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/cosmos-provider/eval.yaml)","tokens":300,"sizeBytes":228},{"name":"eval.yaml","path":"eng/harness-evaluation/skills/make-custom-agent/eval.yaml","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/make-custom-agent/eval.yaml","title":"Make-custom-agent Skill","category":"anthropic-skill","format":"yaml","content":"# Make-custom-agent Skill\n\nPath: `eng/harness-evaluation/skills/make-custom-agent/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/make-custom-agent/eval.yaml)","tokens":300,"sizeBytes":234},{"name":"eval.yaml","path":"eng/harness-evaluation/skills/make-github-actions-workflow/eval.yaml","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/make-github-actions-workflow/eval.yaml","title":"Make-github-actions-workflow Skill","category":"anthropic-skill","format":"yaml","content":"# Make-github-actions-workflow Skill\n\nPath: `eng/harness-evaluation/skills/make-github-actions-workflow/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/make-github-actions-workflow/eval.yaml)","tokens":300,"sizeBytes":267},{"name":"eval.yaml","path":"eng/harness-evaluation/skills/make-instructions/eval.yaml","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/make-instructions/eval.yaml","title":"Make-instructions Skill","category":"anthropic-skill","format":"yaml","content":"# Make-instructions Skill\n\nPath: `eng/harness-evaluation/skills/make-instructions/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/make-instructions/eval.yaml)","tokens":300,"sizeBytes":234},{"name":"eval.yaml","path":"eng/harness-evaluation/skills/make-skill/eval.yaml","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/make-skill/eval.yaml","title":"Make-skill Skill","category":"anthropic-skill","format":"yaml","content":"# Make-skill Skill\n\nPath: `eng/harness-evaluation/skills/make-skill/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/make-skill/eval.yaml)","tokens":300,"sizeBytes":213},{"name":"eval.yaml","path":"eng/harness-evaluation/skills/migrations/eval.yaml","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/migrations/eval.yaml","title":"Migrations Skill","category":"anthropic-skill","format":"yaml","content":"# Migrations Skill\n\nPath: `eng/harness-evaluation/skills/migrations/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/migrations/eval.yaml)","tokens":300,"sizeBytes":213},{"name":"source-context.md","path":"eng/harness-evaluation/skills/migrations/fixtures/upgrade-only/source-context.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/migrations/fixtures/upgrade-only/source-context.md","title":"Upgrade-only Skill","category":"anthropic-skill","format":"markdown","content":"# Upgrade-only Skill\n\nPath: `eng/harness-evaluation/skills/migrations/fixtures/upgrade-only/source-context.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/migrations/fixtures/upgrade-only/source-context.md)","tokens":300,"sizeBytes":275},{"name":"eval.yaml","path":"eng/harness-evaluation/skills/model-building/eval.yaml","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/model-building/eval.yaml","title":"Model-building Skill","category":"anthropic-skill","format":"yaml","content":"# Model-building Skill\n\nPath: `eng/harness-evaluation/skills/model-building/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/model-building/eval.yaml)","tokens":300,"sizeBytes":225},{"name":"eval.yaml","path":"eng/harness-evaluation/skills/query-pipeline/eval.yaml","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/query-pipeline/eval.yaml","title":"Query-pipeline Skill","category":"anthropic-skill","format":"yaml","content":"# Query-pipeline Skill\n\nPath: `eng/harness-evaluation/skills/query-pipeline/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/query-pipeline/eval.yaml)","tokens":300,"sizeBytes":225},{"name":"source-context.md","path":"eng/harness-evaluation/skills/query-pipeline/fixtures/provider-test-placement/source-context.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/query-pipeline/fixtures/provider-test-placement/source-context.md","title":"Provider-test-placement Skill","category":"anthropic-skill","format":"markdown","content":"# Provider-test-placement Skill\n\nPath: `eng/harness-evaluation/skills/query-pipeline/fixtures/provider-test-placement/source-context.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/query-pipeline/fixtures/provider-test-placement/source-context.md)","tokens":300,"sizeBytes":316},{"name":"split-query-review.md","path":"eng/harness-evaluation/skills/query-pipeline/fixtures/query-pipeline/split-query-review.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/query-pipeline/fixtures/query-pipeline/split-query-review.md","title":"Query-pipeline Skill","category":"anthropic-skill","format":"markdown","content":"# Query-pipeline Skill\n\nPath: `eng/harness-evaluation/skills/query-pipeline/fixtures/query-pipeline/split-query-review.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/query-pipeline/fixtures/query-pipeline/split-query-review.md)","tokens":300,"sizeBytes":297},{"name":"integration.md","path":"eng/harness-evaluation/skills/query-pipeline/fixtures/single-result-lifting/integration.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/query-pipeline/fixtures/single-result-lifting/integration.md","title":"Single-result-lifting Skill","category":"anthropic-skill","format":"markdown","content":"# Single-result-lifting Skill\n\nPath: `eng/harness-evaluation/skills/query-pipeline/fixtures/single-result-lifting/integration.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/query-pipeline/fixtures/single-result-lifting/integration.md)","tokens":300,"sizeBytes":304},{"name":"eval.yaml","path":"eng/harness-evaluation/skills/run-apichief/eval.yaml","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/run-apichief/eval.yaml","title":"Run-apichief Skill","category":"anthropic-skill","format":"yaml","content":"# Run-apichief Skill\n\nPath: `eng/harness-evaluation/skills/run-apichief/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/run-apichief/eval.yaml)","tokens":300,"sizeBytes":219},{"name":"eval.yaml","path":"eng/harness-evaluation/skills/scaffolding/eval.yaml","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/scaffolding/eval.yaml","title":"Scaffolding Skill","category":"anthropic-skill","format":"yaml","content":"# Scaffolding Skill\n\nPath: `eng/harness-evaluation/skills/scaffolding/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/scaffolding/eval.yaml)","tokens":300,"sizeBytes":216},{"name":"eval.yaml","path":"eng/harness-evaluation/skills/servicing-pr/eval.yaml","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/servicing-pr/eval.yaml","title":"Servicing-pr Skill","category":"anthropic-skill","format":"yaml","content":"# Servicing-pr Skill\n\nPath: `eng/harness-evaluation/skills/servicing-pr/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/servicing-pr/eval.yaml)","tokens":300,"sizeBytes":219},{"name":"eval.yaml","path":"eng/harness-evaluation/skills/sqlite-adonet/eval.yaml","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/sqlite-adonet/eval.yaml","title":"Sqlite-adonet Skill","category":"anthropic-skill","format":"yaml","content":"# Sqlite-adonet Skill\n\nPath: `eng/harness-evaluation/skills/sqlite-adonet/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/sqlite-adonet/eval.yaml)","tokens":300,"sizeBytes":222},{"name":"eval.yaml","path":"eng/harness-evaluation/skills/tooling/eval.yaml","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/tooling/eval.yaml","title":"Tooling Skill","category":"anthropic-skill","format":"yaml","content":"# Tooling Skill\n\nPath: `eng/harness-evaluation/skills/tooling/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/tooling/eval.yaml)","tokens":300,"sizeBytes":204},{"name":"eval.yaml","path":"eng/harness-evaluation/skills/triage/eval.yaml","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/triage/eval.yaml","title":"Triage Skill","category":"anthropic-skill","format":"yaml","content":"# Triage Skill\n\nPath: `eng/harness-evaluation/skills/triage/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/triage/eval.yaml)","tokens":300,"sizeBytes":201},{"name":"embedded-directive.md","path":"eng/harness-evaluation/skills/triage/fixtures/sandbox/embedded-directive.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/triage/fixtures/sandbox/embedded-directive.md","title":"Sandbox Skill","category":"anthropic-skill","format":"markdown","content":"# Sandbox Skill\n\nPath: `eng/harness-evaluation/skills/triage/fixtures/sandbox/embedded-directive.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/triage/fixtures/sandbox/embedded-directive.md)","tokens":300,"sizeBytes":260},{"name":"issue-context.md","path":"eng/harness-evaluation/skills/triage/fixtures/sandbox/issue-context.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/triage/fixtures/sandbox/issue-context.md","title":"Sandbox Skill","category":"anthropic-skill","format":"markdown","content":"# Sandbox Skill\n\nPath: `eng/harness-evaluation/skills/triage/fixtures/sandbox/issue-context.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/triage/fixtures/sandbox/issue-context.md)","tokens":300,"sizeBytes":250},{"name":"security-report.md","path":"eng/harness-evaluation/skills/triage/fixtures/sandbox/security-report.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/triage/fixtures/sandbox/security-report.md","title":"Sandbox Skill","category":"anthropic-skill","format":"markdown","content":"# Sandbox Skill\n\nPath: `eng/harness-evaluation/skills/triage/fixtures/sandbox/security-report.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/triage/fixtures/sandbox/security-report.md)","tokens":300,"sizeBytes":254},{"name":"unsafe-setup.md","path":"eng/harness-evaluation/skills/triage/fixtures/sandbox/unsafe-setup.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/triage/fixtures/sandbox/unsafe-setup.md","title":"Sandbox Skill","category":"anthropic-skill","format":"markdown","content":"# Sandbox Skill\n\nPath: `eng/harness-evaluation/skills/triage/fixtures/sandbox/unsafe-setup.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/triage/fixtures/sandbox/unsafe-setup.md)","tokens":300,"sizeBytes":248},{"name":"eval.yaml","path":"eng/harness-evaluation/skills/update-pipeline/eval.yaml","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/update-pipeline/eval.yaml","title":"Update-pipeline Skill","category":"anthropic-skill","format":"yaml","content":"# Update-pipeline Skill\n\nPath: `eng/harness-evaluation/skills/update-pipeline/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/update-pipeline/eval.yaml)","tokens":300,"sizeBytes":228},{"name":"source-excerpts.md","path":"eng/harness-evaluation/skills/update-pipeline/fixtures/shared-identity/source-excerpts.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/update-pipeline/fixtures/shared-identity/source-excerpts.md","title":"Shared-identity Skill","category":"anthropic-skill","format":"markdown","content":"# Shared-identity Skill\n\nPath: `eng/harness-evaluation/skills/update-pipeline/fixtures/shared-identity/source-excerpts.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/update-pipeline/fixtures/shared-identity/source-excerpts.md)","tokens":300,"sizeBytes":296},{"name":"copilot-instructions.md","path":".github/copilot-instructions.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/.github/copilot-instructions.md","title":"GitHub Copilot Instructions","category":"copilot-instructions","format":"markdown","content":"# GitHub Copilot Instructions\n\nPath: `.github/copilot-instructions.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.github/copilot-instructions.md)","tokens":300,"sizeBytes":186},{"name":"settings.json","path":".github/copilot/settings.json","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/.github/copilot/settings.json","title":"GitHub Copilot Instructions","category":"copilot-instructions","format":"markdown","content":"# GitHub Copilot Instructions\n\nPath: `.github/copilot/settings.json`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.github/copilot/settings.json)","tokens":300,"sizeBytes":182},{"name":"README.md","path":"eng/Tools/ApiChief/README.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/Tools/ApiChief/README.md","title":"ApiChief Documentation","category":"plugin-manifest","format":"markdown","content":"# ApiChief Documentation\n\nPath: `eng/Tools/ApiChief/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/Tools/ApiChief/README.md)","tokens":300,"sizeBytes":175},{"name":"README.md","path":"src/EFCore.Tools/README.md","rawUrl":"https://raw.githubusercontent.com/dotnet/efcore/HEAD/src/EFCore.Tools/README.md","title":"EFCore.Tools Documentation","category":"plugin-manifest","format":"markdown","content":"# EFCore.Tools Documentation\n\nPath: `src/EFCore.Tools/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/src/EFCore.Tools/README.md)","tokens":300,"sizeBytes":175}],"systemPromptSnippet":"<yakaai_skills repo=\"dotnet/efcore\">\n<!-- File: .agents/skills/change-tracking/SKILL.md (Tokens: ~499 | Category: anthropic-skill) -->\n---\nname: change-tracking\ndescription: 'Implementation details for EF Core change tracking. Use when changing InternalEntityEntry, ChangeDetector, SnapshotFactoryFactory, or related entity state, snapshot, or property accessor code.'\nuser-invocable: false\n---\n\n# Change Tracking\n\nManages entity states and detects changes for `SaveChanges()`.\n\n## Core Components\n\n- `StateManager` — owns tracked entries, identity/reference maps, fixup, cascades, notifications, and changed counts\n- `InternalEntryBase` and derived classes — own per-entry state, flags, values, snapshots, and ordered state transitions\n- `ChangeDetector` — compares current values with baselines and reports changes through entry mutation APIs\n- `SnapshotFactoryFactory` subclasses — create passive original- and relationship-value baselines\n- `IdentityMap` — permits one active entry per key; shared identity pairs a replacement with the prior `Deleted` entry\n- `PropertyAccessorsFactory`, `ClrPropertyGetterFactory` and `ClrPropertySetterFactory` compile property accessors for efficient snapshotting and change detection\n  - Ordinals in `indices` parameter specify element at each complex collection depth\n\n## Change Detection\n\n- Snapshot and notification strategies both call `SetPropertyModified()` to keep property flags and entity state consistent.\n- `SetEntityState()` validates values, updates flags and complex entries, changes state, then runs manager bookkeeping hooks.\n\n## Shared-Identity Replacement\n\n`SharedIdentityEntry` is the invariant that distinguishes an old deleted entry from its replacement with the same identity. When attaching a replacement graph, a deleted nested entry should be reconsidered only when its source entry has a replacement; do not broadly process every deleted node. Likewise, cascading from the old replaced principal must not delete dependents that belong to the replacement graph. Keep synchronous and asynchronous graph-attach paths equivalent and preserve unrelated values in replacement tests so they isolate the identity transition.\n\n## Testing\n\nUnit tests: `test/EFCore.Tests/ChangeTracking/`. Functional tests: `test/EFCore.Specification.Tests/GraphUpdates/`.\n\n## Common Pitfalls\n\n| Pitfall | Solution |\n|---------|----------|\n| State-based checks treat every Added/Deleted entry as a replacement | Scope replacement behavior through `SharedIdentityEntry` and the graph source |\n\n## Validation\n\n- `DetectChanges()` identifies modified properties via snapshot comparison\n- Setting original values marks properties as modified or unchanged based on comparison with current values\n\n<!-- File: .agents/skills/code-review/references/api-review.md (Tokens: ~300 | Category: anthropic-skill) -->\n# References Skill\n\nPath: `.agents/skills/code-review/references/api-review.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/code-review/references/api-review.md)\n\n<!-- File: .agents/skills/code-review/references/conventions.md (Tokens: ~300 | Category: anthropic-skill) -->\n# References Skill\n\nPath: `.agents/skills/code-review/references/conventions.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/code-review/references/conventions.md)\n\n<!-- File: .agents/skills/code-review/references/security-review.md (Tokens: ~300 | Category: anthropic-skill) -->\n# References Skill\n\nPath: `.agents/skills/code-review/references/security-review.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/code-review/references/security-review.md)\n\n<!-- File: .agents/skills/code-review/SKILL.md (Tokens: ~2267 | Category: anthropic-skill) -->\n---\nname: code-review\ndescription: 'Review EF Core pull requests or local changes for concrete correctness, compatibility, performance, security, and test-coverage problems. Use when asked to review, critique, or check code changes before merge or submission.'\n---\n\n# EF Core Code Review\n\nReview pull requests and local working-tree changes without modifying source. Findings must be concrete, evidence-backed problems introduced or exposed by the change, not style preferences or general improvement ideas.\n\n## Scope and Safety\n\n- Review the provided pull request, or staged, unstaged, and untracked local changes. Ask for clarification when both are plausible.\n- Never checkout, switch branches, stash, reset, clean, or otherwise mutate the working tree, except for checking out the requested head for review purposes. Never edit source as part of a review.\n- For a pull request, record its base, head, and immutable head SHA. If local `HEAD` differs, use read-only repository or GitHub context when sufficient; otherwise ask the user to checkout the requested commit.\n- Never submit an `APPROVE` or `REQUEST_CHANGES` event. COMMENT emission follows Step 8.\n- Do not use this skill to address existing review comments or implement fixes.\n\n## Workflow\n\n### 1. Establish the Review Surface\n\n1. Load `.github/copilot-instructions.md` and any area skill whose description matches the changed implementation.\n2. Obtain the complete diff and changed-file list once. Include staged, unstaged, and untracked files for local reviews.\n3. For pull requests, gather the base/head refs and head SHA, but defer the PR body, linked issues, and prior review comments until Step 3.\n4. Stop with a clear limitation if the requested change surface cannot be established.\n\n### 2. Form an Independent Assessment\n\nBefore reading the author's narrative:\n\n1. Read each changed implementation beyond its diff hunk. Diff-only review is insufficient evidence for a finding. For very large files, read the containing members, their contracts, and relevant state. When many files are changed, use subagents to break down the review into manageable parts and gather context incrementally.\n2. Search callers, implementations, overrides, sibling provider paths, and nearby tests. Read shared helpers whose contracts control the changed behavior.\n3. When logic moves, compare the old and new input domains. Check the moved member's XML contract as well as regression coverage.\n4. Use focused history to explain invariants, reverts, or prior rejected approaches; establish what makes a repeated approach viable now.\n5. Describe the old and new behavior, likely motivation, affected callers/providers, and initial concerns in your own words.\n\n### 3. Holistic PR Assessment\n\nAssess the overall approach before refining implementation details:\n\n- Require a concrete need for added code, APIs, abstractions, and flags. Prefer the simplest sufficient alternative; weigh benefits against complexity, surface area, and long-term maintenance.\n- Prefer root-cause fixes at the owning layer. Challenge a flawed direction early rather than polishing its implementation.\n- Require BenchmarkDotNet results or equivalent measurements for performance claims; prefer focused local runs for experimental or iterative work.\n - Explain and address scenario-specific regressions even when aggregate results improve.\n- Scale required benefit and validation with regression risk and blast radius, especially for stable code.\n\n### 4. Reconcile Pull Request Context\n\nFor pull requests, now read the description, linked issues, and existing review threads. Treat them as claims to verify against the code. Also flag found problems the PR narrative doesn't acknowledge.\n\nIf the additional context reveals information that genuinely changes your evaluation, update your holistic assessment accordingly. But do not soften findings just because the PR description sounds reasonable.\n\n### 5. Route Conditional Reviews\n\n- Read [references/api-review.md](references/api-review.md) when the change adds, removes, or changes supported public or protected API outside an `.Internal` namespace and not annotated with `[EntityFrameworkInternal]`.\n- Read [references/security-review.md](references/security-review.md) when changed data crosses a documented trust boundary or the change affects serialization, generated code from database metadata, command construction, sensitive-data handling, caches or complexity bounds, assembly loading, elevated operations, or another high-risk path.\n\n### 6. Analyze Behavior and Coverage\n\nFor each non-trivial production change, identify:\n\n1. **Changed behavior**: the concrete old and new code paths.\n2. **Affected surfaces**: callers, providers, public contracts, generated output, persistence, diagnostics, and concurrency where applicable.\n3. **Regression risks**: plausible inputs, interleavings, failures, or compatibility breaks.\n4. **Expected coverage**: the focused test that would fail without the change or expose the regression.\n5. **Coverage gaps**: affected behavior not exercised by changed or existing tests.\n\nCheck correctness, error handling, async behavior, concurrency, state and resource lifetime, compatibility, provider hierarchy behavior, NativeAOT constraints, and performance only where the changed path plausibly makes them relevant.\n\nFor exception cleanup around shared or concurrent state, distinguish whether this invocation acquired each resource from whether the resource currently appears held. Cover both a failing owner releasing its acquisition and a failing contender preserving another owner's acquisition, including preexisting nested state. Construct a concrete interleaving without weakening existing reentrancy or nesting behavior.\n\nFor new functionality consider other feature areas that might be affected but are not directly touched by the change.\n\nDo not request tests for documentation-only changes, comments, formatting, or demonstrably behavior-preserving mechanical changes. Do not flag issues that the compiler, formatter, or existing analyzers deterministically report.\n\n### 7. Optional Multi-Model Review\n\nWhen the environment supports launching sub-agents with different models (e.g., the `task` tool with a `model` parameter), run the review in parallel across multiple model families to get diverse perspectives. Different models catch different classes of issues. If the environment does not support this, proceed with a single-model review.\n\n1. Inspect the available model list and select models from 2-3 distinct model families, up to 3 sub-agent models total. If fewer than 2 eligible families are available, use what is available.\n   - Pick only from models explicitly listed as available in the environment. Do not guess or assume model names.\n   - Never pick models labeled \"mini\", \"fast\", or \"cheap\" for code review.\n   - Do not select a model from the same family that is already running the primary review (i.e. the currently used model).\n   - If multiple models exist in the same family, pick the one with the highest version number. Prefer \"-codex\" variants over general-purpose.\n   - If the model supports effort configuration use the one closest to the current effort level.\n2. Launch a sub-agent for each selected model in parallel, giving each the same review prompt: the PR diff, the review rules from this skill, and instructions to produce findings in the severity format defined above.\n3. Wait for all agents to complete, then synthesize: deduplicate findings that appear across models, elevate issues flagged by multiple models (higher confidence), and include unique findings from individual models that meet the confidence bar. If a sub-agent has not completed after 10 minutes and you have results from other agents, proceed with the results you have.\n4. Present a single unified review to the user, noting when an issue was flagged by multiple models. Do not wait for any remaining sub-agents and do not attempt retries if any failed. The review is complete once the report operation succeeds.\n\n### 7. Verify and Report Findings\n\nBefore reporting a concern:\n\n- Verify it against surrounding and unchanged code, including caller/callee defenses.\n- Identify a realistic failure or user impact. Do not promote a theoretical possibility with negligible likelihood into a finding.\n- Verify factual claims about APIs from repository evidence or current documentation; never rely on model memory to claim an API is absent, deprecated, or unavailable.\n- Report only test results actually observed. Separate unexecuted validation and residual risk from findings.\n\nOrder findings by severity:\n\n- ❌ **Critical**: practical exploitation, arbitrary code execution, widespread data loss, or similarly catastrophic impact.\n- 🔴 **High**: merge-blocking correctness, security, compatibility, data-integrity, or concurrency defect.\n- ⚠️ **Medium**: concrete defect with limited impact or a meaningful regression gap for changed behavior.\n- 🔵 **Low**: minor but real defect worth fixing in this change.\n- 💡 **Info**: observations or suggestions that do not constitute a defect but may improve code quality or maintainability.\n\nEach finding must contain:\n\n1. Severity and concise title.\n2. Certainty level or confidence in the finding based on the available evidence.\n3. Changed file and line or symbol.\n4. Concrete failure mode and impact.\n5. Evidence that makes the finding actionable.\n6. Fix direction and, when relevant, the missing regression-test shape.\n\nPresent the holistic assessment before findings. Do not add praise or filler.\n\n**Motivation**: <1-2 sentences on whether the PR is justified and the problem is real>\n\n**Approach**: <1-2 sentences on whether the fix/change takes the right approach>\n\n**Summary**: <✅ LGTM / ⚠️ Needs Human Review / ⚠️ Needs Changes / ❌ Reject>. <2-3 sentence summary of the overall verdict and key points. If \"Needs Human Review,\" explicitly state which findings you are uncertain about and what a human reviewer should focus on.>\n\n### 8. Optionally Post Pull Request Comments\n\nPosting is allowed through either authorization path:\n\n- **Direct invocation**: number the findings, let the user select or edit them, and obtain explicit confirmation before posting.\n- **Code-reviewer agent delegation**: an invoking code-reviewer agent may explicitly authorize COMMENT emission and provide the selected findings or complete review payload. That caller contract is sufficient authorization; do not add a redundant confirmation prompt. An analysis-only delegation does not authorize posting.\n\nImmediately before posting, confirm that the pull request is still open and its base, head, and head SHA match the reviewed revision. If they changed, stop and refresh the review context.\n\nCreate a pending review, add only authorized findings, and submit it as `COMMENT`. Never approve or request changes. Include a concise AI-generated disclosure when posting under a user's identity rather than a bot identity. Do not post findings that are similar to existing or resolved comments; for multiple defects in the same area, consolidate them into a single finding when appropriate.\n\n## Validation\n\n- Every finding resolves to changed code or a changed contract and cites supporting repository evidence.\n- Test requests follow the behavior-impact analysis.\n- No source or worktree mutation occurred.\n- Any posted review used the reviewed head SHA and COMMENT-only authorization.\n\n## Common Pitfalls\n\n- Reviewing hunks without their callers or provider hierarchy.\n- Treating a public CLR member in `.Internal` as supported public API.\n- Reporting a security keyword without tracing attacker-controlled data to an impact.\n- Inferring that passing broad tests covers the changed failure mode.\n- Turning uncertainty into a firm finding instead of investigating or recording a limitation.\n\n<!-- File: .agents/skills/cosmos-provider/SKILL.md (Tokens: ~199 | Category: anthropic-skill) -->\n---\nname: cosmos-provider\ndescription: 'Implementation details for the EF Core Azure Cosmos DB provider. Use when changing Cosmos-specific code.'\nuser-invocable: false\n---\n\n# Cosmos DB Provider\n\nNon-relational provider with its own parallel query pipeline. Uses JSON for document materialization.\n\n## Key Differences from Relational\n\n- No migrations — use `EnsureCreated()`\n- Documents as JSON — owned and complex types become embedded objects\n- Partition key configuration required for performance\n- `ETag` for optimistic concurrency\n- No cross-container joins\n\n## Azure Cosmos DB Emulator for Tests\n\n- `TestEnvironment.InitializeAsync()` auto-starts a `Testcontainers.CosmosDb` container when `Test__Cosmos__DefaultConnection` is not set. Set the env var to use an existing emulator instead.\n- Skip tests requiring unsupported features on the Linux emulator with ` [ConditionalFact(typeof(CosmosTestEnvironment), nameof(CosmosTestEnvironment.IsNotLinuxEmulator))]`.\n\n<!-- File: .agents/skills/make-custom-agent/SKILL.md (Tokens: ~2394 | Category: anthropic-skill) -->\n---\nname: make-custom-agent\ndescription: 'Create, review, or fix custom GitHub Copilot agents. Use when asked to create, scaffold, configure, review, or restrict a custom agent, declarative agent, or @-invokable chat participant for GitHub Copilot.'\n---\n\n# Create Custom Agent\n\nThis skill guides you through creating a custom GitHub Copilot agent — an `@`-invokable chat participant that extends Copilot with domain-specific expertise. Custom agents are distinct from Agent Skills: skills provide reusable instructions loaded on demand, while agents own the full conversational interaction and can orchestrate tools, call APIs, and maintain their own prompt strategies.\n\n## When Not to Use\n\n- Adding reusable, invokable workflows — use Agent Skills (`.agents/skills/`) instead\n- Adding background coding guidelines — use file-based instructions (`.github/instructions/`) instead\n- Adding project-wide context for Copilot — use `.github/copilot-instructions.md` instead\n- Creating reusable prompts — use .prompt.md instead\n\n## Workflow\n\nFor an existing proposal, audit the full definition rather than just its tools: the description must identify natural requests that should discover it, the body must add domain knowledge beyond root instructions, and the paired eval must isolate its contribution. Compare every tool and behavior to the user's intended authority. A command-free reviewer must not gain command execution or publication through a wildcard tool, handoff, or otherwise read-only workflow.\n\n### Step 1: Choose the agent type\n\n| Type | Location | Best for |\n|---|---|---|\n| Declarative (prompt file) | `.github/agents/<name>.md` | Simple prompt-driven cross-surface agents with no code |\n| Extension-based (chat participant) | VS Code extension project | Full control, tool calling, VS Code API access |\n| GitHub App (Copilot Extension) | Hosted service + GitHub App | Cross-surface agents (github.com, VS Code, Visual Studio) |\n\nIf the agent only needs a scoped system prompt and doesn't require custom code, start with a declarative agent.\n\n### Step 2: Create a declarative agent (prompt file)\n\nDeclarative agents are Markdown files in `.github/agents/`. VS Code and GitHub Copilot discover them automatically.\n\n```\n.github/agents/\n└── <agent-name>.md        # Agent definition\n```\n\nTemplate:\n\n```markdown\n---\nname: my-agent\ndescription: A short description of what this agent does and when to use it.\n---\n\n# <Agent Title>\n\nYou are an expert in <domain>. Your job is to:\n- <behavior 1>\n- <behavior 2>\n\n## Guidelines\n\n- <guideline 1>\n- <guideline 2>\n\n## Workflow\n\n1. <step 1>\n2. <step 2>\n\n## Constraints\n\n- <constraint 1>\n- <constraint 2>\n\n```\n\nSupported frontmatter fields:\n\n| Field | Required | Description |\n|---|---|---|\n| `name` | Yes | Lowercase, hyphens allowed. Used for `@`-mention. |\n| `description` | Yes | What the agent does and when to use it. Shown in the participant list. |\n| `target` | No | Target environment: `vscode` or `github-copilot` (defaults to both) |\n| `tools` | No | List of allowed tools/tool sets |\n| `model` | No | LLM name or prioritized array of models |\n| `user-invocable` | No | Show in agents dropdown (default: true) |\n| `disable-model-invocation` | No | Prevent subagent invocation (default: false) |\n| `mcp-servers` | No | MCP server configs for GitHub Copilot target |\n| `metadata` | No | Key-value mapping for additional arbitrary metadata. |\n| `argument-hint` | No | Hint text guiding user interaction (VS Code only) |\n| `agents` | No | List of allowed subagents (`*` for all, `[]` for none, VS Code only) |\n| `handoffs` | No | List of next-step agent transitions (VS Code only) |\n\n\nTips for instructions:\n- Use Markdown links to reference other files\n- Reference tools with `#tool:<tool-name>` syntax\n- Be specific about agent behavior and constraints\n\n### Step 3: Configure tools\n\nSpecify which tools the agent can use:\n\n```yaml\ntools:\n  - search              # Built-in tool\n  - fetch               # Built-in tool\n  - codebase            # Tool set\n  - myServer/*          # All tools from MCP server\n```\n\nCommon tool patterns:\n- **Read-only agents**: `['search', 'fetch', 'codebase']`\n- **Full editing agents**: `['*']` or specific editing tools\n- **Specialized agents**: Cherry-pick specific tools\n\n### Step 4: Add handoffs (optional, VS Code only)\n\nConfigure transitions to other agents:\n\n```yaml\nhandoffs:\n  - label: Start Implementation\n    agent: implementation\n    prompt: Implement the plan outlined above.\n    send: false\n    model: GPT-5.2 (copilot)\n```\n\nHandoff fields:\n- `label`: Button text displayed to user\n- `agent`: Target agent identifier\n- `prompt`: Pre-filled prompt for target agent\n- `send`: Auto-submit prompt (default: false)\n- `model`: Optional model override for handoff\n\n### Step 5: Create an extension-based chat participant (VS Code only)\n\nFor full control, implement a VS Code extension with a chat participant:\n\n1. **Define the participant** in `package.json`:\n\n```json\n\"contributes\": {\n    \"chatParticipants\": [\n        {\n            \"id\": \"my-extension.my-agent\",\n            \"name\": \"my-agent\",\n            \"fullName\": \"My Agent\",\n            \"description\": \"Short description shown in chat input\",\n            \"isSticky\": false,\n            \"commands\": [\n                {\n                    \"name\": \"explain\",\n                    \"description\": \"Explain the selected code\"\n                }\n            ]\n        }\n    ]\n}\n```\n\n2. **Register and implement the request handler** in `extension.ts`:\n\n```typescript\nexport function activate(context: vscode.ExtensionContext) {\n    const agent = vscode.chat.createChatParticipant('my-extension.my-agent', handler);\n    agent.iconPath = vscode.Uri.joinPath(context.extensionUri, 'icon.png');\n}\n\nconst handler: vscode.ChatRequestHandler = async (\n    request: vscode.ChatRequest,\n    context: vscode.ChatContext,\n    stream: vscode.ChatResponseStream,\n    token: vscode.CancellationToken\n) => {\n    const model = request.model;\n    const messages = [\n        vscode.LanguageModelChatMessage.User(request.prompt)\n    ];\n    const response = await model.sendRequest(messages, {}, token);\n    for await (const fragment of response.text) {\n        stream.markdown(fragment);\n    }\n};\n```\n\n3. **Declare the extension dependency** in `package.json`:\n\n```json\n\"extensionDependencies\": [\"github.copilot-chat\"]\n```\n\n4. **Add tool calling (optional)**\n\nAgents can invoke language model tools registered by other extensions:\n\n```typescript\nconst tools = vscode.lm.tools.filter(tool => tool.tags.includes('my-domain'));\nconst result = await chatUtils.sendChatParticipantRequest(request, context, {\n    prompt: 'You are an expert in <domain>.',\n    tools,\n    responseStreamOptions: { stream, references: true, responseText: true }\n}, token);\nreturn await result.result;\n```\n\n### Step 6: Create a GitHub App (Copilot Extension) for cross-surface availability (optional)\n\nIf the agent should be available on GitHub.com, Visual Studio, JetBrains, and VS Code simultaneously, implement a GitHub App that acts as a Copilot Extension. The app registers a webhook endpoint, receives chat requests, and streams responses back.\n\nKey considerations:\n- The GitHub App must be installed on the user's account or organization\n- Responses are streamed via Server-Sent Events (SSE)\n- Use the [GitHub Copilot Extensions documentation](https://docs.github.com/en/copilot/building-copilot-extensions/about-building-copilot-extensions) for the full integration guide\n- For VS Code-specific features (editor access, file trees, command buttons), prefer an extension-based participant instead\n\n### Step 7: Author the harness evaluation\n\nCreate `eng/harness-evaluation/agents/<agent-id>/eval.yaml` and follow `eng/harness-evaluation/README.md`.\n\n- Declare only the agent file in the eval's root `agent_environment.files`; the experiment removes it from the control.\n- Use realistic stimuli that exercise behavior distinctive to the agent without stating the expected diagnosis or implementation in the prompt.\n- Combine deterministic output checks, a focused semantic rubric, bounded resources, token grading, and a committed scoring threshold.\n- Keep the eval name and directory-derived component ID identical to the agent ID.\n\n### Step 8: Validate\n\nAfter creating or modifying an agent, verify:\n\n- [ ] `name` is lowercase, uses hyphens (no spaces), and is unique\n- [ ] `description` clearly describes what the agent does and when to invoke it\n- [ ] Frontmatter YAML is valid (no syntax errors)\n- [ ] Declarative agent file is in `.github/agents/`\n- [ ] Tools list contains only available tools\n- [ ] Extension-based agent: participant ID matches in `package.json` and `createChatParticipant` call\n- [ ] Agent does not duplicate functionality of built-in agents (`@workspace`, `@vscode`, `@terminal`)\n- [ ] Handoff agent names match existing agents\n- [ ] Agent instructions don't include secrets, tokens, or internal URLs\n- [ ] The paired harness eval targets only this agent and is meant to meaningfully distinguish treatment from control\n\n## Common Pitfalls\n\n| Pitfall | Solution |\n|---------|----------|\n| Agent name conflicts with built-in participants | Use a unique prefix (domain name) |\n| Description is too vague | Include specific keywords users would naturally say |\n| System prompt is too long | Keep instructions to essential behaviors; move reference material to Agent Skills |\n| Agent requires VS Code API but is authored as declarative | Switch to extension-based participant |\n| Using `isSticky: true` unnecessarily | Only set sticky if the agent should persist between turns by default |\n| No `extensionDependencies` on `github.copilot-chat` | Add it; otherwise the contribution point may not be available |\n| Agent invoked as subagent unexpectedly | Set `disable-model-invocation: true` |\n| Subagent appears in the dropdown | Set `user-invocable: false` |\n\n## References\n\n- [VS Code Chat Participant API](https://code.visualstudio.com/api/extension-guides/ai/chat)\n- [VS Code AI Extensibility Overview](https://code.visualstudio.com/api/extension-guides/ai/ai-extensibility-overview)\n- [VS Code Extension Samples – chat-sample](https://github.com/microsoft/vscode-extension-samples/tree/main/chat-sample)\n- [GitHub Copilot Extensions documentation](https://docs.github.com/en/copilot/building-copilot-extensions/about-building-copilot-extensions)\n- [GitHub Copilot Custom agents configuration](https://docs.github.com/en/copilot/reference/custom-agents-configuration)\n- [Agent Skills Specification](https://agentskills.io/specification)\n- Related repository skills: `make-skill` and `make-instructions`\n\n<!-- File: .agents/skills/make-github-actions-workflow/SKILL.md (Tokens: ~1992 | Category: anthropic-skill) -->\n---\nname: make-github-actions-workflow\ndescription: 'Create or modify GitHub Actions workflows for CI, automation, or PR management. Use when asked to create, scaffold, add, extend, or fix a workflow (.yml file under .github/workflows/), including existing pull-request policy and comment automation.'\n---\n\n# Create GitHub Actions Workflow\n\nCreate and configure GitHub Actions workflows that follow this repository's conventions and patterns. Workflows automate tasks like CI validation, PR management, issue labeling, and notifications.\n\n## Repository Conventions\n\nThis repository uses specific patterns across all workflows. Follow these conventions when creating new workflows:\n\n### File Location and Naming\n\n- All workflows live in `.github/workflows/`\n- Use kebab-case names: `label-and-milestone-issues.yml`, `validate-pr-target-branch.yml`\n- Start with a descriptive comment block explaining the workflow's purpose\n\n### Runner\n\n- Use `ubuntu-latest` for general-purpose jobs\n- Use `ubuntu-24.04` when a specific OS version is needed (e.g., copilot setup steps)\n\n### Permissions\n\n- **Always** declare explicit permissions — never rely on defaults\n- Use **minimal permissions**: only request what the workflow needs\n- Common patterns:\n  - Read-only: `permissions: {}`\n  - PR comments: `pull-requests: write`\n  - Issue management: `issues: write`\n  - Code read: `contents: read`\n- For workflows that need write access to PRs from external contributors, use `pull_request_target` instead of `pull_request`\n  - **Security warning:** `pull_request_target` workflows run in the base repository context with its permissions. Do **not** check out or execute code from the PR branch in these workflows. Instead, use the event payload and/or GitHub API (`actions/github-script`, `github.rest.*`, etc.) to inspect and act on the PR safely.\n\n### Scripting\n\n- Use `actions/github-script@v8` for complex logic instead of shell scripts\n- Write JavaScript with `async/await` — the `github` object (Octokit) and `context` are available\n- Use `github.rest.*` for REST API calls and `github.graphql()` for GraphQL queries\n- Access PR/issue data via `context.payload.pull_request`, `context.repo.owner`, `context.repo.repo`\n- Log with `console.log()` for debugging; use `core.setFailed()` for errors\n\n### Error Handling\n\n- Wrap API calls in try/catch blocks\n- Collect errors and report at the end rather than failing on the first error\n- Log skipped operations with a reason\n\n## Workflow\n\n### Step 1: Understand the Requirements\n\nBefore writing the workflow, clarify:\n- [ ] What event(s) should trigger it? (push, pull_request, check_suite, schedule, etc.)\n- [ ] What permissions are needed?\n- [ ] What conditions should gate execution? (author, branch, labels, etc.)\n- [ ] What API calls are needed?\n- [ ] Are there rate limiting or idempotency concerns?\n\n### Step 2: Choose the Trigger Event\n\n| Use case | Event | Notes |\n|----------|-------|-------|\n| PR opened/updated | `pull_request` | Read-only access to PR |\n| PR with write access | `pull_request_target` | Can comment, label, close |\n| PR merged | `pull_request_target: [closed]` | Check `github.event.pull_request.merged == true` |\n| CI checks complete | `check_suite: [completed]` | Filter `app.slug != 'github-actions'` to skip self |\n| Code pushed | `push` | Filter by branches/paths |\n| Manual trigger | `workflow_dispatch` | Add `inputs:` for parameters |\n| Scheduled | `schedule` | Use cron syntax |\n\n### Step 3: Write the Workflow\n\nCreate the YAML file following this template:\n\n```yaml\n# Description of what this workflow does and why.\n\nname: Descriptive Workflow Name\n\non:\n  <trigger_event>:\n    types: [<event_types>]\n\npermissions:\n  <resource>: <read|write>\n\njobs:\n  <job-name>:\n    if: <guard_condition>  # Optional: skip when not needed\n    runs-on: ubuntu-latest\n    steps:\n      - name: Descriptive step name\n        uses: actions/github-script@v8\n        with:\n          script: |\n            // Your logic here\n```\n\n### Step 4: Implement Guard Conditions\n\nAdd conditions to avoid unnecessary runs:\n- Job-level `if:` for event payload checks (e.g., `github.event.check_suite.app.slug != 'github-actions'`)\n- Early `return` in scripts for PR author, draft status, etc.\n- Idempotency checks (e.g., hidden HTML comments as tags to prevent duplicate actions)\n\nFor `pull_request_target` policy workflows that react to `opened`, `edited`, and `reopened`:\n\n- On `edited`, return unless `context.payload.changes?.base` is present; title or body edits must not reapply a target-branch policy.\n- Check permissions for `context.actor`, not only the PR author. A maintainer may edit or reopen an external PR, and that action must use the maintainer's authority.\n- For `opened`, the actor and author are the same, so perform one permission lookup and reuse it for policy and labeling decisions.\n- Exclude automation when either the actor or author is a bot.\n- Encode the prohibited branch class directly (for example, `release/*`) instead of requiring a single allowed branch such as `main`.\n- If permission lookup fails, stop without taking a destructive action; unknown access is not evidence that the contributor is external.\n\n### Step 5: Validate\n\nAfter creating the workflow:\n- [ ] Permissions are minimal and explicitly declared\n- [ ] Uses `actions/github-script@v8` for complex logic\n- [ ] Guard conditions prevent unnecessary runs\n- [ ] API calls handle pagination where needed (use `per_page: 100`)\n- [ ] Error handling doesn't silently swallow failures\n- [ ] No secrets or tokens are hardcoded\n- [ ] Workflow doesn't create infinite loops (e.g., a workflow that triggers itself)\n\n## Existing Workflows in This Repository\n\nStudy these workflows as reference:\n\n| Workflow | Trigger | Purpose |\n|----------|---------|---------|\n| `validate-pr-target-branch.yml` | `pull_request_target: [opened, edited, reopened]` | Closes external PRs targeting release branches, adds community labels |\n| `label-and-milestone-issues.yml` | `pull_request_target: [closed]` | Labels and milestones issues when their fixing PR is merged |\n| `copilot-setup-steps.yml` | `workflow_dispatch`, `push`, `pull_request` | Sets up the development environment for Copilot |\n| `inter-branch-merge-flow.yml` | `push` to `release/**` | Triggers inter-branch merge via arcade |\n\n## Common Patterns\n\n### Commenting on a PR\n\n```javascript\nawait github.rest.issues.createComment({\n  owner: context.repo.owner,\n  repo: context.repo.repo,\n  issue_number: prNumber,\n  body: 'Comment text'\n});\n```\n\n### Checking User Permissions\n\n```javascript\nconst { data: permissions } = await github.rest.repos.getCollaboratorPermissionLevel({\n  owner: context.repo.owner,\n  repo: context.repo.repo,\n  username: context.actor\n});\nconst hasWriteAccess = ['admin', 'write'].includes(permissions.permission);\n```\n\n### Updating Bot-Owned Comments Idempotently\n\nA hidden marker identifies the workflow's comment but does not establish ownership: contributors and other apps can place the same marker in their comments. Match both the marker and the exact `github-actions[bot]` login, then update that comment or create a new one. A generic `user.type === 'Bot'` check does not establish workflow ownership. Preserve the workflow's pinned action SHA and never execute code from a pull-request fork in a `pull_request_target` job.\n\n```javascript\nconst marker = '<!-- validate-pr-target-branch -->';\nconst comments = await github.paginate(github.rest.issues.listComments, {\n  owner: context.repo.owner,\n  repo: context.repo.repo,\n  issue_number: prNumber,\n  per_page: 100\n});\n\nconst body = `${marker}\\nComment text`;\nconst existing = comments.find(comment =>\n  comment.user?.login === 'github-actions[bot]' && comment.body?.includes(marker));\n\nif (existing) {\n  await github.rest.issues.updateComment({\n    owner: context.repo.owner,\n    repo: context.repo.repo,\n    comment_id: existing.id,\n    body\n  });\n} else {\n  await github.rest.issues.createComment({\n    owner: context.repo.owner,\n    repo: context.repo.repo,\n    issue_number: prNumber,\n    body\n  });\n}\n```\n\n### Reading Repository Files at a Specific Commit\n\n```javascript\nconst { data: fileData } = await github.rest.repos.getContent({\n  owner, repo,\n  path: 'eng/Versions.props',\n  ref: commitSha\n});\nconst content = Buffer.from(fileData.content, 'base64').toString('utf-8');\n```\n\n## References\n\n- [GitHub Actions documentation](https://docs.github.com/en/actions)\n- [Workflow syntax](https://docs.github.com/en/actions/using-workflows/workflow-syntax-for-github-actions)\n- [Events that trigger workflows](https://docs.github.com/en/actions/using-workflows/events-that-trigger-workflows)\n- [actions/github-script](https://github.com/actions/github-script)\n\n<!-- File: .agents/skills/make-instructions/SKILL.md (Tokens: ~1145 | Category: anthropic-skill) -->\n---\nname: make-instructions\ndescription: 'Create and evaluate VS Code file-based instructions (.instructions.md files). Use when asked to create, scaffold, or add file-based instructions for Copilot. Generates scoped instructions and a paired Vally harness eval.'\n---\n\n# Create File-Based Instructions\n\nThis skill helps you scaffold VS Code file-based instructions (`.instructions.md` files) that provide background knowledge to Copilot about specific parts of the codebase. These files are applied automatically based on glob patterns or semantic matching, giving Copilot domain-specific context when working on matching files.\n\n## When Not to Use\n\n- Setting project-wide instructions — use `.github/copilot-instructions.md` or `AGENTS.md` instead\n- Creating reusable agent workflows with structured steps — use Agent Skills instead\n- Adding instructions that need to be invokable on demand — use Agent Skills instead\n\n## Workflow\n\n### Step 1: Investigate the topic\n\nBuild understanding of the area the instructions should cover. Identify:\n\n- [ ] What files or file patterns the instructions apply to\n- [ ] Key conventions, patterns, or architectural rules for that area\n- [ ] Common pitfalls that Copilot should avoid\n- [ ] Non-obvious domain knowledge that isn't discoverable from code alone\n\nRead the repository-wide instruction files that apply to the same paths and make an explicit exclusion list. Do not repeat those rules in the new file, even when they are relevant examples for the scoped area; include only guidance that becomes more specific or materially different at the narrower scope.\n\nIf the scope is unclear or overlaps with existing instructions, ask the user for clarification.\n\n### Step 2: Choose the file location\n\nInstructions files go in `.github/instructions/` by default. Pick a descriptive filename:\n\n```\n.github/instructions/<topic>.instructions.md\n```\n\nExamples: `csharp-style.instructions.md`, `query-pipeline.instructions.md`, `test-conventions.instructions.md`\n\n### Step 3: Generate the file with YAML frontmatter\n\nCreate the file with the required YAML frontmatter header:\n\n```yaml\n---\nname: '<Display Name>'              # Optional. Display name in the UI. Defaults to filename.\ndescription: '<Short description>'  # Optional. Shown on hover. Also used for semantic matching.\napplyTo: '<glob pattern>'           # Optional. Glob pattern relative to workspace root. Omit to require manual attachment or rely on semantic matching only.\n---\n```\n\nCommon `applyTo` patterns:\n\n- `**/*.cs` — all C# files\n- `test/**` — files under a specific folder\n\n### Step 4: Write the body content\n\nWrite concise, actionable Markdown content. Follow these principles:\n\n- **Be concise** — instructions share the context window; only include what the agent wouldn't already know\n- **Be specific** — use concrete rules, not vague guidance\n- **Include examples** — short code snippets showing preferred vs. avoided patterns are very effective\n- **Explain why** — when a rule exists for a non-obvious reason, state it so the agent applies it correctly in edge cases\n- **Skip linter-enforced rules** — don't repeat what formatters and linters already catch\n- **Use Markdown links** to reference specific files or URLs for additional context\n\nRecommended sections (adapt as needed):\n\n1. **<Title>** — one-line heading describing the domain\n2. **Context paragraph** — brief explanation of what this area is and why these rules matter\n3. **Guidelines / Conventions** — bullet list of concrete rules\n4. **Examples** — short code blocks showing do/don't patterns (optional)\n5. **Key Files** — table of important files for orientation (optional)\n6. **Common Pitfalls** — traps to avoid (optional)\n\n### Step 5: Author and validate the harness evaluation\n\nCreate `eng/harness-evaluation/instructions/<id>/eval.yaml`, where `<id>` is the instruction path relative to `.github/instructions/` with its suffix removed and nested path separators replaced by `--`.\n\nFollow the authoring and validation rules in `eng/harness-evaluation/README.md`. Exercise guidance distinctive to the instruction and ensure the treatment meaningfully outperforms the omitted-instruction control.\n\nFor initial authoring, produce and lint the requested instruction and eval before running behavioral comparisons.\n\nAfter creating the file, verify:\n\n- [ ] File is in `.github/instructions/` (or a configured instructions folder)\n- [ ] Filename ends with `.instructions.md` and only contains lowercase letters, numbers, and hyphens\n- [ ] YAML frontmatter is valid\n- [ ] `applyTo` glob matches the intended files\n- [ ] Content is concise (aim for under 500 lines or 5000 tokens) — long instructions dilute effectiveness\n- [ ] No secrets, tokens, or internal URLs included\n- [ ] Instructions don't duplicate what's already in `.github/copilot-instructions.md` or under `.agents/skills/`\n- [ ] The paired eval demonstrates behavior that the omitted-instruction control does not provide reliably\n\n## Common Pitfalls\n\n| Pitfall | Solution |\n|---------|----------|\n| `applyTo` too broad | Use specific globs; `**` applies to every file and wastes context |\n| Missing `applyTo` | Without it, instructions won't auto-apply — they require manual attachment or semantic matching via `description` |\n| Vague guidance | Replace \"write good tests\" with something like \"add both positive and negative test cases using `[ConditionalFact]` methods\" |\n\n<!-- File: .agents/skills/make-skill/SKILL.md (Tokens: ~767 | Category: anthropic-skill) -->\n---\nname: make-skill\ndescription: 'Create, review, or fix Agent Skills for GitHub Copilot. Use when asked to create, scaffold, improve, or repair a SKILL.md and its paired harness evaluation.'\n---\n\n# Create Or Fix A Skill\n\nProduce concise, stable task guidance that adds knowledge an agent cannot reliably infer from source alone, together with a paired evaluation that proves the guidance changes behavior.\n\n## Choose The Right Primitive\n\n- Use a skill for a task-specific workflow or body of knowledge loaded on demand.\n- Use file instructions for background guidance scoped to paths.\n- Use a custom agent when context isolation or distinct tool restrictions are required.\n- Prefer an existing skill over creating an overlapping one.\n\n## Workflow\n\n1. Read the relevant implementation, tests, repository instructions, and neighboring customizations.\n2. Identify repeated mistakes or non-obvious invariants. Do not turn source inventories, line counts, or facts easily rediscovered from code into skill content.\n3. Create `.agents/skills/<name>/SKILL.md`. The frontmatter `name` must exactly match the directory; the description must state what the skill does and when natural user requests should trigger it.\n4. Mark background domain guidance `user-invocable: false`. Keep user-invocable workflows focused on an outcome a user would deliberately request.\n5. Write actionable guidance with observable validation. Explain why edge cases matter; avoid generic engineering advice already present in repository instructions.\n6. Create `eng/harness-evaluation/skills/<name>/eval.yaml` and follow `eng/harness-evaluation/README.md`.\n7. Lint the customization and inspect both control and treatment artifacts before accepting it.\n\n## Paired Evaluation\n\n- The eval root `agent_environment.skills` contains only the target skill. Stimulus inputs belong under each stimulus's `agent_environment.files`.\n- The runner removes the root skill for control and separately verifies treatment activation. Do not add a `skill-invocation` grader and do not tell the agent to invoke the skill in the shared prompt.\n- Prompts may identify fixtures, proposed code, fixed IDs, and output paths, but must not reveal the expected diagnosis, owning mechanism, or regression-test design.\n- Stage self-contained source snapshots rather than diffs or commit references; fixture context must not require fetching a repository revision.\n- Use deterministic graders for observable artifacts, a narrow semantic rubric for behavior, and a `token-budget` grader. Define bounded turns, tokens, and duration plus a committed scoring threshold.\n- The task must exercise guidance distinctive to the skill. A control that consistently matches treatment means the skill or eval is not useful enough.\n\n## Validation\n\n- Frontmatter parses and the name matches the directory.\n- The skill is concise, stable, and does not duplicate root or scoped instructions.\n- File references are relative and exist.\n- Validation steps are observable and task-specific.\n- The paired eval targets only the skill, has complete bounded grading, and uses a solution-neutral prompt.\n- `npm run lint` and the harness inventory tests pass.\n\n## Common Pitfalls\n\n| Pitfall | Correction |\n|---|---|\n| Copying implementation inventories into the skill | Keep only non-obvious invariants and routing decisions |\n| Exact line counts or volatile metrics | Remove them; point to stable symbols or behavior |\n| Generic test-folder guidance | Describe the distinctive test shape or omit it |\n| Eval prompt tells the agent what to find | Move expected facts into the hidden rubric |\n| Eval root contains repository fixtures | Keep only the target skill at root; stage fixtures per stimulus |\n| Prompt instructs skill invocation | Let the treatment-only runner gate enforce activation |\n| Initial scaffold launches multi-model review | First produce and lint the requested artifacts; run expensive behavioral validation separately |\n\n<!-- File: .agents/skills/migrations/SKILL.md (Tokens: ~548 | Category: anthropic-skill) -->\n---\nname: migrations\ndescription: 'Implementation details for EF Core migrations. Use when changing MigrationsSqlGenerator, model diffing, migration operations, HistoryRepository, the Migrator or related classes.'\nuser-invocable: false\n---\n\n# Migrations\n\n## Pipeline\n\n**Add migration**: `MigrationsScaffolder.ScaffoldMigration()` → `MigrationsModelDiffer.GetDifferences()` → list of `MigrationOperation` → `CSharpMigrationsGenerator` and `CSharpSnapshotGenerator` produce Up/Down/Snapshot code\n\n**Apply migration**: `Migrator.MigrateAsync()` → reads `__EFMigrationsHistory` → per pending: `MigrationsSqlGenerator.Generate(operations)` → `MigrationCommandExecutor` executes\n\n## Model Snapshot\n\n- Model snapshots use `typeof(Dictionary<string, object>)` (property bag format), not the actual CLR type. When examining the `ClrType` in a snapshot, don't assume it matches the real entity type.\n- `SnapshotModelProcessor.Process()` is used at design-time to fixup older model snapshots for backward compatibility.\n- `MigrationsModelDiffer` uses provider-agnostic structural comparison between relational models to determine what migration operations are necessary.\n\nFor an upgrade-only regression, derive a concrete old `ModelSnapshot`, process its model with `SnapshotModelProcessor.Process(..., resetVersion: true)`, and compare it with the equivalent current design-time model through `MigrationsModelDiffer.GetDifferences()`. Preserve the property-bag CLR types emitted by old snapshots and omit APIs that would explicitly configure metadata that was absent in that version. The regression succeeds only when the resulting operation list is empty.\n\nLegacy snapshot normalization belongs in `SnapshotModelProcessor`, not in runtime migration application. Scope a compatibility branch to the exact released versions that could emit the affected snapshot shape; versions from before the feature existed should not be included merely because they are numerically older. Prefer the mutable metadata interface when it exposes the required setter rather than casting to a concrete metadata implementation. Do not use a missing configuration source as the test for missing historical snapshot metadata: old snapshots may already configure a value using the current default. For metadata whose semantics changed, use the snapshot's product version to restore the old invariant. Add focused coverage for every version family named by the gate, plus the first unaffected version.\n\n## Testing\n\nMigration operation tests: `test/EFCore.Relational.Tests/Migrations/`. Functional tests: `test/EFCore.{Provider}.FunctionalTests/Migrations/`. Model differ tests: `test/EFCore.Relational.Tests/Migrations/Internal/MigrationsModelDifferTest*.cs`.\n\nTo simulate a snapshot model use `ModelBuilder` calls without conventions.\n\n<!-- File: .agents/skills/model-building/SKILL.md (Tokens: ~1568 | Category: anthropic-skill) -->\n---\nname: model-building\ndescription: 'Implementation details for EF Core model building. Use when changing ConventionSet, ModelBuilder, IConvention implementations, ModelRuntimeInitializer, RuntimeModel, or related classes.'\nuser-invocable: false\n---\n\n# Model Building, Conventions & Initialization\n\nCovers model construction (conventions, fluent API, metadata hierarchy) and model initialization (runtime annotation propagation, compiled model filtering).\n\n## Convention System\n\n`ConventionSet` (`src/EFCore/Metadata/Conventions/ConventionSet.cs`) holds `List<I*Convention>` for every metadata event. Key conventions in `src/EFCore/Metadata/Conventions/`:\n\n- `DbSetFindingConvention` — discovers entities from `DbSet<T>`\n- `PropertyDiscoveryConvention` — discovers properties from CLR types\n- `KeyDiscoveryConvention` — finds PKs (`Id`, `TypeId`)\n- `RelationshipDiscoveryConvention` — infers FKs from navigations\n- `RuntimeModelConvention` — creates optimized `RuntimeModel` from mutable model\n\nOverride `ConfigureConventions(ModelConfigurationBuilder)` to add/remove conventions.\n\nConvention fixes must preserve dispatcher behavior and ambiguity information. For inverse-navigation attributes, do not solve recursion by permanently ignoring an ambiguous navigation: removing one candidate can make another ambiguity appear unique and configure the wrong relationship. `InversePropertyAttributeConvention` records inverse candidates and uses `AddInverseNavigation`, `TryRemoveIfAmbiguous`, and `FindAmbiguousInverse` while still allowing convention processing to continue.\n\nTest the state transitions, not only the initially ambiguous model: first verify that multiple interacting candidates configure no relationship; then genuinely remove ambiguity both by ignoring/removing one competing navigation and by removing a competing entity type, and verify that the remaining inverse relationship is configured. These cases distinguish candidate bookkeeping from a permanent-ignore workaround.\n\n## Metadata Interface Hierarchy\n\n`IReadOnly*` → `IMutable*` → `IConvention*` → `IRuntime*`\n\nApplies to: Model, EntityType, Property, Key, ForeignKey, Navigation, Index, etc. Builders follow: `*Builder` → `IConvention*Builder`.\n\n## Adding A Configurable Metadata Facet\n\nFollow the nearest existing facet end to end rather than stopping at the public interface:\n\n1. Add the read-only, mutable, and convention metadata contracts, concrete storage, default, configuration source, convention setter, and builder precedence checks. Preserve the facet when metadata is replaced or a relationship is rebuilt.\n2. If changes are observable to conventions, add the convention interface, every `ConventionSet` add/replace/remove path, and immediate plus delayed dispatcher scopes and nodes.\n3. Carry the value into the optimized runtime metadata through `RuntimeModelConvention`, runtime constructors/builders, and `CSharpRuntimeModelCodeGenerator` so compiled models preserve it.\n4. If snapshots persist the facet, update the fluent builder API and `CSharpSnapshotGenerator`; keep the old absence equivalent to the historical default.\n5. Update public API baselines and cover configuration-source precedence, convention dispatch, runtime/compiled model propagation, and snapshot round trips.\n\n## Model Lifecycle\n\n1. **Mutable Model** — built by `ModelBuilder` during `OnModelCreating`, made read-only by `FinalizeModel()`\n2. **Design-Time Model** — finalized read-only `Model` that also contains design-time-only annotations used in migrations\n3. **Runtime Model** — an optimized read-only model created by `RuntimeModelConvention.ProcessModelFinalized()`, does not contain design-time-only annotations\n\n`ModelRuntimeInitializer.Initialize()` (called by `DbContextServices.CreateModel()`):\n\n```\nInitialize(model, designTime, validationLogger)\n├─ FinalizeModel() if mutable\n├─ Set ModelDependencies, InitializeModel\n└─ RuntimeModelConvention creates RuntimeModel, copies/filters annotations\n```\n\n## Complex Type Property Recursion\n\nWhen processing properties in conventions or validation, remember that complex types can contain their own declared properties. Use `GetFlattenedProperties()` to iterate all properties (including on nested non-collection complex types) or manually recurse through `GetDeclaredComplexProperties()` → `complexProperty.ComplexType`.\n\n## Adding a New Annotation\n\n1. Add constant to `CoreAnnotationNames` and its `AllNames`\n2. Filter in `RuntimeModelConvention.ProcessModelAnnotations` if it's a design-time-only annotation (only used in migration operations)\n   1. If it was filtered out, add logic to the getters that throws an exception if accessed on the runtime model\n3. Filter in `CSharpRuntimeAnnotationCodeGenerator.Generate` if it can be computed lazily at runtime (e.g. based on other annotations)\n4. Propagate in `RelationalAnnotationProvider` if used in up-migrations or the relational model and `IMigrationsAnnotationProvider` if used in down-migrations\n\n## Relational Model\n\n`RelationalModel` (`src/EFCore.Relational/Metadata/Internal/RelationalModel.cs`) is a database-centric view of the EF model, mapping entity types to physical database objects: `Tables`, `Views`, `Functions`, `Queries`, and `DefaultTables`. `DefaultTables` are pseudo-table objects only used for `FromSql` queries.\n\nCreated lazily by `RelationalModelRuntimeInitializer`, accessed via `model.GetRelationalModel()`. Used by migrations (`MigrationsModelDiffer`), update and query pipelines.\n\n`RelationalAnnotationProvider` populates annotations on relational model elements. Provider subclasses (e.g., `SqlServerAnnotationProvider`) add provider-specific annotations. `IMigrationsAnnotationProvider` controls annotations used in down-migration operations.\n\n## Model Validation\n\n`ModelValidator` (`src/EFCore/Infrastructure/ModelValidator.cs`) and `RelationalModelValidator` (`src/EFCore.Relational/Infrastructure/RelationalModelValidator.cs`) run after model finalization, during `ModelRuntimeInitializer.Initialize()` between the pre- and post-validation `InitializeModel` calls.\n\n## Migration Snapshot Compatibility\n\nModel-building changes can trigger spurious migrations for users who upgrade. Two causes:\n\n1. **New metadata written to the snapshot** — old snapshots won't have it; `MigrationsModelDiffer` sees a diff. Fix: ensure absence of the annotation in an old snapshot is treated as the old default.\n2. **Annotation renamed or reinterpreted** — old snapshots produce a different model. Fix: keep backward-compatible reading logic.\n\nInspect `CSharpSnapshotGenerator` (what gets written) and `MigrationsModelDiffer` (how absence is handled). Add a snapshot round-trip test in `test/EFCore.Design.Tests/Migrations/ModelSnapshotSqlServerTest.cs`.\n\n## Testing\n\n| Area | Location |\n|------|----------|\n| Convention unit tests | `test/EFCore.Tests/Metadata/Conventions/` |\n| Metadata unit tests | `test/EFCore.Tests/Metadata/Internal/` |\n| Model builder API tests | `test/EFCore.Specification.Tests/ModelBuilding/ModelBuilderTest*.cs` |\n| Relationship discovery tests | `test/EFCore.Specification.Tests/ModelBuilding101*.cs` |\n| Model validation tests | `test/EFCore.Tests/Infrastructure/ModelValidatorTest*.cs` |\n| Compiled model tests | `test/EFCore.Specification.Tests/Scaffolding/CompiledModelTestBase.cs` |\n\n## Validation\n\n- Model builds without `InvalidOperationException` during finalization\n- All new API is covered by tests\n- Compiled model baselines update cleanly with `EF_TEST_REWRITE_BASELINES=1`\n- `ToString()` on metadata objects shows concise contents without throwing exceptions\n- No spurious migration is generated against a project with an existing snapshot\n\n<!-- File: .agents/skills/query-pipeline/SKILL.md (Tokens: ~982 | Category: anthropic-skill) -->\n---\nname: query-pipeline\ndescription: 'Implement and review EF Core query translation, projection visitors, split-query enumeration, and query regression tests. Use when changing query-pipeline code or choosing specification and provider coverage for a query regression.'\nuser-invocable: false\n---\n\n# Query Pipeline\n\n## Regression Test Ownership\n\n- Group query specification tests by a cohesive query or model trait. Do not create a generic bucket merely because tests use custom models; use the existing trait-specific hierarchy, such as owned-entity queries.\n- Inspect the specification base and provider overrides before placing a regression. Keep the LINQ query, model setup, and result assertions in the shared virtual test; provider overrides call the base and add only provider-specific baselines or established limitations.\n- A provider-only test can leave every other provider untested even when its SQL assertion is correct. Preserve override guards without adding a guard that forces unrelated redundant overrides.\n- For an optimization, cover both eligible and rejected shapes with exact result assertions in sync and async. Supply a concrete provider override and SQL baseline or established limitation; an abstract test base or expression-shape check alone does not prove execution coverage.\n\n## Translation\n\n- Translation fallback must distinguish established unsupported shapes from unexpected defects. Do not turn arbitrary exceptions into a successful fallback.\n- Check whether a failed rewrite mutated state that fallback will reuse. For test coordination, establish the actual collection, assembly, and async-flow boundaries before claiming shared static state can race; theory rows are not inherently parallel, and reset in `finally` is not mutual exclusion.\n\n## Optimizations\n\n- Match the equivalence needed by the rewrite, not blindly by expression equality.\n- Preserve context-specific null semantics. SQL UNKNOWN can be filtered like `false` in a predicate but not in a projected value or under negation; `UseRelationalNulls`, null-containing `IN`/`NOT IN`, and scalar versus composite LINQ join keys require different compensation.\n- Preserve cardinality and operator order, not just matching rows. Moving predicates across outer joins, adding keys under `Distinct`/`GroupBy`, or converting correlated APPLY to JOIN can change results; per-parent pagination must retain its partitioning and ordering, and remaining outer references must prevent decorrelation.\n- Share repeated subqueries only when their evaluation and row selection are equivalent. Volatile expressions, query filters introduced during later navigation expansion, and required-navigation joins can change evaluation count or which row survives a limit. Check determinism and row preservation before reuse, and collect candidates within their own lambda scope.\n- Preserve SQL typing and CLR result semantics separately. Remove a cast only when its store-type effect is redundant; casts on constants can establish necessary SQL typing. SQL nullable columns do not alone describe shaper nullability: `DefaultIfEmpty` on a non-nullable scalar may require `COALESCE` to its CLR default.\n- Remap dependent state when changing query shape. Subquery pushdown or join replacement must update scoped column references, predicates, orderings, projection bindings, and shapers; retain or recompute identifiers and their comparers when multiplicity or null extension changes.\n- Prove pruning safety beyond the final projection. An unused join can still filter or multiply rows, so honor explicit prunability and references from other clauses. Unreferenced columns can still define distinct/set-operation membership or a scalar subquery's result; preserve those contracts and compatible set-operation projections.\n\n## Split Queries\n\n- When changing `SplitQueryResultCoordinator`, check both `SplitQueryingEnumerable` and `GroupBySplitQueryingEnumerable`, including their synchronous and asynchronous paths. End-of-stream validation belongs at true outer-stream exhaustion, not at a group boundary or early disposal.\n- A grouped reader can reach physical EOF while assembling a final group that still must be yielded. Test that successful move separately from the subsequent terminal move, including verification failure and repeated terminal calls; cleanup must preserve the original failure.\n- Account for internal buffering as well as caller materialization when assessing memory use. Earlier split-query result sets may need buffering when the provider cannot keep multiple readers active; retrying execution strategies can also require buffering.\n- Buffering does not give separate query commands a consistent database snapshot. Concurrent writes between commands can produce an inconsistent result graph; consider snapshot or serializable transactions when consistency is required, accounting for provider support and transaction costs.\n- Prove cross-command consistency with a writer transaction and an explicit barrier between reads, not sleeps or a prose-only scenario. Assert a root/child value combination, not just matching keys; state the isolation and retry-strategy boundaries of the test.\n\n## Validation\n\n- `ToQueryString()` shows generated SQL without executing\n- `ExpressionPrinter` dumps expression trees at any pipeline stage\n- SQL baselines verified via `AssertSql()` in provider functional tests and the generated SQL corresponds to the LINQ query in the base method\n\n<!-- File: .agents/skills/run-apichief/SKILL.md (Tokens: ~1325 | Category: anthropic-skill) -->\n---\nname: run-apichief\ndescription: 'Run ApiChief in the EF Core repo to emit baselines, summaries, deltas, review files, or breaking-change checks. Use when refreshing `*.baseline.json`, preparing API review artifacts, or validating API changes.'\nuser-invocable: false\n---\n\n# Run ApiChief\n\nUse the ApiChief tool documented at `eng/Tools/ApiChief/README.md` to inspect or refresh EF Core public API baselines for projects under `src/`.\n\nApiChief can run against either a compiled assembly or a previously emitted baseline JSON file. Prefer the repo-local `.dotnet` SDK and the checked-in build scripts in this repo.\n\n## Commands\n\n| Command | Description | Extra arguments |\n| --- | --- | --- |\n| `emit baseline` | Emit a JSON API baseline | `-o <file>` |\n| `emit summary` | Emit a human-readable API summary | `-o <file>`, `-x` |\n| `emit review` | Emit API review files | `-o <dir>`, `-n` |\n| `emit delta` | Emit a delta against an existing baseline, or markdown diff review files | `<baseline-path>`, `-o <file-or-dir>`, `--diff` |\n| `check breaking` | Fail if breaking changes exist vs. a baseline | `<baseline-path>` |\n\nDefault to `emit baseline` if the user only asks to \"run ApiChief\".\n\n## Workflow\n\n### 1. Identify the target project(s)\n\n- Match user intent against project folders under `src/`.\n- Ask for clarification only if the target is ambiguous.\n- The checked-in baseline path convention in this repo is `src/<ProjectName>/<ProjectName>.baseline.json`.\n- If asked just to update the baselines, run EFCore.ApiBaseline.Tests tests and skip the rest of the steps below.\n\n### 2. Prepare the environment\n\nAlways initialize the repo environment before building or running the tool:\n\n```powershell\n.\\restore.cmd\n. .\\activate.ps1\ndotnet build .\\eng\\Tools\\ApiChief\\ApiChief.csproj --nologo --verbosity q\n```\n\nOn Bash:\n\n```bash\n./restore.sh\n. ./activate.sh\ndotnet build ./eng/Tools/ApiChief/ApiChief.csproj --nologo --verbosity q\n```\n\n### 3. Ensure the target binaries exist\n\nApiChief operates on built assemblies. If the target project has not been built yet, build it first.\n\nPreferred options:\n\n```powershell\n# Refreshes checked-in baselines after the normal build\n.\\build.cmd -c Debug\n\n# Or build a single project when working narrowly\ndotnet build .\\src\\<ProjectName>\\<ProjectName>.csproj --nologo --verbosity q\n```\n\nUse the highest available `net*` TFM under `artifacts/bin/<ProjectName>/<Configuration>/` by default. Avoid `netstandard*` and `net4*` targets unless the user explicitly asks for them.\n\n### 4. Locate the built ApiChief binary and target assembly\n\n```powershell\n$dotnet = \".\\\\.dotnet\\\\dotnet\"\n$apiChiefProject = \".\\\\eng\\\\Tools\\\\ApiChief\\\\ApiChief.csproj\"\n$apiChief = (& $dotnet msbuild $apiChiefProject --getProperty:TargetPath -p:Configuration=Debug --nologo).Trim()\n\n$name = \"<ProjectName>\"\n$tfm = Get-ChildItem \".\\\\artifacts\\\\bin\\\\$name\\\\Debug\" -Directory |\n    Where-Object { $_.Name -match '^net\\d+\\.\\d+$' } |\n    Sort-Object { [version]($_.Name -replace '^net', '') } -Descending |\n    Select-Object -First 1 -ExpandProperty Name\n\n$assemblyName = (& $dotnet msbuild \".\\\\src\\\\$name\\\\$name.csproj\" --getProperty:AssemblyName -p:Configuration=Debug --nologo).Trim()\nif ([string]::IsNullOrWhiteSpace($assemblyName))\n{\n    $assemblyName = $name\n}\n\n$assemblyPath = \".\\\\artifacts\\\\bin\\\\$name\\\\Debug\\\\$tfm\\\\$assemblyName.dll\"\n```\n\nBefore running, report the selected TFM if it matters for the task.\n\n### 5. Run the requested ApiChief command\n\n```powershell\n# Emit a baseline\n& $dotnet $apiChief $assemblyPath emit baseline -o \".\\\\src\\\\$name\\\\$name.baseline.json\"\n\n# Emit a summary\n& $dotnet $apiChief $assemblyPath emit summary\n\n# Emit a delta\n& $dotnet $apiChief $assemblyPath emit delta \".\\\\src\\\\$name\\\\$name.baseline.json\" -o \".\\\\artifacts\\\\tmp\\\\$name.delta.json\"\n\n# Check for breaking changes\n& $dotnet $apiChief $assemblyPath check breaking \".\\\\src\\\\$name\\\\$name.baseline.json\"\n\n# Emit API review artifacts\n& $dotnet $apiChief $assemblyPath emit review -o \".\\\\artifacts\\\\tmp\\\\API.$name\"\n\n# Emit GitHub-friendly markdown diff files against a baseline\n& $dotnet $apiChief $assemblyPath emit delta \".\\\\src\\\\$name\\\\$name.baseline.json\" --diff -o \".\\\\artifacts\\\\tmp\\\\API.$name.Diff\"\n```\n\n`emit delta` also supports passing a `.json` file as the current input instead of a DLL.\n\n### 6. Review or clean up baseline changes\n\nAfter `emit baseline`:\n\n- preserve the original BOM and trailing newline behavior of the committed file\n- revert version-only diffs in the `\"Name\"` field\n- inspect removed `//` instruction comments in previous baselines and carry forward any still-needed manual edits\n- if those comments reference GitHub issues, check whether the underlying issue is still open before reapplying the workaround\n\n### 7. Report results clearly\n\n- list the processed project(s)\n- show the chosen TFM(s)\n- report the output path(s)\n- for `check breaking`, state pass/fail\n- for `emit delta` and `emit delta --diff`, mention that exit code `0` means changes, `2` means no changes, and `-1` means an error\n- prefer `emit delta --diff` output because it generates ready-to-post ```diff fenced markdown split across per-type `.md` files\n\n<!-- File: .agents/skills/scaffolding/SKILL.md (Tokens: ~315 | Category: anthropic-skill) -->\n---\nname: scaffolding\ndescription: 'Implementation details for EF Core scaffolding (reverse engineering). Use when changing ef dbcontext scaffold pipeline implementation, database schema reading, CSharpModelGenerator, or related classes.'\nuser-invocable: false\n---\n\n# Scaffolding\n\nGenerates C# code from database schemas (reverse engineering).\n\n## When Not to Use\n\n- Working on compiled model generation (`dotnet ef dbcontext optimize`)\n\n## Reverse Engineering\n\nPipeline: `IDatabaseModelFactory` (reads schema) → `IScaffoldingModelFactory` (builds EF model) → `IModelCodeGenerator` (generates C#)\n- `IReverseEngineerScaffolder` — orchestrates full pipeline\n\n## Schema Query Compatibility\n\nProvider schema readers often query one-to-many metadata tables. Preserve anti-semi semantics when adapting SQL for a limited engine: a `LEFT JOIN` containing the complete excluded-property predicate in `ON`, followed by a null filter on a non-nullable joined key, is equivalent to `NOT EXISTS`. Unrelated metadata rows do not join; any matching excluded row makes the joined key non-null and excludes the object. Do not move parts of the excluded-property predicate to `WHERE` or join all metadata rows and filter individual rows afterward. An equivalent non-correlated anti-set form, such as `NOT IN (SELECT key ... WHERE excluded-condition)`, also works when the subquery cannot return null keys. Cover objects with no metadata, unrelated metadata only, the excluded property only, and both excluded and unrelated properties.\n\n<!-- File: .agents/skills/servicing-pr/SKILL.md (Tokens: ~300 | Category: anthropic-skill) -->\n# servicing-pr\n\nPath: `.agents/skills/servicing-pr/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/servicing-pr/SKILL.md)\n\n<!-- File: .agents/skills/sqlite-adonet/SKILL.md (Tokens: ~300 | Category: anthropic-skill) -->\n# sqlite-adonet\n\nPath: `.agents/skills/sqlite-adonet/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/sqlite-adonet/SKILL.md)\n\n<!-- File: .agents/skills/tooling/SKILL.md (Tokens: ~300 | Category: anthropic-skill) -->\n# tooling\n\nPath: `.agents/skills/tooling/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/tooling/SKILL.md)\n\n<!-- File: .agents/skills/triage/SKILL.md (Tokens: ~300 | Category: anthropic-skill) -->\n# triage\n\nPath: `.agents/skills/triage/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/triage/SKILL.md)\n\n<!-- File: .agents/skills/update-pipeline/SKILL.md (Tokens: ~300 | Category: anthropic-skill) -->\n# update-pipeline\n\nPath: `.agents/skills/update-pipeline/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.agents/skills/update-pipeline/SKILL.md)\n\n<!-- File: .github/skills/agentic-workflows/SKILL.md (Tokens: ~300 | Category: anthropic-skill) -->\n# agentic-workflows\n\nPath: `.github/skills/agentic-workflows/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/.github/skills/agentic-workflows/SKILL.md)\n\n<!-- File: eng/harness-evaluation/skills/change-tracking/eval.yaml (Tokens: ~300 | Category: anthropic-skill) -->\n# Change-tracking Skill\n\nPath: `eng/harness-evaluation/skills/change-tracking/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/change-tracking/eval.yaml)\n\n<!-- File: eng/harness-evaluation/skills/code-review/eval.yaml (Tokens: ~300 | Category: anthropic-skill) -->\n# Code-review Skill\n\nPath: `eng/harness-evaluation/skills/code-review/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/code-review/eval.yaml)\n\n<!-- File: eng/harness-evaluation/skills/code-review/fixtures/query-comment/context/review-context.md (Tokens: ~300 | Category: anthropic-skill) -->\n# Context Skill\n\nPath: `eng/harness-evaluation/skills/code-review/fixtures/query-comment/context/review-context.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/code-review/fixtures/query-comment/context/review-context.md)\n\n<!-- File: eng/harness-evaluation/skills/cosmos-provider/eval.yaml (Tokens: ~300 | Category: anthropic-skill) -->\n# Cosmos-provider Skill\n\nPath: `eng/harness-evaluation/skills/cosmos-provider/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/cosmos-provider/eval.yaml)\n\n<!-- File: eng/harness-evaluation/skills/make-custom-agent/eval.yaml (Tokens: ~300 | Category: anthropic-skill) -->\n# Make-custom-agent Skill\n\nPath: `eng/harness-evaluation/skills/make-custom-agent/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/make-custom-agent/eval.yaml)\n\n<!-- File: eng/harness-evaluation/skills/make-github-actions-workflow/eval.yaml (Tokens: ~300 | Category: anthropic-skill) -->\n# Make-github-actions-workflow Skill\n\nPath: `eng/harness-evaluation/skills/make-github-actions-workflow/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/make-github-actions-workflow/eval.yaml)\n\n<!-- File: eng/harness-evaluation/skills/make-instructions/eval.yaml (Tokens: ~300 | Category: anthropic-skill) -->\n# Make-instructions Skill\n\nPath: `eng/harness-evaluation/skills/make-instructions/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/make-instructions/eval.yaml)\n\n<!-- File: eng/harness-evaluation/skills/make-skill/eval.yaml (Tokens: ~300 | Category: anthropic-skill) -->\n# Make-skill Skill\n\nPath: `eng/harness-evaluation/skills/make-skill/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/make-skill/eval.yaml)\n\n<!-- File: eng/harness-evaluation/skills/migrations/eval.yaml (Tokens: ~300 | Category: anthropic-skill) -->\n# Migrations Skill\n\nPath: `eng/harness-evaluation/skills/migrations/eval.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/dotnet/efcore/HEAD/eng/harness-evaluation/skills/migrations/eval.yaml)\n\n<!-- ... +22 more modular skills available via /api/skills/dotnet/efcore?path={path} -->\n</yakaai_skills>"}