package internal import ( "fmt" "regexp" "strings" "sigs.k8s.io/kustomize/kyaml/yaml" "edge-infra.dev/pkg/f8n/warehouse/capability" "edge-infra.dev/pkg/f8n/warehouse/lift" ) // capability is a CapabilityConfig that has been processed (eg regexp compiled) // and used to sort manifests into distinct layers during packing type Capability struct { Name capability.Capability // regexps are the compiled regexp from the list of APIGroup expressions that // control which K8s objects go into the capability's layer regexps []*regexp.Regexp // maps of kinds and api groups to explicitly ignore ignoreKinds map[string]bool ignoreAPIGroups map[string]bool } func (c Capability) Matches(y *yaml.RNode) bool { apiVersion := y.GetApiVersion() if apiVersion == "" { return false } apiGroup := strings.ToLower(strings.Split(apiVersion, "/")[0]) if !matchesAny(c.regexps, apiGroup) { return false } // check if object is explicitly ignored / excluded from match kind := strings.ToLower(y.GetKind()) // return false if the object is explicitly ignored return !(c.ignoreKinds[kind] || c.ignoreAPIGroups[apiGroup]) } func NewCapability(name capability.Capability, cfg lift.CapabilityConfig) (Capability, error) { c := Capability{ Name: name, regexps: make([]*regexp.Regexp, len(cfg.ResourceMatcher.APIGroups)), ignoreKinds: make(map[string]bool, len(cfg.ResourceMatcher.Ignore.Kinds)), ignoreAPIGroups: make(map[string]bool, len(cfg.ResourceMatcher.Ignore.APIGroups)), } for _, i := range cfg.ResourceMatcher.Ignore.Kinds { c.ignoreKinds[strings.ToLower(i)] = true } for _, i := range cfg.ResourceMatcher.Ignore.APIGroups { c.ignoreAPIGroups[strings.ToLower(i)] = true } for i, a := range cfg.ResourceMatcher.APIGroups { r, err := regexp.Compile(strings.ToLower(a)) if err != nil { return Capability{}, fmt.Errorf("invalid capability provider: invalid APIGroup "+ "regular expression %s: %w", a, err) } c.regexps[i] = r } return c, nil } func matchesAny(rr []*regexp.Regexp, s string) bool { for _, r := range rr { if r.MatchString(strings.ToLower(s)) { return true } } return false }