update dev300-m58
[ooovba.git] / svx / source / form / dataaccessdescriptor.cxx
blobdc122712211498573603641d07782f19961ea8d4
1 /*************************************************************************
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * Copyright 2008 by Sun Microsystems, Inc.
7 * OpenOffice.org - a multi-platform office productivity suite
9 * $RCSfile: dataaccessdescriptor.cxx,v $
10 * $Revision: 1.17 $
12 * This file is part of OpenOffice.org.
14 * OpenOffice.org is free software: you can redistribute it and/or modify
15 * it under the terms of the GNU Lesser General Public License version 3
16 * only, as published by the Free Software Foundation.
18 * OpenOffice.org is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU Lesser General Public License version 3 for more details
22 * (a copy is included in the LICENSE file that accompanied this code).
24 * You should have received a copy of the GNU Lesser General Public License
25 * version 3 along with OpenOffice.org. If not, see
26 * <http://www.openoffice.org/license.html>
27 * for a copy of the LGPLv3 License.
29 ************************************************************************/
31 // MARKER(update_precomp.py): autogen include statement, do not remove
32 #include "precompiled_svx.hxx"
33 #include <svx/dataaccessdescriptor.hxx>
34 #include <comphelper/stl_types.hxx>
35 #include <comphelper/propertysetinfo.hxx>
36 #include <comphelper/genericpropertyset.hxx>
37 #include <osl/diagnose.h>
38 #include <com/sun/star/sdbc/XConnection.hpp>
39 #include <com/sun/star/ucb/XContent.hpp>
40 #include <com/sun/star/beans/PropertyAttribute.hpp>
41 #include <tools/urlobj.hxx>
43 //........................................................................
44 namespace svx
46 //........................................................................
48 using namespace ::com::sun::star::uno;
49 using namespace ::com::sun::star::sdbc;
50 using namespace ::com::sun::star::beans;
51 using namespace ::com::sun::star::ucb;
52 using namespace ::comphelper;
54 #define CONST_CHAR( propname ) propname, sizeof(propname) - 1
56 #ifndef SVX_LIGHT
57 //====================================================================
58 //= ODADescriptorImpl
59 //====================================================================
60 class ODADescriptorImpl
62 protected:
63 sal_Bool m_bSetOutOfDate : 1;
64 sal_Bool m_bSequenceOutOfDate : 1;
66 public:
67 typedef ::std::map< DataAccessDescriptorProperty, Any > DescriptorValues;
68 DescriptorValues m_aValues;
69 Sequence< PropertyValue > m_aAsSequence;
70 Reference< XPropertySet > m_xAsSet;
72 typedef ::std::map< ::rtl::OUString, PropertyMapEntry* > MapString2PropertyEntry;
74 public:
75 ODADescriptorImpl();
76 ODADescriptorImpl(const ODADescriptorImpl& _rSource);
78 void invalidateExternRepresentations();
80 void updateSequence();
81 void updateSet();
83 /** builds the descriptor from a property value sequence
84 @return <TRUE/>
85 if and only if the sequence contained valid properties only
87 sal_Bool buildFrom( const Sequence< PropertyValue >& _rValues );
89 /** builds the descriptor from a property set
90 @return <TRUE/>
91 if and only if the set contained valid properties only
93 sal_Bool buildFrom( const Reference< XPropertySet >& _rValues );
95 protected:
96 static PropertyValue buildPropertyValue( const DescriptorValues::const_iterator& _rPos );
97 static const MapString2PropertyEntry& getPropertyMap( );
98 static PropertyMapEntry* getPropertyMapEntry( const DescriptorValues::const_iterator& _rPos );
101 //--------------------------------------------------------------------
102 ODADescriptorImpl::ODADescriptorImpl()
103 :m_bSetOutOfDate(sal_True)
104 ,m_bSequenceOutOfDate(sal_True)
108 //--------------------------------------------------------------------
109 ODADescriptorImpl::ODADescriptorImpl(const ODADescriptorImpl& _rSource)
110 :m_bSetOutOfDate( _rSource.m_bSetOutOfDate )
111 ,m_bSequenceOutOfDate( _rSource.m_bSequenceOutOfDate )
112 ,m_aValues( _rSource.m_aValues )
114 if (!m_bSetOutOfDate)
115 m_xAsSet = _rSource.m_xAsSet;
116 if (!m_bSequenceOutOfDate)
117 m_aAsSequence = _rSource.m_aAsSequence;
120 //--------------------------------------------------------------------
121 sal_Bool ODADescriptorImpl::buildFrom( const Sequence< PropertyValue >& _rValues )
123 const MapString2PropertyEntry& rProperties = getPropertyMap();
125 sal_Bool bValidPropsOnly = sal_True;
127 // loop through the sequence, and fill our m_aValues
128 const PropertyValue* pValues = _rValues.getConstArray();
129 const PropertyValue* pValuesEnd = pValues + _rValues.getLength();
130 for (;pValues != pValuesEnd; ++pValues)
132 MapString2PropertyEntry::const_iterator aPropPos = rProperties.find( pValues->Name );
133 if ( aPropPos != rProperties.end() )
135 DataAccessDescriptorProperty eProperty = (DataAccessDescriptorProperty)aPropPos->second->mnHandle;
136 m_aValues[eProperty] = pValues->Value;
138 else
139 // unknown property
140 bValidPropsOnly = sal_False;
143 if (bValidPropsOnly)
145 m_aAsSequence = _rValues;
146 m_bSequenceOutOfDate = sal_False;
148 else
149 m_bSequenceOutOfDate = sal_True;
151 return bValidPropsOnly;
154 //--------------------------------------------------------------------
155 sal_Bool ODADescriptorImpl::buildFrom( const Reference< XPropertySet >& _rxValues )
157 Reference< XPropertySetInfo > xPropInfo;
158 if (_rxValues.is())
159 xPropInfo = _rxValues->getPropertySetInfo();
160 if (!xPropInfo.is())
162 OSL_ENSURE(sal_False, "ODADescriptorImpl::buildFrom: invalid property set!");
163 return sal_False;
166 // build a PropertyValue sequence with the current values
167 Sequence< Property > aProperties = xPropInfo->getProperties();
168 const Property* pProperty = aProperties.getConstArray();
169 const Property* pPropertyEnd = pProperty + aProperties.getLength();
171 Sequence< PropertyValue > aValues(aProperties.getLength());
172 PropertyValue* pValues = aValues.getArray();
174 for (;pProperty != pPropertyEnd; ++pProperty, ++pValues)
176 pValues->Name = pProperty->Name;
177 pValues->Value = _rxValues->getPropertyValue(pProperty->Name);
180 sal_Bool bValidPropsOnly = buildFrom(aValues);
181 if (bValidPropsOnly)
183 m_xAsSet = _rxValues;
184 m_bSetOutOfDate = sal_False;
186 else
187 m_bSetOutOfDate = sal_True;
189 return bValidPropsOnly;
192 //--------------------------------------------------------------------
193 void ODADescriptorImpl::invalidateExternRepresentations()
195 m_bSetOutOfDate = sal_True;
196 m_bSequenceOutOfDate = sal_True;
199 //--------------------------------------------------------------------
200 const ODADescriptorImpl::MapString2PropertyEntry& ODADescriptorImpl::getPropertyMap( )
202 // the properties we know
203 static MapString2PropertyEntry s_aProperties;
204 if ( s_aProperties.empty() )
206 static PropertyMapEntry s_aDesriptorProperties[] =
208 { CONST_CHAR("ActiveConnection"), daConnection, &::getCppuType( static_cast< Reference< XConnection >* >(NULL) ), PropertyAttribute::TRANSIENT, 0 },
209 { CONST_CHAR("BookmarkSelection"), daBookmarkSelection, &::getBooleanCppuType( ), PropertyAttribute::TRANSIENT, 0 },
210 { CONST_CHAR("Column"), daColumnObject, &::getCppuType( static_cast< Reference< XPropertySet >* >(NULL) ), PropertyAttribute::TRANSIENT, 0 },
211 { CONST_CHAR("ColumnName"), daColumnName, &::getCppuType( static_cast< ::rtl::OUString* >(NULL) ), PropertyAttribute::TRANSIENT, 0 },
212 { CONST_CHAR("Command"), daCommand, &::getCppuType( static_cast< ::rtl::OUString* >(NULL) ), PropertyAttribute::TRANSIENT, 0 },
213 { CONST_CHAR("CommandType"), daCommandType, &::getCppuType( static_cast< sal_Int32* >(NULL) ), PropertyAttribute::TRANSIENT, 0 },
214 { CONST_CHAR("Component"), daComponent, &::getCppuType( static_cast< Reference< XContent >* >(NULL) ), PropertyAttribute::TRANSIENT, 0 },
215 { CONST_CHAR("ConnectionResource"), daConnectionResource, &::getCppuType( static_cast< ::rtl::OUString* >(NULL) ), PropertyAttribute::TRANSIENT, 0 },
216 { CONST_CHAR("Cursor"), daCursor, &::getCppuType( static_cast< Reference< XResultSet>* >(NULL) ), PropertyAttribute::TRANSIENT, 0 },
217 { CONST_CHAR("DataSourceName"), daDataSource, &::getCppuType( static_cast< ::rtl::OUString* >(NULL) ), PropertyAttribute::TRANSIENT, 0 },
218 { CONST_CHAR("DatabaseLocation"), daDatabaseLocation, &::getCppuType( static_cast< ::rtl::OUString* >(NULL) ), PropertyAttribute::TRANSIENT, 0 },
219 { CONST_CHAR("EscapeProcessing"), daEscapeProcessing, &::getBooleanCppuType( ), PropertyAttribute::TRANSIENT, 0 },
220 { CONST_CHAR("Filter"), daFilter, &::getCppuType( static_cast< ::rtl::OUString* >(NULL) ), PropertyAttribute::TRANSIENT, 0 },
221 { CONST_CHAR("Selection"), daSelection, &::getCppuType( static_cast< Sequence< Any >* >(NULL) ), PropertyAttribute::TRANSIENT, 0 },
222 { NULL, 0, 0, NULL, 0, 0 }
225 PropertyMapEntry* pEntry = s_aDesriptorProperties;
226 while ( pEntry->mpName )
228 s_aProperties[ ::rtl::OUString::createFromAscii( pEntry->mpName ) ] = pEntry;
229 ++pEntry;
233 return s_aProperties;
236 //--------------------------------------------------------------------
237 PropertyMapEntry* ODADescriptorImpl::getPropertyMapEntry( const DescriptorValues::const_iterator& _rPos )
239 const MapString2PropertyEntry& rProperties = getPropertyMap();
241 sal_Int32 nNeededHandle = (sal_Int32)(_rPos->first);
243 for ( MapString2PropertyEntry::const_iterator loop = rProperties.begin();
244 loop != rProperties.end();
245 ++loop
248 if ( nNeededHandle == loop->second->mnHandle )
249 return loop->second;
251 throw RuntimeException();
254 //--------------------------------------------------------------------
255 PropertyValue ODADescriptorImpl::buildPropertyValue( const DescriptorValues::const_iterator& _rPos )
257 // the map entry
258 PropertyMapEntry* pProperty = getPropertyMapEntry( _rPos );
260 // build the property value
261 PropertyValue aReturn;
262 aReturn.Name = ::rtl::OUString( pProperty->mpName, pProperty->mnNameLen, RTL_TEXTENCODING_ASCII_US );
263 aReturn.Handle = pProperty->mnHandle;
264 aReturn.Value = _rPos->second;
265 aReturn.State = PropertyState_DIRECT_VALUE;
267 // outta here
268 return aReturn;
271 //--------------------------------------------------------------------
272 void ODADescriptorImpl::updateSequence()
274 if (!m_bSequenceOutOfDate)
275 return;
277 m_aAsSequence.realloc(m_aValues.size());
278 PropertyValue* pValue = m_aAsSequence.getArray();
280 // loop through all our values
281 for ( DescriptorValues::const_iterator aLoop = m_aValues.begin();
282 aLoop != m_aValues.end();
283 ++aLoop, ++pValue
286 *pValue = buildPropertyValue(aLoop);
289 // don't need to rebuild next time
290 m_bSequenceOutOfDate = sal_False;
293 //--------------------------------------------------------------------
294 void ODADescriptorImpl::updateSet()
296 if (!m_bSetOutOfDate)
297 return;
299 // will be the current values
300 Sequence< PropertyValue > aValuesToSet(m_aValues.size());
301 PropertyValue* pValuesToSet = aValuesToSet.getArray();
303 // build a new property set info
304 PropertySetInfo* pPropSetInfo = new PropertySetInfo;
306 // loop through all our values
307 for ( DescriptorValues::const_iterator aLoop = m_aValues.begin();
308 aLoop != m_aValues.end();
309 ++aLoop, ++pValuesToSet
312 PropertyMapEntry* pMapEntry = getPropertyMapEntry( aLoop );
313 pPropSetInfo->add( pMapEntry, 1 );
315 *pValuesToSet = buildPropertyValue(aLoop);
318 // create the generic set
319 m_xAsSet = GenericPropertySet_CreateInstance( pPropSetInfo );
321 // no we have the set, still need to set the current values
322 const PropertyValue* pSetValues = aValuesToSet.getConstArray();
323 const PropertyValue* pSetValuesEnd = pSetValues + aValuesToSet.getLength();
324 for (; pSetValues != pSetValuesEnd; ++pSetValues)
325 m_xAsSet->setPropertyValue(pSetValues->Name, pSetValues->Value);
327 // don't need to rebuild next time
328 m_bSetOutOfDate = sal_True;
330 #endif
332 //====================================================================
333 //= ODataAccessDescriptor
334 //====================================================================
335 //--------------------------------------------------------------------
336 ODataAccessDescriptor::ODataAccessDescriptor()
337 #ifndef SVX_LIGHT
338 :m_pImpl(new ODADescriptorImpl)
339 #else
340 :m_pImpl(NULL)
341 #endif
345 //--------------------------------------------------------------------
346 ODataAccessDescriptor::ODataAccessDescriptor( const ODataAccessDescriptor& _rSource )
347 #ifndef SVX_LIGHT
348 :m_pImpl(new ODADescriptorImpl(*_rSource.m_pImpl))
349 #else
350 :m_pImpl(NULL)
351 #endif
355 //--------------------------------------------------------------------
356 const ODataAccessDescriptor& ODataAccessDescriptor::operator=(const ODataAccessDescriptor& _rSource)
358 #ifndef SVX_LIGHT
359 delete m_pImpl;
360 m_pImpl = new ODADescriptorImpl(*_rSource.m_pImpl);
361 #else
362 OSL_ENSURE(sal_False, "ODataAccessDescriptor::operator=: not available in the SVX_LIGHT version!");
363 #endif
364 return *this;
367 //--------------------------------------------------------------------
368 ODataAccessDescriptor::ODataAccessDescriptor( const Reference< XPropertySet >& _rValues )
369 #ifndef SVX_LIGHT
370 :m_pImpl(new ODADescriptorImpl)
371 #else
372 :m_pImpl(NULL)
373 #endif
375 #ifndef SVX_LIGHT
376 m_pImpl->buildFrom(_rValues);
377 #else
378 OSL_ENSURE(sal_False, "ODataAccessDescriptor::ODataAccessDescriptor: not available in the SVX_LIGHT version!");
379 #endif
382 //--------------------------------------------------------------------
383 ODataAccessDescriptor::ODataAccessDescriptor( const Any& _rValues )
384 #ifndef SVX_LIGHT
385 :m_pImpl(new ODADescriptorImpl)
386 #else
387 :m_pImpl(NULL)
388 #endif
390 #ifndef SVX_LIGHT
391 // check if we know the format in the Any
392 Sequence< PropertyValue > aValues;
393 Reference< XPropertySet > xValues;
394 if ( _rValues >>= aValues )
395 m_pImpl->buildFrom( aValues );
396 else if ( _rValues >>= xValues )
397 m_pImpl->buildFrom( xValues );
398 #else
399 OSL_ENSURE(sal_False, "ODataAccessDescriptor::ODataAccessDescriptor: not available in the SVX_LIGHT version!");
400 #endif
403 //--------------------------------------------------------------------
404 ODataAccessDescriptor::ODataAccessDescriptor( const Sequence< PropertyValue >& _rValues )
405 #ifndef SVX_LIGHT
406 :m_pImpl(new ODADescriptorImpl)
407 #else
408 :m_pImpl(NULL)
409 #endif
411 #ifndef SVX_LIGHT
412 m_pImpl->buildFrom(_rValues);
413 #else
414 OSL_ENSURE(sal_False, "ODataAccessDescriptor::ODataAccessDescriptor: not available in the SVX_LIGHT version!");
415 #endif
418 //--------------------------------------------------------------------
419 ODataAccessDescriptor::~ODataAccessDescriptor()
421 delete m_pImpl;
424 //--------------------------------------------------------------------
425 void ODataAccessDescriptor::clear()
427 #ifndef SVX_LIGHT
428 m_pImpl->m_aValues.clear();
429 #endif
432 //--------------------------------------------------------------------
433 void ODataAccessDescriptor::erase(DataAccessDescriptorProperty _eWhich)
435 #ifndef SVX_LIGHT
436 OSL_ENSURE(has(_eWhich), "ODataAccessDescriptor::erase: invalid call!");
437 if (has(_eWhich))
438 m_pImpl->m_aValues.erase(_eWhich);
439 #endif
442 //--------------------------------------------------------------------
443 sal_Bool ODataAccessDescriptor::has(DataAccessDescriptorProperty _eWhich) const
445 #ifndef SVX_LIGHT
446 return m_pImpl->m_aValues.find(_eWhich) != m_pImpl->m_aValues.end();
447 #else
448 return sal_False;
449 #endif
452 //--------------------------------------------------------------------
453 const Any& ODataAccessDescriptor::operator [] ( DataAccessDescriptorProperty _eWhich ) const
455 #ifndef SVX_LIGHT
456 if (!has(_eWhich))
458 OSL_ENSURE(sal_False, "ODataAccessDescriptor::operator[]: invalid acessor!");
459 static const Any aDummy;
460 return aDummy;
463 return m_pImpl->m_aValues[_eWhich];
464 #else
465 static const Any aDummy;
466 return aDummy;
467 #endif
470 //--------------------------------------------------------------------
471 Any& ODataAccessDescriptor::operator[] ( DataAccessDescriptorProperty _eWhich )
473 #ifndef SVX_LIGHT
474 m_pImpl->invalidateExternRepresentations();
475 return m_pImpl->m_aValues[_eWhich];
476 #else
477 static const Any aDummy;
478 return aDummy;
479 #endif
482 //--------------------------------------------------------------------
483 void ODataAccessDescriptor::initializeFrom(const Reference< XPropertySet >& _rxValues, sal_Bool _bClear)
485 #ifndef SVX_LIGHT
486 if (_bClear)
487 clear();
488 m_pImpl->buildFrom(_rxValues);
489 #endif
492 //--------------------------------------------------------------------
493 void ODataAccessDescriptor::initializeFrom(const Sequence< PropertyValue >& _rValues, sal_Bool _bClear)
495 #ifndef SVX_LIGHT
496 if (_bClear)
497 clear();
498 m_pImpl->buildFrom(_rValues);
499 #endif
502 //--------------------------------------------------------------------
503 Sequence< PropertyValue > ODataAccessDescriptor::createPropertyValueSequence()
505 #ifndef SVX_LIGHT
506 m_pImpl->updateSequence();
507 return m_pImpl->m_aAsSequence;
508 #else
509 return Sequence< PropertyValue >();
510 #endif
512 //--------------------------------------------------------------------
513 Sequence< Any > ODataAccessDescriptor::createAnySequence()
515 #ifndef SVX_LIGHT
516 m_pImpl->updateSequence();
517 Sequence< Any > aRet(m_pImpl->m_aAsSequence.getLength());
518 const PropertyValue* pBegin = m_pImpl->m_aAsSequence.getConstArray();
519 const PropertyValue* pEnd = pBegin + m_pImpl->m_aAsSequence.getLength();
520 for(sal_Int32 i=0;pBegin != pEnd;++pBegin,++i)
521 aRet[i] <<= *pBegin;
522 return aRet;
523 #else
524 return Sequence< createAnySequence >();
525 #endif
528 //--------------------------------------------------------------------
529 Reference< XPropertySet > ODataAccessDescriptor::createPropertySet()
531 #ifndef SVX_LIGHT
532 m_pImpl->updateSet();
533 return m_pImpl->m_xAsSet;
534 #else
535 return Reference< XPropertySet >();
536 #endif
538 //--------------------------------------------------------------------
539 ::rtl::OUString ODataAccessDescriptor::getDataSource() const
541 #ifndef SVX_LIGHT
542 ::rtl::OUString sDataSourceName;
543 if ( has(daDataSource) )
544 (*this)[daDataSource] >>= sDataSourceName;
545 else if ( has(daDatabaseLocation) )
546 (*this)[daDatabaseLocation] >>= sDataSourceName;
547 return sDataSourceName;
548 #else
549 return ::rtl::OUString();
550 #endif
552 //--------------------------------------------------------------------
553 void ODataAccessDescriptor::setDataSource(const ::rtl::OUString& _sDataSourceNameOrLocation)
555 #ifndef SVX_LIGHT
556 if ( _sDataSourceNameOrLocation.getLength() )
558 INetURLObject aURL(_sDataSourceNameOrLocation);
559 (*this)[ (( aURL.GetProtocol() == INET_PROT_FILE ) ? daDatabaseLocation : daDataSource)] <<= _sDataSourceNameOrLocation;
561 else
562 (*this)[ daDataSource ] <<= ::rtl::OUString();
563 #endif
566 //........................................................................
567 } // namespace svx
568 //........................................................................