MCPcopy Create free account
hub / github.com/github/gh-aw / detectCircularModelAliases

Function detectCircularModelAliases

pkg/workflow/model_alias_validation.go:241–277  ·  view source on GitHub ↗

─── V-MAF-010: circular alias detection ───────────────────────────────────── detectCircularModelAliases performs a full DFS cycle check over the merged alias map and returns an error naming every alias in the cycle (V-MAF-010). Algorithm (Section 8.6.1): For each alias key, perform a depth-first

(aliasMap map[string][]string, markdownPath string)

Source from the content-addressed store, hash-verified

239// If any traversal reaches an alias key already on the current path, a cycle
240// is detected and MUST be reported as a compile-time error.
241func detectCircularModelAliases(aliasMap map[string][]string, markdownPath string) error {
242 modelAliasValidationLog.Printf("Checking for circular alias references in %d aliases", len(aliasMap))
243
244 // visited tracks keys for which all DFS descendants have been fully explored
245 // (no cycle detected from that key).
246 visited := map[string]struct {
247 }{}
248
249 // Iterate keys in deterministic order for reproducible error messages.
250 keys := sliceutil.SortedKeys(aliasMap)
251
252 state := &dfsState{
253 aliasMap: aliasMap,
254 visited: visited,
255 onPath: make(map[string]bool, 16),
256 path: make([]string, 0, 16),
257 }
258
259 for _, key := range keys {
260 if setutil.Contains(visited, key) {
261 continue
262 }
263 clear(state.onPath)
264 state.path = state.path[:0]
265 if cycle := state.dfs(key); cycle != nil {
266 // Format cycle chain for a clear error message.
267 chain := strings.Join(append(cycle, cycle[0]), " → ")
268 return formatCompilerError(markdownPath, "error",
269 fmt.Sprintf("circular alias reference detected: %s\n\n"+
270 "Circular alias references are prohibited. Remove or rewrite the cycle in the 'models:' "+
271 "frontmatter section (V-MAF-010).", chain),
272 nil)
273 }
274 }
275
276 return nil
277}
278
279// dfsState holds the mutable state for a single DFS traversal.
280type dfsState struct {

Calls 5

dfsMethod · 0.95
SortedKeysFunction · 0.92
ContainsFunction · 0.92
formatCompilerErrorFunction · 0.85
PrintfMethod · 0.45