Skip to content

fix: don't derive write-sink guard-policy for repos="public"/"all", add guard-policies to stdio schema, and smoke-test guard policy#20749

Closed
Copilot wants to merge 5 commits intomainfrom
copilot/review-min-integrity-implementation
Closed

fix: don't derive write-sink guard-policy for repos="public"/"all", add guard-policies to stdio schema, and smoke-test guard policy#20749
Copilot wants to merge 5 commits intomainfrom
copilot/review-min-integrity-implementation

Conversation

Copy link
Contributor

Copilot AI commented Mar 13, 2026

Two bugs in the repos/secrecy/min-integrity guard policy implementation for the GitHub tool, plus a smoke test to exercise the new guard policy feature.

Issues

Invalid write-sink pattern for global repos keywords: repos="public" produced accept: ["private:*"] (and after an intermediate fix, accept: ["public:*"]) in the derived safe-outputs write-sink policy. However, the safeoutputs server requires owner-scoped patterns like "public:owner/*" or "public:owner/repo" — bare wildcards without an owner component are not valid scopes. The global string keywords "all" and "public" cannot be expressed as owner-scoped patterns, so no write-sink guard-policy should be derived for them.

Schema gap: stdioServerConfig in the public MCP gateway schema (docs/public/schemas/mcp-gateway-config.schema.json) had additionalProperties: false but no guard-policies property, despite the compiler emitting it for local (Docker) mode. httpServerConfig already had the field.

Changes

  • mcp_github_config.go: Fix deriveSafeOutputsGuardPolicyFromGitHub so that:
    • repos="public" or repos="all" → no write-sink guard-policy derived (global keywords cannot be expressed as owner-scoped patterns; consistent with docs: "If you use repos: all or repos: public, no safeoutputs guard-policy is derived")
    • Array of patterns → accept: ["private:owner/repo", "private:owner/*", ...] (owner-scoped, unchanged)
    • Single specific string pattern (e.g., "owner/repo") → accept: ["private:owner/repo"] (owner-scoped, unchanged)
  • docs/public/schemas/mcp-gateway-config.schema.json: Add guard-policies to stdioServerConfig properties, consistent with httpServerConfig.
  • safeoutputs_guard_policy_test.go: Update expected values — repos="public" and repos="all" now expect nil (no policy derived).
  • .github/workflows/smoke-copilot.md: Add repos: public and min-integrity: approved guard policy to the smoke-copilot workflow to exercise the feature end-to-end.
# repos="public" / repos="all": no write-sink derived (bare wildcard not owner-scoped)
tools:
  github:
    repos: public
    min-integrity: approved
# safeoutputs write-sink: not generated ← correct

# repos as array: owner-scoped accept entries derived
tools:
  github:
    repos:
      - "myorg/private-repo"
      - "myorg/*"
    min-integrity: approved
# safeoutputs write-sink: accept: ["private:myorg/private-repo", "private:myorg/*"]  ← correct
Original prompt

Review the repos/secrecy/min-integrity implementation for the github tool according to the MCP gateway specification


💡 You can make Copilot smarter by setting up custom instructions, customizing its development environment and configuring Model Context Protocol (MCP) servers. Learn more Copilot coding agent tips in the docs.



✨ PR Review Safe Output Test - Run 23033417149

💥 [THE END] — Illustrated by Smoke Claude ·

Copilot AI and others added 2 commits March 13, 2026 02:00
Co-authored-by: pelikhan <4175913+pelikhan@users.noreply.github.com>
…ic schema

Co-authored-by: pelikhan <4175913+pelikhan@users.noreply.github.com>
Copilot AI changed the title [WIP] Review min-integrity implementation for GitHub tool fix: correct write-sink secrecy level for repos="public" and add guard-policies to stdio schema Mar 13, 2026
Copilot AI requested a review from pelikhan March 13, 2026 02:17
@pelikhan
Copy link
Contributor

@copilot add

repos: public
min-integrity: approved

to smoke-copilot

…opilot

Co-authored-by: pelikhan <4175913+pelikhan@users.noreply.github.com>
Copy link
Contributor Author

Copilot AI commented Mar 13, 2026

@copilot add

...

Done in ee9c867. Added repos: public and min-integrity: approved to the github: tool in smoke-copilot. The compiled lock file correctly shows:

  • allow-only: { repos: "public", min-integrity: "approved" } for the GitHub MCP server
  • write-sink: { accept: ["public:*"] } for safe-outputs (using our repos="public"public:* fix)

Copilot AI changed the title fix: correct write-sink secrecy level for repos="public" and add guard-policies to stdio schema fix: correct write-sink secrecy level for repos="public", add guard-policies to stdio schema, and smoke-test guard policy Mar 13, 2026
@pelikhan pelikhan added the smoke label Mar 13, 2026
@github-actions
Copy link
Contributor

github-actions bot commented Mar 13, 2026

✅ All tools validated successfully! Agent Container Smoke Test confirms agent container is ready.

@github-actions
Copy link
Contributor

📰 BREAKING: Smoke Copilot is now investigating this pull request. Sources say the story is developing...

@github-actions
Copy link
Contributor

github-actions bot commented Mar 13, 2026

🎬 THE ENDSmoke Claude MISSION: ACCOMPLISHED! The hero saves the day! ✨

@github-actions
Copy link
Contributor

github-actions bot commented Mar 13, 2026

🌑 The shadows whisper... Smoke Codex failed. The oracle requires further meditation...

@github-actions
Copy link
Contributor

Agent Container Tool Check

Tool Status Version
bash 5.2.21
sh available
git 2.53.0
jq 1.7
yq 4.52.4
curl 8.5.0
gh 2.87.3
node 20.20.0
python3 3.12.3
go 1.24.13
java 10.0.102
dotnet 10.0.102

Result: 12/12 tools available ✅

Overall Status: PASS

🔧 Tool validation by Agent Container Smoke Test ·

@github-actions
Copy link
Contributor

Smoke Test Results — Run §23033417149

Test Status
GitHub MCP
GH CLI (mcpscripts)
Serena MCP (16+ symbols)
Make Build
Playwright (github.com)
Tavily Search
File Write + Bash
Discussion Comment
Agentic Workflows MCP
Update PR Body (#11)
PR Review Comments (#12)
Submit PR Review (#13)
Resolve Thread (#14) ⚠️ skipped
Add Reviewer (#15)
Push to PR Branch (#16)
Close PR (#17) ⚠️ skipped

Overall: PARTIAL (15 ✅, 2 ⚠️ skipped, 0 ❌)

💥 [THE END] — Illustrated by Smoke Claude ·

Copy link
Contributor

@github-actions github-actions bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💥 Automated smoke test review - all systems nominal!

💥 [THE END] — Illustrated by Smoke Claude

@github-actions
Copy link
Contributor

📰 VERDICT: Smoke Copilot has concluded. All systems operational. This is a developing story. 🎤

@pelikhan
Copy link
Contributor

Review this error message:

deriveSafeOutputsGuardPolicyFromGitHub() in pkg/workflow/mcp_github_config.go generates "public:*" for repos="public", but the safeoutputs server requires owner-scoped patterns like "public:github/*" or "public:owner/repo". The bare * wildcard is not a valid scope.

@copilot

Update compiler

…id bare wildcard scope)

Co-authored-by: pelikhan <4175913+pelikhan@users.noreply.github.com>
Copy link
Contributor Author

Copilot AI commented Mar 13, 2026

Review this error message:

deriveSafeOutputsGuardPolicyFromGitHub() in pkg/workflow/mcp_github_config.go generates "public:*" for repos="public", but the safeoutputs server requires owner-sco...

Fixed in 4b900f8. For repos="public" and repos="all" (global string keywords), deriveSafeOutputsGuardPolicyFromGitHub now returns nil — no write-sink guard-policy is derived, since the safeoutputs server requires owner-scoped patterns ("prefix:owner/repo") and there's no way to express "all public repos" without an owner. Only array patterns like ["owner/repo", "owner/*"] still produce owner-scoped accept entries. This matches the documented behavior: "If you use repos: all or repos: public, no safeoutputs guard-policy is derived."

Warning

Firewall rules blocked me from connecting to one or more addresses (expand for details)

I tried to connect to the following addresses, but was blocked by firewall rules:

  • https://api.github.com/graphql
    • Triggering command: /usr/bin/gh /usr/bin/gh api graphql -f query=query($owner: String!, $name: String!) { repository(owner: $owner, name: $name) { hasDiscussionsEnabled } } -f owner=github -f name=gh-aw (http block)
    • Triggering command: /usr/bin/gh /usr/bin/gh api graphql -f query=query($owner: String!, $name: String!) { repository(owner: $owner, name: $name) { hasDiscussionsEnabled } } -f owner=github -f name=gh-aw g/workflow/testd/home/REDACTED/work/gh-aw/gh-aw/actions/setup/js/node_modules/.bin/pre�� (http block)
    • Triggering command: /usr/bin/gh /usr/bin/gh api graphql -f query=query($owner: String!, $name: String!) { repository(owner: $owner, name: $name) { hasDiscussionsEnabled } } -f owner=github -f name=gh-aw g/sliceutil/slic/home/REDACTED/.npm/_npx/b388654678d519d9/node_modules/.bin/prettier g/logger/slog_ad--write x_amd64/link g/lo�� h ../../../.pret.prettierignore g/logger/logger.--log-level=error (http block)
  • https://api.github.com/repos/actions/ai-inference/git/ref/tags/v1
    • Triggering command: /usr/bin/gh gh api /repos/actions/ai-inference/git/ref/tags/v1 --jq .object.sha /tmp/TestHashConsistency_GoAndJavaScript89840716/001/test-completest-logs/run-4 UIYjN6c4lmkV /usr/bin/git */*.ts&#39; &#39;**/*.jsgit security r: $owner, name:--show-toplevel git conf�� image:v1.0.0 test@example.com /usr/bin/git */*.json&#39; &#39;!../.git /tmp/go-build191rev-parse k/_temp/uv-pytho--show-toplevel git (http block)
  • https://api.github.com/repos/actions/checkout/git/ref/tags/v3
    • Triggering command: /usr/bin/gh gh api /repos/actions/checkout/git/ref/tags/v3 --jq .object.sha gawJ/DeNJzGr-D7xkIC-EgawJ rev-parse /usr/bin/git --noprofile .cfg odules/npm/node_--show-toplevel git 5394�� /home/REDACTED/work/gh-aw/gh-aw/.github/workflows l /opt/hostedtoolcache/go/1.25.0/x64/pkg/tool/linux_amd64/link on&#39; --ignore-patgit (http block)
  • https://api.github.com/repos/actions/checkout/git/ref/tags/v5
    • Triggering command: /usr/bin/gh gh api /repos/actions/checkout/git/ref/tags/v5 --jq .object.sha --noprofile (http block)
    • Triggering command: /usr/bin/gh gh api /repos/actions/checkout/git/ref/tags/v5 --jq .object.sha --show-toplevel /opt/hostedtoolcremote.origin.url /usr/bin/git -unreachable=falgit /tmp/go-build191rev-parse k/_temp/uv-pytho--show-toplevel git rev-�� --show-toplevel /opt/hostedtoolcache/go/1.25.0/x-f /usr/bin/git ithub/workflows -buildtags cal/bin/node /usr/bin/git (http block)
    • Triggering command: /usr/bin/gh gh api /repos/actions/checkout/git/ref/tags/v5 --jq .object.sha --show-toplevel sh /usr/bin/git ithub/workflows (http block)
  • https://api.github.com/repos/actions/checkout/git/ref/tags/v6
    • Triggering command: /usr/bin/gh gh api /repos/actions/checkout/git/ref/tags/v6 --jq .object.sha /tmp/compile-instructions-test-1646553795/.github/workflows rev-parse /usr/bin/git se 8843969/b210/vetrev-parse r: $owner, name:--show-toplevel git rev-�� --show-toplevel ache/go/1.25.0/x64/pkg/tool/linu-f /usr/bin/unpigz repos set to\|regit (http block)
    • Triggering command: /usr/bin/gh gh api /repos/actions/checkout/git/ref/tags/v6 --jq .object.sha --get remote.origin.url /opt/hostedtoolcache/node/24.14.0/x64/bin/node se 8843969/b219/vetrev-parse de_modules/.bin/--show-toplevel node /tmp�� /tmp/TestHashConsistency_GoAndJavaScript89840716/001/test-complex-frontmatter-with-tools.md ache/go/1.25.0/xrev-parse ache/node/24.14.0/x64/bin/node */*.ts&#39; &#39;**/*.jsgit (http block)
    • Triggering command: /usr/bin/gh gh api /repos/actions/checkout/git/ref/tags/v6 --jq .object.sha --show-toplevel sh /usr/bin/git ithub/workflows (http block)
  • https://api.github.com/repos/actions/github-script/git/ref/tags/v8
    • Triggering command: /usr/bin/gh gh api /repos/actions/github-script/git/ref/tags/v8 --jq .object.sha se 8843969/b105/vetowner=github ache/go/1.25.0/x-f (http block)
    • Triggering command: /usr/bin/gh gh api /repos/actions/github-script/git/ref/tags/v8 --jq .object.sha se 8843969/b205/vet.cfg ache/go/1.25.0/x64/pkg/tool/linux_amd64/vet (http block)
    • Triggering command: /usr/bin/gh gh api /repos/actions/github-script/git/ref/tags/v8 --jq .object.sha cli/install.sh...&#34; rty ache/go/1.25.0/x64/pkg/tool/linux_amd64/vet (http block)
  • https://api.github.com/repos/actions/setup-go/git/ref/tags/v4
    • Triggering command: /usr/bin/gh gh api /repos/actions/setup-go/git/ref/tags/v4 --jq .object.sha --show-toplevel -tests /usr/bin/git from .github/aw git 8843969/b214/vetrev-parse r: $owner, name:--show-toplevel git rev-�� --show-toplevel ache/go/1.25.0/xconfig ache/node/24.14.0/x64/bin/node --noprofile (http block)
  • https://api.github.com/repos/actions/setup-node/git/ref/tags/v4
    • Triggering command: /usr/bin/gh gh api /repos/actions/setup-node/git/ref/tags/v4 --jq .object.sha /repos/actions/github-script/git/ref/tags/v8 --jq ache/node/24.14.0/x64/bin/node se 8843969/b205/vetrev-parse ache/go/1.25.0/x--show-toplevel git t-75�� k/gh-aw/gh-aw/.github/workflows/ai-moderator.md ache/go/1.25.0/xconfig /usr/bin/git --noprofile (http block)
  • https://api.github.com/repos/actions/upload-artifact/git/ref/tags/v4
    • Triggering command: /usr/bin/gh gh api /repos/actions/upload-artifact/git/ref/tags/v4 --jq .object.sha g_.a rev-parse /home/REDACTED/go/bin/node re --log-level=egit .cfg $name) { has--show-toplevel node /opt�� atjTay5oJ @sentry/mcp-server@0.29.0 /usr/bin/git js/**/*.json&#39; --git .cfg 64/pkg/tool/linu--show-toplevel git (http block)
  • https://api.github.com/repos/astral-sh/setup-uv/git/ref/tags/eac588ad8def6316056a12d4907a9d4d84ff7a3b
    • Triggering command: /usr/bin/gh gh api /repos/astral-sh/setup-uv/git/ref/tags/eac588ad8def6316056a12d4907a9d4d84ff7a3b --jq .object.sha ath ../../../.pr**/*.json user.email modules/@npmcli/run-script/lib/node-gyp-bin/node (http block)
  • https://api.github.com/repos/github/gh-aw/actions/runs/1/artifacts
    • Triggering command: /usr/bin/gh gh run download 1 --dir test-logs/run-1 f me: String!) { -importcfg &#43;30 r (http block)
  • https://api.github.com/repos/github/gh-aw/actions/runs/12345/artifacts
    • Triggering command: /usr/bin/gh gh run download 12345 --dir test-logs/run-12345 -tests x_amd64/compile (http block)
  • https://api.github.com/repos/github/gh-aw/actions/runs/12346/artifacts
    • Triggering command: /usr/bin/gh gh run download 12346 --dir test-logs/run-12346 -tests x_amd64/link (http block)
  • https://api.github.com/repos/github/gh-aw/actions/runs/2/artifacts
    • Triggering command: /usr/bin/gh gh run download 2 --dir test-logs/run-2 -tests bin/node (http block)
  • https://api.github.com/repos/github/gh-aw/actions/runs/3/artifacts
    • Triggering command: /usr/bin/gh gh run download 3 --dir test-logs/run-3 -tests ache/go/1.25.0/x-lang=go1.25 (http block)
  • https://api.github.com/repos/github/gh-aw/actions/runs/4/artifacts
    • Triggering command: /usr/bin/gh gh run download 4 --dir test-logs/run-4 -tests x_amd64/compile (http block)
  • https://api.github.com/repos/github/gh-aw/actions/runs/5/artifacts
    • Triggering command: /usr/bin/gh gh run download 5 --dir test-logs/run-5 -tests me: String!) { -nolocalimports (http block)
  • https://api.github.com/repos/github/gh-aw/actions/workflows
    • Triggering command: /usr/bin/gh gh workflow list --json name,state,path ../pkg/workflow/js/**/*.json&#39; --ignore-path ../../../.prettierignore (http block)
    • Triggering command: /usr/bin/gh gh run list --json databaseId,number,url,status,conclusion,workflowName,createdAt,startedAt,updatedAt,event,headBranch,headSha,displayTitle --workflow nonexistent-workflow-12345 --limit 100 /home/REDACTED/wor--norc /home/REDACTED/wor--noprofile /opt/hostedtoolcache/go/1.25.0/x-f 0/x6�� -unreachable=false /tmp/go-build1918843969/b020/vetowner=github repository(owner: $owner, name:-f (http block)
    • Triggering command: /usr/bin/gh gh run list --json databaseId,number,url,status,conclusion,workflowName,createdAt,startedAt,updatedAt,event,headBranch,headSha,displayTitle --workflow nonexistent-workflow-12345 --limit 6 og.go ed } } x_amd64/compile nt_t�� ithub/workflows build_command.go /opt/hostedtoolcache/go/1.25.0/x-lang=go1.25 (http block)
  • https://api.github.com/repos/github/gh-aw/git/ref/tags/a70c5eada06553e3510ac27f2c3bda9d3705bccb
    • Triggering command: /usr/bin/gh gh api /repos/github/gh-aw/git/ref/tags/a70c5eada06553e3510ac27f2c3bda9d3705bccb --jq .object.sha --local user.email 64/pkg/tool/linux_amd64/vet (http block)
  • https://api.github.com/repos/github/gh-aw/git/ref/tags/v1.0.0
    • Triggering command: /usr/bin/gh gh api /repos/github/gh-aw/git/ref/tags/v1.0.0 --jq .object.sha ithub/workflows (http block)
  • https://api.github.com/repos/github/gh-aw/git/ref/tags/v1.2.3
    • Triggering command: /usr/bin/gh gh api /repos/github/gh-aw/git/ref/tags/v1.2.3 --jq .object.sha &#39;**/*.ts&#39; &#39;**/*.json&#39; --ignore-path ../../../.pr**/*.json 8843969/b303/vet.cfg 8843969/b157/vet.cfg (http block)
  • https://api.github.com/repos/github/gh-aw/git/ref/tags/v2.0.0
    • Triggering command: /usr/bin/gh gh api /repos/github/gh-aw/git/ref/tags/v2.0.0 --jq .object.sha &#39;**/*.ts&#39; &#39;**/*.json&#39; --ignore-p-f (http block)
    • Triggering command: /usr/bin/gh gh api /repos/github/gh-aw/git/ref/tags/v2.0.0 --jq .object.sha &#39;**/*.ts&#39; &#39;**/*.-f (http block)
  • https://api.github.com/repos/github/gh-aw/git/ref/tags/v3.0.0
    • Triggering command: /usr/bin/gh gh api /repos/github/gh-aw/git/ref/tags/v3.0.0 --jq .object.sha &#39;**/*.ts&#39; &#39;**/*.remote.origin.url (http block)
  • https://api.github.com/repos/githubnext/agentics/git/ref/tags/
    • Triggering command: /usr/bin/gh gh api /repos/githubnext/agentics/git/ref/tags/# --jq .object.sha tions/setup/js/s!../../../pkg/workflow/js/**/*.json .cfg 64/pkg/tool/linu../../../.prettierignore (http block)
  • https://api.github.com/repos/nonexistent/action/git/ref/tags/v999.999.999
    • Triggering command: /usr/bin/gh gh api /repos/nonexistent/action/git/ref/tags/v999.999.999 --jq .object.sha te &#39;../../../**/*.json&#39; &#39;!../../../pkg/workflow/js/**/*.json&#39; --ignore-path ../../../.prettieriggit -goversion /opt/hostedtoolcache/node/24.14.0/x64/bin/bash -c=4 -nolocalimports -importcfg bash --no�� ithub/workflows /home/REDACTED/work/gh-aw/gh-aw/pkg/workflow/importable_tools_test.go /home/REDACTED/work/gh-aw/node_modules/.bin/node ata/wasm_golden/git ata/wasm_golden/rev-parse ata/wasm_golden/--show-toplevel node (http block)
  • https://api.github.com/repos/nonexistent/repo/actions/runs/12345
    • Triggering command: /usr/bin/gh gh run view 12345 --repo nonexistent/repo --json status,conclusion (http block)
  • https://api.github.com/repos/owner/repo/actions/workflows
    • Triggering command: /usr/bin/gh gh workflow list --json name,state,path --repo owner/repo ache/go/1.25.0/x64/pkg/tool/linux_amd64/vet (http block)
    • Triggering command: /usr/bin/gh gh workflow list --json name,state,path --repo owner/repo 64/bin/gofmt /home/REDACTED/wor/usr/bin/gh /home/REDACTED/worapi /home/REDACTED/worgraphql 64/bin/gofmt --no�� --noprofile o r: $owner, name:-f (http block)
  • https://api.github.com/repos/owner/repo/contents/file.md
    • Triggering command: /tmp/go-build1805394461/b383/cli.test /tmp/go-build1805394461/b383/cli.test -test.testlogfile=/tmp/go-build1805394461/b383/testlog.txt -test.paniconexit0 -test.v=true -test.parallel=4 -test.timeout=10m0s -test.run=^Test -test.short=true (http block)
  • https://api.github.com/repos/test-owner/test-repo/actions/secrets
    • Triggering command: /usr/bin/gh gh api /repos/test-owner/test-repo/actions/secrets --jq .secrets[].name ../pkg/workflow/remote.origin.url 8843969/b092/vet.cfg ache/go/1.25.0/x64/pkg/tool/linux_amd64/vet (http block)

If you need me to access, download, or install something from one of these locations, you can either:

Copilot AI changed the title fix: correct write-sink secrecy level for repos="public", add guard-policies to stdio schema, and smoke-test guard policy fix: don't derive write-sink guard-policy for repos="public"/"all", add guard-policies to stdio schema, and smoke-test guard policy Mar 13, 2026
@pelikhan pelikhan closed this Mar 13, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants