001/* 002 * This library is part of OpenCms - 003 * the Open Source Content Management System 004 * 005 * Copyright (c) Alkacon Software GmbH & Co. KG (https://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: https://www.alkacon.com 019 * 020 * For further information about OpenCms, please see the 021 * project website: https://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.CmsAliasFilter; 033import org.opencms.db.CmsDbContext; 034import org.opencms.db.CmsDbEntryNotFoundException; 035import org.opencms.db.CmsDbIoException; 036import org.opencms.db.CmsDbSqlException; 037import org.opencms.db.CmsDriverManager; 038import org.opencms.db.CmsModificationContext; 039import org.opencms.db.CmsPreparedStatementIntParameter; 040import org.opencms.db.CmsPreparedStatementLongParameter; 041import org.opencms.db.CmsPreparedStatementStringParameter; 042import org.opencms.db.CmsPublishList; 043import org.opencms.db.CmsPublishedResource; 044import org.opencms.db.CmsResourceState; 045import org.opencms.db.CmsVisitEntryFilter; 046import org.opencms.db.I_CmsDriver; 047import org.opencms.db.I_CmsHistoryDriver; 048import org.opencms.db.I_CmsPreparedStatementParameter; 049import org.opencms.db.I_CmsProjectDriver; 050import org.opencms.db.I_CmsVfsDriver; 051import org.opencms.db.log.CmsLogEntry; 052import org.opencms.db.log.CmsLogEntryType; 053import org.opencms.db.log.CmsLogFilter; 054import org.opencms.db.userpublishlist.CmsUserPublishListEntry; 055import org.opencms.file.CmsDataAccessException; 056import org.opencms.file.CmsFile; 057import org.opencms.file.CmsFolder; 058import org.opencms.file.CmsGroup; 059import org.opencms.file.CmsProject; 060import org.opencms.file.CmsProperty; 061import org.opencms.file.CmsPropertyDefinition; 062import org.opencms.file.CmsResource; 063import org.opencms.file.CmsResourceFilter; 064import org.opencms.file.CmsUser; 065import org.opencms.file.CmsVfsResourceAlreadyExistsException; 066import org.opencms.file.CmsVfsResourceNotFoundException; 067import org.opencms.file.history.CmsHistoryFile; 068import org.opencms.file.types.CmsResourceTypeFolder; 069import org.opencms.i18n.CmsMessageContainer; 070import org.opencms.lock.CmsLock; 071import org.opencms.lock.CmsLockType; 072import org.opencms.main.CmsEvent; 073import org.opencms.main.CmsException; 074import org.opencms.main.CmsLog; 075import org.opencms.main.I_CmsEventListener; 076import org.opencms.main.OpenCms; 077import org.opencms.publish.CmsPublishJobInfoBean; 078import org.opencms.relations.CmsRelationFilter; 079import org.opencms.report.I_CmsReport; 080import org.opencms.security.CmsOrganizationalUnit; 081import org.opencms.security.I_CmsPrincipal; 082import org.opencms.staticexport.CmsStaticExportManager; 083import org.opencms.util.CmsPair; 084import org.opencms.util.CmsStringUtil; 085import org.opencms.util.CmsUUID; 086 087import java.io.ByteArrayInputStream; 088import java.io.ByteArrayOutputStream; 089import java.io.IOException; 090import java.io.ObjectInputStream; 091import java.io.ObjectOutputStream; 092import java.sql.Connection; 093import java.sql.PreparedStatement; 094import java.sql.ResultSet; 095import java.sql.SQLException; 096import java.util.ArrayList; 097import java.util.Collection; 098import java.util.Collections; 099import java.util.HashMap; 100import java.util.HashSet; 101import java.util.Iterator; 102import java.util.List; 103import java.util.Map; 104import java.util.Set; 105 106import org.apache.commons.logging.Log; 107 108import com.google.common.collect.Sets; 109 110/** 111 * Generic (ANSI-SQL) implementation of the project driver methods.<p> 112 * 113 * @since 6.0.0 114 */ 115public class CmsProjectDriver implements I_CmsDriver, I_CmsProjectDriver { 116 117 /** 118 * This private class is a temporary storage for the method {@link CmsProjectDriver#readLocks(CmsDbContext)}.<p> 119 */ 120 private class CmsTempResourceLock { 121 122 /** The lock type. */ 123 private int m_lockType; 124 125 /** The project id. */ 126 private CmsUUID m_projectId; 127 128 /** The resource path. */ 129 private String m_resourcePath; 130 131 /** The user id. */ 132 private CmsUUID m_userId; 133 134 /** 135 * The constructor.<p> 136 * 137 * @param resourcePath resource path 138 * @param userId user id 139 * @param projectId project id 140 * @param lockType lock type 141 */ 142 public CmsTempResourceLock(String resourcePath, CmsUUID userId, CmsUUID projectId, int lockType) { 143 144 m_resourcePath = resourcePath; 145 m_userId = userId; 146 m_projectId = projectId; 147 m_lockType = lockType; 148 } 149 150 /** 151 * Returns the lockType.<p> 152 * 153 * @return the lockType 154 */ 155 public int getLockType() { 156 157 return m_lockType; 158 } 159 160 /** 161 * Returns the projectId.<p> 162 * 163 * @return the projectId 164 */ 165 public CmsUUID getProjectId() { 166 167 return m_projectId; 168 } 169 170 /** 171 * Returns the resourcePath.<p> 172 * 173 * @return the resourcePath 174 */ 175 public String getResourcePath() { 176 177 return m_resourcePath; 178 } 179 180 /** 181 * Returns the userId.<p> 182 * 183 * @return the userId 184 */ 185 public CmsUUID getUserId() { 186 187 return m_userId; 188 } 189 190 } 191 192 /** Attribute name for reading the project of a resource. */ 193 public static final String DBC_ATTR_READ_PROJECT_FOR_RESOURCE = "DBC_ATTR_READ_PROJECT_FOR_RESOURCE"; 194 195 /** The log object for this class. */ 196 private static final Log LOG = CmsLog.getLog(org.opencms.db.generic.CmsProjectDriver.class); 197 198 /** The driver manager. */ 199 protected CmsDriverManager m_driverManager; 200 201 /** The SQL manager. */ 202 protected CmsSqlManager m_sqlManager; 203 204 /** 205 * @see org.opencms.db.I_CmsProjectDriver#cleanupPublishHistory(org.opencms.db.CmsDbContext, org.opencms.db.generic.CmsPublishHistoryCleanupFilter) 206 */ 207 public int cleanupPublishHistory(CmsDbContext dbc, CmsPublishHistoryCleanupFilter filter) 208 throws CmsDataAccessException { 209 210 Connection conn = null; 211 PreparedStatement stmt = null; 212 int rowsAffected = 0; 213 214 try { 215 // get a JDBC connection from the OpenCms standard pool 216 conn = m_sqlManager.getConnection(dbc); 217 switch (filter.getMode()) { 218 219 case single: 220 default: 221 stmt = m_sqlManager.getPreparedStatement(conn, "C_CLEANUP_PUBLISH_HISTORY_SINGLE"); 222 stmt.setString(1, filter.getHistoryId().toString()); 223 rowsAffected = stmt.executeUpdate(); 224 break; 225 case allUnreferenced: 226 String statementText = m_sqlManager.readQuery("C_CLEANUP_PUBLISH_HISTORY_ALL"); 227 if (filter.getExceptions().size() > 0) { 228 List<String> parts = new ArrayList<>(); 229 // it's safe to construct the clause as a string here because UUIDs can only contain dashes and hex digits 230 parts.add("'" + CmsUUID.getNullUUID() + "'"); 231 for (CmsUUID id : filter.getExceptions()) { 232 parts.add("'" + id.toString() + "'"); 233 } 234 String exceptionListStr = "(" + CmsStringUtil.listAsString(parts, ",") + ")"; 235 statementText += " AND CMS_PUBLISH_HISTORY.HISTORY_ID NOT IN " + exceptionListStr; 236 } 237 stmt = m_sqlManager.getPreparedStatementForSql(conn, statementText); 238 rowsAffected = stmt.executeUpdate(); 239 break; 240 } 241 LOG.info( 242 "executed publish list cleanup in mode " + filter.getMode() + ", " + rowsAffected + " rows deleted"); 243 return rowsAffected; 244 } catch (SQLException e) { 245 throw new CmsDbSqlException( 246 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 247 e); 248 } finally { 249 m_sqlManager.closeAll(dbc, conn, stmt, null); 250 251 } 252 253 } 254 255 /** 256 * @see org.opencms.db.I_CmsProjectDriver#createProject(org.opencms.db.CmsDbContext, CmsUUID, org.opencms.file.CmsUser, org.opencms.file.CmsGroup, org.opencms.file.CmsGroup, java.lang.String, java.lang.String, int, CmsProject.CmsProjectType) 257 */ 258 public CmsProject createProject( 259 CmsDbContext dbc, 260 CmsUUID id, 261 CmsUser owner, 262 CmsGroup group, 263 CmsGroup managergroup, 264 String projectFqn, 265 String description, 266 int flags, 267 CmsProject.CmsProjectType type) 268 throws CmsDataAccessException { 269 270 CmsProject project = null; 271 272 if ((description == null) || (description.length() < 1)) { 273 description = " "; 274 } 275 276 Connection conn = null; 277 PreparedStatement stmt = null; 278 279 try { 280 // get a JDBC connection from the OpenCms standard pool 281 conn = m_sqlManager.getConnection(dbc); 282 stmt = m_sqlManager.getPreparedStatement(conn, "C_PROJECTS_CREATE_10"); 283 284 stmt.setString(1, id.toString()); 285 stmt.setString(2, owner.getId().toString()); 286 stmt.setString(3, group.getId().toString()); 287 stmt.setString(4, managergroup.getId().toString()); 288 stmt.setString(5, CmsOrganizationalUnit.getSimpleName(projectFqn)); 289 stmt.setString(6, description); 290 stmt.setInt(7, flags); 291 stmt.setInt(9, type.getMode()); 292 stmt.setString(10, CmsOrganizationalUnit.SEPARATOR + CmsOrganizationalUnit.getParentFqn(projectFqn)); 293 294 synchronized (this) { 295 long createTime = System.currentTimeMillis(); 296 stmt.setLong(8, createTime); 297 stmt.executeUpdate(); 298 try { 299 // this is an ugly hack, but for MySQL (and maybe other DBs as well) 300 // there is a UNIQUE INDEX constraint on the project name+createTime 301 // so theoretically if 2 projects with the same name are created very fast, this 302 // SQL restraint would be violated if we don't wait here 303 Thread.sleep(50); 304 } catch (InterruptedException e) { 305 // continue 306 } 307 project = new CmsProject( 308 id, 309 projectFqn, 310 description, 311 owner.getId(), 312 group.getId(), 313 managergroup.getId(), 314 flags, 315 createTime, 316 type); 317 } 318 } catch (SQLException e) { 319 throw new CmsDbSqlException( 320 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 321 e); 322 } finally { 323 m_sqlManager.closeAll(dbc, conn, stmt, null); 324 } 325 326 return project; 327 } 328 329 /** 330 * @see org.opencms.db.I_CmsProjectDriver#createProjectResource(org.opencms.db.CmsDbContext, CmsUUID, java.lang.String) 331 */ 332 public void createProjectResource(CmsDbContext dbc, CmsUUID projectId, String resourcePath) 333 throws CmsDataAccessException { 334 335 // do not create entries for online-project 336 PreparedStatement stmt = null; 337 Connection conn = null; 338 339 boolean projectResourceExists = false; 340 try { 341 readProjectResource(dbc, projectId, resourcePath); 342 projectResourceExists = true; 343 } catch (CmsVfsResourceNotFoundException e) { 344 // resource does not exist yet, everything is okay 345 projectResourceExists = false; 346 } 347 348 if (projectResourceExists) { 349 throw new CmsVfsResourceAlreadyExistsException( 350 Messages.get().container( 351 Messages.ERR_RESOURCE_WITH_NAME_ALREADY_EXISTS_1, 352 dbc.removeSiteRoot(resourcePath))); 353 } 354 355 try { 356 conn = getSqlManager().getConnection(dbc); 357 stmt = m_sqlManager.getPreparedStatement(conn, "C_PROJECTRESOURCES_CREATE_2"); 358 359 // write new resource to the database 360 stmt.setString(1, projectId.toString()); 361 stmt.setString(2, resourcePath); 362 363 stmt.executeUpdate(); 364 } catch (SQLException e) { 365 throw new CmsDbSqlException( 366 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 367 e); 368 } finally { 369 m_sqlManager.closeAll(dbc, conn, stmt, null); 370 } 371 } 372 373 /** 374 * @see org.opencms.db.I_CmsProjectDriver#createPublishJob(org.opencms.db.CmsDbContext, org.opencms.publish.CmsPublishJobInfoBean) 375 */ 376 public void createPublishJob(CmsDbContext dbc, CmsPublishJobInfoBean publishJob) throws CmsDataAccessException { 377 378 Connection conn = null; 379 PreparedStatement stmt = null; 380 381 try { 382 CmsPublishJobInfoBean currentJob = readPublishJob(dbc, publishJob.getPublishHistoryId()); 383 LOG.error("wanted to write: " + publishJob); 384 LOG.error("already on db: " + currentJob); 385 return; 386 } catch (CmsDbEntryNotFoundException e) { 387 // ok, this is the expected behavior 388 } 389 try { 390 conn = m_sqlManager.getConnection(dbc); 391 stmt = m_sqlManager.getPreparedStatement(conn, "C_PUBLISHJOB_CREATE"); 392 393 stmt.setString(1, publishJob.getPublishHistoryId().toString()); 394 stmt.setString(2, publishJob.getProjectId().toString()); 395 stmt.setString(3, publishJob.getProjectName()); 396 stmt.setString(4, publishJob.getUserId().toString()); 397 stmt.setString(5, publishJob.getLocale().toString()); 398 stmt.setInt(6, publishJob.getFlags()); 399 stmt.setInt(7, publishJob.getSize()); 400 stmt.setLong(8, publishJob.getEnqueueTime()); 401 stmt.setLong(9, publishJob.getStartTime()); 402 stmt.setLong(10, publishJob.getFinishTime()); 403 404 byte[] publishList = internalSerializePublishList(publishJob.getPublishList()); 405 if (publishList.length < 2000) { 406 stmt.setBytes(11, publishList); 407 } else { 408 stmt.setBinaryStream(11, new ByteArrayInputStream(publishList), publishList.length); 409 } 410 411 stmt.executeUpdate(); 412 } catch (SQLException e) { 413 throw new CmsDbSqlException( 414 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 415 e); 416 } catch (IOException e) { 417 throw new CmsDbIoException( 418 Messages.get().container( 419 Messages.ERR_SERIALIZING_PUBLISHLIST_1, 420 publishJob.getPublishHistoryId().toString()), 421 e); 422 } finally { 423 m_sqlManager.closeAll(dbc, conn, stmt, null); 424 } 425 } 426 427 /** 428 * @see org.opencms.db.I_CmsProjectDriver#deleteAllStaticExportPublishedResources(org.opencms.db.CmsDbContext, int) 429 */ 430 public void deleteAllStaticExportPublishedResources(CmsDbContext dbc, int linkType) throws CmsDataAccessException { 431 432 Connection conn = null; 433 PreparedStatement stmt = null; 434 435 try { 436 conn = m_sqlManager.getConnection(dbc); 437 stmt = m_sqlManager.getPreparedStatement(conn, "C_STATICEXPORT_DELETE_ALL_PUBLISHED_LINKS"); 438 stmt.setInt(1, linkType); 439 stmt.executeUpdate(); 440 } catch (SQLException e) { 441 throw new CmsDbSqlException( 442 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 443 e); 444 } finally { 445 m_sqlManager.closeAll(dbc, conn, stmt, null); 446 } 447 } 448 449 /** 450 * @see org.opencms.db.I_CmsProjectDriver#deleteLog(org.opencms.db.CmsDbContext, org.opencms.db.log.CmsLogFilter) 451 */ 452 public void deleteLog(CmsDbContext dbc, CmsLogFilter filter) throws CmsDataAccessException { 453 454 Connection conn = null; 455 PreparedStatement stmt = null; 456 457 try { 458 conn = m_sqlManager.getConnection(dbc); 459 // compose statement 460 StringBuffer queryBuf = new StringBuffer(256); 461 queryBuf.append(m_sqlManager.readQuery("C_LOG_DELETE_ENTRIES")); 462 463 CmsPair<String, List<I_CmsPreparedStatementParameter>> conditionsAndParams = prepareLogConditions(filter); 464 queryBuf.append(conditionsAndParams.getFirst()); 465 if (LOG.isDebugEnabled()) { 466 LOG.debug(queryBuf.toString()); 467 } 468 stmt = m_sqlManager.getPreparedStatementForSql(conn, queryBuf.toString()); 469 List<I_CmsPreparedStatementParameter> params = conditionsAndParams.getSecond(); 470 for (int i = 0; i < params.size(); i++) { 471 I_CmsPreparedStatementParameter param = conditionsAndParams.getSecond().get(i); 472 param.insertIntoStatement(stmt, i + 1); 473 } 474 475 // execute 476 stmt.executeUpdate(); 477 } catch (SQLException e) { 478 throw new CmsDbSqlException( 479 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 480 e); 481 } finally { 482 m_sqlManager.closeAll(dbc, conn, stmt, null); 483 } 484 } 485 486 /** 487 * @see org.opencms.db.I_CmsProjectDriver#deleteProject(org.opencms.db.CmsDbContext, org.opencms.file.CmsProject) 488 */ 489 public void deleteProject(CmsDbContext dbc, CmsProject project) throws CmsDataAccessException { 490 491 // delete the resources from project_resources 492 deleteProjectResources(dbc, project); 493 494 // remove the project id form all resources within their project 495 unmarkProjectResources(dbc, project); 496 497 // finally delete the project 498 Connection conn = null; 499 PreparedStatement stmt = null; 500 try { 501 conn = m_sqlManager.getConnection(dbc); 502 stmt = m_sqlManager.getPreparedStatement(conn, "C_PROJECTS_DELETE_1"); 503 // create the statement 504 stmt.setString(1, project.getUuid().toString()); 505 stmt.executeUpdate(); 506 } catch (SQLException e) { 507 throw new CmsDbSqlException( 508 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 509 e); 510 } finally { 511 m_sqlManager.closeAll(dbc, conn, stmt, null); 512 } 513 } 514 515 /** 516 * @see org.opencms.db.I_CmsProjectDriver#deleteProjectResource(org.opencms.db.CmsDbContext, CmsUUID, java.lang.String) 517 */ 518 public void deleteProjectResource(CmsDbContext dbc, CmsUUID projectId, String resourceName) 519 throws CmsDataAccessException { 520 521 Connection conn = null; 522 PreparedStatement stmt = null; 523 try { 524 conn = m_sqlManager.getConnection(dbc); 525 stmt = m_sqlManager.getPreparedStatement(conn, "C_PROJECTRESOURCES_DELETE_2"); 526 // delete resource from the database 527 stmt.setString(1, projectId.toString()); 528 stmt.setString(2, resourceName); 529 stmt.executeUpdate(); 530 } catch (SQLException e) { 531 throw new CmsDbSqlException( 532 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 533 e); 534 } finally { 535 m_sqlManager.closeAll(dbc, conn, stmt, null); 536 } 537 } 538 539 /** 540 * @see org.opencms.db.I_CmsProjectDriver#deleteProjectResources(org.opencms.db.CmsDbContext, org.opencms.file.CmsProject) 541 */ 542 public void deleteProjectResources(CmsDbContext dbc, CmsProject project) throws CmsDataAccessException { 543 544 Connection conn = null; 545 PreparedStatement stmt = null; 546 547 try { 548 conn = m_sqlManager.getConnection(dbc); 549 stmt = m_sqlManager.getPreparedStatement(conn, "C_PROJECTRESOURCES_DELETEALL_1"); 550 stmt.setString(1, project.getUuid().toString()); 551 stmt.executeUpdate(); 552 } catch (SQLException e) { 553 throw new CmsDbSqlException( 554 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 555 e); 556 } finally { 557 m_sqlManager.closeAll(dbc, conn, stmt, null); 558 } 559 } 560 561 /** 562 * @see org.opencms.db.I_CmsProjectDriver#deletePublishHistory(org.opencms.db.CmsDbContext, CmsUUID, int) 563 */ 564 public void deletePublishHistory(CmsDbContext dbc, CmsUUID projectId, int maxpublishTag) 565 throws CmsDataAccessException { 566 567 PreparedStatement stmt = null; 568 Connection conn = null; 569 570 try { 571 conn = m_sqlManager.getConnection(dbc); 572 stmt = m_sqlManager.getPreparedStatement(conn, projectId, "C_DELETE_PUBLISH_HISTORY"); 573 stmt.setInt(1, maxpublishTag); 574 stmt.executeUpdate(); 575 } catch (SQLException e) { 576 throw new CmsDbSqlException( 577 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 578 e); 579 } finally { 580 m_sqlManager.closeAll(dbc, conn, stmt, null); 581 } 582 } 583 584 /** 585 * @see org.opencms.db.I_CmsProjectDriver#deletePublishHistoryEntry(org.opencms.db.CmsDbContext, org.opencms.util.CmsUUID, org.opencms.db.CmsPublishedResource) 586 */ 587 public void deletePublishHistoryEntry( 588 CmsDbContext dbc, 589 CmsUUID publishHistoryId, 590 CmsPublishedResource publishedResource) 591 throws CmsDataAccessException { 592 593 Connection conn = null; 594 PreparedStatement stmt = null; 595 596 try { 597 conn = m_sqlManager.getConnection(dbc); 598 stmt = m_sqlManager.getPreparedStatement(conn, "C_RESOURCES_DELETE_PUBLISH_HISTORY_ENTRY"); 599 stmt.setString(1, publishHistoryId.toString()); 600 stmt.setInt(2, publishedResource.getPublishTag()); 601 stmt.setString(3, publishedResource.getStructureId().toString()); 602 stmt.setString(4, publishedResource.getRootPath()); 603 stmt.executeUpdate(); 604 } catch (SQLException e) { 605 throw new CmsDbSqlException( 606 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 607 e); 608 } finally { 609 m_sqlManager.closeAll(dbc, conn, stmt, null); 610 } 611 } 612 613 /** 614 * @see org.opencms.db.I_CmsProjectDriver#deletePublishJob(org.opencms.db.CmsDbContext, org.opencms.util.CmsUUID) 615 */ 616 public void deletePublishJob(CmsDbContext dbc, CmsUUID publishHistoryId) throws CmsDataAccessException { 617 618 Connection conn = null; 619 PreparedStatement stmt = null; 620 621 try { 622 conn = m_sqlManager.getConnection(dbc); 623 stmt = m_sqlManager.getPreparedStatement(conn, "C_PUBLISHJOB_DELETE"); 624 stmt.setString(1, publishHistoryId.toString()); 625 stmt.executeUpdate(); 626 } catch (SQLException e) { 627 throw new CmsDbSqlException( 628 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 629 e); 630 } finally { 631 m_sqlManager.closeAll(dbc, conn, stmt, null); 632 } 633 } 634 635 /** 636 * @see org.opencms.db.I_CmsProjectDriver#deletePublishList(org.opencms.db.CmsDbContext, org.opencms.util.CmsUUID) 637 */ 638 public void deletePublishList(CmsDbContext dbc, CmsUUID publishHistoryId) throws CmsDataAccessException { 639 640 Connection conn = null; 641 PreparedStatement stmt = null; 642 643 try { 644 conn = m_sqlManager.getConnection(dbc); 645 stmt = m_sqlManager.getPreparedStatement(conn, "C_PUBLISHJOB_DELETE_PUBLISHLIST"); 646 stmt.setString(1, publishHistoryId.toString()); 647 stmt.executeUpdate(); 648 } catch (SQLException e) { 649 throw new CmsDbSqlException( 650 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 651 e); 652 } finally { 653 m_sqlManager.closeAll(dbc, conn, stmt, null); 654 } 655 } 656 657 /** 658 * @see org.opencms.db.I_CmsProjectDriver#deleteStaticExportPublishedResource(org.opencms.db.CmsDbContext, java.lang.String, int, java.lang.String) 659 */ 660 public void deleteStaticExportPublishedResource( 661 CmsDbContext dbc, 662 String resourceName, 663 int linkType, 664 String linkParameter) 665 throws CmsDataAccessException { 666 667 Connection conn = null; 668 PreparedStatement stmt = null; 669 670 try { 671 conn = m_sqlManager.getConnection(dbc); 672 if (linkParameter == null) { 673 stmt = m_sqlManager.getPreparedStatement(conn, "C_STATICEXPORT_DELETE_RFSPATH_PUBLISHED_LINKS"); 674 stmt.setString(1, resourceName); 675 stmt.setInt(2, linkType); 676 stmt.executeUpdate(); 677 } else { 678 stmt = m_sqlManager.getPreparedStatement(conn, "C_STATICEXPORT_DELETE_PUBLISHED_LINKS"); 679 stmt.setString(1, resourceName); 680 stmt.setInt(2, linkType); 681 stmt.setString(3, linkParameter); 682 stmt.executeUpdate(); 683 } 684 } catch (SQLException e) { 685 throw new CmsDbSqlException( 686 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 687 e); 688 } finally { 689 m_sqlManager.closeAll(dbc, conn, stmt, null); 690 } 691 } 692 693 /** 694 * @see org.opencms.db.I_CmsProjectDriver#deleteUserPublishListEntries(org.opencms.db.CmsDbContext, java.util.List) 695 */ 696 public void deleteUserPublishListEntries(CmsDbContext dbc, List<CmsUserPublishListEntry> publishListDeletions) 697 throws CmsDbSqlException { 698 699 if (publishListDeletions.isEmpty()) { 700 return; 701 } 702 Connection conn = null; 703 PreparedStatement stmt = null; 704 705 try { 706 conn = m_sqlManager.getConnection(dbc); 707 String sql = m_sqlManager.readQuery("C_USER_PUBLISH_LIST_DELETE_3"); 708 stmt = m_sqlManager.getPreparedStatementForSql(conn, sql); 709 for (CmsUserPublishListEntry entry : publishListDeletions) { 710 stmt.setString(1, entry.getStructureId().toString()); 711 stmt.setString(2, entry.getUserId() != null ? entry.getUserId().toString() : null); 712 stmt.setInt(3, entry.getUserId() == null ? 1 : 0); 713 stmt.addBatch(); 714 } 715 stmt.executeBatch(); 716 } catch (SQLException e) { 717 throw new CmsDbSqlException( 718 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 719 e); 720 } finally { 721 m_sqlManager.closeAll(dbc, conn, stmt, null); 722 } 723 724 } 725 726 /** 727 * @see org.opencms.db.I_CmsProjectDriver#destroy() 728 */ 729 public void destroy() throws Throwable { 730 731 m_sqlManager = null; 732 m_driverManager = null; 733 734 if (CmsLog.INIT.isInfoEnabled()) { 735 CmsLog.INIT.info(Messages.get().getBundle().key(Messages.INIT_SHUTDOWN_DRIVER_1, getClass().getName())); 736 } 737 } 738 739 /** 740 * @see org.opencms.db.I_CmsProjectDriver#fillDefaults(org.opencms.db.CmsDbContext) 741 */ 742 public void fillDefaults(CmsDbContext dbc) throws CmsDataAccessException { 743 744 try { 745 if (readProject(dbc, CmsProject.ONLINE_PROJECT_ID) != null) { 746 // online-project exists - no need of filling defaults 747 return; 748 } 749 } catch (CmsDataAccessException exc) { 750 // ignore the exception - the project was not readable so fill in the defaults 751 } 752 753 if (CmsLog.INIT.isInfoEnabled()) { 754 CmsLog.INIT.info(Messages.get().getBundle().key(Messages.INIT_FILL_DEFAULTS_0)); 755 } 756 757 String adminUser = OpenCms.getDefaultUsers().getUserAdmin(); 758 CmsUser admin = m_driverManager.readUser(dbc, adminUser); 759 760 String administratorsGroup = OpenCms.getDefaultUsers().getGroupAdministrators(); 761 CmsGroup administrators = m_driverManager.readGroup(dbc, administratorsGroup); 762 763 String usersGroup = OpenCms.getDefaultUsers().getGroupUsers(); 764 CmsGroup users = m_driverManager.readGroup(dbc, usersGroup); 765 766 //////////////////////////////////////////////////////////////////////////////////////////// 767 // online project stuff 768 //////////////////////////////////////////////////////////////////////////////////////////// 769 770 // create the online project 771 CmsProject onlineProject = createProject( 772 dbc, 773 CmsProject.ONLINE_PROJECT_ID, 774 admin, 775 users, 776 administrators, 777 CmsProject.ONLINE_PROJECT_NAME, 778 "The Online project", 779 I_CmsPrincipal.FLAG_ENABLED, 780 CmsProject.PROJECT_TYPE_NORMAL); 781 782 // create the root-folder for the online project 783 CmsFolder rootFolder = new CmsFolder( 784 new CmsUUID(), 785 new CmsUUID(), 786 "/", 787 CmsResourceTypeFolder.RESOURCE_TYPE_ID, 788 0, 789 onlineProject.getUuid(), 790 CmsResource.STATE_CHANGED, 791 0, 792 admin.getId(), 793 0, 794 admin.getId(), 795 CmsResource.DATE_RELEASED_DEFAULT, 796 CmsResource.DATE_EXPIRED_DEFAULT, 797 0); 798 799 m_driverManager.getVfsDriver(dbc).createResource(dbc, onlineProject.getUuid(), rootFolder, null); 800 801 // important: must access through driver manager to ensure proper cascading 802 m_driverManager.getProjectDriver(dbc).createProjectResource( 803 dbc, 804 onlineProject.getUuid(), 805 rootFolder.getRootPath()); 806 807 // create the system-folder for the online project 808 CmsFolder systemFolder = new CmsFolder( 809 new CmsUUID(), 810 new CmsUUID(), 811 "/system", 812 CmsResourceTypeFolder.RESOURCE_TYPE_ID, 813 0, 814 onlineProject.getUuid(), 815 CmsResource.STATE_CHANGED, 816 0, 817 admin.getId(), 818 0, 819 admin.getId(), 820 CmsResource.DATE_RELEASED_DEFAULT, 821 CmsResource.DATE_EXPIRED_DEFAULT, 822 0); 823 824 m_driverManager.getVfsDriver(dbc).createResource(dbc, onlineProject.getUuid(), systemFolder, null); 825 826 //////////////////////////////////////////////////////////////////////////////////////////// 827 // setup project stuff 828 //////////////////////////////////////////////////////////////////////////////////////////// 829 830 // important: must access through driver manager to ensure proper cascading 831 CmsProject setupProject = m_driverManager.getProjectDriver(dbc).createProject( 832 dbc, 833 CmsUUID.getConstantUUID(SETUP_PROJECT_NAME), 834 admin, 835 administrators, 836 administrators, 837 SETUP_PROJECT_NAME, 838 "The Project for the initial import", 839 I_CmsPrincipal.FLAG_ENABLED, 840 CmsProject.PROJECT_TYPE_TEMPORARY); 841 842 rootFolder.setState(CmsResource.STATE_CHANGED); 843 // create the root-folder for the offline project 844 CmsResource offlineRootFolder = m_driverManager.getVfsDriver( 845 dbc).createResource(dbc, setupProject.getUuid(), rootFolder, null); 846 847 offlineRootFolder.setState(CmsResource.STATE_UNCHANGED); 848 849 m_driverManager.getVfsDriver( 850 dbc).writeResource(dbc, setupProject.getUuid(), offlineRootFolder, CmsDriverManager.NOTHING_CHANGED); 851 852 // important: must access through driver manager to ensure proper cascading 853 m_driverManager.getProjectDriver(dbc).createProjectResource( 854 dbc, 855 setupProject.getUuid(), 856 offlineRootFolder.getRootPath()); 857 858 systemFolder.setState(CmsResource.STATE_CHANGED); 859 // create the system-folder for the offline project 860 CmsResource offlineSystemFolder = m_driverManager.getVfsDriver( 861 dbc).createResource(dbc, setupProject.getUuid(), systemFolder, null); 862 863 offlineSystemFolder.setState(CmsResource.STATE_UNCHANGED); 864 865 m_driverManager.getVfsDriver( 866 dbc).writeResource(dbc, setupProject.getUuid(), offlineSystemFolder, CmsDriverManager.NOTHING_CHANGED); 867 } 868 869 /** 870 * @see org.opencms.db.I_CmsProjectDriver#getSqlManager() 871 */ 872 public CmsSqlManager getSqlManager() { 873 874 return m_sqlManager; 875 } 876 877 /** 878 * @see org.opencms.db.I_CmsProjectDriver#getUsersPubList(org.opencms.db.CmsDbContext, org.opencms.util.CmsUUID) 879 */ 880 public List<CmsResource> getUsersPubList(CmsDbContext dbc, CmsUUID userId) throws CmsDataAccessException { 881 882 List<CmsResource> result = new ArrayList<CmsResource>(); 883 Connection conn = null; 884 PreparedStatement stmt = null; 885 ResultSet res = null; 886 try { 887 conn = m_sqlManager.getConnection(dbc); 888 String sql = m_sqlManager.readQuery("C_USER_PUBLISH_LIST_READ_1"); 889 sql = sql.replace("${PROJECT}", "OFFLINE"); 890 stmt = m_sqlManager.getPreparedStatementForSql(conn, sql); 891 stmt.setString(1, userId.toString()); 892 res = stmt.executeQuery(); 893 while (res.next()) { 894 CmsResource resource = m_driverManager.getVfsDriver(dbc).createResource( 895 res, 896 dbc.currentProject().getUuid()); 897 long date = res.getLong("DATE_CHANGED"); 898 resource.setDateLastModified(date); 899 result.add(resource); 900 } 901 return result; 902 } catch (SQLException e) { 903 throw new CmsDbSqlException( 904 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 905 e); 906 } finally { 907 m_sqlManager.closeAll(dbc, conn, stmt, res); 908 } 909 } 910 911 /** 912 * @see org.opencms.db.I_CmsDriver#init(CmsDbContext, CmsConfigurationManager, List, CmsDriverManager) 913 */ 914 public void init( 915 CmsDbContext dbc, 916 CmsConfigurationManager configurationManager, 917 List<String> successiveDrivers, 918 CmsDriverManager driverManager) { 919 920 CmsParameterConfiguration configuration = configurationManager.getConfiguration(); 921 String poolUrl = configuration.get("db.project.pool"); 922 String classname = configuration.get("db.project.sqlmanager"); 923 m_sqlManager = initSqlManager(classname); 924 m_sqlManager.init(I_CmsProjectDriver.DRIVER_TYPE_ID, poolUrl); 925 926 m_driverManager = driverManager; 927 928 if (CmsLog.INIT.isInfoEnabled()) { 929 CmsLog.INIT.info(Messages.get().getBundle().key(Messages.INIT_ASSIGNED_POOL_1, poolUrl)); 930 } 931 932 if ((successiveDrivers != null) && !successiveDrivers.isEmpty()) { 933 if (LOG.isWarnEnabled()) { 934 LOG.warn( 935 Messages.get().getBundle().key( 936 Messages.LOG_SUCCESSIVE_DRIVERS_UNSUPPORTED_1, 937 getClass().getName())); 938 } 939 } 940 } 941 942 /** 943 * @see org.opencms.db.I_CmsProjectDriver#initSqlManager(String) 944 */ 945 public org.opencms.db.generic.CmsSqlManager initSqlManager(String classname) { 946 947 return CmsSqlManager.getInstance(classname); 948 } 949 950 /** 951 * @see org.opencms.db.I_CmsProjectDriver#log(org.opencms.db.CmsDbContext, java.util.List) 952 */ 953 public void log(CmsDbContext dbc, List<CmsLogEntry> logEntries) throws CmsDbSqlException { 954 955 Connection conn = null; 956 PreparedStatement stmt = null; 957 958 try { 959 conn = m_sqlManager.getConnection(dbc); 960 stmt = m_sqlManager.getPreparedStatement(conn, "C_LOG_CREATE_5"); 961 962 for (CmsLogEntry logEntry : logEntries) { 963 stmt.setString(1, logEntry.getUserId().toString()); 964 stmt.setLong(2, logEntry.getDate()); 965 stmt.setString(3, logEntry.getStructureId() == null ? null : logEntry.getStructureId().toString()); 966 stmt.setInt(4, logEntry.getType().getId()); 967 stmt.setString(5, CmsStringUtil.arrayAsString(logEntry.getData(), "|")); 968 try { 969 stmt.executeUpdate(); 970 } catch (SQLException e) { 971 // ignore, most likely a duplicate entry 972 LOG.debug( 973 Messages.get().container( 974 Messages.ERR_GENERIC_SQL_1, 975 CmsDbSqlException.getErrorQuery(stmt)).key(), 976 e); 977 } 978 } 979 } catch (SQLException e) { 980 throw new CmsDbSqlException( 981 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 982 e); 983 } finally { 984 try { 985 m_sqlManager.closeAll(dbc, conn, stmt, null); 986 } catch (Throwable t) { 987 // this could happen during shutdown 988 LOG.debug(t.getLocalizedMessage(), t); 989 } 990 } 991 } 992 993 /** 994 * @see org.opencms.db.I_CmsProjectDriver#publishDeletedFolder(org.opencms.db.CmsDbContext, org.opencms.report.I_CmsReport, int, int, org.opencms.file.CmsProject, org.opencms.file.CmsFolder, org.opencms.util.CmsUUID, int) 995 */ 996 public void publishDeletedFolder( 997 CmsDbContext dbc, 998 I_CmsReport report, 999 int m, 1000 int n, 1001 CmsProject onlineProject, 1002 CmsFolder currentFolder, 1003 CmsUUID publishHistoryId, 1004 int publishTag) 1005 throws CmsDataAccessException { 1006 1007 try { 1008 report.print( 1009 org.opencms.report.Messages.get().container( 1010 org.opencms.report.Messages.RPT_SUCCESSION_2, 1011 String.valueOf(m), 1012 String.valueOf(n)), 1013 I_CmsReport.FORMAT_NOTE); 1014 report.print(Messages.get().container(Messages.RPT_DELETE_FOLDER_0), I_CmsReport.FORMAT_NOTE); 1015 report.print( 1016 org.opencms.report.Messages.get().container( 1017 org.opencms.report.Messages.RPT_ARGUMENT_1, 1018 dbc.removeSiteRoot(currentFolder.getRootPath()))); 1019 report.print(org.opencms.report.Messages.get().container(org.opencms.report.Messages.RPT_DOTS_0)); 1020 1021 CmsResourceState folderState = fixMovedResource( 1022 dbc, 1023 onlineProject, 1024 currentFolder, 1025 publishHistoryId, 1026 publishTag); 1027 1028 // read the folder online 1029 CmsFolder onlineFolder = m_driverManager.readFolder( 1030 dbc, 1031 currentFolder.getRootPath(), 1032 CmsResourceFilter.ALL); 1033 1034 // if the folder in the online-project contains any files, these need to be removed. 1035 // this can occur if these files were moved in the offline-project 1036 List<CmsResource> movedFiles = null; 1037 I_CmsVfsDriver vfsDriver = m_driverManager.getVfsDriver(dbc); 1038 movedFiles = vfsDriver.readResourceTree( 1039 dbc, 1040 onlineProject.getUuid(), 1041 currentFolder.getRootPath(), 1042 CmsDriverManager.READ_IGNORE_TYPE, 1043 null, 1044 CmsDriverManager.READ_IGNORE_TIME, 1045 CmsDriverManager.READ_IGNORE_TIME, 1046 CmsDriverManager.READ_IGNORE_TIME, 1047 CmsDriverManager.READ_IGNORE_TIME, 1048 CmsDriverManager.READ_IGNORE_TIME, 1049 CmsDriverManager.READ_IGNORE_TIME, 1050 CmsDriverManager.READMODE_INCLUDE_TREE); 1051 1052 for (CmsResource delFile : movedFiles) { 1053 try { 1054 CmsResource offlineResource = vfsDriver.readResource( 1055 dbc, 1056 dbc.currentProject().getUuid(), 1057 delFile.getStructureId(), 1058 true); 1059 if (offlineResource.isFile()) { 1060 CmsFile offlineFile = new CmsFile(offlineResource); 1061 offlineFile.setContents( 1062 vfsDriver.readContent(dbc, dbc.currentProject().getUuid(), offlineFile.getResourceId())); 1063 internalWriteHistory( 1064 dbc, 1065 offlineFile, 1066 CmsResource.STATE_DELETED, 1067 null, 1068 publishHistoryId, 1069 publishTag); 1070 vfsDriver.deletePropertyObjects( 1071 dbc, 1072 onlineProject.getUuid(), 1073 delFile, 1074 CmsProperty.DELETE_OPTION_DELETE_STRUCTURE_AND_RESOURCE_VALUES); 1075 vfsDriver.removeFile(dbc, onlineProject.getUuid(), delFile); 1076 } else if (offlineResource.isFolder()) { 1077 1078 internalWriteHistory( 1079 dbc, 1080 offlineResource, 1081 CmsResource.STATE_DELETED, 1082 null, 1083 publishHistoryId, 1084 publishTag); 1085 vfsDriver.deletePropertyObjects( 1086 dbc, 1087 onlineProject.getUuid(), 1088 delFile, 1089 CmsProperty.DELETE_OPTION_DELETE_STRUCTURE_AND_RESOURCE_VALUES); 1090 vfsDriver.removeFolder(dbc, onlineProject, delFile); 1091 } 1092 } catch (CmsDataAccessException e) { 1093 if (LOG.isWarnEnabled()) { 1094 LOG.warn( 1095 Messages.get().getBundle().key(Messages.LOG_REMOVING_RESOURCE_1, delFile.getName()), 1096 e); 1097 } 1098 } 1099 } 1100 1101 // write history before deleting 1102 internalWriteHistory(dbc, currentFolder, folderState, null, publishHistoryId, publishTag); 1103 1104 try { 1105 // delete the properties online and offline 1106 vfsDriver.deletePropertyObjects( 1107 dbc, 1108 onlineProject.getUuid(), 1109 onlineFolder, 1110 CmsProperty.DELETE_OPTION_DELETE_STRUCTURE_AND_RESOURCE_VALUES); 1111 vfsDriver.deletePropertyObjects( 1112 dbc, 1113 dbc.currentProject().getUuid(), 1114 currentFolder, 1115 CmsProperty.DELETE_OPTION_DELETE_STRUCTURE_AND_RESOURCE_VALUES); 1116 } catch (CmsDataAccessException e) { 1117 if (LOG.isErrorEnabled()) { 1118 LOG.error( 1119 Messages.get().getBundle().key(Messages.LOG_DELETING_PROPERTIES_1, currentFolder.getRootPath()), 1120 e); 1121 } 1122 throw e; 1123 } 1124 1125 try { 1126 // remove the folder online and offline 1127 vfsDriver.removeFolder(dbc, dbc.currentProject(), currentFolder); 1128 vfsDriver.removeFolder(dbc, onlineProject, currentFolder); 1129 } catch (CmsDataAccessException e) { 1130 if (LOG.isErrorEnabled()) { 1131 LOG.error( 1132 Messages.get().getBundle().key(Messages.LOG_REMOVING_RESOURCE_1, currentFolder.getRootPath()), 1133 e); 1134 } 1135 throw e; 1136 } 1137 1138 try { 1139 // remove the ACL online and offline 1140 m_driverManager.getUserDriver(dbc).removeAccessControlEntries( 1141 dbc, 1142 onlineProject, 1143 onlineFolder.getResourceId()); 1144 m_driverManager.getUserDriver(dbc).removeAccessControlEntries( 1145 dbc, 1146 dbc.currentProject(), 1147 currentFolder.getResourceId()); 1148 } catch (CmsDataAccessException e) { 1149 if (LOG.isErrorEnabled()) { 1150 LOG.error( 1151 Messages.get().getBundle().key(Messages.LOG_REMOVING_ACL_1, currentFolder.getRootPath()), 1152 e); 1153 } 1154 throw e; 1155 } 1156 1157 // remove relations 1158 try { 1159 vfsDriver.deleteRelations(dbc, onlineProject.getUuid(), onlineFolder, CmsRelationFilter.TARGETS); 1160 vfsDriver.deleteRelations( 1161 dbc, 1162 dbc.currentProject().getUuid(), 1163 currentFolder, 1164 CmsRelationFilter.TARGETS); 1165 } catch (CmsDataAccessException e) { 1166 if (LOG.isErrorEnabled()) { 1167 LOG.error( 1168 Messages.get().getBundle().key(Messages.LOG_REMOVING_RELATIONS_1, currentFolder.getRootPath()), 1169 e); 1170 } 1171 throw e; 1172 } 1173 1174 // remove project resources 1175 String deletedResourceRootPath = currentFolder.getRootPath(); 1176 Iterator<CmsProject> itProjects = readProjectsForResource(dbc, deletedResourceRootPath).iterator(); 1177 while (itProjects.hasNext()) { 1178 CmsProject project = itProjects.next(); 1179 deleteProjectResource(dbc, project.getUuid(), deletedResourceRootPath); 1180 } 1181 1182 try { 1183 m_driverManager.getVfsDriver(dbc).deleteAliases( 1184 dbc, 1185 onlineProject, 1186 new CmsAliasFilter(null, null, currentFolder.getStructureId())); 1187 } catch (CmsDataAccessException e) { 1188 LOG.error("Could not delete aliases: " + e.getLocalizedMessage(), e); 1189 } 1190 1191 report.println( 1192 org.opencms.report.Messages.get().container(org.opencms.report.Messages.RPT_OK_0), 1193 I_CmsReport.FORMAT_OK); 1194 1195 if (LOG.isDebugEnabled()) { 1196 if (LOG.isDebugEnabled()) { 1197 LOG.debug( 1198 Messages.get().getBundle().key( 1199 Messages.LOG_DEL_FOLDER_3, 1200 currentFolder.getRootPath(), 1201 String.valueOf(m), 1202 String.valueOf(n))); 1203 } 1204 } 1205 } finally { 1206 // notify the app. that the published folder and it's properties have been modified offline 1207 OpenCms.fireCmsEvent( 1208 new CmsEvent( 1209 I_CmsEventListener.EVENT_RESOURCE_AND_PROPERTIES_MODIFIED, 1210 Collections.<String, Object> singletonMap(I_CmsEventListener.KEY_RESOURCE, currentFolder))); 1211 } 1212 } 1213 1214 /** 1215 * @see org.opencms.db.I_CmsProjectDriver#publishFile(org.opencms.db.CmsDbContext, org.opencms.report.I_CmsReport, int, int, org.opencms.file.CmsProject, org.opencms.file.CmsResource, java.util.Set, org.opencms.util.CmsUUID, int) 1216 */ 1217 public void publishFile( 1218 CmsDbContext dbc, 1219 I_CmsReport report, 1220 int m, 1221 int n, 1222 CmsProject onlineProject, 1223 CmsResource offlineResource, 1224 Set<CmsUUID> publishedContentIds, 1225 CmsUUID publishHistoryId, 1226 int publishTag) 1227 throws CmsDataAccessException { 1228 1229 /* 1230 * Never use onlineResource.getState() here! 1231 * Only use offlineResource.getState() to determine the state of an offline resource! 1232 * 1233 * In case a resource has siblings, after a sibling was published the structure 1234 * and resource states are reset to UNCHANGED -> the state of the corresponding 1235 * onlineResource is still NEW, DELETED or CHANGED. 1236 * Thus, using onlineResource.getState() will inevitably result in unpublished resources! 1237 */ 1238 1239 try { 1240 report.print( 1241 org.opencms.report.Messages.get().container( 1242 org.opencms.report.Messages.RPT_SUCCESSION_2, 1243 String.valueOf(m), 1244 String.valueOf(n)), 1245 I_CmsReport.FORMAT_NOTE); 1246 1247 if (offlineResource.getState().isDeleted()) { 1248 report.print(Messages.get().container(Messages.RPT_DELETE_FILE_0), I_CmsReport.FORMAT_NOTE); 1249 report.print( 1250 org.opencms.report.Messages.get().container( 1251 org.opencms.report.Messages.RPT_ARGUMENT_1, 1252 dbc.removeSiteRoot(offlineResource.getRootPath()))); 1253 report.print(org.opencms.report.Messages.get().container(org.opencms.report.Messages.RPT_DOTS_0)); 1254 1255 publishDeletedFile(dbc, onlineProject, offlineResource, publishHistoryId, publishTag); 1256 1257 dbc.pop(); 1258 List<CmsProperty> props = m_driverManager.readPropertyObjects(dbc, offlineResource, true); 1259 boolean removeDeleted = Boolean.parseBoolean( 1260 CmsProperty.get(CmsPropertyDefinition.PROPERTY_HISTORY_REMOVE_DELETED, props).getValue("false")); 1261 // delete old historical entries 1262 m_driverManager.getHistoryDriver(dbc).deleteEntries( 1263 dbc, 1264 new CmsHistoryFile(offlineResource), 1265 removeDeleted ? 0 : OpenCms.getSystemInfo().getHistoryVersionsAfterDeletion(), 1266 -1); 1267 1268 report.println( 1269 org.opencms.report.Messages.get().container(org.opencms.report.Messages.RPT_OK_0), 1270 I_CmsReport.FORMAT_OK); 1271 1272 if (LOG.isDebugEnabled()) { 1273 LOG.debug( 1274 Messages.get().getBundle().key( 1275 Messages.LOG_DEL_FILE_3, 1276 String.valueOf(m), 1277 String.valueOf(n), 1278 offlineResource.getRootPath())); 1279 } 1280 1281 } else if (offlineResource.getState().isChanged()) { 1282 report.print(Messages.get().container(Messages.RPT_PUBLISH_FILE_0), I_CmsReport.FORMAT_NOTE); 1283 report.print( 1284 org.opencms.report.Messages.get().container( 1285 org.opencms.report.Messages.RPT_ARGUMENT_1, 1286 dbc.removeSiteRoot(offlineResource.getRootPath()))); 1287 report.print(org.opencms.report.Messages.get().container(org.opencms.report.Messages.RPT_DOTS_0)); 1288 1289 publishChangedFile( 1290 dbc, 1291 onlineProject, 1292 offlineResource, 1293 publishedContentIds, 1294 publishHistoryId, 1295 publishTag); 1296 1297 dbc.pop(); 1298 // delete old historical entries 1299 m_driverManager.getHistoryDriver(dbc).deleteEntries( 1300 dbc, 1301 new CmsHistoryFile(offlineResource), 1302 OpenCms.getSystemInfo().getHistoryVersions(), 1303 -1); 1304 1305 report.println( 1306 org.opencms.report.Messages.get().container(org.opencms.report.Messages.RPT_OK_0), 1307 I_CmsReport.FORMAT_OK); 1308 1309 if (LOG.isDebugEnabled()) { 1310 LOG.debug( 1311 Messages.get().getBundle().key( 1312 Messages.LOG_PUBLISHING_FILE_3, 1313 offlineResource.getRootPath(), 1314 String.valueOf(m), 1315 String.valueOf(n))); 1316 } 1317 } else if (offlineResource.getState().isNew()) { 1318 report.print(Messages.get().container(Messages.RPT_PUBLISH_FILE_0), I_CmsReport.FORMAT_NOTE); 1319 report.print( 1320 org.opencms.report.Messages.get().container( 1321 org.opencms.report.Messages.RPT_ARGUMENT_1, 1322 dbc.removeSiteRoot(offlineResource.getRootPath()))); 1323 report.print(org.opencms.report.Messages.get().container(org.opencms.report.Messages.RPT_DOTS_0)); 1324 1325 publishNewFile(dbc, onlineProject, offlineResource, publishedContentIds, publishHistoryId, publishTag); 1326 1327 dbc.pop(); 1328 // delete old historical entries 1329 m_driverManager.getHistoryDriver(dbc).deleteEntries( 1330 dbc, 1331 new CmsHistoryFile(offlineResource), 1332 OpenCms.getSystemInfo().getHistoryVersions(), 1333 -1); 1334 1335 report.println( 1336 org.opencms.report.Messages.get().container(org.opencms.report.Messages.RPT_OK_0), 1337 I_CmsReport.FORMAT_OK); 1338 1339 if (LOG.isDebugEnabled()) { 1340 if (LOG.isDebugEnabled()) { 1341 LOG.debug( 1342 Messages.get().getBundle().key( 1343 Messages.LOG_PUBLISHING_FILE_3, 1344 offlineResource.getRootPath(), 1345 String.valueOf(m), 1346 String.valueOf(n))); 1347 } 1348 } 1349 } else { 1350 // state == unchanged !!?? something went really wrong 1351 report.print(Messages.get().container(Messages.RPT_PUBLISH_FILE_0), I_CmsReport.FORMAT_NOTE); 1352 report.print( 1353 org.opencms.report.Messages.get().container( 1354 org.opencms.report.Messages.RPT_ARGUMENT_1, 1355 dbc.removeSiteRoot(offlineResource.getRootPath()))); 1356 report.print(org.opencms.report.Messages.get().container(org.opencms.report.Messages.RPT_DOTS_0)); 1357 report.println( 1358 org.opencms.report.Messages.get().container(org.opencms.report.Messages.RPT_FAILED_0), 1359 I_CmsReport.FORMAT_ERROR); 1360 1361 if (LOG.isErrorEnabled()) { 1362 // the whole resource is printed out here 1363 LOG.error( 1364 Messages.get().getBundle().key( 1365 Messages.LOG_PUBLISHING_FILE_3, 1366 String.valueOf(m), 1367 String.valueOf(n), 1368 offlineResource)); 1369 } 1370 } 1371 m_driverManager.publishUrlNameMapping(dbc, offlineResource); 1372 if (offlineResource.getState().isDeleted()) { 1373 m_driverManager.getVfsDriver(dbc).deleteAliases( 1374 dbc, 1375 onlineProject, 1376 new CmsAliasFilter(null, null, offlineResource.getStructureId())); 1377 } 1378 } catch (CmsException e) { 1379 throw new CmsDataAccessException(e.getMessageContainer(), e); 1380 } finally { 1381 // notify the app. that the published file and it's properties have been modified offline 1382 Map<String, Object> data = new HashMap<String, Object>(2); 1383 data.put(I_CmsEventListener.KEY_RESOURCE, offlineResource); 1384 data.put(I_CmsEventListener.KEY_SKIPINDEX, Boolean.valueOf(true)); 1385 1386 OpenCms.fireCmsEvent(new CmsEvent(I_CmsEventListener.EVENT_RESOURCE_AND_PROPERTIES_MODIFIED, data)); 1387 } 1388 } 1389 1390 /** 1391 * @see org.opencms.db.I_CmsProjectDriver#publishFileContent(CmsDbContext, CmsProject, CmsProject, CmsResource, Set, boolean, int) 1392 */ 1393 public CmsFile publishFileContent( 1394 CmsDbContext dbc, 1395 CmsProject offlineProject, 1396 CmsProject onlineProject, 1397 CmsResource offlineResource, 1398 Set<CmsUUID> publishedResourceIds, 1399 boolean needToUpdateContent, 1400 int publishTag) 1401 throws CmsDataAccessException { 1402 1403 CmsFile newFile = null; 1404 try { 1405 // read the file content offline 1406 CmsUUID projectId = dbc.getProjectId(); 1407 boolean dbcHasProjectId = (projectId != null) && !projectId.isNullUUID(); 1408 CmsUUID projectIdForReading = (!dbcHasProjectId ? offlineProject.getUuid() : CmsProject.ONLINE_PROJECT_ID); 1409 dbc.setProjectId(offlineProject.getUuid()); 1410 byte[] offlineContent = m_driverManager.getVfsDriver(dbc).readContent( 1411 dbc, 1412 projectIdForReading, 1413 offlineResource.getResourceId()); 1414 CmsFile offlineFile = new CmsFile(offlineResource); 1415 offlineFile.setContents(offlineContent); 1416 dbc.setProjectId(projectId); 1417 1418 // create the file online 1419 newFile = (CmsFile)offlineFile.clone(); 1420 newFile.setState(CmsResource.STATE_UNCHANGED); 1421 1422 boolean createSibling = true; 1423 // check if we are facing with a create new sibling operation 1424 if (!offlineFile.getState().isNew()) { 1425 createSibling = false; 1426 } else { 1427 // check if the resource entry already exists 1428 if (!m_driverManager.getVfsDriver(dbc).validateResourceIdExists( 1429 dbc, 1430 onlineProject.getUuid(), 1431 offlineFile.getResourceId())) { 1432 // we are creating a normal resource and not a sibling 1433 createSibling = false; 1434 } 1435 } 1436 1437 // only update the content if it was not updated before 1438 boolean alreadyPublished = publishedResourceIds.contains(offlineResource.getResourceId()); 1439 needToUpdateContent &= !alreadyPublished; 1440 1441 if (createSibling) { 1442 if (!alreadyPublished) { 1443 // create the file online, the first time a sibling is published also the resource entry has to be actualized 1444 m_driverManager.getVfsDriver(dbc).createResource(dbc, onlineProject.getUuid(), newFile, null); 1445 } else { 1446 // create the sibling online 1447 m_driverManager.getVfsDriver(dbc).createSibling(dbc, onlineProject, offlineResource); 1448 } 1449 newFile = new CmsFile(offlineResource); 1450 newFile.setContents(offlineContent); 1451 } else { 1452 // update the online/offline structure and resource records of the file 1453 m_driverManager.getVfsDriver(dbc).publishResource(dbc, onlineProject, newFile, offlineFile); 1454 } 1455 // update version numbers 1456 m_driverManager.getVfsDriver(dbc).publishVersions(dbc, offlineResource, !alreadyPublished); 1457 1458 // create/update the content 1459 m_driverManager.getVfsDriver(dbc).createOnlineContent( 1460 dbc, 1461 offlineFile.getResourceId(), 1462 offlineFile.getContents(), 1463 publishTag, 1464 true, 1465 needToUpdateContent); 1466 1467 // mark the resource as written to avoid that the same content is written for each sibling instance 1468 publishedResourceIds.add(offlineResource.getResourceId()); 1469 } catch (CmsDataAccessException e) { 1470 if (LOG.isErrorEnabled()) { 1471 LOG.error( 1472 Messages.get().getBundle().key(Messages.LOG_PUBLISHING_FILE_CONTENT_1, offlineResource.toString()), 1473 e); 1474 } 1475 throw e; 1476 } 1477 return newFile; 1478 } 1479 1480 /** 1481 * @see org.opencms.db.I_CmsProjectDriver#publishFolder(org.opencms.db.CmsDbContext, org.opencms.report.I_CmsReport, int, int, org.opencms.file.CmsProject, org.opencms.file.CmsFolder, org.opencms.util.CmsUUID, int) 1482 */ 1483 public void publishFolder( 1484 CmsDbContext dbc, 1485 I_CmsReport report, 1486 int m, 1487 int n, 1488 CmsProject onlineProject, 1489 CmsFolder offlineFolder, 1490 CmsUUID publishHistoryId, 1491 int publishTag) 1492 throws CmsDataAccessException { 1493 1494 try { 1495 report.print( 1496 org.opencms.report.Messages.get().container( 1497 org.opencms.report.Messages.RPT_SUCCESSION_2, 1498 String.valueOf(m), 1499 String.valueOf(n)), 1500 I_CmsReport.FORMAT_NOTE); 1501 report.print(Messages.get().container(Messages.RPT_PUBLISH_FOLDER_0), I_CmsReport.FORMAT_NOTE); 1502 report.print( 1503 org.opencms.report.Messages.get().container( 1504 org.opencms.report.Messages.RPT_ARGUMENT_1, 1505 dbc.removeSiteRoot(offlineFolder.getRootPath()))); 1506 report.print(org.opencms.report.Messages.get().container(org.opencms.report.Messages.RPT_DOTS_0)); 1507 1508 CmsResourceState resourceState = fixMovedResource( 1509 dbc, 1510 onlineProject, 1511 offlineFolder, 1512 publishHistoryId, 1513 publishTag); 1514 1515 CmsResource onlineFolder = null; 1516 if (offlineFolder.getState().isNew()) { 1517 try { 1518 // create the folder online 1519 CmsResource newFolder = (CmsFolder)offlineFolder.clone(); 1520 newFolder.setState(CmsResource.STATE_UNCHANGED); 1521 1522 onlineFolder = m_driverManager.getVfsDriver( 1523 dbc).createResource(dbc, onlineProject.getUuid(), newFolder, null); 1524 m_driverManager.getVfsDriver(dbc).publishResource(dbc, onlineProject, onlineFolder, offlineFolder); 1525 // update version numbers 1526 m_driverManager.getVfsDriver(dbc).publishVersions(dbc, offlineFolder, true); 1527 } catch (CmsVfsResourceAlreadyExistsException e) { 1528 if (!offlineFolder.getRootPath().equals("/") 1529 && !offlineFolder.getRootPath().equals("/system/") 1530 && LOG.isWarnEnabled()) { 1531 LOG.warn( 1532 Messages.get().getBundle().key( 1533 Messages.LOG_WARN_FOLDER_WRONG_STATE_CN_1, 1534 offlineFolder.getRootPath())); 1535 } 1536 try { 1537 onlineFolder = m_driverManager.getVfsDriver(dbc).readFolder( 1538 dbc, 1539 onlineProject.getUuid(), 1540 offlineFolder.getRootPath()); 1541 m_driverManager.getVfsDriver( 1542 dbc).publishResource(dbc, onlineProject, onlineFolder, offlineFolder); 1543 // update version numbers 1544 m_driverManager.getVfsDriver(dbc).publishVersions(dbc, offlineFolder, true); 1545 } catch (CmsDataAccessException e1) { 1546 if (LOG.isErrorEnabled()) { 1547 LOG.error( 1548 Messages.get().getBundle().key( 1549 Messages.LOG_READING_RESOURCE_1, 1550 offlineFolder.getRootPath()), 1551 e); 1552 } 1553 throw e1; 1554 } 1555 } catch (CmsDataAccessException e) { 1556 if (LOG.isErrorEnabled()) { 1557 LOG.error( 1558 Messages.get().getBundle().key( 1559 Messages.LOG_PUBLISHING_RESOURCE_1, 1560 offlineFolder.getRootPath()), 1561 e); 1562 } 1563 throw e; 1564 } 1565 } else if (offlineFolder.getState().isChanged()) { 1566 try { 1567 // read the folder online 1568 onlineFolder = m_driverManager.getVfsDriver(dbc).readFolder( 1569 dbc, 1570 onlineProject.getUuid(), 1571 offlineFolder.getStructureId()); 1572 } catch (CmsVfsResourceNotFoundException e) { 1573 if (LOG.isWarnEnabled()) { 1574 LOG.warn( 1575 Messages.get().getBundle().key( 1576 Messages.LOG_WARN_FOLDER_WRONG_STATE_NC_1, 1577 offlineFolder.getRootPath())); 1578 } 1579 try { 1580 onlineFolder = m_driverManager.getVfsDriver( 1581 dbc).createResource(dbc, onlineProject.getUuid(), offlineFolder, null); 1582 internalResetResourceState(dbc, onlineFolder); 1583 } catch (CmsDataAccessException e1) { 1584 if (LOG.isErrorEnabled()) { 1585 LOG.error( 1586 Messages.get().getBundle().key( 1587 Messages.LOG_PUBLISHING_RESOURCE_1, 1588 offlineFolder.getRootPath()), 1589 e); 1590 } 1591 throw e1; 1592 } 1593 } 1594 1595 try { 1596 // update the folder online 1597 m_driverManager.getVfsDriver(dbc).publishResource(dbc, onlineProject, onlineFolder, offlineFolder); 1598 // update version numbers 1599 m_driverManager.getVfsDriver(dbc).publishVersions(dbc, offlineFolder, true); 1600 } catch (CmsDataAccessException e) { 1601 if (LOG.isErrorEnabled()) { 1602 LOG.error( 1603 Messages.get().getBundle().key( 1604 Messages.LOG_PUBLISHING_RESOURCE_1, 1605 offlineFolder.getRootPath()), 1606 e); 1607 } 1608 throw e; 1609 } 1610 } 1611 1612 if (onlineFolder != null) { 1613 try { 1614 // write the ACL online 1615 m_driverManager.getUserDriver(dbc).publishAccessControlEntries( 1616 dbc, 1617 dbc.currentProject(), 1618 onlineProject, 1619 offlineFolder.getResourceId(), 1620 onlineFolder.getResourceId()); 1621 } catch (CmsDataAccessException e) { 1622 if (LOG.isErrorEnabled()) { 1623 LOG.error( 1624 Messages.get().getBundle().key(Messages.LOG_PUBLISHING_ACL_1, offlineFolder.getRootPath()), 1625 e); 1626 } 1627 throw e; 1628 } 1629 } 1630 1631 List<CmsProperty> offlineProperties = null; 1632 try { 1633 // write the properties online 1634 m_driverManager.getVfsDriver(dbc).deletePropertyObjects( 1635 dbc, 1636 onlineProject.getUuid(), 1637 onlineFolder, 1638 CmsProperty.DELETE_OPTION_DELETE_STRUCTURE_AND_RESOURCE_VALUES); 1639 offlineProperties = m_driverManager.getVfsDriver(dbc).readPropertyObjects( 1640 dbc, 1641 dbc.currentProject(), 1642 offlineFolder); 1643 CmsProperty.setAutoCreatePropertyDefinitions(offlineProperties, true); 1644 m_driverManager.getVfsDriver( 1645 dbc).writePropertyObjects(dbc, onlineProject, onlineFolder, offlineProperties); 1646 } catch (CmsDataAccessException e) { 1647 if (LOG.isErrorEnabled()) { 1648 LOG.error( 1649 Messages.get().getBundle().key( 1650 Messages.LOG_PUBLISHING_PROPERTIES_1, 1651 offlineFolder.getRootPath()), 1652 e); 1653 } 1654 throw e; 1655 } 1656 1657 internalWriteHistory(dbc, offlineFolder, resourceState, offlineProperties, publishHistoryId, publishTag); 1658 1659 m_driverManager.getVfsDriver(dbc).updateRelations(dbc, onlineProject, offlineFolder); 1660 1661 report.println( 1662 org.opencms.report.Messages.get().container(org.opencms.report.Messages.RPT_OK_0), 1663 I_CmsReport.FORMAT_OK); 1664 1665 if (LOG.isDebugEnabled()) { 1666 LOG.debug( 1667 Messages.get().getBundle().key( 1668 Messages.LOG_PUBLISHING_FOLDER_3, 1669 String.valueOf(m), 1670 String.valueOf(n), 1671 offlineFolder.getRootPath())); 1672 } 1673 } finally { 1674 // notify the app. that the published folder and it's properties have been modified offline 1675 OpenCms.fireCmsEvent( 1676 new CmsEvent( 1677 I_CmsEventListener.EVENT_RESOURCE_AND_PROPERTIES_MODIFIED, 1678 Collections.<String, Object> singletonMap(I_CmsEventListener.KEY_RESOURCE, offlineFolder))); 1679 } 1680 } 1681 1682 /** 1683 * @see org.opencms.db.I_CmsProjectDriver#publishProject(org.opencms.db.CmsDbContext, org.opencms.report.I_CmsReport, org.opencms.file.CmsProject, org.opencms.db.CmsPublishList, int) 1684 */ 1685 public void publishProject( 1686 CmsDbContext dbc, 1687 I_CmsReport report, 1688 CmsProject onlineProject, 1689 CmsPublishList publishList, 1690 int publishTag) 1691 throws CmsException { 1692 1693 int publishedFolderCount = 0; 1694 int deletedFolderCount = 0; 1695 int publishedFileCount = 0; 1696 Set<CmsUUID> publishedContentIds = new HashSet<CmsUUID>(); 1697 Set<CmsUUID> publishedIds = new HashSet<CmsUUID>(); 1698 1699 try { 1700 1701 //////////////////////////////////////////////////////////////////////////////////////// 1702 // write the historical project entry 1703 1704 if (OpenCms.getSystemInfo().isHistoryEnabled()) { 1705 try { 1706 // write an entry in the publish project log 1707 m_driverManager.getHistoryDriver(dbc).writeProject(dbc, publishTag, System.currentTimeMillis()); 1708 dbc.pop(); 1709 } catch (Throwable t) { 1710 dbc.report( 1711 report, 1712 Messages.get().container( 1713 Messages.ERR_WRITING_HISTORY_OF_PROJECT_1, 1714 dbc.currentProject().getName()), 1715 t); 1716 } 1717 } 1718 1719 /////////////////////////////////////////////////////////////////////////////////////// 1720 // publish new/changed folders 1721 1722 if (LOG.isDebugEnabled()) { 1723 LOG.debug( 1724 Messages.get().getBundle().key( 1725 Messages.LOG_START_PUBLISHING_PROJECT_2, 1726 dbc.currentProject().getName(), 1727 dbc.currentUser().getName())); 1728 } 1729 1730 publishedFolderCount = 0; 1731 int foldersSize = publishList.getFolderList().size(); 1732 if (foldersSize > 0) { 1733 report.println( 1734 Messages.get().container(Messages.RPT_PUBLISH_FOLDERS_BEGIN_0), 1735 I_CmsReport.FORMAT_HEADLINE); 1736 } 1737 1738 Iterator<CmsResource> itFolders = publishList.getFolderList().iterator(); 1739 I_CmsProjectDriver projectDriver = m_driverManager.getProjectDriver(dbc); 1740 I_CmsHistoryDriver historyDriver = m_driverManager.getHistoryDriver(dbc); 1741 while (itFolders.hasNext()) { 1742 CmsResource currentFolder = itFolders.next(); 1743 try { 1744 if (currentFolder.getState().isNew() || currentFolder.getState().isChanged()) { 1745 // bounce the current publish task through all project drivers 1746 projectDriver.publishFolder( 1747 dbc, 1748 report, 1749 ++publishedFolderCount, 1750 foldersSize, 1751 onlineProject, 1752 new CmsFolder(currentFolder), 1753 publishList.getPublishHistoryId(), 1754 publishTag); 1755 1756 dbc.pop(); 1757 1758 publishedIds.add(currentFolder.getStructureId()); 1759 // log it 1760 CmsLogEntryType type = currentFolder.getState().isNew() 1761 ? CmsLogEntryType.RESOURCE_PUBLISHED_NEW 1762 : CmsLogEntryType.RESOURCE_PUBLISHED_MODIFIED; 1763 m_driverManager.log( 1764 dbc, 1765 new CmsLogEntry( 1766 dbc, 1767 currentFolder.getStructureId(), 1768 type, 1769 new String[] {currentFolder.getRootPath()}), 1770 true); 1771 1772 // delete old historical entries 1773 historyDriver.deleteEntries( 1774 dbc, 1775 new CmsHistoryFile(currentFolder), 1776 OpenCms.getSystemInfo().getHistoryVersions(), 1777 -1); 1778 1779 // reset the resource state to UNCHANGED and the last-modified-in-project-ID to 0 1780 internalResetResourceState(dbc, currentFolder); 1781 1782 if (!CmsModificationContext.isInOnlineFolder(currentFolder.getRootPath())) { 1783 m_driverManager.unlockResource(dbc, currentFolder, true, true); 1784 } 1785 } else { 1786 // state == unchanged !!?? something went really wrong 1787 report.print(Messages.get().container(Messages.RPT_PUBLISH_FOLDER_0), I_CmsReport.FORMAT_NOTE); 1788 report.print( 1789 org.opencms.report.Messages.get().container( 1790 org.opencms.report.Messages.RPT_ARGUMENT_1, 1791 dbc.removeSiteRoot(currentFolder.getRootPath()))); 1792 report.print( 1793 org.opencms.report.Messages.get().container(org.opencms.report.Messages.RPT_DOTS_0)); 1794 report.println( 1795 org.opencms.report.Messages.get().container(org.opencms.report.Messages.RPT_FAILED_0), 1796 I_CmsReport.FORMAT_ERROR); 1797 1798 if (LOG.isErrorEnabled()) { 1799 // the whole resource is printed out here 1800 LOG.error( 1801 Messages.get().getBundle().key( 1802 Messages.LOG_PUBLISHING_FILE_3, 1803 String.valueOf(++publishedFolderCount), 1804 String.valueOf(foldersSize), 1805 currentFolder)); 1806 } 1807 } 1808 1809 dbc.pop(); 1810 } catch (Throwable t) { 1811 dbc.report( 1812 report, 1813 Messages.get().container(Messages.ERR_ERROR_PUBLISHING_FOLDER_1, currentFolder.getRootPath()), 1814 t); 1815 } 1816 } 1817 1818 if (foldersSize > 0) { 1819 report.println( 1820 Messages.get().container(Messages.RPT_PUBLISH_FOLDERS_END_0), 1821 I_CmsReport.FORMAT_HEADLINE); 1822 } 1823 1824 /////////////////////////////////////////////////////////////////////////////////////// 1825 // publish changed/new/deleted files 1826 1827 publishedFileCount = 0; 1828 int filesSize = publishList.getFileList().size(); 1829 1830 if (filesSize > 0) { 1831 report.println( 1832 Messages.get().container(Messages.RPT_PUBLISH_FILES_BEGIN_0), 1833 I_CmsReport.FORMAT_HEADLINE); 1834 } 1835 1836 Set<CmsUUID> deletedResourceIds = new HashSet<CmsUUID>(); 1837 Set<CmsUUID> changedResourceIds = new HashSet<CmsUUID>(); 1838 for (CmsResource res : publishList.getFileList()) { 1839 if (res.getState().isDeleted()) { 1840 deletedResourceIds.add(res.getResourceId()); 1841 } else { 1842 changedResourceIds.add(res.getResourceId()); 1843 } 1844 } 1845 Set<CmsUUID> changedAndDeletedResourceIds = Sets.intersection(deletedResourceIds, changedResourceIds); 1846 dbc.setAttribute(CmsDriverManager.KEY_CHANGED_AND_DELETED, changedAndDeletedResourceIds); 1847 1848 Iterator<CmsResource> itFiles = publishList.getFileList().iterator(); 1849 while (itFiles.hasNext()) { 1850 CmsResource currentResource = itFiles.next(); 1851 try { 1852 // bounce the current publish task through all project drivers 1853 projectDriver.publishFile( 1854 dbc, 1855 report, 1856 ++publishedFileCount, 1857 filesSize, 1858 onlineProject, 1859 currentResource, 1860 publishedContentIds, 1861 publishList.getPublishHistoryId(), 1862 publishTag); 1863 1864 CmsResourceState state = currentResource.getState(); 1865 if (!state.isDeleted()) { 1866 // reset the resource state to UNCHANGED and the last-modified-in-project-ID to 0 1867 internalResetResourceState(dbc, currentResource); 1868 } 1869 1870 // unlock it 1871 if (!CmsModificationContext.isInOnlineFolder(currentResource.getRootPath())) { 1872 m_driverManager.unlockResource(dbc, currentResource, true, true); 1873 } 1874 // log it 1875 CmsLogEntryType type = state.isNew() 1876 ? CmsLogEntryType.RESOURCE_PUBLISHED_NEW 1877 : (state.isDeleted() 1878 ? CmsLogEntryType.RESOURCE_PUBLISHED_DELETED 1879 : CmsLogEntryType.RESOURCE_PUBLISHED_MODIFIED); 1880 m_driverManager.log( 1881 dbc, 1882 new CmsLogEntry( 1883 dbc, 1884 currentResource.getStructureId(), 1885 type, 1886 new String[] {currentResource.getRootPath()}), 1887 true); 1888 1889 publishedIds.add(currentResource.getStructureId()); 1890 dbc.pop(); 1891 } catch (Throwable t) { 1892 dbc.report( 1893 report, 1894 Messages.get().container(Messages.ERR_ERROR_PUBLISHING_FILE_1, currentResource.getRootPath()), 1895 t); 1896 } 1897 } 1898 1899 if (filesSize > 0) { 1900 report.println(Messages.get().container(Messages.RPT_PUBLISH_FILES_END_0), I_CmsReport.FORMAT_HEADLINE); 1901 } 1902 1903 //////////////////////////////////////////////////////////////////////////////////////// 1904 1905 // publish deleted folders 1906 List<CmsResource> deletedFolders = publishList.getDeletedFolderList(); 1907 if (deletedFolders.isEmpty()) { 1908 return; 1909 } 1910 1911 deletedFolderCount = 0; 1912 int deletedFoldersSize = deletedFolders.size(); 1913 if (deletedFoldersSize > 0) { 1914 report.println( 1915 Messages.get().container(Messages.RPT_DELETE_FOLDERS_BEGIN_0), 1916 I_CmsReport.FORMAT_HEADLINE); 1917 } 1918 1919 Iterator<CmsResource> itDeletedFolders = deletedFolders.iterator(); 1920 while (itDeletedFolders.hasNext()) { 1921 CmsResource currentFolder = itDeletedFolders.next(); 1922 1923 try { 1924 // bounce the current publish task through all project drivers 1925 projectDriver.publishDeletedFolder( 1926 dbc, 1927 report, 1928 ++deletedFolderCount, 1929 deletedFoldersSize, 1930 onlineProject, 1931 new CmsFolder(currentFolder), 1932 publishList.getPublishHistoryId(), 1933 publishTag); 1934 1935 dbc.pop(); 1936 // delete old historical entries 1937 m_driverManager.getHistoryDriver(dbc).deleteEntries( 1938 dbc, 1939 new CmsHistoryFile(currentFolder), 1940 OpenCms.getSystemInfo().getHistoryVersionsAfterDeletion(), 1941 -1); 1942 1943 publishedIds.add(currentFolder.getStructureId()); 1944 // unlock it 1945 if (!CmsModificationContext.isInOnlineFolder(currentFolder.getRootPath())) { 1946 m_driverManager.unlockResource(dbc, currentFolder, true, true); 1947 } 1948 // log it 1949 m_driverManager.log( 1950 dbc, 1951 new CmsLogEntry( 1952 dbc, 1953 currentFolder.getStructureId(), 1954 CmsLogEntryType.RESOURCE_PUBLISHED_DELETED, 1955 new String[] {currentFolder.getRootPath()}), 1956 true); 1957 1958 dbc.pop(); 1959 } catch (Throwable t) { 1960 dbc.report( 1961 report, 1962 Messages.get().container( 1963 Messages.ERR_ERROR_PUBLISHING_DELETED_FOLDER_1, 1964 currentFolder.getRootPath()), 1965 t); 1966 } 1967 } 1968 1969 if (deletedFoldersSize > 0) { 1970 report.println( 1971 Messages.get().container(Messages.RPT_DELETE_FOLDERS_END_0), 1972 I_CmsReport.FORMAT_HEADLINE); 1973 } 1974 } catch (OutOfMemoryError o) { 1975 // clear all caches to reclaim memory 1976 OpenCms.fireCmsEvent( 1977 new CmsEvent(I_CmsEventListener.EVENT_CLEAR_CACHES, Collections.<String, Object> emptyMap())); 1978 1979 CmsMessageContainer message = Messages.get().container(Messages.ERR_OUT_OF_MEMORY_0); 1980 if (LOG.isErrorEnabled()) { 1981 LOG.error(message.key(), o); 1982 } 1983 throw new CmsDataAccessException(message, o); 1984 } finally { 1985 // reset vfs driver internal info after publishing 1986 m_driverManager.getVfsDriver(dbc).publishVersions(dbc, null, false); 1987 Object[] msgArgs = new Object[] { 1988 String.valueOf(publishedFileCount), 1989 String.valueOf(publishedFolderCount), 1990 String.valueOf(deletedFolderCount), 1991 report.formatRuntime()}; 1992 1993 CmsMessageContainer message = Messages.get().container(Messages.RPT_PUBLISH_STAT_4, msgArgs); 1994 if (LOG.isInfoEnabled()) { 1995 LOG.info(message.key()); 1996 } 1997 report.println(message); 1998 } 1999 } 2000 2001 /** 2002 * @see org.opencms.db.I_CmsProjectDriver#readLocks(org.opencms.db.CmsDbContext) 2003 */ 2004 public List<CmsLock> readLocks(CmsDbContext dbc) throws CmsDataAccessException { 2005 2006 Connection conn = null; 2007 PreparedStatement stmt = null; 2008 List<CmsTempResourceLock> tmpLocks = new ArrayList<CmsTempResourceLock>(256); 2009 List<CmsLock> locks = new ArrayList<CmsLock>(256); 2010 try { 2011 conn = m_sqlManager.getConnection(dbc); 2012 stmt = m_sqlManager.getPreparedStatement(conn, "C_RESOURCE_LOCKS_READALL"); 2013 ResultSet rs = stmt.executeQuery(); 2014 while (rs.next()) { 2015 String resourcePath = rs.getString(m_sqlManager.readQuery("C_RESOURCE_LOCKS_RESOURCE_PATH")); 2016 CmsUUID userId = new CmsUUID(rs.getString(m_sqlManager.readQuery("C_RESOURCE_LOCKS_USER_ID"))); 2017 CmsUUID projectId = new CmsUUID(rs.getString(m_sqlManager.readQuery("C_RESOURCE_LOCKS_PROJECT_ID"))); 2018 int lockType = rs.getInt(m_sqlManager.readQuery("C_RESOURCE_LOCKS_LOCK_TYPE")); 2019 CmsTempResourceLock tmpLock = new CmsTempResourceLock(resourcePath, userId, projectId, lockType); 2020 tmpLocks.add(tmpLock); 2021 } 2022 } catch (SQLException e) { 2023 throw new CmsDbSqlException( 2024 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2025 e); 2026 } finally { 2027 m_sqlManager.closeAll(dbc, conn, stmt, null); 2028 } 2029 2030 for (CmsTempResourceLock tmpLock : tmpLocks) { 2031 CmsProject project; 2032 try { 2033 project = readProject(dbc, tmpLock.getProjectId()); 2034 } catch (CmsDataAccessException dae) { 2035 // the project does not longer exist, ignore this lock (should usually not happen) 2036 project = null; 2037 } 2038 if (project != null) { 2039 CmsLock lock = new CmsLock( 2040 tmpLock.getResourcePath(), 2041 tmpLock.getUserId(), 2042 project, 2043 CmsLockType.valueOf(tmpLock.getLockType())); 2044 locks.add(lock); 2045 } 2046 } 2047 if (LOG.isDebugEnabled()) { 2048 LOG.debug(Messages.get().getBundle().key(Messages.LOG_DBG_READ_LOCKS_1, Integer.valueOf(locks.size()))); 2049 } 2050 return locks; 2051 } 2052 2053 /** 2054 * @see org.opencms.db.I_CmsProjectDriver#readLog(org.opencms.db.CmsDbContext, org.opencms.db.log.CmsLogFilter) 2055 */ 2056 public List<CmsLogEntry> readLog(CmsDbContext dbc, CmsLogFilter filter) throws CmsDataAccessException { 2057 2058 List<CmsLogEntry> entries = new ArrayList<CmsLogEntry>(); 2059 2060 Connection conn = null; 2061 PreparedStatement stmt = null; 2062 ResultSet res = null; 2063 2064 try { 2065 conn = m_sqlManager.getConnection(dbc); 2066 // compose statement 2067 StringBuffer queryBuf = new StringBuffer(256); 2068 queryBuf.append(m_sqlManager.readQuery("C_LOG_READ_ENTRIES")); 2069 CmsPair<String, List<I_CmsPreparedStatementParameter>> conditionsAndParameters = prepareLogConditions( 2070 filter); 2071 List<I_CmsPreparedStatementParameter> params = conditionsAndParameters.getSecond(); 2072 queryBuf.append(conditionsAndParameters.getFirst()); 2073 2074 if (LOG.isDebugEnabled()) { 2075 LOG.debug(queryBuf.toString()); 2076 } 2077 stmt = m_sqlManager.getPreparedStatementForSql(conn, queryBuf.toString()); 2078 for (int i = 0; i < params.size(); i++) { 2079 I_CmsPreparedStatementParameter param = params.get(i); 2080 param.insertIntoStatement(stmt, i + 1); 2081 } 2082 2083 // execute 2084 res = stmt.executeQuery(); 2085 while (res.next()) { 2086 // get results 2087 entries.add(internalReadLogEntry(res)); 2088 } 2089 } catch (SQLException e) { 2090 throw new CmsDbSqlException( 2091 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2092 e); 2093 } finally { 2094 m_sqlManager.closeAll(dbc, conn, stmt, res); 2095 } 2096 return entries; 2097 } 2098 2099 /** 2100 * @see org.opencms.db.I_CmsProjectDriver#readProject(org.opencms.db.CmsDbContext, CmsUUID) 2101 */ 2102 public CmsProject readProject(CmsDbContext dbc, CmsUUID id) throws CmsDataAccessException { 2103 2104 PreparedStatement stmt = null; 2105 CmsProject project = null; 2106 ResultSet res = null; 2107 Connection conn = null; 2108 2109 try { 2110 conn = m_sqlManager.getConnection(dbc); 2111 stmt = m_sqlManager.getPreparedStatement(conn, "C_PROJECTS_READ_1"); 2112 2113 stmt.setString(1, id.toString()); 2114 res = stmt.executeQuery(); 2115 2116 if (res.next()) { 2117 project = internalCreateProject(res); 2118 while (res.next()) { 2119 // do nothing only move through all rows because of mssql odbc driver 2120 } 2121 } else { 2122 throw new CmsDbEntryNotFoundException( 2123 Messages.get().container(Messages.ERR_NO_PROJECT_WITH_ID_1, String.valueOf(id))); 2124 } 2125 } catch (SQLException e) { 2126 throw new CmsDbSqlException( 2127 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2128 e); 2129 } finally { 2130 m_sqlManager.closeAll(dbc, conn, stmt, res); 2131 } 2132 2133 return project; 2134 } 2135 2136 /** 2137 * @see org.opencms.db.I_CmsProjectDriver#readProject(org.opencms.db.CmsDbContext, java.lang.String) 2138 */ 2139 public CmsProject readProject(CmsDbContext dbc, String projectFqn) throws CmsDataAccessException { 2140 2141 PreparedStatement stmt = null; 2142 CmsProject project = null; 2143 ResultSet res = null; 2144 Connection conn = null; 2145 2146 try { 2147 conn = m_sqlManager.getConnection(dbc); 2148 stmt = m_sqlManager.getPreparedStatement(conn, "C_PROJECTS_READ_BYNAME_2"); 2149 2150 stmt.setString(1, CmsOrganizationalUnit.getSimpleName(projectFqn)); 2151 stmt.setString(2, CmsOrganizationalUnit.SEPARATOR + CmsOrganizationalUnit.getParentFqn(projectFqn)); 2152 res = stmt.executeQuery(); 2153 2154 if (res.next()) { 2155 project = internalCreateProject(res); 2156 while (res.next()) { 2157 // do nothing only move through all rows because of mssql odbc driver 2158 } 2159 } else { 2160 throw new CmsDbEntryNotFoundException( 2161 Messages.get().container(Messages.ERR_NO_PROJECT_WITH_NAME_1, projectFqn)); 2162 } 2163 } catch (SQLException e) { 2164 throw new CmsDbSqlException( 2165 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2166 e); 2167 } finally { 2168 m_sqlManager.closeAll(dbc, conn, stmt, res); 2169 } 2170 2171 return project; 2172 } 2173 2174 /** 2175 * @see org.opencms.db.I_CmsProjectDriver#readProjectResource(org.opencms.db.CmsDbContext, CmsUUID, java.lang.String) 2176 */ 2177 public String readProjectResource(CmsDbContext dbc, CmsUUID projectId, String resourcePath) 2178 throws CmsDataAccessException { 2179 2180 PreparedStatement stmt = null; 2181 Connection conn = null; 2182 ResultSet res = null; 2183 String resName = null; 2184 2185 try { 2186 conn = getSqlManager().getConnection(dbc); 2187 stmt = m_sqlManager.getPreparedStatement(conn, "C_PROJECTRESOURCES_READ_2"); 2188 2189 // select resource from the database 2190 stmt.setString(1, projectId.toString()); 2191 stmt.setString(2, resourcePath); 2192 res = stmt.executeQuery(); 2193 2194 if (res.next()) { 2195 resName = res.getString("RESOURCE_PATH"); 2196 while (res.next()) { 2197 // do nothing only move through all rows because of mssql odbc driver 2198 } 2199 } else { 2200 throw new CmsVfsResourceNotFoundException( 2201 Messages.get().container(Messages.ERR_NO_PROJECTRESOURCE_1, resourcePath)); 2202 } 2203 } catch (SQLException e) { 2204 throw new CmsDbSqlException( 2205 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2206 e); 2207 } finally { 2208 m_sqlManager.closeAll(dbc, conn, stmt, res); 2209 } 2210 return resName; 2211 } 2212 2213 /** 2214 * @see org.opencms.db.I_CmsProjectDriver#readProjectResources(org.opencms.db.CmsDbContext, org.opencms.file.CmsProject) 2215 */ 2216 public List<String> readProjectResources(CmsDbContext dbc, CmsProject project) throws CmsDataAccessException { 2217 2218 PreparedStatement stmt = null; 2219 Connection conn = null; 2220 ResultSet res = null; 2221 List<String> result = new ArrayList<String>(); 2222 2223 try { 2224 conn = m_sqlManager.getConnection(dbc); 2225 stmt = m_sqlManager.getPreparedStatement(conn, "C_PROJECTRESOURCES_READ_BY_ID_1"); 2226 stmt.setString(1, project.getUuid().toString()); 2227 res = stmt.executeQuery(); 2228 2229 while (res.next()) { 2230 result.add(res.getString("RESOURCE_PATH")); 2231 } 2232 } catch (SQLException e) { 2233 throw new CmsDbSqlException( 2234 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2235 e); 2236 } finally { 2237 m_sqlManager.closeAll(dbc, conn, stmt, res); 2238 } 2239 2240 return result; 2241 } 2242 2243 /** 2244 * @see org.opencms.db.I_CmsProjectDriver#readProjects(org.opencms.db.CmsDbContext, String) 2245 */ 2246 public List<CmsProject> readProjects(CmsDbContext dbc, String ouFqn) throws CmsDataAccessException { 2247 2248 if ((dbc.getRequestContext() != null) 2249 && (dbc.getRequestContext().getAttribute(DBC_ATTR_READ_PROJECT_FOR_RESOURCE) != null)) { 2250 dbc.getRequestContext().removeAttribute(DBC_ATTR_READ_PROJECT_FOR_RESOURCE); 2251 // TODO: this should get its own method in the interface 2252 return readProjectsForResource(dbc, ouFqn); 2253 } 2254 List<CmsProject> projects = new ArrayList<CmsProject>(); 2255 ResultSet res = null; 2256 PreparedStatement stmt = null; 2257 Connection conn = null; 2258 2259 try { 2260 // create the statement 2261 conn = m_sqlManager.getConnection(dbc); 2262 stmt = m_sqlManager.getPreparedStatement(conn, "C_PROJECTS_READ_BYOU_1"); 2263 2264 stmt.setString(1, CmsOrganizationalUnit.SEPARATOR + ouFqn + "%"); 2265 res = stmt.executeQuery(); 2266 2267 while (res.next()) { 2268 projects.add(internalCreateProject(res)); 2269 } 2270 } catch (SQLException e) { 2271 throw new CmsDbSqlException( 2272 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2273 e); 2274 } finally { 2275 m_sqlManager.closeAll(dbc, conn, stmt, res); 2276 } 2277 2278 return (projects); 2279 } 2280 2281 /** 2282 * @see org.opencms.db.I_CmsProjectDriver#readProjectsForGroup(org.opencms.db.CmsDbContext, org.opencms.file.CmsGroup) 2283 */ 2284 public List<CmsProject> readProjectsForGroup(CmsDbContext dbc, CmsGroup group) throws CmsDataAccessException { 2285 2286 List<CmsProject> projects = new ArrayList<CmsProject>(); 2287 ResultSet res = null; 2288 Connection conn = null; 2289 PreparedStatement stmt = null; 2290 2291 try { 2292 // create the statement 2293 conn = m_sqlManager.getConnection(dbc); 2294 stmt = m_sqlManager.getPreparedStatement(conn, "C_PROJECTS_READ_BYGROUP_2"); 2295 2296 stmt.setString(1, group.getId().toString()); 2297 stmt.setString(2, group.getId().toString()); 2298 res = stmt.executeQuery(); 2299 2300 while (res.next()) { 2301 projects.add(internalCreateProject(res)); 2302 } 2303 } catch (SQLException e) { 2304 throw new CmsDbSqlException( 2305 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2306 e); 2307 } finally { 2308 m_sqlManager.closeAll(dbc, conn, stmt, res); 2309 } 2310 return (projects); 2311 } 2312 2313 /** 2314 * @see org.opencms.db.I_CmsProjectDriver#readProjectsForManagerGroup(org.opencms.db.CmsDbContext, org.opencms.file.CmsGroup) 2315 */ 2316 public List<CmsProject> readProjectsForManagerGroup(CmsDbContext dbc, CmsGroup group) 2317 throws CmsDataAccessException { 2318 2319 List<CmsProject> projects = new ArrayList<CmsProject>(); 2320 ResultSet res = null; 2321 PreparedStatement stmt = null; 2322 Connection conn = null; 2323 2324 try { 2325 // create the statement 2326 conn = m_sqlManager.getConnection(dbc); 2327 stmt = m_sqlManager.getPreparedStatement(conn, "C_PROJECTS_READ_BYMANAGER_1"); 2328 2329 stmt.setString(1, group.getId().toString()); 2330 res = stmt.executeQuery(); 2331 2332 while (res.next()) { 2333 projects.add(internalCreateProject(res)); 2334 } 2335 } catch (SQLException e) { 2336 throw new CmsDbSqlException( 2337 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2338 e); 2339 } finally { 2340 m_sqlManager.closeAll(dbc, conn, stmt, res); 2341 } 2342 return (projects); 2343 } 2344 2345 /** 2346 * Returns the projects of a given resource.<p> 2347 * 2348 * @param dbc the database context 2349 * @param rootPath the resource root path 2350 * 2351 * @return the projects of the resource, as a list of projects 2352 * 2353 * @throws CmsDataAccessException if something goes wrong 2354 */ 2355 public List<CmsProject> readProjectsForResource(CmsDbContext dbc, String rootPath) throws CmsDataAccessException { 2356 2357 PreparedStatement stmt = null; 2358 List<CmsProject> projects = new ArrayList<CmsProject>(); 2359 ResultSet res = null; 2360 Connection conn = null; 2361 2362 try { 2363 conn = m_sqlManager.getConnection(dbc); 2364 stmt = m_sqlManager.getPreparedStatement(conn, "C_PROJECTS_READ_BYRESOURCE_1"); 2365 2366 stmt.setString(1, rootPath + "%"); 2367 res = stmt.executeQuery(); 2368 2369 if (res.next()) { 2370 projects.add(internalCreateProject(res)); 2371 while (res.next()) { 2372 // do nothing only move through all rows because of mssql odbc driver 2373 } 2374 } 2375 } catch (SQLException e) { 2376 throw new CmsDbSqlException( 2377 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2378 e); 2379 } finally { 2380 m_sqlManager.closeAll(dbc, conn, stmt, res); 2381 } 2382 2383 return projects; 2384 } 2385 2386 /** 2387 * @see org.opencms.db.I_CmsProjectDriver#readProjectsForUser(org.opencms.db.CmsDbContext, org.opencms.file.CmsUser) 2388 */ 2389 public List<CmsProject> readProjectsForUser(CmsDbContext dbc, CmsUser user) throws CmsDataAccessException { 2390 2391 List<CmsProject> projects = new ArrayList<CmsProject>(); 2392 ResultSet res = null; 2393 PreparedStatement stmt = null; 2394 Connection conn = null; 2395 2396 try { 2397 // create the statement 2398 conn = m_sqlManager.getConnection(dbc); 2399 stmt = m_sqlManager.getPreparedStatement(conn, "C_PROJECTS_READ_BYUSER_1"); 2400 2401 stmt.setString(1, user.getId().toString()); 2402 res = stmt.executeQuery(); 2403 2404 while (res.next()) { 2405 projects.add(internalCreateProject(res)); 2406 } 2407 } catch (SQLException e) { 2408 throw new CmsDbSqlException( 2409 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2410 e); 2411 } finally { 2412 m_sqlManager.closeAll(dbc, conn, stmt, res); 2413 } 2414 return (projects); 2415 } 2416 2417 /** 2418 * @see org.opencms.db.I_CmsProjectDriver#readPublishedResources(org.opencms.db.CmsDbContext, org.opencms.util.CmsUUID) 2419 */ 2420 public List<CmsPublishedResource> readPublishedResources(CmsDbContext dbc, CmsUUID publishHistoryId) 2421 throws CmsDataAccessException { 2422 2423 Connection conn = null; 2424 PreparedStatement stmt = null; 2425 ResultSet res = null; 2426 List<CmsPublishedResource> publishedResources = new ArrayList<CmsPublishedResource>(); 2427 2428 try { 2429 conn = m_sqlManager.getConnection(dbc); 2430 stmt = m_sqlManager.getPreparedStatement(conn, "C_SELECT_PUBLISHED_RESOURCES"); 2431 stmt.setString(1, publishHistoryId.toString()); 2432 res = stmt.executeQuery(); 2433 2434 while (res.next()) { 2435 CmsUUID structureId = new CmsUUID(res.getString("STRUCTURE_ID")); 2436 CmsUUID resourceId = new CmsUUID(res.getString("RESOURCE_ID")); 2437 String rootPath = res.getString("RESOURCE_PATH"); 2438 int resourceState = res.getInt("RESOURCE_STATE"); 2439 int resourceType = res.getInt("RESOURCE_TYPE"); 2440 int siblingCount = res.getInt("SIBLING_COUNT"); 2441 int publishTag = res.getInt("PUBLISH_TAG"); 2442 2443 // compose the resource state 2444 CmsResourceState state; 2445 if (resourceState == CmsPublishedResource.STATE_MOVED_SOURCE.getState()) { 2446 state = CmsPublishedResource.STATE_MOVED_SOURCE; 2447 } else if (resourceState == CmsPublishedResource.STATE_MOVED_DESTINATION.getState()) { 2448 state = CmsPublishedResource.STATE_MOVED_DESTINATION; 2449 } else { 2450 state = CmsResourceState.valueOf(resourceState); 2451 } 2452 2453 publishedResources.add( 2454 new CmsPublishedResource( 2455 structureId, 2456 resourceId, 2457 publishTag, 2458 rootPath, 2459 resourceType, 2460 structureId.isNullUUID() ? false : CmsFolder.isFolderType(resourceType), 2461 state, 2462 siblingCount)); 2463 } 2464 } catch (SQLException e) { 2465 throw new CmsDbSqlException( 2466 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2467 e); 2468 } finally { 2469 m_sqlManager.closeAll(dbc, conn, stmt, res); 2470 } 2471 2472 return publishedResources; 2473 } 2474 2475 /** 2476 * @see org.opencms.db.I_CmsProjectDriver#readPublishJob(org.opencms.db.CmsDbContext, org.opencms.util.CmsUUID) 2477 */ 2478 public CmsPublishJobInfoBean readPublishJob(CmsDbContext dbc, CmsUUID publishHistoryId) 2479 throws CmsDataAccessException { 2480 2481 Connection conn = null; 2482 PreparedStatement stmt = null; 2483 ResultSet res = null; 2484 2485 CmsPublishJobInfoBean result = null; 2486 try { 2487 conn = m_sqlManager.getConnection(dbc); 2488 stmt = m_sqlManager.getPreparedStatement(conn, "C_PUBLISHJOB_READ_JOB"); 2489 stmt.setString(1, publishHistoryId.toString()); 2490 res = stmt.executeQuery(); 2491 2492 if (res.next()) { 2493 result = createPublishJobInfoBean(res); 2494 while (res.next()) { 2495 // do nothing only move through all rows because of mssql odbc driver 2496 } 2497 } else { 2498 throw new CmsDbEntryNotFoundException( 2499 Messages.get().container(Messages.ERR_READ_PUBLISH_JOB_1, publishHistoryId.toString())); 2500 } 2501 } catch (SQLException e) { 2502 throw new CmsDbSqlException( 2503 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2504 e); 2505 } finally { 2506 m_sqlManager.closeAll(dbc, conn, stmt, res); 2507 } 2508 2509 return result; 2510 } 2511 2512 /** 2513 * @see org.opencms.db.I_CmsProjectDriver#readPublishJobs(org.opencms.db.CmsDbContext, long, long) 2514 */ 2515 public List<CmsPublishJobInfoBean> readPublishJobs(CmsDbContext dbc, long startTime, long endTime) 2516 throws CmsDataAccessException { 2517 2518 Connection conn = null; 2519 PreparedStatement stmt = null; 2520 ResultSet res = null; 2521 2522 List<CmsPublishJobInfoBean> result = null; 2523 try { 2524 conn = m_sqlManager.getConnection(dbc); 2525 stmt = m_sqlManager.getPreparedStatement(conn, "C_PUBLISHJOB_READ_JOBS_IN_TIMERANGE"); 2526 stmt.setLong(1, startTime); 2527 stmt.setLong(2, endTime); 2528 res = stmt.executeQuery(); 2529 2530 result = new ArrayList<CmsPublishJobInfoBean>(); 2531 while (res.next()) { 2532 result.add(createPublishJobInfoBean(res)); 2533 } 2534 } catch (SQLException e) { 2535 throw new CmsDbSqlException( 2536 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2537 e); 2538 } finally { 2539 m_sqlManager.closeAll(dbc, conn, stmt, res); 2540 } 2541 2542 return result; 2543 } 2544 2545 /** 2546 * @see org.opencms.db.I_CmsProjectDriver#readPublishList(org.opencms.db.CmsDbContext, org.opencms.util.CmsUUID) 2547 */ 2548 public CmsPublishList readPublishList(CmsDbContext dbc, CmsUUID publishHistoryId) throws CmsDataAccessException { 2549 2550 Connection conn = null; 2551 PreparedStatement stmt = null; 2552 ResultSet res = null; 2553 CmsPublishList publishList = null; 2554 2555 try { 2556 conn = m_sqlManager.getConnection(dbc); 2557 stmt = m_sqlManager.getPreparedStatement(conn, "C_PUBLISHJOB_READ_PUBLISHLIST"); 2558 stmt.setString(1, publishHistoryId.toString()); 2559 res = stmt.executeQuery(); 2560 2561 if (res.next()) { 2562 byte[] bytes = m_sqlManager.getBytes(res, "PUBLISH_LIST"); 2563 publishList = internalDeserializePublishList(bytes); 2564 while (res.next()) { 2565 // do nothing only move through all rows because of mssql odbc driver 2566 } 2567 } else { 2568 throw new CmsDataAccessException( 2569 Messages.get().container(Messages.ERR_READ_PUBLISH_JOB_1, publishHistoryId.toString())); 2570 } 2571 } catch (SQLException e) { 2572 throw new CmsDbSqlException( 2573 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2574 e); 2575 } catch (Exception e) { 2576 throw new CmsDataAccessException( 2577 Messages.get().container(Messages.ERR_PUBLISHLIST_DESERIALIZATION_FAILED_1, publishHistoryId), 2578 e); 2579 } finally { 2580 m_sqlManager.closeAll(dbc, conn, stmt, res); 2581 } 2582 2583 return publishList; 2584 } 2585 2586 /** 2587 * @see org.opencms.db.I_CmsProjectDriver#readPublishReportContents(org.opencms.db.CmsDbContext, org.opencms.util.CmsUUID) 2588 */ 2589 public byte[] readPublishReportContents(CmsDbContext dbc, CmsUUID publishHistoryId) throws CmsDataAccessException { 2590 2591 PreparedStatement stmt = null; 2592 ResultSet res = null; 2593 Connection conn = null; 2594 byte[] bytes = null; 2595 2596 try { 2597 conn = m_sqlManager.getConnection(dbc); 2598 2599 stmt = m_sqlManager.getPreparedStatement(conn, "C_PUBLISHJOB_READ_REPORT"); 2600 stmt.setString(1, publishHistoryId.toString()); 2601 res = stmt.executeQuery(); 2602 2603 if (res.next()) { 2604 // query to read Array of bytes for the given attribute 2605 bytes = m_sqlManager.getBytes(res, "PUBLISH_REPORT"); 2606 while (res.next()) { 2607 // do nothing only move through all rows because of mssql odbc driver 2608 } 2609 } else { 2610 throw new CmsDataAccessException( 2611 Messages.get().container(Messages.ERR_READ_PUBLISH_JOB_1, publishHistoryId.toString())); 2612 } 2613 } catch (SQLException e) { 2614 LOG.error(CmsDbSqlException.getErrorQuery(stmt), e); 2615 bytes = Messages.get().container( 2616 Messages.ERR_GENERIC_SQL_1, 2617 CmsDbSqlException.getErrorQuery(stmt)).key().getBytes(); 2618 } finally { 2619 m_sqlManager.closeAll(dbc, conn, stmt, res); 2620 } 2621 return bytes; 2622 } 2623 2624 /** 2625 * @see org.opencms.db.I_CmsProjectDriver#readStaticExportPublishedResourceParameters(org.opencms.db.CmsDbContext, java.lang.String) 2626 */ 2627 public String readStaticExportPublishedResourceParameters(CmsDbContext dbc, String rfsName) 2628 throws CmsDataAccessException { 2629 2630 String returnValue = null; 2631 Connection conn = null; 2632 PreparedStatement stmt = null; 2633 ResultSet res = null; 2634 2635 try { 2636 conn = m_sqlManager.getConnection(dbc); 2637 stmt = m_sqlManager.getPreparedStatement(conn, "C_STATICEXPORT_READ_PUBLISHED_LINK_PARAMETERS"); 2638 stmt.setString(1, rfsName); 2639 res = stmt.executeQuery(); 2640 // add all resourcenames to the list of return values 2641 if (res.next()) { 2642 returnValue = res.getString(1); 2643 while (res.next()) { 2644 // do nothing only move through all rows because of mssql odbc driver 2645 } 2646 } 2647 } catch (SQLException e) { 2648 throw new CmsDbSqlException( 2649 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2650 e); 2651 } finally { 2652 m_sqlManager.closeAll(dbc, conn, stmt, res); 2653 } 2654 2655 return returnValue; 2656 } 2657 2658 /** 2659 * @see org.opencms.db.I_CmsProjectDriver#readStaticExportResources(org.opencms.db.CmsDbContext, int, long) 2660 */ 2661 public List<String> readStaticExportResources(CmsDbContext dbc, int parameterResources, long timestamp) 2662 throws CmsDataAccessException { 2663 2664 Connection conn = null; 2665 PreparedStatement stmt = null; 2666 ResultSet res = null; 2667 List<String> returnValue = new ArrayList<String>(); 2668 2669 if (parameterResources == CmsStaticExportManager.EXPORT_LINK_WITHOUT_PARAMETER) { 2670 timestamp = 0; 2671 } 2672 try { 2673 conn = m_sqlManager.getConnection(dbc); 2674 stmt = m_sqlManager.getPreparedStatement(conn, "C_STATICEXPORT_READ_ALL_PUBLISHED_LINKS"); 2675 stmt.setInt(1, parameterResources); 2676 stmt.setLong(2, timestamp); 2677 res = stmt.executeQuery(); 2678 // add all resourcenames to the list of return values 2679 while (res.next()) { 2680 returnValue.add(res.getString(1)); 2681 } 2682 } catch (SQLException e) { 2683 throw new CmsDbSqlException( 2684 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2685 e); 2686 } finally { 2687 m_sqlManager.closeAll(dbc, conn, stmt, res); 2688 } 2689 2690 return returnValue; 2691 } 2692 2693 /** 2694 * @see org.opencms.db.I_CmsProjectDriver#setDriverManager(org.opencms.db.CmsDriverManager) 2695 */ 2696 public void setDriverManager(CmsDriverManager driverManager) { 2697 2698 m_driverManager = driverManager; 2699 } 2700 2701 /** 2702 * @see org.opencms.db.I_CmsProjectDriver#setSqlManager(org.opencms.db.CmsSqlManager) 2703 */ 2704 public void setSqlManager(org.opencms.db.CmsSqlManager manager) { 2705 2706 m_sqlManager = (CmsSqlManager)manager; 2707 } 2708 2709 /** 2710 * @see org.opencms.db.I_CmsProjectDriver#unmarkProjectResources(org.opencms.db.CmsDbContext, org.opencms.file.CmsProject) 2711 */ 2712 public void unmarkProjectResources(CmsDbContext dbc, CmsProject project) throws CmsDataAccessException { 2713 2714 // finally remove the project id form all resources 2715 2716 Connection conn = null; 2717 PreparedStatement stmt = null; 2718 try { 2719 conn = m_sqlManager.getConnection(dbc); 2720 stmt = m_sqlManager.getPreparedStatement(conn, "C_RESOURCES_UNMARK"); 2721 // create the statement 2722 stmt.setString(1, project.getUuid().toString()); 2723 stmt.executeUpdate(); 2724 } catch (SQLException e) { 2725 throw new CmsDbSqlException( 2726 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2727 e); 2728 } finally { 2729 m_sqlManager.closeAll(dbc, conn, stmt, null); 2730 } 2731 } 2732 2733 /** 2734 * @see org.opencms.db.I_CmsProjectDriver#writeLocks(org.opencms.db.CmsDbContext, java.util.List) 2735 */ 2736 public void writeLocks(CmsDbContext dbc, List<CmsLock> locks) throws CmsDataAccessException { 2737 2738 Connection conn = null; 2739 PreparedStatement stmt = null; 2740 try { 2741 conn = m_sqlManager.getConnection(dbc); 2742 stmt = m_sqlManager.getPreparedStatement(conn, "C_RESOURCE_LOCKS_DELETEALL"); 2743 int deleted = stmt.executeUpdate(); 2744 if (LOG.isDebugEnabled()) { 2745 LOG.debug(Messages.get().getBundle().key(Messages.LOG_DBG_CLEAR_LOCKS_1, Integer.valueOf(deleted))); 2746 } 2747 stmt = m_sqlManager.getPreparedStatement(conn, "C_RESOURCE_LOCK_WRITE"); 2748 if (LOG.isDebugEnabled()) { 2749 LOG.debug("SQL :" + m_sqlManager.readQuery("C_RESOURCE_LOCK_WRITE")); 2750 } 2751 Iterator<CmsLock> i = locks.iterator(); 2752 int count = 0; 2753 while (i.hasNext()) { 2754 CmsLock lock = i.next(); 2755 // only persist locks that should be written to the DB 2756 CmsLock sysLock = lock.getSystemLock(); 2757 if (sysLock.isPersistent()) { 2758 // persist system lock 2759 stmt.setString(1, sysLock.getResourceName()); 2760 stmt.setString(2, sysLock.getUserId().toString()); 2761 stmt.setString(3, sysLock.getProjectId().toString()); 2762 stmt.setInt(4, sysLock.getType().hashCode()); 2763 stmt.executeUpdate(); 2764 count++; 2765 } 2766 CmsLock editLock = lock.getEditionLock(); 2767 if (editLock.isPersistent()) { 2768 // persist edition lock 2769 stmt.setString(1, editLock.getResourceName()); 2770 stmt.setString(2, editLock.getUserId().toString()); 2771 stmt.setString(3, editLock.getProjectId().toString()); 2772 stmt.setInt(4, editLock.getType().hashCode()); 2773 stmt.executeUpdate(); 2774 count++; 2775 } 2776 } 2777 if (LOG.isDebugEnabled()) { 2778 LOG.debug(Messages.get().getBundle().key(Messages.LOG_DBG_WRITE_LOCKS_1, Integer.valueOf(count))); 2779 } 2780 } catch (SQLException e) { 2781 throw new CmsDbSqlException( 2782 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2783 e); 2784 } finally { 2785 m_sqlManager.closeAll(dbc, conn, stmt, null); 2786 } 2787 } 2788 2789 /** 2790 * @see org.opencms.db.I_CmsProjectDriver#writeProject(org.opencms.db.CmsDbContext, org.opencms.file.CmsProject) 2791 */ 2792 public void writeProject(CmsDbContext dbc, CmsProject project) throws CmsDataAccessException { 2793 2794 if (CmsStringUtil.isEmptyOrWhitespaceOnly(project.getDescription())) { 2795 project.setDescription(" "); 2796 } 2797 Connection conn = null; 2798 PreparedStatement stmt = null; 2799 2800 try { 2801 // get a JDBC connection from the OpenCms standard pools 2802 conn = m_sqlManager.getConnection(dbc); 2803 2804 stmt = m_sqlManager.getPreparedStatement(conn, "C_PROJECTS_WRITE_6"); 2805 stmt.setString(1, project.getDescription()); 2806 stmt.setString(2, project.getGroupId().toString()); 2807 stmt.setString(3, project.getManagerGroupId().toString()); 2808 stmt.setInt(4, project.getFlags()); 2809 stmt.setInt(5, project.getType().getMode()); 2810 stmt.setString(6, project.getUuid().toString()); 2811 stmt.executeUpdate(); 2812 } catch (SQLException e) { 2813 throw new CmsDbSqlException( 2814 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2815 e); 2816 } finally { 2817 m_sqlManager.closeAll(dbc, conn, stmt, null); 2818 } 2819 } 2820 2821 /** 2822 * @see org.opencms.db.I_CmsProjectDriver#writePublishHistory(org.opencms.db.CmsDbContext, org.opencms.util.CmsUUID, org.opencms.db.CmsPublishedResource) 2823 */ 2824 public void writePublishHistory(CmsDbContext dbc, CmsUUID publishId, CmsPublishedResource resource) 2825 throws CmsDataAccessException { 2826 2827 Connection conn = null; 2828 PreparedStatement stmt = null; 2829 2830 try { 2831 conn = m_sqlManager.getConnection(dbc); 2832 stmt = m_sqlManager.getPreparedStatement(conn, "C_RESOURCES_WRITE_PUBLISH_HISTORY"); 2833 stmt.setInt(1, resource.getPublishTag()); 2834 stmt.setString(2, resource.getStructureId().toString()); 2835 stmt.setString(3, resource.getResourceId().toString()); 2836 stmt.setString(4, resource.getRootPath()); 2837 stmt.setInt(5, resource.getMovedState().getState()); 2838 stmt.setInt(6, resource.getType()); 2839 stmt.setString(7, publishId.toString()); 2840 stmt.setInt(8, resource.getSiblingCount()); 2841 stmt.executeUpdate(); 2842 } catch (SQLException e) { 2843 throw new CmsDbSqlException( 2844 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2845 e); 2846 } finally { 2847 m_sqlManager.closeAll(dbc, conn, stmt, null); 2848 } 2849 } 2850 2851 /** 2852 * @see org.opencms.db.I_CmsProjectDriver#writePublishJob(org.opencms.db.CmsDbContext, org.opencms.publish.CmsPublishJobInfoBean) 2853 */ 2854 public void writePublishJob(CmsDbContext dbc, CmsPublishJobInfoBean publishJob) throws CmsDataAccessException { 2855 2856 Connection conn = null; 2857 PreparedStatement stmt = null; 2858 2859 try { 2860 conn = m_sqlManager.getConnection(dbc); 2861 stmt = m_sqlManager.getPreparedStatement(conn, "C_PUBLISHJOB_WRITE"); 2862 stmt.setString(1, publishJob.getProjectId().toString()); 2863 stmt.setString(2, publishJob.getProjectName()); 2864 stmt.setString(3, publishJob.getUserId().toString()); 2865 stmt.setString(4, publishJob.getLocale().toString()); 2866 stmt.setInt(5, publishJob.getFlags()); 2867 stmt.setInt(6, publishJob.getSize()); 2868 stmt.setLong(7, publishJob.getEnqueueTime()); 2869 stmt.setLong(8, publishJob.getStartTime()); 2870 stmt.setLong(9, publishJob.getFinishTime()); 2871 stmt.setString(10, publishJob.getPublishHistoryId().toString()); 2872 stmt.executeUpdate(); 2873 } catch (SQLException e) { 2874 throw new CmsDbSqlException( 2875 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2876 e); 2877 } finally { 2878 m_sqlManager.closeAll(dbc, conn, stmt, null); 2879 } 2880 } 2881 2882 /** 2883 * @see org.opencms.db.I_CmsProjectDriver#writePublishReport(org.opencms.db.CmsDbContext, org.opencms.util.CmsUUID, byte[]) 2884 */ 2885 public void writePublishReport(CmsDbContext dbc, CmsUUID publishId, byte[] content) throws CmsDataAccessException { 2886 2887 Connection conn = null; 2888 PreparedStatement stmt = null; 2889 2890 try { 2891 conn = m_sqlManager.getConnection(dbc); 2892 stmt = m_sqlManager.getPreparedStatement(conn, "C_PUBLISHJOB_WRITE_REPORT"); 2893 2894 if (content.length < 2000) { 2895 stmt.setBytes(1, content); 2896 } else { 2897 stmt.setBinaryStream(1, new ByteArrayInputStream(content), content.length); 2898 } 2899 2900 stmt.setString(2, publishId.toString()); 2901 stmt.executeUpdate(); 2902 } catch (SQLException e) { 2903 throw new CmsDbSqlException( 2904 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2905 e); 2906 } finally { 2907 m_sqlManager.closeAll(dbc, conn, stmt, null); 2908 } 2909 } 2910 2911 /** 2912 * @see org.opencms.db.I_CmsProjectDriver#writeStaticExportPublishedResource(org.opencms.db.CmsDbContext, java.lang.String, int, java.lang.String, long) 2913 */ 2914 public void writeStaticExportPublishedResource( 2915 CmsDbContext dbc, 2916 String resourceName, 2917 int linkType, 2918 String linkParameter, 2919 long timestamp) 2920 throws CmsDataAccessException { 2921 2922 Connection conn = null; 2923 PreparedStatement stmt = null; 2924 ResultSet res = null; 2925 int returnValue = 0; 2926 // first check if a record with this resource name does already exist 2927 try { 2928 conn = m_sqlManager.getConnection(dbc); 2929 stmt = m_sqlManager.getPreparedStatement(conn, "C_STATICEXPORT_READ_PUBLISHED_RESOURCES"); 2930 stmt.setString(1, resourceName); 2931 res = stmt.executeQuery(); 2932 if (res.next()) { 2933 returnValue = res.getInt(1); 2934 while (res.next()) { 2935 // do nothing only move through all rows because of mssql odbc driver 2936 } 2937 } 2938 } catch (SQLException e) { 2939 throw new CmsDbSqlException( 2940 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2941 e); 2942 } finally { 2943 m_sqlManager.closeAll(dbc, conn, stmt, res); 2944 } 2945 2946 // there was no entry found, so add it to the database 2947 if (returnValue == 0) { 2948 try { 2949 conn = m_sqlManager.getConnection(dbc); 2950 stmt = m_sqlManager.getPreparedStatement(conn, "C_STATICEXPORT_WRITE_PUBLISHED_LINKS"); 2951 stmt.setString(1, new CmsUUID().toString()); 2952 stmt.setString(2, resourceName); 2953 stmt.setInt(3, linkType); 2954 stmt.setString(4, linkParameter); 2955 stmt.setLong(5, timestamp); 2956 stmt.executeUpdate(); 2957 } catch (SQLException e) { 2958 throw new CmsDbSqlException(Messages.get().container(Messages.ERR_GENERIC_SQL_1, stmt), e); 2959 } finally { 2960 m_sqlManager.closeAll(dbc, conn, stmt, null); 2961 } 2962 } 2963 } 2964 2965 /** 2966 * @see org.opencms.db.I_CmsProjectDriver#writeUserPublishListEntries(org.opencms.db.CmsDbContext, java.util.List) 2967 */ 2968 public void writeUserPublishListEntries(CmsDbContext dbc, List<CmsUserPublishListEntry> publishListAdditions) 2969 throws CmsDbSqlException { 2970 2971 if (publishListAdditions.isEmpty()) { 2972 return; 2973 } 2974 2975 // first remove all entries with the same keys 2976 deleteUserPublishListEntries(dbc, publishListAdditions); 2977 2978 Connection conn = null; 2979 PreparedStatement stmt = null; 2980 try { 2981 conn = m_sqlManager.getConnection(dbc); 2982 String sql = m_sqlManager.readQuery("C_USER_PUBLISH_LIST_INSERT_3"); 2983 stmt = m_sqlManager.getPreparedStatementForSql(conn, sql); 2984 for (CmsUserPublishListEntry entry : publishListAdditions) { 2985 stmt.setString(1, entry.getUserId().toString()); 2986 stmt.setString(2, entry.getStructureId().toString()); 2987 stmt.setLong(3, entry.getDateChanged()); 2988 stmt.addBatch(); 2989 } 2990 stmt.executeBatch(); 2991 } catch (SQLException e) { 2992 throw new CmsDbSqlException( 2993 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 2994 e); 2995 } finally { 2996 m_sqlManager.closeAll(dbc, conn, stmt, null); 2997 } 2998 2999 } 3000 3001 /** 3002 * Creates a <code>CmsPublishJobInfoBean</code> from a result set.<p> 3003 * 3004 * @param res the result set 3005 * @return an initialized <code>CmsPublishJobInfoBean</code> 3006 * @throws SQLException if something goes wrong 3007 */ 3008 protected CmsPublishJobInfoBean createPublishJobInfoBean(ResultSet res) throws SQLException { 3009 3010 return new CmsPublishJobInfoBean( 3011 new CmsUUID(res.getString("HISTORY_ID")), 3012 new CmsUUID(res.getString("PROJECT_ID")), 3013 res.getString("PROJECT_NAME"), 3014 new CmsUUID(res.getString("USER_ID")), 3015 res.getString("PUBLISH_LOCALE"), 3016 res.getInt("PUBLISH_FLAGS"), 3017 res.getInt("RESOURCE_COUNT"), 3018 res.getLong("ENQUEUE_TIME"), 3019 res.getLong("START_TIME"), 3020 res.getLong("FINISH_TIME")); 3021 } 3022 3023 /** 3024 * Checks if the given resource (by id) is available in the online project, 3025 * if there exists a resource with a different path (a moved file), then the 3026 * online entry is moved to the right (new) location before publishing.<p> 3027 * 3028 * @param dbc the db context 3029 * @param onlineProject the online project 3030 * @param offlineResource the offline resource to check 3031 * @param publishHistoryId the publish history id 3032 * @param publishTag the publish tag 3033 * 3034 * @return <code>true</code> if the resource has actually been moved 3035 * 3036 * @throws CmsDataAccessException if something goes wrong 3037 */ 3038 protected CmsResourceState fixMovedResource( 3039 CmsDbContext dbc, 3040 CmsProject onlineProject, 3041 CmsResource offlineResource, 3042 CmsUUID publishHistoryId, 3043 int publishTag) 3044 throws CmsDataAccessException { 3045 3046 CmsResource onlineResource; 3047 // check if the resource has been moved since last publishing 3048 try { 3049 onlineResource = m_driverManager.getVfsDriver( 3050 dbc).readResource(dbc, onlineProject.getUuid(), offlineResource.getStructureId(), true); 3051 if (onlineResource.getRootPath().equals(offlineResource.getRootPath())) { 3052 // resource changed, not moved 3053 return offlineResource.getState(); 3054 } 3055 } catch (CmsVfsResourceNotFoundException e) { 3056 // ok, resource new, not moved 3057 return offlineResource.getState(); 3058 } 3059 3060 // move the online resource to the new position 3061 m_driverManager.getVfsDriver( 3062 dbc).moveResource(dbc, onlineProject.getUuid(), onlineResource, offlineResource.getRootPath()); 3063 3064 try { 3065 // write the resource to the publish history 3066 m_driverManager.getProjectDriver(dbc).writePublishHistory( 3067 dbc, 3068 publishHistoryId, 3069 new CmsPublishedResource(onlineResource, publishTag, CmsPublishedResource.STATE_MOVED_SOURCE)); 3070 } catch (CmsDataAccessException e) { 3071 if (LOG.isErrorEnabled()) { 3072 LOG.error( 3073 Messages.get().getBundle().key( 3074 Messages.LOG_WRITING_PUBLISHING_HISTORY_1, 3075 onlineResource.getRootPath()), 3076 e); 3077 } 3078 throw e; 3079 } 3080 return offlineResource.getState().isDeleted() 3081 ? CmsResource.STATE_DELETED 3082 : CmsPublishedResource.STATE_MOVED_DESTINATION; 3083 } 3084 3085 /** 3086 * Returns a SQL parameter string for the given data.<p> 3087 * 3088 * @param data the data 3089 * 3090 * @return the SQL parameter 3091 */ 3092 protected String getParameterString(Collection<?> data) { 3093 3094 StringBuffer conditions = new StringBuffer(); 3095 conditions.append(BEGIN_CONDITION); 3096 Iterator<?> it = data.iterator(); 3097 while (it.hasNext()) { 3098 it.next(); 3099 conditions.append("?"); 3100 if (it.hasNext()) { 3101 conditions.append(", "); 3102 } 3103 } 3104 conditions.append(END_CONDITION); 3105 return conditions.toString(); 3106 } 3107 3108 /** 3109 * Implementation of reading the user publish list which uses the log table.<p> 3110 * 3111 * This is the old implementation of the user publish list and can get pretty slow.<p> 3112 * 3113 * @param dbc the current database context 3114 * @param userId the id of the user for which we want the user publish list 3115 * 3116 * @return the publish list for the given user 3117 * 3118 * @throws CmsDataAccessException if something goes wrong 3119 */ 3120 protected List<CmsResource> getUsersPubListFromLog(CmsDbContext dbc, CmsUUID userId) throws CmsDataAccessException { 3121 3122 Connection conn = null; 3123 PreparedStatement stmt = null; 3124 ResultSet res = null; 3125 3126 List<CmsResource> result = null; 3127 try { 3128 conn = m_sqlManager.getConnection(dbc); 3129 stmt = m_sqlManager.getPreparedStatement(conn, dbc.currentProject().getUuid(), "C_LOG_READ_PUBLISH_LIST_2"); 3130 stmt.setString(1, userId.toString()); 3131 stmt.setString(2, userId.toString()); 3132 res = stmt.executeQuery(); 3133 3134 result = new ArrayList<CmsResource>(); 3135 while (res.next()) { 3136 CmsResource resource = m_driverManager.getVfsDriver(dbc).createResource( 3137 res, 3138 dbc.currentProject().getUuid()); 3139 long date = res.getLong(m_sqlManager.readQuery("C_LOG_DATE")); 3140 resource.setDateLastModified(date); 3141 result.add(resource); 3142 } 3143 } catch (SQLException e) { 3144 throw new CmsDbSqlException( 3145 Messages.get().container(Messages.ERR_GENERIC_SQL_1, CmsDbSqlException.getErrorQuery(stmt)), 3146 e); 3147 } finally { 3148 m_sqlManager.closeAll(dbc, conn, stmt, res); 3149 } 3150 return result; 3151 } 3152 3153 /** 3154 * Creates a new project from the current row of the given result set.<p> 3155 * 3156 * @param res the result set 3157 * 3158 * @return the new project 3159 * 3160 * @throws SQLException is something goes wrong 3161 */ 3162 protected CmsProject internalCreateProject(ResultSet res) throws SQLException { 3163 3164 String ou = CmsOrganizationalUnit.removeLeadingSeparator( 3165 res.getString(m_sqlManager.readQuery("C_PROJECTS_PROJECT_OU_0"))); 3166 return new CmsProject( 3167 new CmsUUID(res.getString(m_sqlManager.readQuery("C_PROJECTS_PROJECT_ID_0"))), 3168 ou + res.getString(m_sqlManager.readQuery("C_PROJECTS_PROJECT_NAME_0")), 3169 res.getString(m_sqlManager.readQuery("C_PROJECTS_PROJECT_DESCRIPTION_0")), 3170 new CmsUUID(res.getString(m_sqlManager.readQuery("C_PROJECTS_USER_ID_0"))), 3171 new CmsUUID(res.getString(m_sqlManager.readQuery("C_PROJECTS_GROUP_ID_0"))), 3172 new CmsUUID(res.getString(m_sqlManager.readQuery("C_PROJECTS_MANAGERGROUP_ID_0"))), 3173 res.getInt(m_sqlManager.readQuery("C_PROJECTS_PROJECT_FLAGS_0")), 3174 res.getLong(m_sqlManager.readQuery("C_PROJECTS_DATE_CREATED_0")), 3175 CmsProject.CmsProjectType.valueOf(res.getInt(m_sqlManager.readQuery("C_PROJECTS_PROJECT_TYPE_0")))); 3176 } 3177 3178 /** 3179 * Builds a publish list from serialized data.<p> 3180 * 3181 * @param bytes the byte array containing the serailized data for the publish list 3182 * @return the initialized publish list 3183 * 3184 * @throws IOException if deserialization fails 3185 * @throws ClassNotFoundException if deserialization fails 3186 */ 3187 protected CmsPublishList internalDeserializePublishList(byte[] bytes) throws IOException, ClassNotFoundException { 3188 3189 ByteArrayInputStream bin = new ByteArrayInputStream(bytes); 3190 ObjectInputStream oin = new ObjectInputStream(bin); 3191 return (CmsPublishList)oin.readObject(); 3192 } 3193 3194 /** 3195 * Creates a new {@link CmsLogEntry} object from the given result set entry.<p> 3196 * 3197 * @param res the result set 3198 * 3199 * @return the new {@link CmsLogEntry} object 3200 * 3201 * @throws SQLException if something goes wrong 3202 */ 3203 protected CmsLogEntry internalReadLogEntry(ResultSet res) throws SQLException { 3204 3205 CmsUUID userId = new CmsUUID(res.getString(m_sqlManager.readQuery("C_LOG_USER_ID"))); 3206 long date = res.getLong(m_sqlManager.readQuery("C_LOG_DATE")); 3207 CmsUUID structureId = new CmsUUID(res.getString(m_sqlManager.readQuery("C_LOG_STRUCTURE_ID"))); 3208 CmsLogEntryType type = CmsLogEntryType.valueOf(res.getInt(m_sqlManager.readQuery("C_LOG_TYPE"))); 3209 String[] data = CmsStringUtil.splitAsArray(res.getString(m_sqlManager.readQuery("C_LOG_DATA")), '|'); 3210 return new CmsLogEntry(userId, date, structureId, type, data); 3211 } 3212 3213 /** 3214 * Resets the state to UNCHANGED for a specified resource.<p> 3215 * 3216 * @param dbc the current database context 3217 * @param resource the Cms resource 3218 * 3219 * @throws CmsDataAccessException if something goes wrong 3220 */ 3221 protected void internalResetResourceState(CmsDbContext dbc, CmsResource resource) throws CmsDataAccessException { 3222 3223 try { 3224 // reset the resource state 3225 resource.setState(CmsResource.STATE_UNCHANGED); 3226 m_driverManager.getVfsDriver( 3227 dbc).writeResourceState(dbc, dbc.currentProject(), resource, CmsDriverManager.UPDATE_ALL, true); 3228 } catch (CmsDataAccessException e) { 3229 if (LOG.isErrorEnabled()) { 3230 LOG.error( 3231 Messages.get().getBundle().key( 3232 Messages.LOG_ERROR_RESETTING_RESOURCE_STATE_1, 3233 resource.getRootPath()), 3234 e); 3235 } 3236 throw e; 3237 } 3238 } 3239 3240 /** 3241 * Serialize publish list to write it as byte array to the database.<p> 3242 * 3243 * @param publishList the publish list 3244 * @return byte array containing the publish list data 3245 * @throws IOException if something goes wrong 3246 */ 3247 protected byte[] internalSerializePublishList(CmsPublishList publishList) throws IOException { 3248 3249 // serialize the publish list 3250 ByteArrayOutputStream bout = new ByteArrayOutputStream(); 3251 ObjectOutputStream oout = new ObjectOutputStream(bout); 3252 oout.writeObject(publishList); 3253 oout.close(); 3254 return bout.toByteArray(); 3255 } 3256 3257 /** 3258 * Writes the needed history entries.<p> 3259 * 3260 * @param dbc the current database context 3261 * @param resource the offline resource 3262 * @param state the state to store in the publish history entry 3263 * @param properties the offline properties 3264 * @param publishHistoryId the current publish process id 3265 * @param publishTag the current publish process tag 3266 * 3267 * @throws CmsDataAccessException if something goes wrong 3268 */ 3269 protected void internalWriteHistory( 3270 CmsDbContext dbc, 3271 CmsResource resource, 3272 CmsResourceState state, 3273 List<CmsProperty> properties, 3274 CmsUUID publishHistoryId, 3275 int publishTag) 3276 throws CmsDataAccessException { 3277 3278 try { 3279 if (OpenCms.getSystemInfo().isHistoryEnabled()) { 3280 // write the resource to the historical archive 3281 if (properties == null) { 3282 properties = m_driverManager.getVfsDriver(dbc).readPropertyObjects( 3283 dbc, 3284 dbc.currentProject(), 3285 resource); 3286 } 3287 m_driverManager.getHistoryDriver(dbc).writeResource(dbc, resource, properties, publishTag); 3288 } 3289 // write the resource to the publish history 3290 m_driverManager.getProjectDriver(dbc).writePublishHistory( 3291 dbc, 3292 publishHistoryId, 3293 new CmsPublishedResource(resource, publishTag, state)); 3294 } catch (CmsDataAccessException e) { 3295 if (LOG.isErrorEnabled()) { 3296 LOG.error( 3297 Messages.get().getBundle().key(Messages.LOG_WRITING_PUBLISHING_HISTORY_1, resource.getRootPath()), 3298 e); 3299 } 3300 throw e; 3301 } 3302 } 3303 3304 /** 3305 * Build the whole WHERE SQL statement part for the given log entry filter.<p> 3306 * 3307 * @param filter the filter 3308 * 3309 * @return a pair containing both the SQL and the parameters for it 3310 */ 3311 protected CmsPair<String, List<I_CmsPreparedStatementParameter>> prepareLogConditions(CmsLogFilter filter) { 3312 3313 List<I_CmsPreparedStatementParameter> params = new ArrayList<I_CmsPreparedStatementParameter>(); 3314 StringBuffer conditions = new StringBuffer(); 3315 3316 // user id filter 3317 if (filter.getUserId() != null) { 3318 if (conditions.length() == 0) { 3319 conditions.append(BEGIN_CONDITION); 3320 } else { 3321 conditions.append(BEGIN_INCLUDE_CONDITION); 3322 } 3323 conditions.append(m_sqlManager.readQuery("C_LOG_FILTER_USER_ID")); 3324 params.add(new CmsPreparedStatementStringParameter(filter.getUserId().toString())); 3325 conditions.append(END_CONDITION); 3326 } 3327 3328 // resource id filter 3329 if (filter.getStructureId() != null) { 3330 if (conditions.length() == 0) { 3331 conditions.append(BEGIN_CONDITION); 3332 } else { 3333 conditions.append(BEGIN_INCLUDE_CONDITION); 3334 } 3335 conditions.append(m_sqlManager.readQuery("C_LOG_FILTER_RESOURCE_ID")); 3336 params.add(new CmsPreparedStatementStringParameter(filter.getStructureId().toString())); 3337 conditions.append(END_CONDITION); 3338 } 3339 3340 // date from filter 3341 if (filter.getDateFrom() != CmsResource.DATE_RELEASED_DEFAULT) { 3342 if (conditions.length() == 0) { 3343 conditions.append(BEGIN_CONDITION); 3344 } else { 3345 conditions.append(BEGIN_INCLUDE_CONDITION); 3346 } 3347 conditions.append(m_sqlManager.readQuery("C_LOG_FILTER_DATE_FROM")); 3348 params.add(new CmsPreparedStatementLongParameter(filter.getDateFrom())); 3349 conditions.append(END_CONDITION); 3350 } 3351 3352 // date to filter 3353 if (filter.getDateTo() != CmsResource.DATE_RELEASED_DEFAULT) { 3354 if (conditions.length() == 0) { 3355 conditions.append(BEGIN_CONDITION); 3356 } else { 3357 conditions.append(BEGIN_INCLUDE_CONDITION); 3358 } 3359 conditions.append(m_sqlManager.readQuery("C_LOG_FILTER_DATE_TO")); 3360 params.add(new CmsPreparedStatementLongParameter(filter.getDateTo())); 3361 conditions.append(END_CONDITION); 3362 } 3363 3364 // include type filter 3365 Set<CmsLogEntryType> includeTypes = filter.getIncludeTypes(); 3366 if (!includeTypes.isEmpty()) { 3367 if (conditions.length() == 0) { 3368 conditions.append(BEGIN_CONDITION); 3369 } else { 3370 conditions.append(BEGIN_INCLUDE_CONDITION); 3371 } 3372 conditions.append(m_sqlManager.readQuery("C_LOG_FILTER_INCLUDE_TYPE")); 3373 conditions.append(BEGIN_CONDITION); 3374 Iterator<CmsLogEntryType> it = includeTypes.iterator(); 3375 while (it.hasNext()) { 3376 CmsLogEntryType type = it.next(); 3377 conditions.append("?"); 3378 params.add(new CmsPreparedStatementIntParameter(type.getId())); 3379 if (it.hasNext()) { 3380 conditions.append(", "); 3381 } 3382 } 3383 conditions.append(END_CONDITION); 3384 conditions.append(END_CONDITION); 3385 } 3386 3387 // exclude type filter 3388 Set<CmsLogEntryType> excludeTypes = filter.getExcludeTypes(); 3389 if (!excludeTypes.isEmpty()) { 3390 if (conditions.length() == 0) { 3391 conditions.append(BEGIN_CONDITION); 3392 } else { 3393 conditions.append(BEGIN_INCLUDE_CONDITION); 3394 } 3395 conditions.append(m_sqlManager.readQuery("C_LOG_FILTER_EXCLUDE_TYPE")); 3396 conditions.append(BEGIN_CONDITION); 3397 Iterator<CmsLogEntryType> it = excludeTypes.iterator(); 3398 while (it.hasNext()) { 3399 CmsLogEntryType type = it.next(); 3400 conditions.append("?"); 3401 params.add(new CmsPreparedStatementIntParameter(type.getId())); 3402 if (it.hasNext()) { 3403 conditions.append(", "); 3404 } 3405 } 3406 conditions.append(END_CONDITION); 3407 conditions.append(END_CONDITION); 3408 } 3409 return CmsPair.create(conditions.toString(), params); 3410 } 3411 3412 /** 3413 * Publishes a changed file.<p> 3414 * 3415 * @param dbc the current database context 3416 * @param onlineProject the online project 3417 * @param offlineResource the resource to publish 3418 * @param publishedResourceIds contains the UUIDs of already published content records 3419 * @param publishHistoryId the publish history id 3420 * @param publishTag the publish tag 3421 * 3422 * @throws CmsDataAccessException is something goes wrong 3423 */ 3424 protected void publishChangedFile( 3425 CmsDbContext dbc, 3426 CmsProject onlineProject, 3427 CmsResource offlineResource, 3428 Set<CmsUUID> publishedResourceIds, 3429 CmsUUID publishHistoryId, 3430 int publishTag) 3431 throws CmsDataAccessException { 3432 3433 CmsResource onlineResource = null; 3434 boolean needToUpdateContent = true; 3435 boolean existsOnline = m_driverManager.getVfsDriver(dbc).validateStructureIdExists( 3436 dbc, 3437 CmsProject.ONLINE_PROJECT_ID, 3438 offlineResource.getStructureId()); 3439 CmsResourceState resourceState = existsOnline 3440 ? fixMovedResource(dbc, onlineProject, offlineResource, publishHistoryId, publishTag) 3441 : offlineResource.getState(); 3442 try { 3443 // reset the labeled link flag before writing the online file 3444 int flags = offlineResource.getFlags(); 3445 flags &= ~CmsResource.FLAG_LABELED; 3446 offlineResource.setFlags(flags); 3447 3448 if (existsOnline) { 3449 // read the file header online 3450 onlineResource = m_driverManager.getVfsDriver( 3451 dbc).readResource(dbc, onlineProject.getUuid(), offlineResource.getStructureId(), false); 3452 needToUpdateContent = (onlineResource.getDateContent() < offlineResource.getDateContent()); 3453 // delete the properties online 3454 m_driverManager.getVfsDriver(dbc).deletePropertyObjects( 3455 dbc, 3456 onlineProject.getUuid(), 3457 onlineResource, 3458 CmsProperty.DELETE_OPTION_DELETE_STRUCTURE_AND_RESOURCE_VALUES); 3459 3460 // if the offline file has a resource ID different from the online file 3461 // (probably because a deleted file was replaced by a new file with the 3462 // same name), the properties mapped to the "old" resource ID have to be 3463 // deleted also offline. if this is the case, the online and offline structure 3464 // ID's do match, but the resource ID's are different. structure IDs are reused 3465 // to prevent orphan structure records in the online project. 3466 3467 // Addendum (2023): It shouldn't be possible for resources to be in this state anymore, 3468 // since creating new resources over deleted ones isn't really possible anymore, 3469 // but apparently it can still happen, though I can't reproduce it. 3470 if (!onlineResource.getResourceId().equals(offlineResource.getResourceId())) { 3471 List<CmsProperty> offlineProperties = m_driverManager.getVfsDriver(dbc).readPropertyObjects( 3472 dbc, 3473 dbc.currentProject(), 3474 onlineResource); 3475 if (offlineProperties.size() > 0) { 3476 List<CmsProperty> newProperties = new ArrayList<>(); 3477 for (int i = 0; i < offlineProperties.size(); i++) { 3478 CmsProperty oldProperty = offlineProperties.get(i); 3479 // property may be frozen (non-modifiable), so create a new one 3480 CmsProperty newProperty = new CmsProperty( 3481 oldProperty.getName(), 3482 null, 3483 CmsProperty.DELETE_VALUE); 3484 newProperties.add(newProperty); 3485 } 3486 m_driverManager.getVfsDriver( 3487 dbc).writePropertyObjects(dbc, dbc.currentProject(), onlineResource, newProperties); 3488 } 3489 } 3490 } 3491 } catch (CmsDataAccessException e) { 3492 if (LOG.isErrorEnabled()) { 3493 LOG.error( 3494 Messages.get().getBundle().key(Messages.LOG_DELETING_PROPERTIES_1, offlineResource.toString()), 3495 e); 3496 } 3497 throw e; 3498 } 3499 3500 CmsFile newFile; 3501 try { 3502 // publish the file content 3503 newFile = m_driverManager.getProjectDriver(dbc).publishFileContent( 3504 dbc, 3505 dbc.currentProject(), 3506 onlineProject, 3507 offlineResource, 3508 publishedResourceIds, 3509 needToUpdateContent, 3510 publishTag); 3511 3512 } catch (CmsDataAccessException e) { 3513 if (LOG.isErrorEnabled()) { 3514 LOG.error( 3515 Messages.get().getBundle().key(Messages.LOG_PUBLISHING_RESOURCE_1, offlineResource.getRootPath()), 3516 e); 3517 } 3518 throw e; 3519 } 3520 3521 List<CmsProperty> offlineProperties; 3522 try { 3523 // write the properties online 3524 offlineProperties = m_driverManager.getVfsDriver(dbc).readPropertyObjects( 3525 dbc, 3526 dbc.currentProject(), 3527 offlineResource); 3528 CmsProperty.setAutoCreatePropertyDefinitions(offlineProperties, true); 3529 m_driverManager.getVfsDriver(dbc).writePropertyObjects(dbc, onlineProject, newFile, offlineProperties); 3530 } catch (CmsDataAccessException e) { 3531 if (LOG.isErrorEnabled()) { 3532 LOG.error( 3533 Messages.get().getBundle().key(Messages.LOG_PUBLISHING_PROPERTIES_1, newFile.getRootPath()), 3534 e); 3535 } 3536 throw e; 3537 } 3538 3539 try { 3540 // write the ACL online 3541 m_driverManager.getUserDriver(dbc).publishAccessControlEntries( 3542 dbc, 3543 dbc.currentProject(), 3544 onlineProject, 3545 newFile.getResourceId(), 3546 offlineResource.getResourceId()); 3547 } catch (CmsDataAccessException e) { 3548 if (LOG.isErrorEnabled()) { 3549 LOG.error(Messages.get().getBundle().key(Messages.LOG_PUBLISHING_ACL_1, newFile.getRootPath()), e); 3550 } 3551 throw e; 3552 } 3553 3554 CmsFile offlineFile = new CmsFile(offlineResource); 3555 offlineFile.setContents(newFile.getContents()); 3556 internalWriteHistory(dbc, offlineFile, resourceState, offlineProperties, publishHistoryId, publishTag); 3557 3558 m_driverManager.getVfsDriver(dbc).updateRelations(dbc, onlineProject, offlineResource); 3559 } 3560 3561 /** 3562 * Publishes a deleted file.<p> 3563 * 3564 * @param dbc the current database context 3565 * @param onlineProject the online project 3566 * @param offlineResource the resource to publish 3567 * @param publishHistoryId the publish history id 3568 * @param publishTag the publish tag 3569 * 3570 * @throws CmsDataAccessException is something goes wrong 3571 */ 3572 protected void publishDeletedFile( 3573 CmsDbContext dbc, 3574 CmsProject onlineProject, 3575 CmsResource offlineResource, 3576 CmsUUID publishHistoryId, 3577 int publishTag) 3578 throws CmsDataAccessException { 3579 3580 CmsResourceState resourceState = fixMovedResource( 3581 dbc, 3582 onlineProject, 3583 offlineResource, 3584 publishHistoryId, 3585 publishTag); 3586 3587 boolean existsOnline = m_driverManager.getVfsDriver(dbc).validateStructureIdExists( 3588 dbc, 3589 CmsProject.ONLINE_PROJECT_ID, 3590 offlineResource.getStructureId()); 3591 CmsResource onlineResource = null; 3592 if (existsOnline) { 3593 try { 3594 // read the file header online 3595 onlineResource = m_driverManager.getVfsDriver( 3596 dbc).readResource(dbc, onlineProject.getUuid(), offlineResource.getStructureId(), true); 3597 } catch (CmsDataAccessException e) { 3598 if (LOG.isErrorEnabled()) { 3599 LOG.error( 3600 Messages.get().getBundle().key(Messages.LOG_READING_RESOURCE_1, offlineResource.getRootPath()), 3601 e); 3602 } 3603 throw e; 3604 } 3605 } 3606 if (offlineResource.isLabeled() && !m_driverManager.labelResource(dbc, offlineResource, null, 2)) { 3607 // update the resource flags to "unlabeled" of the siblings of the offline resource 3608 int flags = offlineResource.getFlags(); 3609 flags &= ~CmsResource.FLAG_LABELED; 3610 offlineResource.setFlags(flags); 3611 } 3612 3613 // write history before deleting 3614 CmsFile offlineFile = new CmsFile(offlineResource); 3615 offlineFile.setContents( 3616 m_driverManager.getVfsDriver(dbc).readContent( 3617 dbc, 3618 dbc.currentProject().getUuid(), 3619 offlineFile.getResourceId())); 3620 internalWriteHistory(dbc, offlineFile, resourceState, null, publishHistoryId, publishTag); 3621 3622 int propertyDeleteOption = -1; 3623 try { 3624 // delete the properties online and offline 3625 if (offlineResource.getSiblingCount() > 1) { 3626 // there are other siblings- delete only structure property values and keep the resource property values 3627 propertyDeleteOption = CmsProperty.DELETE_OPTION_DELETE_STRUCTURE_VALUES; 3628 } else { 3629 // there are no other siblings- delete both the structure and resource property values 3630 propertyDeleteOption = CmsProperty.DELETE_OPTION_DELETE_STRUCTURE_AND_RESOURCE_VALUES; 3631 } 3632 3633 if (existsOnline) { 3634 m_driverManager.getVfsDriver( 3635 dbc).deletePropertyObjects(dbc, onlineProject.getUuid(), onlineResource, propertyDeleteOption); 3636 } 3637 m_driverManager.getVfsDriver( 3638 dbc).deletePropertyObjects(dbc, dbc.currentProject().getUuid(), offlineResource, propertyDeleteOption); 3639 3640 // if the offline file has a resource ID different from the online file 3641 // (probably because a (deleted) file was replaced by a new file with the 3642 // same name), the properties with the "old" resource ID have to be 3643 // deleted also offline 3644 if (existsOnline 3645 && (onlineResource != null) 3646 && !onlineResource.getResourceId().equals(offlineResource.getResourceId())) { 3647 m_driverManager.getVfsDriver(dbc).deletePropertyObjects( 3648 dbc, 3649 dbc.currentProject().getUuid(), 3650 onlineResource, 3651 CmsProperty.DELETE_OPTION_DELETE_STRUCTURE_AND_RESOURCE_VALUES); 3652 } 3653 } catch (CmsDataAccessException e) { 3654 if (LOG.isErrorEnabled()) { 3655 LOG.error( 3656 Messages.get().getBundle().key(Messages.LOG_DELETING_PROPERTIES_1, offlineResource.getRootPath()), 3657 e); 3658 } 3659 throw e; 3660 } 3661 3662 try { 3663 // remove the file online and offline 3664 m_driverManager.getVfsDriver(dbc).removeFile(dbc, dbc.currentProject().getUuid(), offlineResource); 3665 if (existsOnline && (onlineResource != null)) { 3666 m_driverManager.getVfsDriver(dbc).removeFile(dbc, onlineProject.getUuid(), onlineResource); 3667 } 3668 } catch (CmsDataAccessException e) { 3669 if (LOG.isErrorEnabled()) { 3670 LOG.error( 3671 Messages.get().getBundle().key(Messages.LOG_REMOVING_RESOURCE_1, offlineResource.getRootPath()), 3672 e); 3673 } 3674 throw e; 3675 } 3676 3677 // delete the ACL online and offline 3678 try { 3679 if (existsOnline && (onlineResource != null) && (onlineResource.getSiblingCount() == 1)) { 3680 // only if no siblings left 3681 m_driverManager.getUserDriver(dbc).removeAccessControlEntries( 3682 dbc, 3683 onlineProject, 3684 onlineResource.getResourceId()); 3685 } 3686 if (offlineResource.getSiblingCount() == 1) { 3687 // only if no siblings left 3688 m_driverManager.getUserDriver(dbc).removeAccessControlEntries( 3689 dbc, 3690 dbc.currentProject(), 3691 offlineResource.getResourceId()); 3692 } 3693 } catch (CmsDataAccessException e) { 3694 if (LOG.isErrorEnabled()) { 3695 LOG.error(Messages.get().getBundle().key(Messages.LOG_REMOVING_ACL_1, offlineResource.toString()), e); 3696 } 3697 throw e; 3698 } 3699 3700 try { 3701 // delete relations online and offline 3702 m_driverManager.getVfsDriver( 3703 dbc).deleteRelations(dbc, onlineProject.getUuid(), offlineResource, CmsRelationFilter.TARGETS); 3704 m_driverManager.getVfsDriver( 3705 dbc).deleteRelations(dbc, dbc.currentProject().getUuid(), offlineResource, CmsRelationFilter.TARGETS); 3706 } catch (CmsDataAccessException e) { 3707 if (LOG.isErrorEnabled()) { 3708 LOG.error( 3709 Messages.get().getBundle().key(Messages.LOG_REMOVING_RELATIONS_1, offlineResource.toString()), 3710 e); 3711 } 3712 throw e; 3713 } 3714 3715 if (OpenCms.getSubscriptionManager().isEnabled()) { 3716 try { 3717 // delete visited information for resource from log 3718 CmsVisitEntryFilter filter = CmsVisitEntryFilter.ALL.filterResource(offlineResource.getStructureId()); 3719 m_driverManager.getSubscriptionDriver().deleteVisits( 3720 dbc, 3721 OpenCms.getSubscriptionManager().getPoolName(), 3722 filter); 3723 } catch (CmsDataAccessException e) { 3724 if (LOG.isErrorEnabled()) { 3725 LOG.error( 3726 Messages.get().getBundle().key(Messages.LOG_REMOVING_VISITEDLOG_1, offlineResource.toString()), 3727 e); 3728 } 3729 throw e; 3730 } 3731 3732 try { 3733 // mark the subscribed resource as deleted 3734 /* changed to subscription driver */ 3735 // m_driverManager.getUserDriver(dbc).setSubscribedResourceAsDeleted( 3736 // dbc, 3737 // OpenCms.getSubscriptionManager().getPoolName(), 3738 // offlineResource); 3739 m_driverManager.getSubscriptionDriver().setSubscribedResourceAsDeleted( 3740 dbc, 3741 OpenCms.getSubscriptionManager().getPoolName(), 3742 offlineResource); 3743 } catch (CmsDataAccessException e) { 3744 if (LOG.isErrorEnabled()) { 3745 LOG.error( 3746 Messages.get().getBundle().key( 3747 Messages.LOG_REMOVING_SUBSCRIPTIONS_1, 3748 offlineResource.toString()), 3749 e); 3750 } 3751 throw e; 3752 } 3753 } 3754 } 3755 3756 /** 3757 * Publishes a new file.<p> 3758 * 3759 * @param dbc the current database context 3760 * @param onlineProject the online project 3761 * @param offlineResource the resource to publish 3762 * @param publishedContentIds contains the UUIDs of already published content records 3763 * @param publishHistoryId the publish history id 3764 * @param publishTag the publish tag 3765 * 3766 * @throws CmsDataAccessException is something goes wrong 3767 */ 3768 protected void publishNewFile( 3769 CmsDbContext dbc, 3770 CmsProject onlineProject, 3771 CmsResource offlineResource, 3772 Set<CmsUUID> publishedContentIds, 3773 CmsUUID publishHistoryId, 3774 int publishTag) 3775 throws CmsDataAccessException { 3776 3777 CmsResourceState resourceState = fixMovedResource( 3778 dbc, 3779 onlineProject, 3780 offlineResource, 3781 publishHistoryId, 3782 publishTag); 3783 3784 CmsFile newFile; 3785 try { 3786 // reset the labeled link flag before writing the online file 3787 int flags = offlineResource.getFlags(); 3788 flags &= ~CmsResource.FLAG_LABELED; 3789 offlineResource.setFlags(flags); 3790 3791 // publish the file content 3792 newFile = m_driverManager.getProjectDriver(dbc).publishFileContent( 3793 dbc, 3794 dbc.currentProject(), 3795 onlineProject, 3796 offlineResource, 3797 publishedContentIds, 3798 true, 3799 publishTag); 3800 3801 } catch (CmsVfsResourceAlreadyExistsException e) { 3802 try { 3803 // remove the existing file and ensure that it's content is written 3804 // in any case by removing it's resource ID from the set of published resource IDs 3805 m_driverManager.getVfsDriver(dbc).removeFile(dbc, onlineProject.getUuid(), offlineResource); 3806 publishedContentIds.remove(offlineResource.getResourceId()); 3807 newFile = m_driverManager.getProjectDriver(dbc).publishFileContent( 3808 dbc, 3809 dbc.currentProject(), 3810 onlineProject, 3811 offlineResource, 3812 publishedContentIds, 3813 true, 3814 publishTag); 3815 3816 } catch (CmsDataAccessException e1) { 3817 if (LOG.isErrorEnabled()) { 3818 LOG.error( 3819 Messages.get().getBundle().key( 3820 Messages.LOG_PUBLISHING_RESOURCE_1, 3821 offlineResource.getRootPath()), 3822 e); 3823 } 3824 throw e1; 3825 } 3826 } catch (CmsDataAccessException e) { 3827 if (LOG.isErrorEnabled()) { 3828 LOG.error( 3829 Messages.get().getBundle().key(Messages.LOG_PUBLISHING_RESOURCE_1, offlineResource.getRootPath()), 3830 e); 3831 } 3832 throw e; 3833 } 3834 3835 List<CmsProperty> offlineProperties; 3836 try { 3837 // write the properties online 3838 offlineProperties = m_driverManager.getVfsDriver(dbc).readPropertyObjects( 3839 dbc, 3840 dbc.currentProject(), 3841 offlineResource); 3842 CmsProperty.setAutoCreatePropertyDefinitions(offlineProperties, true); 3843 m_driverManager.getVfsDriver(dbc).writePropertyObjects(dbc, onlineProject, newFile, offlineProperties); 3844 } catch (CmsDataAccessException e) { 3845 if (LOG.isErrorEnabled()) { 3846 LOG.error( 3847 Messages.get().getBundle().key(Messages.LOG_PUBLISHING_PROPERTIES_1, newFile.getRootPath()), 3848 e); 3849 } 3850 3851 throw e; 3852 } 3853 3854 try { 3855 // write the ACL online 3856 m_driverManager.getUserDriver(dbc).publishAccessControlEntries( 3857 dbc, 3858 dbc.currentProject(), 3859 onlineProject, 3860 offlineResource.getResourceId(), 3861 newFile.getResourceId()); 3862 } catch (CmsDataAccessException e) { 3863 if (LOG.isErrorEnabled()) { 3864 LOG.error(Messages.get().getBundle().key(Messages.LOG_PUBLISHING_ACL_1, newFile.getRootPath()), e); 3865 } 3866 throw e; 3867 } 3868 3869 CmsFile offlineFile = new CmsFile(offlineResource); 3870 offlineFile.setContents(newFile.getContents()); 3871 internalWriteHistory(dbc, offlineFile, resourceState, offlineProperties, publishHistoryId, publishTag); 3872 3873 m_driverManager.getVfsDriver(dbc).updateRelations(dbc, onlineProject, offlineResource); 3874 } 3875 3876}