xref: /trunk/main/desktop/source/app/configinit.cxx (revision 2722cedd)
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 
25 // MARKER(update_precomp.py): autogen include statement, do not remove
26 #include "precompiled_desktop.hxx"
27 
28 #include "configinit.hxx"
29 
30 #include "desktop.hrc"
31 #include "app.hxx"
32 #include <comphelper/processfactory.hxx>
33 #include <uno/current_context.hxx>
34 #include <cppuhelper/implbase1.hxx>
35 #include <rtl/ustrbuf.hxx>
36 #include <osl/diagnose.h>
37 #include <stdio.h>
38 #include <map>
39 #include <com/sun/star/lang/ServiceNotRegisteredException.hpp>
40 #include <com/sun/star/configuration/CannotLoadConfigurationException.hpp>
41 #include <com/sun/star/configuration/InvalidBootstrapFileException.hpp>
42 #include <com/sun/star/configuration/backend/BackendSetupException.hpp>
43 #include <com/sun/star/configuration/backend/CannotConnectException.hpp>
44 
45 // ----------------------------------------------------------------------------
46 
47 namespace uno           = ::com::sun::star::uno;
48 namespace lang          = ::com::sun::star::lang;
49 namespace configuration = ::com::sun::star::configuration;
50 namespace backend       = ::com::sun::star::configuration::backend;
51 using rtl::OUString;
52 using uno::UNO_QUERY;
53 using desktop::Desktop;
54 
55 // ----------------------------------------------------------------------------
56 static char const CONFIGURATION_PROVIDER[]  = "com.sun.star.configuration.ConfigurationProvider";
57 
58 static char const CONFIGURATION_ERROR_HANDLER[]  = "com.sun.star.configuration.backend.InteractionHandler";
59 
60 // must be aligned with configmgr/source/misc/configinteractionhandler
61 static char const CONFIG_ERROR_HANDLER[] = "configuration.interaction-handler";
62 // ----------------------------------------------------------------------------
63 
64 // ----------------------------------------------------------------------------
65 #define arraysize( arr ) ( sizeof (arr)/sizeof *(arr) )
66 
67 typedef uno::Reference< lang::XMultiServiceFactory > ConfigurationProvider;
68 
69 #define OUSTRING( constascii ) OUString( RTL_CONSTASCII_USTRINGPARAM( constascii ) )
70 
71 #define OU2O( ustr, enc ) rtl::OUStringToOString( (ustr), RTL_TEXTENCODING_ ## enc )
72 
73 #define k_PROVIDER OUSTRING( CONFIGURATION_PROVIDER )
74 #define k_ERRORHANDLER OUSTRING( CONFIGURATION_ERROR_HANDLER )
75 // ----------------------------------------------------------------------------
76 // Get a message string securely. There is a fallback string if the resource
77 // is not available. Adapted from Desktop::GetMsgString()
78 
getMsgString(sal_uInt16 nId,char const * aFallBackMsg)79 OUString getMsgString( sal_uInt16 nId, char const * aFallBackMsg )
80 {
81     ResMgr* pResMgr = Desktop::GetDesktopResManager();
82     if ( !pResMgr || !nId )
83         return OUString::createFromAscii(aFallBackMsg);
84     else
85         return OUString( String(ResId( nId, *pResMgr )));
86 }
87 // ----------------------------------------------------------------------------
88 /** Creates the normal configuration provider.
89 
90 */
91 static
createDefaultConfigurationProvider()92 ConfigurationProvider createDefaultConfigurationProvider( )
93 {
94     uno::Reference< lang::XMultiServiceFactory > xServiceManager = ::comphelper::getProcessServiceFactory();
95 
96     OSL_ENSURE( xServiceManager.is(),"No ServiceManager set for CreateApplicationConfigurationProvider");
97 
98     ConfigurationProvider xProvider;
99 
100     if (xServiceManager.is())
101     {
102 
103             xProvider.set( xServiceManager->createInstance(k_PROVIDER),  UNO_QUERY);
104     }
105 
106     if (!xProvider.is())
107     {
108         OUString const sMsg = OUSTRING("Service \"") + k_PROVIDER +
109                                 OUSTRING("\" is not available at the service manager.");
110 
111         throw lang::ServiceNotRegisteredException(sMsg, xServiceManager);
112     }
113 
114     return xProvider;
115 }
116 // ----------------------------------------------------------------------------
117 /// @attention this method must be called from a catch statement!
handleGeneralException(uno::Exception & aException,const rtl::OUString & aMessage)118 static void handleGeneralException(uno::Exception& aException,
119                                    const rtl::OUString& aMessage)
120 {
121     aException.Message = aMessage ;
122     throw ;
123 }
124 // ----------------------------------------------------------------------------
125 
CreateApplicationConfigurationProvider()126 uno::Reference< lang::XMultiServiceFactory > CreateApplicationConfigurationProvider( )
127 {
128     uno::Reference< lang::XMultiServiceFactory > xProvider;
129 
130     try
131     {
132         xProvider = createDefaultConfigurationProvider( );
133     }
134     catch (configuration::InvalidBootstrapFileException & exception)
135     {
136         handleGeneralException(exception,
137                 getMsgString( STR_CONFIG_ERR_SETTINGS_INCOMPLETE,
138                             "The startup settings for your configuration settings are incomplete. "));
139     }
140      catch (backend::CannotConnectException & exception)
141     {
142         handleGeneralException(exception,
143                 getMsgString( STR_CONFIG_ERR_CANNOT_CONNECT,
144                             "A connection to your configuration settings could not be established. "));
145     }
146     catch (backend::BackendSetupException & exception)
147     {
148         handleGeneralException(exception,
149                 getMsgString( STR_CONFIG_ERR_CANNOT_CONNECT,
150                             "A connection to your configuration settings could not be established. "));
151     }
152     catch (configuration::CannotLoadConfigurationException & exception)
153     {
154         handleGeneralException(exception,
155                 getMsgString( STR_CONFIG_ERR_CANNOT_CONNECT,
156                             "A connection to your configuration settings could not be established. "));
157     }
158     catch (uno::Exception & exception)
159     {
160         handleGeneralException(exception,
161                 getMsgString( STR_CONFIG_ERR_ACCESS_GENERAL,
162                             "A general error occurred while accessing your configuration settings."));
163     }
164 
165 
166     return xProvider ;
167 }
168 // ----------------------------------------------------------------------------
169 
170 
171 
172 
173 // ----------------------------------------------------------------------------
174 // ----------------------------------------------------------------------------
175 // ConfigurationErrorHandler
176 // ----------------------------------------------------------------------------
177 
178 namespace
179 {
180     typedef uno::Reference< uno::XCurrentContext > CurrentContext;
181     class SimpleCurrentContext : public cppu::WeakImplHelper1< uno::XCurrentContext >
182     {
183         CurrentContext m_xChainedContext;
184     public:
185         explicit
SimpleCurrentContext(const CurrentContext & xChainedContext)186         SimpleCurrentContext(const CurrentContext & xChainedContext)
187         : m_xChainedContext(xChainedContext)
188         {}
189 
install()190         void install()      { uno::setCurrentContext(this); }
deinstall()191         void deinstall()    { uno::setCurrentContext(m_xChainedContext); }
192 
getChainedValueByName(OUString const & aName) const193         uno::Any getChainedValueByName( OUString const & aName) const
194         {
195             return m_xChainedContext.is()
196                             ? m_xChainedContext->getValueByName(aName)
197                             : uno::Any();
198         }
199 
200         // XCurrentContext
201         virtual uno::Any SAL_CALL
202             getValueByName( OUString const & aName)
203                 throw (uno::RuntimeException);
204     };
205 
206     uno::Any SAL_CALL
getValueByName(OUString const & aName)207         SimpleCurrentContext::getValueByName( OUString const & aName)
208             throw (uno::RuntimeException)
209     {
210         return getChainedValueByName(aName);
211     }
212 
213 }
214 
215 // ----------------------------------------------------------------------------
216 class ConfigurationErrorHandler::Context : public SimpleCurrentContext
217 {
218 public:
Context()219     Context()
220     : SimpleCurrentContext( uno::getCurrentContext() )
221     {
222     }
223 
~Context()224     ~Context()
225     {
226     }
227 
228     // XCurrentContext
229     virtual uno::Any SAL_CALL
230         getValueByName( OUString const & aName)
231             throw (uno::RuntimeException);
232 
233 private:
234     InteractionHandler  m_xHandler;
235 };
236 
237 //------------------------------------------------------------------------------
getValueByName(OUString const & aName)238 uno::Any SAL_CALL ConfigurationErrorHandler::Context::getValueByName( OUString const & aName)
239         throw (uno::RuntimeException)
240 {
241     if ( aName.equalsAscii( CONFIG_ERROR_HANDLER ) )
242     {
243         if ( !m_xHandler.is() )
244             m_xHandler = ConfigurationErrorHandler::getDefaultInteractionHandler();
245         return uno::Any( m_xHandler );
246     }
247     return SimpleCurrentContext::getValueByName( aName );
248 }
249 
250 //------------------------------------------------------------------------------
~ConfigurationErrorHandler()251 ConfigurationErrorHandler::~ConfigurationErrorHandler()
252 {
253     deactivate();
254 }
255 
256 //------------------------------------------------------------------------------
257 /// installs the handler into the current context
activate()258 void ConfigurationErrorHandler::activate()
259 {
260     if (!m_pContext)
261     {
262         m_pContext = new Context;
263         m_pContext->acquire();
264     }
265     m_pContext->install();
266 }
267 
268 //------------------------------------------------------------------------------
269 /// deinstalls the handler from the current context, restoring the previous context
deactivate()270 void ConfigurationErrorHandler::deactivate()
271 {
272     if (m_pContext)
273     {
274         m_pContext->deinstall();
275         m_pContext->release();
276         m_pContext = 0;
277     }
278 }
279 //------------------------------------------------------------------------------
280 
getDefaultInteractionHandler()281 ConfigurationErrorHandler::InteractionHandler ConfigurationErrorHandler::getDefaultInteractionHandler()
282 {
283     uno::Reference< lang::XMultiServiceFactory > xServiceManager = ::comphelper::getProcessServiceFactory();
284 
285     OSL_ENSURE( xServiceManager.is(),"No ServiceManager set for ConfigurationErrorHandler");
286 
287     InteractionHandler xHandler;
288 
289     if (xServiceManager.is())
290     {
291         xHandler.set( xServiceManager->createInstance(k_ERRORHANDLER), UNO_QUERY );
292     }
293 
294     return xHandler;
295 }
296 //------------------------------------------------------------------------------
297 
298 
299 
300