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  // MARKER(update_precomp.py): autogen include statement, do not remove
25  #include "precompiled_connectivity.hxx"
26  
27  #include "NDatabaseMetaData.hxx"
28  #include "NConnection.hxx"
29  #include "NResultSet.hxx"
30  #include "propertyids.hxx"
31  #include "resource/evoab2_res.hrc"
32  #include "TSortIndex.hxx"
33  #include <algorithm>
34  
35  #include <com/sun/star/beans/PropertyAttribute.hpp>
36  #include <com/sun/star/lang/DisposedException.hpp>
37  #include <com/sun/star/sdb/ErrorCondition.hpp>
38  #include <com/sun/star/sdbc/DataType.hpp>
39  #include <com/sun/star/sdbc/FetchDirection.hpp>
40  #include <com/sun/star/sdbc/ResultSetConcurrency.hpp>
41  #include <com/sun/star/sdbc/ResultSetType.hpp>
42  
43  #include <comphelper/componentcontext.hxx>
44  #include <comphelper/extract.hxx>
45  #include <comphelper/property.hxx>
46  #include <comphelper/sequence.hxx>
47  #include <comphelper/types.hxx>
48  #include <connectivity/dbexception.hxx>
49  #include <connectivity/sqlerror.hxx>
50  #include <cppuhelper/typeprovider.hxx>
51  #include <rtl/string.hxx>
52  #include <tools/diagnose_ex.h>
53  #include <unotools/syslocale.hxx>
54  #include <unotools/intlwrapper.hxx>
55  
56  #include <cstring>
57  #include <vector>
58  
59  namespace connectivity { namespace evoab {
60  
61  using namespace ::comphelper;
62  using namespace com::sun::star;
63  using namespace com::sun::star::uno;
64  using namespace com::sun::star::lang;
65  using namespace com::sun::star::beans;
66  using namespace com::sun::star::sdbc;
67  using namespace com::sun::star::sdbcx;
68  using namespace com::sun::star::container;
69  using namespace com::sun::star::io;
70  namespace ErrorCondition = ::com::sun::star::sdb::ErrorCondition;
71  
72  //------------------------------------------------------------------------------
getImplementationName()73  ::rtl::OUString SAL_CALL OEvoabResultSet::getImplementationName(  ) throw ( RuntimeException)	\
74  {
75  	return ::rtl::OUString::createFromAscii("com.sun.star.sdbcx.evoab.ResultSet");
76  }
77  // -------------------------------------------------------------------------
getSupportedServiceNames()78   Sequence< ::rtl::OUString > SAL_CALL OEvoabResultSet::getSupportedServiceNames(  ) throw( RuntimeException)
79  {
80  	 Sequence< ::rtl::OUString > aSupported(1);
81  	aSupported[0] = ::rtl::OUString::createFromAscii("com.sun.star.sdbc.ResultSet");
82  	return aSupported;
83  }
84  // -------------------------------------------------------------------------
supportsService(const::rtl::OUString & _rServiceName)85  sal_Bool SAL_CALL OEvoabResultSet::supportsService( const ::rtl::OUString& _rServiceName ) throw( RuntimeException)
86  {
87  	Sequence< ::rtl::OUString > aSupported(getSupportedServiceNames());
88  	const ::rtl::OUString* pSupported = aSupported.getConstArray();
89  	const ::rtl::OUString* pEnd = pSupported + aSupported.getLength();
90  	for (;pSupported != pEnd && !pSupported->equals(_rServiceName); ++pSupported)
91  		;
92  
93  	return pSupported != pEnd;
94  }
95  
96  // -------------------------------------------------------------------------
OEvoabResultSet(OCommonStatement * pStmt,OEvoabConnection * pConnection)97  OEvoabResultSet::OEvoabResultSet( OCommonStatement* pStmt, OEvoabConnection *pConnection )
98  	:OResultSet_BASE(m_aMutex)
99      ,::comphelper::OPropertyContainer( OResultSet_BASE::rBHelper )
100  	,m_pStatement(pStmt)
101  	,m_pConnection(pConnection)
102      ,m_xMetaData(NULL)
103  	,m_bWasNull(sal_True)
104  	,m_nFetchSize(0)
105  	,m_nResultSetType(ResultSetType::SCROLL_INSENSITIVE)
106  	,m_nFetchDirection(FetchDirection::FORWARD)
107  	,m_nResultSetConcurrency(ResultSetConcurrency::READ_ONLY)
108      ,m_pContacts(NULL)
109  	,m_nIndex(-1)
110  	,m_nLength(0)
111  {
112      #define REGISTER_PROP( id, member ) \
113          registerProperty( \
114              OMetaConnection::getPropMap().getNameByIndex( id ), \
115              id, \
116              PropertyAttribute::READONLY, \
117              &member, \
118              ::getCppuType( &member ) \
119          );
120  
121      REGISTER_PROP( PROPERTY_ID_FETCHSIZE, m_nFetchSize );
122      REGISTER_PROP( PROPERTY_ID_RESULTSETTYPE, m_nResultSetType );
123  	REGISTER_PROP( PROPERTY_ID_FETCHDIRECTION, m_nFetchDirection );
124      REGISTER_PROP( PROPERTY_ID_RESULTSETCONCURRENCY, m_nResultSetConcurrency );
125  }
126  
127  // -------------------------------------------------------------------------
~OEvoabResultSet()128  OEvoabResultSet::~OEvoabResultSet()
129  {
130  }
131  
132  // -------------------------------------------------------------------------
133  
134  static ESource *
findSource(const char * name)135  findSource( const char *name )
136  {
137  	ESourceList *pSourceList = NULL;
138  
139  	g_return_val_if_fail (name != NULL, NULL);
140  
141  	if (!e_book_get_addressbooks (&pSourceList, NULL))
142  		pSourceList = NULL;
143  
144  	for ( GSList *g = e_source_list_peek_groups (pSourceList); g; g = g->next)
145  	{
146  		for (GSList *s = e_source_group_peek_sources (E_SOURCE_GROUP (g->data)); s; s = s->next)
147  		{
148  			ESource *pSource = E_SOURCE (s->data);
149  			if (!strcmp (e_source_peek_name (pSource), name))
150  				return pSource;
151  		}
152  	}
153  	return NULL;
154  }
155  
156  static EBook *
openBook(const char * abname)157  openBook( const char *abname )
158  {
159  	ESource *pSource = findSource (abname);
160  	EBook *pBook = NULL;
161  	if (pSource)
162  			pBook = e_book_new (pSource, NULL);
163  
164  	if (pBook && !e_book_open (pBook, TRUE, NULL))
165  	{
166  		g_object_unref (G_OBJECT (pBook));
167  		pBook = NULL;
168  	}
169  
170  	return pBook;
171  }
172  
isLDAP(EBook * pBook)173  static bool isLDAP( EBook *pBook )
174  {
175  	return pBook && !strncmp( "ldap://", e_book_get_uri( pBook ), 6 );
176  }
177  
isLocal(EBook * pBook)178  static bool isLocal( EBook *pBook )
179  {
180  	return pBook && !strncmp( "file://", e_book_get_uri( pBook ), 6 );
181  }
182  
isAuthRequired(EBook * pBook)183  static bool isAuthRequired( EBook *pBook )
184  {
185  	return e_source_get_property( e_book_get_source( pBook ),
186  								  "auth" ) != NULL;
187  }
188  
getUserName(EBook * pBook)189  static rtl::OString getUserName( EBook *pBook )
190  {
191  	rtl::OString aName;
192  	if( isLDAP( pBook ) )
193  		aName = e_source_get_property( e_book_get_source( pBook ), "binddn" );
194  	else
195  		aName = e_source_get_property( e_book_get_source( pBook ), "user" );
196  	return aName;
197  }
198  
199  static ::rtl::OUString
valueToOUString(GValue & _rValue)200  valueToOUString( GValue& _rValue )
201  {
202  	const char *pStr = g_value_get_string( &_rValue );
203  	rtl::OString aStr( pStr ? pStr : "" );
204      ::rtl::OUString sResult( ::rtl::OStringToOUString( aStr, RTL_TEXTENCODING_UTF8 ) );
205  	g_value_unset( &_rValue );
206      return sResult;
207  }
208  
209  static bool
valueToBool(GValue & _rValue)210  valueToBool( GValue& _rValue )
211  {
212  	bool bResult = g_value_get_boolean( &_rValue );
213  	g_value_unset( &_rValue );
214      return bResult;
215  }
216  
217  static bool
executeQuery(EBook * pBook,EBookQuery * pQuery,GList ** ppList,rtl::OString & rPassword,GError ** pError)218  executeQuery (EBook* pBook, EBookQuery* pQuery, GList **ppList,
219  			  rtl::OString &rPassword, GError **pError)
220  {
221  	ESource *pSource = e_book_get_source( pBook );
222  	bool bSuccess = false;
223  	bool bAuthSuccess = true;
224  
225  	*ppList = NULL;
226  
227  	if( isAuthRequired( pBook ) )
228  	{
229  		rtl::OString aUser( getUserName( pBook ) );
230  		const char *pAuth = e_source_get_property( pSource, "auth" );
231  		bAuthSuccess = e_book_authenticate_user( pBook, aUser, rPassword, pAuth, pError );
232  	}
233  
234  	if (bAuthSuccess)
235  		bSuccess = e_book_get_contacts( pBook, pQuery, ppList, pError );
236  
237  	return bSuccess;
238  }
239  
240  static int
whichAddress(int value)241  whichAddress(int value)
242  {
243  	int fieldEnum;
244  	switch (value)
245  	{
246  		case HOME_ADDR_LINE1:
247  		case HOME_ADDR_LINE2:
248  		case HOME_CITY:
249  		case HOME_STATE:
250  		case HOME_COUNTRY:
251  		case HOME_ZIP:
252  			fieldEnum = e_contact_field_id("address_home");
253  			break;
254  
255  		case WORK_ADDR_LINE1:
256  		case WORK_ADDR_LINE2:
257  		case WORK_CITY:
258  		case WORK_STATE:
259  		case WORK_COUNTRY:
260  		case WORK_ZIP:
261  			fieldEnum = e_contact_field_id("address_work");
262  			break;
263  
264  		case OTHER_ADDR_LINE1:
265  		case OTHER_ADDR_LINE2:
266  		case OTHER_CITY:
267  		case OTHER_STATE:
268  		case OTHER_COUNTRY:
269  		case OTHER_ZIP:
270  			fieldEnum = e_contact_field_id("address_other");
271  			break;
272  
273  	    	default: fieldEnum = e_contact_field_id("address_home");
274  	  }
275  	return fieldEnum;
276  }
277  
278  /*
279  * This function decides the default column values based on the first field of EContactAddress.
280  * The search order is Work->Home->other(defaults).
281  */
282  static EContactAddress *
getDefaultContactAddress(EContact * pContact,int * value)283  getDefaultContactAddress( EContact *pContact,int *value )
284  {
285  	EContactAddress *ec = (EContactAddress *)e_contact_get(pContact,whichAddress(WORK_ADDR_LINE1));
286  	if ( ec && (strlen(ec->street)>0) )
287  	{
288  		*value= *value +WORK_ADDR_LINE1 -1;
289  		return ec;
290  	}
291  	else
292  		{
293  			ec = (EContactAddress *)e_contact_get(pContact,whichAddress(HOME_ADDR_LINE1));
294  			if ( ec && (strlen(ec->street)>0) )
295  			{
296  				*value=*value+HOME_ADDR_LINE1-1;
297  				return ec;
298  			}
299  		}
300  
301  	*value=*value+OTHER_ADDR_LINE1-1;
302  	return (EContactAddress *)e_contact_get(pContact,whichAddress(OTHER_ADDR_LINE1));
303  }
304  
305  static EContactAddress*
getContactAddress(EContact * pContact,int * address_enum)306  getContactAddress( EContact *pContact, int * address_enum )
307  {
308  	EContactAddress *ec = NULL;
309      switch (*address_enum) {
310  
311          case DEFAULT_ADDR_LINE1:
312          case DEFAULT_ADDR_LINE2:
313          case DEFAULT_CITY:
314          case DEFAULT_STATE:
315          case DEFAULT_COUNTRY:
316          case DEFAULT_ZIP:
317  			ec = getDefaultContactAddress(pContact,address_enum);break;
318     		default:
319  			ec = (EContactAddress *)e_contact_get(pContact,whichAddress(*address_enum));
320      }
321  	return ec;
322  }
323  
324  static bool
handleSplitAddress(EContact * pContact,GValue * pStackValue,int value)325  handleSplitAddress( EContact *pContact,GValue *pStackValue, int value )
326  {
327  	EContactAddress *ec = getContactAddress(pContact,&value) ;
328  
329  	if (ec==NULL)
330  		return true;
331  
332  	switch (value) {
333      	case WORK_ADDR_LINE1:
334  		    g_value_set_string(pStackValue,ec->street ); break;
335  	    case WORK_ADDR_LINE2:
336  		    g_value_set_string(pStackValue,ec->po ); break;
337      	case WORK_CITY:
338  	    	g_value_set_string(pStackValue,ec->locality ); break;
339      	case WORK_STATE:
340   	    	g_value_set_string(pStackValue,ec->region ); break;
341      	case WORK_COUNTRY:
342  	    	g_value_set_string(pStackValue,ec->country ); break;
343      	case WORK_ZIP:
344  	    	g_value_set_string(pStackValue,ec->code ); break;
345  
346          case HOME_ADDR_LINE1:
347  			g_value_set_string(pStackValue,ec->street ); break;
348          case HOME_ADDR_LINE2:
349  			g_value_set_string(pStackValue,ec->po ); break;
350          case HOME_CITY:
351  			g_value_set_string(pStackValue,ec->locality ); break;
352          case HOME_STATE:
353  			g_value_set_string(pStackValue,ec->region ); break;
354          case HOME_COUNTRY:
355  			g_value_set_string(pStackValue,ec->country ); break;
356          case HOME_ZIP:
357  			g_value_set_string(pStackValue,ec->code ); break;
358  
359          case OTHER_ADDR_LINE1:
360  			g_value_set_string(pStackValue,ec->street ); break;
361          case OTHER_ADDR_LINE2:
362  			g_value_set_string(pStackValue,ec->po ); break;
363          case OTHER_CITY:
364  			g_value_set_string(pStackValue,ec->locality ); break;
365          case OTHER_STATE:
366  			g_value_set_string(pStackValue,ec->region ); break;
367          case OTHER_COUNTRY:
368  			g_value_set_string(pStackValue,ec->country ); break;
369          case OTHER_ZIP:
370  			g_value_set_string(pStackValue,ec->code ); break;
371  
372  	}
373  
374      return false;
375  }
376  static bool
getValue(EContact * pContact,sal_Int32 nColumnNum,GType nType,GValue * pStackValue,bool & _out_rWasNull)377  getValue( EContact* pContact, sal_Int32 nColumnNum, GType nType, GValue* pStackValue, bool& _out_rWasNull )
378  {
379  	const ColumnProperty * pSpecs = evoab::getField( nColumnNum );
380  	if ( !pSpecs )
381  		return false;
382  
383  	GParamSpec* pSpec = pSpecs->pField;
384  	gboolean bIsSplittedColumn = pSpecs->bIsSplittedValue;
385  
386  	_out_rWasNull = true;
387  	if ( !pSpec || !pContact)
388  		return false;
389  
390  	if ( G_PARAM_SPEC_VALUE_TYPE (pSpec) != nType )
391  	{
392  
393  		OSL_TRACE( "Wrong type (0x%x) (0x%x) '%s'",
394  				   (int)G_PARAM_SPEC_VALUE_TYPE (pSpec), (int) nType,
395  				   pSpec->name ? pSpec->name : "<noname>");
396  		return false;
397  	}
398  
399      g_value_init( pStackValue, nType );
400  	if ( bIsSplittedColumn )
401  	{
402          const SplitEvoColumns* evo_addr( get_evo_addr() );
403  		for (int i=0;i<OTHER_ZIP;i++)
404  		{
405  			if (0 == strcmp (g_param_spec_get_name ((GParamSpec *)pSpec), evo_addr[i].pColumnName))
406  			{
407  				_out_rWasNull = handleSplitAddress( pContact, pStackValue, evo_addr[i].value );
408  				return true;
409  			}
410  		}
411  	}
412  	else
413  	{
414  		g_object_get_property( G_OBJECT (pContact),
415  							   g_param_spec_get_name ((GParamSpec *) pSpec),
416  							   pStackValue );
417  		if ( G_VALUE_TYPE( pStackValue ) != nType )
418  		{
419  			OSL_TRACE( "Fetched type mismatch" );
420  			g_value_unset( pStackValue );
421  			return false;
422  		}
423  	}
424  	_out_rWasNull = false;
425  	return true;
426  }
427  
428  namespace
429  {
430      struct ComparisonData
431      {
432          const SortDescriptor&   rSortOrder;
433          IntlWrapper             aIntlWrapper;
434  
ComparisonDataconnectivity::evoab::__anonf578c7320111::ComparisonData435          ComparisonData( const SortDescriptor& _rSortOrder, const Reference< XMultiServiceFactory >& _rxFactory )
436              :rSortOrder( _rSortOrder )
437              ,aIntlWrapper( _rxFactory, SvtSysLocale().GetLocaleData().getLocale() )
438          {
439          }
440      };
441  }
442  
443  extern "C"
CompareContacts(gconstpointer _lhs,gconstpointer _rhs,gpointer _userData)444  int CompareContacts( gconstpointer _lhs, gconstpointer _rhs, gpointer _userData )
445  {
446      EContact* lhs = static_cast< EContact* >( const_cast< gpointer >( _lhs ) );
447      EContact* rhs = static_cast< EContact* >( const_cast< gpointer >( _rhs ) );
448  
449      GValue aLhsValue = { 0, { { 0 } } };
450      GValue aRhsValue = { 0, { { 0 } } };
451      bool bLhsNull = true;
452      bool bRhsNull = true;
453  
454      ::rtl::OUString sLhs, sRhs;
455      bool bLhs(false), bRhs(false);
456  
457      const ComparisonData& rCompData = *static_cast< const ComparisonData* >( _userData );
458      for (   SortDescriptor::const_iterator sortCol = rCompData.rSortOrder.begin();
459              sortCol != rCompData.rSortOrder.end();
460              ++sortCol
461          )
462      {
463          sal_Int32 nField = sortCol->nField;
464          GType eFieldType = evoab::getGFieldType( nField );
465  
466          bool success =  getValue( lhs, nField, eFieldType, &aLhsValue, bLhsNull )
467                      &&  getValue( rhs, nField, eFieldType, &aRhsValue, bRhsNull );
468          OSL_ENSURE( success, "CompareContacts: could not retrieve both values!" );
469          if ( !success )
470              return 0;
471  
472          if ( bLhsNull && !bRhsNull )
473              return -1;
474          if ( !bLhsNull && bRhsNull )
475              return 1;
476          if ( bLhsNull && bRhsNull )
477              continue;
478  
479          if ( eFieldType == G_TYPE_STRING )
480          {
481              sLhs = valueToOUString( aLhsValue );
482              sRhs = valueToOUString( aRhsValue );
483              sal_Int32 nCompResult = rCompData.aIntlWrapper.getCaseCollator()->compareString( sLhs, sRhs );
484              if ( nCompResult != 0 )
485                  return nCompResult;
486              continue;
487          }
488  
489          bLhs = valueToBool( aLhsValue );
490          bRhs = valueToBool( aRhsValue );
491          if ( bLhs && !bRhs )
492              return -1;
493          if ( !bLhs && bRhs )
494              return 1;
495          continue;
496      }
497  
498      return 0;
499  }
500  
501  static GList*
sortContacts(GList * _pContactList,const ComparisonData & _rCompData)502  sortContacts( GList* _pContactList, const ComparisonData& _rCompData )
503  {
504      OSL_ENSURE( !_rCompData.rSortOrder.empty(), "sortContacts: no need to call this without any sort order!" );
505      ENSURE_OR_THROW( _rCompData.aIntlWrapper.getCaseCollator(), "no collator for comparing strings" );
506  
507      return g_list_sort_with_data( _pContactList, &CompareContacts, const_cast< gpointer >( static_cast< gconstpointer >( &_rCompData ) ) );
508  }
509  
510  // -------------------------------------------------------------------------
construct(const QueryData & _rData)511  void OEvoabResultSet::construct( const QueryData& _rData )
512  {
513      ENSURE_OR_THROW( _rData.getQuery(), "internal error: no EBookQuery" );
514  
515      EBook *pBook = openBook( ::rtl::OUStringToOString( _rData.sTable, RTL_TEXTENCODING_UTF8 ) );
516      if ( !pBook )
517          m_pConnection->throwGenericSQLException( STR_CANNOT_OPEN_BOOK, *this );
518  
519  	g_list_free(m_pContacts);
520  	m_pContacts = NULL;
521      bool bExecuteQuery = true;
522      switch ( _rData.eFilterType )
523      {
524          case eFilterNone:
525              if ( !isLocal( pBook ) )
526              {
527                  SQLError aErrorFactory( m_pConnection->getDriver().getMSFactory() );
528                  SQLException aAsException = aErrorFactory.getSQLException( ErrorCondition::DATA_CANNOT_SELECT_UNFILTERED, *this );
529                  m_aWarnings.appendWarning( SQLWarning(
530                      aAsException.Message,
531                      aAsException.Context,
532                      aAsException.SQLState,
533                      aAsException.ErrorCode,
534                      aAsException.NextException
535                  ) );
536                  bExecuteQuery = false;
537              }
538              break;
539          case eFilterAlwaysFalse:
540              bExecuteQuery = false;
541              break;
542          case eFilterOther:
543              bExecuteQuery = true;
544              break;
545      }
546      if ( bExecuteQuery )
547  	{
548  		rtl::OString aPassword = m_pConnection->getPassword();
549  		executeQuery( pBook, _rData.getQuery(), &m_pContacts, aPassword, NULL );
550  		m_pConnection->setPassword( aPassword );
551  
552          if ( m_pContacts && !_rData.aSortOrder.empty() )
553          {
554              ComparisonData aCompData( _rData.aSortOrder, getConnection()->getDriver().getMSFactory() );
555              m_pContacts = sortContacts( m_pContacts, aCompData );
556          }
557  	}
558  	m_nLength = g_list_length( m_pContacts );
559  	OSL_TRACE( "Query return %d records", m_nLength );
560  	m_nIndex = -1;
561  
562      // create our meta data (need the EBookQuery for this)
563      OEvoabResultSetMetaData* pMeta = new OEvoabResultSetMetaData( _rData.sTable );
564  	m_xMetaData = pMeta;
565  
566  	pMeta->setEvoabFields( _rData.xSelectColumns );
567  }
568  
569  // -------------------------------------------------------------------------
disposing(void)570  void OEvoabResultSet::disposing(void)
571  {
572  	::comphelper::OPropertyContainer::disposing();
573  
574  	::osl::MutexGuard aGuard(m_aMutex);
575  	g_list_free(m_pContacts);
576  	m_pContacts = NULL;
577  	m_pStatement = NULL;
578  m_xMetaData.clear();
579  }
580  // -------------------------------------------------------------------------
queryInterface(const Type & rType)581  Any SAL_CALL OEvoabResultSet::queryInterface( const Type & rType ) throw(RuntimeException)
582  {
583  	Any aRet = ::comphelper::OPropertyContainer::queryInterface(rType);
584  	if(!aRet.hasValue())
585  		aRet = OResultSet_BASE::queryInterface(rType);
586  	return aRet;
587  }
588  // -------------------------------------------------------------------------
getTypes()589  Sequence< Type > SAL_CALL OEvoabResultSet::getTypes(  ) throw( RuntimeException)
590  {
591  	return ::comphelper::concatSequences(
592          OResultSet_BASE::getTypes(),
593          ::comphelper::OPropertyContainer::getTypes()
594      );
595  }
596  
597  // -------------------------------------------------------------------------
598  // XRow Interface
599  
600  /**
601   * getString:
602   * @nColumnNum: The column index from the table.
603   *
604   * If the equivalent NResultSetMetaData.cxx marks the columntype of
605   * nColumnNum as DataType::VARCHAR this accessor is used.
606   */
getString(sal_Int32 nColumnNum)607  ::rtl::OUString SAL_CALL OEvoabResultSet::getString( sal_Int32 nColumnNum ) throw(SQLException, RuntimeException)
608  {
609  	::osl::MutexGuard aGuard( m_aMutex );
610  	checkDisposed(OResultSet_BASE::rBHelper.bDisposed);
611  	rtl::OUString aResult;
612  	if ( m_xMetaData.is())
613      {
614          OEvoabResultSetMetaData *pMeta = (OEvoabResultSetMetaData *) m_xMetaData.get();
615          sal_Int32 nFieldNumber = pMeta->fieldAtColumn(nColumnNum);
616  		GValue aValue = { 0, { { 0 } } };
617  		if ( getValue( getCur(), nFieldNumber, G_TYPE_STRING, &aValue, m_bWasNull ) )
618              aResult = valueToOUString( aValue );
619  	}
620  	return aResult;
621  }
622  // -------------------------------------------------------------------------
getBoolean(sal_Int32 nColumnNum)623  sal_Bool SAL_CALL OEvoabResultSet::getBoolean( sal_Int32 nColumnNum ) throw(SQLException, RuntimeException)
624  {
625  	::osl::MutexGuard aGuard( m_aMutex );
626  	checkDisposed(OResultSet_BASE::rBHelper.bDisposed);
627  	sal_Bool bResult = sal_False;
628  
629  	if ( m_xMetaData.is())
630      {
631          OEvoabResultSetMetaData *pMeta = (OEvoabResultSetMetaData *) m_xMetaData.get();
632          sal_Int32 nFieldNumber = pMeta->fieldAtColumn(nColumnNum);
633  		GValue aValue = { 0, { { 0 } } };
634  		if ( getValue( getCur(), nFieldNumber, G_TYPE_BOOLEAN, &aValue, m_bWasNull ) )
635              bResult = valueToBool( aValue );
636  	}
637  	return bResult ? sal_True : sal_False;
638  }
639  // -------------------------------------------------------------------------
getLong(sal_Int32)640  sal_Int64 SAL_CALL OEvoabResultSet::getLong( sal_Int32 /*nColumnNum*/ ) throw(SQLException, RuntimeException)
641  {
642      ::dbtools::throwFunctionNotSupportedException( "XRow::getLong", *this );
643  	return sal_Int64();
644  }
645  // -------------------------------------------------------------------------
getArray(sal_Int32)646  Reference< XArray > SAL_CALL OEvoabResultSet::getArray( sal_Int32 /*nColumnNum*/ ) throw(SQLException, RuntimeException)
647  {
648      ::dbtools::throwFunctionNotSupportedException( "XRow::getArray", *this );
649  	return NULL;
650  }
651  // -------------------------------------------------------------------------
getClob(sal_Int32)652  Reference< XClob > SAL_CALL OEvoabResultSet::getClob( sal_Int32 /*nColumnNum*/ ) throw(SQLException, RuntimeException)
653  {
654      ::dbtools::throwFunctionNotSupportedException( "XRow::getClob", *this );
655  	return NULL;
656  }
657  // -------------------------------------------------------------------------
getBlob(sal_Int32)658  Reference< XBlob > SAL_CALL OEvoabResultSet::getBlob( sal_Int32 /*nColumnNum*/ ) throw(SQLException, RuntimeException)
659  {
660      ::dbtools::throwFunctionNotSupportedException( "XRow::getBlob", *this );
661  	return NULL;
662  }
663  // -------------------------------------------------------------------------
getRef(sal_Int32)664  Reference< XRef > SAL_CALL OEvoabResultSet::getRef( sal_Int32 /*nColumnNum*/ ) throw(SQLException, RuntimeException)
665  {
666      ::dbtools::throwFunctionNotSupportedException( "XRow::getRef", *this );
667  	return NULL;
668  }
669  // -------------------------------------------------------------------------
getObject(sal_Int32,const Reference<::com::sun::star::container::XNameAccess> &)670  Any SAL_CALL OEvoabResultSet::getObject( sal_Int32 /*nColumnNum*/, const Reference< ::com::sun::star::container::XNameAccess >& /*typeMap*/ ) throw(SQLException, RuntimeException)
671  {
672      ::dbtools::throwFunctionNotSupportedException( "XRow::getObject", *this );
673  	return Any();
674  }
675  // -------------------------------------------------------------------------
getShort(sal_Int32)676  sal_Int16 SAL_CALL OEvoabResultSet::getShort( sal_Int32 /*nColumnNum*/ ) throw(SQLException, RuntimeException)
677  {
678      ::dbtools::throwFunctionNotSupportedException( "XRow::getShort", *this );
679  	return 0;
680  }
681  // -------------------------------------------------------------------------
getTime(sal_Int32)682  ::com::sun::star::util::Time SAL_CALL OEvoabResultSet::getTime( sal_Int32 /*nColumnNum*/ ) throw(SQLException, RuntimeException)
683  {
684      ::dbtools::throwFunctionNotSupportedException( "XRow::getTime", *this );
685  	return ::com::sun::star::util::Time();
686  }
687  // -------------------------------------------------------------------------
getTimestamp(sal_Int32)688  util::DateTime SAL_CALL OEvoabResultSet::getTimestamp( sal_Int32 /*nColumnNum*/ ) throw(SQLException, RuntimeException)
689  {
690      ::dbtools::throwFunctionNotSupportedException( "XRow::getTimestamp", *this );
691  	return ::com::sun::star::util::DateTime();
692  }
693  // -------------------------------------------------------------------------
getBinaryStream(sal_Int32)694  Reference< XInputStream > SAL_CALL OEvoabResultSet::getBinaryStream( sal_Int32 /*nColumnNum*/ ) throw(SQLException, RuntimeException)
695  {
696      ::dbtools::throwFunctionNotSupportedException( "XRow::getBinaryStream", *this );
697  	return NULL;
698  }
699  // -------------------------------------------------------------------------
getCharacterStream(sal_Int32)700  Reference< XInputStream > SAL_CALL OEvoabResultSet::getCharacterStream( sal_Int32 /*nColumnNum*/ ) throw(SQLException, RuntimeException)
701  {
702      ::dbtools::throwFunctionNotSupportedException( "XRow::getCharacterStream", *this );
703  	return NULL;
704  }
705  // -------------------------------------------------------------------------
getByte(sal_Int32)706  sal_Int8 SAL_CALL OEvoabResultSet::getByte( sal_Int32 /*nColumnNum*/ ) throw(SQLException, RuntimeException)
707  {
708      ::dbtools::throwFunctionNotSupportedException( "XRow::getByte", *this );
709  	return 0;
710  }
711  // -------------------------------------------------------------------------
getBytes(sal_Int32)712  Sequence< sal_Int8 > SAL_CALL OEvoabResultSet::getBytes( sal_Int32 /*nColumnNum*/ ) throw(SQLException, RuntimeException)
713  {
714      ::dbtools::throwFunctionNotSupportedException( "XRow::getBytes", *this );
715  	return Sequence< sal_Int8 >();
716  }
717  // -------------------------------------------------------------------------
getDate(sal_Int32)718  ::com::sun::star::util::Date SAL_CALL OEvoabResultSet::getDate( sal_Int32 /*nColumnNum*/ ) throw(SQLException, RuntimeException)
719  {
720      ::dbtools::throwFunctionNotSupportedException( "XRow::getDate", *this );
721  	return ::com::sun::star::util::Date();
722  }
723  // -------------------------------------------------------------------------
getDouble(sal_Int32)724  double SAL_CALL OEvoabResultSet::getDouble( sal_Int32 /*nColumnNum*/ ) throw(SQLException, RuntimeException)
725  {
726      ::dbtools::throwFunctionNotSupportedException( "XRow::getDouble", *this );
727  	return 0;
728  }
729  // -------------------------------------------------------------------------
getFloat(sal_Int32)730  float SAL_CALL OEvoabResultSet::getFloat( sal_Int32 /*nColumnNum*/ ) throw(SQLException, RuntimeException)
731  {
732      ::dbtools::throwFunctionNotSupportedException( "XRow::getFloat", *this );
733  	return 0;
734  }
735  // -------------------------------------------------------------------------
getInt(sal_Int32)736  sal_Int32 SAL_CALL OEvoabResultSet::getInt( sal_Int32 /*nColumnNum*/ ) throw(SQLException, RuntimeException)
737  {
738      ::dbtools::throwFunctionNotSupportedException( "XRow::getInt", *this );
739  	return 0;
740  }
741  // XRow Interface Ends
742  // -------------------------------------------------------------------------
743  
744  // XResultSetMetaDataSupplier Interface
getMetaData()745  Reference< XResultSetMetaData > SAL_CALL OEvoabResultSet::getMetaData(  ) throw(SQLException, RuntimeException)
746  {
747  	::osl::MutexGuard aGuard( m_aMutex );
748  	checkDisposed(OResultSet_BASE::rBHelper.bDisposed);
749  
750      // the meta data should have been created at construction time
751      ENSURE_OR_THROW( m_xMetaData.is(), "internal error: no meta data" );
752  	return m_xMetaData;
753  }
754  // XResultSetMetaDataSupplier Interface Ends
755  // -------------------------------------------------------------------------
756  
757  // XResultSet Interface
next()758  sal_Bool SAL_CALL OEvoabResultSet::next(  ) throw(SQLException, RuntimeException)
759  {
760  	::osl::MutexGuard aGuard( m_aMutex );
761  	checkDisposed(OResultSet_BASE::rBHelper.bDisposed);
762  	if (m_nIndex+1 < m_nLength) {
763  		++m_nIndex ;
764  		return true;
765  	}
766  	else
767  		return false;
768  }
769  // -------------------------------------------------------------------------
wasNull()770  sal_Bool SAL_CALL OEvoabResultSet::wasNull(  ) throw(SQLException, RuntimeException)
771  {
772  	::osl::MutexGuard aGuard( m_aMutex );
773  	checkDisposed(OResultSet_BASE::rBHelper.bDisposed);
774  
775  	return m_bWasNull;
776  }
777  // -------------------------------------------------------------------------
isBeforeFirst()778  sal_Bool SAL_CALL OEvoabResultSet::isBeforeFirst(  ) throw(SQLException, RuntimeException)
779  {
780  	::osl::MutexGuard aGuard( m_aMutex );
781  	checkDisposed(OResultSet_BASE::rBHelper.bDisposed);
782  
783  	return m_nIndex < 0;
784  }
785  // -------------------------------------------------------------------------
getRow()786  sal_Int32 SAL_CALL OEvoabResultSet::getRow(  ) throw(SQLException, RuntimeException)
787  {
788  	::osl::MutexGuard aGuard( m_aMutex );
789  	checkDisposed(OResultSet_BASE::rBHelper.bDisposed);
790  
791  	return m_nIndex;
792  }
793  // -------------------------------------------------------------------------
isAfterLast()794  sal_Bool SAL_CALL OEvoabResultSet::isAfterLast(  ) throw(SQLException, RuntimeException)
795  {
796  	::osl::MutexGuard aGuard( m_aMutex );
797  	checkDisposed(OResultSet_BASE::rBHelper.bDisposed);
798  
799  	return m_nIndex >= m_nLength;
800  }
801  // -------------------------------------------------------------------------
isFirst()802  sal_Bool SAL_CALL OEvoabResultSet::isFirst(  ) throw(SQLException, RuntimeException)
803  {
804  	::osl::MutexGuard aGuard( m_aMutex );
805  	checkDisposed(OResultSet_BASE::rBHelper.bDisposed);
806  
807  	return m_nIndex == 0;
808  }
809  // -------------------------------------------------------------------------
isLast()810  sal_Bool SAL_CALL OEvoabResultSet::isLast(  ) throw(SQLException, RuntimeException)
811  {
812  	::osl::MutexGuard aGuard( m_aMutex );
813  	checkDisposed(OResultSet_BASE::rBHelper.bDisposed);
814  
815  	return m_nIndex == m_nLength - 1;
816  }
817  // -------------------------------------------------------------------------
beforeFirst()818  void SAL_CALL OEvoabResultSet::beforeFirst(  ) throw(SQLException, RuntimeException)
819  {
820  	::osl::MutexGuard aGuard( m_aMutex );
821  	checkDisposed(OResultSet_BASE::rBHelper.bDisposed);
822  
823  	m_nIndex = -1;
824  }
825  // -------------------------------------------------------------------------
afterLast()826  void SAL_CALL OEvoabResultSet::afterLast(  ) throw(SQLException, RuntimeException)
827  {
828  	::osl::MutexGuard aGuard( m_aMutex );
829  	checkDisposed(OResultSet_BASE::rBHelper.bDisposed);
830  
831  	m_nIndex = m_nLength;
832  }
833  // -------------------------------------------------------------------------
834  
first()835  sal_Bool SAL_CALL OEvoabResultSet::first(  ) throw(SQLException, RuntimeException)
836  {
837  	::osl::MutexGuard aGuard( m_aMutex );
838  	checkDisposed(OResultSet_BASE::rBHelper.bDisposed);
839  
840  	m_nIndex = 0;
841  	return true;
842  }
843  // -------------------------------------------------------------------------
844  
last()845  sal_Bool SAL_CALL OEvoabResultSet::last(  ) throw(SQLException, RuntimeException)
846  {
847  	::osl::MutexGuard aGuard( m_aMutex );
848  	checkDisposed(OResultSet_BASE::rBHelper.bDisposed);
849  
850  	m_nIndex = m_nLength - 1;
851  	return true;
852  }
853  // -------------------------------------------------------------------------
absolute(sal_Int32 row)854  sal_Bool SAL_CALL OEvoabResultSet::absolute( sal_Int32 row ) throw(SQLException, RuntimeException)
855  {
856  	::osl::MutexGuard aGuard( m_aMutex );
857  	checkDisposed(OResultSet_BASE::rBHelper.bDisposed);
858  	if (row < m_nLength) {
859  		m_nIndex = row;
860  		return true;
861  	}
862  	else
863  		return false;
864  }
865  // -------------------------------------------------------------------------
relative(sal_Int32 row)866  sal_Bool SAL_CALL OEvoabResultSet::relative( sal_Int32 row ) throw(SQLException, RuntimeException)
867  {
868  	::osl::MutexGuard aGuard( m_aMutex );
869  	checkDisposed(OResultSet_BASE::rBHelper.bDisposed);
870  
871  	if ((m_nIndex+row) < m_nLength) {
872  		m_nIndex += row;
873  		return true;
874  	}
875  	else
876  		return false;
877  }
878  // -------------------------------------------------------------------------
previous()879  sal_Bool SAL_CALL OEvoabResultSet::previous(  ) throw(SQLException, RuntimeException)
880  {
881  	::osl::MutexGuard aGuard( m_aMutex );
882  	checkDisposed(OResultSet_BASE::rBHelper.bDisposed);
883  
884  	if(m_nIndex > 0) {
885  		m_nIndex--;
886  		return true;
887  	}
888          else
889  		return false;
890  }
891  // -------------------------------------------------------------------------
getStatement()892  Reference< XInterface > SAL_CALL OEvoabResultSet::getStatement(  ) throw(SQLException, RuntimeException)
893  {
894  	::osl::MutexGuard aGuard( m_aMutex );
895  	checkDisposed(OResultSet_BASE::rBHelper.bDisposed);
896  ::com::sun::star::uno::WeakReferenceHelper      aStatement((OWeakObject*)m_pStatement);
897  	return aStatement.get();
898  }
899  // -------------------------------------------------------------------------
900  
rowDeleted()901  sal_Bool SAL_CALL OEvoabResultSet::rowDeleted(  ) throw(SQLException, RuntimeException)
902  {
903  	::osl::MutexGuard aGuard( m_aMutex );
904  	checkDisposed(OResultSet_BASE::rBHelper.bDisposed);
905  
906  	return sal_False;
907  }
908  // -------------------------------------------------------------------------
rowInserted()909  sal_Bool SAL_CALL OEvoabResultSet::rowInserted(  ) throw(SQLException, RuntimeException)
910  {
911  	::osl::MutexGuard aGuard( m_aMutex );
912  	checkDisposed(OResultSet_BASE::rBHelper.bDisposed);
913  
914  	return sal_False;
915  }
916  // -------------------------------------------------------------------------
rowUpdated()917  sal_Bool SAL_CALL OEvoabResultSet::rowUpdated(  ) throw(SQLException, RuntimeException)
918  {
919  	::osl::MutexGuard aGuard( m_aMutex );
920  	checkDisposed(OResultSet_BASE::rBHelper.bDisposed);
921  
922  	return sal_False;
923  }
924  // -------------------------------------------------------------------------
refreshRow()925  void SAL_CALL OEvoabResultSet::refreshRow(  ) throw(SQLException, RuntimeException)
926  {
927  	::osl::MutexGuard aGuard( m_aMutex );
928  	checkDisposed(OResultSet_BASE::rBHelper.bDisposed);
929  }
930  //XResult Interface ends
931  // -------------------------------------------------------------------------
932  // XCancellable
933  
cancel()934  void SAL_CALL OEvoabResultSet::cancel(  ) throw(RuntimeException)
935  {
936  	::osl::MutexGuard aGuard( m_aMutex );
937  	checkDisposed(OResultSet_BASE::rBHelper.bDisposed);
938  	OSL_TRACE("In/Out: OEvoabResultSet::cancel" );
939  
940  }
941  
942  //XCloseable
close()943  void SAL_CALL OEvoabResultSet::close(  ) throw(SQLException, RuntimeException)
944  {
945  	{
946  		::osl::MutexGuard aGuard( m_aMutex );
947  		checkDisposed(OResultSet_BASE::rBHelper.bDisposed);
948  	}
949  	OSL_TRACE("In/Out: OEvoabResultSet::close" );
950  	dispose();
951  }
952  
953  // XWarningsSupplier
954  // -------------------------------------------------------------------------
clearWarnings()955  void SAL_CALL OEvoabResultSet::clearWarnings(  ) throw(SQLException, RuntimeException)
956  {
957  	OSL_TRACE("In/Out: OEvoabResultSet::clearWarnings" );
958      m_aWarnings.clearWarnings();
959  }
960  // -------------------------------------------------------------------------
getWarnings()961  Any SAL_CALL OEvoabResultSet::getWarnings(  ) throw(SQLException, RuntimeException)
962  {
963  	OSL_TRACE("In/Out: OEvoabResultSet::getWarnings" );
964      return m_aWarnings.getWarnings();
965  }
966  // -------------------------------------------------------------------------
967  //XColumnLocate Interface
findColumn(const::rtl::OUString & columnName)968  sal_Int32 SAL_CALL OEvoabResultSet::findColumn( const ::rtl::OUString& columnName ) throw(SQLException, RuntimeException)
969  {
970  	::osl::MutexGuard aGuard( m_aMutex );
971  	checkDisposed(OResultSet_BASE::rBHelper.bDisposed);
972  
973  	// find the first column with the name columnName
974  	Reference< XResultSetMetaData > xMeta = getMetaData();
975  	sal_Int32 nLen = xMeta->getColumnCount();
976  	sal_Int32 i = 1;
977  	for(;i<=nLen;++i)
978  		if(xMeta->isCaseSensitive(i) ? columnName == xMeta->getColumnName(i) :
979  				columnName.equalsIgnoreAsciiCase(xMeta->getColumnName(i)))
980  			break;
981  	return i;
982  }
983  // -------------------------------------------------------------------------
984  //XColumnLocate interface ends
985  
986  // -------------------------------------------------------------------------
createArrayHelper() const987  ::cppu::IPropertyArrayHelper* OEvoabResultSet::createArrayHelper( ) const
988  {
989      Sequence< Property > aProps;
990      describeProperties( aProps );
991      return new ::cppu::OPropertyArrayHelper( aProps );
992  }
993  // -------------------------------------------------------------------------
getInfoHelper()994  ::cppu::IPropertyArrayHelper & OEvoabResultSet::getInfoHelper()
995  {
996  	return *const_cast<OEvoabResultSet*>(this)->getArrayHelper();
997  }
998  // -----------------------------------------------------------------------------
acquire()999  void SAL_CALL OEvoabResultSet::acquire() throw()
1000  {
1001  	OResultSet_BASE::acquire();
1002  }
1003  // -----------------------------------------------------------------------------
release()1004  void SAL_CALL OEvoabResultSet::release() throw()
1005  {
1006  	OResultSet_BASE::release();
1007  }
1008  // -----------------------------------------------------------------------------
1009  ::com::sun::star::uno::Reference< ::com::sun::star::beans::XPropertySetInfo > SAL_CALL
getPropertySetInfo()1010  OEvoabResultSet::getPropertySetInfo(  ) throw(::com::sun::star::uno::RuntimeException)
1011  {
1012  	return ::cppu::OPropertySetHelper::createPropertySetInfo(getInfoHelper());
1013  }
1014  // -----------------------------------------------------------------------------
1015  
1016  } } // connectivity::evoab
1017