1*6d739b60SAndrew Rist /**************************************************************
2cdf0e10cSrcweir *
3*6d739b60SAndrew Rist * Licensed to the Apache Software Foundation (ASF) under one
4*6d739b60SAndrew Rist * or more contributor license agreements. See the NOTICE file
5*6d739b60SAndrew Rist * distributed with this work for additional information
6*6d739b60SAndrew Rist * regarding copyright ownership. The ASF licenses this file
7*6d739b60SAndrew Rist * to you under the Apache License, Version 2.0 (the
8*6d739b60SAndrew Rist * "License"); you may not use this file except in compliance
9*6d739b60SAndrew Rist * with the License. You may obtain a copy of the License at
10*6d739b60SAndrew Rist *
11*6d739b60SAndrew Rist * http://www.apache.org/licenses/LICENSE-2.0
12*6d739b60SAndrew Rist *
13*6d739b60SAndrew Rist * Unless required by applicable law or agreed to in writing,
14*6d739b60SAndrew Rist * software distributed under the License is distributed on an
15*6d739b60SAndrew Rist * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16*6d739b60SAndrew Rist * KIND, either express or implied. See the License for the
17*6d739b60SAndrew Rist * specific language governing permissions and limitations
18*6d739b60SAndrew Rist * under the License.
19*6d739b60SAndrew Rist *
20*6d739b60SAndrew Rist *************************************************************/
21*6d739b60SAndrew Rist
22*6d739b60SAndrew Rist
23cdf0e10cSrcweir
24cdf0e10cSrcweir // MARKER(update_precomp.py): autogen include statement, do not remove
25cdf0e10cSrcweir #include "precompiled_framework.hxx"
26cdf0e10cSrcweir
27cdf0e10cSrcweir //________________________________
28cdf0e10cSrcweir // my own includes
29cdf0e10cSrcweir #include <jobs/configaccess.hxx>
30cdf0e10cSrcweir #include <threadhelp/readguard.hxx>
31cdf0e10cSrcweir #include <threadhelp/writeguard.hxx>
32cdf0e10cSrcweir #include <threadhelp/resetableguard.hxx>
33cdf0e10cSrcweir #include <general.h>
34cdf0e10cSrcweir #include <services.h>
35cdf0e10cSrcweir
36cdf0e10cSrcweir //________________________________
37cdf0e10cSrcweir // interface includes
38cdf0e10cSrcweir #include <com/sun/star/beans/XPropertySet.hpp>
39cdf0e10cSrcweir #include <com/sun/star/beans/XMultiHierarchicalPropertySet.hpp>
40cdf0e10cSrcweir #include <com/sun/star/container/XNameAccess.hpp>
41cdf0e10cSrcweir #include <com/sun/star/beans/PropertyValue.hpp>
42cdf0e10cSrcweir #include <com/sun/star/util/XChangesBatch.hpp>
43cdf0e10cSrcweir
44cdf0e10cSrcweir //________________________________
45cdf0e10cSrcweir // includes of other projects
46cdf0e10cSrcweir #include <unotools/configpathes.hxx>
47cdf0e10cSrcweir #include <rtl/ustrbuf.hxx>
48cdf0e10cSrcweir
49cdf0e10cSrcweir //________________________________
50cdf0e10cSrcweir // namespace
51cdf0e10cSrcweir
52cdf0e10cSrcweir namespace framework{
53cdf0e10cSrcweir
54cdf0e10cSrcweir //________________________________
55cdf0e10cSrcweir // non exported const
56cdf0e10cSrcweir
57cdf0e10cSrcweir //________________________________
58cdf0e10cSrcweir // non exported definitions
59cdf0e10cSrcweir
60cdf0e10cSrcweir //________________________________
61cdf0e10cSrcweir // declarations
62cdf0e10cSrcweir
63cdf0e10cSrcweir //________________________________
64cdf0e10cSrcweir /**
65cdf0e10cSrcweir @short open the configuration of this job
66cdf0e10cSrcweir @descr We open the configuration of this job only. Not the whole package or the whole
67cdf0e10cSrcweir job set. We are interested on our own properties only.
68cdf0e10cSrcweir We set the opened configuration access as our member. So any following method,
69cdf0e10cSrcweir which needs cfg access, can use it. That prevent us against multiple open/close requests.
70cdf0e10cSrcweir But you can use this method to upgrade an already opened configuration too.
71cdf0e10cSrcweir
72cdf0e10cSrcweir @param eMode
73cdf0e10cSrcweir force opening of the configuration access in readonly or in read/write mode
74cdf0e10cSrcweir */
ConfigAccess(const css::uno::Reference<css::lang::XMultiServiceFactory> & xSMGR,const::rtl::OUString & sRoot)75cdf0e10cSrcweir ConfigAccess::ConfigAccess( /*IN*/ const css::uno::Reference< css::lang::XMultiServiceFactory >& xSMGR ,
76cdf0e10cSrcweir /*IN*/ const ::rtl::OUString& sRoot )
77cdf0e10cSrcweir : ThreadHelpBase( )
78cdf0e10cSrcweir , m_xSMGR ( xSMGR )
79cdf0e10cSrcweir , m_sRoot ( sRoot )
80cdf0e10cSrcweir , m_eMode ( E_CLOSED )
81cdf0e10cSrcweir {
82cdf0e10cSrcweir }
83cdf0e10cSrcweir
84cdf0e10cSrcweir //________________________________
85cdf0e10cSrcweir /**
86cdf0e10cSrcweir @short last chance to close an open configuration access point
87cdf0e10cSrcweir @descr In case our user forgot to close this configuration point
88cdf0e10cSrcweir in the right way, normaly he will run into some trouble -
89cdf0e10cSrcweir e.g. losing data.
90cdf0e10cSrcweir */
~ConfigAccess()91cdf0e10cSrcweir ConfigAccess::~ConfigAccess()
92cdf0e10cSrcweir {
93cdf0e10cSrcweir close();
94cdf0e10cSrcweir }
95cdf0e10cSrcweir
96cdf0e10cSrcweir //________________________________
97cdf0e10cSrcweir /**
98cdf0e10cSrcweir @short return the internal mode of this instance
99cdf0e10cSrcweir @descr May be the outside user need any information about successfully opened
100cdf0e10cSrcweir or closed config access point objects. He can control the internal mode to do so.
101cdf0e10cSrcweir
102cdf0e10cSrcweir @return The internal open state of this object.
103cdf0e10cSrcweir */
getMode() const104cdf0e10cSrcweir ConfigAccess::EOpenMode ConfigAccess::getMode() const
105cdf0e10cSrcweir {
106cdf0e10cSrcweir /* SAFE { */
107cdf0e10cSrcweir ReadGuard aReadLock(m_aLock);
108cdf0e10cSrcweir return m_eMode;
109cdf0e10cSrcweir /* } SAFE */
110cdf0e10cSrcweir }
111cdf0e10cSrcweir
112cdf0e10cSrcweir //________________________________
113cdf0e10cSrcweir /**
114cdf0e10cSrcweir @short open the configuration access in the specified mode
115cdf0e10cSrcweir @descr We set the opened configuration access as our member. So any following method,
116cdf0e10cSrcweir which needs cfg access, can use it. That prevent us against multiple open/close requests.
117cdf0e10cSrcweir But you can use this method to upgrade an already opened configuration too.
118cdf0e10cSrcweir It's possible to open a config access in READONLY mode first and "open" it at a second
119cdf0e10cSrcweir time within the mode READWRITE. Then we will upgrade it. Dowgrade will be possible too.
120cdf0e10cSrcweir
121cdf0e10cSrcweir But note: closing will be done explicitly by calling method close() ... not by
122cdf0e10cSrcweir downgrading with mode CLOSED!
123cdf0e10cSrcweir
124cdf0e10cSrcweir @param eMode
125cdf0e10cSrcweir force (re)opening of the configuration access in readonly or in read/write mode
126cdf0e10cSrcweir */
open(EOpenMode eMode)127cdf0e10cSrcweir void ConfigAccess::open( /*IN*/ EOpenMode eMode )
128cdf0e10cSrcweir {
129cdf0e10cSrcweir /* SAFE { */
130cdf0e10cSrcweir // We must lock the whole method to be shure, that nobody
131cdf0e10cSrcweir // outside uses our internal member m_xAccess!
132cdf0e10cSrcweir WriteGuard aWriteLock(m_aLock);
133cdf0e10cSrcweir
134cdf0e10cSrcweir // check if configuration is already open in the right mode.
135cdf0e10cSrcweir // By the way: Don't allow closing by using this method!
136cdf0e10cSrcweir if (
137cdf0e10cSrcweir (eMode !=E_CLOSED) &&
138cdf0e10cSrcweir (m_eMode!=eMode )
139cdf0e10cSrcweir )
140cdf0e10cSrcweir {
141cdf0e10cSrcweir // We have to close the old access point without any question here.
142cdf0e10cSrcweir // It will be open again using the new mode.
143cdf0e10cSrcweir // can be called without checks! It does the checks by itself ...
144cdf0e10cSrcweir // e.g. for already closed or not opened configuration.
145cdf0e10cSrcweir // Flushing of all made changes will be done here too.
146cdf0e10cSrcweir close();
147cdf0e10cSrcweir
148cdf0e10cSrcweir // create the configuration provider, which provides sub access points
149cdf0e10cSrcweir css::uno::Reference< css::lang::XMultiServiceFactory > xConfigProvider(m_xSMGR->createInstance(SERVICENAME_CFGPROVIDER), css::uno::UNO_QUERY);
150cdf0e10cSrcweir if (xConfigProvider.is())
151cdf0e10cSrcweir {
152cdf0e10cSrcweir css::beans::PropertyValue aParam;
153cdf0e10cSrcweir aParam.Name = DECLARE_ASCII("nodepath");
154cdf0e10cSrcweir aParam.Value <<= m_sRoot;
155cdf0e10cSrcweir
156cdf0e10cSrcweir css::uno::Sequence< css::uno::Any > lParams(1);
157cdf0e10cSrcweir lParams[0] <<= aParam;
158cdf0e10cSrcweir
159cdf0e10cSrcweir // open it
160cdf0e10cSrcweir try
161cdf0e10cSrcweir {
162cdf0e10cSrcweir if (eMode==E_READONLY)
163cdf0e10cSrcweir m_xConfig = xConfigProvider->createInstanceWithArguments(SERVICENAME_CFGREADACCESS , lParams);
164cdf0e10cSrcweir else
165cdf0e10cSrcweir if (eMode==E_READWRITE)
166cdf0e10cSrcweir m_xConfig = xConfigProvider->createInstanceWithArguments(SERVICENAME_CFGUPDATEACCESS, lParams);
167cdf0e10cSrcweir }
168cdf0e10cSrcweir catch(css::uno::Exception& ex)
169cdf0e10cSrcweir {
170cdf0e10cSrcweir (void) ex; // avoid warning
171cdf0e10cSrcweir LOG_WARNING("open config ...", U2B(ex.Message))
172cdf0e10cSrcweir }
173cdf0e10cSrcweir
174cdf0e10cSrcweir m_eMode = E_CLOSED;
175cdf0e10cSrcweir if (m_xConfig.is())
176cdf0e10cSrcweir m_eMode = eMode;
177cdf0e10cSrcweir }
178cdf0e10cSrcweir }
179cdf0e10cSrcweir
180cdf0e10cSrcweir aWriteLock.unlock();
181cdf0e10cSrcweir /* } SAFE */
182cdf0e10cSrcweir }
183cdf0e10cSrcweir
184cdf0e10cSrcweir //________________________________
185cdf0e10cSrcweir /**
186cdf0e10cSrcweir @short close the internal opened configuration access and flush all changes
187cdf0e10cSrcweir @descr It checks, if the given access is valid and react in the right way.
188cdf0e10cSrcweir It flushes all changes ... so nobody else must know this state.
189cdf0e10cSrcweir */
close()190cdf0e10cSrcweir void ConfigAccess::close()
191cdf0e10cSrcweir {
192cdf0e10cSrcweir /* SAFE { */
193cdf0e10cSrcweir // Lock the whole method, to be shure that nobody else uses our internal members
194cdf0e10cSrcweir // during this time.
195cdf0e10cSrcweir WriteGuard aWriteLock(m_aLock);
196cdf0e10cSrcweir
197cdf0e10cSrcweir // check already closed configuration
198cdf0e10cSrcweir if (m_xConfig.is())
199cdf0e10cSrcweir {
200cdf0e10cSrcweir css::uno::Reference< css::util::XChangesBatch > xFlush(m_xConfig, css::uno::UNO_QUERY);
201cdf0e10cSrcweir if (xFlush.is())
202cdf0e10cSrcweir xFlush->commitChanges();
203cdf0e10cSrcweir m_xConfig = css::uno::Reference< css::uno::XInterface >();
204cdf0e10cSrcweir m_eMode = E_CLOSED;
205cdf0e10cSrcweir }
206cdf0e10cSrcweir
207cdf0e10cSrcweir aWriteLock.unlock();
208cdf0e10cSrcweir /* } SAFE */
209cdf0e10cSrcweir }
210cdf0e10cSrcweir
211cdf0e10cSrcweir //________________________________
212cdf0e10cSrcweir /**
213cdf0e10cSrcweir @short provides an access to the internal wrapped configuration access
214cdf0e10cSrcweir @descr It's not allowed to safe this c++ (!) reference outside. You have
215cdf0e10cSrcweir to use it directly. Further you must use our public lock member m_aLock
216cdf0e10cSrcweir to synchronize your code with our internal structures and our interface
217cdf0e10cSrcweir methods. Acquire it before you call cfg() and release it afterwards immediatly.
218cdf0e10cSrcweir
219cdf0e10cSrcweir E.g.: ConfigAccess aAccess(...);
220cdf0e10cSrcweir ReadGuard aReadLock(aAccess.m_aLock);
221cdf0e10cSrcweir Reference< XPropertySet > xSet(aAccess.cfg(), UNO_QUERY);
222cdf0e10cSrcweir Any aProp = xSet->getPropertyValue("...");
223cdf0e10cSrcweir aReadLock.unlock();
224cdf0e10cSrcweir
225cdf0e10cSrcweir @attention During this time it's not allowed to call the methods open() or close()!
226cdf0e10cSrcweir Otherwhise you will change your own referenced config access. Anything will
227cdf0e10cSrcweir be possible then.
228cdf0e10cSrcweir
229cdf0e10cSrcweir @return A c++(!) reference to the uno instance of the configuration access point.
230cdf0e10cSrcweir */
cfg()231cdf0e10cSrcweir const css::uno::Reference< css::uno::XInterface >& ConfigAccess::cfg()
232cdf0e10cSrcweir {
233cdf0e10cSrcweir // must be synchronized from outside!
234cdf0e10cSrcweir // => no lock here ...
235cdf0e10cSrcweir return m_xConfig;
236cdf0e10cSrcweir }
237cdf0e10cSrcweir
238cdf0e10cSrcweir } // namespace framework
239