kubernetes/kops · error

parsing presigned url: %w

Error message

parsing presigned url: %w

What it means

This error wraps a failure from Go's net/url.Parse when parsing the URL produced by the AWS STS PresignGetCallerIdentity call in buildSTSRequestValidator. The presigned URL string returned by the AWS SDK could not be parsed into a url.URL, so the verifier cannot extract the Host needed to validate STS requests. This is nearly always a symptom of an AWS SDK misconfiguration (e.g. custom STS endpoint) rather than a logic bug.

Source

Thrown at pkg/bootstrap/awsbootstrap/verifier.go:485

	callerIdentity := &GetCallerIdentityResponse{}
	err = xml.NewDecoder(bytes.NewReader(responseBody)).Decode(callerIdentity)
	if err != nil {
		return nil, fmt.Errorf("decoding STS response: %v", err)
	}

	return callerIdentity, nil
}

// buildSTSRequestValidator determines the form of a valid STS presigned URL.
func buildSTSRequestValidator(ctx context.Context, stsClient *sts.Client) (*stsRequestValidator, error) {
	// We build a presigned token ourselves, primarily to get the expected hostname for the endpoint.
	signed, err := sts.NewPresignClient(stsClient).PresignGetCallerIdentity(ctx, &sts.GetCallerIdentityInput{})
	if err != nil {
		return nil, fmt.Errorf("building presigned request: %w", err)
	}
	u, err := url.Parse(signed.URL)
	if err != nil {
		return nil, fmt.Errorf("parsing presigned url: %w", err)
	}
	return &stsRequestValidator{Host: u.Host}, nil
}

// GetInstanceCertificateNames returns the instance names and addresses that should go into
// certificates: the instance ID, the private DNS name and the IP addresses.
func GetInstanceCertificateNames(instances *ec2.DescribeInstancesOutput) (addrs []string, err error) {
	if len(instances.Reservations) != 1 {
		return nil, fmt.Errorf("too many reservations returned for the single instance-id")
	}

	if len(instances.Reservations[0].Instances) != 1 {
		return nil, fmt.Errorf("too many instances returned for the single instance-id")
	}

	instance := instances.Reservations[0].Instances[0]

	addrs = append(addrs, *instance.InstanceId)

View on GitHub (pinned to 4c8573c808)

Solutions

  1. Check the STS endpoint configuration (AWS_ENDPOINT_URL_STS, custom resolvers, base URL) and ensure it is a valid absolute http(s) URL
  2. Log signed.URL when the error occurs to see exactly what string fails to parse
  3. Remove any custom endpoint overrides and retry with default AWS endpoints to isolate the cause
  4. Verify AWS SDK versions are consistent (aws-sdk-go-v2) and not mismatched between presign client and config

Example fix

// before: opaque custom endpoint
stsClient := sts.NewFromConfig(cfg, func(o *sts.Options) { o.BaseEndpoint = aws.String(os.Getenv("STS_URL")) })
// after: validate the endpoint before building the client
ep := os.Getenv("STS_URL")
if ep != "" {
  if _, err := url.Parse(ep); err != nil { return nil, fmt.Errorf("invalid STS endpoint %q: %w", ep, err) }
}
stsClient := sts.NewFromConfig(cfg, func(o *sts.Options) { o.BaseEndpoint = aws.String(ep) })
Defensive patterns

Strategy: validation

Validate before calling

u, err := url.Parse(presignedURL)
if err != nil || u.Host == "" {
  return fmt.Errorf("invalid presigned STS url %q: %w", presignedURL, err)
}

Type guard

func isValidURL(s string) bool {
  u, err := url.Parse(s)
  return err == nil && u.Host != ""
}

Try / catch

u, err := url.Parse(signed.URL)
if err != nil {
  return nil, fmt.Errorf("parsing presigned url (raw=%q): %w", signed.URL, err)
}

Prevention

When it happens

Trigger: NewAWSVerifier calls buildSTSRequestValidator; sts.NewPresignClient(stsClient).PresignGetCallerIdentity returns a signed.URL that url.Parse rejects — e.g. a custom STS endpoint configured via AWS_ENDPOINT_URL_STS or the client config that yields a malformed URL string.

Common situations: Developers pointing the SDK at a proxy or local endpoint (LocalStack, custom endpoint resolver) with an invalid or empty URL; corrupted environment variables like AWS_ENDPOINT_URL_STS containing spaces or missing scheme; unusual SDK versions returning unexpected presigned URL formats.

Related errors


AI-assisted analysis of kubernetes/kops@4c8573c808 (2026-09-05). Data as JSON: /api/errors/a6b564000d09eda4. Report an issue: GitHub.