`
liukai
  • 浏览: 702161 次
  • 性别: Icon_minigender_1
  • 来自: 成都
社区版块
存档分类
最新评论

Spring3MVC和jQuery的集成

阅读更多
在本教程.我们将使用Spring MVC建立一个简单的基于jQuery的计算器AJAX应用.
为了便于对比.
我们将创建两个页面.
一个传统的页面.
一个是基于AJAX的页面.

什么是jQuery?

引用
Jquery是继prototype之后又一个优秀的Javascrīpt框架。它是轻量级的js库(压缩后只有21k) ,它兼容CSS3,还兼容各种浏览器 (IE 6.0+, FF 1.5+, Safari 2.0+, Opera 9.0+)。jQuery使用户能更方便地处理HTML documents、events、实现动画效果,并且方便地为网站提供AJAX交互。jQuery还有一个比较大的优势是,它的文档说明很全,而且各种应用也说得很详细,同时还有许多成熟的插件可供选择。jQuery能够使用户的html页保持代码和html内容分离,也就是说,不用再在html里面插入一堆js来调用命令了,只需定义id即可


JQuery官网

jQuery最新版本是1.5.1
在此教程我们使用1.4.4

jQuery下载地址


什么是AJAX?

引用
AJAX全称为“Asynchronous JavaScript and XML”(异步JavaScript和XML),是一种创建交互式网页应用的网页开发技术。根据Ajax提出者Jesse James Garrett建议[1],AJAX:

    * 使用XHTML+CSS来表示信息;
    * 使用JavaScript操作DOM(Document Object Model)进行动态显示及交互;
    * 使用XML和XSLT进行数据交换及相关操作;
    * 使用XMLHttpRequest对象与Web服务器进行异步数据交换;
    * 使用JavaScript将所有的东西绑定在一起。

类似于DHTML或LAMP,AJAX不是指一种单一的技术,而是有机地利用了一系列相关的技术。事实上,一些基于AJAX的“派生/合成”式(derivative/composite)的技术正在出现,如AFLAX。




我们的应用程序是一个能进行简单的算术运算:增加两个数字并显示他们的和.
这里有两张截图:
一张是非AJAX版本.




一张是AJAX版本.




两者没有什么不同.但是非AJAX版本的将会在另外一个页面显示结果.
我们会看到明显的页面刷新过程

而AJAX版本将在同一个页面上显示结果.
我们几乎感觉不到页面刷新.

在此之前我们添加Spring MVC所必须的配置.

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

	<servlet>
		<servlet-name>spring</servlet-name>
		<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
		<load-on-startup>1</load-on-startup>
	</servlet>

	<servlet-mapping>
		<servlet-name>spring</servlet-name>
		<url-pattern>/</url-pattern>
	</servlet-mapping>

	<listener>
		<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
	</listener>

</web-app>



在web.xml中我们定义servlet:spring.
按照惯例,我们必须声明一个spring-servle.xml


spring-servle.xml


<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
	xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:p="http://www.springframework.org/schema/p"
	xsi:schemaLocation="http://www.springframework.org/schema/beans 
	   		http://www.springframework.org/schema/beans/spring-beans-3.0.xsd">

	<!-- 定义一个视图解析器 -->
	<bean id="viewResolver"
		class="org.springframework.web.servlet.view.InternalResourceViewResolver"
		p:prefix="/WEB-INF/jsp/" p:suffix=".jsp" />

</beans>

这个XML配置声明一个视图解析器.在控制器中会根据JSP名映射到/ WEB-INF/jsp中相应的位置.

然后创建一个applicationContext.xml.

applicationContext.xml
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
	xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
	xmlns:context="http://www.springframework.org/schema/context"
	xmlns:mvc="http://www.springframework.org/schema/mvc"
	xsi:schemaLocation="http://www.springframework.org/schema/beans 
	   		http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
	   		http://www.springframework.org/schema/context
	   		http://www.springframework.org/schema/context/spring-context-3.0.xsd
			http://www.springframework.org/schema/mvc 
			http://www.springframework.org/schema/mvc/spring-mvc-3.0.xsd">

	<!-- 激活spring的注解. -->
	<context:annotation-config />

	<!-- 扫描注解组件并且自动的注入spring beans中. 
	例如,他会扫描@Controller 和@Service下的文件.所以确保此base-package设置正确. -->
	<context:component-scan base-package="org.liukai.tutorial" />

	<!-- 配置注解驱动的Spring MVC Controller 的编程模型.注:次标签只在 Servlet MVC工作! -->
	<mvc:annotation-driven />
	
</beans>




在webapp下创建一个resources的文件夹用于放置JS和CSS等静态文件.
如下图




然后就是在pom.xml添加必须的jar包





实现一个简单的 POJO service层

ArithmeticService.java

package org.liukai.tutorial.service;

import org.apache.log4j.Logger;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

@Service("arithmeticService")
@Transactional
public class ArithmeticService {

	protected static Logger logger = Logger.getLogger("service");
	
	/**
	 * 实现一个加法运算
	 */
	public Integer add(Integer operand1,Integer operand2){
		logger.debug("Adding two numbers");
		return operand1 + operand2;
	}
	
}



这是一个非常简单的POJO service,其中包含了一个实现加法运算的方法:add().



非AJAX版本

首先我们编写一个非AJAX版本的SpringMVC应用程序.

写一个处理用户请求的controller类:NonAjaxController.java

NonAjaxController.java

package org.liukai.tutorial.controller;

import javax.annotation.Resource;

import org.apache.log4j.Logger;
import org.liukai.tutorial.service.ArithmeticService;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RequestParam;

/**
 * 用于处理非AJAX运算.
 */
@Controller
@RequestMapping("/main/nonajax")
public class NonAjaxController {

	protected static Logger logger = Logger.getLogger("controller");

	@Resource(name = "arithmeticService")
	private ArithmeticService arithmeticService;

	/**
	 * 根据请求映射跳转到nonajax-add-page.jsp
	 */
	@RequestMapping(value = "/add", method = RequestMethod.GET)
	public String getNonAjaxAddPage() {
		logger.debug("Received request to show non-AJAX, ordinary add page");

		// 他将会解析 /WEB-INF/jsp/nonajax-add-page.jsp
		return "nonajax-add-page";
	}

	/**
	 * 提交表单并进行运算.
	 * @RequestParam表示从JSP页面接收值.
	 * 是springMVC重要的传递参数手段之一.
	 */
	@RequestMapping(value = "/add", method = RequestMethod.POST)
	public String add(
			@RequestParam(value = "inputNumber1", required = true) Integer inputNumber1,
			@RequestParam(value = "inputNumber2", required = true) Integer inputNumber2,
			Model model) {
		logger.debug("Received request to add two numbers");

		// 实现运算
		Integer sum = arithmeticService.add(inputNumber1, inputNumber2);

		// 添加到model返回到页面
		model.addAttribute("sum", sum);

		// 他将会解析 /WEB-INF/jsp/nonajax-add-result-page.jsp
		//并把model传递到该JSP页面.
		return "nonajax-add-result-page";
	}
}


这个controller声明了2个映射:
/main/nonajax/add    (GET) - 用于跳转到add页面
/main/nonajax/add    (POST) -计算值并将结果返回到指定的页面

下面是JSP页面

nonajax-add-page.jsp

<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
	<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
	
	<title>Spring MVC - jQuery 整合教程</title>
</head>
<body>

<h3>Spring MVC - jQuery 整合教程</h3>
<h4>Non-AJAX version</h4>

<c:url var="addUrl" value="/main/nonajax/add" />

<form method="POST" action="${addUrl}">

Demo 1 
<div style="border: 1px solid #ccc; width: 250px;">
	Add Two Numbers: <br/>
	<input id="inputNumber1" name="inputNumber1" type="text" size="5"> +
	<input id="inputNumber2" name="inputNumber2" type="text" size="5">
	<input type="submit" value="Add" /> <br/>
	Sum: (Result will be shown on another page)
</div>

</form>

</body>
</html>



nonajax-add-result-page.jsp

<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
	<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
	
	<title>Spring MVC - jQuery 整合教程</title>
</head>
<body>

<h3>Spring MVC - jQuery 整合教程</h3>
<h4>Non-AJAX version</h4>

Demo 1 Result
<div style="border: 1px solid #ccc; width: 250px;">
	Sum: ${sum}
</div>

</body>
</html>



启动web服务器.
我们添加两个数字:12和13.我们预期为25.
输入URL地址
http://localhost:8080/spring-jquery/main/nonajax/add



得到的结果如下:



注意:结果是在另外一个页面显示的.

AJAX版本

现在让我们使用AJAX版本来实现该功能.
首先还是controller

AjaxController.java
package org.liukai.tutorial.controller;

import javax.annotation.Resource;

import org.apache.log4j.Logger;
import org.liukai.tutorial.service.ArithmeticService;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.ResponseBody;

@Controller
@RequestMapping("/main/ajax")
public class AjaxController {

	protected static Logger logger = Logger.getLogger("controller");

	@Resource(name = "arithmeticService")
	private ArithmeticService arithmeticService;

	/**
	 * 根据映射跳转到指定的页面
	 */
	@RequestMapping(value = "/add", method = RequestMethod.GET)
	public String getAjaxAddPage() {
		logger.debug("Received request to show AJAX, add page");

		// 解析 /WEB-INF/jsp/ajax-add-page.jsp
		return "ajax-add-page";
	}

	/**
	 * 提交表单并进行运算.
	 */
	@RequestMapping(value = "/add", method = RequestMethod.POST)
	public @ResponseBody
	Integer add(
			@RequestParam(value = "inputNumber1", required = true) Integer inputNumber1,
			@RequestParam(value = "inputNumber2", required = true) Integer inputNumber2,
			Model model) {
		logger.debug("Received request to add two numbers");

		// 实现运算
		Integer sum = arithmeticService.add(inputNumber1, inputNumber2);

		// @ResponseBody 会自动的将返回值转换成JSON格式
		// 但是你必须添加jackson的jar包!!!
		return sum;
	}
}



该controll还是声明了两个映射:
/main/ajax/add     (GET) - 跳转到指定页面.
/main/ajax/add     (POST) - 实现加法的过程.


注意:
POST方法的映射将返回一个注解了@ResponseBody的Integer类型的整数.
这个注解(@ResponseBody)的意思表示:
Spring将返回的数据自动的转换为Json格式.
要实现@ResponseBody的注解必须导入Jackson的包.


Jackson是什么?
引用
Jackson 是一个 Java 用来处理 JSON 格式数据的类库,性能非常好。


我们可以在Jackson的官方网站上了解更多关于jackson的信息.

对于jackson的性能JavaEye已经有同学做了测试.json工具性能比较:json-lib和jackson进行Java对象到json字符串序列化

关于@ResponseBody更多信息可以看Spring官方BlogAjax Simplifications in Spring 3.0



@ResponseBody的用法实在是很简便.

以前我们处理AJAX是用类似下面的代码来进行的.

		JSONArray array = JSONArray.fromCollection(list);
		PrintWriter out = response.getWriter();
		out.write("{datalist:" + array + ",totalPages:" + totalPages
				+ ",curPage:" + toPage + ",pageCount:" + pageSize + ",total:"
				+ total + "}");
		out.flush();
		out.close();
		return null;


而现在我们只需要在方法返回对象前添加@ResponseBody即可,极大的简化了代码量.



关于JSP页面

ajax-add-page.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
	<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">

	<script type="text/javascript" src="/spring-jquery/resources/js/jquery/jquery-1.4.4.min.js"></script>
	
	<title>Spring MVC - jQuery 整合教程</title>

</head>
<body>

<h3>Spring MVC - jQuery 整合教程</h3>
<h4>AJAX version</h4>

Demo 1
<div style="border: 1px solid #ccc; width: 250px;">
	Add Two Numbers: <br/>
	<input id="inputNumber1" type="text" size="5"> +
	<input id="inputNumber2" type="text" size="5">
	<input type="submit" value="Add" onclick="add()" /> <br/>
	Sum: <span id="sum">(Result will be shown here)</span>
</div>


<script type="text/javascript"> 

function add() {
	$(function() {
		$.post("/spring-jquery/main/ajax/add",
					{ 	inputNumber1:  $("#inputNumber1").val(),
				  		inputNumber2:  $("#inputNumber2").val() },
						function(data){
							// data contains the result
							// Assign result to the sum id
							$("#sum").replaceWith('<span id="sum">'+ data + '</span>');
					});
	});
}

</script>
</body>
</html>


让我们运行web服务器.
http://localhost:8080/spring-jquery/main/ajax/add



输入结果后页面将没有任何动静.如果是用firebug.将会得到 $未定义的错误.
实际上就是jquery没有导入.
可是我们导入的路径的确是正确的啊!

出现这个结果的原因在于web.xml中的

<servlet-mapping>
		<servlet-name>spring</servlet-name>
		<url-pattern>/</url-pattern>
	</servlet-mapping>


他能使得我们的URL没有后缀.做到和JavaEye一样的REST风格的URL
而不是类似以前的http://****/**.do

但是这就有个问题了:
他会把所有的资源文件通过DispatcherServlet进行转发.
可是后缀是.js或.css的你转发给谁?
我们以前是用UrlRewriteFilter来进行URL的重定向.
现在我们通过
<mvc:resources location="/resources/" mapping="/resources/**"/>  

来避免DispatcherServlet对静态资源的处理.
但是注意一点.
此功能是在spring3.0.4出现的!所以spring3.0.4之前的版本是没有此注解的

关于这些方面的信息可以看JavaEye一位同学的Blog:
spring3.0.4 新增加的注解(mvc:resources)

所以在applicationContext.xml中我们还需要添加
<mvc:resources location="/resources/" mapping="/resources/**"/>  



applicationContext.xml

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
	xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
	xmlns:context="http://www.springframework.org/schema/context"
	xmlns:mvc="http://www.springframework.org/schema/mvc"
	xsi:schemaLocation="http://www.springframework.org/schema/beans 
	   		http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
	   		http://www.springframework.org/schema/context
	   		http://www.springframework.org/schema/context/spring-context-3.0.xsd
			http://www.springframework.org/schema/mvc 
			http://www.springframework.org/schema/mvc/spring-mvc-3.0.xsd">

	<!-- 激活spring的注解. -->
	<context:annotation-config />

	<!-- 扫描注解组件并且自动的注入spring beans中. 
	例如,他会扫描@Controller 和@Service下的文件.所以确保此base-package设置正确. -->
	<context:component-scan base-package="org.liukai.tutorial" />

	<!-- 配置注解驱动的Spring MVC Controller 的编程模型.注:次标签只在 Servlet MVC工作! -->
	<mvc:annotation-driven />

	<!-- resources下的静态资源不被DispatcherServlet接收处理  -->
	<mvc:resources location="/resources/" mapping="/resources/**"/>
	
</beans>




重新输入得到的结果:



可以看到结果是显示在同一页上,极大的提高的用户的体验.而不像非AJAX版本那样需要在另外一个页面显示.


总结:
这样,我们完成了预定的目标:成功的用SpringMVC搭建起了一个简单的基于jQuery的AJAX应用程序.我们还了解了如何利用@ResponseBody和Jackson来进行简便的Json操作.



BTW:附件为本次教程源码.你可以下载后直接在tomcat或其他web服务器启动.也可以自行添加
maven插件启动.
  • 大小: 19.1 KB
  • 大小: 4.4 KB
  • 大小: 4.6 KB
  • 大小: 5 KB
  • 大小: 2.9 KB
  • 大小: 4.9 KB
  • 大小: 4.2 KB
  • 大小: 9.1 KB
分享到:
评论
13 楼 smileyangtest 2016-06-16  
按了add怎么什么反映都没有,也没有报错什么的,什么都没有,请问是怎么回事呀?还请问下哪里有jquery+spring mvc的详细资料
vvsuperman 写道
我按了add怎么什么反映都没有,也没有报错什么的,什么都没有,请问是怎么回事呀?还请问下哪里有jquery+spring mvc的详细资料

@Controller 中的函数返回值改为String的才好用  
11 楼 vvsuperman 2012-11-18  
另外,我想问下用这种方式做登录认证该怎么做,网上查了资料很少,用传统的session与cookies方式可以吗?但有人说这种方式貌似不符合rest的无状态要求
10 楼 vvsuperman 2012-11-18  
liukai 写道
vvsuperman 写道
我按了add怎么什么反映都没有,也没有报错什么的,什么都没有,请问是怎么回事呀?还请问下哪里有jquery+spring mvc的详细资料

确认你导入了jquery包..
如果按照我说的步骤来的话,应该不会有错.
jquery建议你单独花2天时间好好学习下.其实很简单的.只要熟练的使用几个选择区的API就OK了

另外Spring3MVC的资料现在网上已经很多了.


解决了,是引用包的问题,我用myeclipse的导入包
9 楼 liukai 2012-11-03  
vvsuperman 写道
我按了add怎么什么反映都没有,也没有报错什么的,什么都没有,请问是怎么回事呀?还请问下哪里有jquery+spring mvc的详细资料

确认你导入了jquery包..
如果按照我说的步骤来的话,应该不会有错.
jquery建议你单独花2天时间好好学习下.其实很简单的.只要熟练的使用几个选择区的API就OK了

另外Spring3MVC的资料现在网上已经很多了.
8 楼 vvsuperman 2012-10-28  
我按了add怎么什么反映都没有,也没有报错什么的,什么都没有,请问是怎么回事呀?还请问下哪里有jquery+spring mvc的详细资料
7 楼 mojunbin 2011-11-21  
很不错嘛~~呵呵。喜欢这类帖子,虽然不算深入,但是至少清晰条理
6 楼 lshoo 2011-05-22  
为什么不用Maven?知识点比较简单,容易理解啊。如果用Spring,最好还是用SpringSource Site Tools(sts)。
英文好的可以参考原文:krams915.blogspot.com
5 楼 wuliaolll 2011-05-11  
我觉得楼主写springmvc教程是好,但最好是纯净的教学,不应用maven,对于没用过maven的人来说,是看得一头雾水,教程没有有效地组织起来形成连贯
4 楼 bushkarl 2011-05-10  
rocketball 写道
好贴,今天看到说得最清楚的,要是有spring mvc juery整合的原始资料提供,那就更好了

这篇文章也很原始嚒
3 楼 zwt2001267 2011-05-02  
不错,支持楼主的分享精神和辛苦写作。
2 楼 runjia1987 2011-04-22  
支持,很清晰明了!
1 楼 rocketball 2011-04-21  
好贴,今天看到说得最清楚的,要是有spring mvc juery整合的原始资料提供,那就更好了

相关推荐

Global site tag (gtag.js) - Google Analytics