水果系统项目分析pro10-fruit1.5-thymeleaf

发布时间 2023-10-04 20:33:35作者: harper886

水果系统项目分析pro10-fruit1.5-thymeleaf

基本架构

image-20231003221603202

增加

  • 增加水果
  • 删除水果
  • 渲染页面
  • 更新库存

如上面所示的功能

indexServlet

package com.atguigu.fruit.servlets;

import com.atguigu.fruit.dao.FruitDAO;
import com.atguigu.fruit.dao.impl.FruitDAOImpl;
import com.atguigu.fruit.pojo.Fruit;
import com.atguigu.myssm.myspringmvc.ViewBaseServlet;

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 java.io.IOException;
import java.util.List;

//Servlet从3.0版本开始支持注解方式的注册
@WebServlet("/index")
public class IndexServlet extends ViewBaseServlet {
    @Override
    public void doGet(HttpServletRequest request , HttpServletResponse response)throws IOException, ServletException {
        FruitDAO fruitDAO = new FruitDAOImpl();
        List<Fruit> fruitList = fruitDAO.getFruitList();
        //保存到session作用域
        HttpSession session = request.getSession() ;
        session.setAttribute("fruitList",fruitList);
        //此处的视图名称是 index
        //那么thymeleaf会将这个 逻辑视图名称 对应到 物理视图 名称上去
        //逻辑视图名称 :   index
        //物理视图名称 :   view-prefix + 逻辑视图名称 + view-suffix
        //所以真实的视图名称是:      /       index       .html
        super.processTemplate("index",request,response);
    }
}

和上一个版本一样没什么太大的变化主要还是是去渲染html页面

DelServlet

package com.atguigu.fruit.servlets;

import com.atguigu.fruit.dao.FruitDAO;
import com.atguigu.fruit.dao.impl.FruitDAOImpl;
import com.atguigu.myssm.myspringmvc.ViewBaseServlet;
import com.atguigu.myssm.util.StringUtil;

import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;

@WebServlet("/del.do")
public class DelServlet extends ViewBaseServlet {
    private FruitDAO fruitDAO = new FruitDAOImpl();
    @Override
    public void doGet(HttpServletRequest request , HttpServletResponse response)throws IOException, ServletException {
        String fidStr = request.getParameter("fid");
        if(StringUtil.isNotEmpty(fidStr)){
            int fid = Integer.parseInt(fidStr);
            fruitDAO.delFruit(fid);

            //super.processTemplate("index",request,response);
            response.sendRedirect("index");
        }
    }
}

使用了注解/del.do当页面进入del.do的时候执行这个Servlet从写了doget方法当点击删除的时候将会给DelServlet发送请求,这时候我们可以获取到想要删除的水果的fidStr,当fidStr不为null或者不为空串的时候,将其转数字fid,然后盗用delFruit()方法在数据库中将这条记录删除.执行完成之后客户端冲定向到index页面

AddServlet

package com.atguigu.fruit.servlets;

import com.atguigu.fruit.dao.FruitDAO;
import com.atguigu.fruit.dao.impl.FruitDAOImpl;
import com.atguigu.fruit.pojo.Fruit;
import com.atguigu.myssm.myspringmvc.ViewBaseServlet;

import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;

@WebServlet("/add.do")
public class AddServlet extends ViewBaseServlet {

    private FruitDAO fruitDAO = new FruitDAOImpl();

    @Override
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        request.setCharacterEncoding("UTF-8");

        String fname = request.getParameter("fname");
        Integer price = Integer.parseInt(request.getParameter("price")) ;
        Integer fcount = Integer.parseInt(request.getParameter("fcount"));
        String remark = request.getParameter("remark");

        Fruit fruit = new Fruit(0,fname , price , fcount , remark ) ;

        fruitDAO.addFruit(fruit);

        response.sendRedirect("index");

    }
}

当add.do点击增加按钮的时候的时候执行这个Servlet方法.

  1. 先设置编码为utf-8防止乱码
  2. 获取输入框中水果的全部信息.
  3. 将水果信息封装为一个fruit对象
  4. 调用addFruit()方法将这个friut对象放入数据库
  5. 客户端从定向为index页面

EditServlet

package com.atguigu.fruit.servlets;

import com.atguigu.fruit.dao.FruitDAO;
import com.atguigu.fruit.dao.impl.FruitDAOImpl;
import com.atguigu.fruit.pojo.Fruit;
import com.atguigu.myssm.myspringmvc.ViewBaseServlet;
import com.atguigu.myssm.util.StringUtil;

import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;

@WebServlet("/edit.do")
public class EditServlet extends ViewBaseServlet {

    private FruitDAO fruitDAO = new FruitDAOImpl();

    @Override
    public void doGet(HttpServletRequest request , HttpServletResponse response)throws IOException, ServletException {
        String fidStr = request.getParameter("fid");
        if(StringUtil.isNotEmpty(fidStr)){
            int fid = Integer.parseInt(fidStr);
            Fruit fruit = fruitDAO.getFruitByFid(fid);
            request.setAttribute("fruit",fruit);
            super.processTemplate("edit",request,response);
        }
    }
}

这个方法是给edit.do页面做渲染使用的

  1. 当用户点击了某个数据,将该数据的fidStr获取出来
  2. 当fidStr不为空的时候,将其转化为数字fid
  3. 然后通过fruit.DAO()方法将这个对象获取出来,并且保存到request作用域里面.
  4. 然后将也面交给thymeleaf渲染到edit.html页面上面

UpdateServlet

package com.atguigu.fruit.servlets;

import com.atguigu.fruit.dao.FruitDAO;
import com.atguigu.fruit.dao.impl.FruitDAOImpl;
import com.atguigu.fruit.pojo.Fruit;
import com.atguigu.myssm.myspringmvc.ViewBaseServlet;

import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;

@WebServlet("/update.do")
public class UpdateServlet extends ViewBaseServlet {

    private FruitDAO fruitDAO = new FruitDAOImpl();

    @Override
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        //1.设置编码
        request.setCharacterEncoding("utf-8");

        //2.获取参数
        String fidStr = request.getParameter("fid");
        Integer fid = Integer.parseInt(fidStr);
        String fname = request.getParameter("fname");
        String priceStr = request.getParameter("price");
        int price = Integer.parseInt(priceStr);
        String fcountStr = request.getParameter("fcount");
        Integer fcount = Integer.parseInt(fcountStr);
        String remark = request.getParameter("remark");

        //3.执行更新
        fruitDAO.updateFruit(new Fruit(fid,fname, price ,fcount ,remark ));

        //4.资源跳转
        //super.processTemplate("index",request,response);
        //request.getRequestDispatcher("index.html").forward(request,response);
        //此处需要重定向,目的是重新给IndexServlet发请求,重新获取furitList,然后覆盖到session中,这样index.html页面上显示的session中的数据才是最新的
        response.sendRedirect("index");
    }
}

// java.lang.NumberFormatException: For input string: ""

当进入edit页面修改完信息并且点击完提交按钮之后执行这里面的Servlet方法

  1. 先设置编码
  2. 获取修改完之后的水果信息并且封装成对象放入updateFruit()方法里面进行更新.
  3. 将页面重新定向到index页面上面.

FruitDAO

package com.atguigu.fruit.dao;

import com.atguigu.fruit.pojo.Fruit;

import java.util.List;

public interface FruitDAO {
    //获取所有的库存列表信息
    List<Fruit> getFruitList();

    //根据fid获取特定的水果库存信息
    Fruit getFruitByFid(Integer fid);

    //修改指定的库存记录
    void updateFruit(Fruit fruit);

    //根据fid删除指定的库存记录
    void delFruit(Integer fid);

    //添加新库存记录
    void addFruit(Fruit fruit);
}

FruitDAOImpl

package com.atguigu.fruit.dao.impl;

import com.atguigu.fruit.dao.FruitDAO;
import com.atguigu.fruit.pojo.Fruit;
import com.atguigu.myssm.basedao.BaseDAO;

import java.util.List;

public class FruitDAOImpl extends BaseDAO<Fruit> implements FruitDAO {
    @Override
    public List<Fruit> getFruitList() {
        return super.executeQuery("select * from t_fruit");
    }

    @Override
    public Fruit getFruitByFid(Integer fid) {
        return super.load("select * from t_fruit where fid = ? " , fid);
    }

    @Override
    public void updateFruit(Fruit fruit) {
        String sql = "update t_fruit set fname = ? , price = ? , fcount = ? , remark = ? where fid = ? " ;
        super.executeUpdate(sql,fruit.getFname(),fruit.getPrice(),fruit.getFcount(),fruit.getRemark(),fruit.getFid());
    }

    @Override
    public void delFruit(Integer fid) {
        super.executeUpdate("delete from t_fruit where fid = ? " , fid) ;
    }

    @Override
    public void addFruit(Fruit fruit) {
        String sql = "insert into t_fruit values(0,?,?,?,?)";
        super.executeUpdate(sql,fruit.getFname(),fruit.getPrice(),fruit.getFcount(),fruit.getRemark());
    }
}

Fruit

package com.atguigu.fruit.pojo;

public class Fruit {
    private Integer fid ;
    private String fname ;
    private Integer price ;
    private Integer fcount ;
    private String remark ;

    public Fruit(){}

    public Fruit(Integer fid, String fname, Integer price, Integer fcount, String remark) {
        this.fid = fid;
        this.fname = fname;
        this.price = price;
        this.fcount = fcount;
        this.remark = remark;
    }

    public Integer getFid() {
        return fid;
    }

    public void setFid(Integer fid) {
        this.fid = fid;
    }

    public String getFname() {
        return fname;
    }

    public void setFname(String fname) {
        this.fname = fname;
    }

    public Integer getPrice() {
        return price;
    }

    public void setPrice(Integer price) {
        this.price = price;
    }

    public Integer getFcount() {
        return fcount;
    }

    public void setFcount(Integer fcount) {
        this.fcount = fcount;
    }

    public String getRemark() {
        return remark;
    }

    public void setRemark(String remark) {
        this.remark = remark;
    }

    @Override
    public String toString() {
        return fid + "\t\t" + fname + "\t\t" + price +"\t\t" + fcount +"\t\t" + remark ;
    }
}

add.html

<html xmlns:th="http://www.thymeleaf.org">
<head>
	<meta charset="utf-8">
	<link rel="stylesheet" href="css/add.css">
</head>
<body>
<div id="div_container">
	<div id="div_fruit_list">
		<p class="center f30">新增库存信息2</p>
		<!--<form action="add.do" method="post">-->
		<form action="add.do" method="post">
			<table id="tbl_fruit">
				<tr>
					<th class="w20">名称:</th>
					<!-- <td><input type="text" name="fname" th:value="${fruit.fname}"/></td> -->
					<td><input type="text" name="fname" /></td>
				</tr>
				<tr>
					<th class="w20">单价:</th>
					<td><input type="text" name="price" /></td>
				</tr>
				<tr>
					<th class="w20">库存:</th>
					<td><input type="text" name="fcount" /></td>
				</tr>
				<tr>
					<th class="w20">备注:</th>
					<td><input type="text" name="remark" /></td>
				</tr>
				<tr>
					<th colspan="2">
						<input type="submit" value="添加" />
					</th>
				</tr>
			</table>
		</form>
	</div>
</div>
</body>
</html>

这是增加库存的页面,我们填好信息然后点击添加就会交给add.do处理.

edit.html

<html xmlns:th="http://www.thymeleaf.org">
<head>
	<meta charset="utf-8">
	<link rel="stylesheet" href="css/edit.css">
</head>
<body>
<div id="div_container">
	<div id="div_fruit_list">
		<p class="center f30">编辑库存信息3</p>
		<form th:action="@{/update.do}" method="post" th:object="${fruit}">
			<!-- 隐藏域 : 功能类似于文本框 , 它的值会随着表单的发送也会发送给服务器,但是界面上用户看不到 -->
			<input type="hidden" name="fid" th:value="*{fid}"/>
			<table id="tbl_fruit">
				<tr>
					<th class="w20">名称:</th>
					<!-- <td><input type="text" name="fname" th:value="${fruit.fname}"/></td> -->
					<td><input type="text" name="fname" th:value="*{fname}"/></td>
				</tr>
				<tr>
					<th class="w20">单价:</th>
					<td><input type="text" name="price" th:value="*{price}"/></td>
				</tr>
				<tr>
					<th class="w20">库存:</th>
					<td><input type="text" name="fcount" th:value="*{fcount}"/></td>
				</tr>
				<tr>
					<th class="w20">备注:</th>
					<td><input type="text" name="remark" th:value="*{remark}"/></td>
				</tr>
				<tr>
					<th colspan="2">
						<input type="submit" value="修改" />
					</th>
				</tr>
			</table>
		</form>
	</div>
</div>
</body>
</html>

这个页面会通过thymeleaf该fid的数据信息,同时还有一个隐藏的fid发送过来便于后面的操作.当我们点击修改的时候又会把数据发送给update.do Servlet来更新这些信息.

index.html

<html xmlns:th="http://www.thymeleaf.org">
	<head>
		<meta charset="utf-8">
		<link rel="stylesheet" href="css/index.css">
        <script language="JavaScript" src="js/index.js"></script>
	</head>
	<body>
		<div id="div_container">
			<div id="div_fruit_list">
				<p class="center f30">欢迎使用水果库存后台管理系统</p>
				<div style="border:0px solid red;width:60%;margin-left:20%;text-align:right;">
					<a th:href="@{/add.html}" style="border:0px solid blue;margin-bottom:4px;">添加新库存记录</a>
				</div>
				<table id="tbl_fruit">
					<tr>
						<th class="w20">名称1</th>
						<th class="w20">单价</th>
						<th class="w20">库存</th>
						<th>操作</th>
					</tr>
					<tr th:if="${#lists.isEmpty(session.fruitList)}">
						<td colspan="4">对不起,库存为空!</td>
					</tr>
					<tr th:unless="${#lists.isEmpty(session.fruitList)}" th:each="fruit : ${session.fruitList}">
						<!-- <td><a th:text="${fruit.fname}" th:href="@{'/edit.do?fid='+${fruit.fid}}">苹果</a></td> -->
						<td><a th:text="${fruit.fname}" th:href="@{/edit.do(fid=${fruit.fid})}">苹果</a></td>
						<td th:text="${fruit.price}">5</td>
						<td th:text="${fruit.fcount}">20</td>
						<!-- <td><img src="imgs/del.jpg" class="delImg" th:onclick="'delFruit('+${fruit.fid}+')'"/></td> -->
                        <td><img src="imgs/del.jpg" class="delImg" th:onclick="|delFruit(${fruit.fid})|"/></td>
					</tr>
				</table>
			</div>
		</div>
	</body>
</html>

index.css

*{
	color: threeddarkshadow;
}
a{
	text-decoration: none;
}
body{
	margin:0;
	padding:0;
	background-color:#808080;
}
div{
	position:relative;
	float:left;
}

#div_container{
	width:80%;
	height:100%;
	border:0px solid blue;
	margin-left:10%;
	float:left;
	background-color: honeydew;
	border-radius:8px;
}
#div_fruit_list{
	width:100%;
	border:0px solid red;
}
#tbl_fruit{
	width:60%;
	line-height:28px;
	margin-top:16px;
	margin-left:20%;
}
#tbl_fruit , #tbl_fruit tr , #tbl_fruit th , #tbl_fruit td{
	border:1px solid gray;
	border-collapse:collapse;
	text-align:center;
	font-size:16px;
	font-family:"黑体";
	font-weight:lighter;
	
}
.w20{
	width:20%;
}
.delImg{
	width:24px;
	height:24px;
}
.btn{
	border:1px solid lightgray;
	width:80px;
	height:24px;
}

.center{
	text-align:center;
}
.f30{
	font-size: 30px;
}

add.css

*{
	color: threeddarkshadow;
}
body{
	margin:0;
	padding:0;
	background-color:#808080;
}
div{
	position:relative;
	float:left;
}

#div_container{
	width:80%;
	height:100%;
	border:0px solid blue;
	margin-left:10%;
	float:left;
	background-color: honeydew;
	border-radius:8px;
}
#div_fruit_list{
	width:100%;
	border:0px solid red;
}
#tbl_fruit{
	width:60%;
	line-height:28px;
	margin-top:16px;
	margin-left:20%;
}
#tbl_fruit , #tbl_fruit tr , #tbl_fruit th , #tbl_fruit td{
	border:1px solid gray;
	border-collapse:collapse;
	text-align:center;
	font-size:16px;
	font-family:"黑体";
	font-weight:lighter;
	
}
.w20{
	width:20%;
}
.delImg{
	width:24px;
	height:24px;
}
.btn{
	border:1px solid lightgray;
	width:80px;
	height:24px;
}

.center{
	text-align:center;
}
.f30{
	font-size: 30px;
}

edit.css

*{
	color: threeddarkshadow;
}
body{
	margin:0;
	padding:0;
	background-color:#808080;
}
div{
	position:relative;
	float:left;
}

#div_container{
	width:80%;
	height:100%;
	border:0px solid blue;
	margin-left:10%;
	float:left;
	background-color: honeydew;
	border-radius:8px;
}
#div_fruit_list{
	width:100%;
	border:0px solid red;
}
#tbl_fruit{
	width:60%;
	line-height:28px;
	margin-top:16px;
	margin-left:20%;
}
#tbl_fruit , #tbl_fruit tr , #tbl_fruit th , #tbl_fruit td{
	border:1px solid gray;
	border-collapse:collapse;
	text-align:center;
	font-size:16px;
	font-family:"黑体";
	font-weight:lighter;
	
}
.w20{
	width:20%;
}
.delImg{
	width:24px;
	height:24px;
}
.btn{
	border:1px solid lightgray;
	width:80px;
	height:24px;
}

.center{
	text-align:center;
}
.f30{
	font-size: 30px;
}

index.js

function delFruit(fid){
    if(confirm('是否确认删除?')){
        window.location.href='del.do?fid='+fid;
    }
}

web.xml

<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd"
         version="4.0">
    <!-- 配置上下文参数 -->
    <context-param>
        <param-name>view-prefix</param-name>
        <param-value>/</param-value>
    </context-param>
    <context-param>
        <param-name>view-suffix</param-name>
        <param-value>.html</param-value>
    </context-param>
</web-app>