SpringMvc---表现层框架
首先来对两个概念进行区分:
1.三层架构和MVC框架(二者都可采用分层思想)
三层架构(应用程序):三层是从整个应用程序架构的角度来分的三层,他将整个应用程序分为表现层、业务逻辑层、数据访问层
MVC模式:是基于表现层的框架。MVC把用户界面独立的到一些文件中(View),把一些和用户交互的程序逻辑(Controller)独立到一些文件中。在view和controller中传递数据使用一些专门封装数据的实体对象,这些对象统称为models
2.SpringMVC
Spring Web MVC是一种基于Java的实现了Web MVC设计模式的请求驱动类型的轻量级Web框架。(它是WEB层的一个应用)
1) SpringMVC运行原理
首先先来熟悉几个概念:
前端控制器:
处理器映射器:
处理器适配器:
视图解析器:
它们都是由SpringMVC提供的,我们只需要开发传统的MVC部分。
它的运行原理如下:
当请求到达前端控制器,它就会调用处理器映射器去找地址,
映射器找到地址就将其返回给前端控制器
前端控制器再根据这个地址去调用处理器适配器,
处理器是配置调用控制器,
控制器调用服务层
服务层调用Dao层
Dao层完成数据的交互,再将最终的结果ModelAndView,逐层递交回去
最后前端控制器得到结果,再调用视图解析器返回view
前端控制器得到VIEW,再将其渲染,然后返还给用户。
3配置
那么我们就来看一下怎么配置SpringMvc。
1)首先来配置前端控制器(DispatcherServlet)
前端控制器,在WEB-IF下的web.xml当中配置,这样当服务器启动的时候就会去加载这个配置文件,我们在此配置文件当中指明其它配置文件的位置即可,当然我们今天只是SpringMvc,只是与SpringMvc的配置文件相关联,在以后的整合当中会对所有的配置文件进行关联。好了,我们接下来就进行配置:
主要可分为五步:
由于web.xml当中对各个节点的顺序是有限制,的这个搭建可以去通过源码看的建
见,那么我们就按照顺序,来进行编码的配置:
<web-app>
<display-name>Archetype Created Web Application</display-name>
编码的配置我们是通过过滤器来进行的,因此用到的是Filter节点和他对应的Mapping节点;
<filter>
首先对该节点命名,以便于后面的Mapping节点知道,给指定的过滤的文件转换的编码是什么;
<filter-name>myf</filter-name>
这个我们用到的类就是,CharacterEcondingFilter这个类来进行编码;
<filter-class>org.springframework.web.filter.CharacterEncodingFilter</filter-class>
接下来,我们进行编码的具体指定,在初始化参数当中进行指定,并且value为utf-8
<init-param>
<param-name>econding</param-name>
<param-value>utf--8</param-value>
</init-param>
在这个我们有一个属性就是forceEconding用来强制编码,也就是说只要是指定后缀的文件都要进行统一的编码;
<init-param>
<param-name>forceEncoding</param-name>
<param-value>true</param-value>
</init-param>
</filter>
下面就进行的是具体文件的指定,/*指的就是所有文件
<filter-mapping>
<filter-name>myf</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
接下来我们就进行前端控制器的配置我们使用的是DispatcherServlet来进行指定:
<servlet>
首先对节点进行命名:
< servlet-name >SpringMvc</servlet-name>
指定前端控制器:
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
关联核心配置文件
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath:applicationContext.xml</param-value>
</init-param>
</servlet>
最后进行的就是请求后缀的规定,在这里以.do为例当然你也可以是其它,看个人习惯
<servlet-mapping>
<servlet-name>SpringMvc</servlet-name>
<url-pattern>*.do</url-pattern>
</servlet-mapping>
</web-app>
以上就是在web.xml当中进行的前端控制器的配置,顺便进行了编码的配置;
2) 处理器映射器,适配器以及视图解析器的配置
这个我们再核心配置文件当中配置,这个核心配置文件我们仍然命名为applicationContext.xml,当然你也可以用其他命名只要配置的时候对应即可;
代码如下:
<!-- 配置处理器映射器,BeanNameUrlHandlerMapping这个类的作用就是更具名字来查找URL-->
<bean class="org.springframework.web.servlet.handler.BeanNameUrlHandlerMapping"></bean>
<!-- 配置处理器适配器-->
<bean class="org.springframework.web.servlet.mvc.SimpleControllerHandlerAdapter"></bean>
<!-- 配置视图解析器-->
<bean class="org.springframework.web.servlet.view.InternalResourceViewResolver"></bean>
4开发控制器
我们有三只方法来实现;
首先第一种就是写一个类实现Controller接口,再实现其当中的方法,这个类即使一个控制类,代码如下:
public class UserController implements Controller {
@Override
public ModelAndView handleRequest(HttpServletRequest request, HttpServletResponse response) throws Exception {
// ModelAndView就是之前提及的处理器适配器通过控制器等的交互后返回的值;
ModelAndView modelAndView=new ModelAndView();
//返回的是ModelAndView,所以应该对它进行数据的渲染
这条语句就是转递值,再这里添加了之后就可以在jsp页面中通过EL表达式取出来显示在页面,从而完成从方法到页面数据的交互,这个我们会在后面详细介绍;
modelAndView.addObject("傅往","123456");
,//最后指向渲染页面
modelAndView.setViewName("/index.jsp");
return modelAndView;
}
}
这样一个简单的控制类就开发完成;
接下我们还需要对这个控制类进行配置,创建表现层对象,同样只需要再之前的核心配置文件当中加一句话就可以:
之前说到过这种方法是通过Name来查找Url的,所以这儿的name就是相当于,以前写在servlet上面的注解;
<bean name="/hello.action" class="com.qf.controller.UserController"></bean>
这样我们一个简单的Springmvc就配置完了,接下来在jsp页面当中协商taglib等标签,来来允许EL表达式,将属性改为不忽略EL表达式,这样就可以在页面当中访问到我们置入的数据;
注意访问的时候看清之际项目的/代表的是什么,最后根据之前的name进行访问即可;
5第二种方式
接下类我们来讲解第二种方式,它是根据ID来查找的,与之前的相比只是几个实现类不同,具体代码如下:
首先对于前端控制器的配置是一样的;
在这里我们首先进行控制类的开发这样在配置的时候会好理解一些:
首先我们写一个类实现的是HTTPRequestHandler接口
与之前的实现相比,它实现的方法是没有返回值得,但是作用是一样得,代码如下:
public class UserController implements HttpRequestHandler {
@Override
public void handleRequest(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
因为它是没有返回值得这儿我们就要request域对象来进行数据得传递;
request.setAttribute("name","111");
同样通过request得转发,从方法到页面
request.getRequestDispatcher("/index.jsp").forward(request,response);
}
}
接下来就是对其它几个的配置:
首先我们来创建表现层对象
<bean id="UserController" class="com.qf.controller.UserController"></bean>
在接下来就是处理器映射器得配置,与之前得不同得是我们用到得是SimpleUrlHandlerMapping这个类,可根据id查找,所以上面创建表现层对象得时候用得是id属性而不是name
<bean class="org.springframework.web.servlet.handler.SimpleUrlHandlerMapping">
在这里就是具体得关联,完成请求于控制类得对应;
<property name="mappings">
<props>
<prop key="/User.do">UserController</prop>
</props>
</property>
</bean>
接下来就是处理器适配器得配置我们所用到得类是HttpRequestHandlerAdapter
<bean class="org.springframework.web.servlet.mvc.HttpRequestHandlerAdapter"></bean>
最后对于视图解析器是不变的我们同样用的是之前用到的InternalResourceViewResolver
<bean class="org.springframework.web.servlet.view.InternalResourceViewResolver"></bean>
这样就可以了,之后同样对其测试即可,测试即启动项目即可,不用和之前的博文一样船舰测试类;
当然也不是说以后就不用了,之后再进行整合之后对局部的方法还是要进行这样的测试的,这样效率会更加高,这也就是单元测试的优势所在,当然还有断言测试等,以后会提及。
6第三种方式
注解(重点)
1) 同样在这里我们对前端控制器的方式是不变的;
,之后配置映射器以及适配器,这两个是一对(可以这样来记忆)
RequestMappingHandlerMapping 和 RequestMapping HandlerAdapter
之后就是一直都没有改变的InteralResourcesViewResolver
2) J接下来我们进行的就是注解控制类的开发
之前我们提及到的@Component衍生出来的三个注解,其中一个就是控制类的注解即@Controller将这个注解加再类之上,
优势一:就表示这是一个控制类,不用在去实现方法;
优势二:方法可以随便写,这样后面进行模块开发的时候,一个模块的功能我们就可以放在一个控制类里面,而之前的每一个都要写一个,比如说:与用户有关的登录,注册等等就可以写在一起;
接下类我们就看看控制类的一个简单演示:
@Controller
public class UserController {
下面的这个注解作用在方法之上,表示的就是请求路径,即映射路径
@RequestMapping("/add.do")
public ModelAndView addUser(HttpServletRequest request, HttpServletResponse response){
ModelAndView modelAndView=new ModelAndView();
modelAndView.addObject("aaa","efdddasd");
modelAndView.setViewName("/index.jsp");
return modelAndView;
}
}
之后我们就核心文件进行配置:
其中前三个的配置是不变的,实现类和第二种一致,之前的框架中提到够,注解方式我们只需要开启扫描即可:
<bean class="org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping"></bean>
<bean class="org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter"></bean>
这里前两个的配置可以有简写形式即:
<mvc:annotation-driven></mvc:annotation-driven>
<bean class="org.springframework.web.servlet.view.InternalResourceViewResolver"></bean>
在这里去开启扫描,之前的博文中说明了很多这里就不在解释:
<context:component-scanbase-package="com.www.controller"></context:component-scan>
注:当@RequestMapping("/user")作用在类上面的时候指的是请求跟路径,不是具体的路径,所以在返回页面的时候为/user/add.do;
相对路径指的就是,相对于上一个路径比如说上一个路径你是通过:
Localhost:8080/user/add.do访问进来的
相对路指的就是del.do这个默认指的就是Localhost:8080/user下的del.do
但是如果这时候你写为/del.do则会找不到资源。因为一般项目的默认方位路径是Localhost:8080/而这个目录下是没有del.do的所以会找不到;
所以大家要区分相对路径以及绝对路径;
@RequestMapping("/user")加上这个,则相当于你有了请求根路径,如果跳转的时候不带则会出错,所以当跳转到同一个控制类中的可直接使用del.do,若是不同的控制类则必须要加了。当然你每次都要绝对路径就不会出错了,初学建议多用绝对路径。
以上就是简单的Springmvc的配置基本需求可以满足了,之后的博文会介绍,方法到方法的转发,页面到方法,方法到页面等,之后一会介绍Mybatis最后将三者整合。
敬请期待!!!!
版权声明:本文为博主原创文章,未经博主允许不得转载