MyBatis实战指南(九)MyBatis+JSP+MySQL 前端页面实现数据库的增加与删除显示数据
前言
- 在上一篇博客中,我们深入探讨了 MyBatis 的核心应用技巧,包括日志配置、缓存优化以及映射机制等关键知识点。
- 本篇将进一步结合 JSP 前端技术与 MySQL 数据库,
- 通过完整的示例代码演示如何实现数据的增删查找操作,并将结果实时展示在 Web 页面上。
我的个人主页,欢迎来阅读我的其他文章
https://blog.csdn.net/2402_83322742?spm=1011.2415.3001.5343
我的MyBatis实战指南知识文章专栏
欢迎来阅读指出不足
https://blog.csdn.net/2402_83322742/category_12969707.html?spm=1001.2014.3001.5482
一、首先我们需要导入我们的Maven并且创建项目框架
1. 配置Maven
我的Maven如何导入在这篇博客里
https://blog.csdn.net/2402_83322742/article/details/147976581
- 然后创建以下JSP框架
Servlet-MyBatis-001/
├── src/
│ ├── main/
│ │ ├── java/
│ │ │ └── com/
│ │ │ └── niit/
│ │ │ ├── mapper/ # MyBatis映射接口
│ │ │ ├── pojo/ # 实体类
│ │ │ ├── service/ # 业务逻辑层
│ │ │ ├── servlet/ # Web Servlet
│ │ │ └── util/ # 工具类
│ │ └── resources/
│ │ ├── com/
│ │ │ └── niit/
│ │ │ └── mapper/ # SQL映射XML文件
│ │ └── mybatis-config.xml # MyBatis核心配置
│ └── test/
│ └── java/
├── pom.xml # Maven依赖配置
└── target/ # 编译输出目录
2. 配置Maven依赖包
<!-- JSP API依赖 - 提供JSP页面开发支持 -->
<dependency>
<groupId>javax.servlet.jsp</groupId>
<artifactId>javax.servlet.jsp-api</artifactId>
<version>2.3.3</version>
<scope>provided</scope> <!-- 由Servlet容器提供,无需打包进应用 -->
</dependency>
<!-- Servlet API依赖 - 提供Servlet开发支持 -->
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>javax.servlet-api</artifactId>
<version>3.1.0</version>
<scope>provided</scope> <!-- 由Servlet容器提供,无需打包进应用 -->
</dependency>
<!-- JSTL表达式语言依赖 - 简化JSP页面开发 -->
<dependency>
<groupId>javax.servlet.jsp.jstl</groupId>
<artifactId>jstl-api</artifactId>
<version>1.2</version>
</dependency>
<!-- JSTL标准标签库实现 - 提供核心标签和格式化标签 -->
<dependency>
<groupId>taglibs</groupId>
<artifactId>standard</artifactId>
<version>1.1.2</version>
</dependency>
<!-- JSTL 1.2实现 - 替代taglibs:standard的另一种选择 -->
<dependency>
<groupId>jstl</groupId>
<artifactId>jstl</artifactId>
<version>1.2</version>
</dependency>
<!-- MySQL数据库驱动 - 用于连接MySQL 8.x数据库 -->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>8.0.33</version>
</dependency>
<!-- MyBatis持久层框架 - 简化数据库操作 -->
<dependency>
<groupId>org.mybatis</groupId>
<artifactId>mybatis</artifactId>
<version>3.5.19</version>
</dependency>
<!-- SLF4J日志API - 提供统一的日志接口 -->
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
<version>2.0.7</version>
</dependency>
<!-- Jackson JSON处理库 - 用于JSON与Java对象的互相转换 -->
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-databind</artifactId>
<version>2.15.2</version>
</dependency>
<!-- Lombok代码简化工具 - 通过注解减少样板代码 -->
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>1.18.38</version>
<scope>provided</scope> <!-- 编译时使用,无需打包进应用 -->
</dependency>
<!-- JUnit测试框架 - 用于编写单元测试 -->
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.13.2</version>
<scope>test</scope> <!-- 仅在测试时使用 -->
</dependency>
3. 创建web文件
- 点击创建工件和应用
然后创建一个与class同级的目录lib
点击加号,导入全部库文件
二、连接数据库
- 在recourse下的mybatis-config.xml文件里加入以下代码
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE configuration
PUBLIC "-//mybatis.org//DTD Config 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-config.dtd">
<configuration>
<settings>
<setting name="logImpl" value="STDOUT_LOGGING"/>
<setting name="mapUnderscoreToCamelCase" value="true"/>
<setting name="autoMappingBehavior" value="FULL"/>
<setting name="autoMappingUnknownColumnBehavior" value="WARNING"/>
</settings>
<environments default="development">
<environment id="development">
<transactionManager type="JDBC"/>
<dataSource type="POOLED">
<property name="driver" value="com.mysql.cj.jdbc.Driver"/>
<property name="url" value="jdbc:mysql://localhost:3306/2023se3"/>
<property name="username" value="root"/>
<property name="password" value=" "/>
</dataSource>
</environment>
</environments>
<mappers>
<mapper resource="com.niit/mapper/UserMapper.xml"/>
<mapper resource="com.niit/mapper/MachineMapper.xml"/>
</mappers>
</configuration>
其中
<dataSource type="POOLED">
<property name="driver" value="com.mysql.cj.jdbc.Driver"/>
<property name="url" value="jdbc:mysql://localhost:3306/2023se3"/>
<property name="username" value="root"/>
<property name="password" value=" "/>
</dataSource>
这里需要与我们的数据库信息链接
三、在pojo包下加入代码
- 创建Machine类,定义机器实体的数据结构,作为系统数据交互的基础载体
package com.niit.pojo;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.util.Date;
@AllArgsConstructor
@NoArgsConstructor
@Data
public class Machine {
private int id;
private String domain;
private String ip;
private String sphinxPath;
private String remark;
private String createTime;
}
四、在Mapper包下加入以下代码
- 接口类名MachineMapper
- 映射文件:MachineMapper.xml
package com.niit.pojo;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.util.Date;
@AllArgsConstructor
@NoArgsConstructor
@Data
public class Machine {
private int id;
private String domain;
private String ip;
private String sphinxPath;
private String remark;
private String createTime;
}
五、在servlet包下加入以下代码
- MachineServlet,处理 HTTP 请求,协调服务层与视图层的数据交互
package com.niit.service;
import com.niit.mapper.MachineMapper;
import com.niit.pojo.Machine;
import com.niit.util.MybatisUtil;
import org.apache.ibatis.session.SqlSession;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
public class MachineService {
public List<Machine> findMachines() {
try (SqlSession sqlSession = MybatisUtil.getSqlSession()) {
MachineMapper mapper = sqlSession.getMapper(MachineMapper.class);
return mapper.findMachines();
}
}
public Machine findMachineById(int id) {
try (SqlSession sqlSession = MybatisUtil.getSqlSession()) {
MachineMapper mapper = sqlSession.getMapper(MachineMapper.class);
return mapper.findMachineById(id);
}
}
public int addMachine(Machine machine) {
try (SqlSession sqlSession = MybatisUtil.getSqlSession()) {
MachineMapper mapper = sqlSession.getMapper(MachineMapper.class);
int result = mapper.addMachine(machine);
sqlSession.commit();
return result;
} catch (Exception e) {
System.err.println("添加机器失败: " + e.getMessage());
throw e; // 抛出异常,让调用者处理
}
}
public int updateMachine(Machine machine) {
try (SqlSession sqlSession = MybatisUtil.getSqlSession()) {
MachineMapper mapper = sqlSession.getMapper(MachineMapper.class);
int result = mapper.updateMachine(machine);
sqlSession.commit();
return result;
} catch (Exception e) {
System.err.println("更新机器失败: " + e.getMessage());
throw e; // 抛出异常,让调用者处理
}
}
public int deleteMachine(int id) {
System.out.println("开始删除机器,ID: " + id);
try (SqlSession sqlSession = MybatisUtil.getSqlSession()) {
MachineMapper mapper = sqlSession.getMapper(MachineMapper.class);
int result = mapper.deleteMachine(id);
System.out.println("删除结果: " + result);
sqlSession.commit();
return result;
} catch (Exception e) {
System.err.println("删除机器失败: " + e.getMessage());
e.printStackTrace(); // 打印完整堆栈信息
throw e;
}
}
// 添加搜索方法
public List<Machine> searchMachines(String keyword) {
try (SqlSession sqlSession = MybatisUtil.getSqlSession()) {
MachineMapper mapper = sqlSession.getMapper(MachineMapper.class);
Map<String, Object> params = new HashMap<>();
params.put("keyword", "%" + keyword + "%");
return mapper.searchMachines(params);
}
}
}
六、在service包下加入以下代码
- MachineService 类
- 封装机器管理的业务逻辑,处理数据库事务和异常
package com.niit.servlet;
import com.niit.pojo.Machine;
import com.niit.service.MachineService;
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 java.io.IOException;
import java.util.List;
@WebServlet("/machine")
public class MachineServlet extends HttpServlet {
private MachineService machineService = new MachineService();
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
String action = req.getParameter("action");
String keyword = req.getParameter("keyword");
if ("add".equals(action)) {
// 跳转到添加页面
req.getRequestDispatcher("machine.jsp").forward(req, resp);
} else if ("edit".equals(action)) {
String idStr = req.getParameter("id");
if (idStr != null) {
int id = Integer.parseInt(idStr);
Machine machine = machineService.findMachineById(id);
if (machine != null) {
req.setAttribute("machine", machine);
System.out.println("已设置编辑机器: " + machine.getDomain()); // 添加调试输出
} else {
req.setAttribute("error", "未找到该机器信息");
}
} else {
req.setAttribute("error", "缺少机器ID参数");
}
req.getRequestDispatcher("machine.jsp").forward(req, resp);
} else if ("delete".equals(action)) {
String idStr = req.getParameter("id");
if (idStr != null) {
int id = Integer.parseInt(idStr);
try {
int result = machineService.deleteMachine(id);
if (result > 0) {
// 成功时直接返回JSON格式的成功标识(而非重定向)
resp.setContentType("application/json;charset=UTF-8");
resp.getWriter().write("{\"success\":true,\"message\":\"删除成功\"}");
return;
} else {
resp.setContentType("application/json;charset=UTF-8");
resp.getWriter().write("{\"success\":false,\"message\":\"删除失败:记录不存在\"}");
return;
}
} catch (Exception e) {
System.err.println("删除异常:" + e.getMessage());
resp.setContentType("application/json;charset=UTF-8");
resp.getWriter().write("{\"success\":false,\"message\":\"删除失败:" + e.getMessage() + "\"}");
return;
}
}
// ID为空的情况
resp.setContentType("application/json;charset=UTF-8");
resp.getWriter().write("{\"success\":false,\"message\":\"删除失败:缺少ID参数\"}");
}else {
List<Machine> machines;
if (keyword != null && !keyword.trim().isEmpty()) {
// 执行搜索
machines = machineService.searchMachines(keyword.trim());
req.setAttribute("searchKeyword", keyword.trim());
} else {
// 查询所有机器
machines = machineService.findMachines();
}
req.setAttribute("machines", machines);
req.getRequestDispatcher("machine.jsp").forward(req, resp);
}
}
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
req.setCharacterEncoding("utf-8");
String action = req.getParameter("action");
if ("add".equals(action)) {
// 处理添加机器请求
String domain = req.getParameter("domain");
String ip = req.getParameter("ip");
String sphinxPath = req.getParameter("sphinxPath");
String remark = req.getParameter("remark");
// 数据验证
if (domain == null || domain.trim().isEmpty() ||
ip == null || ip.trim().isEmpty()) {
req.setAttribute("error", "域名和IP为必填项");
// 添加失败,返回添加页面
req.getRequestDispatcher("machine.jsp").forward(req, resp);
return;
}
// 设置创建时间
java.text.SimpleDateFormat dateFormat = new java.text.SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
String createTime = dateFormat.format(new java.util.Date());
Machine machine = new Machine();
machine.setDomain(domain);
machine.setIp(ip);
machine.setSphinxPath(sphinxPath);
machine.setRemark(remark);
machine.setCreateTime(createTime);
int result = machineService.addMachine(machine);
if (result > 0) {
resp.sendRedirect(req.getContextPath() + "/machine");
} else {
req.setAttribute("error", "添加机器失败");
req.getRequestDispatcher("machine.jsp").forward(req, resp);
}
} else if ("edit".equals(action)) {
// 处理编辑机器请求
String idStr = req.getParameter("id");
if (idStr == null) {
resp.sendRedirect(req.getContextPath() + "/machine");
return;
}
int id = Integer.parseInt(idStr);
String domain = req.getParameter("domain");
String ip = req.getParameter("ip");
String sphinxPath = req.getParameter("sphinxPath");
String remark = req.getParameter("remark");
// 数据验证
if (domain == null || domain.trim().isEmpty() ||
ip == null || ip.trim().isEmpty()) {
req.setAttribute("error", "域名和IP为必填项");
// 编辑失败,返回当前页面并显示错误
Machine machine = new Machine();
machine.setId(id);
machine.setDomain(domain);
machine.setIp(ip);
machine.setSphinxPath(sphinxPath);
machine.setRemark(remark);
req.setAttribute("machine", machine);
req.getRequestDispatcher("machine.jsp").forward(req, resp);
return;
}
Machine machine = new Machine();
machine.setId(id);
machine.setDomain(domain);
machine.setIp(ip);
machine.setSphinxPath(sphinxPath);
machine.setRemark(remark);
int result = machineService.updateMachine(machine);
if (result > 0) {
resp.sendRedirect(req.getContextPath() + "/machine");
} else {
req.setAttribute("error", "更新机器失败");
req.setAttribute("machine", machine);
req.getRequestDispatcher("machine.jsp").forward(req, resp);
}
}
}
}
七、在Util包下加入以下代码
- MybatisUtil,封装 MyBatis 初始化和 SqlSession 管理,提供统一的数据库连接入口
package com.niit.util;
import java.io.IOException;
import java.io.InputStream;
import org.apache.ibatis.io.Resources;
import org.apache.ibatis.session.SqlSession;
import org.apache.ibatis.session.SqlSessionFactory;
import org.apache.ibatis.session.SqlSessionFactoryBuilder;
public class MybatisUtil {
private static SqlSessionFactory factory = null;
static {
try {
// 1、定义 mybatis 主配置文件的位置,从类路径开始的相对路径
String configXml = "mybatis-config.xml";
// 2、读取主配置文件,使用 mybatis 框架中的 Resources 类
InputStream inputStream = Resources.getResourceAsStream(configXml);
// 3、创建 SqlSessionFactory 对象, 使用 SqlSessionFactoryBuilder 类
factory = new SqlSessionFactoryBuilder().build(inputStream);
} catch (IOException e) {
e.printStackTrace();
}
}
public static SqlSession getSqlSession() {
SqlSession sqlSession = null;
if (null != factory) {
// 不自动提交事务(autoCommit: false)
sqlSession = factory.openSession();
}
return sqlSession;
}
}
八 在recourse/com.niit.mapper目录文件下创建MachineMapper.xml并在里面加入以下代码
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper
PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.niit.mapper.MachineMapper">
<select id="findMachines" resultType="com.niit.pojo.Machine">
SELECT
id,
domain,
ip,
sphinx_path as sphinxPath,
remark,
create_time as createTime
FROM machine_info;
</select>
<select id="findMachineById" resultType="com.niit.pojo.Machine" parameterType="int">
SELECT
id,
domain,
ip,
sphinx_path as sphinxPath,
remark,
create_time as createTime
FROM machine_info WHERE id = #{id};
</select>
<insert id="addMachine" parameterType="com.niit.pojo.Machine">
INSERT INTO machine_info (domain, ip, sphinx_path, remark, create_time)
VALUES (#{domain}, #{ip}, #{sphinxPath}, #{remark}, #{createTime})
</insert>
<update id="updateMachine" parameterType="com.niit.pojo.Machine">
UPDATE machine_info
SET domain = #{domain},
ip = #{ip},
sphinx_path = #{sphinxPath},
remark = #{remark}
WHERE id = #{id}
</update>
<delete id="deleteMachine" parameterType="int">
DELETE FROM machine_info WHERE id = #{id}
</delete>
<!-- 搜索机器的SQL,支持按域名、IP搜索 -->
<select id="searchMachines" resultType="com.niit.pojo.Machine" parameterType="map">
SELECT
id,
domain,
ip,
sphinx_path as sphinxPath,
remark,
create_time as createTime
FROM machine_info
<where>
<if test="keyword != null and keyword != ''">
(domain LIKE CONCAT('%', #{keyword}, '%')
OR ip LIKE CONCAT('%', #{keyword}, '%'))
</if>
</where>
ORDER BY id DESC
</select>
</mapper>
九 在mybatis-config.xml文件里加入映射文件
<mapper resource="com.niit/mapper/MachineMapper.xml"/>
十、导入并修改HTML文件
- 我们的HTML例子文件
<!DOCTYPE html>
<html lang="zh-CN">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1 , user-scalable=no">
<title>pha-Admin</title>
<link rel="stylesheet" href="css/bootstrap.min.css"/>
<link rel="stylesheet" href="css/bootstrap-maizi.css"/>
<link rel="stylesheet" href="css/content-style.css"/>
<link rel="stylesheet" href="css/mricode.pagination.css"/>
<link rel="stylesheet" href="css/jquery.fancybox.css"/>
<link rel="stylesheet" href="css/sweetalert.css"/>
</head>
<body>
<!--导航-->
<nav class="navbar navbar-inverse navbar-fixed-top">
<div class="container">
<!--小屏幕导航按钮和logo-->
<div class="navbar-header">
<button class="navbar-toggle" data-toggle="collapse" data-target=".navbar-collapse">
<span class="icon-bar"></span>
<span class="icon-bar"></span>
<span class="icon-bar"></span>
</button>
<a href="index.html" class="navbar-brand"> pha-Admin</a>
</div>
<!--小屏幕导航按钮和logo-->
<!--导航-->
<div class="navbar-collapse collapse">
<ul class="nav navbar-nav">
<li><a href="index.html"><span class="glyphicon glyphicon-home"></span> 后台首页</a></li>
<li><a href="user.html"><span class="glyphicon glyphicon-user"></span> 用户管理</a></li>
<li class="active"><a href="machine.html"><span class="glyphicon glyphicon-expand"></span> 机器管理</a></li>
<li><a href="service.html"><span class="glyphicon glyphicon-tasks"></span> 服务管理</a></li>
<li><a href="log.html"><span class="glyphicon glyphicon-list-alt"></span> 日志管理</a></li>
<li><a href="wiki.html"><span class="glyphicon glyphicon-book"></span> 使用文档</a></li>
</ul>
<ul class="nav navbar-nav navbar-right">
<li class="dropdown">
<a id="dLabel" type="button" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
admin
<span class="caret"></span>
</a>
<ul class="dropdown-menu" aria-labelledby="dLabel">
<li><a href="index.html"><span class="glyphicon glyphicon-cog"></span> 个人设置</a></li>
</ul>
</li>
<li><a href="#bbs"><span class="glyphicon glyphicon-off"></span> 退出</a></li>
</ul>
</div>
<!--导航-->
</div>
</nav>
<!--导航-->
<div class="container">
<div class="row">
<div class="col-md-12">
<div class="panel-body" style="padding: 15px 0;">
<ul class="nav nav-tabs">
<li class="active"><a href="#list" aria-controls="machine" role="tab" data-toggle="tab">机器列表</a></li>
<li><a href="#form" aria-controls="machine" role="tab" data-toggle="tab">添加机器</a></li>
</ul>
</div>
<div class="tab-content">
<div role="tabpanel" class="tab-pane active" id="list">
<div class="panel-body">
<div class="row">
<form>
<div class="col-md-3 col-lg-offset-9">
<div class="input-group">
<input class="form-control" type="text" value="" placeholder="用户名" name="keyword">
<span class="input-group-btn">
<button type="submit" class="btn btn-primary"><i class="glyphicon glyphicon-search"></i></button>
</span>
</div>
</div>
</form>
</div>
</div>
<div class="panel panel-default">
<div class="table-responsive">
<table class="table table-bordered">
<thead>
<tr>
<th class="w8p">id</th>
<th class="w18p">域名</th>
<th class="w18p">ip</th>
<th class="w13p">sphinx路径</th>
<th class="w10p">备注</th>
<th class="w15p">创建时间</th>
<th class="w15p">操作</th>
</tr>
</thead>
<tbody>
<tr>
<td class="center">1</td>
<td>sphinx.test.com.cn</td>
<td>192.168.128.12</td>
<td>/usr/local/sphinx</td>
<td class="center">主机</td>
<td class="center">2017-03-28 12:21:09</td>
<td class="center"><a name="remove" onclick="Common.confirm('确认要删除吗?')"><i class="glyphicon glyphicon-remove"></i>删除</a></td>
</tr>
<tr>
<td class="center">2</td>
<td>sphinx.test.com.cn</td>
<td>192.168.128.13</td>
<td>/usr/local/sphinx</td>
<td class="center">备机</td>
<td class="center">2017-03-28 12:21:09</td>
<td class="center"><a name="remove" onclick="Common.confirm('确认要屏蔽吗?')"><i class="glyphicon glyphicon-remove"></i>删除</a></td>
</tr>
<tr>
<td class="center">3</td>
<td>sphinx.video.com.cn</td>
<td>192.168.158.13</td>
<td>/usr/local/sphinx</td>
<td class="center">主机</td>
<td class="center">2017-03-28 12:21:09</td>
<td class="center"><a name="remove" onclick="Common.confirm('确认要屏蔽吗?')"><i class="glyphicon glyphicon-remove"></i>删除</a></td>
</tr>
<tr>
<td class="center">4</td>
<td>sphinx.test.com.cn</td>
<td>192.168.158.14</td>
<td>/usr/local/sphinx</td>
<td class="center">备机</td>
<td class="center">2017-03-28 12:21:09</td>
<td class="center"><a name="remove" onclick="Common.confirm('确认要屏蔽吗?')"><i class="glyphicon glyphicon-remove"></i>删除</a></td>
</tr>
</tbody>
</table>
</div>
<div class="panel-footer">
<div class="row">
<div class="col-md-8 m-pagination" id="paginator">
</div>
</div>
</div>
</div>
</div>
<div role="tabpanel" class="tab-pane" id="form">
<div class="panel-body">
<form class="form-horizontal">
<div class="form-group">
<label class="col-sm-1 control-label"><span class="text-danger"></span>域名</label>
<div class="col-sm-4">
<input type="text" name="username" class="form-control" placeholder="机器域名" required>
</div>
</div>
<div class="form-group">
<label class="col-sm-1 control-label"><span class="text-danger"> * </span>IP</label>
<div class="col-sm-4">
<input type="email" name="email" class="form-control" placeholder="机器ip" required>
</div>
</div>
<div class="form-group">
<label class="col-sm-1 control-label"><span class="text-danger"> * </span>Sphinx<br>安装目录</label>
<div class="col-sm-4">
<input type="text" name="sphinx_path" class="form-control" placeholder="sphinx安装目录">
</div>
</div>
<div class="form-group">
<label class="col-sm-1 control-label"><span class="text-danger"></span>备注信息</label>
<div class="col-sm-4">
<input type="text" class="form-control" placeholder="备注" required>
</div>
</div>
<div class="form-group">
<div class="col-sm-offset-1 col-sm-10">
<button type="submit" onclick="" class="btn btn-success">保存</button>
</div>
</div>
</form>
<hr>
</div>
</div>
</div>
</div>
</div>
</div>
<!--footer-->
<footer>
<div class="container">
<div class="row">
<div class="col-md-12">
<p class="text-muted center">
Copyright © 2017-2018 phachon@163.com
</p>
</div>
</div>
</div>
</footer>
<!--footer-->
<script src="js/plugins/jquery/jquery.js"></script>
<script src="js/bootstrap.min.js"></script>
<script src="js/plugins/pagination/mricode.pagination.js"></script>
<script src="js/plugins/fancybox/jquery.fancybox.js"></script>
<script src="js/plugins/sweetalert/sweetalert.min.js"></script>
<script src="js/common/common.js"></script>
<script src="js/module/account.js"></script>
<script type="text/javascript">
var pageData = [];
pageData.push({'pageSize': '10', 'total': '1000', 'pageIndex': '2'});
Common.paginator("#paginator", pageData);
Account.bindFancyBox();
</script>
</body>
</html>
修改之后的样子
<%@ page import="com.niit.service.MachineService" %>
<%@ page import="java.util.List" %>
<%@ page import="com.niit.pojo.Machine" %>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
<%@ taglib prefix="fmt" uri="http://java.sun.com/jsp/jstl/fmt" %>
<!DOCTYPE html>
<html lang="zh-CN">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1 , user-scalable=no">
<title>机器管理 - pha-Admin</title>
<link rel="stylesheet" href="css/bootstrap.min.css"/>
<link rel="stylesheet" href="css/bootstrap-maizi.css"/>
<link rel="stylesheet" href="css/content-style.css"/>
<link rel="stylesheet" href="css/mricode.pagination.css"/>
<link rel="stylesheet" href="css/jquery.fancybox.css"/>
<link rel="stylesheet" href="css/sweetalert.css"/>
</head>
<body>
<!--导航-->
<nav class="navbar navbar-inverse navbar-fixed-top">
<div class="container">
<div class="navbar-header">
<button class="navbar-toggle" data-toggle="collapse" data-target=".navbar-collapse">
<span class="icon-bar"></span>
<span class="icon-bar"></span>
<span class="icon-bar"></span>
</button>
<a href="index.jsp" class="navbar-brand"> pha-Admin</a>
</div>
<div class="navbar-collapse collapse">
<ul class="nav navbar-nav">
<li><a href="index.jsp"><span class="glyphicon glyphicon-home"></span> 后台首页</a></li>
<li><a href="/user"><span class="glyphicon glyphicon-user"></span> 用户管理</a></li>
<li class="active"><a href="machine.jsp"><span class="glyphicon glyphicon-expand"></span> 机器管理</a></li>
<li><a href="service.jsp"><span class="glyphicon glyphicon-tasks"></span> 服务管理</a></li>
<li><a href="log.jsp"><span class="glyphicon glyphicon-list-alt"></span> 日志管理</a></li>
<li><a href="wiki.jsp"><span class="glyphicon glyphicon-book"></span> 使用文档</a></li>
</ul>
<ul class="nav navbar-nav navbar-right">
<li class="dropdown">
<a id="dLabel" type="button" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
<%
String displayName = (String) session.getAttribute("displayName");
out.print(displayName != null ? displayName : "admin");
%>
<span class="caret"></span>
</a>
<ul class="dropdown-menu" aria-labelledby="dLabel">
<li><a href="index.jsp"><span class="glyphicon glyphicon-cog"></span> 个人设置</a></li>
</ul>
</li>
<li><a href="#bbs"><span class="glyphicon glyphicon-off"></span> 退出</a></li>
</ul>
</div>
</div>
</nav><!--导航-->
<div class="container">
<div class="row">
<div class="col-md-12">
<div class="panel-body" style="padding: 15px 0;">
<ul class="nav nav-tabs">
<li class="active"><a href="#list" aria-controls="machine" role="tab" data-toggle="tab">机器列表</a></li>
<li><a href="#form" aria-controls="machine" role="tab" data-toggle="tab">添加机器</a></li>
</ul>
</div>
<div class="tab-content">
<div role="tabpanel" class="tab-pane active" id="list">
<div class="panel-body">
<div class="row">
<form action="machine" method="get">
<div class="col-md-3 col-lg-offset-9">
<div class="input-group">
<input class="form-control" type="text"
value="${searchKeyword != null ? searchKeyword : ''}"
placeholder="输入域名或IP搜索" name="keyword">
<span class="input-group-btn">
<button type="submit" class="btn btn-primary"><i class="glyphicon glyphicon-search"></i> 搜索</button>
</span>
</div>
</div>
</form>
</div>
<!-- 搜索结果提示 -->
<c:if test="${searchKeyword != null and not empty searchKeyword}">
<div class="alert alert-info">
搜索结果: " ${searchKeyword} "
<c:if test="${empty machines}">
<span class="text-danger"> - 未找到匹配的机器</span>
</c:if>
</div>
</c:if>
</div>
<div class="panel panel-default">
<div class="table-responsive">
<table class="table table-bordered" id="machineTable">
<thead>
<tr>
<th class="w8p">ID</th>
<th class="w18p">域名</th>
<th class="w18p">IP</th>
<th class="w13p">Sphinx路径</th>
<th class="w10p">备注</th>
<th class="w15p">创建时间</th>
<th class="w15p">操作</th>
</tr>
</thead>
<tbody>
<c:choose>
<c:when test="${not empty machines}">
<c:forEach items="${machines}" var="machine">
<tr>
<td class="center">${machine.id}</td>
<td>${machine.domain}</td>
<td>${machine.ip}</td>
<td>${machine.sphinxPath}</td>
<td class="center">${machine.remark}</td>
<td class="center">${machine.createTime}</td>
<td class="center">
<a href="javascript:;" onclick="deleteMachine(${machine.id})"><i class="glyphicon glyphicon-remove"></i>删除</a>
</td>
</tr>
</c:forEach>
</c:when>
<c:otherwise>
<tr>
<td colspan="7" class="text-center">没有找到机器数据</td>
</tr>
</c:otherwise>
</c:choose>
</tbody>
</table>
</div>
<div class="panel-footer">
<div class="row">
<div class="col-md-8 m-pagination" id="paginator">
</div>
</div>
</div>
</div>
</div>
<div role="tabpanel" class="tab-pane" id="form">
<div class="panel-body">
<c:if test="${not empty error}">
<div class="alert alert-danger" role="alert">
${error}
</div>
</c:if>
<form class="form-horizontal" action="machine" method="post">
<input type="hidden" name="action" value="add">
<div class="form-group">
<label class="col-sm-1 control-label"><span class="text-danger">*</span>域名</label>
<div class="col-sm-4">
<input type="text" name="domain" class="form-control" placeholder="机器域名" required>
</div>
</div>
<div class="form-group">
<label class="col-sm-1 control-label"><span class="text-danger">*</span>IP</label>
<div class="col-sm-4">
<input type="text" name="ip" class="form-control" placeholder="机器IP" required>
</div>
</div>
<div class="form-group">
<label class="col-sm-1 control-label"><span class="text-danger"></span>Sphinx<br>安装目录</label>
<div class="col-sm-4">
<input type="text" name="sphinxPath" class="form-control" placeholder="Sphinx安装目录">
</div>
</div>
<div class="form-group">
<label class="col-sm-1 control-label"><span class="text-danger"></span>备注信息</label>
<div class="col-sm-4">
<input type="text" name="remark" class="form-control" placeholder="备注信息">
</div>
</div>
<div class="form-group">
<div class="col-sm-offset-1 col-sm-10">
<button type="submit" class="btn btn-success">保存</button>
<a href="machine" class="btn btn-default">取消</a>
</div>
</div>
</form>
<hr>
</div>
</div>
</div>
</div>
</div>
</div>
<footer>
<div class="container">
<div class="row">
<div class="col-md-12">
<p class="text-muted center">
Copyright © 2017-2025 phachon@163.com
</p>
</div>
</div>
</div>
</footer>
<!--footer-->
<script src="js/plugins/jquery/jquery.js"></script>
<script src="js/bootstrap.min.js"></script>
<script src="js/plugins/pagination/mricode.pagination.js"></script>
<script src="js/plugins/fancybox/jquery.fancybox.js"></script>
<script src="js/plugins/sweetalert/sweetalert.min.js"></script>
<script src="js/common/common.js"></script>
<!-- 替换旧版JS -->
<script src="https://cdn.jsdelivr.net/npm/sweetalert2@11"></script>
<script type="text/javascript">
// 初始化分页
var pageData = [];
pageData.push({'pageSize': '10', 'total': '100', 'pageIndex': '1'});
Common.paginator("#paginator", pageData);
function deleteMachine(id) {
Swal.fire({ // 注意Swal.fire替换旧版swal
title: "确认删除?",
text: "此操作将永久删除该机器信息,无法恢复!",
icon: "warning",
showCancelButton: true,
confirmButtonText: "删除",
cancelButtonText: "取消",
dangerMode: true
}).then((result) => {
if (result.isConfirmed) {
$.ajax({
url: "machine?action=delete&id=" + id,
type: "GET",
success: function(response) {
if (response.includes("删除成功")) {
Swal.fire("已删除!", "该机器信息已被成功删除。", "success")
.then(() => location.reload());
} else {
Swal.fire("删除失败", response, "error");
}
},
error: function(xhr, status, error) {
Swal.fire("删除错误", "服务器错误:" + error, "error");
}
});
}
});
}
</script>
</body>
</html>
搜索表单动态化
- 表单添加
action="machine" method="get"
,支持后端接收搜索参数。 - 输入框默认值使用EL表达式获取前端传递的搜索关键词:
<input class="form-control" type="text" value="${searchKeyword != null ? searchKeyword : ''}" placeholder="输入域名或IP搜索" name="keyword">
- 添加搜索结果提示信息,使用JSTL条件判断:
<c:if test="${searchKeyword != null and not empty searchKeyword}"> <div class="alert alert-info"> 搜索结果: " ${searchKeyword} " <c:if test="${empty machines}"> <span class="text-danger"> - 未找到匹配的机器</span> </c:if> </div> </c:if>
- 表单添加
表格数据动态渲染
- 移除原始静态数据行,使用JSTL循环渲染后端传递的
machines
列表:<c:forEach items="${machines}" var="machine"> <tr> <td class="center">${machine.id}</td> <td>${machine.domain}</td> <td>${machine.ip}</td> <td>${machine.sphinxPath}</td> <td class="center">${machine.remark}</td> <td class="center">${machine.createTime}</td> <td class="center"> <a href="javascript:;" onclick="deleteMachine(${machine.id})"><i class="glyphicon glyphicon-remove"></i>删除</a> </td> </tr> </c:forEach>
- 无数据时显示提示信息:
<c:otherwise> <tr> <td colspan="7" class="text-center">没有找到机器数据</td> </tr> </c:otherwise>
- 移除原始静态数据行,使用JSTL循环渲染后端传递的
表单提交逻辑修改
- 表单
action="machine" method="post"
,添加隐藏字段action="add"
标识添加操作。 - 新增错误提示区域,使用JSTL显示后端错误信息:
<c:if test="${not empty error}"> <div class="alert alert-danger" role="alert"> ${error} </div> </c:if>
- 表单
十一、运行项目
以上就是这篇博客的全部内容,下一篇我们将继续探索MyBatis的更多精彩内容。
我的个人主页,欢迎来阅读我的其他文章
https://blog.csdn.net/2402_83322742?spm=1011.2415.3001.5343
我的MyBatis实战指南知识文章专栏
欢迎来阅读指出不足
https://blog.csdn.net/2402_83322742/category_12969707.html?spm=1001.2014.3001.5482
非常感谢您的阅读,喜欢的话记得三连哦 |