KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > springframework > webflow > definition > registry > ExternalizedFlowDefinitionRegistrar


1 /*
2  * Copyright 2002-2006 the original author or authors.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */

16 package org.springframework.webflow.definition.registry;
17
18 import java.util.Arrays JavaDoc;
19 import java.util.HashSet JavaDoc;
20 import java.util.Iterator JavaDoc;
21 import java.util.Set JavaDoc;
22
23 import org.springframework.core.io.Resource;
24 import org.springframework.core.style.ToStringCreator;
25
26 /**
27  * A flow definition registrar that populates a flow definition registry from
28  * flow definitions defined within externalized resources. Encapsulates
29  * registration behaivior common to all externalized registrars and is not tied
30  * to a specific flow definition format (e.g. xml).
31  * <p>
32  * Concrete subclasses are expected to derive from this class to provide
33  * knowledge about a particular kind of definition format by implementing the
34  * abstract template methods in this class.
35  * <p>
36  * By default, when configuring the {@link #setLocations(Resource[]) locations}
37  * property, flow definitions at those locations will be assigned a registry
38  * identifier equal to the filename of the underlying definition resource, minus
39  * the filename extension. For example, a XML-based flow definition defined in
40  * the file "flow1.xml" will be identified as "flow1" when registered in a
41  * registry.
42  * <p>
43  * For full control over the assignment of flow identifiers and flow properties,
44  * configure formal
45  * {@link org.springframework.webflow.definition.registry.FlowDefinitionResource}
46  * instances using the {@link #setResources(FlowDefinitionResource[] resources)} property.
47  *
48  * @see org.springframework.webflow.definition.registry.FlowDefinitionResource
49  * @see org.springframework.webflow.definition.registry.FlowDefinitionRegistry
50  *
51  * @author Keith Donald
52  */

53 public abstract class ExternalizedFlowDefinitionRegistrar implements FlowDefinitionRegistrar {
54
55     /**
56      * File locations of externalized flow definition resources to load.
57      * A set of {@link Resource}} objects.
58      */

59     private Set JavaDoc locations = new HashSet JavaDoc();
60
61     /**
62      * A set of formal externalized flow definitions to load.
63      * A set of {@link FlowDefinitionResource} objects.
64      */

65     private Set JavaDoc resources = new HashSet JavaDoc();
66
67     /**
68      * Sets the locations (file paths) pointing to externalized flow
69      * definitions.
70      * <p>
71      * Flows registered from this set will be automatically assigned an id based
72      * on the filename of the flow resource.
73      * @param locations the resource locations
74      */

75     public void setLocations(Resource[] locations) {
76         this.locations = new HashSet JavaDoc(Arrays.asList(locations));
77     }
78
79     /**
80      * Sets the formal set of externalized flow definitions this registrar will
81      * register.
82      * <p>
83      * Use this method when you want full control over the assigned flow id and
84      * the set of properties applied to the externalized flow resources.
85      * @param resources the externalized flow definition specifications
86      */

87     public void setResources(FlowDefinitionResource[] resources) {
88         this.resources = new HashSet JavaDoc(Arrays.asList(resources));
89     }
90
91     /**
92      * Adds a flow location pointing to an externalized flow resource.
93      * <p>
94      * The flow registered from this location will automatically assigned an id
95      * based on the filename of the flow resource.
96      * @param location the definition location
97      */

98     public boolean addLocation(Resource location) {
99         return locations.add(location);
100     }
101
102     /**
103      * Adds the flow locations pointing to externalized flow resources.
104      * <p>
105      * The flow registered from this location will automatically assigned an id
106      * based on the filename of the flow resource.
107      * @param locations the definition locations
108      */

109     public boolean addLocations(Resource[] locations) {
110         if (locations == null) {
111             return false;
112         }
113         return this.locations.addAll(Arrays.asList(locations));
114     }
115
116     /**
117      * Adds an externalized flow definition specification pointing to an
118      * externalized flow resource.
119      * <p>
120      * Use this method when you want full control over the assigned flow id and
121      * the set of properties applied to the externalized flow resource.
122      * @param resource the definition the definition resource
123      */

124     public boolean addResource(FlowDefinitionResource resource) {
125         return resources.add(resource);
126     }
127
128     /**
129      * Adds the externalized flow definitions pointing to externalized flow
130      * resources.
131      * <p>
132      * Use this method when you want full control over the assigned flow id and
133      * the set of properties applied to the externalized flow resources.
134      * @param resources the definitions
135      */

136     public boolean addResources(FlowDefinitionResource[] resources) {
137         if (resources == null) {
138             return false;
139         }
140         return this.resources.addAll(Arrays.asList(resources));
141     }
142
143     public void registerFlowDefinitions(FlowDefinitionRegistry registry) {
144         processLocations(registry);
145         processResources(registry);
146     }
147     
148     // internal helpers
149

150     /**
151      * Register the flow definitions at the configured file locations.
152      * @param registry the registry
153      */

154     private void processLocations(FlowDefinitionRegistry registry) {
155         Iterator JavaDoc it = locations.iterator();
156         while (it.hasNext()) {
157             Resource location = (Resource)it.next();
158             if (isFlowDefinitionResource(location)) {
159                 FlowDefinitionResource resource = createFlowDefinitionResource(location);
160                 register(resource, registry);
161             }
162         }
163     }
164
165     /**
166      * Register the flow definitions at the configured file locations.
167      * @param registry the registry
168      */

169     private void processResources(FlowDefinitionRegistry registry) {
170         Iterator JavaDoc it = resources.iterator();
171         while (it.hasNext()) {
172             FlowDefinitionResource resource = (FlowDefinitionResource)it.next();
173             register(resource, registry);
174         }
175     }
176
177     /**
178      * Helper method to register the flow built from an externalized resource in
179      * the registry.
180      * @param resource representation of the externalized flow definition
181      * resource
182      * @param registry the flow registry to register the flow in
183      */

184     protected final void register(FlowDefinitionResource resource, FlowDefinitionRegistry registry) {
185         registry.registerFlowDefinition(createFlowDefinitionHolder(resource));
186     }
187
188     // subclassing hooks
189

190     /**
191      * Template method that calculates if the given file resource is actually a
192      * flow definition resource. Resources that aren't flow definitions will be
193      * ignored. Subclasses may override; this implementation simply returns
194      * true.
195      * @param resource the underlying resource
196      * @return true if yes, false otherwise
197      */

198     protected boolean isFlowDefinitionResource(Resource resource) {
199         return true;
200     }
201
202     /**
203      * Factory method that creates a flow definition from an externalized
204      * resource location.
205      * @param location the location of the resource
206      * @return the externalized flow definition pointer
207      */

208     protected FlowDefinitionResource createFlowDefinitionResource(Resource location) {
209         return new FlowDefinitionResource(location);
210     }
211
212     /**
213      * Template factory method subclasses must override to return the holder for
214      * the flow definition to be registered loaded from the specified resource.
215      * @param resource the externalized resource
216      * @return the flow definition holder
217      */

218     protected abstract FlowDefinitionHolder createFlowDefinitionHolder(FlowDefinitionResource resource);
219
220     public String JavaDoc toString() {
221         return new ToStringCreator(this).append("locations", locations).append("resources", resources).toString();
222     }
223 }
Popular Tags