Compose grouped underlays in shared load lifecycle

This commit is contained in:
2026-09-29 17:52:20 +00:00
parent 90c6e8ed7e
commit 1cdf90d831
7 changed files with 494 additions and 25 deletions

View File

@@ -121,14 +121,27 @@ func Load[T any](source Source, secrets SecretBinding, supplied ...Options[T]) (
}
func loadWithSecretLookup[T any](source Source, secrets SecretBinding, lookup secretLookup, supplied ...Options[T]) (*Loaded[T], error) {
accumulator := diagnosticAccumulator{}
options, diagnostics := selectOptions(source, supplied)
accumulator.add(diagnostics...)
if len(diagnostics) != 0 {
return nil, accumulator.loadError()
return nil, (&diagnosticAccumulator{diagnostics: diagnostics}).loadError()
}
request := loadRequest[T]{
main: loadInput{source: source, imports: options.Imports, filesystem: options.Filesystem},
definition: options.Definition, overlay: options.Overlay,
overrides: options.Overrides, ordinary: true,
}
return executeLoadRequest(request, secrets, lookup)
}
func executeLoadRequest[T any](request loadRequest[T], secrets SecretBinding, lookup secretLookup) (*Loaded[T], error) {
accumulator := diagnosticAccumulator{}
accounting := &importAccounting{}
mainOptions := Options[T]{Definition: request.definition, Imports: request.main.imports, Filesystem: request.main.filesystem}
if request.ordinary {
mainOptions.Overlay = request.overlay
}
input, diagnostics := assembleBaseInput(source, options)
input, diagnostics := assembleBaseInputTracked(request.main.source, mainOptions, accounting, nil, nil)
accumulator.sources = input.sources
accumulator.add(diagnostics...)
if len(diagnostics) != 0 {
@@ -139,24 +152,28 @@ func loadWithSecretLookup[T any](source Source, secrets SecretBinding, lookup se
accumulator.add(diagnosticFromSchemaIssue(schemaIssue))
return nil, accumulator.loadError()
}
versionDiagnostics := checkVersion(options.Definition.Version, input.document)
versionDiagnostics := checkVersion(request.definition.Version, input.document)
accumulator.add(versionDiagnostics...)
if hasErrors(versionDiagnostics) {
return nil, accumulator.loadError()
}
input, diagnostics = applyInputLayers(source, options, input)
if request.ordinary {
input, diagnostics = applyInputLayers(request.main.source, Options[T]{Definition: request.definition, Overlay: request.overlay, Filesystem: request.main.filesystem, Overrides: request.overrides}, input)
} else {
input, diagnostics = assembleLayeredInput(request, input, accounting)
}
accumulator.sources = input.sources
accumulator.add(diagnostics...)
if len(diagnostics) != 0 {
return nil, accumulator.loadError()
}
decoded, diagnostics := decodeLoadInput(schema, options.Definition, input)
decoded, diagnostics := decodeLoadInput(schema, request.definition, input)
accumulator.add(diagnostics...)
if len(diagnostics) != 0 {
return nil, accumulator.loadError()
}
resolved, diagnostics := resolveLoadInput(schema, options.Definition, input, decoded)
resolved, diagnostics := resolveLoadInput(schema, request.definition, input, decoded)
accumulator.add(diagnostics...)
if hasErrors(diagnostics) {
return nil, accumulator.loadError()
@@ -177,8 +194,8 @@ func loadWithSecretLookup[T any](source Source, secrets SecretBinding, lookup se
if hasErrors(secretResolution.diagnostics) {
return nil, accumulator.loadError()
}
if options.Definition.Validate != nil {
diagnostics = runValidation(&configuration, options.Definition.Validate, schema, resolved.final, input.document, secretResolution.lookups)
if request.definition.Validate != nil {
diagnostics = runValidation(&configuration, request.definition.Validate, schema, resolved.final, input.document, secretResolution.lookups)
accumulator.add(diagnostics...)
if hasErrors(diagnostics) {
return nil, accumulator.loadError()
@@ -187,5 +204,5 @@ func loadWithSecretLookup[T any](source Source, secrets SecretBinding, lookup se
resolved.configuration = configuration
// Publication detaches equal-valued validator replacements, preserving the
// validated secret state, then finalizes metadata and sensitivity.
return publishLoadResult(schema, options.Definition, resolved, secretResolution.references, &accumulator)
return publishLoadResult(schema, request.definition, resolved, secretResolution.references, &accumulator)
}