1 /**************************************************************
2  *
3  * Licensed to the Apache Software Foundation (ASF) under one
4  * or more contributor license agreements.  See the NOTICE file
5  * distributed with this work for additional information
6  * regarding copyright ownership.  The ASF licenses this file
7  * to you under the Apache License, Version 2.0 (the
8  * "License"); you may not use this file except in compliance
9  * with the License.  You may obtain a copy of the License at
10  *
11  *   http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing,
14  * software distributed under the License is distributed on an
15  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16  * KIND, either express or implied.  See the License for the
17  * specific language governing permissions and limitations
18  * under the License.
19  *
20  *************************************************************/
21 
22 
23 
24 // MARKER(update_precomp.py): autogen include statement, do not remove
25 #include "precompiled_ucbhelper.hxx"
26 #include <ucbhelper/registerucb.hxx>
27 #include <com/sun/star/lang/XMultiServiceFactory.hpp>
28 #include <com/sun/star/ucb/XContentProviderManager.hpp>
29 #include <com/sun/star/ucb/XParameterizedContentProvider.hpp>
30 #include <com/sun/star/ucb/XContentProviderFactory.hpp>
31 #include <com/sun/star/uno/RuntimeException.hpp>
32 
33 #include "osl/diagnose.h"
34 
35 using namespace com::sun::star;
36 
37 namespace ucbhelper {
38 
39 //============================================================================
40 //
41 //  registerAtUcb
42 //
43 //============================================================================
44 
45 bool
registerAtUcb(uno::Reference<ucb::XContentProviderManager> const & rManager,uno::Reference<lang::XMultiServiceFactory> const & rServiceFactory,rtl::OUString const & rName,rtl::OUString const & rArguments,rtl::OUString const & rTemplate,ContentProviderRegistrationInfo * pInfo)46 registerAtUcb(
47     uno::Reference< ucb::XContentProviderManager > const & rManager,
48 	uno::Reference< lang::XMultiServiceFactory > const & rServiceFactory,
49 	rtl::OUString const & rName,
50 	rtl::OUString const & rArguments,
51 	rtl::OUString const & rTemplate,
52 	ContentProviderRegistrationInfo * pInfo)
53 	throw (uno::RuntimeException)
54 {
55 	OSL_ENSURE(rServiceFactory.is(),
56 			   "ucb::registerAtUcb(): No service factory");
57 
58 	bool bNoProxy
59 		= rArguments.compareToAscii(RTL_CONSTASCII_STRINGPARAM("{noproxy}"))
60 		      == 0;
61 	rtl::OUString
62 		aProviderArguments(bNoProxy ?
63 						       rArguments.
64 						           copy(RTL_CONSTASCII_LENGTH("{noproxy}")) :
65 						       rArguments);
66 
67 	// First, try to instantiate proxy for provider:
68 	uno::Reference< ucb::XContentProvider > xProvider;
69 	if (!bNoProxy)
70 	{
71 		uno::Reference< ucb::XContentProviderFactory > xProxyFactory;
72 		try
73 		{
74 			xProxyFactory
75 				= uno::Reference< ucb::XContentProviderFactory >(
76 					  rServiceFactory->
77 				          createInstance(
78 							  rtl::OUString(
79 								  RTL_CONSTASCII_USTRINGPARAM(
80 							"com.sun.star.ucb.ContentProviderProxyFactory"))),
81 					  uno::UNO_QUERY);
82 		}
83 		catch (uno::Exception const &) {}
84 		OSL_ENSURE(xProxyFactory.is(), "No ContentProviderProxyFactory");
85 		if (xProxyFactory.is())
86 			xProvider = xProxyFactory->createContentProvider(rName);
87 	}
88 
89 	// Then, try to instantiate provider directly:
90 	if (!xProvider.is())
91 		try
92 		{
93 			xProvider = uno::Reference< ucb::XContentProvider >(
94 				            rServiceFactory->createInstance(rName),
95 							uno::UNO_QUERY);
96 		}
97 		catch (uno::RuntimeException const &) { throw; }
98 		catch (uno::Exception const &) {}
99 
100 	uno::Reference< ucb::XContentProvider >
101 		xOriginalProvider(xProvider);
102 	uno::Reference< ucb::XParameterizedContentProvider >
103 		xParameterized(xProvider, uno::UNO_QUERY);
104 	if (xParameterized.is())
105 	{
106 		uno::Reference< ucb::XContentProvider > xInstance;
107 		try
108 		{
109 			xInstance = xParameterized->registerInstance(rTemplate,
110 														 aProviderArguments,
111 														 true);
112 				//@@@ if this call replaces an old instance, the commit-or-
113 				// rollback code below will not work
114 		}
115 		catch (lang::IllegalArgumentException const &) {}
116 
117 		if (xInstance.is())
118 			xProvider = xInstance;
119 	}
120 
121 	bool bSuccess = false;
122 	if (rManager.is() && xProvider.is())
123 		try
124 		{
125 			rManager->registerContentProvider(xProvider, rTemplate, true);
126 			bSuccess = true;
127 		}
128 		catch (ucb::DuplicateProviderException const &)
129 		{
130 			if (xParameterized.is())
131 				try
132 				{
133 					xParameterized->deregisterInstance(rTemplate,
134 													   aProviderArguments);
135 				}
136 				catch (lang::IllegalArgumentException const &) {}
137 		}
138 		catch (...)
139 		{
140 			if (xParameterized.is())
141 				try
142 				{
143 					xParameterized->deregisterInstance(rTemplate,
144 													   aProviderArguments);
145 				}
146 				catch (lang::IllegalArgumentException const &) {}
147 				catch (uno::RuntimeException const &) {}
148 			throw;
149 		}
150 
151 	if (bSuccess && pInfo)
152 	{
153 		pInfo->m_xProvider = xOriginalProvider;
154 		pInfo->m_aArguments = aProviderArguments;
155 		pInfo->m_aTemplate = rTemplate;
156 	}
157 	return bSuccess;
158 }
159 
160 }
161