【Jsp】第十三课 MVC+三层架构(一)

概念

MVC模式的核心思想是把一个应用的输入、处理、输出流程按照Model、View、Controller的方式进行分离,这样一个应用被分成三个层:模型层、视图层、控制层

MVC模式详细定义这3部分之间的交互:

  • 用户和视图(View)进行交互,输入数据并点击按钮
  • 控制器(Controller)收到来自视图的事件,并对模型(Model)进行操作,根据用户提供的数据更新模型(Model)
  • 视图同时也会收到“模型更新”的事件通知,从而更新自己,呈现结果给用户

MVC模式在Web中应用:

  • View处于Web层或者说是Client层,通常是JSP或Servlet,即页面显示部分。
  • Controller也处于Web层,通常用Servlet来实现,即页面显示的逻辑部分实现。
  • Model处于Middle层,通常用服务端的JavaBean或者EJB实现,即业务逻辑部分的实现

 

JSP页面身兼View和Controller两种角色,将控制逻辑和表现逻辑混杂在一起,JSP页面的编写者必须即是网页的设计者又是Java的开发者。

内嵌的逻辑使开发人员要理解应用程序的整个流程,必须浏览所有的页面,工作量很大。HTML标签、Java代码和JavaScript代码集中在同一个页面中,使调试变得很困难。

强耦合性,变更业务逻辑和数据会涉及到多个页面 

 该框架的核心是前端控制器(Front Controller),它被实现为Servlet,主要作用在于初始化并解析配置文件,并将用户请求的URL映射到需要被执行的命令实例,命令实例其实就是Action。

前端控制器接受用户的每个请求,并简单地把请求委托给调度器(Dispatcher),由调度器执行相应的动作(Action)。调度器把Action返回的url返回给前端控制器,并由前端控制器负责转发。

 MVC+三层架构开发模式

M:mode  模型
V:view   视图
C:controller  控制

三层架构:
控制层
业务逻辑层
数据访问层

 

开发步骤

1.创建项目并分层

我们这里使用前面几篇文章中的数据库作为项目的数据使用,这里创建数据库的过程就不再赘述,如果初学者对数据库的建立不熟练的可以查看【Jsp】第十一课 JDBC的回顾及单元测试框架的使用_笔触狂放的博客-CSDN博客 

创建好web服务端项目之后,在src文件夹中进行建立不同的包,作为项目的分层。

com.student.filter,com.student.controller,com.student.service,com.student.dao,com.student.util等等。

2.创建过滤器

按照流程图,浏览器通过地址访问需要过滤器的拦截审核,因此我们先在com.student.filter包下建立MyFilter过滤器,将拦截地址设置为/*用于拦截所有浏览器的访问请求。

package com.student.filter;

import java.io.IOException;
import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.annotation.WebFilter;

/**
 * 拦截浏览器所有访问服务器的请求
 */
@WebFilter("/*")
public class MyFilter implements Filter {

    /**
     * Default constructor. 
     */
    public MyFilter() {
        // TODO Auto-generated constructor stub
    }

	/**
	 * @see Filter#destroy()
	 */
	public void destroy() {
		// TODO Auto-generated method stub
	}

	/**
	 * @see Filter#doFilter(ServletRequest, ServletResponse, FilterChain)
	 */
	public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
		response.setContentType("text/html");
		response.setCharacterEncoding("UTF-8");
		request.setCharacterEncoding("UTF-8");
		chain.doFilter(request, response);
	}

	/**
	 * @see Filter#init(FilterConfig)
	 */
	public void init(FilterConfig fConfig) throws ServletException {
		// TODO Auto-generated method stub
	}

}

并在允许继续访问之前,将request和response对象的数据的编码格式提前改为UTF-8格式,为控制层的Servlet节省重复性的代码,提高项目的高内聚,低耦合的性能。

3.创建控制层

按照流程图来看,开始进入控制层,我们在 com.student.controller包中建立HomeServlet用于处理浏览器需要展示数据库中所有学生信息列表的请求。

package com.student.controller;

import java.io.IOException;
import java.util.List;
import java.util.Map;

import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;

import com.student.service.IStudentService;
import com.student.service.StudentServiceImp;

/**
 * Servlet implementation class HomeServlet
 */
@WebServlet("/HomeServlet")
public class HomeServlet extends HttpServlet {
	private static final long serialVersionUID = 1L;
       
    /**
     * @see HttpServlet#HttpServlet()
     */
    public HomeServlet() {
        super();
        // TODO Auto-generated constructor stub
    }

	/**
	 * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
	 */
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		//接收浏览器的任务,要所有学生信息
		//给业务逻辑层下达任务
		
		
	}

	/**
	 * @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse response)
	 */
	protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		// TODO Auto-generated method stub
		doGet(request, response);
	}

}

并将该Servlet作为项目的默认访问地址,在web.xml文件中设置

<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://xmlns.jcp.org/xml/ns/javaee" xmlns:jsp="http://java.sun.com/xml/ns/javaee/jsp" xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd" id="WebApp_ID" version="3.1">
  <display-name>Day17Jsp</display-name>
  <welcome-file-list>
    <welcome-file>HomeServlet</welcome-file>
  </welcome-file-list>
 
</web-app>

 4.建立业务逻辑层

按流程图控制层需要将任务发给业务逻辑层执行,因此我们在com.student.service中建立接口文件IStudentService(I表示该文件是接口文件,Student表示该文件操作Student学生表,Service表示该文件是业务逻辑层文件),在该接口中建立接收控制层任务的方法:

package com.student.service;
/**
 * 业务逻辑层操作学生表的接口
 * @author Administrator
 *
 */

import java.util.List;
import java.util.Map;

public interface IStudentService {
	
	List<Map<String, Object>> getStudents();
	
}

 因接口是不能实现未实现的方法,需要建立该接口的实现类,StudentServiceImp(Student表示操作Student表的文件,Service表示该文件是业务逻辑层的文件,Imp表示该文件是接口文件的实现类):

package com.student.service;

import java.util.List;
import java.util.Map;

import com.student.dao.IStudentDao;
import com.student.dao.StudentDaoImp;

/**
 * 业务逻辑层操作学生表的接口实现类
 * @author Administrator
 *
 */
public class StudentServiceImp implements IStudentService {

	@Override
	public List<Map<String, Object>> getStudents() {
		
		return null;
	}

}

接着按流程图将控制层中的任务交给业务逻辑层的接口执行:

/**
	 * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
	 */
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		//接收浏览器的任务,要所有学生信息
		//给业务逻辑层下达任务
		IStudentService service=new StudentServiceImp();
		List<Map<String, Object>> oList=
				service.getStudents();
		
		
	}

5.建立数据访问层

按流程图可以看到,业务逻辑层实现类需要将任务发给数据访问层,因此我们在com.student.dao包中建立IStudentDao(I表示该文件是接口文件,Student表示该文件操作Student表,Dao表示该文件是数据访问层的文件):

package com.student.dao;
/**
 * 数据访问层操作学生表的接口
 * @author Administrator
 *
 */

import java.util.List;
import java.util.Map;

public interface IStudentDao {
	
	List<Map<String, Object>> getStudents();
	
	
}

并创建该接口的实现类:

package com.student.dao;

import java.util.List;
import java.util.Map;

import com.student.utils.DBUtil;

/**
 * 数据访问层操作学生表的接口实现类
 * @author Administrator
 *
 */
public class StudentDaoImp implements IStudentDao {

	@Override
	public List<Map<String, Object>> getStudents() {
		return null;
	}

	
}

按流程图业务逻辑层实现类需要将任务交给数据访问层接口,因此在StudentServiceImp实现类中调用IStudentDao:

 6.建立数据库连接池工具类

按流程图可看出数据访问层实现类需要操作JDBC连接数据库并执行操作,根据我们之前学习的内容,这里我们采用Druid创建连接池的方式并结合Spring框架的JDBCTemplate类完成数据库的增删改查操作,在com.student.util包中创建DBUtil类:

package com.student.utils;

import java.io.IOException;
import java.io.InputStream;
import java.util.Properties;

import javax.sql.DataSource;

import org.springframework.jdbc.core.JdbcTemplate;

import com.alibaba.druid.pool.DruidDataSourceFactory;

public class DBUtil {
	
	public static JdbcTemplate jt=null;
	static {
		//使用反射机制将druid配置文件转换成输入流
		InputStream is=DBUtil.class
				.getClassLoader()
				.getResourceAsStream
				("com/student/utils/druid.properties");
		Properties properties=new Properties();
		try {
			properties.load(is);
			//获得连接池对象
			DataSource ds=DruidDataSourceFactory
					.createDataSource(properties);
			jt=new JdbcTemplate(ds);
		} catch (Exception e) {
			e.printStackTrace();
		}
	}
}

并将Druid插件导入lib文件夹,将Druid配置文件导入com.student.util包下

 

并将JDBCTemplate需要的jar包导入lib文件夹

 

 

再将数据库连接桥插件导入lib文件夹

 

然后只需要在数据访问层实现类中调用DBUtil工具类执行sql语句即可完成数据库的查询操作

 根据流程图的操作,数据库中查询的数据将一层层往上返回,最终返回值至控制层的HomeServlet中,控制层拿到所有数据需要将数据发给Jsp页面进行展示。

7.建立视图层

按照流程图控制层将获得的数据发送给Jsp页面进行显示,因此我们在WebContent文件件下新建Jsp文件,index.jsp,因查询出来的数据是学生列表信息,在jsp页面中使用表格标签进行展示,并结合核心标签库的迭代标签以及EL表达式的知识将数据展示。

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
    <%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>学生信息列表</title>
<style type="text/css">
	input{
		color: white;
		font-weight: bold;
		padding-top: 5px;
		padding-bottom: 5px;
		padding-left: 10px;
		padding-right: 10px;
		border-width: 0px;
		border-radius: 5px;
	}
	
	.in1{
		background-color: green;
	}
	.in2{
		background-color: blue;
	}
	.in3{
		background-color: red;
	}
</style>
</head>
<body>
	<!-- 使用表格展示学生信息 -->
	<div align="center">
		<table border="1" style="width: 400px;
		border-collapse: collapse;text-align: center;">
			<tr>
				<th>学号</th>
				<th>姓名</th>
				<th>年龄</th>
				<th>操作</th>
			</tr>
			<c:forEach items="${students}" var="map" varStatus="v">
				<tr>
					<td>${map.id }</td>
					<td>${map.name }</td>
					<td>${map.age }</td>
					<td>
						<a ><input class="in1" type="button" value="添加"></a>
						<a ><input class="in2" type="button" value="修改"></a>
						<a ><input class="in3" type="button" value="删除"></a>
					</td>
				</tr>
			</c:forEach>
		</table>
	</div>
</body>
</html>

 效果

猜你喜欢

转载自blog.csdn.net/u010321564/article/details/121869454