001: /*
002: * Copyright 2001-2006 C:1 Financial Services GmbH
003: *
004: * This software is free software; you can redistribute it and/or
005: * modify it under the terms of the GNU Lesser General Public
006: * License Version 2.1, as published by the Free Software Foundation.
007: *
008: * This software is distributed in the hope that it will be useful,
009: * but WITHOUT ANY WARRANTY; without even the implied warranty of
010: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
011: * Lesser General Public License for more details.
012: *
013: * You should have received a copy of the GNU Lesser General Public
014: * License along with this library; if not, write to the Free Software
015: * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA
016: */
017:
018: package de.finix.contelligent.components.util;
019:
020: import java.io.IOException;
021: import java.io.Writer;
022: import java.util.Collection;
023: import java.util.HashMap;
024: import java.util.Iterator;
025: import java.util.Map;
026: import java.util.NoSuchElementException;
027: import java.util.StringTokenizer;
028:
029: import de.finix.contelligent.CallData;
030: import de.finix.contelligent.Component;
031: import de.finix.contelligent.ComponentManager;
032: import de.finix.contelligent.ComponentPath;
033: import de.finix.contelligent.components.Folder;
034: import de.finix.contelligent.core.AbstractCallDataImpl;
035: import de.finix.contelligent.exception.CircularRenderException;
036: import de.finix.contelligent.exception.ContelligentException;
037: import de.finix.contelligent.logging.LoggingService;
038: import de.finix.contelligent.render.ParameterDescription;
039: import de.finix.contelligent.render.Renderable;
040: import de.finix.contelligent.render.Renderer;
041:
042: public class ParameterRelocator extends Folder implements Renderable,
043: Renderer {
044:
045: private final static org.apache.log4j.Logger log = LoggingService
046: .getLogger(ParameterRelocator.class);
047:
048: final private static ComponentPath CONTENT = new ComponentPath(
049: "content");
050:
051: /**
052: * Renders the subcomponent "content" with a set of render parameters
053: * renamed, as specified in the metadata. The key for any mapping entries is
054: * "renameParameter" and the value is of the format "newParam=oldParam"
055: * where oldParam and newParam are the parameter names. Once the content has
056: * been rendered (or aborted through an exception), the old parameter map is
057: * restored.
058: */
059: public void render(Writer globalWriter, Map parameterMap,
060: CallData callData) throws ContelligentException,
061: IOException {
062:
063: ComponentManager cm = callData.getActualManager();
064: Component comp = cm.getSubcomponent(this , CONTENT, callData);
065:
066: if (comp instanceof Renderable) {
067: Renderer renderer = ((Renderable) comp).getRenderer();
068:
069: ComponentPath myPath = this .getComponentContext().getPath();
070: ComponentPath realContentPath = comp.getComponentContext()
071: .getPath();
072:
073: if (callData.checkRenderStack(realContentPath)) {
074: throw new CircularRenderException();
075: }
076:
077: // Set up new parameter map
078: Map oldParameterMap = callData.getParameters();
079: HashMap newParameterMap = new HashMap(oldParameterMap);
080: Iterator values = getComponentContext().getMetadata()
081: .getValues("renameParameter").iterator();
082: while (values.hasNext()) {
083: String value = (String) values.next();
084: try {
085: StringTokenizer st = new StringTokenizer(value, "=");
086: String newParam = st.nextToken();
087: String oldParam = st.nextToken();
088: if (newParameterMap.containsKey(oldParam)) {
089: newParameterMap.put(newParam, newParameterMap
090: .get(oldParam));
091: } else {
092: log.debug("Old parameter '" + oldParam
093: + "' not found in parameter map.");
094: }
095: } catch (NoSuchElementException nsee) {
096: // Just continue with the other entries
097: log
098: .debug("renameParameter entry has incorrect format: "
099: + value);
100: }
101: }
102: AbstractCallDataImpl cImpl = (AbstractCallDataImpl) callData;
103: try {
104: cImpl.setParameters(newParameterMap);
105: cImpl.pushRenderStack(realContentPath);
106: renderer.render(globalWriter, parameterMap, callData);
107: cImpl.popRenderStack();
108: } finally {
109: // Make sure the old parameter map is restored
110: cImpl.setParameters(oldParameterMap);
111: }
112: } else {
113: throw new ContelligentException(
114: "A required subcomponent is not renderable.");
115: }
116: }
117:
118: public Renderer getRenderer() {
119: return this ;
120: }
121:
122: public ParameterDescription[] getParameterDescription() {
123: return new ParameterDescription[0];
124: }
125:
126: public Collection getSensitiveCategories() {
127: return null;
128: }
129:
130: }
|