0001: /*
0002: * File : $Source: /usr/local/cvs/opencms/src-modules/org/opencms/workplace/tools/content/CmsElementRename.java,v $
0003: * Date : $Date: 2008-02-27 12:05:36 $
0004: * Version: $Revision: 1.18 $
0005: *
0006: * This library is part of OpenCms -
0007: * the Open Source Content Management System
0008: *
0009: * Copyright (c) 2002 - 2008 Alkacon Software GmbH (http://www.alkacon.com)
0010: *
0011: * This library is free software; you can redistribute it and/or
0012: * modify it under the terms of the GNU Lesser General Public
0013: * License as published by the Free Software Foundation; either
0014: * version 2.1 of the License, or (at your option) any later version.
0015: *
0016: * This library is distributed in the hope that it will be useful,
0017: * but WITHOUT ANY WARRANTY; without even the implied warranty of
0018: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
0019: * Lesser General Public License for more details.
0020: *
0021: * For further information about Alkacon Software GmbH, please see the
0022: * company website: http://www.alkacon.com
0023: *
0024: * For further information about OpenCms, please see the
0025: * project website: http://www.opencms.org
0026: *
0027: * You should have received a copy of the GNU Lesser General Public
0028: * License along with this library; if not, write to the Free Software
0029: * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
0030: */
0031:
0032: package org.opencms.workplace.tools.content;
0033:
0034: import org.opencms.file.CmsFile;
0035: import org.opencms.file.CmsObject;
0036: import org.opencms.file.CmsProperty;
0037: import org.opencms.file.CmsPropertyDefinition;
0038: import org.opencms.file.CmsResource;
0039: import org.opencms.file.CmsResourceFilter;
0040: import org.opencms.file.types.CmsResourceTypeXmlPage;
0041: import org.opencms.i18n.CmsLocaleManager;
0042: import org.opencms.i18n.CmsMessages;
0043: import org.opencms.jsp.CmsJspActionElement;
0044: import org.opencms.lock.CmsLock;
0045: import org.opencms.main.CmsException;
0046: import org.opencms.main.CmsLog;
0047: import org.opencms.main.OpenCms;
0048: import org.opencms.report.I_CmsReport;
0049: import org.opencms.util.CmsStringUtil;
0050: import org.opencms.workplace.CmsReport;
0051: import org.opencms.workplace.CmsWorkplace;
0052: import org.opencms.workplace.CmsWorkplaceSettings;
0053: import org.opencms.workplace.editors.CmsDialogElement;
0054: import org.opencms.workplace.explorer.CmsNewResourceXmlPage;
0055: import org.opencms.xml.CmsXmlException;
0056: import org.opencms.xml.page.CmsXmlPage;
0057: import org.opencms.xml.page.CmsXmlPageFactory;
0058: import org.opencms.xml.types.CmsXmlHtmlValue;
0059:
0060: import java.util.ArrayList;
0061: import java.util.HashSet;
0062: import java.util.Iterator;
0063: import java.util.List;
0064: import java.util.Locale;
0065: import java.util.Map;
0066: import java.util.Set;
0067: import java.util.StringTokenizer;
0068: import java.util.TreeMap;
0069:
0070: import javax.servlet.http.HttpServletRequest;
0071: import javax.servlet.http.HttpServletResponse;
0072: import javax.servlet.jsp.JspException;
0073: import javax.servlet.jsp.PageContext;
0074:
0075: import org.apache.commons.logging.Log;
0076:
0077: /**
0078: * Provides methods for the change page element name dialog.<p>
0079: *
0080: * @author Armen Markarian
0081: *
0082: * @version $Revision: 1.18 $
0083: *
0084: * @since 6.0.0
0085: */
0086: public class CmsElementRename extends CmsReport {
0087:
0088: /** A constant representing the select option all templates. */
0089: public static final String ALL = "ALL";
0090:
0091: /** The dialog type. */
0092: public static final String DIALOG_TYPE = "renameelement";
0093:
0094: /** Request parameter name for the locale. */
0095: public static final String PARAM_LOCALE = "locale";
0096:
0097: /** Request parameter name for the new element name. */
0098: public static final String PARAM_NEW_ELEMENT = "newelement";
0099:
0100: /** Request parameter name for the old element name. */
0101: public static final String PARAM_OLD_ELEMENT = "oldelement";
0102:
0103: /** Request parameter name for the recursive search. */
0104: public static final String PARAM_RECURSIVE = "recursive";
0105:
0106: /** Request parameter name for the remove empty elements. */
0107: public static final String PARAM_REMOVE_EMPTYELEMENTS = "removeemptyelements";
0108:
0109: /** Request parameter name for the template. */
0110: public static final String PARAM_TEMPLATE = "template";
0111:
0112: /** Request parameter name for the validate new element. */
0113: public static final String PARAM_VALIDATE_NEW_ELEMENT = "validatenewelement";
0114:
0115: /** The log object for this class. */
0116: private static final Log LOG = CmsLog
0117: .getLog(CmsElementRename.class);
0118:
0119: /** the cms object. */
0120: private CmsObject m_cms;
0121: /** the error message. */
0122: private String m_errorMessage;
0123: /** the locale use for content definition. */
0124: private String m_paramLocale;
0125: /** The new page element name. */
0126: private String m_paramNewElement;
0127: /** The old page element name. */
0128: private String m_paramOldElement;
0129: /** The recursive parameter. */
0130: private String m_paramRecursive;
0131: /** the flag indicating to remove empty elements. */
0132: private String m_paramRemoveEmptyElements;
0133: /** the template use for all pages (optional). */
0134: private String m_paramTemplate;
0135: /** the flag indicating to remove empty elements. */
0136: private String m_paramValidateNewElement;
0137: /** the report for the output. */
0138: private I_CmsReport m_report;
0139:
0140: /**
0141: * Public constructor with JSP action element.<p>
0142: *
0143: * @param jsp an initialized JSP action element
0144: */
0145: public CmsElementRename(CmsJspActionElement jsp) {
0146:
0147: super (jsp);
0148: }
0149:
0150: /**
0151: * Public constructor for testcase using.<p>
0152: *
0153: * @param jsp an initialized JSP action element
0154: * @param cms the cms object
0155: * @param resource the resource path
0156: * @param recursive if true then do read recursive from the folder
0157: * @param template the template
0158: * @param locale the locale
0159: * @param oldElement the old element name
0160: * @param newElement the new element name
0161: * @param removeEmptyElements if true then remove all invalid elements with no content
0162: * @param validateNewElement if true then validate the new element before renaming
0163: */
0164: public CmsElementRename(CmsJspActionElement jsp, CmsObject cms,
0165: String resource, String recursive, String template,
0166: String locale, String oldElement, String newElement,
0167: String removeEmptyElements, String validateNewElement) {
0168:
0169: super (jsp);
0170: m_cms = cms;
0171: setParamResource(resource);
0172: setParamRecursive(recursive);
0173: setParamTemplate(template);
0174: setParamLocale(locale);
0175: setParamOldElement(oldElement);
0176: setParamNewElement(newElement);
0177: setParamRemoveEmptyElements(removeEmptyElements);
0178: setParamValidateNewElement(validateNewElement);
0179: }
0180:
0181: /**
0182: * Public constructor with JSP variables.<p>
0183: *
0184: * @param context the JSP page context
0185: * @param req the JSP request
0186: * @param res the JSP response
0187: */
0188: public CmsElementRename(PageContext context,
0189: HttpServletRequest req, HttpServletResponse res) {
0190:
0191: this (new CmsJspActionElement(context, req, res));
0192: }
0193:
0194: /**
0195: * Renames the element name on the specified resources.<p>
0196: *
0197: * @param report the cms report
0198: */
0199: public void actionRename(I_CmsReport report) {
0200:
0201: m_report = report;
0202: List locales = OpenCms.getLocaleManager().getAvailableLocales();
0203: List xmlPages = getXmlPages();
0204: if (ALL.equals(getParamLocale())) {
0205: Iterator i = locales.iterator();
0206: while (i.hasNext()) {
0207: Locale locale = (Locale) i.next();
0208: performRenameOperation(xmlPages, locale);
0209: }
0210: } else {
0211: performRenameOperation(xmlPages, CmsLocaleManager
0212: .getLocale(getParamLocale()));
0213: }
0214: }
0215:
0216: /**
0217: * Performs the move report, will be called by the JSP page.<p>
0218: *
0219: * @throws JspException if problems including sub-elements occur
0220: */
0221: public void actionReport() throws JspException {
0222:
0223: // save initialized instance of this class in request attribute for included sub-elements
0224: getJsp().getRequest().setAttribute(SESSION_WORKPLACE_CLASS,
0225: this );
0226: switch (getAction()) {
0227: case ACTION_REPORT_END:
0228: actionCloseDialog();
0229: break;
0230: case ACTION_REPORT_UPDATE:
0231: setParamAction(REPORT_UPDATE);
0232: getJsp().include(FILE_REPORT_OUTPUT);
0233: break;
0234: case ACTION_REPORT_BEGIN:
0235: case ACTION_CONFIRMED:
0236: default:
0237: CmsElementRenameThread thread = new CmsElementRenameThread(
0238: getCms(), this );
0239: thread.start();
0240: setParamAction(REPORT_BEGIN);
0241: setParamThread(thread.getUUID().toString());
0242: getJsp().include(FILE_REPORT_OUTPUT);
0243: break;
0244: }
0245: }
0246:
0247: /**
0248: * Builds the html for the available locales select box.<p>
0249: *
0250: * @param attributes optional attributes for the <select> tag
0251: *
0252: * @return the html for the available locales select box
0253: */
0254: public String buildSelectLocales(String attributes) {
0255:
0256: List options = new ArrayList();
0257: List values = new ArrayList();
0258: List locales = OpenCms.getLocaleManager().getAvailableLocales();
0259: int selectedIndex = -1;
0260: if (locales == null) {
0261: // no locales found, return empty String
0262: return "";
0263: } else {
0264: // locales found, create option and value lists
0265: CmsMessages messages = Messages.get()
0266: .getBundle(getLocale());
0267: options.add(messages.key(Messages.GUI_PLEASE_SELECT_0));
0268: values.add("");
0269: options.add(messages.key(Messages.GUI_BUTTON_ALL_0));
0270: values.add(ALL);
0271: if (ALL.equals(getParamLocale())) {
0272: selectedIndex = 1;
0273: }
0274: Iterator i = locales.iterator();
0275: int counter = 2;
0276: while (i.hasNext()) {
0277: Locale locale = (Locale) i.next();
0278: String language = locale.getLanguage();
0279: String displayLanguage = locale.getDisplayLanguage();
0280: if (language.equals(getParamLocale())) {
0281: selectedIndex = counter;
0282: }
0283: options.add(displayLanguage);
0284: values.add(language);
0285: counter++;
0286: }
0287: }
0288:
0289: return CmsWorkplace.buildSelect(attributes, options, values,
0290: selectedIndex, false);
0291: }
0292:
0293: /**
0294: * Builds the html for the template select box.<p>
0295: *
0296: * @param attributes optional attributes for the <select> tag
0297: * @return the html for the template select box
0298: */
0299: public String buildSelectTemplates(String attributes) {
0300:
0301: List options = new ArrayList();
0302: List values = new ArrayList();
0303: TreeMap templates = null;
0304: int selectedIndex = -1;
0305: try {
0306: // get all available templates
0307: templates = CmsNewResourceXmlPage.getTemplates(getCms(),
0308: null);
0309: } catch (CmsException e) {
0310: // can usually be ignored
0311: if (LOG.isInfoEnabled()) {
0312: LOG.info(e);
0313: }
0314: }
0315: if (templates == null) {
0316: // no templates found, return empty String
0317: return "";
0318: } else {
0319: // templates found, create option and value lists
0320: CmsMessages messages = Messages.get()
0321: .getBundle(getLocale());
0322: options.add(messages.key(Messages.GUI_PLEASE_SELECT_0));
0323: values.add("");
0324: options.add(messages.key(Messages.GUI_BUTTON_ALL_0));
0325: values.add(ALL);
0326: if (ALL.equals(getParamTemplate())) {
0327: selectedIndex = 1;
0328: }
0329: Iterator i = templates.entrySet().iterator();
0330: int counter = 2;
0331: while (i.hasNext()) {
0332: Map.Entry entry = (Map.Entry) i.next();
0333: String key = (String) entry.getKey();
0334: String path = (String) entry.getValue();
0335: if (path.equals(getParamTemplate())) {
0336: selectedIndex = counter;
0337: }
0338: options.add(key);
0339: values.add(path);
0340: counter++;
0341: }
0342: }
0343: return buildSelect(attributes, options, values, selectedIndex,
0344: false);
0345: }
0346:
0347: /**
0348: * @see org.opencms.workplace.CmsWorkplace#getCms()
0349: */
0350: public CmsObject getCms() {
0351:
0352: if (m_cms == null) {
0353: return super .getCms();
0354: }
0355:
0356: return m_cms;
0357: }
0358:
0359: /**
0360: * Returns the errorMessage.<p>
0361: *
0362: * @return the errorMessage
0363: */
0364: public String getErrorMessage() {
0365:
0366: if (CmsStringUtil.isEmpty(m_errorMessage)) {
0367: return "";
0368: }
0369:
0370: return m_errorMessage;
0371: }
0372:
0373: /**
0374: * Returns the paramLocale.<p>
0375: *
0376: * @return the paramLocale
0377: */
0378: public String getParamLocale() {
0379:
0380: return m_paramLocale;
0381: }
0382:
0383: /**
0384: * Returns the value of the newvalue parameter.<p>
0385: *
0386: * @return the value of the newvalue parameter
0387: */
0388: public String getParamNewElement() {
0389:
0390: return m_paramNewElement;
0391: }
0392:
0393: /**
0394: * Returns the value of the oldvalue parametere.<p>
0395: *
0396: * @return the value of the oldvalue parameter
0397: */
0398: public String getParamOldElement() {
0399:
0400: return m_paramOldElement;
0401: }
0402:
0403: /**
0404: * Returns the value of the recursive parameter.<p>
0405: *
0406: * @return the value of the recursive parameter
0407: */
0408: public String getParamRecursive() {
0409:
0410: return m_paramRecursive;
0411: }
0412:
0413: /**
0414: * Returns true if the user has set remove empty elements parameter; otherwise false.<p>
0415: *
0416: * @return true if the user has set remove empty elements parameter; otherwise false
0417: */
0418: public String getParamRemoveEmptyElements() {
0419:
0420: return m_paramRemoveEmptyElements;
0421: }
0422:
0423: /**
0424: * Returns the template.<p>
0425: *
0426: * @return the template
0427: */
0428: public String getParamTemplate() {
0429:
0430: return m_paramTemplate;
0431: }
0432:
0433: /**
0434: * Returns true if the user has set validate new element parameter; otherwise false.<p>.<p>
0435: *
0436: * @return true if the user has set validate new element parameter; otherwise false
0437: */
0438: public String getParamValidateNewElement() {
0439:
0440: return m_paramValidateNewElement;
0441: }
0442:
0443: /**
0444: * Sets the errorMessage.<p>
0445: *
0446: * @param errorMessage the errorMessage to set
0447: */
0448: public void setErrorMessage(String errorMessage) {
0449:
0450: m_errorMessage = errorMessage;
0451: }
0452:
0453: /**
0454: * Sets the locale.<p>
0455: *
0456: * @param paramLocale the locale to set
0457: */
0458: public void setParamLocale(String paramLocale) {
0459:
0460: m_paramLocale = paramLocale;
0461: }
0462:
0463: /**
0464: * Sets the value of the newvalue parameter.<p>
0465: *
0466: * @param paramNewValue the value of the newvalue parameter
0467: */
0468: public void setParamNewElement(String paramNewValue) {
0469:
0470: m_paramNewElement = paramNewValue;
0471: }
0472:
0473: /**
0474: * Sets the value of the oldvalue parameter.<p>
0475: *
0476: * @param paramOldValue the value of the oldvalue parameter
0477: */
0478: public void setParamOldElement(String paramOldValue) {
0479:
0480: m_paramOldElement = paramOldValue;
0481: }
0482:
0483: /**
0484: * Sets the value of the recursive parameter.<p>
0485: *
0486: * @param paramRecursive the value of the recursive parameter
0487: */
0488: public void setParamRecursive(String paramRecursive) {
0489:
0490: m_paramRecursive = paramRecursive;
0491: }
0492:
0493: /**
0494: * Sets the remove empty elements parameter to true or false.<p>
0495: *
0496: * @param paramRemoveEmptyElements the remove empty elements parameter to set
0497: */
0498: public void setParamRemoveEmptyElements(
0499: String paramRemoveEmptyElements) {
0500:
0501: m_paramRemoveEmptyElements = paramRemoveEmptyElements;
0502: }
0503:
0504: /**
0505: * Sets the param Template.<p>
0506: *
0507: * @param paramTemplate the template name to set
0508: */
0509: public void setParamTemplate(String paramTemplate) {
0510:
0511: m_paramTemplate = paramTemplate;
0512: }
0513:
0514: /**
0515: * Sets the paramValidateNewElement.<p>
0516: *
0517: * @param paramValidateNewElement the validate new element parameter to set
0518: */
0519: public void setParamValidateNewElement(
0520: String paramValidateNewElement) {
0521:
0522: m_paramValidateNewElement = paramValidateNewElement;
0523: }
0524:
0525: /**
0526: * Does validate the request parameters and returns a buffer with error messages.<p>
0527: *
0528: * If there were no error messages, the buffer is empty.<p>
0529: */
0530: public void validateParameters() {
0531:
0532: // localisation
0533: CmsMessages messages = Messages.get().getBundle(getLocale());
0534:
0535: StringBuffer validationErrors = new StringBuffer();
0536: if (CmsStringUtil.isEmpty(getParamResource())) {
0537: validationErrors
0538: .append(
0539: messages
0540: .key(Messages.GUI_ELEM_RENAME_VALIDATE_RESOURCE_FOLDER_0))
0541: .append("<br>");
0542: }
0543: if (CmsStringUtil.isEmpty(getParamTemplate())) {
0544: validationErrors
0545: .append(
0546: messages
0547: .key(Messages.GUI_ELEM_RENAME_VALIDATE_SELECT_TEMPLATE_0))
0548: .append("<br>");
0549: }
0550: if (CmsStringUtil.isEmpty(getParamLocale())) {
0551: validationErrors
0552: .append(
0553: messages
0554: .key(Messages.GUI_ELEM_RENAME_VALIDATE_SELECT_LANGUAGE_0))
0555: .append("<br>");
0556: }
0557: if (CmsStringUtil.isEmpty(getParamOldElement())) {
0558: validationErrors
0559: .append(
0560: messages
0561: .key(Messages.GUI_ELEM_RENAME_VALIDATE_ENTER_OLD_ELEM_0))
0562: .append("<br>");
0563: }
0564: if (CmsStringUtil.isEmpty(getParamNewElement())) {
0565: validationErrors
0566: .append(
0567: messages
0568: .key(Messages.GUI_ELEM_RENAME_VALIDATE_ENTER_NEW_ELEM_0))
0569: .append("<br>");
0570: }
0571: if (!isValidElement(getParamNewElement())) {
0572: validationErrors
0573: .append(
0574: messages
0575: .key(
0576: Messages.GUI_ELEM_RENAME_VALIDATE_INVALID_NEW_ELEM_2,
0577: getParamNewElement(),
0578: getParamTemplate()))
0579: .append("<br>");
0580: }
0581:
0582: setErrorMessage(validationErrors.toString());
0583: }
0584:
0585: /**
0586: * @see org.opencms.workplace.CmsWorkplace#initWorkplaceRequestValues(org.opencms.workplace.CmsWorkplaceSettings, javax.servlet.http.HttpServletRequest)
0587: */
0588: protected void initWorkplaceRequestValues(
0589: CmsWorkplaceSettings settings, HttpServletRequest request) {
0590:
0591: // fill the parameter values in the get/set methods
0592: fillParamValues(request);
0593: // set the dialog type
0594: setParamDialogtype(DIALOG_TYPE);
0595: // set the action for the JSP switch
0596: // set the action for the JSP switch
0597: if (DIALOG_CONFIRMED.equals(getParamAction())) {
0598: setAction(ACTION_CONFIRMED);
0599: } else if (DIALOG_OK.equals(getParamAction())) {
0600: setAction(ACTION_OK);
0601: } else if (DIALOG_CANCEL.equals(getParamAction())) {
0602: setAction(ACTION_CANCEL);
0603: } else if (REPORT_UPDATE.equals(getParamAction())) {
0604: setAction(ACTION_REPORT_UPDATE);
0605: } else if (REPORT_BEGIN.equals(getParamAction())) {
0606: setAction(ACTION_REPORT_BEGIN);
0607: } else if (REPORT_END.equals(getParamAction())) {
0608: setAction(ACTION_REPORT_END);
0609: } else {
0610: setAction(ACTION_DEFAULT);
0611: // add the title for the dialog
0612: setParamTitle(key("title.renameelement"));
0613: }
0614: }
0615:
0616: /**
0617: * Returns a retained list of xml pages that belongs to the specified template.<p>
0618: *
0619: * @param xmlPages a list of all xml pages
0620: * @return a retained list of xml pages that belongs to the specified template
0621: */
0622: private List getRetainedPagesWithTemplate(List xmlPages) {
0623:
0624: // list of resources belongs to the selected template
0625: List resourcesWithTemplate = new ArrayList();
0626: TreeMap templates = null;
0627: try {
0628: templates = CmsNewResourceXmlPage.getTemplates(getCms(),
0629: null);
0630: } catch (CmsException e) {
0631: if (LOG.isErrorEnabled()) {
0632: LOG.error(e.getLocalizedMessage(), e);
0633: }
0634: }
0635: // check if the users selected template is valid.
0636: if ((templates != null)
0637: && templates.containsValue(getParamTemplate())) {
0638: // iterate the xmlPages list and add all resources with the specified template to the resourcesWithTemplate list
0639: Iterator i = xmlPages.iterator();
0640: while (i.hasNext()) {
0641: CmsResource currentPage = (CmsResource) i.next();
0642: // read the template property
0643: CmsProperty templateProperty;
0644: try {
0645: templateProperty = getCms().readPropertyObject(
0646: getCms().getSitePath(currentPage),
0647: CmsPropertyDefinition.PROPERTY_TEMPLATE,
0648: false);
0649: } catch (CmsException e2) {
0650: if (LOG.isErrorEnabled()) {
0651: LOG.error(e2);
0652: }
0653: continue;
0654: }
0655: // add currentResource if the template property value is the same as the given template
0656: if (getParamTemplate().equals(
0657: templateProperty.getValue())) {
0658: resourcesWithTemplate.add(currentPage);
0659: }
0660: }
0661: // retain the list of pages against the list with template
0662: xmlPages.retainAll(resourcesWithTemplate);
0663: }
0664:
0665: return xmlPages;
0666: }
0667:
0668: /**
0669: * Returns a set of elements stored in the given template property.<p>
0670: *
0671: * The elements are stored in the property I_CmsConstants.C_PROPERTY_TEMPLATE_ELEMENTS.<p>
0672: *
0673: * @param currentTemplate the path of the template to look in
0674: * @return a set of elements stored in the given template path
0675: */
0676: private Set getTemplateElements(String currentTemplate) {
0677:
0678: Set templateElements = new HashSet();
0679:
0680: if ((currentTemplate != null) && (currentTemplate.length() > 0)) {
0681: // template found, check template-elements property
0682: String elements = null;
0683: try {
0684: // read the property from the template file
0685: elements = getCms()
0686: .readPropertyObject(
0687: currentTemplate,
0688: CmsPropertyDefinition.PROPERTY_TEMPLATE_ELEMENTS,
0689: false).getValue(null);
0690: } catch (CmsException e) {
0691: if (LOG.isWarnEnabled()) {
0692: LOG.warn(e.getLocalizedMessage());
0693: }
0694: }
0695: if (elements != null) {
0696: // elements are defined on template file, merge with available elements
0697: StringTokenizer T = new StringTokenizer(elements, ",");
0698: while (T.hasMoreTokens()) {
0699: String currentElement = T.nextToken();
0700: String niceName = null;
0701: boolean mandatory = false;
0702: int sepIndex = currentElement.indexOf("|");
0703: if (sepIndex != -1) {
0704: // nice name found for current element, extract it
0705: niceName = currentElement
0706: .substring(sepIndex + 1);
0707: currentElement = currentElement.substring(0,
0708: sepIndex);
0709: }
0710: if (currentElement.endsWith("*")) {
0711: // element is mandatory
0712: mandatory = true;
0713: currentElement = currentElement.substring(0,
0714: currentElement.length() - 1);
0715: }
0716:
0717: CmsDialogElement element = new CmsDialogElement(
0718: currentElement, niceName, mandatory, true,
0719: false);
0720: templateElements.add(element);
0721: }
0722: }
0723: }
0724:
0725: return templateElements;
0726: }
0727:
0728: /**
0729: * Returns a list of xml pages from the specified folder.<p>
0730: *
0731: * @return a list of xml pages from the specified folder
0732: */
0733: private List getXmlPages() {
0734:
0735: boolean isRecursive = Boolean.valueOf(getParamRecursive())
0736: .booleanValue();
0737: // filterdefinition to read only the required resources
0738: CmsResourceFilter filter = CmsResourceFilter.IGNORE_EXPIRATION
0739: .addRequireType(CmsResourceTypeXmlPage
0740: .getStaticTypeId());
0741: // trying to read the resources
0742: List xmlPages = null;
0743:
0744: try {
0745: xmlPages = getCms().readResources(getParamResource(),
0746: filter, isRecursive);
0747: } catch (CmsException e) {
0748: if (LOG.isErrorEnabled()) {
0749: LOG.error(e.getLocalizedMessage(), e);
0750: }
0751: }
0752:
0753: return xmlPages;
0754: }
0755:
0756: /**
0757: * Checks if the specified element/locale of the given page has a content.<p>
0758: *
0759: * @param page the xml page
0760: * @param element the element name
0761: * @param locale the locale
0762: * @return false if the specified element/locale of the given page has a content; otherwise true
0763: */
0764: private boolean isEmptyElement(CmsXmlPage page, String element,
0765: Locale locale) {
0766:
0767: CmsXmlHtmlValue xmlHtmlValue = (CmsXmlHtmlValue) page.getValue(
0768: element, locale);
0769: if (CmsStringUtil.isNotEmpty(xmlHtmlValue
0770: .getPlainText(getCms()))) {
0771: return false;
0772: }
0773:
0774: return true;
0775: }
0776:
0777: /**
0778: * Checks if the selected new element is valid for the selected template.<p>
0779: *
0780: * @param page the xml page
0781: * @param element the element name
0782: *
0783: * @return true if ALL_TEMPLATES selected or the element is valid for the selected template; otherwise false
0784: */
0785: private boolean isValidElement(CmsXmlPage page, String element) {
0786:
0787: CmsFile file = page.getFile();
0788: String template;
0789: try {
0790: template = getCms().readPropertyObject(
0791: getCms().getSitePath(file),
0792: CmsPropertyDefinition.PROPERTY_TEMPLATE, true)
0793: .getValue(null);
0794: } catch (CmsException e) {
0795: return false;
0796: }
0797:
0798: return isValidTemplateElement(template, element);
0799: }
0800:
0801: /**
0802: * Checks if the selected new element is valid for the selected template.<p>
0803: *
0804: * @param element the element name
0805: *
0806: * @return true if ALL_TEMPLATES selected or the element is valid for the selected template; otherwise false
0807: */
0808: private boolean isValidElement(String element) {
0809:
0810: boolean validateNewElement = Boolean.valueOf(
0811: getParamValidateNewElement()).booleanValue();
0812: if (ALL.equals(getParamTemplate()) || !validateNewElement) {
0813: return true;
0814: }
0815:
0816: return isValidTemplateElement(getParamTemplate(), element);
0817: }
0818:
0819: /**
0820: * Check if the given template includes the specified element.<p>
0821: *
0822: * @param template the template
0823: * @param element the element name
0824: * @return true if the template includes the given element
0825: */
0826: private boolean isValidTemplateElement(String template,
0827: String element) {
0828:
0829: List elements = new ArrayList(getTemplateElements(template));
0830: Iterator i = elements.iterator();
0831: while (i.hasNext()) {
0832: CmsDialogElement currElement = (CmsDialogElement) i.next();
0833: if (element.equals(currElement.getName())) {
0834: return true;
0835: }
0836: }
0837:
0838: return false;
0839: }
0840:
0841: /**
0842: * Performs the main element rename operation on the filtered resources.<p>
0843: *
0844: * @param xmlPages the list of xml pages
0845: * @param locale the locale specifying the xmlpage node to perform the operation on
0846: */
0847: private void performRenameOperation(List xmlPages, Locale locale) {
0848:
0849: // partial localized (stopped due to low prio).
0850: boolean removeEmptyElements = Boolean.valueOf(
0851: getParamRemoveEmptyElements()).booleanValue();
0852: boolean validateNewElement = Boolean.valueOf(
0853: getParamValidateNewElement()).booleanValue();
0854: // the list including at least one resource
0855: if ((xmlPages != null) && (xmlPages.size() > 0)) {
0856: m_report.println(Messages.get().container(
0857: Messages.RPT_RENAME_LANG_1, locale.getLanguage()),
0858: I_CmsReport.FORMAT_HEADLINE);
0859: // if user has not selected ALL templates, then retain pages with specified template
0860: if (!ALL.equals(getParamTemplate())) {
0861: xmlPages = getRetainedPagesWithTemplate(xmlPages);
0862: }
0863: int m = 0;
0864: int n = xmlPages.size();
0865: // loop over remained pages
0866: Iterator i = xmlPages.iterator();
0867: while (i.hasNext()) {
0868: m++;
0869: CmsXmlPage page = null;
0870: try {
0871: // next file from the list
0872: CmsResource res = (CmsResource) i.next();
0873: CmsFile file;
0874:
0875: m_report
0876: .print(
0877: org.opencms.report.Messages
0878: .get()
0879: .container(
0880: org.opencms.report.Messages.RPT_SUCCESSION_2,
0881: String.valueOf(m),
0882: String.valueOf(n)),
0883: I_CmsReport.FORMAT_NOTE);
0884: m_report.print(Messages.get().container(
0885: Messages.RPT_PROCESSING_PAGE_0),
0886: I_CmsReport.FORMAT_NOTE);
0887: m_report
0888: .print(org.opencms.report.Messages
0889: .get()
0890: .container(
0891: org.opencms.report.Messages.RPT_ARGUMENT_1,
0892: getCms().getSitePath(res)));
0893: m_report
0894: .println(org.opencms.report.Messages
0895: .get()
0896: .container(
0897: org.opencms.report.Messages.RPT_DOTS_0));
0898:
0899: try {
0900: file = getCms().readFile(
0901: getCms().getSitePath(res),
0902: CmsResourceFilter.IGNORE_EXPIRATION);
0903: } catch (CmsException e2) {
0904: if (LOG.isErrorEnabled()) {
0905: LOG.error(e2);
0906: }
0907: m_report.println(e2);
0908: continue;
0909: }
0910: // try unmarshaling to xml page
0911: try {
0912: page = CmsXmlPageFactory.unmarshal(getCms(),
0913: file);
0914: } catch (CmsXmlException e) {
0915: m_report.println(e);
0916: continue;
0917: }
0918:
0919: // check if the source element exists in the page
0920: if (!page.hasValue(getParamOldElement(), locale)) {
0921: m_report.println(Messages.get().container(
0922: Messages.RPT_NONEXISTANT_ELEM_1,
0923: getParamOldElement()),
0924: I_CmsReport.FORMAT_NOTE);
0925: continue;
0926: }
0927:
0928: // check if the target element already exists in the page
0929: if (page.hasValue(getParamNewElement(), locale)) {
0930: // the page contains already the new element with speicific content.
0931: // renaming the old will invalid the xml page
0932: m_report.println(Messages.get().container(
0933: Messages.RPT_NEW_ELEM_EXISTS_0),
0934: I_CmsReport.FORMAT_NOTE);
0935: continue;
0936: }
0937:
0938: if (validateNewElement) {
0939: // check if the target element is valid for the template
0940: if (!isValidElement(page, getParamNewElement())) {
0941: m_report.println(Messages.get().container(
0942: Messages.RPT_INVALID_ARGUMENT_1,
0943: getParamNewElement()),
0944: I_CmsReport.FORMAT_NOTE);
0945: continue;
0946: }
0947: }
0948:
0949: try {
0950: // rename the element from the old value to the new
0951: page.renameValue(getParamOldElement(),
0952: getParamNewElement(), locale);
0953: // write the page with the new content
0954: writePageAndReport(page, true);
0955: } catch (Throwable t) {
0956: LOG.error(t);
0957: m_report.println(t);
0958: continue;
0959: }
0960:
0961: } catch (Throwable t) {
0962: LOG.error(t);
0963: m_report.println(t);
0964: } finally {
0965: // finally do remove empty elements of the page
0966: // the remove operation is executed if the user has checked the specified checkbox and selected a template (NOT ALL)
0967: if (removeEmptyElements) {
0968: removeInValidElements(page, locale);
0969: }
0970: }
0971: }
0972: }
0973: }
0974:
0975: /**
0976: * Analyzes xml page and removes any element if this is not valid for the specified template and has no content.<p>
0977: *
0978: * @param page a xml page
0979: * @param locale the locale
0980: */
0981: private void removeInValidElements(CmsXmlPage page, Locale locale) {
0982:
0983: if (page == null) {
0984: return;
0985: }
0986:
0987: if (ALL.equals(getParamTemplate())) {
0988: return;
0989: }
0990:
0991: // get all elements of this page
0992: List pageElements = page.getNames(locale);
0993: if (pageElements != null) {
0994: Iterator i = pageElements.iterator();
0995: while (i.hasNext()) {
0996: String currElement = (String) i.next();
0997: // remove current element only is invalid and has no content
0998: if (!isValidElement(currElement)
0999: && isEmptyElement(page, currElement, locale)) {
1000: page.removeValue(currElement, locale);
1001: try {
1002: writePageAndReport(page, false);
1003: m_report
1004: .println(
1005: Messages
1006: .get()
1007: .container(
1008: Messages.RPT_REMOVE_INVALID_EMPTY_ELEM_1,
1009: currElement),
1010: I_CmsReport.FORMAT_NOTE);
1011: } catch (CmsException e) {
1012: // ignore
1013: }
1014: }
1015: }
1016: }
1017: }
1018:
1019: /**
1020: * Writes the given xml page by reporting the result.<p>
1021: *
1022: * @param page the xml page
1023: * @param report if true then some output will be written to the report
1024: * @throws CmsException if operation failed
1025: */
1026: private void writePageAndReport(CmsXmlPage page, boolean report)
1027: throws CmsException {
1028:
1029: CmsFile file = page.getFile();
1030: byte[] content = page.marshal();
1031: file.setContents(content);
1032: // check lock
1033: CmsLock lock = getCms().getLock(file);
1034: if (lock.isNullLock()
1035: || lock.isOwnedBy(getCms().getRequestContext()
1036: .currentUser())) {
1037: // lock the page
1038: checkLock(getCms().getSitePath(file));
1039: // write the file with the new content
1040: getCms().writeFile(file);
1041: // unlock the page
1042: getCms().unlockResource(getCms().getSitePath(file));
1043: if (report) {
1044: m_report.println(Messages.get().container(
1045: Messages.RPT_ELEM_RENAME_2,
1046: getParamOldElement(), getParamNewElement()),
1047: I_CmsReport.FORMAT_OK);
1048: }
1049: }
1050: }
1051: }
|