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.action.system;
019:
020: import java.security.PrivilegedExceptionAction;
021:
022: import de.finix.contelligent.CallData;
023: import de.finix.contelligent.Component;
024: import de.finix.contelligent.ComponentPath;
025: import de.finix.contelligent.Container;
026: import de.finix.contelligent.core.AbstractCallDataImpl;
027: import de.finix.contelligent.core.ComponentManagerInternal;
028: import de.finix.contelligent.core.EnvironmentManager;
029: import de.finix.contelligent.exception.ContelligentException;
030: import de.finix.contelligent.exception.ContelligentExceptionID;
031: import de.finix.contelligent.exception.ContelligentSecurityException;
032: import de.finix.contelligent.logging.LoggingService;
033:
034: /**
035: * This {@link de.finix.contelligent.action.Action} is just a hook for method
036: * {@link de.finix.contelligent.ComponentManager#createComponent}.
037: *
038: * @see de.finix.contelligent.ComponentManager#createComponent
039: */
040: public class CreateComponentAction extends SystemAction {
041: final static org.apache.log4j.Logger log = LoggingService
042: .getLogger(CreateComponentAction.class);
043:
044: final static public String PARAMETER_TYPE = "TYPE";
045:
046: final static public String PARAMETER_DIR = "DIR";
047:
048: final static public String PARAMETER_NAME = "NAME";
049:
050: // optional:
051: final static public String PARAMETER_OVERWRITE = "OVERWRITE"; // default:
052:
053: // false
054:
055: /**
056: * Calls {@link de.finix.contelligent.ComponentManager#createComponent} once
057: * for every parameter-triple {TYPE,NAME,DIR} which creates a new
058: * {@link de.finix.contelligent.Component} from scratch using a specified
059: * type.
060: *
061: * @param callData
062: * a <code>CallData</code> value
063: * @return a <code>Component</code> value
064: * @exception de.finix.contelligent.action.ActionException
065: * if an error occurs
066: */
067: protected String doPerform(CallData callData,
068: SystemActionResult response) throws Exception {
069: {
070: checkUserAgent(callData);
071: String environment = callData.getEnvironment();
072: boolean wfOnly = EnvironmentManager.getInstance()
073: .getEditInWorkflowOnly(callData, environment);
074: if (wfOnly && (callData.getActualManager().isRoot())) {
075: throw new ContelligentSecurityException(
076: "Current environment forbids editing in Production.");
077: }
078: ComponentPath envRoot = EnvironmentManager.getInstance()
079: .getEnvironmentRoot(callData, environment);
080:
081: ComponentPath parentPath = null;
082:
083: final ComponentManagerInternal componentManager = (ComponentManagerInternal) ctx
084: .getCallManager();
085: String[] typeNameArray = (String[]) getParameter(
086: PARAMETER_TYPE, callData);
087: String[] dirArray = (String[]) getParameter(PARAMETER_DIR,
088: callData);
089: String[] nameArray = (String[]) getParameter(
090: PARAMETER_NAME, callData);
091: String[] overwriteArray = (String[]) getParameter(
092: PARAMETER_OVERWRITE, callData);
093:
094: if ((typeNameArray.length != dirArray.length)
095: || (typeNameArray.length != nameArray.length)) {
096: log
097: .error("'"
098: + this
099: + "' - the paramter arrays don't have equal length!");
100: throw new ContelligentException(
101: ContelligentExceptionID.action_invalidParameters);
102: }
103:
104: for (int i = 0; i < typeNameArray.length; i++) {
105: boolean overwrite = Boolean.valueOf(overwriteArray[i])
106: .booleanValue();
107: parentPath = new ComponentPath(dirArray[i]);
108: ComponentPath targetPath = parentPath
109: .append(nameArray[i]);
110:
111: String typeName = typeNameArray[i];
112: String allowed = EnvironmentManager.getInstance()
113: .getAllowedTypes(callData, environment);
114: String favorite = EnvironmentManager.getInstance()
115: .getFavoriteTypes(callData, environment);
116:
117: //log.info("Env: ["+environment+"] / Types: ["+allowed+"]");
118: if ((!EnvironmentManager.getInstance().matchType(
119: typeName, allowed))
120: && (!EnvironmentManager.getInstance()
121: .matchType(typeName, favorite))) {
122: throw new ContelligentSecurityException(
123: "No permission to create requested type.");
124: }
125: if ((!targetPath.isSubPathOf(envRoot))
126: && (!targetPath.equals(envRoot))) {
127: throw new ContelligentSecurityException(
128: "No permission to modify this path in the current environment.");
129: }
130:
131: if (overwrite
132: && componentManager.componentExists(targetPath)) {
133: log.debug("'" + this
134: + "' - ... deleting existing target-path '"
135: + targetPath + "' ...");
136: final ComponentPath targetPathA = targetPath;
137: final AbstractCallDataImpl callDataA = (AbstractCallDataImpl) callData;
138: callDataA
139: .doWithoutRelationsCheck(new PrivilegedExceptionAction() {
140: public Object run() throws Exception {
141: componentManager
142: .deleteComponentTree(
143: callDataA,
144: targetPathA);
145: return null;
146: }
147: });
148: }
149: Component parentComponent = componentManager
150: .getComponent(parentPath, callData);
151: if (parentComponent instanceof Container) {
152: Container parentContainer = (Container) parentComponent;
153: componentManager.createComponent(parentContainer,
154: nameArray[i], typeNameArray[i], null, null,
155: callData);
156: } else {
157: throw new ContelligentException(
158: ContelligentExceptionID.component_noContainer,
159: new Object[] { parentComponent });
160: }
161: if (overwrite) {
162: // Now we have to check whether we would create any dead
163: // relations
164: // and generate an exception if so.
165: componentManager.checkRelations(callData);
166: }
167: }
168:
169: response.setState(SystemActionResult.OK);
170: setResult(RESULT_KEY, response, callData);
171: return ROUTING_OK;
172: }
173: }
174: }
|