aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--mammoth/docx/body_xml.py29
-rw-r--r--tests/docx/body_xml_tests.py14
2 files changed, 31 insertions, 12 deletions
diff --git a/mammoth/docx/body_xml.py b/mammoth/docx/body_xml.py
index f66eeae..854ccf2 100644
--- a/mammoth/docx/body_xml.py
+++ b/mammoth/docx/body_xml.py
@@ -100,6 +100,7 @@ def _create_reader(numbering, content_types, relationships, styles, docx_file, f
def paragraph(element):
+ messages = []
properties = element.find_child_or_null("w:pPr")
style_id = properties \
.find_child_or_null("w:pStyle") \
@@ -108,19 +109,29 @@ def _create_reader(numbering, content_types, relationships, styles, docx_file, f
if style_id is None:
style_name = None
else:
- style_name = styles.find_paragraph_style_by_id(style_id).name
+ style = styles.find_paragraph_style_by_id(style_id)
+ if style is None:
+ style_name = None
+ messages.append(_undefined_style_warning("Paragraph", style_id))
+ else:
+ style_name = style.name
numbering = _read_numbering_properties(properties.find_child_or_null("w:numPr"))
return _read_xml_elements(element.children) \
- .map(lambda children: documents.paragraph(
- children=children,
- style_id=style_id,
- style_name=style_name,
- numbering=numbering,
- )) \
+ .bind(lambda children: _element_result_with_messages(
+ documents.paragraph(
+ children=children,
+ style_id=style_id,
+ style_name=style_name,
+ numbering=numbering,
+ ),
+ messages)) \
.append_extra()
+ def _undefined_style_warning(style_type, style_id):
+ return results.warning("{0} style with ID {1} was referenced but not defined in the document".format(style_type, style_id))
+
def _read_numbering_properties(element):
num_id = element.find_child_or_null("w:numId").attributes.get("w:val")
level_index = element.find_child_or_null("w:ilvl").attributes.get("w:val")
@@ -341,6 +352,10 @@ class _ReadResult(object):
result = self._result.map(lambda value: func(value[0]))
return _ReadResult(result.value, self.extra, result.messages)
+ def bind(self, func):
+ result = self._result.bind(lambda value: func(value[0]))
+ return _ReadResult(result.value, self.extra, result.messages)
+
def to_extra(self):
return _ReadResult(None, _concat(self.extra, self.value), self.messages)
diff --git a/tests/docx/body_xml_tests.py b/tests/docx/body_xml_tests.py
index ddfa9b2..a3a7802 100644
--- a/tests/docx/body_xml_tests.py
+++ b/tests/docx/body_xml_tests.py
@@ -40,7 +40,7 @@ class ReadXmlElementTests(object):
assert_equal(None, _read_and_get_document_xml_element(element).style_id)
@istest
- def paragraph_has_style_id_read_from_paragraph_properties_if_present(self):
+ def paragraph_has_style_id_and_name_read_from_paragraph_properties_if_present(self):
style_xml = xml_element("w:pStyle", {"w:val": "Heading1"})
properties_xml = xml_element("w:pPr", {}, [style_xml])
paragraph_xml = xml_element("w:p", {}, [properties_xml])
@@ -49,17 +49,21 @@ class ReadXmlElementTests(object):
paragraph = _read_and_get_document_xml_element(paragraph_xml, styles=styles)
assert_equal("Heading1", paragraph.style_id)
+ assert_equal("Heading 1", paragraph.style_name)
@istest
- def paragraph_has_style_name_read_from_paragraph_properties_and_styles(self):
+ def warning_is_emitted_when_paragraph_style_cannot_be_found(self):
style_xml = xml_element("w:pStyle", {"w:val": "Heading1"})
properties_xml = xml_element("w:pPr", {}, [style_xml])
paragraph_xml = xml_element("w:p", {}, [properties_xml])
- styles = Styles({"Heading1": Style(style_id="Heading1", name="Heading 1")}, {})
+ styles = Styles({}, {})
- paragraph = _read_and_get_document_xml_element(paragraph_xml, styles=styles)
- assert_equal("Heading 1", paragraph.style_name)
+ result = _read_document_xml_element(paragraph_xml, styles=styles)
+ paragraph = result.value
+ assert_equal("Heading1", paragraph.style_id)
+ assert_equal(None, paragraph.style_name)
+ assert_equal([results.warning("Paragraph style with ID Heading1 was referenced but not defined in the document")], result.messages)
@istest
def paragraph_has_no_numbering_if_it_has_no_numbering_properties(self):