1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
3 * This file is part of the LibreOffice project.
5 * This Source Code Form is subject to the terms of the Mozilla Public
6 * License, v. 2.0. If a copy of the MPL was not distributed with this
7 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
9 * This file incorporates work covered by the following license notice:
11 * Licensed to the Apache Software Foundation (ASF) under one or more
12 * contributor license agreements. See the NOTICE file distributed
13 * with this work for additional information regarding copyright
14 * ownership. The ASF licenses this file to you under the Apache
15 * License, Version 2.0 (the "License"); you may not use this file
16 * except in compliance with the License. You may obtain a copy of
17 * the License at http://www.apache.org/licenses/LICENSE-2.0 .
20 #include <ado/AResultSet.hxx>
21 #include <ado/AResultSetMetaData.hxx>
22 #include <com/sun/star/sdbc/DataType.hpp>
23 #include <com/sun/star/sdbc/KeyRule.hpp>
24 #include <com/sun/star/sdbc/IndexType.hpp>
25 #include <com/sun/star/sdbcx/CompareBookmark.hpp>
26 #include <comphelper/property.hxx>
27 #include <com/sun/star/lang/DisposedException.hpp>
28 #include <com/sun/star/sdbc/ResultSetConcurrency.hpp>
29 #include <com/sun/star/sdbc/ResultSetType.hpp>
30 #include <com/sun/star/sdbc/FetchDirection.hpp>
31 #include <cppuhelper/typeprovider.hxx>
32 #include <cppuhelper/supportsservice.hxx>
33 #include <comphelper/sequence.hxx>
34 #include <com/sun/star/beans/PropertyAttribute.hpp>
35 #include <comphelper/seqstream.hxx>
36 #include <connectivity/dbexception.hxx>
37 #include <connectivity/dbtools.hxx>
38 #include <comphelper/types.hxx>
40 using namespace ::comphelper
;
45 #define CHECK_RETURN(x) \
47 ADOS::ThrowException(m_pStmt->m_pConnection->getConnection(),*this);
49 using namespace connectivity::ado
;
50 using namespace com::sun::star::uno
;
51 using namespace com::sun::star::lang
;
52 using namespace com::sun::star::beans
;
53 using namespace com::sun::star::sdbc
;
56 // IMPLEMENT_SERVICE_INFO(OResultSet,"com.sun.star.sdbcx.AResultSet","com.sun.star.sdbc.ResultSet");
57 OUString SAL_CALL
OResultSet::getImplementationName( )
59 return "com.sun.star.sdbcx.ado.ResultSet";
62 css::uno::Sequence
< OUString
> SAL_CALL
OResultSet::getSupportedServiceNames( )
64 return {"com.sun.star.sdbc.ResultSet","com.sun.star.sdbcx.ResultSet"};
67 sal_Bool SAL_CALL
OResultSet::supportsService( const OUString
& _rServiceName
)
69 return cppu::supportsService(this, _rServiceName
);
72 OResultSet::OResultSet(ADORecordset
* _pRecordSet
,OStatement_Base
* pStmt
) : OResultSet_BASE(m_aMutex
)
73 ,OPropertySetHelper(OResultSet_BASE::rBHelper
)
74 ,m_pRecordSet(_pRecordSet
)
79 ,m_bOnFirstAfterOpen(false)
83 OResultSet::OResultSet(ADORecordset
* _pRecordSet
) : OResultSet_BASE(m_aMutex
)
84 ,OPropertySetHelper(OResultSet_BASE::rBHelper
)
85 ,m_pRecordSet(_pRecordSet
)
89 ,m_bOnFirstAfterOpen(false)
93 void OResultSet::construct()
95 osl_atomic_increment( &m_refCount
);
98 OSL_FAIL( "OResultSet::construct: no RecordSet!" );
99 Reference
< XInterface
> xInt( *this );
100 osl_atomic_decrement( &m_refCount
);
101 ::dbtools::throwFunctionSequenceException( xInt
);
103 m_pRecordSet
->AddRef();
104 VARIANT_BOOL bIsAtBOF
;
105 CHECK_RETURN(m_pRecordSet
->get_BOF(&bIsAtBOF
))
106 m_bOnFirstAfterOpen
= bIsAtBOF
!= VARIANT_TRUE
;
107 osl_atomic_decrement( &m_refCount
);
110 OResultSet::~OResultSet()
113 m_pRecordSet
->Release();
116 void OResultSet::disposing()
118 OPropertySetHelper::disposing();
120 ::osl::MutexGuard
aGuard(m_aMutex
);
122 m_pRecordSet
->Close();
123 m_xStatement
.clear();
127 Any SAL_CALL
OResultSet::queryInterface( const Type
& rType
)
129 Any aRet
= OPropertySetHelper::queryInterface(rType
);
130 return aRet
.hasValue() ? aRet
: OResultSet_BASE::queryInterface(rType
);
133 css::uno::Sequence
< css::uno::Type
> SAL_CALL
OResultSet::getTypes( )
135 ::cppu::OTypeCollection
aTypes( cppu::UnoType
<css::beans::XMultiPropertySet
>::get(),
136 cppu::UnoType
<css::beans::XFastPropertySet
>::get(),
137 cppu::UnoType
<css::beans::XPropertySet
>::get());
139 return ::comphelper::concatSequences(aTypes
.getTypes(),OResultSet_BASE::getTypes());
143 sal_Int32 SAL_CALL
OResultSet::findColumn( const OUString
& columnName
)
145 ::osl::MutexGuard
aGuard( m_aMutex
);
146 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
149 Reference
< XResultSetMetaData
> xMeta
= getMetaData();
150 sal_Int32 nLen
= xMeta
->getColumnCount();
154 if(xMeta
->isCaseSensitive(i
) ? columnName
== xMeta
->getColumnName(i
) :
155 columnName
.equalsIgnoreAsciiCase(xMeta
->getColumnName(i
)))
159 ::dbtools::throwInvalidColumnException( columnName
, *this );
161 return 0; // Never reached
163 #define BLOCK_SIZE 256
165 Reference
< css::io::XInputStream
> SAL_CALL
OResultSet::getBinaryStream( sal_Int32 columnIndex
)
167 ::osl::MutexGuard
aGuard( m_aMutex
);
168 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
170 WpADOField aField
= ADOS::getField(m_pRecordSet
,columnIndex
);
172 if((aField
.GetAttributes() & adFldLong
) == adFldLong
)
174 //Copy the data only up to the Actual Size of Field.
175 sal_Int32 nSize
= aField
.GetActualSize();
176 Sequence
<sal_Int8
> aData(nSize
);
180 m_aValue
= aField
.GetChunk(BLOCK_SIZE
);
181 if(m_aValue
.isNull())
184 for(LONG index2
= 0;index2
< BLOCK_SIZE
;++index2
)
186 HRESULT hr
= ::SafeArrayGetElement(m_aValue
.parray
,&index2
,&chData
);
189 //Take BYTE by BYTE and advance Memory Location
190 aData
.getArray()[index
++] = chData
;
197 return new ::comphelper::SequenceInputStream(aData
);
199 // else we ask for a bytesequence
200 aField
.get_Value(m_aValue
);
202 return m_aValue
.isNull() ? nullptr : new ::comphelper::SequenceInputStream(m_aValue
.getByteSequence());
205 Reference
< css::io::XInputStream
> SAL_CALL
OResultSet::getCharacterStream( sal_Int32
/*columnIndex*/ )
207 ::dbtools::throwFeatureNotImplementedSQLException( "XRow::getCharacterStream", *this );
211 OLEVariant
OResultSet::getValue(sal_Int32 columnIndex
)
213 ::osl::MutexGuard
aGuard( m_aMutex
);
214 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
216 WpADOField aField
= ADOS::getField(m_pRecordSet
,columnIndex
);
217 aField
.get_Value(m_aValue
);
221 sal_Bool SAL_CALL
OResultSet::getBoolean( sal_Int32 columnIndex
)
223 return getValue(columnIndex
).getBool();
227 sal_Int8 SAL_CALL
OResultSet::getByte( sal_Int32 columnIndex
)
229 return getValue(columnIndex
).getInt8();
233 Sequence
< sal_Int8
> SAL_CALL
OResultSet::getBytes( sal_Int32 columnIndex
)
235 return getValue(columnIndex
).getByteSequence();
239 css::util::Date SAL_CALL
OResultSet::getDate( sal_Int32 columnIndex
)
241 return getValue(columnIndex
).getDate();
245 double SAL_CALL
OResultSet::getDouble( sal_Int32 columnIndex
)
247 return getValue(columnIndex
).getDouble();
251 float SAL_CALL
OResultSet::getFloat( sal_Int32 columnIndex
)
253 return getValue(columnIndex
).getFloat();
257 sal_Int32 SAL_CALL
OResultSet::getInt( sal_Int32 columnIndex
)
259 return getValue(columnIndex
).getInt32();
263 sal_Int32 SAL_CALL
OResultSet::getRow( )
265 ::osl::MutexGuard
aGuard( m_aMutex
);
266 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
269 PositionEnum_Param aPos
;
270 m_pRecordSet
->get_AbsolutePosition(&aPos
);
271 return (aPos
> 0) ? static_cast<sal_Int32
>(aPos
) : m_nRowPos
;
272 // return the rowcount from driver if the driver doesn't support this return our count
276 sal_Int64 SAL_CALL
OResultSet::getLong( sal_Int32
/*columnIndex*/ )
278 ::dbtools::throwFeatureNotImplementedSQLException( "XRow::getLong", *this );
283 Reference
< XResultSetMetaData
> SAL_CALL
OResultSet::getMetaData( )
285 ::osl::MutexGuard
aGuard( m_aMutex
);
286 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
289 if(!m_xMetaData
.is())
290 m_xMetaData
= new OResultSetMetaData(m_pRecordSet
);
294 Reference
< XArray
> SAL_CALL
OResultSet::getArray( sal_Int32
/*columnIndex*/ )
296 ::dbtools::throwFeatureNotImplementedSQLException( "XRow::getArray", *this );
301 Reference
< XClob
> SAL_CALL
OResultSet::getClob( sal_Int32
/*columnIndex*/ )
303 ::dbtools::throwFeatureNotImplementedSQLException( "XRow::getClob", *this );
307 Reference
< XBlob
> SAL_CALL
OResultSet::getBlob( sal_Int32
/*columnIndex*/ )
309 ::dbtools::throwFeatureNotImplementedSQLException( "XRow::getBlob", *this );
314 Reference
< XRef
> SAL_CALL
OResultSet::getRef( sal_Int32
/*columnIndex*/ )
316 ::dbtools::throwFeatureNotImplementedSQLException( "XRow::getRef", *this );
321 Any SAL_CALL
OResultSet::getObject( sal_Int32 columnIndex
, const Reference
< css::container::XNameAccess
>& /*typeMap*/ )
323 return getValue(columnIndex
).makeAny();
327 sal_Int16 SAL_CALL
OResultSet::getShort( sal_Int32 columnIndex
)
329 return getValue(columnIndex
).getInt16();
333 OUString SAL_CALL
OResultSet::getString( sal_Int32 columnIndex
)
335 return getValue(columnIndex
).getString();
339 css::util::Time SAL_CALL
OResultSet::getTime( sal_Int32 columnIndex
)
341 return getValue(columnIndex
).getTime();
345 css::util::DateTime SAL_CALL
OResultSet::getTimestamp( sal_Int32 columnIndex
)
347 return getValue(columnIndex
).getDateTime();
351 sal_Bool SAL_CALL
OResultSet::isAfterLast( )
353 ::osl::MutexGuard
aGuard( m_aMutex
);
354 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
357 VARIANT_BOOL bIsAtEOF
;
358 CHECK_RETURN(m_pRecordSet
->get_EOF(&bIsAtEOF
))
359 return bIsAtEOF
== VARIANT_TRUE
;
362 sal_Bool SAL_CALL
OResultSet::isFirst( )
364 ::osl::MutexGuard
aGuard( m_aMutex
);
365 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
368 return m_nRowPos
== 1;
371 sal_Bool SAL_CALL
OResultSet::isLast( )
373 ::osl::MutexGuard
aGuard( m_aMutex
);
374 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
380 void SAL_CALL
OResultSet::beforeFirst( )
382 ::osl::MutexGuard
aGuard( m_aMutex
);
383 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
387 m_bOnFirstAfterOpen
= !previous();
390 void SAL_CALL
OResultSet::afterLast( )
392 ::osl::MutexGuard
aGuard( m_aMutex
);
393 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
402 void SAL_CALL
OResultSet::close( )
405 ::osl::MutexGuard
aGuard( m_aMutex
);
406 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
413 sal_Bool SAL_CALL
OResultSet::first( )
415 ::osl::MutexGuard
aGuard( m_aMutex
);
416 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
419 if(SUCCEEDED(m_pRecordSet
->MoveFirst()))
422 m_bOnFirstAfterOpen
= false;
429 sal_Bool SAL_CALL
OResultSet::last( )
431 ::osl::MutexGuard
aGuard( m_aMutex
);
432 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
435 bool bRet
= SUCCEEDED(m_pRecordSet
->MoveLast());
438 m_pRecordSet
->get_RecordCount(&m_nRowPos
);
439 m_bOnFirstAfterOpen
= false;
444 sal_Bool SAL_CALL
OResultSet::absolute( sal_Int32 row
)
446 ::osl::MutexGuard
aGuard( m_aMutex
);
447 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
450 if(!row
) // absolute with zero not allowed
451 ::dbtools::throwFunctionSequenceException(*this);
456 bCheck
= SUCCEEDED(m_pRecordSet
->MoveLast());
459 while(++row
< 0 && bCheck
)
460 bCheck
= SUCCEEDED(m_pRecordSet
->MovePrevious());
468 bCheck
= SUCCEEDED(m_pRecordSet
->Move(row
-1,aEmpty
)); // move to row -1 because we stand already on the first
473 m_bOnFirstAfterOpen
= false;
477 sal_Bool SAL_CALL
OResultSet::relative( sal_Int32 row
)
479 ::osl::MutexGuard
aGuard( m_aMutex
);
480 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
485 sal_Int32 nNewPos
= row
;
486 if ( m_bOnFirstAfterOpen
&& nNewPos
> 0 )
488 bool bRet
= SUCCEEDED(m_pRecordSet
->Move(row
,aEmpty
));
492 m_bOnFirstAfterOpen
= false;
497 sal_Bool SAL_CALL
OResultSet::previous( )
499 ::osl::MutexGuard
aGuard( m_aMutex
);
500 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
502 bool bRet
= SUCCEEDED(m_pRecordSet
->MovePrevious());
506 m_bOnFirstAfterOpen
= false;
511 Reference
< XInterface
> SAL_CALL
OResultSet::getStatement( )
513 ::osl::MutexGuard
aGuard( m_aMutex
);
514 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
519 sal_Bool SAL_CALL
OResultSet::rowDeleted( )
521 ::osl::MutexGuard
aGuard( m_aMutex
);
522 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
526 m_pRecordSet
->get_Status(&eRec
);
527 bool bRet
= (RecordStatusEnum(eRec
) & adRecDeleted
) == adRecDeleted
;
533 sal_Bool SAL_CALL
OResultSet::rowInserted( )
534 { ::osl::MutexGuard
aGuard( m_aMutex
);
535 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
539 m_pRecordSet
->get_Status(&eRec
);
540 bool bRet
= (RecordStatusEnum(eRec
) & adRecNew
) == adRecNew
;
546 sal_Bool SAL_CALL
OResultSet::rowUpdated( )
548 ::osl::MutexGuard
aGuard( m_aMutex
);
549 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
553 m_pRecordSet
->get_Status(&eRec
);
554 return (RecordStatusEnum(eRec
) & adRecModified
) == adRecModified
;
558 sal_Bool SAL_CALL
OResultSet::isBeforeFirst( )
560 ::osl::MutexGuard
aGuard( m_aMutex
);
561 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
564 OSL_ENSURE(!m_nRowPos
,"OResultSet::isBeforeFirst: Error in setting m_nRowPos!");
565 VARIANT_BOOL bIsAtBOF
= VARIANT_TRUE
;
566 if(!m_bOnFirstAfterOpen
)
568 OSL_ENSURE(!m_nRowPos
,"OResultSet::isBeforeFirst: Error in setting m_nRowPos!");
569 m_pRecordSet
->get_BOF(&bIsAtBOF
);
571 return bIsAtBOF
== VARIANT_TRUE
;
575 sal_Bool SAL_CALL
OResultSet::next( )
577 ::osl::MutexGuard
aGuard( m_aMutex
);
578 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
582 if(m_bOnFirstAfterOpen
)
584 m_bOnFirstAfterOpen
= false;
589 bRet
= SUCCEEDED(m_pRecordSet
->MoveNext());
593 VARIANT_BOOL bIsAtEOF
;
594 CHECK_RETURN(m_pRecordSet
->get_EOF(&bIsAtEOF
))
595 bRet
= bIsAtEOF
!= VARIANT_TRUE
;
599 ADOS::ThrowException(m_pStmt
->m_pConnection
->getConnection(),*this);
606 sal_Bool SAL_CALL
OResultSet::wasNull( )
608 ::osl::MutexGuard
aGuard( m_aMutex
);
609 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
612 return m_aValue
.isNull();
616 void SAL_CALL
OResultSet::cancel( )
618 ::osl::MutexGuard
aGuard( m_aMutex
);
619 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
622 m_pRecordSet
->Cancel();
625 void SAL_CALL
OResultSet::clearWarnings( )
629 Any SAL_CALL
OResultSet::getWarnings( )
634 void SAL_CALL
OResultSet::insertRow( )
636 ::osl::MutexGuard
aGuard( m_aMutex
);
637 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
642 m_pRecordSet
->AddNew(aEmpty
,aEmpty
);
645 void SAL_CALL
OResultSet::updateRow( )
647 ::osl::MutexGuard
aGuard( m_aMutex
);
648 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
653 m_pRecordSet
->Update(aEmpty
,aEmpty
);
656 void SAL_CALL
OResultSet::deleteRow( )
658 ::osl::MutexGuard
aGuard( m_aMutex
);
659 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
662 m_pRecordSet
->Delete();
663 m_pRecordSet
->UpdateBatch(adAffectCurrent
);
667 void SAL_CALL
OResultSet::cancelRowUpdates( )
669 ::osl::MutexGuard
aGuard( m_aMutex
);
670 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
673 m_pRecordSet
->CancelUpdate();
677 void SAL_CALL
OResultSet::moveToInsertRow( )
679 // ::osl::MutexGuard aGuard( m_aMutex );
680 //checkDisposed(OResultSet_BASE::rBHelper.bDisposed);
681 // if ( getResultSetConcurrency() == ResultSetConcurrency::READ_ONLY )
682 // throw SQLException();
686 void SAL_CALL
OResultSet::moveToCurrentRow( )
690 void OResultSet::updateValue(sal_Int32 columnIndex
,const OLEVariant
& x
)
692 ::osl::MutexGuard
aGuard( m_aMutex
);
693 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
695 WpADOField aField
= ADOS::getField(m_pRecordSet
,columnIndex
);
699 void SAL_CALL
OResultSet::updateNull( sal_Int32 columnIndex
)
703 updateValue(columnIndex
,x
);
707 void SAL_CALL
OResultSet::updateBoolean( sal_Int32 columnIndex
, sal_Bool x
)
709 updateValue(columnIndex
,bool(x
));
712 void SAL_CALL
OResultSet::updateByte( sal_Int32 columnIndex
, sal_Int8 x
)
714 updateValue(columnIndex
,x
);
718 void SAL_CALL
OResultSet::updateShort( sal_Int32 columnIndex
, sal_Int16 x
)
720 updateValue(columnIndex
,x
);
723 void SAL_CALL
OResultSet::updateInt( sal_Int32 columnIndex
, sal_Int32 x
)
725 updateValue(columnIndex
,x
);
728 void SAL_CALL
OResultSet::updateLong( sal_Int32 columnIndex
, sal_Int64 x
)
730 updateValue(columnIndex
,x
);
733 void SAL_CALL
OResultSet::updateFloat( sal_Int32 columnIndex
, float x
)
735 updateValue(columnIndex
,x
);
739 void SAL_CALL
OResultSet::updateDouble( sal_Int32 columnIndex
, double x
)
741 updateValue(columnIndex
,x
);
744 void SAL_CALL
OResultSet::updateString( sal_Int32 columnIndex
, const OUString
& x
)
746 updateValue(columnIndex
,x
);
749 void SAL_CALL
OResultSet::updateBytes( sal_Int32 columnIndex
, const Sequence
< sal_Int8
>& x
)
751 updateValue(columnIndex
,x
);
754 void SAL_CALL
OResultSet::updateDate( sal_Int32 columnIndex
, const css::util::Date
& x
)
756 updateValue(columnIndex
,x
);
760 void SAL_CALL
OResultSet::updateTime( sal_Int32 columnIndex
, const css::util::Time
& x
)
762 updateValue(columnIndex
,x
);
766 void SAL_CALL
OResultSet::updateTimestamp( sal_Int32 columnIndex
, const css::util::DateTime
& x
)
768 updateValue(columnIndex
,x
);
772 void SAL_CALL
OResultSet::updateBinaryStream( sal_Int32 columnIndex
, const Reference
< css::io::XInputStream
>& x
, sal_Int32 length
)
775 ::dbtools::throwFunctionSequenceException(*this);
777 Sequence
<sal_Int8
> aSeq
;
778 x
->readBytes(aSeq
,length
);
779 updateBytes(columnIndex
,aSeq
);
782 void SAL_CALL
OResultSet::updateCharacterStream( sal_Int32 columnIndex
, const Reference
< css::io::XInputStream
>& x
, sal_Int32 length
)
785 ::dbtools::throwFunctionSequenceException(*this);
787 Sequence
<sal_Int8
> aSeq
;
788 x
->readBytes(aSeq
,length
);
789 updateBytes(columnIndex
,aSeq
);
792 void SAL_CALL
OResultSet::refreshRow( )
794 ::osl::MutexGuard
aGuard( m_aMutex
);
795 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
798 m_pRecordSet
->Resync(adAffectCurrent
);
801 void SAL_CALL
OResultSet::updateObject( sal_Int32 columnIndex
, const Any
& x
)
803 if (!::dbtools::implUpdateObject(this, columnIndex
, x
))
804 throw SQLException();
808 void SAL_CALL
OResultSet::updateNumericObject( sal_Int32 columnIndex
, const Any
& x
, sal_Int32
/*scale*/ )
810 if (!::dbtools::implUpdateObject(this, columnIndex
, x
))
811 throw SQLException();
815 Any SAL_CALL
OResultSet::getBookmark( )
817 ::osl::MutexGuard
aGuard( m_aMutex
);
818 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
820 if(m_nRowPos
< static_cast<sal_Int32
>(m_aBookmarks
.size())) // this bookmark was already fetched
821 return Any(sal_Int32(m_nRowPos
-1));
824 m_pRecordSet
->get_Bookmark(&aVar
);
825 m_aBookmarks
.push_back(aVar
);
826 return Any(static_cast<sal_Int32
>(m_aBookmarks
.size()-1));
830 sal_Bool SAL_CALL
OResultSet::moveToBookmark( const Any
& bookmark
)
832 ::osl::MutexGuard
aGuard( m_aMutex
);
833 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
838 OSL_ENSURE(nPos
>= 0 && nPos
< static_cast<sal_Int32
>(m_aBookmarks
.size()),"Invalid Index for vector");
839 if(nPos
< 0 || nPos
>= static_cast<sal_Int32
>(m_aBookmarks
.size()))
840 ::dbtools::throwFunctionSequenceException(*this);
842 return SUCCEEDED(m_pRecordSet
->Move(0,m_aBookmarks
[nPos
]));
845 sal_Bool SAL_CALL
OResultSet::moveRelativeToBookmark( const Any
& bookmark
, sal_Int32 rows
)
847 ::osl::MutexGuard
aGuard( m_aMutex
);
848 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
854 OSL_ENSURE(nPos
>= 0 && nPos
< static_cast<sal_Int32
>(m_aBookmarks
.size()),"Invalid Index for vector");
855 if(nPos
< 0 || nPos
>= static_cast<sal_Int32
>(m_aBookmarks
.size()))
856 ::dbtools::throwFunctionSequenceException(*this);
857 return SUCCEEDED(m_pRecordSet
->Move(rows
,m_aBookmarks
[nPos
]));
860 sal_Int32 SAL_CALL
OResultSet::compareBookmarks( const Any
& bookmark1
, const Any
& bookmark2
)
862 ::osl::MutexGuard
aGuard( m_aMutex
);
863 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
869 if(nPos1
== nPos2
) // they should be equal
870 return css::sdbcx::CompareBookmark::EQUAL
;
872 OSL_ENSURE((nPos1
>= 0 && nPos1
< static_cast<sal_Int32
>(m_aBookmarks
.size())) || (nPos1
>= 0 && nPos2
< static_cast<sal_Int32
>(m_aBookmarks
.size())),"Invalid Index for vector");
875 m_pRecordSet
->CompareBookmarks(m_aBookmarks
[nPos1
],m_aBookmarks
[nPos2
],&eNum
);
876 return static_cast<sal_Int32
>(eNum
) - 1;
879 sal_Bool SAL_CALL
OResultSet::hasOrderedBookmarks( )
881 ::osl::MutexGuard
aGuard( m_aMutex
);
882 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
885 WpADOProperties aProps
;
886 m_pRecordSet
->get_Properties(&aProps
);
887 ADOS::ThrowException(static_cast<OConnection
*>(m_pStmt
->getConnection().get())->getConnection(),*this);
888 OSL_ENSURE(aProps
.IsValid(),"There are no properties at the connection");
890 WpADOProperty
aProp(aProps
.GetItem(OUString("Bookmarks Ordered")));
893 aVar
= aProp
.GetValue();
895 ADOS::ThrowException(static_cast<OConnection
*>(m_pStmt
->getConnection().get())->getConnection(),*this);
898 if(!aVar
.isNull() && !aVar
.isEmpty())
899 bValue
= aVar
.getBool();
903 sal_Int32 SAL_CALL
OResultSet::hashBookmark( const Any
& bookmark
)
905 ::osl::MutexGuard
aGuard( m_aMutex
);
906 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
915 Sequence
< sal_Int32
> SAL_CALL
OResultSet::deleteRows( const Sequence
< Any
>& rows
)
917 ::osl::MutexGuard
aGuard( m_aMutex
);
918 checkDisposed(OResultSet_BASE::rBHelper
.bDisposed
);
924 // Create SafeArray Bounds and initialize the array
925 SAFEARRAYBOUND rgsabound
[1];
926 rgsabound
[0].lLbound
= 0;
927 rgsabound
[0].cElements
= rows
.getLength();
928 SAFEARRAY
*psa
= SafeArrayCreate( VT_VARIANT
, 1, rgsabound
);
930 const Any
* pBegin
= rows
.getConstArray();
931 const Any
* pEnd
= pBegin
+ rows
.getLength();
932 for(sal_Int32 i
=0;pBegin
!= pEnd
;++pBegin
,++i
)
935 SafeArrayPutElement(psa
,&i
,&m_aBookmarks
[nPos
]);
938 // Initialize and fill the SafeArray
940 vsa
.setArray(psa
,VT_VARIANT
);
942 m_pRecordSet
->put_Filter(vsa
);
943 m_pRecordSet
->Delete(adAffectGroup
);
944 m_pRecordSet
->UpdateBatch(adAffectGroup
);
946 Sequence
< sal_Int32
> aSeq(rows
.getLength());
949 sal_Int32
* pSeq
= aSeq
.getArray();
953 OSL_ENSURE(i
<aSeq
.getLength(),"Index greater than length of sequence");
954 m_pRecordSet
->get_Status(&pSeq
[i
]);
955 if(pSeq
[i
++] == adRecDeleted
)
963 sal_Int32
OResultSet::getResultSetConcurrency() const
965 sal_Int32 nValue
=ResultSetConcurrency::READ_ONLY
;
967 if(!SUCCEEDED(m_pRecordSet
->get_LockType(&eRet
)))
972 nValue
= ResultSetConcurrency::READ_ONLY
;
975 nValue
= ResultSetConcurrency::UPDATABLE
;
982 sal_Int32
OResultSet::getResultSetType() const
986 if(!SUCCEEDED(m_pRecordSet
->get_CursorType(&eRet
)))
990 case adOpenUnspecified
:
991 case adOpenForwardOnly
:
992 nValue
= ResultSetType::FORWARD_ONLY
;
996 nValue
= ResultSetType::SCROLL_INSENSITIVE
;
999 nValue
= ResultSetType::SCROLL_SENSITIVE
;
1006 sal_Int32
OResultSet::getFetchDirection()
1008 return FetchDirection::FORWARD
;
1011 sal_Int32
OResultSet::getFetchSize() const
1013 sal_Int32 nValue
=-1;
1014 m_pRecordSet
->get_CacheSize(&nValue
);
1018 OUString
OResultSet::getCursorName()
1024 void OResultSet::setFetchDirection(sal_Int32
/*_par0*/)
1026 ::dbtools::throwFeatureNotImplementedSQLException( "ResultSet::FetchDirection", *this );
1029 void OResultSet::setFetchSize(sal_Int32 _par0
)
1031 m_pRecordSet
->put_CacheSize(_par0
);
1034 ::cppu::IPropertyArrayHelper
* OResultSet::createArrayHelper( ) const
1036 return new ::cppu::OPropertyArrayHelper
1040 ::connectivity::OMetaConnection::getPropMap().getNameByIndex(PROPERTY_ID_FETCHDIRECTION
),
1041 PROPERTY_ID_FETCHDIRECTION
, cppu::UnoType
<sal_Int32
>::get(), 0
1044 ::connectivity::OMetaConnection::getPropMap().getNameByIndex(PROPERTY_ID_FETCHSIZE
),
1045 PROPERTY_ID_FETCHSIZE
, cppu::UnoType
<sal_Int32
>::get(), 0
1048 ::connectivity::OMetaConnection::getPropMap().getNameByIndex(PROPERTY_ID_ISBOOKMARKABLE
),
1049 PROPERTY_ID_ISBOOKMARKABLE
, cppu::UnoType
<bool>::get(), PropertyAttribute::READONLY
1052 ::connectivity::OMetaConnection::getPropMap().getNameByIndex(PROPERTY_ID_RESULTSETCONCURRENCY
),
1053 PROPERTY_ID_RESULTSETCONCURRENCY
, cppu::UnoType
<sal_Int32
>::get(), PropertyAttribute::READONLY
1056 ::connectivity::OMetaConnection::getPropMap().getNameByIndex(PROPERTY_ID_RESULTSETTYPE
),
1057 PROPERTY_ID_RESULTSETTYPE
, cppu::UnoType
<sal_Int32
>::get(), PropertyAttribute::READONLY
1063 ::cppu::IPropertyArrayHelper
& OResultSet::getInfoHelper()
1065 return *getArrayHelper();
1068 sal_Bool
OResultSet::convertFastPropertyValue(
1069 Any
& rConvertedValue
,
1076 case PROPERTY_ID_ISBOOKMARKABLE
:
1077 case PROPERTY_ID_CURSORNAME
:
1078 case PROPERTY_ID_RESULTSETCONCURRENCY
:
1079 case PROPERTY_ID_RESULTSETTYPE
:
1080 throw css::lang::IllegalArgumentException();
1082 case PROPERTY_ID_FETCHDIRECTION
:
1083 return ::comphelper::tryPropertyValue(rConvertedValue
, rOldValue
, rValue
, getFetchDirection());
1084 case PROPERTY_ID_FETCHSIZE
:
1085 return ::comphelper::tryPropertyValue(rConvertedValue
, rOldValue
, rValue
, getFetchSize());
1092 void OResultSet::setFastPropertyValue_NoBroadcast(sal_Int32 nHandle
,const Any
& rValue
)
1096 case PROPERTY_ID_ISBOOKMARKABLE
:
1097 case PROPERTY_ID_CURSORNAME
:
1098 case PROPERTY_ID_RESULTSETCONCURRENCY
:
1099 case PROPERTY_ID_RESULTSETTYPE
:
1100 throw Exception("cannot set prop " + OUString::number(nHandle
), nullptr);
1102 case PROPERTY_ID_FETCHDIRECTION
:
1103 setFetchDirection(getINT32(rValue
));
1105 case PROPERTY_ID_FETCHSIZE
:
1106 setFetchSize(getINT32(rValue
));
1113 void OResultSet::getFastPropertyValue(Any
& rValue
,sal_Int32 nHandle
) const
1117 case PROPERTY_ID_ISBOOKMARKABLE
:
1120 m_pRecordSet
->Supports(adBookmark
,&bBool
);
1121 rValue
<<= (bBool
== VARIANT_TRUE
);
1124 case PROPERTY_ID_CURSORNAME
:
1125 rValue
<<= getCursorName();
1127 case PROPERTY_ID_RESULTSETCONCURRENCY
:
1128 rValue
<<= getResultSetConcurrency();
1130 case PROPERTY_ID_RESULTSETTYPE
:
1131 rValue
<<= getResultSetType();
1133 case PROPERTY_ID_FETCHDIRECTION
:
1134 rValue
<<= getFetchDirection();
1136 case PROPERTY_ID_FETCHSIZE
:
1137 rValue
<<= getFetchSize();
1142 void SAL_CALL
OResultSet::acquire() noexcept
1144 OResultSet_BASE::acquire();
1147 void SAL_CALL
OResultSet::release() noexcept
1149 OResultSet_BASE::release();
1152 css::uno::Reference
< css::beans::XPropertySetInfo
> SAL_CALL
OResultSet::getPropertySetInfo( )
1154 return ::cppu::OPropertySetHelper::createPropertySetInfo(getInfoHelper());
1158 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */