Skip to content
Snippets Groups Projects
Commit 7fbe71df authored by Robin Sonnabend's avatar Robin Sonnabend
Browse files

Better error messages for some errors in parser

parent 2eb49f03
Branches
No related tags found
No related merge requests found
...@@ -66,9 +66,7 @@ class Element: ...@@ -66,9 +66,7 @@ class Element:
if match is None: if match is None:
raise ParserException("Source does not match!", linenumber) raise ParserException("Source does not match!", linenumber)
length = match.group().count("\n") length = match.group().count("\n")
if linenumber is None: return length + (0 if linenumber is None else linenumber)
return length
return linenumber + length
@staticmethod @staticmethod
def parse_outer(element, current): def parse_outer(element, current):
...@@ -88,8 +86,9 @@ class Element: ...@@ -88,8 +86,9 @@ class Element:
PATTERN = r"x(?<!x)" # yes, a master piece, but it should never be called PATTERN = r"x(?<!x)" # yes, a master piece, but it should never be called
class Content(Element): class Content(Element):
def __init__(self, children): def __init__(self, children, linenumber):
self.children = children self.children = children
self.linenumber = linenumber
def render(self): def render(self):
return "".join(map(lambda e: e.render(), self.children)) return "".join(map(lambda e: e.render(), self.children))
...@@ -127,7 +126,7 @@ class Content(Element): ...@@ -127,7 +126,7 @@ class Content(Element):
break break
if not matched: if not matched:
raise ParserException("Content does not match inner!", linenumber) raise ParserException("Content does not match inner!", linenumber)
return Content(children) return Content(children, linenumber)
# v1: has problems with missing semicolons # v1: has problems with missing semicolons
#PATTERN = r"\s*(?<content>(?:[^\[\];]+)?(?:\[[^\]]+\][^;\[\]]*)*);" #PATTERN = r"\s*(?<content>(?:[^\[\];]+)?(?:\[[^\]]+\][^;\[\]]*)*);"
...@@ -135,8 +134,9 @@ class Content(Element): ...@@ -135,8 +134,9 @@ class Content(Element):
PATTERN = r"\s*(?<content>(?:[^\[\];\r\n]+)?(?:\[[^\]\r\n]+\][^;\[\]\r\n]*)*);?" PATTERN = r"\s*(?<content>(?:[^\[\];\r\n]+)?(?:\[[^\]\r\n]+\][^;\[\]\r\n]*)*);?"
class Text: class Text:
def __init__(self, text): def __init__(self, text, linenumber):
self.text = text self.text = text
self.linenumber = linenumber
def render(self): def render(self):
return self.text return self.text
...@@ -153,15 +153,16 @@ class Text: ...@@ -153,15 +153,16 @@ class Text:
content = match.group("text") content = match.group("text")
if content is None: if content is None:
raise ParserException("Text is empty!", linenumber) raise ParserException("Text is empty!", linenumber)
return Text(content) return Text(content, linenumber)
PATTERN = r"(?<text>[^\[]+)(?:(?=\[)|$)" PATTERN = r"(?<text>[^\[]+)(?:(?=\[)|$)"
class Tag: class Tag:
def __init__(self, name, values): def __init__(self, name, values, linenumber):
self.name = name self.name = name
self.values = values self.values = values
self.linenumber = linenumber
def render(self): def render(self):
return r"\textbf{{{}:}} {}".format(self.name, "; ".join(self.values)); return r"\textbf{{{}:}} {}".format(self.name, "; ".join(self.values));
...@@ -179,13 +180,13 @@ class Tag: ...@@ -179,13 +180,13 @@ class Tag:
if content is None: if content is None:
raise ParserException("Tag is empty!", linenumber) raise ParserException("Tag is empty!", linenumber)
parts = content.split(";") parts = content.split(";")
return Tag(parts[0], parts[1:]) return Tag(parts[0], parts[1:], linenumber)
PATTERN = r"\[(?<content>(?:[^;\]]*;)*(?:[^;\]]*))\]" PATTERN = r"\[(?<content>(?:[^;\]]*;)*(?:[^;\]]*))\]"
class Empty(Element): class Empty(Element):
def __init__(self): def __init__(self, linenumber):
pass linenumber = linenumber
def render(self): def render(self):
return "" return ""
...@@ -203,9 +204,10 @@ class Empty(Element): ...@@ -203,9 +204,10 @@ class Empty(Element):
PATTERN = r"\s+" PATTERN = r"\s+"
class Remark(Element): class Remark(Element):
def __init__(self, name, value): def __init__(self, name, value, linenumber):
self.name = name self.name = name
self.value = value self.value = value
self.linenumber = linenumber
def render(self): def render(self):
return r"\textbf{{{}}}: {}".format(self.name, self.value) return r"\textbf{{{}}}: {}".format(self.name, self.value)
...@@ -225,17 +227,18 @@ class Remark(Element): ...@@ -225,17 +227,18 @@ class Remark(Element):
if len(parts) < 2: if len(parts) < 2:
raise ParserException("Remark value is empty!", linenumber) raise ParserException("Remark value is empty!", linenumber)
name, value = parts name, value = parts
element = Remark(name, value) element = Remark(name, value, linenumber)
current = Element.parse_outer(element, current) current = Element.parse_outer(element, current)
return current, linenumber return current, linenumber
PATTERN = r"\s*\#(?<content>[^\n]+)" PATTERN = r"\s*\#(?<content>[^\n]+)"
class Fork(Element): class Fork(Element):
def __init__(self, environment, name, parent, children=None): def __init__(self, environment, name, parent, linenumber, children=None):
self.environment = environment if environment is None or len(environment) > 0 else None self.environment = environment if environment is None or len(environment) > 0 else None
self.name = name if name is None or len(name) > 0 else None self.name = name if name is None or len(name) > 0 else None
self.parent = parent self.parent = parent
self.linenumber = linenumber
self.children = [] if children is None else children self.children = [] if children is None else children
def dump(self, level=None): def dump(self, level=None):
...@@ -259,7 +262,7 @@ class Fork(Element): ...@@ -259,7 +262,7 @@ class Fork(Element):
@staticmethod @staticmethod
def create_root(): def create_root():
return Fork(None, None, None) return Fork(None, None, None, 0)
@staticmethod @staticmethod
def parse(match, current, linenumber=None): def parse(match, current, linenumber=None):
...@@ -272,7 +275,7 @@ class Fork(Element): ...@@ -272,7 +275,7 @@ class Fork(Element):
name = name1 name = name1
if name2 is not None: if name2 is not None:
name += " {}".format(name2) name += " {}".format(name2)
element = Fork(environment, name, current) element = Fork(environment, name, current, linenumber)
current = Element.parse_outer(element, current) current = Element.parse_outer(element, current)
return current, linenumber return current, linenumber
...@@ -319,7 +322,7 @@ def parse(source): ...@@ -319,7 +322,7 @@ def parse(source):
if not found: if not found:
raise ParserException("No matching syntax element found!", linenumber) raise ParserException("No matching syntax element found!", linenumber)
if current is not tree: if current is not tree:
raise ParserException("Source ended within fork!") raise ParserException("Source ended within fork! (started at line {})".format(current.linenumber))
return tree return tree
def main(test_file_name=None): def main(test_file_name=None):
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment