Skip to content

Commit

Permalink
Fixed parsing of strings containing formatters ({0}, {1}, etc)
Browse files Browse the repository at this point in the history
  • Loading branch information
OmegaK2 committed Oct 8, 2020
1 parent a34fe32 commit cf17937
Show file tree
Hide file tree
Showing 2 changed files with 62 additions and 34 deletions.
89 changes: 56 additions & 33 deletions PyPoE/poe/text.py
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@
# Python
import re
from functools import partial
from typing import Callable, Dict, Union, List

# 3rd-party

Expand Down Expand Up @@ -68,40 +69,61 @@ class Tag(ReprMixin):
Parameters
----------
id : str
id
identifier string of the tag
parent : tag
parent
parent Tag instance if any
children : list[str or Tag]
children
list of child strings or tag instances
parameter : str
parameter
parameter specified in the text to this tag if any
"""
__slots__ = ['id', 'parent', 'parameter', 'children']

_REPR_ARGUMENTS_IGNORE = {'parent'}

def __init__(self, id=None, parent=None, children=None, parameter=None):
def __init__(self,
id: Union[str, None] = None,
parent: Union['Tag', None] = None,
children: Union[List[Union[str, 'Tag']], None] = None,
parameter: Union[str, None] = None):
"""
Parameters
----------
id : str
id
identifier string of the tag
parent : tag
parent
parent Tag instance if any
children : list[str or Tag]
children
list of child strings or tag instances
parameter : str
parameter
parameter specified in the text to this tag if any
"""
self.id = id
self.parent = parent
self.parameter = parameter
self.id: Union[str, None] = id
self.parent: Union['Tag', None] = parent
self.parameter: Union[str, None] = parameter
if children is None:
self.children = []
self.children: List[Union[str, 'Tag']] = []

def root(self):
def append_to_children(self, text: str):
"""
Appends a given text to the children attribute
Parameters
----------
text
Text to append to the children
"""
if self.children:
if isinstance(self.children[-1], Tag):
self.children.append(text)
else:
self.children[-1] += text
else:
self.children.append(text)

def root(self) -> 'Tag':
"""
Returns the root Tag node
Expand All @@ -116,13 +138,13 @@ def root(self):

return parent

def handle_tags(self, handlers):
def handle_tags(self, handlers: Dict[str, Callable]) -> str:
"""
Handle this and child tags with the handlers passed to this function.
Parameters
----------
handlers : dict[str, callable]
handlers
Dictionary containing a mapping of handler ids to callables that
handle them.
Expand All @@ -132,7 +154,6 @@ def handle_tags(self, handlers):
Returns
-------
str
The handled string
Raises
Expand All @@ -154,19 +175,18 @@ def handle_tags(self, handlers):
# =============================================================================


def parse_description_tags(text):
def parse_description_tags(text: str) -> Tag:
"""
Parses a text containing description tags into :class:`Tag` classes which
can be used for further handling.
Parameters
----------
text : str
text
The text to parse
Returns
-------
Tag
the parsed text as Tag class (with no id)
"""
def f(scanner, result, tid):
Expand All @@ -186,6 +206,7 @@ def f(scanner, result, tid):

in_tag = [False]
in_text = [True]
has_tag = [False]
parameter = [False]
depth = 0
out = Tag(id=None)
Expand All @@ -195,18 +216,26 @@ def f(scanner, result, tid):
if tid == 'lt':
depth += 1
in_tag.append(True)
has_tag.append(True)
parameter.append(False)
elif tid == 'gt':
in_tag[depth] = False
parameter[depth] = False
elif tid == 'lbrace':
in_text.append(True)
if has_tag[depth]:
in_text.append(True)
else:
last.append_to_children(text)
elif tid == 'rbrace':
del in_tag[depth]
del in_text[depth]
del parameter[depth]
last = last.parent
depth -= 1
if has_tag[depth]:
del in_tag[depth]
del in_text[depth]
del parameter[depth]
del has_tag[depth]
last = last.parent
depth -= 1
else:
last.append_to_children(text)
elif tid == 'colon':
if in_tag[depth]:
parameter[depth] = True
Expand All @@ -221,12 +250,6 @@ def f(scanner, result, tid):
last.children.append(tag)
last = tag
else:
if last.children:
if isinstance(last.children[-1], Tag):
last.children.append(text)
else:
last.children[-1] += text
else:
last.children.append(text)
last.append_to_children(text)

return out
7 changes: 6 additions & 1 deletion tests/PyPoE/poe/test_text.py
Original file line number Diff line number Diff line change
Expand Up @@ -79,7 +79,12 @@ class TestTags():
'Test <<TEST>>',
'Test <<TEST>>',
[],
)
),
(
'Format string {0} test',
'Format string {0} test',
[],
),
]

@pytest.mark.parametrize('input,output,handler_ids', sample_strings)
Expand Down

0 comments on commit cf17937

Please sign in to comment.