func (l *Lexer) readToken() *Token {
	positionAfterWhitespace(l)

	if l.currPos >= len(l.source) {
		return newToken(EOF, l.currPos)
	}

	start := l.currPos
	code, size := utf8.DecodeRuneInString(l.source[l.currPos:])
	l.currPos += size

	if code < 0x0020 && code != 0x0009 && code != 0x000A && code != 0x000D {
		log.Fatalf("Invalid character %U", code)
	}

	switch {
	case code == '#':
		return readComment(l, start)
	case code == '{':
		return newToken(BRACE_L, start)
	case code == '}':
		return newToken(BRACE_R, start)
	case code == '!':
		return newToken(BANG, start)
	case code == '$':
		return newToken(DOLLAR, start)
	case code == '(':
		return newToken(PAREN_L, start)
	case code == ')':
		return newToken(PAREN_R, start)
	case strings.HasPrefix(l.source[start:], "..."):
		l.currPos = start + 3
		return newToken(SPREAD, start)
	case code == ':':
		return newToken(COLON, start)
	case code == '=':
		return newToken(EQUALS, start)
	case code == '@':
		return newToken(AT, start)
	case code == '[':
		return newToken(BRACKET_L, start)
	case code == ']':
		return newToken(BRACKET_R, start)
	case code == '|':
		return newToken(PIPE, start)
	case ('_' == code) || (code >= 'A' && code <= 'Z') || (code >= 'a' && code <= 'z'):
		return readName(l, start)
	case (code >= '0' && code <= '9') || code == '-':
		return readNumber(l, start, code)
	case code == '"':
		return readString(l, start)
	}

	return newToken(LEX_ERROR, l.currPos, fmt.Sprintf("Invalid charactère code '%c'", code))
}
// ReadToken returns the next token
ReadToken returns the next token
// ReadToken returns the next token
func (l *Lexer) readToken() *Token {
	positionAfterWhitespace(l)
	if l.currPos >= len(l.source) {
		return newToken(EOF, l.currPos)
	}
	start := l.currPos
	code, size := utf8.DecodeRuneInString(l.source[l.currPos:])
	l.currPos += size
	if code < 0x0020 && code != 0x0009 && code != 0x000A && code != 0x000D {
		log.Fatalf("Invalid character %U", code)
	}
	switch {
	case code == '#':
		return readComment(l, start)
	case code == '{':
		return newToken(BRACE_L, start)
	case code == '}':
		return newToken(BRACE_R, start)
	case code == '!':
		return newToken(BANG, start)
	case code == '$':
		return newToken(DOLLAR, start)
	case code == '(':
		return newToken(PAREN_L, start)
	case code == ')':
		return newToken(PAREN_R, start)
	case strings.HasPrefix(l.source[start:], "..."):
		l.currPos = start + 3
		return newToken(SPREAD, start)
	case code == ':':
		return newToken(COLON, start)
	case code == '=':
		return newToken(EQUALS, start)
	case code == '@':
		return newToken(AT, start)
	case code == '[':
		return newToken(BRACKET_L, start)
	case code == ']':
		return newToken(BRACKET_R, start)
	case code == '|':
		return newToken(PIPE, start)
	case ('_' == code) || (code >= 'A' && code <= 'Z') || (code >= 'a' && code <= 'z'):
		return readName(l, start)
	case (code >= '0' && code <= '9') || code == '-':
		return readNumber(l, start, code)
	case code == '"':
		return readString(l, start)
	}
	return newToken(LEX_ERROR, l.currPos, fmt.Sprintf("Invalid charactère code '%c'", code))
}
func ( l * Lexer ) readToken ( ) * Token { positionAfterWhitespace ( l ) if l . currPos >= len ( l . source ) { return newToken ( EOF , l . currPos ) } start := l . currPos code , size := utf8 . DecodeRuneInString ( l . source [ l . currPos : ] ) l . currPos += size if code < 0x0020 && code != 0x0009 && code != 0x000A && code != 0x000D { log . Fatalf ( " " , code ) } switch { case code == '#' : return readComment ( l , start ) case code == '{' : return newToken ( BRACE_L , start ) case code == '}' : return newToken ( BRACE_R , start ) case code == '!' : return newToken ( BANG , start ) case code == '$' : return newToken ( DOLLAR , start ) case code == '(' : return newToken ( PAREN_L , start ) case code == ')' : return newToken ( PAREN_R , start ) case strings . HasPrefix ( l . source [ start : ] , " " ) : l . currPos = start + 3 return newToken ( SPREAD , start ) case code == ':' : return newToken ( COLON , start ) case code == '=' : return newToken ( EQUALS , start ) case code == '@' : return newToken ( AT , start ) case code == '[' : return newToken ( BRACKET_L , start ) case code == ']' : return newToken ( BRACKET_R , start ) case code == '|' : return newToken ( PIPE , start ) case ( '_' == code ) || ( code >= 'A' && code <= 'Z' ) || ( code >= 'a' && code <= 'z' ) : return readName ( l , start ) case ( code >= '0' && code <= '9' ) || code == '-' : return readNumber ( l , start , code ) case code == '"' : return readString ( l , start ) } return newToken ( LEX_ERROR , l . currPos , fmt . Sprintf ( " , ode) ) }
ReadToken returns the next token
ReadToken returns the next token