Problem
The container field in MCP server configuration rejects @sha256: digest-pinned image references. The current regex pattern only allows tag-based references (image:tag):
// internal/config/validation_schema.go:62
containerPattern = regexp.MustCompile(`^[a-zA-Z0-9][a-zA-Z0-9./_-]*(:([a-zA-Z0-9._-]+|latest))?$`)
// internal/config/schema/mcp-gateway-config.schema.json
"pattern": "^[a-zA-Z0-9][a-zA-Z0-9./_-]*(:([a-zA-Z0-9._-]+|latest))?$"
This means digest-pinned references like ghcr.io/github/github-mcp-server:v0.32.0@sha256:2763823c... are rejected during config validation, preventing immutable container image pinning.
Context
The gh-aw compiler is adding SHA-256 digest pinning for supply-chain security (github/gh-aw#25072). The compiler currently works around this by stripping the @sha256: part before writing the container field and only using the full digest-pinned ref in docker pull commands. Supporting digests natively in the gateway would be cleaner and allow operators to pin images in their own configs.
Proposed Fix
1. Update the regex pattern
Allow an optional @sha256:<hex> suffix after the tag:
// Allows: image, image:tag, image@sha256:abc123, image:tag@sha256:abc123
containerPattern = regexp.MustCompile(`^[a-zA-Z0-9][a-zA-Z0-9./_-]*(:([a-zA-Z0-9._-]+|latest))?(@sha256:[a-fA-F0-9]{64})?$`)
2. Update the JSON schema
{
"pattern": "^[a-zA-Z0-9][a-zA-Z0-9./_-]*(:([a-zA-Z0-9._-]+|latest))?(@sha256:[a-fA-F0-9]{64})?$"
}
3. Pass through the full reference to Docker
Ensure the launcher passes the complete image:tag@sha256:... reference to docker run so Docker resolves by content address.
4. Add tests
- Valid:
ghcr.io/github/github-mcp-server:v0.32.0@sha256:2763823c... (tag + digest)
- Valid:
ghcr.io/github/github-mcp-server@sha256:2763823c... (digest only, no tag)
- Valid:
ghcr.io/github/github-mcp-server:v0.32.0 (tag only, existing behavior)
- Invalid:
ghcr.io/github/github-mcp-server@sha256:short (digest too short)
- Invalid:
ghcr.io/github/github-mcp-server@md5:abc (wrong algorithm)
Files to Change
internal/config/validation_schema.go — containerPattern regex
internal/config/schema/mcp-gateway-config.schema.json — container property pattern
internal/config/validation_schema_test.go — add digest test cases
internal/config/validation_string_patterns_test.go — add digest pattern tests
internal/config/rules/rules_test.go — add valid digest case
References
Problem
The
containerfield in MCP server configuration rejects@sha256:digest-pinned image references. The current regex pattern only allows tag-based references (image:tag):This means digest-pinned references like
ghcr.io/github/github-mcp-server:v0.32.0@sha256:2763823c...are rejected during config validation, preventing immutable container image pinning.Context
The gh-aw compiler is adding SHA-256 digest pinning for supply-chain security (github/gh-aw#25072). The compiler currently works around this by stripping the
@sha256:part before writing thecontainerfield and only using the full digest-pinned ref indocker pullcommands. Supporting digests natively in the gateway would be cleaner and allow operators to pin images in their own configs.Proposed Fix
1. Update the regex pattern
Allow an optional
@sha256:<hex>suffix after the tag:2. Update the JSON schema
{ "pattern": "^[a-zA-Z0-9][a-zA-Z0-9./_-]*(:([a-zA-Z0-9._-]+|latest))?(@sha256:[a-fA-F0-9]{64})?$" }3. Pass through the full reference to Docker
Ensure the launcher passes the complete
image:tag@sha256:...reference todocker runso Docker resolves by content address.4. Add tests
ghcr.io/github/github-mcp-server:v0.32.0@sha256:2763823c...(tag + digest)ghcr.io/github/github-mcp-server@sha256:2763823c...(digest only, no tag)ghcr.io/github/github-mcp-server:v0.32.0(tag only, existing behavior)ghcr.io/github/github-mcp-server@sha256:short(digest too short)ghcr.io/github/github-mcp-server@md5:abc(wrong algorithm)Files to Change
internal/config/validation_schema.go—containerPatternregexinternal/config/schema/mcp-gateway-config.schema.json—containerproperty patterninternal/config/validation_schema_test.go— add digest test casesinternal/config/validation_string_patterns_test.go— add digest pattern testsinternal/config/rules/rules_test.go— add valid digest caseReferences