/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
/*
* This file is part of the LibreOffice project.
*
* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/.
*/
#include <test/unoapi_test.hxx>
#include <com/sun/star/document/XExtendedFilterDetection.hpp>
#include <com/sun/star/lang/XServiceInfo.hpp>
#include <com/sun/star/document/XTypeDetection.hpp>
#include <com/sun/star/drawing/XDrawPagesSupplier.hpp>
#include <com/sun/star/sheet/XCellRangesAccess.hpp>
#include <com/sun/star/sheet/XSpreadsheetDocument.hpp>
#include <com/sun/star/text/XTextDocument.hpp>
#include <comphelper/configuration.hxx>
#include <comphelper/propertyvalue.hxx>
#include <officecfg/Office/Common.hxx>
#include <osl/file.hxx>
#include <sfx2/docfac.hxx>
#include <unotools/mediadescriptor.hxx>
#include <unotools/streamwrap.hxx>
#include <tools/stream.hxx>
namespace com::sun::star::io
{
class XInputStream;
}
using namespace com::sun::star;
namespace
{
bool supportsService(const uno::Reference<lang::XComponent>& x, const OUString& s)
{
return uno::Reference<lang::XServiceInfo>(x, uno::UNO_QUERY_THROW)->supportsService(s);
}
/// Test class for PlainTextFilterDetect.
class TextFilterDetectTest : public UnoApiTest
{
public:
TextFilterDetectTest()
: UnoApiTest(u"/filter/qa/unit/data/"_ustr)
{
}
};
CPPUNIT_TEST_FIXTURE(TextFilterDetectTest, testTdf114428)
{
uno::Reference<document::XExtendedFilterDetection> xDetect(
getMultiServiceFactory()->createInstance(
u"com.sun.star.comp.filters.PlainTextFilterDetect"_ustr),
uno::UNO_QUERY);
OUString aURL = createFileURL(u"tdf114428.xhtml");
SvFileStream aStream(aURL, StreamMode::READ);
uno::Reference<io::XInputStream> xStream(new utl::OStreamWrapper(aStream));
uno::Sequence<beans::PropertyValue> aDescriptor
= { comphelper::makePropertyValue(u"DocumentService"_ustr,
u"com.sun.star.text.TextDocument"_ustr),
comphelper::makePropertyValue(u"InputStream"_ustr, xStream),
comphelper::makePropertyValue(u"TypeName"_ustr, u"generic_HTML"_ustr) };
xDetect->detect(aDescriptor);
utl::MediaDescriptor aMediaDesc(aDescriptor);
OUString aFilterName = aMediaDesc.getUnpackedValueOrDefault(u"FilterName"_ustr, OUString());
// This was empty, XML declaration caused HTML detect to not handle XHTML.
CPPUNIT_ASSERT_EQUAL(u"HTML (StarWriter)"_ustr, aFilterName);
}
CPPUNIT_TEST_FIXTURE(TextFilterDetectTest, testEmptyFile)
{
// Given an empty file, with a pptx extension
// When loading the file
loadFromFile(u"empty.pptx");
// Then make sure it is opened in Impress.
// Without the accompanying fix in place, this test would have failed, as it was opened in
// Writer instead.
CPPUNIT_ASSERT(
supportsService(mxComponent, u"com.sun.star.presentation.PresentationDocument"_ustr));
// Now also test ODT
loadFromFile(u"empty.odt");
// Make sure it opens in Writer.
CPPUNIT_ASSERT(supportsService(mxComponent, u"com.sun.star.text.TextDocument"_ustr));
// ... and ODS
loadFromFile(u"empty.ods");
// Make sure it opens in Calc.
CPPUNIT_ASSERT(supportsService(mxComponent, u"com.sun.star.sheet.SpreadsheetDocument"_ustr));
// ... and ODP
loadFromFile(u"empty.odp");
// Without the accompanying fix in place, this test would have failed, as it was opened in
// Writer instead.
CPPUNIT_ASSERT(
supportsService(mxComponent, u"com.sun.star.presentation.PresentationDocument"_ustr));
// ... and DOC
// Without the accompanying fix in place, this test would have failed, the import filter aborted
// loading.
loadFromFile(u"empty.doc");
CPPUNIT_ASSERT(supportsService(mxComponent, u"com.sun.star.text.TextDocument"_ustr));
{
uno::Reference<frame::XModel> xModel(mxComponent, uno::UNO_QUERY);
uno::Sequence<beans::PropertyValue> aArgs = xModel->getArgs();
comphelper::SequenceAsHashMap aMap(aArgs);
OUString aFilterName;
aMap[u"FilterName"_ustr] >>= aFilterName;
// Without the accompanying fix in place, this test would have failed with:
// - Expected: MS Word 97
// - Actual : MS WinWord 6.0
// i.e. opening worked, but saving back failed instead of producing a WW8 binary file.
CPPUNIT_ASSERT_EQUAL(u"MS Word 97"_ustr, aFilterName);
}
// Now test with default templates set
SfxObjectFactory::SetStandardTemplate(u"com.sun.star.presentation.PresentationDocument"_ustr,
createFileURL(u"impress.otp"));
SfxObjectFactory::SetStandardTemplate(u"com.sun.star.text.TextDocument"_ustr,
createFileURL(u"writer.ott"));
SfxObjectFactory::SetStandardTemplate(u"com.sun.star.sheet.SpreadsheetDocument"_ustr,
createFileURL(u"calc.ots"));
loadFromFile(u"empty.pptx");
{
uno::Reference<drawing::XDrawPagesSupplier> xDoc(mxComponent, uno::UNO_QUERY_THROW);
uno::Reference<drawing::XDrawPages> xPages(xDoc->getDrawPages(), uno::UNO_SET_THROW);
uno::Reference<drawing::XDrawPage> xPage(xPages->getByIndex(0), uno::UNO_QUERY_THROW);
uno::Reference<text::XTextRange> xBox(xPage->getByIndex(0), uno::UNO_QUERY_THROW);
// Make sure the template's text was loaded
CPPUNIT_ASSERT_EQUAL(u"Title of Impress template"_ustr, xBox->getString());
}
loadFromFile(u"empty.odt");
{
uno::Reference<text::XTextDocument> xDoc(mxComponent, uno::UNO_QUERY_THROW);
uno::Reference<container::XEnumerationAccess> xEA(xDoc->getText(), uno::UNO_QUERY_THROW);
uno::Reference<container::XEnumeration> xEnum(xEA->createEnumeration(), uno::UNO_SET_THROW);
uno::Reference<text::XTextRange> xParagraph(xEnum->nextElement(), uno::UNO_QUERY_THROW);
// Make sure the template's text was loaded
CPPUNIT_ASSERT_EQUAL(u"Writer template’s first line"_ustr, xParagraph->getString());
}
loadFromFile(u"empty.ods");
{
uno::Reference<sheet::XSpreadsheetDocument> xDoc(mxComponent, uno::UNO_QUERY_THROW);
uno::Reference<sheet::XCellRangesAccess> xRA(xDoc->getSheets(), uno::UNO_QUERY_THROW);
uno::Reference<text::XTextRange> xC(xRA->getCellByPosition(0, 0, 0), uno::UNO_QUERY_THROW);
// Make sure the template's text was loaded
CPPUNIT_ASSERT_EQUAL(u"Calc template’s first cell"_ustr, xC->getString());
}
loadFromFile(u"empty.odp");
{
uno::Reference<drawing::XDrawPagesSupplier> xDoc(mxComponent, uno::UNO_QUERY_THROW);
uno::Reference<drawing::XDrawPages> xPages(xDoc->getDrawPages(), uno::UNO_SET_THROW);
uno::Reference<drawing::XDrawPage> xPage(xPages->getByIndex(0), uno::UNO_QUERY_THROW);
uno::Reference<text::XTextRange> xBox(xPage->getByIndex(0), uno::UNO_QUERY_THROW);
// Make sure the template's text was loaded
CPPUNIT_ASSERT_EQUAL(u"Title of Impress template"_ustr, xBox->getString());
}
loadFromFile(u"empty.doc");
{
uno::Reference<text::XTextDocument> xDoc(mxComponent, uno::UNO_QUERY_THROW);
uno::Reference<container::XEnumerationAccess> xEA(xDoc->getText(), uno::UNO_QUERY_THROW);
uno::Reference<container::XEnumeration> xEnum(xEA->createEnumeration(), uno::UNO_SET_THROW);
uno::Reference<text::XTextRange> xParagraph(xEnum->nextElement(), uno::UNO_QUERY_THROW);
// Make sure the template's text was loaded
CPPUNIT_ASSERT_EQUAL(u"Writer template’s first line"_ustr, xParagraph->getString());
}
}
// The unit test fails on some Linux systems. Until it is found out why the file URLs are broken
// there, let it be Windows-only, since the original issue tested here was Windows-specific.
// See https://lists.freedesktop.org/archives/libreoffice/2023-December/091265.html for details.
#ifdef _WIN32
CPPUNIT_TEST_FIXTURE(TextFilterDetectTest, testHybridPDFFile)
{
// Make sure that file locking is ON
{
std::shared_ptr<comphelper::ConfigurationChanges> xChanges(
comphelper::ConfigurationChanges::create());
officecfg::Office::Common::Misc::UseDocumentSystemFileLocking::set(true, xChanges);
xChanges->commit();
}
// Given a hybrid PDF file
{
// Created in Writer
utl::TempFileNamed nonAsciiName(u"абв_αβγ_");
nonAsciiName.EnableKillingFile();
CPPUNIT_ASSERT_EQUAL(
osl::FileBase::E_None,
osl::File::copy(createFileURL(u"hybrid_writer.pdf"), nonAsciiName.GetURL()));
loadFromURL(nonAsciiName.GetURL());
// Make sure it opens in Writer.
// Without the accompanying fix in place, this test would have failed on Windows, as it was
// opened in Draw instead.
CPPUNIT_ASSERT(supportsService(mxComponent, "com.sun.star.text.TextDocument"));
}
{
// Created in Calc
utl::TempFileNamed nonAsciiName(u"абв_αβγ_");
nonAsciiName.EnableKillingFile();
CPPUNIT_ASSERT_EQUAL(
osl::FileBase::E_None,
osl::File::copy(createFileURL(u"hybrid_calc.pdf"), nonAsciiName.GetURL()));
loadFromURL(nonAsciiName.GetURL());
// Make sure it opens in Calc.
CPPUNIT_ASSERT(supportsService(mxComponent, "com.sun.star.sheet.SpreadsheetDocument"));
}
{
// Created in Impress
utl::TempFileNamed nonAsciiName(u"абв_αβγ_");
nonAsciiName.EnableKillingFile();
CPPUNIT_ASSERT_EQUAL(
osl::FileBase::E_None,
osl::File::copy(createFileURL(u"hybrid_impress.pdf"), nonAsciiName.GetURL()));
loadFromURL(nonAsciiName.GetURL());
// Make sure it opens in Impress.
CPPUNIT_ASSERT(
supportsService(mxComponent, "com.sun.star.presentation.PresentationDocument"));
}
}
#endif // _WIN32
CPPUNIT_TEST_FIXTURE(TextFilterDetectTest, testTdf163295)
{
// Given a file with a content of "<?xmlpwi" - yes, it's not an XML, and not a pwi file
auto xDetection(comphelper::getProcessServiceFactory()
->createInstance(u"com.sun.star.document.TypeDetection"_ustr)
.queryThrow<document::XTypeDetection>());
OUString url = createFileURL(u"test_pseudo_pwi.xml");
css::uno::Sequence mediaDescriptor{ comphelper::makePropertyValue(u"URL"_ustr, url) };
OUString detection = xDetection->queryTypeByDescriptor(mediaDescriptor, true);
// Without the fix, this was "writer_PocketWord_File"
CPPUNIT_ASSERT_EQUAL(u"generic_Text"_ustr, detection);
}
}
CPPUNIT_PLUGIN_IMPLEMENT();
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
↑ V530 The return value of function 'loadFromFile' is required to be utilized.
↑ V530 The return value of function 'loadFromFile' is required to be utilized.
↑ V530 The return value of function 'loadFromFile' is required to be utilized.
↑ V530 The return value of function 'loadFromFile' is required to be utilized.
↑ V530 The return value of function 'loadFromFile' is required to be utilized.
↑ V530 The return value of function 'loadFromFile' is required to be utilized.
↑ V530 The return value of function 'loadFromFile' is required to be utilized.
↑ V530 The return value of function 'loadFromFile' is required to be utilized.
↑ V530 The return value of function 'loadFromFile' is required to be utilized.
↑ V530 The return value of function 'loadFromFile' is required to be utilized.