package main import ( "errors" "fmt" "github.com/goccy/go-yaml" "net" ) func validateCIDR(cidr string) error { _, _, err := net.ParseCIDR(cidr) return err } type CIDR string // UnmarshalYAML implements the yaml.Unmarshaler interface func (c *CIDR) UnmarshalYAML(value []byte) error { // Get the string value from the node var s string if err := yaml.Unmarshal(value, &s); err != nil { return err } if err := validateCIDR(s); err != nil { return err } *c = CIDR(s) return nil } // MarshalYAML implements the yaml.Marshaler interface func (c CIDR) MarshalYAML() ([]byte, error) { // Do any custom processing here before marshalling return []byte(string(c)), nil } // Network represents each network entry in the YAML type Network struct { Name string `yaml:"name"` CIDR CIDR `yaml:"cidr"` Except []CIDR `yaml:"except,omitempty"` } type Application struct { Name string `yaml:"name"` Ports []string `yaml:"ports,omitempty"` MatchLabels map[string]string `yaml:"matchLabels"` } type Namespace struct { Name string `yaml:"name"` Capabilities []string `yaml:"capabilities"` Applications []Application `yaml:"applications"` } type Communication struct { From []string `yaml:"from"` To []string `yaml:"to"` Ports []string `yaml:"ports"` } // Config represents the top-level YAML structure type Config struct { Networks []Network `yaml:"networks,omitempty"` Namespaces []Namespace `yaml:"namespaces,omitempty"` Communications []Communication `yaml:"communications,omitempty"` } func (c Config) Validate() error { errs := make([]error, 0) // namesapaces must be unique ns := make(map[string]bool) for _, namespace := range c.Namespaces { if ns[namespace.Name] { errs = append(errs, fmt.Errorf("Duplicate namespace name %s", namespace.Name)) } ns[namespace.Name] = true } // network names mus tbe unique networks := make(map[string]bool) for _, network := range c.Networks { if networks[network.Name] { errs = append(errs, fmt.Errorf("Duplicate network name %s", network.Name)) } networks[network.Name] = true } // application names must be unique apps := make(map[string]bool) for _, namespace := range c.Namespaces { for _, app := range namespace.Applications { if apps[app.Name] { errs = append(errs, fmt.Errorf("Duplicate application %s (%s)", app.Name, namespace.Name)) } apps[app.Name] = true } } // applications mentioned in a communication must exist for _, communication := range c.Communications { for _, from := range communication.From { if !apps[from] { errs = append(errs, fmt.Errorf("Application does not exist: %s referenced in a communication (%+v)", from, communication)) } } for _, to := range communication.To { if !apps[to] { errs = append(errs, fmt.Errorf("Application does not exist: %s referenced in a communication (%+v)", to, communication)) } } } return errors.Join(errs...) }