xref: /AOO41X/main/connectivity/source/drivers/adabas/BUser.cxx (revision 1ecadb572e7010ff3b3382ad9bf179dbc6efadbb)
1 /*************************************************************************
2  *
3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4  *
5  * Copyright 2000, 2010 Oracle and/or its affiliates.
6  *
7  * OpenOffice.org - a multi-platform office productivity suite
8  *
9  * This file is part of OpenOffice.org.
10  *
11  * OpenOffice.org is free software: you can redistribute it and/or modify
12  * it under the terms of the GNU Lesser General Public License version 3
13  * only, as published by the Free Software Foundation.
14  *
15  * OpenOffice.org is distributed in the hope that it will be useful,
16  * but WITHOUT ANY WARRANTY; without even the implied warranty of
17  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18  * GNU Lesser General Public License version 3 for more details
19  * (a copy is included in the LICENSE file that accompanied this code).
20  *
21  * You should have received a copy of the GNU Lesser General Public License
22  * version 3 along with OpenOffice.org.  If not, see
23  * <http://www.openoffice.org/license.html>
24  * for a copy of the LGPLv3 License.
25  *
26  ************************************************************************/
27 
28 // MARKER(update_precomp.py): autogen include statement, do not remove
29 #include "precompiled_connectivity.hxx"
30 #include "adabas/BUser.hxx"
31 #include "adabas/BGroups.hxx"
32 #include <com/sun/star/sdbc/XRow.hpp>
33 #include <com/sun/star/sdbc/XResultSet.hpp>
34 #include "adabas/BConnection.hxx"
35 #include "connectivity/dbtools.hxx"
36 #include "connectivity/dbexception.hxx"
37 #include <com/sun/star/sdbcx/Privilege.hpp>
38 #include <com/sun/star/sdbcx/PrivilegeObject.hpp>
39 #include "resource/adabas_res.hrc"
40 
41 using namespace connectivity::adabas;
42 using namespace ::com::sun::star::uno;
43 using namespace ::com::sun::star::beans;
44 using namespace ::com::sun::star::sdbcx;
45 using namespace ::com::sun::star::sdbc;
46 using namespace ::com::sun::star::container;
47 using namespace ::com::sun::star::lang;
48 // -------------------------------------------------------------------------
49 OAdabasUser::OAdabasUser(	OAdabasConnection* _pConnection) : connectivity::sdbcx::OUser(sal_True)
50 				,m_pConnection(_pConnection)
51 {
52 	construct();
53 }
54 // -------------------------------------------------------------------------
55 OAdabasUser::OAdabasUser(   OAdabasConnection* _pConnection,
56 				const ::rtl::OUString& _Name
57 			) : connectivity::sdbcx::OUser(_Name,sal_True)
58 				,m_pConnection(_pConnection)
59 {
60 	construct();
61 }
62 // -------------------------------------------------------------------------
63 void OAdabasUser::refreshGroups()
64 {
65 	if(!m_pConnection)
66 		return;
67 
68 	TStringVector aVector;
69 	aVector.reserve(7); // we don't know the excatly count of users but this should fit the normal need
70 	Reference< XStatement > xStmt = m_pConnection->createStatement(  );
71 	::rtl::OUString aSql = ::rtl::OUString::createFromAscii("SELECT DISTINCT GROUPNAME FROM DOMAIN.USERS WHERE GROUPNAME IS NOT NULL AND GROUPNAME <> ' ' AND USERNAME = '");
72 	aSql += getName( );
73 	aSql += ::rtl::OUString::createFromAscii("'");
74 
75     Reference< XResultSet > xResult = xStmt->executeQuery(aSql);
76 	if(xResult.is())
77 	{
78                 Reference< XRow > xRow(xResult,UNO_QUERY);
79 		while(xResult->next())
80 			aVector.push_back(xRow->getString(1));
81 		::comphelper::disposeComponent(xResult);
82 	}
83 	::comphelper::disposeComponent(xStmt);
84 
85 	if(m_pGroups)
86 		m_pGroups->reFill(aVector);
87 	else
88 		m_pGroups = new OGroups(*this,m_aMutex,aVector,m_pConnection,this);
89 }
90 // -------------------------------------------------------------------------
91 OUserExtend::OUserExtend(	OAdabasConnection* _pConnection) : OAdabasUser(_pConnection)
92 {
93 	construct();
94 }
95 // -------------------------------------------------------------------------
96 typedef connectivity::sdbcx::OUser	OUser_TYPEDEF;
97 void OUserExtend::construct()
98 {
99 
100 	registerProperty(OMetaConnection::getPropMap().getNameByIndex(PROPERTY_ID_PASSWORD),	PROPERTY_ID_PASSWORD,0,&m_Password,::getCppuType(reinterpret_cast< ::rtl::OUString*>(NULL)));
101 }
102 // -----------------------------------------------------------------------------
103 cppu::IPropertyArrayHelper* OUserExtend::createArrayHelper() const
104 {
105 	Sequence< Property > aProps;
106 	describeProperties(aProps);
107 	return new cppu::OPropertyArrayHelper(aProps);
108 }
109 // -------------------------------------------------------------------------
110 cppu::IPropertyArrayHelper & OUserExtend::getInfoHelper()
111 {
112 	return *OUserExtend_PROP::getArrayHelper();
113 }
114 typedef connectivity::sdbcx::OUser_BASE OUser_BASE_RBHELPER;
115 // -----------------------------------------------------------------------------
116 sal_Int32 SAL_CALL OAdabasUser::getPrivileges( const ::rtl::OUString& objName, sal_Int32 objType ) throw(SQLException, RuntimeException)
117 {
118     if ( objType != PrivilegeObject::TABLE )
119         return 0;
120 
121 	::osl::MutexGuard aGuard(m_aMutex);
122 	checkDisposed(OUser_BASE_RBHELPER::rBHelper.bDisposed);
123 
124 	sal_Int32 nRights,nRightsWithGrant;
125 	getAnyTablePrivileges(objName,nRights,nRightsWithGrant);
126 	return nRights;
127 }
128 // -----------------------------------------------------------------------------
129 void OAdabasUser::getAnyTablePrivileges(const ::rtl::OUString& objName, sal_Int32& nRights,sal_Int32& nRightsWithGrant) throw(SQLException, RuntimeException)
130 {
131 	nRightsWithGrant = nRights = 0;
132 	// first we need to create the sql stmt to select the privs
133 	Reference<XDatabaseMetaData> xMeta = m_pConnection->getMetaData();
134 	::rtl::OUString sCatalog,sSchema,sTable;
135 	::dbtools::qualifiedNameComponents(xMeta,objName,sCatalog,sSchema,sTable,::dbtools::eInDataManipulation);
136 	Reference<XStatement> xStmt = m_pConnection->createStatement();
137 	::rtl::OUString sSql = ::rtl::OUString::createFromAscii("SELECT REFTABLENAME,PRIVILEGES FROM DOMAIN.USR_USES_TAB WHERE REFOBJTYPE <> 'SYSTEM' AND DEFUSERNAME = '");
138 	sSql += m_Name;
139 	sSql += ::rtl::OUString::createFromAscii("' AND REFTABLENAME = '");
140 	sSql += sTable;
141 	sSql += ::rtl::OUString::createFromAscii("'");
142 	if(xStmt.is())
143 	{
144 		Reference<XResultSet> xRes = xStmt->executeQuery(sSql);
145 		if(xRes.is())
146 		{
147 			Reference<XRow> xRow(xRes,UNO_QUERY);
148 			if(xRow.is() && xRes->next())
149 			{
150 				::rtl::OUString sPrivs = xRow->getString(2);
151 
152                 struct _priv_nam
153                 {
154                     const sal_Char* pAsciiName;
155                     sal_Int32       nNumericValue;
156                 } privileges[] =
157                 {
158                     { "INS", Privilege::INSERT },
159                     { "DEL", Privilege::DELETE },
160                     { "UPD", Privilege::UPDATE },
161                     { "ALT", Privilege::ALTER },
162                     { "SEL", Privilege::SELECT },
163                     { "REF", Privilege::REFERENCE }
164                 };
165                 for ( size_t i = 0; i < sizeof( privileges ) / sizeof( privileges[0] ); ++i )
166                 {
167                     sal_Int32 nIndex = sPrivs.indexOf( ::rtl::OUString::createFromAscii( privileges[i].pAsciiName ) );
168                     if ( nIndex == -1 )
169                         continue;
170 
171                     nRights |= privileges[i].nNumericValue;
172                     if ( sPrivs.copy( nIndex + 2, 1 ).equalsAscii( "+" ) )
173                         nRightsWithGrant |= privileges[i].nNumericValue;
174                 }
175 			}
176 			::comphelper::disposeComponent(xRes);
177 		}
178 		::comphelper::disposeComponent(xStmt);
179 	}
180 }
181 // -------------------------------------------------------------------------
182 sal_Int32 SAL_CALL OAdabasUser::getGrantablePrivileges( const ::rtl::OUString& objName, sal_Int32 objType ) throw(SQLException, RuntimeException)
183 {
184     if ( objType != PrivilegeObject::TABLE )
185         return 0;
186 
187 	::osl::MutexGuard aGuard(m_aMutex);
188 	checkDisposed(OUser_BASE_RBHELPER::rBHelper.bDisposed);
189 
190 	sal_Int32 nRights,nRightsWithGrant;
191 	getAnyTablePrivileges(objName,nRights,nRightsWithGrant);
192 	return nRightsWithGrant;
193 }
194 // -------------------------------------------------------------------------
195 void SAL_CALL OAdabasUser::grantPrivileges( const ::rtl::OUString& objName, sal_Int32 objType, sal_Int32 objPrivileges ) throw(SQLException, RuntimeException)
196 {
197     if ( objType != PrivilegeObject::TABLE )
198         m_pConnection->throwGenericSQLException(STR_PRIVILEGE_NOT_GRANTED,*this);
199 
200 	::osl::MutexGuard aGuard(m_aMutex);
201 	::rtl::OUString sPrivs = getPrivilegeString(objPrivileges);
202 	if(sPrivs.getLength())
203 	{
204 		::rtl::OUString sGrant;
205 		sGrant += ::rtl::OUString::createFromAscii("GRANT ");
206 		sGrant += sPrivs;
207 		sGrant += ::rtl::OUString::createFromAscii(" ON ");
208 		Reference<XDatabaseMetaData> xMeta = m_pConnection->getMetaData();
209 		sGrant += ::dbtools::quoteTableName(xMeta,objName,::dbtools::eInDataManipulation);
210 		sGrant += ::rtl::OUString::createFromAscii(" TO ");
211 		sGrant += m_Name;
212 
213 		Reference<XStatement> xStmt = m_pConnection->createStatement();
214 		if(xStmt.is())
215 			xStmt->execute(sGrant);
216 		::comphelper::disposeComponent(xStmt);
217 	}
218 }
219 // -------------------------------------------------------------------------
220 void SAL_CALL OAdabasUser::revokePrivileges( const ::rtl::OUString& objName, sal_Int32 objType, sal_Int32 objPrivileges ) throw(SQLException, RuntimeException)
221 {
222     if ( objType != PrivilegeObject::TABLE )
223         m_pConnection->throwGenericSQLException(STR_PRIVILEGE_NOT_REVOKED,*this);
224 
225 	::osl::MutexGuard aGuard(m_aMutex);
226 	checkDisposed(OUser_BASE_RBHELPER::rBHelper.bDisposed);
227     ::rtl::OUString sPrivs = getPrivilegeString(objPrivileges);
228 	if(sPrivs.getLength())
229 	{
230 		::rtl::OUString sGrant;
231 		sGrant += ::rtl::OUString::createFromAscii("REVOKE ");
232 		sGrant += sPrivs;
233 		sGrant += ::rtl::OUString::createFromAscii(" ON ");
234 		Reference<XDatabaseMetaData> xMeta = m_pConnection->getMetaData();
235 		sGrant += ::dbtools::quoteTableName(xMeta,objName,::dbtools::eInDataManipulation);
236 		sGrant += ::rtl::OUString::createFromAscii(" FROM ");
237 		sGrant += m_Name;
238 
239 		Reference<XStatement> xStmt = m_pConnection->createStatement();
240 		if(xStmt.is())
241 			xStmt->execute(sGrant);
242 		::comphelper::disposeComponent(xStmt);
243 	}
244 }
245 // -----------------------------------------------------------------------------
246 // XUser
247 void SAL_CALL OAdabasUser::changePassword( const ::rtl::OUString& objPassword, const ::rtl::OUString& newPassword ) throw(SQLException, RuntimeException)
248 {
249 	::osl::MutexGuard aGuard(m_aMutex);
250 	checkDisposed(OUser_BASE_RBHELPER::rBHelper.bDisposed);
251 	::rtl::OUString sAlterPwd;
252 	sAlterPwd = ::rtl::OUString::createFromAscii("ALTER PASSWORD \"");
253 	sAlterPwd += objPassword.toAsciiUpperCase();
254 	sAlterPwd += ::rtl::OUString::createFromAscii("\" TO \"") ;
255 	sAlterPwd += newPassword.toAsciiUpperCase();
256 	sAlterPwd += ::rtl::OUString::createFromAscii("\"") ;
257 
258 	sal_Bool bDisposeConnection = sal_False;
259 	Reference<XConnection> xConnection = m_pConnection;
260 	if(m_pConnection->getMetaData()->getUserName() != m_Name)
261 	{
262 		OAdabasConnection* pNewConnection = new OAdabasConnection(m_pConnection->getDriverHandle(),m_pConnection->getDriver());
263 		xConnection = pNewConnection;
264 		if(pNewConnection)
265 		{
266 			Sequence< PropertyValue> aSeq(2);
267 			aSeq.getArray()[0].Name		= ::rtl::OUString::createFromAscii("user") ;
268 			aSeq.getArray()[0].Value	<<= m_Name;
269 			aSeq.getArray()[1].Name		= ::rtl::OUString::createFromAscii("password") ;
270 			aSeq.getArray()[1].Value	<<= objPassword;
271 			pNewConnection->Construct(m_pConnection->getMetaData()->getURL(),aSeq);
272 		}
273 		bDisposeConnection = sal_True;
274 	}
275 	if(xConnection.is())
276 	{
277 		Reference<XStatement> xStmt = xConnection->createStatement();
278 		if(xStmt.is())
279 			xStmt->execute(sAlterPwd);
280 		::comphelper::disposeComponent(xStmt);
281 		if(bDisposeConnection)
282 			::comphelper::disposeComponent(xConnection);
283 	}
284 	else
285 		::dbtools::throwFunctionSequenceException(*this);
286 }
287 // -----------------------------------------------------------------------------
288 ::rtl::OUString OAdabasUser::getPrivilegeString(sal_Int32 nRights) const
289 {
290 	::rtl::OUString sPrivs;
291 	if((nRights & Privilege::INSERT) == Privilege::INSERT)
292 		sPrivs += ::rtl::OUString::createFromAscii("INSERT");
293 
294 	if((nRights & Privilege::DELETE) == Privilege::DELETE)
295 	{
296 		if(sPrivs.getLength())
297 			sPrivs += ::rtl::OUString::createFromAscii(",");
298 		sPrivs += ::rtl::OUString::createFromAscii("DELETE");
299 	}
300 
301 	if((nRights & Privilege::UPDATE) == Privilege::UPDATE)
302 	{
303 		if(sPrivs.getLength())
304 			sPrivs += ::rtl::OUString::createFromAscii(",");
305 		sPrivs += ::rtl::OUString::createFromAscii("UPDATE");
306 	}
307 
308 	if((nRights & Privilege::ALTER) == Privilege::ALTER)
309 	{
310 		if(sPrivs.getLength())
311 			sPrivs += ::rtl::OUString::createFromAscii(",");
312 		sPrivs += ::rtl::OUString::createFromAscii("ALTER");
313 	}
314 
315 	if((nRights & Privilege::SELECT) == Privilege::SELECT)
316 	{
317 		if(sPrivs.getLength())
318 			sPrivs += ::rtl::OUString::createFromAscii(",");
319 		sPrivs += ::rtl::OUString::createFromAscii("SELECT");
320 	}
321 
322 	if((nRights & Privilege::REFERENCE) == Privilege::REFERENCE)
323 	{
324 		if(sPrivs.getLength())
325 			sPrivs += ::rtl::OUString::createFromAscii(",");
326 		sPrivs += ::rtl::OUString::createFromAscii("REFERENCES");
327 	}
328 
329 	return sPrivs;
330 }
331 // -----------------------------------------------------------------------------
332 
333