github.com/vcilabs/webrpc@v0.5.2-0.20201116131534-162e27b1b33b/schema/ridl/type_parser.go (about)

     1  package ridl
     2  
     3  import (
     4  	"errors"
     5  )
     6  
     7  func (p *parser) expectMapDefinition() (*token, error) {
     8  
     9  	tok := p.cursor()
    10  	if tok.val != "map" {
    11  		return nil, errors.New(`expecting "map"`)
    12  	}
    13  	p.next()
    14  
    15  	tokens := []*token{tok}
    16  
    17  loop:
    18  	for {
    19  		tok := p.cursor()
    20  
    21  		switch tok.tt {
    22  
    23  		case tokenWhitespace:
    24  			p.next()
    25  			continue loop
    26  
    27  		case tokenCloseAngleBracket:
    28  			p.next()
    29  			break loop
    30  
    31  		case tokenOpenAngleBracket:
    32  			types, err := p.expectTypeList()
    33  			if err != nil {
    34  				return nil, err
    35  			}
    36  
    37  			tokens = append(tokens, types)
    38  			continue loop
    39  
    40  		default:
    41  			return nil, errUnexpectedToken
    42  		}
    43  	}
    44  
    45  	return composedValue(tokens)
    46  }
    47  
    48  func (p *parser) expectArgumentList() ([]*ArgumentNode, error) {
    49  	values := []*ArgumentNode{}
    50  
    51  	matches, err := p.match(tokenWord, tokenWhitespace)
    52  	if err == nil {
    53  		if matches[0].val != "stream" {
    54  			return nil, errUnexpectedToken
    55  		}
    56  	}
    57  
    58  	tok, err := p.match(tokenOpenParen)
    59  	if err != nil {
    60  		return nil, err
    61  	}
    62  
    63  	tokens := []*token{tok[0]}
    64  
    65  loop:
    66  	for {
    67  		tok := p.cursor()
    68  
    69  		switch tok.tt {
    70  
    71  		case tokenWhitespace:
    72  			p.next()
    73  			continue
    74  
    75  		case tokenCloseParen:
    76  			tokens = append(tokens, tok)
    77  			p.next()
    78  			break loop
    79  
    80  		case tokenComma:
    81  			tokens = append(tokens, tok)
    82  			p.next()
    83  
    84  		case tokenWord:
    85  			var argument []*token
    86  			var name *token
    87  
    88  			optional := false
    89  
    90  			matches, err := p.match(tokenWord, tokenQuestionMark, tokenColon, tokenWhitespace)
    91  			if err == nil {
    92  				argument = []*token{matches[0], matches[1], matches[2]}
    93  				name = matches[0]
    94  				optional = true
    95  			} else {
    96  				matches, err = p.match(tokenWord, tokenColon, tokenWhitespace)
    97  				if err != nil {
    98  					return nil, err
    99  				}
   100  				argument = []*token{matches[0], matches[1]}
   101  				name = matches[0]
   102  			}
   103  
   104  			varType, err := p.expectType()
   105  			if err != nil {
   106  				return nil, err
   107  			}
   108  
   109  			values = append(values, &ArgumentNode{
   110  				name:         newTokenNode(name),
   111  				argumentType: newTokenNode(varType),
   112  				optional:     optional,
   113  			})
   114  
   115  			tokens = append(tokens, append(argument, varType)...)
   116  
   117  		default:
   118  			return nil, errUnexpectedToken
   119  
   120  		}
   121  	}
   122  
   123  	//return composedValue(tokens)
   124  
   125  	return values, nil
   126  }
   127  
   128  func (p *parser) expectTypeList() (*token, error) {
   129  
   130  	tok, err := p.match(tokenOpenAngleBracket)
   131  	if err != nil {
   132  		return nil, err
   133  	}
   134  
   135  	tokens := []*token{tok[0]}
   136  
   137  loop:
   138  	for {
   139  		tok := p.cursor()
   140  
   141  		switch tok.tt {
   142  
   143  		case tokenWhitespace:
   144  			p.next()
   145  			continue
   146  
   147  		case tokenCloseAngleBracket:
   148  			tokens = append(tokens, tok)
   149  			break loop
   150  
   151  		case tokenComma:
   152  			tokens = append(tokens, tok)
   153  			p.next()
   154  
   155  		case tokenWord, tokenOpenBracket:
   156  			tok, err := p.expectType()
   157  			if err != nil {
   158  				return nil, err
   159  			}
   160  
   161  			tokens = append(tokens, tok)
   162  
   163  		default:
   164  			return nil, errUnexpectedToken
   165  		}
   166  	}
   167  
   168  	return composedValue(tokens)
   169  }
   170  
   171  func (p *parser) expectType() (*token, error) {
   172  	tokens := []*token{}
   173  
   174  loop:
   175  	for {
   176  		tok := p.cursor()
   177  
   178  		switch tok.tt {
   179  
   180  		case tokenNewLine, tokenWhitespace, tokenComma, tokenCloseAngleBracket, tokenCloseParen, tokenHash:
   181  			break loop
   182  
   183  		case tokenEOF:
   184  			return nil, errUnexpectedEOF
   185  
   186  		case tokenOpenBracket:
   187  			brackets, err := p.match(tokenOpenBracket, tokenCloseBracket)
   188  			if err != nil {
   189  				return nil, err
   190  			}
   191  
   192  			typeName, err := p.expectType()
   193  			if err != nil {
   194  				return nil, err
   195  			}
   196  
   197  			tokens = append(tokens, append(brackets, typeName)...)
   198  			continue loop
   199  
   200  		case tokenWord:
   201  
   202  			switch tok.val {
   203  
   204  			case "map":
   205  				var err error
   206  
   207  				tok, err = p.expectMapDefinition()
   208  				if err != nil {
   209  					return nil, err
   210  				}
   211  
   212  				tokens = append(tokens, tok)
   213  				continue loop
   214  			}
   215  
   216  			tokens = append(tokens, tok)
   217  			p.next()
   218  			continue
   219  
   220  		default:
   221  			return nil, errUnexpectedToken
   222  		}
   223  
   224  		p.next()
   225  	}
   226  
   227  	return composedValue(tokens)
   228  }