nektos/act · error
unresolved alias node
Error message
unresolved alias node
What it means
While inlining YAML aliases, resolveAliasesExt found an AliasNode whose .Alias pointer is nil — an alias node (*name) that does not point at any decoded anchor. Well-formed parsers never produce this, but truncated files, manual construction of yaml.Node trees, or pre-parsing that strips anchors can leave dangling alias nodes, which this guard rejects with 'unresolved alias node'.
Source
Thrown at pkg/model/anchors.go:17
package model
import (
"errors"
"gopkg.in/yaml.v3"
)
func resolveAliasesExt(node *yaml.Node, path map[*yaml.Node]bool, skipCheck bool) error {
if !skipCheck && path[node] {
return errors.New("circular alias")
}
switch node.Kind {
case yaml.AliasNode:
aliasTarget := node.Alias
if aliasTarget == nil {
return errors.New("unresolved alias node")
}
path[node] = true
*node = *aliasTarget
if err := resolveAliasesExt(node, path, true); err != nil {
return err
}
delete(path, node)
case yaml.DocumentNode, yaml.MappingNode, yaml.SequenceNode:
for _, child := range node.Content {
if err := resolveAliasesExt(child, path, false); err != nil {
return err
}
}
}
return nil
}
View on GitHub (pinned to 4f41128141)
Solutions
- Search the workflow for every '*name' usage and add the missing '&name:' anchor or fix the typo.
- Replace the alias with a literal value if the anchor was intentionally removed.
- If you preprocess YAML, run the alias check on the final merged document, not fragments.
- Lint the file with any YAML validator to surface the undefined alias before running act.
Example fix
# before
jobs:
build: &job_template
runs-on: ubuntu-latest
deploy: *job_templete # typo -> unresolved alias node
# after
jobs:
build: &job_template
runs-on: ubuntu-latest
deploy: *job_template Defensive patterns
Strategy: validation
Validate before calling
# Verify every alias has a matching anchor
python3 - <<'EOF'
import re, sys
text = open(sys.argv[1]).read()
anchors = set(re.findall(r'&(\w+)', text))
aliases = set(re.findall(r'\*(\w+)', text))
missing = aliases - anchors
if missing:
sys.exit(f"unresolved aliases: {sorted(missing)}")
print("ok")
EOF Try / catch
if err := model.NewSingleWorkflowPlanner(path)(...) ; err != nil {
if strings.Contains(err.Error(), "unresolved alias node") {
return fmt.Errorf("an alias (*name) has no matching anchor (&name) in the workflow: %w", err)
}
return err
} Prevention
- After refactoring workflow YAML, grep aliases and anchors to confirm they pair up.
- Never copy an '*alias' snippet without its '&' anchor definition.
- Apply script-based YAML edits to the whole document, not fragments.
When it happens
Trigger: A workflow YAML containing '*foo' with no matching '&foo' anchor in the document; programmatically built or mutated yaml.Node trees where aliases were cloned without their targets; documents preprocessed by a tool that removed anchor definitions but kept the alias usages.
Common situations: Copy-pasting a snippet that uses an alias defined elsewhere in the original file; sed/script-based workflow refactors that delete the anchor line but not its references; partial merges of reusable workflow YAML; typos in alias names.
Related errors
- circular alias
- ErrShortRef
- --pid: invalid PID mode
- network-scoped aliases are only supported for user-defined n
- links are only supported for user-defined networks
AI-assisted analysis of nektos/act@4f41128141 (2026-08-15).
Data as JSON: /api/errors/abb7b9e4c80405d0.
Report an issue: GitHub.