Documentation
¶
Overview ¶
Package extract statically parses k3s/RKE2's pkg/cli/cmds source (via go/ast) to recover the urfave/cli flag list they declare, without ever compiling or importing that package. Their go.mod replace directives make importing them as a real dependency unsafe -- see docs/agent/design-config-codegen.md for the full reasoning.
Index ¶
- func BuildK3SFlagOptionIndex(files ...*ast.File) map[string]K3SFlagOption
- func BuildVarIndex(files ...*ast.File) map[string]*ast.CompositeLit
- func DisableSetCalls(file *ast.File) []string
- func FindK3SFlagSet(file *ast.File) *ast.CompositeLit
- func ParseK3SFlagSet(optIndex map[string]K3SFlagOption, mapLit *ast.CompositeLit) (map[string]K3SFlagOption, error)
- func StringListDecl(name string, files ...*ast.File) ([]string, bool)
- type Components
- type Flag
- type K3SFlagOption
- type Manifest
Constants ¶
This section is empty.
Variables ¶
This section is empty.
Functions ¶
func BuildK3SFlagOptionIndex ¶
func BuildK3SFlagOptionIndex(files ...*ast.File) map[string]K3SFlagOption
BuildK3SFlagOptionIndex indexes every top-level "Name = &K3SFlagOption{...}" var declaration across files -- RKE2's k3sopts.go declares the four convenience vars (copyFlag, dropFlag, hideFlag, ignoreFlag) this way, and a K3SFlagSet{...} map literal's entries reference them by bare identifier.
func BuildVarIndex ¶
func BuildVarIndex(files ...*ast.File) map[string]*ast.CompositeLit
BuildVarIndex indexes every top-level "Name = &cli.XFlag{...}" declaration across files, so ExtractFlags can resolve the bare identifiers a []cli.Flag{...} literal references -- k3s declares many shared flags once and lists them by name in both the server and agent flag slices.
func DisableSetCalls ¶
DisableSetCalls collects the value of every `<ctx>.Set("disable", "<literal>")` call in file. RKE2's validateCNI disables the multus charts that way rather than listing them in pkg/cli/types.go, so scanning for the call recovers them without hardcoding chart names here.
func FindK3SFlagSet ¶
func FindK3SFlagSet(file *ast.File) *ast.CompositeLit
FindK3SFlagSet locates the single "K3SFlagSet{...}" map composite literal in file -- RKE2's server.go/agent.go each build one inline as an argument to mustCmdFromK3S(...).
func ParseK3SFlagSet ¶
func ParseK3SFlagSet(optIndex map[string]K3SFlagOption, mapLit *ast.CompositeLit) (map[string]K3SFlagOption, error)
ParseK3SFlagSet resolves a K3SFlagSet{...} map literal's entries into flag name -> K3SFlagOption, using optIndex (see BuildK3SFlagOptionIndex) to resolve bare-identifier values (copyFlag, dropFlag, ...) and parsing inline/elided "*K3SFlagOption{...}" literal values directly.
func StringListDecl ¶
StringListDecl finds the top-level const or var named name across files and returns the string items it declares. Both shapes k3s and RKE2 use are handled:
const DisableItems = "coredns, servicelb, traefik" // k3s, pkg/cli/cmds/stage.go
var DisableItems = []string{"rke2-coredns", ...} // rke2, pkg/cli/types.go
Elements that aren't string literals are skipped rather than guessed at, the same way buildFlag surfaces an unresolvable flag name instead of inventing one.
Types ¶
type Components ¶
type Components struct {
// Disable is the set of packaged components `disable:` accepts.
Disable []string
// CNI is the set of values `cni:` accepts. Empty for distros that don't declare one.
CNI []string
// Ingress is the set of values `ingress-controller:` accepts. Empty for distros that
// don't declare one.
Ingress []string
}
Components is the packaged-component vocabulary recovered for one distro/version -- the values a flag accepts, as opposed to the flag names ExtractFlags recovers. k3s and RKE2 both declare these as plain package-level lists outside the files that hold the []cli.Flag{...} literal, so they need their own pull and their own extraction pass.
type Flag ¶
type Flag struct {
Name string `json:"name"`
Type string `json:"type,omitempty"`
Slice bool `json:"slice,omitempty"`
Hidden bool `json:"hidden,omitempty"`
Destination string `json:"destination,omitempty"`
Value string `json:"value,omitempty"`
// Unresolved is set when the []cli.Flag{...} literal referenced a bare identifier (e.g.
// ConfigFlag) that isn't declared as a "Name = &cli.XFlag{...}" var anywhere in the parsed
// file set. k3s spreads shared flags across files this package is often not given; losing
// those is an acceptable, visible gap rather than a reason to fail extraction.
Unresolved bool `json:"unresolved,omitempty"`
// UnknownType is set when the flag's cli.XFlag type isn't in flagTypes.
UnknownType bool `json:"unknownType,omitempty"`
// AliasOf holds the canonical flag Name when this flag's Destination matches one already
// seen earlier in the same list -- k3s's pattern for a deprecated flag name that populates
// the same struct field as its replacement.
AliasOf string `json:"aliasOf,omitempty"`
}
Flag is one urfave/cli flag recovered from a []cli.Flag{...} literal.
func ApplyK3SFlagSet ¶
func ApplyK3SFlagSet(k3sFlags []Flag, flagSet map[string]K3SFlagOption) (flags []Flag, unmapped []string)
ApplyK3SFlagSet transforms k3s's own extracted flags the way RKE2's commandFromK3S does: flags with Drop:true are excluded, flags with Hide:true are kept but marked Hidden, and everything else passes through unchanged. A k3s flag with no matching flagSet entry is kept unchanged -- upstream treats that as a hard error (every k3s flag must be explicitly accounted for), but here it's more useful to keep the flag and surface the gap to the caller than to silently drop real config.yaml keys because our own K3SFlagSet parsing missed an entry.
func ExtractFlags ¶
ExtractFlags finds the []cli.Flag{...} literal in file and resolves each element: inline &cli.XFlag{...} literals directly, bare identifiers via varIndex.
type K3SFlagOption ¶
K3SFlagOption is the Drop/Hide subset of RKE2's own K3SFlagOption struct (pkg/cli/cmds/k3sopts.go) that matters for config.yaml key generation. RKE2 wraps every k3s flag it imports through a K3SFlagSet{...} map keyed by flag name, using this to decide whether the flag survives into RKE2's own command at all, and whether it's hidden.