Skip to content

Commit ff61650

Browse files
committed
spec_object_parser: a slot for XHTML attribute stripped from namespace info
1 parent d18343d commit ff61650

4 files changed

Lines changed: 80 additions & 4 deletions

File tree

reqif/helpers/lxml.py

Lines changed: 15 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -87,7 +87,15 @@ def stringify_children(node):
8787
(node.text,),
8888
chain(
8989
*(
90-
(tostring(child, encoding=str, with_tail=False), child.tail)
90+
(
91+
tostring(
92+
child,
93+
encoding=str,
94+
with_tail=False,
95+
pretty_print=True,
96+
),
97+
child.tail,
98+
)
9199
for child in node.getchildren()
92100
)
93101
),
@@ -111,6 +119,12 @@ def lxml_convert_from_reqif_ns_xhtml_string(lxml_node) -> str:
111119
).rstrip()
112120

113121

122+
def lxml_convert_children_from_reqif_ns_xhtml_string(lxml_node) -> str:
123+
lxml_node_deep_copy = deepcopy(lxml_node)
124+
lxml_strip_namespace_from_xml(lxml_node_deep_copy, full=True)
125+
return stringify_children(lxml_node_deep_copy)
126+
127+
114128
def is_self_closed_tag(xml):
115129
# The tag cannot be closed if it has children or has a non-None text.
116130
if len(xml.getchildren()) > 0:

reqif/models/reqif_spec_object.py

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,16 +6,20 @@
66

77
@auto_described
88
class SpecObjectAttribute:
9-
def __init__(
9+
def __init__( # pylint: disable=too-many-arguments
1010
self,
1111
attribute_type: SpecObjectAttributeType,
1212
definition_ref: str,
1313
value: Union[str, List[str]],
14+
value_stripped_xhtml: Optional[str] = None,
1415
xml_node: Optional[Any] = None,
1516
):
1617
self.attribute_type: SpecObjectAttributeType = attribute_type
1718
self.definition_ref: str = definition_ref
1819
self.value: Union[str, List[str]] = value
20+
# Only for XHTML attributes: A valud stripped of the
21+
# <xhtml:...> namespace. <xhtml:div> becomes <div>...
22+
self.value_stripped_xhtml: Optional[str] = value_stripped_xhtml
1923
self.xml_node: Optional[Any] = xml_node
2024

2125

reqif/parsers/spec_object_parser.py

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,11 @@
33

44
from lxml import etree
55

6-
from reqif.helpers.lxml import stringify_namespaced_children
6+
from reqif.helpers.lxml import (
7+
lxml_convert_children_from_reqif_ns_xhtml_string,
8+
stringify_namespaced_children,
9+
)
10+
from reqif.helpers.string.xhtml_indent import reqif_unindent_xhtml_string
711
from reqif.models.reqif_spec_object import (
812
ReqIFSpecObject,
913
SpecObjectAttribute,
@@ -202,16 +206,20 @@ def parse(spec_object_xml) -> ReqIFSpecObject:
202206
elif attribute_xml.tag == "ATTRIBUTE-VALUE-XHTML":
203207
the_value = attribute_xml.find("THE-VALUE")
204208
attribute_value = stringify_namespaced_children(the_value)
209+
attribute_value_stripped_xhtml = reqif_unindent_xhtml_string(
210+
lxml_convert_children_from_reqif_ns_xhtml_string(the_value)
211+
)
205212
attribute_definition_ref = (
206213
attribute_xml.find("DEFINITION")
207214
.find("ATTRIBUTE-DEFINITION-XHTML-REF")
208215
.text
209216
)
210217
attribute = SpecObjectAttribute(
211-
xml_node=attribute_xml,
212218
attribute_type=SpecObjectAttributeType.XHTML,
213219
definition_ref=attribute_definition_ref,
214220
value=attribute_value,
221+
value_stripped_xhtml=attribute_value_stripped_xhtml,
222+
xml_node=attribute_xml,
215223
)
216224
else:
217225
raise NotImplementedError(etree.tostring(attribute_xml))
Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,50 @@
1+
from reqif.parser import ReqIFParser
2+
3+
4+
def test_01_indenting_unintended_xhtml():
5+
input_reqif = """\
6+
<?xml version="1.0" encoding="UTF-8"?>
7+
<REQ-IF xmlns="http://www.omg.org/spec/ReqIF/20110401/reqif.xsd" xmlns:configuration="http://eclipse.org/rmf/pror/toolextensions/1.0" xmlns:xhtml="http://www.w3.org/1999/xhtml">
8+
<CORE-CONTENT>
9+
<REQ-IF-CONTENT>
10+
<SPEC-OBJECTS>
11+
<SPEC-OBJECT IDENTIFIER="TEST_SPEC_OBJECT_IDENTIFIER" LAST-CHANGE="2021-10-15T11:34:36.007+02:00">
12+
<VALUES>
13+
<ATTRIBUTE-VALUE-XHTML>
14+
<DEFINITION>
15+
<ATTRIBUTE-DEFINITION-XHTML-REF>_gFhrXWojEeuExICsU7Acmg</ATTRIBUTE-DEFINITION-XHTML-REF>
16+
</DEFINITION>
17+
<THE-VALUE>
18+
<xhtml:div>
19+
<xhtml:p style=" font-style: italic">Delay <xhtml:span style="text-decoration: underline;">&lt;= 5s</xhtml:span></xhtml:p>
20+
</xhtml:div>
21+
</THE-VALUE>
22+
</ATTRIBUTE-VALUE-XHTML>
23+
</VALUES>
24+
<TYPE>
25+
<SPEC-OBJECT-TYPE-REF>TEST_SPEC_OBJECT_TYPE_IDENTIFIER_FUNCTIONAL</SPEC-OBJECT-TYPE-REF>
26+
</TYPE>
27+
</SPEC-OBJECT>
28+
</SPEC-OBJECTS>
29+
</REQ-IF-CONTENT>
30+
</CORE-CONTENT>
31+
</REQ-IF>
32+
""" # noqa: E501
33+
34+
expected_stripped_xhtml = """\
35+
<div>
36+
<p style=" font-style: italic">Delay <span style="text-decoration: underline;">&lt;= 5s</span></p>
37+
</div>\
38+
""" # noqa: E501
39+
40+
reqif_bundle = ReqIFParser.parse_from_string(input_reqif)
41+
spec_object = reqif_bundle.get_spec_object_by_ref(
42+
"TEST_SPEC_OBJECT_IDENTIFIER"
43+
)
44+
45+
assert (
46+
spec_object.attribute_map[
47+
"_gFhrXWojEeuExICsU7Acmg"
48+
].value_stripped_xhtml
49+
== expected_stripped_xhtml
50+
)

0 commit comments

Comments
 (0)