package engine import "gitea.maximumdirect.net/eric/ConfigKit/internal/document" const inheritanceKey = "extends" // These private records keep structural evidence separate from acquired source // records. Later inspection can project a transfer onto individual descendants. type inheritanceTransfer struct { from Path to Path reference Path locations []Location } type inheritanceControl struct { path Path locations []Location cancelled bool } type inheritanceScope struct { root *document.Node origins map[string]Origin transfers []inheritanceTransfer controls []inheritanceControl replacements []inheritanceReplacement operations []inheritanceOperation } type inheritanceOperation struct { control *inheritanceControl transfer *inheritanceTransfer controlOrigin Origin parent *document.Node effective *document.Node parentOrigins map[string]Origin effectiveOrigins map[string]Origin } // A replacement retains the displaced source/derivation record while the // effective origin belongs to the child. Value trees are borrowed immutable // inputs or detached templates and are budgeted with retained history later. type inheritanceReplacement struct { path Path before *document.Node after *document.Node previous []displacedDefinition effective Origin } // A link represents one shared relationship edge. Each contributor retains // its original semantic path independently of source line/column coordinates. type inheritanceTrace struct { previous *inheritanceTrace transfer *inheritanceTransfer } type inheritanceContributor struct { source Path location Location trace *inheritanceTrace } // expandSiblingDefinitions resolves only the mappings directly in scope. // Nested instructions remain in the returned templates for destination-local // resolution. This private entry point does not participate in public loading. func expandSiblingDefinitions(scope *document.Node, scopePath Path) (*inheritanceScope, []Diagnostic) { return expandSiblingDefinitionsWithLimits(scope, scopePath, defaultProjectionLimits()) } func expandSiblingDefinitionsWithLimits(scope *document.Node, scopePath Path, limits projectionLimits) (*inheritanceScope, []Diagnostic) { return expandSiblingDefinitionsWithOrigins(scope, scopePath, limits, nil) } func inheritanceDirective(node *document.Node) (document.Entry, bool) { for _, entry := range node.Mapping { if entry.Key == inheritanceKey { return entry, true } } return document.Entry{}, false } func inheritanceDirectiveLocation(node *document.Node) Location { entry, _ := inheritanceDirective(node) return publicLocation(entry.Value.Location) } func withoutInheritanceDirective(node *document.Node) *document.Node { payload := *node payload.Mapping = make([]document.Entry, 0, len(node.Mapping)) for _, entry := range node.Mapping { if entry.Key != inheritanceKey { payload.Mapping = append(payload.Mapping, entry) } } return &payload } func inheritanceDiagnostic(code Code, path Path, primary Location, related []Location, message string) Diagnostic { return Diagnostic{ Code: code, Severity: SeverityError, Path: path, Message: message, Primary: &primary, Related: related, } }