Related: tdf#160260 Drop xpdfimport.err.pdf, let PDF import return false

The problem was, that upon any error in opening a PDF, out Poppler
wrapper used another bundled document, with a single page with a static
text "This PDF file is encrypted and can't be opened.". That happened
regardless of the nature of the problem (it could be an IO problem, as
in tdf#160260, or other things from Poppler's poppler/ErrorCodes.h).
For automated import (command line or API), it meant that it was not
possible to detect the failure.

This replaces this strange mechanism with a normal error reporting. For
now, a simple "general input/output error" will be reported; but it is
possible to use interaction handler to show details (see comment in
xpdf_ImportFromFile).

Change-Id: I30493118fc5dd0b1c62cae7718acfe95bb4b13b5
Reviewed-on: https://gerrit.libreoffice.org/c/core/+/165771
Tested-by: Jenkins
Reviewed-by: Mike Kaganski <mike.kaganski@collabora.com>
This commit is contained in:
Mike Kaganski 2024-04-04 09:41:50 +05:00
parent cab028121b
commit cc89565130
4 changed files with 9 additions and 31 deletions

View file

@ -9,6 +9,4 @@
$(eval $(call gb_Package_Package,sdext_pdfimport_pdf,$(SRCDIR)/sdext)) $(eval $(call gb_Package_Package,sdext_pdfimport_pdf,$(SRCDIR)/sdext))
$(eval $(call gb_Package_add_file,sdext_pdfimport_pdf,$(LIBO_SHARE_FOLDER)/xpdfimport/xpdfimport_err.pdf,source/pdfimport/dialogs/xpdfimport_err.pdf))
# vim: set noet sw=4 ts=4: # vim: set noet sw=4 ts=4:

View file

@ -1079,24 +1079,12 @@ bool xpdf_ImportFromFile(const OUString& rURL,
OUString converterURL("$BRAND_BASE_DIR/" LIBO_BIN_FOLDER "/xpdfimport"); OUString converterURL("$BRAND_BASE_DIR/" LIBO_BIN_FOLDER "/xpdfimport");
rtl::Bootstrap::expandMacros(converterURL); //TODO: detect failure rtl::Bootstrap::expandMacros(converterURL); //TODO: detect failure
// Determine pathname of xpdfimport_err.pdf:
OUString errPathname("$BRAND_BASE_DIR/" LIBO_SHARE_FOLDER "/xpdfimport/xpdfimport_err.pdf");
rtl::Bootstrap::expandMacros(errPathname); //TODO: detect failure
if (osl::FileBase::getSystemPathFromFileURL(errPathname, errPathname)
!= osl::FileBase::E_None)
{
SAL_WARN(
"sdext.pdfimport",
"getSystemPathFromFileURL(" << errPathname << ") failed");
return false;
}
// spawn separate process to keep LGPL/GPL code apart. // spawn separate process to keep LGPL/GPL code apart.
OUString aOptFlag("-o"); OUString aOptFlag("-o");
rtl_uString* args[] = { aSysUPath.pData, errPathname.pData, rtl_uString* args[] = { aSysUPath.pData,
aOptFlag.pData, rFilterOptions.pData }; aOptFlag.pData, rFilterOptions.pData };
sal_Int32 nArgs = rFilterOptions.isEmpty() ? 2 : 4; sal_Int32 nArgs = rFilterOptions.isEmpty() ? std::size(args) - 2 : std::size(args);
oslProcess aProcess; oslProcess aProcess;
oslFileHandle pIn = nullptr; oslFileHandle pIn = nullptr;
@ -1206,6 +1194,7 @@ bool xpdf_ImportFromFile(const OUString& rURL,
"sdext.pdfimport", "sdext.pdfimport",
"getProcessInfo of " << converterURL "getProcessInfo of " << converterURL
<< " failed with exit code " << info.Code); << " failed with exit code " << info.Code);
// TODO: use xIHdl and/or exceptions to inform the user; see poppler/ErrorCodes.h
bRet = false; bRet = false;
} }
} }

View file

@ -152,7 +152,6 @@ int main(int argc, char **argv)
// PDFDoc takes over ownership for all strings below // PDFDoc takes over ownership for all strings below
GooString* pFileName = new GooString(myStringToStdString(argv[1])); GooString* pFileName = new GooString(myStringToStdString(argv[1]));
GooString* pErrFileName = new GooString(myStringToStdString(argv[2]));
// check for password string(s) // check for password string(s)
GooString* pOwnerPasswordStr( aPwBuf[0] != 0 GooString* pOwnerPasswordStr( aPwBuf[0] != 0
@ -182,30 +181,22 @@ int main(int argc, char **argv)
PDFDoc aDoc( std::make_unique<GooString>(pFileName), PDFDoc aDoc( std::make_unique<GooString>(pFileName),
std::optional<GooString>(pOwnerPasswordStr), std::optional<GooString>(pOwnerPasswordStr),
std::optional<GooString>(pUserPasswordStr) ); std::optional<GooString>(pUserPasswordStr) );
PDFDoc aErrDoc( std::make_unique<GooString>(pErrFileName),
std::optional<GooString>(pOwnerPasswordStr),
std::optional<GooString>(pUserPasswordStr) );
#else #else
PDFDoc aDoc( pFileName, PDFDoc aDoc( pFileName,
pOwnerPasswordStr, pOwnerPasswordStr,
pUserPasswordStr ); pUserPasswordStr );
PDFDoc aErrDoc( pErrFileName,
pOwnerPasswordStr,
pUserPasswordStr );
#endif #endif
// Check various permissions for aDoc. if (!aDoc.isOk())
PDFDoc &rDoc = aDoc.isOk()? aDoc: aErrDoc; return aDoc.getErrorCode();
pdfi::PDFOutDev aOutDev(&rDoc); pdfi::PDFOutDev aOutDev(&aDoc);
if (options == TO_STRING_VIEW("SkipImages")) { if (options == TO_STRING_VIEW("SkipImages")) {
aOutDev.setSkipImages(true); aOutDev.setSkipImages(true);
} }
// tell the receiver early - needed for proper progress calculation // tell the receiver early - needed for proper progress calculation
const int nPages = rDoc.isOk()? rDoc.getNumPages(): 0; const int nPages = aDoc.getNumPages();
pdfi::PDFOutDev::setPageNum(nPages); pdfi::PDFOutDev::setPageNum(nPages);
// virtual resolution of the PDF OutputDev in dpi // virtual resolution of the PDF OutputDev in dpi
@ -214,12 +205,12 @@ int main(int argc, char **argv)
// do the conversion // do the conversion
for (int i = 1; i <= nPages; ++i) for (int i = 1; i <= nPages; ++i)
{ {
rDoc.displayPage(&aOutDev, aDoc.displayPage(&aOutDev,
i, i,
PDFI_OUTDEV_RESOLUTION, PDFI_OUTDEV_RESOLUTION,
PDFI_OUTDEV_RESOLUTION, PDFI_OUTDEV_RESOLUTION,
0, true, true, true); 0, true, true, true);
rDoc.processLinks(&aOutDev, i); aDoc.processLinks(&aOutDev, i);
} }
return 0; return 0;