JavaWeb-03-Servlet-07-在线考试管理系统
JavaWeb-03-Servlet-07-在线考试管理系统-用户信息管理模块
试题信息管理传送门:试题信息管理
考试管理模块传送门:考试管理
本次项目文件:点击下载
提取码:922w
1.目标
用户信息管理模块
2.功能实现
- 用户信息注册
- 用户信息查询
- 用户信息删除
- 用户信息更新
- 用户登录验证
3.准备工作
3.1创建用户信息表(t_users.frm)
drop table if exists t_users;
create table t_users (
userId int primary key auto_increment,#用户编号,设置为自增
userName varchar(255), #用户名
passWord varchar(255), #用户密码
sex char(1), #用户性别'男'or'女'
age int, #用户年龄
email varchar(255) unique #用户邮箱,设置为唯一不可重复
);
insert into t_users(userName,passWord,sex,age,email) value('张三','111','男',20,'zhangsan@qq.com');
insert into t_users(userName,passWord,sex,age,email) value('李四','222','女',21,'lisi@qq.com');
commit;
select * from t_users;
导入数据库中:
3.2创建用户信息表对应实体类Users
在src下,创建com.tsccg.entity.Users实体类
package com.tsccg.entity;
import org.omg.PortableInterceptor.INACTIVE;
/**
* @Author: TSCCG
* @Date: 2021/08/14 15:18
* 用户信息表对应的实体类
*/
public class Users {
private Integer userId;
private String userName;
private String passWord;
private String sex;
private Integer age;
private String email;
/**
* 无参构造
*/
public Users() {
}
/**
* 有参构造
* @param userId 用户编号
* @param userName 用户名
* @param passWord 用户密码
* @param sex 用户性别'男'or'女'
* @param age 用户年龄
* @param email 用户邮箱
*/
public Users(Integer userId, String userName, String passWord, String sex, Integer age, String email) {
this.userId = userId;
this.userName = userName;
this.passWord = passWord;
this.sex = sex;
this.age = age;
this.email = email;
}
public Integer getUserId() {
return userId;
}
public void setUserId(Integer userId) {
this.userId = userId;
}
public String getUserName() {
return userName;
}
public void setUserName(String userName) {
this.userName = userName;
}
public String getPassWord() {
return passWord;
}
public void setPassWord(String passWord) {
this.passWord = passWord;
}
public String getSex() {
return sex;
}
public void setSex(String sex) {
this.sex = sex;
}
public Integer getAge() {
return age;
}
public void setAge(Integer age) {
this.age = age;
}
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
}
3.3编写JDBC工具类
在/web/WEB-INF目录下,创建一个文件夹,命名为lib,将MySQL驱动放进去。
在src下,创建一个配置文件JDBC.properties。把驱动名、数据库等信息都放到里面。
driverName=com.mysql.jdbc.Driver
url=jdbc:mysql://localhost:3306/db_user
user=root
password=123456
在src下,创建com.tsccg.util.JdbcUtil工具类。
使用资源绑定器获取相关信息。
package com.tsccg.util;
import java.sql.*;
import java.util.ResourceBundle;
/**
* @Author: TSCCG
* @Date: 2021/08/14 15:32
* JDBC工具类
* 1.注册驱动*
* 2.获取连接*
* 3.获取预编译的数据库操作对象
* 4.执行sql
* 5.处理查询结果集
* 6.关闭资源*
*/
public class JdbcUtil {
/**
* 创建资源绑定器对象
*/
private static final ResourceBundle BUNDLE = ResourceBundle.getBundle("JDBC");
//1.注册驱动
static {
try {
Class.forName(BUNDLE.getString("driverName"));
} catch (ClassNotFoundException e) {
e.printStackTrace();
}
}
/**
* 2.获取连接
* @return 返回连接对象
* @throws SQLException 将SQLException异常上抛
*/
public static Connection connect() throws SQLException {
return DriverManager.getConnection(BUNDLE.getString("url"),
BUNDLE.getString("user"),BUNDLE.getString("password"));
}
/**
* 6.释放资源
* @param conn 连接对象
* @param stmt 数据库操作对象
* @param rs 查询结果集对象
*/
public static void closeAll(Connection conn, Statement stmt, ResultSet rs) {
if(rs != null) {
try {
rs.close();
} catch (SQLException throwables) {
throwables.printStackTrace();
}
}
if(stmt != null) {
try {
stmt.close();
} catch (SQLException throwables) {
throwables.printStackTrace();
}
}
if(conn != null) {
try {
conn.close();
} catch (SQLException throwables) {
throwables.printStackTrace();
}
}
}
}
4.导航页面
在从浏览器向服务器发送请求时,需要发送各种地址,为了方便用户操作,需要一个导航页面。
在/web目录下新建一个html文件,命名为index.html
<html>
<head>
<meta charset="UTF-8">
<title>导航栏</title>
</head>
<frameset rows="15%,85%">
<frame name="top" src="/MyWeb/top.html" />
<frameset cols="15%,85%">
<frame name="left" src="/MyWeb/left.html"/>
<frame name="right"/>
</frameset>
</frameset>
</html>
在/web目录下新建top.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>top</title>
</head>
<body style="background-color: #00fff6">
<h1 align="center" style="color: #ff0000">在线考试管理系统</h1>
</body>
</html>
在/web目录下新建left.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>left</title>
</head>
<body>
<ul>
<li>用户信息管理
<ol>
<li><a href="/MyWeb/user_add.html" target="right">用户信息注册</a></li>
<li><a href="/MyWeb/user/find" target="right">用户信息查询</a></li>
</ol>
</li>
<li>试题信息管理</li>
<li>考试管理</li>
</ul>
</body>
</html>
5.用户信息注册
5.1用户信息注册流程图
5.2创建前台页面
HTML文件属于静态资源文件,需要放在/web目录下。
在/web目录下新建user_add.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>用户注册</title>
</head>
<body>
<form action="http://localhost:8080/MyWeb/user/add" method="GET" id="form">
<h2 align="center">用户注册</h2>
<table align="center">
<!-- 用户名 -->
<tr>
<td>用户名:</td>
<td><input type="text" name="userName"></td>
</tr>
<!-- 密码 -->
<tr>
<td>密码:</td>
<td><input type="password" name="passWord"></td>
</tr>
<!-- 性别 -->
<tr>
<td>性别:</td>
<td>
<label>
<input type="radio" name="sex" value="男" checked="checked">男
</label>
<label>
<input type="radio" name="sex" value="女">女
</label>
</td>
</tr>
<!-- 年龄 -->
<tr>
<td>年龄:</td>
<td><input type="text" name="age"></td>
</tr>
<!-- 邮箱地址 -->
<tr>
<td>邮箱地址:</td>
<td><input type="text" name="email"></td>
</tr>
<!-- 提交 -->
<tr>
<td><input type="submit" value="提交"></td>
<td><input type="reset" value="重置"></td>
</tr>
</table>
</form>
</body>
</html>
5.3编写JDBC类【UserDao】
这个类的主要作用就是连接数据库,对数据库中的数据进行增删查改。
这里先实现【添加】功能,将用户信息写入数据库中。
package com.tsccg.com.tsccg.dao;
import com.tsccg.entity.Users;
import com.tsccg.util.JdbcUtil;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.SQLException;
/**
* @Author: TSCCG
* @Date: 2021/08/14 21:07
*/
public class UserDao {
/**
* 向数据库中添加用户信息
* @param users 用户信息表对应实体类
* @return 返回
*/
public boolean add(Users users) {
Connection conn = null;
PreparedStatement ps = null;
boolean result = false;
try {
//注册、获取连接对象
conn = JdbcUtil.connect();
//获取预编译的数据库操作对象
String sql = "insert into t_users(userName,passWord,sex,age,email) " +
"value(?,?,?,?,?)";
ps = conn.prepareStatement(sql);
ps.setString(1,users.getUserName());
ps.setString(2,users.getPassWord());
ps.setString(3,users.getSex());
ps.setInt(4,users.getAge());
ps.setString(5,users.getEmail());
if(ps.executeUpdate() > 0) {
result = true;
}
} catch (SQLException throwables) {
throwables.printStackTrace();
} finally {
JdbcUtil.closeAll(conn,ps,null);
}
return result;
}
}
5.4编写Servlet接口实现类【UserAddServlet】
这个类的主要作用有三个:
- 调用【请求对象】读取请求头/请求体中的请求参数信息,也就是用户输入的信息
- 调用【UserDao】将用户信息放入insert命令,并借助JDBC规范发送到数据库服务器
- 调用【响应对象】将【处理结果】以二进制形式写入响应体中
package com.tsccg.controller;
import com.tsccg.com.tsccg.dao.UserDao;
import com.tsccg.entity.Users;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.PrintWriter;
/**
* @Author: TSCCG
* @Date: 2021/08/14 20:11
*/
public class UserAddServlet extends HttpServlet {
@Override
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
//通知请求对象,使用utf-8字符集对请求体内的二进制内容进行一次重新解码
request.setCharacterEncoding("utf-8");
insert(request,response);
}
@Override
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
insert(request,response);
}
private static void insert(HttpServletRequest request, HttpServletResponse response) throws IOException {
//1.调用【请求对象】读取【请求头】中的请求参数信息,得到用户的信息
String userName,passWord,sex,age,email;
UserDao dao = null;
Users users = null;
PrintWriter out = null;
userName = request.getParameter("userName");
passWord = request.getParameter("passWord");
sex = request.getParameter("sex");
age = request.getParameter("age");
email = request.getParameter("email");
//2.调用【UserDao】将用户信息放入insert命令,并借助JDBC规范发送到数据库服务器
dao = new UserDao();
users = new Users(null,userName,passWord,sex,Integer.valueOf(age),email);
boolean result = dao.add(users);
//3.调用【响应对象】将【处理结果】以二进制形式写入响应体中
response.setContentType("text/html;charset=utf-8");
out = response.getWriter();
out.print(result ? "<font style='color: green;font-size: 30px'>注册成功</font>"
: "<font style='color: red;font-size: 30px'>注册失败</font>");
}
}
5.5注册功能测试
发布网站,开启服务器。
如果用户信息成功写入数据库,则显示【注册成功】,反之显示【注册失败】。
6.用户信息查询
6.1用户信息查询流程图
6.2在【UserDao】类中添加查询功能
package com.tsccg.com.tsccg.dao;
import com.tsccg.entity.Users;
import com.tsccg.util.JdbcUtil;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;
/**
* @Author: TSCCG
* @Date: 2021/08/14 21:07
*/
public class UserDao {
/**
* 向数据库中添加用户信息
* @param users 用户信息表对应实体类
* @return 返回
*/
public boolean add(Users users) {...}
/**
* 查询所有用户信息
* @return List<Users> 存放User对象的List集合
*/
public List<Users> findAll() {
Connection conn = null;
PreparedStatement ps = null;
ResultSet rs = null;
//创建一个Users对象,用于存储单条用户记录
Users users = null;
//创建一个List集合,用于存储Users对象
List<Users> userList = new ArrayList<>();
try {
conn = JdbcUtil.connect();
String sql = "select * from t_users";
ps = conn.prepareStatement(sql);
rs = ps.executeQuery();
//遍历查询结果集
while(rs.next()) {
//获取查询结果集中单条记录中的用户信息
Integer userId = rs.getInt("userId");
String userName = rs.getString("userName");
String passWord = rs.getString("passWord");
String sex = rs.getString("sex");
Integer age = rs.getInt("age");
String email = rs.getString("email");
//将单条用户记录放入User对象中
users = new Users(userId,userName,passWord,sex,age,email);
//将Users对象添加到List集合中
userList.add(users);
}
} catch (SQLException e) {
e.printStackTrace();
} finally {
//释放资源
JdbcUtil.closeAll(conn,ps,rs);
}
//将存储用户信息的List集合对象返回
return userList;
}
}
6.3编写Servlet接口实现类【UserFindServlet】
这个类的作用主要有两个:
- 调用【UserDao】类将查询命令发送到数据库服务器上,得到所有的用户信息【List】
- 调用【响应对象】将用户信息结合< table>标签命令以二进制形式写入响应体中。
package com.tsccg.controller;
import com.tsccg.com.tsccg.dao.UserDao;
import com.tsccg.entity.Users;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.PrintWriter;
import java.util.List;
/**
* @Author: TSCCG
* @Date: 2021/08/15 16:52
*/
public class UserFindServlet extends HttpServlet {
@Override
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
UserDao dao = new UserDao();
List<Users> usersList = null;
PrintWriter out = null;
//1. 调用【UserDao】类将查询命令发送到数据库服务器上,得到所有的用户信息【List】
usersList = dao.findAll();
//2. 调用【响应对象】将用户信息结合< table>标签命令以二进制形式写入响应体中。
//在获取输出流前,通过响应对象设置浏览器解析响应体内容的方式以及字符集
response.setContentType("text/html;charset=utf-8");
//通过响应对象向Tomcat服务器借用输出流
out = response.getWriter();
/*
<table border="1" align="center" cellspacing="0" cellpadding="0">
<!-- 标题行 -->
<tr>
<th>用户编号</th>
<th>用户姓名</th>
<th>用户密码</th>
<th>用户性别</th>
<th>用户年龄</th>
<th>用户邮箱</th>
</tr>
<!-- 数据行 -->
<tr>
<th>1</th>
<th>张三</th>
<th>111</th>
<th>男</th>
<th>20</th>
<th>zhangsan@qq.com</th>
</tr>
</table>
*/
//写入响应体
out.print("<table border='1' align='center' cellspacing='0' cellpadding='0'>");
//标题行
out.print("<tr>");
out.print("<th>用户编号</th>");
out.print("<th>用户姓名</th>");
out.print("<th>用户密码</th>");
out.print("<th>用户性别</th>");
out.print("<th>用户年龄</th>");
out.print("<th>用户邮箱</th>");
out.print("</tr>");
//数据行
for (Users users : usersList) {
out.print("<tr>");
out.print("<td>" + users.getUserId() + "</td>");
out.print("<td>" + users.getUserName() + "</td>");
out.print("<td>" + users.getPassWord() + "</td>");
out.print("<td>" + users.getSex() + "</td>");
out.print("<td>" + users.getAge() + "</td>");
out.print("<td>" + users.getEmail() + "</td>");
out.print("</tr>");
}
out.print("</table>");
}
}
6.4查询功能测试
7.用户信息删除
7.1添加删除列
在查询出的用户信息表中额外添加一列,用于删除用户信息。
在UserFindServlet类里,在发送回浏览器的用户信息表的【标题行】内添加一个【操作】列,在【数据行】内添加【删除用户】列。
【删除用户】是一个超链接,点击发送请求:"/MyWeb/user/delete?userId=" + users.getUserId()
携带的参数是该行用户的用户编号。
out.print("<table border='1' align='center' cellspacing='0' cellpadding='0'>");
//标题行
out.print("<tr>");
out.print("<th>用户编号</th>");
out.print("<th>用户姓名</th>");
out.print("<th>用户密码</th>");
out.print("<th>用户性别</th>");
out.print("<th>用户年龄</th>");
out.print("<th>用户邮箱</th>");
out.print("<th>操作</th>");//修改1
out.print("</tr>");
//数据行
for (Users users : usersList) {
out.print("<tr>");
out.print("<td>" + users.getUserId() + "</td>");
out.print("<td>" + users.getUserName() + "</td>");
out.print("<td>" + users.getPassWord() + "</td>");
out.print("<td>" + users.getSex() + "</td>");
out.print("<td>" + users.getAge() + "</td>");
out.print("<td>" + users.getEmail() + "</td>");
out.print("<td><a href='/MyWeb/user/delete?userId="
+ users.getUserId() + "'>删除用户</a></td>");//修改2
out.print("</tr>");
}
out.print("</table>");
7.2在【UserDao】类中添加删除功能
package com.tsccg.com.tsccg.dao;
import com.tsccg.entity.Users;
import com.tsccg.util.JdbcUtil;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;
/**
* @Author: TSCCG
* @Date: 2021/08/14 21:07
*/
public class UserDao {
/**
* 向数据库中添加用户信息
* @param users 用户信息表对应实体类
* @return 返回处理结果,添加成功返回true,失败返回false
*/
public boolean add(Users users) {...}
/**
* 查询所有用户信息
* @return List<Users> 存放User对象的List集合
*/
public List<Users> findAll() {...}
/**
* 删除用户信息
* @param userId 用户编号
* @return 返回处理结果,删除成功返回true,失败返回false
*/
public boolean delete(String userId) {
Connection conn = null;
PreparedStatement ps = null;
boolean result = false;
try {
conn = JdbcUtil.connect();
String sql = "delete from t_users where userId = ?";
ps = conn.prepareStatement(sql);
ps.setInt(1,Integer.parseInt(userId));
if(ps.executeUpdate() > 0) {
result = true;
}
} catch (SQLException e) {
e.printStackTrace();
} finally {
JdbcUtil.closeAll(conn,ps,null);
}
return result;
}
}
7.3编写Servlet接口实现类【UserDeleteServlet】
该类主要作用三个:
- 调用【请求对象】读取请求头中的请求参数信息,也就是【用户编号】
- 调用【UserDao】将【用户编号】插入delete命令,并借助JDBC规范发送到数据库服务器
- 调用【响应对象】将【处理结果】以二进制形式写入响应体中
package com.tsccg.controller;
import com.tsccg.com.tsccg.dao.UserDao;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.PrintWriter;
/**
* @Author: TSCCG
* @Date: 2021/08/15 20:38
*/
public class UserDeleteServlet extends HttpServlet {
@Override
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
//1. 调用【请求对象】读取请求头中的请求参数信息,也就是【用户编号】
String userId = request.getParameter("userId");
//2. 调用【UserDao】将【用户编号】插入delete命令,并借助JDBC规范发送到数据库服务器
UserDao dao = new UserDao();
boolean result = dao.delete(userId);
//3. 调用【响应对象】将【处理结果】以二进制形式写入响应体中
response.setContentType("text/html;charset=utf-8");
PrintWriter out = response.getWriter();
out.print(result ? "<font style='color: green;font-size: 30px'>删除用户成功</font>"
:"<font style='color: red;font-size: 30px'>删除用户失败</font>");
}
}
7.4删除功能测试
8.用户登录验证
8.1登录验证流程图
8.2编写登录页面
要求:
- 用户名
- 长度不得为空
- 长度不得大于10
- 密码
- 长度不得为空
- 长度不得小于3且不能大于20
- 所有信息都合法才能提交表单
在/web目录下新建login.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>登录</title>
<style type="text/css">
h1 {
font-size: 30px;
}
table {
font-size: 20px;
position: absolute;
top: 100px;
left: 600px;
}
span {
font-size: 14px;
color: red;
}
</style>
</head>
<body>
<h1 align="center">登录</h1>
<form action="/MyWeb/login" method="post" id="form">
<table>
<tr>
<td>用户名:</td>
<td><input type="text" name="userName" id="userName"/></td>
<td><span id="userNameError"></span></td>
</tr>
<tr>
<td>密 码:</td>
<td><input type="password" name="passWord" id="passWord"/></td>
<td><span id="passWordError"></span></td>
</tr>
<tr>
<td>
<input type="button" value="登录" id="subBtn"/>
</td>
<td>
<input type="reset" value="重置"/>
</td>
</tr>
</table>
</form>
<script type="text/javascript">
window.onload = function() {
/*
1.检查用户名文本框
用户名不为空;
用户名长度不得超过10;
*/
//获取用户名后面的span对象
const userNameErrorElt = document.getElementById("userNameError");
//获取用户名文本框对象
const userNameElt = document.getElementById("userName");
//当光标离开用户名文本框时检查value是否合法
userNameElt.onblur = function() {
//获取用户名文本框的value,并去除左右空白
const userName = userNameElt.value.trim();
if(userName.length === 0) {
userNameErrorElt.innerText = "用户名不能为空!";
} else if(userName.length > 10) {
userNameErrorElt.innerText = "用户名长度不得大于10!";
}
clear(userNameElt,userNameErrorElt);
}
/*
2.检查密码文本框
密码不为空;
密码长度不得超过20且不能小于3;
*/
//获取用户名后面的span对象
const passWordErrorElt = document.getElementById("passWordError");
//获取用户名文本框对象
const passWordElt = document.getElementById("passWord");
//当光标离开用户名文本框时检查value是否合法
passWordElt.onblur = function() {
//获取用户名文本框的value,并去除左右空白
const passWord = passWordElt.value.trim();
if(passWord.length === 0) {
passWordErrorElt.innerText = "密码不能为空!";
} else if(passWord.length < 3 || passWord.length > 20) {
passWordErrorElt.innerText = "密码长度为[3~20]!";
}
clear(passWordElt,passWordErrorElt);
}
/*
3.当光标回到文本框内时,清空提示信息、不合法内容
textElt:文本框对象
errorElt:文本框后面的提示信息span对象
*/
const clear = function(textElt,errorElt) {
textElt.onfocus = function() {
//如果文本框后面存在提示信息,则文本框内容不合法
if(errorElt.innerText) {
//清空不合法内容
textElt.value = "";
}
//清空提示信息
errorElt.innerText = "";
}
}
/*
4.当所有文本框里的内容都合法时,才能登录
*/
//获取登录按钮对象
const subBtnElt = document.getElementById("subBtn");
subBtnElt.onclick = function() {
//触发一次所有文本框的获得焦点、失去焦点事件
userNameElt.focus();
userNameElt.blur();
passWordElt.focus();
passWordElt.blur();
//判断所有文本框后面是否有提示信息
if (userNameErrorElt.innerText.length ===0
&& passWordErrorElt.innerText.length ===0) {
//获取表单对象
const formElt = document.getElementById("form");
//提交表单
formElt.submit();
}
}
}
</script>
</body>
</html>
8.3编写登录失败页面
登录失败页面就是在登录页面的基础上,在上方添加一句:”登录失败,请重新登录“
在/web目录下,新建loginError.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>登录</title>
<style type="text/css">
h1 {
font-size: 30px;
}
table {
font-size: 20px;
position: absolute;
top: 100px;
left: 600px;
}
span {
font-size: 14px;
color: red;
}
#loginError {
font-size: 30px;
color: red;
}
</style>
</head>
<body>
<div id="loginError" align="center">登录失败,请重新登录</div>
<h1 align="center">登录</h1>
<form action="/MyWeb/login" method="post" id="form">
<table>
<tr>
<td>用户名:</td>
<td><input type="text" name="userName" id="userName"/></td>
<td><span id="userNameError"></span></td>
</tr>
<tr>
<td>密 码:</td>
<td><input type="password" name="passWord" id="passWord"/></td>
<td><span id="passWordError"></span></td>
</tr>
<tr>
<td>
<input type="button" value="登录" id="subBtn"/>
</td>
<td>
<input type="reset" value="重置"/>
</td>
</tr>
</table>
</form>
<script type="text/javascript">
window.onload = function() {
/*
1.检查用户名文本框
用户名不为空;
用户名长度不得超过10;
*/
//获取用户名后面的span对象
const userNameErrorElt = document.getElementById("userNameError");
//获取用户名文本框对象
const userNameElt = document.getElementById("userName");
//当光标离开用户名文本框时检查value是否合法
userNameElt.onblur = function() {
//获取用户名文本框的value,并去除左右空白
const userName = userNameElt.value.trim();
if(userName.length === 0) {
userNameErrorElt.innerText = "用户名不能为空!";
} else if(userName.length > 10) {
userNameErrorElt.innerText = "用户名长度不得大于10!";
}
clear(userNameElt,userNameErrorElt);
}
/*
2.检查密码文本框
密码不为空;
密码长度不得超过20且不能小于3;
*/
//获取用户名后面的span对象
const passWordErrorElt = document.getElementById("passWordError");
//获取用户名文本框对象
const passWordElt = document.getElementById("passWord");
//当光标离开用户名文本框时检查value是否合法
passWordElt.onblur = function() {
//获取用户名文本框的value,并去除左右空白
const passWord = passWordElt.value.trim();
if(passWord.length === 0) {
passWordErrorElt.innerText = "密码不能为空!";
} else if(passWord.length < 3 || passWord.length > 20) {
passWordErrorElt.innerText = "密码长度为[3~20]!";
}
clear(passWordElt,passWordErrorElt);
}
/*
3.当光标回到文本框内时,清空提示信息、不合法内容
textElt:文本框对象
errorElt:文本框后面的提示信息span对象
*/
const clear = function(textElt,errorElt) {
textElt.onfocus = function() {
//如果文本框后面存在提示信息,则文本框内容不合法
if(errorElt.innerText) {
//清空不合法内容
textElt.value = "";
}
//清空提示信息
errorElt.innerText = "";
}
}
/*
4.当所有文本框里的内容都合法时,才能登录
*/
//获取登录按钮对象
const subBtnElt = document.getElementById("subBtn");
subBtnElt.onclick = function() {
//触发一次所有文本框的获得焦点、失去焦点事件
userNameElt.focus();
userNameElt.blur();
passWordElt.focus();
passWordElt.blur();
//判断所有文本框后面是否有提示信息
if (userNameErrorElt.innerText.length ===0
&& passWordErrorElt.innerText.length ===0) {
//获取表单对象
const formElt = document.getElementById("form");
//提交表单
formElt.submit();
}
}
}
</script>
</body>
</html>
8.4在【UserDao】类中添加登录验证功能
package com.tsccg.com.tsccg.dao;
import com.tsccg.entity.Users;
import com.tsccg.util.JdbcUtil;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;
/**
* @Author: TSCCG
* @Date: 2021/08/14 21:07
*/
public class UserDao {
/**
* 向数据库中添加用户信息
* @param users 用户信息表对应实体类
* @return 返回处理结果,添加成功返回true,失败返回false
*/
public boolean add(Users users) {...}
/**
* 查询所有用户信息
* @return List<Users> 存放User对象的List集合
*/
public List<Users> findAll() {...}
/**
* 删除用户信息
* @param userId 用户编号
* @return 返回处理结果,删除成功返回true,失败返回false
*/
public boolean delete(String userId) {...}
/**
* 验证用户信息
* @param userName 用户名
* @param passWord 用户密码
* @return 返回验证结果,成功返回true,失败返回false
*/
public boolean login(String userName,String passWord) {
Connection conn = null;
PreparedStatement ps = null;
ResultSet rs = null;
boolean result = false;
try {
conn = JdbcUtil.connect();
String sql = "select * from t_users where userName=? and passWord=?";
ps = conn.prepareStatement(sql);
ps.setString(1,userName);
ps.setString(2,passWord);
//执行sql语句,得到查询结果集
rs = ps.executeQuery();
//如果查询到数据,那么说明验证成功
if(rs.next()) {
result = true;
}
} catch (SQLException e) {
e.printStackTrace();
} finally {
JdbcUtil.closeAll(conn,ps,rs);
}
return result;
}
}
8.5编写Servlet接口实现类【LoginServlet】
1.告诉请求对象使用【utf-8】的方式对请求体中的内容进行重新编译
2.调用请求对象获取请求体中的【请求参数信息】
3.调用【UserDao】类将登录验证信息发送给数据库服务器
4.调用响应对象,根据验证结果,将不同【资源文件地址】写入响应头中的location属性,发送给浏览器
package com.tsccg.controller;
import com.tsccg.com.tsccg.dao.UserDao;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.PrintWriter;
/**
* @Author: TSCCG
* @Date: 2021/08/15 23:51
*/
public class LoginServlet extends HttpServlet {
@Override
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
//1.告诉请求对象使用【utf-8】的方式对请求体中的内容进行重新编译
request.setCharacterEncoding("utf-8");
//2.调用请求对象获取请求体中的【请求参数信息】
String userName = request.getParameter("userName");
String passWord = request.getParameter("passWord");
//3.调用【UserDao】类将登录验证信息发送给数据库服务器
UserDao dao = new UserDao();
boolean result = dao.login(userName,passWord);
//4.调用响应对象,根据验证结果,将不同【资源文件地址】写入响应头中的location属性,发送给浏览器
if(result) {
response.sendRedirect("/MyWeb/index.html");
} else {
response.sendRedirect("/MyWeb/loginError.html");
}
}
}
8.6验证登录验证功能
9.设置欢迎资源文件
当你想要打开百度时,可能会在浏览器地址栏里写上百度的默认网址【http://www.baidu.com】,但大概率不会加上百度网站下某个具体的资源文件名【https://www.baidu.com/index.html】。
用户会记住一个网站的名字,但通常不会记网站里的某个资源文件名。
正常请求:http://localhost:8080/MyWeb/index.html【请求访问index.html资源文件】
默认请求:http://localhost:8080/MyWeb【未说明想要访问的资源文件】
为了方便用户访问,当用户针对某一个网站发送了默认请求时,服务器会将网站中某一个【资源文件】发送过去。而这个默认的资源文件就叫做【欢迎资源文件】。
以Tomcat举例,
Tomcat对于默认欢迎资源文件定位规则:
- 规则设置位置:Tomcat安装位置/conf/web.xml
- 规则命令:
<welcome-file-list>
<welcome-file>index.html</welcome-file><!-- 首选资源文件 -->
<welcome-file>index.htm</welcome-file><!-- 次选资源文件 -->
<welcome-file>index.jsp</welcome-file><!-- 前面的文件都没有找到,才选择这个资源文件 -->
<!-- 如果上面的文件都没有找到,返回404状态码给浏览器 -->
</welcome-file-list>
我们在开发中,可以设定当前网站的默认欢迎文件规则:
- 设置位置:当前网站/web/WEB-INF/web.xml
- 规则命令:
<welcome-file-list>
<welcome-file>login.html</welcome-file>
<welcome-file>user/add</welcome-file><!-- 如果设置的是动态资源文件,前面不用加斜杠【/】 -->
</welcome-file-list>
开启服务器,默认打开当前项目的登录页面【login.html】: