使用 SpringSource Slices 构建模块化 Web 应用程序

工程 | Rob Harrop | 2009年6月22日 | ...

更新:为 Git 添加了子模块说明。

我之前谈过关于提供对真正模块化应用程序的支持,我很高兴地宣布您现在可以访问 **SpringSource Slices** 的早期原型代码。

构建和安装

您可以从我们的 Git 仓库访问源代码。

git clone git://git.springsource.org/slices/slices.git
git submodule init
git submodule update

要构建 Slices 的打包版本,只需从 build-slices 目录运行 ant clean jar package

cd slices/build-slices
ant clean jar package

这将在 target/artifacts 中生成一个 zip 文件,其中包含 Slices 子系统,然后可以将其安装到 dm Server 2.0 之上。

安装 Slices 只需将新子系统添加到 dm Server,然后更新 dmServer 的配置文件以启动新子系统即可。Slices 应该适用于任何最近的 dm Server 2.0 快照版本。这里我使用的是 2.0.0.CI-R326-B274,我已经下载并解压缩到我的桌面上。

 unzip target/artifacts/springsource-slices-BUILD-20090622083953.zip -d ~/Desktop/springsource-dm-server-2.0.0.CI-R326-B274

接下来,必须更新 dm Server 的 kernel.properties 配置以包含新的 slices 子系统。打开 dm Server 安装目录下的 config/kernel.properties 文件,并编辑配置文件部分以列出 slices 子系统并为配置文件提供一个合适的名称(我将其命名为 slices)。

#######################
# Profile Configuration
#######################
profile.name=slices
profile.subsystems=	com.springsource.server.web,com.springsource.osgi.slices
profile.optionalSubsystems=

保存更新的文件,您就可以尝试 Slices 示例应用程序了。

尝试示例应用程序

Slices 存储库包含 Spring 3 的 PetClinic 示例的一个版本,在我们向 Slices 添加新功能时,我们不断对其进行增强和改进。

在使用示例之前,必须将其依赖项添加到您的 dm Server 安装中。依赖项列在示例的 dependencies.txt 文件中。将列出的每个依赖项下载到安装目录的 repository/bundles/usr 目录。接下来,使用 -clean 启动选项启动 dm Server。

./bin/startup.sh -clean

现在是构建和部署示例的时候了。进入 slices/samples/slices-petclinic/com.springsource.slices.petclinic.host 目录并运行 ant clean jar

cd samples/slices-petclinic/com.springsource.slices.petclinic.host
ant clean jar

然后可以通过将生成的 war 文件复制到 dm Server 的 pickup 目录来部署主机。

 cp target/artifacts/com.springsource.slices.petclinic.host.war ~/Desktop/springsource-dm-server-2.0.0.CI-R326-B274/pickup/

现在可以通过 https://127.0.0.1:8080/petclinic 访问主机。

petclinic-no-slices

接下来,进入 slices/samples/slices-petclinic/com.springsource.slices.petclinic.appointments 目录并运行 ant clean jar 以构建 appointments 切片。

cd samples/slices-petclinic/com.springsource.slices.petclinic.appointments
ant clean jar

现在可以通过将生成的 war 文件复制到 dm Server 的 pickup 目录来部署切片。

cp target/artifacts/com.springsource.slices.petclinic.appointments.war  ~/Desktop/springsource-dm-server-2.0.0.CI-R326-B274/pickup/

刷新 https://127.0.0.1:8080/petclinic,它现在将反映 appointments 切片的存在,并显示一个新的 Appointments 链接。

petclinic-appointments-slice

如果需要,您现在可以从 pickup 目录中删除 appointments war 以查看切片再次消失。

Slices 应用程序的结构

使用 Slices,您可以从多个 OSGi 捆绑包构建一个 Web 应用程序,每个捆绑包都为应用程序 URL 空间的不同子部分提供内容。Slices 应用程序以父子结构排列,每个应用程序最多有一个父应用程序(称为 **主机**)和零个或多个子应用程序(称为 **切片**)。我们正在开发一个简单的 Slices 示例,如下所示。

slice-anatomy

主机内部

petclinic.host 捆绑包包含所有共享内容,例如图像和 CSS,以及用于提供主页的控制器和 JSP。主机捆绑包只是一个符合 RFC66 的 Web 捆绑包,其 web.xml 中配置了 SliceHostFilter。以下代码片段显示了来自 petclinic.host 捆绑包的 web.xml
<?xml version="1.0" encoding="UTF-8"?>
<web-app version="2.5" xmlns="http://java.sun.com/xml/ns/javaee"
	xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
	xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd">
	
    <filter>
    	<filter-name>host-filter</filter-name>
    	<filter-class>com.springsource.osgi.slices.core.SliceHostFilter</filter-class>
    </filter>

    <filter-mapping>
        <filter-name>host-filter</filter-name>
        <url-pattern>/*</url-pattern>
    </filter-mapping>

	<!-- Enables clean URLs with JSP views e.g. /welcome instead of /app/welcome -->
	<filter>
		<filter-name>UrlRewriteFilter</filter-name>
		<filter-class>org.tuckey.web.filters.urlrewrite.UrlRewriteFilter</filter-class>
	</filter>

	<filter-mapping>
		<filter-name>UrlRewriteFilter</filter-name>
		<url-pattern>/*</url-pattern>
	</filter-mapping>
		
	<!-- Handles all requests into the application -->
	<servlet>
		<servlet-name>Spring MVC Dispatcher Servlet</servlet-name>
		<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
		<init-param>
			<param-name>contextConfigLocation</param-name>
			<param-value>
				/WEB-INF/spring/*.xml
			</param-value>
		</init-param>
		<load-on-startup>1</load-on-startup>
	</servlet>
		
	<!-- Maps all /app requests to the DispatcherServlet for handling -->
	<servlet-mapping>
		<servlet-name>Spring MVC Dispatcher Servlet</servlet-name>
		<url-pattern>/app/*</url-pattern>
	</servlet-mapping>

  	<!-- Serves static resource content from the webapp root & .jar files such as spring-js.jar -->
	<servlet>
		<servlet-name>Resources Servlet</servlet-name>
		<servlet-class>org.springframework.js.resource.ResourceServlet</servlet-class>
		<load-on-startup>0</load-on-startup>
	</servlet>
		
	<!-- Map all /resources requests to the Resource Servlet for handling -->
	<servlet-mapping>
		<servlet-name>Resources Servlet</servlet-name>
		<url-pattern>/resources/*</url-pattern>
	</servlet-mapping>	
	
</web-app>

如您所见,主机可以拥有任何正常的 servlet 和过滤器映射,但它需要 SliceHostFilter 才能将请求路由到其切片。

切片内部

切片是一个看起来和功能都像标准 RFC66 Web 捆绑包的捆绑包,除了它没有自己的 ServletContext。相反,切片在其主机的 ServletContext 下运行。

Slices 的主要设计目标之一是确保切片开发尽可能类似于标准 Web 应用程序开发。为此,您可以使用 web.xml 以与为任何应用程序创建 Web 内容完全相同的方式创建切片 Web 内容。这是来自 petclinic.appointments 捆绑包的 web.xml

<?xml version="1.0" encoding="UTF-8"?>
<web-app version="2.5" xmlns="http://java.sun.com/xml/ns/javaee"
	xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
	xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd">

	<!-- Handles all requests into the application -->
	<servlet>
		<servlet-name>appointments</servlet-name>
		<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>		
		<load-on-startup>1</load-on-startup>
	</servlet>
		
	<!-- Maps all /app requests to the DispatcherServlet for handling -->
	<servlet-mapping>
		<servlet-name>appointments</servlet-name>
		<url-pattern>/app/*</url-pattern>
	</servlet-mapping>
	
</web-app>

appointments 切片只是委托到 Spring DispatcherServlet。可以在切片中照常使用 Spring MVC。

切片可以通过简单地引用切片本身不存在的资源名称来访问主机捆绑包中的资源。如果切片想要访问主机中的资源,即使它本身也具有同名资源,它也可以使用 host: 前缀来实现。

ServletContext context =  getServletContext();
context.getResource("host:/WEB-INF/some.config.xml");

切片需要定义它想要附加到的主机,并使用 Slice-Host 清单头来实现。 Slice-ContextPath 头定义了切片处理的 URL 部分。

Bundle-SymbolicName: petclininc.appointments
Slice-Host: petclinic.host;version="[1.0, 2.0)"
Slice-ContextPath: /appointments

切片生命周期

主机可以在没有任何相应的切片附加的情况下运行。当安装到服务器中的切片与主机匹配时,该切片将 **附加** 到主机。此时,与新附加的切片的 Slice-ContextPath 匹配的主机 URL 部分将路由到该切片。

当卸载切片时,路由到该切片的 URL 空间部分现在将直接路由到主机。通过这种方式,您可以在主机中创建内容来处理缺失的切片。

我今天可以在切片中做什么?

在撰写本文时,Slices 代码库在切片中支持以下功能。

  • Servlet 和 servlet 映射
  • JSP
  • Spring MVC
  • 切片本地会话
  • 自动回退到应用程序范围的会话
  • 通过 ServletContext 进行切片本地资源查找
  • 自动回退到主机中的资源查找
  • 使用 host: 进行显式主机资源查找

接下来是什么?

我们正在为 Slices 开发许多有趣的新功能,包括

  • 切片中的过滤器和过滤器映射
  • 切片中的侦听器
  • UI 组成框架。您可以在 Petclinic 示例中看到对此进行手动操作的方法。
  • Tiles 2 集成
  • 完整的示例应用程序
  • SpringSource Tool Suite 支持

如果您有任何功能建议或发现错误,请随时在 我们的 JIRA 上提出问题

如果您想密切关注进度,则可以关注我们的 Git 仓库和我们的 #dmserver Twitter 标签。

获取 Spring 新闻通讯

通过 Spring 新闻通讯保持联系

订阅

领先一步

VMware 提供培训和认证,以加速您的进步。

了解更多

获取支持

Tanzu Spring 在一个简单的订阅中提供 OpenJDK™、Spring 和 Apache Tomcat® 的支持和二进制文件。

了解更多

即将举行的活动

查看 Spring 社区中所有即将举行的活动。

查看全部