1 17 18 19 20 package org.apache.lenya.workflow.impl; 21 22 import java.io.File ; 23 import java.io.IOException ; 24 import java.util.HashMap ; 25 import java.util.Map ; 26 27 import javax.xml.parsers.ParserConfigurationException ; 28 29 import org.apache.lenya.workflow.Action; 30 import org.apache.lenya.workflow.Condition; 31 import org.apache.lenya.workflow.Event; 32 import org.apache.lenya.workflow.Workflow; 33 import org.apache.lenya.workflow.WorkflowException; 34 import org.apache.lenya.xml.DocumentHelper; 35 import org.apache.log4j.Category; 36 import org.w3c.dom.Document ; 37 import org.w3c.dom.Element ; 38 import org.w3c.dom.NodeList ; 39 import org.xml.sax.SAXException ; 40 41 44 public class WorkflowBuilder { 45 46 private static final Category log = Category.getInstance(WorkflowBuilder.class); 47 48 51 protected WorkflowBuilder() { 52 } 53 54 60 public static WorkflowImpl buildWorkflow(File file) throws WorkflowException { 61 WorkflowImpl workflow; 62 63 try { 64 Document document = DocumentHelper.readDocument(file); 65 workflow = buildWorkflow(document); 66 } catch (Exception e) { 67 throw new WorkflowException(e); 68 } 69 70 return workflow; 71 } 72 73 82 protected static WorkflowImpl buildWorkflow(Document document) 83 throws ParserConfigurationException , SAXException , IOException , WorkflowException { 84 85 Element root = document.getDocumentElement(); 86 StateImpl initialState = null; 87 88 Map states = new HashMap (); 89 Map events = new HashMap (); 90 Map variables = new HashMap (); 91 92 NodeList stateElements = root.getElementsByTagNameNS(Workflow.NAMESPACE, STATE_ELEMENT); 94 95 for (int i = 0; i < stateElements.getLength(); i++) { 96 Element element = (Element ) stateElements.item(i); 97 StateImpl state = buildState(element); 98 String id = state.getId(); 99 states.put(id, state); 100 101 if (isInitialStateElement(element)) { 102 initialState = state; 103 } 104 } 105 106 WorkflowImpl workflow = new WorkflowImpl(initialState); 107 108 NodeList variableElements = 110 root.getElementsByTagNameNS(Workflow.NAMESPACE, VARIABLE_ELEMENT); 111 112 for (int i = 0; i < variableElements.getLength(); i++) { 113 Element element = (Element ) variableElements.item(i); 114 BooleanVariableImpl variable = buildVariable(element); 115 variables.put(variable.getName(), variable); 116 workflow.addVariable(variable); 117 } 118 119 NodeList eventElements = root.getElementsByTagNameNS(Workflow.NAMESPACE, EVENT_ELEMENT); 121 122 for (int i = 0; i < eventElements.getLength(); i++) { 123 EventImpl event = buildEvent((Element ) eventElements.item(i)); 124 String id = event.getName(); 125 events.put(id, event); 126 workflow.addEvent(event); 127 } 128 129 NodeList transitionElements = 131 root.getElementsByTagNameNS(Workflow.NAMESPACE, TRANSITION_ELEMENT); 132 133 for (int i = 0; i < transitionElements.getLength(); i++) { 134 TransitionImpl transition = 135 buildTransition((Element ) transitionElements.item(i), states, events, variables); 136 workflow.addTransition(transition); 137 } 138 139 return workflow; 140 } 141 142 147 protected static boolean isInitialStateElement(Element element) { 148 String initialAttribute = element.getAttribute(INITIAL_ATTRIBUTE); 149 150 return (initialAttribute != null) 151 && (initialAttribute.equals("yes") || initialAttribute.equals("true")); 152 } 153 154 protected static final String STATE_ELEMENT = "state"; 155 protected static final String TRANSITION_ELEMENT = "transition"; 156 protected static final String EVENT_ELEMENT = "event"; 157 protected static final String CONDITION_ELEMENT = "condition"; 158 protected static final String ACTION_ELEMENT = "action"; 159 protected static final String ID_ATTRIBUTE = "id"; 160 protected static final String INITIAL_ATTRIBUTE = "initial"; 161 protected static final String SOURCE_ATTRIBUTE = "source"; 162 protected static final String DESTINATION_ATTRIBUTE = "destination"; 163 protected static final String CLASS_ATTRIBUTE = "class"; 164 protected static final String VARIABLE_ELEMENT = "variable"; 165 protected static final String ASSIGNMENT_ELEMENT = "assign"; 166 protected static final String VARIABLE_ATTRIBUTE = "variable"; 167 protected static final String VALUE_ATTRIBUTE = "value"; 168 protected static final String NAME_ATTRIBUTE = "name"; 169 protected static final String SYNCHRONIZED_ATTRIBUTE = "synchronized"; 170 171 176 protected static StateImpl buildState(Element element) { 177 String id = element.getAttribute(ID_ATTRIBUTE); 178 StateImpl state = new StateImpl(id); 179 180 return state; 181 } 182 183 192 protected static TransitionImpl buildTransition( 193 Element element, 194 Map states, 195 Map events, 196 Map variables) 197 throws WorkflowException { 198 199 if (log.isDebugEnabled()) { 200 log.debug("Building transition"); 201 } 202 203 String sourceId = element.getAttribute(SOURCE_ATTRIBUTE); 204 String destinationId = element.getAttribute(DESTINATION_ATTRIBUTE); 205 206 StateImpl source = (StateImpl) states.get(sourceId); 207 StateImpl destination = (StateImpl) states.get(destinationId); 208 209 TransitionImpl transition = new TransitionImpl(source, destination); 210 211 Element eventElement = 213 (Element ) element.getElementsByTagNameNS(Workflow.NAMESPACE, EVENT_ELEMENT).item(0); 214 String id = eventElement.getAttribute(ID_ATTRIBUTE); 215 Event event = (Event) events.get(id); 216 transition.setEvent(event); 217 218 if (log.isDebugEnabled()) { 219 log.debug(" Event: [" + event + "]"); 220 } 221 222 NodeList conditionElements = 224 element.getElementsByTagNameNS(Workflow.NAMESPACE, CONDITION_ELEMENT); 225 226 for (int i = 0; i < conditionElements.getLength(); i++) { 227 Condition condition = buildCondition((Element ) conditionElements.item(i)); 228 transition.addCondition(condition); 229 } 230 231 NodeList assignmentElements = 233 element.getElementsByTagNameNS(Workflow.NAMESPACE, ASSIGNMENT_ELEMENT); 234 235 for (int i = 0; i < assignmentElements.getLength(); i++) { 236 BooleanVariableAssignmentImpl action = 237 buildAssignment(variables, (Element ) assignmentElements.item(i)); 238 transition.addAction(action); 239 } 240 241 NodeList actionElements = 243 element.getElementsByTagNameNS(Workflow.NAMESPACE, ACTION_ELEMENT); 244 245 for (int i = 0; i < actionElements.getLength(); i++) { 246 Action action = buildAction((Element ) actionElements.item(i)); 247 transition.addAction(action); 248 } 249 250 if (element.hasAttribute(SYNCHRONIZED_ATTRIBUTE)) { 252 Boolean isSynchronized = Boolean.valueOf(element.getAttribute(SYNCHRONIZED_ATTRIBUTE)); 253 transition.setSynchronized(isSynchronized.booleanValue()); 254 } 255 256 return transition; 257 } 258 259 264 protected static EventImpl buildEvent(Element element) { 265 String id = element.getAttribute(ID_ATTRIBUTE); 266 EventImpl event = new EventImpl(id); 267 268 return event; 269 } 270 271 277 protected static Condition buildCondition(Element element) throws WorkflowException { 278 String className = element.getAttribute(CLASS_ATTRIBUTE); 279 String expression = DocumentHelper.getSimpleElementText(element); 280 Condition condition = ConditionFactory.createCondition(className, expression); 281 282 return condition; 283 } 284 285 290 protected static Action buildAction(Element element) { 291 String id = element.getAttribute(ID_ATTRIBUTE); 292 Action action = new ActionImpl(id); 293 294 return action; 295 } 296 297 302 protected static BooleanVariableImpl buildVariable(Element element) { 303 String name = element.getAttribute(NAME_ATTRIBUTE); 304 String value = element.getAttribute(VALUE_ATTRIBUTE); 305 306 return new BooleanVariableImpl(name, Boolean.getBoolean(value)); 307 } 308 309 316 protected static BooleanVariableAssignmentImpl buildAssignment(Map variables, Element element) 317 throws WorkflowException { 318 String variableName = element.getAttribute(VARIABLE_ATTRIBUTE); 319 320 String valueString = element.getAttribute(VALUE_ATTRIBUTE); 321 boolean value = Boolean.valueOf(valueString).booleanValue(); 322 323 BooleanVariableImpl variable = (BooleanVariableImpl) variables.get(variableName); 324 325 return new BooleanVariableAssignmentImpl(variable, value); 326 } 327 } 328 | Popular Tags |