1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*************************************************************************
4 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
6 * Copyright 2000, 2010 Oracle and/or its affiliates.
8 * OpenOffice.org - a multi-platform office productivity suite
10 * This file is part of OpenOffice.org.
12 * OpenOffice.org is free software: you can redistribute it and/or modify
13 * it under the terms of the GNU Lesser General Public License version 3
14 * only, as published by the Free Software Foundation.
16 * OpenOffice.org is distributed in the hope that it will be useful,
17 * but WITHOUT ANY WARRANTY; without even the implied warranty of
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 * GNU Lesser General Public License version 3 for more details
20 * (a copy is included in the LICENSE file that accompanied this code).
22 * You should have received a copy of the GNU Lesser General Public License
23 * version 3 along with OpenOffice.org. If not, see
24 * <http://www.openoffice.org/license.html>
25 * for a copy of the LGPLv3 License.
27 ************************************************************************/
28 #include <connectivity/paramwrapper.hxx>
30 /** === begin UNO includes === **/
31 #include <com/sun/star/beans/PropertyAttribute.hpp>
32 #include <com/sun/star/sdbc/DataType.hpp>
33 #include <com/sun/star/lang/WrappedTargetException.hpp>
34 #include <com/sun/star/sdb/XParametersSupplier.hpp>
35 #include <com/sun/star/lang/DisposedException.hpp>
36 /** === end UNO includes === **/
38 #include <tools/diagnose_ex.h>
39 #include <comphelper/enumhelper.hxx>
41 #define PROPERTY_ID_VALUE 1000
43 //........................................................................
48 //........................................................................
50 /** === begin UNO using === **/
51 using ::com::sun::star::uno::Reference
;
52 using ::com::sun::star::beans::XPropertySet
;
53 using ::com::sun::star::sdbc::XParameters
;
54 using ::com::sun::star::uno::Sequence
;
55 using ::com::sun::star::uno::Type
;
56 using ::com::sun::star::uno::RuntimeException
;
57 using ::com::sun::star::uno::XWeak
;
58 using ::com::sun::star::beans::XPropertySet
;
59 using ::com::sun::star::beans::XFastPropertySet
;
60 using ::com::sun::star::beans::XMultiPropertySet
;
61 using ::com::sun::star::beans::XPropertySetInfo
;
62 using ::com::sun::star::beans::Property
;
63 using ::com::sun::star::uno::Exception
;
64 using ::com::sun::star::uno::UNO_QUERY_THROW
;
65 using ::com::sun::star::uno::Any
;
66 using ::com::sun::star::lang::IllegalArgumentException
;
67 using ::com::sun::star::sdbc::SQLException
;
68 using ::com::sun::star::lang::WrappedTargetException
;
69 using ::com::sun::star::lang::IndexOutOfBoundsException
;
70 using ::com::sun::star::container::XEnumeration
;
71 using ::com::sun::star::sdb::XSingleSelectQueryAnalyzer
;
72 using ::com::sun::star::sdb::XParametersSupplier
;
73 using ::com::sun::star::lang::DisposedException
;
74 /** === end UNO using === **/
75 namespace PropertyAttribute
= ::com::sun::star::beans::PropertyAttribute
;
76 namespace DataType
= ::com::sun::star::sdbc::DataType
;
78 //====================================================================
80 //====================================================================
81 //--------------------------------------------------------------------
82 ParameterWrapper::ParameterWrapper( const Reference
< XPropertySet
>& _rxColumn
)
83 :PropertyBase( m_aBHelper
)
84 ,m_xDelegator( _rxColumn
)
86 if ( m_xDelegator
.is() )
87 m_xDelegatorPSI
= m_xDelegator
->getPropertySetInfo();
88 if ( !m_xDelegatorPSI
.is() )
89 throw RuntimeException();
92 //--------------------------------------------------------------------
93 ParameterWrapper::ParameterWrapper( const Reference
< XPropertySet
>& _rxColumn
,
94 const Reference
< XParameters
>& _rxAllParameters
, const ::std::vector
< sal_Int32
>& _rIndexes
)
95 :PropertyBase( m_aBHelper
)
96 ,m_aIndexes( _rIndexes
)
97 ,m_xDelegator( _rxColumn
)
98 ,m_xValueDestination( _rxAllParameters
)
100 if ( m_xDelegator
.is() )
101 m_xDelegatorPSI
= m_xDelegator
->getPropertySetInfo();
102 if ( !m_xDelegatorPSI
.is() )
103 throw RuntimeException();
105 OSL_ENSURE( !m_aIndexes
.empty(), "ParameterWrapper::ParameterWrapper: sure about the indexes?" );
108 //--------------------------------------------------------------------
109 ParameterWrapper::~ParameterWrapper()
113 //--------------------------------------------------------------------
114 IMPLEMENT_FORWARD_XINTERFACE2( ParameterWrapper
, UnoBase
, PropertyBase
)
116 //--------------------------------------------------------------------
117 Sequence
< Type
> SAL_CALL
ParameterWrapper::getTypes( ) throw(RuntimeException
)
119 Sequence
< Type
> aTypes( 4 );
120 aTypes
[ 1 ] = ::getCppuType( static_cast< Reference
< XWeak
>* >( NULL
) );
121 aTypes
[ 1 ] = ::getCppuType( static_cast< Reference
< XPropertySet
>* >( NULL
) );
122 aTypes
[ 2 ] = ::getCppuType( static_cast< Reference
< XFastPropertySet
>* >( NULL
) );
123 aTypes
[ 3 ] = ::getCppuType( static_cast< Reference
< XMultiPropertySet
>* >( NULL
) );
127 //--------------------------------------------------------------------
128 IMPLEMENT_GET_IMPLEMENTATION_ID( ParameterWrapper
)
130 //--------------------------------------------------------------------
131 ::rtl::OUString
ParameterWrapper::impl_getPseudoAggregatePropertyName( sal_Int32 _nHandle
) const
133 Reference
< XPropertySetInfo
> xInfo
= const_cast<ParameterWrapper
*>( this )->getPropertySetInfo();
134 Sequence
< Property
> aProperties
= xInfo
->getProperties();
135 const Property
* pProperties
= aProperties
.getConstArray();
136 for ( sal_Int32 i
= 0; i
< aProperties
.getLength(); ++i
, ++pProperties
)
138 if ( pProperties
->Handle
== _nHandle
)
139 return pProperties
->Name
;
142 OSL_FAIL( "ParameterWrapper::impl_getPseudoAggregatePropertyName: invalid argument!" );
143 return ::rtl::OUString();
146 //--------------------------------------------------------------------
147 Reference
< XPropertySetInfo
> ParameterWrapper::getPropertySetInfo() throw( RuntimeException
)
149 return createPropertySetInfo( getInfoHelper() );
152 //--------------------------------------------------------------------
153 ::cppu::IPropertyArrayHelper
& ParameterWrapper::getInfoHelper()
155 if ( !m_pInfoHelper
.get() )
157 Sequence
< Property
> aProperties
;
160 aProperties
= m_xDelegatorPSI
->getProperties();
161 sal_Int32
nProperties( aProperties
.getLength() );
162 aProperties
.realloc( nProperties
+ 1 );
163 aProperties
[ nProperties
] = Property(
164 ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "Value" ) ),
166 ::cppu::UnoType
< Any
>::get(),
167 PropertyAttribute::TRANSIENT
| PropertyAttribute::MAYBEVOID
170 catch( const Exception
& )
172 DBG_UNHANDLED_EXCEPTION();
175 m_pInfoHelper
.reset( new ::cppu::OPropertyArrayHelper( aProperties
, false ) );
177 return *m_pInfoHelper
;
180 //--------------------------------------------------------------------
181 sal_Bool
ParameterWrapper::convertFastPropertyValue(Any
& rConvertedValue
, Any
& rOldValue
, sal_Int32 nHandle
, const Any
& rValue
) throw( IllegalArgumentException
)
183 OSL_ENSURE( PROPERTY_ID_VALUE
== nHandle
, "ParameterWrapper::convertFastPropertyValue: the only non-readonly prop should be our PROPERTY_VALUE!" );
186 // we're lazy here ...
187 rOldValue
= m_aValue
.makeAny();
188 rConvertedValue
= rValue
;
189 return sal_True
; // assume "modified" ...
192 //--------------------------------------------------------------------
193 void ParameterWrapper::setFastPropertyValue_NoBroadcast( sal_Int32 nHandle
, const Any
& rValue
) throw( Exception
)
195 if ( nHandle
== PROPERTY_ID_VALUE
)
199 // TODO : aParamType & nScale can be obtained within the constructor ....
200 sal_Int32 nParamType
= DataType::VARCHAR
;
201 OSL_VERIFY( m_xDelegator
->getPropertyValue( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "Type" ) ) ) >>= nParamType
);
203 sal_Int32 nScale
= 0;
204 if ( m_xDelegatorPSI
->hasPropertyByName( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "Scale" ) ) ) )
205 OSL_VERIFY( m_xDelegator
->getPropertyValue( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "Scale" ) ) ) >>= nScale
);
207 if ( m_xValueDestination
.is() )
209 for ( ::std::vector
< sal_Int32
>::iterator aIter
= m_aIndexes
.begin(); aIter
!= m_aIndexes
.end(); ++aIter
)
211 m_xValueDestination
->setObjectWithInfo( *aIter
+ 1, rValue
, nParamType
, nScale
);
212 // (the index of the parameters is one-based)
218 catch( SQLException
& e
)
220 WrappedTargetException aExceptionWrapper
;
221 aExceptionWrapper
.Context
= e
.Context
;
222 aExceptionWrapper
.Message
= e
.Message
;
223 aExceptionWrapper
.TargetException
<<= e
;
224 throw WrappedTargetException( aExceptionWrapper
);
229 ::rtl::OUString aName
= impl_getPseudoAggregatePropertyName( nHandle
);
230 m_xDelegator
->setPropertyValue( aName
, rValue
);
234 //--------------------------------------------------------------------
235 void ParameterWrapper::getFastPropertyValue( Any
& rValue
, sal_Int32 nHandle
) const
237 if ( nHandle
== PROPERTY_ID_VALUE
)
239 rValue
= m_aValue
.makeAny();
243 ::rtl::OUString aName
= impl_getPseudoAggregatePropertyName( nHandle
);
244 rValue
= m_xDelegator
->getPropertyValue( aName
);
248 //--------------------------------------------------------------------
249 void SAL_CALL
ParameterWrapper::dispose()
251 ::osl::MutexGuard
aGuard( m_aMutex
);
254 m_aIndexes
.resize(0);
255 m_xDelegator
.clear();
256 m_xDelegatorPSI
.clear();
257 m_xValueDestination
.clear();
259 m_aBHelper
.bDisposed
= sal_True
;
262 //====================================================================
263 //= ParameterWrapperContainer
264 //====================================================================
265 //--------------------------------------------------------------------
266 ParameterWrapperContainer::ParameterWrapperContainer()
267 :ParameterWrapperContainer_Base( m_aMutex
)
271 //--------------------------------------------------------------------
272 ParameterWrapperContainer::ParameterWrapperContainer( const Reference
< XSingleSelectQueryAnalyzer
>& _rxComposer
)
273 :ParameterWrapperContainer_Base( m_aMutex
)
275 Reference
< XParametersSupplier
> xSuppParams( _rxComposer
, UNO_QUERY_THROW
);
276 Reference
< XIndexAccess
> xParameters( xSuppParams
->getParameters(), UNO_QUERY_THROW
);
277 sal_Int32
nParamCount( xParameters
->getCount() );
278 m_aParameters
.reserve( nParamCount
);
279 for ( sal_Int32 i
=0; i
<nParamCount
; ++i
)
281 m_aParameters
.push_back( new ParameterWrapper( Reference
< XPropertySet
>( xParameters
->getByIndex( i
), UNO_QUERY_THROW
) ) );
285 //--------------------------------------------------------------------
286 ParameterWrapperContainer::~ParameterWrapperContainer()
290 //--------------------------------------------------------------------
291 Type SAL_CALL
ParameterWrapperContainer::getElementType() throw( RuntimeException
)
293 ::osl::MutexGuard
aGuard( m_aMutex
);
294 impl_checkDisposed_throw();
295 return ::getCppuType( static_cast< Reference
< XPropertySet
>* >( NULL
) );
298 //--------------------------------------------------------------------
299 sal_Bool SAL_CALL
ParameterWrapperContainer::hasElements() throw( RuntimeException
)
301 ::osl::MutexGuard
aGuard( m_aMutex
);
302 impl_checkDisposed_throw();
303 return !m_aParameters
.empty();
306 //--------------------------------------------------------------------
307 sal_Int32 SAL_CALL
ParameterWrapperContainer::getCount() throw( RuntimeException
)
309 ::osl::MutexGuard
aGuard( m_aMutex
);
310 impl_checkDisposed_throw();
311 return m_aParameters
.size();
314 //--------------------------------------------------------------------
315 Any SAL_CALL
ParameterWrapperContainer::getByIndex( sal_Int32 _nIndex
) throw( IndexOutOfBoundsException
, WrappedTargetException
, RuntimeException
)
317 ::osl::MutexGuard
aGuard( m_aMutex
);
318 impl_checkDisposed_throw();
320 if ( ( _nIndex
< 0 ) || ( _nIndex
>= (sal_Int32
)m_aParameters
.size() ) )
321 throw IndexOutOfBoundsException();
323 return makeAny( Reference
< XPropertySet
>( m_aParameters
[ _nIndex
].get() ) );
326 //--------------------------------------------------------------------
327 Reference
< XEnumeration
> ParameterWrapperContainer::createEnumeration() throw( RuntimeException
)
329 ::osl::MutexGuard
aGuard( m_aMutex
);
330 impl_checkDisposed_throw();
332 return new ::comphelper::OEnumerationByIndex( static_cast< XIndexAccess
* >( this ) );
335 //--------------------------------------------------------------------
336 void ParameterWrapperContainer::impl_checkDisposed_throw()
338 if ( rBHelper
.bDisposed
)
339 throw DisposedException( ::rtl::OUString(), *this );
342 //--------------------------------------------------------------------
343 void SAL_CALL
ParameterWrapperContainer::disposing()
345 ::osl::MutexGuard
aGuard( m_aMutex
);
346 impl_checkDisposed_throw();
348 for ( Parameters::const_iterator param
= m_aParameters
.begin();
349 param
!= m_aParameters
.end();
357 m_aParameters
.swap( aEmpty
);
360 //........................................................................
361 } } // namespace dbtools::param
362 //........................................................................
364 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */