1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
3 * This file is part of the LibreOffice project.
5 * This Source Code Form is subject to the terms of the Mozilla Public
6 * License, v. 2.0. If a copy of the MPL was not distributed with this
7 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
9 * This file incorporates work covered by the following license notice:
11 * Licensed to the Apache Software Foundation (ASF) under one or more
12 * contributor license agreements. See the NOTICE file distributed
13 * with this work for additional information regarding copyright
14 * ownership. The ASF licenses this file to you under the Apache
15 * License, Version 2.0 (the "License"); you may not use this file
16 * except in compliance with the License. You may obtain a copy of
17 * the License at http://www.apache.org/licenses/LICENSE-2.0 .
22 #include <com/sun/star/awt/XWindow.hpp>
23 #include <com/sun/star/configuration/theDefaultProvider.hpp>
24 #include <com/sun/star/configuration/backend/MergeRecoveryRequest.hpp>
25 #include <com/sun/star/configuration/backend/StratumCreationException.hpp>
26 #include <com/sun/star/container/XHierarchicalNameAccess.hpp>
27 #include <com/sun/star/document/BrokenPackageRequest.hpp>
28 #include <com/sun/star/document/ExoticFileLoadException.hpp>
29 #include <com/sun/star/task/DocumentMacroConfirmationRequest.hpp>
30 #include <com/sun/star/java/WrongJavaVersionException.hpp>
31 #include <com/sun/star/lang/XInitialization.hpp>
32 #include <com/sun/star/lang/XMultiServiceFactory.hpp>
33 #include <com/sun/star/script/ModuleSizeExceededRequest.hpp>
34 #include <com/sun/star/task/ErrorCodeIOException.hpp>
35 #include <com/sun/star/task/ErrorCodeRequest.hpp>
36 #include <com/sun/star/task/InteractionHandler.hpp>
37 #include <com/sun/star/task/XInteractionAbort.hpp>
38 #include <com/sun/star/task/XInteractionApprove.hpp>
39 #include <com/sun/star/task/XInteractionDisapprove.hpp>
40 #include <com/sun/star/task/XInteractionHandler2.hpp>
41 #include <com/sun/star/task/XInteractionRequest.hpp>
42 #include <com/sun/star/ucb/AuthenticationFallbackRequest.hpp>
43 #include <com/sun/star/ucb/InteractiveAppException.hpp>
44 #include <com/sun/star/ucb/InteractiveLockingLockedException.hpp>
45 #include <com/sun/star/ucb/InteractiveLockingNotLockedException.hpp>
46 #include <com/sun/star/ucb/InteractiveLockingLockExpiredException.hpp>
47 #include <com/sun/star/ucb/InteractiveNetworkConnectException.hpp>
48 #include <com/sun/star/ucb/InteractiveNetworkOffLineException.hpp>
49 #include <com/sun/star/ucb/InteractiveNetworkReadException.hpp>
50 #include <com/sun/star/ucb/InteractiveNetworkResolveNameException.hpp>
51 #include <com/sun/star/ucb/InteractiveNetworkWriteException.hpp>
52 #include <com/sun/star/ucb/InteractiveWrongMediumException.hpp>
53 #include <com/sun/star/ucb/NameClashException.hpp>
54 #include <com/sun/star/ucb/NameClashResolveRequest.hpp>
55 #include <com/sun/star/ucb/UnsupportedNameClashException.hpp>
56 #include <com/sun/star/ucb/XInteractionReplaceExistingData.hpp>
57 #include <com/sun/star/ucb/XInteractionSupplyName.hpp>
58 #include <com/sun/star/xforms/InvalidDataOnSubmitException.hpp>
59 #include <com/sun/star/loader/CannotActivateFactoryException.hpp>
61 #include <sal/log.hxx>
62 #include <rtl/ustrbuf.hxx>
63 #include <osl/conditn.hxx>
64 #include <unotools/resmgr.hxx>
66 #include <vcl/errinf.hxx>
67 #include <vcl/svapp.hxx>
68 #include <vcl/weld.hxx>
69 #include <comphelper/diagnose_ex.hxx>
70 #include <comphelper/documentconstants.hxx>
71 #include <comphelper/propertysequence.hxx>
72 #include <svtools/sfxecode.hxx>
73 #include <unotools/configmgr.hxx>
74 #include <comphelper/namedvaluecollection.hxx>
75 #include <typelib/typedescription.hxx>
76 #include <unotools/confignode.hxx>
80 #include <strings.hrc>
82 #include "getcontinuations.hxx"
83 #include "secmacrowarnings.hxx"
86 #include "nameclashdlg.hxx"
88 using ::com::sun::star::uno::Sequence
;
89 using ::com::sun::star::uno::UNO_QUERY
;
90 using ::com::sun::star::uno::Reference
;
91 using ::com::sun::star::task::XInteractionContinuation
;
92 using ::com::sun::star::task::XInteractionAbort
;
93 using ::com::sun::star::task::XInteractionApprove
;
94 using ::com::sun::star::uno::XInterface
;
95 using ::com::sun::star::lang::XInitialization
;
96 using ::com::sun::star::uno::UNO_QUERY_THROW
;
97 using ::com::sun::star::task::InteractionHandler
;
98 using ::com::sun::star::task::XInteractionHandler2
;
99 using ::com::sun::star::uno::Exception
;
100 using ::com::sun::star::uno::Any
;
101 using ::com::sun::star::task::XInteractionRequest
;
102 using ::com::sun::star::lang::XMultiServiceFactory
;
104 using namespace ::com::sun::star
;
108 class HandleData
: public osl::Condition
112 uno::Reference
< task::XInteractionRequest
> xRequest
)
113 : m_rRequest(std::move(xRequest
)),
117 uno::Reference
< task::XInteractionRequest
> m_rRequest
;
119 beans::Optional
< OUString
> m_aResult
;
124 UUIInteractionHelper::UUIInteractionHelper(
125 uno::Reference
< uno::XComponentContext
> xContext
)
126 : m_xContext(std::move(xContext
))
130 UUIInteractionHelper::~UUIInteractionHelper()
134 void UUIInteractionHelper::handlerequest(
135 void* pHandleData
, void* pInteractionHelper
)
138 = static_cast< HandleData
* >(pHandleData
);
139 UUIInteractionHelper
* pUUI
140 = static_cast< UUIInteractionHelper
* >(pInteractionHelper
);
144 = pUUI
->handleRequest_impl(pHND
->m_rRequest
, false, bDummy
, aDummy
);
149 UUIInteractionHelper::handleRequest(
150 uno::Reference
< task::XInteractionRequest
> const & rRequest
)
152 if(!Application::IsMainThread() && GetpApp())
154 // we are not in the main thread, let it handle that stuff
155 HandleData
aHD(rRequest
);
156 Link
<void*,void> aLink(&aHD
,handlerequest
);
157 Application::PostUserEvent(aLink
,this);
158 comphelper::SolarMutex
& rSolarMutex
= Application::GetSolarMutex();
159 sal_uInt32 nLockCount
= (rSolarMutex
.IsCurrentThread()) ? rSolarMutex
.release(true) : 0;
162 rSolarMutex
.acquire(nLockCount
);
169 return handleRequest_impl(rRequest
, false, bDummy
, aDummy
);
173 void UUIInteractionHelper::getstringfromrequest(
174 void* pHandleData
,void* pInteractionHelper
)
176 HandleData
* pHND
= static_cast<HandleData
*>(pHandleData
);
177 UUIInteractionHelper
* pUUI
= static_cast<UUIInteractionHelper
*>(pInteractionHelper
);
178 pHND
->m_aResult
= pUUI
->getStringFromRequest_impl(pHND
->m_rRequest
);
182 beans::Optional
< OUString
>
183 UUIInteractionHelper::getStringFromRequest_impl(
184 uno::Reference
< task::XInteractionRequest
> const & rRequest
)
186 bool bSuccess
= false;
188 handleRequest_impl(rRequest
, true, bSuccess
, aMessage
);
190 OSL_ENSURE(bSuccess
||
191 !isInformationalErrorMessageRequest(
192 rRequest
->getContinuations()),
193 "Interaction request is a candidate for a string representation."
194 "Please implement!");
196 return beans::Optional
< OUString
>(bSuccess
, aMessage
);
199 beans::Optional
< OUString
>
200 UUIInteractionHelper::getStringFromRequest(
201 uno::Reference
< task::XInteractionRequest
> const & rRequest
)
203 if(!Application::IsMainThread() && GetpApp())
205 // we are not in the main thread, let it handle that stuff
206 HandleData
aHD(rRequest
);
207 Link
<void*,void> aLink(&aHD
,getstringfromrequest
);
208 Application::PostUserEvent(aLink
,this);
209 comphelper::SolarMutex
& rSolarMutex
= Application::GetSolarMutex();
210 sal_uInt32 nLockCount
= (rSolarMutex
.IsCurrentThread()) ? rSolarMutex
.release(true) : 0;
213 rSolarMutex
.acquire(nLockCount
);
214 return aHD
.m_aResult
;
217 return getStringFromRequest_impl(rRequest
);
221 UUIInteractionHelper::replaceMessageWithArguments(
222 const OUString
& _aMessage
,
223 std::vector
< OUString
> const & rArguments
)
225 OUString aMessage
= _aMessage
;
227 SAL_WARN_IF(rArguments
.empty(), "uui", "replaceMessageWithArguments: No arguments passed!");
228 for (size_t i
= 0; i
< rArguments
.size(); ++i
)
230 const OUString sReplaceTemplate
= "$(ARG" + OUString::number(i
+1) + ")";
231 aMessage
= aMessage
.replaceAll(sReplaceTemplate
, rArguments
[i
]);
238 UUIInteractionHelper::isInformationalErrorMessageRequest(
239 uno::Sequence
< uno::Reference
< task::XInteractionContinuation
> > const &
242 // Only requests with a single continuation (user has no choice, request
243 // is just informational)
244 if (rContinuations
.getLength() != 1 )
247 // user can only abort or approve, all other continuations are not
248 // considered to be informational.
249 uno::Reference
< task::XInteractionApprove
> xApprove(
250 rContinuations
[0], uno::UNO_QUERY
);
254 uno::Reference
< task::XInteractionAbort
> xAbort(
255 rContinuations
[0], uno::UNO_QUERY
);
260 UUIInteractionHelper::tryOtherInteractionHandler(
261 uno::Reference
< task::XInteractionRequest
> const & rRequest
)
263 InteractionHandlerDataList dataList
;
264 getInteractionHandlerList(dataList
);
266 return std::any_of(dataList
.cbegin(), dataList
.cend(),
267 [&](const InteractionHandlerData
& rData
) { return handleCustomRequest( rRequest
, rData
.ServiceName
); });
273 bool lcl_matchesRequest( const Any
& i_rRequest
, const OUString
& i_rTypeName
, std::u16string_view i_rPropagation
)
275 const css::uno::TypeDescription
aTypeDesc( i_rTypeName
);
276 const typelib_TypeDescription
* pTypeDesc
= aTypeDesc
.get();
277 if ( !pTypeDesc
|| !pTypeDesc
->pWeakRef
)
279 SAL_WARN( "uui","no type found for '" << i_rTypeName
<< "'" );
282 const css::uno::Type
aType( pTypeDesc
->pWeakRef
);
284 const bool bExactMatch
= i_rPropagation
== u
"named-only";
286 return i_rRequest
.getValueType().equals( aType
);
288 return i_rRequest
.isExtractableTo( aType
);
293 bool UUIInteractionHelper::handleCustomRequest( const Reference
< XInteractionRequest
>& i_rRequest
, const OUString
& i_rServiceName
) const
297 Reference
< XInteractionHandler2
> xHandler( m_xContext
->getServiceManager()->createInstanceWithContext( i_rServiceName
, m_xContext
), UNO_QUERY_THROW
);
299 Reference
< XInitialization
> xHandlerInit( xHandler
, UNO_QUERY
);
300 if ( xHandlerInit
.is() )
302 ::comphelper::NamedValueCollection aInitArgs
;
303 aInitArgs
.put( "Parent", getParentXWindow() );
304 xHandlerInit
->initialize( aInitArgs
.getWrappedPropertyValues() );
307 if ( xHandler
->handleInteractionRequest( i_rRequest
) )
310 catch( const Exception
& )
312 DBG_UNHANDLED_EXCEPTION("uui");
318 bool UUIInteractionHelper::handleTypedHandlerImplementations( Reference
< XInteractionRequest
> const & rRequest
)
321 const Any
aRequest( rRequest
->getRequest() );
323 const StringHashMap::const_iterator aCacheHitTest
= m_aTypedCustomHandlers
.find( aRequest
.getValueTypeName() );
324 if ( aCacheHitTest
!= m_aTypedCustomHandlers
.end() )
325 return handleCustomRequest( rRequest
, aCacheHitTest
->second
);
327 // the base registration node for "typed" interaction handlers
328 const ::utl::OConfigurationTreeRoot
aConfigRoot( ::utl::OConfigurationTreeRoot::createWithComponentContext(
330 "/org.openoffice.Interaction/InteractionHandlers",
332 ::utl::OConfigurationTreeRoot::CM_READONLY
335 // loop through all registered implementations
336 const Sequence
< OUString
> aRegisteredHandlers( aConfigRoot
.getNodeNames() );
337 for ( auto const & handlerName
: aRegisteredHandlers
)
339 const ::utl::OConfigurationNode
aHandlerNode( aConfigRoot
.openNode( handlerName
) );
340 const ::utl::OConfigurationNode
aTypesNode( aHandlerNode
.openNode( "HandledRequestTypes" ) );
342 // loop through all the types which the current handler is registered for
343 const Sequence
< OUString
> aHandledTypes( aTypesNode
.getNodeNames() );
344 for ( auto const & type
: aHandledTypes
)
346 // the UNO type is the node name
347 ::utl::OConfigurationNode
aType( aTypesNode
.openNode( type
) );
348 // and there's a child denoting how the responsibility propagates
349 OUString sPropagation
;
350 OSL_VERIFY( aType
.getNodeValue( "Propagation" ) >>= sPropagation
);
351 if ( lcl_matchesRequest( aRequest
, type
, sPropagation
) )
353 // retrieve the service/implementation name of the handler
354 OUString sServiceName
;
355 OSL_VERIFY( aHandlerNode
.getNodeValue( "ServiceName" ) >>= sServiceName
);
356 // cache the information who feels responsible for requests of this type
357 m_aTypedCustomHandlers
[ aRequest
.getValueTypeName() ] = sServiceName
;
358 // actually handle the request
359 return handleCustomRequest( rRequest
, sServiceName
);
368 UUIInteractionHelper::handleRequest_impl(
369 uno::Reference
< task::XInteractionRequest
> const & rRequest
,
370 bool bObtainErrorStringOnly
,
371 bool & bHasErrorString
,
372 OUString
& rErrorString
)
379 uno::Any
aAnyRequest(rRequest
->getRequest());
381 script::ModuleSizeExceededRequest aModSizeException
;
382 if (aAnyRequest
>>= aModSizeException
)
384 std::vector
< OUString
> aArguments
;
385 uno::Sequence
< OUString
> sModules
386 = aModSizeException
.Names
;
387 if ( sModules
.hasElements() )
389 OUStringBuffer aName
;
390 for ( sal_Int32 index
=0; index
< sModules
.getLength(); ++index
)
394 aName
.append(sModules
[index
]);
396 aArguments
.push_back( aName
.makeStringAndClear() );
398 handleErrorHandlerRequest( task::InteractionClassification_WARNING
,
399 ERRCODE_UUI_IO_MODULESIZEEXCEEDED
,
401 rRequest
->getContinuations(),
402 bObtainErrorStringOnly
,
408 document::ExoticFileLoadException aExoticFileLoadException
;
409 if (aAnyRequest
>>= aExoticFileLoadException
)
411 std::vector
< OUString
> aArguments
;
413 if( !aExoticFileLoadException
.URL
.isEmpty() )
415 aArguments
.push_back( aExoticFileLoadException
.URL
);
417 if( !aExoticFileLoadException
.FilterUIName
.isEmpty() )
419 aArguments
.push_back( aExoticFileLoadException
.FilterUIName
);
422 handleErrorHandlerRequest( task::InteractionClassification_WARNING
,
423 ERRCODE_UUI_IO_EXOTICFILEFORMAT
,
425 rRequest
->getContinuations(),
426 bObtainErrorStringOnly
,
432 ucb::NameClashException aNCException
;
433 if (aAnyRequest
>>= aNCException
)
435 ErrCode nErrorCode
= ERRCODE_UUI_IO_TARGETALREADYEXISTS
;
436 std::vector
< OUString
> aArguments
;
438 if( !aNCException
.Name
.isEmpty() )
440 nErrorCode
= ERRCODE_UUI_IO_ALREADYEXISTS
;
441 aArguments
.push_back( aNCException
.Name
);
444 handleErrorHandlerRequest( aNCException
.Classification
,
447 rRequest
->getContinuations(),
448 bObtainErrorStringOnly
,
454 ucb::UnsupportedNameClashException aUORequest
;
455 if (aAnyRequest
>>= aUORequest
)
458 uno::Reference
< task::XInteractionApprove
> xApprove
;
459 uno::Reference
< task::XInteractionDisapprove
> xDisapprove
;
461 rRequest
->getContinuations(), &xApprove
, &xDisapprove
);
463 if ( xApprove
.is() && xDisapprove
.is() )
465 std::vector
< OUString
> aArguments
;
466 handleErrorHandlerRequest( task::InteractionClassification_QUERY
,
467 ERRCODE_UUI_IO_UNSUPPORTEDOVERWRITE
,
469 rRequest
->getContinuations(),
470 bObtainErrorStringOnly
,
477 if ( handleInteractiveIOException( rRequest
,
478 bObtainErrorStringOnly
,
483 ucb::InteractiveAppException aAppException
;
484 if (aAnyRequest
>>= aAppException
)
486 std::vector
< OUString
> aArguments
;
487 handleErrorHandlerRequest( aAppException
.Classification
,
488 ErrCode(aAppException
.Code
),
490 rRequest
->getContinuations(),
491 bObtainErrorStringOnly
,
497 ucb::InteractiveNetworkException aNetworkException
;
498 if (aAnyRequest
>>= aNetworkException
)
501 std::vector
< OUString
> aArguments
;
502 ucb::InteractiveNetworkOffLineException aOffLineException
;
503 ucb::InteractiveNetworkResolveNameException aResolveNameException
;
504 ucb::InteractiveNetworkConnectException aConnectException
;
505 ucb::InteractiveNetworkReadException aReadException
;
506 ucb::InteractiveNetworkWriteException aWriteException
;
507 if (aAnyRequest
>>= aOffLineException
)
508 nErrorCode
= ERRCODE_INET_OFFLINE
;
509 else if (aAnyRequest
>>= aResolveNameException
)
511 nErrorCode
= ERRCODE_INET_NAME_RESOLVE
;
512 aArguments
.push_back(aResolveNameException
.Server
);
514 else if (aAnyRequest
>>= aConnectException
)
516 nErrorCode
= ERRCODE_INET_CONNECT
;
517 aArguments
.push_back(aConnectException
.Server
);
519 else if (aAnyRequest
>>= aReadException
)
521 nErrorCode
= ERRCODE_INET_READ
;
522 aArguments
.push_back(aReadException
.Diagnostic
);
524 else if (aAnyRequest
>>= aWriteException
)
526 nErrorCode
= ERRCODE_INET_WRITE
;
527 aArguments
.push_back(aWriteException
.Diagnostic
);
530 nErrorCode
= ERRCODE_INET_GENERAL
;
532 handleErrorHandlerRequest(aNetworkException
.Classification
,
535 rRequest
->getContinuations(),
536 bObtainErrorStringOnly
,
542 ucb::InteractiveWrongMediumException aWrongMediumException
;
543 if (aAnyRequest
>>= aWrongMediumException
)
545 sal_Int32 nMedium
= 0;
546 aWrongMediumException
.Medium
>>= nMedium
;
547 std::vector
< OUString
> aArguments
{ OUString::number(nMedium
+ 1) };
548 handleErrorHandlerRequest(aWrongMediumException
.Classification
,
549 ERRCODE_UUI_WRONGMEDIUM
,
551 rRequest
->getContinuations(),
552 bObtainErrorStringOnly
,
558 java::WrongJavaVersionException aWrongJavaVersionException
;
559 if (aAnyRequest
>>= aWrongJavaVersionException
)
562 std::vector
< OUString
> aArguments
;
563 if (aWrongJavaVersionException
.DetectedVersion
.isEmpty())
564 if (aWrongJavaVersionException
.LowestSupportedVersion
.isEmpty())
565 nErrorCode
= ERRCODE_UUI_WRONGJAVA
;
568 nErrorCode
= ERRCODE_UUI_WRONGJAVA_MIN
;
569 aArguments
.push_back(aWrongJavaVersionException
.LowestSupportedVersion
);
571 else if (aWrongJavaVersionException
.LowestSupportedVersion
.isEmpty())
573 nErrorCode
= ERRCODE_UUI_WRONGJAVA_VERSION
;
574 aArguments
.push_back(aWrongJavaVersionException
.DetectedVersion
);
578 nErrorCode
= ERRCODE_UUI_WRONGJAVA_VERSION_MIN
;
579 aArguments
.reserve(2);
580 aArguments
.push_back(aWrongJavaVersionException
.DetectedVersion
);
581 aArguments
.push_back(aWrongJavaVersionException
.LowestSupportedVersion
);
583 handleErrorHandlerRequest(task::InteractionClassification_ERROR
,
586 rRequest
->getContinuations(),
587 bObtainErrorStringOnly
,
593 configuration::backend::MergeRecoveryRequest aMergeRecoveryRequest
;
594 if (aAnyRequest
>>= aMergeRecoveryRequest
)
596 ErrCode nErrorCode
= aMergeRecoveryRequest
.IsRemovalRequest
597 ? ERRCODE_UUI_CONFIGURATION_BROKENDATA_WITHREMOVE
598 : ERRCODE_UUI_CONFIGURATION_BROKENDATA_NOREMOVE
;
600 std::vector
< OUString
> aArguments
{ aMergeRecoveryRequest
.ErrorLayerId
};
602 handleErrorHandlerRequest(task::InteractionClassification_ERROR
,
605 rRequest
->getContinuations(),
606 bObtainErrorStringOnly
,
612 configuration::backend::StratumCreationException
613 aStratumCreationException
;
615 if (aAnyRequest
>>= aStratumCreationException
)
617 const ErrCode nErrorCode
= ERRCODE_UUI_CONFIGURATION_BACKENDMISSING
;
619 OUString aStratum
= aStratumCreationException
.StratumData
;
620 if (aStratum
.isEmpty())
621 aStratum
= aStratumCreationException
.StratumService
;
623 std::vector
< OUString
> aArguments
{ aStratum
};
625 handleErrorHandlerRequest(task::InteractionClassification_ERROR
,
628 rRequest
->getContinuations(),
629 bObtainErrorStringOnly
,
635 xforms::InvalidDataOnSubmitException aInvalidDataOnSubmitException
;
636 if (aAnyRequest
>>= aInvalidDataOnSubmitException
)
638 const ErrCode nErrorCode
=
639 ERRCODE_UUI_INVALID_XFORMS_SUBMISSION_DATA
;
641 std::vector
< OUString
> aArguments
;
643 handleErrorHandlerRequest(task::InteractionClassification_QUERY
,
646 rRequest
->getContinuations(),
647 bObtainErrorStringOnly
,
653 ucb::InteractiveLockingLockedException aLLException
;
654 if (aAnyRequest
>>= aLLException
)
656 ErrCode nErrorCode
= aLLException
.SelfOwned
657 ? ERRCODE_UUI_LOCKING_LOCKED_SELF
: ERRCODE_UUI_LOCKING_LOCKED
;
658 std::vector
< OUString
> aArguments
{ aLLException
.Url
};
660 handleErrorHandlerRequest( aLLException
.Classification
,
663 rRequest
->getContinuations(),
664 bObtainErrorStringOnly
,
670 ucb::InteractiveLockingNotLockedException aLNLException
;
671 if (aAnyRequest
>>= aLNLException
)
673 std::vector
< OUString
> aArguments
{ aLNLException
.Url
};
675 handleErrorHandlerRequest( aLNLException
.Classification
,
676 ERRCODE_UUI_LOCKING_NOT_LOCKED
,
678 rRequest
->getContinuations(),
679 bObtainErrorStringOnly
,
685 ucb::InteractiveLockingLockExpiredException aLLEException
;
686 if (aAnyRequest
>>= aLLEException
)
688 std::vector
< OUString
> aArguments
{ aLLEException
.Url
};
690 handleErrorHandlerRequest( aLLEException
.Classification
,
691 ERRCODE_UUI_LOCKING_LOCK_EXPIRED
,
693 rRequest
->getContinuations(),
694 bObtainErrorStringOnly
,
700 document::BrokenPackageRequest aBrokenPackageRequest
;
701 if (aAnyRequest
>>= aBrokenPackageRequest
)
703 std::vector
< OUString
> aArguments
;
705 if( !aBrokenPackageRequest
.aName
.isEmpty() )
706 aArguments
.push_back( aBrokenPackageRequest
.aName
);
708 handleBrokenPackageRequest( aArguments
,
709 rRequest
->getContinuations(),
710 bObtainErrorStringOnly
,
716 task::ErrorCodeRequest aErrorCodeRequest
;
717 if (aAnyRequest
>>= aErrorCodeRequest
)
719 handleGenericErrorRequest( ErrCode(aErrorCodeRequest
.ErrCode
),
720 rRequest
->getContinuations(),
721 bObtainErrorStringOnly
,
727 task::ErrorCodeIOException aErrorCodeIOException
;
728 if (aAnyRequest
>>= aErrorCodeIOException
)
730 handleGenericErrorRequest( ErrCode(aErrorCodeIOException
.ErrCode
),
731 rRequest
->getContinuations(),
732 bObtainErrorStringOnly
,
738 loader::CannotActivateFactoryException aCannotActivateFactoryException
;
739 if (aAnyRequest
>>= aCannotActivateFactoryException
)
741 std::vector
< OUString
> aArguments
{ aCannotActivateFactoryException
.Message
};
743 handleErrorHandlerRequest( task::InteractionClassification_ERROR
,
744 ERRCODE_UUI_CANNOT_ACTIVATE_FACTORY
,
746 rRequest
->getContinuations(),
747 bObtainErrorStringOnly
,
754 // Handle requests which do not have a plain string representation.
756 if (!bObtainErrorStringOnly
)
758 ucb::AuthenticationFallbackRequest anAuthFallbackRequest
;
759 if ( aAnyRequest
>>= anAuthFallbackRequest
)
761 handleAuthFallbackRequest( anAuthFallbackRequest
.instructions
,
762 anAuthFallbackRequest
.url
, rRequest
->getContinuations() );
766 if ( handleAuthenticationRequest( rRequest
) )
769 if ( handleCertificateValidationRequest( rRequest
) )
772 ucb::NameClashResolveRequest aNameClashResolveRequest
;
773 if (aAnyRequest
>>= aNameClashResolveRequest
)
775 handleNameClashResolveRequest(aNameClashResolveRequest
,
776 rRequest
->getContinuations());
780 if ( handleMasterPasswordRequest( rRequest
) )
783 if ( handlePasswordRequest( rRequest
) )
786 if ( handleNoSuchFilterRequest( rRequest
) )
789 if ( handleFilterOptionsRequest( rRequest
) )
792 if ( handleLockedDocumentRequest( rRequest
) )
795 if ( handleChangedByOthersRequest( rRequest
) )
798 if ( handleLockFileProblemRequest( rRequest
) )
801 if ( handleReloadEditableRequest( rRequest
) )
804 task::DocumentMacroConfirmationRequest aMacroConfirmRequest
;
805 if (aAnyRequest
>>= aMacroConfirmRequest
)
807 handleMacroConfirmRequest(
808 aMacroConfirmRequest
.DocumentURL
,
809 aMacroConfirmRequest
.DocumentStorage
,
810 !aMacroConfirmRequest
.DocumentVersion
.isEmpty() ? aMacroConfirmRequest
.DocumentVersion
: ODFVER_013_TEXT
,
811 aMacroConfirmRequest
.DocumentSignatureInformation
,
812 rRequest
->getContinuations());
816 // Last chance: interaction handlers registered in the configuration
819 // typed InteractionHandlers (ooo.Interactions)
820 if ( handleTypedHandlerImplementations( rRequest
) )
823 // legacy configuration (ooo.ucb.InteractionHandlers)
824 if (tryOtherInteractionHandler( rRequest
))
831 catch( const uno::RuntimeException
& )
833 throw; // allowed to leave here
835 catch( const uno::Exception
& )
837 DBG_UNHANDLED_EXCEPTION("uui");
843 UUIInteractionHelper::getInteractionHandlerList(
844 InteractionHandlerDataList
&rdataList
)
848 uno::Reference
< lang::XMultiServiceFactory
> xConfigProv
=
849 configuration::theDefaultProvider::get( m_xContext
);
851 uno::Sequence
<uno::Any
> aArguments(comphelper::InitAnyPropertySequence(
853 {"nodepath", uno::Any(OUString("/org.openoffice.ucb.InteractionHandler/InteractionHandlers"))}
856 uno::Reference
< uno::XInterface
> xInterface(
857 xConfigProv
->createInstanceWithArguments(
858 "com.sun.star.configuration.ConfigurationAccess" , aArguments
) );
860 if ( !xInterface
.is() )
861 throw uno::RuntimeException("unable to instantiate config access");
863 uno::Reference
< container::XNameAccess
> xNameAccess(
864 xInterface
, uno::UNO_QUERY_THROW
);
865 const uno::Sequence
< OUString
> aElems
= xNameAccess
->getElementNames();
867 if ( aElems
.hasElements() )
869 uno::Reference
< container::XHierarchicalNameAccess
>
870 xHierNameAccess( xInterface
, uno::UNO_QUERY_THROW
);
872 // Iterate over children.
873 for ( const auto& rElem
: aElems
)
877 InteractionHandlerData aInfo
;
879 // Obtain service name.
880 OUString aKeyBuffer
= "['" + rElem
+ "']/ServiceName";
883 if ( !( xHierNameAccess
->getByHierarchicalName(
884 aKeyBuffer
) >>= aValue
) )
886 OSL_FAIL( "GetInteractionHandlerList - "
887 "Error getting item value!" );
891 aInfo
.ServiceName
= aValue
;
893 // Append info to list.
894 rdataList
.push_back( aInfo
);
896 catch ( container::NoSuchElementException
& )
898 // getByHierarchicalName
900 OSL_FAIL( "GetInteractionHandlerList - "
901 "caught NoSuchElementException!" );
906 catch ( uno::RuntimeException
const & )
910 catch ( uno::Exception
const & )
912 TOOLS_WARN_EXCEPTION( "uui", "GetInteractionHandlerList" );
916 const uno::Reference
< awt::XWindow
>&
917 UUIInteractionHelper::getParentXWindow() const
919 return m_xWindowParam
;
922 uno::Reference
< task::XInteractionHandler2
>
923 UUIInteractionHelper::getInteractionHandler() const
925 return InteractionHandler::createWithParentAndContext(
926 m_xContext
, m_xWindowParam
,
934 weld::Window
* pParent
,
935 OUString
const & rTitle
,
936 OUString
const & rMessage
,
937 VclMessageType eMessageType
)
939 SolarMutexGuard aGuard
;
941 std::unique_ptr
<weld::MessageDialog
> xBox(Application::CreateMessageDialog(pParent
, eMessageType
,
942 eMessageType
== VclMessageType::Question
? VclButtonsType::YesNo
: VclButtonsType::Ok
, rMessage
));
943 xBox
->set_title(rTitle
);
945 short nMessResult
= xBox
->run();
946 DialogMask aResult
= DialogMask::NONE
;
950 aResult
= DialogMask::ButtonsOk
;
953 aResult
= DialogMask::ButtonsCancel
;
956 aResult
= DialogMask::ButtonsYes
;
959 aResult
= DialogMask::ButtonsNo
;
968 NameClashResolveDialogResult
executeSimpleNameClashResolveDialog(weld::Window
*pParent
,
969 OUString
const & rTargetFolderURL
,
970 OUString
const & rClashingName
,
971 OUString
& rProposedNewName
,
972 bool bAllowOverwrite
)
974 std::locale aResLocale
= Translate::Create("uui");
975 NameClashDialog
aDialog(pParent
, aResLocale
, rTargetFolderURL
,
976 rClashingName
, rProposedNewName
, bAllowOverwrite
);
978 NameClashResolveDialogResult eResult
= static_cast<NameClashResolveDialogResult
>(aDialog
.run());
979 rProposedNewName
= aDialog
.getNewName();
986 UUIInteractionHelper::handleNameClashResolveRequest(
987 ucb::NameClashResolveRequest
const & rRequest
,
988 uno::Sequence
< uno::Reference
<
989 task::XInteractionContinuation
> > const & rContinuations
)
991 OSL_ENSURE(!rRequest
.TargetFolderURL
.isEmpty(),
992 "NameClashResolveRequest must not contain empty TargetFolderURL" );
994 OSL_ENSURE(!rRequest
.ClashingName
.isEmpty(),
995 "NameClashResolveRequest must not contain empty ClashingName" );
997 uno::Reference
< task::XInteractionAbort
> xAbort
;
998 uno::Reference
< ucb::XInteractionSupplyName
> xSupplyName
;
999 uno::Reference
< ucb::XInteractionReplaceExistingData
> xReplaceExistingData
;
1001 rContinuations
, &xAbort
, &xSupplyName
, &xReplaceExistingData
);
1003 OSL_ENSURE( xAbort
.is(),
1004 "NameClashResolveRequest must contain Abort continuation" );
1006 OSL_ENSURE( xSupplyName
.is(),
1007 "NameClashResolveRequest must contain SupplyName continuation" );
1009 NameClashResolveDialogResult eResult
= ABORT
;
1010 OUString
aProposedNewName( rRequest
.ProposedNewName
);
1012 uno::Reference
<awt::XWindow
> xParent
= getParentXWindow();
1013 eResult
= executeSimpleNameClashResolveDialog(Application::GetFrameWeld(xParent
),
1014 rRequest
.TargetFolderURL
,
1015 rRequest
.ClashingName
,
1017 xReplaceExistingData
.is());
1026 xSupplyName
->setName( aProposedNewName
);
1027 xSupplyName
->select();
1032 xReplaceExistingData
.is(),
1033 "Invalid NameClashResolveDialogResult: OVERWRITE - "
1034 "No ReplaceExistingData continuation available!" );
1035 xReplaceExistingData
->select();
1041 UUIInteractionHelper::handleGenericErrorRequest(
1043 uno::Sequence
< uno::Reference
<
1044 task::XInteractionContinuation
> > const & rContinuations
,
1045 bool bObtainErrorStringOnly
,
1046 bool & bHasErrorString
,
1047 OUString
& rErrorString
)
1049 if (bObtainErrorStringOnly
)
1051 bHasErrorString
= isInformationalErrorMessageRequest(rContinuations
);
1052 if (bHasErrorString
)
1054 OUString aErrorString
;
1055 ErrorHandler::GetErrorString(nErrorCode
, aErrorString
);
1056 rErrorString
= aErrorString
;
1061 uno::Reference
< task::XInteractionAbort
> xAbort
;
1062 uno::Reference
< task::XInteractionApprove
> xApprove
;
1063 getContinuations(rContinuations
, &xApprove
, &xAbort
);
1065 // Note: It's important to convert the transported long to the
1066 // required unsigned long value. Otherwise using as flag field
1068 ErrCode
nError(nErrorCode
);
1069 bool bWarning
= !nError
.IgnoreWarning();
1071 if ( nError
== ERRCODE_SFX_INCOMPLETE_ENCRYPTION
)
1073 // the security warning box needs a special title
1074 OUString aErrorString
;
1075 ErrorHandler::GetErrorString( nErrorCode
, aErrorString
);
1077 std::locale aResLocale
= Translate::Create("uui");
1078 OUString
aTitle( utl::ConfigManager::getProductName() );
1080 OUString aErrTitle
= Translate::get(STR_WARNING_INCOMPLETE_ENCRYPTION_TITLE
, aResLocale
);
1082 if ( !aTitle
.isEmpty() && !aErrTitle
.isEmpty() )
1084 aTitle
+= aErrTitle
;
1086 uno::Reference
<awt::XWindow
> xParent
= getParentXWindow();
1087 executeMessageBox(Application::GetFrameWeld(xParent
), aTitle
, aErrorString
, VclMessageType::Error
);
1091 uno::Reference
<awt::XWindow
> xParent
= getParentXWindow();
1092 ErrorHandler::HandleError(nErrorCode
, Application::GetFrameWeld(xParent
));
1095 if (xApprove
.is() && bWarning
)
1097 else if (xAbort
.is())
1103 UUIInteractionHelper::handleMacroConfirmRequest(
1104 const OUString
& aDocumentURL
,
1105 const uno::Reference
< embed::XStorage
>& xZipStorage
,
1106 const OUString
& aDocumentVersion
,
1107 const uno::Sequence
< security::DocumentSignatureInformation
>& aSignInfo
,
1108 uno::Sequence
< uno::Reference
< task::XInteractionContinuation
> > const &
1111 uno::Reference
< task::XInteractionAbort
> xAbort
;
1112 uno::Reference
< task::XInteractionApprove
> xApprove
;
1113 getContinuations( rContinuations
, &xApprove
, &xAbort
);
1115 bool bApprove
= false;
1117 bool bShowSignatures
= aSignInfo
.hasElements();
1118 uno::Reference
<awt::XWindow
> xParent
= getParentXWindow();
1119 MacroWarning
aWarning(Application::GetFrameWeld(xParent
), bShowSignatures
);
1121 aWarning
.SetDocumentURL(aDocumentURL
);
1122 if ( aSignInfo
.getLength() > 1 )
1124 aWarning
.SetStorage(xZipStorage
, aDocumentVersion
, aSignInfo
);
1126 else if ( aSignInfo
.getLength() == 1 )
1128 aWarning
.SetCertificate(aSignInfo
[0].Signer
);
1131 bApprove
= aWarning
.run() == RET_OK
;
1133 if ( bApprove
&& xApprove
.is() )
1135 else if ( xAbort
.is() )
1140 UUIInteractionHelper::handleBrokenPackageRequest(
1141 std::vector
< OUString
> const & rArguments
,
1142 uno::Sequence
< uno::Reference
< task::XInteractionContinuation
> > const &
1144 bool bObtainErrorStringOnly
,
1145 bool & bHasErrorString
,
1146 OUString
& rErrorString
)
1148 if (bObtainErrorStringOnly
)
1150 bHasErrorString
= isInformationalErrorMessageRequest(rContinuations
);
1151 if (!bHasErrorString
)
1155 uno::Reference
< task::XInteractionApprove
> xApprove
;
1156 uno::Reference
< task::XInteractionDisapprove
> xDisapprove
;
1157 uno::Reference
< task::XInteractionAbort
> xAbort
;
1158 getContinuations(rContinuations
, &xApprove
, &xDisapprove
, &xAbort
);
1161 if( xApprove
.is() && xDisapprove
.is() )
1163 nErrorCode
= ERRCODE_UUI_IO_BROKENPACKAGE
;
1165 else if ( xAbort
.is() )
1167 nErrorCode
= ERRCODE_UUI_IO_BROKENPACKAGE_CANTREPAIR
;
1174 std::locale aResLocale
= Translate::Create("uui");
1175 ErrorResource
aErrorResource(RID_UUI_ERRHDL
, aResLocale
);
1176 if (!aErrorResource
.getString(nErrorCode
, aMessage
))
1180 aMessage
= replaceMessageWithArguments( aMessage
, rArguments
);
1182 if (bObtainErrorStringOnly
)
1184 rErrorString
= aMessage
;
1188 VclMessageType eMessageType
;
1189 if( xApprove
.is() && xDisapprove
.is() )
1190 eMessageType
= VclMessageType::Question
;
1191 else if ( xAbort
.is() )
1192 eMessageType
= VclMessageType::Warning
;
1197 utl::ConfigManager::getProductName() +
1199 utl::ConfigManager::getProductVersion() );
1201 uno::Reference
<awt::XWindow
> xParent
= getParentXWindow();
1202 switch (executeMessageBox(Application::GetFrameWeld(xParent
), title
, aMessage
, eMessageType
))
1204 case DialogMask::ButtonsOk
:
1205 OSL_ENSURE( xAbort
.is(), "unexpected situation" );
1210 case DialogMask::ButtonsNo
:
1211 OSL_ENSURE(xDisapprove
.is(), "unexpected situation");
1212 if (xDisapprove
.is())
1213 xDisapprove
->select();
1216 case DialogMask::ButtonsYes
:
1217 OSL_ENSURE(xApprove
.is(), "unexpected situation");
1226 // ErrorResource Implementation
1227 bool ErrorResource::getString(ErrCode nErrorCode
, OUString
&rString
) const
1229 for (const std::pair
<TranslateId
, ErrCode
>* pStringArray
= m_pStringArray
; pStringArray
->first
; ++pStringArray
)
1231 if (nErrorCode
.StripWarningAndDynamic() == pStringArray
->second
.StripWarningAndDynamic())
1233 rString
= Translate::get(pStringArray
->first
, m_rResLocale
);
1240 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */