desktop/source/lib/init.cxx | 39 ++- desktop/source/lib/lokinteractionhandler.cxx | 284 +++++++++++++++++++++------ desktop/source/lib/lokinteractionhandler.hxx | 33 ++- include/LibreOfficeKit/LibreOfficeKitEnums.h | 14 + libreofficekit/source/gtk/lokdocview.cxx | 21 + 5 files changed, 313 insertions(+), 78 deletions(-)
New commits: commit 64c1690fa31937bb4adfe0eb7beb42f105841c3b Author: Jan Holesovsky <ke...@collabora.com> Date: Tue Feb 2 22:59:34 2016 +0100 lok interaction handler: Add handling of io and network errors. Change-Id: If7c84a7b24f2072439718fb0c473b73243f2ecc1 diff --git a/desktop/source/lib/init.cxx b/desktop/source/lib/init.cxx index 0fbece0..c4d4450 100644 --- a/desktop/source/lib/init.cxx +++ b/desktop/source/lib/init.cxx @@ -271,7 +271,7 @@ static OUString getAbsoluteURL(const char* pURL) return OUString(); } -static void jsonToPropertyValues(const char* pJSON, uno::Sequence<beans::PropertyValue>& rPropertyValues) +static std::vector<beans::PropertyValue> jsonToPropertyValuesVector(const char* pJSON) { std::vector<beans::PropertyValue> aArguments; if (pJSON) @@ -298,11 +298,11 @@ static void jsonToPropertyValues(const char* pJSON, uno::Sequence<beans::Propert else if (rType == "unsigned short") aValue.Value <<= static_cast<sal_uInt16>(OString(rValue.c_str()).toUInt32()); else - SAL_WARN("desktop.lib", "jsonToPropertyValues: unhandled type '"<<rType<<"'"); + SAL_WARN("desktop.lib", "jsonToPropertyValuesVector: unhandled type '"<<rType<<"'"); aArguments.push_back(aValue); } } - rPropertyValues = comphelper::containerToSequence(aArguments); + return aArguments; } extern "C" @@ -549,7 +549,7 @@ static LibreOfficeKitDocument* lo_documentLoadWithOptions(LibreOfficeKit* pThis, beans::PropertyState_DIRECT_VALUE); rtl::Reference<LOKInteractionHandler> const pInteraction( - new LOKInteractionHandler(::comphelper::getProcessComponentContext(), pLib)); + new LOKInteractionHandler(::comphelper::getProcessComponentContext(), "load", pLib)); auto const pair(pLib->mInteractionMap.insert(std::make_pair(aURL.toUtf8(), pInteraction))); uno::Reference<task::XInteractionHandler2> const xInteraction(pInteraction.get()); aFilterOptions[1].Name = "InteractionHandler"; @@ -1034,9 +1034,9 @@ static void doc_initializeForRendering(LibreOfficeKitDocument* pThis, if (pDoc) { doc_iniUnoCommands(); - uno::Sequence<beans::PropertyValue> aPropertyValues; - jsonToPropertyValues(pArguments, aPropertyValues); - pDoc->initializeForTiledRendering(aPropertyValues); + + pDoc->initializeForTiledRendering( + comphelper::containerToSequence(jsonToPropertyValuesVector(pArguments))); } } @@ -1126,20 +1126,33 @@ public: static void doc_postUnoCommand(LibreOfficeKitDocument* pThis, const char* pCommand, const char* pArguments, bool bNotifyWhenFinished) { OUString aCommand(pCommand, strlen(pCommand), RTL_TEXTENCODING_UTF8); + LibLODocument_Impl* pDocument = static_cast<LibLODocument_Impl*>(pThis); - uno::Sequence<beans::PropertyValue> aPropertyValues; - jsonToPropertyValues(pArguments, aPropertyValues); - bool bResult = false; + std::vector<beans::PropertyValue> aPropertyValuesVector(jsonToPropertyValuesVector(pArguments)); - LibLODocument_Impl* pDocument = static_cast<LibLODocument_Impl*>(pThis); + // handle potential interaction + if (aCommand == ".uno:Save") + { + rtl::Reference<LOKInteractionHandler> const pInteraction( + new LOKInteractionHandler(::comphelper::getProcessComponentContext(), "save", gImpl, pDocument)); + uno::Reference<task::XInteractionHandler2> const xInteraction(pInteraction.get()); + + beans::PropertyValue aValue; + aValue.Name = "InteractionHandler"; + aValue.Value <<= xInteraction; + + aPropertyValuesVector.push_back(aValue); + } + + bool bResult = false; if (bNotifyWhenFinished && pDocument->mpCallback) { - bResult = comphelper::dispatchCommand(aCommand, aPropertyValues, + bResult = comphelper::dispatchCommand(aCommand, comphelper::containerToSequence(aPropertyValuesVector), new DispatchResultListener(pCommand, pDocument->mpCallback, pDocument->mpCallbackData)); } else - bResult = comphelper::dispatchCommand(aCommand, aPropertyValues); + bResult = comphelper::dispatchCommand(aCommand, comphelper::containerToSequence(aPropertyValuesVector)); if (!bResult) { diff --git a/desktop/source/lib/lokinteractionhandler.cxx b/desktop/source/lib/lokinteractionhandler.cxx index 86f521e..a4a60c2 100644 --- a/desktop/source/lib/lokinteractionhandler.cxx +++ b/desktop/source/lib/lokinteractionhandler.cxx @@ -19,12 +19,21 @@ #include "lokinteractionhandler.hxx" +#include <boost/property_tree/json_parser.hpp> + #include <rtl/ref.hxx> #include <cppuhelper/supportsservice.hxx> #include <com/sun/star/task/XInteractionAbort.hpp> #include <com/sun/star/task/XInteractionApprove.hpp> #include <com/sun/star/task/XInteractionPassword2.hpp> +#include <com/sun/star/ucb/InteractiveNetworkConnectException.hpp> +#include <com/sun/star/ucb/InteractiveNetworkOffLineException.hpp> + +#include <com/sun/star/ucb/InteractiveIOException.hpp> +#include <com/sun/star/ucb/InteractiveNetworkReadException.hpp> +#include <com/sun/star/ucb/InteractiveNetworkResolveNameException.hpp> +#include <com/sun/star/ucb/InteractiveNetworkWriteException.hpp> #define LOK_USE_UNSTABLE_API #include <../../inc/lib/init.hxx> @@ -35,8 +44,12 @@ using namespace com::sun::star; LOKInteractionHandler::LOKInteractionHandler( uno::Reference<uno::XComponentContext> const & /*rxContext*/, - desktop::LibLibreOffice_Impl *const pLOKit) + const OString& rCommand, + desktop::LibLibreOffice_Impl *const pLOKit, + desktop::LibLODocument_Impl *const pLOKDocument) : m_pLOKit(pLOKit) + , m_pLOKDocument(pLOKDocument) + , m_command(rCommand) , m_usePassword(false) { assert(m_pLOKit); @@ -79,8 +92,157 @@ throw (uno::RuntimeException, std::exception) handleInteractionRequest(xRequest); } -sal_Bool LOKInteractionHandler::handlePasswordRequest(const uno::Sequence<uno::Reference<task::XInteractionContinuation>> &rContinuations, const task::DocumentPasswordRequest2& passwordRequest) +void LOKInteractionHandler::postError(css::task::InteractionClassification classif, const char* kind, ErrCode code, const OUString &message) { + const char *classification = "error"; + switch (classif) + { + case task::InteractionClassification_ERROR: break; + case task::InteractionClassification_WARNING: classification = "warning"; break; + case task::InteractionClassification_INFO: classification = "info"; break; + case task::InteractionClassification_QUERY: classification = "query"; break; + default: assert(false); break; + } + + // create the JSON representation + boost::property_tree::ptree aTree; + aTree.put("classification", classification); + aTree.put("cmd", m_command.getStr()); + aTree.put("kind", kind); + aTree.put("code", code); + aTree.put("message", message.toUtf8()); + + std::stringstream aStream; + boost::property_tree::write_json(aStream, aTree); + + if (m_pLOKDocument) + m_pLOKDocument->mpCallback(LOK_CALLBACK_ERROR, aStream.str().c_str(), m_pLOKDocument->mpCallbackData); + else + m_pLOKit->mpCallback(LOK_CALLBACK_ERROR, aStream.str().c_str(), m_pLOKit->mpCallbackData); +} + +namespace { + +/// Just approve the interaction. +void selectApproved(uno::Sequence<uno::Reference<task::XInteractionContinuation>> const &rContinuations) +{ + for (sal_Int32 i = 0; i < rContinuations.getLength(); ++i) + { + uno::Reference<task::XInteractionApprove> xApprove(rContinuations[i], uno::UNO_QUERY); + if (xApprove.is()) + xApprove->select(); + } +} + +} + +bool LOKInteractionHandler::handleIOException(const css::uno::Sequence<css::uno::Reference<css::task::XInteractionContinuation>> &rContinuations, const css::uno::Any& rRequest) +{ + ucb::InteractiveIOException aIoException; + if (!(rRequest >>= aIoException)) + return false; + + static ErrCode const aErrorCode[ucb::IOErrorCode_WRONG_VERSION + 1] = + { + ERRCODE_IO_ABORT, + ERRCODE_IO_ACCESSDENIED, + ERRCODE_IO_ALREADYEXISTS, + ERRCODE_IO_BADCRC, + ERRCODE_IO_CANTCREATE, + ERRCODE_IO_CANTREAD, + ERRCODE_IO_CANTSEEK, + ERRCODE_IO_CANTTELL, + ERRCODE_IO_CANTWRITE, + ERRCODE_IO_CURRENTDIR, + ERRCODE_IO_DEVICENOTREADY, + ERRCODE_IO_NOTSAMEDEVICE, + ERRCODE_IO_GENERAL, + ERRCODE_IO_INVALIDACCESS, + ERRCODE_IO_INVALIDCHAR, + ERRCODE_IO_INVALIDDEVICE, + ERRCODE_IO_INVALIDLENGTH, + ERRCODE_IO_INVALIDPARAMETER, + ERRCODE_IO_ISWILDCARD, + ERRCODE_IO_LOCKVIOLATION, + ERRCODE_IO_MISPLACEDCHAR, + ERRCODE_IO_NAMETOOLONG, + ERRCODE_IO_NOTEXISTS, + ERRCODE_IO_NOTEXISTSPATH, + ERRCODE_IO_NOTSUPPORTED, + ERRCODE_IO_NOTADIRECTORY, + ERRCODE_IO_NOTAFILE, + ERRCODE_IO_OUTOFSPACE, + ERRCODE_IO_TOOMANYOPENFILES, + ERRCODE_IO_OUTOFMEMORY, + ERRCODE_IO_PENDING, + ERRCODE_IO_RECURSIVE, + ERRCODE_IO_UNKNOWN, + ERRCODE_IO_WRITEPROTECTED, + ERRCODE_IO_WRONGFORMAT, + ERRCODE_IO_WRONGVERSION, + }; + + postError(aIoException.Classification, "io", aErrorCode[aIoException.Code], ""); + selectApproved(rContinuations); + + return true; +} + +bool LOKInteractionHandler::handleNetworkException(const uno::Sequence<uno::Reference<task::XInteractionContinuation>> &rContinuations, const uno::Any &rRequest) +{ + ucb::InteractiveNetworkException aNetworkException; + if (!(rRequest >>= aNetworkException)) + return false; + + ErrCode nErrorCode; + OUString aMessage; + + ucb::InteractiveNetworkOffLineException aOffLineException; + ucb::InteractiveNetworkResolveNameException aResolveNameException; + ucb::InteractiveNetworkConnectException aConnectException; + ucb::InteractiveNetworkReadException aReadException; + ucb::InteractiveNetworkWriteException aWriteException; + if (rRequest >>= aOffLineException) + { + nErrorCode = ERRCODE_INET_OFFLINE; + } + else if (rRequest >>= aResolveNameException) + { + nErrorCode = ERRCODE_INET_NAME_RESOLVE; + aMessage = aResolveNameException.Server; + } + else if (rRequest >>= aConnectException) + { + nErrorCode = ERRCODE_INET_CONNECT; + aMessage = aConnectException.Server; + } + else if (rRequest >>= aReadException) + { + nErrorCode = ERRCODE_INET_READ; + aMessage = aReadException.Diagnostic; + } + else if (rRequest >>= aWriteException) + { + nErrorCode = ERRCODE_INET_WRITE; + aMessage = aWriteException.Diagnostic; + } + else + { + nErrorCode = ERRCODE_INET_GENERAL; + } + + postError(aNetworkException.Classification, "network", nErrorCode, aMessage); + selectApproved(rContinuations); + + return true; +} + +bool LOKInteractionHandler::handlePasswordRequest(const uno::Sequence<uno::Reference<task::XInteractionContinuation>> &rContinuations, const uno::Any &rRequest) +{ + task::DocumentPasswordRequest2 passwordRequest; + if (!(rRequest >>= passwordRequest)) + return false; + if (m_pLOKit->hasOptionalFeature((passwordRequest.IsRequestPasswordToModify) ? LOK_FEATURE_DOCUMENT_PASSWORD_TO_MODIFY : LOK_FEATURE_DOCUMENT_PASSWORD)) @@ -135,28 +297,26 @@ sal_Bool LOKInteractionHandler::handlePasswordRequest(const uno::Sequence<uno::R } } } - return sal_True; + return true; } sal_Bool SAL_CALL LOKInteractionHandler::handleInteractionRequest( - const uno::Reference<task::XInteractionRequest>& xRequest) -throw (uno::RuntimeException, std::exception) + const uno::Reference<task::XInteractionRequest>& xRequest) throw (uno::RuntimeException, std::exception) { uno::Sequence<uno::Reference<task::XInteractionContinuation>> const &rContinuations = xRequest->getContinuations(); - uno::Any const request(xRequest->getRequest()); - task::DocumentPasswordRequest2 passwordRequest; - if (request >>= passwordRequest) - return handlePasswordRequest(rContinuations, passwordRequest); - // TODO: add LOK api that allows handling this for real, for the moment we - // just set the interaction as 'Approved' - for (sal_Int32 i = 0; i < rContinuations.getLength(); ++i) - { - uno::Reference<task::XInteractionApprove> xApprove(rContinuations[i], uno::UNO_QUERY); - if (xApprove.is()) - xApprove->select(); - } + if (handleIOException(rContinuations, request)) + return true; + + if (handleNetworkException(rContinuations, request)) + return true; + + if (handlePasswordRequest(rContinuations, request)) + return true; + + // TODO: perform more interactions 'for real' like the above + selectApproved(rContinuations); return sal_True; } diff --git a/desktop/source/lib/lokinteractionhandler.hxx b/desktop/source/lib/lokinteractionhandler.hxx index 3c18864..4a453c3 100644 --- a/desktop/source/lib/lokinteractionhandler.hxx +++ b/desktop/source/lib/lokinteractionhandler.hxx @@ -22,13 +22,18 @@ #include <osl/conditn.hxx> #include <cppuhelper/implbase.hxx> +#include <tools/errcode.hxx> #include <com/sun/star/lang/XInitialization.hpp> #include <com/sun/star/lang/XServiceInfo.hpp> #include <com/sun/star/task/DocumentPasswordRequest2.hpp> #include <com/sun/star/task/InteractionHandler.hpp> +#include <com/sun/star/ucb/InteractiveNetworkException.hpp> -namespace desktop { struct LibLibreOffice_Impl; } +namespace desktop { + struct LibLibreOffice_Impl; + struct LibLODocument_Impl; +} /** InteractionHandler is an interface that provides the user with various dialogs / error messages. @@ -44,6 +49,11 @@ class LOKInteractionHandler: public cppu::WeakImplHelper<com::sun::star::lang::X { private: desktop::LibLibreOffice_Impl * m_pLOKit; + desktop::LibLODocument_Impl * m_pLOKDocument; + + /// Command for which we use this interaction handler (like "load", "save", "saveas", ...) + OString m_command; + OUString m_Password; bool m_usePassword; osl::Condition m_havePassword; @@ -51,14 +61,30 @@ private: LOKInteractionHandler(const LOKInteractionHandler&) SAL_DELETED_FUNCTION; LOKInteractionHandler& operator=(const LOKInteractionHandler&) SAL_DELETED_FUNCTION; - sal_Bool handlePasswordRequest(const css::uno::Sequence<css::uno::Reference<css::task::XInteractionContinuation>> &rContinuations, const css::task::DocumentPasswordRequest2& passwordRequest); + /** Call the LOK_CALLBACK_ERROR on the LOK document (if available) or LOK lib. + + The error itself is a JSON message, like: + { + "classification": "error" | "warning" | "info" + "kind": "network" etc. + "code": 403 | 404 | ... + "message": freeform description + } + */ + void postError(css::task::InteractionClassification classif, const char* kind, ErrCode code, const OUString &message); + + bool handleIOException(const css::uno::Sequence<css::uno::Reference<css::task::XInteractionContinuation>> &rContinuations, const css::uno::Any& rRequest); + bool handleNetworkException(const css::uno::Sequence<css::uno::Reference<css::task::XInteractionContinuation>> &rContinuations, const css::uno::Any& rRequest); + bool handlePasswordRequest(const css::uno::Sequence<css::uno::Reference<css::task::XInteractionContinuation>> &rContinuations, const css::uno::Any& rRequest); public: void SetPassword(char const* pPassword); explicit LOKInteractionHandler( com::sun::star::uno::Reference<com::sun::star::uno::XComponentContext> const & rxContext, - desktop::LibLibreOffice_Impl *); + const OString& rCommand, + desktop::LibLibreOffice_Impl *, + desktop::LibLODocument_Impl *pLOKDocumt = nullptr); virtual ~LOKInteractionHandler(); diff --git a/include/LibreOfficeKit/LibreOfficeKitEnums.h b/include/LibreOfficeKit/LibreOfficeKitEnums.h index 5931f78..3f2a6ea 100644 --- a/include/LibreOfficeKit/LibreOfficeKitEnums.h +++ b/include/LibreOfficeKit/LibreOfficeKitEnums.h @@ -265,6 +265,20 @@ typedef enum * lok::Office::setDocumentPassword(). */ LOK_CALLBACK_DOCUMENT_PASSWORD_TO_MODIFY, + + /** + * An error happened. + * + * The payload returns information further identifying the error, like: + * + * { + * "classification": "error" | "warning" | "info" + * "kind": "network" etc. + * "code": 403 | 404 | ... + * "message": freeform description + * } + */ + LOK_CALLBACK_ERROR, } LibreOfficeKitCallbackType; diff --git a/libreofficekit/source/gtk/lokdocview.cxx b/libreofficekit/source/gtk/lokdocview.cxx index bdf3a19..cad178b 100644 --- a/libreofficekit/source/gtk/lokdocview.cxx +++ b/libreofficekit/source/gtk/lokdocview.cxx @@ -199,6 +199,8 @@ struct LOKDocView_Impl void searchNotFound(const std::string& rPayload); /// LOK decided to change parts, need to update UI. void setPart(const std::string& rPayload); + /// LOK got an error callback. + void reportError(const std::string& rPayload); }; namespace { @@ -935,6 +937,8 @@ const char* LOKDocView_Impl::callbackTypeToString(int nType) return "LOK_CALLBACK_DOCUMENT_SIZE_CHANGED"; case LOK_CALLBACK_SET_PART: return "LOK_CALLBACK_SET_PART"; + case LOK_CALLBACK_ERROR: + return "LOK_CALLBACK_ERROR"; } return 0; } @@ -1042,6 +1046,11 @@ gboolean LOKDocView_Impl::callbackImpl(CallbackData* pCallback) setPart(pCallback->m_aPayload); } break; + case LOK_CALLBACK_ERROR: + { + reportError(pCallback->m_aPayload); + } + break; default: g_assert(false); break; @@ -1109,6 +1118,18 @@ void LOKDocView_Impl::setPart(const std::string& rString) renderDocument(0); } +void LOKDocView_Impl::reportError(const std::string& rString) +{ + GtkWidget *dialog = gtk_message_dialog_new(nullptr, + GTK_DIALOG_DESTROY_WITH_PARENT, + GTK_MESSAGE_ERROR, + GTK_BUTTONS_CLOSE, + "%s", + rString.c_str()); + gtk_dialog_run(GTK_DIALOG(dialog)); + gtk_widget_destroy(dialog); +} + static void lok_docview_class_init( gpointer ptr ) { LOKDocViewClass* pClass = static_cast<LOKDocViewClass *>(ptr); commit 0fa0bc66e2010d01947671022926c3ae920fbf11 Author: Jan Holesovsky <ke...@collabora.com> Date: Tue Feb 2 11:54:35 2016 +0100 lok interaction handler: Move password handling to an own method. Change-Id: I1b3cfdef5f4f81c9138ad5600e43755841df5d75 diff --git a/desktop/source/lib/lokinteractionhandler.cxx b/desktop/source/lib/lokinteractionhandler.cxx index 50a7972..86f521e 100644 --- a/desktop/source/lib/lokinteractionhandler.cxx +++ b/desktop/source/lib/lokinteractionhandler.cxx @@ -25,7 +25,6 @@ #include <com/sun/star/task/XInteractionAbort.hpp> #include <com/sun/star/task/XInteractionApprove.hpp> #include <com/sun/star/task/XInteractionPassword2.hpp> -#include <com/sun/star/task/DocumentPasswordRequest2.hpp> #define LOK_USE_UNSTABLE_API #include <../../inc/lib/init.hxx> @@ -80,76 +79,75 @@ throw (uno::RuntimeException, std::exception) handleInteractionRequest(xRequest); } -sal_Bool SAL_CALL LOKInteractionHandler::handleInteractionRequest( - const uno::Reference<task::XInteractionRequest>& xRequest) -throw (uno::RuntimeException, std::exception) +sal_Bool LOKInteractionHandler::handlePasswordRequest(const uno::Sequence<uno::Reference<task::XInteractionContinuation>> &rContinuations, const task::DocumentPasswordRequest2& passwordRequest) { - uno::Sequence<uno::Reference<task::XInteractionContinuation>> const &rContinuations = xRequest->getContinuations(); - - uno::Any const request(xRequest->getRequest()); - task::DocumentPasswordRequest2 passwordRequest; - if (request >>= passwordRequest) + if (m_pLOKit->hasOptionalFeature((passwordRequest.IsRequestPasswordToModify) + ? LOK_FEATURE_DOCUMENT_PASSWORD_TO_MODIFY + : LOK_FEATURE_DOCUMENT_PASSWORD)) { - if (m_pLOKit->hasOptionalFeature((passwordRequest.IsRequestPasswordToModify) - ? LOK_FEATURE_DOCUMENT_PASSWORD_TO_MODIFY - : LOK_FEATURE_DOCUMENT_PASSWORD)) - { - OString const url(passwordRequest.Name.toUtf8()); - m_pLOKit->mpCallback(passwordRequest.IsRequestPasswordToModify - ? LOK_CALLBACK_DOCUMENT_PASSWORD_TO_MODIFY - : LOK_CALLBACK_DOCUMENT_PASSWORD, - url.getStr(), - m_pLOKit->mpCallbackData); - - // block until SetPassword is called - m_havePassword.wait(); - m_havePassword.reset(); - } + OString const url(passwordRequest.Name.toUtf8()); + m_pLOKit->mpCallback(passwordRequest.IsRequestPasswordToModify + ? LOK_CALLBACK_DOCUMENT_PASSWORD_TO_MODIFY + : LOK_CALLBACK_DOCUMENT_PASSWORD, + url.getStr(), + m_pLOKit->mpCallbackData); + + // block until SetPassword is called + m_havePassword.wait(); + m_havePassword.reset(); + } - for (sal_Int32 i = 0; i < rContinuations.getLength(); ++i) + for (sal_Int32 i = 0; i < rContinuations.getLength(); ++i) + { + if (m_usePassword) { - if (m_usePassword) + if (passwordRequest.IsRequestPasswordToModify) { - if (passwordRequest.IsRequestPasswordToModify) - { - uno::Reference<task::XInteractionPassword2> const xIPW2( - rContinuations[i], uno::UNO_QUERY); - xIPW2->setPasswordToModify(m_Password); - xIPW2->select(); - } - else - { - uno::Reference<task::XInteractionPassword> const xIPW( - rContinuations[i], uno::UNO_QUERY); - if (xIPW.is()) - { - xIPW->setPassword(m_Password); - xIPW->select(); - } - } + uno::Reference<task::XInteractionPassword2> const xIPW2(rContinuations[i], uno::UNO_QUERY); + xIPW2->setPasswordToModify(m_Password); + xIPW2->select(); } else { - if (passwordRequest.IsRequestPasswordToModify) + uno::Reference<task::XInteractionPassword> const xIPW(rContinuations[i], uno::UNO_QUERY); + if (xIPW.is()) { - uno::Reference<task::XInteractionPassword2> const xIPW2( - rContinuations[i], uno::UNO_QUERY); - xIPW2->setRecommendReadOnly(true); - xIPW2->select(); + xIPW->setPassword(m_Password); + xIPW->select(); } - else + } + } + else + { + if (passwordRequest.IsRequestPasswordToModify) + { + uno::Reference<task::XInteractionPassword2> const xIPW2(rContinuations[i], uno::UNO_QUERY); + xIPW2->setRecommendReadOnly(true); + xIPW2->select(); + } + else + { + uno::Reference<task::XInteractionAbort> const xAbort(rContinuations[i], uno::UNO_QUERY); + if (xAbort.is()) { - uno::Reference<task::XInteractionAbort> const xAbort( - rContinuations[i], uno::UNO_QUERY); - if (xAbort.is()) - { - xAbort->select(); - } + xAbort->select(); } } } - return sal_True; } + return sal_True; +} + +sal_Bool SAL_CALL LOKInteractionHandler::handleInteractionRequest( + const uno::Reference<task::XInteractionRequest>& xRequest) +throw (uno::RuntimeException, std::exception) +{ + uno::Sequence<uno::Reference<task::XInteractionContinuation>> const &rContinuations = xRequest->getContinuations(); + + uno::Any const request(xRequest->getRequest()); + task::DocumentPasswordRequest2 passwordRequest; + if (request >>= passwordRequest) + return handlePasswordRequest(rContinuations, passwordRequest); // TODO: add LOK api that allows handling this for real, for the moment we // just set the interaction as 'Approved' diff --git a/desktop/source/lib/lokinteractionhandler.hxx b/desktop/source/lib/lokinteractionhandler.hxx index 2999cbb..3c18864 100644 --- a/desktop/source/lib/lokinteractionhandler.hxx +++ b/desktop/source/lib/lokinteractionhandler.hxx @@ -25,6 +25,7 @@ #include <com/sun/star/lang/XInitialization.hpp> #include <com/sun/star/lang/XServiceInfo.hpp> +#include <com/sun/star/task/DocumentPasswordRequest2.hpp> #include <com/sun/star/task/InteractionHandler.hpp> namespace desktop { struct LibLibreOffice_Impl; } @@ -50,6 +51,8 @@ private: LOKInteractionHandler(const LOKInteractionHandler&) SAL_DELETED_FUNCTION; LOKInteractionHandler& operator=(const LOKInteractionHandler&) SAL_DELETED_FUNCTION; + sal_Bool handlePasswordRequest(const css::uno::Sequence<css::uno::Reference<css::task::XInteractionContinuation>> &rContinuations, const css::task::DocumentPasswordRequest2& passwordRequest); + public: void SetPassword(char const* pPassword); _______________________________________________ Libreoffice-commits mailing list libreoffice-comm...@lists.freedesktop.org http://lists.freedesktop.org/mailman/listinfo/libreoffice-commits