Skip to content

Propagate enterprise host context into curated DIFC/CLI proxy env#41912

Open
Copilot wants to merge 2 commits into
mainfrom
copilot/fix-difc-proxy-env-issue
Open

Propagate enterprise host context into curated DIFC/CLI proxy env#41912
Copilot wants to merge 2 commits into
mainfrom
copilot/fix-difc-proxy-env-issue

Conversation

Copilot AI commented Jun 27, 2026

Copy link
Copy Markdown
Contributor

On *.ghe.com data-residency tenants, the compiler started the mcpg DIFC proxy with a curated env that dropped the enterprise host context. The proxy then defaulted to github.com/api.github.com, causing forwarded gh api calls to fail before the agent could start.

  • Compiler: forward enterprise host context into proxy startup

    • Add the upstream GitHub env needed by proxy startup steps:
      • GH_HOST
      • GITHUB_HOST
      • GITHUB_ENTERPRISE_HOST
      • GITHUB_SERVER_URL
      • GITHUB_API_URL
      • GITHUB_GRAPHQL_URL
      • GITHUB_COPILOT_BASE_URL
    • Apply the same curated env shape to both:
      • Start DIFC Proxy
      • Start CLI Proxy
  • Proxy startup scripts: derive tenant-aware endpoints

    • Normalize the effective GitHub host from GITHUB_SERVER_URL / host env.
    • When the target is *.ghe.com, derive tenant-specific upstreams instead of falling back to public GitHub:
      • https://api.<tenant>.ghe.com
      • https://api.<tenant>.ghe.com/graphql
      • https://copilot-api.<tenant>.ghe.com
    • Preserve explicit overrides when already provided.
  • Regression coverage

    • Extend proxy compiler tests to assert the curated env contains enterprise host fields.
    • Update the pi golden so the CLI proxy path exercises the new env propagation.

Example of the generated proxy startup env:

- name: Start CLI Proxy
  env:
    GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
    GITHUB_SERVER_URL: ${{ github.server_url }}
    GITHUB_API_URL: ${{ github.api_url }}
    GH_HOST: ${{ env.GH_HOST }}
    GITHUB_HOST: ${{ env.GITHUB_HOST }}
    GITHUB_ENTERPRISE_HOST: ${{ env.GITHUB_ENTERPRISE_HOST }}
    GITHUB_GRAPHQL_URL: ${{ env.GITHUB_GRAPHQL_URL }}
    GITHUB_COPILOT_BASE_URL: ${{ env.GITHUB_COPILOT_BASE_URL }}

Co-authored-by: lpcox <15877973+lpcox@users.noreply.github.com>
Copilot AI changed the title [WIP] Fix enterprise host propagation in DIFC proxy environment Propagate enterprise host context into curated DIFC/CLI proxy env Jun 27, 2026
Copilot finished work on behalf of lpcox June 27, 2026 18:04
Copilot AI requested a review from lpcox June 27, 2026 18:04
@pelikhan pelikhan marked this pull request as ready for review June 27, 2026 18:31
Copilot AI review requested due to automatic review settings June 27, 2026 18:31

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Pull request overview

This PR fixes enterprise/data-residency (*.ghe.com) routing for the DIFC/CLI proxy by ensuring the proxy start steps receive the necessary upstream GitHub host context (previously dropped by the curated env), and by deriving tenant-aware upstream API/GraphQL/Copilot endpoints in the proxy start scripts.

Changes:

  • Forward a curated set of upstream GitHub environment variables into both “Start DIFC Proxy” and “Start CLI Proxy” compiler-generated steps.
  • Enhance DIFC/CLI proxy startup scripts to normalize the effective GitHub host and derive tenant-aware upstream endpoints for *.ghe.com (while keeping explicit overrides when present).
  • Extend compiler tests and update the pi golden to cover the new env propagation.
Show a summary per file
File Description
pkg/workflow/testdata/TestWasmGolden_AllEngines/pi.golden Updates golden workflow output to include enterprise host context variables for the CLI proxy start step.
pkg/workflow/compiler_difc_proxy.go Adds a shared helper to emit a consistent curated upstream env for both DIFC and CLI proxy start steps.
pkg/workflow/compiler_difc_proxy_test.go Adds assertions that the proxy start steps include the curated upstream env variables.
actions/setup/sh/start_difc_proxy.sh Derives tenant-aware upstream endpoints and passes enterprise host context env vars into the DIFC proxy container.
actions/setup/sh/start_cli_proxy.sh Derives tenant-aware upstream endpoints and passes enterprise host context env vars into the CLI proxy container.

Review details

Tip

Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

  • Files reviewed: 5/5 changed files
  • Comments generated: 3
  • Review effort level: Low

Comment on lines +49 to +54
export GH_HOST="${GH_HOST:-$github_host}"

if [ "$github_host" != "github.com" ]; then
export GITHUB_HOST="${GITHUB_HOST:-$github_host}"
export GITHUB_ENTERPRISE_HOST="${GITHUB_ENTERPRISE_HOST:-$github_host}"
fi
Comment on lines +46 to +51
export GH_HOST="${GH_HOST:-$github_host}"

if [ "$github_host" != "github.com" ]; then
export GITHUB_HOST="${GITHUB_HOST:-$github_host}"
export GITHUB_ENTERPRISE_HOST="${GITHUB_ENTERPRISE_HOST:-$github_host}"
fi
Comment on lines +32 to +36
derive_proxy_upstream_env() {
local server_url="${GITHUB_SERVER_URL:-https://github.com}"
local server_host
local github_host="${GH_HOST:-${GITHUB_HOST:-${GITHUB_ENTERPRISE_HOST:-}}}"

@github-actions

github-actions Bot commented Jun 27, 2026

Copy link
Copy Markdown
Contributor

🧠 Matt Pocock Skills Reviewer has completed the skills-based review. ✅

@github-actions

github-actions Bot commented Jun 27, 2026

Copy link
Copy Markdown
Contributor

Test Quality Sentinel completed test quality analysis.

@github-actions

github-actions Bot commented Jun 27, 2026

Copy link
Copy Markdown
Contributor

PR Code Quality Reviewer completed the code quality review.

@github-actions

github-actions Bot commented Jun 27, 2026

Copy link
Copy Markdown
Contributor

Design Decision Gate 🏗️ completed the design decision gate check.

No ADR enforcement needed: PR #41912 does not have the 'implementation' label and has only 35 new lines of code in business logic directories (threshold: 100).

@github-actions github-actions Bot mentioned this pull request Jun 27, 2026
@github-actions

Copy link
Copy Markdown
Contributor

🧪 Test Quality Sentinel Report

⚠️ Test Quality Score: 70/100 — Acceptable

Analyzed 2 modified test(s): 2 design, 0 implementation, 0 guideline violation(s).

📊 Metrics & Test Classification (2 tests analyzed)
Metric Value
New/modified tests analyzed 2
✅ Design tests (behavioral contracts) 2 (100%)
⚠️ Implementation tests (low value) 0 (0%)
Tests with error/edge cases 0 (0%)
Duplicate test clusters 0
Test inflation detected No (test +13 / prod +16 = 0.81×)
🚨 Coding-guideline violations 0
Test File Classification Issues Detected
TestGenerateStartDIFCProxyStep / "generates start step with guard policy and custom steps" pkg/workflow/compiler_difc_proxy_test.go:333 ✅ Design
TestBuildStartCliProxyStepYAML / "emits correct step structure" pkg/workflow/compiler_difc_proxy_test.go:906 ✅ Design

A new helper assertProxyCuratedUpstreamEnv was extracted (7 assertions, all with descriptive messages) — this is a quality improvement, not a new test function. Go: 2 (*_test.go); JavaScript: 0.

Note on edge case coverage (0%): The score is penalised for lack of error-path assertions, but this is appropriate for the change: the PR fixes env-var propagation, and the tests correctly verify the positive contract (all 7 env vars are present). No error-path testing was needed. Consider adding a negative test (e.g. assert the old missing vars no longer cause misrouting) if relevant scenarios exist.

Verdict

Check passed. 0% implementation tests (threshold: 30%). Both modified test sub-cases verify observable behavioral contracts — that the proxy step YAML contains all required enterprise host env vars (GH_HOST, GITHUB_HOST, GITHUB_ENTERPRISE_HOST, etc.). All assertions carry descriptive messages and no mock libraries were used.

🧪 Test quality analysis by Test Quality Sentinel · 101.1 AIC · ⌖ 19.4 AIC · ⊞ 8.4K ·

@github-actions github-actions Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

✅ Test Quality Sentinel: 70/100. Test quality is acceptable — 0% of new tests are implementation tests (threshold: 30%).

@github-actions

Copy link
Copy Markdown
Contributor

Review Summary

7 inline comments postedREQUEST_CHANGES submitted.

Top issues to address:

  1. DRY violation (/improve-codebase-architecture) — normalize_github_host() now has 3 copies across the shell scripts; derive_proxy_upstream_env() is duplicated between both proxy scripts. Extract to a shared proxy_env_lib.sh.

  2. Port-stripping bug (/diagnose) — normalize_github_host does not strip ports, so (ghes.example.com/redacted) produces ghes.example.com:8443 as the host value, breaking *.ghe.com matching and passing a malformed GH_HOST to docker.

  3. Silent GH_HOST override (/diagnose) — when GITHUB_SERVER_URL is a non-github.com host, an explicitly-set GH_HOST=github.com is quietly replaced. Document the precedence rule or tighten the condition.

  4. Missing shell unit tests (/tdd) — derive_proxy_upstream_env has 5 conditional branches with no shell tests. Follow the configure_gh_for_ghe_test.sh pattern.

  5. Undocumented GITHUB_COPILOT_BASE_URL gap (/diagnose) — only auto-derived for *.ghe.com, not for GHES. Add a comment or a fallback.

The core fix (propagating 7 env vars into proxy startup) is correct and the Go-level tests are well-written. The issues above are about hardening the shell-side runtime logic.

@copilot please address the review comments above.

🧠 Reviewed using Matt Pocock's skills by Matt Pocock Skills Reviewer · 96.1 AIC · ⌖ 10.6 AIC · ⊞ 6.6K ·

@github-actions github-actions Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Skills-Based Review 🧠

Applied /improve-codebase-architecture, /diagnose, and /tdd — requesting changes on DRY violations, a concrete host-parsing bug, and missing shell-level test coverage.

📋 Key Themes & Highlights

Key Themes

  • DRY violation (high): normalize_github_host() now exists in 3 separate files (configure_gh_for_ghe.sh, start_cli_proxy.sh, start_difc_proxy.sh) and derive_proxy_upstream_env() is duplicated between both proxy scripts. A shared library would make future fixes safe and single-point.
  • Port-stripping bug (medium): normalize_github_host does not strip port numbers, so (ghes.example.com/redacted)ghes.example.com:8443, which breaks *.ghe.com pattern matching and produces an invalid GH_HOST.
  • Silent GH_HOST override (medium): When GITHUB_SERVER_URL points to a non-github.com host, an explicitly-passed GH_HOST=github.com is quietly replaced — surprising behaviour that could mask misconfiguration.
  • Missing shell unit tests (medium): The 5-branch derivation logic in derive_proxy_upstream_env has no shell-level tests. The existing configure_gh_for_ghe_test.sh demonstrates exactly how to do this.
  • Copilot URL gap (low): GITHUB_COPILOT_BASE_URL is only auto-derived for *.ghe.com; the asymmetry vs GITHUB_API_URL / GITHUB_GRAPHQL_URL (which both have GHES fallbacks) is undocumented.

Positive Highlights

  • ✅ Correct fix: forwarding 7 enterprise host context variables into proxy startup is exactly the right approach
  • writeProxyUpstreamEnv() is a clean abstraction that applies consistently to both DIFC and CLI proxy steps
  • ✅ Go-level regression tests are well-structured and immediately verify the compile-time env shape
  • ✅ Updated pi.golden clearly documents the new generated output
  • ✅ Good use of ${VAR:-} safe-expansion throughout to avoid set -e failures on unset vars

🧠 Reviewed using Matt Pocock's skills by Matt Pocock Skills Reviewer · 96.1 AIC · ⌖ 10.6 AIC · ⊞ 6.6K


set -e

normalize_github_host() {

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

[/improve-codebase-architecture] normalize_github_host() is now a third copy of the same function — identical implementations already live in configure_gh_for_ghe.sh and start_difc_proxy.sh. Drift between copies is a real risk here.

💡 Suggested fix

Extract the shared logic into a sourced library (e.g., actions/setup/sh/proxy_env_lib.sh) and replace all three copies with a single source call. The existing configure_gh_for_ghe_test.sh also inlines a fourth copy for testing, so a shared lib + one proxy_env_lib_test.sh would consolidate all instances.

@copilot please address this.

echo "$host"
}

derive_proxy_upstream_env() {

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

[/improve-codebase-architecture] derive_proxy_upstream_env() is duplicated verbatim between start_cli_proxy.sh and start_difc_proxy.sh. Any future fix to the host-resolution logic must be applied in two places, which will be easy to miss.

💡 Suggested fix

Move both normalize_github_host() and derive_proxy_upstream_env() into a shared library script (e.g., actions/setup/sh/proxy_env_lib.sh) and source it in both proxy scripts:

SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
# shellcheck source=./proxy_env_lib.sh
source "${SCRIPT_DIR}/proxy_env_lib.sh"

This also gives a natural home for a proxy_env_lib_test.sh that can test derive_proxy_upstream_env in isolation (see the /tdd comment on line 32).

@copilot please address this.


server_url="${server_url%/}"
server_host="$(normalize_github_host "$server_url")"
if [ -z "$github_host" ] || { [ "$server_host" != "github.com" ] && [ "$github_host" = "github.com" ]; }; then

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

[/diagnose] This condition silently overrides an explicitly-set GH_HOST=github.com when GITHUB_SERVER_URL points to a non-github.com host. If a caller deliberately passes GH_HOST=github.com (e.g., for a specific routing reason), this will quietly replace it with the server URL hostname.

💡 Explanation & suggested change

Current logic:

if [ -z "$github_host" ] || { [ "$server_host" != "github.com" ] && [ "$github_host" = "github.com" ]; }; then
  github_host="$server_host"
fi

The second branch (server_host != github.com AND github_host == github.com) fires even when GH_HOST was explicitly provided by the caller. The intent seems to be "if the host resolved from the env looks like a stale default, prefer the server URL" — but "stale default" and "explicit override" are indistinguishable here.

Consider narrowing the condition to only override when github_host came from a lower-priority var than GITHUB_SERVER_URL, or document clearly that GITHUB_SERVER_URL takes precedence over GH_HOST when they disagree.

@copilot please address this.

if [[ "$host" =~ ^https?:// ]]; then
host="${host#http://}"
host="${host#https://}"
host="${host%%/*}"

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

[/diagnose] normalize_github_host does not strip port numbers. A URL like (ghes.example.com/redacted) produces ghes.example.com:8443, which then gets exported as GH_HOST and used to pattern-match *.ghe.com. This would misroute GHES on non-standard ports.

💡 Suggested fix

Add a port strip after the path strip:

normalize_github_host() {
  local host="$1"
  host="${host%/}"
  if [[ "$host" =~ ^https?:// ]]; then
    host="${host#(redacted)
    host="${host#https://}"
    host="${host%%/*}"
  fi
  host="${host%%:*}"   # strip port if present
  echo "$host"
}

Also add a test case in the test suite:

["(ghes.example.com/redacted)"]="ghes.example.com"

@copilot please address this.

if [ -z "${GITHUB_COPILOT_BASE_URL:-}" ] && [[ "$github_host" == *.ghe.com ]]; then
export GITHUB_COPILOT_BASE_URL="https://copilot-api.${github_host}"
fi
}

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

[/tdd] derive_proxy_upstream_env() contains 5 conditional branches (empty host, *.ghe.com, GHES fallback, public GitHub, override guard) with no shell-level unit tests. The Go tests only verify the compiler emits the env var names; they do not exercise the runtime derivation logic.

💡 Suggested tests

Following the configure_gh_for_ghe_test.sh pattern, add a start_cli_proxy_test.sh (or better, a proxy_env_lib_test.sh after extracting to a shared lib) with cases like:

# Case: *.ghe.com tenant — API URL should be tenant-scoped
GITHUB_SERVER_URL="(myorg.ghe.com/redacted)" derive_proxy_upstream_env
assert_eq "$GITHUB_API_URL" "(api.myorg.ghe.com/redacted)"
assert_eq "$GITHUB_COPILOT_BASE_URL" "(copilotapi.myorg.ghe.com/redacted)"

# Case: GHES custom host — API URL should use /api/v3
GITHUB_SERVER_URL="(ghes.example.com/redacted)" derive_proxy_upstream_env
assert_eq "$GITHUB_API_URL" "(ghes.example.com/redacted)

# Case: public GitHub — should not override
GITHUB_SERVER_URL="https://github.com" derive_proxy_upstream_env
assert_eq "$GITHUB_API_URL" "https://api.github.com"

@copilot please address this.

fi
fi

if [ -z "${GITHUB_COPILOT_BASE_URL:-}" ] && [[ "$github_host" == *.ghe.com ]]; then

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

[/diagnose] GITHUB_COPILOT_BASE_URL is only auto-derived for *.ghe.com tenants, not for GHES (non-*.ghe.com). This creates asymmetric behaviour: GITHUB_API_URL and GITHUB_GRAPHQL_URL both have GHES fallbacks (${server_url}/api/v3, ${server_url}/api/graphql), but Copilot does not.

💡 Suggested change

If GHES also exposes a Copilot endpoint, add a fallback. If it is not yet supported, document the gap explicitly with a comment:

# NOTE: GITHUB_COPILOT_BASE_URL is not auto-derived for GHES (non-*.ghe.com).
# GHES Copilot endpoint is not yet standardised; callers must set this explicitly.
if [ -z "${GITHUB_COPILOT_BASE_URL:-}" ] && [[ "$github_host" == *.ghe.com ]]; then
  export GITHUB_COPILOT_BASE_URL="(copilotapi/redacted)${github_host}"
fi

Either way, making the intent explicit prevents future confusion.

@copilot please address this.

"github.com/stretchr/testify/require"
)

func assertProxyCuratedUpstreamEnv(t *testing.T, result string) {

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

[/tdd] assertProxyCuratedUpstreamEnv uses only assert.Contains checks, which cannot detect duplicate env keys or verify that vars belong to a specific step. If GITHUB_SERVER_URL were accidentally written twice (once by writeProxyUpstreamEnv and once by a lingering call site), or if env vars leaked into the wrong step, these assertions would still pass.

💡 Suggested improvement

For the most critical fields, count occurrences or verify exact substrings with surrounding context:

func assertProxyCuratedUpstreamEnv(t *testing.T, result string) {
    t.Helper()
    assert.Contains(t, result, "GITHUB_SERVER_URL: ${{ github.server_url }}")
    // Ensure exactly one occurrence to catch accidental duplication
    assert.Equal(t, 1, strings.Count(result, "GITHUB_SERVER_URL:"), "GITHUB_SERVER_URL should appear exactly once")
    assert.Equal(t, 1, strings.Count(result, "GITHUB_API_URL:"), "GITHUB_API_URL should appear exactly once")
    // ... etc.
}

This is a low-friction improvement that closes the "duplicate field" regression class.

@copilot please address this.

@github-actions

Copy link
Copy Markdown
Contributor

🤖 PR Triage

Attribute Value
Category bug
Risk 🟡 Medium
Priority 🔴 High
Score 76/100
Action fast_track

Score breakdown: Impact 38 + Urgency 22 + Quality 16 = 76

Assessment: Production fix for GHE tenants on *.ghe.com where enterprise host context (GH_HOST, GITHUB_ENTERPRISE_HOST, etc.) was dropped from the DIFC/CLI proxy startup env, causing all forwarded gh api calls to fail before the agent starts. Targeted scope (5 files, +171/-4). CI mostly passing (11 success, 15 skipped, 3 in-progress). No existing reviews. Recommend expedited human review.

Run §28298156610

Generated by 🔧 PR Triage Agent · 74.3 AIC · ⌖ 8.1 AIC · ⊞ 5.4K ·

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.

3 participants