"""Testcases for new cssutils.tokenize.Tokenizer TODO: old tests as new ones are **not complete**! """ import sys import pytest import cssutils.tokenize2 as tokenize2 from cssutils.tokenize2 import Tokenizer class TestTokenizer: testsall = { # IDENT 'äöü߀': [('IDENT', 'äöü߀', 1, 1)], ' a ': [('S', ' ', 1, 1), ('IDENT', 'a', 1, 2), ('S', ' ', 1, 3)], '_a': [('IDENT', '_a', 1, 1)], '-a': [('IDENT', '-a', 1, 1)], '--a': [('IDENT', '--a', 1, 1)], 'aA-_\200\377': [('IDENT', 'aA-_\200\377', 1, 1)], 'a1': [('IDENT', 'a1', 1, 1)], # escapes must end with S or max 6 digits: '\\44 b': [('IDENT', 'Db', 1, 1)], '\\44 b': [('IDENT', 'D', 1, 1), ('S', ' ', 1, 5), ('IDENT', 'b', 1, 6)], '\\44\nb': [('IDENT', 'Db', 1, 1)], '\\44\rb': [('IDENT', 'Db', 1, 1)], '\\44\fb': [('IDENT', 'Db', 1, 1)], '\\44\n*': [('IDENT', 'D', 1, 1), ('CHAR', '*', 2, 1)], '\\44 a': [('IDENT', 'D', 1, 1), ('S', ' ', 1, 5), ('IDENT', 'a', 1, 6)], # TODO: # Note that this means that a "real" space after the escape sequence # must itself either be escaped or doubled: '\\44\\ x': [('IDENT', 'D\\ x', 1, 1)], '\\44 ': [('IDENT', 'D', 1, 1), ('S', ' ', 1, 5)], r'\44': [('IDENT', 'D', 1, 1)], r'\\': [('IDENT', r'\\', 1, 1)], r'\{': [('IDENT', r'\{', 1, 1)], r'\"': [('IDENT', r'\"', 1, 1)], r'\(': [('IDENT', r'\(', 1, 1)], r'\1 \22 \333 \4444 \55555 \666666 \777777 7 \7777777': [ ( ('IDENT', '\x01"\u0333\u4444\U00055555\\666666 \\777777 7', 1, 1) if sys.maxunicode > 0x10000 else ('IDENT', '\x01"\u0333\u4444\\55555 \\666666 \\777777 7', 1, 1) ), ('S', ' ', 1, 43), ('IDENT', '\\7777777', 1, 44), ], # Not a function, important for media queries 'and(': [('IDENT', 'and', 1, 1), ('CHAR', '(', 1, 4)], '\\1 b': [('IDENT', '\x01b', 1, 1)], # repeat: '\\44 b': [('IDENT', 'Db', 1, 1)], '\\123 b': [('IDENT', '\u0123b', 1, 1)], '\\1234 b': [('IDENT', '\u1234b', 1, 1)], '\\12345 b': [ ( ('IDENT', '\U00012345b', 1, 1) if sys.maxunicode > 0x10000 else ('IDENT', '\\12345 b', 1, 1) ) ], '\\123456 b': [('IDENT', '\\123456 b', 1, 1)], '\\1234567 b': [ ('IDENT', '\\1234567', 1, 1), ('S', ' ', 1, 9), ('IDENT', 'b', 1, 10), ], '\\{\\}\\(\\)\\[\\]\\#\\@\\.\\,': [ ('IDENT', '\\{\\}\\(\\)\\[\\]\\#\\@\\.\\,', 1, 1) ], # STRING ' "" ': [('S', ' ', 1, 1), ('STRING', '""', 1, 2), ('S', ' ', 1, 4)], ' "\'" ': [('S', ' ', 1, 1), ('STRING', '"\'"', 1, 2), ('S', ' ', 1, 5)], " '' ": [('S', ' ', 1, 1), ('STRING', "''", 1, 2), ('S', ' ', 1, 4)], "'\\\n'": [('STRING', "''", 1, 1)], "'\\\n\\\n\\\n'": [('STRING', "''", 1, 1)], "'\\\f'": [('STRING', "''", 1, 1)], "'\\\r'": [('STRING', "''", 1, 1)], "'1\\\n2'": [('STRING', "'12'", 1, 1)], "'1\\\r\n2'": [('STRING', "'12'", 1, 1)], # r'"\0020|\0020"': [('STRING', '"\\0020|\\0020"', 1, 1)], r'"\61|\0061"': [('STRING', '"a|a"', 1, 1)], # HASH ' #a ': [('S', ' ', 1, 1), ('HASH', '#a', 1, 2), ('S', ' ', 1, 4)], '#ccc': [('HASH', '#ccc', 1, 1)], '#111': [('HASH', '#111', 1, 1)], '#a1a1a1': [('HASH', '#a1a1a1', 1, 1)], '#1a1a1a': [('HASH', '#1a1a1a', 1, 1)], # NUMBER, for plus see CSS3 ' 0 ': [('S', ' ', 1, 1), ('NUMBER', '0', 1, 2), ('S', ' ', 1, 3)], ' 0.1 ': [('S', ' ', 1, 1), ('NUMBER', '0.1', 1, 2), ('S', ' ', 1, 5)], ' .0 ': [('S', ' ', 1, 1), ('NUMBER', '.0', 1, 2), ('S', ' ', 1, 4)], ' -0 ': [ ('S', ' ', 1, 1), # ('CHAR', '-', 1, 2), # ('NUMBER', '0', 1, 3), ('NUMBER', '-0', 1, 2), ('S', ' ', 1, 4), ], # PERCENTAGE ' 0% ': [('S', ' ', 1, 1), ('PERCENTAGE', '0%', 1, 2), ('S', ' ', 1, 4)], ' .5% ': [('S', ' ', 1, 1), ('PERCENTAGE', '.5%', 1, 2), ('S', ' ', 1, 5)], # URI ' url() ': [('S', ' ', 1, 1), ('URI', 'url()', 1, 2), ('S', ' ', 1, 7)], ' url(a) ': [('S', ' ', 1, 1), ('URI', 'url(a)', 1, 2), ('S', ' ', 1, 8)], ' url("a") ': [('S', ' ', 1, 1), ('URI', 'url("a")', 1, 2), ('S', ' ', 1, 10)], ' url( a ) ': [('S', ' ', 1, 1), ('URI', 'url( a )', 1, 2), ('S', ' ', 1, 10)], # UNICODE-RANGE # CDO ' "': [('STRING', '""', 1, 7)], # CDC ' --> ': [('S', ' ', 1, 1), ('CDC', '-->', 1, 2), ('S', ' ', 1, 5)], # S ' ': [('S', ' ', 1, 1)], ' ': [('S', ' ', 1, 1)], '\r': [('S', '\r', 1, 1)], '\n': [('S', '\n', 1, 1)], '\r\n': [('S', '\r\n', 1, 1)], '\f': [('S', '\f', 1, 1)], '\t': [('S', '\t', 1, 1)], '\r\n\r\n\f\t ': [('S', '\r\n\r\n\f\t ', 1, 1)], # COMMENT, for incomplete see later '/*x*/ ': [('COMMENT', '/*x*/', 1, 1), ('S', ' ', 1, 6)], # FUNCTION ' x( ': [('S', ' ', 1, 1), ('FUNCTION', 'x(', 1, 2), ('S', ' ', 1, 4)], # INCLUDES ' ~= ': [('S', ' ', 1, 1), ('INCLUDES', '~=', 1, 2), ('S', ' ', 1, 4)], '~==': [('INCLUDES', '~=', 1, 1), ('CHAR', '=', 1, 3)], # DASHMATCH ' |= ': [('S', ' ', 1, 1), ('DASHMATCH', '|=', 1, 2), ('S', ' ', 1, 4)], '|==': [('DASHMATCH', '|=', 1, 1), ('CHAR', '=', 1, 3)], # CHAR ' @ ': [('S', ' ', 1, 1), ('CHAR', '@', 1, 2), ('S', ' ', 1, 3)], # --- overwritten for CSS 2.1 --- # LBRACE ' { ': [('S', ' ', 1, 1), ('CHAR', '{', 1, 2), ('S', ' ', 1, 3)], # PLUS ' + ': [('S', ' ', 1, 1), ('CHAR', '+', 1, 2), ('S', ' ', 1, 3)], # GREATER ' > ': [('S', ' ', 1, 1), ('CHAR', '>', 1, 2), ('S', ' ', 1, 3)], # COMMA ' , ': [('S', ' ', 1, 1), ('CHAR', ',', 1, 2), ('S', ' ', 1, 3)], # class ' . ': [('S', ' ', 1, 1), ('CHAR', '.', 1, 2), ('S', ' ', 1, 3)], } tests3 = { # UNICODE-RANGE ' u+0 ': [('S', ' ', 1, 1), ('UNICODE-RANGE', 'u+0', 1, 2), ('S', ' ', 1, 5)], ' u+01 ': [('S', ' ', 1, 1), ('UNICODE-RANGE', 'u+01', 1, 2), ('S', ' ', 1, 6)], ' u+012 ': [ ('S', ' ', 1, 1), ('UNICODE-RANGE', 'u+012', 1, 2), ('S', ' ', 1, 7), ], ' u+0123 ': [ ('S', ' ', 1, 1), ('UNICODE-RANGE', 'u+0123', 1, 2), ('S', ' ', 1, 8), ], ' u+01234 ': [ ('S', ' ', 1, 1), ('UNICODE-RANGE', 'u+01234', 1, 2), ('S', ' ', 1, 9), ], ' u+012345 ': [ ('S', ' ', 1, 1), ('UNICODE-RANGE', 'u+012345', 1, 2), ('S', ' ', 1, 10), ], ' u+0123456 ': [ ('S', ' ', 1, 1), ('UNICODE-RANGE', 'u+012345', 1, 2), ('NUMBER', '6', 1, 10), ('S', ' ', 1, 11), ], ' U+123456 ': [ ('S', ' ', 1, 1), ('UNICODE-RANGE', 'U+123456', 1, 2), ('S', ' ', 1, 10), ], ' \\55+abcdef ': [ ('S', ' ', 1, 1), ('UNICODE-RANGE', 'U+abcdef', 1, 2), ('S', ' ', 1, 12), ], ' \\75+abcdef ': [ ('S', ' ', 1, 1), ('UNICODE-RANGE', 'u+abcdef', 1, 2), ('S', ' ', 1, 12), ], ' u+0-1 ': [ ('S', ' ', 1, 1), ('UNICODE-RANGE', 'u+0-1', 1, 2), ('S', ' ', 1, 7), ], ' u+0-1, u+123456-abcdef ': [ ('S', ' ', 1, 1), ('UNICODE-RANGE', 'u+0-1', 1, 2), ('CHAR', ',', 1, 7), ('S', ' ', 1, 8), ('UNICODE-RANGE', 'u+123456-abcdef', 1, 9), ('S', ' ', 1, 24), ], # specials 'c\\olor': [('IDENT', 'c\\olor', 1, 1)], # '-1': [('CHAR', '-', 1, 1), ('NUMBER', '1', 1, 2)], # '-1px': [('CHAR', '-', 1, 1), ('DIMENSION', '1px', 1, 2)], '-1': [('NUMBER', '-1', 1, 1)], '-1px': [('DIMENSION', '-1px', 1, 1)], # ATKEYWORD ' @x ': [('S', ' ', 1, 1), ('ATKEYWORD', '@x', 1, 2), ('S', ' ', 1, 4)], '@X': [('ATKEYWORD', '@X', 1, 1)], '@\\x': [('ATKEYWORD', '@\\x', 1, 1)], # - '@1x': [('CHAR', '@', 1, 1), ('DIMENSION', '1x', 1, 2)], # DIMENSION ' 0px ': [('S', ' ', 1, 1), ('DIMENSION', '0px', 1, 2), ('S', ' ', 1, 5)], ' 1s ': [('S', ' ', 1, 1), ('DIMENSION', '1s', 1, 2), ('S', ' ', 1, 4)], '0.2EM': [('DIMENSION', '0.2EM', 1, 1)], '1p\\x': [('DIMENSION', '1p\\x', 1, 1)], '1PX': [('DIMENSION', '1PX', 1, 1)], # NUMBER ' - 0 ': [ ('S', ' ', 1, 1), ('CHAR', '-', 1, 2), ('S', ' ', 1, 3), ('NUMBER', '0', 1, 4), ('S', ' ', 1, 5), ], ' + 0 ': [ ('S', ' ', 1, 1), ('CHAR', '+', 1, 2), ('S', ' ', 1, 3), ('NUMBER', '0', 1, 4), ('S', ' ', 1, 5), ], # PREFIXMATCH ' ^= ': [('S', ' ', 1, 1), ('PREFIXMATCH', '^=', 1, 2), ('S', ' ', 1, 4)], '^==': [('PREFIXMATCH', '^=', 1, 1), ('CHAR', '=', 1, 3)], # SUFFIXMATCH ' $= ': [('S', ' ', 1, 1), ('SUFFIXMATCH', '$=', 1, 2), ('S', ' ', 1, 4)], '$==': [('SUFFIXMATCH', '$=', 1, 1), ('CHAR', '=', 1, 3)], # SUBSTRINGMATCH ' *= ': [('S', ' ', 1, 1), ('SUBSTRINGMATCH', '*=', 1, 2), ('S', ' ', 1, 4)], '*==': [('SUBSTRINGMATCH', '*=', 1, 1), ('CHAR', '=', 1, 3)], # BOM only at start '\xfe\xff ': [('BOM', '\xfe\xff', 1, 1), ('S', ' ', 1, 1)], ' \xfe\xff ': [('S', ' ', 1, 1), ('IDENT', '\xfe\xff', 1, 2), ('S', ' ', 1, 4)], '\xef\xbb\xbf ': [('BOM', '\xef\xbb\xbf', 1, 1), ('S', ' ', 1, 1)], ' \xef\xbb\xbf ': [ ('S', ' ', 1, 1), ('IDENT', '\xef\xbb\xbf', 1, 2), ('S', ' ', 1, 5), ], } tests2 = { # escapes work not for a-f! # IMPORT_SYM ' @import ': [ ('S', ' ', 1, 1), ('IMPORT_SYM', '@import', 1, 2), ('S', ' ', 1, 9), ], '@IMPORT': [('IMPORT_SYM', '@IMPORT', 1, 1)], '@\\49\r\nMPORT': [('IMPORT_SYM', '@\\49\r\nMPORT', 1, 1)], r'@\i\m\p\o\r\t': [('IMPORT_SYM', r'@\i\m\p\o\r\t', 1, 1)], r'@\I\M\P\O\R\T': [('IMPORT_SYM', r'@\I\M\P\O\R\T', 1, 1)], r'@\49 \04d\0050\0004f\000052\54': [ ('IMPORT_SYM', r'@\49 \04d\0050\0004f\000052\54', 1, 1) ], r'@\69 \06d\0070\0006f\000072\74': [ ('IMPORT_SYM', r'@\69 \06d\0070\0006f\000072\74', 1, 1) ], # PAGE_SYM ' @page ': [('S', ' ', 1, 1), ('PAGE_SYM', '@page', 1, 2), ('S', ' ', 1, 7)], '@PAGE': [('PAGE_SYM', '@PAGE', 1, 1)], r'@\pa\ge': [('PAGE_SYM', r'@\pa\ge', 1, 1)], r'@\PA\GE': [('PAGE_SYM', r'@\PA\GE', 1, 1)], r'@\50\41\47\45': [('PAGE_SYM', r'@\50\41\47\45', 1, 1)], r'@\70\61\67\65': [('PAGE_SYM', r'@\70\61\67\65', 1, 1)], # MEDIA_SYM ' @media ': [('S', ' ', 1, 1), ('MEDIA_SYM', '@media', 1, 2), ('S', ' ', 1, 8)], '@MEDIA': [('MEDIA_SYM', '@MEDIA', 1, 1)], r'@\med\ia': [('MEDIA_SYM', r'@\med\ia', 1, 1)], r'@\MED\IA': [('MEDIA_SYM', r'@\MED\IA', 1, 1)], '@\\4d\n\\45\r\\44\t\\49\r\nA': [ ('MEDIA_SYM', '@\\4d\n\\45\r\\44\t\\49\r\nA', 1, 1) ], '@\\4d\n\\45\r\\44\t\\49\r\\41\f': [ ('MEDIA_SYM', '@\\4d\n\\45\r\\44\t\\49\r\\41\f', 1, 1) ], '@\\6d\n\\65\r\\64\t\\69\r\\61\f': [ ('MEDIA_SYM', '@\\6d\n\\65\r\\64\t\\69\r\\61\f', 1, 1) ], # FONT_FACE_SYM ' @font-face ': [ ('S', ' ', 1, 1), ('FONT_FACE_SYM', '@font-face', 1, 2), ('S', ' ', 1, 12), ], '@FONT-FACE': [('FONT_FACE_SYM', '@FONT-FACE', 1, 1)], r'@f\o\n\t\-face': [('FONT_FACE_SYM', r'@f\o\n\t\-face', 1, 1)], r'@F\O\N\T\-FACE': [('FONT_FACE_SYM', r'@F\O\N\T\-FACE', 1, 1)], # TODO: "-" as hex! r'@\46\4f\4e\54\-\46\41\43\45': [ ('FONT_FACE_SYM', r'@\46\4f\4e\54\-\46\41\43\45', 1, 1) ], r'@\66\6f\6e\74\-\66\61\63\65': [ ('FONT_FACE_SYM', r'@\66\6f\6e\74\-\66\61\63\65', 1, 1) ], # CHARSET_SYM only if "@charset "! '@charset ': [('CHARSET_SYM', '@charset ', 1, 1), ('S', ' ', 1, 10)], ' @charset ': [ ('S', ' ', 1, 1), ('CHARSET_SYM', '@charset ', 1, 2), # not at start ('S', ' ', 1, 11), ], '@charset': [('ATKEYWORD', '@charset', 1, 1)], # no ending S '@CHARSET ': [('ATKEYWORD', '@CHARSET', 1, 1), ('S', ' ', 1, 9)], # uppercase '@cha\\rset ': [ ('ATKEYWORD', '@cha\\rset', 1, 1), # not literal ('S', ' ', 1, 10), ], # NAMESPACE_SYM ' @namespace ': [ ('S', ' ', 1, 1), ('NAMESPACE_SYM', '@namespace', 1, 2), ('S', ' ', 1, 12), ], r'@NAMESPACE': [('NAMESPACE_SYM', r'@NAMESPACE', 1, 1)], r'@\na\me\s\pace': [('NAMESPACE_SYM', r'@\na\me\s\pace', 1, 1)], r'@\NA\ME\S\PACE': [('NAMESPACE_SYM', r'@\NA\ME\S\PACE', 1, 1)], r'@\4e\41\4d\45\53\50\41\43\45': [ ('NAMESPACE_SYM', r'@\4e\41\4d\45\53\50\41\43\45', 1, 1) ], r'@\6e\61\6d\65\73\70\61\63\65': [ ('NAMESPACE_SYM', r'@\6e\61\6d\65\73\70\61\63\65', 1, 1) ], # ATKEYWORD ' @unknown ': [ ('S', ' ', 1, 1), ('ATKEYWORD', '@unknown', 1, 2), ('S', ' ', 1, 10), ], # STRING # strings with linebreak in it ' "\\na"\na': [ ('S', ' ', 1, 1), ('STRING', '"\\na"', 1, 2), ('S', '\n', 1, 7), ('IDENT', 'a', 2, 1), ], " '\\na'\na": [ ('S', ' ', 1, 1), ('STRING', "'\\na'", 1, 2), ('S', '\n', 1, 7), ('IDENT', 'a', 2, 1), ], ' "\\r\\n\\t\\n\\ra"a': [ ('S', ' ', 1, 1), ('STRING', '"\\r\\n\\t\\n\\ra"', 1, 2), ('IDENT', 'a', 1, 15), ], # IMPORTANT_SYM is not IDENT!!! ' !important ': [ ('S', ' ', 1, 1), ('CHAR', '!', 1, 2), ('IDENT', 'important', 1, 3), ('S', ' ', 1, 12), ], '! /*1*/ important ': [ ('CHAR', '!', 1, 1), ('S', ' ', 1, 2), ('COMMENT', '/*1*/', 1, 3), ('S', ' ', 1, 8), ('IDENT', 'important', 1, 9), ('S', ' ', 1, 18), ], '! important': [ ('CHAR', '!', 1, 1), ('S', ' ', 1, 2), ('IDENT', 'important', 1, 3), ], '!\n\timportant': [ ('CHAR', '!', 1, 1), ('S', '\n\t', 1, 2), ('IDENT', 'important', 2, 2), ], '!IMPORTANT': [('CHAR', '!', 1, 1), ('IDENT', 'IMPORTANT', 1, 2)], r'!\i\m\p\o\r\ta\n\t': [ ('CHAR', '!', 1, 1), ('IDENT', r'\i\m\p\o\r\ta\n\t', 1, 2), ], r'!\I\M\P\O\R\Ta\N\T': [ ('CHAR', '!', 1, 1), ('IDENT', r'\I\M\P\O\R\Ta\N\T', 1, 2), ], r'!\49\4d\50\4f\52\54\41\4e\54': [ ('CHAR', '!', 1, 1), ('IDENT', r'IMPORTANT', 1, 2), ], r'!\69\6d\70\6f\72\74\61\6e\74': [ ('CHAR', '!', 1, 1), ('IDENT', r'important', 1, 2), ], } # overwriting tests in testsall tests2only = { # LBRACE ' { ': [('S', ' ', 1, 1), ('LBRACE', '{', 1, 2), ('S', ' ', 1, 3)], # PLUS ' + ': [('S', ' ', 1, 1), ('PLUS', '+', 1, 2), ('S', ' ', 1, 3)], # GREATER ' > ': [('S', ' ', 1, 1), ('GREATER', '>', 1, 2), ('S', ' ', 1, 3)], # COMMA ' , ': [('S', ' ', 1, 1), ('COMMA', ',', 1, 2), ('S', ' ', 1, 3)], # class ' . ': [('S', ' ', 1, 1), ('CLASS', '.', 1, 2), ('S', ' ', 1, 3)], } testsfullsheet = { # escape ends with explicit space but \r\n as single space '\\65\r\nb': [('IDENT', 'eb', 1, 1)], # STRING r'"\""': [('STRING', r'"\""', 1, 1)], r'"\" "': [('STRING', r'"\" "', 1, 1)], """'\\''""": [('STRING', """'\\''""", 1, 1)], ' "\na': [ ('S', ' ', 1, 1), ('INVALID', '"', 1, 2), ('S', '\n', 1, 3), ('IDENT', 'a', 2, 1), ], # strings with linebreak in it ' "\\na\na': [ ('S', ' ', 1, 1), ('INVALID', '"\\na', 1, 2), ('S', '\n', 1, 6), ('IDENT', 'a', 2, 1), ], ' "\\r\\n\\t\\n\\ra\na': [ ('S', ' ', 1, 1), ('INVALID', '"\\r\\n\\t\\n\\ra', 1, 2), ('S', '\n', 1, 14), ('IDENT', 'a', 2, 1), ], # URI 'ur\\l(a)': [('URI', 'ur\\l(a)', 1, 1)], 'url(a)': [('URI', 'url(a)', 1, 1)], '\\55r\\4c(a)': [('URI', 'UrL(a)', 1, 1)], '\\75r\\6c(a)': [('URI', 'url(a)', 1, 1)], ' url())': [('S', ' ', 1, 1), ('URI', 'url()', 1, 2), ('CHAR', ')', 1, 7)], 'url("x"))': [('URI', 'url("x")', 1, 1), ('CHAR', ')', 1, 9)], "url('x'))": [('URI', "url('x')", 1, 1), ('CHAR', ')', 1, 9)], } # tests if fullsheet=False is set on tokenizer testsfullsheetfalse = { # COMMENT incomplete '/*': [('CHAR', '/', 1, 1), ('CHAR', '*', 1, 2)], # INVALID incomplete ' " ': [('S', ' ', 1, 1), ('INVALID', '" ', 1, 2)], " 'abc\"with quote\" in it": [ ('S', ' ', 1, 1), ('INVALID', "'abc\"with quote\" in it", 1, 2), ], # URI incomplete 'url(a': [('FUNCTION', 'url(', 1, 1), ('IDENT', 'a', 1, 5)], 'url("a': [('FUNCTION', 'url(', 1, 1), ('INVALID', '"a', 1, 5)], "url('a": [('FUNCTION', 'url(', 1, 1), ('INVALID', "'a", 1, 5)], "UR\\l('a": [('FUNCTION', 'UR\\l(', 1, 1), ('INVALID', "'a", 1, 6)], } # tests if fullsheet=True is set on tokenizer testsfullsheettrue = { # COMMENT incomplete '/*': [('COMMENT', '/**/', 1, 1)], # # INVALID incomplete => STRING ' " ': [('S', ' ', 1, 1), ('STRING', '" "', 1, 2)], " 'abc\"with quote\" in it": [ ('S', ' ', 1, 1), ('STRING', "'abc\"with quote\" in it'", 1, 2), ], # URI incomplete FUNC => URI 'url(a': [('URI', 'url(a)', 1, 1)], 'url( a': [('URI', 'url( a)', 1, 1)], 'url("a': [('URI', 'url("a")', 1, 1)], 'url( "a ': [('URI', 'url( "a ")', 1, 1)], "url('a": [('URI', "url('a')", 1, 1)], 'url("a"': [('URI', 'url("a")', 1, 1)], "url('a'": [('URI', "url('a')", 1, 1)], } def setup_method(self): # log = cssutils.errorhandler.ErrorHandler() self.tokenizer = Tokenizer() def test_tokenize(self): "cssutils Tokenizer().tokenize()" import cssutils.cssproductions tokenizer = Tokenizer( cssutils.cssproductions.MACROS, cssutils.cssproductions.PRODUCTIONS ) tests = {} tests.update(self.testsall) tests.update(self.tests2) tests.update(self.tests3) tests.update(self.testsfullsheet) tests.update(self.testsfullsheetfalse) for css in tests: # check token format tokens = tokenizer.tokenize(css) for i, actual in enumerate(tokens): expected = tests[css][i] assert expected == actual # check if all same number of tokens tokens = list(tokenizer.tokenize(css)) assert len(tokens) == len(tests[css]) def test_tokenizefullsheet(self): "cssutils Tokenizer().tokenize(fullsheet=True)" import cssutils.cssproductions tokenizer = Tokenizer( cssutils.cssproductions.MACROS, cssutils.cssproductions.PRODUCTIONS ) tests = {} tests.update(self.testsall) tests.update(self.tests2) tests.update(self.tests3) tests.update(self.testsfullsheet) tests.update(self.testsfullsheettrue) for css in tests: # check token format tokens = tokenizer.tokenize(css, fullsheet=True) for i, actual in enumerate(tokens): try: expected = tests[css][i] except IndexError: # EOF is added assert actual[0] == 'EOF' else: assert expected == actual # check if all same number of tokens tokens = list(tokenizer.tokenize(css, fullsheet=True)) # EOF is added so -1 assert len(tokens) - 1 == len(tests[css]) class TestTokenizerUtils: """Tests for the util functions of tokenize""" has_at_cases = [ ('foo', 0, 'foo', True), ('foo', 0, 'f', True), ('foo', 1, 'o', True), ('foo', 1, 'oo', True), ('foo', 4, 'foo', False), ('foo', 0, 'bar', False), ('foo', 0, 'foobar', False), ] @pytest.mark.parametrize("string, pos, text, expected", has_at_cases) def test_has_at(self, string, pos, text, expected): assert tokenize2.has_at(string, pos, text) == expected suffix_eq_cases = [ ('foobar', 0, 'foobar', True), ('foobar', 3, 'bar', True), ('foobar', 3, 'foo', False), ('foobar', 10, 'bar', False), ] @pytest.mark.parametrize("string, pos, suffix, expected", suffix_eq_cases) def test_suffix_eq(self, string, pos, suffix, expected): assert tokenize2.suffix_eq(string, pos, suffix) == expected