diff options
author | Mike Kaganski <mike.kaganski@collabora.com> | 2022-11-29 20:23:13 +0300 |
---|---|---|
committer | Mike Kaganski <mike.kaganski@collabora.com> | 2022-11-30 06:52:09 +0100 |
commit | dda4867a0b5a2d29d8a01a3656e0c8dac7626d2f (patch) | |
tree | 0f0b2b2a41b7e7be7413407f37709cecb8a78e84 /sw | |
parent | 98d8adc5b377039d5dee0d5046ece721010a960c (diff) |
tdf#152289: implement external glossary relations roundtrip
Change-Id: I20f4439abfbf73485734fd8373fffb2916d390f0
Reviewed-on: https://gerrit.libreoffice.org/c/core/+/143470
Tested-by: Jenkins
Reviewed-by: Mike Kaganski <mike.kaganski@collabora.com>
Diffstat (limited to 'sw')
-rw-r--r-- | sw/qa/extras/ooxmlexport/data/glossaryWithEmail.docx | bin | 0 -> 19290 bytes | |||
-rw-r--r-- | sw/qa/extras/ooxmlexport/ooxmlexport3.cxx | 11 | ||||
-rw-r--r-- | sw/source/filter/ww8/docxexport.cxx | 42 |
3 files changed, 44 insertions, 9 deletions
diff --git a/sw/qa/extras/ooxmlexport/data/glossaryWithEmail.docx b/sw/qa/extras/ooxmlexport/data/glossaryWithEmail.docx Binary files differnew file mode 100644 index 000000000000..5ec375adf3ac --- /dev/null +++ b/sw/qa/extras/ooxmlexport/data/glossaryWithEmail.docx diff --git a/sw/qa/extras/ooxmlexport/ooxmlexport3.cxx b/sw/qa/extras/ooxmlexport/ooxmlexport3.cxx index fe1aa44d75e7..9930fa27b768 100644 --- a/sw/qa/extras/ooxmlexport/ooxmlexport3.cxx +++ b/sw/qa/extras/ooxmlexport/ooxmlexport3.cxx @@ -991,6 +991,17 @@ CPPUNIT_TEST_FIXTURE(Test, testGlossary) assertXPath(pXmlDoc, "/w:glossaryDocument", "Ignorable", "w14 wp14"); } +CPPUNIT_TEST_FIXTURE(Test, testGlossaryWithEmail) +{ + // tdf#152289 + loadAndSave("glossaryWithEmail.docx"); + xmlDocUniquePtr pXmlDoc = parseExport("word/glossary/_rels/document.xml.rels"); + assertXPath(pXmlDoc, "/rels:Relationships/rels:Relationship[@Id='rId4' " + "and @Type='http://schemas.openxmlformats.org/officeDocument/2006/relationships/hyperlink' " + "and @Target='mailto:emailgoeshere@example.com' " + "and @TargetMode='External']"); +} + DECLARE_OOXMLEXPORT_TEST(testFdo71785, "fdo71785.docx") { // crashtest diff --git a/sw/source/filter/ww8/docxexport.cxx b/sw/source/filter/ww8/docxexport.cxx index 97875b28817d..ea59775eda15 100644 --- a/sw/source/filter/ww8/docxexport.cxx +++ b/sw/source/filter/ww8/docxexport.cxx @@ -1484,6 +1484,7 @@ void DocxExport::WriteTheme() uno::Sequence< beans::StringPair >() ); } +// See OOXMLDocumentImpl::resolveGlossaryStream void DocxExport::WriteGlossary() { uno::Reference< beans::XPropertySet > xPropSet( m_rDoc.GetDocShell()->GetBaseModel(), uno::UNO_QUERY_THROW ); @@ -1494,7 +1495,7 @@ void DocxExport::WriteGlossary() return; uno::Reference<xml::dom::XDocument> glossaryDocDom; - uno::Sequence< uno::Sequence< uno::Any> > glossaryDomList; + uno::Sequence< uno::Sequence<beans::NamedValue> > glossaryDomList; uno::Sequence< beans::PropertyValue > propList; xPropSet->getPropertyValue( aName ) >>= propList; sal_Int32 collectedProperties = 0; @@ -1532,20 +1533,43 @@ void DocxExport::WriteGlossary() serializer->serialize( uno::Reference< xml::sax::XDocumentHandler >( writer, uno::UNO_QUERY_THROW ), uno::Sequence< beans::StringPair >() ); - for ( const uno::Sequence< uno::Any>& glossaryElement : std::as_const(glossaryDomList)) + for (const uno::Sequence<beans::NamedValue>& glossaryElement : glossaryDomList) { - OUString gTarget, gType, gId, contentType; + OUString gTarget, gType, gId, contentType, targetMode; uno::Reference<xml::dom::XDocument> xDom; - glossaryElement[0] >>= xDom; - glossaryElement[1] >>= gId; - glossaryElement[2] >>= gType; - glossaryElement[3] >>= gTarget; - glossaryElement[4] >>= contentType; + for (const auto& [name, value] : glossaryElement) + { + if (name == "Id") + value >>= gId; + else if (name == "Type") + value >>= gType; + else if (name == "Target") + value >>= gTarget; + else if (name == "TargetMode") + value >>= targetMode; + else if (name == "_contentType") + value >>= contentType; + else if (name == "_relDom") + value >>= xDom; + } + if (gId.isEmpty() || gType.isEmpty() || gTarget.isEmpty()) + continue; + const bool bExternal = targetMode == "External"; + if (!bExternal && !xDom) + { + // Some internal relation, but we didn't create a DOM for it + // in OOXMLDocumentImpl::resolveGlossaryStream? + SAL_WARN("sw.ww8", "Glossary internal relation without DOM: Id=\"" + gId + + "\" Type=\"" + gType + "\" Target=\"" + gTarget + "\""); + continue; + } gId = gId.copy(3); //"rId" only save the numeric value PropertySet aProps(xOutputStream); aProps.setAnyProperty( PROP_RelId, uno::Any( gId.toInt32() )); - m_rFilter.addRelation( xOutputStream, gType, gTarget); + m_rFilter.addRelation(xOutputStream, gType, gTarget, bExternal); + if (!xDom) + continue; // External relation, no stream to write uno::Reference< xml::sax::XSAXSerializable > gserializer( xDom, uno::UNO_QUERY ); writer->setOutputStream(GetFilter().openFragmentStream( "word/glossary/" + gTarget, contentType ) ); gserializer->serialize( uno::Reference< xml::sax::XDocumentHandler >( writer, uno::UNO_QUERY_THROW ), |