19b5730f6SAndrew Rist /**************************************************************
2cdf0e10cSrcweir *
39b5730f6SAndrew Rist * Licensed to the Apache Software Foundation (ASF) under one
49b5730f6SAndrew Rist * or more contributor license agreements. See the NOTICE file
59b5730f6SAndrew Rist * distributed with this work for additional information
69b5730f6SAndrew Rist * regarding copyright ownership. The ASF licenses this file
79b5730f6SAndrew Rist * to you under the Apache License, Version 2.0 (the
89b5730f6SAndrew Rist * "License"); you may not use this file except in compliance
99b5730f6SAndrew Rist * with the License. You may obtain a copy of the License at
109b5730f6SAndrew Rist *
119b5730f6SAndrew Rist * http://www.apache.org/licenses/LICENSE-2.0
129b5730f6SAndrew Rist *
139b5730f6SAndrew Rist * Unless required by applicable law or agreed to in writing,
149b5730f6SAndrew Rist * software distributed under the License is distributed on an
159b5730f6SAndrew Rist * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
169b5730f6SAndrew Rist * KIND, either express or implied. See the License for the
179b5730f6SAndrew Rist * specific language governing permissions and limitations
189b5730f6SAndrew Rist * under the License.
199b5730f6SAndrew Rist *
209b5730f6SAndrew Rist *************************************************************/
219b5730f6SAndrew Rist
229b5730f6SAndrew Rist
23cdf0e10cSrcweir
24cdf0e10cSrcweir // MARKER(update_precomp.py): autogen include statement, do not remove
25cdf0e10cSrcweir #include "precompiled_connectivity.hxx"
26cdf0e10cSrcweir
27cdf0e10cSrcweir #include <ctype.h>
28cdf0e10cSrcweir #include "flat/ETable.hxx"
29cdf0e10cSrcweir #include <com/sun/star/sdbc/ColumnValue.hpp>
30cdf0e10cSrcweir #include <com/sun/star/sdbc/DataType.hpp>
31cdf0e10cSrcweir #include <com/sun/star/ucb/XContentAccess.hpp>
32cdf0e10cSrcweir #include <svl/converter.hxx>
33cdf0e10cSrcweir #include "flat/EConnection.hxx"
34cdf0e10cSrcweir #include "flat/EColumns.hxx"
35cdf0e10cSrcweir #include <osl/thread.h>
36cdf0e10cSrcweir #include <tools/config.hxx>
37cdf0e10cSrcweir #include <comphelper/sequence.hxx>
38cdf0e10cSrcweir #include <svl/zforlist.hxx>
39cdf0e10cSrcweir #include <rtl/math.hxx>
40cdf0e10cSrcweir #include <stdio.h> //sprintf
41cdf0e10cSrcweir #include <comphelper/extract.hxx>
42cdf0e10cSrcweir #include <comphelper/numbers.hxx>
43cdf0e10cSrcweir #include "flat/EDriver.hxx"
44cdf0e10cSrcweir #include <com/sun/star/util/NumberFormat.hpp>
45cdf0e10cSrcweir #include <unotools/configmgr.hxx>
46cdf0e10cSrcweir #include <i18npool/mslangid.hxx>
47cdf0e10cSrcweir #include "connectivity/dbconversion.hxx"
48cdf0e10cSrcweir #include <comphelper/types.hxx>
49cdf0e10cSrcweir #include "file/quotedstring.hxx"
50cdf0e10cSrcweir #include <unotools/syslocale.hxx>
51cdf0e10cSrcweir #include <rtl/logfile.hxx>
52cdf0e10cSrcweir
53cdf0e10cSrcweir using namespace ::comphelper;
54cdf0e10cSrcweir using namespace connectivity;
55cdf0e10cSrcweir using namespace connectivity::flat;
56cdf0e10cSrcweir using namespace connectivity::file;
57cdf0e10cSrcweir using namespace ::cppu;
58cdf0e10cSrcweir using namespace utl;
59cdf0e10cSrcweir using namespace ::com::sun::star::uno;
60cdf0e10cSrcweir using namespace ::com::sun::star::ucb;
61cdf0e10cSrcweir using namespace ::com::sun::star::beans;
62cdf0e10cSrcweir using namespace ::com::sun::star::sdbcx;
63cdf0e10cSrcweir using namespace ::com::sun::star::sdbc;
64cdf0e10cSrcweir using namespace ::com::sun::star::container;
65cdf0e10cSrcweir using namespace ::com::sun::star::lang;
66cdf0e10cSrcweir
67cdf0e10cSrcweir // -------------------------------------------------------------------------
fillColumns(const::com::sun::star::lang::Locale & _aLocale)68cdf0e10cSrcweir void OFlatTable::fillColumns(const ::com::sun::star::lang::Locale& _aLocale)
69cdf0e10cSrcweir {
70cdf0e10cSrcweir RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "flat", "Ocke.Janssen@sun.com", "OFlatTable::fillColumns" );
71cdf0e10cSrcweir sal_Bool bRead = sal_True;
72cdf0e10cSrcweir
73cdf0e10cSrcweir QuotedTokenizedString aHeaderLine;
74cdf0e10cSrcweir OFlatConnection* pConnection = (OFlatConnection*)m_pConnection;
75cdf0e10cSrcweir const sal_Bool bHasHeaderLine = pConnection->isHeaderLine();
766c882b5cSdamjan sal_Int32 nCurPos;
77cdf0e10cSrcweir if ( bHasHeaderLine )
78cdf0e10cSrcweir {
79cdf0e10cSrcweir while(bRead && !aHeaderLine.Len())
80cdf0e10cSrcweir {
816c882b5cSdamjan bRead = readLine(aHeaderLine, nCurPos);
82cdf0e10cSrcweir }
83cdf0e10cSrcweir m_nStartRowFilePos = m_pFileStream->Tell();
84cdf0e10cSrcweir }
85cdf0e10cSrcweir
86cdf0e10cSrcweir // read first row
87cdf0e10cSrcweir QuotedTokenizedString aFirstLine;
886c882b5cSdamjan bRead = readLine(aFirstLine, nCurPos);
89cdf0e10cSrcweir
90cdf0e10cSrcweir if ( !bHasHeaderLine || !aHeaderLine.Len())
91cdf0e10cSrcweir {
92cdf0e10cSrcweir while(bRead && !aFirstLine.Len())
93cdf0e10cSrcweir {
946c882b5cSdamjan bRead = readLine(aFirstLine, nCurPos);
95cdf0e10cSrcweir }
96cdf0e10cSrcweir // use first row as headerline because we need the number of columns
97cdf0e10cSrcweir aHeaderLine = aFirstLine;
98cdf0e10cSrcweir }
99cdf0e10cSrcweir // column count
100*f13410cfSDamjan Jovanovic const sal_Int32 nFieldCount = aHeaderLine.GetTokenCount(m_cFieldDelimiter,m_cStringDelimiter);
101cdf0e10cSrcweir
102cdf0e10cSrcweir if(!m_aColumns.isValid())
103cdf0e10cSrcweir m_aColumns = new OSQLColumns();
104cdf0e10cSrcweir else
105cdf0e10cSrcweir m_aColumns->get().clear();
106cdf0e10cSrcweir
107cdf0e10cSrcweir m_aTypes.clear();
108cdf0e10cSrcweir m_aPrecisions.clear();
109cdf0e10cSrcweir m_aScales.clear();
110cdf0e10cSrcweir // reserve some space
111cdf0e10cSrcweir m_aColumns->get().reserve(nFieldCount+1);
112cdf0e10cSrcweir m_aTypes.assign(nFieldCount+1,DataType::SQLNULL);
113cdf0e10cSrcweir m_aPrecisions.assign(nFieldCount+1,-1);
114cdf0e10cSrcweir m_aScales.assign(nFieldCount+1,-1);
115cdf0e10cSrcweir
116cdf0e10cSrcweir const sal_Bool bCase = m_pConnection->getMetaData()->supportsMixedCaseQuotedIdentifiers();
117cdf0e10cSrcweir CharClass aCharClass(pConnection->getDriver()->getFactory(),_aLocale);
118cdf0e10cSrcweir // read description
119cdf0e10cSrcweir const sal_Unicode cDecimalDelimiter = pConnection->getDecimalDelimiter();
120cdf0e10cSrcweir const sal_Unicode cThousandDelimiter = pConnection->getThousandDelimiter();
121*f13410cfSDamjan Jovanovic ::rtl::OUString aColumnName;
122cdf0e10cSrcweir ::rtl::OUString aTypeName;
123cdf0e10cSrcweir ::comphelper::UStringMixEqual aCase(bCase);
124cdf0e10cSrcweir ::std::vector<String> aColumnNames,m_aTypeNames;
125cdf0e10cSrcweir m_aTypeNames.resize(nFieldCount);
126cdf0e10cSrcweir const sal_Int32 nMaxRowsToScan = pConnection->getMaxRowsToScan();
127cdf0e10cSrcweir sal_Int32 nRowCount = 0;
128cdf0e10cSrcweir do
129cdf0e10cSrcweir {
130*f13410cfSDamjan Jovanovic sal_Int32 nStartPosHeaderLine = 0; // use for eficient way to get the tokens
131*f13410cfSDamjan Jovanovic sal_Int32 nStartPosFirstLine = 0; // use for eficient way to get the tokens
132*f13410cfSDamjan Jovanovic sal_Int32 nStartPosFirstLine2 = 0;
133*f13410cfSDamjan Jovanovic for (sal_Int32 i = 0; i < nFieldCount; i++)
134cdf0e10cSrcweir {
135cdf0e10cSrcweir if ( nRowCount == 0)
136cdf0e10cSrcweir {
137cdf0e10cSrcweir if ( bHasHeaderLine )
138cdf0e10cSrcweir {
139*f13410cfSDamjan Jovanovic aHeaderLine.GetTokenSpecial(&aColumnName,nStartPosHeaderLine,m_cFieldDelimiter,m_cStringDelimiter);
140*f13410cfSDamjan Jovanovic if ( aColumnName.isEmpty() )
141cdf0e10cSrcweir {
142*f13410cfSDamjan Jovanovic aColumnName = ::rtl::OUString::createFromAscii( "C" );
143cdf0e10cSrcweir aColumnName += String::CreateFromInt32(i+1);
144cdf0e10cSrcweir }
145cdf0e10cSrcweir }
146cdf0e10cSrcweir else
147cdf0e10cSrcweir {
148cdf0e10cSrcweir // no column name so ...
149*f13410cfSDamjan Jovanovic aColumnName = ::rtl::OUString::createFromAscii( "C" );
150cdf0e10cSrcweir aColumnName += String::CreateFromInt32(i+1);
151cdf0e10cSrcweir }
152cdf0e10cSrcweir aColumnNames.push_back(aColumnName);
153cdf0e10cSrcweir }
154cdf0e10cSrcweir impl_fillColumnInfo_nothrow(aFirstLine,nStartPosFirstLine,nStartPosFirstLine2,m_aTypes[i],m_aPrecisions[i],m_aScales[i],m_aTypeNames[i],cDecimalDelimiter,cThousandDelimiter,aCharClass);
155cdf0e10cSrcweir }
156cdf0e10cSrcweir ++nRowCount;
157cdf0e10cSrcweir }
1586c882b5cSdamjan while(nRowCount < nMaxRowsToScan && readLine(aFirstLine,nCurPos) && !m_pFileStream->IsEof());
159cdf0e10cSrcweir
160*f13410cfSDamjan Jovanovic for (sal_Int32 i = 0; i < nFieldCount; i++)
161cdf0e10cSrcweir {
162cdf0e10cSrcweir // check if the columname already exists
163cdf0e10cSrcweir String aAlias(aColumnNames[i]);
164cdf0e10cSrcweir OSQLColumns::Vector::const_iterator aFind = connectivity::find(m_aColumns->get().begin(),m_aColumns->get().end(),aAlias,aCase);
165cdf0e10cSrcweir sal_Int32 nExprCnt = 0;
166cdf0e10cSrcweir while(aFind != m_aColumns->get().end())
167cdf0e10cSrcweir {
168cdf0e10cSrcweir (aAlias = aColumnNames[i]) += String::CreateFromInt32(++nExprCnt);
169cdf0e10cSrcweir aFind = connectivity::find(m_aColumns->get().begin(),m_aColumns->get().end(),aAlias,aCase);
170cdf0e10cSrcweir }
171cdf0e10cSrcweir
172cdf0e10cSrcweir sdbcx::OColumn* pColumn = new sdbcx::OColumn(aAlias,m_aTypeNames[i],::rtl::OUString(),::rtl::OUString(),
173cdf0e10cSrcweir ColumnValue::NULLABLE,
174cdf0e10cSrcweir m_aPrecisions[i],
175cdf0e10cSrcweir m_aScales[i],
176cdf0e10cSrcweir m_aTypes[i],
177cdf0e10cSrcweir sal_False,
178cdf0e10cSrcweir sal_False,
179cdf0e10cSrcweir sal_False,
180cdf0e10cSrcweir bCase);
181cdf0e10cSrcweir Reference< XPropertySet> xCol = pColumn;
182cdf0e10cSrcweir m_aColumns->get().push_back(xCol);
183cdf0e10cSrcweir }
184cdf0e10cSrcweir m_pFileStream->Seek(m_nStartRowFilePos);
185cdf0e10cSrcweir }
impl_fillColumnInfo_nothrow(QuotedTokenizedString & aFirstLine,sal_Int32 & nStartPosFirstLine,sal_Int32 & nStartPosFirstLine2,sal_Int32 & io_nType,sal_Int32 & io_nPrecisions,sal_Int32 & io_nScales,String & o_sTypeName,const sal_Unicode cDecimalDelimiter,const sal_Unicode cThousandDelimiter,const CharClass & aCharClass)186*f13410cfSDamjan Jovanovic void OFlatTable::impl_fillColumnInfo_nothrow(QuotedTokenizedString& aFirstLine,sal_Int32& nStartPosFirstLine,sal_Int32& nStartPosFirstLine2
187cdf0e10cSrcweir ,sal_Int32& io_nType,sal_Int32& io_nPrecisions,sal_Int32& io_nScales,String& o_sTypeName
188cdf0e10cSrcweir ,const sal_Unicode cDecimalDelimiter,const sal_Unicode cThousandDelimiter,const CharClass& aCharClass)
189cdf0e10cSrcweir {
190cdf0e10cSrcweir if ( io_nType != DataType::VARCHAR )
191cdf0e10cSrcweir {
192cdf0e10cSrcweir sal_Bool bNumeric = io_nType == DataType::SQLNULL || io_nType == DataType::DOUBLE || io_nType == DataType::DECIMAL || io_nType == DataType::INTEGER;
193cdf0e10cSrcweir sal_uLong nIndex = 0;
194cdf0e10cSrcweir
195cdf0e10cSrcweir if ( bNumeric )
196cdf0e10cSrcweir {
197cdf0e10cSrcweir // first without fielddelimiter
198*f13410cfSDamjan Jovanovic ::rtl::OUString aField;
199*f13410cfSDamjan Jovanovic aFirstLine.GetTokenSpecial(&aField,nStartPosFirstLine,m_cFieldDelimiter,'\0');
200*f13410cfSDamjan Jovanovic if ( aField.isEmpty() ||
201*f13410cfSDamjan Jovanovic (m_cStringDelimiter && m_cStringDelimiter == aField[0]))
202cdf0e10cSrcweir {
203cdf0e10cSrcweir bNumeric = sal_False;
204cdf0e10cSrcweir if ( m_cStringDelimiter != '\0' )
205*f13410cfSDamjan Jovanovic aFirstLine.GetTokenSpecial(&aField,nStartPosFirstLine2,m_cFieldDelimiter,m_cStringDelimiter);
206cdf0e10cSrcweir else
207cdf0e10cSrcweir nStartPosFirstLine2 = nStartPosFirstLine;
208cdf0e10cSrcweir }
209cdf0e10cSrcweir else
210cdf0e10cSrcweir {
211*f13410cfSDamjan Jovanovic ::rtl::OUString aField2;
212cdf0e10cSrcweir if ( m_cStringDelimiter != '\0' )
213*f13410cfSDamjan Jovanovic aFirstLine.GetTokenSpecial(&aField2,nStartPosFirstLine2,m_cFieldDelimiter,m_cStringDelimiter);
214cdf0e10cSrcweir else
215cdf0e10cSrcweir aField2 = aField;
216cdf0e10cSrcweir
217*f13410cfSDamjan Jovanovic if ( aField2.isEmpty() )
218cdf0e10cSrcweir {
219cdf0e10cSrcweir bNumeric = sal_False;
220cdf0e10cSrcweir }
221cdf0e10cSrcweir else
222cdf0e10cSrcweir {
223cdf0e10cSrcweir bNumeric = sal_True;
224cdf0e10cSrcweir xub_StrLen nDot = 0;
225cdf0e10cSrcweir xub_StrLen nDecimalDelCount = 0;
226cdf0e10cSrcweir xub_StrLen nSpaceCount = 0;
227*f13410cfSDamjan Jovanovic for (sal_Int32 j = 0; j < aField2.getLength(); j++)
228cdf0e10cSrcweir {
229*f13410cfSDamjan Jovanovic const sal_Unicode c = aField2[j];
230cdf0e10cSrcweir if ( j == nSpaceCount && m_cFieldDelimiter != 32 && c == 32 )
231cdf0e10cSrcweir {
232cdf0e10cSrcweir ++nSpaceCount;
233cdf0e10cSrcweir continue;
234cdf0e10cSrcweir }
235cdf0e10cSrcweir // nur Ziffern und Dezimalpunkt und Tausender-Trennzeichen?
236cdf0e10cSrcweir if ( ( !cDecimalDelimiter || c != cDecimalDelimiter ) &&
237cdf0e10cSrcweir ( !cThousandDelimiter || c != cThousandDelimiter ) &&
238cdf0e10cSrcweir !aCharClass.isDigit(aField2,j) &&
239cdf0e10cSrcweir ( j != 0 || (c != '+' && c != '-' ) ) )
240cdf0e10cSrcweir {
241cdf0e10cSrcweir bNumeric = sal_False;
242cdf0e10cSrcweir break;
243cdf0e10cSrcweir }
244cdf0e10cSrcweir if (cDecimalDelimiter && c == cDecimalDelimiter)
245cdf0e10cSrcweir {
246cdf0e10cSrcweir io_nPrecisions = 15; // we have an decimal value
247cdf0e10cSrcweir io_nScales = 2;
248cdf0e10cSrcweir ++nDecimalDelCount;
249cdf0e10cSrcweir } // if (cDecimalDelimiter && c == cDecimalDelimiter)
250cdf0e10cSrcweir if ( c == '.' )
251cdf0e10cSrcweir ++nDot;
252cdf0e10cSrcweir }
253cdf0e10cSrcweir
254cdf0e10cSrcweir if (nDecimalDelCount > 1 || nDot > 1 ) // if there is more than one dot it isn't a number
255cdf0e10cSrcweir bNumeric = sal_False;
256cdf0e10cSrcweir if (bNumeric && cThousandDelimiter)
257cdf0e10cSrcweir {
258cdf0e10cSrcweir // Ist der Trenner richtig angegeben?
259*f13410cfSDamjan Jovanovic sal_Int32 tokenIdx = 0;
260*f13410cfSDamjan Jovanovic const ::rtl::OUString aValue = aField2.getToken(0,cDecimalDelimiter,tokenIdx);
261*f13410cfSDamjan Jovanovic for (sal_Int32 j = aValue.getLength() - 4; j >= 0; j -= 4)
262cdf0e10cSrcweir {
263*f13410cfSDamjan Jovanovic const sal_Unicode c = aValue[j];
264cdf0e10cSrcweir // nur Ziffern und Dezimalpunkt und Tausender-Trennzeichen?
265cdf0e10cSrcweir if (c == cThousandDelimiter && j)
266cdf0e10cSrcweir continue;
267cdf0e10cSrcweir else
268cdf0e10cSrcweir {
269cdf0e10cSrcweir bNumeric = sal_False;
270cdf0e10cSrcweir break;
271cdf0e10cSrcweir }
272cdf0e10cSrcweir }
273cdf0e10cSrcweir }
274cdf0e10cSrcweir
275cdf0e10cSrcweir // jetzt koennte es noch ein Datumsfeld sein
276cdf0e10cSrcweir if (!bNumeric)
277cdf0e10cSrcweir {
278cdf0e10cSrcweir try
279cdf0e10cSrcweir {
280cdf0e10cSrcweir nIndex = m_xNumberFormatter->detectNumberFormat(::com::sun::star::util::NumberFormat::ALL,aField2);
281cdf0e10cSrcweir }
282cdf0e10cSrcweir catch(Exception&)
283cdf0e10cSrcweir {
284cdf0e10cSrcweir }
285cdf0e10cSrcweir }
286cdf0e10cSrcweir }
287cdf0e10cSrcweir }
288cdf0e10cSrcweir }
289cdf0e10cSrcweir else if ( io_nType == DataType::DATE || io_nType == DataType::TIMESTAMP || io_nType == DataType::TIME)
290cdf0e10cSrcweir {
291*f13410cfSDamjan Jovanovic ::rtl::OUString aField;
292*f13410cfSDamjan Jovanovic aFirstLine.GetTokenSpecial(&aField,nStartPosFirstLine,m_cFieldDelimiter,'\0');
293*f13410cfSDamjan Jovanovic if ( aField.isEmpty() ||
294*f13410cfSDamjan Jovanovic (m_cStringDelimiter && m_cStringDelimiter == aField[0]))
295cdf0e10cSrcweir {
296cdf0e10cSrcweir }
297cdf0e10cSrcweir else
298cdf0e10cSrcweir {
299*f13410cfSDamjan Jovanovic ::rtl::OUString aField2;
300cdf0e10cSrcweir if ( m_cStringDelimiter != '\0' )
301*f13410cfSDamjan Jovanovic aFirstLine.GetTokenSpecial(&aField2,nStartPosFirstLine2,m_cFieldDelimiter,m_cStringDelimiter);
302cdf0e10cSrcweir else
303cdf0e10cSrcweir aField2 = aField;
304*f13410cfSDamjan Jovanovic if ( !aField2.isEmpty() )
305cdf0e10cSrcweir {
306cdf0e10cSrcweir try
307cdf0e10cSrcweir {
308cdf0e10cSrcweir nIndex = m_xNumberFormatter->detectNumberFormat(::com::sun::star::util::NumberFormat::ALL,aField2);
309cdf0e10cSrcweir }
310cdf0e10cSrcweir catch(Exception&)
311cdf0e10cSrcweir {
312cdf0e10cSrcweir }
313cdf0e10cSrcweir }
314cdf0e10cSrcweir }
315cdf0e10cSrcweir }
316cdf0e10cSrcweir
317cdf0e10cSrcweir sal_Int32 nFlags = 0;
318cdf0e10cSrcweir if (bNumeric)
319cdf0e10cSrcweir {
320cdf0e10cSrcweir if (cDecimalDelimiter)
321cdf0e10cSrcweir {
322cdf0e10cSrcweir if(io_nPrecisions)
323cdf0e10cSrcweir {
324cdf0e10cSrcweir io_nType = DataType::DECIMAL;
325cdf0e10cSrcweir static const ::rtl::OUString s_sDECIMAL(RTL_CONSTASCII_USTRINGPARAM("DECIMAL"));
326cdf0e10cSrcweir o_sTypeName = s_sDECIMAL;
327cdf0e10cSrcweir }
328cdf0e10cSrcweir else
329cdf0e10cSrcweir {
330cdf0e10cSrcweir io_nType = DataType::DOUBLE;
331cdf0e10cSrcweir static const ::rtl::OUString s_sDOUBLE(RTL_CONSTASCII_USTRINGPARAM("DOUBLE"));
332cdf0e10cSrcweir o_sTypeName = s_sDOUBLE;
333cdf0e10cSrcweir }
334cdf0e10cSrcweir }
335cdf0e10cSrcweir else
336cdf0e10cSrcweir {
337cdf0e10cSrcweir io_nType = DataType::INTEGER;
338cdf0e10cSrcweir io_nPrecisions = 0;
339cdf0e10cSrcweir io_nScales = 0;
340cdf0e10cSrcweir }
341cdf0e10cSrcweir nFlags = ColumnSearch::BASIC;
342cdf0e10cSrcweir }
343cdf0e10cSrcweir else
344cdf0e10cSrcweir {
345cdf0e10cSrcweir switch (comphelper::getNumberFormatType(m_xNumberFormatter,nIndex))
346cdf0e10cSrcweir {
347cdf0e10cSrcweir case NUMBERFORMAT_DATE:
348cdf0e10cSrcweir io_nType = DataType::DATE;
349cdf0e10cSrcweir {
350cdf0e10cSrcweir static const ::rtl::OUString s_sDATE(RTL_CONSTASCII_USTRINGPARAM("DATE"));
351cdf0e10cSrcweir o_sTypeName = s_sDATE;
352cdf0e10cSrcweir }
353cdf0e10cSrcweir break;
354cdf0e10cSrcweir case NUMBERFORMAT_DATETIME:
355cdf0e10cSrcweir io_nType = DataType::TIMESTAMP;
356cdf0e10cSrcweir {
357cdf0e10cSrcweir static const ::rtl::OUString s_sTIMESTAMP(RTL_CONSTASCII_USTRINGPARAM("TIMESTAMP"));
358cdf0e10cSrcweir o_sTypeName = s_sTIMESTAMP;
359cdf0e10cSrcweir }
360cdf0e10cSrcweir break;
361cdf0e10cSrcweir case NUMBERFORMAT_TIME:
362cdf0e10cSrcweir io_nType = DataType::TIME;
363cdf0e10cSrcweir {
364cdf0e10cSrcweir static const ::rtl::OUString s_sTIME(RTL_CONSTASCII_USTRINGPARAM("TIME"));
365cdf0e10cSrcweir o_sTypeName = s_sTIME;
366cdf0e10cSrcweir }
367cdf0e10cSrcweir break;
368cdf0e10cSrcweir default:
369cdf0e10cSrcweir io_nType = DataType::VARCHAR;
370cdf0e10cSrcweir io_nPrecisions = 0; // nyi: Daten koennen aber laenger sein!
371cdf0e10cSrcweir io_nScales = 0;
372cdf0e10cSrcweir {
373cdf0e10cSrcweir static const ::rtl::OUString s_sVARCHAR(RTL_CONSTASCII_USTRINGPARAM("VARCHAR"));
374cdf0e10cSrcweir o_sTypeName = s_sVARCHAR;
375cdf0e10cSrcweir }
376cdf0e10cSrcweir };
377cdf0e10cSrcweir nFlags |= ColumnSearch::CHAR;
378cdf0e10cSrcweir }
379cdf0e10cSrcweir }
380cdf0e10cSrcweir else
381cdf0e10cSrcweir {
382*f13410cfSDamjan Jovanovic ::rtl::OUString aField;
383*f13410cfSDamjan Jovanovic aFirstLine.GetTokenSpecial(&aField,nStartPosFirstLine,m_cFieldDelimiter,'\0');
384*f13410cfSDamjan Jovanovic if ( aField.isEmpty() ||
385*f13410cfSDamjan Jovanovic (m_cStringDelimiter && m_cStringDelimiter == aField[0]))
386cdf0e10cSrcweir {
387cdf0e10cSrcweir if ( m_cStringDelimiter != '\0' )
388*f13410cfSDamjan Jovanovic aFirstLine.GetTokenSpecial(&aField,nStartPosFirstLine2,m_cFieldDelimiter,m_cStringDelimiter);
389cdf0e10cSrcweir else
390cdf0e10cSrcweir nStartPosFirstLine2 = nStartPosFirstLine;
391cdf0e10cSrcweir }
392cdf0e10cSrcweir else
393cdf0e10cSrcweir {
394*f13410cfSDamjan Jovanovic ::rtl::OUString aField2;
395cdf0e10cSrcweir if ( m_cStringDelimiter != '\0' )
396*f13410cfSDamjan Jovanovic aFirstLine.GetTokenSpecial(&aField2,nStartPosFirstLine2,m_cFieldDelimiter,m_cStringDelimiter);
397cdf0e10cSrcweir }
398cdf0e10cSrcweir }
399cdf0e10cSrcweir }
400cdf0e10cSrcweir // -------------------------------------------------------------------------
OFlatTable(sdbcx::OCollection * _pTables,OFlatConnection * _pConnection,const::rtl::OUString & _Name,const::rtl::OUString & _Type,const::rtl::OUString & _Description,const::rtl::OUString & _SchemaName,const::rtl::OUString & _CatalogName)401cdf0e10cSrcweir OFlatTable::OFlatTable(sdbcx::OCollection* _pTables,OFlatConnection* _pConnection,
402cdf0e10cSrcweir const ::rtl::OUString& _Name,
403cdf0e10cSrcweir const ::rtl::OUString& _Type,
404cdf0e10cSrcweir const ::rtl::OUString& _Description ,
405cdf0e10cSrcweir const ::rtl::OUString& _SchemaName,
406cdf0e10cSrcweir const ::rtl::OUString& _CatalogName
407cdf0e10cSrcweir ) : OFlatTable_BASE(_pTables,_pConnection,_Name,
408cdf0e10cSrcweir _Type,
409cdf0e10cSrcweir _Description,
410cdf0e10cSrcweir _SchemaName,
411cdf0e10cSrcweir _CatalogName)
412cdf0e10cSrcweir ,m_nStartRowFilePos(0)
413cdf0e10cSrcweir ,m_nRowPos(0)
414cdf0e10cSrcweir ,m_nMaxRowCount(0)
415cdf0e10cSrcweir ,m_cStringDelimiter(_pConnection->getStringDelimiter())
416cdf0e10cSrcweir ,m_cFieldDelimiter(_pConnection->getFieldDelimiter())
417cdf0e10cSrcweir ,m_bNeedToReadLine(false)
418cdf0e10cSrcweir {
419cdf0e10cSrcweir RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "flat", "Ocke.Janssen@sun.com", "OFlatTable::OFlatTable" );
420cdf0e10cSrcweir
421cdf0e10cSrcweir }
422cdf0e10cSrcweir // -----------------------------------------------------------------------------
construct()423cdf0e10cSrcweir void OFlatTable::construct()
424cdf0e10cSrcweir {
425cdf0e10cSrcweir RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "flat", "Ocke.Janssen@sun.com", "OFlatTable::construct" );
426cdf0e10cSrcweir SvtSysLocale aLocale;
427cdf0e10cSrcweir ::com::sun::star::lang::Locale aAppLocale(aLocale.GetLocaleDataPtr()->getLocale());
428cdf0e10cSrcweir Sequence< ::com::sun::star::uno::Any > aArg(1);
429cdf0e10cSrcweir aArg[0] <<= aAppLocale;
430cdf0e10cSrcweir
431cdf0e10cSrcweir Reference< ::com::sun::star::util::XNumberFormatsSupplier > xSupplier(m_pConnection->getDriver()->getFactory()->createInstanceWithArguments(::rtl::OUString::createFromAscii("com.sun.star.util.NumberFormatsSupplier"),aArg),UNO_QUERY);
432cdf0e10cSrcweir m_xNumberFormatter = Reference< ::com::sun::star::util::XNumberFormatter >(m_pConnection->getDriver()->getFactory()->createInstance(::rtl::OUString::createFromAscii("com.sun.star.util.NumberFormatter")),UNO_QUERY);
433cdf0e10cSrcweir m_xNumberFormatter->attachNumberFormatsSupplier(xSupplier);
434cdf0e10cSrcweir Reference<XPropertySet> xProp(xSupplier->getNumberFormatSettings(),UNO_QUERY);
435cdf0e10cSrcweir xProp->getPropertyValue(::rtl::OUString::createFromAscii("NullDate")) >>= m_aNullDate;
436cdf0e10cSrcweir
437cdf0e10cSrcweir INetURLObject aURL;
438cdf0e10cSrcweir aURL.SetURL(getEntry());
439cdf0e10cSrcweir
440cdf0e10cSrcweir if(aURL.getExtension() != rtl::OUString(m_pConnection->getExtension()))
441cdf0e10cSrcweir aURL.setExtension(m_pConnection->getExtension());
442cdf0e10cSrcweir
443cdf0e10cSrcweir String aFileName = aURL.GetMainURL(INetURLObject::NO_DECODE);
444cdf0e10cSrcweir
445cdf0e10cSrcweir m_pFileStream = createStream_simpleError( aFileName,STREAM_READWRITE | STREAM_NOCREATE | STREAM_SHARE_DENYWRITE);
446cdf0e10cSrcweir
447cdf0e10cSrcweir if(!m_pFileStream)
448cdf0e10cSrcweir m_pFileStream = createStream_simpleError( aFileName,STREAM_READ | STREAM_NOCREATE | STREAM_SHARE_DENYNONE);
449cdf0e10cSrcweir
450cdf0e10cSrcweir if(m_pFileStream)
451cdf0e10cSrcweir {
452cdf0e10cSrcweir m_pFileStream->Seek(STREAM_SEEK_TO_END);
453cdf0e10cSrcweir sal_Int32 nSize = m_pFileStream->Tell();
454cdf0e10cSrcweir m_pFileStream->Seek(STREAM_SEEK_TO_BEGIN);
455cdf0e10cSrcweir
456cdf0e10cSrcweir // Buffersize abhaengig von der Filegroesse
457cdf0e10cSrcweir m_pFileStream->SetBufferSize(nSize > 1000000 ? 32768 :
458cdf0e10cSrcweir nSize > 100000 ? 16384 :
459cdf0e10cSrcweir nSize > 10000 ? 4096 : 1024);
460cdf0e10cSrcweir
461cdf0e10cSrcweir fillColumns(aAppLocale);
462cdf0e10cSrcweir
463cdf0e10cSrcweir refreshColumns();
464cdf0e10cSrcweir }
465cdf0e10cSrcweir }
466cdf0e10cSrcweir // -------------------------------------------------------------------------
getEntry()467cdf0e10cSrcweir String OFlatTable::getEntry()
468cdf0e10cSrcweir {
469cdf0e10cSrcweir RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "flat", "Ocke.Janssen@sun.com", "OFlatTable::getEntry" );
470cdf0e10cSrcweir ::rtl::OUString sURL;
471cdf0e10cSrcweir try
472cdf0e10cSrcweir {
473cdf0e10cSrcweir Reference< XResultSet > xDir = m_pConnection->getDir()->getStaticResultSet();
474cdf0e10cSrcweir Reference< XRow> xRow(xDir,UNO_QUERY);
475cdf0e10cSrcweir ::rtl::OUString sName;
476cdf0e10cSrcweir ::rtl::OUString sExt;
477cdf0e10cSrcweir
478cdf0e10cSrcweir INetURLObject aURL;
479cdf0e10cSrcweir xDir->beforeFirst();
480cdf0e10cSrcweir static const ::rtl::OUString s_sSeparator(RTL_CONSTASCII_USTRINGPARAM("/"));
481cdf0e10cSrcweir while(xDir->next())
482cdf0e10cSrcweir {
483cdf0e10cSrcweir sName = xRow->getString(1);
484cdf0e10cSrcweir aURL.SetSmartProtocol(INET_PROT_FILE);
485cdf0e10cSrcweir String sUrl = m_pConnection->getURL() + s_sSeparator + sName;
486cdf0e10cSrcweir aURL.SetSmartURL( sUrl );
487cdf0e10cSrcweir
488cdf0e10cSrcweir // cut the extension
489cdf0e10cSrcweir sExt = aURL.getExtension();
490cdf0e10cSrcweir
491cdf0e10cSrcweir // name and extension have to coincide
492cdf0e10cSrcweir if ( m_pConnection->matchesExtension( sExt ) )
493cdf0e10cSrcweir {
494*f13410cfSDamjan Jovanovic if ( !sExt.isEmpty() )
495cdf0e10cSrcweir sName = sName.replaceAt(sName.getLength()-(sExt.getLength()+1),sExt.getLength()+1,::rtl::OUString());
496cdf0e10cSrcweir if ( sName == m_Name )
497cdf0e10cSrcweir {
498cdf0e10cSrcweir Reference< XContentAccess > xContentAccess( xDir, UNO_QUERY );
499cdf0e10cSrcweir sURL = xContentAccess->queryContentIdentifierString();
500cdf0e10cSrcweir break;
501cdf0e10cSrcweir }
502cdf0e10cSrcweir }
503cdf0e10cSrcweir }
504cdf0e10cSrcweir xDir->beforeFirst(); // move back to before first record
505cdf0e10cSrcweir }
506cdf0e10cSrcweir catch(Exception&)
507cdf0e10cSrcweir {
508cdf0e10cSrcweir OSL_ASSERT(0);
509cdf0e10cSrcweir }
510cdf0e10cSrcweir return sURL.getStr();
511cdf0e10cSrcweir }
512cdf0e10cSrcweir // -------------------------------------------------------------------------
refreshColumns()513cdf0e10cSrcweir void OFlatTable::refreshColumns()
514cdf0e10cSrcweir {
515cdf0e10cSrcweir RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "flat", "Ocke.Janssen@sun.com", "OFlatTable::refreshColumns" );
516cdf0e10cSrcweir ::osl::MutexGuard aGuard( m_aMutex );
517cdf0e10cSrcweir
518cdf0e10cSrcweir TStringVector aVector;
519cdf0e10cSrcweir aVector.reserve(m_aColumns->get().size());
520cdf0e10cSrcweir
521cdf0e10cSrcweir for(OSQLColumns::Vector::const_iterator aIter = m_aColumns->get().begin();aIter != m_aColumns->get().end();++aIter)
522cdf0e10cSrcweir aVector.push_back(Reference< XNamed>(*aIter,UNO_QUERY)->getName());
523cdf0e10cSrcweir
524cdf0e10cSrcweir if(m_pColumns)
525cdf0e10cSrcweir m_pColumns->reFill(aVector);
526cdf0e10cSrcweir else
527cdf0e10cSrcweir m_pColumns = new OFlatColumns(this,m_aMutex,aVector);
528cdf0e10cSrcweir }
529cdf0e10cSrcweir
530cdf0e10cSrcweir // -------------------------------------------------------------------------
disposing(void)531cdf0e10cSrcweir void SAL_CALL OFlatTable::disposing(void)
532cdf0e10cSrcweir {
533cdf0e10cSrcweir RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "flat", "Ocke.Janssen@sun.com", "OFlatTable::disposing" );
534cdf0e10cSrcweir OFileTable::disposing();
535cdf0e10cSrcweir ::osl::MutexGuard aGuard(m_aMutex);
536cdf0e10cSrcweir m_aColumns = NULL;
537cdf0e10cSrcweir }
538cdf0e10cSrcweir // -------------------------------------------------------------------------
getTypes()539cdf0e10cSrcweir Sequence< Type > SAL_CALL OFlatTable::getTypes( ) throw(RuntimeException)
540cdf0e10cSrcweir {
541cdf0e10cSrcweir Sequence< Type > aTypes = OTable_TYPEDEF::getTypes();
542cdf0e10cSrcweir ::std::vector<Type> aOwnTypes;
543cdf0e10cSrcweir aOwnTypes.reserve(aTypes.getLength());
544cdf0e10cSrcweir const Type* pBegin = aTypes.getConstArray();
545cdf0e10cSrcweir const Type* pEnd = pBegin + aTypes.getLength();
546cdf0e10cSrcweir for(;pBegin != pEnd;++pBegin)
547cdf0e10cSrcweir {
548cdf0e10cSrcweir if(!(*pBegin == ::getCppuType((const Reference<XKeysSupplier>*)0) ||
549cdf0e10cSrcweir *pBegin == ::getCppuType((const Reference<XRename>*)0) ||
550cdf0e10cSrcweir *pBegin == ::getCppuType((const Reference<XIndexesSupplier>*)0) ||
551cdf0e10cSrcweir *pBegin == ::getCppuType((const Reference<XAlterTable>*)0) ||
552cdf0e10cSrcweir *pBegin == ::getCppuType((const Reference<XDataDescriptorFactory>*)0)))
553cdf0e10cSrcweir {
554cdf0e10cSrcweir aOwnTypes.push_back(*pBegin);
555cdf0e10cSrcweir }
556cdf0e10cSrcweir }
557cdf0e10cSrcweir Type *pTypes = aOwnTypes.empty() ? 0 : &aOwnTypes[0];
558cdf0e10cSrcweir return Sequence< Type >(pTypes, aOwnTypes.size());
559cdf0e10cSrcweir }
560cdf0e10cSrcweir
561cdf0e10cSrcweir // -------------------------------------------------------------------------
queryInterface(const Type & rType)562cdf0e10cSrcweir Any SAL_CALL OFlatTable::queryInterface( const Type & rType ) throw(RuntimeException)
563cdf0e10cSrcweir {
564cdf0e10cSrcweir if( rType == ::getCppuType((const Reference<XKeysSupplier>*)0) ||
565cdf0e10cSrcweir rType == ::getCppuType((const Reference<XIndexesSupplier>*)0) ||
566cdf0e10cSrcweir rType == ::getCppuType((const Reference<XRename>*)0) ||
567cdf0e10cSrcweir rType == ::getCppuType((const Reference<XAlterTable>*)0) ||
568cdf0e10cSrcweir rType == ::getCppuType((const Reference<XDataDescriptorFactory>*)0))
569cdf0e10cSrcweir return Any();
570cdf0e10cSrcweir
571cdf0e10cSrcweir Any aRet = OTable_TYPEDEF::queryInterface(rType);
572cdf0e10cSrcweir return aRet.hasValue() ? aRet : ::cppu::queryInterface(rType,static_cast< ::com::sun::star::lang::XUnoTunnel*> (this));
573cdf0e10cSrcweir }
574cdf0e10cSrcweir
575cdf0e10cSrcweir //--------------------------------------------------------------------------
getUnoTunnelImplementationId()576cdf0e10cSrcweir Sequence< sal_Int8 > OFlatTable::getUnoTunnelImplementationId()
577cdf0e10cSrcweir {
578cdf0e10cSrcweir static ::cppu::OImplementationId * pId = 0;
579cdf0e10cSrcweir if (! pId)
580cdf0e10cSrcweir {
581cdf0e10cSrcweir ::osl::MutexGuard aGuard( ::osl::Mutex::getGlobalMutex() );
582cdf0e10cSrcweir if (! pId)
583cdf0e10cSrcweir {
584cdf0e10cSrcweir static ::cppu::OImplementationId aId;
585cdf0e10cSrcweir pId = &aId;
586cdf0e10cSrcweir }
587cdf0e10cSrcweir }
588cdf0e10cSrcweir return pId->getImplementationId();
589cdf0e10cSrcweir }
590cdf0e10cSrcweir
591cdf0e10cSrcweir // com::sun::star::lang::XUnoTunnel
592cdf0e10cSrcweir //------------------------------------------------------------------
getSomething(const Sequence<sal_Int8> & rId)593cdf0e10cSrcweir sal_Int64 OFlatTable::getSomething( const Sequence< sal_Int8 > & rId ) throw (RuntimeException)
594cdf0e10cSrcweir {
595cdf0e10cSrcweir RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "flat", "Ocke.Janssen@sun.com", "OFlatTable::getSomething" );
596cdf0e10cSrcweir return (rId.getLength() == 16 && 0 == rtl_compareMemory(getUnoTunnelImplementationId().getConstArray(), rId.getConstArray(), 16 ) )
597cdf0e10cSrcweir ? reinterpret_cast< sal_Int64 >( this )
598cdf0e10cSrcweir : OFlatTable_BASE::getSomething(rId);
599cdf0e10cSrcweir }
600cdf0e10cSrcweir //------------------------------------------------------------------
fetchRow(OValueRefRow & _rRow,const OSQLColumns & _rCols,sal_Bool bIsTable,sal_Bool bRetrieveData)601cdf0e10cSrcweir sal_Bool OFlatTable::fetchRow(OValueRefRow& _rRow,const OSQLColumns & _rCols,sal_Bool bIsTable,sal_Bool bRetrieveData)
602cdf0e10cSrcweir {
603cdf0e10cSrcweir RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "flat", "Ocke.Janssen@sun.com", "OFlatTable::fetchRow" );
604cdf0e10cSrcweir *(_rRow->get())[0] = m_nFilePos;
605cdf0e10cSrcweir
606cdf0e10cSrcweir if (!bRetrieveData)
607cdf0e10cSrcweir return sal_True;
608cdf0e10cSrcweir if ( m_bNeedToReadLine )
609cdf0e10cSrcweir {
610cdf0e10cSrcweir sal_Int32 nCurrentPos = 0;
611cdf0e10cSrcweir m_pFileStream->Seek(m_nFilePos);
612cdf0e10cSrcweir readLine(nCurrentPos);
613cdf0e10cSrcweir m_bNeedToReadLine = false;
614cdf0e10cSrcweir }
615cdf0e10cSrcweir
616cdf0e10cSrcweir OFlatConnection* pConnection = (OFlatConnection*)m_pConnection;
617cdf0e10cSrcweir const sal_Unicode cDecimalDelimiter = pConnection->getDecimalDelimiter();
618cdf0e10cSrcweir const sal_Unicode cThousandDelimiter = pConnection->getThousandDelimiter();
619cdf0e10cSrcweir // Felder:
620*f13410cfSDamjan Jovanovic sal_Int32 nStartPos = 0;
621*f13410cfSDamjan Jovanovic ::rtl::OUString aStr;
622cdf0e10cSrcweir OSQLColumns::Vector::const_iterator aIter = _rCols.get().begin();
623cdf0e10cSrcweir OSQLColumns::Vector::const_iterator aEnd = _rCols.get().end();
624cdf0e10cSrcweir const OValueRefVector::Vector::size_type nCount = _rRow->get().size();
625cdf0e10cSrcweir for (OValueRefVector::Vector::size_type i = 1; aIter != aEnd && i < nCount;
626cdf0e10cSrcweir ++aIter, i++)
627cdf0e10cSrcweir {
628*f13410cfSDamjan Jovanovic m_aCurrentLine.GetTokenSpecial(&aStr,nStartPos,m_cFieldDelimiter,m_cStringDelimiter);
629cdf0e10cSrcweir
630*f13410cfSDamjan Jovanovic if (aStr.isEmpty())
631cdf0e10cSrcweir (_rRow->get())[i]->setNull();
632cdf0e10cSrcweir else
633cdf0e10cSrcweir {
634cdf0e10cSrcweir // Laengen je nach Datentyp:
635cdf0e10cSrcweir sal_Int32 nLen,
636cdf0e10cSrcweir nType = 0;
637cdf0e10cSrcweir if(bIsTable)
638cdf0e10cSrcweir {
639cdf0e10cSrcweir nLen = m_aPrecisions[i-1];
640cdf0e10cSrcweir nType = m_aTypes[i-1];
641cdf0e10cSrcweir }
642cdf0e10cSrcweir else
643cdf0e10cSrcweir {
644cdf0e10cSrcweir Reference< XPropertySet> xColumn = *aIter;
645cdf0e10cSrcweir xColumn->getPropertyValue(OMetaConnection::getPropMap().getNameByIndex(PROPERTY_ID_PRECISION)) >>= nLen;
646cdf0e10cSrcweir xColumn->getPropertyValue(OMetaConnection::getPropMap().getNameByIndex(PROPERTY_ID_TYPE)) >>= nType;
647cdf0e10cSrcweir }
648cdf0e10cSrcweir switch(nType)
649cdf0e10cSrcweir {
650cdf0e10cSrcweir case DataType::TIMESTAMP:
651cdf0e10cSrcweir case DataType::DATE:
652cdf0e10cSrcweir case DataType::TIME:
653cdf0e10cSrcweir {
654cdf0e10cSrcweir try
655cdf0e10cSrcweir {
656cdf0e10cSrcweir double nRes = m_xNumberFormatter->convertStringToNumber(::com::sun::star::util::NumberFormat::ALL,aStr);
657cdf0e10cSrcweir
658cdf0e10cSrcweir switch(nType)
659cdf0e10cSrcweir {
660cdf0e10cSrcweir case DataType::DATE:
661cdf0e10cSrcweir *(_rRow->get())[i] = ::dbtools::DBTypeConversion::toDouble(::dbtools::DBTypeConversion::toDate(nRes,m_aNullDate));
662cdf0e10cSrcweir break;
663cdf0e10cSrcweir case DataType::TIMESTAMP:
664cdf0e10cSrcweir *(_rRow->get())[i] = ::dbtools::DBTypeConversion::toDouble(::dbtools::DBTypeConversion::toDateTime(nRes,m_aNullDate));
665cdf0e10cSrcweir break;
666cdf0e10cSrcweir default:
667cdf0e10cSrcweir *(_rRow->get())[i] = ::dbtools::DBTypeConversion::toDouble(::dbtools::DBTypeConversion::toTime(nRes));
668cdf0e10cSrcweir }
669cdf0e10cSrcweir }
670cdf0e10cSrcweir catch(Exception&)
671cdf0e10cSrcweir {
672cdf0e10cSrcweir (_rRow->get())[i]->setNull();
673cdf0e10cSrcweir }
674cdf0e10cSrcweir } break;
675cdf0e10cSrcweir case DataType::DOUBLE:
676cdf0e10cSrcweir case DataType::INTEGER:
677cdf0e10cSrcweir case DataType::DECIMAL: // #99178# OJ
678cdf0e10cSrcweir case DataType::NUMERIC:
679cdf0e10cSrcweir {
680cdf0e10cSrcweir
681cdf0e10cSrcweir String aStrConverted;
682cdf0e10cSrcweir if ( DataType::INTEGER != nType )
683cdf0e10cSrcweir {
684*f13410cfSDamjan Jovanovic sal_Unicode* pData = aStrConverted.AllocBuffer(aStr.getLength());
685cdf0e10cSrcweir const sal_Unicode* pStart = pData;
686cdf0e10cSrcweir
687cdf0e10cSrcweir OSL_ENSURE(cDecimalDelimiter && nType != DataType::INTEGER ||
688cdf0e10cSrcweir !cDecimalDelimiter && nType == DataType::INTEGER,
689cdf0e10cSrcweir "FalscherTyp");
690cdf0e10cSrcweir
691cdf0e10cSrcweir // In Standard-Notation (DezimalPUNKT ohne Tausender-Komma) umwandeln:
692*f13410cfSDamjan Jovanovic for (sal_Int32 j = 0; j < aStr.getLength(); ++j)
693cdf0e10cSrcweir {
694*f13410cfSDamjan Jovanovic const sal_Unicode cChar = aStr[j];
695cdf0e10cSrcweir if (cDecimalDelimiter && cChar == cDecimalDelimiter)
696cdf0e10cSrcweir *pData++ = '.';
697cdf0e10cSrcweir //aStrConverted.Append( '.' );
698cdf0e10cSrcweir else if ( cChar == '.' ) // special case, if decimal seperator isn't '.' we have to put the string after it
699cdf0e10cSrcweir continue; // #99189# OJ
700cdf0e10cSrcweir else if (cThousandDelimiter && cChar == cThousandDelimiter)
701cdf0e10cSrcweir {
702cdf0e10cSrcweir // weglassen
703cdf0e10cSrcweir }
704cdf0e10cSrcweir else
705cdf0e10cSrcweir *pData++ = cChar;
706cdf0e10cSrcweir //aStrConverted.Append(cChar);
707*f13410cfSDamjan Jovanovic } // for (sal_Int32 j = 0; j < aStr.Len(); ++j)
708cdf0e10cSrcweir aStrConverted.ReleaseBufferAccess(xub_StrLen(pData - pStart));
709cdf0e10cSrcweir } // if ( DataType::INTEGER != nType )
710cdf0e10cSrcweir else
711cdf0e10cSrcweir {
712cdf0e10cSrcweir aStrConverted = aStr;
713cdf0e10cSrcweir if ( cThousandDelimiter )
714cdf0e10cSrcweir aStrConverted.EraseAllChars(cThousandDelimiter);
715cdf0e10cSrcweir }
716cdf0e10cSrcweir const double nVal = ::rtl::math::stringToDouble(aStrConverted,'.',',',NULL,NULL);
717cdf0e10cSrcweir
718cdf0e10cSrcweir // #99178# OJ
719cdf0e10cSrcweir if ( DataType::DECIMAL == nType || DataType::NUMERIC == nType )
720cdf0e10cSrcweir *(_rRow->get())[i] = ::rtl::OUString::valueOf(nVal);
721cdf0e10cSrcweir else
722cdf0e10cSrcweir *(_rRow->get())[i] = nVal;
723cdf0e10cSrcweir } break;
724cdf0e10cSrcweir
725cdf0e10cSrcweir default:
726cdf0e10cSrcweir {
727cdf0e10cSrcweir // Wert als String in Variable der Row uebernehmen
728cdf0e10cSrcweir *(_rRow->get())[i] = ORowSetValue(aStr);
729cdf0e10cSrcweir }
730cdf0e10cSrcweir break;
731cdf0e10cSrcweir } // switch(nType)
732cdf0e10cSrcweir (_rRow->get())[i]->setTypeKind(nType);
733cdf0e10cSrcweir }
734cdf0e10cSrcweir }
735cdf0e10cSrcweir return sal_True;
736cdf0e10cSrcweir }
refreshHeader()737cdf0e10cSrcweir void OFlatTable::refreshHeader()
738cdf0e10cSrcweir {
739cdf0e10cSrcweir m_nRowPos = 0;
740cdf0e10cSrcweir }
741cdf0e10cSrcweir // -----------------------------------------------------------------------------
seekRow(IResultSetHelper::Movement eCursorPosition,sal_Int32 nOffset,sal_Int32 & nCurPos)742cdf0e10cSrcweir sal_Bool OFlatTable::seekRow(IResultSetHelper::Movement eCursorPosition, sal_Int32 nOffset, sal_Int32& nCurPos)
743cdf0e10cSrcweir {
744cdf0e10cSrcweir RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "flat", "Ocke.Janssen@sun.com", "OFlatTable::seekRow" );
745cdf0e10cSrcweir OSL_ENSURE(m_pFileStream,"OFlatTable::seekRow: FileStream is NULL!");
746cdf0e10cSrcweir // ----------------------------------------------------------
747cdf0e10cSrcweir // Positionierung vorbereiten:
748cdf0e10cSrcweir m_nFilePos = nCurPos;
749cdf0e10cSrcweir
750cdf0e10cSrcweir switch(eCursorPosition)
751cdf0e10cSrcweir {
752cdf0e10cSrcweir case IResultSetHelper::FIRST:
753cdf0e10cSrcweir m_nRowPos = 0;
754cdf0e10cSrcweir // run through
755cdf0e10cSrcweir case IResultSetHelper::NEXT:
756cdf0e10cSrcweir {
757cdf0e10cSrcweir ++m_nRowPos;
758cdf0e10cSrcweir ::std::map<sal_Int32,TRowPositionsInFile::iterator>::const_iterator aFind = m_aRowPosToFilePos.find(m_nRowPos);
759cdf0e10cSrcweir m_bNeedToReadLine = aFind != m_aRowPosToFilePos.end();
760cdf0e10cSrcweir if ( m_bNeedToReadLine )
761cdf0e10cSrcweir {
762cdf0e10cSrcweir m_nFilePos = aFind->second->first;
763cdf0e10cSrcweir nCurPos = aFind->second->second;
764cdf0e10cSrcweir } // if ( m_bNeedToReadLine )
765cdf0e10cSrcweir else
766cdf0e10cSrcweir {
767cdf0e10cSrcweir if ( m_nRowPos == 1 )
768cdf0e10cSrcweir m_nFilePos = m_nStartRowFilePos;
769cdf0e10cSrcweir m_pFileStream->Seek(m_nFilePos);
770cdf0e10cSrcweir if ( m_pFileStream->IsEof() || !readLine(nCurPos) /*|| !checkHeaderLine()*/)
771cdf0e10cSrcweir {
772cdf0e10cSrcweir m_nMaxRowCount = m_nRowPos -1;
773cdf0e10cSrcweir return sal_False;
774cdf0e10cSrcweir } // if ( m_pFileStream->IsEof() || !readLine(nCurPos) /*|| !checkHeaderLine()*/)
775cdf0e10cSrcweir
776cdf0e10cSrcweir TRowPositionsInFile::iterator aPos = m_aFilePosToEndLinePos.insert(TRowPositionsInFile::value_type(m_nFilePos,nCurPos)).first;
777cdf0e10cSrcweir m_aRowPosToFilePos.insert(::std::map<sal_Int32,TRowPositionsInFile::iterator>::value_type(m_nRowPos,aPos));
778cdf0e10cSrcweir }
779cdf0e10cSrcweir }
780cdf0e10cSrcweir
781cdf0e10cSrcweir break;
782cdf0e10cSrcweir case IResultSetHelper::PRIOR:
783cdf0e10cSrcweir --m_nRowPos;
784cdf0e10cSrcweir if(m_nRowPos > 0)
785cdf0e10cSrcweir {
786cdf0e10cSrcweir TRowPositionsInFile::iterator aPositions = m_aRowPosToFilePos[m_nRowPos];
787cdf0e10cSrcweir m_nFilePos = aPositions->first;
788cdf0e10cSrcweir nCurPos = aPositions->second;
789cdf0e10cSrcweir m_bNeedToReadLine = true;
790cdf0e10cSrcweir }
791cdf0e10cSrcweir else
792cdf0e10cSrcweir m_nRowPos = 0;
793cdf0e10cSrcweir
794cdf0e10cSrcweir break;
795cdf0e10cSrcweir case IResultSetHelper::LAST:
796cdf0e10cSrcweir if ( m_nMaxRowCount )
797cdf0e10cSrcweir {
798cdf0e10cSrcweir ::std::map<sal_Int32,TRowPositionsInFile::iterator>::reverse_iterator aLastPos = m_aRowPosToFilePos.rbegin();
799cdf0e10cSrcweir m_nRowPos = aLastPos->first;
800cdf0e10cSrcweir m_nFilePos = aLastPos->second->first;
801cdf0e10cSrcweir nCurPos = aLastPos->second->second;
802cdf0e10cSrcweir
803cdf0e10cSrcweir //m_pFileStream->Seek(m_nFilePos);
804cdf0e10cSrcweir m_bNeedToReadLine = true;
805cdf0e10cSrcweir //if ( m_pFileStream->IsEof() /*|| !checkHeaderLine()*/ || !readLine(nCurPos) )
806cdf0e10cSrcweir // return sal_False;
807cdf0e10cSrcweir }
808cdf0e10cSrcweir else
809cdf0e10cSrcweir {
810cdf0e10cSrcweir while(seekRow(IResultSetHelper::NEXT,1,nCurPos)) ; // run through after last row
811cdf0e10cSrcweir // now I know all
812cdf0e10cSrcweir seekRow(IResultSetHelper::PRIOR,1,nCurPos);
813cdf0e10cSrcweir }
814cdf0e10cSrcweir break;
815cdf0e10cSrcweir case IResultSetHelper::RELATIVE:
816cdf0e10cSrcweir if(nOffset > 0)
817cdf0e10cSrcweir {
818cdf0e10cSrcweir for(sal_Int32 i = 0;i<nOffset;++i)
819cdf0e10cSrcweir seekRow(IResultSetHelper::NEXT,1,nCurPos);
820cdf0e10cSrcweir }
821cdf0e10cSrcweir else if(nOffset < 0)
822cdf0e10cSrcweir {
823cdf0e10cSrcweir for(sal_Int32 i = nOffset;i;++i)
824cdf0e10cSrcweir seekRow(IResultSetHelper::PRIOR,1,nCurPos);
825cdf0e10cSrcweir }
826cdf0e10cSrcweir break;
827cdf0e10cSrcweir case IResultSetHelper::ABSOLUTE:
828cdf0e10cSrcweir {
829cdf0e10cSrcweir if(nOffset < 0)
830cdf0e10cSrcweir nOffset = m_nRowPos + nOffset;
831cdf0e10cSrcweir ::std::map<sal_Int32,TRowPositionsInFile::iterator>::const_iterator aIter = m_aRowPosToFilePos.find(nOffset);
832cdf0e10cSrcweir if(aIter != m_aRowPosToFilePos.end())
833cdf0e10cSrcweir {
834cdf0e10cSrcweir m_nFilePos = aIter->second->first;
835cdf0e10cSrcweir nCurPos = aIter->second->second;
836cdf0e10cSrcweir //m_pFileStream->Seek(m_nFilePos);
837cdf0e10cSrcweir m_bNeedToReadLine = true;
838cdf0e10cSrcweir //if ( m_pFileStream->IsEof() /*|| !checkHeaderLine()*/ || !readLine(nCurPos) )
839cdf0e10cSrcweir // return sal_False;
840cdf0e10cSrcweir }
841cdf0e10cSrcweir else if(m_nMaxRowCount && nOffset > m_nMaxRowCount) // offset is outside the table
842cdf0e10cSrcweir {
843cdf0e10cSrcweir m_nRowPos = m_nMaxRowCount;
844cdf0e10cSrcweir return sal_False;
845cdf0e10cSrcweir }
846cdf0e10cSrcweir else
847cdf0e10cSrcweir {
848cdf0e10cSrcweir aIter = m_aRowPosToFilePos.upper_bound(nOffset);
849cdf0e10cSrcweir if(aIter == m_aRowPosToFilePos.end())
850cdf0e10cSrcweir {
851cdf0e10cSrcweir ::std::map<sal_Int32,TRowPositionsInFile::iterator>::reverse_iterator aLastPos = m_aRowPosToFilePos.rbegin();
852cdf0e10cSrcweir m_nRowPos = aLastPos->first;
853cdf0e10cSrcweir nCurPos = m_nFilePos = aLastPos->second->first;
854cdf0e10cSrcweir while(m_nRowPos != nOffset)
855cdf0e10cSrcweir seekRow(IResultSetHelper::NEXT,1,nCurPos);
856cdf0e10cSrcweir }
857cdf0e10cSrcweir else
858cdf0e10cSrcweir {
859cdf0e10cSrcweir --aIter;
860cdf0e10cSrcweir m_nRowPos = aIter->first;
861cdf0e10cSrcweir m_nFilePos = aIter->second->first;
862cdf0e10cSrcweir nCurPos = aIter->second->second;
863cdf0e10cSrcweir //m_pFileStream->Seek(m_nFilePos);
864cdf0e10cSrcweir m_bNeedToReadLine = true;
865cdf0e10cSrcweir //if ( m_pFileStream->IsEof() /*|| !checkHeaderLine()*/ || !readLine(nCurPos) )
866cdf0e10cSrcweir // return sal_False;
867cdf0e10cSrcweir }
868cdf0e10cSrcweir }
869cdf0e10cSrcweir }
870cdf0e10cSrcweir
871cdf0e10cSrcweir break;
872cdf0e10cSrcweir case IResultSetHelper::BOOKMARK:
873cdf0e10cSrcweir {
874cdf0e10cSrcweir TRowPositionsInFile::const_iterator aFind = m_aFilePosToEndLinePos.find(nOffset);
875cdf0e10cSrcweir m_bNeedToReadLine = aFind != m_aFilePosToEndLinePos.end();
876cdf0e10cSrcweir if ( m_bNeedToReadLine )
877cdf0e10cSrcweir {
878cdf0e10cSrcweir m_nFilePos = aFind->first;
879cdf0e10cSrcweir nCurPos = aFind->second;
880cdf0e10cSrcweir }
881cdf0e10cSrcweir else
882cdf0e10cSrcweir {
883cdf0e10cSrcweir m_nFilePos = nOffset;
884cdf0e10cSrcweir m_pFileStream->Seek(nOffset);
885cdf0e10cSrcweir if (m_pFileStream->IsEof() || !readLine(nCurPos) )
886cdf0e10cSrcweir return sal_False;
887cdf0e10cSrcweir }
888cdf0e10cSrcweir break;
889cdf0e10cSrcweir }
890cdf0e10cSrcweir }
891cdf0e10cSrcweir
892cdf0e10cSrcweir //nCurPos = m_nFilePos;
893cdf0e10cSrcweir
894cdf0e10cSrcweir return sal_True;
895cdf0e10cSrcweir }
896cdf0e10cSrcweir // -----------------------------------------------------------------------------
readLine(sal_Int32 & _rnCurrentPos)897cdf0e10cSrcweir sal_Bool OFlatTable::readLine(sal_Int32& _rnCurrentPos)
8986c882b5cSdamjan {
8996c882b5cSdamjan return readLine(m_aCurrentLine, _rnCurrentPos);
9006c882b5cSdamjan }
9016c882b5cSdamjan // -----------------------------------------------------------------------------
readLine(QuotedTokenizedString & lineOut,sal_Int32 & _rnCurrentPos)902*f13410cfSDamjan Jovanovic sal_Bool OFlatTable::readLine(QuotedTokenizedString& lineOut, sal_Int32& _rnCurrentPos)
903cdf0e10cSrcweir {
904cdf0e10cSrcweir RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "flat", "Ocke.Janssen@sun.com", "OFlatTable::readLine" );
905cdf0e10cSrcweir const rtl_TextEncoding nEncoding = m_pConnection->getTextEncoding();
906*f13410cfSDamjan Jovanovic ::rtl::OUStringBuffer lineBuffer( 4096 );
907*f13410cfSDamjan Jovanovic ::rtl::OUString separator = ::rtl::OUString();
908*f13410cfSDamjan Jovanovic static ::rtl::OUString lf = ::rtl::OUString::createFromAscii( "\n" );
9092cbc43e9Sdamjan bool isFieldStarting = true;
910*f13410cfSDamjan Jovanovic bool inQuotedField = false;
911*f13410cfSDamjan Jovanovic sal_Bool result = sal_True;
912*f13410cfSDamjan Jovanovic do
913cdf0e10cSrcweir {
914*f13410cfSDamjan Jovanovic ::rtl::OUString line;
915*f13410cfSDamjan Jovanovic m_pFileStream->ReadByteStringLine(line,nEncoding);
916*f13410cfSDamjan Jovanovic if (m_pFileStream->IsEof())
917*f13410cfSDamjan Jovanovic {
918*f13410cfSDamjan Jovanovic result = sal_False;
919*f13410cfSDamjan Jovanovic break;
920*f13410cfSDamjan Jovanovic }
9212cbc43e9Sdamjan
922*f13410cfSDamjan Jovanovic bool wasPreviousQuote = false;
923*f13410cfSDamjan Jovanovic for ( sal_Int32 i = 0; i < line.getLength(); i++ )
924cdf0e10cSrcweir {
925*f13410cfSDamjan Jovanovic sal_Unicode ch = line[i];
926*f13410cfSDamjan Jovanovic if ( ch == m_cStringDelimiter )
9272cbc43e9Sdamjan {
928*f13410cfSDamjan Jovanovic if ( isFieldStarting )
929*f13410cfSDamjan Jovanovic {
930*f13410cfSDamjan Jovanovic isFieldStarting = false;
931*f13410cfSDamjan Jovanovic inQuotedField = true;
932*f13410cfSDamjan Jovanovic }
9332cbc43e9Sdamjan else
9342cbc43e9Sdamjan {
935*f13410cfSDamjan Jovanovic wasPreviousQuote = !wasPreviousQuote;
9362cbc43e9Sdamjan }
9372cbc43e9Sdamjan }
938*f13410cfSDamjan Jovanovic else if ( ch == m_cFieldDelimiter )
9392cbc43e9Sdamjan {
940*f13410cfSDamjan Jovanovic if ( !inQuotedField )
9412cbc43e9Sdamjan isFieldStarting = true;
9422cbc43e9Sdamjan }
943*f13410cfSDamjan Jovanovic else
9442cbc43e9Sdamjan {
945*f13410cfSDamjan Jovanovic if ( wasPreviousQuote )
946*f13410cfSDamjan Jovanovic inQuotedField = false;
947*f13410cfSDamjan Jovanovic wasPreviousQuote = false;
9482cbc43e9Sdamjan }
949cdf0e10cSrcweir }
950*f13410cfSDamjan Jovanovic if ( wasPreviousQuote )
951*f13410cfSDamjan Jovanovic inQuotedField = false;
952*f13410cfSDamjan Jovanovic
953*f13410cfSDamjan Jovanovic lineBuffer.append( separator );
954*f13410cfSDamjan Jovanovic separator = lf;
955*f13410cfSDamjan Jovanovic lineBuffer.append( line );
956*f13410cfSDamjan Jovanovic
957*f13410cfSDamjan Jovanovic } while ( inQuotedField );
958*f13410cfSDamjan Jovanovic
959*f13410cfSDamjan Jovanovic lineOut = lineBuffer.makeStringAndClear();
960cdf0e10cSrcweir _rnCurrentPos = m_pFileStream->Tell();
961*f13410cfSDamjan Jovanovic return result;
962cdf0e10cSrcweir }
963