view tests/test_algpseudo.py @ 123:4d96ace53ba1

Make it work on Python2 too with all tests by explicitely declaring some strings to be Unicode strings. No tests need to be skipped on Python2 now.
author Franz Glasner <fzglas.hg@dom66.de>
date Wed, 06 May 2026 15:53:24 +0200
parents d84f1fd10e64
children 380d2607d5c7
line wrap: on
line source

# -*- coding: utf-8 -*-
# :-
# SPDX-FileCopyrightText: © 2026 Franz Glasner
# SPDX-License-Identifier: MIT
# :-

from _tsetup import ALGLEXERFILENAME, ALGLEXERCLASS

import unittest

import pygments
import pygments.lexers
import pygments.formatters

import _testhelper


class TestSnippets(unittest.TestCase, _testhelper.TokenAssertHelper):

    def setUp(self):
        self.lexer = pygments.lexers.load_lexer_from_file(
            ALGLEXERFILENAME, ALGLEXERCLASS)

    def test_lf(self):
        self.assertTokenStreamEqualComplete(
            [("Text.Whitespace", "\n")],
            pygments.lex("\n", self.lexer))

    def test_protected_lf(self):
        self.assertTokenStreamEqualComplete(
            [("Text", "\\\n")],
            pygments.lex("\\\n", self.lexer))

    def test_number_int(self):
        self.assertTokenStreamEqualComplete(
            [("Number.Integer", "10"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex("10", self.lexer))

    def test_number_float_1(self):
        self.assertTokenStreamEqualComplete(
            [("Number.Float", "3.1415926"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex("3.1415926", self.lexer))

    def test_number_float_2(self):
        self.assertTokenStreamEqualComplete(
            [("Number.Float", "3.14e-12"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex("3.14e-12", self.lexer))

    def test_string_s_1(self):
        self.assertTokenStreamEqualComplete(
            [("String.Single", "'"),
             ("String.Single", "HU"),
             ("String.Single", '"'),
             ("String.Single", "HE HA"),
             ("String.Escape", "\\'"),
             ("String.Single", "HO"),
             ("String.Single", "'"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex("""'HU"HE HA\\'HO'""", self.lexer))

    def test_string_s_2(self):
        self.assertTokenStreamEqual(
            [("String.Single", "'"),
             ("String.Single", "HUHU"),
             ("Error", "\n"),
             ],
            pygments.lex("'HUHU\nHEHE'", self.lexer))

    def test_string_ts_1(self):
        self.assertTokenStreamEqualComplete(
            [("String.Single", "'''"),
             ("String.Single", "HUHU HEHE"),
             ("String.Single", "'''"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex("'''HUHU HEHE'''", self.lexer))

    def test_string_ts_2(self):
        self.assertTokenStreamEqualComplete(
            [("String.Single", "'''"),
             ("String.Single", "HI"),
             ("String.Single", "'"),
             ("String.Single", "HU"),
             ("String.Single", "\n"),
             ("String.Single", "HE"),
             ("String.Single", '"'),
             ("String.Single", "HA"),
             ("String.Single", "'''"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex("""'''HI'HU\nHE"HA'''""", self.lexer))

    def test_string_d_1(self):
        self.assertTokenStreamEqualComplete(
            [("String.Double", '"'),
             ("String.Double", 'HU'),
             ("String.Double", "'"),
             ("String.Double", 'HE HA'),
             ("String.Escape", '\\"'),
             ("String.Double", 'HO'),
             ("String.Double", '"'),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex('''"HU'HE HA\\"HO"''', self.lexer))

    def test_string_d_2(self):
        self.assertTokenStreamEqual(
            [("String.Double", '"'),
             ("String.Double", "HUHU"),
             ("Error", "\n"),
             ],
            pygments.lex('"HUHU\nHEHE"', self.lexer))

    def test_string_td_1(self):
        self.assertTokenStreamEqualComplete(
            [("String.Double", '"""'),
             ("String.Double", 'HUHU HAHA'),
             ("String.Double", '"""'),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex('"""HUHU HAHA"""', self.lexer))

    def test_string_td_2(self):
        self.assertTokenStreamEqualComplete(
            [("String.Double", '"""'),
             ("String.Double", 'HU'),
             ("String.Double", '"'),
             ("String.Double", "HO"),
             ("String.Double", "\n"),
             ("String.Double", "HE"),
             ("String.Double", "'"),
             ("String.Double", "HA"),
             ("String.Double", '"""'),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex('''"""HU"HO\nHE'HA"""''', self.lexer))

    def test_proc(self):
        self.assertTokenStreamEqualComplete(
            [("Keyword", "PROCEDURE"),
             ("Text.Whitespace", " "),
             ("Name.Entity", "the name"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex("\\PROC {the name}", self.lexer))

    def test_proc_with_symbols_in_name(self):
        self.assertTokenStreamEqualComplete(
            [("Keyword", "PROCEDURE"),
             ("Text.Whitespace", " "),
             ("Name.Entity", "the name sqrt ! <="),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex("\\PROC {the name sqrt ! <=}", self.lexer))

    def test_proc_with_escape_in_name(self):
        self.assertTokenStreamEqualComplete(
            [("Keyword", "PROCEDURE"),
             ("Text.Whitespace", " "),
             ("Name.Entity", "t"),
             ("Name.Entity", "\\"),
             ("Name.Entity", "he "),
             ("Name.Entity", "\\"),
             ("Name.Entity", "}"),
             ("Name.Entity", "name"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"\PROC {t\he \\\}name}", self.lexer))

    def test_endproc(self):
        self.assertTokenStreamEqualComplete(
            [("Keyword", "END OF PROCEDURE"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex("\\END-PROCEDURE", self.lexer))

    def test_endproc_with_entityname(self):
        self.assertTokenStreamEqualComplete(
            [("Keyword", "END OF PROCEDURE"),
             ("Text.Whitespace", " "),
             ("Name.Entity", "the procedure name"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex("\\ENDPROCEDURE {the procedure name}", self.lexer))

    def test_endproc_with_entityname_2(self):
        self.assertTokenStreamEqualComplete(
            [("Keyword", "END OF PROCEDURE"),
             ("Text.Whitespace", " "),
             ("Name.Entity", "the procedure name"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex("\\END-PROC {the procedure name}", self.lexer))

    def test_endproc_with_entityname_3(self):
        self.assertTokenStreamEqualComplete(
            [("Keyword", "END OF PROCEDURE"),
             ("Text.Whitespace", " "),
             ("Name.Entity", "the procedure name with pow and symbols ! <= "),
             ("Name.Entity", "}"),
             ("Name.Entity", "<-"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(
                "\\END-PROC"
                " {the procedure name with pow and symbols ! <= \\}<-}",
                self.lexer))

    def test_proc_de(self):
        lexer = pygments.lexers.load_lexer_from_file(
            ALGLEXERFILENAME, "AlgPseudocodeLexer_DE")
        self.assertTokenStreamEqualComplete(
            [("Keyword", "PROZEDUR"),
             ("Text.Whitespace", " "),
             ("Name.Entity", " also {nichtxs"),
             ("Name.Entity", "}"),
             ("Name.Entity", " hier"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"\PROC  { also {nichtxs\} hier}", lexer))

    def test_loop_de_not_yet_translated(self):
        lexer = pygments.lexers.load_lexer_from_file(
            ALGLEXERFILENAME, "AlgPseudocodeLexer_DE")
        self.assertTokenStreamEqualComplete(
            [("Keyword", "LOOP"),
             ("Text", " "),
             ("Name.Entity", "a"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"\LOOP a", lexer))

    def test_function_1(self):
        self.assertTokenStreamEqualComplete(
            [("Keyword", "FUNCTION"),
             ("Text.Whitespace", " "),
             ("Name.Entity", "1"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex("\\FUNC{1}", self.lexer))

    def test_function_2(self):
        self.assertTokenStreamEqualComplete(
            [("Keyword", "FUNCTION"),
             ("Text.Whitespace", " "),
             ("Name.Entity", "line 1\nline 2\n"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex("\\FUNCTION{line 1\nline 2\n}", self.lexer))

    def test_function_3(self):
        self.assertTokenStreamEqualComplete(
            [("Keyword", "FUNCTION"),
             ("Text.Whitespace", " "),
             ("Name.Entity", "\\"),
             ("Name.Entity", "n"),
             ("Name.Entity", "}"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"\FN {\n\}}", self.lexer))

    def test_class(self):
        self.assertTokenStreamEqualComplete(
            [("Keyword", "CLASS"),
             ("Text.Whitespace", " "),
             ("Name.Entity", "\\"),
             ("Name.Entity", "n"),
             ("Name.Entity", "}"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"\CLASS {\n\}}", self.lexer))

    def test_class_fr(self):
        lexer = pygments.lexers.load_lexer_from_file(
            ALGLEXERFILENAME, "AlgPseudocodeLexer_FR")
        self.assertTokenStreamEqualComplete(
            [("Keyword", "CLASSE"),
             ("Text.Whitespace", " "),
             ("Name.Entity", "\\"),
             ("Name.Entity", "n"),
             ("Name.Entity", "}"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex("\\CLASS {\\n\\}}", lexer))

    def test_class_de_with_noend_option(self):
        lexer = pygments.lexers.load_lexer_from_file(
            ALGLEXERFILENAME, "AlgPseudocodeLexer_DE", no_end="True")
        self.assertTokenStreamEqualComplete(
            [("Keyword", "KLASSE"),
             ("Text.Whitespace", " "),
             ("Name.Entity", "\\"),
             ("Name.Entity", "n"),
             ("Name.Entity", "}"),
             ("Text.Whitespace", "\n"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex("\\CLASS {\\n\\}}\n\\ENDCLASS", lexer))

    def test_class_de_with_noend_option_and_name(self):
        lexer = pygments.lexers.load_lexer_from_file(
            ALGLEXERFILENAME, "AlgPseudocodeLexer_DE", no_end="True")
        self.assertTokenStreamEqualComplete(
            [("Keyword", "KLASSE"),
             ("Text.Whitespace", " "),
             ("Name.Entity", "\\"),
             ("Name.Entity", "n"),
             ("Name.Entity", "}"),
             ("Text.Whitespace", "\n"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex("\\CLASS {\\n\\}}\n\\ENDCLASS {end class}", lexer))

    def test_remark_1(self):
        self.assertTokenStreamEqualComplete(
            [("Comment.Single", u"▷"),
             ("Comment.Single", "  the remark"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex("\\REMARK  the remark\n", self.lexer))

    def test_remark_2(self):
        self.assertTokenStreamEqualComplete(
            [("Comment.Single", u"▷"),
             ("Comment.Single", "  the remark 1"),
             ("Text.Whitespace", "\n"),
             ("Comment.Single", u"▷"),
             ("Comment.Single", "  the remark 2"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(
                """\\remArk  the remark 1
\\Rem  the remark 2
""", self.lexer))

    def test_remark_custom(self):
        # With the APL comment symbol
        lexer = pygments.lexers.load_lexer_from_file(
            ALGLEXERFILENAME, ALGLEXERCLASS, remark=u"⍝")
        self.assertTokenStreamEqualComplete(
            [("Comment.Single", u"⍝"),  # U+235D ⍝ APL FUNC. SYMBOL UP SHOE JOT
             ("Comment.Single", "  another remark"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(u"\\REMARK  another remark\n", lexer))

    def test_remark_in_text(self):
        self.assertTokenStreamEqualComplete(
            [("Text", "the text  "),
             ("Comment.Single", u"▷"),
             ("Comment.Single", " the remark"),
             ("Text.Whitespace", "\n"),
             ("Text", "the next text line"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(
                """\\TEXT{the text  \\rem the remark\nthe next text line}""",
                self.lexer))

    def test_comment_single_1(self):
        self.assertTokenStreamEqualComplete(
            [("Comment.Single", "// foo bar"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"// foo bar", self.lexer))

    def test_comment_single_2(self):
        self.assertTokenStreamEqualComplete(
            [("Comment.Single", "#  foo bar"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"#  foo bar", self.lexer))

    def test_expr_and_text(self):
        self.assertTokenStreamEqualComplete(
            [("Name.Entity", "a"),
             ("Text", " "),
             ("Text", "multiplied by"),
             ("Text", " "),
             ("Name.Entity", "b"),
             ("Text", " "),
             ("Text", "is"),
             ("Text", " "),
             ("Number.Integer", "0"),
             ("Text", "  "),
             ("Text", "mod"),
             ("Text", " "),
             ("Name.Entity", "p"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(
                r"""a \TEXT{multiplied by} b \text{is} 0  \text{mod} p""",
                self.lexer))

    def test_expr_and_text_with_escaped_characters(self):
        self.assertTokenStreamEqualComplete(
            [("Name.Entity", "a"),
             ("Text", " "),
             ("Text", "multiplied by {escaped"),
             ("Text", "}"),
             ("Text", " "),
             ("Text", " "),
             ("Name.Entity", "b"),
             ("Text", " "),
             ("Text", "is "),
             ("Text", "\\"),
             ("Text", " not"),
             ("Text", " "),
             ("Number.Integer", "0"),
             ("Text", "  "),
             ("Text", "mod"),
             ("Text", " "),
             ("Name.Entity", "p"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(
                r"""a \TEXT{multiplied by {escaped\} } b \text{is \ not} 0"""
                r"  \text{mod} p""",
                self.lexer))

    def test_punctuation(self):
        self.assertTokenStreamEqualComplete(
            [("Punctuation", "{"),
             ("Punctuation", "}"),
             ("Punctuation", ":"),
             ("Punctuation", "("),
             ("Punctuation", ")"),
             ("Punctuation", ","),
             ("Punctuation", ";"),
             ("Punctuation", "["),
             ("Punctuation", "]"),
             ("Punctuation", "?"),
             ("Punctuation", "@"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"{}:(),;[]?@", self.lexer))

    def test_block_empty(self):
        self.assertTokenStreamEqualComplete(
            [("Text", u"◆"),
             ("Text.Whitespace", " "),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"\block{}", self.lexer))

    def test_block_with_text(self):
        self.assertTokenStreamEqualComplete(
            [("Text", u"◆"),
             ("Text.Whitespace", " "),
             ("Text", "a b c"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"\block{\text{a b c}}", self.lexer))

    def test_block_with_escaped_text(self):
        self.assertTokenStreamEqualComplete(
            [("Text", u"◆"),
             ("Text.Whitespace", " "),
             ("Text", "\\"),
             ("Name.Entity", "text"),
             ("Punctuation", "{"),
             ("Name.Entity", "a"),
             ("Text", " "),
             ("Name.Entity", "b"),
             ("Text", " "),
             ("Name.Entity", "c"),
             ("Punctuation", "}"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"\block{\\text{a b c\}}", self.lexer))

    def test_block(self):
        self.assertTokenStreamEqualComplete(
            [("Text", u"◆"),
             ("Text.Whitespace", " "),
             ("Name.Entity", "a"),
             ("Text", " "),
             ("Number.Float", "1.2"),
             ("Text", " "),
             ("Punctuation", "{"),
             ("Name.Entity", "x"),
             ("Text", " "),
             ("Operator.Word", "in"),
             ("Text", " "),
             ("Name.Entity", "X"),
             ("Punctuation", "}"),
             ("Text", " "),
             ("Name.Entity", "c"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"\state{a 1.2 {x in X\} c}", self.lexer))

    def test_tstate_empty(self):
        self.assertTokenStreamEqualComplete(
            [("Text", u"▪"),
             ("Text.Whitespace", " "),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"\tstate{}", self.lexer))

    def test_tstate_with_expr(self):
        self.assertTokenStreamEqualComplete(
            [("Text", u"▪"),
             ("Text.Whitespace", " "),
             ("Text", "a 1.2 "),
             ("Name.Entity", "x"),
             ("Text", " "),
             ("Operator.Word", "in"),
             ("Text", " "),
             ("Name.Entity", "X"),
             ("Punctuation", "}"),
             ("Text", " c"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"\tstate{a 1.2 \expr{x in X\}} c}", self.lexer))

    def test_tstate_with_escaped_expr(self):
        self.assertTokenStreamEqualComplete(
            [("Text", u"▪"),
             ("Text.Whitespace", " "),
             ("Text", "a 1.2 "),
             ("Text", "\\"),
             ("Text", "expr{x in X"),
             ("Text", "}"),
             ("Text", " c"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"\tstate{a 1.2 \\expr{x in X\} c}", self.lexer))

    def test_text_in_expr(self):
        self.assertTokenStreamEqualComplete(
            [("Name.Entity", "first"),
             ("Text", " "),
             ("Name.Entity", "expression"),
             ("Text", "  "),
             ("Name.Entity", "second"),
             ("Text", " "),
             ("Name.Entity", "expression"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(
                r"\TEXT{\EXPRESSION{first expression}  "
                r"\EXPR{second expression}}",
                self.lexer))

    def test_explicit_extended_single_tokentype_1(self):
        self.assertTokenStreamEqualComplete(
            [("Operator", "%"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"\ttx-o:%:", self.lexer))

    def test_explicit_extended_single_tokentype_2(self):
        self.assertTokenStreamEqualComplete(
            [("Operator", "{"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"\ttx-o{{}", self.lexer))

    def test_explicit_extended_single_tokentype_3(self):
        self.assertTokenStreamEqualComplete(
            [("Operator", "<"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"\ttx-o<<>", self.lexer))

    def test_explicit_extended_single_tokentype_4(self):
        self.assertTokenStreamEqualComplete(
            [("Operator", "("),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"\ttx-o(()", self.lexer))

    def test_explicit_extended_multi_tokentype_1(self):
        self.assertTokenStreamEqualComplete(
            [("Operator", "xxx in A"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"\ttx-o/xxx in A/", self.lexer))

    def test_explicit_extended_multi_tokentype_2(self):
        self.assertTokenStreamEqualComplete(
            [("Operator", "xxx in B"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"\ttx-o{xxx in B}", self.lexer))

    def test_explicit_extended_multi_tokentype_3(self):
        self.assertTokenStreamEqualComplete(
            [("Operator", "xxx in C"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"\ttx-o<xxx in C>", self.lexer))

    def test_explicit_extended_multi_tokentype_4(self):
        self.assertTokenStreamEqualComplete(
            [("Operator", "xxx in D"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"\ttx-o(xxx in D)", self.lexer))

    def test_explicit_tokentype_simple_1(self):
        self.assertTokenStreamEqualComplete(
            [("Operator", "}"),
             ("Operator", "/"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"\tt-o/}\tt-o//", self.lexer))

    def test_explicit_tokentype_simple_2(self):
        self.assertTokenStreamEqualComplete(
            [("Operator", "\n"),
             ("Operator", "/"),
             ("Text", " "),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex("\\tt-o/\n\\tt-o// ", self.lexer))

    def test_explicit_tokentype_with_remark(self):
        self.assertTokenStreamEqualComplete(
            [("Operator", u"∈ ∌"),
             ("Text", "    "),
             ("Comment.Single", u"▷"),
             ("Comment.Single", u" ∈ ∌ as (ordinary) operators"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(
                u"""\\ttx-o<∈ ∌>    \\rem ∈ ∌ as (ordinary) operators""",
                self.lexer))

    def test_explicit_tokentype_with_remark_2(self):
        self.assertTokenStreamEqualComplete(
            [("Operator", "new_operator"),
             ("Text", "  "),
             ("Comment.Single", u"▷"),
             ("Comment.Single", " a (synthesized) operator"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(
                r"""\ttx-o<new_operator>  \rem a (synthesized) operator""",
                self.lexer))

    def test_explicit_tokentype_with_possibly_conflicting_parens(self):
        self.assertTokenStreamEqualComplete(
            [("Name.Function", u"∈_∌"),
             ("Punctuation", "("),
             ("Name.Entity", "p1"),
             ("Punctuation", ","),
             ("Text", " "),
             ("Name.Entity", "p2"),
             ("Punctuation", ")"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(
                u"""\\ttx-nf<∈_∌>(p1, p2)""",
                self.lexer))

    def test_explicit_tokentype_with_possibly_conflicting_parens_2(self):
        self.assertTokenStreamEqualComplete(
            [("Name.Decorator", "a_Decorator"),
             ("Punctuation", "("),
             ("Name.Entity", "p1"),
             ("Punctuation", ","),
             ("Text", " "),
             ("Name.Entity", "p2"),
             ("Punctuation", ")"),
             ("Text", "   "),
             ("Comment.Single", u"▷"),
             ("Comment.Single", " (Python) decorator"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(
                r"""\ttx-nd<a_Decorator>(p1, p2)   \rem (Python) decorator""",
                self.lexer))

    def test_explicit_tokentype_with_possibly_conflicting_parens_3(self):
        self.assertTokenStreamEqualComplete(
            [("Name.Decorator", "a_Decorator"),
             ("Punctuation", "("),
             ("Name.Entity", "p1"),
             ("Punctuation", ","),
             ("Text", " "),
             ("Name.Entity", "p2"),
             ("Punctuation", ")"),
             ("Text", "   "),
             ("Comment.Single", u"▷"),
             ("Comment.Single", " (Python) annotation"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(
                r"""\ttx-nd[a_Decorator](p1, p2)   \rem (Python) annotation""",
                self.lexer))

    def test_explicit_tokentype_error(self):
        self.assertTokenStreamEqualComplete(
            [("Generic.Error", r"""\ttx-non-existing[a_Decorator]"""),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(
                r"""\ttx-non-existing[a_Decorator]""",
                self.lexer))

    def test_end_combinations(self):
        self.assertTokenStreamEqualComplete(
            [("Keyword", "BEGIN"),
             ("Text", "  "),
             ("Keyword", "END"),
             ("Text", "  "),
             ("Keyword", "END OF FUNCTION"),
             ("Text", "  "),
             ("Keyword", "END OF FUNCTION"),
             ("Text.Whitespace", " "),
             ("Name.Entity", "An End of a Function"),
             ("Text", "  "),
             ("Keyword", "END OF FUNCTION"),
             ("Text.Whitespace", " "),
             ("Name.Entity", "The End of the Next Function"),
             ("Text", " "),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(
                r"""\begin  \end  \end-fn  \end-fn {An End of a Function}"""
                r"""  \end fn {The End of the Next Function} """,
                self.lexer))

    def test_unicode_math_operator(self):
        self.assertTokenStreamEqualComplete(
            [("Operator", u"∈"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(u"∈", self.lexer))

    def test_ascii_math_operator(self):
        self.assertTokenStreamEqualComplete(
            [("Operator", "="),
             ("Operator", "!"),
             ("Operator", "&"),
             ("Operator", "<"),
             ("Text", " "),
             ("Operator", ">"),
             ("Operator", "+"),
             ("Operator", "-"),
             ("Operator", "*"),
             ("Operator", "/"),
             ("Operator", "%"),
             ("Operator", "|"),
             ("Operator", "~"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex("=!&< >+-*/%|~", self.lexer))

    def test_ascii_math_operator_with_replacements(self):
        self.assertTokenStreamEqualComplete(
            [("Operator", u"⇔"),
             ("Text", " "),
             ("Operator", u"⟷"),
             ("Text", " "),
             ("Operator", u"⟵"),
             ("Text", " "),
             ("Operator", u"⟶"),
             ("Text", " "),
             ("Operator", u"⇒"),
             ("Text", " "),
             ("Operator", u"≤"),
             ("Text", " "),
             ("Operator", u"≥"),
             ("Text", " "),
             ("Operator", u"≠"),
             ("Text", " "),
             ("Operator", u"≠"),
             ("Text", " "),
             ("Operator", u"∶="),   # u"≔"),
             ("Text", " "),
             ("Operator", u"=∶"),   # u"≕"),
             ("Text", " "),
             ("Operator", u"≟"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(u"<=> <-> <- -> => <= >= <> != := =: ?=", self.lexer))

    def test_word_operators(self):
        self.assertTokenStreamEqualComplete(
            [("Operator.Word", "IN"),
             ("Text", " "),
             ("Operator.Word", "is"),
             ("Text", " "),
             ("Operator.Word", "And"),
             ("Text", " "),
             ("Operator.Word", "Or"),
             ("Text", " "),
             ("Operator.Word", "XOR"),
             ("Text", " "),
             ("Operator.Word", "not"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex("IN is And Or XOR not", self.lexer))

    def test_keyword_constants(self):
        self.assertTokenStreamEqualComplete(
            [("Keyword.Constant", "true"),
             ("Text", " "),
             ("Keyword.Constant", "FALSE"),
             ("Text", " "),
             ("Keyword.Constant", "None"),
             ("Text", " "),
             ("Keyword.Constant", "nil"),
             ("Text", " "),
             ("Keyword.Constant", "NULL"),
             ("Text", " "),
             ("Keyword.Constant", "Empty"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex("true FALSE None nil NULL Empty", self.lexer))

    def test_math_builtins(self):
        self.assertTokenStreamEqualComplete(
            [("Name.Builtin", "sqrt"),
             ("Punctuation", "("),
             ("Name.Entity", "Foo"),
             ("Punctuation", ")"),
             ("Punctuation", ";"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex("sqrt(Foo);", self.lexer))

    def test_math_builtins_nested(self):
        self.assertTokenStreamEqualComplete(
            [("Name.Builtin", "pow"),
             ("Punctuation", "("),
             ("Number.Integer", "2"),
             ("Punctuation", ","),
             ("Text", " "),
             ("Number.Integer", "8"),
             ("Punctuation", ")"),
             ("Punctuation", ";"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex("\\text{\\expr{pow(2, 8);}}", self.lexer))

    def test_math_letters(self):
        self.assertTokenStreamEqualComplete(
            [("Name.Entity", "a"),
             ("Text", " "),
             ("Operator.Word", "in"),
             ("Text", " "),
             ("Name.Entity", u"ℂ"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(u"a in ℂ", self.lexer))

    def test_other_symbols(self):
        self.assertTokenStreamEqualComplete(
            [("Name.Entity", "b"),
             ("Text", " "),
             ("Operator.Word", "in"),
             ("Text", " "),
             ("Text", u"℀"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(u"b in ℀", self.lexer))

    def test_escaped_string_start_1(self):
        self.assertTokenStreamEqualComplete(
            [("Text", "flow "),
             ("Name.Entity", "f"),
             ("Punctuation", "'"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"\TEXT{flow \expr{f\'}}", self.lexer))

    def test_escaped_string_start_2(self):
        self.assertTokenStreamEqualComplete(
            [("Text", "flow "),
             ("Name.Entity", "f"),
             ("Punctuation", '"'),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r'\TEXT{flow \expr{f\"}}', self.lexer))

    def test_gets_default(self):
        self.assertTokenStreamEqualComplete(
            [("Name.Entity", "a"),
             ("Text", " "),
             ("Operator", u"⟵"),     # U+27F5 (Supplemental Arrows-A)
             ("Text", " "),
             ("Number.Integer", "2"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"a \gets 2", self.lexer))

    def test_gets_custom(self):
        lexer = pygments.lexers.load_lexer_from_file(
            ALGLEXERFILENAME, ALGLEXERCLASS, gets="::=")
        self.assertTokenStreamEqualComplete(
            [("Name.Entity", "a"),
             ("Text", " "),
             ("Operator", "::="),
             ("Text", " "),
             ("Number.Float", "2.7"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"a \gets 2.7", lexer))

    def test_call(self):
        self.assertTokenStreamEqualComplete(
            [("Name.Entity", "a function"),
             ("Punctuation", "("),
             ("Name.Entity", "p1"),
             ("Punctuation", ","),
             ("Text", " "),
             ("Name.Entity", "p2"),
             ("Punctuation", ")"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"\CALL{a function}(p1, p2)", self.lexer))

    def test_call_in_expr(self):
        self.assertTokenStreamEqualComplete(
            [("Name.Entity", "a procedure"),
             ("Punctuation", "("),
             ("Name.Entity", "arg1"),
             ("Punctuation", ","),
             ("Text", " "),
             ("Name.Entity", "arg2"),
             ("Punctuation", ","),
             ("Text", " "),
             ("Name.Entity", "arg3"),
             ("Punctuation", ")"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"\TEXT{\EXPR{\CALL{a procedure}(arg1, arg2, arg3)}}",
                         self.lexer))

    def test_comment_multi(self):
        self.assertTokenStreamEqualComplete(
            [("Comment.Multiline", "/*"),
             ("Comment.Multiline", " word1 "),
             ("Comment.Multiline", "*"),
             ("Comment.Multiline", " word2 "),
             ("Comment.Multiline", "/"),
             ("Comment.Multiline", " word3 "),
             ("Comment.Multiline", "/"),
             ("Comment.Multiline", "/"),
             ("Comment.Multiline", " word4 "),
             ("Comment.Multiline", "*/"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"/* word1 * word2 / word3 // word4 */", self.lexer))

    def test_comment_multi_alt(self):
        self.assertTokenStreamEqualComplete(
            [("Comment.Multiline", "(*"),
             ("Comment.Multiline", " word1 "),
             ("Comment.Multiline", "*"),
             ("Comment.Multiline", " word2 "),
             ("Comment.Multiline", "("),
             ("Comment.Multiline", " word3 "),
             ("Comment.Multiline", ")"),
             ("Comment.Multiline", " word4 "),
             ("Comment.Multiline", "("),
             ("Comment.Multiline", ")"),
             ("Comment.Multiline", " word5 "),
             ("Comment.Multiline", "*)"),
             ("Text.Whitespace", "\n"),
             ],
            pygments.lex(r"(* word1 * word2 ( word3 ) word4 () word5 *)",
                         self.lexer))


class PygmentizeCompletely(unittest.TestCase):

    def setUp(self):
        self.lexer = pygments.lexers.load_lexer_from_file(
            ALGLEXERFILENAME, ALGLEXERCLASS)

    def test_pygmentize_html(self):
        html_formatter = pygments.formatters.get_formatter_by_name("html")
        highlighted = pygments.highlight(
            '"""FOO"""',
            self.lexer,
            html_formatter,
            outfile=None)
        self.assertTrue(highlighted.startswith("""<div class="highlight">"""))

    def test_pygmentize_latex(self):
        latex_formatter = pygments.formatters.get_formatter_by_name("latex")
        highlighted = pygments.highlight(
            '"""FOO"""',
            self.lexer,
            latex_formatter,
            outfile=None)
        self.assertTrue(highlighted.startswith(r"""\begin{Verbatim}"""))


if __name__ == "__main__":
    unittest.main()