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 ************************************************************************/
30 /**************************************************************************
32 **************************************************************************
34 *************************************************************************/
38 #include "osl/diagnose.h"
39 #include "ucbhelper/contentidentifier.hxx"
41 #include "tdoc_datasupplier.hxx"
42 #include "tdoc_content.hxx"
44 using namespace com::sun::star
;
45 using namespace tdoc_ucp
;
50 //=========================================================================
52 // struct ResultListEntry.
54 //=========================================================================
56 struct ResultListEntry
59 uno::Reference
< ucb::XContentIdentifier
> xId
;
60 uno::Reference
< ucb::XContent
> xContent
;
61 uno::Reference
< sdbc::XRow
> xRow
;
63 ResultListEntry( const rtl::OUString
& rURL
) : aURL( rURL
) {}
66 //=========================================================================
70 //=========================================================================
72 typedef std::vector
< ResultListEntry
* > ResultList
;
74 //=========================================================================
76 // struct DataSupplier_Impl.
78 //=========================================================================
80 struct DataSupplier_Impl
83 ResultList m_aResults
;
84 rtl::Reference
< Content
> m_xContent
;
85 uno::Reference
< lang::XMultiServiceFactory
> m_xSMgr
;
86 uno::Sequence
< rtl::OUString
> * m_pNamesOfChildren
;
87 sal_Int32 m_nOpenMode
;
89 bool m_bThrowException
;
92 const uno::Reference
< lang::XMultiServiceFactory
>& rxSMgr
,
93 const rtl::Reference
< Content
>& rContent
,
95 : m_xContent( rContent
), m_xSMgr( rxSMgr
),
96 m_pNamesOfChildren( 0 ), m_nOpenMode( nOpenMode
),
97 m_bCountFinal( false ), m_bThrowException( false )
102 //=========================================================================
103 DataSupplier_Impl::~DataSupplier_Impl()
105 ResultList::const_iterator it
= m_aResults
.begin();
106 ResultList::const_iterator end
= m_aResults
.end();
114 delete m_pNamesOfChildren
;
119 //=========================================================================
120 //=========================================================================
122 // DataSupplier Implementation.
124 //=========================================================================
125 //=========================================================================
127 ResultSetDataSupplier::ResultSetDataSupplier(
128 const uno::Reference
< lang::XMultiServiceFactory
>& rxSMgr
,
129 const rtl::Reference
< Content
>& rContent
,
130 sal_Int32 nOpenMode
)
131 : m_pImpl( new DataSupplier_Impl( rxSMgr
, rContent
, nOpenMode
) )
135 //=========================================================================
137 ResultSetDataSupplier::~ResultSetDataSupplier()
142 //=========================================================================
145 ResultSetDataSupplier::queryContentIdentifierString( sal_uInt32 nIndex
)
147 osl::Guard
< osl::Mutex
> aGuard( m_pImpl
->m_aMutex
);
149 if ( nIndex
< m_pImpl
->m_aResults
.size() )
151 rtl::OUString aId
= m_pImpl
->m_aResults
[ nIndex
]->aURL
;
152 if ( !aId
.isEmpty() )
159 if ( getResult( nIndex
) )
161 // Note: getResult fills m_pImpl->m_aResults[ nIndex ]->aURL.
162 return m_pImpl
->m_aResults
[ nIndex
]->aURL
;
164 return rtl::OUString();
167 //=========================================================================
169 uno::Reference
< ucb::XContentIdentifier
>
170 ResultSetDataSupplier::queryContentIdentifier( sal_uInt32 nIndex
)
172 osl::Guard
< osl::Mutex
> aGuard( m_pImpl
->m_aMutex
);
174 if ( nIndex
< m_pImpl
->m_aResults
.size() )
176 uno::Reference
< ucb::XContentIdentifier
> xId
177 = m_pImpl
->m_aResults
[ nIndex
]->xId
;
185 rtl::OUString aId
= queryContentIdentifierString( nIndex
);
186 if ( !aId
.isEmpty() )
188 uno::Reference
< ucb::XContentIdentifier
> xId
189 = new ::ucbhelper::ContentIdentifier( aId
);
190 m_pImpl
->m_aResults
[ nIndex
]->xId
= xId
;
193 return uno::Reference
< ucb::XContentIdentifier
>();
196 //=========================================================================
198 uno::Reference
< ucb::XContent
>
199 ResultSetDataSupplier::queryContent( sal_uInt32 nIndex
)
201 osl::Guard
< osl::Mutex
> aGuard( m_pImpl
->m_aMutex
);
203 if ( nIndex
< m_pImpl
->m_aResults
.size() )
205 uno::Reference
< ucb::XContent
> xContent
206 = m_pImpl
->m_aResults
[ nIndex
]->xContent
;
214 uno::Reference
< ucb::XContentIdentifier
> xId
215 = queryContentIdentifier( nIndex
);
220 uno::Reference
< ucb::XContent
> xContent
221 = m_pImpl
->m_xContent
->getProvider()->queryContent( xId
);
222 m_pImpl
->m_aResults
[ nIndex
]->xContent
= xContent
;
226 catch ( ucb::IllegalIdentifierException
const & )
230 return uno::Reference
< ucb::XContent
>();
233 //=========================================================================
235 sal_Bool
ResultSetDataSupplier::getResult( sal_uInt32 nIndex
)
237 osl::ClearableGuard
< osl::Mutex
> aGuard( m_pImpl
->m_aMutex
);
239 if ( m_pImpl
->m_aResults
.size() > nIndex
)
241 // Result already present.
245 // Result not (yet) present.
247 if ( m_pImpl
->m_bCountFinal
)
250 // Try to obtain result...
252 sal_uInt32 nOldCount
= m_pImpl
->m_aResults
.size();
255 if ( queryNamesOfChildren() )
257 for ( sal_uInt32 n
= nOldCount
;
258 n
< sal::static_int_cast
<sal_uInt32
>(
259 m_pImpl
->m_pNamesOfChildren
->getLength());
262 const rtl::OUString
& rName
263 = m_pImpl
->m_pNamesOfChildren
->getConstArray()[ n
];
265 if ( rName
.isEmpty() )
267 OSL_FAIL( "ResultDataSupplier::getResult - Empty name!" );
271 // Assemble URL for child.
272 rtl::OUString aURL
= assembleChildURL( rName
);
274 m_pImpl
->m_aResults
.push_back( new ResultListEntry( aURL
) );
286 m_pImpl
->m_bCountFinal
= sal_True
;
288 rtl::Reference
< ::ucbhelper::ResultSet
> xResultSet
= getResultSet().get();
289 if ( xResultSet
.is() )
294 if ( nOldCount
< m_pImpl
->m_aResults
.size() )
295 xResultSet
->rowCountChanged( nOldCount
, m_pImpl
->m_aResults
.size() );
297 if ( m_pImpl
->m_bCountFinal
)
298 xResultSet
->rowCountFinal();
304 //=========================================================================
306 sal_uInt32
ResultSetDataSupplier::totalCount()
308 osl::ClearableGuard
< osl::Mutex
> aGuard( m_pImpl
->m_aMutex
);
310 if ( m_pImpl
->m_bCountFinal
)
311 return m_pImpl
->m_aResults
.size();
313 sal_uInt32 nOldCount
= m_pImpl
->m_aResults
.size();
315 if ( queryNamesOfChildren() )
317 for ( sal_uInt32 n
= nOldCount
;
318 n
< sal::static_int_cast
<sal_uInt32
>(
319 m_pImpl
->m_pNamesOfChildren
->getLength());
322 const rtl::OUString
& rName
323 = m_pImpl
->m_pNamesOfChildren
->getConstArray()[ n
];
325 if ( rName
.isEmpty() )
327 OSL_FAIL( "ResultDataSupplier::getResult - Empty name!" );
331 // Assemble URL for child.
332 rtl::OUString aURL
= assembleChildURL( rName
);
334 m_pImpl
->m_aResults
.push_back( new ResultListEntry( aURL
) );
338 m_pImpl
->m_bCountFinal
= sal_True
;
340 rtl::Reference
< ::ucbhelper::ResultSet
> xResultSet
= getResultSet().get();
341 if ( xResultSet
.is() )
346 if ( nOldCount
< m_pImpl
->m_aResults
.size() )
347 xResultSet
->rowCountChanged( nOldCount
, m_pImpl
->m_aResults
.size() );
349 xResultSet
->rowCountFinal();
352 return m_pImpl
->m_aResults
.size();
355 //=========================================================================
357 sal_uInt32
ResultSetDataSupplier::currentCount()
359 return m_pImpl
->m_aResults
.size();
362 //=========================================================================
364 sal_Bool
ResultSetDataSupplier::isCountFinal()
366 return m_pImpl
->m_bCountFinal
;
369 //=========================================================================
371 uno::Reference
< sdbc::XRow
>
372 ResultSetDataSupplier::queryPropertyValues( sal_uInt32 nIndex
)
374 osl::Guard
< osl::Mutex
> aGuard( m_pImpl
->m_aMutex
);
376 if ( nIndex
< m_pImpl
->m_aResults
.size() )
378 uno::Reference
< sdbc::XRow
> xRow
= m_pImpl
->m_aResults
[ nIndex
]->xRow
;
386 if ( getResult( nIndex
) )
388 uno::Reference
< sdbc::XRow
> xRow
= Content::getPropertyValues(
390 getResultSet()->getProperties(),
391 m_pImpl
->m_xContent
->getContentProvider().get(),
392 queryContentIdentifierString( nIndex
) );
393 m_pImpl
->m_aResults
[ nIndex
]->xRow
= xRow
;
397 return uno::Reference
< sdbc::XRow
>();
400 //=========================================================================
402 void ResultSetDataSupplier::releasePropertyValues( sal_uInt32 nIndex
)
404 osl::Guard
< osl::Mutex
> aGuard( m_pImpl
->m_aMutex
);
406 if ( nIndex
< m_pImpl
->m_aResults
.size() )
407 m_pImpl
->m_aResults
[ nIndex
]->xRow
= uno::Reference
< sdbc::XRow
>();
410 //=========================================================================
412 void ResultSetDataSupplier::close()
416 //=========================================================================
418 void ResultSetDataSupplier::validate()
419 throw( ucb::ResultSetException
)
421 if ( m_pImpl
->m_bThrowException
)
422 throw ucb::ResultSetException();
425 //=========================================================================
426 bool ResultSetDataSupplier::queryNamesOfChildren()
428 osl::Guard
< osl::Mutex
> aGuard( m_pImpl
->m_aMutex
);
430 if ( m_pImpl
->m_pNamesOfChildren
== 0 )
432 uno::Sequence
< rtl::OUString
> * pNamesOfChildren
433 = new uno::Sequence
< rtl::OUString
>();
435 if ( !m_pImpl
->m_xContent
->getContentProvider()->queryNamesOfChildren(
436 m_pImpl
->m_xContent
->getIdentifier()->getContentIdentifier(),
437 *pNamesOfChildren
) )
439 OSL_FAIL( "Got no list of children!" );
440 m_pImpl
->m_bThrowException
= sal_True
;
445 m_pImpl
->m_pNamesOfChildren
= pNamesOfChildren
;
451 //=========================================================================
453 ResultSetDataSupplier::assembleChildURL( const ::rtl::OUString
& aName
)
455 rtl::OUString aContURL
456 = m_pImpl
->m_xContent
->getIdentifier()->getContentIdentifier();
457 rtl::OUString
aURL( aContURL
);
459 sal_Int32 nUrlEnd
= aURL
.lastIndexOf( '/' );
460 if ( nUrlEnd
!= aURL
.getLength() - 1 )
461 aURL
+= rtl::OUString("/");
467 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */