3月21日,晴天。白色玉兰和紫叶李竞相开放,樱花和紫叶李乍看有些相似,但实际上却是完全不同的两种树,二者最大的区别在于叶子。樱叶大多为椭圆形,前端突然变长变尖,叶子边缘还有很细的小“裂齿”,叶面是深绿的。而紫叶李叶片边缘有大的锯齿,叶片、叶柄都呈暗红色。
紫叶李
樱花
在第一个例子中,各位看官,是否觉得Controller
的实现,不够纯粹,需要继承 AbstractController。你的担忧可以打消了,Spring 2.5 之后版本为 Spring MVC 引入了注解驱动功能。现在你无须让 Controller 继承任何接口,无需在 XML 配置文件中定义请求和 Controller 的映射关系,仅仅使用注解就可以让一个 POJO 具有 Controller 的绝大部分功能。下面改进前面的HelloWord实例:
改进一:myOneMVC-servlet.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" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-2.5.xsd"> <span style="color:#3333FF;"><context:component-scan base-package="edu.eurasia.controller" /></span> </beans>
这里,所有通过 <bean> 元素定义 Bean 的配置内容已经被移除,仅需要添加一行 <context:component-scan/> 配置就解决所有问题了——Spring XML 配置文件得到了极致的简化(当然配置元数据还是需要的,只不过以注释形式存在罢了)。<context:component-scan/> 的 base-package 属性指定了需要扫描的类包,类包及其递归子包中所有的类都会被处理。对controller包中的所有类进行扫描,以完成Bean创建和自动依赖注入的功能。
因为 Spring 所有功能都在 Bean 的基础上演化而来,所以必须事先将 Controller 变成 Bean,这是通过在类中标注 @Controller 并在myOneMVC-servlet.xml 中启用组件扫描机制来完成的。
改进二:在WelcomeController.java 重新定义,处使用了两个注解,分别是 @Controller 和 @RequestMapping。
package edu.eurasia.controller; import org.springframework.stereotype.Controller; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.servlet.ModelAndView; @Controller public class WelcomeController { @RequestMapping("/hello.html") public ModelAndView helloWorld() { ModelAndView mav = new ModelAndView("hello.jsp"); mav.addObject("message", "Hello World!"); return mav; } @RequestMapping("/hi.html") public ModelAndView hi() { ModelAndView mav = new ModelAndView("hello.jsp"); mav.addObject("message", "Hi, World!"); return mav; } }
可以看出 WelcomeController 和一般的类并没有区别,它没有实现任何特殊的接口,因而是一个地道的 POJO。让这个 POJO 与众不同的魔棒就是 Spring MVC 的注解!
在这里,我们分别为helloWorld() 和 hi() 方法标注了 @RequestMapping 注解,分别指定这两个方法处理的 URL 请求。这样 /hello.html 的 URL 请求将由helloWorld()
负责处理,而 /hi.html 的 URL 请求则由 hi() 方法处理。
结果如下:
http://localhost:8080/springMVC_hello/hello.html
输出:Hello World!
http://localhost:8080/springMVC_hello/hi.html
输出:Hi, World!
用@Controller注释的类才会被SpringMVC解析器搜索到,这个注释是必须的。@RequestMapping注释用于 指定controller类里面的方法的URL索引。如果用于类索引,就是一个URL,可以省略。 WelcomeController.java的代码可以改成:package edu.eurasia.controller; import org.springframework.stereotype.Controller; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.servlet.ModelAndView; @Controller @RequestMapping("/hi") //父索引 可省略 public class WelcomeController { @RequestMapping("/hello.html") public ModelAndView helloWorld() { ModelAndView mav = new ModelAndView("hello.jsp"); mav.addObject("message", "Hello World!"); return mav; } @RequestMapping("/hi.html") public ModelAndView hi() { ModelAndView mav = new ModelAndView("hello.jsp"); mav.addObject("message", "Hi, World!"); return mav; } }在有父索引的请况下,访问:http://localhost:8080/你的工程名/hi/hi.html
在省略父索引的请况下,访问:http://localhost:8080/你的工程名/hi.html 就可将请求发送到所需controller方法。
可是,运行结果却是当头一棒——警告: No mapping found for HTTP request with URI [/springMVC_hello/hi/hi.html] in DispatcherServlet with name 'myOneMVC'。
原因是:spring 2.5.6这个版本好像不支持父索引。换成spring
3.1.1版,图省事,把dist目录下所有jar 包导入。就可以了。不过,hello.jsp要放到hi这个文件夹下,因为默认的路径变成了http://localhost:8080/你的工程名/hi。