1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17 package org.springframework.remoting.jaxws;
18
19 import java.util.Arrays;
20 import java.util.LinkedHashSet;
21 import java.util.Map;
22 import java.util.Set;
23 import java.util.concurrent.Executor;
24 import javax.jws.WebService;
25 import javax.xml.ws.Endpoint;
26 import javax.xml.ws.WebServiceFeature;
27 import javax.xml.ws.WebServiceProvider;
28
29 import org.springframework.beans.BeanUtils;
30 import org.springframework.beans.factory.BeanFactory;
31 import org.springframework.beans.factory.BeanFactoryAware;
32 import org.springframework.beans.factory.CannotLoadBeanClassException;
33 import org.springframework.beans.factory.DisposableBean;
34 import org.springframework.beans.factory.InitializingBean;
35 import org.springframework.beans.factory.ListableBeanFactory;
36 import org.springframework.beans.factory.config.ConfigurableBeanFactory;
37 import org.springframework.lang.UsesJava7;
38 import org.springframework.util.Assert;
39 import org.springframework.util.ClassUtils;
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56 public abstract class AbstractJaxWsServiceExporter implements BeanFactoryAware, InitializingBean, DisposableBean {
57
58 private Map<String, Object> endpointProperties;
59
60 private Executor executor;
61
62 private String bindingType;
63
64 private WebServiceFeature[] endpointFeatures;
65
66 private Object[] webServiceFeatures;
67
68 private ListableBeanFactory beanFactory;
69
70 private final Set<Endpoint> publishedEndpoints = new LinkedHashSet<Endpoint>();
71
72
73
74
75
76
77
78
79
80 public void setEndpointProperties(Map<String, Object> endpointProperties) {
81 this.endpointProperties = endpointProperties;
82 }
83
84
85
86
87
88
89 public void setExecutor(Executor executor) {
90 this.executor = executor;
91 }
92
93
94
95
96
97 public void setBindingType(String bindingType) {
98 this.bindingType = bindingType;
99 }
100
101
102
103
104
105
106 public void setEndpointFeatures(WebServiceFeature... endpointFeatures) {
107 this.endpointFeatures = endpointFeatures;
108 }
109
110
111
112
113
114
115
116
117
118
119 @Deprecated
120 public void setWebServiceFeatures(Object[] webServiceFeatures) {
121 this.webServiceFeatures = webServiceFeatures;
122 }
123
124
125
126
127 @Override
128 public void setBeanFactory(BeanFactory beanFactory) {
129 if (!(beanFactory instanceof ListableBeanFactory)) {
130 throw new IllegalStateException(getClass().getSimpleName() + " requires a ListableBeanFactory");
131 }
132 this.beanFactory = (ListableBeanFactory) beanFactory;
133 }
134
135
136
137
138
139
140 @Override
141 public void afterPropertiesSet() throws Exception {
142 publishEndpoints();
143 }
144
145
146
147
148
149
150 public void publishEndpoints() {
151 Set<String> beanNames = new LinkedHashSet<String>(this.beanFactory.getBeanDefinitionCount());
152 beanNames.addAll(Arrays.asList(this.beanFactory.getBeanDefinitionNames()));
153 if (this.beanFactory instanceof ConfigurableBeanFactory) {
154 beanNames.addAll(Arrays.asList(((ConfigurableBeanFactory) this.beanFactory).getSingletonNames()));
155 }
156 for (String beanName : beanNames) {
157 try {
158 Class<?> type = this.beanFactory.getType(beanName);
159 if (type != null && !type.isInterface()) {
160 WebService wsAnnotation = type.getAnnotation(WebService.class);
161 WebServiceProvider wsProviderAnnotation = type.getAnnotation(WebServiceProvider.class);
162 if (wsAnnotation != null || wsProviderAnnotation != null) {
163 Endpoint endpoint = createEndpoint(this.beanFactory.getBean(beanName));
164 if (this.endpointProperties != null) {
165 endpoint.setProperties(this.endpointProperties);
166 }
167 if (this.executor != null) {
168 endpoint.setExecutor(this.executor);
169 }
170 if (wsAnnotation != null) {
171 publishEndpoint(endpoint, wsAnnotation);
172 }
173 else {
174 publishEndpoint(endpoint, wsProviderAnnotation);
175 }
176 this.publishedEndpoints.add(endpoint);
177 }
178 }
179 }
180 catch (CannotLoadBeanClassException ex) {
181
182 }
183 }
184 }
185
186
187
188
189
190
191
192
193 @UsesJava7
194 protected Endpoint createEndpoint(Object bean) {
195 if (this.endpointFeatures != null || this.webServiceFeatures != null) {
196 WebServiceFeature[] endpointFeaturesToUse = this.endpointFeatures;
197 if (endpointFeaturesToUse == null) {
198 endpointFeaturesToUse = new WebServiceFeature[this.webServiceFeatures.length];
199 for (int i = 0; i < this.webServiceFeatures.length; i++) {
200 endpointFeaturesToUse[i] = convertWebServiceFeature(this.webServiceFeatures[i]);
201 }
202 }
203 return Endpoint.create(this.bindingType, bean, endpointFeaturesToUse);
204 }
205 else {
206 return Endpoint.create(this.bindingType, bean);
207 }
208 }
209
210 private WebServiceFeature convertWebServiceFeature(Object feature) {
211 Assert.notNull(feature, "WebServiceFeature specification object must not be null");
212 if (feature instanceof WebServiceFeature) {
213 return (WebServiceFeature) feature;
214 }
215 else if (feature instanceof Class) {
216 return (WebServiceFeature) BeanUtils.instantiate((Class<?>) feature);
217 }
218 else if (feature instanceof String) {
219 try {
220 Class<?> featureClass = getBeanClassLoader().loadClass((String) feature);
221 return (WebServiceFeature) BeanUtils.instantiate(featureClass);
222 }
223 catch (ClassNotFoundException ex) {
224 throw new IllegalArgumentException("Could not load WebServiceFeature class [" + feature + "]");
225 }
226 }
227 else {
228 throw new IllegalArgumentException("Unknown WebServiceFeature specification type: " + feature.getClass());
229 }
230 }
231
232 private ClassLoader getBeanClassLoader() {
233 return (beanFactory instanceof ConfigurableBeanFactory ?
234 ((ConfigurableBeanFactory) beanFactory).getBeanClassLoader() : ClassUtils.getDefaultClassLoader());
235 }
236
237
238
239
240
241
242
243 protected abstract void publishEndpoint(Endpoint endpoint, WebService annotation);
244
245
246
247
248
249
250 protected abstract void publishEndpoint(Endpoint endpoint, WebServiceProvider annotation);
251
252
253
254
255
256 @Override
257 public void destroy() {
258 for (Endpoint endpoint : this.publishedEndpoints) {
259 endpoint.stop();
260 }
261 }
262
263 }