awsssm

package
v0.9.2 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Sep 5, 2026 License: Apache-2.0 Imports: 8 Imported by: 0

Documentation

Overview

Package awsssm reads and writes AWS Systems Manager Parameter Store values.

WHAT IT IS FOR is the deployment identity material two controllers have to share: the node-wire certificate authority and the GitHub App private key. The codebuild backend already wrote single-use runner registrations here, so the service, the endpoint derivation, the signing vectors and the SecureString rules are all measured behaviour billet already has — what is new is the READ.

THE RESPONSE CARRIES THE SECRET, WHICH THE WRITE PATH NEVER DID. Every rule the codebuild JIT channel states is about keeping a request out of a log; here the value comes BACK, so nothing derived from a GetParameter response is ever rendered, and the error paths say what failed without saying what was in it.

IT IS NOT REACHABLE FROM THE LEDGER PACKAGES, and that is enforced rather than intended: depguard's `ledgerwriters` rule bans net/http from internal/state, internal/alloc and internal/rollout, because DB.Tx holds the single writer slot from BEGIN and a remote call inside one stalls every scheduling write in the process. Nothing here may be called from inside a transaction.

Index

Constants

This section is empty.

Variables

View Source
var ErrAlreadyExists = errors.New("awsssm: a parameter already exists under that name")

ErrAlreadyExists means a no-overwrite write found the name taken.

A REFUSAL RATHER THAN A REPLACEMENT is the whole point of the flag that produces it: the GitHub App private key is issued once and can never be re-fetched, so publishing it must never be able to overwrite anything.

View Source
var ErrNotFound = errors.New("awsssm: no parameter of that name")

ErrNotFound means Parameter Store has no value under that name.

ITS OWN ERROR BECAUSE ABSENCE IS AN ORDINARY STATE FOR SOME CALLERS AND A FAULT FOR OTHERS. A deployment that has never published its authority has none here, which is day one; a controller that expects one and finds nothing has lost it. Only the caller can tell those apart, so the client refuses to.

Functions

func PathFor

func PathFor(prefix, leaf string) string

PathFor joins a prefix and a leaf into a Parameter Store name.

PARAMETER STORE NAMES ARE PATHS and a doubled or missing separator is a different parameter, not a formatting nicety — so this is one function rather than a concatenation at each call site.

Types

type Client

type Client struct {
	// contains filtered or unexported fields
}

Client reads and writes Parameter Store values for one region.

func New

func New(region string, creds awscreds.Source) *Client

New builds a client for one region.

THE ENDPOINT IS DERIVED AND NOT CONFIGURABLE, which is the rule the codebuild backend already states for this service and which matters more here: an operator override would be a way to send a deployment's private key to a host of somebody's choosing. A partition billet has not been taught about needs a code change rather than a config field.

func (*Client) Delete

func (c *Client) Delete(ctx context.Context, name string) error

Delete removes one parameter.

ABSENCE IS SUCCESS, because every caller of this is a cleanup that has already decided the value should not exist — and a delete that fails because somebody else got there first has produced the outcome it wanted.

func (Client) Format

func (c Client) Format(f fmt.State, _ rune)

Format catches every verb, so no fallback prints the struct.

func (*Client) Get

func (c *Client) Get(ctx context.Context, name string) (Parameter, error)

Get reads one parameter, decrypting a SecureString.

WithDecryption IS ALWAYS TRUE, because every value billet stores here is one. Making it a parameter would be offering a caller a way to receive ciphertext it cannot use and would then have to detect.

func (Client) GoString

func (c Client) GoString() string

GoString covers %#v.

func (Client) LogValue

func (c Client) LogValue() slog.Value

LogValue is what slog consults; its JSON handler ignores fmt entirely.

IT MUST RETURN slog.Value, NOT any. slog.LogValuer is a named interface, and a method with a different result type does not implement it — the handler then falls back to reflecting over the struct, which is the whole failure this is here to prevent.

func (Client) MarshalJSON

func (c Client) MarshalJSON() ([]byte, error)

MarshalJSON keeps a client out of anything that serializes it structurally.

func (*Client) Put

func (c *Client) Put(ctx context.Context, name, value string, opts PutOptions) (int64, error)

Put writes one SecureString and returns the version it became.

INTELLIGENT-TIERING, AND THE REASON IS MEASURED. A standard parameter caps its value at 4096 characters, and that limit is what stopped the codebuild backend running a single job until it was found: a real GitHub JIT registration exceeds it. An authority document carrying two certificates and two private keys exceeds it comfortably. Intelligent-Tiering keeps a parameter standard while the value fits and promotes it only when it does not.

func (Client) String

func (c Client) String() string

REDACTED, BECAUSE IT HOLDS A CREDENTIAL SOURCE IN AN UNEXPORTED FIELD.

awsjson.Client redacts itself, and that is not enough: reflect refuses to call methods through an unexported field, so `%+v` on this struct would walk past that redaction into the source's own fields. The same trap awscreds.IMDS records, two packages along.

type Parameter

type Parameter struct {
	Name    string
	Value   string
	Version int64
}

Parameter is one stored value and the version it was read at.

THE VERSION IS THE PART A CALLER REASONS ABOUT. Parameter Store reads are eventually consistent, so "I fetched something" is not "I fetched the newest thing"; a caller that has recorded a floor elsewhere compares against this.

NO String, GoString OR MarshalJSON, DELIBERATELY. This type IS the secret, and giving it a redacted rendering would make it look safe to log — which is the opposite of what a caller should conclude. Nothing in billet prints one.

type PutOptions

type PutOptions struct {
	// Overwrite REPLACES an existing value. False is a refusal, and it is what
	// publishing an unrepeatable credential uses.
	Overwrite bool

	// KMSKeyID names the key that encrypts the SecureString. Empty uses the
	// account's default SSM key, which is what a deployment that has not chosen
	// one gets.
	KMSKeyID string

	// Description is what an operator finding this parameter reads before deciding
	// whether removing it is safe.
	Description string
}

PutOptions are the choices a write makes that are not the value.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL