Commit 3478a3af authored by Eckhart Arnold's avatar Eckhart Arnold
Browse files

subtle refactorings

parent 9af7ce39
Loading
Loading
Loading
Loading
+8 −1
Original line number Diff line number Diff line
@@ -140,7 +140,14 @@ class Error:
    @property
    def severity(self):
        """Returns a string representation of the error level, e.g. "warning"."""
        return "Warning" if is_warning(self.code) else "Error"
        if self.code < Error.WARNING:
            return "Notice"
        elif self.code < Error.ERROR:
            return "Warning"
        elif self.code < Error.FATAL:
            return "Error"
        else:
            return "Fatal"

    def visualize(self, document: str) -> str:
        """Shows the line of the document and the position where the error
+11 −3
Original line number Diff line number Diff line
@@ -73,6 +73,7 @@ __all__ = ('start_logging',
           'clear_logs',
           'NONE_TAG',
           'NONE_NODE',
           'freeze_callstack',
           'HistoryRecord',
           'log_ST',
           'log_parsing_history')
@@ -246,6 +247,11 @@ NONE_TAG = ":None"
NONE_NODE = FrozenNode(NONE_TAG, '')


def freeze_callstack(call_stack: List[Tuple[str, int]]) -> Tuple[Tuple[str, int], ...]:
    """Returns a frozen copy of the call stack."""
    return  tuple((tn, pos) for tn, pos in call_stack if tn != ":Forward")


class HistoryRecord:
    """
    Stores debugging information about one completed step in the
@@ -292,15 +298,17 @@ class HistoryRecord:
        '</style>\n</head>\n<body>\n')
    HTML_LEAD_OUT = '\n</body>\n</html>\n'

    def __init__(self, call_stack: List[Tuple[str, int]],
    def __init__(self, call_stack: Union[List[Tuple[str, int]], Tuple[Tuple[str, int], ...]],
                 node: Optional[Node],
                 text: StringView,
                 line_col: Tuple[int, int],
                 errors: List[Error] = []) -> None:
        # copy call stack, dropping uninformative Forward-Parsers
        # self.call_stack = call_stack    # type: Tuple[Tuple[str, int],...]
        self.call_stack = tuple((tn, pos) for tn, pos in call_stack
                                if tn != ":Forward")     # type: Tuple[Tuple[str, int],...]
        if isinstance(call_stack, tuple):
            self.call_stack = call_stack  # type: Tuple[Tuple[str, int],...]
        else:
            self.call_stack = freeze_callstack(call_stack)
        self.node = NONE_NODE if node is None else node  # type: Node
        self.text = text                                 # type: StringView
        self.line_col = line_col                         # type: Tuple[int, int]
+5 −4
Original line number Diff line number Diff line
@@ -73,6 +73,7 @@ __all__ = ('ParserError',
           'Option',
           'ZeroOrMore',
           'OneOrMore',
           'MandatoryNary',
           'Series',
           'Alternative',
           'AllOf',
@@ -1835,7 +1836,7 @@ MessagesType = List[Tuple[Union[str, Any], str]]
NO_MANDATORY = 1000


class MandatoryElementsParser(NaryParser):
class MandatoryNary(NaryParser):
    r"""
    Attributes:
        mandatory:  Number of the element starting at which the element
@@ -1856,7 +1857,7 @@ class MandatoryElementsParser(NaryParser):
                 mandatory: int = NO_MANDATORY,
                 err_msgs: MessagesType = [],
                 skip: ResumeList = []) -> None:
        super(MandatoryElementsParser, self).__init__(*parsers)
        super(MandatoryNary, self).__init__(*parsers)
        length = len(self.parsers)
        if mandatory < 0:
            mandatory += length
@@ -1947,7 +1948,7 @@ class MandatoryElementsParser(NaryParser):
        return error, err_node, text_[i:]


class Series(MandatoryElementsParser):
class Series(MandatoryNary):
    r"""
    Matches if each of a series of parsers matches exactly in the order of
    the series.
@@ -2119,7 +2120,7 @@ class Alternative(NaryParser):
        return self


class AllOf(MandatoryElementsParser):
class AllOf(MandatoryNary):
    """
    Matches if all elements of a list of parsers match. Each parser must
    match exactly once. Other than in a sequence, the order in which
+21 −24
Original line number Diff line number Diff line
@@ -29,7 +29,7 @@ from typing import Tuple, Optional, List, Iterable, Union
from DHParser.error import Error, line_col
from DHParser.stringview import StringView
from DHParser.syntaxtree import Node, REGEXP_PTYPE, TOKEN_PTYPE, WHITESPACE_PTYPE, ZOMBIE_TAG
from DHParser.log import HistoryRecord
from DHParser.log import freeze_callstack, HistoryRecord
from DHParser.parse import Grammar, Parser, ParserError, ParseFunc

__all__ = ('trace_history', 'all_descendants', 'set_tracer',
@@ -52,10 +52,6 @@ def trace_history(self: Parser, text: StringView) -> Tuple[Optional[Node], Strin
                if not nd.children and nd.tag_name != ZOMBIE_TAG)
        text_ = pe.rest[l:]
        lc = line_col(grammar.document_lbreaks__, pe.error.pos)
        # grammar.history__.append(
        #     HistoryRecord(grammar.call_stack__, pe.node, text_, lc, [pe.error]))

        if grammar.resume_notices__:
        target = text
        if len(target) >= 10:
            target = target[:7] + '...'
@@ -70,12 +66,11 @@ def trace_history(self: Parser, text: StringView) -> Tuple[Optional[Node], Strin
            notice = Error('Skipping within parser {} to point {}'
                           .format(grammar.call_stack__[-1][0], repr(target)),
                           self._grammar.document_length__ - len(text_), Error.RESUME_NOTICE)

        if grammar.resume_notices__:
            grammar.tree__.add_error(pe.node, notice)
        errors.append(notice)

        grammar.history__.append(HistoryRecord(
            grammar.call_stack__, pe.node, text_, lc, errors))
            getattr(pe, 'frozen_callstack', grammar.call_stack__), pe.node, text_, lc, errors))

    grammar.call_stack__.append(
        ((self.repr if self.tag_name in (REGEXP_PTYPE, TOKEN_PTYPE)
@@ -85,8 +80,8 @@ def trace_history(self: Parser, text: StringView) -> Tuple[Optional[Node], Strin
    try:
        node, rest = self._parse(text)   # <===== call to the actual parser!
    except ParserError as pe:
        grammar.call_stack__.pop()
        if pe.first_throw:
            pe.frozen_callstack = freeze_callstack(grammar.call_stack__)
            grammar.most_recent_error__ = pe
        if self == grammar.start_parser__:
            fe = grammar.most_recent_error__
@@ -95,6 +90,7 @@ def trace_history(self: Parser, text: StringView) -> Tuple[Optional[Node], Strin
            nd = fe.node
            grammar.history__.append(
                HistoryRecord(grammar.call_stack__, nd, fe.rest[len(nd):], lc, [fe.error]))
        grammar.call_stack__.pop()
        raise pe

    # Mind that memoized parser calls will not appear in the history record!
@@ -110,7 +106,8 @@ def trace_history(self: Parser, text: StringView) -> Tuple[Optional[Node], Strin
        record = HistoryRecord(grammar.call_stack__, nd, rest, lc, [])
        cs_len = len(record.call_stack)
        if (not grammar.history__ or lc != grammar.history__[-1].line_col
                or record.call_stack != grammar.history__[-1].call_stack[:cs_len]):
                or record.call_stack != grammar.history__[-1].call_stack[:cs_len]
                or self == grammar.start_parser__):
            grammar.history__.append(record)

    grammar.moving_forward__ = False