hashicorp/packer · error
create GitHub OIDC request: %w
Error message
create GitHub OIDC request: %w
What it means
http.NewRequestWithContext failed to build the GET request to GitHub's OIDC token endpoint. Given that the URL already parsed successfully, this almost always means the constructed URL string (after adding the audience query parameter) is invalid — practically only via an invalid method/URL combination or context-related construction edge cases.
Source
Thrown at internal/attestation/sign_keyless.go:338
requestURL := strings.TrimSpace(env["ACTIONS_ID_TOKEN_REQUEST_URL"])
requestToken := strings.TrimSpace(env["ACTIONS_ID_TOKEN_REQUEST_TOKEN"])
if requestURL == "" || requestToken == "" {
return "", nil
}
parsedURL, err := url.Parse(requestURL)
if err != nil {
return "", fmt.Errorf("parse GitHub OIDC request URL: %w", err)
}
query := parsedURL.Query()
if query.Get("audience") == "" {
query.Set("audience", "sigstore")
parsedURL.RawQuery = query.Encode()
}
req, err := http.NewRequestWithContext(ctx, http.MethodGet, parsedURL.String(), nil)
if err != nil {
return "", fmt.Errorf("create GitHub OIDC request: %w", err)
}
req.Header.Set("Authorization", "Bearer "+requestToken)
client := &http.Client{Timeout: 30 * time.Second}
resp, err := client.Do(req)
if err != nil {
return "", fmt.Errorf("request GitHub OIDC token: %w", err)
}
defer func() { _ = resp.Body.Close() }()
if resp.StatusCode/100 != 2 {
return "", fmt.Errorf("request GitHub OIDC token: unexpected status %s", resp.Status)
}
var payload struct {
Value string `json:"value"`
}
if err := json.NewDecoder(resp.Body).Decode(&payload); err != nil {View on GitHub (pinned to eb36e3c3e4)
Solutions
- Ensure ACTIONS_ID_TOKEN_REQUEST_URL is an absolute URL with scheme and host (https://...).
- Compare the URL string before and after audience-parameter augmentation to spot corruption.
- Check the wrapped error's URL field for the exact rejected value.
- Bypass by exporting SIGSTORE_ID_TOKEN directly if the endpoint override cannot be fixed.
Example fix
// before env["ACTIONS_ID_TOKEN_REQUEST_URL"] = "localhost:8080/tokens" // after env["ACTIONS_ID_TOKEN_REQUEST_URL"] = "http://localhost:8080/tokens"
Defensive patterns
Strategy: validation
Validate before calling
raw := strings.TrimSpace(env["ACTIONS_ID_TOKEN_REQUEST_URL"])
if u, err := url.Parse(raw); err != nil || u.Scheme == "" || u.Host == "" {
return fmt.Errorf("ACTIONS_ID_TOKEN_REQUEST_URL must be an absolute URL with scheme and host")
} Type guard
func isAbsoluteHTTPURL(raw string) bool {
u, err := url.Parse(strings.TrimSpace(raw))
return err == nil && (u.Scheme == "http" || u.Scheme == "https") && u.Host != ""
} Try / catch
signer, err := newKeylessSigner(ctx, cfg)
if err != nil && strings.Contains(err.Error(), "create GitHub OIDC request") {
return fmt.Errorf("could not build OIDC token request; check ACTIONS_ID_TOKEN_REQUEST_URL is absolute: %w", err)
} Prevention
- Use absolute URLs (with scheme) when overriding the OIDC endpoint.
- Test overrides by hitting the URL with curl before wiring it in.
- Keep the default GitHub-injected value whenever possible.
- Sanitize the URL string after appending the audience query parameter.
When it happens
Trigger: resolveGitHubActionsIDToken calls http.NewRequestWithContext with the audience-augmented ACTIONS_ID_TOKEN_REQUEST_URL, and Go's request constructor rejects the resulting absolute URL (e.g. a scheme-less URL that only worked for url.Parse).
Common situations: ACTIONS_ID_TOKEN_REQUEST_URL overridden to a relative or scheme-less value like "localhost/token" that url.Parse accepts but the HTTP client's request constructor deems invalid for a request target.
Related errors
- request GitHub OIDC token: %w
- request GitHub OIDC token: unexpected status %s
- parse GitHub OIDC request URL: %w
- decode GitHub OIDC token response: %w
- signing_mode %q requires an ambient OIDC token; set SIGSTORE
AI-assisted analysis of hashicorp/packer@eb36e3c3e4 (2026-09-05).
Data as JSON: /api/errors/958a4df40ffa9972.
Report an issue: GitHub.