2015-03-06 23:57:32 +08:00
|
|
|
[[web-integration]]
|
2017-10-11 04:12:12 +08:00
|
|
|
= Other Web Frameworks
|
2015-03-06 23:57:32 +08:00
|
|
|
|
2017-10-04 06:06:13 +08:00
|
|
|
This chapter details Spring's integration with third party web frameworks.
|
2015-03-06 23:57:32 +08:00
|
|
|
|
|
|
|
|
One of the core value propositions of the Spring Framework is that of enabling
|
2018-09-17 22:36:43 +08:00
|
|
|
_choice_. In a general sense, Spring does not force you to use or buy into any
|
2015-03-06 23:57:32 +08:00
|
|
|
particular architecture, technology, or methodology (although it certainly recommends
|
|
|
|
|
some over others). This freedom to pick and choose the architecture, technology, or
|
|
|
|
|
methodology that is most relevant to a developer and their development team is
|
|
|
|
|
arguably most evident in the web area, where Spring provides its own web framework
|
2018-09-17 22:36:43 +08:00
|
|
|
(<<mvc,Spring MVC>>) while, at the same time, providing integration with a number of
|
2017-10-04 06:06:13 +08:00
|
|
|
popular third party web frameworks.
|
2015-03-06 23:57:32 +08:00
|
|
|
|
|
|
|
|
|
2017-10-19 02:24:17 +08:00
|
|
|
|
2018-10-25 21:15:58 +08:00
|
|
|
|
2015-03-06 23:57:32 +08:00
|
|
|
[[web-integration-common]]
|
2018-09-17 22:36:43 +08:00
|
|
|
== Common Configuration
|
2018-10-25 21:15:58 +08:00
|
|
|
|
2015-03-06 23:57:32 +08:00
|
|
|
Before diving into the integration specifics of each supported web framework, let us
|
2018-09-17 22:36:43 +08:00
|
|
|
first take a look at the Spring configuration that is not specific to any one web
|
2015-03-06 23:57:32 +08:00
|
|
|
framework. (This section is equally applicable to Spring's own web framework, Spring
|
|
|
|
|
MVC.)
|
|
|
|
|
|
2018-09-17 22:36:43 +08:00
|
|
|
One of the concepts (for want of a better word) espoused by Spring's lightweight
|
|
|
|
|
application model is that of a layered architecture. Remember that in a "`classic`"
|
|
|
|
|
layered architecture, the web layer is but one of many layers. It serves as one of the
|
|
|
|
|
entry points into a server-side application, and it delegates to service objects
|
|
|
|
|
(facades) that are defined in a service layer to satisfy business-specific (and
|
2015-03-06 23:57:32 +08:00
|
|
|
presentation-technology agnostic) use cases. In Spring, these service objects, any other
|
2018-09-17 22:36:43 +08:00
|
|
|
business-specific objects, data-access objects, and others exist in a distinct "`business
|
|
|
|
|
context`", which contains no web or presentation layer objects (presentation objects
|
|
|
|
|
,such as Spring MVC controllers, are typically configured in a distinct "`presentation
|
|
|
|
|
context`"). This section details how you can configure a Spring container (a
|
|
|
|
|
`WebApplicationContext`) that contains all of the 'business beans' in your application.
|
2015-03-06 23:57:32 +08:00
|
|
|
|
2018-09-17 22:36:43 +08:00
|
|
|
Moving on to specifics, all you one need to do is declare a
|
2015-10-27 21:31:00 +08:00
|
|
|
{api-spring-framework}/web/context/ContextLoaderListener.html[`ContextLoaderListener`]
|
2018-09-17 22:36:43 +08:00
|
|
|
in the standard Java EE servlet `web.xml` file of your web application and add a
|
2015-03-06 23:57:32 +08:00
|
|
|
`contextConfigLocation`<context-param/> section (in the same file) that defines which
|
|
|
|
|
set of Spring XML configuration files to load.
|
|
|
|
|
|
2018-09-17 22:36:43 +08:00
|
|
|
Consider the following `<listener/>` configuration:
|
2015-03-06 23:57:32 +08:00
|
|
|
|
2018-09-17 22:36:43 +08:00
|
|
|
====
|
2015-03-06 23:57:32 +08:00
|
|
|
[source,xml,indent=0]
|
|
|
|
|
[subs="verbatim,quotes"]
|
|
|
|
|
----
|
|
|
|
|
<listener>
|
|
|
|
|
<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
|
|
|
|
|
</listener>
|
|
|
|
|
----
|
2018-09-17 22:36:43 +08:00
|
|
|
====
|
2015-03-06 23:57:32 +08:00
|
|
|
|
2018-09-17 22:36:43 +08:00
|
|
|
Further consider the following `<context-param/>` configuration:
|
2015-03-06 23:57:32 +08:00
|
|
|
|
2018-09-17 22:36:43 +08:00
|
|
|
====
|
2015-03-06 23:57:32 +08:00
|
|
|
[source,xml,indent=0]
|
|
|
|
|
[subs="verbatim,quotes"]
|
|
|
|
|
----
|
|
|
|
|
<context-param>
|
|
|
|
|
<param-name>contextConfigLocation</param-name>
|
|
|
|
|
<param-value>/WEB-INF/applicationContext*.xml</param-value>
|
|
|
|
|
</context-param>
|
|
|
|
|
----
|
2018-09-17 22:36:43 +08:00
|
|
|
====
|
2015-03-06 23:57:32 +08:00
|
|
|
|
2018-09-17 22:36:43 +08:00
|
|
|
If you do not specify the `contextConfigLocation` context parameter, the
|
|
|
|
|
`ContextLoaderListener` looks for a file called `/WEB-INF/applicationContext.xml` to
|
2015-03-06 23:57:32 +08:00
|
|
|
load. Once the context files are loaded, Spring creates a
|
2015-10-27 21:31:00 +08:00
|
|
|
{api-spring-framework}/web/context/WebApplicationContext.html[`WebApplicationContext`]
|
2015-03-06 23:57:32 +08:00
|
|
|
object based on the bean definitions and stores it in the `ServletContext` of the web
|
|
|
|
|
application.
|
|
|
|
|
|
2018-09-17 22:36:43 +08:00
|
|
|
All Java web frameworks are built on top of the Servlet API, so you can use the
|
|
|
|
|
following code snippet to get access to this "`business context`" `ApplicationContext`
|
2015-03-06 23:57:32 +08:00
|
|
|
created by the `ContextLoaderListener`.
|
|
|
|
|
|
2018-09-17 22:36:43 +08:00
|
|
|
The following example shows how to get the `WebApplicationContext`:
|
|
|
|
|
|
|
|
|
|
====
|
2015-03-06 23:57:32 +08:00
|
|
|
[source,java,indent=0]
|
|
|
|
|
[subs="verbatim,quotes"]
|
|
|
|
|
----
|
|
|
|
|
WebApplicationContext ctx = WebApplicationContextUtils.getWebApplicationContext(servletContext);
|
|
|
|
|
----
|
2018-09-17 22:36:43 +08:00
|
|
|
====
|
2015-03-06 23:57:32 +08:00
|
|
|
|
|
|
|
|
The
|
2015-10-27 21:31:00 +08:00
|
|
|
{api-spring-framework}/web/context/support/WebApplicationContextUtils.html[`WebApplicationContextUtils`]
|
2018-09-17 22:36:43 +08:00
|
|
|
class is for convenience, so you need not remember the name of the `ServletContext`
|
|
|
|
|
attribute. Its `getWebApplicationContext()` method returns `null` if an object
|
|
|
|
|
does not exist under the `WebApplicationContext.ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE`
|
|
|
|
|
key. Rather than risk getting `NullPointerExceptions` in your application, it is better
|
2015-03-06 23:57:32 +08:00
|
|
|
to use the `getRequiredWebApplicationContext()` method. This method throws an exception
|
|
|
|
|
when the `ApplicationContext` is missing.
|
|
|
|
|
|
|
|
|
|
Once you have a reference to the `WebApplicationContext`, you can retrieve beans by
|
|
|
|
|
their name or type. Most developers retrieve beans by name and then cast them to one of
|
|
|
|
|
their implemented interfaces.
|
|
|
|
|
|
|
|
|
|
Fortunately, most of the frameworks in this section have simpler ways of looking up
|
|
|
|
|
beans. Not only do they make it easy to get beans from a Spring container, but they also
|
2018-09-17 22:36:43 +08:00
|
|
|
let you use dependency injection on their controllers. Each web framework section
|
2015-03-06 23:57:32 +08:00
|
|
|
has more detail on its specific integration strategies.
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2018-10-25 21:15:58 +08:00
|
|
|
|
2015-03-06 23:57:32 +08:00
|
|
|
[[jsf]]
|
2017-10-19 02:24:17 +08:00
|
|
|
== JSF
|
2018-09-17 22:36:43 +08:00
|
|
|
|
2015-03-06 23:57:32 +08:00
|
|
|
JavaServer Faces (JSF) is the JCP's standard component-based, event-driven web user
|
|
|
|
|
interface framework. As of Java EE 5, it is an official part of the Java EE umbrella.
|
|
|
|
|
|
|
|
|
|
For a popular JSF runtime as well as for popular JSF component libraries, check out the
|
|
|
|
|
http://myfaces.apache.org/[Apache MyFaces project]. The MyFaces project also provides
|
2018-09-17 22:36:43 +08:00
|
|
|
common JSF extensions, such as http://myfaces.apache.org/orchestra/[MyFaces Orchestra]
|
|
|
|
|
(a Spring-based JSF extension that provides rich conversation scope support).
|
2015-03-06 23:57:32 +08:00
|
|
|
|
2018-09-17 22:36:43 +08:00
|
|
|
NOTE: Spring Web Flow 2.0 provides rich JSF support through its newly established Spring Faces
|
2015-03-06 23:57:32 +08:00
|
|
|
module, both for JSF-centric usage (as described in this section) and for Spring-centric
|
2018-09-17 22:36:43 +08:00
|
|
|
usage (using JSF views within a Spring MVC dispatcher). See the
|
|
|
|
|
http://projects.spring.io/spring-webflow[Spring Web Flow website] for details.
|
2015-03-06 23:57:32 +08:00
|
|
|
|
|
|
|
|
The key element in Spring's JSF integration is the JSF `ELResolver` mechanism.
|
|
|
|
|
|
2017-10-19 02:24:17 +08:00
|
|
|
|
|
|
|
|
|
2015-03-06 23:57:32 +08:00
|
|
|
[[jsf-springbeanfaceselresolver]]
|
2017-10-07 01:11:15 +08:00
|
|
|
=== Spring Bean Resolver
|
2018-09-17 22:36:43 +08:00
|
|
|
|
2017-10-19 02:24:17 +08:00
|
|
|
`SpringBeanFacesELResolver` is a JSF 1.2+ compliant `ELResolver` implementation,
|
2018-09-17 22:36:43 +08:00
|
|
|
integrating with the standard Unified EL as used by JSF 1.2 and JSP 2.1. As
|
|
|
|
|
`SpringBeanVariableResolver`, it delegates to Spring's "`business context`"
|
|
|
|
|
`WebApplicationContext` first and then to the default resolver of the underlying JSF
|
2015-03-06 23:57:32 +08:00
|
|
|
implementation.
|
|
|
|
|
|
2018-09-17 22:36:43 +08:00
|
|
|
Configuration-wise, you can define `SpringBeanFacesELResolver` in your JSF
|
|
|
|
|
`faces-context.xml` file, as the following example shows:
|
2015-03-06 23:57:32 +08:00
|
|
|
|
2018-09-17 22:36:43 +08:00
|
|
|
====
|
2015-03-06 23:57:32 +08:00
|
|
|
[source,xml,indent=0]
|
|
|
|
|
[subs="verbatim,quotes"]
|
|
|
|
|
----
|
|
|
|
|
<faces-config>
|
|
|
|
|
<application>
|
|
|
|
|
<el-resolver>org.springframework.web.jsf.el.SpringBeanFacesELResolver</el-resolver>
|
|
|
|
|
...
|
|
|
|
|
</application>
|
|
|
|
|
</faces-config>
|
|
|
|
|
----
|
2018-09-17 22:36:43 +08:00
|
|
|
====
|
2015-03-06 23:57:32 +08:00
|
|
|
|
|
|
|
|
|
2017-10-19 02:24:17 +08:00
|
|
|
|
2015-03-06 23:57:32 +08:00
|
|
|
[[jsf-facescontextutils]]
|
2018-09-17 22:36:43 +08:00
|
|
|
=== Using `FacesContextUtils`
|
|
|
|
|
|
|
|
|
|
A custom `VariableResolver` works well when mapping your properties to beans
|
|
|
|
|
in `faces-config.xml`, but, at times, you may need to explicitly grab a bean. The
|
2015-10-27 21:31:00 +08:00
|
|
|
{api-spring-framework}/web/jsf/FacesContextUtils.html[`FacesContextUtils`]
|
2015-03-06 23:57:32 +08:00
|
|
|
class makes this easy. It is similar to `WebApplicationContextUtils`, except that it
|
|
|
|
|
takes a `FacesContext` parameter rather than a `ServletContext` parameter.
|
|
|
|
|
|
2018-09-17 22:36:43 +08:00
|
|
|
The following example shows how to use `FacesContextUtils`:
|
|
|
|
|
|
|
|
|
|
====
|
2015-03-06 23:57:32 +08:00
|
|
|
[source,java,indent=0]
|
|
|
|
|
[subs="verbatim,quotes"]
|
|
|
|
|
----
|
|
|
|
|
ApplicationContext ctx = FacesContextUtils.getWebApplicationContext(FacesContext.getCurrentInstance());
|
|
|
|
|
----
|
2018-09-17 22:36:43 +08:00
|
|
|
====
|
2015-03-06 23:57:32 +08:00
|
|
|
|
|
|
|
|
|
2017-10-19 02:24:17 +08:00
|
|
|
|
2018-10-25 21:15:58 +08:00
|
|
|
|
2015-03-06 23:57:32 +08:00
|
|
|
[[struts]]
|
|
|
|
|
== Apache Struts 2.x
|
2018-09-17 22:36:43 +08:00
|
|
|
|
|
|
|
|
Invented by Craig McClanahan, http://struts.apache.org[Struts] is an open-source project
|
2015-03-06 23:57:32 +08:00
|
|
|
hosted by the Apache Software Foundation. At the time, it greatly simplified the
|
|
|
|
|
JSP/Servlet programming paradigm and won over many developers who were using proprietary
|
2018-09-17 22:36:43 +08:00
|
|
|
frameworks. It simplified the programming model, it was open source (and thus free, as in
|
|
|
|
|
beer), and it had a large community, which let the project grow and become popular
|
2015-03-06 23:57:32 +08:00
|
|
|
among Java web developers.
|
|
|
|
|
|
|
|
|
|
Check out the Struts
|
|
|
|
|
https://struts.apache.org/release/2.3.x/docs/spring-plugin.html[Spring Plugin] for the
|
|
|
|
|
built-in Spring integration shipped with Struts.
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2018-10-25 21:15:58 +08:00
|
|
|
|
2015-03-06 23:57:32 +08:00
|
|
|
[[tapestry]]
|
|
|
|
|
== Tapestry 5.x
|
|
|
|
|
|
2018-09-17 22:36:43 +08:00
|
|
|
http://tapestry.apache.org/[Tapestry] is a ""Component oriented framework for creating dynamic, robust,
|
|
|
|
|
highly scalable web applications in Java.""
|
2015-03-06 23:57:32 +08:00
|
|
|
|
|
|
|
|
While Spring has its own <<mvc,powerful web layer>>, there are a number of unique
|
2018-09-17 22:36:43 +08:00
|
|
|
advantages to building an enterprise Java application by using a combination of Tapestry
|
2015-03-06 23:57:32 +08:00
|
|
|
for the web user interface and the Spring container for the lower layers.
|
|
|
|
|
|
2018-09-17 22:36:43 +08:00
|
|
|
For more information, see Tapestry's dedicated
|
2015-03-06 23:57:32 +08:00
|
|
|
https://tapestry.apache.org/integrating-with-spring-framework.html[integration module for
|
|
|
|
|
Spring].
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
2018-10-25 21:15:58 +08:00
|
|
|
|
2015-03-06 23:57:32 +08:00
|
|
|
[[web-integration-resources]]
|
|
|
|
|
== Further Resources
|
2018-10-25 21:15:58 +08:00
|
|
|
|
2018-09-17 22:36:43 +08:00
|
|
|
The following links go to further resources about the various web frameworks described in this
|
2015-03-06 23:57:32 +08:00
|
|
|
chapter.
|
|
|
|
|
|
|
|
|
|
* The http://www.oracle.com/technetwork/java/javaee/javaserverfaces-139869.html[JSF] homepage
|
|
|
|
|
* The http://struts.apache.org/[Struts] homepage
|
|
|
|
|
* The http://tapestry.apache.org/[Tapestry] homepage
|