Arrays, empty structures, assignment objects accepted
This commit is contained in:
parent
2fae04dacf
commit
23e6ebe938
14
ast.go
14
ast.go
@ -11,10 +11,20 @@ const (
|
||||
type Node interface{}
|
||||
|
||||
type ObjectNode struct {
|
||||
Elem map[string][]Node
|
||||
Key string
|
||||
Elem []Node
|
||||
}
|
||||
|
||||
type ValueNode struct {
|
||||
type AssignmentNode struct {
|
||||
Key string
|
||||
Value Node
|
||||
}
|
||||
|
||||
type ListNode struct {
|
||||
Elem []Node
|
||||
}
|
||||
|
||||
type LiteralNode struct {
|
||||
Type ValueType
|
||||
Value interface{}
|
||||
}
|
||||
|
8
parse.go
8
parse.go
@ -20,7 +20,13 @@ func Parse(v string) (*ObjectNode, error) {
|
||||
hclResult = nil
|
||||
|
||||
// Parse
|
||||
hclParse(&hclLex{Input: v})
|
||||
lex := &hclLex{Input: v}
|
||||
hclParse(lex)
|
||||
|
||||
// If we have an error in the lexer itself, return it
|
||||
if lex.err != nil {
|
||||
return nil, lex.err
|
||||
}
|
||||
|
||||
// Build up the errors
|
||||
var err error
|
||||
|
88
parse.y
88
parse.y
@ -13,9 +13,9 @@ package hcl
|
||||
str string
|
||||
}
|
||||
|
||||
%type <list> list
|
||||
%type <listitem> listitem
|
||||
%type <obj> block object objectlist
|
||||
%type <list> list objectlist
|
||||
%type <listitem> listitem objectitem
|
||||
%type <obj> block object
|
||||
%type <str> blockId
|
||||
|
||||
%token <num> NUMBER
|
||||
@ -28,60 +28,64 @@ top:
|
||||
objectlist
|
||||
{
|
||||
hclResult = &ObjectNode{
|
||||
Elem: $1.Elem,
|
||||
Key: "",
|
||||
Elem: $1,
|
||||
}
|
||||
}
|
||||
|
||||
objectlist:
|
||||
object
|
||||
objectitem
|
||||
{
|
||||
$$ = $1
|
||||
$$ = []Node{$1}
|
||||
}
|
||||
| object objectlist
|
||||
| objectitem objectlist
|
||||
{
|
||||
$$ = $1
|
||||
for k, v := range $2.Elem {
|
||||
if _, ok := $$.Elem[k]; ok {
|
||||
$$.Elem[k] = append($$.Elem[k], v...)
|
||||
} else {
|
||||
$$.Elem[k] = v
|
||||
}
|
||||
}
|
||||
$$ = append($2, $1)
|
||||
}
|
||||
|
||||
object:
|
||||
LEFTBRACE objectlist RIGHTBRACE
|
||||
{
|
||||
$$ = ObjectNode{Elem: $2}
|
||||
}
|
||||
| LEFTBRACE RIGHTBRACE
|
||||
{
|
||||
$$ = ObjectNode{}
|
||||
}
|
||||
|
||||
objectitem:
|
||||
IDENTIFIER EQUAL NUMBER
|
||||
{
|
||||
$$ = ObjectNode{
|
||||
Elem: map[string][]Node{
|
||||
$1: []Node{
|
||||
ValueNode{
|
||||
Type: ValueTypeInt,
|
||||
Value: $3,
|
||||
},
|
||||
},
|
||||
$$ = AssignmentNode{
|
||||
Key: $1,
|
||||
Value: LiteralNode{
|
||||
Type: ValueTypeInt,
|
||||
Value: $3,
|
||||
},
|
||||
}
|
||||
}
|
||||
| IDENTIFIER EQUAL STRING
|
||||
{
|
||||
$$ = ObjectNode{
|
||||
Elem: map[string][]Node{
|
||||
$1: []Node{
|
||||
ValueNode{
|
||||
Type: ValueTypeString,
|
||||
Value: $3,
|
||||
},
|
||||
},
|
||||
$$ = AssignmentNode{
|
||||
Key: $1,
|
||||
Value: LiteralNode{
|
||||
Type: ValueTypeString,
|
||||
Value: $3,
|
||||
},
|
||||
}
|
||||
}
|
||||
| IDENTIFIER EQUAL object
|
||||
{
|
||||
$$ = AssignmentNode{
|
||||
Key: $1,
|
||||
Value: $3,
|
||||
}
|
||||
}
|
||||
| IDENTIFIER EQUAL LEFTBRACKET list RIGHTBRACKET
|
||||
{
|
||||
$$ = ObjectNode{
|
||||
Elem: map[string][]Node{
|
||||
$1: $4,
|
||||
},
|
||||
$$ = AssignmentNode{
|
||||
Key: $1,
|
||||
Value: ListNode{Elem: $4},
|
||||
}
|
||||
}
|
||||
| block
|
||||
@ -90,20 +94,16 @@ object:
|
||||
}
|
||||
|
||||
block:
|
||||
blockId LEFTBRACE objectlist RIGHTBRACE
|
||||
blockId object
|
||||
{
|
||||
$$ = ObjectNode{
|
||||
Elem: map[string][]Node{
|
||||
$1: []Node{$3},
|
||||
},
|
||||
}
|
||||
$$ = $2
|
||||
$$.Key = $1
|
||||
}
|
||||
| blockId block
|
||||
{
|
||||
$$ = ObjectNode{
|
||||
Elem: map[string][]Node{
|
||||
$1: []Node{$2},
|
||||
},
|
||||
Key: $1,
|
||||
Elem: []Node{$2},
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -15,9 +15,11 @@ func TestParse(t *testing.T) {
|
||||
{
|
||||
"comment.hcl",
|
||||
&ObjectNode{
|
||||
Elem: map[string][]Node{
|
||||
"foo": []Node{
|
||||
ValueNode{
|
||||
Key: "",
|
||||
Elem: []Node{
|
||||
AssignmentNode{
|
||||
Key: "foo",
|
||||
Value: LiteralNode{
|
||||
Type: ValueTypeString,
|
||||
Value: "bar",
|
||||
},
|
||||
@ -25,6 +27,7 @@ func TestParse(t *testing.T) {
|
||||
},
|
||||
},
|
||||
},
|
||||
/*
|
||||
{
|
||||
"multiple.hcl",
|
||||
&ObjectNode{
|
||||
@ -44,17 +47,19 @@ func TestParse(t *testing.T) {
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
"structure_basic.hcl",
|
||||
&ObjectNode{
|
||||
Elem: map[string][]Node{
|
||||
"foo": []Node{
|
||||
ObjectNode{
|
||||
Elem: map[string][]Node{
|
||||
"value": []Node{
|
||||
ValueNode{
|
||||
Type: ValueTypeInt,
|
||||
Value: 7,
|
||||
/*
|
||||
{
|
||||
"structure_basic.hcl",
|
||||
&ObjectNode{
|
||||
Elem: map[string][]Node{
|
||||
"foo": []Node{
|
||||
ObjectNode{
|
||||
Elem: map[string][]Node{
|
||||
"value": []Node{
|
||||
ValueNode{
|
||||
Type: ValueTypeInt,
|
||||
Value: 7,
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
@ -62,31 +67,31 @@ func TestParse(t *testing.T) {
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
"structure.hcl",
|
||||
&ObjectNode{
|
||||
Elem: map[string][]Node{
|
||||
"foo": []Node{
|
||||
ObjectNode{
|
||||
Elem: map[string][]Node{
|
||||
"bar": []Node{
|
||||
ObjectNode{
|
||||
Elem: map[string][]Node{
|
||||
"baz": []Node{
|
||||
ObjectNode{
|
||||
Elem: map[string][]Node{
|
||||
"key": []Node{
|
||||
ValueNode{
|
||||
Type: ValueTypeInt,
|
||||
Value: 7,
|
||||
{
|
||||
"structure.hcl",
|
||||
&ObjectNode{
|
||||
Elem: map[string][]Node{
|
||||
"foo": []Node{
|
||||
ObjectNode{
|
||||
Elem: map[string][]Node{
|
||||
"bar": []Node{
|
||||
ObjectNode{
|
||||
Elem: map[string][]Node{
|
||||
"baz": []Node{
|
||||
ObjectNode{
|
||||
Elem: map[string][]Node{
|
||||
"key": []Node{
|
||||
ValueNode{
|
||||
Type: ValueTypeInt,
|
||||
Value: 7,
|
||||
},
|
||||
},
|
||||
},
|
||||
|
||||
"foo": []Node{
|
||||
ValueNode{
|
||||
Type: ValueTypeString,
|
||||
Value: "bar",
|
||||
"foo": []Node{
|
||||
ValueNode{
|
||||
Type: ValueTypeString,
|
||||
Value: "bar",
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
@ -100,7 +105,7 @@ func TestParse(t *testing.T) {
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
*/
|
||||
{
|
||||
"complex.hcl",
|
||||
nil,
|
||||
|
5
test-fixtures/assign_deep.hcl
Normal file
5
test-fixtures/assign_deep.hcl
Normal file
@ -0,0 +1,5 @@
|
||||
resource = [{
|
||||
foo = [{
|
||||
bar = {}
|
||||
}]
|
||||
}]
|
@ -1,5 +1,5 @@
|
||||
// This is a test structure for the lexer
|
||||
foo bar "baz" {
|
||||
key = 7
|
||||
foo = "bar"
|
||||
}
|
||||
// This is a test structure for the lexer
|
||||
foo bar "baz" {
|
||||
key = 7
|
||||
foo = "bar"
|
||||
}
|
||||
|
1
test-fixtures/structure_empty.hcl
Normal file
1
test-fixtures/structure_empty.hcl
Normal file
@ -0,0 +1 @@
|
||||
resource "foo" "bar" {}
|
Loading…
Reference in New Issue
Block a user