001/* 002 * This library is part of OpenCms - 003 * the Open Source Content Management System 004 * 005 * Copyright (c) Alkacon Software GmbH & Co. KG (http://www.alkacon.com) 006 * 007 * This library is free software; you can redistribute it and/or 008 * modify it under the terms of the GNU Lesser General Public 009 * License as published by the Free Software Foundation; either 010 * version 2.1 of the License, or (at your option) any later version. 011 * 012 * This library is distributed in the hope that it will be useful, 013 * but WITHOUT ANY WARRANTY; without even the implied warranty of 014 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 015 * Lesser General Public License for more details. 016 * 017 * For further information about Alkacon Software GmbH & Co. KG, please see the 018 * company website: http://www.alkacon.com 019 * 020 * For further information about OpenCms, please see the 021 * project website: http://www.opencms.org 022 * 023 * You should have received a copy of the GNU Lesser General Public 024 * License along with this library; if not, write to the Free Software 025 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 026 */ 027 028package org.opencms.db.generic; 029 030import org.opencms.configuration.CmsConfigurationManager; 031import org.opencms.configuration.CmsParameterConfiguration; 032import org.opencms.db.CmsDbContext; 033import org.opencms.db.CmsDbEntryAlreadyExistsException; 034import org.opencms.db.CmsDbEntryNotFoundException; 035import org.opencms.db.CmsDbIoException; 036import org.opencms.db.CmsDbSqlException; 037import org.opencms.db.CmsDbUtil; 038import org.opencms.db.CmsDriverManager; 039import org.opencms.db.CmsUserSettings; 040import org.opencms.db.CmsVisitEntryFilter; 041import org.opencms.db.I_CmsProjectDriver; 042import org.opencms.db.I_CmsUserDriver; 043import org.opencms.file.CmsDataAccessException; 044import org.opencms.file.CmsFolder; 045import org.opencms.file.CmsGroup; 046import org.opencms.file.CmsProject; 047import org.opencms.file.CmsProperty; 048import org.opencms.file.CmsPropertyDefinition; 049import org.opencms.file.CmsResource; 050import org.opencms.file.CmsResourceFilter; 051import org.opencms.file.CmsUser; 052import org.opencms.file.CmsUserSearchParameters; 053import org.opencms.file.CmsVfsResourceNotFoundException; 054import org.opencms.file.types.CmsResourceTypeFolder; 055import org.opencms.i18n.CmsEncoder; 056import org.opencms.i18n.CmsLocaleManager; 057import org.opencms.i18n.CmsMessageContainer; 058import org.opencms.main.CmsEvent; 059import org.opencms.main.CmsException; 060import org.opencms.main.CmsInitException; 061import org.opencms.main.CmsLog; 062import org.opencms.main.I_CmsEventListener; 063import org.opencms.main.OpenCms; 064import org.opencms.monitor.CmsMemoryMonitor; 065import org.opencms.relations.CmsRelation; 066import org.opencms.relations.CmsRelationFilter; 067import org.opencms.relations.CmsRelationType; 068import org.opencms.security.CmsAccessControlEntry; 069import org.opencms.security.CmsOrganizationalUnit; 070import org.opencms.security.CmsPasswordEncryptionException; 071import org.opencms.security.CmsRole; 072import org.opencms.security.I_CmsPrincipal; 073import org.opencms.util.CmsDataTypeUtil; 074import org.opencms.util.CmsMacroResolver; 075import org.opencms.util.CmsPair; 076import org.opencms.util.CmsStringUtil; 077import org.opencms.util.CmsUUID; 078 079import java.io.IOException; 080import java.security.MessageDigest; 081import java.security.NoSuchAlgorithmException; 082import java.sql.Connection; 083import java.sql.PreparedStatement; 084import java.sql.ResultSet; 085import java.sql.SQLException; 086import java.util.ArrayList; 087import java.util.Collections; 088import java.util.HashMap; 089import java.util.Iterator; 090import java.util.List; 091import java.util.Locale; 092import java.util.Map; 093import java.util.Map.Entry; 094import java.util.concurrent.locks.Lock; 095 096import org.apache.commons.logging.Log; 097 098import com.google.common.util.concurrent.Striped; 099 100/** 101 * Generic (ANSI-SQL) database server implementation of the user driver methods.<p> 102 * 103 * @since 6.0.0 104 */ 105public class CmsUserDriver implements I_CmsUserDriver { 106 107 /** The root path for organizational units. */ 108 public static final String ORGUNIT_BASE_FOLDER = "/system/orgunits/"; 109 110 /** The internal request attribute to indicate that the password has not to be digested. */ 111 public static final String REQ_ATTR_DONT_DIGEST_PASSWORD = "DONT_DIGEST_PASSWORD"; 112 113 // TODO: remove all these constants 114 /** Attribute WRITE USER_ADDINFO. */ 115 private static final String ATTRIBUTE_USERADDINFO = "A_USERADDINFO"; 116 117 /** Attribute WRITE USER_ADDINFO value delete. */ 118 private static final String ATTRIBUTE_USERADDINFO_VALUE_DELETE = "delete"; 119 120 /** Attribute WRITE USER_ADDINFO value insert. */ 121 private static final String ATTRIBUTE_USERADDINFO_VALUE_INSERT = "insert"; 122 123 /** Attribute WRITE USER_ADDINFO value update. */ 124 private static final String ATTRIBUTE_USERADDINFO_VALUE_UPDATE = "update"; 125 126 /** The log object for this class. */ 127 private static final Log LOG = CmsLog.getLog(org.opencms.db.generic.CmsUserDriver.class); 128 129 /** The name of the offline project. */ 130 private static final String OFFLINE_PROJECT_NAME = "Offline"; 131 132 /** Property for the organizational unit description. */ 133 private static final String ORGUNIT_PROPERTY_DESCRIPTION = CmsPropertyDefinition.PROPERTY_DESCRIPTION; 134 135 /** Property for the organizational unit default project id. */ 136 private static final String ORGUNIT_PROPERTY_PROJECTID = CmsPropertyDefinition.PROPERTY_KEYWORDS; 137 138 /** Striped lock used to synchronize writing of additional infos for users. */ 139 private static Striped<Lock> USER_INFO_LOCKS = Striped.lock(16); 140 141 /** A digest to encrypt the passwords. */ 142 protected MessageDigest m_digest; 143 144 /** The algorithm used to encode passwords. */ 145 protected String m_digestAlgorithm; 146 147 /** The file.encoding to code passwords after encryption with digest. */ 148 protected String m_digestFileEncoding; 149 150 /** The driver manager. */ 151 protected CmsDriverManager m_driverManager; 152 153 /** The SQL manager. */ 154 protected CmsSqlManager m_sqlManager; 155 156 /** 157 * @see org.opencms.db.I_CmsUserDriver#addResourceToOrganizationalUnit(org.opencms.db.CmsDbContext, org.opencms.security.CmsOrganizationalUnit, org.opencms.file.CmsResource) 158 */ 159 public void addResourceToOrganizationalUnit(CmsDbContext dbc, CmsOrganizationalUnit orgUnit, CmsResource resource) 160 throws CmsDataAccessException { 161 162 try { 163 // check if the resource is a folder 164 if (resource.isFile()) { 165 throw new CmsDataAccessException( 166 Messages.get().container( 167 Messages.ERR_ORGUNIT_RESOURCE_IS_NOT_FOLDER_2, 168 orgUnit.getName(), 169 dbc.removeSiteRoot(resource.getRootPath()))); 170 } 171 172 // read the resource representing the organizational unit 173 CmsResource ouResource = m_driverManager.readResource( 174 dbc, 175 ORGUNIT_BASE_FOLDER + orgUnit.getName(), 176 CmsResourceFilter.ALL); 177 178 // get the associated resources 179 List<String> vfsPaths = new ArrayList<String>(internalResourcesForOrgUnit(dbc, ouResource)); 180 181 // check resource scope for non root ous 182 if (orgUnit.getParentFqn() != null) { 183 // get the parent ou 184 CmsOrganizationalUnit parentOu = m_driverManager.readOrganizationalUnit(dbc, orgUnit.getParentFqn()); 185 // validate 186 internalValidateResourceForOrgUnit(dbc, parentOu, resource.getRootPath()); 187 } else { 188 // allow to set the first resource 189 if (!vfsPaths.isEmpty()) { 190 throw new CmsDataAccessException( 191 org.opencms.security.Messages.get().container( 192 org.opencms.security.Messages.ERR_ORGUNIT_ROOT_EDITION_0)); 193 } 194 } 195 196 // add the new resource 197 CmsRelation relation = new CmsRelation(ouResource, resource, CmsRelationType.OU_RESOURCE); 198 m_driverManager.getVfsDriver(dbc).createRelation(dbc, dbc.currentProject().getUuid(), relation); 199 m_driverManager.getVfsDriver(dbc).createRelation(dbc, CmsProject.ONLINE_PROJECT_ID, relation); 200 201 try { 202 // be sure the project was not deleted 203 CmsProject project = m_driverManager.readProject(dbc, orgUnit.getProjectId()); 204 // maintain the default project synchronized 205 m_driverManager.getProjectDriver(dbc).createProjectResource( 206 dbc, 207 orgUnit.getProjectId(), 208 resource.getRootPath()); 209 210 OpenCms.fireCmsEvent( 211 I_CmsEventListener.EVENT_PROJECT_MODIFIED, 212 Collections.<String, Object> singletonMap("project", project)); 213 } catch (CmsDbEntryNotFoundException e) { 214 // ignore 215 } finally { 216 // fire a resource modification event 217 Map<String, Object> data = new HashMap<String, Object>(2); 218 data.put(I_CmsEventListener.KEY_RESOURCE, ouResource); 219 data.put(I_CmsEventListener.KEY_CHANGE, Integer.valueOf(CmsDriverManager.CHANGED_RESOURCE)); 220 OpenCms.fireCmsEvent(new CmsEvent(I_CmsEventListener.EVENT_RESOURCE_MODIFIED, data)); 221 } 222 } catch (CmsException e) { 223 throw new CmsDataAccessException(e.getMessageContainer(), e); 224 } 225 } 226 227 /** 228 * @see org.opencms.db.I_CmsUserDriver#countUsers(org.opencms.db.CmsDbContext, org.opencms.file.CmsUserSearchParameters) 229 */ 230 public long countUsers(CmsDbContext dbc, CmsUserSearchParameters searchParams) throws CmsDataAccessException { 231 232 CmsPair<String, List<Object>> queryAndParams = createUserQuery(searchParams, true); 233 ResultSet res = null; 234 PreparedStatement stmt = null; 235 Connection conn = null; 236 try { 237 conn = m_sqlManager.getConnection(dbc); 238 stmt = m_sqlManager.getPreparedStatementForSql(conn, queryAndParams.getFirst()); 239 CmsDbUtil.fillParameters(stmt, queryAndParams.getSecond()); 240 res = stmt.executeQuery(); 241 long result = 0; 242 while (res.next()) { 243 result = res.getLong(1); 244 } 245 return result; 246 } catch (SQLException e) { 247 throw new CmsDbSqlException( 248 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 249 e); 250 } finally { 251 m_sqlManager.closeAll(dbc, conn, stmt, res); 252 } 253 254 } 255 256 /** 257 * @see org.opencms.db.I_CmsUserDriver#createAccessControlEntry(org.opencms.db.CmsDbContext, org.opencms.file.CmsProject, org.opencms.util.CmsUUID, org.opencms.util.CmsUUID, int, int, int) 258 */ 259 public void createAccessControlEntry( 260 CmsDbContext dbc, 261 CmsProject project, 262 CmsUUID resource, 263 CmsUUID principal, 264 int allowed, 265 int denied, 266 int flags) 267 throws CmsDataAccessException { 268 269 PreparedStatement stmt = null; 270 Connection conn = null; 271 272 try { 273 conn = m_sqlManager.getConnection(dbc); 274 stmt = m_sqlManager.getPreparedStatement(conn, project, "C_ACCESS_CREATE_5"); 275 276 stmt.setString(1, resource.toString()); 277 stmt.setString(2, principal.toString()); 278 stmt.setInt(3, allowed); 279 stmt.setInt(4, denied); 280 stmt.setInt(5, flags); 281 282 stmt.executeUpdate(); 283 } catch (SQLException e) { 284 throw new CmsDbSqlException( 285 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 286 e); 287 } finally { 288 m_sqlManager.closeAll(dbc, conn, stmt, null); 289 } 290 } 291 292 /** 293 * @see org.opencms.db.I_CmsUserDriver#createGroup(org.opencms.db.CmsDbContext, org.opencms.util.CmsUUID, java.lang.String, java.lang.String, int, java.lang.String) 294 */ 295 public CmsGroup createGroup( 296 CmsDbContext dbc, 297 CmsUUID groupId, 298 String groupFqn, 299 String description, 300 int flags, 301 String parentGroupFqn) 302 throws CmsDataAccessException { 303 304 CmsUUID parentId = CmsUUID.getNullUUID(); 305 CmsGroup group = null; 306 Connection conn = null; 307 PreparedStatement stmt = null; 308 309 if (existsGroup(dbc, groupFqn)) { 310 CmsMessageContainer message = Messages.get().container( 311 Messages.ERR_GROUP_WITH_NAME_ALREADY_EXISTS_1, 312 groupFqn); 313 if (LOG.isErrorEnabled()) { 314 LOG.error(message.key()); 315 } 316 throw new CmsDbEntryAlreadyExistsException(message); 317 } 318 319 try { 320 // get the id of the parent group if necessary 321 if (CmsStringUtil.isNotEmpty(parentGroupFqn)) { 322 parentId = readGroup(dbc, parentGroupFqn).getId(); 323 } 324 325 conn = getSqlManager().getConnection(dbc); 326 stmt = m_sqlManager.getPreparedStatement(conn, "C_GROUPS_CREATE_GROUP_6"); 327 328 // write new group to the database 329 stmt.setString(1, groupId.toString()); 330 stmt.setString(2, parentId.toString()); 331 stmt.setString(3, CmsOrganizationalUnit.getSimpleName(groupFqn)); 332 stmt.setString(4, m_sqlManager.validateEmpty(description)); 333 stmt.setInt(5, flags); 334 stmt.setString(6, CmsOrganizationalUnit.SEPARATOR + CmsOrganizationalUnit.getParentFqn(groupFqn)); 335 stmt.executeUpdate(); 336 337 group = new CmsGroup(groupId, parentId, groupFqn, description, flags); 338 } catch (SQLException e) { 339 throw new CmsDbSqlException( 340 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 341 e); 342 } finally { 343 m_sqlManager.closeAll(dbc, conn, stmt, null); 344 } 345 346 return group; 347 } 348 349 /** 350 * @see org.opencms.db.I_CmsUserDriver#createOrganizationalUnit(org.opencms.db.CmsDbContext, java.lang.String, java.lang.String, int, org.opencms.security.CmsOrganizationalUnit, String) 351 */ 352 public CmsOrganizationalUnit createOrganizationalUnit( 353 CmsDbContext dbc, 354 String name, 355 String description, 356 int flags, 357 CmsOrganizationalUnit parent, 358 String associatedResource) 359 throws CmsDataAccessException { 360 361 // check the parent 362 if ((parent == null) && !name.equals("")) { 363 throw new CmsDataAccessException( 364 org.opencms.db.Messages.get().container(org.opencms.db.Messages.ERR_PARENT_ORGUNIT_NULL_0)); 365 } 366 try { 367 // get the parent ou folder 368 CmsResource parentFolder = internalOrgUnitFolder(dbc, parent); 369 370 CmsResource resource = null; 371 // only normal OUs have to have at least one resource 372 if (((flags & CmsOrganizationalUnit.FLAG_WEBUSERS) == 0) || (associatedResource != null)) { 373 // check that the associated resource exists and if is a folder 374 resource = m_driverManager.readFolder(dbc, associatedResource, CmsResourceFilter.ALL); 375 } 376 377 String ouPath = ORGUNIT_BASE_FOLDER; 378 // validate resource 379 if ((parentFolder != null) && (resource != null)) { 380 internalValidateResourceForOrgUnit( 381 dbc, 382 internalCreateOrgUnitFromResource(dbc, parentFolder), 383 resource.getRootPath()); 384 } 385 if (parentFolder != null) { 386 ouPath = parentFolder.getRootPath(); 387 if (!ouPath.endsWith("/")) { 388 ouPath += "/"; 389 } 390 } 391 392 // create the resource 393 CmsResource ouFolder = internalCreateResourceForOrgUnit(dbc, ouPath + name, flags); 394 395 // write description property 396 internalWriteOrgUnitProperty( 397 dbc, 398 ouFolder, 399 new CmsProperty(ORGUNIT_PROPERTY_DESCRIPTION, description, null)); 400 401 // create the ou object 402 CmsOrganizationalUnit ou = internalCreateOrgUnitFromResource(dbc, ouFolder); 403 404 if ((ou.getParentFqn() != null)) { 405 // if not the root ou, create default roles & groups 406 // for the root ou, are created in #fillDefaults 407 Locale locale = CmsLocaleManager.getDefaultLocale(); 408 if (dbc.getRequestContext() != null) { 409 locale = dbc.getRequestContext().getLocale(); 410 } 411 // create default groups 412 internalCreateDefaultGroups(dbc, ou.getName(), ou.getDisplayName(locale), ou.hasFlagWebuser()); 413 if (!ou.hasFlagWebuser()) { 414 // create default project 415 CmsProject project = m_driverManager.createProject( 416 dbc, 417 ou.getName() + OFFLINE_PROJECT_NAME, 418 "", 419 ou.getName() + OpenCms.getDefaultUsers().getGroupUsers(), 420 ou.getName() + OpenCms.getDefaultUsers().getGroupUsers(), 421 CmsProject.PROJECT_TYPE_NORMAL); 422 423 // write project id property 424 internalWriteOrgUnitProperty( 425 dbc, 426 ouFolder, 427 new CmsProperty(ORGUNIT_PROPERTY_PROJECTID, project.getUuid().toString(), null)); 428 } else { 429 // write project id property 430 internalWriteOrgUnitProperty( 431 dbc, 432 ouFolder, 433 new CmsProperty(ORGUNIT_PROPERTY_PROJECTID, CmsUUID.getNullUUID().toString(), null)); 434 } 435 } else { 436 // write project id property 437 internalWriteOrgUnitProperty( 438 dbc, 439 ouFolder, 440 new CmsProperty(ORGUNIT_PROPERTY_PROJECTID, CmsUUID.getNullUUID().toString(), null)); 441 } 442 // reread the ou, to actualize the project id 443 ou = internalCreateOrgUnitFromResource(dbc, ouFolder); 444 if (resource != null) { 445 // add the given resource 446 m_driverManager.addResourceToOrgUnit(dbc, ou, resource); 447 } 448 OpenCms.fireCmsEvent(I_CmsEventListener.EVENT_CLEAR_ONLINE_CACHES, null); 449 // return the new created ou 450 return ou; 451 } catch (CmsException e) { 452 throw new CmsDataAccessException(e.getMessageContainer(), e); 453 } 454 } 455 456 /** 457 * @see org.opencms.db.I_CmsUserDriver#createRootOrganizationalUnit(org.opencms.db.CmsDbContext) 458 */ 459 public void createRootOrganizationalUnit(CmsDbContext dbc) { 460 461 try { 462 readOrganizationalUnit(dbc, ""); 463 } catch (CmsException e) { 464 try { 465 CmsProject onlineProject = dbc.currentProject(); 466 CmsProject setupProject = onlineProject; 467 // get the right offline project 468 try { 469 // this if setting up OpenCms 470 setupProject = m_driverManager.readProject(dbc, I_CmsProjectDriver.SETUP_PROJECT_NAME); 471 } catch (CmsException exc) { 472 // this if updating OpenCms 473 try { 474 setupProject = m_driverManager.readProject(dbc, "Offline"); 475 } catch (CmsException exc2) { 476 // there is nothing to do, if no offline project found 477 } 478 } 479 dbc.getRequestContext().setCurrentProject(setupProject); 480 try { 481 createOrganizationalUnit( 482 dbc, 483 "", 484 CmsMacroResolver.localizedKeyMacro(Messages.GUI_ORGUNIT_ROOT_DESCRIPTION_0, null), 485 0, 486 null, 487 "/"); 488 } finally { 489 dbc.getRequestContext().setCurrentProject(onlineProject); 490 } 491 if (CmsLog.INIT.isInfoEnabled()) { 492 CmsLog.INIT.info(Messages.get().getBundle().key(Messages.INIT_ROOT_ORGUNIT_DEFAULTS_INITIALIZED_0)); 493 } 494 } catch (CmsException exc) { 495 if (CmsLog.INIT.isErrorEnabled()) { 496 CmsLog.INIT.error( 497 Messages.get().getBundle().key(Messages.INIT_ROOT_ORGUNIT_INITIALIZATION_FAILED_0), 498 exc); 499 } 500 throw new CmsInitException(Messages.get().container(Messages.ERR_INITIALIZING_USER_DRIVER_0), exc); 501 } 502 } 503 } 504 505 /** 506 * @see org.opencms.db.I_CmsUserDriver#createUser(CmsDbContext, CmsUUID, String, String, String, String, String, long, int, long, Map) 507 */ 508 public CmsUser createUser( 509 CmsDbContext dbc, 510 CmsUUID id, 511 String userFqn, 512 String password, 513 String firstname, 514 String lastname, 515 String email, 516 long lastlogin, 517 int flags, 518 long dateCreated, 519 Map<String, Object> additionalInfos) 520 throws CmsDataAccessException { 521 522 Connection conn = null; 523 PreparedStatement stmt = null; 524 525 if (existsUser(dbc, userFqn)) { 526 CmsMessageContainer message = Messages.get().container( 527 Messages.ERR_USER_WITH_NAME_ALREADY_EXISTS_1, 528 userFqn); 529 if (LOG.isErrorEnabled()) { 530 LOG.error(message.key()); 531 } 532 throw new CmsDbEntryAlreadyExistsException(message); 533 } 534 535 try { 536 conn = m_sqlManager.getConnection(dbc); 537 stmt = m_sqlManager.getPreparedStatement(conn, "C_USERS_ADD_10"); 538 539 stmt.setString(1, id.toString()); 540 stmt.setString(2, CmsOrganizationalUnit.getSimpleName(userFqn)); 541 stmt.setString(3, password); 542 stmt.setString(4, m_sqlManager.validateEmpty(firstname)); 543 stmt.setString(5, m_sqlManager.validateEmpty(lastname)); 544 stmt.setString(6, m_sqlManager.validateEmpty(email)); 545 stmt.setLong(7, lastlogin); 546 stmt.setInt(8, flags); 547 stmt.setString(9, CmsOrganizationalUnit.SEPARATOR + CmsOrganizationalUnit.getParentFqn(userFqn)); 548 stmt.setLong(10, (dateCreated == 0 ? System.currentTimeMillis() : dateCreated)); 549 stmt.executeUpdate(); 550 } catch (SQLException e) { 551 throw new CmsDbSqlException( 552 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 553 e); 554 } finally { 555 m_sqlManager.closeAll(dbc, conn, stmt, null); 556 } 557 internalWriteUserInfos(dbc, id, additionalInfos); 558 559 return readUser(dbc, id); 560 } 561 562 /** 563 * @see org.opencms.db.I_CmsUserDriver#createUserInGroup(org.opencms.db.CmsDbContext, org.opencms.util.CmsUUID, org.opencms.util.CmsUUID) 564 */ 565 public void createUserInGroup(CmsDbContext dbc, CmsUUID userId, CmsUUID groupId) throws CmsDataAccessException { 566 567 Connection conn = null; 568 PreparedStatement stmt = null; 569 570 // check if user is already in group 571 if (!internalValidateUserInGroup(dbc, userId, groupId)) { 572 // if not, add this user to the group 573 try { 574 conn = getSqlManager().getConnection(dbc); 575 stmt = m_sqlManager.getPreparedStatement(conn, "C_GROUPS_ADD_USER_TO_GROUP_3"); 576 577 // write the new assignment to the database 578 stmt.setString(1, groupId.toString()); 579 stmt.setString(2, userId.toString()); 580 // flag field is not used yet 581 stmt.setInt(3, 0); 582 stmt.executeUpdate(); 583 } catch (SQLException e) { 584 throw new CmsDbSqlException( 585 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 586 e); 587 } finally { 588 m_sqlManager.closeAll(dbc, conn, stmt, null); 589 } 590 } 591 } 592 593 /** 594 * @see org.opencms.db.I_CmsUserDriver#deleteGroup(org.opencms.db.CmsDbContext, java.lang.String) 595 */ 596 public void deleteGroup(CmsDbContext dbc, String groupFqn) throws CmsDataAccessException { 597 598 Connection conn = null; 599 PreparedStatement stmt = null; 600 601 try { 602 conn = getSqlManager().getConnection(dbc); 603 stmt = m_sqlManager.getPreparedStatement(conn, "C_GROUPS_DELETE_GROUP_2"); 604 605 stmt.setString(1, CmsOrganizationalUnit.getSimpleName(groupFqn)); 606 stmt.setString(2, CmsOrganizationalUnit.SEPARATOR + CmsOrganizationalUnit.getParentFqn(groupFqn)); 607 stmt.executeUpdate(); 608 } catch (SQLException e) { 609 throw new CmsDbSqlException( 610 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 611 e); 612 } finally { 613 m_sqlManager.closeAll(dbc, conn, stmt, null); 614 } 615 } 616 617 /** 618 * @see org.opencms.db.I_CmsUserDriver#deleteOrganizationalUnit(org.opencms.db.CmsDbContext, org.opencms.security.CmsOrganizationalUnit) 619 */ 620 public void deleteOrganizationalUnit(CmsDbContext dbc, CmsOrganizationalUnit organizationalUnit) 621 throws CmsDataAccessException { 622 623 try { 624 CmsResource resource = m_driverManager.readResource( 625 dbc, 626 ORGUNIT_BASE_FOLDER + organizationalUnit.getName(), 627 CmsResourceFilter.DEFAULT); 628 internalDeleteOrgUnitResource(dbc, resource); 629 if (organizationalUnit.getProjectId() != null) { 630 try { 631 // maintain the default project synchronized 632 m_driverManager.deleteProject( 633 dbc, 634 m_driverManager.readProject(dbc, organizationalUnit.getProjectId()), 635 false); 636 } catch (CmsDbEntryNotFoundException e) { 637 // ignore 638 } 639 } 640 } catch (CmsException e) { 641 throw new CmsDataAccessException(e.getMessageContainer(), e); 642 } 643 } 644 645 /** 646 * @see org.opencms.db.I_CmsUserDriver#deleteUser(org.opencms.db.CmsDbContext, java.lang.String) 647 */ 648 public void deleteUser(CmsDbContext dbc, String userFqn) throws CmsDataAccessException { 649 650 CmsUser user = readUser(dbc, userFqn); 651 652 Connection conn = null; 653 PreparedStatement stmt = null; 654 655 try { 656 conn = getSqlManager().getConnection(dbc); 657 stmt = m_sqlManager.getPreparedStatement(conn, "C_USERS_DELETE_2"); 658 659 stmt.setString(1, CmsOrganizationalUnit.getSimpleName(userFqn)); 660 stmt.setString(2, CmsOrganizationalUnit.SEPARATOR + CmsOrganizationalUnit.getParentFqn(userFqn)); 661 stmt.executeUpdate(); 662 } catch (SQLException e) { 663 throw new CmsDbSqlException( 664 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 665 e); 666 } finally { 667 m_sqlManager.closeAll(dbc, conn, stmt, null); 668 } 669 // delete the additional infos 670 deleteUserInfos(dbc, user.getId()); 671 672 if (OpenCms.getSubscriptionManager().isEnabled()) { 673 // delete visited resource information from log 674 CmsVisitEntryFilter filter = CmsVisitEntryFilter.ALL.filterUser(user.getId()); 675 m_driverManager.getSubscriptionDriver().deleteVisits( 676 dbc, 677 OpenCms.getSubscriptionManager().getPoolName(), 678 filter); 679 680 // delete all subscribed resources for user 681 m_driverManager.getSubscriptionDriver().unsubscribeAllResourcesFor( 682 dbc, 683 OpenCms.getSubscriptionManager().getPoolName(), 684 user); 685 } 686 } 687 688 /** 689 * @see org.opencms.db.I_CmsUserDriver#deleteUserInfos(org.opencms.db.CmsDbContext, org.opencms.util.CmsUUID) 690 */ 691 public void deleteUserInfos(CmsDbContext dbc, CmsUUID userId) throws CmsDataAccessException { 692 693 Connection conn = null; 694 PreparedStatement stmt = null; 695 696 try { 697 conn = getSqlManager().getConnection(dbc); 698 stmt = m_sqlManager.getPreparedStatement(conn, "C_USERDATA_DELETE_1"); 699 700 stmt.setString(1, userId.toString()); 701 stmt.executeUpdate(); 702 } catch (SQLException e) { 703 throw new CmsDbSqlException( 704 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 705 e); 706 } finally { 707 m_sqlManager.closeAll(dbc, conn, stmt, null); 708 } 709 } 710 711 /** 712 * @see org.opencms.db.I_CmsUserDriver#deleteUserInGroup(org.opencms.db.CmsDbContext, org.opencms.util.CmsUUID, org.opencms.util.CmsUUID) 713 */ 714 public void deleteUserInGroup(CmsDbContext dbc, CmsUUID userId, CmsUUID groupId) throws CmsDataAccessException { 715 716 PreparedStatement stmt = null; 717 Connection conn = null; 718 try { 719 conn = getSqlManager().getConnection(dbc); 720 stmt = m_sqlManager.getPreparedStatement(conn, "C_GROUPS_REMOVE_USER_FROM_GROUP_2"); 721 722 stmt.setString(1, groupId.toString()); 723 stmt.setString(2, userId.toString()); 724 stmt.executeUpdate(); 725 } catch (SQLException e) { 726 throw new CmsDbSqlException( 727 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 728 e); 729 } finally { 730 m_sqlManager.closeAll(dbc, conn, stmt, null); 731 } 732 } 733 734 /** 735 * @see org.opencms.db.I_CmsUserDriver#destroy() 736 */ 737 public void destroy() throws Throwable { 738 739 m_sqlManager = null; 740 m_driverManager = null; 741 742 if (CmsLog.INIT.isInfoEnabled()) { 743 CmsLog.INIT.info(Messages.get().getBundle().key(Messages.INIT_SHUTDOWN_DRIVER_1, getClass().getName())); 744 } 745 } 746 747 /** 748 * @see org.opencms.db.I_CmsUserDriver#existsGroup(org.opencms.db.CmsDbContext, java.lang.String) 749 */ 750 public boolean existsGroup(CmsDbContext dbc, String groupFqn) throws CmsDataAccessException { 751 752 ResultSet res = null; 753 PreparedStatement stmt = null; 754 Connection conn = null; 755 boolean result = false; 756 757 try { 758 conn = getSqlManager().getConnection(dbc); 759 stmt = m_sqlManager.getPreparedStatement(conn, "C_GROUPS_READ_BY_NAME_2"); 760 761 stmt.setString(1, CmsOrganizationalUnit.getSimpleName(groupFqn)); 762 stmt.setString(2, CmsOrganizationalUnit.SEPARATOR + CmsOrganizationalUnit.getParentFqn(groupFqn)); 763 res = stmt.executeQuery(); 764 765 // create new Cms group object 766 if (res.next()) { 767 result = true; 768 while (res.next()) { 769 // do nothing only move through all rows because of mssql odbc driver 770 } 771 } else { 772 result = false; 773 } 774 775 } catch (SQLException e) { 776 throw new CmsDbSqlException( 777 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 778 e); 779 } finally { 780 m_sqlManager.closeAll(dbc, conn, stmt, res); 781 } 782 783 return result; 784 } 785 786 /** 787 * @see org.opencms.db.I_CmsUserDriver#existsUser(org.opencms.db.CmsDbContext, java.lang.String) 788 */ 789 public boolean existsUser(CmsDbContext dbc, String userFqn) throws CmsDataAccessException { 790 791 PreparedStatement stmt = null; 792 ResultSet res = null; 793 Connection conn = null; 794 boolean result = false; 795 796 try { 797 conn = getSqlManager().getConnection(dbc); 798 stmt = m_sqlManager.getPreparedStatement(conn, "C_USERS_READ_BY_NAME_2"); 799 stmt.setString(1, CmsOrganizationalUnit.getSimpleName(userFqn)); 800 stmt.setString(2, CmsOrganizationalUnit.SEPARATOR + CmsOrganizationalUnit.getParentFqn(userFqn)); 801 802 res = stmt.executeQuery(); 803 804 if (res.next()) { 805 result = true; 806 while (res.next()) { 807 // do nothing only move through all rows because of mssql odbc driver 808 } 809 } else { 810 result = false; 811 } 812 } catch (SQLException e) { 813 throw new CmsDbSqlException( 814 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 815 e); 816 } finally { 817 m_sqlManager.closeAll(dbc, conn, stmt, res); 818 } 819 820 return result; 821 } 822 823 /** 824 * @see org.opencms.db.I_CmsUserDriver#fillDefaults(org.opencms.db.CmsDbContext) 825 */ 826 public void fillDefaults(CmsDbContext dbc) throws CmsInitException { 827 828 try { 829 CmsOrganizationalUnit ou = (CmsOrganizationalUnit)(dbc.getAttribute(CmsDriverManager.ATTR_INIT_OU)); 830 if (ou == null) { 831 internalCreateDefaultGroups(dbc, "", "", false); 832 } else { 833 internalCreateDefaultGroups(dbc, ou.getName(), ou.getDescription(), ou.hasFlagWebuser()); 834 } 835 } catch (CmsException e) { 836 if (CmsLog.INIT.isErrorEnabled()) { 837 CmsLog.INIT.error(Messages.get().getBundle().key(Messages.INIT_DEFAULT_USERS_CREATION_FAILED_0), e); 838 } 839 throw new CmsInitException(Messages.get().container(Messages.ERR_INITIALIZING_USER_DRIVER_0), e); 840 } 841 } 842 843 /** 844 * @see org.opencms.db.I_CmsUserDriver#getGroups(org.opencms.db.CmsDbContext, org.opencms.security.CmsOrganizationalUnit, boolean, boolean) 845 */ 846 public List<CmsGroup> getGroups( 847 CmsDbContext dbc, 848 CmsOrganizationalUnit orgUnit, 849 boolean includeSubOus, 850 boolean readRoles) 851 throws CmsDataAccessException { 852 853 // compose the query 854 String sqlQuery = createRoleQuery("C_GROUPS_GET_GROUPS_0", includeSubOus, readRoles); 855 // adjust parameter to use with LIKE 856 String ouFqn = CmsOrganizationalUnit.SEPARATOR + orgUnit.getName(); 857 if (includeSubOus) { 858 ouFqn += "%"; 859 } 860 861 // execute it 862 List<CmsGroup> groups = new ArrayList<CmsGroup>(); 863 ResultSet res = null; 864 PreparedStatement stmt = null; 865 Connection conn = null; 866 try { 867 // create statement 868 conn = m_sqlManager.getConnection(dbc); 869 stmt = m_sqlManager.getPreparedStatementForSql(conn, sqlQuery); 870 871 stmt.setString(1, ouFqn); 872 stmt.setInt(2, I_CmsPrincipal.FLAG_GROUP_ROLE); 873 874 res = stmt.executeQuery(); 875 876 // create new Cms group objects 877 while (res.next()) { 878 groups.add(internalCreateGroup(res)); 879 } 880 } catch (SQLException e) { 881 throw new CmsDbSqlException( 882 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 883 e); 884 } finally { 885 m_sqlManager.closeAll(dbc, conn, stmt, res); 886 } 887 return groups; 888 } 889 890 /** 891 * @see org.opencms.db.I_CmsUserDriver#getOrganizationalUnits(org.opencms.db.CmsDbContext, org.opencms.security.CmsOrganizationalUnit, boolean) 892 */ 893 public List<CmsOrganizationalUnit> getOrganizationalUnits( 894 CmsDbContext dbc, 895 CmsOrganizationalUnit parent, 896 boolean includeChildren) 897 throws CmsDataAccessException { 898 899 List<CmsOrganizationalUnit> orgUnits = new ArrayList<CmsOrganizationalUnit>(); 900 try { 901 CmsResource parentFolder = internalOrgUnitFolder(dbc, parent); 902 Iterator<CmsResource> itResources = m_driverManager.readResources( 903 dbc, 904 parentFolder, 905 CmsResourceFilter.DEFAULT, 906 includeChildren).iterator(); 907 while (itResources.hasNext()) { 908 CmsResource resource = itResources.next(); 909 orgUnits.add(internalCreateOrgUnitFromResource(dbc, resource)); 910 } 911 } catch (CmsException e) { 912 throw new CmsDataAccessException(e.getMessageContainer(), e); 913 } 914 return orgUnits; 915 } 916 917 /** 918 * @see org.opencms.db.I_CmsUserDriver#getResourcesForOrganizationalUnit(org.opencms.db.CmsDbContext, org.opencms.security.CmsOrganizationalUnit) 919 */ 920 public List<CmsResource> getResourcesForOrganizationalUnit(CmsDbContext dbc, CmsOrganizationalUnit orgUnit) 921 throws CmsDataAccessException { 922 923 List<CmsResource> result = new ArrayList<CmsResource>(); 924 try { 925 CmsResource ouResource = m_driverManager.readResource( 926 dbc, 927 ORGUNIT_BASE_FOLDER + orgUnit.getName(), 928 CmsResourceFilter.ALL); 929 Iterator<String> itPaths = internalResourcesForOrgUnit(dbc, ouResource).iterator(); 930 while (itPaths.hasNext()) { 931 String path = itPaths.next(); 932 try { 933 result.add(m_driverManager.readResource(dbc, path, CmsResourceFilter.ALL)); 934 } catch (CmsVfsResourceNotFoundException e) { 935 if (LOG.isWarnEnabled()) { 936 LOG.warn(e.getLocalizedMessage(), e); 937 } 938 } 939 } 940 } catch (CmsException e) { 941 throw new CmsDataAccessException(e.getMessageContainer(), e); 942 } 943 return result; 944 } 945 946 /** 947 * @see org.opencms.db.I_CmsUserDriver#getSqlManager() 948 */ 949 public CmsSqlManager getSqlManager() { 950 951 return m_sqlManager; 952 } 953 954 /** 955 * @see org.opencms.db.I_CmsUserDriver#getUsers(org.opencms.db.CmsDbContext, org.opencms.security.CmsOrganizationalUnit, boolean) 956 */ 957 public List<CmsUser> getUsers(CmsDbContext dbc, CmsOrganizationalUnit orgUnit, boolean recursive) 958 throws CmsDataAccessException { 959 960 return internalGetUsers(dbc, orgUnit, recursive, true); 961 } 962 963 /** 964 * @see org.opencms.db.I_CmsUserDriver#getUsersWithoutAdditionalInfo(org.opencms.db.CmsDbContext, org.opencms.security.CmsOrganizationalUnit, boolean) 965 */ 966 public List<CmsUser> getUsersWithoutAdditionalInfo( 967 CmsDbContext dbc, 968 CmsOrganizationalUnit orgUnit, 969 boolean recursive) 970 throws CmsDataAccessException { 971 972 return internalGetUsers(dbc, orgUnit, recursive, false); 973 } 974 975 /** 976 * @see org.opencms.db.I_CmsDriver#init(org.opencms.db.CmsDbContext, org.opencms.configuration.CmsConfigurationManager, java.util.List, org.opencms.db.CmsDriverManager) 977 */ 978 public void init( 979 CmsDbContext dbc, 980 CmsConfigurationManager configurationManager, 981 List<String> successiveDrivers, 982 CmsDriverManager driverManager) { 983 984 CmsParameterConfiguration config = configurationManager.getConfiguration(); 985 986 String poolUrl = config.get("db.user.pool"); 987 String classname = config.get("db.user.sqlmanager"); 988 m_sqlManager = initSqlManager(classname); 989 m_sqlManager.init(I_CmsUserDriver.DRIVER_TYPE_ID, poolUrl); 990 991 m_driverManager = driverManager; 992 993 if (CmsLog.INIT.isInfoEnabled()) { 994 CmsLog.INIT.info(Messages.get().getBundle().key(Messages.INIT_ASSIGNED_POOL_1, poolUrl)); 995 } 996 997 m_digestAlgorithm = config.getString(CmsDriverManager.CONFIGURATION_DB + ".user.digest.type", "MD5"); 998 if (CmsLog.INIT.isInfoEnabled()) { 999 CmsLog.INIT.info(Messages.get().getBundle().key(Messages.INIT_DIGEST_ALGORITHM_1, m_digestAlgorithm)); 1000 } 1001 1002 m_digestFileEncoding = config.getString( 1003 CmsDriverManager.CONFIGURATION_DB + ".user.digest.encoding", 1004 CmsEncoder.ENCODING_UTF_8); 1005 if (CmsLog.INIT.isInfoEnabled()) { 1006 CmsLog.INIT.info(Messages.get().getBundle().key(Messages.INIT_DIGEST_ENCODING_1, m_digestFileEncoding)); 1007 } 1008 1009 // create the digest 1010 try { 1011 m_digest = MessageDigest.getInstance(m_digestAlgorithm); 1012 if (CmsLog.INIT.isInfoEnabled()) { 1013 CmsLog.INIT.info( 1014 Messages.get().getBundle().key( 1015 Messages.INIT_DIGEST_ENC_3, 1016 m_digest.getAlgorithm(), 1017 m_digest.getProvider().getName(), 1018 String.valueOf(m_digest.getProvider().getVersion()))); 1019 } 1020 } catch (NoSuchAlgorithmException e) { 1021 if (CmsLog.INIT.isInfoEnabled()) { 1022 CmsLog.INIT.info(Messages.get().getBundle().key(Messages.INIT_SET_DIGEST_ERROR_0), e); 1023 } 1024 } 1025 1026 if ((successiveDrivers != null) && !successiveDrivers.isEmpty()) { 1027 if (LOG.isWarnEnabled()) { 1028 LOG.warn( 1029 Messages.get().getBundle().key( 1030 Messages.LOG_SUCCESSIVE_DRIVERS_UNSUPPORTED_1, 1031 getClass().getName())); 1032 } 1033 } 1034 } 1035 1036 /** 1037 * @see org.opencms.db.I_CmsUserDriver#initSqlManager(String) 1038 */ 1039 public org.opencms.db.generic.CmsSqlManager initSqlManager(String classname) { 1040 1041 return CmsSqlManager.getInstance(classname); 1042 } 1043 1044 /** 1045 * @see org.opencms.db.I_CmsUserDriver#publishAccessControlEntries(org.opencms.db.CmsDbContext, org.opencms.file.CmsProject, org.opencms.file.CmsProject, org.opencms.util.CmsUUID, org.opencms.util.CmsUUID) 1046 */ 1047 public void publishAccessControlEntries( 1048 CmsDbContext dbc, 1049 CmsProject offlineProject, 1050 CmsProject onlineProject, 1051 CmsUUID offlineId, 1052 CmsUUID onlineId) 1053 throws CmsDataAccessException { 1054 1055 // at first, we remove all access contries of this resource in the online project 1056 m_driverManager.getUserDriver(dbc).removeAccessControlEntries(dbc, onlineProject, onlineId); 1057 1058 // then, we copy the access control entries from the offline project into the online project 1059 CmsUUID dbcProjectId = dbc.getProjectId(); 1060 if ((dbcProjectId != null) && !dbc.getProjectId().isNullUUID()) { 1061 dbc.setProjectId(offlineProject.getUuid()); 1062 } else { 1063 dbc.setProjectId(CmsUUID.getNullUUID()); 1064 } 1065 List<CmsAccessControlEntry> aces = m_driverManager.getUserDriver( 1066 dbc).readAccessControlEntries(dbc, offlineProject, offlineId, false); 1067 dbc.setProjectId(dbcProjectId); 1068 1069 for (CmsAccessControlEntry ace : aces) { 1070 m_driverManager.getUserDriver(dbc).writeAccessControlEntry(dbc, onlineProject, ace); 1071 } 1072 } 1073 1074 /** 1075 * @see org.opencms.db.I_CmsUserDriver#readAccessControlEntries(org.opencms.db.CmsDbContext, org.opencms.file.CmsProject, org.opencms.util.CmsUUID, boolean) 1076 */ 1077 public List<CmsAccessControlEntry> readAccessControlEntries( 1078 CmsDbContext dbc, 1079 CmsProject project, 1080 CmsUUID resource, 1081 boolean inheritedOnly) 1082 throws CmsDataAccessException { 1083 1084 List<CmsAccessControlEntry> aceList = new ArrayList<CmsAccessControlEntry>(); 1085 PreparedStatement stmt = null; 1086 Connection conn = null; 1087 ResultSet res = null; 1088 1089 try { 1090 conn = m_sqlManager.getConnection(dbc); 1091 if (resource.equals(CmsAccessControlEntry.PRINCIPAL_READALL_ID)) { 1092 stmt = m_sqlManager.getPreparedStatement(conn, project, "C_ACCESS_READ_ENTRIES_0"); 1093 } else { 1094 stmt = m_sqlManager.getPreparedStatement(conn, project, "C_ACCESS_READ_ENTRIES_1"); 1095 String resId = resource.toString(); 1096 stmt.setString(1, resId); 1097 } 1098 1099 res = stmt.executeQuery(); 1100 1101 // create new CmsAccessControlEntry and add to list 1102 while (res.next()) { 1103 CmsAccessControlEntry ace = internalCreateAce(res); 1104 if (inheritedOnly && !ace.isInheriting()) { 1105 continue; 1106 } 1107 if (inheritedOnly && ace.isInheriting()) { 1108 ace.setFlags(CmsAccessControlEntry.ACCESS_FLAGS_INHERITED); 1109 } 1110 aceList.add(ace); 1111 } 1112 return aceList; 1113 } catch (SQLException e) { 1114 throw new CmsDbSqlException( 1115 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 1116 e); 1117 } finally { 1118 m_sqlManager.closeAll(dbc, conn, stmt, res); 1119 } 1120 } 1121 1122 /** 1123 * @see org.opencms.db.I_CmsUserDriver#readAccessControlEntry(org.opencms.db.CmsDbContext, org.opencms.file.CmsProject, org.opencms.util.CmsUUID, org.opencms.util.CmsUUID) 1124 */ 1125 public CmsAccessControlEntry readAccessControlEntry( 1126 CmsDbContext dbc, 1127 CmsProject project, 1128 CmsUUID resource, 1129 CmsUUID principal) 1130 throws CmsDataAccessException { 1131 1132 CmsAccessControlEntry ace = null; 1133 PreparedStatement stmt = null; 1134 Connection conn = null; 1135 ResultSet res = null; 1136 1137 try { 1138 conn = m_sqlManager.getConnection(dbc); 1139 stmt = m_sqlManager.getPreparedStatement(conn, project, "C_ACCESS_READ_ENTRY_2"); 1140 1141 stmt.setString(1, resource.toString()); 1142 stmt.setString(2, principal.toString()); 1143 1144 res = stmt.executeQuery(); 1145 1146 // create new CmsAccessControlEntry 1147 if (res.next()) { 1148 ace = internalCreateAce(res); 1149 while (res.next()) { 1150 // do nothing only move through all rows because of mssql odbc driver 1151 } 1152 } else { 1153 res.close(); 1154 res = null; 1155 throw new CmsDbEntryNotFoundException( 1156 Messages.get().container(Messages.ERR_NO_ACE_FOUND_2, resource, principal)); 1157 } 1158 1159 return ace; 1160 1161 } catch (SQLException e) { 1162 throw new CmsDbSqlException( 1163 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 1164 e); 1165 } finally { 1166 m_sqlManager.closeAll(dbc, conn, stmt, res); 1167 } 1168 } 1169 1170 /** 1171 * @see org.opencms.db.I_CmsUserDriver#readChildGroups(org.opencms.db.CmsDbContext, java.lang.String) 1172 */ 1173 public List<CmsGroup> readChildGroups(CmsDbContext dbc, String parentGroupFqn) throws CmsDataAccessException { 1174 1175 List<CmsGroup> children = new ArrayList<CmsGroup>(); 1176 ResultSet res = null; 1177 PreparedStatement stmt = null; 1178 Connection conn = null; 1179 try { 1180 // get parent group 1181 CmsGroup parent = m_driverManager.getUserDriver(dbc).readGroup(dbc, parentGroupFqn); 1182 // parent group exists, so get all children 1183 if (parent != null) { 1184 // create statement 1185 conn = m_sqlManager.getConnection(dbc); 1186 stmt = m_sqlManager.getPreparedStatement(conn, "C_GROUPS_GET_CHILD_1"); 1187 stmt.setString(1, parent.getId().toString()); 1188 res = stmt.executeQuery(); 1189 // create new Cms group objects 1190 while (res.next()) { 1191 children.add(internalCreateGroup(res)); 1192 } 1193 } 1194 } catch (SQLException e) { 1195 throw new CmsDbSqlException( 1196 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 1197 e); 1198 } finally { 1199 // close all db-resources 1200 m_sqlManager.closeAll(dbc, conn, stmt, res); 1201 } 1202 return children; 1203 } 1204 1205 /** 1206 * @see org.opencms.db.I_CmsUserDriver#readGroup(org.opencms.db.CmsDbContext, org.opencms.util.CmsUUID) 1207 */ 1208 public CmsGroup readGroup(CmsDbContext dbc, CmsUUID groupId) throws CmsDataAccessException { 1209 1210 CmsGroup group = null; 1211 ResultSet res = null; 1212 PreparedStatement stmt = null; 1213 Connection conn = null; 1214 1215 try { 1216 conn = m_sqlManager.getConnection(dbc); 1217 stmt = m_sqlManager.getPreparedStatement(conn, "C_GROUPS_READ_BY_ID_1"); 1218 1219 // read the group from the database 1220 stmt.setString(1, groupId.toString()); 1221 res = stmt.executeQuery(); 1222 // create new Cms group object 1223 if (res.next()) { 1224 group = internalCreateGroup(res); 1225 while (res.next()) { 1226 // do nothing only move through all rows because of mssql odbc driver 1227 } 1228 } else { 1229 CmsMessageContainer message = Messages.get().container(Messages.ERR_NO_GROUP_WITH_ID_1, groupId); 1230 if (LOG.isDebugEnabled()) { 1231 LOG.debug(message.key()); 1232 } 1233 throw new CmsDbEntryNotFoundException(message); 1234 } 1235 1236 } catch (SQLException e) { 1237 throw new CmsDbSqlException( 1238 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 1239 e); 1240 } finally { 1241 m_sqlManager.closeAll(dbc, conn, stmt, res); 1242 } 1243 1244 return group; 1245 } 1246 1247 /** 1248 * @see org.opencms.db.I_CmsUserDriver#readGroup(org.opencms.db.CmsDbContext, java.lang.String) 1249 */ 1250 public CmsGroup readGroup(CmsDbContext dbc, String groupFqn) throws CmsDataAccessException { 1251 1252 CmsGroup group = null; 1253 ResultSet res = null; 1254 PreparedStatement stmt = null; 1255 Connection conn = null; 1256 1257 try { 1258 conn = m_sqlManager.getConnection(dbc); 1259 stmt = m_sqlManager.getPreparedStatement(conn, "C_GROUPS_READ_BY_NAME_2"); 1260 1261 // read the group from the database 1262 stmt.setString(1, CmsOrganizationalUnit.getSimpleName(groupFqn)); 1263 stmt.setString(2, CmsOrganizationalUnit.SEPARATOR + CmsOrganizationalUnit.getParentFqn(groupFqn)); 1264 res = stmt.executeQuery(); 1265 1266 // create new Cms group object 1267 if (res.next()) { 1268 group = internalCreateGroup(res); 1269 while (res.next()) { 1270 // do nothing only move through all rows because of mssql odbc driver 1271 } 1272 } else { 1273 CmsMessageContainer message = org.opencms.db.Messages.get().container( 1274 org.opencms.db.Messages.ERR_UNKNOWN_GROUP_1, 1275 groupFqn); 1276 if (LOG.isDebugEnabled()) { 1277 LOG.debug(message.key(), new Exception()); 1278 } 1279 throw new CmsDbEntryNotFoundException(message); 1280 } 1281 } catch (SQLException e) { 1282 throw new CmsDbSqlException( 1283 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 1284 e); 1285 } finally { 1286 m_sqlManager.closeAll(dbc, conn, stmt, res); 1287 } 1288 return group; 1289 } 1290 1291 /** 1292 * @see org.opencms.db.I_CmsUserDriver#readGroupsOfUser(CmsDbContext, CmsUUID, String, boolean, String, boolean) 1293 */ 1294 public List<CmsGroup> readGroupsOfUser( 1295 CmsDbContext dbc, 1296 CmsUUID userId, 1297 String ouFqn, 1298 boolean includeChildOus, 1299 String remoteAddress, 1300 boolean readRoles) 1301 throws CmsDataAccessException { 1302 1303 // compose the query 1304 String sqlQuery = createRoleQuery("C_GROUPS_GET_GROUPS_OF_USER_1", includeChildOus, readRoles); 1305 // adjust parameter to use with LIKE 1306 String ouFqnParam = CmsOrganizationalUnit.SEPARATOR + ouFqn; 1307 if (includeChildOus) { 1308 ouFqnParam += "%"; 1309 } 1310 1311 // execute it 1312 List<CmsGroup> groups = new ArrayList<CmsGroup>(); 1313 1314 PreparedStatement stmt = null; 1315 ResultSet res = null; 1316 Connection conn = null; 1317 1318 try { 1319 conn = m_sqlManager.getConnection(dbc); 1320 stmt = m_sqlManager.getPreparedStatementForSql(conn, sqlQuery); 1321 1322 // get all all groups of the user 1323 stmt.setString(1, userId.toString()); 1324 stmt.setString(2, ouFqnParam); 1325 stmt.setInt(3, I_CmsPrincipal.FLAG_GROUP_ROLE); 1326 1327 res = stmt.executeQuery(); 1328 1329 while (res.next()) { 1330 groups.add(internalCreateGroup(res)); 1331 } 1332 } catch (SQLException e) { 1333 throw new CmsDbSqlException( 1334 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 1335 e); 1336 } finally { 1337 m_sqlManager.closeAll(dbc, conn, stmt, res); 1338 } 1339 return groups; 1340 } 1341 1342 /** 1343 * @see org.opencms.db.I_CmsUserDriver#readOrganizationalUnit(org.opencms.db.CmsDbContext, String) 1344 */ 1345 public CmsOrganizationalUnit readOrganizationalUnit(CmsDbContext dbc, String ouFqn) throws CmsDataAccessException { 1346 1347 try { 1348 CmsResource resource = m_driverManager.readResource( 1349 dbc, 1350 ORGUNIT_BASE_FOLDER + ouFqn, 1351 CmsResourceFilter.DEFAULT); 1352 return internalCreateOrgUnitFromResource(dbc, resource); 1353 } catch (CmsVfsResourceNotFoundException e) { 1354 throw new CmsDbEntryNotFoundException(Messages.get().container(Messages.ERR_READ_ORGUNIT_1, ouFqn), e); 1355 } catch (CmsException e) { 1356 throw new CmsDataAccessException(e.getMessageContainer(), e); 1357 } 1358 } 1359 1360 /** 1361 * @see org.opencms.db.I_CmsUserDriver#readUser(org.opencms.db.CmsDbContext, org.opencms.util.CmsUUID) 1362 */ 1363 public CmsUser readUser(CmsDbContext dbc, CmsUUID id) throws CmsDataAccessException { 1364 1365 PreparedStatement stmt = null; 1366 ResultSet res = null; 1367 CmsUser user = null; 1368 Connection conn = null; 1369 1370 try { 1371 conn = m_sqlManager.getConnection(dbc); 1372 stmt = m_sqlManager.getPreparedStatement(conn, "C_USERS_READ_BY_ID_1"); 1373 1374 stmt.setString(1, id.toString()); 1375 res = stmt.executeQuery(); 1376 1377 // create new Cms user object 1378 if (res.next()) { 1379 user = internalCreateUser(dbc, res); 1380 while (res.next()) { 1381 // do nothing only move through all rows because of mssql odbc driver 1382 } 1383 } else { 1384 CmsMessageContainer message = Messages.get().container(Messages.ERR_NO_USER_WITH_ID_1, id); 1385 if (LOG.isDebugEnabled()) { 1386 LOG.debug(message.key()); 1387 } 1388 throw new CmsDbEntryNotFoundException(message); 1389 } 1390 } catch (SQLException e) { 1391 throw new CmsDbSqlException( 1392 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 1393 e); 1394 } finally { 1395 m_sqlManager.closeAll(dbc, conn, stmt, res); 1396 } 1397 1398 Map<String, Object> info = readUserInfos(dbc, user.getId()); 1399 user.setAdditionalInfo(info); 1400 return user; 1401 } 1402 1403 /** 1404 * @see org.opencms.db.I_CmsUserDriver#readUser(org.opencms.db.CmsDbContext, java.lang.String) 1405 */ 1406 public CmsUser readUser(CmsDbContext dbc, String userFqn) throws CmsDataAccessException { 1407 1408 PreparedStatement stmt = null; 1409 ResultSet res = null; 1410 CmsUser user = null; 1411 Connection conn = null; 1412 1413 try { 1414 conn = m_sqlManager.getConnection(dbc); 1415 stmt = m_sqlManager.getPreparedStatement(conn, "C_USERS_READ_BY_NAME_2"); 1416 stmt.setString(1, CmsOrganizationalUnit.getSimpleName(userFqn)); 1417 stmt.setString(2, CmsOrganizationalUnit.SEPARATOR + CmsOrganizationalUnit.getParentFqn(userFqn)); 1418 1419 res = stmt.executeQuery(); 1420 1421 if (res.next()) { 1422 user = internalCreateUser(dbc, res); 1423 while (res.next()) { 1424 // do nothing only move through all rows because of mssql odbc driver 1425 } 1426 } else { 1427 CmsMessageContainer message = org.opencms.db.Messages.get().container( 1428 org.opencms.db.Messages.ERR_UNKNOWN_USER_1, 1429 userFqn); 1430 if (LOG.isDebugEnabled()) { 1431 LOG.debug(message.key()); 1432 } 1433 throw new CmsDbEntryNotFoundException(message); 1434 } 1435 } catch (SQLException e) { 1436 throw new CmsDbSqlException( 1437 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 1438 e); 1439 } finally { 1440 m_sqlManager.closeAll(dbc, conn, stmt, res); 1441 } 1442 1443 Map<String, Object> info = readUserInfos(dbc, user.getId()); 1444 user.setAdditionalInfo(info); 1445 return user; 1446 } 1447 1448 /** 1449 * @see org.opencms.db.I_CmsUserDriver#readUser(org.opencms.db.CmsDbContext, java.lang.String, java.lang.String, String) 1450 */ 1451 public CmsUser readUser(CmsDbContext dbc, String userFqn, String password, String remoteAddress) 1452 throws CmsDataAccessException { 1453 1454 PreparedStatement stmt = null; 1455 ResultSet res = null; 1456 CmsUser user = null; 1457 Connection conn = null; 1458 1459 try { 1460 conn = m_sqlManager.getConnection(dbc); 1461 stmt = m_sqlManager.getPreparedStatement(conn, "C_USERS_READ_BY_NAME_2"); 1462 stmt.setString(1, CmsOrganizationalUnit.getSimpleName(userFqn)); 1463 stmt.setString(2, CmsOrganizationalUnit.SEPARATOR + CmsOrganizationalUnit.getParentFqn(userFqn)); 1464 res = stmt.executeQuery(); 1465 1466 boolean success = false; 1467 // create the user object 1468 if (res.next()) { 1469 user = internalCreateUser(dbc, res); 1470 // validate the password stored for the user 1471 success = OpenCms.getPasswordHandler().checkPassword(password, user.getPassword(), true); 1472 1473 while (res.next()) { 1474 // do nothing only move through all rows because of mssql odbc driver 1475 } 1476 } 1477 if (!success) { 1478 CmsMessageContainer message = org.opencms.db.Messages.get().container( 1479 org.opencms.db.Messages.ERR_UNKNOWN_USER_1, 1480 userFqn); 1481 if (LOG.isDebugEnabled()) { 1482 LOG.debug(message.key()); 1483 } 1484 throw new CmsDbEntryNotFoundException(message); 1485 } 1486 } catch (SQLException e) { 1487 throw new CmsDbSqlException( 1488 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 1489 e); 1490 } finally { 1491 m_sqlManager.closeAll(dbc, conn, stmt, res); 1492 } 1493 1494 @SuppressWarnings("null") 1495 Map<String, Object> info = readUserInfos(dbc, user.getId()); 1496 user.setAdditionalInfo(info); 1497 return user; 1498 } 1499 1500 /** 1501 * @see org.opencms.db.I_CmsUserDriver#readUserInfos(org.opencms.db.CmsDbContext, org.opencms.util.CmsUUID) 1502 */ 1503 public Map<String, Object> readUserInfos(CmsDbContext dbc, CmsUUID userId) throws CmsDataAccessException { 1504 1505 Map<String, Object> infos = new HashMap<String, Object>(); 1506 1507 ResultSet res = null; 1508 PreparedStatement stmt = null; 1509 Connection conn = null; 1510 try { 1511 // create statement 1512 conn = m_sqlManager.getConnection(dbc); 1513 stmt = m_sqlManager.getPreparedStatement(conn, "C_USERDATA_READ_1"); 1514 1515 stmt.setString(1, userId.toString()); 1516 res = stmt.executeQuery(); 1517 // read the infos 1518 while (res.next()) { 1519 String key = res.getString(m_sqlManager.readQuery("C_USERDATA_KEY_0")); 1520 String type = res.getString(m_sqlManager.readQuery("C_USERDATA_TYPE_0")); 1521 byte[] value = m_sqlManager.getBytes(res, m_sqlManager.readQuery("C_USERDATA_VALUE_0")); 1522 // deserialize 1523 Object data = null; 1524 try { 1525 1526 if (LOG.isDebugEnabled()) { 1527 LOG.debug(Messages.get().getBundle().key(Messages.LOG_DBG_READUSERINFO_2, key, type)); 1528 if (value != null) { 1529 try { 1530 LOG.debug( 1531 Messages.get().getBundle().key( 1532 Messages.LOG_DBG_READUSERINFO_VALUE_1, 1533 new String(value))); 1534 } catch (Exception e) { 1535 // noop 1536 } 1537 } else { 1538 LOG.debug(Messages.get().getBundle().key(Messages.LOG_DBG_READUSERINFO_VALUE_1, null)); 1539 } 1540 } 1541 1542 data = CmsDataTypeUtil.dataDeserialize(value, type); 1543 1544 } catch (Exception e) { 1545 LOG.error( 1546 Messages.get().container(Messages.ERR_READING_ADDITIONAL_INFO_1, userId.toString()).key(), 1547 e); 1548 } 1549 if ((key != null) && (data != null)) { 1550 infos.put(key, data); 1551 } 1552 } 1553 } catch (SQLException e) { 1554 throw new CmsDbSqlException( 1555 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 1556 e); 1557 } finally { 1558 m_sqlManager.closeAll(dbc, conn, stmt, res); 1559 } 1560 1561 return infos; 1562 } 1563 1564 /** 1565 * @see org.opencms.db.I_CmsUserDriver#readUsersOfGroup(CmsDbContext, String, boolean) 1566 */ 1567 public List<CmsUser> readUsersOfGroup(CmsDbContext dbc, String groupFqn, boolean includeOtherOuUsers) 1568 throws CmsDataAccessException { 1569 1570 String sqlQuery = "C_GROUPS_GET_USERS_OF_GROUP_2"; 1571 if (includeOtherOuUsers) { 1572 sqlQuery = "C_GROUPS_GET_ALL_USERS_OF_GROUP_2"; 1573 } 1574 1575 List<CmsUser> users = new ArrayList<CmsUser>(); 1576 1577 PreparedStatement stmt = null; 1578 ResultSet res = null; 1579 Connection conn = null; 1580 1581 try { 1582 conn = m_sqlManager.getConnection(dbc); 1583 stmt = m_sqlManager.getPreparedStatement(conn, sqlQuery); 1584 stmt.setString(1, CmsOrganizationalUnit.getSimpleName(groupFqn)); 1585 stmt.setString(2, CmsOrganizationalUnit.SEPARATOR + CmsOrganizationalUnit.getParentFqn(groupFqn)); 1586 1587 res = stmt.executeQuery(); 1588 1589 while (res.next()) { 1590 users.add(internalCreateUser(dbc, res)); 1591 } 1592 } catch (SQLException e) { 1593 throw new CmsDbSqlException( 1594 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 1595 e); 1596 } finally { 1597 m_sqlManager.closeAll(dbc, conn, stmt, res); 1598 } 1599 1600 for (CmsUser user : users) { 1601 Map<String, Object> info = readUserInfos(dbc, user.getId()); 1602 user.setAdditionalInfo(info); 1603 } 1604 return users; 1605 } 1606 1607 /** 1608 * @see org.opencms.db.I_CmsUserDriver#removeAccessControlEntries(org.opencms.db.CmsDbContext, org.opencms.file.CmsProject, org.opencms.util.CmsUUID) 1609 */ 1610 public void removeAccessControlEntries(CmsDbContext dbc, CmsProject project, CmsUUID resource) 1611 throws CmsDataAccessException { 1612 1613 PreparedStatement stmt = null; 1614 Connection conn = null; 1615 1616 try { 1617 conn = m_sqlManager.getConnection(dbc); 1618 stmt = m_sqlManager.getPreparedStatement(conn, project, "C_ACCESS_REMOVE_ALL_1"); 1619 1620 stmt.setString(1, resource.toString()); 1621 1622 stmt.executeUpdate(); 1623 1624 } catch (SQLException e) { 1625 throw new CmsDbSqlException( 1626 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 1627 e); 1628 } finally { 1629 m_sqlManager.closeAll(dbc, conn, stmt, null); 1630 } 1631 } 1632 1633 /** 1634 * @see org.opencms.db.I_CmsUserDriver#removeAccessControlEntriesForPrincipal(org.opencms.db.CmsDbContext, org.opencms.file.CmsProject, org.opencms.file.CmsProject, org.opencms.util.CmsUUID) 1635 */ 1636 public void removeAccessControlEntriesForPrincipal( 1637 CmsDbContext dbc, 1638 CmsProject project, 1639 CmsProject onlineProject, 1640 CmsUUID principal) 1641 throws CmsDataAccessException { 1642 1643 PreparedStatement stmt = null; 1644 Connection conn = null; 1645 // TODO: refactor for only one project at a time 1646 if (dbc.getProjectId().isNullUUID()) { 1647 // offline project available 1648 try { 1649 conn = m_sqlManager.getConnection(dbc); 1650 stmt = m_sqlManager.getPreparedStatement(conn, project, "C_ACCESS_REMOVE_ALL_FOR_PRINCIPAL_1"); 1651 stmt.setString(1, principal.toString()); 1652 stmt.executeUpdate(); 1653 } catch (SQLException e) { 1654 throw new CmsDbSqlException( 1655 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 1656 e); 1657 } finally { 1658 m_sqlManager.closeAll(dbc, conn, stmt, null); 1659 } 1660 } 1661 1662 try { 1663 conn = m_sqlManager.getConnection(dbc); 1664 stmt = m_sqlManager.getPreparedStatement(conn, onlineProject, "C_ACCESS_REMOVE_ALL_FOR_PRINCIPAL_1"); 1665 stmt.setString(1, principal.toString()); 1666 stmt.executeUpdate(); 1667 } catch (SQLException e) { 1668 throw new CmsDbSqlException( 1669 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 1670 e); 1671 } finally { 1672 m_sqlManager.closeAll(dbc, conn, stmt, null); 1673 } 1674 } 1675 1676 /** 1677 * @see org.opencms.db.I_CmsUserDriver#removeAccessControlEntry(org.opencms.db.CmsDbContext, org.opencms.file.CmsProject, org.opencms.util.CmsUUID, org.opencms.util.CmsUUID) 1678 */ 1679 public void removeAccessControlEntry(CmsDbContext dbc, CmsProject project, CmsUUID resource, CmsUUID principal) 1680 throws CmsDataAccessException { 1681 1682 PreparedStatement stmt = null; 1683 Connection conn = null; 1684 1685 try { 1686 conn = m_sqlManager.getConnection(dbc); 1687 stmt = m_sqlManager.getPreparedStatement(conn, project, "C_ACCESS_REMOVE_2"); 1688 1689 stmt.setString(1, resource.toString()); 1690 stmt.setString(2, principal.toString()); 1691 stmt.executeUpdate(); 1692 1693 } catch (SQLException e) { 1694 throw new CmsDbSqlException( 1695 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 1696 e); 1697 } finally { 1698 m_sqlManager.closeAll(dbc, conn, stmt, null); 1699 } 1700 } 1701 1702 /** 1703 * @see org.opencms.db.I_CmsUserDriver#removeResourceFromOrganizationalUnit(org.opencms.db.CmsDbContext, org.opencms.security.CmsOrganizationalUnit, CmsResource) 1704 */ 1705 public void removeResourceFromOrganizationalUnit( 1706 CmsDbContext dbc, 1707 CmsOrganizationalUnit orgUnit, 1708 CmsResource resource) 1709 throws CmsDataAccessException { 1710 1711 // check for root ou 1712 if (orgUnit.getParentFqn() == null) { 1713 throw new CmsDataAccessException( 1714 org.opencms.security.Messages.get().container( 1715 org.opencms.security.Messages.ERR_ORGUNIT_ROOT_EDITION_0)); 1716 } 1717 1718 try { 1719 // read the representing resource 1720 CmsResource ouResource = m_driverManager.readResource( 1721 dbc, 1722 ORGUNIT_BASE_FOLDER + orgUnit.getName(), 1723 CmsResourceFilter.ALL); 1724 1725 // get the associated resources 1726 List<String> vfsPaths = new ArrayList<String>(internalResourcesForOrgUnit(dbc, ouResource)); 1727 1728 // check if associated 1729 if (!vfsPaths.contains(resource.getRootPath())) { 1730 throw new CmsDataAccessException( 1731 Messages.get().container( 1732 Messages.ERR_ORGUNIT_DOESNOT_CONTAINS_RESOURCE_2, 1733 orgUnit.getName(), 1734 dbc.removeSiteRoot(resource.getRootPath()))); 1735 } 1736 if ((vfsPaths.size() == 1) && !orgUnit.hasFlagWebuser()) { 1737 // normal ous have to have at least one resource 1738 throw new CmsDataAccessException( 1739 Messages.get().container( 1740 Messages.ERR_ORGUNIT_REMOVE_LAST_RESOURCE_2, 1741 orgUnit.getName(), 1742 dbc.removeSiteRoot(resource.getRootPath()))); 1743 } 1744 1745 // remove the resource 1746 CmsRelationFilter filter = CmsRelationFilter.TARGETS.filterPath(resource.getRootPath()); 1747 m_driverManager.getVfsDriver(dbc).deleteRelations(dbc, dbc.currentProject().getUuid(), ouResource, filter); 1748 m_driverManager.getVfsDriver(dbc).deleteRelations(dbc, CmsProject.ONLINE_PROJECT_ID, ouResource, filter); 1749 1750 try { 1751 // be sure the project was not deleted 1752 CmsProject project = m_driverManager.readProject(dbc, orgUnit.getProjectId()); 1753 // maintain the default project synchronized 1754 m_driverManager.getProjectDriver(dbc).deleteProjectResource( 1755 dbc, 1756 orgUnit.getProjectId(), 1757 resource.getRootPath()); 1758 1759 OpenCms.fireCmsEvent( 1760 I_CmsEventListener.EVENT_PROJECT_MODIFIED, 1761 Collections.<String, Object> singletonMap("project", project)); 1762 } catch (CmsDbEntryNotFoundException e) { 1763 // ignore 1764 } finally { 1765 Map<String, Object> data = new HashMap<String, Object>(2); 1766 data.put(I_CmsEventListener.KEY_RESOURCE, ouResource); 1767 data.put(I_CmsEventListener.KEY_CHANGE, Integer.valueOf(CmsDriverManager.CHANGED_RESOURCE)); 1768 OpenCms.fireCmsEvent(new CmsEvent(I_CmsEventListener.EVENT_RESOURCE_MODIFIED, data)); 1769 } 1770 } catch (CmsException e) { 1771 throw new CmsDataAccessException(e.getMessageContainer(), e); 1772 } 1773 } 1774 1775 /** 1776 * @see org.opencms.db.I_CmsUserDriver#searchUsers(org.opencms.db.CmsDbContext, org.opencms.file.CmsUserSearchParameters) 1777 */ 1778 public List<CmsUser> searchUsers(CmsDbContext dbc, CmsUserSearchParameters searchParams) 1779 throws CmsDataAccessException { 1780 1781 List<CmsUser> users = new ArrayList<CmsUser>(); 1782 CmsPair<String, List<Object>> queryAndParams = createUserQuery(searchParams, false); 1783 ResultSet res = null; 1784 PreparedStatement stmt = null; 1785 Connection conn = null; 1786 try { 1787 conn = m_sqlManager.getConnection(dbc); 1788 stmt = m_sqlManager.getPreparedStatementForSql(conn, queryAndParams.getFirst()); 1789 CmsDbUtil.fillParameters(stmt, queryAndParams.getSecond()); 1790 res = stmt.executeQuery(); 1791 while (res.next()) { 1792 CmsUser user = internalCreateUser(dbc, res); 1793 users.add(user); 1794 } 1795 } catch (SQLException e) { 1796 throw new CmsDbSqlException( 1797 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 1798 e); 1799 } finally { 1800 m_sqlManager.closeAll(dbc, conn, stmt, res); 1801 } 1802 for (CmsUser user : users) { 1803 Map<String, Object> info = readUserInfos(dbc, user.getId()); 1804 user.setAdditionalInfo(info); 1805 } 1806 return users; 1807 } 1808 1809 /** 1810 * @see org.opencms.db.I_CmsUserDriver#setDriverManager(org.opencms.db.CmsDriverManager) 1811 */ 1812 public void setDriverManager(CmsDriverManager driverManager) { 1813 1814 m_driverManager = driverManager; 1815 } 1816 1817 /** 1818 * @see org.opencms.db.I_CmsUserDriver#setSqlManager(org.opencms.db.CmsSqlManager) 1819 */ 1820 public void setSqlManager(org.opencms.db.CmsSqlManager sqlManager) { 1821 1822 m_sqlManager = (CmsSqlManager)sqlManager; 1823 } 1824 1825 /** 1826 * @see org.opencms.db.I_CmsUserDriver#setUsersOrganizationalUnit(org.opencms.db.CmsDbContext, org.opencms.security.CmsOrganizationalUnit, org.opencms.file.CmsUser) 1827 */ 1828 public void setUsersOrganizationalUnit(CmsDbContext dbc, CmsOrganizationalUnit orgUnit, CmsUser user) 1829 throws CmsDataAccessException { 1830 1831 PreparedStatement stmt = null; 1832 Connection conn = null; 1833 1834 try { 1835 conn = m_sqlManager.getConnection(dbc); 1836 stmt = m_sqlManager.getPreparedStatement(conn, "C_USERS_SET_ORGUNIT_2"); 1837 1838 if (orgUnit == null) { 1839 stmt.setString(1, null); 1840 } else { 1841 stmt.setString(1, CmsOrganizationalUnit.SEPARATOR + orgUnit.getName()); 1842 } 1843 stmt.setString(2, user.getId().toString()); 1844 1845 stmt.executeUpdate(); 1846 } catch (SQLException e) { 1847 throw new CmsDbSqlException( 1848 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 1849 e); 1850 } finally { 1851 m_sqlManager.closeAll(dbc, conn, stmt, null); 1852 } 1853 } 1854 1855 /** 1856 * @see org.opencms.db.I_CmsUserDriver#writeAccessControlEntry(org.opencms.db.CmsDbContext, org.opencms.file.CmsProject, org.opencms.security.CmsAccessControlEntry) 1857 */ 1858 public void writeAccessControlEntry(CmsDbContext dbc, CmsProject project, CmsAccessControlEntry acEntry) 1859 throws CmsDataAccessException { 1860 1861 PreparedStatement stmt = null; 1862 Connection conn = null; 1863 ResultSet res = null; 1864 CmsAccessControlEntry ace = null; 1865 1866 try { 1867 conn = m_sqlManager.getConnection(dbc); 1868 stmt = m_sqlManager.getPreparedStatement(conn, project, "C_ACCESS_READ_ENTRY_2"); 1869 1870 stmt.setString(1, acEntry.getResource().toString()); 1871 stmt.setString(2, acEntry.getPrincipal().toString()); 1872 1873 res = stmt.executeQuery(); 1874 if (res.next()) { 1875 ace = internalCreateAce(res); 1876 } 1877 1878 } catch (SQLException e) { 1879 throw new CmsDbSqlException( 1880 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 1881 e); 1882 } finally { 1883 m_sqlManager.closeAll(dbc, conn, stmt, res); 1884 } 1885 1886 if (ace == null) { 1887 m_driverManager.getUserDriver(dbc).createAccessControlEntry( 1888 dbc, 1889 project, 1890 acEntry.getResource(), 1891 acEntry.getPrincipal(), 1892 acEntry.getAllowedPermissions(), 1893 acEntry.getDeniedPermissions(), 1894 acEntry.getFlags()); 1895 return; 1896 } else { 1897 try { 1898 conn = m_sqlManager.getConnection(dbc); 1899 1900 // otherwise update the already existing entry 1901 stmt = m_sqlManager.getPreparedStatement(conn, project, "C_ACCESS_UPDATE_5"); 1902 1903 stmt.setInt(1, acEntry.getAllowedPermissions()); 1904 stmt.setInt(2, acEntry.getDeniedPermissions()); 1905 stmt.setInt(3, acEntry.getFlags()); 1906 stmt.setString(4, acEntry.getResource().toString()); 1907 stmt.setString(5, acEntry.getPrincipal().toString()); 1908 1909 stmt.executeUpdate(); 1910 } catch (SQLException e) { 1911 throw new CmsDbSqlException( 1912 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 1913 e); 1914 } finally { 1915 m_sqlManager.closeAll(dbc, conn, stmt, null); 1916 } 1917 } 1918 1919 } 1920 1921 /** 1922 * @see org.opencms.db.I_CmsUserDriver#writeGroup(org.opencms.db.CmsDbContext, org.opencms.file.CmsGroup) 1923 */ 1924 public void writeGroup(CmsDbContext dbc, CmsGroup group) throws CmsDataAccessException { 1925 1926 PreparedStatement stmt = null; 1927 Connection conn = null; 1928 if (group != null) { 1929 try { 1930 conn = getSqlManager().getConnection(dbc); 1931 stmt = m_sqlManager.getPreparedStatement(conn, "C_GROUPS_WRITE_GROUP_4"); 1932 1933 stmt.setString(1, m_sqlManager.validateEmpty(group.getDescription())); 1934 stmt.setInt(2, group.getFlags()); 1935 stmt.setString(3, group.getParentId().toString()); 1936 stmt.setString(4, group.getId().toString()); 1937 stmt.executeUpdate(); 1938 1939 } catch (SQLException e) { 1940 throw new CmsDbSqlException( 1941 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 1942 e); 1943 } finally { 1944 m_sqlManager.closeAll(dbc, conn, stmt, null); 1945 } 1946 } else { 1947 throw new CmsDbEntryNotFoundException( 1948 org.opencms.db.Messages.get().container(org.opencms.db.Messages.ERR_UNKNOWN_GROUP_1, "null")); 1949 } 1950 } 1951 1952 /** 1953 * @see org.opencms.db.I_CmsUserDriver#writeOrganizationalUnit(org.opencms.db.CmsDbContext, org.opencms.security.CmsOrganizationalUnit) 1954 */ 1955 public void writeOrganizationalUnit(CmsDbContext dbc, CmsOrganizationalUnit organizationalUnit) 1956 throws CmsDataAccessException { 1957 1958 try { 1959 CmsResource resource = m_driverManager.readResource( 1960 dbc, 1961 organizationalUnit.getId(), 1962 CmsResourceFilter.DEFAULT); 1963 1964 // write the properties 1965 internalWriteOrgUnitProperty( 1966 dbc, 1967 resource, 1968 new CmsProperty(ORGUNIT_PROPERTY_DESCRIPTION, organizationalUnit.getDescription(), null)); 1969 1970 CmsUUID projectId = ((dbc.getProjectId() == null) || dbc.getProjectId().isNullUUID()) 1971 ? dbc.currentProject().getUuid() 1972 : dbc.getProjectId(); 1973 // update the resource flags 1974 resource.setFlags(organizationalUnit.getFlags() | CmsResource.FLAG_INTERNAL); 1975 m_driverManager.writeResource(dbc, resource); 1976 resource.setState(CmsResource.STATE_UNCHANGED); 1977 m_driverManager.getVfsDriver(dbc).writeResource(dbc, projectId, resource, CmsDriverManager.NOTHING_CHANGED); 1978 1979 if (!dbc.currentProject().isOnlineProject()) { 1980 // online persistence 1981 CmsProject onlineProject = m_driverManager.readProject(dbc, CmsProject.ONLINE_PROJECT_ID); 1982 resource.setState(CmsResource.STATE_UNCHANGED); 1983 m_driverManager.getVfsDriver( 1984 dbc).writeResource(dbc, onlineProject.getUuid(), resource, CmsDriverManager.NOTHING_CHANGED); 1985 } 1986 1987 OpenCms.fireCmsEvent(I_CmsEventListener.EVENT_CLEAR_ONLINE_CACHES, null); 1988 } catch (CmsException e) { 1989 throw new CmsDataAccessException(e.getMessageContainer(), e); 1990 } 1991 } 1992 1993 /** 1994 * @see org.opencms.db.I_CmsUserDriver#writePassword(org.opencms.db.CmsDbContext, java.lang.String, java.lang.String, java.lang.String) 1995 */ 1996 public void writePassword(CmsDbContext dbc, String userFqn, String oldPassword, String newPassword) 1997 throws CmsDataAccessException, CmsPasswordEncryptionException { 1998 1999 PreparedStatement stmt = null; 2000 Connection conn = null; 2001 2002 // check if the old password is valid 2003 if (oldPassword != null) { 2004 readUser(dbc, userFqn, oldPassword, ""); 2005 } 2006 String pwd = newPassword; 2007 if (dbc.getRequestContext().getAttribute(REQ_ATTR_DONT_DIGEST_PASSWORD) == null) { 2008 pwd = OpenCms.getPasswordHandler().digest(newPassword); 2009 } 2010 2011 try { 2012 conn = getSqlManager().getConnection(dbc); 2013 stmt = m_sqlManager.getPreparedStatement(conn, "C_USERS_SET_PWD_3"); 2014 stmt.setString(1, pwd); 2015 stmt.setString(2, CmsOrganizationalUnit.getSimpleName(userFqn)); 2016 stmt.setString(3, CmsOrganizationalUnit.SEPARATOR + CmsOrganizationalUnit.getParentFqn(userFqn)); 2017 stmt.executeUpdate(); 2018 } catch (SQLException e) { 2019 throw new CmsDbSqlException( 2020 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2021 e); 2022 } finally { 2023 m_sqlManager.closeAll(dbc, conn, stmt, null); 2024 } 2025 } 2026 2027 /** 2028 * @see org.opencms.db.I_CmsUserDriver#writeUser(org.opencms.db.CmsDbContext, org.opencms.file.CmsUser) 2029 */ 2030 public void writeUser(CmsDbContext dbc, CmsUser user) throws CmsDataAccessException { 2031 2032 // get the login attribute 2033 String att_login = (String)dbc.getAttribute(CmsDriverManager.ATTRIBUTE_LOGIN); 2034 2035 PreparedStatement stmt = null; 2036 Connection conn = null; 2037 2038 // if the login attribute is set, do only update the last login information of this user 2039 // otherwise write the complete user data 2040 if (CmsStringUtil.isNotEmpty(att_login)) { 2041 2042 try { 2043 conn = getSqlManager().getConnection(dbc); 2044 stmt = m_sqlManager.getPreparedStatement(conn, "C_USERS_WRITE_2"); 2045 // write data to database 2046 stmt.setLong(1, user.getLastlogin()); 2047 stmt.setString(2, user.getId().toString()); 2048 stmt.executeUpdate(); 2049 } catch (SQLException e) { 2050 throw new CmsDbSqlException( 2051 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2052 e); 2053 } finally { 2054 m_sqlManager.closeAll(dbc, conn, stmt, null); 2055 } 2056 // store user info values which may have been modified by the login code 2057 internalWriteUserInfos(dbc, user.getId(), user.getAdditionalInfo()); 2058 } else { 2059 2060 try { 2061 conn = getSqlManager().getConnection(dbc); 2062 stmt = m_sqlManager.getPreparedStatement(conn, "C_USERS_WRITE_6"); 2063 // write data to database 2064 stmt.setString(1, m_sqlManager.validateEmpty(user.getFirstname())); 2065 stmt.setString(2, m_sqlManager.validateEmpty(user.getLastname())); 2066 stmt.setString(3, m_sqlManager.validateEmpty(user.getEmail())); 2067 stmt.setLong(4, user.getLastlogin()); 2068 stmt.setInt(5, user.getFlags()); 2069 stmt.setString(6, user.getId().toString()); 2070 stmt.executeUpdate(); 2071 } catch (SQLException e) { 2072 throw new CmsDbSqlException( 2073 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2074 e); 2075 } finally { 2076 m_sqlManager.closeAll(dbc, conn, stmt, null); 2077 } 2078 internalWriteUserInfos(dbc, user.getId(), user.getAdditionalInfo()); 2079 } 2080 } 2081 2082 /** 2083 * @see org.opencms.db.I_CmsUserDriver#writeUserInfo(org.opencms.db.CmsDbContext, org.opencms.util.CmsUUID, java.lang.String, java.lang.Object) 2084 */ 2085 public void writeUserInfo(CmsDbContext dbc, CmsUUID userId, String key, Object value) 2086 throws CmsDataAccessException { 2087 2088 // analyse the dbc attribute what to do here 2089 String mode = (String)dbc.getAttribute(ATTRIBUTE_USERADDINFO); 2090 2091 // delete the user info 2092 if (CmsStringUtil.isNotEmpty(mode) && mode.equals(ATTRIBUTE_USERADDINFO_VALUE_DELETE)) { 2093 internalDeleteUserInfo(dbc, userId, key); 2094 } else if (CmsStringUtil.isNotEmpty(mode) && mode.equals(ATTRIBUTE_USERADDINFO_VALUE_UPDATE)) { 2095 internalUpdateUserInfo(dbc, userId, key, value); 2096 } else { 2097 // default is to insert or update a new value 2098 internalWriteUserInfo(dbc, userId, key, value); 2099 } 2100 } 2101 2102 /** 2103 * Returns a sql query to select groups.<p> 2104 * 2105 * @param mainQuery the main select sql query 2106 * @param includeSubOus if groups in sub-ous should be included in the selection 2107 * @param readRoles if groups or roles whould be selected 2108 * 2109 * @return a sql query to select groups 2110 */ 2111 protected String createRoleQuery(String mainQuery, boolean includeSubOus, boolean readRoles) { 2112 2113 String sqlQuery = m_sqlManager.readQuery(mainQuery); 2114 sqlQuery += " "; 2115 if (includeSubOus) { 2116 sqlQuery += m_sqlManager.readQuery("C_GROUPS_GROUP_OU_LIKE_1"); 2117 } else { 2118 sqlQuery += m_sqlManager.readQuery("C_GROUPS_GROUP_OU_EQUALS_1"); 2119 } 2120 sqlQuery += AND_CONDITION; 2121 if (readRoles) { 2122 sqlQuery += m_sqlManager.readQuery("C_GROUPS_SELECT_ROLES_1"); 2123 } else { 2124 sqlQuery += m_sqlManager.readQuery("C_GROUPS_SELECT_GROUPS_1"); 2125 } 2126 sqlQuery += " "; 2127 sqlQuery += m_sqlManager.readQuery("C_GROUPS_ORDER_0"); 2128 return sqlQuery; 2129 } 2130 2131 /** 2132 * Creates a query for searching users.<p> 2133 * 2134 * @param searchParams the user search criteria 2135 * @param countOnly if true, the query will only count the total number of results instead of returning them 2136 * 2137 * @return a pair consisting of the query string and its parameters 2138 */ 2139 protected CmsPair<String, List<Object>> createUserQuery(CmsUserSearchParameters searchParams, boolean countOnly) { 2140 2141 CmsUserQueryBuilder queryBuilder = createUserQueryBuilder(); 2142 return queryBuilder.createUserQuery(searchParams, countOnly); 2143 } 2144 2145 /** 2146 * Creates a new user query builder.<p> 2147 * 2148 * @return the new user query builder 2149 */ 2150 protected CmsUserQueryBuilder createUserQueryBuilder() { 2151 2152 return new CmsUserQueryBuilder(); 2153 } 2154 2155 /** 2156 * Internal helper method to create an access control entry from a database record.<p> 2157 * 2158 * @param res resultset of the current query 2159 * 2160 * @return a new {@link CmsAccessControlEntry} initialized with the values from the current database record 2161 * 2162 * @throws SQLException if something goes wrong 2163 */ 2164 protected CmsAccessControlEntry internalCreateAce(ResultSet res) throws SQLException { 2165 2166 return internalCreateAce(res, new CmsUUID(res.getString(m_sqlManager.readQuery("C_ACCESS_RESOURCE_ID_0")))); 2167 } 2168 2169 /** 2170 * Internal helper method to create an access control entry from a database record.<p> 2171 * 2172 * @param res resultset of the current query 2173 * @param newId the id of the new access control entry 2174 * 2175 * @return a new {@link CmsAccessControlEntry} initialized with the values from the current database record 2176 * 2177 * @throws SQLException if something goes wrong 2178 */ 2179 protected CmsAccessControlEntry internalCreateAce(ResultSet res, CmsUUID newId) throws SQLException { 2180 2181 return new CmsAccessControlEntry( 2182 newId, 2183 new CmsUUID(res.getString(m_sqlManager.readQuery("C_ACCESS_PRINCIPAL_ID_0"))), 2184 res.getInt(m_sqlManager.readQuery("C_ACCESS_ACCESS_ALLOWED_0")), 2185 res.getInt(m_sqlManager.readQuery("C_ACCESS_ACCESS_DENIED_0")), 2186 res.getInt(m_sqlManager.readQuery("C_ACCESS_ACCESS_FLAGS_0"))); 2187 } 2188 2189 /** 2190 * Creates the default groups and user for the given organizational unit.<p> 2191 * 2192 * @param dbc the database context 2193 * @param ouFqn the fully qualified name of the organizational unit to create the principals for 2194 * @param ouDescription the description of the given organizational unit 2195 * @param webuser the webuser ou flag 2196 * 2197 * @throws CmsException if something goes wrong 2198 */ 2199 protected void internalCreateDefaultGroups(CmsDbContext dbc, String ouFqn, String ouDescription, boolean webuser) 2200 throws CmsException { 2201 2202 // create roles 2203 String rootAdminRole = CmsRole.ROOT_ADMIN.getGroupName(); 2204 boolean isRootOu = CmsOrganizationalUnit.getParentFqn(ouFqn) == null; 2205 try { 2206 for (CmsRole role : CmsRole.getSystemRoles()) { 2207 if (webuser && (role != CmsRole.ACCOUNT_MANAGER)) { 2208 // if webuser ou and not account manager role 2209 continue; 2210 } 2211 if (role.isOrganizationalUnitIndependent() && !isRootOu) { 2212 // if role is ou independent and not in the root ou 2213 continue; 2214 } 2215 String groupName = ouFqn + role.getGroupName(); 2216 int flags = I_CmsPrincipal.FLAG_ENABLED | I_CmsPrincipal.FLAG_GROUP_ROLE; 2217 if (!existsGroup(dbc, groupName)) { 2218 createGroup(dbc, CmsUUID.getConstantUUID(groupName), groupName, "A system role group", flags, null); 2219 } 2220 } 2221 if (isRootOu && CmsLog.INIT.isInfoEnabled()) { 2222 CmsLog.INIT.info(Messages.get().getBundle().key(Messages.INIT_SYSTEM_ROLES_CREATED_0)); 2223 } 2224 } catch (CmsException e) { 2225 if (isRootOu && CmsLog.INIT.isErrorEnabled()) { 2226 CmsLog.INIT.error(Messages.get().getBundle().key(Messages.INIT_SYSTEM_ROLES_CREATION_FAILED_0), e); 2227 } 2228 throw new CmsInitException(Messages.get().container(Messages.ERR_INITIALIZING_USER_DRIVER_0), e); 2229 } 2230 2231 if (dbc.getAttribute(CmsDriverManager.ATTR_INIT_OU) != null) { 2232 return; 2233 } 2234 2235 if (webuser) { 2236 // no default groups for webuser ou 2237 return; 2238 } 2239 2240 // create groups 2241 String administratorsGroup = ouFqn + OpenCms.getDefaultUsers().getGroupAdministrators(); 2242 String guestGroup = ouFqn + OpenCms.getDefaultUsers().getGroupGuests(); 2243 String usersGroup = ouFqn + OpenCms.getDefaultUsers().getGroupUsers(); 2244 String guestUser = ouFqn + OpenCms.getDefaultUsers().getUserGuest(); 2245 String adminUser = ouFqn + OpenCms.getDefaultUsers().getUserAdmin(); 2246 String exportUser = ouFqn + OpenCms.getDefaultUsers().getUserExport(); 2247 String deleteUser = ouFqn + OpenCms.getDefaultUsers().getUserDeletedResource(); 2248 2249 if (existsGroup(dbc, administratorsGroup)) { 2250 if (isRootOu) { 2251 // check the flags of existing groups, for compatibility checks 2252 internalUpdateRoleGroup(dbc, administratorsGroup, CmsRole.ROOT_ADMIN); 2253 internalUpdateRoleGroup(dbc, usersGroup, CmsRole.ELEMENT_AUTHOR.forOrgUnit(ouFqn)); 2254 } 2255 return; 2256 } 2257 String parentOu = CmsOrganizationalUnit.getParentFqn(ouFqn); 2258 String groupDescription = (CmsStringUtil.isNotEmptyOrWhitespaceOnly(ouDescription) 2259 ? CmsMacroResolver.localizedKeyMacro( 2260 Messages.GUI_DEFAULTGROUP_OU_USERS_DESCRIPTION_1, 2261 new String[] {ouDescription}) 2262 : CmsMacroResolver.localizedKeyMacro(Messages.GUI_DEFAULTGROUP_ROOT_USERS_DESCRIPTION_0, null)); 2263 createGroup( 2264 dbc, 2265 CmsUUID.getConstantUUID(usersGroup), 2266 usersGroup, 2267 groupDescription, 2268 I_CmsPrincipal.FLAG_ENABLED | CmsRole.ELEMENT_AUTHOR.getVirtualGroupFlags(), 2269 null); 2270 2271 if (parentOu != null) { 2272 // default users/groups(except the users group) are only for the root ou 2273 return; 2274 } 2275 2276 CmsGroup guests = createGroup( 2277 dbc, 2278 CmsUUID.getConstantUUID(guestGroup), 2279 guestGroup, 2280 CmsMacroResolver.localizedKeyMacro(Messages.GUI_DEFAULTGROUP_ROOT_GUESTS_DESCRIPTION_0, null), 2281 I_CmsPrincipal.FLAG_ENABLED, 2282 null); 2283 2284 int flags = CmsRole.ROOT_ADMIN.getVirtualGroupFlags(); 2285 createGroup( 2286 dbc, 2287 CmsUUID.getConstantUUID(administratorsGroup), 2288 administratorsGroup, 2289 CmsMacroResolver.localizedKeyMacro(Messages.GUI_DEFAULTGROUP_ROOT_ADMINS_DESCRIPTION_0, null), 2290 I_CmsPrincipal.FLAG_ENABLED | flags, 2291 null); 2292 2293 CmsUser guest = createUser( 2294 dbc, 2295 CmsUUID.getConstantUUID(guestUser), 2296 guestUser, 2297 OpenCms.getPasswordHandler().digest((new CmsUUID()).toString()), 2298 " ", 2299 " ", 2300 " ", 2301 0, 2302 I_CmsPrincipal.FLAG_ENABLED, 2303 0, 2304 Collections.singletonMap( 2305 CmsUserSettings.ADDITIONAL_INFO_DESCRIPTION, 2306 (Object)CmsMacroResolver.localizedKeyMacro(Messages.GUI_DEFAULTUSER_ROOT_GUEST_DESCRIPTION_0, null))); 2307 createUserInGroup(dbc, guest.getId(), guests.getId()); 2308 2309 CmsUser admin = createUser( 2310 dbc, 2311 CmsUUID.getConstantUUID(adminUser), 2312 adminUser, 2313 OpenCms.getPasswordHandler().digest("admin"), 2314 " ", 2315 " ", 2316 " ", 2317 0, 2318 I_CmsPrincipal.FLAG_ENABLED, 2319 0, 2320 Collections.singletonMap( 2321 CmsUserSettings.ADDITIONAL_INFO_DESCRIPTION, 2322 (Object)CmsMacroResolver.localizedKeyMacro(Messages.GUI_DEFAULTUSER_ROOT_ADMIN_DESCRIPTION_0, null))); 2323 createUserInGroup(dbc, admin.getId(), CmsUUID.getConstantUUID(CmsRole.ROOT_ADMIN.getGroupName())); 2324 createUserInGroup(dbc, admin.getId(), CmsUUID.getConstantUUID(administratorsGroup)); 2325 2326 if (!OpenCms.getDefaultUsers().getUserExport().equals(OpenCms.getDefaultUsers().getUserAdmin()) 2327 && !OpenCms.getDefaultUsers().getUserExport().equals(OpenCms.getDefaultUsers().getUserGuest())) { 2328 2329 CmsUser export = createUser( 2330 dbc, 2331 CmsUUID.getConstantUUID(exportUser), 2332 exportUser, 2333 OpenCms.getPasswordHandler().digest((new CmsUUID()).toString()), 2334 " ", 2335 " ", 2336 " ", 2337 0, 2338 I_CmsPrincipal.FLAG_ENABLED, 2339 0, 2340 Collections.singletonMap( 2341 CmsUserSettings.ADDITIONAL_INFO_DESCRIPTION, 2342 (Object)CmsMacroResolver.localizedKeyMacro( 2343 Messages.GUI_DEFAULTUSER_ROOT_EXPORT_DESCRIPTION_0, 2344 null))); 2345 createUserInGroup(dbc, export.getId(), guests.getId()); 2346 } 2347 2348 if (!OpenCms.getDefaultUsers().getUserDeletedResource().equals(OpenCms.getDefaultUsers().getUserAdmin()) 2349 && !OpenCms.getDefaultUsers().getUserDeletedResource().equals(OpenCms.getDefaultUsers().getUserGuest()) 2350 && !OpenCms.getDefaultUsers().getUserDeletedResource().equals(OpenCms.getDefaultUsers().getUserExport())) { 2351 2352 createUser( 2353 dbc, 2354 CmsUUID.getConstantUUID(deleteUser), 2355 deleteUser, 2356 OpenCms.getPasswordHandler().digest((new CmsUUID()).toString()), 2357 " ", 2358 " ", 2359 " ", 2360 0, 2361 I_CmsPrincipal.FLAG_ENABLED, 2362 0, 2363 Collections.singletonMap( 2364 CmsUserSettings.ADDITIONAL_INFO_DESCRIPTION, 2365 (Object)CmsMacroResolver.localizedKeyMacro( 2366 Messages.GUI_DEFAULTUSER_ROOT_DELETED_DESCRIPTION_0, 2367 null))); 2368 } 2369 2370 if (CmsLog.INIT.isInfoEnabled()) { 2371 CmsLog.INIT.info(Messages.get().getBundle().key(Messages.INIT_DEFAULT_USERS_CREATED_0)); 2372 } 2373 } 2374 2375 /** 2376 * Semi-constructor to create a {@link CmsGroup} instance from a JDBC result set. 2377 * 2378 * @param res the JDBC ResultSet 2379 * @return CmsGroup the new CmsGroup object 2380 * 2381 * @throws SQLException in case the result set does not include a requested table attribute 2382 */ 2383 protected CmsGroup internalCreateGroup(ResultSet res) throws SQLException { 2384 2385 String ou = CmsOrganizationalUnit.removeLeadingSeparator( 2386 res.getString(m_sqlManager.readQuery("C_GROUPS_GROUP_OU_0"))); 2387 String description = res.getString(m_sqlManager.readQuery("C_GROUPS_GROUP_DESCRIPTION_0")); 2388 return new CmsGroup( 2389 new CmsUUID(res.getString(m_sqlManager.readQuery("C_GROUPS_GROUP_ID_0"))), 2390 new CmsUUID(res.getString(m_sqlManager.readQuery("C_GROUPS_PARENT_GROUP_ID_0"))), 2391 ou + res.getString(m_sqlManager.readQuery("C_GROUPS_GROUP_NAME_0")), 2392 description, 2393 res.getInt(m_sqlManager.readQuery("C_GROUPS_GROUP_FLAGS_0"))); 2394 } 2395 2396 /** 2397 * Returns the organizational unit represented by the given resource.<p> 2398 * 2399 * @param dbc the current db context 2400 * @param resource the resource that represents an organizational unit 2401 * 2402 * @return the organizational unit represented by the given resource 2403 * 2404 * @throws CmsException if something goes wrong 2405 */ 2406 protected CmsOrganizationalUnit internalCreateOrgUnitFromResource(CmsDbContext dbc, CmsResource resource) 2407 throws CmsException { 2408 2409 if (!resource.getRootPath().startsWith(ORGUNIT_BASE_FOLDER)) { 2410 throw new CmsDataAccessException( 2411 Messages.get().container(Messages.ERR_READ_ORGUNIT_1, resource.getRootPath())); 2412 } 2413 // get the data 2414 String name = resource.getRootPath().substring(ORGUNIT_BASE_FOLDER.length()); 2415 if ((name.length() > 0) && !name.endsWith(CmsOrganizationalUnit.SEPARATOR)) { 2416 name += CmsOrganizationalUnit.SEPARATOR; 2417 } 2418 String description = m_driverManager.readPropertyObject( 2419 dbc, 2420 resource, 2421 ORGUNIT_PROPERTY_DESCRIPTION, 2422 false).getStructureValue(); 2423 int flags = (resource.getFlags() & ~CmsResource.FLAG_INTERNAL); // remove the internal flag 2424 String projectId = m_driverManager.readPropertyObject( 2425 dbc, 2426 resource, 2427 ORGUNIT_PROPERTY_PROJECTID, 2428 false).getStructureValue(); 2429 // create the object 2430 return new CmsOrganizationalUnit( 2431 resource.getStructureId(), 2432 name, 2433 description, 2434 flags, 2435 (projectId == null ? null : new CmsUUID(projectId))); 2436 } 2437 2438 /** 2439 * Creates a folder with the given path an properties, offline AND online.<p> 2440 * 2441 * @param dbc the current database context 2442 * @param path the path to create the folder 2443 * @param flags the resource flags 2444 * 2445 * @return the new created offline folder 2446 * 2447 * @throws CmsException if something goes wrong 2448 */ 2449 protected CmsResource internalCreateResourceForOrgUnit(CmsDbContext dbc, String path, int flags) 2450 throws CmsException { 2451 2452 // create the offline folder 2453 CmsResource resource = new CmsFolder( 2454 new CmsUUID(), 2455 new CmsUUID(), 2456 path, 2457 CmsResourceTypeFolder.RESOURCE_TYPE_ID, 2458 (CmsResource.FLAG_INTERNAL | flags), 2459 dbc.currentProject().getUuid(), 2460 CmsResource.STATE_NEW, 2461 0, 2462 dbc.currentUser().getId(), 2463 0, 2464 dbc.currentUser().getId(), 2465 CmsResource.DATE_RELEASED_DEFAULT, 2466 CmsResource.DATE_EXPIRED_DEFAULT, 2467 0); 2468 2469 CmsUUID projectId = ((dbc.getProjectId() == null) || dbc.getProjectId().isNullUUID()) 2470 ? dbc.currentProject().getUuid() 2471 : dbc.getProjectId(); 2472 2473 m_driverManager.getVfsDriver(dbc).createResource(dbc, projectId, resource, null); 2474 resource.setState(CmsResource.STATE_UNCHANGED); 2475 m_driverManager.getVfsDriver(dbc).writeResource(dbc, projectId, resource, CmsDriverManager.NOTHING_CHANGED); 2476 2477 if (!dbc.currentProject().isOnlineProject() && dbc.getProjectId().isNullUUID()) { 2478 // online persistence 2479 CmsProject onlineProject = m_driverManager.readProject(dbc, CmsProject.ONLINE_PROJECT_ID); 2480 m_driverManager.getVfsDriver(dbc).createResource(dbc, onlineProject.getUuid(), resource, null); 2481 } 2482 2483 // clear the internal caches 2484 OpenCms.getMemoryMonitor().clearAccessControlListCache(); 2485 OpenCms.getMemoryMonitor().flushCache(CmsMemoryMonitor.CacheType.PROPERTY); 2486 OpenCms.getMemoryMonitor().flushCache(CmsMemoryMonitor.CacheType.PROPERTY_LIST); 2487 2488 // fire an event that a new resource has been created 2489 OpenCms.fireCmsEvent( 2490 new CmsEvent( 2491 I_CmsEventListener.EVENT_RESOURCE_CREATED, 2492 Collections.<String, Object> singletonMap(I_CmsEventListener.KEY_RESOURCE, resource))); 2493 2494 return resource; 2495 } 2496 2497 /** 2498 * Semi-constructor to create a {@link CmsUser} instance from a JDBC result set.<p> 2499 * 2500 * @param dbc the current database context 2501 * @param res the JDBC ResultSet 2502 * 2503 * @return the new CmsUser object 2504 * 2505 * @throws SQLException in case the result set does not include a requested table attribute 2506 */ 2507 protected CmsUser internalCreateUser(CmsDbContext dbc, ResultSet res) throws SQLException { 2508 2509 String userName = res.getString(m_sqlManager.readQuery("C_USERS_USER_NAME_0")); 2510 String ou = CmsOrganizationalUnit.removeLeadingSeparator( 2511 res.getString(m_sqlManager.readQuery("C_USERS_USER_OU_0"))); 2512 CmsUUID userId = new CmsUUID(res.getString(m_sqlManager.readQuery("C_USERS_USER_ID_0"))); 2513 2514 if (LOG.isDebugEnabled()) { 2515 LOG.debug(Messages.get().getBundle().key(Messages.LOG_DBG_CREATE_USER_1, userName)); 2516 } 2517 2518 return new CmsUser( 2519 userId, 2520 ou + userName, 2521 res.getString(m_sqlManager.readQuery("C_USERS_USER_PASSWORD_0")), 2522 res.getString(m_sqlManager.readQuery("C_USERS_USER_FIRSTNAME_0")), 2523 res.getString(m_sqlManager.readQuery("C_USERS_USER_LASTNAME_0")), 2524 res.getString(m_sqlManager.readQuery("C_USERS_USER_EMAIL_0")), 2525 res.getLong(m_sqlManager.readQuery("C_USERS_USER_LASTLOGIN_0")), 2526 res.getInt(m_sqlManager.readQuery("C_USERS_USER_FLAGS_0")), 2527 res.getLong(m_sqlManager.readQuery("C_USERS_USER_DATECREATED_0")), 2528 null); 2529 } 2530 2531 /** 2532 * Deletes a resource representing a organizational unit, offline AND online.<p> 2533 * 2534 * @param dbc the current database context 2535 * @param resource the resource to delete 2536 * 2537 * @throws CmsException if something goes wrong 2538 */ 2539 protected void internalDeleteOrgUnitResource(CmsDbContext dbc, CmsResource resource) throws CmsException { 2540 2541 CmsRelationFilter filter = CmsRelationFilter.TARGETS; 2542 2543 // first the online version 2544 if (!dbc.currentProject().isOnlineProject()) { 2545 // online persistence 2546 CmsProject project = dbc.currentProject(); 2547 dbc.getRequestContext().setCurrentProject(m_driverManager.readProject(dbc, CmsProject.ONLINE_PROJECT_ID)); 2548 2549 try { 2550 // delete properties 2551 m_driverManager.getVfsDriver(dbc).deletePropertyObjects( 2552 dbc, 2553 CmsProject.ONLINE_PROJECT_ID, 2554 resource, 2555 CmsProperty.DELETE_OPTION_DELETE_STRUCTURE_AND_RESOURCE_VALUES); 2556 2557 // remove the online folder only if it is really deleted offline 2558 m_driverManager.getVfsDriver(dbc).removeFolder(dbc, dbc.currentProject(), resource); 2559 2560 // remove ACL 2561 m_driverManager.getUserDriver(dbc).removeAccessControlEntries( 2562 dbc, 2563 dbc.currentProject(), 2564 resource.getResourceId()); 2565 2566 // delete relations 2567 m_driverManager.getVfsDriver( 2568 dbc).deleteRelations(dbc, dbc.getRequestContext().getCurrentProject().getUuid(), resource, filter); 2569 } finally { 2570 dbc.getRequestContext().setCurrentProject(project); 2571 } 2572 } 2573 // delete properties 2574 m_driverManager.getVfsDriver(dbc).deletePropertyObjects( 2575 dbc, 2576 CmsProject.ONLINE_PROJECT_ID, 2577 resource, 2578 CmsProperty.DELETE_OPTION_DELETE_STRUCTURE_AND_RESOURCE_VALUES); 2579 2580 // remove the online folder only if it is really deleted offline 2581 m_driverManager.getVfsDriver(dbc).removeFolder(dbc, dbc.currentProject(), resource); 2582 2583 // remove ACL 2584 m_driverManager.getUserDriver(dbc).removeAccessControlEntries( 2585 dbc, 2586 dbc.currentProject(), 2587 resource.getResourceId()); 2588 2589 // delete relations 2590 m_driverManager.getVfsDriver( 2591 dbc).deleteRelations(dbc, dbc.getRequestContext().getCurrentProject().getUuid(), resource, filter); 2592 2593 // flush all relevant caches 2594 OpenCms.getMemoryMonitor().clearAccessControlListCache(); 2595 OpenCms.getMemoryMonitor().flushCache(CmsMemoryMonitor.CacheType.PROPERTY); 2596 OpenCms.getMemoryMonitor().flushCache(CmsMemoryMonitor.CacheType.PROPERTY_LIST); 2597 OpenCms.getMemoryMonitor().flushCache(CmsMemoryMonitor.CacheType.PROJECT_RESOURCES); 2598 2599 // fire events 2600 OpenCms.fireCmsEvent( 2601 new CmsEvent( 2602 I_CmsEventListener.EVENT_RESOURCE_DELETED, 2603 Collections.<String, Object> singletonMap( 2604 I_CmsEventListener.KEY_RESOURCES, 2605 Collections.singletonList(resource)))); 2606 OpenCms.fireCmsEvent( 2607 new CmsEvent( 2608 I_CmsEventListener.EVENT_RESOURCE_AND_PROPERTIES_MODIFIED, 2609 Collections.<String, Object> singletonMap(I_CmsEventListener.KEY_RESOURCE, resource))); 2610 } 2611 2612 /** 2613 * Deletes an additional user info.<p> 2614 * @param dbc the current dbc 2615 * @param userId the user to delete additional info from 2616 * @param key the additional info to delete 2617 * @throws CmsDataAccessException if something goes wrong 2618 */ 2619 protected void internalDeleteUserInfo(CmsDbContext dbc, CmsUUID userId, String key) throws CmsDataAccessException { 2620 2621 PreparedStatement stmt = null; 2622 Connection conn = null; 2623 2624 try { 2625 conn = getSqlManager().getConnection(dbc); 2626 stmt = m_sqlManager.getPreparedStatement(conn, "C_USERDATA_DELETE_2"); 2627 // write data to database 2628 stmt.setString(1, userId.toString()); 2629 stmt.setString(2, key); 2630 stmt.executeUpdate(); 2631 } catch (SQLException e) { 2632 throw new CmsDbSqlException( 2633 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2634 e); 2635 } finally { 2636 m_sqlManager.closeAll(dbc, conn, stmt, null); 2637 } 2638 } 2639 2640 /** 2641 * Internal implementation for reading users of an OU, with or without additional infos.<p> 2642 * 2643 * @param dbc the database context 2644 * @param orgUnit the OU 2645 * @param recursive if true, sub-OUs should be searched 2646 * @param readAdditionalInfos if true, additional infos should be read 2647 * @return the users which have been read 2648 * @throws CmsDataAccessException if something goes wrong 2649 */ 2650 protected List<CmsUser> internalGetUsers( 2651 CmsDbContext dbc, 2652 CmsOrganizationalUnit orgUnit, 2653 boolean recursive, 2654 boolean readAdditionalInfos) 2655 throws CmsDataAccessException { 2656 2657 List<CmsUser> users = new ArrayList<CmsUser>(); 2658 ResultSet res = null; 2659 PreparedStatement stmt = null; 2660 Connection conn = null; 2661 try { 2662 // create statement 2663 conn = m_sqlManager.getConnection(dbc); 2664 if (orgUnit.hasFlagWebuser()) { 2665 stmt = m_sqlManager.getPreparedStatement(conn, "C_USERS_GET_WEBUSERS_FOR_ORGUNIT_1"); 2666 } else { 2667 stmt = m_sqlManager.getPreparedStatement(conn, "C_USERS_GET_USERS_FOR_ORGUNIT_1"); 2668 } 2669 2670 String param = CmsOrganizationalUnit.SEPARATOR + orgUnit.getName(); 2671 if (recursive) { 2672 param += "%"; 2673 } 2674 stmt.setString(1, param); 2675 res = stmt.executeQuery(); 2676 // create new Cms group objects 2677 while (res.next()) { 2678 users.add(internalCreateUser(dbc, res)); 2679 } 2680 } catch (SQLException e) { 2681 throw new CmsDbSqlException( 2682 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2683 e); 2684 } finally { 2685 m_sqlManager.closeAll(dbc, conn, stmt, res); 2686 } 2687 if (readAdditionalInfos) { 2688 for (CmsUser user : users) { 2689 Map<String, Object> info = readUserInfos(dbc, user.getId()); 2690 user.setAdditionalInfo(info); 2691 } 2692 } 2693 return users; 2694 2695 } 2696 2697 /** 2698 * Returns the folder for the given organizational units, or the base folder if <code>null</code>.<p> 2699 * 2700 * The base folder will be created if it does not exist.<p> 2701 * 2702 * @param dbc the current db context 2703 * @param orgUnit the organizational unit to get the folder for 2704 * 2705 * @return the base folder for organizational units 2706 * 2707 * @throws CmsException if something goes wrong 2708 */ 2709 protected CmsResource internalOrgUnitFolder(CmsDbContext dbc, CmsOrganizationalUnit orgUnit) throws CmsException { 2710 2711 if (orgUnit != null) { 2712 return m_driverManager.readResource( 2713 dbc, 2714 ORGUNIT_BASE_FOLDER + orgUnit.getName(), 2715 CmsResourceFilter.DEFAULT); 2716 } else { 2717 return null; 2718 } 2719 } 2720 2721 /** 2722 * Returns the list of root paths associated to the organizational unit represented by the given resource.<p> 2723 * 2724 * @param dbc the current db context 2725 * @param ouResource the resource that represents the organizational unit to get the resources for 2726 * 2727 * @return the list of associated resource names 2728 * 2729 * @throws CmsException if something goes wrong 2730 */ 2731 protected List<String> internalResourcesForOrgUnit(CmsDbContext dbc, CmsResource ouResource) throws CmsException { 2732 2733 List<CmsRelation> relations = m_driverManager.getRelationsForResource( 2734 dbc, 2735 ouResource, 2736 CmsRelationFilter.TARGETS); 2737 List<String> paths = new ArrayList<String>(); 2738 Iterator<CmsRelation> it = relations.iterator(); 2739 while (it.hasNext()) { 2740 CmsRelation relation = it.next(); 2741 paths.add(relation.getTargetPath()); 2742 } 2743 return paths; 2744 } 2745 2746 /** 2747 * Updates a group to a virtual group.<p> 2748 * 2749 * @param dbc the database context 2750 * @param groupName the name of the group to update 2751 * @param role the role for this group 2752 * 2753 * @throws CmsDataAccessException if something goes wrong 2754 */ 2755 protected void internalUpdateRoleGroup(CmsDbContext dbc, String groupName, CmsRole role) 2756 throws CmsDataAccessException { 2757 2758 if (LOG.isDebugEnabled()) { 2759 LOG.debug( 2760 Messages.get().getBundle().key(Messages.LOG_DBG_UPDATE_ROLEGROUP_2, role.getRoleName(), groupName)); 2761 } 2762 2763 CmsGroup group = readGroup(dbc, groupName); 2764 if ((CmsRole.valueOf(group) == null) || !CmsRole.valueOf(group).equals(role)) { 2765 CmsGroup roleGroup = readGroup(dbc, role.getGroupName()); 2766 2767 if (LOG.isDebugEnabled()) { 2768 LOG.debug(Messages.get().getBundle().key(Messages.LOG_DBG_UPDATE_ROLEGROUP_1, roleGroup)); 2769 } 2770 2771 // copy all users from the group to the role 2772 Iterator<CmsUser> it; 2773 try { 2774 // read all users, also indirect assigned 2775 it = m_driverManager.getUsersOfGroup(dbc, groupName, false, false, false).iterator(); 2776 } catch (CmsException e) { 2777 // should never happen 2778 LOG.error(e.getLocalizedMessage(), e); 2779 // read only direct assigned users 2780 it = readUsersOfGroup(dbc, groupName, false).iterator(); 2781 } 2782 while (it.hasNext()) { 2783 CmsUser user = it.next(); 2784 2785 if (LOG.isDebugEnabled()) { 2786 LOG.debug(Messages.get().getBundle().key(Messages.LOG_DBG_UPDATE_ROLEGROUP_USER_1, user)); 2787 } 2788 createUserInGroup(dbc, user.getId(), roleGroup.getId()); 2789 } 2790 // set the right flags 2791 group.setFlags(role.getVirtualGroupFlags()); 2792 try { 2793 writeGroup(dbc, group); 2794 } catch (Exception e) { 2795 LOG.error("Could not write group flags in internalUpdateRoleGroup: " + e.getLocalizedMessage(), e); 2796 } 2797 } 2798 } 2799 2800 /** 2801 * Updates additional user info.<p> 2802 * @param dbc the current dbc 2803 * @param userId the user id to add the user info for 2804 * @param key the name of the additional user info 2805 * @param value the value of the additional user info 2806 * @throws CmsDataAccessException if something goes wrong 2807 */ 2808 protected void internalUpdateUserInfo(CmsDbContext dbc, CmsUUID userId, String key, Object value) 2809 throws CmsDataAccessException { 2810 2811 PreparedStatement stmt = null; 2812 Connection conn = null; 2813 2814 try { 2815 conn = getSqlManager().getConnection(dbc); 2816 stmt = m_sqlManager.getPreparedStatement(conn, "C_USERDATA_UPDATE_4"); 2817 // write data to database 2818 m_sqlManager.setBytes(stmt, 1, CmsDataTypeUtil.dataSerialize(value)); 2819 stmt.setString(2, value.getClass().getName()); 2820 stmt.setString(3, userId.toString()); 2821 stmt.setString(4, key); 2822 stmt.executeUpdate(); 2823 } catch (SQLException e) { 2824 throw new CmsDbSqlException( 2825 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2826 e); 2827 } catch (IOException e) { 2828 throw new CmsDbIoException(Messages.get().container(Messages.ERR_SERIALIZING_USER_DATA_1, userId), e); 2829 } finally { 2830 m_sqlManager.closeAll(dbc, conn, stmt, null); 2831 } 2832 } 2833 2834 /** 2835 * Validates the given root path to be in the scope of the resources of the given organizational unit.<p> 2836 * 2837 * @param dbc the current db context 2838 * @param orgUnit the organizational unit 2839 * @param rootPath the root path to check 2840 * 2841 * @throws CmsException if something goes wrong 2842 */ 2843 protected void internalValidateResourceForOrgUnit(CmsDbContext dbc, CmsOrganizationalUnit orgUnit, String rootPath) 2844 throws CmsException { 2845 2846 CmsResource parentResource = m_driverManager.readResource( 2847 dbc, 2848 ORGUNIT_BASE_FOLDER + orgUnit.getName(), 2849 CmsResourceFilter.ALL); 2850 // assume not in scope 2851 boolean found = false; 2852 // iterate parent paths 2853 Iterator<String> itParentPaths = internalResourcesForOrgUnit(dbc, parentResource).iterator(); 2854 // until the given resource is found in scope 2855 while (!found && itParentPaths.hasNext()) { 2856 String parentPath = itParentPaths.next(); 2857 // check the scope 2858 if (rootPath.startsWith(parentPath)) { 2859 found = true; 2860 } 2861 } 2862 // if not in scope throw exception 2863 if (!found) { 2864 throw new CmsException( 2865 Messages.get().container( 2866 Messages.ERR_PATH_NOT_IN_PARENT_ORGUNIT_SCOPE_2, 2867 orgUnit.getName(), 2868 dbc.removeSiteRoot(rootPath))); 2869 } 2870 } 2871 2872 /** 2873 * Checks if a user is member of a group.<p> 2874 * 2875 * @param dbc the database context 2876 * @param userId the id of the user to check 2877 * @param groupId the id of the group to check 2878 * 2879 * @return true if user is member of group 2880 * 2881 * @throws CmsDataAccessException if operation was not succesful 2882 */ 2883 protected boolean internalValidateUserInGroup(CmsDbContext dbc, CmsUUID userId, CmsUUID groupId) 2884 throws CmsDataAccessException { 2885 2886 boolean userInGroup = false; 2887 PreparedStatement stmt = null; 2888 ResultSet res = null; 2889 Connection conn = null; 2890 2891 try { 2892 conn = getSqlManager().getConnection(dbc); 2893 stmt = m_sqlManager.getPreparedStatement(conn, "C_GROUPS_USER_IN_GROUP_2"); 2894 2895 stmt.setString(1, groupId.toString()); 2896 stmt.setString(2, userId.toString()); 2897 res = stmt.executeQuery(); 2898 if (res.next()) { 2899 userInGroup = true; 2900 while (res.next()) { 2901 // do nothing only move through all rows because of mssql odbc driver 2902 } 2903 } 2904 } catch (SQLException e) { 2905 throw new CmsDbSqlException( 2906 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2907 e); 2908 } finally { 2909 m_sqlManager.closeAll(dbc, conn, stmt, res); 2910 } 2911 2912 return userInGroup; 2913 } 2914 2915 /** 2916 * Writes a property for an organizational unit resource, online AND offline.<p> 2917 * 2918 * @param dbc the current database context 2919 * @param resource the resource representing the organizational unit 2920 * @param property the property to write 2921 * 2922 * @throws CmsException if something goes wrong 2923 */ 2924 protected void internalWriteOrgUnitProperty(CmsDbContext dbc, CmsResource resource, CmsProperty property) 2925 throws CmsException { 2926 2927 CmsUUID projectId = ((dbc.getProjectId() == null) || dbc.getProjectId().isNullUUID()) 2928 ? dbc.currentProject().getUuid() 2929 : dbc.getProjectId(); 2930 // write the property 2931 m_driverManager.writePropertyObject(dbc, resource, property); 2932 resource.setState(CmsResource.STATE_UNCHANGED); 2933 m_driverManager.getVfsDriver(dbc).writeResource(dbc, projectId, resource, CmsDriverManager.NOTHING_CHANGED); 2934 2935 // online persistence 2936 CmsProject project = dbc.currentProject(); 2937 dbc.getRequestContext().setCurrentProject(m_driverManager.readProject(dbc, CmsProject.ONLINE_PROJECT_ID)); 2938 try { 2939 m_driverManager.writePropertyObject(dbc, resource, property); // assume the resource is identical in both projects 2940 resource.setState(CmsResource.STATE_UNCHANGED); 2941 m_driverManager.getVfsDriver( 2942 dbc).writeResource(dbc, dbc.currentProject().getUuid(), resource, CmsDriverManager.NOTHING_CHANGED); 2943 } finally { 2944 dbc.getRequestContext().setCurrentProject(project); 2945 } 2946 } 2947 2948 /** 2949 * Writes a new additional user info.<p> 2950 * @param dbc the current dbc 2951 * @param userId the user id to add the user info for 2952 * @param key the name of the additional user info 2953 * @param value the value of the additional user info 2954 * @throws CmsDataAccessException if something goes wrong 2955 */ 2956 protected void internalWriteUserInfo(CmsDbContext dbc, CmsUUID userId, String key, Object value) 2957 throws CmsDataAccessException { 2958 2959 PreparedStatement stmt = null; 2960 Connection conn = null; 2961 2962 try { 2963 conn = getSqlManager().getConnection(dbc); 2964 stmt = m_sqlManager.getPreparedStatement(conn, "C_USERDATA_WRITE_4"); 2965 // write data to database 2966 stmt.setString(1, userId.toString()); 2967 stmt.setString(2, key); 2968 m_sqlManager.setBytes(stmt, 3, CmsDataTypeUtil.dataSerialize(value)); 2969 stmt.setString(4, value.getClass().getName()); 2970 stmt.executeUpdate(); 2971 } catch (SQLException e) { 2972 throw new CmsDbSqlException( 2973 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2974 e); 2975 } catch (IOException e) { 2976 throw new CmsDbIoException(Messages.get().container(Messages.ERR_SERIALIZING_USER_DATA_1, userId), e); 2977 } finally { 2978 m_sqlManager.closeAll(dbc, conn, stmt, null); 2979 } 2980 } 2981 2982 /** 2983 * Updates the user additional information map.<p> 2984 * 2985 * @param dbc the current database context 2986 * @param userId the id of the user to update 2987 * @param additionalInfo the info to write 2988 * 2989 * @throws CmsDataAccessException if user data could not be written 2990 */ 2991 protected void internalWriteUserInfos(CmsDbContext dbc, CmsUUID userId, Map<String, Object> additionalInfo) 2992 throws CmsDataAccessException { 2993 2994 Lock lock = USER_INFO_LOCKS.get(userId); 2995 try { 2996 lock.lock(); 2997 2998 // get the map of existing additional infos to compare it new additional infos 2999 Map<String, Object> existingInfos = readUserInfos(dbc, userId); 3000 3001 // loop over all entries of the existing additional infos 3002 Iterator<Entry<String, Object>> itEntries = existingInfos.entrySet().iterator(); 3003 while (itEntries.hasNext()) { 3004 Entry<String, Object> entry = itEntries.next(); 3005 if ((entry.getKey() != null) && (entry.getValue() != null)) { 3006 // entry does not exist or is null in new additional infos -> delete it 3007 if (null == additionalInfo.get(entry.getKey())) { 3008 dbc.setAttribute(ATTRIBUTE_USERADDINFO, ATTRIBUTE_USERADDINFO_VALUE_DELETE); 3009 writeUserInfo(dbc, userId, entry.getKey(), entry.getValue()); 3010 } else { 3011 Object newValue = additionalInfo.get(entry.getKey()); 3012 // entry does exist but has different value -> update it 3013 if ((newValue != null) && !newValue.equals(entry.getValue())) { 3014 dbc.setAttribute(ATTRIBUTE_USERADDINFO, ATTRIBUTE_USERADDINFO_VALUE_UPDATE); 3015 writeUserInfo(dbc, userId, entry.getKey(), newValue); 3016 } 3017 } 3018 } 3019 } 3020 3021 // loop over all entries of the new additional infos 3022 Iterator<Entry<String, Object>> itNewEntries = additionalInfo.entrySet().iterator(); 3023 while (itNewEntries.hasNext()) { 3024 Entry<String, Object> entry = itNewEntries.next(); 3025 if ((entry.getKey() != null) && (entry.getValue() != null)) { 3026 // entry doews not exist in the existing additional infos -> create a new one 3027 if (!existingInfos.containsKey(entry.getKey())) { 3028 dbc.setAttribute(ATTRIBUTE_USERADDINFO, ATTRIBUTE_USERADDINFO_VALUE_INSERT); 3029 writeUserInfo(dbc, userId, entry.getKey(), entry.getValue()); 3030 } 3031 } 3032 } 3033 3034 } finally { 3035 lock.unlock(); 3036 } 3037 3038 } 3039 3040}