mirror of
https://gitea.com/gitea/act_runner.git
synced 2026-03-20 03:46:09 +08:00
fix: anchor cyclic detection (#30)
Closes #25 Reviewed-on: https://gitea.com/actions-oss/act-cli/pulls/30 Co-authored-by: Christopher Homberger <christopher.homberger@web.de> Co-committed-by: Christopher Homberger <christopher.homberger@web.de>
This commit is contained in:
committed by
ChristopherHX
parent
13e0654fd7
commit
6c827eba95
@@ -21,7 +21,7 @@ func resolveAliasesExt(node *yaml.Node, path map[*yaml.Node]bool, skipCheck bool
|
||||
if err := resolveAliasesExt(node, path, true); err != nil {
|
||||
return err
|
||||
}
|
||||
delete(path, aliasTarget)
|
||||
delete(path, node)
|
||||
|
||||
case yaml.DocumentNode, yaml.MappingNode, yaml.SequenceNode:
|
||||
for _, child := range node.Content {
|
||||
|
||||
@@ -7,29 +7,6 @@ import (
|
||||
"gopkg.in/yaml.v3"
|
||||
)
|
||||
|
||||
func TestVerifyCycleIsInvalid(t *testing.T) {
|
||||
var node yaml.Node
|
||||
err := yaml.Unmarshal([]byte(`
|
||||
a: &a
|
||||
ref: *b
|
||||
|
||||
b: &b
|
||||
ref: *a
|
||||
`), &node)
|
||||
assert.Error(t, err)
|
||||
}
|
||||
|
||||
func TestVerifyCycleIsInvalid2(t *testing.T) {
|
||||
var node yaml.Node
|
||||
err := yaml.Unmarshal([]byte(`
|
||||
a: &a
|
||||
ref: *a
|
||||
`), &node)
|
||||
assert.NoError(t, err)
|
||||
err = resolveAliases(&node)
|
||||
assert.Error(t, err)
|
||||
}
|
||||
|
||||
func TestVerifyNilAliasError(t *testing.T) {
|
||||
var node yaml.Node
|
||||
err := yaml.Unmarshal([]byte(`
|
||||
@@ -44,3 +21,94 @@ test:
|
||||
err = resolveAliases(&node)
|
||||
assert.Error(t, err)
|
||||
}
|
||||
|
||||
func TestVerifyNoRecursion(t *testing.T) {
|
||||
table := []struct {
|
||||
name string
|
||||
yaml string
|
||||
yamlErr bool
|
||||
anchorErr bool
|
||||
}{
|
||||
{
|
||||
name: "no anchors",
|
||||
yaml: `
|
||||
a: x
|
||||
b: y
|
||||
c: z
|
||||
`,
|
||||
yamlErr: false,
|
||||
anchorErr: false,
|
||||
},
|
||||
{
|
||||
name: "simple anchors",
|
||||
yaml: `
|
||||
a: &a x
|
||||
b: &b y
|
||||
c: *a
|
||||
`,
|
||||
yamlErr: false,
|
||||
anchorErr: false,
|
||||
},
|
||||
{
|
||||
name: "nested anchors",
|
||||
yaml: `
|
||||
a: &a
|
||||
val: x
|
||||
b: &b
|
||||
val: y
|
||||
c: *a
|
||||
`,
|
||||
yamlErr: false,
|
||||
anchorErr: false,
|
||||
},
|
||||
{
|
||||
name: "circular anchors",
|
||||
yaml: `
|
||||
a: &b
|
||||
ref: *c
|
||||
b: &c
|
||||
ref: *b
|
||||
`,
|
||||
yamlErr: true,
|
||||
anchorErr: false,
|
||||
},
|
||||
{
|
||||
name: "self-referencing anchor",
|
||||
yaml: `
|
||||
a: &a
|
||||
ref: *a
|
||||
`,
|
||||
yamlErr: false,
|
||||
anchorErr: true,
|
||||
},
|
||||
{
|
||||
name: "reuse snippet with anchors",
|
||||
yaml: `
|
||||
a: &b x
|
||||
b: &a
|
||||
ref: *b
|
||||
c: *a
|
||||
`,
|
||||
yamlErr: false,
|
||||
anchorErr: false,
|
||||
},
|
||||
}
|
||||
|
||||
for _, tt := range table {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
var node yaml.Node
|
||||
err := yaml.Unmarshal([]byte(tt.yaml), &node)
|
||||
if tt.yamlErr {
|
||||
assert.Error(t, err)
|
||||
return
|
||||
}
|
||||
assert.NoError(t, err)
|
||||
err = resolveAliases(&node)
|
||||
if tt.anchorErr {
|
||||
assert.Error(t, err)
|
||||
} else {
|
||||
assert.NoError(t, err)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
@@ -614,17 +614,21 @@ jobs:
|
||||
|
||||
func TestReadWorkflow_Anchor(t *testing.T) {
|
||||
yaml := `
|
||||
on: push
|
||||
|
||||
jobs:
|
||||
test:
|
||||
runs-on: &runner ubuntu-latest
|
||||
steps:
|
||||
- uses: &checkout actions/checkout@v5
|
||||
test2:
|
||||
test2: &job
|
||||
runs-on: *runner
|
||||
steps:
|
||||
- uses: *checkout
|
||||
- run: echo $TRIGGER
|
||||
env:
|
||||
TRIGGER: &trigger push
|
||||
test3: *job
|
||||
on: push #*trigger
|
||||
`
|
||||
|
||||
w, err := ReadWorkflow(strings.NewReader(yaml), false)
|
||||
|
||||
Reference in New Issue
Block a user