CCM NG: Migrated BebopConfig to new configuration system

git-svn-id: https://svn.libreccm.org/ccm/ccm_ng@3795 8810af33-2d31-482b-a856-94f89814c4df
pull/2/head
jensp 2016-01-14 09:14:28 +00:00
parent 3ce721d6e3
commit d1251b5fc0
11 changed files with 547 additions and 504 deletions

View File

@ -1,40 +0,0 @@
/*
* Copyright (C) 2003-2004 Red Hat Inc. All Rights Reserved.
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public License
* as published by the Free Software Foundation; either version 2.1 of
* the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*
*/
package com.arsdigita.bebop;
import org.apache.log4j.Logger;
/**
* @author Justin Ross
* @see com.arsdigita.bebop.BebopConfig
* @version $Id$
*/
public final class Bebop {
private static final Logger s_log = Logger.getLogger(Bebop.class);
private static BebopConfig s_config = BebopConfig.getInstance();
/**
* Gets the <code>BebopConfig</code> object.
*/
public static BebopConfig getConfig() {
return s_config;
}
}

View File

@ -1,191 +1,283 @@
/*
* Copyright (C) 2003-2004 Red Hat Inc. All Rights Reserved.
* Copyright (C) 2016 LibreCCM Foundation.
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public License
* as published by the Free Software Foundation; either version 2.1 of
* the License, or (at your option) any later version.
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
* MA 02110-1301 USA
*/
package com.arsdigita.bebop;
import com.arsdigita.bebop.page.PageTransformer;
import com.arsdigita.bebop.util.BebopConstants;
import com.arsdigita.runtime.AbstractConfig;
import com.arsdigita.templating.PresentationManager;
import com.arsdigita.ui.SimplePage;
import com.arsdigita.util.parameter.BooleanParameter;
import com.arsdigita.util.parameter.ClassParameter;
import com.arsdigita.util.parameter.EnumerationParameter;
import com.arsdigita.util.parameter.Parameter;
import com.arsdigita.util.parameter.SingletonParameter;
import com.arsdigita.util.parameter.StringParameter;
import org.apache.log4j.Logger;
import com.arsdigita.util.UncheckedWrapperException;
import java.util.Arrays;
import java.util.HashSet;
import java.util.Objects;
import java.util.Set;
import java.util.StringJoiner;
import org.libreccm.cdi.utils.CdiUtil;
import org.libreccm.configuration.Configuration;
import org.libreccm.configuration.ConfigurationManager;
import org.libreccm.configuration.Setting;
/**
* @author Justin Ross
* @see com.arsdigita.bebop.Bebop
* @version $Id: BebopConfig.java 1498 2007-03-19 16:22:15Z apevec $
*
* @author <a href="mailto:jens.pelzetter@googlemail.com">Jens Pelzetter</a>
*/
public final class BebopConfig extends AbstractConfig {
/** A logger instance to assist debugging. */
private static final Logger s_log = Logger.getLogger(BebopConfig.class);
@Configuration(descBundle = "com.arsdigita.bebop.BebopConfigDescription",
descKey = "bebop.config.description")
public final class BebopConfig {
/** Singleton config object. */
private static BebopConfig s_config;
/**
* Gain a BebopConfig object.
*
* Singleton pattern, don't instantiate a config object using the
* constructor directly!
* @return
*/
public static synchronized BebopConfig getInstance() {
if (s_config == null) {
s_config = new BebopConfig();
s_config.load();
@Setting(descKey = "bebop.config.presenter_class_name")
private String presenterClassName = PageTransformer.class.getName();
@Setting(descKey = "bebop.config.base_page_name")
private String basePageClassName = SimplePage.class.getName();
@Setting(descKey = "bebop.config.tidy_config_file")
private String tidyConfigFile
= "com/arsdigita/bebop/parameters/tidy.properties";
@Setting(descKey = "bebop.config.fancy_errors")
private Boolean fancyErrors = false;
@Setting(descKey = "bebop.config.dcp_on_buttons")
private Boolean dcpOnButtons = true;
@Setting(descKey = "bebop.config.dcp_on_links")
private Boolean dcpOnLinks = false;
@Setting(descKey = "bebop.config.tree_select_enabled")
private Boolean treeSelectEnabled = false;
@Setting(descKey = "bebop.config.dhtml_editors")
private Set<String> dhtmlEditors = new HashSet<>(
Arrays.asList(new String[]{BebopConstants.BEBOP_XINHAEDITOR,
BebopConstants.BEBOP_FCKEDITOR,
BebopConstants.BEBOP_DHTMLEDITOR}));
@Setting(descKey = "bebop.config.default_dhtml_editor")
private String defaultDhtmlEditor = BebopConstants.BEBOP_XINHAEDITOR;
@Setting(descKey = "bebop.config.dhtml_editor_srcfile")
private String dhtmlEditorSrcFile = "/assets/xinha/XinhaLoader.js";
@Setting(descKey = "bebop.config.show_class_name")
private Boolean showClassName = false;
public static BebopConfig getConfig() {
final CdiUtil cdiUtil = new CdiUtil();
final ConfigurationManager confManager = cdiUtil.findBean(
ConfigurationManager.class);
return confManager.findConfiguration(BebopConfig.class);
}
public String getPresenterClassName() {
return presenterClassName;
}
public Class<PresentationManager> getPresenterClass() {
try {
return (Class<PresentationManager>) Class.
forName(presenterClassName);
} catch (ClassNotFoundException ex) {
throw new UncheckedWrapperException(ex);
}
return s_config;
}
// set of configuration parameters
// /////////////////////////////////////////////////////////////////
/**
* */
private final Parameter m_presenter = new SingletonParameter
("waf.bebop.presentation_manager", Parameter.REQUIRED,
new PageTransformer());
/**
*
*/
private final Parameter m_page = new ClassParameter
("waf.bebop.base_page", Parameter.REQUIRED, SimplePage.class);
/** Pointer to JTidy validation listener config file */
private final Parameter m_tidy = new StringParameter
("waf.bebop.tidy_config_file", Parameter.REQUIRED,
"com/arsdigita/bebop/parameters/tidy.properties");
private final Parameter m_fancyErrors = new BooleanParameter
("waf.bebop.fancy_xsl_errors",
Parameter.REQUIRED,
Boolean.FALSE);
/** Double Click Protection, enabled by default for all buttons in a form.*/
private final Parameter m_dcpOnButtons = new BooleanParameter
("waf.bebop.dcp_on_buttons", Parameter.REQUIRED, Boolean.TRUE);
/** Double Click Protection, disabled by default for all links. */
private final Parameter m_dcpOnLinks = new BooleanParameter
("waf.bebop.dcp_on_links", Parameter.REQUIRED, Boolean.FALSE);
/**
*
*/
private final Parameter m_enableTreeSelect = new BooleanParameter
("waf.bebop.enable_tree_select_attribute",
Parameter.REQUIRED,
Boolean.FALSE);
/** List of supported DHTML editors, first one is default (Xinha) */
private final EnumerationParameter m_dhtmlEditor;
/** Path to DHTML editor source file, relativ to document root */
private final Parameter m_dhtmlEditorSrcFile;
/** */
private final Parameter m_showClassName = new BooleanParameter
("waf.bebop.show_class_name", Parameter.OPTIONAL, Boolean.FALSE);
/**
* Constructor.
* Singelton pattern, don't instantiate a config object using the
* constructor directly! Use getConfig() instead.
*
*/
public BebopConfig() {
/** List of supported DHTML editors, first one is default (Xinha) */
m_dhtmlEditor = new EnumerationParameter("waf.bebop.dhtml_editor",
Parameter.REQUIRED,BebopConstants.BEBOP_XINHAEDITOR);
m_dhtmlEditor.put("Xinha", BebopConstants.BEBOP_XINHAEDITOR);
m_dhtmlEditor.put("FCKeditor", BebopConstants.BEBOP_FCKEDITOR);
// HTMLArea for backwards compatibility with old XSL. to be removed soon!
m_dhtmlEditor.put("HTMLArea", BebopConstants.BEBOP_DHTMLEDITOR);
// Xinha is now default!
m_dhtmlEditorSrcFile = new StringParameter
("waf.bebop.dhtml_editor_src", Parameter.REQUIRED,
"/assets/xinha/XinhaLoader.js");
register(m_presenter);
register(m_page);
register(m_tidy);
register(m_fancyErrors);
register(m_dhtmlEditor);
register(m_dhtmlEditorSrcFile);
register(m_dcpOnButtons);
register(m_dcpOnLinks);
register(m_enableTreeSelect);
register(m_showClassName);
loadInfo();
public void setPresenterClassName(final String presenterClassName) {
this.presenterClassName = presenterClassName;
}
/**
* Gets the configured <code>PresentationManger</code>.
*/
public final PresentationManager getPresentationManager() {
return (PresentationManager) get(m_presenter);
public void setPresenterClass(
final Class<PresentationManager> presenterClass) {
setPresenterClassName(presenterClass.getName());
}
final Class getBasePageClass() {
return (Class) get(m_page);
public String getBasePageClassName() {
return basePageClassName;
}
/**
* I don't *want* to make this public. XXX
*/
public final String getTidyConfigFile() {
return (String) get(m_tidy);
public Class<BasePage> getBasePageClass() {
try {
return (Class<BasePage>)Class.forName(basePageClassName);
} catch (ClassNotFoundException ex) {
throw new UncheckedWrapperException(ex);
}
}
public boolean wantFancyXSLErrors() {
return ((Boolean)get(m_fancyErrors)).booleanValue();
public void setBasePageClassName(final String basePageClassName) {
this.basePageClassName = basePageClassName;
}
public final boolean doubleClickProtectionOnButtons() {
return ((Boolean) get(m_dcpOnButtons)).booleanValue();
public void setBasePageClass(final Class<BasePage> basePageClass) {
setBasePageClassName(basePageClass.getName());
}
public final boolean doubleClickProtectionOnLinks() {
return ((Boolean) get(m_dcpOnLinks)).booleanValue();
public String getTidyConfigFile() {
return tidyConfigFile;
}
public final boolean treeSelectAttributeEnabled() {
return ((Boolean) get(m_enableTreeSelect)).booleanValue();
public void setTidyConfigFile(final String tidyConfigFile) {
this.tidyConfigFile = tidyConfigFile;
}
/**
* Gets the DHTML editor to use
*/
public final String getDHTMLEditor() {
return (String) get(m_dhtmlEditor);
public Boolean getFancyErrors() {
return fancyErrors;
}
/**
* Gets the location of DHTML editor's source file
*/
public final String getDHTMLEditorSrcFile() {
return (String) get(m_dhtmlEditorSrcFile);
public void setFancyErrors(final Boolean fancyErrors) {
this.fancyErrors = fancyErrors;
}
public final boolean showClassName() {
return ((Boolean) get(m_showClassName)).booleanValue();
public Boolean getDcpOnButtons() {
return dcpOnButtons;
}
public void setDcpOnButtons(final Boolean dcpOnButtons) {
this.dcpOnButtons = dcpOnButtons;
}
public Boolean getDcpOnLinks() {
return dcpOnLinks;
}
public void setDcpOnLinks(final Boolean dcpOnLinks) {
this.dcpOnLinks = dcpOnLinks;
}
public Boolean isTreeSelectEnabled() {
return treeSelectEnabled;
}
public void setTreeSelectEnabled(final Boolean treeSelectEnabled) {
this.treeSelectEnabled = treeSelectEnabled;
}
public Set<String> getDhtmlEditors() {
return new HashSet<>(dhtmlEditors);
}
public void setDhtmlEditors(final Set<String> dhtmlEditors) {
this.dhtmlEditors = dhtmlEditors;
}
public String getDefaultDhtmlEditor() {
return defaultDhtmlEditor;
}
public void setDefaultDhtmlEditor(final String defaultDhtmlEditor) {
this.defaultDhtmlEditor = defaultDhtmlEditor;
}
public String getDhtmlEditorSrcFile() {
return dhtmlEditorSrcFile;
}
public void setDhtmlEditorSrcFile(final String dhtmlEditorSrcFile) {
this.dhtmlEditorSrcFile = dhtmlEditorSrcFile;
}
public Boolean getShowClassName() {
return showClassName;
}
public void setShowClassName(final Boolean showClassName) {
this.showClassName = showClassName;
}
@Override
public int hashCode() {
int hash = 7;
hash = 89 * hash + Objects.hashCode(tidyConfigFile);
hash = 89 * hash + Objects.hashCode(fancyErrors);
hash = 89 * hash + Objects.hashCode(dcpOnButtons);
hash = 89 * hash + Objects.hashCode(dcpOnLinks);
hash = 89 * hash + Objects.hashCode(treeSelectEnabled);
hash = 89 * hash + Objects.hashCode(dhtmlEditors);
hash = 89 * hash + Objects.hashCode(defaultDhtmlEditor);
hash = 89 * hash + Objects.hashCode(dhtmlEditorSrcFile);
hash = 89 * hash + Objects.hashCode(showClassName);
return hash;
}
@Override
public boolean equals(final Object obj) {
if (this == obj) {
return true;
}
if (obj == null) {
return false;
}
if (!(obj instanceof BebopConfig)) {
return false;
}
final BebopConfig other = (BebopConfig) obj;
if (!Objects.equals(tidyConfigFile, other.getTidyConfigFile())) {
return false;
}
if (!Objects.equals(defaultDhtmlEditor, other.getDefaultDhtmlEditor())) {
return false;
}
if (!Objects.equals(dhtmlEditorSrcFile, other.getDhtmlEditorSrcFile())) {
return false;
}
if (!Objects.equals(fancyErrors, other.getFancyErrors())) {
return false;
}
if (!Objects.equals(dcpOnButtons, other.getDcpOnButtons())) {
return false;
}
if (!Objects.equals(dcpOnLinks, other.getDcpOnLinks())) {
return false;
}
if (!Objects.equals(treeSelectEnabled, other.isTreeSelectEnabled())) {
return false;
}
if (!Objects.equals(dhtmlEditors, other.getDhtmlEditors())) {
return false;
}
return Objects.equals(showClassName, other.getShowClassName());
}
@Override
public String toString() {
final StringJoiner joiner = new StringJoiner(", ");
dhtmlEditors.forEach(s -> joiner.add(s));
return String.format("%s{ "
+ "tidyConfigFile = %s, "
+ "fancyErrors = %b, "
+ "dcpOnButtons = %b, "
+ "dcpOnLinks = %b, "
+ "treeSelectEnabled = %b, "
+ "dhtmlEditors = { %s }, "
+ "defaultDhtmlEditor = %s, "
+ "dhtmlEditorSrcFile = %s, "
+ "showClassName = %b"
+ " }",
super.toString(),
tidyConfigFile,
fancyErrors,
dcpOnButtons,
dcpOnLinks,
treeSelectEnabled,
joiner.toString(),
defaultDhtmlEditor,
dhtmlEditorSrcFile,
showClassName);
}
}

View File

@ -170,7 +170,7 @@ public class PageFactory {
if (initialized) {
return;
}
setPageClass(Bebop.getConfig().getBasePageClass());
setPageClass(BebopConfig.getConfig().getBasePageClass());
}
/**

View File

@ -295,7 +295,7 @@ public class SimpleComponent extends Completable
m_attr.exportAttributes(target);
}
if (KernelConfig.getConfig().isDebugEnabled() ||
Bebop.getConfig().showClassName()) {
BebopConfig.getConfig().getShowClassName()) {
target.addAttribute("bebop:classname", getClass().getName(),
BEBOP_XML_NS);
}

View File

@ -62,7 +62,7 @@ public class Tree extends SimpleComponent implements Resettable {
Logger.getLogger(Tree.class);
private static final boolean s_selectAttributeEnabled =
Bebop.getConfig().treeSelectAttributeEnabled();
BebopConfig.getConfig().isTreeSelectEnabled();
// Any node id in the currentState is equivalent
// to that node being expanded. If node id is

View File

@ -22,7 +22,7 @@ import java.util.HashSet;
import java.util.Iterator;
import java.util.Set;
import com.arsdigita.bebop.Bebop;
import com.arsdigita.bebop.BebopConfig;
import com.arsdigita.bebop.PageState;
import com.arsdigita.bebop.parameters.ParameterModel;
import com.arsdigita.bebop.parameters.StringParameter;
@ -182,12 +182,13 @@ public class DHTMLEditor extends TextArea {
}
public String getEditorURL() {
return Bebop.getConfig().getDHTMLEditorSrcFile().substring(
0, Bebop.getConfig().getDHTMLEditorSrcFile().lastIndexOf("/") + 1);
return BebopConfig.getConfig().getDhtmlEditorSrcFile().substring(
0,
BebopConfig.getConfig().getDhtmlEditorSrcFile().lastIndexOf("/") + 1);
}
public String getEditorSrc() {
return Bebop.getConfig().getDHTMLEditorSrcFile();
return BebopConfig.getConfig().getDhtmlEditorSrcFile();
}
/**
@ -264,7 +265,7 @@ public class DHTMLEditor extends TextArea {
*/
@Override
protected String getElementTag() {
return Bebop.getConfig().getDHTMLEditor();
return BebopConfig.getConfig().getDefaultDhtmlEditor();
}
/**

View File

@ -18,7 +18,7 @@
*/
package com.arsdigita.bebop.page;
import com.arsdigita.bebop.Bebop;
import com.arsdigita.bebop.BebopConfig;
import com.arsdigita.dispatcher.DispatcherHelper;
import com.arsdigita.globalization.Globalization;
import com.arsdigita.globalization.GlobalizationHelper;
@ -84,199 +84,199 @@ public class PageTransformer implements PresentationManager {
registerXSLParameterGenerator("contextPath",
new XSLParameterGenerator() {
@Override
public String generateValue(
HttpServletRequest request) {
return request
.getContextPath();
}
@Override
public String generateValue(
HttpServletRequest request) {
return request
.getContextPath();
}
});
});
registerXSLParameterGenerator("root-context-prefix",
new XSLParameterGenerator() {
@Override
public String generateValue(
HttpServletRequest request) {
return Web.getConfig()
.getDispatcherContextPath();
}
@Override
public String generateValue(
HttpServletRequest request) {
return Web.getConfig()
.getDispatcherContextPath();
}
});
});
registerXSLParameterGenerator("context-prefix",
new XSLParameterGenerator() {
@Override
public String generateValue(
HttpServletRequest request) {
return Web.getWebContext()
.getRequestURL()
.getContextPath();
}
@Override
public String generateValue(
HttpServletRequest request) {
return Web.getWebContext()
.getRequestURL()
.getContextPath();
}
});
});
registerXSLParameterGenerator("internal-theme",
new XSLParameterGenerator() {
@Override
public String generateValue(
HttpServletRequest request) {
return Web.getWebContext()
.getRequestURL()
.getContextPath()
+ com.arsdigita.web.URL.INTERNAL_THEME_DIR;
}
@Override
public String generateValue(
HttpServletRequest request) {
return Web.getWebContext()
.getRequestURL()
.getContextPath()
+ com.arsdigita.web.URL.INTERNAL_THEME_DIR;
}
});
});
registerXSLParameterGenerator("dispatcher-prefix",
new XSLParameterGenerator() {
@Override
public String generateValue(
HttpServletRequest request) {
return com.arsdigita.web.URL
.getDispatcherPath();
}
@Override
public String generateValue(
HttpServletRequest request) {
return com.arsdigita.web.URL
.getDispatcherPath();
}
});
});
registerXSLParameterGenerator("dcp-on-buttons",
new XSLParameterGenerator() {
@Override
public String generateValue(
HttpServletRequest request) {
if (Bebop.getConfig()
.doubleClickProtectionOnButtons()) {
return "true";
} else {
return null;
}
@Override
public String generateValue(
HttpServletRequest request) {
if (BebopConfig.getConfig()
.getDcpOnButtons()) {
return "true";
} else {
return null;
}
}
}
});
});
registerXSLParameterGenerator("dcp-on-links",
new XSLParameterGenerator() {
@Override
public String generateValue(
HttpServletRequest request) {
if (Bebop.getConfig()
.doubleClickProtectionOnLinks()) {
return "true";
} else {
return null;
}
@Override
public String generateValue(
HttpServletRequest request) {
if (BebopConfig.getConfig()
.getDcpOnLinks()) {
return "true";
} else {
return null;
}
}
}
});
});
registerXSLParameterGenerator("user-agent",
new XSLParameterGenerator() {
@Override
public String generateValue(
HttpServletRequest request) {
return request.getHeader(
"User-Agent");
}
@Override
public String generateValue(
HttpServletRequest request) {
return request.getHeader(
"User-Agent");
}
});
});
registerXSLParameterGenerator("negotiated-language",
new XSLParameterGenerator() {
@Override
public String generateValue(
HttpServletRequest request) {
return GlobalizationHelper
.getNegotiatedLocale()
.getLanguage();
}
@Override
public String generateValue(
HttpServletRequest request) {
return GlobalizationHelper
.getNegotiatedLocale()
.getLanguage();
}
});
});
registerXSLParameterGenerator("selected-language",
new XSLParameterGenerator() {
@Override
public String generateValue(
HttpServletRequest request) {
Locale selectedLocale
= com.arsdigita.globalization.GlobalizationHelper
.getSelectedLocale(request);
return (selectedLocale != null)
? selectedLocale
.toString() : "";
}
@Override
public String generateValue(
HttpServletRequest request) {
Locale selectedLocale
= com.arsdigita.globalization.GlobalizationHelper.
getSelectedLocale(request);
return (selectedLocale != null)
? selectedLocale
.toString() : "";
}
});
});
registerXSLParameterGenerator("request-scheme",
new XSLParameterGenerator() {
@Override
public String generateValue(
HttpServletRequest request) {
return request.getScheme();
}
@Override
public String generateValue(
HttpServletRequest request) {
return request.getScheme();
}
});
});
registerXSLParameterGenerator("server-name",
new XSLParameterGenerator() {
@Override
public String generateValue(
HttpServletRequest request) {
return request.getServerName();
}
@Override
public String generateValue(
HttpServletRequest request) {
return request.getServerName();
}
});
});
registerXSLParameterGenerator("server-port",
new XSLParameterGenerator() {
@Override
public String generateValue(
HttpServletRequest request) {
return Integer.toString(
request.getServerPort());
}
@Override
public String generateValue(
HttpServletRequest request) {
return Integer.toString(
request.getServerPort());
}
});
});
registerXSLParameterGenerator("host",
new XSLParameterGenerator() {
@Override
public String generateValue(
HttpServletRequest request) {
if (request.getServerPort()
== 80) {
return String.format(
"%s://%s", request
.getScheme(), request
.getServerName());
} else {
return String.format(
"%s://%s:%d",
request.getScheme(),
request
.getServerName(),
request
.getServerPort());
}
}
@Override
public String generateValue(
HttpServletRequest request) {
if (request.getServerPort()
== 80) {
return String.format(
"%s://%s", request
.getScheme(), request
.getServerName());
} else {
return String.format(
"%s://%s:%d",
request.getScheme(),
request
.getServerName(),
request
.getServerPort());
}
}
});
});
s_log.debug("Static initalizer finished.");
}
@ -343,7 +343,7 @@ public class PageTransformer implements PresentationManager {
try {
return new PrintWriter(new OutputStreamWriter(resp.
getOutputStream(),
getOutputStream(),
charset));
} catch (IOException ex) {
throw new UncheckedWrapperException(ex);
@ -372,11 +372,11 @@ public class PageTransformer implements PresentationManager {
* always be passed to XSLT, which is the value of
* <code>req.getWebContextPath()</code>.
*
* @param doc the Bebop page to serve
* @param req the servlet request
* @param resp the servlet response
* @param doc the Bebop page to serve
* @param req the servlet request
* @param resp the servlet response
* @param params a set of name-value pairs to pass as parameters to the
* Transformer
* Transformer
*/
public void servePage(final Document doc,
final HttpServletRequest req,
@ -393,24 +393,24 @@ public class PageTransformer implements PresentationManager {
try {
final String charset = Globalization
.getDefaultCharset(DispatcherHelper.getNegotiatedLocale());
.getDefaultCharset(DispatcherHelper.getNegotiatedLocale());
final String output = req.getParameter("output");
s_log.info("output=" + output);
if (output == null) {
boolean fancyErrors = Bebop.getConfig().wantFancyXSLErrors()
|| Boolean.TRUE.equals(req
.getAttribute(
FANCY_ERRORS));
boolean fancyErrors
= BebopConfig.getConfig().getFancyErrors()
|| Boolean.TRUE.equals(req.getAttribute(
FANCY_ERRORS));
// Get the stylesheet transformer object corresponding to the
// current request.
final XSLTemplate template = Templating.getTemplate(
req,
fancyErrors,
!Boolean.TRUE.equals(req.getAttribute(CACHE_XSL_NONE)));
req,
fancyErrors,
!Boolean.TRUE.equals(req.getAttribute(CACHE_XSL_NONE)));
final PrintWriter writer = getWriter(resp, "text/html", charset);
@ -450,15 +450,15 @@ public class PageTransformer implements PresentationManager {
new StreamResult(writer));
} catch (TransformerException ex) {
throw new UncheckedWrapperException(
"cannot transform document", ex);
"cannot transform document", ex);
}
// copy and paste from BasePresentationManager
if (KernelConfig.getConfig().isDebugEnabled()) {
Document origDoc = (Document) req.getAttribute(
"com.arsdigita.xml.Document");
"com.arsdigita.xml.Document");
Debugger.addDebugger(new TransformationDebugger(template.
getSource(), template.getDependents()));
getSource(), template.getDependents()));
writer.print(Debugger.getDebugging(req));
}
@ -478,11 +478,11 @@ public class PageTransformer implements PresentationManager {
// current request.
template = Templating.getTemplate(req,
Boolean.TRUE.equals(req
.getAttribute(
PageTransformer.FANCY_ERRORS)),
.getAttribute(
PageTransformer.FANCY_ERRORS)),
!Boolean.TRUE.equals(req
.getAttribute(
PageTransformer.CACHE_XSL_NONE)));
.getAttribute(
PageTransformer.CACHE_XSL_NONE)));
endTransaction(req);
} finally {
}
@ -490,7 +490,7 @@ public class PageTransformer implements PresentationManager {
try {
Date now = new Date();
SimpleDateFormat fmt = new SimpleDateFormat(
"yyyy-MM-dd-HH-mm");
"yyyy-MM-dd-HH-mm");
String prefix = "waf-xsl-" + fmt.format(now);
final OutputStream os = resp.getOutputStream();
@ -509,7 +509,7 @@ public class PageTransformer implements PresentationManager {
}
} else {
throw new IllegalStateException(output
+ " is an unknown output");
+ " is an unknown output");
}
} finally {
}
@ -524,9 +524,9 @@ public class PageTransformer implements PresentationManager {
private void endTransaction(final HttpServletRequest req) {
// There is no longer any need for a database handle.
if (req.getAttribute(PageContext.EXCEPTION) == null) {
} else {
}
}
@ -577,7 +577,7 @@ public class PageTransformer implements PresentationManager {
HttpServletRequest request) {
XSLParameterGenerator generator
= (XSLParameterGenerator) s_XSLParameters
.get(name);
.get(name);
if (generator != null) {
return generator.generateValue(request);
} else {
@ -600,7 +600,7 @@ public class PageTransformer implements PresentationManager {
final Map.Entry entry = (Map.Entry) entries.next();
String value = ((XSLParameterGenerator) entry.getValue()).
generateValue(request);
generateValue(request);
if (value == null) {
// XSL does not like nulls
value = "";

View File

@ -18,7 +18,7 @@
*/
package com.arsdigita.bebop.parameters;
import com.arsdigita.bebop.Bebop;
import com.arsdigita.bebop.BebopConfig;
import com.arsdigita.bebop.event.ParameterEvent;
import com.arsdigita.bebop.event.ParameterListener;
import com.arsdigita.util.StringUtils;
@ -102,7 +102,7 @@ public class TidyHTMLValidationListener implements ParameterListener {
private static Properties getJTidyProperties() {
if (s_tidyProperties == null) {
s_tidyProperties = new LockableProperties();
String path = Bebop.getConfig().getTidyConfigFile();
String path = BebopConfig.getConfig().getTidyConfigFile();
InputStream is = TidyHTMLValidationListener.class.getClassLoader
().getResourceAsStream(path);

View File

@ -17,7 +17,7 @@
*/
package com.arsdigita.templating;
import com.arsdigita.bebop.Bebop;
import com.arsdigita.bebop.BebopConfig;
import com.arsdigita.kernel.KernelConfig;
import com.arsdigita.util.Assert;
import com.arsdigita.util.ExceptionUnwrapper;
@ -49,8 +49,8 @@ import org.apache.log4j.Logger;
* An entry-point class for the functions of the templating package. The class
* manages access to all theme files (XSL as well as css, pirctures, etc).
*
* This class maintains a cache of <code>XSLTemplate</code> objects, managed
* via the <code>getTemplate</code> and <code>purgeTemplate</code> methods.
* This class maintains a cache of <code>XSLTemplate</code> objects, managed via
* the <code>getTemplate</code> and <code>purgeTemplate</code> methods.
*
* @author Dan Berrange
* @author Justin Ross &lt;jross@redhat.com&gt;
@ -58,21 +58,26 @@ import org.apache.log4j.Logger;
*/
public class Templating {
/** Internal logger instance to faciliate debugging. Enable logging output
* by editing /WEB-INF/conf/log4j.properties int hte runtime environment
* and set com.arsdigita.templating.Templating=DEBUG by uncommenting it
* or adding the line. */
/**
* Internal logger instance to faciliate debugging. Enable logging output by
* editing /WEB-INF/conf/log4j.properties int hte runtime environment and
* set com.arsdigita.templating.Templating=DEBUG by uncommenting it or
* adding the line.
*/
private static final Logger s_log = Logger.getLogger(Templating.class);
/** This is the name of the attribute that is set in the request whose
* value, if present, is a collection of TransformerExceptions that
* can be used to produce a "pretty" error. */
/**
* This is the name of the attribute that is set in the request whose value,
* if present, is a collection of TransformerExceptions that can be used to
* produce a "pretty" error.
*/
public static final String FANCY_ERROR_COLLECTION = "fancyErrorCollection";
/** Config object containing various parameter */
/**
* Config object containing various parameter
*/
private static final TemplatingConfig s_config = TemplatingConfig
.getInstanceOf();
.getInstanceOf();
static {
s_log.debug("Static initalizer starting...");
@ -81,15 +86,14 @@ public class Templating {
TransformerException.class,
new ExceptionUnwrapper() {
@Override
public Throwable unwrap(Throwable t) {
TransformerException ex = (TransformerException) t;
return ex.getCause();
}
});
@Override
public Throwable unwrap(Throwable t) {
TransformerException ex = (TransformerException) t;
return ex.getCause();
}
});
// now we initiate the CacheTable here
// default cache size used to be 50, which is too high I reckon,
// each template can eat up to 4 megs
Integer setting = s_config.getCacheSize();
@ -112,17 +116,16 @@ public class Templating {
/**
* Returns a new instance of the current presentation manager class. This is
* an object which has the
* {@link com.arsdigita.templating.PresentationManager PresentationManager}
* interface which can be used to transform an XML document into an output
* an object which has the
* {@link com.arsdigita.templating.PresentationManager PresentationManager}
* interface which can be used to transform an XML document into an output
* stream.
*
* As of version 6.6.0 the bebop framework is the only instance to provide
* an implementation. To avoid class hierachie kludge we directly return the
* bebop config here.
*
* @return an instance of the <code>PresentationManager</code>
* interface
* @return an instance of the <code>PresentationManager</code> interface
*/
/* NON Javadoc
* Used to be deprecated up to version 6.6.0. Reverted to non-deprecated.
@ -134,17 +137,22 @@ public class Templating {
* instead.
*/
public static PresentationManager getPresentationManager() {
return Bebop.getConfig().getPresentationManager();
try {
return (PresentationManager) BebopConfig.getConfig().
getPresenterClass().newInstance();
} catch (IllegalAccessException | InstantiationException ex) {
throw new UncheckedWrapperException(ex);
}
}
/**
* Retrieves an XSL template. If the template is already loaded in the
* cache, it will be returned. If the template has been modified since
* it was first generated, it will be regenerated first.
* cache, it will be returned. If the template has been modified since it
* was first generated, it will be regenerated first.
*
* @param source the <code>URL</code> to the top-level template resource
* @param source the <code>URL</code> to the top-level template resource
* @return an <code>XSLTemplate</code> instance representing
* <code>source</code>
* <code>source</code>
*/
public static synchronized XSLTemplate getTemplate(final URL source) {
return getTemplate(source, false, true);
@ -152,19 +160,18 @@ public class Templating {
/**
* Retrieves an XSL template. If the template is already loaded in the
* cache, it will be returned. If the template has been modified since
* it was first generated, it will be regenerated first.
* cache, it will be returned. If the template has been modified since it
* was first generated, it will be regenerated first.
*
* @param source the <code>URL</code> to the top-level template resource
* @param fancyErrors Should this place any xsl errors in the request
* for use by another class. If this is true, the
* the errors are stored for later use.
* @param useCache Should the templates be pulled from cache, if available?
* True means they are pulled from cache. False means
* they are pulled from the disk. If this is false
* the pages are also not placed in the cache.
* @param source the <code>URL</code> to the top-level template resource
* @param fancyErrors Should this place any xsl errors in the request for
* use by another class. If this is true, the the errors are stored for
* later use.
* @param useCache Should the templates be pulled from cache, if available?
* True means they are pulled from cache. False means they are pulled from
* the disk. If this is false the pages are also not placed in the cache.
* @return an <code>XSLTemplate</code> instance representing
* <code>source</code>
* <code>source</code>
*/
public static synchronized XSLTemplate getTemplate(final URL source,
boolean fancyErrors,
@ -177,11 +184,11 @@ public class Templating {
Assert.exists(source, URL.class);
XSLTemplate template = null;
if (template == null) {
if (s_log.isInfoEnabled()) {
s_log.info("The template for URL " + source + " is not "
+ "cached; creating and caching it now");
+ "cached; creating and caching it now");
}
if (fancyErrors) {
@ -194,14 +201,14 @@ public class Templating {
}
} else if (KernelConfig.getConfig().isDebugEnabled()
&& template.isModified()) {
&& template.isModified()) {
// XXX referencing Kernel above is a broken dependency.
// Debug mode should be captured at a lower level,
// probably on UtilConfig.
if (s_log.isInfoEnabled()) {
s_log.info("Template " + template + " has been modified; "
+ "recreating it from scratch");
+ "recreating it from scratch");
}
if (fancyErrors) {
@ -220,7 +227,7 @@ public class Templating {
/**
* Resolves and retrieves the template for the given request.
*
* @param sreq The current request object
* @param sreq The current request object
* @return The resolved <code>XSLTemplate</code> instance
*/
public static XSLTemplate getTemplate(final HttpServletRequest sreq) {
@ -231,13 +238,12 @@ public class Templating {
* Resolves the template for the given request to an URL.
*
* @param sreq The current request object
* @param fancyErrors Should this place any xsl errors in the request
* for use by another class. If this is true, the
* the errors are stored for later use.
* @param fancyErrors Should this place any xsl errors in the request for
* use by another class. If this is true, the the errors are stored for
* later use.
* @param useCache Should the templates be pulled from cache, if available?
* True means they are pulled from cache. False means
* they are pulled from the disk. If this is false
* the pages are also not placed in the cache.
* True means they are pulled from cache. False means they are pulled from
* the disk. If this is false the pages are also not placed in the cache.
* @return The resolved <code>XSLTemplate</code> instance
*/
public static XSLTemplate getTemplate(final HttpServletRequest sreq,
@ -253,12 +259,10 @@ public class Templating {
}
/**
* Removes an XSL template from the internal cache. The template
* for <code>source</code> will be regenerated on the next request
* for it.
* Removes an XSL template from the internal cache. The template for
* <code>source</code> will be regenerated on the next request for it.
*
* @param source the <code>URL</code> to the top-level template
* resource
* @param source the <code>URL</code> to the top-level template resource
*/
public static synchronized void purgeTemplate(final URL source) {
if (s_log.isDebugEnabled()) {
@ -269,8 +273,8 @@ public class Templating {
}
/**
* Removes all cached template objects. All template objects will
* be regenerated on-demand as each gets requested.
* Removes all cached template objects. All template objects will be
* regenerated on-demand as each gets requested.
*/
public static synchronized void purgeTemplates() {
if (s_log.isDebugEnabled()) {
@ -318,14 +322,14 @@ public class Templating {
}
/**
* Transforms an URL, that refers to a local resource inside the running
* CCM web application. NON-local URLs remain unmodified.
*
* In case of a virtual path "/resource" it is short-circuiting access to
* the resource servlet. All other http:// URLs are transformed into file://
* for XSLT validation to work for these resources. It has the added benefit
* Transforms an URL, that refers to a local resource inside the running CCM
* web application. NON-local URLs remain unmodified.
*
* In case of a virtual path "/resource" it is short-circuiting access to
* the resource servlet. All other http:// URLs are transformed into file://
* for XSLT validation to work for these resources. It has the added benefit
* of speeding up loading of XSL...
*
*
* Currently the direct file access method is perferred! As soon as we
* refactor to directly access the published XSL files in the database and
* to avoid the unnecessary intermediate step via the file system, we have
@ -335,19 +339,21 @@ public class Templating {
static URL transformURL(URL url) {
HttpHost self = Web.getConfig().getHost();
/** Indicates whether url refers to a local resource inside the
* running CCM web application (inside it's webapp context) */
/**
* Indicates whether url refers to a local resource inside the running
* CCM web application (inside it's webapp context)
*/
Boolean isLocal = false;
/** Contains the transformed "localized" path to url, i.e. without
* host part. */
/**
* Contains the transformed "localized" path to url, i.e. without host
* part.
*/
String localPath = "";
// Check if the url refers to our own host
if (self.getName().equals(url.getHost())
&& ( (self.getPort() == url.getPort())
|| (url.getPort()== -1 && self.getPort()== 80)
)
) {
if (self.getName().equals(url.getHost())
&& ((self.getPort() == url.getPort())
|| (url.getPort() == -1 && self.getPort() == 80))) {
// host part denotes to a local resource, cut off host part.
localPath = url.getPath();
isLocal = true;
@ -365,17 +371,16 @@ public class Templating {
s_log.debug("Installation context is >" + installContext + "<.");
}
if (!installContext.equals("")) {
// CCM is installed into a non-ROOT context
if (localPath.startsWith(installContext)) {
// remove webapp context part
localPath = localPath.substring(installContext.length());
if (s_log.isDebugEnabled()) {
s_log.debug("WebApp context removed: >>" +
localPath + "<<");
}
// CCM is installed into a non-ROOT context
if (localPath.startsWith(installContext)) {
// remove webapp context part
localPath = localPath.substring(installContext.length());
if (s_log.isDebugEnabled()) {
s_log.debug("WebApp context removed: >>" + localPath + "<<");
}
}
}
if (isLocal) {
// url specifies the running CCM host and port (or port isn't
// specified in url and default for running CCM host
@ -385,52 +390,50 @@ public class Templating {
localPath = localPath.substring("/resource".length()); //remove virtual part
URL newURL = Web.findResource(localPath); //without host part here!
if (s_log.isDebugEnabled()) {
s_log.debug("Transforming resource " + url + " to " + newURL);
s_log.
debug("Transforming resource " + url + " to "
+ newURL);
}
return newURL;
} else {
// A real path to disk
final String filename = Web.getServletContext()
.getRealPath(localPath);
.getRealPath(localPath);
File file = new File(filename);
if (file.exists()) {
try {
URL newURL = file.toURL();
if (s_log.isDebugEnabled()) {
s_log.debug("Transforming resource " + url + " to "
+ newURL);
+ newURL);
}
return newURL;
} catch (MalformedURLException ex) {
throw new UncheckedWrapperException(ex);
}
} else {
if (s_log.isDebugEnabled()) {
s_log.debug("File " + filename
+ " doesn't exist on disk");
}
} else if (s_log.isDebugEnabled()) {
s_log.debug("File " + filename
+ " doesn't exist on disk");
}
}
} else {
// url is not the (local) running CCM host, no transformation
// is done
if (s_log.isDebugEnabled()) {
} else // url is not the (local) running CCM host, no transformation
// is done
if (s_log.isDebugEnabled()) {
s_log.debug("URL " + url + " is not local");
}
}
return url; // returns the original, unmodified url here
}
}
/**
*
*
* @author pb
*/
class LoggingErrorListener implements ErrorListener {
private static final Logger s_log =
Logger.getLogger(LoggingErrorListener.class);
private static final Logger s_log
= Logger.getLogger(LoggingErrorListener.class);
private final ArrayList m_errors;
LoggingErrorListener() {
@ -458,7 +461,8 @@ class LoggingErrorListener implements ErrorListener {
private void log(Level level, TransformerException ex) {
s_log.log(level, "Transformer " + level + ": "
+ ex.getLocationAsString() + ": " + ex.getMessage(),
+ ex.getLocationAsString() + ": " + ex.
getMessage(),
ex);
m_errors.add(ex);
}

View File

@ -0,0 +1,30 @@
# Copyright (C) 2016 LibreCCM Foundation.
#
# This library is free software; you can redistribute it and/or
# modify it under the terms of the GNU Lesser General Public
# License as published by the Free Software Foundation; either
# version 2.1 of the License, or (at your option) any later version.
#
# This library is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
# Lesser General Public License for more details.
#
# You should have received a copy of the GNU Lesser General Public
# License along with this library; if not, write to the Free Software
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
# MA 02110-1301 USA
bebop.config.description = Several configuration options for Bebop
bebop.config.presenter_class_name = Determines what implementation of PresentationManager is used to style Bebop pages
bebop.config.base_page_name = Determines what implementation of BasePage is used to serve Bebop pages
bebop.config.tidy_config_file = Points to the configuration file for the JTidy parameter validation listener
bebop.config.fancy_errors = Always display fancy XSL error pages
bebop.config.dcp_on_buttons = Specify whether to apply javascript double click protection to form submits
bebop.config.dcp_on_links = Specify whether to apply javascript double click protection to anchor elements
bebop.config.tree_select_enabled = Specify whether to turn on isSelected XML attribute on bebop.Tree nodes (performance impact)
bebop.config.dhtml_editors = Lists of all available DHTML text input widgets
bebop.config.default_dhtml_editor = Select which DHTML text input widget is used for DHTMLEditor Bebop component.
bebop.config.dhtml_editor_srcfile = Relative path to the source javascript file
bebop.config.show_class_name =

View File

@ -1,44 +0,0 @@
waf.bebop.base_page.title=Bebop base page class
waf.bebop.base_page.purpose=Determines what implementation of BasePage is used to serve Bebop pages
waf.bebop.base_page.example=com.arsdigita.ui.SimplePage
waf.bebop.base_page.format=[classname]
waf.bebop.presentation_manager.title=Bebop presentation manager class
waf.bebop.presentation_manager.purpose=Determines what implementation of PresentationManager is used to style Bebop pages
waf.bebop.presentation_manager.example=com.arsdigita.bebop.page.PageTransformer
waf.bebop.presentation_manager.format=[classname]
waf.bebop.tidy_config_file.title=JTidy validation listener config file
waf.bebop.tidy_config_file.purpose=Points to the configuration file for the JTidy parameter validation listener
waf.bebop.tidy_config_file.example=com/arsdigita/bebop/parameters/tidy.properties
waf.bebop.tidy_config_file.format=[string]
waf.bebop.fancy_xsl_errors.title=Fancy XSL errors
waf.bebop.fancy_xsl_errors.purpose=Always display fancy XSL error pages
waf.bebop.fancy_xsl_errors.example=true|false
waf.bebop.fancy_xsl_errors.format=[boolean]
waf.bebop.dcp_on_buttons.title=Double Click protection for buttons
waf.bebop.dcp_on_buttons.purpose=Specify whether to apply javascript double click protection to form submits
waf.bebop.dcp_on_buttons.example=true|false
waf.bebop.dcp_on_buttons.format=[boolean]
waf.bebop.dcp_on_links.title=Double Click protection for links
waf.bebop.dcp_on_links.purpose=Specify whether to apply javascript double click protection to anchor elements
waf.bebop.dcp_on_links.example=true|false
waf.bebop.dcp_on_links.format=[boolean]
waf.bebop.dhtml_editor.title=DHTML editor implementation
waf.bebop.dhtml_editor.purpose=Select which DHTML text input widget is used for DHTMLEditor Bebop component.
waf.bebop.dhtml_editor.example=FCKeditor
waf.bebop.dhtml_editor.format=Xinha|FCKeditor|HTMLArea
waf.bebop.dhtml_editor_src.title=Relative path to the source javascript file
waf.bebop.dhtml_editor_src.purpose=Relative path to the source javascript file
waf.bebop.dhtml_editor_src.example=/assets/xinha/XinhaLoader.js
waf.bebop.dhtml_editor_src.format=[String]
waf.bebop.enable_tree_select_attribute.title=isSelected attribute for bebop.Tree nodes
waf.bebop.enable_tree_select_attribute.purpose=Specify whether to turn on isSelected XML attribute on bebop.Tree nodes (performance impact)
waf.bebop.enable_tree_select_attribute.example=true|false
waf.bebop.enable_tree_select_attribute.format=[boolean]