001: /*
002: * Copyright 2004-2007 the original author or authors.
003: *
004: * Licensed under the Apache License, Version 2.0 (the "License");
005: * you may not use this file except in compliance with the License.
006: * You may obtain a copy of the License at
007: *
008: * http://www.apache.org/licenses/LICENSE-2.0
009: *
010: * Unless required by applicable law or agreed to in writing, software
011: * distributed under the License is distributed on an "AS IS" BASIS,
012: * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013: * See the License for the specific language governing permissions and
014: * limitations under the License.
015: */
016: package org.springframework.webflow.engine.builder;
017:
018: import org.springframework.beans.factory.BeanFactory;
019: import org.springframework.beans.factory.BeanFactoryAware;
020: import org.springframework.binding.convert.ConversionService;
021: import org.springframework.binding.expression.ExpressionParser;
022: import org.springframework.context.ResourceLoaderAware;
023: import org.springframework.core.io.ResourceLoader;
024: import org.springframework.webflow.action.BeanInvokingActionFactory;
025: import org.springframework.webflow.definition.registry.AbstractFlowDefinitionRegistryFactoryBean;
026: import org.springframework.webflow.definition.registry.FlowDefinitionRegistry;
027: import org.springframework.webflow.engine.Flow;
028: import org.springframework.webflow.engine.State;
029: import org.springframework.webflow.execution.Action;
030:
031: /**
032: * A base class for factory beans that create populated registries of flow
033: * definitions built using a {@link FlowBuilder}, typically a {@link BaseFlowBuilder}
034: * subclass. This base class will setup a {@link FlowServiceLocator} for
035: * use by the flow builder.
036: * <p>
037: * Subclasses should override the {@link #doPopulate(FlowDefinitionRegistry)}
038: * template method to perform the registry population logic, typically delegating to a
039: * {@link org.springframework.webflow.definition.registry.FlowDefinitionRegistrar}
040: * strategy.
041: *
042: * @see org.springframework.webflow.definition.registry.FlowDefinitionRegistry
043: * @see org.springframework.webflow.definition.registry.FlowDefinitionRegistrar
044: *
045: * @author Keith Donald
046: */
047: public abstract class AbstractFlowBuildingFlowRegistryFactoryBean
048: extends AbstractFlowDefinitionRegistryFactoryBean implements
049: BeanFactoryAware, ResourceLoaderAware {
050:
051: /**
052: * The locator of services needed by the flows built for inclusion in the
053: * registry.
054: */
055: private FlowServiceLocator flowServiceLocator;
056:
057: /**
058: * The factory encapsulating the creation of central Flow artifacts such as
059: * {@link Flow flows} and {@link State states}.
060: */
061: private FlowArtifactFactory flowArtifactFactory;
062:
063: /**
064: * The factory encapsulating the creation of bean invoking actions, actions
065: * that adapt methods on objects to the {@link Action} interface.
066: */
067: private BeanInvokingActionFactory beanInvokingActionFactory;
068:
069: /**
070: * The parser for parsing expression strings into evaluatable expression
071: * objects.
072: */
073: private ExpressionParser expressionParser;
074:
075: /**
076: * A conversion service that can convert between types.
077: */
078: private ConversionService conversionService;
079:
080: /**
081: * A resource loader that can load resources.
082: */
083: private ResourceLoader resourceLoader;
084:
085: /**
086: * The Spring bean factory that manages configured flow artifacts.
087: */
088: private BeanFactory beanFactory;
089:
090: /**
091: * Returns the factory encapsulating the creation of central Flow artifacts
092: * such as {@link Flow flows} and {@link State states}.
093: */
094: protected FlowArtifactFactory getFlowArtifactFactory() {
095: return flowArtifactFactory;
096: }
097:
098: /**
099: * Sets the factory encapsulating the creation of central Flow artifacts
100: * such as {@link Flow flows} and {@link State states}.
101: */
102: public void setFlowArtifactFactory(
103: FlowArtifactFactory flowArtifactFactory) {
104: this .flowArtifactFactory = flowArtifactFactory;
105: }
106:
107: /**
108: * Returns the factory for creating bean invoking actions, actions that adapt
109: * methods on objects to the {@link Action} interface.
110: */
111: protected BeanInvokingActionFactory getBeanInvokingActionFactory() {
112: return beanInvokingActionFactory;
113: }
114:
115: /**
116: * Sets the factory for creating bean invoking actions, actions that adapt
117: * methods on objects to the {@link Action} interface.
118: */
119: public void setBeanInvokingActionFactory(
120: BeanInvokingActionFactory beanInvokingActionFactory) {
121: this .beanInvokingActionFactory = beanInvokingActionFactory;
122: }
123:
124: /**
125: * Returns the expression parser responsible for parsing expression strings into
126: * evaluatable expression objects.
127: */
128: protected ExpressionParser getExpressionParser() {
129: return expressionParser;
130: }
131:
132: /**
133: * Set the expression parser responsible for parsing expression strings into
134: * evaluatable expression objects.
135: */
136: public void setExpressionParser(ExpressionParser expressionParser) {
137: this .expressionParser = expressionParser;
138: }
139:
140: /**
141: * Returns the conversion service to use to convert between types; typically
142: * from string to a rich object type.
143: */
144: protected ConversionService getConversionService() {
145: return conversionService;
146: }
147:
148: /**
149: * Set the conversion service to use to convert between types; typically
150: * from string to a rich object type.
151: */
152: public void setConversionService(ConversionService conversionService) {
153: this .conversionService = conversionService;
154: }
155:
156: // implementing ResourceLoaderAware
157:
158: /**
159: * Returns the injected resource loader.
160: */
161: protected ResourceLoader getResourceLoader() {
162: return resourceLoader;
163: }
164:
165: public void setResourceLoader(ResourceLoader resourceLoader) {
166: this .resourceLoader = resourceLoader;
167: }
168:
169: // implementing BeanFactoryAware
170:
171: /**
172: * Returns the bean factory managing this bean.
173: */
174: protected BeanFactory getBeanFactory() {
175: return beanFactory;
176: }
177:
178: public void setBeanFactory(BeanFactory beanFactory) {
179: this .beanFactory = beanFactory;
180: }
181:
182: protected final void init() {
183: flowServiceLocator = createFlowServiceLocator();
184: init(flowServiceLocator);
185: }
186:
187: // subclassing hooks
188:
189: /**
190: * Factory method for creating the service locator used to locate webflow
191: * services during flow assembly. Subclasses may override to customize the
192: * instantiation and configuration of the locator returned.
193: * @return the service locator
194: */
195: protected FlowServiceLocator createFlowServiceLocator() {
196: DefaultFlowServiceLocator serviceLocator = new DefaultFlowServiceLocator(
197: getRegistry(), beanFactory);
198: if (flowArtifactFactory != null) {
199: serviceLocator.setFlowArtifactFactory(flowArtifactFactory);
200: }
201: if (beanInvokingActionFactory != null) {
202: serviceLocator
203: .setBeanInvokingActionFactory(beanInvokingActionFactory);
204: }
205: if (expressionParser != null) {
206: serviceLocator.setExpressionParser(expressionParser);
207: }
208: if (conversionService != null) {
209: serviceLocator.setConversionService(conversionService);
210: }
211: if (resourceLoader != null) {
212: serviceLocator.setResourceLoader(resourceLoader);
213: }
214: return serviceLocator;
215: }
216:
217: /**
218: * Called after properties have been set on the service locator, but before
219: * registry population. Subclasses may override to perform custom initialization
220: * of the flow service locator.
221: * @param flowServiceLocator the flow service locator to use to locate externally managed
222: * services needed during flow building and assembly, typically used by a
223: * {@link org.springframework.webflow.definition.registry.FlowDefinitionRegistrar}
224: */
225: protected void init(FlowServiceLocator flowServiceLocator) {
226: }
227:
228: /**
229: * Returns the strategy for locating dependent artifacts when a flow is
230: * being built. May be called by subclasses during
231: * {@link #doPopulate(FlowDefinitionRegistry) registry population} to wire
232: * in the service locator needed for flow assembly.
233: */
234: protected FlowServiceLocator getFlowServiceLocator() {
235: return flowServiceLocator;
236: }
237:
238: protected abstract void doPopulate(FlowDefinitionRegistry registry);
239: }
|