前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >Jsp开发模式及MVC模型的使用

Jsp开发模式及MVC模型的使用

作者头像
全栈工程师修炼指南
发布2022-09-29 15:58:31
9740
发布2022-09-29 15:58:31
举报

[TOC]

0x00 简述

前面我们说过JavaEE的结构,下面我们又来说说三层结构以及与MVC模式的关联;

  • JavaEE结构:客户端-Web端-业务逻辑层-数据访问层
  • 三层结构:Web层(Servlet/JSP) - 业务逻辑层(Ejb 、JavaBean) - 数据访问层(Dao)

什么是MVC模式?

  • M(Model):模型层主要封装数据采用JavaBean (如:EJB)
  • V(View):视图层JSP负责显示
  • C(Controller):控制层 Serlvet 接受页面请求,然后采用模型层的方法,然后将返回的数据给视图层;

开发模式种类: 开发模式1:JavaBean + JSP

  • 优点:直接在jsp中写java代码
  • 缺点: 后期维护困难代码臃肿 开发模式2:Servlet + JavaBean + JSP
  • 优点: 对于大型项目分层、逻辑比较清楚、便于维护、扩展方便.
  • 缺点: 小型项目如果严格准守MVC代码量增加了.

三层结构与MVC模式的关系:

WeiyiGeek.
WeiyiGeek.

WeiyiGeek.

三层结构的实现操作:

环境基础设置:

  • JDBC
  • commons-dbutils : 对JDBC进行简单的CURDS封装
  • c3p0 : JDBC 连接池

思路原理是最重要的:我们在Dao的前面加入一个业务逻辑服务层(Service),这是由于Dao在实际开发中只做一件事情那就是数据库CURD,而我们为了开发的规范将服务层放置于Servlet与Dao之间,比如下图所示(重点);

WeiyiGeek.三层结构原理
WeiyiGeek.三层结构原理

WeiyiGeek.三层结构原理

测试数据表:

代码语言:javascript
复制
CREATE DATABASE works;
use works;
CREATE TABLE `person` (
  `sid` INT PRIMARY KEY AUTO_INCREMENT,
  `sname` VARCHAR(20) NOT NULL,
  `gender` VARCHAR(5) DEFAULT '未知' COMMENT '性别',
  `telephone` VARCHAR(15)  NOT NULL,
  `job` VARCHAR(200)  NOT NULL,
  `info` VARCHAR(200),
  `jointime` DATE NOT NULL
);

CREATE TABLE `record` (
  `sid` INT COMMENT '用户ID',
  `type` NOT NULL COMMENT '类型1加班调休调休、2.加班费申请、3.调休申请、4.请假申请、5.年假申请',
  `day` DATE NOT NULL,
  CONSTRAINT fk_person FOREIGN KEY (`sid`) REFERENCES person(`sid`)
);

总结: 描述:利用MVC的设计理念,建立一个servlet单独处理数据库流程

1.Dao 利用 数据库 连接的jar包进行数据库相关的CURD,以及异常抛出

代码语言:javascript
复制
//常常是接口的实现类
public class UserDao {
  public boolean find() throw SQLException{
    try{
      //执行的SQL
    } catch (Exception e) {
      e.printStackTrace();
    }
  }
}

2.Service 根据业务校验数据并进行异常抛出;

代码语言:javascript
复制
public class LoginUserService() throw Exception,SQLException {
  try {
  //数据效验
  } catch (Exception e){
    throw new Exception("数据校验说明");
  }
}

3.每一个servlet中接收产生的异常处理并打印

代码语言:javascript
复制
public class UserLoginServlet extends Servlet{
  void doGet(request,response){
    try {
      //功能处理
    } catch (Exception e) {
      //错误处理以及错误打印
    }
  }
}

0x01 实例

项目文件结构以及依赖的jar库:

WeiyiGeek.
WeiyiGeek.

WeiyiGeek.

Person 数据类:

代码语言:javascript
复制
public class Person {
  private int sid;
  private String sname;
  private String gender;
  private String telephone;
  private String job;
  private String info;
  private Date jointime;
  
  //构造方法
  public Person() {
    super();
    // TODO Auto-generated constructor stub
  }
  //插入指定的sid
  public Person(int sid, String sname, String gender, String telephone, String job, String info, Date jointime) {
    super();
    this.sid = sid;
    this.sname = sname;
    this.gender = gender;
    this.telephone = telephone;
    this.job = job;
    this.info = info;
    this.jointime = jointime;
  }
  //重写
  public Person(String sname, String gender, String telephone, String job, String info, Date jointime) {
    super();
    this.sname = sname;
    this.gender = gender;
    this.telephone = telephone;
    this.job = job;
    this.info = info;
    this.jointime = jointime;
  }
  ...... //get / set 方法略去 (自动生成即可)
}
更新信息

文件结构:

代码语言:javascript
复制
#Dao
/Web/src/top/weiyigeek/dao/PersonDao.java  #Dao 层接口
/Web/src/top/weiyigeek/dao/impl/PersonDaoImpl.java # Dao 层实现

#Service
/Web/src/top/weiyigeek/service/PersonService.java  #Service 层接口
/Web/src/top/weiyigeek/service/impl/pagePersonServiceImp.java  #Dervice 层接口

#Servlet
/Web/src/top/weiyigeek/servlet/editPersonServlet.java   #编辑
/Web/src/top/weiyigeek/servlet/updatePersonServlet.java #更新

#JSP
/Web/WebContent/edit.jsp

主要代码:

代码语言:javascript
复制
<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<!-- 使用jstl内置函数 -->
<%@ taglib prefix="fn" uri="http://java.sun.com/jsp/jstl/functions" %>
<script>
function submit_check(){
  if ( confirm("您是否进行更新提交?") ) {
    return true;
  }else{
    return false;
  }
}
</script>
<form action="updatePersonServlet" method="POST" onsubmit="return submit_check()">
<input type="hidden" name="sid" value="${person.sid }">
<!-- 采用表格会更好看一点 -->
<table border="1" width="auto" cellpadding="1" cellspacing="0">
  <tr>
    <td>姓名</td>
    <td><input type="text" name="name" value="${person.sname }"></td>
  </tr>
  <tr>
    <td>性别</td>
    <td>
        <input type="radio"
      name="gender" value="男"
      <c:if test="${person.gender == '男'}">checked</c:if>>男 <input
      type="radio" name="gender" value="女"
      <c:if test="${person.gender == '女'}">checked</c:if>>女
    </td>
  </tr>
  <tr>
    <td>电话</td>
    <td><input type="text" name="telephone" value="${person.telephone }"></td>
  </tr>
  <tr>
    <td>加入时间</td>
    <td><input type="text" name="jointime" value="${person.jointime }"></td>
  </tr>
  <tr>
    <td>job</td>
    <td>
      <input type="checkbox" name="job"value=安全
      <c:if test="${fn:contains(person.job,'安全') }">checked</c:if>>安全
      <input type="checkbox" name="job" value="运维"
      <c:if test="${fn:contains(person.job,'运维') }">checked</c:if>>运维
      <input type="checkbox" name="job" value="开发"
      <c:if test="${fn:contains(person.job,'开发') }">checked</c:if>>开发
      <input type="checkbox" name="job" value="测试"
      <c:if test="${fn:contains(person.job,'测试') }">checked</c:if>>测试
      <input type="checkbox" name="job" value="主管"
      <c:if test="${fn:contains(person.job,'主管') }">checked</c:if>>主管
    </td>
  </tr>
  <tr>
    <td>简介</td>
    <td><textarea name="info" rows="3" cols="20">${person.info }</textarea></td>
  </tr>
  <tr>
    <td colspan="2"><input type="submit" value="更新"></td>
  </tr>
</table>
</form>

Servlet 层

代码语言:javascript
复制
//editPersonServlet.java  
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
    //1.获取要更新资料的sid
    int sid = Integer.parseInt(request.getParameter("sid"));
    
    try {
      //2.根据id获取其个人信息并返还对象给person(注意这里不是List集合)
      PersonService ps = new PersonServiceImpl();
      Person person  = ps.getInfoById(sid);
      
      //3.将数据存入内置作用域对象属性之中并进行跳转到edit.jsp取值
      request.setAttribute("person", person);
      request.getRequestDispatcher("edit.jsp").forward(request, response);
    } catch (SQLException e) {
      // TODO Auto-generated catch block
      e.printStackTrace();
    }
  }


//updatePersonServlet.java
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
    //实际开发中能代码复用的时候一定要代码复用(减少体积)
    //设置编码
    request.setCharacterEncoding("utf-8");

    try {
      //获取收到的参数(实际开发中一定要过滤)
      int sid = Integer.parseInt(request.getParameter("sid"));
      String sname = request.getParameter("name");
      String gender = request.getParameter("gender");
      String telephone = request.getParameter("telephone");
      String info = request.getParameter("info");
      String jointime = request.getParameter("jointime");
      Date date = new SimpleDateFormat("yyyy-MM-dd").parse(jointime);
    
      String [] j = request.getParameterValues("job");
      String sj = Arrays.toString(j);
      String job = sj.substring(1, sj.length()-1);
      
      //将数据装载进对象
      Person person = new Person(sid,sname,gender,telephone,job,info,date);
      
      //利用服务层进行修改更新员工修改
      PersonService ps = new PersonServiceImpl();
      ps.updatePerson(person);
      
      //重新跳转到全部员工信息页面(这里直接指定的是servlet而不是jsp文件由于这里插入了数据就要重新获取数据然后存入作用域之中)
      request.getRequestDispatcher("findall").forward(request, response);
      
    } catch (Exception e) {
      // TODO Auto-generated catch block
      e.printStackTrace();
    }
  }

service 层: 实现

代码语言:javascript
复制
@Override
public Person getInfoById(int sid) throws SQLException {
  PersonDao delps = new PersonDaoImpl();
  return delps.getInfoById(sid);
}

@Override
public void updatePerson(Person person) throws SQLException {
  PersonDao delps = new PersonDaoImpl();
  delps.updatePerson(person);
}

dao 层: 实现

代码语言:javascript
复制
/**
	 * @throws SQLException 
	 * @Desc : 以ID为条件进行查找
	 */
  @Override
  public Person getInfoById(int sid) throws SQLException {
    QueryRunner runner = new QueryRunner(DB.getConn());
    return runner.query("SELECT * FROM person WHERE sid = ?", new BeanHandler<Person>(Person.class) ,sid);
  }

  /**
	 * @throws SQLException 
	 * @Desc:更新人员的修改
	 */
  @Override
  public void updatePerson(Person person) throws SQLException {
    QueryRunner runner = new QueryRunner(DB.getConn());
    int flag = runner.update("UPDATE person SET sname = ?,gender = ?,telephone = ?, job = ? , jointime = ?, info = ? WHERE sid = ?", person.getSname(), person.getGender(),person.getTelephone(),person.getJob(),person.getJointime(),person.getInfo(),person.getSid());		
    if(flag > 0) {
      System.out.println("#更新成功");
    }else {
      System.out.println("#更新失败");
    }
  }
WeiyiGeek.
WeiyiGeek.

WeiyiGeek.

模糊查询

描述:结构与上面大致相同不同的是实现的JSP文件,直接上主要部分代码;

/Web/WebContent/findlist.jsp

代码语言:javascript
复制
<form action="SearchPersonServlet" method="post">
<table border="1" width="auto" cellpadding="1" cellspacing="0">
  <tr>
    <td colspan="8">
        按姓名查询:<input type="text" name="sname"/>
          &nbsp;
          按性别查询:<select name="sgender">
                <option value="">--请选择--
                <option value="男">男
                <option value="女">女
                </select>
          &nbsp;&nbsp;&nbsp;
          <input type="submit" value="查询">
          &nbsp;&nbsp;&nbsp;
          <a href="add.jsp">添加</a>
    </td>
  </tr>
  <tr><th>SID</th><th>姓名</th><th>性别</th><th>电话号码</th><th>工作职位</th><th>加入时间</th><th>备注</th><th>操作</th></tr>
  <!-- jstl 表达式 -->
  <c:forEach items="${ PersonList }" var="person">
  <tr>
    <td>${person.sid}</td>
    <td>${person.sname}</td>
    <td>${person.gender}</td>
    <td>${person.telephone}</td>
    <td>${person.job}</td>
    <td>${person.jointime}</td>
    <td>${person.info}</td>
    <td><a href="editPersonServlet?sid=${ person.sid }">修改</a> | <a href="#" onclick="doDelete(${person.sid})">删除</a></td>
  </tr>
  </c:forEach>
</table>
</form>

servlet 实现:

代码语言:javascript
复制
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
    try {
      //1.获取参数的编码设置
      request.setCharacterEncoding("utf-8");
      
      //2.获取查询参数并传递给service层进行进一步的调用dao
      String sname = request.getParameter("sname");
      String gender = request.getParameter("sgender");
      PersonService ps = new PersonServiceImpl();
      List<Person> list = ps.searchPerson(sname, gender); //返回一个包含Person对象的List集合
      
      //3.将获取的集合对象放入在作用域属性中
      request.setAttribute("PersonList", list);
      
      //4.跳转页面
      request.getRequestDispatcher("findlist.jsp").forward(request, response);;
      
    } catch (SQLException e) {
      // TODO Auto-generated catch block
      e.printStackTrace();
    } 
}

Service 层:

代码语言:javascript
复制
@Override
  public List<Person> searchPerson(String sname, String gender) throws SQLException {
    return new PersonDaoImpl().searchPerson(sname,gender);
  }

Dao 层:

代码语言:javascript
复制
public List<Person> searchPerson(String sname, String gender) throws SQLException {
    QueryRunner runner = new QueryRunner(DB.getConn());
    //情况1.如果姓名和性别都没选择时候默认显示全部
    String sql = "SELECT * FROM person WHERE 1 = 1"; //值得学习
    List<String> param = new ArrayList<String> (); //采用数组集合

// 		判断传入的参数是否为空;
//		public static boolean isEmpty(CharSequence s){
//			return s==null || s.length() == 0;
//		}
    
    //判断有没有姓名, 如果有就组拼到sql语句里面 (重点了解)
    if(sname.length()>0){
      sql = sql + "  and sname like ?";
      param.add("%"+sname+"%"); //模糊查询精妙之处
    }
    
    //判断有没有性别,有的话,就组拼到sql语句里面。
    if(gender.length()>0){
      sql = sql + " and gender = ?";
      param.add(gender);
    }
    System.out.println("执行的SQL: " + sql);
    runner.getDataSource().getLogWriter();
    return runner.query(sql , new BeanListHandler<Person>(Person.class) ,param.toArray());
  }

执行效果:

WeiyiGeek.
WeiyiGeek.

WeiyiGeek.

分页实现

常用的分页方式有两种:

  • 1.物理分页:在进行SQL查询的时候加上获取的条数限制,优点:减少数据库访问负载;
  • 2.逻辑分页:将数据库中的数据读取到内存数据库中比如redis然后采用进行读取,优点:访问速度快;

项目文件结构:

代码语言:javascript
复制
#Dao 数据库连接层
/Web/src/top/weiyigeek/dao/pagePersonDao.java  #接口
/Web/src/top/weiyigeek/dao/impl/pagePersonDaoImp.java #实现

#Service 业务逻辑层
/Web/src/top/weiyigeek/service/pagePersonService.java  #接口
/Web/src/top/weiyigeek/service/impl/pagePersonServiceImp.java #实现

#Servlet 网页请求处理
/Web/src/top/weiyigeek/servlet/pageList.java

#JSP 显示层
/Web/WebContent/pageShow.jsp

公共类:

代码语言:javascript
复制
package top.weiyigeek.main;

import java.util.List;

public class pagePerson {
  private int currentPage; //显示第几页
  private int showCount; //每页显示几条
  private int pageTotal; //一共几页
  private int total; //信息总条数
  private List<Person> lp; //查询到的的数据
  ..... //此处忽略自动get 、 set 生成的代码
}

Dao 数据库操作实现

代码语言:javascript
复制
package top.weiyigeek.dao.impl;

import java.sql.SQLException;
import java.util.List;

import org.apache.commons.dbutils.QueryRunner;
import org.apache.commons.dbutils.handlers.BeanListHandler;
import org.apache.commons.dbutils.handlers.ScalarHandler;

import top.weiyigeek.dao.pagePersonDao;
import top.weiyigeek.main.Person;
import top.weiyigeek.utils.DB;

public class pagePersonDaoImp implements pagePersonDao {

  @Override
  public List<Person> pagePersonData(int page, int count) throws SQLException {
    QueryRunner runner = new QueryRunner(DB.getConn());
    //参数1.显示的条数,参数2,显示第几页的数据(即offset不显示前面多少条)
    return runner.query("SELECT * FROM person Limit ? offset ?", new BeanListHandler<Person>(Person.class),count, (page - 1) * count);
  }

  @Override
  public int dataCount() throws SQLException {
    QueryRunner runner = new  QueryRunner(DB.getConn());
    Long count = (Long)runner.query("SELECT COUNT(*) FROM person",new ScalarHandler());
    return count.intValue();
  }
}

Service 业务逻辑层实现

代码语言:javascript
复制
package top.weiyigeek.service.impl;

import java.sql.SQLException;
import java.util.List;

import top.weiyigeek.dao.pagePersonDao;
import top.weiyigeek.dao.impl.pagePersonDaoImp;
import top.weiyigeek.main.Person;
import top.weiyigeek.main.pagePerson;
import top.weiyigeek.service.pagePersonService;

public class pagePersonServiceImp implements pagePersonService{

  @Override
  public pagePerson pageShow(int page, int count) throws SQLException {
    //实例化对象(父类引用指向子类对象)
    pagePersonDao ppd = new pagePersonDaoImp();
    pagePerson pp = new pagePerson();
    
    //存储从Dao模型中实现数据库查询的所返回的信息
    List<Person> person = ppd.pagePersonData(page,count);
    int resultCount = ppd.dataCount();
    
    //将值存储进分页自定义类中
    pp.setLp(person);         //查询到数据(List 集合)
    pp.setCurrentPage(page);  //查询第几页
    pp.setShowCount(count);    //每页显示多少条
    pp.setTotal(resultCount); //数据总条数
    pp.setPageTotal(resultCount % count == 0 ? resultCount / count : (resultCount / count) + 1 ); //总页数 (看是否可以除尽,否则+1)
    return pp;
  }
}

Servlet

代码语言:javascript
复制
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
    try {
      //1.获取显示的页数以及每页显示好多条
      int page = Integer.parseInt(request.getParameter("page"));
      int count = Integer.parseInt(request.getParameter("count"));
      
      //2.调用服务类并返回查询到数据包括条数 当前页数 、总页数
      pagePersonService pps = new pagePersonServiceImp();
      pagePerson pp = pps.pageShow(page, count);
      
      //3.将对象存进作用域之中
      request.setAttribute("page", pp);
      
      //4.跳转分页显示页面
      request.getRequestDispatcher("pageShow.jsp").forward(request, response);
      
    } catch (SQLException e) {
      // TODO Auto-generated catch block
      e.printStackTrace();
    }
}

JSP(采用jstl) 展示层:

代码语言:javascript
复制
<table border="1" width="auto" cellpadding="1" cellspacing="0">
  <tr><th>SID</th><th>姓名</th><th>性别</th><th>电话号码</th><th>工作职位</th><th>加入时间</th><th>备注</th><th>操作</th></tr>
  <!-- jstl 表达式 -->
  <c:forEach items="${page.lp }" var="person">
  <tr>
    <td>${person.sid}</td>
    <td>${person.sname}</td>
    <td>${person.gender}</td>
    <td>${person.telephone}</td>
    <td>${person.job}</td>
    <td>${person.jointime}</td>
    <td>${person.info}</td>
    <td><a href="editPersonServlet?sid=${person.sid }">修改</a> | <a href="#" onclick="doDelete(${person.sid})">删除</a></td>
  </tr>
  </c:forEach>
  <tr>
  <!-- 
  private int currentPage; //显示第几页
  private int showCount; //每页显示几条
  private int pageTotal; //一共几页
  private int total; //信息总条数
  private List<Person> lp; //查询到的的数据
   -->
  <td colspan="8"> 
  第 ${page.currentPage} / ${page.pageTotal} 页  &nbsp; &nbsp; 
  每页显示:${page.showCount} 条 &nbsp;&nbsp; 
  总共有:${page.total} 条 &nbsp; &nbsp; 
  <c:if test="${ page.currentPage != 1 }">
    <a href="pageList?page=1&count=${page.showCount}">首页</a> &nbsp; 
    <a href="pageList?page=${page.currentPage - 1}&count=${page.showCount}">上一页 </a> &nbsp;  | 
  </c:if>
  
  <!-- 遍历显示页数(坑呀-值得学习),实际情况下采用Bootstrap直接生成即可 -->
  <c:forEach begin="1" end="${page.pageTotal}" var="i">
    <c:if test="${page.currentPage == i}">
      <span style="color:red">${page.currentPage}</span> &nbsp; 
    </c:if>
    <c:if test="${page.currentPage != i}">
      <a href="pageList?page=${i}&count=${page.showCount}">${i}</a> &nbsp; 
    </c:if>
  </c:forEach>

  
  <c:if test="${ page.currentPage != page.pageTotal }">
    | <a href="pageList?page=${page.currentPage + 1}&count=${page.showCount}">下一页 </a> &nbsp; 
    <a href="pageList?page=${page.pageTotal}&count=${page.showCount}">末页 </a> 
  </c:if>
  
</td>
<tr>
</table>

执行效果:

WeiyiGeek.
WeiyiGeek.

WeiyiGeek.


0x02 Ajax & JQuery

描述:补充复习前端知识(详细请看Javascript以及jQuery):

常用的JS框架:

  • JQuery:轻量级,众多的插件
  • Prototype
  • dojo
  • dwr
  • Extjs:表格功能强大;
  • YUI

Q:Ajax是什么?有什么用? A: “Asynchronous Javascript And XML”(异步JavaScript和XML),可以让网页局部进行更新;

代码语言:javascript
复制
function getXMLHttpRequest() {
  var xmlHttpReq=null;
  if (window.XMLHttpRequest) {//Mozilla 浏览器
    xmlHttpReq = new XMLHttpRequest();
  }else {
    if (window.ActiveXObject) {//IE 浏览器
      try {
        xmlHttpReq = new ActiveXObject("Microsoft.XMLHTTP");
      }
      catch (e) {
        try {//IE 浏览器
          xmlHttpReq = new ActiveXObject("Msxml2.XMLHTTP");
        }
        catch (e) {
        }
      }
    }
  }
  return xmlHttpReq;
}

GET/POST集成请求示例:

代码语言:javascript
复制
//执行get请求
function get() {
  //1. 创建xmlhttprequest 对象
  var request = ajaxFunction();
  //2. 发送请求
  request.open("GET" ,"/day16/DemoServlet01?name=aa&age=18" ,true );
  //3. 获取响应数据 注册监听的意思。  一会准备的状态发生了改变,那么就执行 = 号右边的方法
  request.onreadystatechange = function(){
    //前半段表示 已经能够正常处理。  再判断状态码是否是200
    if(request.readyState == 4 && request.status == 200){
      alert(request.responseText);				//弹出响应的信息
    }
  }
  request.send();
}


//post数据请求
function post() {
      //1. 创建对象
      var request = ajaxFunction();
      //2. 发送请求
      request.open( "POST", "/day16/DemoServlet01", true );
      //想获取服务器传送过来的数据, 加一个状态的监听。 
      request.onreadystatechange=function(){
        if(request.readyState==4 && request.status == 200){
          
          alert("post:"+request.responseText);
        }
      }
      //如果使用的是post方式带数据,那么 这里要添加头, 说明提交的数据类型是一个经过url编码的form表单数据
      request.setRequestHeader("Content-type","application/x-www-form-urlencoded");
      //带数据过去  , 在send方法里面写表单数据。 
      request.send("name=aobama&age=19");
    }

Q:JQuery 是什么?有什么用? A:javascript 的代码框架,目的简化代码提高效率write less do more , 写得更少,做的更多

load & get & post 使用案例

代码语言:javascript
复制
* load
$("#元素id").load(url地址);
$("#div1").load(serlvet);   ---> 使用的get请求,回来赋值的时候,使用text() ;去赋值

* get
语法格式:$.get(URL,callback);	
使用案例:$.get("/day16/DemoServlet02"  , function(data ,status) {
  $("#div01").text(data);
});

* post
语法格式:$.post(URL,data,callback);
function post() {
  $.post("/day16/DemoServlet02", {name:"zhangsan",age:18},function(data,status) {
    $("#div01").html(data); //想要放数据到div里面去。 --- 找到div
    $(data).each(function(index,c){
      console.log("索引:"+index,"值:"+c.name);
    });
  });
}

数据在服务端与客户端数据传输方式

  • xml:节点清晰,传输大文本字段
  • json:阅读性更好,容量更小;
异步查询

描述:采用原生的Ajax与JQuery封装过后的Ajax进行实现;

(1) View 层展现 : /Web/WebContent/syncRequest.jsp

代码语言:javascript
复制
<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>异步查询用户名称是否存在</title>
<!-- Jquery 引入外部 JS -->
<script src="https://cdn.staticfile.org/jquery/1.10.2/jquery.min.js"></script>
</head>
<body>
<script>
	//## (1)原生JS实现Ajax异步请求
	function checkUser(){
	    //1.创建ajax请求对象
	    var request = window.XMLHttpRequest ? new XMLHttpRequest():new ActiveXObject("msxml2.XMLHTTP") ? new ActiveXObject("msxml2.XMLHTTP"):new ActiveXObject("Microsoft.XMLHTTP"); 
	    
	    //2.获取输入的用户名
		var user = document.getElementById("username").value;
	    
		//3.ajax请求
		request.open("POST","CheckUserServlet",true);
		request.setRequestHeader("Content-Type","application/x-www-form-urlencoded");
		request.onreadystatechange = function(){
			if(request.readyState == 4 && request.status == 200){
				//解析返回得JSON字符串
			  var jsondata=eval("("+request.responseText+")");
				if(!jsondata.status){
					document.getElementById("msg").innerHTML = "<font color='red'>用户名已存在!</font>";
				}else{
					document.getElementById("msg").innerHTML = "<font color='green'>用户名可用!</font>";
				}
			}
		}
		request.send("checkuser="+user);
	}
	
	//## (2)JQuery实现Ajax异步请求(文档加载完毕时候进行)
	$("document").ready(function(){
	   $("#name").blur(function(){
	      var user = $(this).val();
	      console.log(user);
	      $.post("CheckUserServlet",{checkuser:user},function(data,status){
	          if (status == "success"){
	              //Jquery 直接解析 json 
		      		if(data.status){
					  $("#msg1").html("<font color='green'>姓名可用!</font>");
		      		}else{
		      		  $("#msg1").html("<font color='red'>姓名已存在!</font>");
		      		}
	          }
	      });
	   });
	});
	
</script>
<div align="center">
<form action="RegisterServlet">
  <label for="username">用户名:</label>
  <input type="text" name="username" id="username" onblur="checkUser()"/> &nbsp; <span id="msg"></span><br>
  <label for="name">真实姓名:</label>
  <input type="text" name="username" id="name"/> &nbsp; <span id="msg1"></span> <br>
  <input type="submit" value="注册"/>
</form>
</div>
<br>
</body>
</html>

(2) Dao 层实现: /Web/src/top/weiyigeek/dao/impl/UserDaoimpl.java

代码语言:javascript
复制
public class UserDaoimpl implements UserDao {
    @Override
    public int checkUser(String name) throws SQLException {
        //1.建立数据连接、
        QueryRunner runner = new QueryRunner(DB.getConn());
        Long result = (Long) runner.query("SELECT COUNT(*) FROM user WHERE name = ?",new ScalarHandler(), name);
        System.out.println("查询完成");
        return result.intValue();
    }
}

(3) Service 层实现: /Web/src/top/weiyigeek/service/impl/UserServiceImpl.java

代码语言:javascript
复制
public class UserServiceImpl implements UserService {
    @Override
    public int checkUser(String name) throws SQLException {
        UserDao ud = new UserDaoimpl();
        return ud.checkUser(name);
    }
}

(4) Service 层实现:/Web/src/top/weiyigeek/servlet/CheckUserServlet.java

代码语言:javascript
复制
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
try {
  //1.设置编码并获取传入的值
  request.setCharacterEncoding("UTF-8");
  response.setContentType("application/json; charset=utf-8");
  String name = request.getParameter("checkuser");
  
  //2.调用Service层中的方法进行实现验证
  UserService service = new UserServiceImpl();
      int res = service.checkUser(name);
      System.out.println(name+ " = " + res);
    
      //3.返还数据
      if (res == 0 ) {
          //(1)文本数据
          //response.getWriter().println(1);
          
          //(2)json数据(这里采用手动设置,后面采用专门得json库进行设置)
          response.getWriter().write("{ \"status\": true }");
      }else {
          response.getWriter().write("{ \"status\": false }");
      }
      
  } catch (SQLException e) {
      // TODO Auto-generated catch block
      e.printStackTrace();
  }
}

示例结果:

WeiyiGeek.
WeiyiGeek.

WeiyiGeek.

异步关键字搜寻

描述:采用Servlet 与 JQuery实现模仿百度搜索,以下为关键代码;

(1) Dao接口实现:/Web/src/top/weiyigeek/dao/impl/SearchDaoimpl.java

代码语言:javascript
复制
public class SearchDaoimpl implements SearchDao {
    @Override
    public List<SearchBean> findWords(String key) throws SQLException {
        QueryRunner runner = new QueryRunner(DB.getConn());
        return runner.query("SELECT * FROM page WHERE title like ? limit ?", new BeanListHandler<SearchBean>(SearchBean.class), key+"%",5);
    }
}

(2) Service实现:/Web/src/top/weiyigeek/service/impl/SearchServiceImpl.java

代码语言:javascript
复制
public class SearchServiceImpl implements SearchService {
    @Override
    public List<SearchBean> findWords(String keys) throws SQLException {
        SearchDao sd = new SearchDaoimpl();
        return sd.findWords(keys);
    }
}

(3) Servlet:/Web/src/top/weiyigeek/servlet/SearchServlet.java

代码语言:javascript
复制
public class SearchServlet extends HttpServlet {
  private static final long serialVersionUID = 1L;
  protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
      try {
          //编码与参数获取
          request.setCharacterEncoding("UTF-8");
          String keys = request.getParameter("words");
          
          //调用service层执行数据库Dao
          SearchService ss = new SearchServiceImpl();
            List<SearchBean> result = ss.findWords(keys);
            
            System.out.println("--------- 查询到的数据 ------------");
            for(SearchBean word: result) {
                System.out.println("#"+word.toString());
            }
            //返回查询到的数据
            request.setAttribute("words", result);
            request.getRequestDispatcher("listSearch.jsp").forward(request, response);
        } catch (SQLException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
  }

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

(4) JSP View页面: /Web/WebContent/baidu.jsp

代码语言:javascript
复制
<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>极客搜索</title>
<!-- Jquery 引入外部 JS -->
<script src="https://cdn.staticfile.org/jquery/1.10.2/jquery.min.js"></script>
</head>
<body>

<script type="text/javascript">
//Jquery使用方式之一
$(function(){
    $("#key").keyup(function(){
       $.post("SearchServlet",{words:$(this).val()},function(data,status){
           $("#result").show();
           $("#result").html(data);
       });
    });
});

//设置搜索关键字为查询得关键字
function setting(x){
    $("#key").val(x.innerText);
}

</script>
<div class="main" align="center">
  <h3>极客搜索</h3> <br>
  <input type="text" placeholder="搜索您想要的"  id="key" name="key" style="width:600px;height:25px"/> &nbsp; &nbsp;
  <input type="submit" value="极客搜索"/>
  <br>
  <div id="result" align="left" style="position:relative;left: -56px;border:1px solid black;display: none;width:600px;"></div>
</div>
</body>
</html>

(5) 数据存放页面:/Web/WebContent/listSearch.jsp

代码语言:javascript
复制
<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>
</head>
<body>
<c:forEach items="${words}" var="word">
  <span style="font-size:x-small;" align="left" onclick="setting(this)">${word.title }</span>
  <span style="width: 100%;display: block;border: 0.1px solid black"></span>
</c:forEach>
</body>
</html>

示例结果:

WeiyiGeek.搜索模仿
WeiyiGeek.搜索模仿

WeiyiGeek.搜索模仿


0x03 XML
省市联动

描述:通过xstream将获取到的对象装换成为XML,并且响应给客户端然后jQuery解析xml在页面添加数据;

lib库依赖导包:xpp3_min-1.1.4c.jar / xstream-1.4.4.jar

案例SQL:

代码语言:javascript
复制
--省市
create table province (
  `pid` smallint primary key COMMENT '省市id',
  `pname` varchar(16) not null COMMENT '省市名称'
);

--城市
create table city (
  `cid` smallint primary key COMMENT '城市区县',
  `cname` varchar(32) not null COMMENT '市区名称',
  `pid` smallint not null COMMENT '外键省市id,必须字段',
  CONSTRAINT fk_id FOREIGN KEY(pid)
  REFERENCES province(pid) 
);


insert into province values (1,"北京"),(2,"上海"),(3,"重庆"),(4,"四川"),(5,"西藏");
insert into city values (1,'东城区',1),(2,'西城区',1),(3,'朝阳区',1),(4,'丰台区',1),(5,"石景山区",1);
insert into city values (6,'黄浦区',2),(7,'徐汇区',2),(8,'长宁区',2),(9,'静安区',2),(10,"杨浦区",2);
insert into city values (11,'江北区',3),(12,'渝北区',3),(13,'南岸区',3),(14,'九龙坡区',3),(15,"沙坪坝区",3);
insert into city values (16,'武侯区',4),(17,'武侯区',4),(18,'武侯区',4),(19,'金牛区',4),(20,"成华区",4);

基础实例:

Dao层接口实现:/Web/src/top/weiyigeek/dao/impl/CityDaoImpl.java

代码语言:javascript
复制
public class CityDaoImpl implements CityDao {
    @Override
    public List<CityBean> findCity(int pid) throws SQLException {
        QueryRunner qr = new QueryRunner(DB.getConn());
        return qr.query("SELECT * FROM city WHERE pid = ? ", new BeanListHandler<CityBean>(CityBean.class), pid);
    }
}

Service层接口实现:/Web/src/top/weiyigeek/service/impl/CityServiceImpl.java

代码语言:javascript
复制
public class CityServiceImpl implements CityService {
    @Override
    public List<CityBean> findCity(int pid) throws SQLException {
        CityDao cd = new CityDaoImpl();
        return cd.findCity(pid);
    }
}

Servlet层:/Web/src/top/weiyigeek/servlet/CityServlet.java

代码语言:javascript
复制
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
      try {
          //1.参数获取
          request.setCharacterEncoding("utf-8");
          int pid = Integer.parseInt(request.getParameter("pid"));
          
          //2.从数据库找出省份的城市
          CityService cs = new CityServiceImpl();
          List<CityBean> list = cs.findCity(pid);
          for (CityBean cityBean : list) {
              System.out.println(cityBean.toString());
          }
          
          //3.实例化XML处理的库
          XStream xStream = new XStream();
          xStream.useAttributeFor(CityBean.class, "cid"); //想把id做成属性
          xStream.alias("city", CityBean.class);         //设置别名
          String xml = xStream.toXML(list);              //转化一个对象成xml字符串(当然也可以将xml转化成为一个对象)
          
          //4.返回数据
          response.setContentType("text/xml;charset=utf-8");
          response.getWriter().write(xml);
      } catch (SQLException e) {
          // TODO Auto-generated catch block
          e.printStackTrace();
      }
}

Jsp层:/Web/WebContent/province.jsp

代码语言:javascript
复制
<script type="text/javascript">
//jQuery
$(function(){
   //1.省份元素
   $("#province").change(function() {
      //2.选择的值进行请求该省份的城市数据
      var pid = $(this).val();
      $.post("CityServlet",{pid:pid} ,function(data,status){
        console.log(data.children.contentType);
        $("#msg").html("<pre>"+data.children[0].innerHTML+"</pre>");
    $("#city").html("<option value=''>-请选择-"); //先清空以前的值
    //遍历:从data数据里面找出所有的city,每次遍历就执行一次function方法;
    $(data).find("city").each(function() {
        //console.log($(this));
      //遍历出来的每一个city,取它的孩子id+cname
      var id = $(this).children("cid").text();
      var cname = $(this).children("cname").text();
      $("#city").append("<option value='"+id+"' >"+cname)
    });
  });
   });
    
});
</script>

省份: <select name="province" id ="province">
    <option value="" >-请选择 -
    <option value="1" >北京
    <option value="2" >上海
    <option value="3" >重庆
    <option value="4" >四川
    <option value="5" >西藏
  </select> &nbsp;
城市: 
  <select name="city" id="city">
    <option value="" >-请选择 -
  </select>

执行结果:

代码语言:javascript
复制
收到Post请求.....
CityBean [cid=11, pid=3, cname=江北区]
CityBean [cid=12, pid=3, cname=渝北区]
CityBean [cid=13, pid=3, cname=南岸区]
CityBean [cid=14, pid=3, cname=九龙坡区]
CityBean [cid=15, pid=3, cname=沙坪坝区]
WeiyiGeek.
WeiyiGeek.

WeiyiGeek.


0x04 JSON

描述:JSON转换程序需要依赖jar说明,开发时候需要进行导包;

代码语言:javascript
复制
commons-beanutils-1.8.3.jar    commons-logging-1.1.1.jar
commons-collections-3.2.1.jar  ezmorph-1.0.6.jar
commons-lang-2.5.jar           json-lib-2.4-jdk15.jar
WeiyiGeek.
WeiyiGeek.

WeiyiGeek.

json-lib-2.4 把javaBean 转化成 json数据(包下的常用两个类):

  • JSONArray —> 变成数组 , 集合 []
  • JSONObject —> 变成简单的数据 { name : zhangsan , age:18}

返回JSON数据格式操作唯一于上面不同得是在进行JSON数据封装以及在JQuery中对数据得解析,在Service层以及Dao数据接口层是没有代码上都改变得的;

Servelet:

代码语言:javascript
复制
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
  try {
      //1.参数获取
      request.setCharacterEncoding("utf-8");
      int pid = Integer.parseInt(request.getParameter("pid"));
      
      //2.从数据库找出省份的城市
      CityService cs = new CityServiceImpl();
      List<CityBean> list = cs.findCity(pid);
      
      //3.进行JSON数据封装
      JSONArray json = JSONArray.fromObject(list);
      String res = json.toString();
      System.out.println("JSON:" + res);        
      
      //4.返回数据
      response.setContentType("text/html;charset=utf-8");
      response.getWriter().write(res);
  } catch (SQLException e) {
      // TODO Auto-generated catch block
      e.printStackTrace();
  }
}

JSP:

代码语言:javascript
复制
<script type="text/javascript">
//jQuery
$(function(){
   //1.省份元素
   $("#province").change(function() {
      //2.选择的值进行请求该省份的城市数据
      var pid = $(this).val();
      $.post("CityServlet",{pid:pid} ,function(data,status){
        $("#msg").html("<pre>"+data+"</pre>");
    $("#city").html("<option value=''>-请选择-"); //先清空以前的值
    //遍历:从data数据里面找出所有的city,每次遍历就执行一次function方法;
      $(data).each(function(index,c){
          console.log("Index:"+index+", id:" + c.id + ", name" + c.cname);
      $("#city").append("<option value='"+c.id+"' >"+c.cname)
      });
  },"json");
   });
    
});
</script>

执行结果:

代码语言:javascript
复制
JSON:[{"cid":6,"cname":"黄浦区","pid":2},{"cid":7,"cname":"徐汇区","pid":2},{"cid":8,"cname":"长宁区","pid":2},{"cid":9,"cname":"静安区","pid":2},{"cid":10,"cname":"杨浦区","pid":2}]
WeiyiGeek.
WeiyiGeek.

WeiyiGeek.

本文参与 腾讯云自媒体分享计划,分享自作者个人站点/博客。
原始发表:2020-03-01,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 0x00 简述
  • 0x01 实例
    • 更新信息
      • 模糊查询
        • 分页实现
        • 0x02 Ajax & JQuery
          • 异步查询
            • 异步关键字搜寻
            • 0x03 XML
              • 省市联动
              • 0x04 JSON
              领券
              问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档