diff options
author | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-04-07 09:06:44 +0000 |
---|---|---|
committer | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-04-07 09:06:44 +0000 |
commit | ed5640d8b587fbcfed7dd7967f3de04b37a76f26 (patch) | |
tree | 7a5f7c6c9d02226d7471cb3cc8fbbf631b415303 /include/connectivity | |
parent | Initial commit. (diff) | |
download | libreoffice-ed5640d8b587fbcfed7dd7967f3de04b37a76f26.tar.xz libreoffice-ed5640d8b587fbcfed7dd7967f3de04b37a76f26.zip |
Adding upstream version 4:7.4.7.upstream/4%7.4.7upstream
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to '')
40 files changed, 6720 insertions, 0 deletions
diff --git a/include/connectivity/BlobHelper.hxx b/include/connectivity/BlobHelper.hxx new file mode 100644 index 000000000..95b5892dc --- /dev/null +++ b/include/connectivity/BlobHelper.hxx @@ -0,0 +1,41 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ +#pragma once + +#include <connectivity/dbtoolsdllapi.hxx> +#include <com/sun/star/sdbc/XBlob.hpp> +#include <cppuhelper/implbase.hxx> + +namespace connectivity +{ + class OOO_DLLPUBLIC_DBTOOLS BlobHelper final : public ::cppu::WeakImplHelper< css::sdbc::XBlob > + { + css::uno::Sequence< sal_Int8 > m_aValue; + public: + BlobHelper(const css::uno::Sequence< sal_Int8 >& _val); + private: + virtual ::sal_Int64 SAL_CALL length( ) override; + virtual css::uno::Sequence< ::sal_Int8 > SAL_CALL getBytes( ::sal_Int64 pos, ::sal_Int32 length ) override; + virtual css::uno::Reference< css::io::XInputStream > SAL_CALL getBinaryStream( ) override; + virtual ::sal_Int64 SAL_CALL position( const css::uno::Sequence< ::sal_Int8 >& pattern, ::sal_Int64 start ) override; + virtual ::sal_Int64 SAL_CALL positionOfBlob( const css::uno::Reference< css::sdbc::XBlob >& pattern, ::sal_Int64 start ) override; + }; +} + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/CommonTools.hxx b/include/connectivity/CommonTools.hxx new file mode 100644 index 000000000..a5279024e --- /dev/null +++ b/include/connectivity/CommonTools.hxx @@ -0,0 +1,167 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ +#ifndef INCLUDED_CONNECTIVITY_COMMONTOOLS_HXX +#define INCLUDED_CONNECTIVITY_COMMONTOOLS_HXX + +#include <sal/config.h> +#include <config_java.h> + +#include <map> +#include <string_view> + +#include <rtl/ref.hxx> +#include <rtl/ustring.hxx> +#include <vector> +#include <cppuhelper/weakref.hxx> +#include <comphelper/stl_types.hxx> +#include <com/sun/star/beans/XPropertySet.hpp> +#include <com/sun/star/sdbcx/XColumnsSupplier.hpp> +#include <connectivity/dbtoolsdllapi.hxx> +#include <cppuhelper/supportsservice.hxx> +#include <salhelper/simplereferenceobject.hxx> + +namespace com::sun::star::uno { class XComponentContext; } + +#if HAVE_FEATURE_JAVA +namespace jvmaccess { class VirtualMachine; } +#endif + +namespace connectivity +{ + OOO_DLLPUBLIC_DBTOOLS bool match(const sal_Unicode* pWild, const sal_Unicode* pStr, const sal_Unicode cEscape); + inline bool match(const OUString &rWild, const OUString &rStr, const sal_Unicode cEscape) + { + return match(rWild.getStr(), rStr.getStr(), cEscape); + } + // typedefs + typedef std::vector< css::uno::WeakReferenceHelper > OWeakRefArray; + typedef css::uno::Reference< css::sdbcx::XColumnsSupplier> OSQLTable; + + typedef std::map<OUString,OSQLTable,comphelper::UStringMixLess> OSQLTables; + + // class ORefVector allows reference counting on a std::vector + template< class VectorVal > class ORefVector : public salhelper::SimpleReferenceObject, + public std::vector< VectorVal > + { + protected: + virtual ~ORefVector() override {} + public: + typedef std::vector< VectorVal > Vector; + + ORefVector() {} + ORefVector(size_t _st) : std::vector< VectorVal >(_st) {} + ORefVector(const ORefVector& rOther) + : salhelper::SimpleReferenceObject() + , std::vector< VectorVal >(rOther) + {} + + ORefVector& operator=(const ORefVector& _rRH) + { + if ( &_rRH != this ) + { + std::vector< VectorVal >::operator=(_rRH); + } + return *this; + } + }; + + // class ORowVector includes refcounting and initialize himself + // with at least one element. This first element is reserved for + // the bookmark + template< class VectorVal > class ORowVector : public ORefVector< VectorVal > + { + public: + ORowVector() : ORefVector< VectorVal >(1){} + ORowVector(size_t _st) : ORefVector< VectorVal >(_st+1) + {} + }; + + typedef ORefVector< css::uno::Reference< css::beans::XPropertySet> > OSQLColumns; + + // search from first to last the column with the name _rVal + // when no such column exist last is returned + OOO_DLLPUBLIC_DBTOOLS + OSQLColumns::const_iterator find( const OSQLColumns::const_iterator& first, + const OSQLColumns::const_iterator& last, + std::u16string_view _rVal, + const ::comphelper::UStringMixEqual& _rCase); + + // search from first to last the column with the realname _rVal + // when no such column exist last is returned + OOO_DLLPUBLIC_DBTOOLS + OSQLColumns::const_iterator findRealName( const OSQLColumns::const_iterator& first, + const OSQLColumns::const_iterator& last, + std::u16string_view _rVal, + const ::comphelper::UStringMixEqual& _rCase); + + // the first two find methods are much faster than the one below + // search from first to last the column with the property _rProp equals the value _rVal + // when no such column exist last is returned + OOO_DLLPUBLIC_DBTOOLS + OSQLColumns::const_iterator find( OSQLColumns::const_iterator first, + const OSQLColumns::const_iterator& last, + const OUString& _rProp, + std::u16string_view _rVal, + const ::comphelper::UStringMixEqual& _rCase); + + /// @throws css::lang::DisposedException + OOO_DLLPUBLIC_DBTOOLS void checkDisposed(bool _bThrow); + +#if HAVE_FEATURE_JAVA + /** creates a java virtual machine + @param _rxContext + The ORB. + @return + The JavaVM. + */ + OOO_DLLPUBLIC_DBTOOLS ::rtl::Reference< jvmaccess::VirtualMachine > getJavaVM(const css::uno::Reference< css::uno::XComponentContext >& _rxContext); + + /** return <TRUE/> if the java class exists, otherwise <FALSE/>. + @param _pJVM + The JavaVM. + @param _sClassName + The class name to look for. + */ + OOO_DLLPUBLIC_DBTOOLS bool existsJavaClassByName( const ::rtl::Reference< jvmaccess::VirtualMachine >& _pJVM,std::u16string_view _sClassName ); +#endif +} + +#define DECLARE_SERVICE_INFO() \ + virtual OUString SAL_CALL getImplementationName( ) override; \ + virtual sal_Bool SAL_CALL supportsService( const OUString& rServiceName ) override; \ + virtual css::uno::Sequence< OUString > SAL_CALL getSupportedServiceNames( ) override \ + +#define IMPLEMENT_SERVICE_INFO(classname, implasciiname, serviceasciiname) \ + OUString SAL_CALL classname::getImplementationName( ) \ + { \ + return implasciiname; \ + } \ + css::uno::Sequence< OUString > SAL_CALL classname::getSupportedServiceNames( ) \ + { \ + css::uno::Sequence< OUString > aSupported { serviceasciiname }; \ + return aSupported; \ + } \ + sal_Bool SAL_CALL classname::supportsService( const OUString& rServiceName ) \ + { \ + return cppu::supportsService(this, rServiceName); \ + } \ + +#endif // INCLUDED_CONNECTIVITY_COMMONTOOLS_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/ConnectionWrapper.hxx b/include/connectivity/ConnectionWrapper.hxx new file mode 100644 index 000000000..8eac6a7b9 --- /dev/null +++ b/include/connectivity/ConnectionWrapper.hxx @@ -0,0 +1,92 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#ifndef INCLUDED_CONNECTIVITY_CONNECTIONWRAPPER_HXX +#define INCLUDED_CONNECTIVITY_CONNECTIONWRAPPER_HXX + +#include <cppuhelper/implbase2.hxx> +#include <com/sun/star/lang/XServiceInfo.hpp> +#include <com/sun/star/lang/XUnoTunnel.hpp> +#include <connectivity/CommonTools.hxx> +#include <connectivity/dbtoolsdllapi.hxx> + +namespace com::sun::star::beans { struct PropertyValue; } +namespace com::sun::star::sdbc { class XConnection; } +namespace com::sun::star::uno { class XComponentContext; } + +namespace connectivity +{ + + + //= OConnectionWrapper - wraps all methods to the real connection from the driver + //= but when disposed it doesn't dispose the real connection + + typedef ::cppu::ImplHelper2< css::lang::XServiceInfo, + css::lang::XUnoTunnel + > OConnection_BASE; + + class OOO_DLLPUBLIC_DBTOOLS OConnectionWrapper : public OConnection_BASE + { + protected: + css::uno::Reference< css::uno::XAggregation > m_xProxyConnection; + css::uno::Reference< css::sdbc::XConnection > m_xConnection; + css::uno::Reference< css::lang::XTypeProvider > m_xTypeProvider; + css::uno::Reference< css::lang::XUnoTunnel > m_xUnoTunnel; + css::uno::Reference< css::lang::XServiceInfo > m_xServiceInfo; + + virtual ~OConnectionWrapper(); + void setDelegation(css::uno::Reference< css::uno::XAggregation >& _rxProxyConnection,oslInterlockedCount& _rRefCount); + void setDelegation(const css::uno::Reference< css::sdbc::XConnection >& _xConnection + ,const css::uno::Reference< css::uno::XComponentContext>& _rxContext + ,oslInterlockedCount& _rRefCount); + // must be called from derived classes + void disposing(); + public: + OConnectionWrapper( ); + + // XServiceInfo + DECLARE_SERVICE_INFO(); + virtual css::uno::Any SAL_CALL queryInterface( const css::uno::Type& _rType ) override; + virtual css::uno::Sequence< css::uno::Type > SAL_CALL getTypes( ) override; + + // css::lang::XUnoTunnel + virtual sal_Int64 SAL_CALL getSomething( const css::uno::Sequence< sal_Int8 >& aIdentifier ) override; + static const css::uno::Sequence< sal_Int8 > & getUnoTunnelId(); + /** method to create unique ids + @param _rURL + The URL. + @param _rInfo + The info property of the datasource. It will be resorted if needed. + @param _pBuffer + Here we store the digest. Must not NULL. + @param _rUserName + The user name. + @param _rPassword + The password. + */ + static void createUniqueId( const OUString& _rURL + ,css::uno::Sequence< css::beans::PropertyValue >& _rInfo + ,sal_uInt8* _pBuffer + ,const OUString& _rUserName = OUString() + ,const OUString& _rPassword = OUString()); + }; +} +#endif // INCLUDED_CONNECTIVITY_CONNECTIONWRAPPER_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/DriversConfig.hxx b/include/connectivity/DriversConfig.hxx new file mode 100644 index 000000000..ceb15bedd --- /dev/null +++ b/include/connectivity/DriversConfig.hxx @@ -0,0 +1,82 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ +#ifndef INCLUDED_CONNECTIVITY_DRIVERSCONFIG_HXX +#define INCLUDED_CONNECTIVITY_DRIVERSCONFIG_HXX + +#include <sal/config.h> + +#include <map> +#include <string_view> + +#include <com/sun/star/uno/Sequence.h> +#include <connectivity/dbtoolsdllapi.hxx> +#include <salhelper/singletonref.hxx> +#include <comphelper/namedvaluecollection.hxx> +#include <unotools/confignode.hxx> + +namespace connectivity +{ + struct TInstalledDriver + { + ::comphelper::NamedValueCollection aProperties; + ::comphelper::NamedValueCollection aFeatures; + ::comphelper::NamedValueCollection aMetaData; + OUString sDriverFactory; + OUString sDriverTypeDisplayName; + }; + typedef std::map<OUString, TInstalledDriver> TInstalledDrivers; + + class DriversConfigImpl + { + mutable ::utl::OConfigurationTreeRoot m_aInstalled; + mutable TInstalledDrivers m_aDrivers; + public: + DriversConfigImpl(); + + const TInstalledDrivers& getInstalledDrivers(const css::uno::Reference< css::uno::XComponentContext >& _rxORB) const; + }; + + // Allows to access all driver which are located in the configuration + + class OOO_DLLPUBLIC_DBTOOLS DriversConfig + { + typedef salhelper::SingletonRef<DriversConfigImpl> OSharedConfigNode; + + const ::comphelper::NamedValueCollection& impl_get(std::u16string_view _sURL,sal_Int32 _nProps) const; + public: + DriversConfig(const css::uno::Reference< css::uno::XComponentContext >& _rxORB); + ~DriversConfig(); + + DriversConfig( const DriversConfig& ); + DriversConfig& operator=( const DriversConfig& ); + + OUString getDriverFactoryName(std::u16string_view _sUrl) const; + OUString getDriverTypeDisplayName(std::u16string_view _sUrl) const; + const ::comphelper::NamedValueCollection& getProperties(std::u16string_view _sURL) const; + const ::comphelper::NamedValueCollection& getFeatures(std::u16string_view _sURL) const; + const ::comphelper::NamedValueCollection& getMetaData(std::u16string_view _sURL) const; + css::uno::Sequence< OUString > getURLs() const; + private: + OSharedConfigNode m_aNode; + css::uno::Reference< css::uno::XComponentContext > m_xORB; + }; +} +#endif // INCLUDED_CONNECTIVITY_DRIVERSCONFIG_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/FValue.hxx b/include/connectivity/FValue.hxx new file mode 100644 index 000000000..1fe2b9d5f --- /dev/null +++ b/include/connectivity/FValue.hxx @@ -0,0 +1,490 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#ifndef INCLUDED_CONNECTIVITY_FVALUE_HXX +#define INCLUDED_CONNECTIVITY_FVALUE_HXX + +#include <com/sun/star/sdbc/DataType.hpp> +#include <com/sun/star/uno/Any.hxx> +#include <rtl/ustring.hxx> +#include <salhelper/simplereferenceobject.hxx> +#include <rtl/ref.hxx> +#include <connectivity/dbtoolsdllapi.hxx> +#include <connectivity/CommonTools.hxx> +#include <com/sun/star/util/DateTime.hpp> +#include <com/sun/star/util/Date.hpp> +#include <com/sun/star/util/Time.hpp> +#include <com/sun/star/uno/Sequence.hxx> + +namespace com::sun::star::sdb { class XColumn; } +namespace com::sun::star::sdbc { class XRow; } + +namespace connectivity +{ + namespace detail + { + class IValueSource; + } + + class OOO_DLLPUBLIC_DBTOOLS ORowSetValue + { + union + { + bool m_bBool; + + sal_Int8 m_nInt8; + sal_uInt8 m_uInt8; + + sal_Int16 m_nInt16; + sal_uInt16 m_uInt16; + + sal_Int32 m_nInt32; + sal_uInt32 m_uInt32; + + sal_Int64 m_nInt64; + sal_uInt64 m_uInt64; + + float m_nFloat; + double m_nDouble; + + rtl_uString* m_pString; + + void* m_pValue; // date/time/timestamp/sequence + } m_aValue; + + sal_Int32 m_eTypeKind; // the database type + bool m_bNull : 1; // value is null + bool m_bBound : 1; // is bound + bool m_bModified : 1; // value was changed + bool m_bSigned : 1; // value is signed + + void free() noexcept; + + public: + ORowSetValue() + :m_eTypeKind(css::sdbc::DataType::VARCHAR) + ,m_bNull(true) + ,m_bBound(true) + ,m_bModified(false) + ,m_bSigned(true) + { + m_aValue.m_pString = nullptr; + } + + ORowSetValue(const ORowSetValue& _rRH) + :m_eTypeKind(css::sdbc::DataType::VARCHAR) + ,m_bNull(true) + ,m_bBound(true) + ,m_bModified(false) + ,m_bSigned(true) + { + m_aValue.m_pString = nullptr; + operator=(_rRH); + } + + ORowSetValue(ORowSetValue&& _rRH) noexcept + :m_eTypeKind(css::sdbc::DataType::VARCHAR) + ,m_bNull(true) + ,m_bBound(true) + ,m_bModified(false) + ,m_bSigned(true) + { + m_aValue.m_pString = nullptr; + operator=(std::move(_rRH)); + } + + ORowSetValue(const OUString& _rRH) + :m_eTypeKind(css::sdbc::DataType::VARCHAR) + ,m_bNull(true) + ,m_bBound(true) + ,m_bModified(false) + ,m_bSigned(true) + { + m_aValue.m_pString = nullptr; + operator=(_rRH); + } + + ORowSetValue(const double& _rRH) + :m_eTypeKind(css::sdbc::DataType::DOUBLE) + ,m_bNull(true) + ,m_bBound(true) + ,m_bModified(false) + ,m_bSigned(true) + { + m_aValue.m_pString = nullptr; + operator=(_rRH); + } + + ORowSetValue(float _rRH) + :m_eTypeKind(css::sdbc::DataType::FLOAT) + ,m_bNull(true) + ,m_bBound(true) + ,m_bModified(false) + ,m_bSigned(true) + { + m_aValue.m_pString = nullptr; + operator=(_rRH); + } + + ORowSetValue(sal_Int8 _rRH) + :m_eTypeKind(css::sdbc::DataType::TINYINT) + ,m_bNull(true) + ,m_bBound(true) + ,m_bModified(false) + ,m_bSigned(true) + { + m_aValue.m_pString = nullptr; + operator=(_rRH); + } + + ORowSetValue(sal_Int16 _rRH) + :m_eTypeKind(css::sdbc::DataType::SMALLINT) + ,m_bNull(true) + ,m_bBound(true) + ,m_bModified(false) + ,m_bSigned(true) + { + m_aValue.m_pString = nullptr; + operator=(_rRH); + } + ORowSetValue(sal_uInt16 _rRH) + :m_eTypeKind(css::sdbc::DataType::SMALLINT) + ,m_bNull(true) + ,m_bBound(true) + ,m_bModified(false) + ,m_bSigned(false) + { + m_aValue.m_pString = nullptr; + operator=(_rRH); + } + ORowSetValue(sal_Int32 _rRH) + :m_eTypeKind(css::sdbc::DataType::INTEGER) + ,m_bNull(true) + ,m_bBound(true) + ,m_bModified(false) + ,m_bSigned(true) + { + m_aValue.m_pString = nullptr; + operator=(_rRH); + } + ORowSetValue(sal_uInt32 _rRH) + :m_eTypeKind(css::sdbc::DataType::INTEGER) + ,m_bNull(true) + ,m_bBound(true) + ,m_bModified(false) + ,m_bSigned(false) + { + m_aValue.m_pString = nullptr; + operator=(_rRH); + } + ORowSetValue(sal_Int64 _rRH) + :m_eTypeKind(css::sdbc::DataType::BIGINT) + ,m_bNull(true) + ,m_bBound(true) + ,m_bModified(false) + ,m_bSigned(true) + { + m_aValue.m_pString = nullptr; + operator=(_rRH); + } + ORowSetValue(sal_uInt64 _rRH) + :m_eTypeKind(css::sdbc::DataType::BIGINT) + ,m_bNull(true) + ,m_bBound(true) + ,m_bModified(false) + ,m_bSigned(false) + { + m_aValue.m_pString = nullptr; + operator=(_rRH); + } + + ORowSetValue(bool _rRH) + :m_eTypeKind(css::sdbc::DataType::BIT) + ,m_bNull(true) + ,m_bBound(true) + ,m_bModified(false) + ,m_bSigned(true) + { + m_aValue.m_pString = nullptr; + operator=(_rRH); + } + ORowSetValue(sal_Bool) = delete; // aka sal_uInt8 + + ORowSetValue(const css::util::Date& _rRH) + :m_eTypeKind(css::sdbc::DataType::DATE) + ,m_bNull(true) + ,m_bBound(true) + ,m_bModified(false) + ,m_bSigned(true) + { + m_aValue.m_pString = nullptr; + operator=(_rRH); + } + + ORowSetValue(const css::util::Time& _rRH) + :m_eTypeKind(css::sdbc::DataType::TIME) + ,m_bNull(true) + ,m_bBound(true) + ,m_bModified(false) + ,m_bSigned(true) + { + m_aValue.m_pString = nullptr; + operator=(_rRH); + } + + ORowSetValue(const css::util::DateTime& _rRH) + :m_eTypeKind(css::sdbc::DataType::TIMESTAMP) + ,m_bNull(true) + ,m_bBound(true) + ,m_bModified(false) + ,m_bSigned(true) + { + m_aValue.m_pString = nullptr; + operator=(_rRH); + } + + ORowSetValue(const css::uno::Sequence<sal_Int8>& _rRH) + :m_eTypeKind(css::sdbc::DataType::LONGVARBINARY) + ,m_bNull(true) + ,m_bBound(true) + ,m_bModified(false) + ,m_bSigned(true) + { + m_aValue.m_pString = nullptr; + operator=(_rRH); + } + + // Avoid accidental uses of ORowSetValue(bool const &): + template<typename T> ORowSetValue(T const *) = delete; + + ~ORowSetValue() + { + free(); + } + + ORowSetValue& operator=(const ORowSetValue& _rRH); + ORowSetValue& operator=(ORowSetValue&& _rRH) noexcept; + + // simple types + ORowSetValue& operator=(bool _rRH); + void operator =(sal_Bool) = delete; // aka sal_uInt8 + + ORowSetValue& operator=(sal_Int8 _rRH); + + ORowSetValue& operator=(sal_Int16 _rRH); + ORowSetValue& operator=(sal_uInt16 _rRH); + + ORowSetValue& operator=(sal_Int32 _rRH); + ORowSetValue& operator=(sal_uInt32 _rRH); + + ORowSetValue& operator=(sal_Int64 _rRH); + ORowSetValue& operator=(sal_uInt64 _rRH); + + ORowSetValue& operator=(double _rRH); + ORowSetValue& operator=(float _rRH); + + // ADT's + ORowSetValue& operator=(const css::util::Date& _rRH); + ORowSetValue& operator=(const css::util::Time& _rRH); + ORowSetValue& operator=(const css::util::DateTime& _rRH); + + ORowSetValue& operator=(const OUString& _rRH); + // the type isn't set it will be set to VARCHAR if the type is different change it + ORowSetValue& operator=(const css::uno::Sequence<sal_Int8>& _rRH); + // with the possibility to save an any for bookmarks + ORowSetValue& operator=(const css::uno::Any& _rAny); + + bool operator==(const ORowSetValue& _rRH) const; + bool operator!=(const ORowSetValue& _rRH) const + { + return !( *this == _rRH ); + } + + bool isNull() const + { + return m_bNull; + } + void setNull() + { + free(); + m_bNull = true; + m_aValue.m_pString = nullptr; + } + + bool isBound() const { return m_bBound; } + void setBound(bool _bBound) { m_bBound = _bBound; } + + bool isModified() const { return m_bModified; } + void setModified(bool _bMod) { m_bModified = _bMod; } + + bool isSigned() const { return m_bSigned; } + void setSigned(bool _bSig); + + sal_Int32 getTypeKind() const { return m_eTypeKind; } + void setTypeKind(sal_Int32 _eType); + + bool getBool() const; + + sal_Int8 getInt8() const; + sal_uInt8 getUInt8() const; + + sal_Int16 getInt16() const; + sal_uInt16 getUInt16() const; + + sal_Int32 getInt32() const; + sal_uInt32 getUInt32() const; + + sal_Int64 getLong() const; + sal_uInt64 getULong() const; + + double getDouble() const; + float getFloat() const; + + OUString getString() const; // makes an automatic conversion if type isn't a string + css::util::Date getDate() const; + css::util::Time getTime() const; + css::util::DateTime getDateTime() const; + css::uno::Sequence<sal_Int8> getSequence() const; + // only use for anys + const css::uno::Any& getAny() const { return *static_cast<css::uno::Any*>(m_aValue.m_pValue); } + css::uno::Any makeAny() const; + + /** + fetches a single value out of the row + @param _nPos the current column position + @param _nType the type of the current column + @param _xRow the row where to fetch the data from + */ + void fill(sal_Int32 _nPos, + sal_Int32 _nType, + const css::uno::Reference< css::sdbc::XRow>& _xRow); + + /** + fetches a single value out of the row + @param _nPos the current column position + @param _nType the type of the current column + @param _bNullable if true then it will be checked if the result could be NULL, otherwise not. + @param _xRow the row where to fetch the data from + */ + void fill(sal_Int32 _nPos, + sal_Int32 _nType, + bool _bNullable, + const css::uno::Reference< css::sdbc::XRow>& _xRow); + + void fill(const css::uno::Any& _rValue); + + void fill( const sal_Int32 _nType, + const css::uno::Reference< css::sdb::XColumn >& _rxColumn ); + + private: + void impl_fill( const sal_Int32 _nType, bool _bNullable, const detail::IValueSource& _rValueSource ); + }; + + /// ORowSetValueDecorator decorates an ORowSetValue so the value is "refcounted" + class OOO_DLLPUBLIC_DBTOOLS ORowSetValueDecorator final : public ::salhelper::SimpleReferenceObject + { + ORowSetValue m_aValue; // my own value + public: + ORowSetValueDecorator(){m_aValue.setBound(true);} + ORowSetValueDecorator(const ORowSetValue& _aValue) : m_aValue(_aValue){m_aValue.setBound(true);} + ORowSetValueDecorator& operator=(const ORowSetValue& _aValue); + + operator const ORowSetValue&() const { return m_aValue; } + bool operator ==( const ORowSetValue & _rRH ) { return m_aValue == _rRH; } + const ORowSetValue& getValue() const { return m_aValue; } + ORowSetValue& get() { return m_aValue; } + void setValue(const ORowSetValue& _aValue) { m_aValue = _aValue; } + void setNull() { m_aValue.setNull(); } + void setBound(bool _bBound ) { m_aValue.setBound(_bBound);} + bool isBound( ) const { return m_aValue.isBound();} + void setTypeKind(sal_Int32 _nType) { m_aValue.setTypeKind(_nType); } + void setModified(bool _bModified) { m_aValue.setModified(_bModified); } + + }; + typedef ::rtl::Reference<ORowSetValueDecorator> ORowSetValueDecoratorRef; + + + /// TSetBound is a functor to set the bound value with e.q. for_each call + struct OOO_DLLPUBLIC_DBTOOLS TSetBound + { + bool m_bBound; + TSetBound(bool _bBound) : m_bBound(_bBound){} + void operator()(ORowSetValue& _rValue) const { _rValue.setBound(m_bBound); } + + }; + + + /// TSetBound is a functor to set the bound value with e.q. for_each call + struct OOO_DLLPUBLIC_DBTOOLS TSetRefBound + { + bool m_bBound; + TSetRefBound(bool _bBound) : m_bBound(_bBound){} + void operator()(ORowSetValueDecoratorRef const & _rValue) const { _rValue->setBound(m_bBound); } + + }; + + + // Vector for file based rows + + template< class VectorVal > class ODeleteVector : public connectivity::ORowVector< VectorVal > + { + bool m_bDeleted; + public: + ODeleteVector() : connectivity::ORowVector< VectorVal >() ,m_bDeleted(false) {} + ODeleteVector(size_t _st) : connectivity::ORowVector< VectorVal >(_st) ,m_bDeleted(false) {} + + bool isDeleted() const { return m_bDeleted; } + void setDeleted(bool _bDeleted) { m_bDeleted = _bDeleted; } + }; + + typedef ODeleteVector< ORowSetValue > OValueVector; + + class OOO_DLLPUBLIC_DBTOOLS OValueRefVector : public ODeleteVector< ORowSetValueDecoratorRef > + { + public: + OValueRefVector(){} + OValueRefVector(size_t _st) : ODeleteVector< ORowSetValueDecoratorRef >(_st) + { + for (auto & elem : *this) + elem = new ORowSetValueDecorator; + } + }; + +#define SQL_NO_PARAMETER (SAL_MAX_UINT32) + class OAssignValues final : public OValueRefVector + { + ::std::vector<sal_Int32> m_nParameterIndexes; + public: + OAssignValues(size_type n) : OValueRefVector(n),m_nParameterIndexes(n+1,SQL_NO_PARAMETER){} + + void setParameterIndex(sal_Int32 _nId,sal_Int32 _nParameterIndex) { m_nParameterIndexes[_nId] = _nParameterIndex;} + sal_Int32 getParameterIndex(sal_Int32 _nId) const { return m_nParameterIndexes[_nId]; } + }; + + typedef ::rtl::Reference< OAssignValues > ORefAssignValues; + + + typedef ::rtl::Reference< OValueVector > OValueRow; + typedef ::rtl::Reference< OValueRefVector > OValueRefRow; +} + +#endif // INCLUDED_CONNECTIVITY_FVALUE_HXX + + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/IParseContext.hxx b/include/connectivity/IParseContext.hxx new file mode 100644 index 000000000..51171281d --- /dev/null +++ b/include/connectivity/IParseContext.hxx @@ -0,0 +1,101 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ +#ifndef INCLUDED_CONNECTIVITY_IPARSECONTEXT_HXX +#define INCLUDED_CONNECTIVITY_IPARSECONTEXT_HXX + +#include <rtl/ustring.hxx> +#include <com/sun/star/lang/Locale.hpp> + +namespace connectivity +{ + + //= IParseContext + + class IParseContext + { + public: + enum class ErrorCode + { + General, // "Syntax error in SQL expression" + ValueNoLike, // "The value #1 can not be used with LIKE." + FieldNoLike, // "LIKE can not be used with this field." + InvalidCompare, // "The entered criterion can not be compared with this field." + InvalidIntCompare, // "The field can not be compared with a number." + InvalidDateCompare, // "The field can not be compared with a date." + InvalidRealCompare, // "The field can not be compared with a floating point number." + InvalidTableNosuch, // "The database does not contain a table named \"#\"." + // Named like this to avoid conflict with a #define in the Windows system ODBC headers. + InvalidTableOrQuery, // "The database does contain neither a table nor a query named \"#\"." + InvalidColumn, // "The column \"#1\" is unknown in the table \"#2\"." + InvalidTableExist, // "The database already contains a table or view with name \"#\"." + InvalidQueryExist // "The database already contains a query with name \"#\"."; + }; + + enum class InternationalKeyCode + { + None = 0, + Like, + Not, + Null, + True, + False, + Is, + Between, + Or, + And, + Avg, + Count, + Max, + Min, + Sum, + Every, + Any, + Some, + StdDevPop, + StdDevSamp, + VarSamp, + VarPop, + Collect, + Fusion, + Intersection + }; + + public: + // retrieves language specific error messages + virtual OUString getErrorMessage(ErrorCode _eCodes) const = 0; + + // retrieves language specific keyword strings (only ASCII allowed) + virtual OString getIntlKeywordAscii(InternationalKeyCode _eKey) const = 0; + + // finds out, if we have an international keyword (only ASCII allowed) + virtual InternationalKeyCode getIntlKeyCode(const OString& rToken) const = 0; + + /** gets a locale instance which should be used when parsing in the context specified by this instance + <p>if this is not overridden by derived classes, it returns the static default locale.</p> + */ + virtual css::lang::Locale getPreferredLocale( ) const = 0; + + protected: + ~IParseContext() {} + }; +} + +#endif // INCLUDED_CONNECTIVITY_IPARSECONTEXT_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/PColumn.hxx b/include/connectivity/PColumn.hxx new file mode 100644 index 000000000..46ceaa1bb --- /dev/null +++ b/include/connectivity/PColumn.hxx @@ -0,0 +1,148 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ +#ifndef INCLUDED_CONNECTIVITY_PCOLUMN_HXX +#define INCLUDED_CONNECTIVITY_PCOLUMN_HXX + +#include <sal/config.h> + +#include <map> + +#include <connectivity/dbtoolsdllapi.hxx> +#include <connectivity/sdbcx/VColumn.hxx> +#include <connectivity/CommonTools.hxx> +#include <rtl/ref.hxx> +#include <comphelper/proparrhlp.hxx> + +namespace com::sun::star::container { class XNameAccess; } +namespace com::sun::star::sdbc { class XDatabaseMetaData; } +namespace com::sun::star::sdbc { class XResultSetMetaData; } + +namespace connectivity::parse + { + class OParseColumn; + + typedef sdbcx::OColumn OParseColumn_BASE; + typedef ::comphelper::OPropertyArrayUsageHelper<OParseColumn> OParseColumn_PROP; + + class OOO_DLLPUBLIC_DBTOOLS OParseColumn final : + public OParseColumn_BASE, public OParseColumn_PROP + { + OUString m_aRealName; + OUString m_sLabel; + bool m_bFunction; + bool m_bDbasePrecisionChanged; + bool m_bAggregateFunction; + bool m_bIsSearchable; + + virtual ::cppu::IPropertyArrayHelper* createArrayHelper() const override; + virtual ::cppu::IPropertyArrayHelper & SAL_CALL getInfoHelper() override; + + virtual ~OParseColumn() override; + public: + OParseColumn(const css::uno::Reference< css::beans::XPropertySet>& _xColumn, bool _bCase); + OParseColumn(const OUString& Name, + const OUString& TypeName, + const OUString& DefaultValue, + const OUString& Description, + sal_Int32 IsNullable, + sal_Int32 Precision, + sal_Int32 Scale, + sal_Int32 Type, + bool IsAutoIncrement, + bool IsCurrency, + bool _bCase, + const OUString& CatalogName, + const OUString& SchemaName, + const OUString& TableName); + + virtual void construct() override; + + void setRealName(const OUString& _rName) { m_aRealName = _rName; } + void setLabel(const OUString& i_sLabel) { m_sLabel = i_sLabel; } + void setTableName(const OUString& _rName) { m_TableName = _rName; } + void setFunction(bool _bFunction) { m_bFunction = _bFunction; } + void setAggregateFunction(bool _bFunction) { m_bAggregateFunction = _bFunction; } + void setIsSearchable( bool _bIsSearchable ) { m_bIsSearchable = _bIsSearchable; } + const OUString& getRealName() const { return m_aRealName; } + + /** creates a collection of OParseColumn, as described by a result set meta data instance. + */ + static ::rtl::Reference< OSQLColumns > + createColumnsForResultSet( + const css::uno::Reference< css::sdbc::XResultSetMetaData >& _rxResMetaData, + const css::uno::Reference< css::sdbc::XDatabaseMetaData >& _rxDBMetaData, + const css::uno::Reference< css::container::XNameAccess>& i_xQueryColumns + ); + + typedef std::map<OUString, int> StringMap; + /** creates a single OParseColumn, as described by a result set meta data instance. + The column names are unique. + */ + static rtl::Reference<OParseColumn> + createColumnForResultSet( + const css::uno::Reference< css::sdbc::XResultSetMetaData >& _rxResMetaData, + const css::uno::Reference< css::sdbc::XDatabaseMetaData >& _rxDBMetaData, + sal_Int32 _nColumnPos, + StringMap& _rColumns + ); + + private: + using OParseColumn_BASE::createArrayHelper; + }; + + class OOrderColumn; + + typedef sdbcx::OColumn OOrderColumn_BASE; + typedef ::comphelper::OPropertyArrayUsageHelper<OOrderColumn> OOrderColumn_PROP; + + class OOrderColumn final : + public OOrderColumn_BASE, public OOrderColumn_PROP + { + const bool m_bAscending; + + virtual ::cppu::IPropertyArrayHelper* createArrayHelper() const override; + virtual ::cppu::IPropertyArrayHelper & SAL_CALL getInfoHelper() override; + + virtual ~OOrderColumn() override; + public: + OOrderColumn( + const css::uno::Reference< css::beans::XPropertySet>& _xColumn, + const OUString& i_rOriginatingTableName, + bool _bCase, + bool _bAscending + ); + + OOrderColumn( + const css::uno::Reference< css::beans::XPropertySet>& _xColumn, + bool _bCase, + bool _bAscending + ); + + virtual void construct() override; + + virtual css::uno::Sequence< OUString > SAL_CALL getSupportedServiceNames( ) override; + private: + using OOrderColumn_BASE::createArrayHelper; + }; + +} + +#endif // INCLUDED_CONNECTIVITY_PCOLUMN_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/TColumnsHelper.hxx b/include/connectivity/TColumnsHelper.hxx new file mode 100644 index 000000000..c50aefb27 --- /dev/null +++ b/include/connectivity/TColumnsHelper.hxx @@ -0,0 +1,62 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#ifndef INCLUDED_CONNECTIVITY_TCOLUMNSHELPER_HXX +#define INCLUDED_CONNECTIVITY_TCOLUMNSHELPER_HXX + +#include <memory> +#include <connectivity/sdbcx/VCollection.hxx> +#include <connectivity/dbtoolsdllapi.hxx> + +namespace connectivity +{ + class OTableHelper; + class OColumnsHelperImpl; + /** contains general column handling to create default columns and default sql statements. + */ + class OOO_DLLPUBLIC_DBTOOLS OColumnsHelper : public sdbcx::OCollection + { + std::unique_ptr<OColumnsHelperImpl> m_pImpl; + protected: + OTableHelper* m_pTable; + + virtual sdbcx::ObjectType createObject(const OUString& _rName) override; + virtual void impl_refresh() override; + virtual css::uno::Reference< css::beans::XPropertySet > createDescriptor() override; + virtual sdbcx::ObjectType appendObject( const OUString& _rForName, const css::uno::Reference< css::beans::XPropertySet >& descriptor ) override; + virtual void dropObject(sal_Int32 _nPos, const OUString& _sElementName) override; + public: + OColumnsHelper( ::cppu::OWeakObject& _rParent + ,bool _bCase + ,::osl::Mutex& _rMutex + ,const ::std::vector< OUString> &_rVector + ,bool _bUseHardRef + ); + virtual ~OColumnsHelper() override; + + /** set the parent of the columns. Can also be <NULL/>. + @param _pTable + The parent. + */ + void setParent(OTableHelper* _pTable) { m_pTable = _pTable;} + }; +} +#endif // INCLUDED_CONNECTIVITY_TCOLUMNSHELPER_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/TIndexes.hxx b/include/connectivity/TIndexes.hxx new file mode 100644 index 000000000..4f3a09305 --- /dev/null +++ b/include/connectivity/TIndexes.hxx @@ -0,0 +1,49 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#ifndef INCLUDED_CONNECTIVITY_TINDEXES_HXX +#define INCLUDED_CONNECTIVITY_TINDEXES_HXX + +#include <connectivity/dbtoolsdllapi.hxx> +#include <connectivity/sdbcx/VCollection.hxx> + +namespace connectivity +{ + class OTableHelper; + class OOO_DLLPUBLIC_DBTOOLS OIndexesHelper : public sdbcx::OCollection + { + OTableHelper* m_pTable; + protected: + virtual sdbcx::ObjectType createObject(const OUString& _rName) override; + virtual void impl_refresh() override; + virtual css::uno::Reference< css::beans::XPropertySet > createDescriptor() override; + virtual sdbcx::ObjectType appendObject( const OUString& _rForName, const css::uno::Reference< css::beans::XPropertySet >& descriptor ) override; + virtual void dropObject(sal_Int32 _nPos,const OUString& _sElementName) override; + public: + OIndexesHelper(OTableHelper* _pTable, + ::osl::Mutex& _rMutex, + const ::std::vector< OUString> &_rVector + ); + + }; +} + +#endif // INCLUDED_CONNECTIVITY_TINDEXES_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/TKeys.hxx b/include/connectivity/TKeys.hxx new file mode 100644 index 000000000..ae226b874 --- /dev/null +++ b/include/connectivity/TKeys.hxx @@ -0,0 +1,57 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#ifndef INCLUDED_CONNECTIVITY_TKEYS_HXX +#define INCLUDED_CONNECTIVITY_TKEYS_HXX + +#include <connectivity/sdbcx/VCollection.hxx> +#include <connectivity/dbtoolsdllapi.hxx> + +namespace connectivity +{ + class OTableHelper; + typedef sdbcx::OCollection OKeys_BASE; + class OOO_DLLPUBLIC_DBTOOLS OKeysHelper : public OKeys_BASE + { + OTableHelper* m_pTable; + protected: + virtual sdbcx::ObjectType createObject(const OUString& _rName) override; + virtual void impl_refresh() override; + virtual css::uno::Reference< css::beans::XPropertySet > createDescriptor() override; + virtual sdbcx::ObjectType appendObject( const OUString& _rForName, const css::uno::Reference< css::beans::XPropertySet >& descriptor ) override; + virtual void dropObject(sal_Int32 _nPos, const OUString& _sElementName) override; + + virtual OUString getDropForeignKey() const; + + public: + OKeysHelper( OTableHelper* _pTable, + ::osl::Mutex& _rMutex, + const ::std::vector< OUString>& _rVector + ); + + static void cloneDescriptorColumns( + const sdbcx::ObjectType& _rSourceDescriptor, + const sdbcx::ObjectType& _rDestDescriptor + ); + }; +} + +#endif // INCLUDED_CONNECTIVITY_TKEYS_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/TTableHelper.hxx b/include/connectivity/TTableHelper.hxx new file mode 100644 index 000000000..e987241a6 --- /dev/null +++ b/include/connectivity/TTableHelper.hxx @@ -0,0 +1,168 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#ifndef INCLUDED_CONNECTIVITY_TTABLEHELPER_HXX +#define INCLUDED_CONNECTIVITY_TTABLEHELPER_HXX + +#include <memory> +#include <sal/config.h> + +#include <map> + +#include <connectivity/dbtoolsdllapi.hxx> +#include <connectivity/sdbcx/VTable.hxx> + +namespace com::sun::star::sdbc { class XConnection; } +namespace com::sun::star::sdb::tools { class XIndexAlteration; } +namespace com::sun::star::sdb::tools { class XKeyAlteration; } +namespace com::sun::star::sdb::tools { class XTableAlteration; } +namespace com::sun::star::sdb::tools { class XTableRename; } +namespace connectivity::sdbcx { struct KeyProperties; } + +namespace connectivity +{ + typedef sal_Int32 OrdinalPosition; + struct ColumnDesc + { + OUString sName; + OUString aField6; + OUString sField12; // REMARKS + OUString sField13; + sal_Int32 nField5 + , nField7 + , nField9 + , nField11; + + OrdinalPosition nOrdinalPosition; + + ColumnDesc( const OUString& _rName + , sal_Int32 _nField5 + , const OUString& _aField6 + , sal_Int32 _nField7 + , sal_Int32 _nField9 + , sal_Int32 _nField11 + , const OUString& _sField12 + , const OUString& _sField13 + ,OrdinalPosition _nPosition ) + :sName( _rName ) + ,aField6(_aField6) + ,sField12(_sField12) + ,sField13(_sField13) + ,nField5(_nField5) + ,nField7(_nField7) + ,nField9(_nField9) + ,nField11(_nField11) + ,nOrdinalPosition( _nPosition ) + { + } + }; + typedef connectivity::sdbcx::OTable OTable_TYPEDEF; + + typedef std::map<OUString, std::shared_ptr<sdbcx::KeyProperties>> TKeyMap; + + struct OTableHelperImpl; + + class OOO_DLLPUBLIC_DBTOOLS OTableHelper : public OTable_TYPEDEF + { + ::std::unique_ptr<OTableHelperImpl> m_pImpl; + + void refreshPrimaryKeys(::std::vector< OUString>& _rKeys); + void refreshForeignKeys(::std::vector< OUString>& _rKeys); + + protected: + /** creates the column collection for the table + @param _rNames + The column names. + */ + virtual sdbcx::OCollection* createColumns(const ::std::vector< OUString>& _rNames) = 0; + + /** creates the key collection for the table + @param _rNames + The key names. + */ + virtual sdbcx::OCollection* createKeys(const ::std::vector< OUString>& _rNames) = 0; + + /** creates the index collection for the table + @param _rNames + The index names. + */ + virtual sdbcx::OCollection* createIndexes(const ::std::vector< OUString>& _rNames) = 0; + + /** this function is called upon disposing the component + */ + virtual void SAL_CALL disposing() override; + + /** The default returns "RENAME TABLE " or "RENAME VIEW " depending on the type. + * + * \return The start of the rename statement. + */ + virtual OUString getRenameStart() const; + + virtual ~OTableHelper() override; + + public: + virtual void refreshColumns() override; + virtual void refreshKeys() override; + virtual void refreshIndexes() override; + + const ColumnDesc* getColumnDescription(const OUString& _sName) const; + + public: + OTableHelper( sdbcx::OCollection* _pTables, + const css::uno::Reference< css::sdbc::XConnection >& _xConnection, + bool _bCase); + OTableHelper( sdbcx::OCollection* _pTables, + const css::uno::Reference< css::sdbc::XConnection >& _xConnection, + bool _bCase, + const OUString& Name, + const OUString& Type, + const OUString& Description = OUString(), + const OUString& SchemaName = OUString(), + const OUString& CatalogName = OUString() + ); + + virtual css::uno::Reference< css::sdbc::XDatabaseMetaData> getMetaData() const override; + css::uno::Reference< css::sdbc::XConnection> const & getConnection() const; + + // XRename + virtual void SAL_CALL rename( const OUString& newName ) override; + + // XAlterTable + virtual void SAL_CALL alterColumnByIndex( sal_Int32 index, const css::uno::Reference< css::beans::XPropertySet >& descriptor ) override; + // XNamed + virtual OUString SAL_CALL getName() override; + + // To retrieve the table name only without the schema + const OUString & getTableName(); + + // helper method to get key properties + std::shared_ptr<sdbcx::KeyProperties> getKeyProperties(const OUString& _sName) const; + void addKey(const OUString& _sName,const std::shared_ptr<sdbcx::KeyProperties>& _aKeyProperties); + + virtual OUString getTypeCreatePattern() const; + + css::uno::Reference< css::sdb::tools::XTableRename> const & getRenameService() const; + css::uno::Reference< css::sdb::tools::XTableAlteration> const & getAlterService() const; + css::uno::Reference< css::sdb::tools::XKeyAlteration> const & getKeyService() const; + css::uno::Reference< css::sdb::tools::XIndexAlteration> const & getIndexService() const; + }; +} +#endif // INCLUDED_CONNECTIVITY_TTABLEHELPER_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/conncleanup.hxx b/include/connectivity/conncleanup.hxx new file mode 100644 index 000000000..d243e3842 --- /dev/null +++ b/include/connectivity/conncleanup.hxx @@ -0,0 +1,90 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#ifndef INCLUDED_CONNECTIVITY_CONNCLEANUP_HXX +#define INCLUDED_CONNECTIVITY_CONNCLEANUP_HXX + +#include <cppuhelper/implbase.hxx> +#include <com/sun/star/beans/XPropertyChangeListener.hpp> +#include <com/sun/star/sdbc/XRowSetListener.hpp> +#include <connectivity/dbtoolsdllapi.hxx> + + +namespace com::sun::star::beans { class XPropertySet; } +namespace com::sun::star::sdbc { class XRowSet; } +namespace com::sun::star::sdbc { class XConnection; } + +namespace dbtools +{ + + + //= OAutoConnectionDisposer + + typedef ::cppu::WeakImplHelper < css::beans::XPropertyChangeListener, + css::sdbc::XRowSetListener + > OAutoConnectionDisposer_Base; + + class OOO_DLLPUBLIC_DBTOOLS OAutoConnectionDisposer final : public OAutoConnectionDisposer_Base + { + css::uno::Reference< css::sdbc::XConnection > + m_xOriginalConnection; + css::uno::Reference< css::sdbc::XRowSet > m_xRowSet; // needed to add as listener + bool m_bRSListening : 1; // true when we're listening on rowset + bool m_bPropertyListening : 1; // true when we're listening for property changes + + public: + /** constructs an object + <p>The connection given will be set on the rowset (as ActiveConnection), and the object adds itself as property + change listener for the connection. Once somebody sets a new ActiveConnection, the old one (the one given + here) will be disposed.</p> + */ + OAutoConnectionDisposer( + const css::uno::Reference< css::sdbc::XRowSet >& _rxRowSet, + const css::uno::Reference< css::sdbc::XConnection >& _rxConnection + ); + + private: + // XPropertyChangeListener + virtual void SAL_CALL propertyChange( const css::beans::PropertyChangeEvent& _rEvent ) override; + + // XEventListener + virtual void SAL_CALL disposing( const css::lang::EventObject& _rSource ) override; + + // XRowSetListener + virtual void SAL_CALL cursorMoved( const css::lang::EventObject& event ) override; + virtual void SAL_CALL rowChanged( const css::lang::EventObject& event ) override; + virtual void SAL_CALL rowSetChanged( const css::lang::EventObject& event ) override; + + void clearConnection(); + + void startRowSetListening(); + void stopRowSetListening(); + bool isRowSetListening() const { return m_bRSListening; } + + void startPropertyListening( const css::uno::Reference< css::beans::XPropertySet >& _rxProps ); + void stopPropertyListening( const css::uno::Reference< css::beans::XPropertySet >& _rxEventSource ); + }; + + +} // namespace dbtools + + +#endif // INCLUDED_CONNECTIVITY_CONNCLEANUP_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/dbcharset.hxx b/include/connectivity/dbcharset.hxx new file mode 100644 index 000000000..3ee993243 --- /dev/null +++ b/include/connectivity/dbcharset.hxx @@ -0,0 +1,149 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#ifndef INCLUDED_CONNECTIVITY_DBCHARSET_HXX +#define INCLUDED_CONNECTIVITY_DBCHARSET_HXX + +#include <sal/config.h> + +#include <set> + +#include <rtl/textenc.h> +#include <rtl/tencinfo.h> +#include <rtl/ustring.hxx> +#include <connectivity/dbtoolsdllapi.hxx> + + +namespace dbtools +{ + + + //= OCharsetMap + + /** is a class which translates between different charset representations. + + <p>The set of recognized charsets is very limited: only the ones which are database relevant are + implemented at the moment</p> + + <p>Possible representations are: + <ul> + <li><b>IANA names.</b> + Have a look at <A href="http://www.iana.org/assignments/character-sets">this document</A> for + more details</li> + <li><b>rtl_TextEncoding</b></li> + </ul> + </p> + */ + class OOO_DLLPUBLIC_DBTOOLS OCharsetMap + { + protected: + typedef std::set<rtl_TextEncoding> TextEncBag; + + TextEncBag m_aEncodings; + + public: + class CharsetIterator; + friend class OCharsetMap::CharsetIterator; + typedef CharsetIterator iterator; + typedef CharsetIterator const_iterator; + + OCharsetMap(); + virtual ~OCharsetMap(); + + /** find the given text encoding in the map. + @return the <em>end</em> iterator if the encoding could not be found. + */ + CharsetIterator find(const rtl_TextEncoding _eEncoding) const; + /** find the given IANA name in the map. + @return the <em>end</em> iterator if the IANA name could not be found. + */ + CharsetIterator findIanaName(const OUString& _rIanaName) const; + + /// get access to the first element of the charset collection + CharsetIterator begin() const; + /// get access to the (last + 1st) element of the charset collection + CharsetIterator end() const; + + protected: + // needed because we want to call a virtual method during construction + void lateConstruct(); + void ensureConstructed( ) const { if ( m_aEncodings.empty() ) const_cast< OCharsetMap* >( this )->lateConstruct(); } + + virtual bool approveEncoding( const rtl_TextEncoding _eEncoding, const rtl_TextEncodingInfo& _rInfo ) const; + }; + + + //- CharsetIteratorDerefHelper + + class OOO_DLLPUBLIC_DBTOOLS CharsetIteratorDerefHelper + { + friend class OCharsetMap::CharsetIterator; + + rtl_TextEncoding m_eEncoding; + OUString m_aIanaName; + + public: + CharsetIteratorDerefHelper(const CharsetIteratorDerefHelper& _rSource); + + rtl_TextEncoding getEncoding() const { return m_eEncoding; } + const OUString& getIanaName() const { return m_aIanaName; } + + protected: + CharsetIteratorDerefHelper( const rtl_TextEncoding _eEncoding, const OUString& _rIanaName ); + + }; + + + //- OCharsetMap::CharsetIterator + + class OOO_DLLPUBLIC_DBTOOLS OCharsetMap::CharsetIterator + { + friend class OCharsetMap; + + friend OOO_DLLPUBLIC_DBTOOLS bool operator==(const CharsetIterator& lhs, const CharsetIterator& rhs); + friend bool operator!=(const CharsetIterator& lhs, const CharsetIterator& rhs) { return !(lhs == rhs); } + +// friend sal_Int32 operator-(const CharsetIterator& lhs, const CharsetIterator& rhs); + + const OCharsetMap* m_pContainer; + OCharsetMap::TextEncBag::const_iterator m_aPos; + + public: + CharsetIteratorDerefHelper operator*() const; + // no -> operator + // this would require us to a) store CharsetIteratorDerefHelper instances ourself so that we + // can return a pointer or b) introduce a -> operator on the CharsetIteratorDerefHelper, too. + + /// prefix increment + const CharsetIterator& operator++(); + + /// prefix decrement + const CharsetIterator& operator--(); + + protected: + CharsetIterator(const OCharsetMap* _pContainer, OCharsetMap::TextEncBag::const_iterator const & _aPos ); + }; + + +} // namespace dbtools + + +#endif // INCLUDED_CONNECTIVITY_DBCHARSET_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/dbconversion.hxx b/include/connectivity/dbconversion.hxx new file mode 100644 index 000000000..e9471344c --- /dev/null +++ b/include/connectivity/dbconversion.hxx @@ -0,0 +1,185 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#ifndef INCLUDED_CONNECTIVITY_DBCONVERSION_HXX +#define INCLUDED_CONNECTIVITY_DBCONVERSION_HXX + +#include <com/sun/star/util/Date.hpp> +#include <connectivity/dbtoolsdllapi.hxx> + +namespace com::sun::star::uno { template <typename > class Reference; } + +namespace com::sun::star +{ + namespace lang + { + struct Locale; + } + namespace sdb + { + class XColumn; + class XColumnUpdate; + } + namespace beans + { + class XPropertySet; + } + namespace util + { + class XNumberFormatter; + class XNumberFormatsSupplier; + struct Time; + struct DateTime; + } + namespace script + { + class XTypeConverter; + } +} + +namespace dbtools::DBTypeConversion +{ + OOO_DLLPUBLIC_DBTOOLS css::util::Date const & getStandardDate(); + /// @throws css::lang::IllegalArgumentException + OOO_DLLPUBLIC_DBTOOLS void setValue(const css::uno::Reference< css::sdb::XColumnUpdate>& xVariant, + const css::uno::Reference< css::util::XNumberFormatter>& xFormatter, + const css::util::Date& rNullDate, + const OUString& rString, + sal_Int32 nKey, + sal_Int16 nFieldType, + sal_Int16 nKeyType); + + /// @throws css::lang::IllegalArgumentException + OOO_DLLPUBLIC_DBTOOLS void setValue(const css::uno::Reference< css::sdb::XColumnUpdate>& xVariant, + const css::util::Date& rNullDate, + const double& rValue, + sal_Int16 nKeyType); + + OOO_DLLPUBLIC_DBTOOLS double getValue( const css::uno::Reference< css::sdb::XColumn>& xVariant, const css::util::Date& rNullDate ); + + // get the columnvalue as string with a default format given by the column or a default format + // for the type + OOO_DLLPUBLIC_DBTOOLS OUString getFormattedValue( + const css::uno::Reference< css::beans::XPropertySet>& _xColumn, + const css::uno::Reference< css::util::XNumberFormatter>& xFormatter, + const css::lang::Locale& _rLocale, + const css::util::Date& rNullDate); + + OOO_DLLPUBLIC_DBTOOLS OUString getFormattedValue( + const css::uno::Reference< css::sdb::XColumn>& _xColumn, + const css::uno::Reference< css::util::XNumberFormatter>& xFormatter, + const css::util::Date& rNullDate, + sal_Int32 nKey, + sal_Int16 nKeyType); + + OOO_DLLPUBLIC_DBTOOLS css::util::Date toDate(double dVal, const css::util::Date& _rNullDate = getStandardDate()); + OOO_DLLPUBLIC_DBTOOLS css::util::Date toDate(std::u16string_view _sSQLDate); + OOO_DLLPUBLIC_DBTOOLS css::util::Time toTime(double dVal, short nDigits = 9); + OOO_DLLPUBLIC_DBTOOLS css::util::Time toTime(std::u16string_view _sSQLDate); + OOO_DLLPUBLIC_DBTOOLS css::util::DateTime toDateTime(double dVal, const css::util::Date& _rNullDate = getStandardDate()); + OOO_DLLPUBLIC_DBTOOLS css::util::DateTime toDateTime(const OUString& _sSQLDate); + + OOO_DLLPUBLIC_DBTOOLS sal_Int64 getNsFromTime(const css::util::Time& rVal); + + OOO_DLLPUBLIC_DBTOOLS sal_Int32 toDays(const css::util::Date& _rVal, const css::util::Date& _rNullDate = getStandardDate()); + + OOO_DLLPUBLIC_DBTOOLS double toDouble(const css::util::Date& rVal, const css::util::Date& _rNullDate = getStandardDate()); + OOO_DLLPUBLIC_DBTOOLS double toDouble(const css::util::Time& rVal); + OOO_DLLPUBLIC_DBTOOLS double toDouble(const css::util::DateTime& rVal, const css::util::Date& _rNullDate = getStandardDate()); + + OOO_DLLPUBLIC_DBTOOLS css::util::Date toDate(sal_Int32 _nVal); + OOO_DLLPUBLIC_DBTOOLS css::util::Time toTime(sal_Int64 _nVal); + + /** convert a double which is a date value relative to the standard db null date into a date value relative + to a given fixed date. + */ + inline double toNullDate(const css::util::Date& _rNullDate, double _rVal) { return _rVal - toDays(_rNullDate); } + + // return the date from the numberformatsupplier or the STANDARD_DATE (1900,1,1) + OOO_DLLPUBLIC_DBTOOLS css::util::Date getNULLDate(const css::uno::Reference< css::util::XNumberFormatsSupplier > &xSupplier); + + // return the date in the format %04d-%02d-%02d + OOO_DLLPUBLIC_DBTOOLS OUString toDateString(const css::util::Date& rDate); + // return the time in the format %02d:%02d:%02d + OOO_DLLPUBLIC_DBTOOLS OUString toTimeStringS(const css::util::Time& rTime); + // return the time in the format %02d:%02d:%02d.%09d + OOO_DLLPUBLIC_DBTOOLS OUString toTimeString(const css::util::Time& rTime); + // return the DateTime in the format %04d-%02d-%02d %02d:%02d:%02d.%09d + OOO_DLLPUBLIC_DBTOOLS OUString toDateTimeString(const css::util::DateTime& _rDateTime); + // return the any in an sql standard format + OOO_DLLPUBLIC_DBTOOLS OUString toSQLString(sal_Int32 eType, const css::uno::Any& _rVal, + const css::uno::Reference< css::script::XTypeConverter >& _rxTypeConverter); + + /** converts a Unicode string into a 8-bit string, using the given encoding + + @param _rSource + the source string to convert + @param _rDest + the destination string + @param _eEncoding + the encoding to use for the conversion + + @throws css::sdbc::SQLException + if the given string contains characters which are not convertible using the given encoding + The SQLState of the exception will be set to 22018 ("Invalid character value for cast specification") + + @return + the length of the converted string + */ + OOO_DLLPUBLIC_DBTOOLS sal_Int32 convertUnicodeString( + const OUString& _rSource, + OString& _rDest, + rtl_TextEncoding _eEncoding + ); + + /** converts a Unicode string into a 8-bit string, using the given encoding + + @param _rSource + the source string to convert + + @param _rDest + the destination string + + @param _nMaxLen + the maximum length of the destination string + + @param _eEncoding + the encoding to use for the conversion + + @throws css::sdbc::SQLException + if convertUnicodeString, which is called internally, throws such an exception + + @throws css::sdbc::SQLException + if the conversion results in a string which is longer than _nMaxLen + + @return + the length of the converted string + */ + OOO_DLLPUBLIC_DBTOOLS sal_Int32 convertUnicodeStringToLength( + const OUString& _rSource, + OString& _rDest, + sal_Int32 _nMaxLen, + rtl_TextEncoding _eEncoding + ); + +} // namespace dbtools::DBTypeConversion + +#endif // INCLUDED_CONNECTIVITY_DBCONVERSION_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/dbexception.hxx b/include/connectivity/dbexception.hxx new file mode 100644 index 000000000..8c9dfad33 --- /dev/null +++ b/include/connectivity/dbexception.hxx @@ -0,0 +1,332 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#ifndef INCLUDED_CONNECTIVITY_DBEXCEPTION_HXX +#define INCLUDED_CONNECTIVITY_DBEXCEPTION_HXX + +#include <connectivity/standardsqlstate.hxx> +#include <connectivity/dbtoolsdllapi.hxx> +#include <com/sun/star/uno/Reference.hxx> + +namespace com::sun::star +{ + namespace sdb + { + class SQLContext; + struct SQLErrorEvent; + } + namespace sdbc + { + class SQLWarning; + class SQLException; + } +} + +namespace dbtools +{ + + +//= Special exception if cancel is pressed in DBA UI + +enum OOoBaseErrorCode +{ + ParameterInteractionCancelled = 1 +}; + + +//= SQLExceptionInfo - encapsulating the type info of an SQLException-derived class + + +class OOO_DLLPUBLIC_DBTOOLS SQLExceptionInfo final +{ +public: + enum class TYPE { SQLException, SQLWarning, SQLContext, Undefined }; + +private: + css::uno::Any m_aContent; + TYPE m_eType; // redundant (could be derived from m_aContent.getValueType()) + +public: + SQLExceptionInfo(); + SQLExceptionInfo(const css::sdbc::SQLException& _rError); + SQLExceptionInfo(const css::sdbc::SQLWarning& _rError); + SQLExceptionInfo(const css::sdb::SQLContext& _rError); + + /** convenience constructor + + If your error processing relies on SQLExceptions, and SQLExceptionInfos, you still may + need to display an error which consists of a simple message string only. + In those cases, you can use this constructor, which behaves as if you would have used + an SQLException containing exactly the given error message. + */ + SQLExceptionInfo( const OUString& _rSimpleErrorMessage ); + + // use for events got via XSQLErrorListener::errorOccured + SQLExceptionInfo(const css::uno::Any& _rError); + // use with the Reason member of an SQLErrorEvent or with NextElement of an SQLException + + /** prepends a plain error message to the chain of exceptions + @param _rSimpleErrorMessage + the error message to prepend + */ + void prepend( const OUString& _rErrorMessage ); + + /** appends a plain message to the chain of exceptions + @param _eType + the type of exception to append. Must be SQL_EXCEPTION, SQL_WARNING, SQL_CONTEXT, for all other + values, the behavior is undefined. + @param _rErrorMessage + the message to append + @param _rSQLState + the SQLState of the exception to append + @param _nErrorCode + the error code of the exception to append + */ + void append( TYPE _eType, const OUString& _rErrorMessage, const OUString& _rSQLState = OUString(), const sal_Int32 _nErrorCode = 0 ); + + /** throws (properly typed) the exception contained in the object + @precond + isValid() returns <TRUE/> + @throws SQLException + @throws RuntimeException + if the instance does not contain an SQLException + */ + void doThrow(); + + SQLExceptionInfo& operator=(const css::sdbc::SQLException& _rError); + SQLExceptionInfo& operator=(const css::sdbc::SQLWarning& _rError); + SQLExceptionInfo& operator=(const css::sdb::SQLContext& _rError); + SQLExceptionInfo& operator=(const css::sdb::SQLErrorEvent& _rErrorEvent); + SQLExceptionInfo& operator=(const css::uno::Any& _rCaughtSQLException); + + bool isKindOf(TYPE _eType) const; + // not just a simple comparison ! e.g. getType() == SQL_CONTEXT implies isKindOf(SQL_EXCEPTION) == sal_True ! + bool isValid() const { return m_eType != TYPE::Undefined; } + TYPE getType() const { return m_eType; } + + operator const css::sdbc::SQLException* () const; + operator const css::sdb::SQLContext* () const; + + const css::uno::Any& get() const { return m_aContent; } + + void clear() + { + m_aContent.clear(); + m_eType = TYPE::Undefined; + } + + // create an exception + static css::uno::Any createException(TYPE eType, const OUString& rErrorMessage, const OUString& rSQLState, const sal_Int32 nErrorCode); + + // find the end of the exception chain + static css::sdbc::SQLException* getLastException(css::sdbc::SQLException* pLastException); + +private: + void implDetermineType(); +}; + + +//= SQLExceptionIteratorHelper - iterating through an SQLException chain + + +class OOO_DLLPUBLIC_DBTOOLS SQLExceptionIteratorHelper final +{ + const css::sdbc::SQLException* m_pCurrent; + SQLExceptionInfo::TYPE m_eCurrentType; + +public: + /** constructs an iterator instance from an SQLException + + @param _rChainStart + the start of the exception chain to iterate. Must live as long as the iterator + instances lives, at least. + */ + SQLExceptionIteratorHelper( const css::sdbc::SQLException& _rChainStart ); + + /** constructs an iterator instance from an SQLExceptionInfo + + @param _rErrorInfo + the start of the exception chain to iterate. Must live as long as the iterator + instances lives, at least. + */ + SQLExceptionIteratorHelper( const SQLExceptionInfo& _rErrorInfo ); + + /** determines whether there are more elements in the exception chain + */ + bool hasMoreElements() const { return ( m_pCurrent != nullptr ); } + + /** retrieves the current element in the chain, or <NULL/> if the chain has been completely + traveled. + + In opposite to the second <member>current</member>, this version allows typed access to + the respective SQLException. + */ + void current( SQLExceptionInfo& _out_rInfo ) const; + + /** proceeds to the next element in the chain + + @return the current element in the chain, as <b>before</em> the chain move. + */ + const css::sdbc::SQLException* next(); + + /** proceeds to the next element in the chain + + In opposite to the second <member>current</member>, this version allows typed access to + the respective SQLException. + */ + void next( SQLExceptionInfo& _out_rInfo ); +}; + + +//= StandardExceptions + + +/** returns a standard error string for a given SQLState + + @param _eState + describes the state whose description is to retrieve. Must not be SQL_ERROR_UNSPECIFIED. + @throws RuntimeException + in case of an internal error +*/ +OOO_DLLPUBLIC_DBTOOLS OUString getStandardSQLState( StandardSQLState _eState ); + + +/** throws an exception with SQL state IM001, saying that a certain function is not supported + + @throws css::sdbc::SQLException +*/ +OOO_DLLPUBLIC_DBTOOLS void throwFunctionNotSupportedSQLException( + const OUString& _rFunctionName, + const css::uno::Reference< css::uno::XInterface >& _rxContext + ); + +/// @throws css::uno::RuntimeException +OOO_DLLPUBLIC_DBTOOLS void throwFunctionNotSupportedRuntimeException( + const OUString& _rFunctionName, + const css::uno::Reference< css::uno::XInterface >& _rxContext + ); + +/** throws a function sequence (HY010) exception + + @throws css::sdbc::SQLException +*/ +OOO_DLLPUBLIC_DBTOOLS void throwFunctionSequenceException( + const css::uno::Reference< css::uno::XInterface >& Context, + const css::uno::Any& Next = css::uno::Any() + ); + + +/** throw an invalid index sqlexception + + @throws css::sdbc::SQLException +*/ +OOO_DLLPUBLIC_DBTOOLS void throwInvalidIndexException( + const css::uno::Reference< css::uno::XInterface >& Context, + const css::uno::Any& Next = css::uno::Any() + ); + + +/** throw a generic SQLException, i.e. one with an SQLState of HY000, an ErrorCode of 0 and no NextException + + @throws css::sdbc::SQLException +*/ +OOO_DLLPUBLIC_DBTOOLS void throwGenericSQLException( + const OUString& _rMsg, + const css::uno::Reference< css::uno::XInterface >& _rxSource + ); + + +/** throw a generic SQLException, i.e. one with an SQLState of HY000, an ErrorCode of 0 and no NextException + + @throws css::sdbc::SQLException +*/ +OOO_DLLPUBLIC_DBTOOLS void throwGenericSQLException( + const OUString& _rMsg, + const css::uno::Reference< css::uno::XInterface >& _rxSource, + const css::uno::Any& _rNextException + ); + + +/** throw a SQLException with SQLState HYC00 (Optional feature not implemented) + @param _rFeatureName + a description of the feature which is not implemented. It's recommended that the feature + name is built from the name of the interface plus its method, for instance "XParameters::updateBinaryStream" + @param _rxContext + the context of the exception + @throws css::sdbc::SQLException +*/ +OOO_DLLPUBLIC_DBTOOLS void throwFeatureNotImplementedSQLException( + const OUString& _rFeatureName, + const css::uno::Reference< css::uno::XInterface >& _rxContext, + const css::uno::Any& _rNextException = css::uno::Any() + ); + +/** throw a RuntimeException (Optional feature not implemented) + @param _rFeatureName + a description of the feature which is not implemented. It's recommended that the feature + name is built from the name of the interface plus its method, for instance "XParameters::updateBinaryStream" + @param _rxContext + the context of the exception + @throws css::uno::RuntimeException +*/ +OOO_DLLPUBLIC_DBTOOLS void throwFeatureNotImplementedRuntimeException( + const OUString& _rFeatureName, + const css::uno::Reference< css::uno::XInterface >& _rxContext + ); + +/** throw a SQLException with SQLState 42S22 (Column Not Found) + @param _rColumnNameName + The column that couldn't be found. + @param _rxContext + the context of the exception + @throws css::sdbc::SQLException +*/ +OOO_DLLPUBLIC_DBTOOLS void throwInvalidColumnException( + const OUString& _rColumnName, + const css::uno::Reference< css::uno::XInterface >& _rxContext + ); + + +/** @throws css::sdbc::SQLException +*/ +OOO_DLLPUBLIC_DBTOOLS void throwSQLException( + const OUString& _rMessage, + const OUString& _rSQLState, + const css::uno::Reference< css::uno::XInterface >& _rxContext, + const sal_Int32 _nErrorCode + ); + + +/** @throws css::sdbc::SQLException +*/ +OOO_DLLPUBLIC_DBTOOLS void throwSQLException( + const OUString& _rMessage, + StandardSQLState _eSQLState, + const css::uno::Reference< css::uno::XInterface >& _rxContext, + const sal_Int32 _nErrorCode = 0 + ); + + +} // namespace dbtools + + +#endif // INCLUDED_CONNECTIVITY_DBEXCEPTION_HXX + + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/dbmetadata.hxx b/include/connectivity/dbmetadata.hxx new file mode 100644 index 000000000..17a392dfe --- /dev/null +++ b/include/connectivity/dbmetadata.hxx @@ -0,0 +1,194 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#ifndef INCLUDED_CONNECTIVITY_DBMETADATA_HXX +#define INCLUDED_CONNECTIVITY_DBMETADATA_HXX + +#include <com/sun/star/uno/Reference.hxx> + +#include <memory> +#include <connectivity/dbtoolsdllapi.hxx> + +namespace com::sun::star::sdbc { class XConnection; } +namespace com::sun::star::uno { class XComponentContext; } + +namespace dbtools +{ + + + //= DatabaseMetaData + + struct DatabaseMetaData_Impl; + /** encapsulates meta data about a database/connection which cannot be obtained + from the usual XDatabaseMetaData result set. + + Meta data perhaps isn't really the right term ... Some of the methods + in this class involved heuristics, some are just a convenient wrapper + around more complex ways to obtain the same information. + + @todo + Once CWS dba30 is integrated, we could easily add all the meta data + which is part of the "Info" property of a data source. + */ + class OOO_DLLPUBLIC_DBTOOLS DatabaseMetaData + { + private: + ::std::unique_ptr< DatabaseMetaData_Impl > m_pImpl; + + public: + DatabaseMetaData(); + /** constructs a DatabaseMetaData instance + @param _rxConnection + is the connection whose meta data you're interested in. + Note that some of the information provided by this class can only be obtained + if this connection denotes an application-level connection, i.e. supports + the com.sun.star.sdb.Connection service. + + @throws css::lang::IllegalArgumentException + if the given connection is not <NULL/>, but the XDatabaseMetaData provided by it + are <NULL/> + @throws css::sdbc::SQLException + if obtaining the meta data from the connection throws an SQLException + @throws css::uno::RuntimeException + if obtaining the meta data from the connection throws a RuntimeException + */ + DatabaseMetaData( + const css::uno::Reference< css::sdbc::XConnection >& _connection ); + DatabaseMetaData( const DatabaseMetaData& _copyFrom ); + DatabaseMetaData& operator=( const DatabaseMetaData& _copyFrom ); + DatabaseMetaData(DatabaseMetaData&& _copyFrom) noexcept; + DatabaseMetaData& operator=(DatabaseMetaData&& _copyFrom) noexcept; + + ~DatabaseMetaData(); + + public: + /** determines whether or not the instances is based on a valid connection + + As long as this method returns true<TRUE/>, you should expect all other + methods throwing an SQLException when called. + */ + bool isConnected() const; + + /** resets the instance so that it's based on a new connection + */ + void reset( const css::uno::Reference< css::sdbc::XConnection >& _connection ) + { + *this = DatabaseMetaData( _connection ); + } + + /// wraps XDatabaseMetaData::getIdentifierQuoteString + const OUString& getIdentifierQuoteString() const; + + /// wraps XDatabaseMetaData::getCatalogSeparator + const OUString& getCatalogSeparator() const; + + /** determines whether the database supports sub queries in the FROM part + of a SELECT clause are supported. + @throws css::sdbc::SQLException + with SQLState 08003 (connection does not exist) if the instances was + default-constructed and does not have a connection, yet. + */ + bool supportsSubqueriesInFrom() const; + + /** checks whether the database supports primary keys + + Since there's no dedicated API to ask a database for this, a heuristics needs to be applied. + First, the <code>PrimaryKeySupport<code> settings of the data source is examined. If it is <TRUE/> + or <FALSE/>, then value is returned. If it is <NULL/>, then the database meta data are examined + for support of core SQL grammar, and the result is returned. The assumption is that a database/driver + which supports core SQL grammar usually also supports primary keys, and vice versa. At least, experience + shows this is true most of the time. + */ + bool supportsPrimaryKeys() const; + + /** determines whether names in the database should be restricted to SQL-92 identifiers + + Effectively, this method checks the EnableSQL92Check property of the data source settings, + if present. + */ + bool restrictIdentifiersToSQL92() const; + + /** determines whether when generating SQL statements, an AS keyword should be generated + before a correlation name. + + E.g., it determines whether <code>SELECT * FROM table AS correlation_name</code> or + <code>SELECT * FROM table correlation_name</code> is generated. + */ + bool generateASBeforeCorrelationName() const; + + /** should date time be escaped like '2001-01-01' => {D '2001-01-01' } + */ + bool shouldEscapeDateTime() const; + + /** should named parameters (:foo, [foo]) be replaced by unnamed parameters (?) + */ + bool shouldSubstituteParameterNames() const; + + /** auto increment columns should be automatically used as primary key. + */ + bool isAutoIncrementPrimaryKey() const; + + /** determines the syntax to use for boolean comparison predicates + + @see css::sdb::BooleanComparisonMode + */ + sal_Int32 + getBooleanComparisonMode() const; + + /** determines in relations are supported. + * + * \return <TRUE/> when relations are supported, otherwise <FALSE/> + */ + bool supportsRelations() const; + + /** determines if column alias names can be used in the order by clause. + * + * \return <TRUE/> when relations are supported, otherwise <FALSE/> + */ + bool supportsColumnAliasInOrderBy() const; + + /** determines whether user administration is supported for the database + + User administration support is controlled by the availability of the XUsersSupplier + interface, and it returning a non-NULL users container. + + @param _rContext + the component context we operate in. Might be needed to create the + css.sdbc.DriverManager instance. + */ + bool supportsUserAdministration( const css::uno::Reference<css::uno::XComponentContext>& _rContext ) const; + + /** determines whether in the application UI, empty table folders (aka catalogs/schemas) should be displayed + */ + bool displayEmptyTableFolders() const; + + /** determines that threads are supported. + * + * \return <TRUE/> when threads are supported, otherwise <FALSE/> + */ + bool supportsThreads() const; + }; + + +} // namespace dbtools + + +#endif // INCLUDED_CONNECTIVITY_DBMETADATA_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/dbtools.hxx b/include/connectivity/dbtools.hxx new file mode 100644 index 000000000..58f34f170 --- /dev/null +++ b/include/connectivity/dbtools.hxx @@ -0,0 +1,867 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#ifndef INCLUDED_CONNECTIVITY_DBTOOLS_HXX +#define INCLUDED_CONNECTIVITY_DBTOOLS_HXX + +#include <sal/config.h> + +#include <string_view> + +#include <connectivity/dbexception.hxx> +#include <comphelper/stl_types.hxx> +#include <unotools/sharedunocomponent.hxx> +#include <connectivity/dbtoolsdllapi.hxx> +#include <connectivity/FValue.hxx> + +namespace com::sun::star { + +namespace sdb { + class XSingleSelectQueryComposer; +} +namespace sdbcx { + class XTablesSupplier; +} +namespace sdbc { + class XConnection; + class XDatabaseMetaData; + class XRowSet; + class XDataSource; + class SQLException; + class XParameters; + class XRowUpdate; +} +namespace beans { + class XPropertySet; +} +namespace awt { + class XWindow; +} +namespace lang { + struct Locale; +} +namespace container { + class XNameAccess; +} +namespace uno { + class XComponentContext; +} +namespace util { + class XNumberFormatTypes; + class XNumberFormatsSupplier; +} +namespace task { + class XInteractionHandler; +} + +} + +class SvStream; + +namespace dbtools +{ + class ISQLStatementHelper; + typedef ::utl::SharedUNOComponent< css::sdbc::XConnection > SharedConnection; + + enum class EComposeRule + { + InTableDefinitions, + InIndexDefinitions, + InDataManipulation, + InProcedureCalls, + InPrivilegeDefinitions, + Complete + }; + + // date conversion + + // calculates the default numberformat for a given datatype and a give language + OOO_DLLPUBLIC_DBTOOLS + sal_Int32 getDefaultNumberFormat(const css::uno::Reference< css::beans::XPropertySet >& _xColumn, + const css::uno::Reference< css::util::XNumberFormatTypes >& _xTypes, + const css::lang::Locale& _rLocale); + + // calculates the default numberformat for a given datatype and a give language + // @param _nDataType @see com.sun.star.sdbc.DataType + // @param _nScale can be zero + OOO_DLLPUBLIC_DBTOOLS + sal_Int32 getDefaultNumberFormat(sal_Int32 _nDataType, + sal_Int32 _nScale, + bool _bIsCurrency, + const css::uno::Reference< css::util::XNumberFormatTypes >& _xTypes, + const css::lang::Locale& _rLocale); + + + /** creates a connection which can be used for the rowset given + + The function tries to obtain a connection for the row set with the following + steps (in this order): + <nl> + <li>If the rowset already has an ActiveConnection (means a non-<NULL/> value for this property), + this one is used.</li> + <li>If row set is part of a database form document (see ->isEmbeddedInDatabase), + a connection for the respective database is used.</li> + <li>If in the parent hierarchy of the row set, there is an object supporting + the XConnection interface, this one is returned.</li> + <li>If the DataSourceName property of the row set is not empty, a connection for this + data source is retrieved.</li> + <li>If the URL property of the row set is not empty, a connection for this URL is + retrieved from the driver manager. + </nl> + + The calculated connection is set as ActiveConnection property on the rowset. + + If the connection was newly created by the method, then + the ownership of the connection is delivered to a temporary object, which observes the + row set: As soon as a connection-relevant property of the row set changes, or as soon + as somebody else sets another ActiveConnection at the row set, the original + connection (the one which this function calculated) is disposed and discarded. At this + very moment, also the temporary observer object dies. This way, it is ensured that + there's no resource leak from an un-owned connection object. + + @param _rxRowSet + the row set + + @param _rxFactory + a service factory, which can be used to create data sources, interaction handler etc (the usual stuff) + + */ + OOO_DLLPUBLIC_DBTOOLS + css::uno::Reference< css::sdbc::XConnection> connectRowset( + const css::uno::Reference< css::sdbc::XRowSet>& _rxRowSet, + const css::uno::Reference< css::uno::XComponentContext>& _rxContext, + const css::uno::Reference< css::awt::XWindow>& _rxParent + ); + + /** ensures that a row set has a valid ActiveConnection, if possible + + This function does nearly the same as ->connectRowset. In fact, it is to be preferred over + ->connectRowset, if possible. + + There are a few differences: + <ul><li>If a connection could be determined for the given RowSet, it is always + set as ActiveConnection.</li> + <li>Definition of the ownership of the created connection allows for more scenarios: + <ul><li>If the connection was not newly created, the returned ->SharedConnection + instance will not have the ownership, since in this case it's assumed + that there already is an instance which has the ownership.</li> + <li>If the connection was newly created, then the returned SharedConnection + instance will have the ownership of the XConnection.</li> + </ul> + </li> + </ul> + */ + OOO_DLLPUBLIC_DBTOOLS SharedConnection ensureRowSetConnection( + const css::uno::Reference< css::sdbc::XRowSet>& _rxRowSet, + const css::uno::Reference< css::uno::XComponentContext>& _rxContext, + const css::uno::Reference< css::awt::XWindow>& _rxParent + ); + + /** returns the connection the RowSet is currently working with (which is the ActiveConnection property) + + @throws css::uno::RuntimeException + */ + OOO_DLLPUBLIC_DBTOOLS css::uno::Reference< css::sdbc::XConnection> getConnection(const css::uno::Reference< css::sdbc::XRowSet>& _rxRowSet); + OOO_DLLPUBLIC_DBTOOLS css::uno::Reference< css::sdbc::XConnection> getConnection_withFeedback( + const OUString& _rDataSourceName, + const OUString& _rUser, + const OUString& _rPwd, + const css::uno::Reference< css::uno::XComponentContext>& _rxContext, + const css::uno::Reference< css::awt::XWindow>& _rxParent); + + + /** determines whether the given component is part of a document which is an embedded database + document (such as a form) + */ + OOO_DLLPUBLIC_DBTOOLS bool isEmbeddedInDatabase( + const css::uno::Reference< css::uno::XInterface >& _rxComponent, + css::uno::Reference< css::sdbc::XConnection >& _rxActualConnection + ); + + /** returns the columns of the named table of the given connection + */ + OOO_DLLPUBLIC_DBTOOLS css::uno::Reference< css::container::XNameAccess> getTableFields( + const css::uno::Reference< css::sdbc::XConnection>& _rxConn, + const OUString& _rName + ); + + /** returns the primary key columns of the table + */ + OOO_DLLPUBLIC_DBTOOLS css::uno::Reference< css::container::XNameAccess> getPrimaryKeyColumns_throw( + const css::uno::Any& i_aTable + ); + OOO_DLLPUBLIC_DBTOOLS css::uno::Reference< css::container::XNameAccess> getPrimaryKeyColumns_throw( + const css::uno::Reference< css::beans::XPropertySet >& i_xTable + ); + + /** get fields for a result set given by a "command descriptor" + + <p>A command descriptor here means: + <ul><li>a SDB-level connection (com.sun.star.sdb::Connection</li> + <li>a string specifying the name of an object relative to the connection</li> + <li>a com.sun.star.sdb::CommandType value specifying the type + of the object</type></li> + </ul> + </p> + + @param _rxConnection + the connection relative to which the to-be-examined object exists + + @param _nCommandType + the type of the object + + @param _rCommand + the object. This may be a table name, a query name, or an SQL statement, depending on the value + of <arg>_nCommandType</arg> + + @param _rxCollectionOner + If (and only if) <arg>CommandType</arg> is CommandType.COMMAND, the fields collection which is returned + by this function here is a temporary object. It is kept alive by another object, which is to be + created temporarily, too. To ensure that the fields you get are valid as long as you need them, + the owner which controls their life time is transferred to this parameter upon return.<br/> + + Your fields live as long as this component lives.<br/> + + Additionally, you are encouraged to dispose this component as soon as you don't need the fields anymore. + It depends on the connection's implementation if this is necessary, but the is no guarantee, so to + be on the safe side with respect to resource leaks, you should dispose the component. + + @param _pErrorInfo + If not <NULL/>, then upon return from the function the instance pointed to by this argument will + contain any available error information in case something went wrong. + + @return + the container of the columns (aka fields) of the object + */ + OOO_DLLPUBLIC_DBTOOLS + css::uno::Reference< css::container::XNameAccess > + getFieldsByCommandDescriptor( + const css::uno::Reference< css::sdbc::XConnection >& _rxConnection, + const sal_Int32 _nCommandType, + const OUString& _rCommand, + css::uno::Reference< css::lang::XComponent >& _rxKeepFieldsAlive, + SQLExceptionInfo* _pErrorInfo = nullptr + ); + + + /** get fields for a result set given by a "command descriptor" + + <p>A command descriptor here means: + <ul><li>a SDB-level connection (com.sun.star.sdb::Connection</li> + <li>a string specifying the name of an object relative to the connection</li> + <li>a com.sun.star.sdb::CommandType value specifying the type + of the object</type></li> + </ul> + </p> + + @param _rxConnection + the connection relative to which the to-be-examined object exists + + @param _nCommandType + the type of the object + + @param _rCommand + the object. This may be a table name, a query name, or an SQL statement, depending on the value + of <arg>_nCommandType</arg> + + @param _pErrorInfo + If not <NULL/>, then upon return from the function the instance pointed to by this argument will + contain any available error information in case something went wrong. + + @return + an array of strings containing the names of the columns (aka fields) of the object + */ + OOO_DLLPUBLIC_DBTOOLS css::uno::Sequence< OUString > + getFieldNamesByCommandDescriptor( + const css::uno::Reference< css::sdbc::XConnection >& _rxConnection, + const sal_Int32 _nCommandType, + const OUString& _rCommand, + SQLExceptionInfo* _pErrorInfo = nullptr + ); + + + /** create a new css::sdbc::SQLContext, fill it with the given descriptions and the given source, + and <i>append</i> _rException (i.e. put it into the NextException member of the SQLContext). + */ + OOO_DLLPUBLIC_DBTOOLS + css::sdbc::SQLException prependErrorInfo( + const css::sdbc::SQLException& _rChainedException, + const css::uno::Reference< css::uno::XInterface >& _rxContext, + const OUString& _rAdditionalError, + const StandardSQLState _eSQLState = StandardSQLState::ERROR_UNSPECIFIED); + + /** search the parent hierarchy for a data source. + */ + OOO_DLLPUBLIC_DBTOOLS css::uno::Reference< css::sdbc::XDataSource> findDataSource(const css::uno::Reference< css::uno::XInterface >& _xParent); + + /** determines the value of a boolean data source setting, given by ASCII name + + @param _rxConnection + the connection belonging to the data source whose setting is to be retrieved + @param _pAsciiSettingName + the ASCII name of the setting + */ + OOO_DLLPUBLIC_DBTOOLS bool getBooleanDataSourceSetting( + const css::uno::Reference< css::sdbc::XConnection >& _rxConnection, + const char* _pAsciiSettingName + ); + OOO_DLLPUBLIC_DBTOOLS bool getBooleanDataSourceSetting( + const css::uno::Reference< css::sdbc::XConnection >& _rxConnection, + const OUString& rSettingName + ); + + /** check if a specific property is enabled in the info sequence + @deprecated + Use getBooleanDataSourceSetting instead, which cares for the default of the property itself, + instead of spreading this knowledge through all callers. + */ + OOO_DLLPUBLIC_DBTOOLS + bool isDataSourcePropertyEnabled(const css::uno::Reference< css::uno::XInterface>& _xProp, + const OUString& _sProperty, + bool _bDefault); + + /** retrieves a particular indirect data source setting + + @param _rxDataSource + a data source component + @param _pAsciiSettingsName + the ASCII name of the setting to obtain + @param _rSettingsValue + the value of the setting, upon successful return + + @return + <FALSE/> if the setting is not present in the <member scope="css::sdb">DataSource::Info</member> + member of the data source + <TRUE/> otherwise + */ + OOO_DLLPUBLIC_DBTOOLS + bool getDataSourceSetting( + const css::uno::Reference< css::uno::XInterface >& _rxDataSource, + const char* _pAsciiSettingsName, + css::uno::Any& /* [out] */ _rSettingsValue + ); + OOO_DLLPUBLIC_DBTOOLS + bool getDataSourceSetting( + const css::uno::Reference< css::uno::XInterface >& _rxDataSource, + const OUString& _sSettingsName, + css::uno::Any& /* [out] */ _rSettingsValue + ); + + OOO_DLLPUBLIC_DBTOOLS OUString getDefaultReportEngineServiceName(const css::uno::Reference< css::uno::XComponentContext>& _rxFactory); + + /** quote the given name with the given quote string. + */ + OOO_DLLPUBLIC_DBTOOLS OUString quoteName(const OUString& _rQuote, const OUString& _rName); + + /** quote the given table name (which may contain a catalog and a schema) according to the rules provided by the meta data + */ + OOO_DLLPUBLIC_DBTOOLS + OUString quoteTableName(const css::uno::Reference< css::sdbc::XDatabaseMetaData>& _rxMeta + , const OUString& _rName + ,EComposeRule _eComposeRule); + + /** split a fully qualified table name (including catalog and schema, if applicable) into its component parts. + @param _rxConnMetaData meta data describing the connection where you got the table name from + @param _rQualifiedName fully qualified table name + @param _rCatalog (out parameter) upon return, contains the catalog name + @param _rSchema (out parameter) upon return, contains the schema name + @param _rName (out parameter) upon return, contains the table name + @param _eComposeRule where do you need the name for + */ + OOO_DLLPUBLIC_DBTOOLS void qualifiedNameComponents(const css::uno::Reference< css::sdbc::XDatabaseMetaData >& _rxConnMetaData, + const OUString& _rQualifiedName, OUString& _rCatalog, OUString& _rSchema, OUString& _rName,EComposeRule _eComposeRule); + + /** calculate a NumberFormatsSupplier for use with a given connection + @param _rxConn the connection for which the formatter is requested + @param _bAllowDefault if the connection (and related components, such as its parent) cannot supply + a formatter, we can ask the DatabaseEnvironment for a default one. This parameter + states if this is allowed. + @param _rxFactory required (only of _bAllowDefault is sal_True) for creating the DatabaseEnvironment. + @return the formatter all object related to the given connection should work with. + */ + OOO_DLLPUBLIC_DBTOOLS css::uno::Reference< css::util::XNumberFormatsSupplier> getNumberFormats( + const css::uno::Reference< css::sdbc::XConnection>& _rxConn, + bool _bAllowDefault = false, + const css::uno::Reference< css::uno::XComponentContext>& _rxContext = css::uno::Reference< css::uno::XComponentContext>() + ); + + /** create a css::sdb::XSingleSelectQueryComposer which represents + the current settings (Command/CommandType/Filter/Order) of the given rowset. + + As such an instance can be obtained from a css::sdb::Connection + only the function searches for the connection the RowSet is using via connectRowset. + This implies that a connection will be set on the RowSet if needed. + (need to changes this sometimes ...) + */ + OOO_DLLPUBLIC_DBTOOLS css::uno::Reference< css::sdb::XSingleSelectQueryComposer > getCurrentSettingsComposer( + const css::uno::Reference< css::beans::XPropertySet>& _rxRowSetProps, + const css::uno::Reference< css::uno::XComponentContext>& _rxContext, + const css::uno::Reference< css::awt::XWindow>& _rxParent + ); + + /** transfer and translate properties between two FormComponents + @param _rxOld the source property set + @param _rxNew the destination property set + @param _rLocale the locale for converting number related properties + */ + OOO_DLLPUBLIC_DBTOOLS void TransferFormComponentProperties( + const css::uno::Reference< css::beans::XPropertySet>& _rxOld, + const css::uno::Reference< css::beans::XPropertySet>& _rxNew, + const css::lang::Locale& _rLocale + ); + + /** check if the property "Privileges" supports css::sdbcx::Privilege::INSERT + @param _rxCursorSet the property set + */ + OOO_DLLPUBLIC_DBTOOLS bool canInsert(const css::uno::Reference< css::beans::XPropertySet>& _rxCursorSet); + /** check if the property "Privileges" supports css::sdbcx::Privilege::UPDATE + @param _rxCursorSet the property set + */ + OOO_DLLPUBLIC_DBTOOLS bool canUpdate(const css::uno::Reference< css::beans::XPropertySet>& _rxCursorSet); + /** check if the property "Privileges" supports css::sdbcx::Privilege::DELETE + @param _rxCursorSet the property set + */ + OOO_DLLPUBLIC_DBTOOLS bool canDelete(const css::uno::Reference< css::beans::XPropertySet>& _rxCursorSet); + + + /** compose a complete table name from its up to three parts, regarding to the database meta data composing rules + */ + OOO_DLLPUBLIC_DBTOOLS OUString composeTableName( const css::uno::Reference< css::sdbc::XDatabaseMetaData >& _rxMetaData, + const OUString& _rCatalog, + const OUString& _rSchema, + const OUString& _rName, + bool _bQuote, + EComposeRule _eComposeRule); + + /** composes a table name for usage in a SELECT statement + + This includes quoting of the table as indicated by the connection's meta data, plus respecting + the settings "UseCatalogInSelect" and "UseSchemaInSelect", which might be present + in the data source which the connection belongs to. + */ + OOO_DLLPUBLIC_DBTOOLS OUString composeTableNameForSelect( + const css::uno::Reference< css::sdbc::XConnection >& _rxConnection, + const OUString& _rCatalog, + const OUString& _rSchema, + const OUString& _rName ); + + /** composes a table name for usage in a SELECT statement + + This includes quoting of the table as indicated by the connection's meta data, plus respecting + the settings "UseCatalogInSelect" and "UseSchemaInSelect", which might be present + in the data source which the connection belongs to. + */ + OOO_DLLPUBLIC_DBTOOLS OUString composeTableNameForSelect( + const css::uno::Reference< css::sdbc::XConnection >& _rxConnection, + const css::uno::Reference< css::beans::XPropertySet>& _xTable ); + + /** compose the table name out of the property set which must support the properties from the service <member scope= "css::sdbcx">table</member> + @param _xMetaData + The metadata from the connection. + @param _xTable + The table. + */ + OOO_DLLPUBLIC_DBTOOLS OUString composeTableName( + const css::uno::Reference< css::sdbc::XDatabaseMetaData>& _xMetaData, + const css::uno::Reference< css::beans::XPropertySet>& _xTable, + EComposeRule _eComposeRule, + bool _bQuote); + + + OOO_DLLPUBLIC_DBTOOLS sal_Int32 getSearchColumnFlag( const css::uno::Reference< css::sdbc::XConnection>& _rxConn, + sal_Int32 _nDataType); + // return the datasource for the given datasource name + OOO_DLLPUBLIC_DBTOOLS css::uno::Reference< css::sdbc::XDataSource> getDataSource(const OUString& _rsDataSourceName, + const css::uno::Reference< css::uno::XComponentContext>& _rxContext); + + /** search for a name that is NOT in the NameAcces + @param _rxContainer + the NameAccess container to search in + @param _rBaseName + the base name that should be used to create the new name + @param _bStartWithNumber + When <TRUE/> the name ends with number even when the name itself doesn't occur in the collection. + @return + A name which doesn't exist in the collection. + */ + OOO_DLLPUBLIC_DBTOOLS + OUString createUniqueName(const css::uno::Reference< css::container::XNameAccess>& _rxContainer, + const OUString& _rBaseName, + bool _bStartWithNumber = true); + + /** creates a unique name which is not already used in the given name array + */ + OOO_DLLPUBLIC_DBTOOLS OUString createUniqueName( + const css::uno::Sequence< OUString >& _rNames, + const OUString& _rBaseName, + bool _bStartWithNumber + ); + + /** create a name which is a valid SQL 92 identifier name + @param _rName the string which should be converted + @param _rSpecials @see com.sun.star.sdbc.XDatabaseMetaData.getExtraNameCharacters + + @see isValidSQLName + */ + OOO_DLLPUBLIC_DBTOOLS OUString convertName2SQLName(const OUString& _rName, std::u16string_view _rSpecials); + + /** checks whether the given name is a valid SQL name + + @param _rName the string which should be converted + @param _rSpecials @see com.sun.star.sdbc.XDatabaseMetaData.getExtraNameCharacters + + @see convertName2SQLName + */ + OOO_DLLPUBLIC_DBTOOLS bool isValidSQLName( const OUString& _rName, std::u16string_view _rSpecials ); + + OOO_DLLPUBLIC_DBTOOLS + void showError( const SQLExceptionInfo& _rInfo, + const css::uno::Reference< css::awt::XWindow>& _pParent, + const css::uno::Reference< css::uno::XComponentContext>& _rxContext); + + /** implements <method scope="com.sun.star.sdb">XRowUpdate::updateObject</method> + <p>The object which is to be set is analyzed, and in case it is a simlpe scalar type for which there + is another updateXXX method, this other method is used.</p> + @param _rxUpdatedObject + the interface to forward all updateXXX calls to (except updateObject) + @param _nColumnIndex + the column index to update + @param _rValue + the value to update + @return + <TRUE/> if the update request was successfully re-routed to one of the other updateXXX methods + */ + OOO_DLLPUBLIC_DBTOOLS + bool implUpdateObject( const css::uno::Reference< css::sdbc::XRowUpdate >& _rxUpdatedObject, + const sal_Int32 _nColumnIndex, + const css::uno::Any& _rValue); + + + /** ask the user for parameters if the prepared statement needs some and sets them in the prepared statement + @param _xConnection the connection must be able to create css::sdb::SingleSelectQueryComposers + @param _xPreparedStmt the prepared statement where the parameters could be set when needed + @param _aParametersSet contains which parameters have to asked for and which already have set. + */ + OOO_DLLPUBLIC_DBTOOLS + void askForParameters( const css::uno::Reference< css::sdb::XSingleSelectQueryComposer >& _xComposer, + const css::uno::Reference< css::sdbc::XParameters>& _xParameters, + const css::uno::Reference< css::sdbc::XConnection>& _xConnection, + const css::uno::Reference< css::task::XInteractionHandler >& _rxHandler, + const ::std::vector<bool, std::allocator<bool> >& _aParametersSet = ::std::vector<bool, std::allocator<bool> >()); + + /** call the appropriate set method for the specific sql type @see css::sdbc::DataType + @param _xParams the parameters where to set the value + @param parameterIndex the index of the parameter, 1 based + @param x the value to set + @param sqlType the corresponding sql type @see css::sdbc::DataType + @param scale the scale of the sql type can be 0 + @throws css::sdbc::SQLException + @throws css::uno::RuntimeException + */ + OOO_DLLPUBLIC_DBTOOLS + void setObjectWithInfo( const css::uno::Reference< css::sdbc::XParameters>& _xParameters, + sal_Int32 parameterIndex, + const css::uno::Any& x, + sal_Int32 sqlType, + sal_Int32 scale=0); + + /** call the appropriate set method for the specific sql type @see css::sdbc::DataType + @param _xParams the parameters where to set the value + @param parameterIndex the index of the parameter, 1 based + @param x the value to set + @param sqlType the corresponding sql type @see css::sdbc::DataType + @param scale the scale of the sql type can be 0 + @throws css::sdbc::SQLException + @throws css::uno::RuntimeException + */ + OOO_DLLPUBLIC_DBTOOLS + void setObjectWithInfo( const css::uno::Reference< css::sdbc::XParameters>& _xParameters, + sal_Int32 parameterIndex, + const ::connectivity::ORowSetValue& x, + sal_Int32 sqlType, + sal_Int32 scale); + + + /** implements <method scope="com.sun.star.sdb">XParameters::setObject</method> + <p>The object which is to be set is analyzed, and in case it is a simlpe scalar type for which there + is another setXXX method, this other method is used.</p> + @param _rxParameters + the interface to forward all setXXX calls to (except setObject) + @param _nColumnIndex + the column index to update + @param _rValue + the value to update + @return + <TRUE/> if the update request was successfully re-routed to one of the other updateXXX methods + */ + OOO_DLLPUBLIC_DBTOOLS + bool implSetObject( const css::uno::Reference< css::sdbc::XParameters>& _rxParameters, + const sal_Int32 _nColumnIndex, + const css::uno::Any& _rValue); + + /** creates the standard sql create table statement without the key part. + @param descriptor + The descriptor of the new table. + @param _xConnection + The connection. + @param _bAddScale + The scale will also be added when the value is 0. + */ + OOO_DLLPUBLIC_DBTOOLS + OUString createStandardCreateStatement( const css::uno::Reference< css::beans::XPropertySet >& descriptor, + const css::uno::Reference< css::sdbc::XConnection>& _xConnection, + ISQLStatementHelper* _pHelper, + std::u16string_view _sCreatePattern); + + /** creates the standard sql statement for the key part of a create table statement. + @param descriptor + The descriptor of the new table. + @param _xConnection + The connection. + */ + OOO_DLLPUBLIC_DBTOOLS + OUString createStandardKeyStatement( const css::uno::Reference< css::beans::XPropertySet >& descriptor, + const css::uno::Reference< css::sdbc::XConnection>& _xConnection); + + /** creates the standard sql statement for the type part of a create or alter table statement. + @param _pHelper + Allow to add special SQL constructs. + @param descriptor + The descriptor of the column. + @param _xConnection + The connection. + */ + OOO_DLLPUBLIC_DBTOOLS + OUString createStandardTypePart( const css::uno::Reference< css::beans::XPropertySet >& descriptor + ,const css::uno::Reference< css::sdbc::XConnection>& _xConnection + ,std::u16string_view _sCreatePattern = {}); + + /** creates the standard sql statement for the column part of a create table statement. + @param _pHelper + Allow to add special SQL constructs. + @param descriptor + The descriptor of the column. + @param _xConnection + The connection. + @param _pHelper + Allow to add special SQL constructs. + */ + OOO_DLLPUBLIC_DBTOOLS + OUString createStandardColumnPart( const css::uno::Reference< css::beans::XPropertySet >& descriptor + ,const css::uno::Reference< css::sdbc::XConnection>& _xConnection + ,ISQLStatementHelper* _pHelper = nullptr + ,std::u16string_view _sCreatePattern = {}); + + /** creates a SQL CREATE TABLE statement + + @param descriptor + The descriptor of the new table. + @param _xConnection + The connection. + + @return + The CREATE TABLE statement. + */ + OOO_DLLPUBLIC_DBTOOLS + OUString createSqlCreateTableStatement( const css::uno::Reference< css::beans::XPropertySet >& descriptor + ,const css::uno::Reference< css::sdbc::XConnection>& _xConnection); + + /** creates a SDBC column with the help of getColumns. + @param _xTable + The table. + @param _rName + The name of the column. + @param _bCase + Is the column case sensitive. + @param _bQueryForInfo + If <TRUE/> the autoincrement and currency field will be read from the meta data, otherwise the following parameters will be used instead + @param _bIsAutoIncrement + <TRUE/> if the column is an autoincrement. + @param _bIsCurrency + <TRUE/> if the column is a currency field. + @param _nDataType + The data type of the column. + */ + OOO_DLLPUBLIC_DBTOOLS + css::uno::Reference< css::beans::XPropertySet> + createSDBCXColumn( const css::uno::Reference< css::beans::XPropertySet>& _xTable, + const css::uno::Reference< css::sdbc::XConnection>& _xConnection, + const OUString& _rName, + bool _bCase, + bool _bQueryForInfo, + bool _bIsAutoIncrement, + bool _bIsCurrency, + sal_Int32 _nDataType); + + /** tries to locate the corresponding DataDefinitionSupplier for the given url and connection + @param _rsUrl + The URL used to connect to the database. + @param _xConnection + The connection used to find the correct driver. + @param _rxContext + Used to create the drivermanager. + @return + The datadefinition object. + */ + OOO_DLLPUBLIC_DBTOOLS css::uno::Reference< css::sdbcx::XTablesSupplier> getDataDefinitionByURLAndConnection( + const OUString& _rsUrl, + const css::uno::Reference< css::sdbc::XConnection>& _xConnection, + const css::uno::Reference< css::uno::XComponentContext>& _rxContext); + + /** returns the table privileges to the given parameters + @param _xMetaData + The meta data. + @param _sCatalog + contains the catalog name + @param _sSchema + contains the schema name + @param _sTable + contains the table name + */ + OOO_DLLPUBLIC_DBTOOLS + sal_Int32 getTablePrivileges(const css::uno::Reference< css::sdbc::XDatabaseMetaData>& _xMetaData, + const OUString& _sCatalog, + const OUString& _sSchema, + const OUString& _sTable); + + typedef ::std::pair<bool,bool> TBoolPair; + typedef ::std::pair< TBoolPair,sal_Int32 > ColumnInformation; + typedef ::std::multimap< OUString, ColumnInformation, ::comphelper::UStringMixLess> ColumnInformationMap; + /** collects the information about auto increment, currency and data type for the given column name. + The column must be quoted, * is also valid. + @param _xConnection + The connection. + @param _sComposedTableName + The quoted table name. ccc.sss.ttt + @param _sName + The name of the column, or * + @param _rInfo + The information about the column(s). + */ + OOO_DLLPUBLIC_DBTOOLS + void collectColumnInformation( const css::uno::Reference< css::sdbc::XConnection>& _xConnection, + std::u16string_view _sComposedTableName, + std::u16string_view _rName, + ColumnInformationMap& _rInfo); + + + /** adds a boolean comparison clause to the given SQL predicate + + @param _rExpression + the expression which is to be compared with a boolean value + @param _bValue + the boolean value which the expression is to be compared with + @param _nBooleanComparisonMode + the boolean comparison mode to be used. Usually obtained from + a css.sdb.DataSource's Settings member. + @param _out_rSQLPredicate + the buffer to which the comparison predicate will be appended + */ + OOO_DLLPUBLIC_DBTOOLS void getBooleanComparisonPredicate( + std::u16string_view _rExpression, + const bool _bValue, + const sal_Int32 _nBooleanComparisonMode, + OUStringBuffer& _out_rSQLPredicate + ); + + /** is this field an aggregate? + + @param _xComposer + a query composer that knows the field by name + @param _xField + the field + */ + OOO_DLLPUBLIC_DBTOOLS bool isAggregateColumn( + const css::uno::Reference< css::sdb::XSingleSelectQueryComposer > &_xComposer, + const css::uno::Reference< css::beans::XPropertySet > &_xField + ); + + /** is this column an aggregate? + + @param _xColumns collection of columns + look for column sName in there + @param _sName + name of the column + */ + OOO_DLLPUBLIC_DBTOOLS bool isAggregateColumn( + const css::uno::Reference< css::container::XNameAccess > &_xColumns, + const OUString &_sName + ); + + /** is this column an aggregate? + + @param _xColumn + */ + OOO_DLLPUBLIC_DBTOOLS bool isAggregateColumn( + const css::uno::Reference< css::beans::XPropertySet > &_xColumn + ); + +} // namespace dbtools + +namespace connectivity +{ +namespace dbase +{ + enum DBFType { dBaseIII = 0x03, + dBaseIV = 0x04, + dBaseV = 0x05, + VisualFoxPro = 0x30, + VisualFoxProAuto = 0x31, // Visual FoxPro with AutoIncrement field + dBaseFS = 0x43, + dBaseFSMemo = 0xB3, + dBaseIIIMemo = 0x83, + dBaseIVMemo = 0x8B, + dBaseIVMemoSQL = 0x8E, + FoxProMemo = 0xF5 + }; + + /** decode a DBase file's codepage byte to a RTL charset + @param _out_nCharset + in case of success, the decoded RTL charset is written there. + else, this is not written to. + @param nType + the file's type byte + @param nCodepage + the file's codepage byte + @return + true if a RTL charset was successfully decoded and written to _out_nCharset + false if nothing was written to _out_nCharset + */ + OOO_DLLPUBLIC_DBTOOLS bool dbfDecodeCharset(rtl_TextEncoding &_out_nCharset, sal_uInt8 nType, sal_uInt8 nCodepage); + + /** decode a DBase file's codepage byte to a RTL charset + @param _out_nCharset + in case of success, the decoded RTL charset is written there. + else, this is not written to. + @param dbf_Stream + pointer to a SvStream encapsulating the DBase file. + The stream will be rewinded and read from. + No guarantee is made on its position afterwards. Caller must reposition it itself. + @return + true if a RTL charset was successfully decoded and written to _out_nCharset + false if nothing was written to _out_nCharset + */ + OOO_DLLPUBLIC_DBTOOLS bool dbfReadCharset(rtl_TextEncoding &nCharSet, SvStream* dbf_Stream); + +} // namespace connectivity::dbase +} // namespace connectivity + +#endif // INCLUDED_CONNECTIVITY_DBTOOLS_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/dbtoolsdllapi.hxx b/include/connectivity/dbtoolsdllapi.hxx new file mode 100644 index 000000000..466d5ab23 --- /dev/null +++ b/include/connectivity/dbtoolsdllapi.hxx @@ -0,0 +1,35 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#ifndef INCLUDED_CONNECTIVITY_DBTOOLSDLLAPI_HXX +#define INCLUDED_CONNECTIVITY_DBTOOLSDLLAPI_HXX + +#include <sal/config.h> + +#include <sal/types.h> + +#if defined OOO_DLLIMPLEMENTATION_DBTOOLS +#define OOO_DLLPUBLIC_DBTOOLS SAL_DLLPUBLIC_EXPORT +#else +#define OOO_DLLPUBLIC_DBTOOLS SAL_DLLPUBLIC_IMPORT +#endif + +#endif + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/filtermanager.hxx b/include/connectivity/filtermanager.hxx new file mode 100644 index 000000000..b6f104aa4 --- /dev/null +++ b/include/connectivity/filtermanager.hxx @@ -0,0 +1,114 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ +#ifndef INCLUDED_CONNECTIVITY_FILTERMANAGER_HXX +#define INCLUDED_CONNECTIVITY_FILTERMANAGER_HXX + +#include <com/sun/star/uno/Reference.hxx> + +#include <rtl/ustrbuf.hxx> + +#include <connectivity/dbtoolsdllapi.hxx> + +namespace com::sun::star::beans { class XPropertySet; } + + +namespace dbtools +{ + + + //= FilterManager + + /** manages the filter of a database component with filter properties + + The idea is that the filter which a database component actually really uses is composed of several single + filter components (which all are conjunctive). + + First, there is a component which is visible to the clients of the database component itself - if they ask + the database component for the Filter property, they will get this public filter. + + Second, there is an implicit filter, which is (to be) created from the MasterFields and DetailFields + property of the database component, if the latter denote columns.<br/> + For instance, if there is a link-pair CustomerID->cid, where |CustomerID| is a column of the master + database component, and |cid| is a column of the detail database component (the database component we're responsible for), then there will + be an implicit filter "cid = :param_cid_link" (or something like this), which is never visible + to the clients of the database component, but nevertheless needs to be propagated to the aggregated RowSet.<br/> + Actually, this implicit filter is maintained by the FormParameterManager. + + Potentially, there could be more filter components (for instance, you could imagine database component + controls which act as live filter, which could be implemented with a third component), but + at the moment there are only these two. + */ + class OOO_DLLPUBLIC_DBTOOLS FilterManager + { + public: + enum class FilterComponent + { + PublicFilter, // The filter which is to be published as "Filter" property of the database component. + LinkFilter, // The filter part which is implicitly created for a database component when connecting + // master and detail database components via column names. + PublicHaving, // the same, but should go in HAVING clause instead of WHERE clause + LinkHaving + }; + + private: + css::uno::Reference< css::beans::XPropertySet > m_xComponentAggregate; + OUString m_aPublicFilterComponent; + OUString m_aPublicHavingComponent; + OUString m_aLinkFilterComponent; + OUString m_aLinkHavingComponent; + bool m_bApplyPublicFilter; + + public: + /// ctor + explicit FilterManager(); + + /// late ctor + void initialize(const css::uno::Reference< css::beans::XPropertySet >& _rxComponentAggregate ); + + /// makes the object forgetting the references to the database component + void dispose( ); + + const OUString& getFilterComponent( FilterComponent _eWhich ) const; + void setFilterComponent( FilterComponent _eWhich, const OUString& _rComponent ); + + bool isApplyPublicFilter( ) const { return m_bApplyPublicFilter; } + void setApplyPublicFilter( bool _bApply ); + + private: + /** retrieves a filter which is a conjunction of all single filter components + */ + OUString getComposedFilter( ) const; + OUString getComposedHaving( ) const; + + /** appends one filter component to the statement in our composer + */ + static void appendFilterComponent( OUStringBuffer& io_appendTo, std::u16string_view i_component ); + + /// checks whether there is only one (or even no) non-empty filter component + bool isThereAtMostOneFilterComponent( OUString& o_singleComponent ) const; + bool isThereAtMostOneHavingComponent( OUString& o_singleComponent ) const; + }; + + +} // namespacefrm + + +#endif // CONNECTIVITY_FORMFILTERMANAGER_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/formattedcolumnvalue.hxx b/include/connectivity/formattedcolumnvalue.hxx new file mode 100644 index 000000000..9fdf227ed --- /dev/null +++ b/include/connectivity/formattedcolumnvalue.hxx @@ -0,0 +1,98 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#ifndef INCLUDED_CONNECTIVITY_FORMATTEDCOLUMNVALUE_HXX +#define INCLUDED_CONNECTIVITY_FORMATTEDCOLUMNVALUE_HXX + +#include <connectivity/dbtoolsdllapi.hxx> +#include <rtl/ustring.hxx> +#include <memory> + +namespace com::sun::star::beans { class XPropertySet; } +namespace com::sun::star::sdbc { class XRowSet; } +namespace com::sun::star::sdb { class XColumn; } +namespace com::sun::star::uno { class XComponentContext; } +namespace com::sun::star::uno { template <typename > class Reference; } +namespace com::sun::star::util { class XNumberFormatter; } + +namespace dbtools +{ + struct FormattedColumnValue_Data; + + //= FormattedColumnValue + + /** a class which helps retrieving and setting the value of a database column + as formatted string. + */ + class OOO_DLLPUBLIC_DBTOOLS FormattedColumnValue final + { + public: + /** constructs an instance + + The format key for the string value exchange is taken from the given column object. + If it has a non-<NULL/> property value <code>FormatKey</code>, this key is taken. + Otherwise, a default format matching the column type is determined. + + The locale of this fallback format is the current system locale. + + The number formats supplier is determined from the given <code>RowSet</code>, by + examining its <code>ActiveConnection</code>. + */ + FormattedColumnValue( + const css::uno::Reference< css::uno::XComponentContext >& _rxContext, + const css::uno::Reference< css::sdbc::XRowSet >& _rxRowSet, + const css::uno::Reference< css::beans::XPropertySet >& _rxColumn + ); + + /** constructs an instance + + The format key for the string value exchange is taken from the given column object. + If it has a non-<NULL/> property value <code>FormatKey</code>, this key is taken. + Otherwise, a default format matching the column type is determined. + + The locale of this fallback format is the current system locale. + */ + FormattedColumnValue( + const css::uno::Reference< css::util::XNumberFormatter >& i_rNumberFormatter, + const css::uno::Reference< css::beans::XPropertySet >& i_rColumn + ); + + ~FormattedColumnValue(); + + // access to the details of the formatting we determined + sal_Int16 getKeyType() const; + const css::uno::Reference< css::sdb::XColumn >& + getColumn() const; + + bool setFormattedValue( const OUString& _rFormattedStringValue ) const; + OUString getFormattedValue() const; + + private: + FormattedColumnValue(const FormattedColumnValue&) = delete; + FormattedColumnValue& operator=(const FormattedColumnValue&) = delete; + std::unique_ptr< FormattedColumnValue_Data > m_pData; + }; + + +} // namespace dbtools + + +#endif // INCLUDED_CONNECTIVITY_FORMATTEDCOLUMNVALUE_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/internalnode.hxx b/include/connectivity/internalnode.hxx new file mode 100644 index 000000000..3402f8e3a --- /dev/null +++ b/include/connectivity/internalnode.hxx @@ -0,0 +1,51 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ +#pragma once + +#include <sal/config.h> + +#include <string_view> + +#include <connectivity/sqlnode.hxx> + +namespace connectivity +{ + + //= OSQLInternalNode + + /** special node for avoiding memory leaks + */ + class OSQLInternalNode final : public OSQLParseNode + { + public: + OSQLInternalNode(const char* pNewValue, + SQLNodeType eNodeType, + sal_uInt32 nNodeID = 0); + OSQLInternalNode(std::string_view _rNewValue, + SQLNodeType eNodeType, + sal_uInt32 nNodeID = 0); + OSQLInternalNode(const OUString& _rNewValue, + SQLNodeType eNodeType, + sal_uInt32 nNodeID = 0); + + virtual ~OSQLInternalNode() override; + }; +} + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/odbc.hxx b/include/connectivity/odbc.hxx new file mode 100644 index 000000000..9f1e487eb --- /dev/null +++ b/include/connectivity/odbc.hxx @@ -0,0 +1,94 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ +#pragma once + +#if defined(_WIN32) + +#include <prewin.h> + +// just to go with calling convention of windows +#if SYSTEM_ODBC_HEADERS +#if !defined WIN32_LEAN_AND_MEAN +# define WIN32_LEAN_AND_MEAN +#endif +#include <windows.h> +#define SQL_API __stdcall +#include <sqlext.h> +#else +#define SQL_API __stdcall +#include <odbc/sqlext.h> +#endif +#undef SQL_API +#define SQL_API __stdcall + +#ifndef SQL_C_BOOKMARK +#define SQL_C_BOOKMARK SQL_C_ULONG /* BOOKMARK */ +#endif + +#ifndef SQL_OPT_TRACE_OFF +#define SQL_OPT_TRACE_OFF 0UL +#endif + +#define SDB_ODBC_CHAR UCHAR + +#include <postwin.h> + +#endif + + +#ifdef UNX + +#ifndef ODBC_UNX +#define ODBC_UNX +#endif +#define CALLBACK +#define EXPORT +#ifdef SYSTEM_ODBC_HEADERS +#include <sqlext.h> +#else +#include <odbc/sqlext.h> +#endif + +#define SDB_ODBC_CHAR UCHAR + +#endif // UNX + + +#ifndef SQL_WCHAR +#define SQL_WCHAR (-8) +#endif +#ifndef SQL_WVARCHAR +#define SQL_WVARCHAR (-9) +#endif +#ifndef SQL_WLONGVARCHAR +#define SQL_WLONGVARCHAR (-10) +#endif +#ifndef SQL_C_WCHAR +#define SQL_C_WCHAR SQL_WCHAR +#endif + +#ifndef SQL_C_TCHAR +#ifdef UNICODE +#define SQL_C_TCHAR SQL_C_WCHAR +#else +#define SQL_C_TCHAR SQL_C_CHAR +#endif +#endif + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/parameters.hxx b/include/connectivity/parameters.hxx new file mode 100644 index 000000000..f2196af12 --- /dev/null +++ b/include/connectivity/parameters.hxx @@ -0,0 +1,415 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ +#ifndef INCLUDED_CONNECTIVITY_PARAMETERS_HXX +#define INCLUDED_CONNECTIVITY_PARAMETERS_HXX + +#include <map> +#include <vector> + +#include <com/sun/star/sdb/XSingleSelectQueryComposer.hpp> + +#include <connectivity/dbtoolsdllapi.hxx> +#include <connectivity/paramwrapper.hxx> +#include <unotools/sharedunocomponent.hxx> +#include <comphelper/interfacecontainer3.hxx> + +namespace com::sun::star::beans { class XPropertySet; } +namespace com::sun::star::container { class XIndexAccess; } +namespace com::sun::star::form { class XDatabaseParameterListener; } +namespace com::sun::star::io { class XInputStream; } +namespace com::sun::star::sdbc { class XArray; } +namespace com::sun::star::sdbc { class XBlob; } +namespace com::sun::star::sdbc { class XClob; } +namespace com::sun::star::sdbc { class XConnection; } +namespace com::sun::star::sdbc { class XDatabaseMetaData; } +namespace com::sun::star::sdbc { class XParameters; } +namespace com::sun::star::sdbc { class XRef; } +namespace com::sun::star::task { class XInteractionHandler; } +namespace com::sun::star::uno { class XAggregation; } +namespace com::sun::star::uno { class XComponentContext; } + +namespace dbtools +{ + + + typedef ::utl::SharedUNOComponent< css::sdb::XSingleSelectQueryComposer, ::utl::DisposableComponent > + SharedQueryComposer; + + + //= ParameterManager + + class FilterManager; + class OOO_DLLPUBLIC_DBTOOLS ParameterManager + { + public: + /// classifies the origin of the data to fill a parameter + enum class ParameterClassification + { + /** parameters which are filled from the master-detail relationship, where the detail + name is an explicit parameter name + */ + LinkedByParamName, + /** parameters which are filled from the master-detail relationship, where the detail + name is a column name, so an implicit parameter had to be generated for it + */ + LinkedByColumnName, + /** parameters which are filled externally (i.e. by XParameters::setXXX, or by the parameter listeners) + */ + FilledExternally + }; + /** meta data about an inner parameter + */ + private: + struct ParameterMetaData + { + /// the type of the parameter + ParameterClassification eType; + /// the column object for this parameter, as returned by the query composer + css::uno::Reference< css::beans::XPropertySet > + xComposerColumn; + /// the indices of inner parameters which need to be filled when this concrete parameter is set + ::std::vector< sal_Int32 > aInnerIndexes; + + /// ctor with composer column + ParameterMetaData( const css::uno::Reference< css::beans::XPropertySet >& _rxColumn ) + :eType ( ParameterClassification::FilledExternally ) + ,xComposerColumn ( _rxColumn ) + { + } + }; + + typedef ::std::map< OUString, ParameterMetaData > ParameterInformation; + + private: + ::osl::Mutex& m_rMutex; + ::comphelper::OInterfaceContainerHelper3<css::form::XDatabaseParameterListener> m_aParameterListeners; + + css::uno::Reference< css::uno::XComponentContext > + m_xContext; + + css::uno::WeakReference< css::beans::XPropertySet > + m_xComponent; // the database component whose parameters we're handling + css::uno::Reference< css::uno::XAggregation > + m_xAggregatedRowSet; // the aggregated row set - necessary for unwrapped access to some interfaces + css::uno::Reference< css::sdbc::XParameters > + m_xInnerParamUpdate; // write access to the inner parameters + SharedQueryComposer m_xComposer; // query composer wrapping the statement which the *aggregate* is based on + SharedQueryComposer m_xParentComposer; // query composer wrapping the statement of our parent database component + css::uno::Reference< css::container::XIndexAccess > + m_xInnerParamColumns; // index access to the parameter columns, as got from the query composer + + ::dbtools::param::ParametersContainerRef + m_pOuterParameters; // the container of parameters which still need to be filled in by + // external instances + sal_Int32 m_nInnerCount; // overall number of parameters as required by the database component's aggregate + + ParameterInformation m_aParameterInformation; + + std::vector< OUString > m_aMasterFields; + std::vector< OUString > m_aDetailFields; + + OUString m_sIdentifierQuoteString; + OUString m_sSpecialCharacters; + css::uno::Reference< css::sdbc::XDatabaseMetaData > m_xConnectionMetadata; + + ::std::vector< bool > m_aParametersVisited; + + bool m_bUpToDate; + + public: + /** ctor + */ + explicit ParameterManager( + ::osl::Mutex& _rMutex, + const css::uno::Reference< css::uno::XComponentContext >& _rxContext + ); + + /// late ctor + void initialize( + const css::uno::Reference< css::beans::XPropertySet >& _rxComponent, + const css::uno::Reference< css::uno::XAggregation >& _rxComponentAggregate + ); + + /// makes the object forgetting the references to the database component + void dispose( ); + + /// clears the instance data + void clearAllParameterInformation(); + + /// checks whether the parameter information is up-to-date + bool isUpToDate() const { return m_bUpToDate; } + + /** updates all parameter information represented by the instance + */ + void updateParameterInfo( FilterManager& _rFilterManager ); + + /** fills parameter values, as extensive as possible + + <p>In particular, all values which can be filled from the master-detail relationship of + between our database component and its parent are filled in.</p> + + @param _rxCompletionHandler + an interaction handler which should be used to fill all parameters which + cannot be filled by other means. May be <NULL/> + @param _rClearForNotifies + the mutex guard to be (temporarily) cleared for notifications + + @precond + the instance is alive, i.e. <member>isAlive</member> returns <TRUE/> + + @return + <TRUE/> if and only if the parameter filling has <em>not</em> been cancelled by the user + */ + bool fillParameterValues( + const css::uno::Reference< css::task::XInteractionHandler >& _rxCompletionHandler, + ::osl::ResettableMutexGuard& _rClearForNotifies + ); + + /** sets all parameter values to null (via <member>XParameters::setNull</member>) + + @precond + the instance is alive, i.e. <member>isAlive</member> returns <TRUE/> + */ + void setAllParametersNull(); + + /** resets all detail columns which are, via a parameter, linked to a master column, to + the value of this master column. + + For instance, if the database component is bound to a statement <code>SELECT * from invoice where inv_id = :cid</code>, + and there is <em>one</em> master-detail link from + + @precond + the instance is alive, i.e. <member>isAlive</member> returns <TRUE/> + */ + void resetParameterValues(); + + /** adds the given listener to the list of parameter listeners + */ + void addParameterListener( + const css::uno::Reference< css::form::XDatabaseParameterListener >& _rxListener + ); + + /** removes the given listener from the list of parameter listeners + */ + void removeParameterListener( + const css::uno::Reference< css::form::XDatabaseParameterListener >& _rxListener + ); + + // XParameters equivalents + void setNull ( sal_Int32 _nIndex, sal_Int32 sqlType); + void setObjectNull ( sal_Int32 _nIndex, sal_Int32 sqlType, const OUString& typeName); + void setBoolean ( sal_Int32 _nIndex, bool x); + void setByte ( sal_Int32 _nIndex, sal_Int8 x); + void setShort ( sal_Int32 _nIndex, sal_Int16 x); + void setInt ( sal_Int32 _nIndex, sal_Int32 x); + void setLong ( sal_Int32 _nIndex, sal_Int64 x); + void setFloat ( sal_Int32 _nIndex, float x); + void setDouble ( sal_Int32 _nIndex, double x); + void setString ( sal_Int32 _nIndex, const OUString& x); + void setBytes ( sal_Int32 _nIndex, const css::uno::Sequence< sal_Int8 >& x); + void setDate ( sal_Int32 _nIndex, const css::util::Date& x); + void setTime ( sal_Int32 _nIndex, const css::util::Time& x); + void setTimestamp ( sal_Int32 _nIndex, const css::util::DateTime& x); + void setBinaryStream ( sal_Int32 _nIndex, const css::uno::Reference< css::io::XInputStream>& x, sal_Int32 length); + void setCharacterStream ( sal_Int32 _nIndex, const css::uno::Reference< css::io::XInputStream>& x, sal_Int32 length); + void setObject ( sal_Int32 _nIndex, const css::uno::Any& x); + void setObjectWithInfo ( sal_Int32 _nIndex, const css::uno::Any& x, sal_Int32 targetSqlType, sal_Int32 scale); + void setRef ( sal_Int32 _nIndex, const css::uno::Reference< css::sdbc::XRef>& x); + void setBlob ( sal_Int32 _nIndex, const css::uno::Reference< css::sdbc::XBlob>& x); + void setClob ( sal_Int32 _nIndex, const css::uno::Reference< css::sdbc::XClob>& x); + void setArray ( sal_Int32 _nIndex, const css::uno::Reference< css::sdbc::XArray>& x); + void clearParameters(); + + private: + /// checks whether the object is already initialized, and not yet disposed + bool isAlive() const { return m_xComponent.get().is() && m_xInnerParamUpdate.is(); } + + /** creates a filter expression from a master-detail link where the detail denotes a column name + */ + OUString + createFilterConditionFromColumnLink( + const OUString& /* [in] */ _rMasterColumn, + const css::uno::Reference< css::beans::XPropertySet >& /* [in] */ xDetailColumn, + OUString& /* [out] */ _rNewParamName + ); + + /** initializes our query composer, and the collection of inner parameter columns + + @param _rxComponent + the database component to initialize from. Must not be <NULL/> + @return + <TRUE/> if and only if the initialization was successful + + @postcond + if and only if <TRUE/> is returned, then <member>m_xInnerParamColumns</member> contains the collection of + inner parameters + */ + bool initializeComposerByComponent( + const css::uno::Reference< css::beans::XPropertySet >& _rxComponent + ); + + /** collects initial meta information about inner parameters (i.e. it initially fills + <member>m_aParameterInformation</member>). + + @param _bSecondRun + if <TRUE/>, this is the second run, because we ourself previously extended the filter of + the RowSet + + @precond + <member>m_xInnerParamColumns</member> is not <NULL/> + */ + void collectInnerParameters( bool _bSecondRun ); + + /** analyzes the master-detail links for our database component, and initializes m_aMasterFields and m_aDetailFields + + @param _rFilterManager + the filter manager of the database component + @param _rColumnsInLinkDetails + will be set to <TRUE/> if and only if there were link pairs where the detail field denoted + a column name of our database component + + @precond + the instance is alive, i.e. <member>isAlive</member> returns <TRUE/> + */ + void analyzeFieldLinks( FilterManager& _rFilterManager, bool& /* [out] */ _rColumnsInLinkDetails ); + + /** classifies the link pairs + + @param _rxParentColumns + the columns of the parent database component + + @param _rxColumns + the columns of our own database component + + @param _out_rAdditionalFilterComponents + the additional filter components which are required for master-detail relationships where + the detail part denotes a column name. In such a case, an additional filter needs to be created, + containing a new parameter. + + @param _out_rAdditionalHavingComponents + the additional having clause components which are required for master-detail relationships where + the detail part denotes a column name. In such a case, an additional filter needs to be created, + containing a new parameter. + + @precond + <member>m_aMasterFields</member> and <member>m_aDetailFields</member> have the same length + */ + void classifyLinks( + const css::uno::Reference< css::container::XNameAccess >& _rxParentColumns, + const css::uno::Reference< css::container::XNameAccess >& _rxColumns, + ::std::vector< OUString >& _out_rAdditionalFilterComponents, + ::std::vector< OUString >& _out_rAdditionalHavingComponents + ); + + /** finalizes our <member>m_pOuterParameters</member> so that it can be used for + external parameter listeners + + @precond + <member>m_pOuterParameters</member> is <NULL/> + @precond + <member>m_xInnerParamUpdate</member> is not <NULL/> + */ + void createOuterParameters(); + + /** fills in the parameters values which result from the master-detail relationship + between the database component and its parent + + @param _rxParentColumns + the columns of the parameter database component. Must not be <NULL/> + @precond + the instance is alive, i.e. <member>isAlive</member> returns <TRUE/> + */ + void fillLinkedParameters( + const css::uno::Reference< css::container::XNameAccess >& _rxParentColumns + ); + + /** completes all missing parameters via an interaction handler + + @precond + the instance is alive, i.e. <member>isAlive</member> returns <TRUE/> + + @return + <TRUE/> if and only if the parameter filling has <em>not</em> been cancelled by the user + */ + bool completeParameters( + const css::uno::Reference< css::task::XInteractionHandler >& _rxCompletionHandler, + const css::uno::Reference< css::sdbc::XConnection >& _rxConnection + ); + + /** asks the parameter listeners to fill in final values + + @precond + the instance is alive, i.e. <member>isAlive</member> returns <TRUE/> + + @return + <TRUE/> if and only if the parameter filling has <em>not</em> been cancelled by the user + */ + bool consultParameterListeners( ::osl::ResettableMutexGuard& _rClearForNotifies ); + + /** mark an externally filled parameter as visited + */ + void externalParameterVisited( sal_Int32 _nIndex ); + + private: + /** retrieves the columns of the parent database component + + @precond + the instance is alive, i.e. <member>isAlive</member> returns <TRUE/> + @return + <TRUE/> if and only if the columns could be successfully retrieved + */ + bool getParentColumns( + css::uno::Reference< css::container::XNameAccess >& /* [out] */ _out_rxParentColumns, + bool _bFromComposer + ); + + /** retrieves the columns of our database component + + @param _bFromComposer + if <TRUE/>, the columns are obtained from the composer, else from the living database component itself + @return + <TRUE/> if and only if the columns could be successfully retrieved + */ + bool getColumns( + css::uno::Reference< css::container::XNameAccess >& /* [out] */ _rxColumns, + bool _bFromComposer + ); + + /** retrieves the active connection of the database component + */ + void getConnection( + css::uno::Reference< css::sdbc::XConnection >& /* [out] */ _rxConnection + ); + + /** caches some info about the connection of our database component + */ + void cacheConnectionInfo(); + + private: + ParameterManager( const ParameterManager& ) = delete; + ParameterManager& operator=( const ParameterManager& ) = delete; + }; + + +} // namespacefrm + + +#endif // INCLUDED_CONNECTIVITY_PARAMETERS_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/paramwrapper.hxx b/include/connectivity/paramwrapper.hxx new file mode 100644 index 000000000..bf16e0851 --- /dev/null +++ b/include/connectivity/paramwrapper.hxx @@ -0,0 +1,196 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#ifndef INCLUDED_CONNECTIVITY_PARAMWRAPPER_HXX +#define INCLUDED_CONNECTIVITY_PARAMWRAPPER_HXX + +#include <config_options.h> +#include <connectivity/dbtoolsdllapi.hxx> +#include <connectivity/FValue.hxx> + +#include <com/sun/star/container/XIndexAccess.hpp> +#include <com/sun/star/container/XEnumerationAccess.hpp> + +#include <comphelper/uno3.hxx> +#include <comphelper/broadcasthelper.hxx> +#include <cppuhelper/weak.hxx> +#include <cppuhelper/propshlp.hxx> +#include <cppuhelper/compbase.hxx> + +#include <memory> +#include <vector> + +namespace com::sun::star::sdbc { class XParameters; } +namespace com::sun::star::sdb { class XSingleSelectQueryAnalyzer; } + + +namespace dbtools::param +{ + + + //= ParameterWrapper + + /** wraps a parameter column as got from an SQLQueryComposer, so that it has an additional + property "Value", which is forwarded to an XParameters interface + */ + class UNLESS_MERGELIBS(OOO_DLLPUBLIC_DBTOOLS) ParameterWrapper final : public ::cppu::OWeakObject + ,public css::lang::XTypeProvider + ,public ::comphelper::OMutexAndBroadcastHelper + ,public ::cppu::OPropertySetHelper + { + private: + typedef ::cppu::OWeakObject UnoBase; + typedef ::cppu::OPropertySetHelper PropertyBase; + + private: + /// the most recently set value of the parameter + ::connectivity::ORowSetValue m_aValue; + /// the positions (in our m_xValueDestination) at which the value should be set (0-based!) + ::std::vector< sal_Int32 > m_aIndexes; + + /// the "delegator" column to which standard property requests are forwarded + css::uno::Reference< css::beans::XPropertySet > m_xDelegator; + /// the property set info for our delegator + css::uno::Reference< css::beans::XPropertySetInfo > m_xDelegatorPSI; + /// the component taking the value + css::uno::Reference< css::sdbc::XParameters > m_xValueDestination; + /// helper for implementing XPropertySetInfo + ::std::unique_ptr< ::cppu::OPropertyArrayHelper > m_pInfoHelper; + + + public: + const ::connectivity::ORowSetValue& Value() const { return m_aValue; } + ::connectivity::ORowSetValue& Value() { return m_aValue; } + + public: + ParameterWrapper( + const css::uno::Reference< css::beans::XPropertySet >& _rxColumn + ); + + ParameterWrapper( + const css::uno::Reference< css::beans::XPropertySet >& _rxColumn, + const css::uno::Reference< css::sdbc::XParameters >& _rxAllParameters, + std::vector< sal_Int32 >&& _rIndexes + ); + + DECLARE_XINTERFACE() + + virtual css::uno::Sequence< css::uno::Type > SAL_CALL getTypes( ) override; + virtual css::uno::Sequence< sal_Int8 > SAL_CALL getImplementationId( ) override; + + // XPropertySet + virtual css::uno::Reference< css::beans::XPropertySetInfo > SAL_CALL getPropertySetInfo() override; + virtual ::cppu::IPropertyArrayHelper& SAL_CALL getInfoHelper() override; + + // OPropertySetHelper + virtual sal_Bool SAL_CALL convertFastPropertyValue( css::uno::Any& rConvertedValue, css::uno::Any& rOldValue, sal_Int32 nHandle, const css::uno::Any& rValue) override; + virtual void SAL_CALL setFastPropertyValue_NoBroadcast( sal_Int32 nHandle, const css::uno::Any& rValue ) override; + virtual void SAL_CALL getFastPropertyValue( css::uno::Any& rValue, sal_Int32 nHandle ) const override; + + // pseudo-XComponent + void dispose(); + + private: + virtual ~ParameterWrapper() override; + + // disambiguations + using ::cppu::OPropertySetHelper::getFastPropertyValue; + + OUString impl_getPseudoAggregatePropertyName( sal_Int32 _nHandle ) const; + }; + + + //= ParameterWrapper + + typedef ::std::vector< ::rtl::Reference< ParameterWrapper > > Parameters; + + + //= ParameterWrapperContainer + + typedef ::cppu::WeakComponentImplHelper < css::container::XIndexAccess + , css::container::XEnumerationAccess + > ParameterWrapperContainer_Base; + + /// class for the parameter event @see approveParameter + class OOO_DLLPUBLIC_DBTOOLS ParameterWrapperContainer final : + public ParameterWrapperContainer_Base + { + private: + ::osl::Mutex m_aMutex; + Parameters m_aParameters; + + virtual ~ParameterWrapperContainer() override; + + public: + /** creates an empty container + */ + ParameterWrapperContainer(); + + /** creates a container from a SingleSelectQuerAnalyzer's parameter columns + + Note that here, the simple constructor of the ParameterWrapper will be used, which does not + use a XParameters instance to forward values to, but only remembers the values itself. + */ + ParameterWrapperContainer( const css::uno::Reference< css::sdb::XSingleSelectQueryAnalyzer >& _rxComposer ); + + // css::container::XElementAccess + virtual css::uno::Type SAL_CALL getElementType() override; + virtual sal_Bool SAL_CALL hasElements() override; + + // css::container::XEnumerationAccess + virtual css::uno::Reference< css::container::XEnumeration > SAL_CALL createEnumeration() override; + + // css::container::XIndexAccess + virtual sal_Int32 SAL_CALL getCount() override; + virtual css::uno::Any SAL_CALL getByIndex(sal_Int32 _rIndex) override; + + public: + const Parameters& getParameters() const { return m_aParameters; } + + const ::connectivity::ORowSetValue& operator[]( size_t _index ) const { return m_aParameters[ _index ]->Value(); } + ::connectivity::ORowSetValue& operator[]( size_t _index ) { return m_aParameters[ _index ]->Value(); } + + /** adds a ParameterWrapper to the end of the array + */ + void push_back( ParameterWrapper* _pParameter ) + { + m_aParameters.push_back( _pParameter ); + } + + size_t size() const { return m_aParameters.size(); } + + private: + // XComponent + virtual void SAL_CALL disposing() override; + + void impl_checkDisposed_throw(); + }; + + + //= ParametersContainer + + typedef ::rtl::Reference< ParameterWrapperContainer > ParametersContainerRef; + + +} // namespace dbtools::param + + +#endif // INCLUDED_CONNECTIVITY_PARAMWRAPPER_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/predicateinput.hxx b/include/connectivity/predicateinput.hxx new file mode 100644 index 000000000..3d9fb0a71 --- /dev/null +++ b/include/connectivity/predicateinput.hxx @@ -0,0 +1,129 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#ifndef INCLUDED_CONNECTIVITY_PREDICATEINPUT_HXX +#define INCLUDED_CONNECTIVITY_PREDICATEINPUT_HXX + +#include <connectivity/sqlparse.hxx> +#include <connectivity/dbtoolsdllapi.hxx> +#include <com/sun/star/uno/Any.hxx> + +namespace com::sun::star::beans { class XPropertySet; } +namespace com::sun::star::i18n { class XLocaleData4; } +namespace com::sun::star::sdbc { class XConnection; } +namespace com::sun::star::uno { class XComponentContext; } +namespace com::sun::star::util { class XNumberFormatter; } + + + +namespace dbtools +{ + + + //= OPredicateInputController + + /** A class which allows input of an SQL predicate for a row set column + into an edit field. + */ + class OOO_DLLPUBLIC_DBTOOLS OPredicateInputController + { + private: + css::uno::Reference< css::sdbc::XConnection > + m_xConnection; + css::uno::Reference< css::util::XNumberFormatter > + m_xFormatter; + css::uno::Reference< css::i18n::XLocaleData4 > + m_xLocaleData; + + ::connectivity::OSQLParser + m_aParser; + + public: + OPredicateInputController( + const css::uno::Reference< css::uno::XComponentContext >& rxContext, + const css::uno::Reference< css::sdbc::XConnection >& _rxConnection, + const ::connectivity::IParseContext* _pParseContext = nullptr + ); + + /** transforms a "raw" predicate value (usually obtained from a user input) into a valid predicate for the given column + @param _rPredicateValue + The text to normalize. + @param _rxField + The field for which the text should be a predicate value. + @param _pErrorMessage + If not <NULL/>, and a parsing error occurs, the error message will be copied to the string the argument + points to. + */ + bool normalizePredicateString( + OUString& _rPredicateValue, + const css::uno::Reference< css::beans::XPropertySet >& _rxField, + OUString* _pErrorMessage = nullptr + ) const; + + /** get the value of the predicate, as a string to be used in a WHERE clause + @param _rPredicateValue + the value which has been normalized using normalizePredicateString + @param _rxField + is the field for which a predicate is to be entered + @see normalizePredicateString + */ + OUString getPredicateValueStr( + const OUString& _rPredicateValue, + const css::uno::Reference< css::beans::XPropertySet > & _rxField + ) const; + + OUString getPredicateValueStr( + const OUString& _sField + , const OUString& _rPredicateValue) const; + + /** get the value of the predicate, either as an empty or as a string + @param _rPredicateValue + the value which has been normalized using normalizePredicateString + @param _rxField + is the field for which a predicate is to be entered + @see normalizePredicateString + */ + css::uno::Any getPredicateValue( + const OUString& _rPredicateValue, + const css::uno::Reference< css::beans::XPropertySet > & _rxField + ) const; + + private: + std::unique_ptr<::connectivity::OSQLParseNode> implPredicateTree( + OUString& _rErrorMessage, + const OUString& _rStatement, + const css::uno::Reference< css::beans::XPropertySet > & _rxField + ) const; + + bool getSeparatorChars( + const css::lang::Locale& _rLocale, + sal_Unicode& _rDecSep, + sal_Unicode& _rThdSep + ) const; + + css::uno::Any implParseNode(std::unique_ptr<::connectivity::OSQLParseNode> pParseNode, bool _bForStatementUse) const; + }; + + +} // namespace dbtools + + +#endif // INCLUDED_CONNECTIVITY_PREDICATEINPUT_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/sdbcx/IRefreshable.hxx b/include/connectivity/sdbcx/IRefreshable.hxx new file mode 100644 index 000000000..412ef8079 --- /dev/null +++ b/include/connectivity/sdbcx/IRefreshable.hxx @@ -0,0 +1,56 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ +#ifndef INCLUDED_CONNECTIVITY_SDBCX_IREFRESHABLE_HXX +#define INCLUDED_CONNECTIVITY_SDBCX_IREFRESHABLE_HXX + +#include <connectivity/dbtoolsdllapi.hxx> + +namespace connectivity::sdbcx + { + class OOO_DLLPUBLIC_DBTOOLS SAL_NO_VTABLE IRefreshableGroups + { + public: + virtual void refreshGroups() = 0; + + protected: + ~IRefreshableGroups() {} + }; + + class OOO_DLLPUBLIC_DBTOOLS SAL_NO_VTABLE IRefreshableUsers + { + public: + virtual void refreshUsers() = 0; + + protected: + ~IRefreshableUsers() {} + }; + + class OOO_DLLPUBLIC_DBTOOLS SAL_NO_VTABLE IRefreshableColumns + { + public: + virtual void refreshColumns() = 0; + + protected: + ~IRefreshableColumns() {} + }; + +} +#endif // INCLUDED_CONNECTIVITY_SDBCX_IREFRESHABLE_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/sdbcx/VCollection.hxx b/include/connectivity/sdbcx/VCollection.hxx new file mode 100644 index 000000000..0f5a0b3fb --- /dev/null +++ b/include/connectivity/sdbcx/VCollection.hxx @@ -0,0 +1,225 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#ifndef INCLUDED_CONNECTIVITY_SDBCX_VCOLLECTION_HXX +#define INCLUDED_CONNECTIVITY_SDBCX_VCOLLECTION_HXX + +#include <config_options.h> +#include <cppuhelper/implbase10.hxx> +#include <com/sun/star/container/XNameAccess.hpp> +#include <com/sun/star/container/XIndexAccess.hpp> +#include <com/sun/star/container/XEnumerationAccess.hpp> +#include <com/sun/star/beans/XPropertySet.hpp> +#include <com/sun/star/util/XRefreshable.hpp> +#include <com/sun/star/sdbcx/XDataDescriptorFactory.hpp> +#include <com/sun/star/sdbcx/XAppend.hpp> +#include <com/sun/star/sdbcx/XDrop.hpp> +#include <com/sun/star/sdbc/XColumnLocate.hpp> +#include <comphelper/interfacecontainer3.hxx> +#include <com/sun/star/lang/XServiceInfo.hpp> +#include <connectivity/CommonTools.hxx> +#include <com/sun/star/container/XContainer.hpp> +#include <connectivity/dbtoolsdllapi.hxx> +#include <memory> + +namespace com::sun::star::container { class XEnumeration; } + + +namespace connectivity::sdbcx + { + + // the class OCollection is base class for collections :-) + typedef ::cppu::ImplHelper10< css::container::XNameAccess, + css::container::XIndexAccess, + css::container::XEnumerationAccess, + css::container::XContainer, + css::sdbc::XColumnLocate, + css::util::XRefreshable, + css::sdbcx::XDataDescriptorFactory, + css::sdbcx::XAppend, + css::sdbcx::XDrop, + css::lang::XServiceInfo> OCollectionBase; + + typedef css::uno::Reference< css::beans::XPropertySet > ObjectType; + + class UNLESS_MERGELIBS(OOO_DLLPUBLIC_DBTOOLS) SAL_NO_VTABLE IObjectCollection + { + public: + virtual ~IObjectCollection(); + virtual bool exists(const OUString& _sName ) = 0; + virtual bool empty() = 0; + virtual void swapAll() = 0; + virtual void swap() = 0; + virtual void clear() = 0; + virtual void reFill(const ::std::vector< OUString> &_rVector) = 0; + virtual void insert(const OUString& _sName, const ObjectType& _xObject) = 0; + virtual bool rename(const OUString& _sOldName, const OUString& _sNewName) = 0; + virtual sal_Int32 size() = 0; + virtual css::uno::Sequence< OUString > getElementNames() = 0; + virtual OUString getName(sal_Int32 _nIndex) = 0; + virtual void disposeAndErase(sal_Int32 _nIndex) = 0; + virtual void disposeElements() = 0; + virtual sal_Int32 findColumn( const OUString& columnName ) = 0; + virtual ObjectType getObject(sal_Int32 _nIndex) = 0; + virtual ObjectType getObject(const OUString& columnName) = 0; + virtual void setObject(sal_Int32 _nIndex,const ObjectType& _xObject) = 0; + virtual bool isCaseSensitive() const = 0; + }; + + // OCollection + + class OOO_DLLPUBLIC_DBTOOLS SAL_NO_VTABLE OCollection : + public OCollectionBase + { + protected: + ::std::unique_ptr<IObjectCollection> m_pElements; + + ::comphelper::OInterfaceContainerHelper3<css::container::XContainerListener> m_aContainerListeners; + ::comphelper::OInterfaceContainerHelper3<css::util::XRefreshListener> m_aRefreshListeners; + + protected: + ::cppu::OWeakObject& m_rParent; // parent of the collection + ::osl::Mutex& m_rMutex; // mutex of the parent + bool m_bUseIndexOnly; // is only TRUE when only an indexaccess is needed + + // the implementing class should refresh their elements + /// @throws css::uno::RuntimeException + virtual void impl_refresh() = 0; + + // will be called when an object was requested by one of the accessing methods like getByIndex + virtual ObjectType createObject(const OUString& _rName) = 0; + + // will be called when a new object should be generated by a call of createDataDescriptor + // the returned object is empty will be filled outside and added to the collection + virtual css::uno::Reference< css::beans::XPropertySet > createDescriptor(); + + /** appends an object described by a descriptor, under a given name + @param _rForName + is the name under which the object should be appended. Guaranteed to not be empty. + This is passed for convenience only, since it's the result of a call of + getNameForObject for the given descriptor + @param descriptor + describes the object to append + @return + the new object which is to be inserted into the collection. This might be the result + of a call of <code>createObject( _rForName )</code>, or a clone of the descriptor. + */ + virtual ObjectType appendObject( const OUString& _rForName, const css::uno::Reference< css::beans::XPropertySet >& descriptor ); + + // called when XDrop was called + virtual void dropObject(sal_Int32 _nPos, const OUString& _sElementName); + + /** returns the name for the object. The default implementation ask for the property NAME. If this doesn't satisfy, it has to be overridden. + @param _xObject The object where the name should be extracted. + @return The name of the object. + */ + virtual OUString getNameForObject(const ObjectType& _xObject); + + /** clones the given descriptor + + The method calls createDescriptor to create a new, empty descriptor, and then copies all properties from + _descriptor to the new object, which is returned. + + This method might come handy in derived classes for implementing appendObject, when the object + is not actually appended to any backend (e.g. for the columns collection of a descriptor object itself, + where there is not yet a database backend to append the column to). + */ + ObjectType cloneDescriptor( const ObjectType& _descriptor ); + + OCollection(::cppu::OWeakObject& _rParent, + bool _bCase, + ::osl::Mutex& _rMutex, + const ::std::vector< OUString> &_rVector, + bool _bUseIndexOnly = false, + bool _bUseHardRef = true); + + /** clear the name map + <p>Does <em>not</em> dispose the objects hold by the collection.</p> + */ + void clear_NoDispose(); + + /** insert a new element into the collection + */ + void insertElement(const OUString& _sElementName,const ObjectType& _xElement); + + /** return the object, if not existent it creates it. + @param _nIndex + The index of the object to create. + @return ObjectType + */ + ObjectType getObject(sal_Int32 _nIndex); + + public: + virtual ~OCollection(); + DECLARE_SERVICE_INFO(); + + void reFill(const ::std::vector< OUString> &_rVector); + bool isCaseSensitive() const { return m_pElements->isCaseSensitive(); } + void renameObject(const OUString& _sOldName, const OUString& _sNewName); + + // only the name is identical to ::cppu::OComponentHelper + virtual void disposing(); + // dispatch the refcounting to the parent + virtual void SAL_CALL acquire() noexcept override; + virtual void SAL_CALL release() noexcept override; + + // XInterface + virtual css::uno::Any SAL_CALL queryInterface( const css::uno::Type & rType ) override; + virtual css::uno::Sequence< css::uno::Type > SAL_CALL getTypes() override; + + // css::container::XElementAccess + virtual css::uno::Type SAL_CALL getElementType( ) override; + virtual sal_Bool SAL_CALL hasElements( ) override; + // css::container::XIndexAccess + virtual sal_Int32 SAL_CALL getCount( ) override; + virtual css::uno::Any SAL_CALL getByIndex( sal_Int32 Index ) override; + + // css::container::XNameAccess + virtual css::uno::Any SAL_CALL getByName( const OUString& aName ) override; + virtual css::uno::Sequence< OUString > SAL_CALL getElementNames( ) override; + virtual sal_Bool SAL_CALL hasByName( const OUString& aName ) override; + // XEnumerationAccess + virtual css::uno::Reference< css::container::XEnumeration > SAL_CALL createEnumeration( ) override; + // css::util::XRefreshable + virtual void SAL_CALL refresh( ) override; + virtual void SAL_CALL addRefreshListener( const css::uno::Reference< css::util::XRefreshListener >& l ) override; + virtual void SAL_CALL removeRefreshListener( const css::uno::Reference< css::util::XRefreshListener >& l ) override; + // XDataDescriptorFactory + virtual css::uno::Reference< css::beans::XPropertySet > SAL_CALL createDataDescriptor( ) override; + // XAppend + virtual void SAL_CALL appendByDescriptor( const css::uno::Reference< css::beans::XPropertySet >& descriptor ) override; + // XDrop + virtual void SAL_CALL dropByName( const OUString& elementName ) override; + virtual void SAL_CALL dropByIndex( sal_Int32 index ) override; + // XColumnLocate + virtual sal_Int32 SAL_CALL findColumn( const OUString& columnName ) override; + // css::container::XContainer + virtual void SAL_CALL addContainerListener( const css::uno::Reference< css::container::XContainerListener >& xListener ) override; + virtual void SAL_CALL removeContainerListener( const css::uno::Reference< css::container::XContainerListener >& xListener ) override; + private: + void notifyElementRemoved(const OUString& _sName); + void disposeElements(); + void dropImpl(sal_Int32 _nIndex, bool _bReallyDrop = true); + }; + +} +#endif // INCLUDED_CONNECTIVITY_SDBCX_VCOLLECTION_HXX + + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/sdbcx/VColumn.hxx b/include/connectivity/sdbcx/VColumn.hxx new file mode 100644 index 000000000..579611cdf --- /dev/null +++ b/include/connectivity/sdbcx/VColumn.hxx @@ -0,0 +1,116 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ +#ifndef INCLUDED_CONNECTIVITY_SDBCX_VCOLUMN_HXX +#define INCLUDED_CONNECTIVITY_SDBCX_VCOLUMN_HXX + +#include <com/sun/star/sdbcx/XDataDescriptorFactory.hpp> +#include <com/sun/star/container/XNamed.hpp> +#include <comphelper/IdPropArrayHelper.hxx> +#include <cppuhelper/compbase.hxx> +#include <cppuhelper/implbase1.hxx> +#include <connectivity/CommonTools.hxx> +#include <cppuhelper/basemutex.hxx> +#include <connectivity/sdbcx/VDescriptor.hxx> +#include <connectivity/dbtoolsdllapi.hxx> +#include <com/sun/star/lang/XServiceInfo.hpp> + +namespace connectivity::sdbcx + { + class OColumn; + typedef ::comphelper::OIdPropertyArrayUsageHelper<OColumn> OColumn_PROP; + + typedef ::cppu::WeakComponentImplHelper< css::container::XNamed, + css::lang::XServiceInfo> OColumnDescriptor_BASE; + typedef ::cppu::ImplHelper1< css::sdbcx::XDataDescriptorFactory > OColumn_BASE; + + + class OOO_DLLPUBLIC_DBTOOLS OColumn : + public cppu::BaseMutex, + public OColumn_BASE, + public OColumnDescriptor_BASE, + public OColumn_PROP, + public ODescriptor + { + protected: + OUString m_TypeName; + OUString m_Description; + OUString m_DefaultValue; + + sal_Int32 m_IsNullable; + sal_Int32 m_Precision; + sal_Int32 m_Scale; + sal_Int32 m_Type; + + bool m_IsAutoIncrement; + bool m_IsRowVersion; + bool m_IsCurrency; + + OUString m_CatalogName; + OUString m_SchemaName; + OUString m_TableName; + + using OColumnDescriptor_BASE::rBHelper; + virtual ::cppu::IPropertyArrayHelper* createArrayHelper( sal_Int32 _nId) const override; + virtual ::cppu::IPropertyArrayHelper& SAL_CALL getInfoHelper() override; + + virtual ~OColumn() override; + public: + virtual void SAL_CALL acquire() noexcept override; + virtual void SAL_CALL release() noexcept override; + + OColumn( bool _bCase); + OColumn( const OUString& Name, + const OUString& TypeName, + const OUString& DefaultValue, + const OUString& Description, + sal_Int32 IsNullable, + sal_Int32 Precision, + sal_Int32 Scale, + sal_Int32 Type, + bool IsAutoIncrement, + bool IsRowVersion, + bool IsCurrency, + bool _bCase, + const OUString& CatalogName, + const OUString& SchemaName, + const OUString& TableName); + + DECLARE_SERVICE_INFO(); + //XInterface + virtual css::uno::Any SAL_CALL queryInterface( const css::uno::Type & rType ) override; + //XTypeProvider + virtual css::uno::Sequence< css::uno::Type > SAL_CALL getTypes( ) override; + // ODescriptor + virtual void construct() override; + // ::cppu::OComponentHelper + virtual void SAL_CALL disposing() override; + // XPropertySet + virtual css::uno::Reference< css::beans::XPropertySetInfo > SAL_CALL getPropertySetInfo( ) override; + // XNamed + virtual OUString SAL_CALL getName( ) override; + virtual void SAL_CALL setName( const OUString& aName ) override; + // XDataDescriptorFactory + virtual css::uno::Reference< css::beans::XPropertySet > SAL_CALL createDataDescriptor( ) override; + }; + +} + +#endif // INCLUDED_CONNECTIVITY_SDBCX_VCOLUMN_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/sdbcx/VDescriptor.hxx b/include/connectivity/sdbcx/VDescriptor.hxx new file mode 100644 index 000000000..3147a5187 --- /dev/null +++ b/include/connectivity/sdbcx/VDescriptor.hxx @@ -0,0 +1,83 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#ifndef INCLUDED_CONNECTIVITY_SDBCX_VDESCRIPTOR_HXX +#define INCLUDED_CONNECTIVITY_SDBCX_VDESCRIPTOR_HXX + +#include <comphelper/propertycontainer.hxx> +#include <com/sun/star/lang/XUnoTunnel.hpp> +#include <comphelper/stl_types.hxx> +#include <connectivity/dbtoolsdllapi.hxx> + +namespace connectivity::sdbcx + { + + // = ODescriptor + + typedef ::comphelper::OPropertyContainer ODescriptor_PBASE; + class OOO_DLLPUBLIC_DBTOOLS ODescriptor + :public ODescriptor_PBASE + ,public css::lang::XUnoTunnel + { + protected: + OUString m_Name; + + /** helper for derived classes to implement OPropertyArrayUsageHelper::createArrayHelper + + This method just calls describeProperties, and flags all properties as READONLY if and + only if we do *not* act as descriptor, but as final object. + + @seealso isNew + */ + ::cppu::IPropertyArrayHelper* doCreateArrayHelper() const; + + private: + comphelper::UStringMixEqual m_aCase; + bool m_bNew; + + public: + ODescriptor(::cppu::OBroadcastHelper& _rBHelper, bool _bCase, bool _bNew = false); + + virtual ~ODescriptor() override; + + bool isNew() const { return m_bNew; } + void setNew(bool _bNew); + + bool isCaseSensitive() const { return m_aCase.isCaseSensitive(); } + + virtual void construct(); + + // XInterface + virtual css::uno::Any SAL_CALL queryInterface( const css::uno::Type & rType ) override; + /// @throws css::uno::RuntimeException + virtual css::uno::Sequence< css::uno::Type > SAL_CALL getTypes( ); + + // css::lang::XUnoTunnel + virtual sal_Int64 SAL_CALL getSomething( const css::uno::Sequence< sal_Int8 >& aIdentifier ) override; + static const css::uno::Sequence< sal_Int8 > & getUnoTunnelId(); + + // retrieves the ODescriptor implementation of a given UNO component, and returns its ->isNew flag + static bool isNew( const css::uno::Reference< css::uno::XInterface >& _rxDescriptor ); + }; + +} + +#endif // INCLUDED_CONNECTIVITY_SDBCX_VDESCRIPTOR_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/sdbcx/VTable.hxx b/include/connectivity/sdbcx/VTable.hxx new file mode 100644 index 000000000..6d575615f --- /dev/null +++ b/include/connectivity/sdbcx/VTable.hxx @@ -0,0 +1,142 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#ifndef INCLUDED_CONNECTIVITY_SDBCX_VTABLE_HXX +#define INCLUDED_CONNECTIVITY_SDBCX_VTABLE_HXX + +#include <com/sun/star/sdbcx/XDataDescriptorFactory.hpp> +#include <com/sun/star/sdbcx/XIndexesSupplier.hpp> +#include <com/sun/star/sdbcx/XRename.hpp> +#include <com/sun/star/sdbcx/XAlterTable.hpp> +#include <com/sun/star/sdbcx/XColumnsSupplier.hpp> +#include <com/sun/star/sdbcx/XKeysSupplier.hpp> +#include <com/sun/star/lang/XServiceInfo.hpp> +#include <comphelper/IdPropArrayHelper.hxx> +#include <cppuhelper/compbase.hxx> +#include <cppuhelper/implbase4.hxx> +#include <cppuhelper/basemutex.hxx> +#include <com/sun/star/container/XNamed.hpp> +#include <connectivity/sdbcx/IRefreshable.hxx> +#include <connectivity/sdbcx/VDescriptor.hxx> +#include <connectivity/CommonTools.hxx> +#include <connectivity/dbtoolsdllapi.hxx> + +namespace com::sun::star::sdbc { class XDatabaseMetaData; } + +namespace connectivity::sdbcx + { + + class OTable; + class OCollection; + + typedef ::cppu::WeakComponentImplHelper< css::sdbcx::XColumnsSupplier, + css::sdbcx::XKeysSupplier, + css::container::XNamed, + css::lang::XServiceInfo> OTableDescriptor_BASE; + + typedef ::cppu::ImplHelper4< css::sdbcx::XDataDescriptorFactory, + css::sdbcx::XIndexesSupplier, + css::sdbcx::XRename, + css::sdbcx::XAlterTable > OTable_BASE; + + typedef ::comphelper::OIdPropertyArrayUsageHelper<OTable> OTable_PROP; + + + class OOO_DLLPUBLIC_DBTOOLS OTable : + public cppu::BaseMutex, + public OTable_BASE, + public OTableDescriptor_BASE, + public IRefreshableColumns, + public OTable_PROP, + public ODescriptor + { + protected: + OUString m_CatalogName; + OUString m_SchemaName; + OUString m_Description; + OUString m_Type; + + // no Reference! see OCollection::acquire + std::unique_ptr<OCollection> m_xKeys; + std::unique_ptr<OCollection> m_xColumns; + std::unique_ptr<OCollection> m_xIndexes; + OCollection* m_pTables; // must hold his own container to notify him when renaming + + using OTableDescriptor_BASE::rBHelper; + + // OPropertyArrayUsageHelper + virtual ::cppu::IPropertyArrayHelper* createArrayHelper(sal_Int32 _nId ) const override; + // OPropertySetHelper + virtual ::cppu::IPropertyArrayHelper & SAL_CALL getInfoHelper() override; + public: + OTable( OCollection* _pTables, + bool _bCase); + OTable( OCollection* _pTables, + bool _bCase, + const OUString& Name, + const OUString& Type, + const OUString& Description = OUString(), + const OUString& SchemaName = OUString(), + const OUString& CatalogName = OUString()); + + virtual ~OTable() override; + + DECLARE_SERVICE_INFO(); + //XInterface + virtual void SAL_CALL acquire() noexcept override; + virtual void SAL_CALL release() noexcept override; + virtual css::uno::Any SAL_CALL queryInterface( const css::uno::Type & rType ) override; + //XTypeProvider + virtual css::uno::Sequence< css::uno::Type > SAL_CALL getTypes( ) override; + + // ODescriptor + virtual void construct() override; + virtual void refreshColumns() override; + virtual void refreshKeys(); + virtual void refreshIndexes(); + // ::cppu::OComponentHelper + virtual void SAL_CALL disposing() override; + // XPropertySet + virtual css::uno::Reference< css::beans::XPropertySetInfo > SAL_CALL getPropertySetInfo( ) override; + // XColumnsSupplier + virtual css::uno::Reference< css::container::XNameAccess > SAL_CALL getColumns( ) override; + // XKeysSupplier + virtual css::uno::Reference< css::container::XIndexAccess > SAL_CALL getKeys( ) override; + // XNamed + virtual OUString SAL_CALL getName() override; + virtual void SAL_CALL setName( const OUString& aName ) override; + // XDataDescriptorFactory + virtual css::uno::Reference< css::beans::XPropertySet > SAL_CALL createDataDescriptor() override; + // XIndexesSupplier + virtual css::uno::Reference< css::container::XNameAccess > SAL_CALL getIndexes( ) override; + // XRename + virtual void SAL_CALL rename( const OUString& newName ) override; + // XAlterTable + virtual void SAL_CALL alterColumnByName( const OUString& colName, const css::uno::Reference< css::beans::XPropertySet >& descriptor ) override; + virtual void SAL_CALL alterColumnByIndex( sal_Int32 index, const css::uno::Reference< css::beans::XPropertySet >& descriptor ) override; + + // helper method + virtual css::uno::Reference< css::sdbc::XDatabaseMetaData> getMetaData() const; + }; + +} + +#endif // INCLUDED_CONNECTIVITY_SDBCX_VTABLE_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/sdbcx/VView.hxx b/include/connectivity/sdbcx/VView.hxx new file mode 100644 index 000000000..3a7714f95 --- /dev/null +++ b/include/connectivity/sdbcx/VView.hxx @@ -0,0 +1,93 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#ifndef INCLUDED_CONNECTIVITY_SDBCX_VVIEW_HXX +#define INCLUDED_CONNECTIVITY_SDBCX_VVIEW_HXX + +#include <com/sun/star/sdbcx/XDataDescriptorFactory.hpp> +#include <com/sun/star/lang/XServiceInfo.hpp> +#include <comphelper/broadcasthelper.hxx> +#include <connectivity/CommonTools.hxx> +#include <com/sun/star/container/XNamed.hpp> +#include <connectivity/sdbcx/VDescriptor.hxx> +#include <connectivity/dbtoolsdllapi.hxx> +#include <comphelper/IdPropArrayHelper.hxx> +#include <cppuhelper/implbase.hxx> + +namespace com::sun::star::sdbc { class XDatabaseMetaData; } + +namespace connectivity::sdbcx + { + + typedef ::cppu::WeakImplHelper< css::lang::XServiceInfo, + css::container::XNamed> OView_BASE; + + + class OOO_DLLPUBLIC_DBTOOLS OView : + public ::comphelper::OMutexAndBroadcastHelper, + public OView_BASE, + public ::comphelper::OIdPropertyArrayUsageHelper<OView>, + public ODescriptor + { + protected: + OUString m_CatalogName; + OUString m_SchemaName; + OUString m_Command; + sal_Int32 m_CheckOption; + // need for the getName method + css::uno::Reference< css::sdbc::XDatabaseMetaData > m_xMetaData; + + // OPropertyArrayUsageHelper + virtual ::cppu::IPropertyArrayHelper* createArrayHelper( sal_Int32 _nId) const override; + // OPropertySetHelper + virtual ::cppu::IPropertyArrayHelper & SAL_CALL getInfoHelper() override; + + public: + DECLARE_SERVICE_INFO(); + + OView(bool _bCase,const css::uno::Reference< css::sdbc::XDatabaseMetaData >& _xMetaData); + OView( bool _bCase, + const OUString& _rName, + const css::uno::Reference< css::sdbc::XDatabaseMetaData >& _xMetaData, + const OUString& _rCommand = OUString(), + const OUString& _rSchemaName = OUString(), + const OUString& _rCatalogName = OUString()); + virtual ~OView() override; + + // ODescriptor + virtual void construct() override; + + // XInterface + virtual css::uno::Any SAL_CALL queryInterface( const css::uno::Type & rType ) override; + virtual void SAL_CALL acquire() noexcept override; + virtual void SAL_CALL release() noexcept override; + //XTypeProvider + virtual css::uno::Sequence< css::uno::Type > SAL_CALL getTypes( ) override; + // XPropertySet + virtual css::uno::Reference< css::beans::XPropertySetInfo > SAL_CALL getPropertySetInfo( ) override; + // XNamed + virtual OUString SAL_CALL getName( ) override; + virtual void SAL_CALL setName( const OUString& ) override; + }; + +} + +#endif // INCLUDED_CONNECTIVITY_SDBCX_VVIEW_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/sqlbison_exports.hxx b/include/connectivity/sqlbison_exports.hxx new file mode 100644 index 000000000..ba0dbd9c5 --- /dev/null +++ b/include/connectivity/sqlbison_exports.hxx @@ -0,0 +1,21 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + */ + +#pragma once + +#include <rtl/ustring.hxx> + +namespace connectivity { class OSQLParseNode; } +namespace connectivity { class OSQLParser; } + +OUString ConvertLikeToken(const ::connectivity::OSQLParseNode* pTokenNode, const ::connectivity::OSQLParseNode* pEscapeNode, bool bInternational); +int SQLyyparse(); +void setParser( ::connectivity::OSQLParser* ); + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/sqlerror.hxx b/include/connectivity/sqlerror.hxx new file mode 100644 index 000000000..252fe479e --- /dev/null +++ b/include/connectivity/sqlerror.hxx @@ -0,0 +1,239 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#ifndef INCLUDED_CONNECTIVITY_SQLERROR_HXX +#define INCLUDED_CONNECTIVITY_SQLERROR_HXX + +#include <com/sun/star/sdbc/SQLException.hpp> +#include <connectivity/dbtoolsdllapi.hxx> +#include <optional> +#include <memory> + +namespace connectivity +{ + + + //= ErrorCondition + + /** the type of error codes to be used in SQLExceptions + + @see css::sdbc::SQLException::ErrorCode + */ + typedef ::sal_Int32 ErrorCode; + + /** error condition values as defined in css::sdb::ErrorCondition + */ + typedef ::sal_Int32 ErrorCondition; + + + //= SQLError + + class SQLError_Impl; + + /** a class which provides helpers for working with SQLErrors + + In particular, this class provides vendor-specific error codes (where + the vendor is OpenOffice.org Base), which can be used in OOo's various + database drivers, and checked in application-level code, to properly + recognize highly specific error conditions. + + @see css::sdb::ErrorCondition + */ + class OOO_DLLPUBLIC_DBTOOLS SQLError + { + public: + SQLError(); + ~SQLError(); + + /** returns the message associated with a given error condition, after (optionally) replacing + a placeholder with a given string + + Some error messages need to contain references to runtime-dependent data (say, the + name of a concrete table in the database), which in the resource file's strings are + represented by a placeholder, namely $1$, $2, and so on. This method allows to + retrieve such an error message, and replace up to 3 placeholders with their concrete + values. + + In a non-product build, assertions will fire if the number of placeholders in the + message's resource string does not match the number of passed parameter values. + + As specified in the css::sdb::ErrorCondition type, + error messages thrown by core components of OpenOffice.org Base will contain + a standardized prefix "[OOoBase]" in every message. + + @see css::sdb::ErrorCondition + */ + OUString getErrorMessage( + const ErrorCondition _eCondition + ) const; + + /** returns the error code associated with a given error condition + + @see getErrorMessage + @see css::sdb::ErrorCondition + @see css::sdbc::SQLException::ErrorCode + */ + static ErrorCode + getErrorCode( const ErrorCondition _eCondition ); + + /** returns the prefix which is used for OpenOffice.org Base's error messages + + As specified in the css::sdb::ErrorCondition type, + error messages thrown by core components of OpenOffice.org Base will + contain a standardized prefix in every message. <code>getBaseErrorMessagePrefix</code> + returns this prefix, so clients of such error messages might decide to strip this + prefix before presenting the message to the user, or use it to determine + whether a concrete error has been raised by a OpenOffice.org core component. + */ + static const OUString& + getMessagePrefix(); + + + /** throws an SQLException describing the given error condition + + The thrown SQLException will contain the OOo-specific error code which derives + from the given error condition, and the error message associated with that condition. + + @param _eCondition + the ErrorCondition which hit you + + @param _rxContext + the context in which the error occurred. This will be filled in as + <member scope="css::uno">Exception::Context</member> member. + + @param _rParamValue1 + a runtime-dependent value which should be filled into the error message + which is associated with <arg>_eCondition</arg>, replacing the first placeholder + in this message. + + @param _rParamValue2 + a runtime-dependent value which should be filled into the error message + which is associated with <arg>_eCondition</arg>, replacing the second placeholder + in this message. + + @param _rParamValue3 + a runtime-dependent value which should be filled into the error message + which is associated with <arg>_eCondition</arg>, replacing the third placeholder + in this message. + + @see getErrorMessage + @see getErrorCode + */ + void raiseException( + const ErrorCondition _eCondition, + const css::uno::Reference< css::uno::XInterface >& _rxContext, + const std::optional<OUString>& _rParamValue1 = std::nullopt, + const std::optional<OUString>& _rParamValue2 = std::nullopt, + const std::optional<OUString>& _rParamValue3 = std::nullopt + ) const; + + /** throws an SQLException describing the given error condition + + The thrown SQLException will contain the OOo-specific error code which derives + from the given error condition, and the error message associated with that condition. + + Note: You should prefer the version of raiseException which takes + an additional Context parameter, since this allows clients of your + exception to examine where the error occurred. + + @param _eCondition + the ErrorCondition which hit you + + @see getErrorMessage + @see getErrorCode + */ + void raiseException( + const ErrorCondition _eCondition + ) const; + + /** raises a typed exception, that is, a UNO exception which is derived from + css::sdbc::SQLException + + @param _eCondition + the ErrorCondition which hit you + + @param _rxContext + the context in which the error occurred. This will be filled in as + <member scope="css::uno">Exception::Context</member> member. + + @param _rExceptionType + the type of the exception to throw. This type <em>must</em> specify + an exception class derived from css::sdbc::SQLException. + + @throws ::std::bad_cast + if <arg>_rExceptionType</arg> does not specify an exception class derived from + css::sdbc::SQLException. + + @see getErrorMessage + @see getErrorCode + */ + void raiseTypedException( + const ErrorCondition _eCondition, + const css::uno::Reference< css::uno::XInterface >& _rxContext, + const css::uno::Type& _rExceptionType + ) const; + + /** retrieves an <code>SQLException</code> object which contains information about + the given error condition + + @param _eCondition + the ErrorCondition which hit you + + @param _rxContext + the context in which the error occurred. This will be filled in as + <member scope="css::uno">Exception::Context</member> member. + + @param _rParamValue1 + a runtime-dependent value which should be filled into the error message + which is associated with <arg>_eCondition</arg>, replacing the first placeholder + in this message. + + @param _rParamValue2 + a runtime-dependent value which should be filled into the error message + which is associated with <arg>_eCondition</arg>, replacing the second placeholder + in this message. + + @param _rParamValue3 + a runtime-dependent value which should be filled into the error message + which is associated with <arg>_eCondition</arg>, replacing the third placeholder + in this message. + + @see getErrorMessage + @see getErrorCode + */ + css::sdbc::SQLException + getSQLException( + const ErrorCondition _eCondition, + const css::uno::Reference< css::uno::XInterface >& _rxContext, + const std::optional<OUString>& _rParamValue1 = std::nullopt, + const std::optional<OUString>& _rParamValue2 = std::nullopt, + const std::optional<OUString>& _rParamValue3 = std::nullopt + ) const; + + private: + std::shared_ptr< SQLError_Impl > m_pImpl; + }; + + +} // namespace connectivity + + +#endif // INCLUDED_CONNECTIVITY_SQLERROR_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/sqliterator.hxx b/include/connectivity/sqliterator.hxx new file mode 100644 index 000000000..201b31294 --- /dev/null +++ b/include/connectivity/sqliterator.hxx @@ -0,0 +1,341 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ +#ifndef INCLUDED_CONNECTIVITY_SQLITERATOR_HXX +#define INCLUDED_CONNECTIVITY_SQLITERATOR_HXX + +#include <connectivity/dbtoolsdllapi.hxx> +#include <connectivity/IParseContext.hxx> +#include <com/sun/star/sdbc/DataType.hpp> +#include <com/sun/star/sdbc/SQLException.hpp> +#include <connectivity/CommonTools.hxx> +#include <rtl/ref.hxx> + +#include <memory> +#include <optional> +#include <vector> +#include <o3tl/typed_flags_set.hxx> + +namespace com::sun::star::sdbc { class XConnection; } +namespace com::sun::star::beans { class XPropertySet; } + +namespace connectivity +{ + enum class TraversalParts + { + Parameters = 0x0001, + TableNames = 0x0002, + SelectColumns = 0x0006, // note that this includes TableNames. No SelectColumns without TableNames + + // Those are not implemented currently + // GroupColumns = 0x0008, + // OrderColumns = 0x0010, + // SelectColumns = 0x0020, + // CreateColumns = 0x0040, + + All = 0xFFFF + }; +} +namespace o3tl +{ + template<> struct typed_flags<connectivity::TraversalParts> : is_typed_flags<connectivity::TraversalParts, 0xffff> {}; +} + +namespace connectivity +{ + + class OSQLParseNode; + class OSQLParser; + + typedef ::std::pair<const OSQLParseNode*,const OSQLParseNode* > TNodePair; + + enum class OSQLStatementType { + Unknown, + Select, + Insert, + Update, + Delete, + OdbcCall, + CreateTable + }; + + struct OSQLParseTreeIteratorImpl; + + class OOO_DLLPUBLIC_DBTOOLS OSQLParseTreeIterator final + { + private: + std::optional<css::sdbc::SQLException> m_xErrors; // contains the error while iterating through the statement + const OSQLParseNode* m_pParseTree; // current ParseTree + const OSQLParser& m_rParser; // if set used for general error messages from the context + OSQLStatementType m_eStatementType; + ::rtl::Reference<OSQLColumns> m_aSelectColumns; // all columns from the Select clause + ::rtl::Reference<OSQLColumns> m_aParameters; // all parameters + ::rtl::Reference<OSQLColumns> m_aGroupColumns; // the group by columns + ::rtl::Reference<OSQLColumns> m_aOrderColumns; // the order by columns + ::rtl::Reference<OSQLColumns> m_aCreateColumns; // the columns for Create table clause + + ::std::unique_ptr< OSQLParseTreeIteratorImpl > m_pImpl; + + void traverseParameter(const OSQLParseNode* _pParseNode,const OSQLParseNode* _pColumnRef,const OUString& _aColumnName, OUString& _aTableRange, const OUString& _rColumnAlias); + // inserts a table into the map + void traverseOneTableName( OSQLTables& _rTables,const OSQLParseNode * pTableName, const OUString & rTableRange ); + void traverseSearchCondition(OSQLParseNode const * pSearchCondition); + void traverseOnePredicate( + OSQLParseNode const * pColumnRef, + OUString& aValue, + OSQLParseNode const * pParameter); + void traverseByColumnNames(const OSQLParseNode* pSelectNode, bool _bOrder); + void traverseParameters(const OSQLParseNode* pSelectNode); + + const OSQLParseNode* getTableNode( OSQLTables& _rTables, const OSQLParseNode* pTableRef, OUString& aTableRange ); + void getQualified_join( OSQLTables& _rTables, const OSQLParseNode *pTableRef, OUString& aTableRange ); + void getSelect_statement(OSQLTables& _rTables,const OSQLParseNode* pSelect); + // get all the column names of m_aSelectColumns and return in a vector sorted by a UStringMixLess that's constructed from + // isCaseSensitive() + std::vector<OUString> getSelectColumnNames() const; + // rColumnNames is expected to be sorted as returned by getSelectColumnNames + OUString getUniqueColumnName(const std::vector<OUString>& rColumnNames, const OUString & rColumnName) const; + + /** finds the column with a given name, belonging to a given table, in a given tables collection + @param _rTables + the tables collection to look in + @param rColumnName + the column name to look for + @param rTableRange + the table alias name; if empty, look in all tables + @return + the desired column object, or <NULL/> if no such column could be found + */ + static css::uno::Reference< css::beans::XPropertySet > findColumn( + const OSQLTables& _rTables, const OUString & rColumnName, OUString & rTableRange ); + + /** finds a column with a given name, belonging to a given table + @param rColumnName + the column name to look for + @param rTableRange + the table alias name; if empty, look in all tables + @param _bLookInSubTables + <TRUE/> if and only if not only our direct tables, but also our sub tables (from sub selects) + should be searched + @return + */ + css::uno::Reference< css::beans::XPropertySet > findColumn( + const OUString & rColumnName, OUString & rTableRange, bool _bLookInSubTables ); + + /** finds a column with a given name among the select columns + @param rColumnName + the column name to look for + @return + */ + css::uno::Reference< css::beans::XPropertySet > findSelectColumn( + std::u16string_view rColumnName ); + + void setSelectColumnName(const OUString& rColumnName, const OUString& rColumnAlias, const OUString& rTableRange, bool bFkt = false, sal_Int32 _nType = css::sdbc::DataType::VARCHAR, bool bAggFkt = false); + void appendColumns(const OUString& _rTableAlias, const OSQLTable& _rTable); + // Other member variables that should be available in the "set" functions + // can be defined in the derived class. They can be initialized + // in its constructor and, after the "traverse" routines have been used, + // they can be queried using other functions. + + OSQLParseTreeIterator(const OSQLParseTreeIterator & rIter) = delete; + + public: + OSQLParseTreeIterator( + const css::uno::Reference< css::sdbc::XConnection >& _rxConnection, + const css::uno::Reference< css::container::XNameAccess >& _rxTables, + const OSQLParser& _rParser ); + ~OSQLParseTreeIterator(); + + void dispose(); + bool isCaseSensitive() const; + // The parse tree to be analysed/traversed: + // If NULL is passed, the current parse tree will be deleted and the error status cleared. + void setParseTree(const OSQLParseNode * pNewParseTree); + const OSQLParseNode * getParseTree() const { return m_pParseTree; }; + + // subtrees in case of a select statement + const OSQLParseNode* getWhereTree() const; + const OSQLParseNode* getOrderTree() const; + const OSQLParseNode* getGroupByTree() const; + const OSQLParseNode* getHavingTree() const; + + const OSQLParseNode* getSimpleWhereTree() const; + const OSQLParseNode* getSimpleOrderTree() const; + const OSQLParseNode* getSimpleGroupByTree() const; + const OSQLParseNode* getSimpleHavingTree() const; + + /** returns the errors which occurred during parsing. + + The returned object contains a chain (via SQLException::NextException) of SQLExceptions. + */ + const css::sdbc::SQLException& getErrors() const { return *m_xErrors; } + bool hasErrors() const { return bool(m_xErrors); } + + // statement type (already set in setParseTree): + OSQLStatementType getStatementType() const { return m_eStatementType; } + + /** traverses the complete statement tree, and fills all our data with + the information obatined during traversal. + + Implemented by calling the single traverse* methods in the proper + order (depending on the statement type). + */ + void traverseAll(); + + // The TableRangeMap contains all tables associated with the range name found first. + const OSQLTables& getTables() const; + + const ::rtl::Reference<OSQLColumns>& getSelectColumns() const { return m_aSelectColumns;} + const ::rtl::Reference<OSQLColumns>& getGroupColumns() const { return m_aGroupColumns;} + const ::rtl::Reference<OSQLColumns>& getOrderColumns() const { return m_aOrderColumns;} + const ::rtl::Reference<OSQLColumns>& getParameters() const { return m_aParameters; } + + /** return the columname and the table range + @param _pColumnRef + The column ref parse node. + @param _rColumnName + The column name to be set. + @param _rTableRange + The table range to be set. + */ + void getColumnRange( const OSQLParseNode* _pColumnRef, + OUString &_rColumnName, + OUString& _rTableRange) const; + + /** retrieves a column's name, table range, and alias + + @param _pColumnRef + The column_ref parse node. + @param _out_rColumnName + The column name to be set. + @param _out_rTableRange + The table range to be set. + @param _out_rColumnAliasIfPresent + If the column specified by _pColumnRef is part of the select columns, and contains a column alias there, + this alias is returned here. + */ + void getColumnRange( const OSQLParseNode* _pColumnRef, + OUString& _out_rColumnName, + OUString& _out_rTableRange, + OUString& _out_rColumnAliasIfPresent + ) const; + + /** return the alias name of a column + @param _pDerivedColumn + The parse node where SQL_ISRULE(_pDerivedColumn,derived_column) must be true + @return + The alias name of the column or an empty string. + */ + static OUString getColumnAlias(const OSQLParseNode* _pDerivedColumn); + + /** return the columname and the table range + @param _pColumnRef + The column ref parse node. + @param _xMetaData + The database meta data. + @param _rColumnName + The column name to be set. + @param _rTableRange + The table range to be set. + */ + static void getColumnRange( const OSQLParseNode* _pColumnRef, + const css::uno::Reference< css::sdbc::XConnection >& _rxConnection, + OUString &_rColumnName, + OUString& _rTableRange); + + // return true when the tableNode is a rule like catalog_name, schema_name or table_name + static bool isTableNode(const OSQLParseNode* _pTableNode); + + // tries to find the correct type of the function + sal_Int32 getFunctionReturnType(const OSQLParseNode* _pNode ); + + // returns a lis of all joined columns + ::std::vector< TNodePair >& getJoinConditions() const; + + private: + + /** traverses the list of table names, and fills _rTables + */ + bool traverseTableNames( OSQLTables& _rTables ); + + /// traverses columns in a SELECT statement + bool traverseSelectColumnNames(const OSQLParseNode* pSelectNode); + /// traverses columns in a CREATE TABLE statement + void traverseCreateColumns(const OSQLParseNode* pSelectNode); + + bool traverseOrderByColumnNames(const OSQLParseNode* pSelectNode); + bool traverseGroupByColumnNames(const OSQLParseNode* pSelectNode); + + bool traverseSelectionCriteria(const OSQLParseNode* pSelectNode); + + /** constructs a new iterator, which inherits some of the settings from a parent iterator + */ + OSQLParseTreeIterator( + const OSQLParseTreeIterator& _rParentIterator, + const OSQLParser& _rParser, + const OSQLParseNode* pRoot ); + + /** creates a table object and inserts it into our tables collection + + only used when we're iterating through a CREATE TABLE statement + */ + OSQLTable impl_createTableObject( + const OUString& rTableName, const OUString& rCatalogName, const OUString& rSchemaName ); + + /** locates a record source (a table or query) with the given name + */ + OSQLTable impl_locateRecordSource( + const OUString& _rComposedName + ); + + /** implementation for both traverseAll and traverseSome + */ + void impl_traverse( TraversalParts _nIncludeMask ); + + /** retrieves the parameter columns of the given query + */ + void impl_getQueryParameterColumns( const OSQLTable& _rQuery ); + + void setOrderByColumnName(const OUString & rColumnName, OUString & rTableRange, bool bAscending); + void setGroupByColumnName(const OUString & rColumnName, OUString & rTableRange); + + /** appends an SQLException corresponding to the given error code to our error collection + + @param _eError + the code of the error which occurred + @param _pReplaceToken1 + if not <NULL/>, the first occurrence of '#' in the error message will be replaced + with the given token + @param _pReplaceToken2 + if not <NULL/>, and if _rReplaceToken1 is not <NULL/>, the second occurrence of '#' + in the error message will be replaced with _rReplaceToken2 + */ + void impl_appendError( IParseContext::ErrorCode _eError, + const OUString* _pReplaceToken1 = nullptr, const OUString* _pReplaceToken2 = nullptr ); + + /** appends an SQLException corresponding to the given error code to our error collection + */ + void impl_appendError( const css::sdbc::SQLException& _rError ); + + void impl_fillJoinConditions(const OSQLParseNode* i_pJoinCondition); + }; +} + +#endif // INCLUDED_CONNECTIVITY_SQLITERATOR_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/sqlnode.hxx b/include/connectivity/sqlnode.hxx new file mode 100644 index 000000000..3bd9327e1 --- /dev/null +++ b/include/connectivity/sqlnode.hxx @@ -0,0 +1,455 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ +#ifndef INCLUDED_CONNECTIVITY_SQLNODE_HXX +#define INCLUDED_CONNECTIVITY_SQLNODE_HXX + +#include <connectivity/dbtoolsdllapi.hxx> +#include <connectivity/dbmetadata.hxx> +#include <com/sun/star/uno/Reference.hxx> +#include <memory> +#include <set> +#include <string_view> +#include <vector> +#include <rtl/ustrbuf.hxx> + +namespace com::sun::star::lang { struct Locale; } +namespace com::sun::star::sdbc { class SQLException; } +namespace com::sun::star::sdbc { class XDatabaseMetaData; } + +namespace com::sun::star +{ + namespace beans + { + class XPropertySet; + } + namespace util + { + class XNumberFormatter; + } + namespace container + { + class XNameAccess; + } +} + +#define ORDER_BY_CHILD_POS 5 +#define TABLE_EXPRESSION_CHILD_COUNT 9 + +namespace connectivity +{ + class OSQLParser; + class IParseContext; + + enum class SQLNodeType { Rule, ListRule, CommaListRule, + Keyword, Name, + String, IntNum, ApproxNum, + Equal, Less, Great, LessEq, GreatEq, NotEqual, + Punctuation, AccessDate, Concat}; + + typedef ::std::set< OUString > QueryNameSet; + + //= SQLParseNodeParameter + + struct SQLParseNodeParameter + { + const css::lang::Locale& rLocale; + ::dbtools::DatabaseMetaData aMetaData; + OSQLParser* pParser; + std::shared_ptr< QueryNameSet > pSubQueryHistory; + css::uno::Reference< css::util::XNumberFormatter > xFormatter; + css::uno::Reference< css::beans::XPropertySet > xField; + OUString sPredicateTableAlias; + css::uno::Reference< css::container::XNameAccess > xQueries; // see bParseToSDBCLevel + const IParseContext& m_rContext; + OUString sDecSep; + bool bQuote : 1; /// should we quote identifiers? + bool bInternational : 1; /// should we internationalize keywords and placeholders? + bool bPredicate : 1; /// are we going to parse a mere predicate? + bool bParseToSDBCLevel : 1; /// should we create an SDBC-level statement (e.g. with substituted sub queries)? + + SQLParseNodeParameter( + const css::uno::Reference< css::sdbc::XConnection >& _rxConnection, + const css::uno::Reference< css::util::XNumberFormatter >& _xFormatter, + const css::uno::Reference< css::beans::XPropertySet >& _xField, + const OUString &_sPredicateTableAlias, + const css::lang::Locale& _rLocale, + const IParseContext* _pContext, + bool _bIntl, + bool _bQuote, + OUString _sDecSep, + bool _bPredicate, + bool _bParseToSDBC + ); + }; + + //= OSQLParseNode + + class OOO_DLLPUBLIC_DBTOOLS OSQLParseNode + { + friend class OSQLParser; + + std::vector< std::unique_ptr<OSQLParseNode> > + m_aChildren; + OSQLParseNode* m_pParent; // pParent for reverse linkage in the tree + OUString m_aNodeValue; // token name, or empty in case of rules, + // or OUString in case of + // OUString, INT, etc. + SQLNodeType m_eNodeType; // see above + sal_uInt32 m_nNodeID; // Rule ID (if IsRule()) + // or Token ID (if !IsRule()) + // Rule IDs and Token IDs can't + // be distinguished by their values, + // IsRule has to be used for that! + public: + enum Rule + { + UNKNOWN_RULE = 0, // ID indicating that a node is no rule with a matching Rule-enum value (see getKnownRuleID) + // we make sure it is 0 so that it is the default-constructor value of this enum + // and std::map<foo,Rule>::operator[](bar) default-inserts UNKNOWN_RULE rather than select_statement (!) + select_statement, + table_exp, + table_ref_commalist, + table_ref, + catalog_name, + schema_name, + table_name, + opt_column_commalist, + column_commalist, + column_ref_commalist, + column_ref, + opt_order_by_clause, + ordering_spec_commalist, + ordering_spec, + opt_asc_desc, + where_clause, + opt_where_clause, + search_condition, + comparison, + comparison_predicate, + between_predicate, + like_predicate, + opt_escape, + test_for_null, + scalar_exp_commalist, + scalar_exp, + parameter_ref, + parameter, + general_set_fct, + range_variable, + column, + delete_statement_positioned, + delete_statement_searched, + update_statement_positioned, + update_statement_searched, + assignment_commalist, + assignment, + values_or_query_spec, + insert_statement, + insert_atom_commalist, + insert_atom, + from_clause, + qualified_join, + cross_union, + select_sublist, + derived_column, + column_val, + set_fct_spec, + boolean_term, + boolean_primary, + num_value_exp, + join_type, + position_exp, + extract_exp, + length_exp, + char_value_fct, + odbc_call_spec, + in_predicate, + existence_test, + unique_test, + all_or_any_predicate, + named_columns_join, + join_condition, + joined_table, + boolean_factor, + sql_not, + manipulative_statement, + subquery, + value_exp_commalist, + odbc_fct_spec, + union_statement, + outer_join_type, + char_value_exp, + term, + value_exp_primary, + value_exp, + selection, + fold, + char_substring_fct, + factor, + base_table_def, + base_table_element_commalist, + data_type, + column_def, + table_node, + as_clause, + opt_as, + op_column_commalist, + table_primary_as_range_column, + datetime_primary, + concatenation, + char_factor, + bit_value_fct, + comparison_predicate_part_2, + parenthesized_boolean_value_expression, + character_string_type, + other_like_predicate_part_2, + between_predicate_part_2, + null_predicate_part_2, + cast_spec, + window_function, + rule_count // last value + }; + + // must be ascii encoding for the value + OSQLParseNode(const char* _pValueStr, + SQLNodeType _eNodeType, + sal_uInt32 _nNodeID = 0); + + OSQLParseNode(std::string_view _rValue, + SQLNodeType eNewNodeType, + sal_uInt32 nNewNodeID=0); + + OSQLParseNode(const OUString& _rValue, + SQLNodeType _eNodeType, + sal_uInt32 _nNodeID = 0); + + // copies the respective ParseNode + OSQLParseNode(const OSQLParseNode& rParseNode); + OSQLParseNode& operator=(const OSQLParseNode& rParseNode); + + bool operator==(OSQLParseNode const & rParseNode) const; + + // destructor destructs the tree recursively + virtual ~OSQLParseNode(); + + OSQLParseNode* getParent() const {return m_pParent;}; + + void setParent(OSQLParseNode* pParseNode) {m_pParent = pParseNode;}; + + size_t count() const {return m_aChildren.size();}; + inline OSQLParseNode* getChild(sal_uInt32 nPos) const; + + void append(OSQLParseNode* pNewSubTree); + void insert(sal_uInt32 nPos, OSQLParseNode* pNewSubTree); + + OSQLParseNode* replace(OSQLParseNode* pOldSubTree, OSQLParseNode* pNewSubTree); + + OSQLParseNode* removeAt(sal_uInt32 nPos); + + void replaceNodeValue(const OUString& rTableAlias,const OUString& rColumnName); + + /** parses the node to a string which can be passed to a driver's connection for execution + + Any particles of the parse tree which represent application-level features - such + as queries appearing in the FROM part - are substituted, so that the resulting statement can + be executed at an SDBC-level connection. + + @param _out_rString + is an output parameter taking the resulting SQL statement + + @param _rxConnection + the connection relative to which to parse. This must be an SDB-level connection (e.g. + support the XQueriesSupplier interface) for the method to be able to do all necessary + substitutions. + + @param _rParser + the SQLParser used to create the node. This is needed in case we need to parse + sub queries which are present in the SQL statement - those sub queries need to be parsed, + too, to check whether they contain nested sub queries. + + @param _pErrorHolder + takes the error which occurred while generating the statement, if any. Might be <NULL/>, + in this case the error is not reported back, and can only be recognized by examining the + return value. + + @return + <TRUE/> if and only if the parsing was successful.<br/> + + Currently, there's only one condition how this method can fail: If it contains a nested + query which causes a cycle. E.g., consider a statement <code>SELECT * from "foo"</code>, + where <code>foo</code> is a query defined as <code>SELECT * FROM "bar"</code>, where + <code>bar</code> is defined as <code>SELECT * FROM "foo"</code>. This statement obviously + cannot be parsed to an executable statement. + + If this method returns <FALSE/>, you're encouraged to check and handle the error in + <arg>_pErrorHolder</arg>. + */ + bool parseNodeToExecutableStatement( OUString& _out_rString, + const css::uno::Reference< css::sdbc::XConnection >& _rxConnection, + OSQLParser& _rParser, + css::sdbc::SQLException* _pErrorHolder ) const; + + void parseNodeToStr(OUString& rString, + const css::uno::Reference< css::sdbc::XConnection >& _rxConnection, + const IParseContext* pContext = nullptr, + bool _bIntl = false, + bool _bQuote= true) const; + + // quoted and internationalised + void parseNodeToPredicateStr(OUString& rString, + const css::uno::Reference< css::sdbc::XConnection >& _rxConnection, + const css::uno::Reference< css::util::XNumberFormatter > & xFormatter, + const css::lang::Locale& rIntl, + OUString _sDec, + const IParseContext* pContext = nullptr ) const; + + void parseNodeToPredicateStr(OUString& rString, + const css::uno::Reference< css::sdbc::XConnection >& _rxConnection, + const css::uno::Reference< css::util::XNumberFormatter > & xFormatter, + const css::uno::Reference< css::beans::XPropertySet > & _xField, + const OUString &_sTableAlias, + const css::lang::Locale& rIntl, + OUString strDec, + const IParseContext* pContext = nullptr ) const; + + OSQLParseNode* getByRule(OSQLParseNode::Rule eRule) const; + +#if OSL_DEBUG_LEVEL > 1 + // shows the ParseTree with tabs and linefeeds + void showParseTree( OUString& rString ) const; + void showParseTree( OUStringBuffer& _inout_rBuf, sal_uInt32 nLevel ) const; +#endif + + SQLNodeType getNodeType() const {return m_eNodeType;}; + + // RuleId returns the RuleID of the node's rule (only if IsRule()) + sal_uInt32 getRuleID() const {return m_nNodeID;} + + /** returns the ID of the rule represented by the node + If the node does not represent a rule, UNKNOWN_RULE is returned + */ + Rule getKnownRuleID() const; + + // returns the TokenId of the node's token (only if !isRule()) + sal_uInt32 getTokenID() const {return m_nNodeID;} + + // IsRule tests whether a node is a rule (NonTerminal) + // ATTENTION: rules can be leaves, for example empty lists + bool isRule() const + { return (m_eNodeType == SQLNodeType::Rule) || (m_eNodeType == SQLNodeType::ListRule) + || (m_eNodeType == SQLNodeType::CommaListRule);} + + // IsToken tests whether a Node is a Token (Terminal but not a rule) + bool isToken() const {return !isRule();} + + const OUString& getTokenValue() const {return m_aNodeValue;} + + bool isLeaf() const {return m_aChildren.empty();} + + // negate only a searchcondition, any other rule could cause a gpf + static void negateSearchCondition(OSQLParseNode*& pSearchCondition, bool bNegate=false); + + // normalize a logic form + // e.q. (a or b) and (c or d) <=> a and c or a and d or b and c or b and d + static void disjunctiveNormalForm(OSQLParseNode*& pSearchCondition); + + // Simplifies logic expressions + // a and a = a + // a or a = a + // a and ( a + b) = a + // a or a and b = a + static void absorptions(OSQLParseNode*& pSearchCondition); + + // erase unnecessary braces + static void eraseBraces(OSQLParseNode*& pSearchCondition); + + // makes the logic formula a little smaller + static void compress(OSQLParseNode*& pSearchCondition); + // return the catalog, schema and tablename from this node + // _pTableNode must be a rule of that above or a SQL_TOKEN_NAME + static bool getTableComponents(const OSQLParseNode* _pTableNode, + css::uno::Any &_rCatalog, + OUString &_rSchema, + OUString &_rTable, + const css::uno::Reference< css::sdbc::XDatabaseMetaData >& _xMetaData); + + // substitute all occurrences of :var or [name] into the dynamic parameter ? + // _pNode will be modified if parameters exists + static void substituteParameterNames(OSQLParseNode const * _pNode); + + /** return a table range when it exists. + */ + static OUString getTableRange(const OSQLParseNode* _pTableRef); + + protected: + // ParseNodeToStr concatenates all Tokens (leaves) of the ParseNodes. + void parseNodeToStr(OUString& rString, + const css::uno::Reference< css::sdbc::XConnection >& _rxConnection, + const css::uno::Reference< css::util::XNumberFormatter > & xFormatter, + const css::uno::Reference< css::beans::XPropertySet > & _xField, + const OUString &_sPredicateTableAlias, + const css::lang::Locale& rIntl, + const IParseContext* pContext, + bool _bIntl, + bool _bQuote, + OUString _sDecSep, + bool _bPredicate) const; + + private: + void impl_parseNodeToString_throw( OUStringBuffer& rString, const SQLParseNodeParameter& rParam, bool bSimple=true ) const; + void impl_parseLikeNodeToString_throw( OUStringBuffer& rString, const SQLParseNodeParameter& rParam, bool bSimple=true ) const; + void impl_parseTableRangeNodeToString_throw( OUStringBuffer& rString, const SQLParseNodeParameter& rParam ) const; + + /** parses a table_name node into a SQL statement particle. + @return + <TRUE/> if and only if parsing was successful, <FALSE/> if default handling should + be applied. + */ + bool impl_parseTableNameNodeToString_throw( OUStringBuffer& rString, const SQLParseNodeParameter& rParam ) const; + + bool addDateValue(OUStringBuffer& rString, const SQLParseNodeParameter& rParam) const; + static OUString convertDateTimeString(const SQLParseNodeParameter& rParam, const OUString& rString); + static OUString convertDateString(const SQLParseNodeParameter& rParam, std::u16string_view rString); + static OUString convertTimeString(const SQLParseNodeParameter& rParam, std::u16string_view rString); + void parseLeaf(OUStringBuffer& rString, const SQLParseNodeParameter& rParam) const; + }; + + inline OSQLParseNode* OSQLParseNode::getChild(sal_uInt32 nPos) const + { + return m_aChildren[nPos].get(); + } + + // utilities to query for a specific rule, token or punctuation + #define SQL_ISRULE(pParseNode, eRule) ((pParseNode)->isRule() && (pParseNode)->getRuleID() == OSQLParser::RuleID(OSQLParseNode::eRule)) + #define SQL_ISRULEOR2(pParseNode, e1, e2) ((pParseNode)->isRule() && ( \ + (pParseNode)->getRuleID() == OSQLParser::RuleID(OSQLParseNode::e1) || \ + (pParseNode)->getRuleID() == OSQLParser::RuleID(OSQLParseNode::e2))) + #define SQL_ISRULEOR3(pParseNode, e1, e2, e3) ((pParseNode)->isRule() && ( \ + (pParseNode)->getRuleID() == OSQLParser::RuleID(OSQLParseNode::e1) || \ + (pParseNode)->getRuleID() == OSQLParser::RuleID(OSQLParseNode::e2) || \ + (pParseNode)->getRuleID() == OSQLParser::RuleID(OSQLParseNode::e3))) + #define SQL_ISTOKEN(pParseNode, token) ((pParseNode)->isToken() && (pParseNode)->getTokenID() == SQL_TOKEN_##token) + #define SQL_ISTOKENOR2(pParseNode, tok0, tok1) ((pParseNode)->isToken() && ( (pParseNode)->getTokenID() == SQL_TOKEN_##tok0 || (pParseNode)->getTokenID() == SQL_TOKEN_##tok1 )) + #define SQL_ISTOKENOR3(pParseNode, tok0, tok1, tok2) ((pParseNode)->isToken() && ( (pParseNode)->getTokenID() == SQL_TOKEN_##tok0 || (pParseNode)->getTokenID() == SQL_TOKEN_##tok1 || (pParseNode)->getTokenID() == SQL_TOKEN_##tok2 )) + #define SQL_ISPUNCTUATION(pParseNode, aString) ((pParseNode)->getNodeType() == SQLNodeType::Punctuation && (pParseNode)->getTokenValue() == (aString)) +} + +#endif // INCLUDED_CONNECTIVITY_SQLNODE_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/sqlparse.hxx b/include/connectivity/sqlparse.hxx new file mode 100644 index 000000000..b92ff3b1c --- /dev/null +++ b/include/connectivity/sqlparse.hxx @@ -0,0 +1,230 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ +#ifndef INCLUDED_CONNECTIVITY_SQLPARSE_HXX +#define INCLUDED_CONNECTIVITY_SQLPARSE_HXX + +#include <memory> +#include <string_view> + +#include <com/sun/star/uno/Reference.h> +#include <osl/mutex.hxx> +#include <connectivity/sqlnode.hxx> +#include <connectivity/IParseContext.hxx> +#include <connectivity/dbtoolsdllapi.hxx> +#include <connectivity/sqlerror.hxx> +#include <salhelper/singletonref.hxx> + +#include <map> + +namespace com::sun::star::i18n { class XCharacterClassification; } +namespace com::sun::star::i18n { class XLocaleData4; } + +namespace com::sun::star +{ + namespace beans + { + class XPropertySet; + } + namespace util + { + class XNumberFormatter; + } +} + +namespace connectivity +{ + class OSQLScanner; + + //= OParseContext + + class OParseContext final : public IParseContext + { + public: + OParseContext(); + + virtual ~OParseContext(); + // retrieves language specific error messages + virtual OUString getErrorMessage(ErrorCode _eCodes) const override; + + // retrieves language specific keyword strings (only ASCII allowed) + virtual OString getIntlKeywordAscii(InternationalKeyCode _eKey) const override; + + // finds out, if we have an international keyword (only ASCII allowed) + virtual InternationalKeyCode getIntlKeyCode(const OString& rToken) const override; + + // determines the default international setting + static const css::lang::Locale& getDefaultLocale(); + + /** gets a locale instance which should be used when parsing in the context specified by this instance + <p>if this is not overridden by derived classes, it returns the static default locale.</p> + */ + virtual css::lang::Locale getPreferredLocale( ) const override; + }; + + // OSQLParseNodesContainer + // garbage collection of nodes + + class OSQLParseNodesContainer + { + ::osl::Mutex m_aMutex; + ::std::vector< OSQLParseNode* > m_aNodes; + public: + OSQLParseNodesContainer(); + ~OSQLParseNodesContainer(); + + void push_back(OSQLParseNode* _pNode); + void erase(OSQLParseNode* _pNode); + void clear(); + void clearAndDelete(); + }; + + typedef salhelper::SingletonRef<OSQLParseNodesContainer> OSQLParseNodesGarbageCollector; + + //= OSQLParser + + struct OSQLParser_Data + { + css::lang::Locale aLocale; + ::connectivity::SQLError aErrors; + }; + + /** Parser for SQL92 + */ + class OOO_DLLPUBLIC_DBTOOLS OSQLParser + { + friend class OSQLParseNode; + friend class OSQLInternalNode; + friend struct SQLParseNodeParameter; + + private: + typedef ::std::map< sal_uInt32, OSQLParseNode::Rule > RuleIDMap; + // static parts for parsers + static sal_uInt32 s_nRuleIDs[OSQLParseNode::rule_count + 1]; + static RuleIDMap s_aReverseRuleIDLookup; + static OParseContext s_aDefaultContext; + + static OSQLScanner* s_pScanner; + static OSQLParseNodesGarbageCollector* s_pGarbageCollector; + static sal_Int32 s_nRefCount; + + // information on the current parse action + const IParseContext* m_pContext; + std::unique_ptr<OSQLParseNode> m_pParseTree; // result from parsing + ::std::unique_ptr< OSQLParser_Data > + m_pData; + OUString m_sFieldName; // current field name for a predicate + OUString m_sErrorMessage;// current error msg + + css::uno::Reference< css::beans::XPropertySet > + m_xField; // current field + css::uno::Reference< css::util::XNumberFormatter > + m_xFormatter; // current number formatter + sal_Int32 m_nFormatKey; // numberformat, which should be used + sal_Int32 m_nDateFormatKey; + css::uno::Reference< css::uno::XComponentContext > m_xContext; + css::uno::Reference< css::i18n::XCharacterClassification> m_xCharClass; + static css::uno::Reference< css::i18n::XLocaleData4> s_xLocaleData; + + // convert a string into double trim it to scale of _nscale and then transform it back to string + OUString stringToDouble(const OUString& _rValue,sal_Int16 _nScale); + OSQLParseNode* buildDate(sal_Int32 _nType,OSQLParseNode*& pLiteral); + bool extractDate(OSQLParseNode const * pLiteral,double& _rfValue); + void killThousandSeparator(OSQLParseNode* pLiteral); + OSQLParseNode* convertNode(sal_Int32 nType, OSQLParseNode* pLiteral); + // makes a string out of a number, pLiteral will be deleted + OSQLParseNode* buildNode_STR_NUM(OSQLParseNode*& pLiteral); + OSQLParseNode* buildNode_Date(const double& fValue, sal_Int32 nType); + + static ::osl::Mutex& getMutex(); + + public: + // if NULL, a default context will be used + // the context must live as long as the parser + OSQLParser(const css::uno::Reference< css::uno::XComponentContext >& rxContext, const IParseContext* _pContext = nullptr); + ~OSQLParser(); + + // Parsing an SQLStatement + std::unique_ptr<OSQLParseNode> parseTree(OUString& rErrorMessage, + const OUString& rStatement, + bool bInternational = false); + + // Check a Predicate + // set bUseRealName to false if you pass a xField that comes from where you got that field, + // as opposed from to from yourself. + std::unique_ptr<OSQLParseNode> predicateTree(OUString& rErrorMessage, const OUString& rStatement, + const css::uno::Reference< css::util::XNumberFormatter > & xFormatter, + const css::uno::Reference< css::beans::XPropertySet > & xField, + bool bUseRealName = true); + + // Access to the context + const IParseContext& getContext() const {return *m_pContext;} + + /// access to the SQLError instance owned by this parser + const SQLError& getErrorHelper() const; + + // TokenIDToStr: token name belonging to a token number. + static OString TokenIDToStr(sal_uInt32 nTokenID, const IParseContext* pContext = nullptr); + +#if OSL_DEBUG_LEVEL > 0 + // (empty string if not found) + static OUString RuleIDToStr(sal_uInt32 nRuleID); +#endif + + // StrToRuleID calculates the RuleID for an OUString (that is, css::sdbcx::Index in yytname) + // (0 if not found). The search for an ID based on a String is + // extremely inefficient (sequential search for OUString)! + static sal_uInt32 StrToRuleID(const OString & rValue); + + static OSQLParseNode::Rule RuleIDToRule( sal_uInt32 _nRule ); + + // RuleId with enum, far more efficient + static sal_uInt32 RuleID(OSQLParseNode::Rule eRule); + // compares the _sFunctionName with all known function names and return the DataType of the return value + static sal_Int32 getFunctionReturnType(std::u16string_view _sFunctionName, const IParseContext* pContext); + + // returns the type for a parameter in a given function name + static sal_Int32 getFunctionParameterType(sal_uInt32 _nTokenId,sal_uInt32 _nPos); + + void error(const char *fmt); + static int SQLlex(); +#ifdef YYBISON + void setParseTree(OSQLParseNode * pNewParseTree); + + // Is the parse in a special mode? + // Predicate check is used to check a condition for a field + bool inPredicateCheck() const {return m_xField.is();} + const OUString& getFieldName() const {return m_sFieldName;} + + static void reduceLiteral(OSQLParseNode*& pLiteral, bool bAppendBlank); + // does not change the pLiteral argument + sal_Int16 buildNode(OSQLParseNode*& pAppend,OSQLParseNode* pCompare,OSQLParseNode* pLiteral,OSQLParseNode* pLiteral2); + + sal_Int16 buildComparisonRule(OSQLParseNode*& pAppend,OSQLParseNode* pLiteral); + // pCompre will be deleted if it is not used + sal_Int16 buildPredicateRule(OSQLParseNode*& pAppend,OSQLParseNode* const pLiteral,OSQLParseNode* pCompare,OSQLParseNode* pLiteral2 = nullptr); + + sal_Int16 buildLikeRule(OSQLParseNode* pAppend, OSQLParseNode*& pLiteral, const OSQLParseNode* pEscape); + sal_Int16 buildStringNodes(OSQLParseNode*& pLiteral); +#endif + }; +} + +#endif // INCLUDED_CONNECTIVITY_SQLPARSE_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/sqlscan.hxx b/include/connectivity/sqlscan.hxx new file mode 100644 index 000000000..fe463f506 --- /dev/null +++ b/include/connectivity/sqlscan.hxx @@ -0,0 +1,67 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ +#pragma once + +#include <connectivity/IParseContext.hxx> + +namespace connectivity +{ + + //= OSQLScanner + + /** Scanner for SQL92 + */ + class OSQLScanner + { + const IParseContext* m_pContext; // context for parse, knows all international stuff + OString m_sStatement; // statement to parse + OUString m_sErrorMessage; + + sal_Int32 m_nCurrentPos; // next position to read from the statement + bool m_bInternational; // do we have a statement which may uses + sal_Int32 m_nRule; // rule to be set + + public: + OSQLScanner(); + ~OSQLScanner(); + + sal_Int32 SQLyygetc(); + void SQLyyerror(char const *fmt); + IParseContext::InternationalKeyCode getInternationalTokenID(const char* sToken) const; + + // setting the new information before scanning + void prepareScan(const OUString & rNewStatement, const IParseContext* pContext, bool bInternational); + const OUString& getErrorMessage() const {return m_sErrorMessage;} + const OString& getStatement() const { return m_sStatement; } + + static sal_Int32 SQLlex(); + // set this as scanner for flex + void setScanner(bool _bNull=false); + // rules settings + void SetRule(sal_Int32 nRule) {m_nRule = nRule;} + static sal_Int32 GetGERRule(); + static sal_Int32 GetENGRule(); + static sal_Int32 GetSQLRule(); + static sal_Int32 GetDATERule(); + static sal_Int32 GetSTRINGRule(); + sal_Int32 GetCurrentPos() const { return m_nCurrentPos; } + }; +} + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/standardsqlstate.hxx b/include/connectivity/standardsqlstate.hxx new file mode 100644 index 000000000..2569d3a02 --- /dev/null +++ b/include/connectivity/standardsqlstate.hxx @@ -0,0 +1,57 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#ifndef INCLUDED_CONNECTIVITY_STANDARDSQLSTATE_HXX +#define INCLUDED_CONNECTIVITY_STANDARDSQLSTATE_HXX + +#include <sal/types.h> + +namespace dbtools +{ + + + /** standard SQLStates to be used with an SQLException + + Extend this list whenever you need a new state ... + + @see http://msdn.microsoft.com/library/default.asp?url=/library/en-us/odbc/htm/odbcodbc_error_codes.asp + */ + enum class StandardSQLState + { + INVALID_DESCRIPTOR_INDEX, // 07009 + INVALID_CURSOR_STATE, // 24000 + COLUMN_NOT_FOUND, // 42S22 + GENERAL_ERROR, // HY000 + INVALID_SQL_DATA_TYPE, // HY004 + FUNCTION_SEQUENCE_ERROR, // HY010 + INVALID_CURSOR_POSITION, // HY109 + FEATURE_NOT_IMPLEMENTED, // HYC00 + FUNCTION_NOT_SUPPORTED, // IM001 + CONNECTION_DOES_NOT_EXIST, // 08003 + + ERROR_UNSPECIFIED = SAL_MAX_ENUM // special value indicating that an SQLState is not to be specified + }; + + +} // namespace dbtools + + +#endif // INCLUDED_CONNECTIVITY_STANDARDSQLSTATE_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/statementcomposer.hxx b/include/connectivity/statementcomposer.hxx new file mode 100644 index 000000000..88fa61f55 --- /dev/null +++ b/include/connectivity/statementcomposer.hxx @@ -0,0 +1,105 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#ifndef INCLUDED_CONNECTIVITY_STATEMENTCOMPOSER_HXX +#define INCLUDED_CONNECTIVITY_STATEMENTCOMPOSER_HXX + +#include <rtl/ustring.hxx> + +#include <memory> +#include <connectivity/dbtoolsdllapi.hxx> + +namespace com::sun::star::sdbc { class XConnection; } +namespace com::sun::star::sdb { class XSingleSelectQueryComposer; } +namespace com::sun::star::uno { template <typename > class Reference; } + + +namespace dbtools +{ + + + //= StatementComposer + + struct StatementComposer_Data; + /** a class which is able to compose queries (SELECT statements) from a command and a command type + */ + class OOO_DLLPUBLIC_DBTOOLS StatementComposer + { + ::std::unique_ptr< StatementComposer_Data > m_pData; + + public: + /** constructs an instance + + @param _rxConnection + the connection to work with. Must not be <NULL/>. + */ + StatementComposer( + const css::uno::Reference< css::sdbc::XConnection >& _rxConnection, + const OUString& _rCommand, + const sal_Int32 _nCommandType, + const bool _bEscapeProcessing + ); + + ~StatementComposer(); + + /** controls whether or not the instance disposes its XSingleSelectQueryComposer upon + destruction + + Unless you explicitly call this method with the parameter being <TRUE/>, + the XSingleSelectQueryComposer will be disposed when the StatementComposer + instance is destroyed. + */ + void setDisposeComposer( bool _bDoDispose ); + + void setFilter( const OUString& _rFilter ); + void setHavingClause( const OUString& _rHavingClause ); + void setOrder( const OUString& _rOrder ); + + /** returns the composer which has been fed with the current settings + + @throws css::sdbc::SQLException + if such an exception occurs while creating the composer + */ + css::uno::Reference< css::sdb::XSingleSelectQueryComposer > const & + getComposer(); + + /** returns the composer statement + + Effectively, this is equivalent to calling getComposer, and asking the composer + for its Query attribute. + + @throws css::sdbc::SQLException + if such an exception occurs while creating the composer + */ + OUString + getQuery(); + + private: + StatementComposer(const StatementComposer&) = delete; + StatementComposer& operator=(const StatementComposer&) = delete; + StatementComposer() = delete; + }; + + +} // namespace dbtools + + +#endif // INCLUDED_CONNECTIVITY_STATEMENTCOMPOSER_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ diff --git a/include/connectivity/warningscontainer.hxx b/include/connectivity/warningscontainer.hxx new file mode 100644 index 000000000..7d017057b --- /dev/null +++ b/include/connectivity/warningscontainer.hxx @@ -0,0 +1,84 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + * + * This file incorporates work covered by the following license notice: + * + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed + * with this work for additional information regarding copyright + * ownership. The ASF licenses this file to you under the Apache + * License, Version 2.0 (the "License"); you may not use this file + * except in compliance with the License. You may obtain a copy of + * the License at http://www.apache.org/licenses/LICENSE-2.0 . + */ + +#ifndef INCLUDED_CONNECTIVITY_WARNINGSCONTAINER_HXX +#define INCLUDED_CONNECTIVITY_WARNINGSCONTAINER_HXX + +#include <connectivity/dbtoolsdllapi.hxx> + +#include <com/sun/star/uno/Reference.hxx> + +namespace com::sun::star::sdbc { class SQLException; } +namespace com::sun::star::sdbc { class SQLWarning; } +namespace com::sun::star::sdbc { class XWarningsSupplier; } +namespace com::sun::star::sdb { class SQLContext; } +namespace com::sun::star::uno { class XInterface; } + +namespace dbtools +{ + + /** helper class for implementing XWarningsSupplier, which mixes own warnings with + warnings obtained from an external instance + */ + class OOO_DLLPUBLIC_DBTOOLS WarningsContainer + { + private: + css::uno::Reference< css::sdbc::XWarningsSupplier > m_xExternalWarnings; + css::uno::Any m_aOwnWarnings; + + public: + WarningsContainer() {} + WarningsContainer( const css::uno::Reference< css::sdbc::XWarningsSupplier >& _rxExternalWarnings ) + :m_xExternalWarnings( _rxExternalWarnings ) {} + + void setExternalWarnings( const css::uno::Reference< css::sdbc::XWarningsSupplier >& _rxExternalWarnings ) + { + m_xExternalWarnings = _rxExternalWarnings; + } + + // convenience + /** appends an SQLWarning instance to the chain + @param _rWarning + the warning message + @param _pAsciiSQLState + the SQLState of the warning + @param _rxContext + the context of the warning + */ + void appendWarning( + const OUString& _rWarning, + const char* _pAsciiSQLState, + const css::uno::Reference< css::uno::XInterface >& _rxContext ); + + void appendWarning(const css::sdbc::SQLException& _rWarning); + void appendWarning(const css::sdbc::SQLWarning& _rWarning); + void appendWarning(const css::sdb::SQLContext& _rContext); + + // XWarningsSupplier equivalents + css::uno::Any getWarnings( ) const; + void clearWarnings( ); + }; + + +} // namespace dbtools + + +#endif // INCLUDED_CONNECTIVITY_WARNINGSCONTAINER_HXX + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ |