feat(gcpname): canonical parser for workload identity provider names - #2
Merged
Conversation
The provider resource name is both the coordinate a GCP cloud connection is registered under and the audience of the identity token minted for it, so it gets validated in four places across three repositories. Validating it by prefix admits a host that merely starts with the right characters: strings.HasPrefix against "//iam.googleapis.com" accepts "//iam.googleapis.com.evil/...". Spelling it differently from the provisioned form produces a token that silently fails to exchange. So the grammar is exact rather than a prefix, and Parse followed by String is the identity function on every accepted input. Percent-encoding, query strings, fragments, trailing slashes, extra segments, whitespace and non-ASCII homoglyphs are all refused, each being a way to write a name Google would canonicalize differently from what was provisioned. Project numbers with a leading zero are refused rather than trimmed, since two spellings of one number would mean two spellings of one audience. The package is dependency-free on purpose: its consumers are a provisioner, a resource plugin, a credential broker and a CLI.
The package has four consumers across three repositories, and two of them cannot take the root oox module: the formae CLI pins an older Go than oox root requires, and the credential broker would inherit oox's cloud SDKs in its build graph for what is stdlib-only string handling. Its own module with an empty require block costs every consumer nothing.
Every module in this repo is its own matrix entry, and a new one that is not listed is a module whose tests never run. Pinned to its declared floor with auto-upgrade off, like provx: this module exists partly so consumers on an older Go can take it, and the only thing that proves the floor is building at the floor.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
The workload identity provider resource name is about to be validated in four places across three repositories: the provisioner that creates it, the resource plugin that exchanges a token for it, the credential broker that decides whether to mint for it, and the CLI that registers it. It is worth exactly one parser, because the name is load-bearing twice over — it is the coordinate a GCP cloud connection is registered under, and it is the
audof the identity token minted for that connection.Two failure modes motivate the strictness:
strings.HasPrefixagainst//iam.googleapis.comalso accepts//iam.googleapis.com.evil/projects/.... The prefix constant here includes the following/projects/, and a test mutating it back to the loose form fails.Parsefollowed byStringis the identity function on every accepted input.Project numbers with a leading zero are refused rather than trimmed: two spellings of one number would mean two spellings of one audience.
The package has no dependencies, so the broker and the plugin can take it without inheriting a cloud SDK.