View Javadoc

1   /*
2    * Licensed to the Apache Software Foundation (ASF) under one or more
3    * contributor license agreements.  See the NOTICE file distributed with
4    * this work for additional information regarding copyright ownership.
5    * The ASF licenses this file to You under the Apache License, Version 2.0
6    * (the "License"); you may not use this file except in compliance with
7    * the License.  You may obtain a copy of the License at
8    *
9    *     http://www.apache.org/licenses/LICENSE-2.0
10   *
11   * Unless required by applicable law or agreed to in writing, software
12   * distributed under the License is distributed on an "AS IS" BASIS,
13   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14   * See the License for the specific language governing permissions and
15   * limitations under the License.
16   */
17  package org.apache.commons.scxml.model;
18  
19  import java.io.Serializable;
20  import java.util.HashMap;
21  import java.util.LinkedHashMap;
22  import java.util.Map;
23  
24  import org.apache.commons.scxml.SCXMLHelper;
25  
26  /**
27   * The class in this SCXML object model that corresponds to the
28   * <scxml> root element, and serves as the "document
29   * root".
30   *
31   */
32  public class SCXML implements Serializable, NamespacePrefixesHolder {
33  
34      /**
35       * Serial version UID.
36       */
37      private static final long serialVersionUID = 2L;
38  
39      /**
40       * The SCXML XMLNS.
41       */
42      public static final String XMLNS = "http://www.w3.org/2005/07/scxml";
43  
44      /**
45       * The xmlns attribute on the root <smxml> element.
46       * This must match XMLNS above.
47       */
48      private String xmlns;
49  
50      /**
51       * The SCXML version of this document.
52       */
53      private String version;
54  
55      /**
56       * The initial TransitionTarget for the SCXML executor.
57       */
58      private TransitionTarget initialTarget;
59  
60      /**
61       * The initial transition target ID (used by XML Digester only).
62       */
63      private String initial;
64  
65      /**
66       * Optional property holding the data model for this SCXML document.
67       * This gets merged with the root context and potentially hides any
68       * (namesake) variables in the root context.
69       */
70      private Datamodel datamodel;
71  
72      /**
73       * The immediate child targets of this SCXML document root.
74       */
75      private Map children;
76  
77      /**
78       * A global map of all States and Parallels associated with this
79       * state machine, keyed by their id.
80       */
81      private Map targets;
82  
83      /**
84       * The XML namespaces defined on the SCXML document root node,
85       * preserved primarily for serialization.
86       */
87      private Map namespaces;
88  
89      /**
90       * Indicates whether the legacy parser
91       * ({@link org.apache.commons.scxml.io.SCXMLDigester}) was used.
92       */
93      private boolean legacy = false;
94  
95      /**
96       * Constructor.
97       */
98      public SCXML() {
99          this.children = new LinkedHashMap();
100         this.targets = new HashMap();
101     }
102 
103     /**
104      * Get the initial State.
105      *
106      * @return State Returns the initialstate.
107      *
108      * @deprecated Use getInitialTarget() instead. Returns <code>null</code>
109      *             if the initial target is a Parallel.
110      */
111     public final State getInitialState() {
112         if (initialTarget != null && initialTarget instanceof State) {
113             return (State) initialTarget;
114         }
115         return null;
116     }
117 
118     /**
119      * Set the initial State.
120      *
121      * @param initialState The initialstate to set.
122      *
123      * @deprecated Use setInitialTarget(TransitionTarget) instead.
124      */
125     public final void setInitialState(final State initialState) {
126         this.initialTarget = initialState;
127     }
128 
129     /**
130      * Get the initial TransitionTarget.
131      *
132      * @return Returns the initial target for this state machine.
133      *
134      * @since 0.7
135      */
136     public final TransitionTarget getInitialTarget() {
137         return initialTarget;
138     }
139 
140     /**
141      * Set the initial TransitionTarget.
142      *
143      * @param initialTarget The initial target to set.
144      *
145      * @since 0.7
146      */
147     public final void setInitialTarget(final TransitionTarget initialTarget) {
148         this.initialTarget = initialTarget;
149     }
150 
151     /**
152      * Get the data model placed at document root.
153      *
154      * @return Returns the data model.
155      */
156     public final Datamodel getDatamodel() {
157         return datamodel;
158     }
159 
160     /**
161      * Set the data model at document root.
162      *
163      * @param datamodel The Datamodel to set.
164      */
165     public final void setDatamodel(final Datamodel datamodel) {
166         this.datamodel = datamodel;
167     }
168 
169     /**
170      * Get the children states.
171      *
172      * @return Map Returns map of the child states.
173      *
174      * @deprecated Use getChildren() instead.
175      */
176     public final Map getStates() {
177         return children;
178     }
179 
180     /**
181      * Add a child state.
182      *
183      * @param state The state to be added to the states Map.
184      *
185      * @deprecated Use addChild(TransitionTarget) instead.
186      */
187     public final void addState(final State state) {
188         children.put(state.getId(), state);
189     }
190 
191     /**
192      * Get the immediate child targets of the SCXML root.
193      *
194      * @return Map Returns map of the child targets.
195      *
196      * @since 0.7
197      */
198     public final Map getChildren() {
199         return children;
200     }
201 
202     /**
203      * Add an immediate child target of the SCXML root.
204      *
205      * @param tt The transition target to be added to the states Map.
206      *
207      * @since 0.7
208      */
209     public final void addChild(final TransitionTarget tt) {
210         children.put(tt.getId(), tt);
211     }
212 
213     /**
214      * Get the targets map, which is a Map of all States and Parallels
215      * associated with this state machine, keyed by their id.
216      *
217      * @return Map Returns the targets.
218      */
219     public final Map getTargets() {
220         return targets;
221     }
222 
223     /**
224      * Add a target to this SCXML document.
225      *
226      * @param target The target to be added to the targets Map.
227      */
228     public final void addTarget(final TransitionTarget target) {
229         String id = target.getId();
230         if (!SCXMLHelper.isStringEmpty(id)) {
231             // Target is not anonymous, so makes sense to map it
232             targets.put(id, target);
233         }
234     }
235 
236     /**
237      * Get the SCXML document version.
238      *
239      * @return Returns the version.
240      */
241     public final String getVersion() {
242         return version;
243     }
244 
245     /**
246      * Set the SCXML document version.
247      *
248      * @param version The version to set.
249      */
250     public final void setVersion(final String version) {
251         this.version = version;
252     }
253 
254     /**
255      * Get the xmlns of this SCXML document.
256      *
257      * @return Returns the xmlns.
258      */
259     public final String getXmlns() {
260         return xmlns;
261     }
262 
263     /**
264      * Set the xmlns of this SCXML document.
265      *
266      * @param xmlns The xmlns to set.
267      */
268     public final void setXmlns(final String xmlns) {
269         this.xmlns = xmlns;
270     }
271 
272     /**
273      * Get the namespace definitions specified on the SCXML element.
274      * May be <code>null</code>.
275      *
276      * @return The namespace definitions specified on the SCXML element,
277      *         may be <code>null</code>.
278      */
279     public final Map getNamespaces() {
280         return namespaces;
281     }
282 
283     /**
284      * Set the namespace definitions specified on the SCXML element.
285      *
286      * @param namespaces The namespace definitions specified on the
287      *                   SCXML element.
288      */
289     public final void setNamespaces(final Map namespaces) {
290         this.namespaces = namespaces;
291     }
292 
293     /**
294      * Get the ID of the initial state.
295      *
296      * @return String Returns the initial state ID (used by XML Digester only).
297      * @see #getInitialTarget()
298      * @deprecated Use {@link #getInitial()} instead.
299      */
300     public final String getInitialstate() {
301         return initial;
302     }
303 
304     /**
305      * Set the ID of the initial state.
306      *
307      * @param initialstate The initial state ID (used by XML Digester only).
308      * @see #setInitialTarget(TransitionTarget)
309      * @deprecated Use {@link #setInitial(String)} instead.
310      */
311     public final void setInitialstate(final String initialstate) {
312         this.initial = initialstate;
313     }
314 
315     /**
316      * Get the ID of the initial transition target.
317      *
318      * @return String Returns the initial transition target ID
319      *     (used by XML Digester only).
320      * @see #getInitialTarget()
321      */
322     public final String getInitial() {
323         return initial;
324     }
325 
326     /**
327      * Set the ID of the initial transition target.
328      *
329      * @param initial The initial transition target ID
330      *     (used by XML Digester only).
331      * @see #setInitialTarget(TransitionTarget)
332      */
333     public final void setInitial(final String initial) {
334         this.initial = initial;
335     }
336 
337     /**
338      * Whether the legacy parser was used.
339      *
340      * @return True, if legacy parser was used.
341      *
342      * @since 0.9
343      * @deprecated Will be removed in v1.0
344      */
345     public final boolean isLegacy() {
346         return legacy;
347     }
348 
349     /**
350      * Set whether the legacy parser was used.
351      *
352      * @param legacy True, if legacy parser was used.
353      *
354      * @since 0.9
355      * @deprecated Will be removed in v1.0
356      */
357     public final void setLegacy(final boolean legacy) {
358         this.legacy = legacy;
359     }
360 
361 }
362