package consumers import ( "errors" "io/fs" configkit "gitea.maximumdirect.net/eric/ConfigKit" ) // VersionedServiceConfig demonstrates a mounted main input whose source-local // schema version is retained at the effective service path. type VersionedServiceConfig struct { Service struct { Version string `yaml:"version"` Name string `yaml:"name"` Endpoint string `yaml:"endpoint"` Metadata struct { Release string `yaml:"release"` } `yaml:"metadata"` } `yaml:"service"` } // LoadVersionedService checks the main and underlay declarations with one // application policy. The local rule path is "version" for each source; the // main input's destination places its protected value at /service/version. // Optional CLI overrides are passed through to ConfigKit for normal protection. func LoadVersionedService(mode configkit.SourceVersionMode, overrides ...configkit.Override) (*configkit.Result[VersionedServiceConfig], error) { files, err := fs.Sub(bundledFiles, "testdata/source-version") if err != nil { return nil, err } main, err := fs.ReadFile(files, "main.yml") if err != nil { return nil, err } underlay, err := fs.ReadFile(files, "underlay.yml") if err != nil { return nil, err } definition := configkit.Definition[VersionedServiceConfig]{ Version: &configkit.VersionRule{ Path: configkit.Keys("version"), Check: func(version configkit.Version, _ *configkit.Validation) error { if !version.Present || version.Null || version.Text == "" { return errors.New("a nonempty source version is required") } return nil }, }, Secret: func(path configkit.Path) bool { return path.String() == "/service/version" }, } return configkit.LoadLayered(configkit.Input{ Source: configkit.Bytes("service main", main), Destination: configkit.Keys("service"), }, configkit.LayeredOptions[VersionedServiceConfig]{ Definition: definition, SourceVersionMode: mode, Overrides: overrides, Underlays: []configkit.Underlay{{Inputs: []configkit.Input{{ Source: configkit.Bytes("service defaults", underlay), Destination: configkit.Keys("service"), }}}}, }) }