File: C:/Users/fred/anaconda3/Lib/site-packages/datashader/datashape/tests/test_lexer.py
"""
Test the DataShape lexer.
"""
from __future__ import absolute_import, division, print_function
import unittest
from datashader import datashape
from datashader.datashape import lexer
class TestDataShapeLexer(unittest.TestCase):
def check_isolated_token(self, ds_str, tname, val=None):
# The token name should be a property in parser
tid = getattr(lexer, tname)
# Lexing should produce a single token matching the specification
self.assertEqual(list(lexer.lex(ds_str)),
[lexer.Token(tid, tname, (0, len(ds_str)), val)])
def check_failing_token(self, ds_str):
# Creating the lexer will fail, because the error is
# in the first token.
self.assertRaises(datashape.DataShapeSyntaxError, list, lexer.lex(ds_str))
def test_isolated_tokens(self):
self.check_isolated_token('testing', 'NAME_LOWER', 'testing')
self.check_isolated_token('Testing', 'NAME_UPPER', 'Testing')
self.check_isolated_token('_testing', 'NAME_OTHER', '_testing')
self.check_isolated_token('*', 'ASTERISK')
self.check_isolated_token(',', 'COMMA')
self.check_isolated_token('=', 'EQUAL')
self.check_isolated_token(':', 'COLON')
self.check_isolated_token('[', 'LBRACKET')
self.check_isolated_token(']', 'RBRACKET')
self.check_isolated_token('{', 'LBRACE')
self.check_isolated_token('}', 'RBRACE')
self.check_isolated_token('(', 'LPAREN')
self.check_isolated_token(')', 'RPAREN')
self.check_isolated_token('...', 'ELLIPSIS')
self.check_isolated_token('->', 'RARROW')
self.check_isolated_token('?', 'QUESTIONMARK')
self.check_isolated_token('32102', 'INTEGER', 32102)
self.check_isolated_token('->', 'RARROW')
self.check_isolated_token('"testing"', 'STRING', 'testing')
self.check_isolated_token("'testing'", 'STRING', 'testing')
def test_integer(self):
# Digits
self.check_isolated_token('0', 'INTEGER', 0)
self.check_isolated_token('1', 'INTEGER', 1)
self.check_isolated_token('2', 'INTEGER', 2)
self.check_isolated_token('3', 'INTEGER', 3)
self.check_isolated_token('4', 'INTEGER', 4)
self.check_isolated_token('5', 'INTEGER', 5)
self.check_isolated_token('6', 'INTEGER', 6)
self.check_isolated_token('7', 'INTEGER', 7)
self.check_isolated_token('8', 'INTEGER', 8)
self.check_isolated_token('9', 'INTEGER', 9)
# Various-sized numbers
self.check_isolated_token('10', 'INTEGER', 10)
self.check_isolated_token('102', 'INTEGER', 102)
self.check_isolated_token('1024', 'INTEGER', 1024)
self.check_isolated_token('10246', 'INTEGER', 10246)
self.check_isolated_token('102468', 'INTEGER', 102468)
self.check_isolated_token('1024683', 'INTEGER', 1024683)
self.check_isolated_token('10246835', 'INTEGER', 10246835)
self.check_isolated_token('102468357', 'INTEGER', 102468357)
self.check_isolated_token('1024683579', 'INTEGER', 1024683579)
# Leading zeros are not allowed
self.check_failing_token('00')
self.check_failing_token('01')
self.check_failing_token('090')
def test_string(self):
# Trivial strings
self.check_isolated_token('""', 'STRING', '')
self.check_isolated_token("''", 'STRING', '')
self.check_isolated_token('"test"', 'STRING', 'test')
self.check_isolated_token("'test'", 'STRING', 'test')
# Valid escaped characters
self.check_isolated_token(r'"\"\b\f\n\r\t\ub155"', 'STRING',
u'"\b\f\n\r\t\ub155')
self.check_isolated_token(r"'\'\b\f\n\r\t\ub155'", 'STRING',
u"'\b\f\n\r\t\ub155")
# A sampling of invalid escaped characters
self.check_failing_token(r'''"\'"''')
self.check_failing_token(r"""'\"'""")
self.check_failing_token(r"'\a'")
self.check_failing_token(r"'\s'")
self.check_failing_token(r"'\R'")
self.check_failing_token(r"'\N'")
self.check_failing_token(r"'\U'")
self.check_failing_token(r"'\u123g'")
self.check_failing_token(r"'\u123'")
# Some unescaped and escapted unicode characters
self.check_isolated_token(u'"\uc548\ub155 \\uc548\\ub155"', 'STRING',
u'\uc548\ub155 \uc548\ub155')
def test_failing_tokens(self):
self.check_failing_token('~')
self.check_failing_token('`')
self.check_failing_token('@')
self.check_failing_token('$')
self.check_failing_token('%')
self.check_failing_token('^')
self.check_failing_token('&')
self.check_failing_token('-')
self.check_failing_token('+')
self.check_failing_token(';')
self.check_failing_token('<')
self.check_failing_token('>')
self.check_failing_token('.')
self.check_failing_token('..')
self.check_failing_token('/')
self.check_failing_token('|')
self.check_failing_token('\\')
def test_whitespace(self):
expected_idval = [(lexer.COLON, None),
(lexer.STRING, 'a'),
(lexer.INTEGER, 12345),
(lexer.RARROW, None),
(lexer.EQUAL, None),
(lexer.ASTERISK, None),
(lexer.NAME_OTHER, '_b')]
# With minimal whitespace
toks = list(lexer.lex(':"a"12345->=*_b'))
self.assertEqual([(tok.id, tok.val) for tok in toks], expected_idval)
# With spaces
toks = list(lexer.lex(' : "a" 12345 -> = * _b '))
self.assertEqual([(tok.id, tok.val) for tok in toks], expected_idval)
# With tabs
toks = list(lexer.lex('\t:\t"a"\t12345\t->\t=\t*\t_b\t'))
self.assertEqual([(tok.id, tok.val) for tok in toks], expected_idval)
# With newlines
toks = list(lexer.lex('\n:\n"a"\n12345\n->\n=\n*\n_b\n'))
self.assertEqual([(tok.id, tok.val) for tok in toks], expected_idval)
# With spaces, tabs, newlines and comments
toks = list(lexer.lex('# comment\n' +
': # X\n' +
' "a" # "b"\t\n' +
'\t12345\n\n' +
'->\n' +
'=\n' +
'*\n' +
'_b # comment\n' +
' \t # end'))
self.assertEqual([(tok.id, tok.val) for tok in toks], expected_idval)