Documentation Check / docs-check (push) Has been cancelled
golangci-lint / lint (push) Has been cancelled
GoReleaser Release / release (push) Has been cancelled
Publish to MCP Registry / publish (push) Has been cancelled
CodeQL / Analyze (go) (push) Has been cancelled
CodeQL / Analyze (actions) (push) Has been cancelled
CodeQL / Analyze (javascript) (push) Has been cancelled
MCP Server Diff / mcp-diff (push) Has been cancelled
MCP Server Diff / mcp-diff-http (push) Has been cancelled
Build and Test Go Project / build (macos-latest) (push) Has been cancelled
Build and Test Go Project / build (ubuntu-latest) (push) Has been cancelled
Build and Test Go Project / build (windows-latest) (push) Has been cancelled
Docker / build (push) Has been cancelled
Add a regression test locking in the capability contract set by NewMCPServer:
tools, prompts, and resources are advertised without list-changed
notifications, the deprecated logging capability is not advertised, and the
inferred completions capability is preserved. Covers both the stdio path (full
inventory, items present) and the HTTP path (inventory emptied for the
discovery request), which share the same NewMCPServer entry point.
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
Copilot-Session: 95b8432c-f280-472e-a242-d3ca6dc31f19
The server exposes a static set of tools, prompts, and resources and never
mutates them at runtime, so it never emits list_changed notifications. When
capabilities are left unset, the go-sdk infers listChanged:true from the
presence of items and advertises tools/prompts/resources list-change support
we don't actually provide - and the 2026-07-28 spec (subscriptions/listen)
tightens expectations around this.
Declare empty tools/prompts/resources capabilities in NewMCPServer so both the
stdio and remote servers advertise honestly. The remote HTTP handler already
set these explicitly; that duplication is now removed in favour of the shared
default, leaving only the remote-specific schema cache.
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
Copilot-Session: 95b8432c-f280-472e-a242-d3ca6dc31f19
Move from the v1.7.0-pre.3 pre-release to the final v1.7.0 release, which
consolidates the pre-releases with no further changes. Regenerate the
third-party license files to reflect the new version tag.
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
Copilot-Session: 95b8432c-f280-472e-a242-d3ca6dc31f19
* Promote fields parameter beyond Insiders
Keep fields_param as an independently controlled feature flag while removing it from the Insiders expansion.
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
* Make fields parameter available by default
Remove the fields_param feature flag and legacy tool variants so selected read tools always advertise and honor fields.
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
Copilot-Session: 5c43cc70-27b5-47b4-bbd1-99d20f42d61b
---------
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
Copilot-Session: 5c43cc70-27b5-47b4-bbd1-99d20f42d61b
Keep PEM loading and installation-token provider construction at the CLI leaf, then pass a generic refreshing token provider through the existing HTTP transports. Rebase the feature onto current main and keep the HTTP command unchanged.
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
Copilot-Session: 646357dd-c89f-4973-9a5c-e6c5fc18818c
Add non-interactive GitHub App installation authentication to the stdio
server, so headless deployments (CI, Kubernetes, background agents) can
authenticate without a browser, device code, or elicitation. This is the
outstanding follow-up tracked in #1333: OAuth login shipped the interactive
user-to-server flows, but PEM-based server-to-server auth was still needed to
remove the interactive requirement.
The new internal/githubapp package signs a short-lived RS256 JWT with the
app's private key, exchanges it for an installation access token, and refreshes
it transparently before expiry. It exposes a Provider whose AccessToken method
mirrors oauth.Manager so it plugs into the existing BearerAuthTransport token
provider. Only the standard library and golang.org/x/oauth2 are used.
The private key is injected safely: a file path (GITHUB_APP_PRIVATE_KEY_PATH,
preferred — mountable as a secret and kept off argv and out of the environment)
or an inline GITHUB_APP_PRIVATE_KEY env var. There is intentionally no flag for
the key contents, which would otherwise leak via the process command line.
App auth is mutually exclusive with a PAT and with OAuth login. A loud startup
warning and a dedicated docs page (docs/github-app-auth.md, with Docker and
Kubernetes examples) cover the security considerations: this injects a
high-privilege credential alongside the agent and is not recommended without an
independent security review.
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
* build: require Go 1.25.12
Ensure setup-go and GoReleaser use the patched Go toolchain for release binaries.
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
Copilot-Session: 0b2aa497-b47d-464a-b132-af0dcaf2b621
* build(ui): update fast-uri to 3.1.4
Resolve the high-severity host-confusion advisories reported by npm audit.
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
Copilot-Session: 0b2aa497-b47d-464a-b132-af0dcaf2b621
---------
Co-authored-by: Ross Tarrant <rosstarrant@github.com>
- Assert field.NodeID in Test_ResolveProjectFieldByName_Success.
- Add Test_ResolveProjectFieldByName_NodeIDsForAllVariants covering
single-select, iteration, and generic fields (asserts NodeID + DataType).
- Rename Test_ResolveProjectItemIDByIssueNumber_Success to
Test_ResolveProjectItemByIssueNumber_Success to match the resolver it calls.
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
Copilot-Session: 89f897b0-115f-4435-a071-46fb6c49be86
Split out of #2903 as a small prerequisite refactor.
- Add a NodeID field to ResolvedField, populated for all three field
variants in listAllProjectFields.
- Refactor resolveProjectItemIDByIssueNumber into a thin wrapper over a
new resolveProjectItemByIssueNumber that also returns the item node ID,
delegating to resolveProjectItemByIssueNumberWithProjectID for an
already-resolved project ID. The projectItems query now selects the
item node ID alongside its full database ID.
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
Copilot-Session: 89f897b0-115f-4435-a071-46fb6c49be86
* Add opt-in intent-aware Copilot issue assignment tool
Add `assign_copilot_to_issue_with_intent` in a new non-default toolset
`copilot_issue_intents`. The tool uses GraphQL's object-form
`assignees: [AssigneeUpdateInput!]` so intent metadata (rationale,
confidence, is_suggestion) is attached to the Copilot entry only, while
existing assignees are preserved.
- Reuses the existing Copilot actor lookup, target-repository
resolution, base_ref, custom_instructions, GraphQL-Features header,
and direct-assignment PR polling behavior.
- `is_suggestion: true` records a pending Copilot assignment intent,
returns a suggestion-shaped result, and does not launch Copilot or
poll for a linked PR.
- `rationale` is capped at 280 characters (schema + runtime);
`confidence` is validated against `LOW`/`MEDIUM`/`HIGH`.
- Toolset is non-default so its inputs do not add schema bloat to the
default tool surface; available via `copilot_issue_intents`,
`all`, or explicit tool selection.
Includes unit tests for direct assignment (with existing assignees and
with base_ref/custom_instructions), the suggestion path, invalid
rationale length, invalid confidence, and Copilot-not-available; a
generated toolsnap; regenerated docs; and an e2e test for the
suggestion path.
Refs: github/plan-track-agentic-toolkit#683
* Address review: tighten description, require intent fields
Per review feedback on #2909:
- Trim the tool description to mirror assign_copilot_to_issue and add
"Prefer this tool over assign_copilot_to_issue when available",
removing the verbose is_suggestion narrative from the schema.
- Make rationale, confidence, and is_suggestion required inputs (schema
and runtime). is_suggestion is now always sent explicitly on the
Copilot AssigneeUpdateInput entry.
- Update unit tests to supply the newly-required fields and cover the
missing-rationale and missing-confidence rejection paths.
- Regenerate toolsnap and README.
* Address review: dedupe copilot, require is_suggestion, update doc link
Per @RossTarrant review feedback on #2909:
- Reject requests where `is_suggestion` is omitted from the raw args
before decoding. `mapstructure.WeakDecode` defaults missing bools
to false, which would silently launch Copilot instead of recording a
suggestion. Presence-check the raw map so callers make the choice
explicit.
- Skip the copilot-swe-agent actor when copying existing assignees so
we don't send its actorId twice (once without metadata and once with
intent metadata) when Copilot is already assigned.
- Update the stale about-assigning-tasks-to-copilot reference to the
redirect target (about-cloud-agent). Applied to the const message,
both tool descriptions, and the e2e/unit-test literals that assert
on that message.
New unit tests cover the missing-is_suggestion rejection and the
copilot-dedup behavior. Regenerated toolsnaps.
Adopt the pre.3 protocol correctness fixes without changing server wiring or MCP tool schemas. Update exact SDK license references for all release platforms.
Copilot-Session: f399f533-3d1f-4c76-872b-f9813729a61f
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
Move Octicon base64 encoding to the generation script and embed the generated lookup manifest for zero-allocation reads.
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
Copilot-Session: 5557f448-5cc1-46ce-b5ad-36f9e2e224e0
Move OAuth interception into tool-handler middleware so go-sdk finalizes
multi-round-trip results with resultType input_required. Correlate responses to
a per-flow ID, retire cancellations synchronously, and ignore late completions
from stale flows.
Also preserve actionable URLs for form-only clients and add wire-level,
concurrency, and real manager lifecycle coverage.
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
Copilot-Session: 18e70efa-1b2d-4290-ba51-b82998db4ff8
The go-sdk 1.7.0-pre.2 bump defaults to MCP protocol 2026-07-28, which per
SEP-2322 forbids the server from initiating JSON-RPC requests (including
`elicitation/create`) while serving a request. The OAuth login flow presents
the authorization prompt via `ServerSession.Elicit`, so on 2026-07-28 sessions
it now errors ("cannot be sent while serving a request ... return an
InputRequests map instead"), which broke TestSessionPrompterPromptActions and
would break real 2026-07-28 clients (stdio included, since server/discover is
transport-agnostic).
Migrate the OAuth middleware to multi-round-trip requests (MRTR) while keeping
pre-2026-07-28 clients unchanged:
- Legacy clients (< 2026-07-28) keep presenting the prompt via server-initiated
elicitation exactly as before.
- Modern clients (>= 2026-07-28) receive the authorization prompt as an
`InputRequests` elicitation returned from the tool call; the client fulfills
it and retries, and the middleware then awaits the token and proceeds. This
keeps the authorization URL out of the model context.
oauth.Manager gains AwaitToken (resume half of MRTR) and Cancel (tear down on
decline). Tests cover the accept/decline/no-capability MRTR paths and assert
that server-initiated elicitation is reported undeliverable on 2026-07-28.
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
Copilot-Session: 18e70efa-1b2d-4290-ba51-b82998db4ff8
* Let agents address Project fields, single-select options, and item field values by name through the GitHub MCP server
* Adding a method to resolve params resolveItemIDFromIssueArgs
* Adding the DatabaseID to be able to match the graphQL
* Changing the parsing to strconv.ParseInt
* Changing description.
* update readme
* Fixing copilot comments
* Adding Case-insensitive matching and fields + field_names guard
* running snaps and readme
* Add fields param to six more list/search tools
Extend the optional `fields` response-filtering parameter (gated behind the
`fields_param` feature flag, with adoption/savings telemetry) to six more read
tools, following the dual-variant pattern already used by search_code and
get_file_contents:
- list_issues, list_pull_requests, list_commits, list_releases
- search_issues, search_pull_requests
For each tool, `X` is the flag-enabled variant that advertises `fields` and
filters each result item to the requested subset, while `LegacyX` exposes the
original schema and never filters, acting as a kill switch when the flag is off.
Exactly one variant survives inventory filtering for any flag state via mutually
exclusive FeatureFlagEnable / FeatureFlagDisable annotations. Wrapped responses
(list_issues, search_issues, search_pull_requests) preserve their count /
pagination envelope and only filter the item list; bare-array responses keep
their array shape.
Filtering reuses the shared filterEachField helper. A new fieldsSchemaProperty
helper builds the `fields` schema (search_code and get_file_contents now use it
too), and a shared recordFieldsUsageFor helper centralizes the telemetry
full-size computation. Each field enum lists only the JSON fields the specific
tool actually emits: list_commits omits stats/files (requested without per-file
detail) and list_issues lists only the fields its GraphQL fragment populates.
Adds per-tool field-filtering, telemetry, and Legacy definition tests, extends
the mutual-exclusivity gating test to all eight gated tools, and regenerates the
`_ff_fields_param` toolsnaps and feature-flag docs.
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
* Remove duplicate tool doc comments
Address review: drop the leftover one-line doc comment above each dual-variant
tool constructor (list_issues, list_pull_requests, list_commits, list_releases,
search_issues, search_pull_requests); the detailed variant comment remains.
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
---------
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
* Add fields param to search_code and get_file_contents
Add an optional `fields` array parameter to the `search_code` and
`get_file_contents` tools so callers can request only the fields they
need, reducing tool response size and context usage.
- search_code: filters each result item to the selected fields while
preserving the total_count / incomplete_results wrapper.
- get_file_contents: filters each directory entry when listing a
directory; ignored for single-file responses.
Adds shared filterFields / filterEachField helpers and per-tool field
enums, plus unit tests and regenerated toolsnaps and docs.
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
* Gate fields param behind fields_param flag and add usage telemetry
Register search_code and get_file_contents as two mutually exclusive
variants gated by the new `fields_param` feature flag, following the
existing dual-variant flag pattern:
- The flag-enabled variant advertises the optional `fields` parameter and
filters each result to the requested subset. It owns the
`<tool>_ff_fields_param` toolsnap.
- The Legacy* variant exposes the original schema with no `fields`
parameter and never filters, acting as a kill switch when the flag is
off. It owns the canonical toolsnap.
Add best-effort, low-cardinality telemetry at each tool's filter point to
measure adoption and realized savings:
- `mcp.fields.tool_call` (increment) tagged by tool and whether the
response was filtered.
- `mcp.fields.bytes_full` / `bytes_sent` / `bytes_saved` (counters) tagged
by tool, emitted only when a response was filtered.
Tags are limited to `tool` and `filtered` to bound cardinality; repo,
owner, user, query, and the requested field list are never tagged. The
local server discards these via the noop metrics sink, while hosted
deployments inject a real sink. Metrics accessors now fall back to a noop
sink when no exporter is configured so emitting telemetry never panics.
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
* Drop mcp.fields.bytes_saved metric
Remove the mcp.fields.bytes_saved counter. It is derivable on the
dashboard from the two remaining byte counters, since
sum(bytes_full) - sum(bytes_sent) equals the total saved at any rollup,
so emitting it separately is redundant. Keeping only bytes_full and
bytes_sent shrinks the emitted telemetry surface.
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
---------
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
* Reimplement issue dependencies on go-github v89 REST API
Issue dependencies (blocked_by / blocking) were implemented on GraphQL via
githubv4. Because the pinned githubv4 library predates the dependency
mutations, the code hand-declared AddBlockedByInput / RemoveBlockedByInput
and resolved issue numbers to node IDs with a custom aliased query.
go-github v89 adds first-class REST methods (ListBlockedBy, ListBlocking,
AddBlockedBy, RemoveBlockedBy), so switch issue_dependency_read and
issue_dependency_write to those. This removes the workaround, aligns the
tools with the rest of the REST-based issue tooling, and simplifies tests.
- Rewrite issue_dependencies.go on REST: page-based pagination for reads,
and a single Issues.Get to resolve the blocking issue's database ID for
writes. Preserve the tool surface, self-dependency guard and cross-repo
support.
- Rewrite the issue dependency tests on the REST mock helpers.
- Regenerate the read toolsnap (cursor -> page pagination) and docs.
Refs #950
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
* Normalize issue dependency ref state to match other tools
The REST issue-dependency endpoints return lower-case issue states
(open/closed), whereas the previous GraphQL implementation and the
sibling get_parent tool populate MinimalIssueRef.State from the GraphQL
IssueState enum (OPEN/CLOSED). Upper-case the state in
issueToDependencyRef so the field stays consistent across every tool that
emits a MinimalIssueRef, and guard against a nil issue while here.
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
---------
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
* chore(deps): bump go-github v87 -> v89 and resolve breaking changes
Bumps google/go-github from v87 to v89 across the module and fixes the
resulting breaking changes. No tool or behavior changes.
- Rewrite all import paths go-github/v87 -> go-github/v89.
- gists.go: Gists.Create now takes CreateGistRequest by value and
Gists.Edit is renamed to Gists.Update taking UpdateGistRequest.
- repositories_test.go: adapt to RepositoryRelease fields that became
value types in v89 (ID, TagName, Draft).
- Regenerate third-party license files for the new module path.
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
* Don't clear gist description on update when omitted
update_gist always sent Description as a pointer to the OptionalParam
zero value (""), so omitting description would overwrite an existing gist
description with an empty string. Only set UpdateGistRequest.Description
when the caller actually provided the argument; an explicit empty string
still clears it. Adds a test asserting the description key is absent from
the PATCH body when omitted and present when set.
This addresses a pre-existing behavior surfaced while migrating to the
v89 gist request types.
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
---------
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
* Enrich issue_read get with hierarchy relationship signals
The default issue_read `get` payload surfaced no hierarchy data, forcing
agents to drop to raw REST (parent_issue_url) or scan sibling sub_issues
to discover relationships. Enrich `get` with a layered, zero-extra-round-trip
relationship signal derived from a single combined GraphQL query:
- has_parent / has_children: cheap, always-emitted routing booleans
(addresses Sam Morrow's #2726 review note).
- parent: compact ref (number/title/state/url/repository) mirroring the
existing get_parent payload keys; omitted when there is no parent.
- sub_issues_summary: native subIssuesSummary counts (total/completed/
percent_completed); omitted when there are no sub-issues.
The single-issue field-values GraphQL call in GetIssue is replaced by one
combined query (fetchIssueReadEnrichment) returning field values + parent +
subIssuesSummary, so `get` adds no round-trips. Enrichment is best-effort:
a query failure still returns the base issue and never fails `get`. Parent
titles are sanitized (parent may be cross-repo) and redacted under lockdown
mode unless the parent content can be verified as safe; numeric/structural
fields and counts stay intact. get_parent / sub_issue_write behavior is
unchanged; tool descriptions clarify hierarchy is read here but written via
sub_issue_write (no writable parent field).
Refs github/planning-tracking#3306
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
* Tighten hierarchy tool wording
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
* Omit unverified parent under lockdown instead of redacting title
Align issue_read get parent enrichment with the codebase's existing
lockdown patterns: rather than introducing a third, redaction-with-sentinel
behavior, omit the whole parent reference when its (possibly cross-repo)
content cannot be verified safe. This mirrors how unsafe comments, sub-issues,
and PR reviews are filtered out. has_parent stays true so an agent can still
route to get_parent.
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
* Restore explicit issue read query matcher
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
* Omit hierarchy flags when enrichment fails
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
* Address hierarchy review nits
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
---------
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Co-authored-by: Roberto Nacu <kerobbi@github.com>