parser: more improvements around ATS

This commit is contained in:
Fatih Arslan 2015-10-12 23:44:53 +03:00
parent 8d60ae5dc5
commit 45d01fe82d
2 changed files with 40 additions and 22 deletions

View File

@ -2,18 +2,6 @@ package parser
import "github.com/fatih/hcl/scanner" import "github.com/fatih/hcl/scanner"
type NodeType int
const (
Unknown NodeType = 0
Number
Float
Bool
String
List
Object
)
// Node is an element in the abstract syntax tree. // Node is an element in the abstract syntax tree.
type Node interface { type Node interface {
node() node()
@ -109,15 +97,18 @@ func (o *ObjectStatement) Pos() scanner.Pos {
// LiteralType represents a literal of basic type. Valid types are: // LiteralType represents a literal of basic type. Valid types are:
// scanner.NUMBER, scanner.FLOAT, scanner.BOOL and scanner.STRING // scanner.NUMBER, scanner.FLOAT, scanner.BOOL and scanner.STRING
type LiteralType struct { type LiteralType struct {
token scanner.Token *Ident
} }
func (l *LiteralType) String() string { // isValid() returns true if the underlying identifier satisfies one of the
return l.token.Text // valid types.
} func (l *LiteralType) isValid() bool {
switch l.token.Type {
func (l *LiteralType) Pos() scanner.Pos { case scanner.NUMBER, scanner.FLOAT, scanner.BOOL, scanner.STRING:
return l.token.Pos return true
default:
return false
}
} }
// ListStatement represents a HCL List type // ListStatement represents a HCL List type

View File

@ -55,7 +55,7 @@ func (p *Parser) parseNode() (Node, error) {
if tok.Type.IsLiteral() { if tok.Type.IsLiteral() {
if p.prevTok.Type.IsLiteral() { if p.prevTok.Type.IsLiteral() {
return p.parseObjectType() return p.parseObjectStatement()
} }
tok := p.scan() tok := p.scan()
@ -70,6 +70,7 @@ func (p *Parser) parseNode() (Node, error) {
return nil, errors.New("not yet implemented") return nil, errors.New("not yet implemented")
} }
// parseAssignment parses an assignment and returns a AssignStatement AST
func (p *Parser) parseAssignment() (*AssignStatement, error) { func (p *Parser) parseAssignment() (*AssignStatement, error) {
defer un(trace(p, "ParseAssignment")) defer un(trace(p, "ParseAssignment"))
a := &AssignStatement{ a := &AssignStatement{
@ -88,6 +89,7 @@ func (p *Parser) parseAssignment() (*AssignStatement, error) {
return a, nil return a, nil
} }
// parseIdent parses a generic identifier and returns a Ident AST
func (p *Parser) parseIdent() (*Ident, error) { func (p *Parser) parseIdent() (*Ident, error) {
defer un(trace(p, "ParseIdent")) defer un(trace(p, "ParseIdent"))
@ -100,12 +102,37 @@ func (p *Parser) parseIdent() (*Ident, error) {
}, nil }, nil
} }
func (p *Parser) parseObjectType() (*ObjectStatement, error) { // parseLiteralType parses a literal type and returns a LiteralType AST
func (p *Parser) parseLiteralType() (*LiteralType, error) {
i, err := p.parseIdent()
if err != nil {
return nil, err
}
l := &LiteralType{}
l.Ident = i
if !l.isValid() {
return nil, fmt.Errorf("Identifier is not a LiteralType: %s", l.token)
}
return l, nil
}
// parseObjectStatement parses an object statement returns an ObjectStatement
// AST. ObjectsStatements represents both normal and nested objects statement
func (p *Parser) parseObjectStatement() (*ObjectStatement, error) {
return nil, errors.New("ObjectStatement is not implemented yet") return nil, errors.New("ObjectStatement is not implemented yet")
} }
// parseObjectType parses an object type and returns a ObjectType AST
func (p *Parser) parseObjectType() (*ObjectType, error) {
return nil, errors.New("ObjectType is not implemented yet")
}
// parseListType parses a list type and returns a ListType AST
func (p *Parser) parseListType() (*ListType, error) { func (p *Parser) parseListType() (*ListType, error) {
return nil, errors.New("ListStatement is not implemented yet") return nil, errors.New("ListType is not implemented yet")
} }
// scan returns the next token from the underlying scanner. // scan returns the next token from the underlying scanner.