Skip to content

Commit ee16484

Browse files
committed
Merge pull request #9635 from vpavic:ws-wsdl-exposure
* pr/9635: Polish "Add support for Spring WS auto WSDL/XSD exposure" Add support for Spring WS auto WSDL/XSD exposure
2 parents 32102c6 + 15de653 commit ee16484

File tree

9 files changed

+169
-7
lines changed

9 files changed

+169
-7
lines changed

spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/webservices/WebServicesAutoConfiguration.java

Lines changed: 84 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,23 +16,40 @@
1616

1717
package org.springframework.boot.autoconfigure.webservices;
1818

19+
import java.io.IOException;
20+
import java.util.Collections;
21+
import java.util.List;
1922
import java.util.Map;
2023

24+
import org.springframework.beans.BeansException;
25+
import org.springframework.beans.factory.config.ConfigurableListableBeanFactory;
26+
import org.springframework.beans.factory.config.ConstructorArgumentValues;
27+
import org.springframework.beans.factory.support.BeanDefinitionRegistry;
28+
import org.springframework.beans.factory.support.BeanDefinitionRegistryPostProcessor;
29+
import org.springframework.beans.factory.support.RootBeanDefinition;
2130
import org.springframework.boot.autoconfigure.AutoConfigureAfter;
2231
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
2332
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
2433
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
34+
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
2535
import org.springframework.boot.autoconfigure.condition.ConditionalOnWebApplication;
2636
import org.springframework.boot.autoconfigure.condition.ConditionalOnWebApplication.Type;
2737
import org.springframework.boot.autoconfigure.web.servlet.ServletWebServerFactoryAutoConfiguration;
2838
import org.springframework.boot.context.properties.EnableConfigurationProperties;
39+
import org.springframework.boot.context.properties.bind.Bindable;
40+
import org.springframework.boot.context.properties.bind.Binder;
2941
import org.springframework.boot.web.servlet.ServletRegistrationBean;
3042
import org.springframework.context.ApplicationContext;
43+
import org.springframework.context.ApplicationContextAware;
3144
import org.springframework.context.annotation.Bean;
3245
import org.springframework.context.annotation.Configuration;
46+
import org.springframework.core.io.Resource;
47+
import org.springframework.util.StringUtils;
3348
import org.springframework.ws.config.annotation.EnableWs;
3449
import org.springframework.ws.config.annotation.WsConfigurationSupport;
3550
import org.springframework.ws.transport.http.MessageDispatcherServlet;
51+
import org.springframework.ws.wsdl.wsdl11.SimpleWsdl11Definition;
52+
import org.springframework.xml.xsd.SimpleXsdSchema;
3653

3754
/**
3855
* {@link EnableAutoConfiguration Auto-configuration} for Spring Web Services.
@@ -72,10 +89,77 @@ public ServletRegistrationBean<MessageDispatcherServlet> messageDispatcherServle
7289
return registration;
7390
}
7491

92+
@Bean
93+
@ConditionalOnProperty(prefix = "spring.webservices", name = "wsdl-locations")
94+
public static WsdlDefinitionBeanFactoryPostProcessor wsdlDefinitionBeanFactoryPostProcessor() {
95+
return new WsdlDefinitionBeanFactoryPostProcessor();
96+
}
97+
7598
@Configuration
7699
@EnableWs
77100
protected static class WsConfiguration {
78101

79102
}
80103

104+
private static class WsdlDefinitionBeanFactoryPostProcessor
105+
implements BeanDefinitionRegistryPostProcessor, ApplicationContextAware {
106+
107+
private ApplicationContext applicationContext;
108+
109+
@Override
110+
public void setApplicationContext(ApplicationContext applicationContext) {
111+
this.applicationContext = applicationContext;
112+
}
113+
114+
@Override
115+
public void postProcessBeanDefinitionRegistry(BeanDefinitionRegistry registry)
116+
throws BeansException {
117+
Binder binder = Binder.get(this.applicationContext.getEnvironment());
118+
List<String> wsdlLocations = binder
119+
.bind("spring.webservices.wsdl-locations",
120+
Bindable.listOf(String.class))
121+
.orElse(Collections.emptyList());
122+
for (String wsdlLocation : wsdlLocations) {
123+
registerBeans(wsdlLocation, "*.wsdl", SimpleWsdl11Definition.class, registry);
124+
registerBeans(wsdlLocation, "*.xsd", SimpleXsdSchema.class, registry);
125+
}
126+
}
127+
128+
@Override
129+
public void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory)
130+
throws BeansException {
131+
}
132+
133+
private void registerBeans(String location, String pattern, Class<?> type,
134+
BeanDefinitionRegistry registry) {
135+
for (Resource resource : getResources(location, pattern)) {
136+
RootBeanDefinition beanDefinition = new RootBeanDefinition(type);
137+
ConstructorArgumentValues constructorArguments = new ConstructorArgumentValues();
138+
constructorArguments.addIndexedArgumentValue(0, resource);
139+
beanDefinition.setConstructorArgumentValues(constructorArguments);
140+
registry.registerBeanDefinition(
141+
StringUtils.stripFilenameExtension(resource.getFilename()),
142+
beanDefinition);
143+
}
144+
}
145+
146+
private Resource[] getResources(String location, String pattern) {
147+
try {
148+
return this.applicationContext
149+
.getResources(ensureTrailingSlash(location) + pattern);
150+
}
151+
catch (IOException e) {
152+
return new Resource[0];
153+
}
154+
}
155+
156+
private static String ensureTrailingSlash(String path) {
157+
if (!path.endsWith("/")) {
158+
return path + "/";
159+
}
160+
return path;
161+
}
162+
163+
}
164+
81165
}

spring-boot-autoconfigure/src/main/resources/META-INF/additional-spring-configuration-metadata.json

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1183,6 +1183,11 @@
11831183
{
11841184
"name": "spring.thymeleaf.suffix",
11851185
"defaultValue": ".html"
1186+
},
1187+
{
1188+
"name": "spring.webservices.wsdl-locations",
1189+
"type": "java.util.List<java.lang.String>",
1190+
"description": "Comma-separated list of locations of WSDLs and accompanying XSDs to be exposed as beans."
11861191
}
11871192
],"hints": [
11881193
{

spring-boot-autoconfigure/src/test/java/org/springframework/boot/autoconfigure/webservices/WebServicesAutoConfigurationTests.java

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,8 @@
2626
import org.springframework.boot.web.servlet.ServletRegistrationBean;
2727
import org.springframework.context.ApplicationContext;
2828
import org.springframework.test.util.ReflectionTestUtils;
29+
import org.springframework.ws.wsdl.wsdl11.SimpleWsdl11Definition;
30+
import org.springframework.xml.xsd.SimpleXsdSchema;
2931

3032
import static org.assertj.core.api.Assertions.assertThat;
3133

@@ -90,6 +92,18 @@ public void customInitParameters() {
9092
.containsEntry("key2", "value2"));
9193
}
9294

95+
@Test
96+
public void withWsdlBeans() {
97+
this.contextRunner
98+
.withPropertyValues("spring.webservices.wsdl-locations=classpath:/wsdl")
99+
.run(context -> {
100+
assertThat(context.getBeansOfType(SimpleWsdl11Definition.class))
101+
.hasSize(1).containsKey("service");
102+
assertThat(context.getBeansOfType(SimpleXsdSchema.class)).hasSize(1)
103+
.containsKey("types");
104+
});
105+
}
106+
93107
private Collection<String> getUrlMappings(ApplicationContext context) {
94108
return getServletRegistrationBean(context).getUrlMappings();
95109
}
Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,49 @@
1+
<?xml version="1.0" encoding="UTF-8"?>
2+
<wsdl:definitions xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
3+
xmlns:tns="http://www.springframework.org/spring-ws/wsdl"
4+
xmlns:wsdlsoap="http://schemas.xmlsoap.org/wsdl/soap/"
5+
targetNamespace="http://www.springframework.org/spring-ws/wsdl">
6+
7+
<wsdl:types>
8+
<xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema" elementFormDefault="qualified"
9+
targetNamespace="http://www.springframework.org/spring-ws/wsdl">
10+
<xsd:element name="request" type="xsd:string"/>
11+
<xsd:element name="response" type="xsd:string"/>
12+
</xsd:schema>
13+
</wsdl:types>
14+
15+
<wsdl:message name="responseMessage">
16+
<wsdl:part name="body" element="tns:response"/>
17+
</wsdl:message>
18+
19+
<wsdl:message name="requestMessage">
20+
<wsdl:part name="body" element="tns:request"/>
21+
</wsdl:message>
22+
23+
<wsdl:portType name="portType">
24+
<wsdl:operation name="operation">
25+
<wsdl:input message="tns:requestMessage" name="request"/>
26+
<wsdl:output message="tns:responseMessage" name="response"/>
27+
</wsdl:operation>
28+
</wsdl:portType>
29+
30+
<wsdl:binding name="binding" type="tns:portType">
31+
<wsdlsoap:binding style="document" transport="http://schemas.xmlsoap.org/soap/http"/>
32+
<wsdl:operation name="operation">
33+
<wsdlsoap:operation soapAction=""/>
34+
<wsdl:input name="request">
35+
<wsdlsoap:body use="literal"/>
36+
</wsdl:input>
37+
<wsdl:output name="response">
38+
<wsdlsoap:body use="literal"/>
39+
</wsdl:output>
40+
</wsdl:operation>
41+
</wsdl:binding>
42+
43+
<wsdl:service name="service">
44+
<wsdl:port binding="tns:binding" name="port">
45+
<wsdlsoap:address location="/services"/>
46+
</wsdl:port>
47+
</wsdl:service>
48+
</wsdl:definitions>
49+
Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
<?xml version="1.0" encoding="UTF-8"?>
2+
<schema xmlns="http://www.w3.org/2001/XMLSchema" elementFormDefault="qualified"
3+
targetNamespace="http://www.springframework.org/spring-ws/wsdl/schemas">
4+
<element name="request" type="string"/>
5+
<element name="response" type="string"/>
6+
</schema>

spring-boot-docs/src/main/asciidoc/appendix-application-properties.adoc

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -472,6 +472,7 @@ content into your application; rather pick only the properties that you need.
472472
spring.webservices.path=/services # Path that serves as the base URI for the services.
473473
spring.webservices.servlet.init= # Servlet init parameters to pass to Spring Web Services.
474474
spring.webservices.servlet.load-on-startup=-1 # Load on startup priority of the Spring Web Services servlet.
475+
spring.webservices.wsdl-locations= # Comma-separated list of locations of WSDLs and accompanying XSDs to be exposed as beans.
475476
476477
477478
[[common-application-properties-security]]

spring-boot-docs/src/main/asciidoc/spring-boot-features.adoc

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6560,6 +6560,15 @@ your `Endpoints`.
65606560
The {spring-webservices-reference}[Spring Web Services features] can be easily accessed
65616561
via the `spring-boot-starter-webservices` module.
65626562

6563+
`SimpleWsdl11Definition` and `SimpleXsdSchema` beans can be automatically created for your
6564+
WSDLs and XSDs respectively. To do so, configure their location:
6565+
6566+
6567+
[source,properties,indent=0]
6568+
----
6569+
spring.webservices.wsdl-locations=classpath:/wsdl
6570+
----
6571+
65636572

65646573

65656574
[[boot-features-developing-auto-configuration]]

spring-boot-samples/spring-boot-sample-webservices/src/main/java/sample/webservices/WebServiceConfig.java

Lines changed: 0 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -18,10 +18,8 @@
1818

1919
import org.springframework.context.annotation.Bean;
2020
import org.springframework.context.annotation.Configuration;
21-
import org.springframework.core.io.ClassPathResource;
2221
import org.springframework.ws.config.annotation.WsConfigurerAdapter;
2322
import org.springframework.ws.wsdl.wsdl11.DefaultWsdl11Definition;
24-
import org.springframework.xml.xsd.SimpleXsdSchema;
2523
import org.springframework.xml.xsd.XsdSchema;
2624

2725
@Configuration
@@ -37,9 +35,4 @@ public DefaultWsdl11Definition defaultWsdl11Definition(XsdSchema countriesSchema
3735
return wsdl;
3836
}
3937

40-
@Bean
41-
public XsdSchema countriesSchema() {
42-
return new SimpleXsdSchema(new ClassPathResource("META-INF/schemas/hr.xsd"));
43-
}
44-
4538
}
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
spring.webservices.wsdl-locations=classpath:META-INF/schemas/

0 commit comments

Comments
 (0)