Skip to content
GitLab
Projects
Groups
Snippets
/
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Sign in
Toggle navigation
Menu
9.2.2023: Due to updates GitLab will be unavailable for some minutes between 9:00 and 11:00.
Open sidebar
badw-it
DHParser
Commits
cc08caee
Commit
cc08caee
authored
Jan 05, 2019
by
eckhart
Browse files
- bug fix for resmue after failure
parent
ecd84a51
Changes
5
Hide whitespace changes
Inline
Side-by-side
DHParser/ebnf.py
View file @
cc08caee
...
...
@@ -570,7 +570,6 @@ class EBNFCompiler(Compiler):
definitions
.
append
((
self
.
RAW_WS_KEYWORD
,
"r'{whitespace}'"
.
format
(
**
self
.
directives
)))
definitions
.
append
((
self
.
COMMENT_KEYWORD
,
"r'{comment}'"
.
format
(
**
self
.
directives
)))
definitions
.
append
((
self
.
RESUME_RULES_KEYWORD
,
repr
(
self
.
directives
[
'resume'
])))
print
(
self
.
directives
[
'resume'
])
# prepare parser class header and docstring and
# add EBNF grammar to the doc string of the parser class
...
...
DHParser/parse.py
View file @
cc08caee
...
...
@@ -157,10 +157,13 @@ def reentry_point(rest: StringView, rules: ResumeList) -> int:
def
add_parser_guard
(
parser_func
):
"""
Add a wrapper function to a parser functions (i.e. Parser.__call__ method)
that takes care of memoizing, left recursion and, optionally, tracing
(aka "history tracking") of parser calls. Returns the wrapped call.
that takes care of memoizing, left recursion, error catching and,
optionally, tracing (aka "history tracking") of parser calls.
Returns the wrapped call.
"""
def
guarded_call
(
parser
:
'Parser'
,
text
:
StringView
)
->
Tuple
[
Optional
[
Node
],
StringView
]:
"""Wrapper method for Parser.__call__. This is used to add in an aspect-oriented
fashion the business intelligence that is common to all parsers."""
grammar
=
parser
.
grammar
location
=
grammar
.
document_length__
-
len
(
text
)
...
...
@@ -193,7 +196,7 @@ def add_parser_guard(parser_func):
rules
=
grammar
.
resume_rules__
.
get
(
parser
.
name
,
[])
rest
=
error
.
rest
[
len
(
error
.
node
):]
i
=
reentry_point
(
rest
,
rules
)
if
i
>=
0
or
parser
==
grammar
.
root
__
:
if
i
>=
0
or
parser
==
grammar
.
start_parser
__
:
# apply reentry-rule or catch error at root-parser
if
i
<
0
:
i
=
1
...
...
@@ -538,6 +541,10 @@ class Grammar:
Attributes:
all_parsers__: A set of all parsers connected to this grammar object
start_parser__: During parsing, the parser with which the parsing process
was started (see method `__call__`) or `None` if no parsing process
is running.
history_tracking__: A flag indicating that the parsing history shall
be tracked
...
...
@@ -659,6 +666,7 @@ class Grammar:
def
__init__
(
self
,
root
:
Parser
=
None
)
->
None
:
self
.
all_parsers__
=
set
()
# type: Set[ParserBase]
self
.
start_parser__
=
None
# type: ParserBase
self
.
_dirty_flag__
=
False
# type: bool
self
.
history_tracking__
=
False
# type: bool
self
.
memoization__
=
True
# type: bool
...
...
@@ -738,7 +746,10 @@ class Grammar:
parser
.
grammar
=
self
def
__call__
(
self
,
document
:
str
,
start_parser
=
"root__"
,
track_history
=
False
)
->
RootNode
:
def
__call__
(
self
,
document
:
str
,
start_parser
:
Union
[
str
,
Parser
]
=
"root__"
,
track_history
:
bool
=
False
)
->
RootNode
:
"""
Parses a document with with parser-combinators.
...
...
@@ -779,6 +790,7 @@ class Grammar:
self
.
document_lbreaks__
=
linebreaks
(
document
)
if
self
.
history_tracking__
else
[]
self
.
last_rb__loc__
=
-
1
# rollback location
parser
=
self
[
start_parser
]
if
isinstance
(
start_parser
,
str
)
else
start_parser
self
.
start_parser__
=
parser
assert
parser
.
grammar
==
self
,
"Cannot run parsers from a different grammar object!"
\
" %s vs. %s"
%
(
str
(
self
),
str
(
parser
.
grammar
))
result
=
None
# type: Optional[Node]
...
...
@@ -865,6 +877,7 @@ class Grammar:
# result.collect_errors(self.document__)
if
result
:
self
.
tree__
.
swallow
(
result
)
self
.
start_parser__
=
None
return
self
.
tree__
...
...
examples/LaTeX/LaTeXCompiler.py
View file @
cc08caee
...
...
@@ -59,6 +59,7 @@ class LaTeXGrammar(Grammar):
text_element
=
Forward
()
source_hash__
=
"79e85f223d89452f2ba796f9c40daac9"
parser_initialization__
=
"upon instantiation"
resume_rules__
=
{}
COMMENT__
=
r
'%.*'
WHITESPACE__
=
r
'[ \t]*(?:\n(?![ \t]*\n)[ \t]*)?'
WSP_RE__
=
mixin_comment
(
whitespace
=
WHITESPACE__
,
comment
=
COMMENT__
)
...
...
test/test_parse.py
View file @
cc08caee
...
...
@@ -624,6 +624,15 @@ class TestReentryAfterError:
assert
cst
.
content
==
content
assert
cst
.
pick
(
'alpha'
).
content
.
startswith
(
'ALPHA'
)
def
test_no_resume_rules_partial_parsing
(
self
):
gr
=
self
.
gr
;
gr
.
resume_rules
=
dict
()
content
=
'ALPHA acb'
cst
=
gr
(
content
,
'alpha'
)
# print(cst.as_sxpr())
assert
cst
.
error_flag
assert
cst
.
content
==
content
assert
cst
.
pick
(
'alpha'
).
content
.
startswith
(
'ALPHA'
)
def
test_simple_resume_rule
(
self
):
gr
=
self
.
gr
;
gr
.
resume_rules
=
dict
()
gr
.
resume_rules__
[
'alpha'
]
=
[
'BETA'
]
...
...
test/test_testing.py
View file @
cc08caee
...
...
@@ -315,7 +315,7 @@ class TestLookahead:
def
test_unit_lookahead
(
self
):
errata
=
grammar_unit
(
self
.
cases
,
self
.
grammar_fac
,
self
.
trans_fac
)
assert
not
errata
assert
not
errata
,
str
(
errata
)
errata
=
grammar_unit
(
self
.
fail_cases
,
self
.
grammar_fac
,
self
.
trans_fac
)
assert
errata
...
...
Write
Preview
Supports
Markdown
0%
Try again
or
attach a new file
.
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment