// Single blocks are easy: just pass right through.
returnb.Block.StaticValidateTraversal(traversal)
}
iflen(traversal)==0{
// It's always valid to access a nested block's attribute directly.
returnnil
}
vardiagstfdiags.Diagnostics
next:=traversal[0]
after:=traversal[1:]
switchb.Nesting{
caseNestingSet:
// Can't traverse into a set at all, since it does not have any keys
// to index with.
diags=diags.Append(&hcl.Diagnostic{
Severity:hcl.DiagError,
Summary:`Cannot index a set value`,
Detail:fmt.Sprintf(`Block type %q is represented by a set of objects, and set elements do not have addressable keys. To find elements matching specific criteria, use a "for" expression with an "if" clause.`,typeName),
Subject:next.SourceRange().Ptr(),
})
returndiags
caseNestingList:
if_,ok:=next.(hcl.TraverseIndex);ok{
moreDiags:=b.Block.StaticValidateTraversal(after)
diags=diags.Append(moreDiags)
}else{
diags=diags.Append(&hcl.Diagnostic{
Severity:hcl.DiagError,
Summary:`Invalid operation`,
Detail:fmt.Sprintf(`Block type %q is represented by a list of objects, so it must be indexed using a numeric key, like .%s[0].`,typeName,typeName),
Subject:next.SourceRange().Ptr(),
})
}
returndiags
caseNestingMap:
// Both attribute and index steps are valid for maps, so we'll just
// pass through here and let normal evaluation catch an
// incorrectly-typed index key later, if present.
moreDiags:=b.Block.StaticValidateTraversal(after)
diags=diags.Append(moreDiags)
returndiags
default:
// Invalid nesting type is just ignored. It's checked by
// InternalValidate. (Note that we handled NestingSingle separately