建议从实验一开始从头进行阅读与代码粘贴,因为有些实验的代码是基于前面的实验进行改动。
同时,如果使用的是本文的代码,请将 Tomcat 配置进行如下修改:
搭建Web服务器,配置支持Java EE的开发环境。
Web服务器搭建包括两个部分:
JDK 下载地址:https://www.oracle.com/cn/java/
⚠️ 注意:不同版本的 IDEA,创建 Java Web 工程的方式可能会有所不同。
Tomcat 下载地址:https://tomcat.apache.org/
在 IDEA 中配置 Tomcat 之前,需要保证已经下载并解压了 Tomcat 到磁盘。
接下来,我们在 IDEA 中配置 Tomcat:
Settings --> Build, Execution, Deployment --> Application Servers
配置 Tomcat Server 的位置(根据自己 Tomcat 在磁盘上的安装位置决定):
我们先创建一个普通项目(或模块),命名为 javaweb02:
为当前项目(或模块)添加模块支持:
Project Structure --> Project Settings --> Facets
添加 Servlet 相关库:
此时我们再来看项目(或模块结构):
为了稍后方便测试,我们在 web 文件夹下新增一个 index.jsp
文件:
<%--
Created by IntelliJ IDEA.
User: 狐狸半面添
Date: 2023/10/6
Time: 17:08
To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
狐狸半面添的客栈
欢迎来到狐狸半面添的客栈,持续的实战开发技术分享与编程指南。
浏览器访问:http://localhost:8080/
如果 Tomcat 日志出现乱码:
解决方案:
点击 Help --> Edit custom VM Options
在文件最后面添加:-Dfile.encoding=UTF-8
在当前 Tomcat 实例中配置 VM option,添加:-Dfile.encoding=UTF-8
在当前 Tomcat 实例配置界面的 Startup/Connection 页签的 Run 和 Debug 添加一个 key 为 JAVA_TOOL_OPTIONS
,value 为 -Dfile.encoding=UTF-8
的环境变量。
重启 IDEA;
启动服务。
我们需要安装适合自己操作系统的 JDK,并配置了JAVA_HOME环境变量。这是 Java Web 开发的基础,因为它提供了 Java 编译器和其他必要的工具。
选择合适的 Java Web 服务器,根据自身的需求和项目要求,选择适合的 Java Web 服务器。常见的选择包括 Apache Tomcat、Jetty 和 WildFly 等。了解不同服务器的特点和功能,选择最适合我们项目的服务器。
编写 denglu.html 页面,其中包括表单,用于用户输入注册信息。
DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>登录界面title>
head>
<body>
<form action="/treat.jsp">
<table>
<tr>
<td>姓名td>
<td><input name="username" type="text">td>
tr>
<tr>
<td>密码td>
<td><input name="password" type="password">td>
tr>
<tr>
<td>性别td>
<td>
<label>
<input type="radio" name="gender" value="male"> 男
label>
<label>
<input type="radio" name="gender" value="female"> 女
label>
td>
tr>
<tr>
<td>爱好td>
<td>
<label>
<input type="checkbox" name="hobby" value="sing"> 唱
label>
<label>
<input type="checkbox" name="hobby" value="dance"> 跳
label>
<label>
<input type="checkbox" name="hobby" value="rap"> rap
label>
<label>
<input type="checkbox" name="hobby" value="basketball"> 篮球
label>
td>
tr>
<tr>
<td style="vertical-align: top">自我介绍td>
<td><textarea name="introduce" cols="30" rows="10">textarea>td>
tr>
table>
<input type="submit" value="登录">
<input type="reset" value="重置">
form>
<script>
document.querySelector("[type='submit']").addEventListener("click", evt => {
const username = document.querySelector("[name='username']").value
const password = document.querySelector("[name='password']").value
if (username.trim() === '' || password.trim() === '') {
alert("用户名或密码为空")
evt.preventDefault()
}
})
script>
body>
html>
编写treat.jsp页面,接收表单中的各种信息并显示。
<%@ page import="java.util.Arrays" %>
<%@ page import="java.util.stream.Collectors" %>
<%@ page import="java.util.function.Consumer" %>
<%@ page import="java.util.function.Function" %><%--
Created by IntelliJ IDEA.
User: 狐狸半面添
Date: 2023/10/15
Time: 0:28
To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
处理页面
<%
request.setCharacterEncoding("UTF-8");
String username = request.getParameter("username");
String password = request.getParameter("password");
if (username == null
|| username.trim().isEmpty()
|| password == null
|| password.trim().isEmpty()
) {
// 重定向
response.sendRedirect("/denglu.html");
return;
}
Function genderFun = gender -> {
if ("male".equals(gender)) {
return "男";
} else if ("female".equals(gender)) {
return "女";
} else {
return "未知";
}
};
String gender = genderFun.apply(request.getParameter("gender"));
String hobby = Arrays.asList(request.getParameterValues("hobby")).stream()
.map(item -> {
String name;
switch (item) {
case "sing":
name = "唱";
break;
case "dance":
name = "跳";
break;
case "rap":
name = "rap";
break;
case "basketball":
name = "篮球";
break;
default:
name = "nothing";
}
return name;
}).collect(Collectors.joining(", "));
String introduce = request.getParameter("introduce");
%>
性别:<%=username%>
密码:<%=password%>
性别:<%=gender%>
爱好:<%=hobby%>
自我介绍:<%=introduce%>
目前主流的技术是前后端分离(比如:SpringBoot + Vue/React),而 JSP 技术使用正在逐渐减少,但使用少和没有使用是两个意思,一些老项目和中小公司还在使用 JSP,工作期间,还是可能遇见 JSP。但我们不必深入学习 JSP,只需要能基本使用,能看得懂,能维护相关项目即可。
JavaScript方式的优点:
JavaScript方式的缺点:
JSP方式的优点:
JSP方式的缺点:
基本要求:
扩展要求:
基于 Forward 动作标签,将注册处理页面 treatZhuCe.jsp 拆成三个页面:注册处理页面 treatZhuCe.jsp、注册处理结果页面 zhuCeSuccess.jsp 以及zhuCeFail.jsp。其中注册处理页面 treatZhuCe.jsp 负责接收注册页面 zhuce.jsp 传递过来的用户注册信息,并处理信息,根据注册是否成功分别交给注册处理结果页面 zhuCeSuccess.jsp 以及 zhuCeFail.jsp 显示。具体如下图所示:
基于 Forward 动作标签,将登录处理页面 treatDengLu.jsp 拆成三个页面:登录处理页面 treatDengLu.jsp、登录处理结果页面 dengLuSuccess.jsp 以及 dengLuFail.jsp。其中登录处理页面 treatDengLu.jsp 负责接收登录页面 denglu.jsp 传递过来的用户登录信息,并处理信息,根据登录是否成功分别交给登录处理结果页面 dengLuSuccess.jsp 以及 dengLuFail.jsp 显示。具体如下图所示:
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
主页
注册
登录
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
注册
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
处理注册
<%
request.setCharacterEncoding("UTF-8");
String username = request.getParameter("username");
String password = request.getParameter("password");
String confirmPassword = request.getParameter("confirmPassword");
if (username == null || username.trim().isEmpty() || password == null || password.trim().isEmpty() || confirmPassword == null || confirmPassword.trim().isEmpty()) {
%>
<%
}
if (!password.equals(confirmPassword)) {
%>
<%
}
String info = "您好!" + username + "注册成功!";
%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
注册失败
<%
request.setCharacterEncoding("UTF-8");
String info = request.getParameter("info");
%>
信息:<%=info%>
回到首页
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
注册成功
<%
request.setCharacterEncoding("UTF-8");
String info = request.getParameter("info");
%>
<%=info%>
回到首页
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
登录
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
处理登录
<%
request.setCharacterEncoding("UTF-8");
String username = request.getParameter("username");
String password = request.getParameter("password");
if (username == null || username.trim().isEmpty() || password == null || password.trim().isEmpty()) {
%>
<%
}
if ("姓名".equals(username) && "学号".equals(password)) {
String info = "你好,登陆成功";
%>
<%
} else {
%>
<%
}
%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
登录失败
<%
request.setCharacterEncoding("UTF-8");
String info = request.getParameter("info");
%>
信息: <%=info%>
回到首页
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
登录成功
<%
request.setCharacterEncoding("UTF-8");
String info = request.getParameter("info");
%>
<%=info%>
回到首页
通过对登录注册的处理,我们其实不难看出 JSP 可以对数据进行校验与处理。
JSP 页面本质上是 Servlet 程序,其性能和 Java 相关。第一次访问 JSP 页面的时候,Tomcat 服务器会把 JSP 页面解析成 Java 源文件,并对它编译称为 class 字节码程序。
基本要求:
扩展要求:
基于Forward动作标签,将注册处理页面treatZhuCe.jsp拆成三个页面:注册处理页面treatZhuCe.jsp、注册处理结果页面zhuCeSuccess.jsp以及zhuCeFail.jsp。其中注册处理页面treatZhuCe.jsp负责接收注册页面zhuce.jsp传递过来的用户注册信息,并处理信息,根据注册是否成功分别交给注册处理结果页面zhuCeSuccess.jsp以及zhuCeFail.jsp显示。具体如下图所示:
基于Forward动作标签,将登录处理页面treatDengLu.jsp拆成三个页面:登录处理页面treatDengLu.jsp、登录处理结果页面dengLuSuccess.jsp以及dengLuFail.jsp。其中登录处理页面treatDengLu.jsp负责接收登录页面denglu.jsp传递过来的用户登录信息,并处理信息,根据登录是否成功分别交给登录处理结果页面dengLuSuccess.jsp以及dengLuFail.jsp显示。具体如下图所示:
相较于实验三,我们只需要做以下调整:
<%--
Created by IntelliJ IDEA.
bean.User: 狐狸半面添
Date: 2023/10/15
Time: 1:32
To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
处理注册
<%
request.setCharacterEncoding("UTF-8");
String username = request.getParameter("username");
String password = request.getParameter("password");
String confirmPassword = request.getParameter("confirmPassword");
if (username == null || username.trim().isEmpty() || password == null || password.trim().isEmpty() || confirmPassword == null || confirmPassword.trim().isEmpty()) {
%>
<%
}
if (!password.equals(confirmPassword)) {
%>
<%
}
// 判断是否已经被注册过了
if (application.getAttribute(username) != null) {
String info = "用户名 `" + username + "` 已被注册,请尝试其它用户名";
%>
<%
}
// 将信息存入 application
application.setAttribute(username, password);
String info = "您好!" + username + "注册成功!";
%>
<%--
Created by IntelliJ IDEA.
bean.User: 狐狸半面添
Date: 2023/10/15
Time: 2:01
To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
处理登录
<%
request.setCharacterEncoding("UTF-8");
String username = request.getParameter("username");
String password = request.getParameter("password");
if (username == null || username.trim().isEmpty() || password == null || password.trim().isEmpty()) {
%>
<%
}
String storePassword = (String) application.getAttribute(username);
if (storePassword == null || !storePassword.equals(password)) {
%>
<%
}
// 登录成功
session.setAttribute("isLogin", true);
String info = "你好,+" + username + " 登陆成功";
%>
JSP 内置对象是 Tomcat 在翻译 JSP 页面成为 Servlet 后,内部提供的九大对象。它们可以直接使用,不需要我们再手动定义。
像 application
就对应了 ServletContext
,session
是会话对象。
application
也是域对象,存放的数据在整个 Web 应用运行期间有效。它可以像 Map 一样存取数据。
基于Forward动作标签,将注册处理页面treatZhuCe.jsp拆成三个页面:注册处理页面treatZhuCe.jsp、注册处理结果页面zhuCeSuccess.jsp以及zhuCeFail.jsp。其中注册处理页面treatZhuCe.jsp负责接收注册页面zhuce.jsp传递过来的用户注册信息,并处理信息,根据注册是否成功分别交给注册处理结果页面zhuCeSuccess.jsp以及zhuCeFail.jsp显示。具体如下图所示:
2.基于Forward动作标签,将登录处理页面treatDengLu.jsp拆成三个页面:登录处理页面treatDengLu.jsp、登录处理结果页面dengLuSuccess.jsp以及dengLuFail.jsp。其中登录处理页面treatDengLu.jsp负责接收并处理登录页面denglu.jsp传递过来的用户登录信息,根据登录是否成功分别交给登录处理结果页面dengLuSuccess.jsp以及dengLuFail.jsp显示。具体如下图所示:
在 src/bean 下:
public class UserBean {
private String name;
private String password;
public UserBean(String name, String password) {
this.name = name;
this.password = password;
}
public UserBean() {
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getPassword() {
return password;
}
public void setPassword(String password) {
this.password = password;
}
}
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%@ page import="bean.UserBean" %>
处理注册
<%
request.setCharacterEncoding("UTF-8");
String username = request.getParameter("username");
String password = request.getParameter("password");
String confirmPassword = request.getParameter("confirmPassword");
if (username == null || username.trim().isEmpty() || password == null || password.trim().isEmpty() || confirmPassword == null || confirmPassword.trim().isEmpty()) {
%>
<%
}
if (!password.equals(confirmPassword)) {
%>
<%
}
// 将信息存入 application
application.setAttribute("user", new UserBean(username, password));
String info = "您好!" + username + "注册成功!";
%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%@ page import="bean.UserBean" %>
处理登录
<%
request.setCharacterEncoding("UTF-8");
String username = request.getParameter("username");
String password = request.getParameter("password");
if (username == null || username.trim().isEmpty() || password == null || password.trim().isEmpty()) {
%>
<%
}
UserBean storeUser = (UserBean) application.getAttribute("user");
if (storeUser == null || !storeUser.getName().equals(username) || !storeUser.getPassword().equals(password)) {
%>
<%
}
// 登录成功
session.setAttribute("user", new UserBean(username, password));
String info = "你好," + username + " 登陆成功";
%>
JavaBean 是一种符合特定规范的 Java 类,用于封装数据和提供操作这些数据的方法。它通常被用于在 Web 应用程序中处理业务逻辑和数据交互。
在 JSP 环境下使用和引入 JavaBean 的通常步骤:
<%@ page import="包名.类名" %>
指令来导入 JavaBean 类。将包名和类名替换为你的 JavaBean 类所在的包名和类名;<% %>
中使用这个类。编写一个UserBean类,要求该类具有两个属性name和password,并给出两个属性对应的getter和setter方法。
编写主页面index.jsp,该页面提供两个超链接,分别链接到注册页面和登录页面;
编写一个注册页面zhuce.jsp,包括:用户名,密码,密码确认以及确认和重设按钮;
编写一个登录页面denglu.jsp,包括:用户名,密码以及确认和重设按钮;
注册处理Servlet:treatZhuCe.java。该Servlet判断用户名和密码是否为空、密码和密码确认是否相同。如果用户名和密码不为空且密码和密码确认相同,则认为注册成功,并将用户的姓名和密码生成UserBean类型对象存入application中。否则认为注册失败。处理结果交给zhuCeResult.jsp显示。
登录处理Servlet:treatDengLu.java。该Servlet判断判断用户名和密码是否为空,若不为空,则判断用户名和密码是否为application对象中的键值对。如果用户名和密码是application对象中的键值对,则认为登录成功,生成UserBean对象user,在session对象以“user”的名字存入。其它情况均认为登录失败。处理结果交给dengLuResult.jsp显示。
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
主页
注册
登录
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
注册
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
注册结果
<%
request.setCharacterEncoding("UTF-8");
String info = (String) request.getAttribute("info");
%>
信息:<%=info%>
回到首页
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
登录
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
登录结果
<%
request.setCharacterEncoding("UTF-8");
String info = (String) request.getAttribute("info");
%>
信息:<%=info%>
回到首页
在 src/bean 下新建 UserBean.java
public class UserBean {
private String name;
private String password;
public UserBean(String name, String password) {
this.name = name;
this.password = password;
}
public UserBean() {
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getPassword() {
return password;
}
public void setPassword(String password) {
this.password = password;
}
}
在 src/servlet 下新建 treatZhuCe.java
@WebServlet(urlPatterns = {"/treatZhuCe"})
public class treatZhuCe extends HttpServlet {
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
// 设置字符集避免乱码
req.setCharacterEncoding("UTF-8");
// 获取参数
String username = req.getParameter("username");
String password = req.getParameter("password");
String confirmPassword = req.getParameter("confirmPassword");
String info;
if (username == null || username.isEmpty() || password == null || password.isEmpty() || confirmPassword == null || confirmPassword.isEmpty()) {
info = "用户名或密码为空";
} else if (!password.trim().equals(confirmPassword)) {
info = "两次密码不一致";
} else {
// 将信息存入 application
this.getServletContext().setAttribute("user", new UserBean(username, password));
info = "您好!" + username + "注册成功!";
}
req.setAttribute("info", info);
req.getRequestDispatcher("/zhuCeResult.jsp").forward(req, resp);
}
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
doGet(req, resp);
}
}
在 src/servlet 下新建 treatDengLu.java
@WebServlet(urlPatterns = {"/treatDengLu"})
public class treatDengLu extends HttpServlet {
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
// 设置字符集避免乱码
req.setCharacterEncoding("UTF-8");
// 获取参数
String username = req.getParameter("username");
String password = req.getParameter("password");
String info;
if (username == null || username.isEmpty() || password == null || password.isEmpty()) {
info = "用户名或密码为空";
} else {
ServletContext application = this.getServletContext();
UserBean user = (UserBean) application.getAttribute("user");
if (user.getName().equals(username) && user.getPassword().equals(password)) {
req.getSession().setAttribute("user", new UserBean(username, password));
info = "你好," + username + " 登陆成功";
} else {
info = "用户名或密码错误";
}
}
req.setAttribute("info", info);
req.getRequestDispatcher("/dengLuResult.jsp").forward(req, resp);
}
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
doGet(req, resp);
}
}
在 MVC(Model-View-Controller)框架中,Servlet 扮演着 Controller(控制器)的角色。它负责接收用户的请求并根据请求的类型和参数来决定如何处理请求。Servlet 从用户界面(View)接收输入,并将其传递给模型(Model)进行处理。
编写一个UserBean类,要求该类具有两个属性name和password,并给出两个属性对应的getter和setter方法。
在MySQL数据库中新建wgw数据库,并建立名为tb_user的用户信息表,tb_user表包括name和password两个属性,此两个属性均为varchar(50)类型,均不为空,name为主键。
编写主页面index.jsp,该页面提供两个超链接,分别链接到注册页面和登录页面;
编写一个注册页面zhuce.jsp,包括:用户名,密码,密码确认以及确认和重设按钮;
编写一个登录页面denglu.jsp,包括:用户名,密码以及确认和重设按钮;
注册处理Servlet:treatZhuCe.java。该Servlet判断用户名和密码是否为空、密码和密码确认是否相同。如果用户名和密码不为空且密码和密码确认相同,则认为注册成功,并将用户的姓名和密码存入到数据库wgw的tb_user表中。否则认为注册失败。处理结果交给zhuCeResult.jsp显示。
登录处理Servlet:treatDengLu.java。该Servlet判断判断用户名和密码是否为空,若不为空,在数据库wgw的tb_user表中查询用户名和密码是否匹配。如果匹配则认为登录成功,生成UserBean对象user,在session对象以“user”的名字存入。其它情况均认为登录失败。处理结果交给dengLuResult.jsp显示。
最终项目结构:
基于实验六进行改动即可,所有的 jsp 文件与 Javabean 无需改动。
数据库安装参考:https://blog.csdn.net/qq_62982856/article/details/127768220
CREATE DATABASE wgw;
USE wgw;
CREATE TABLE tb_user (
`name` VARCHAR(50) NOT NULL PRIMARY KEY COMMENT '用户名',
`password` VARCHAR(50) NOT NULL DEFAULT '' COMMENT '密码'
);
这里我们需要下载两个 jar 包,由于我在这里是直接访问外网,因此如果你的网速不行请切换为流量。
下载地址:https://repo1.maven.org/maven2/com/alibaba/druid/1.1.10/
这里需要特别注意,需要下载的数据库驱动 jar 包根据你的 mysql 版本会有所不同。
查看自己的mysql版本:
mysqld --version
1️⃣ 如果你是mysql5.7的版本
下载地址:https://repo1.maven.org/maven2/mysql/mysql-connector-java/5.1.37/
2️⃣ 如果你是mysql8.0的版本
下载地址:https://repo1.maven.org/maven2/mysql/mysql-connector-java/8.0.16/
在 web/WEB-INF 下创建一个 lib
文件夹,将 commons-dbutils、druid、mysql-connector-java 拷贝到 lib 文件夹下。
由于我装的是 mysql8.0 的版本,因此我使用的 mysql jar 包是 mysql-connector-java-8.0.16.jar。
在 src 下创建 druid.properties
# key=value
# 如果 mysql 版本是 5.7,需要将 driverClassName 的值修改为 com.mysql.jdbc.Driver
# 如果 mysql 版本是 8.0,需要将 driverClassName 的值修改为 com.mysql.cj.jdbc.Driver
driverClassName=com.mysql.cj.jdbc.Driver
url=jdbc:mysql://localhost:3306/wgw?characterEncoding=utf-8&useSSL=false&serverTimezone=GMT%2B8
username=root
password=123456
# initial connection Size
initialSize=10
# min idle connecton size
minIdle=5
# max active connection size
maxActive=50
# max wait time (5000 mil seconds)
maxWait=5000
在 src/utils 下创建 JDBCUtilsByDruid.java
public class JDBCUtilsByDruid {
private static DataSource dataSource;
static {
try {
Properties properties = new Properties();
// 因为我们是web项目,他的工作目录在out, 文件的加载,需要使用类加载器
// 找到我们的工作目录
properties.load(JDBCUtilsByDruid.class.getClassLoader().getResourceAsStream("druid.properties"));
dataSource = DruidDataSourceFactory.createDataSource(properties);
} catch (Exception e) {
e.printStackTrace();
}
}
// 获取连接
public static Connection getConnection() {
try {
return dataSource.getConnection();
} catch (SQLException e) {
throw new RuntimeException(e);
}
}
// 关闭连接
public static void close(ResultSet resultSet, PreparedStatement preparedStatement, Connection connection) {
try {
if (resultSet != null) {
resultSet.close();
}
if (preparedStatement != null) {
preparedStatement.close();
}
if (connection != null) {
connection.close();
}
} catch (SQLException e) {
throw new RuntimeException(e);
}
}
}
在 src/dao 下创建 UserDAO.java
public class UserDAO {
// 查询某个用户是否存在
public boolean existUsername(String username) {
PreparedStatement preparedStatement = null;
ResultSet resultSet = null;
Connection conn = null;
try {
// 获取连接
conn = JDBCUtilsByDruid.getConnection();
// 预处理方式
preparedStatement = conn.prepareStatement("SELECT 1 FROM tb_user WHERE `name` = ?");
// 设置第一个问号的参数值
preparedStatement.setString(1, username);
// 执行查询
resultSet = preparedStatement.executeQuery();
// 如果查询到一条记录,则说明用户存在
return resultSet.next();
} catch (SQLException e) {
e.printStackTrace();
} finally {
// 关闭连接
JDBCUtilsByDruid.close(resultSet, preparedStatement, conn);
}
return false;
}
// 将注册用户保存到 tb_user
public void insert(String username, String password) {
PreparedStatement preparedStatement = null;
ResultSet resultSet = null;
Connection conn = null;
try {
// 获取连接
conn = JDBCUtilsByDruid.getConnection();
// 预处理方式
preparedStatement = conn.prepareStatement("INSERT INTO tb_user(`name`, `password`) VALUES(?, ?)");
// 设置第一个问号的参数值
preparedStatement.setString(1, username);
// 设置第二个问号的参数值
preparedStatement.setString(2, password);
// 执行查询
int updateNums = preparedStatement.executeUpdate();
// 如果执行成功,updateNums >= 1
if (updateNums == 0) {
throw new RuntimeException("服务器与数据库发生未知错误");
}
} catch (SQLException e) {
e.printStackTrace();
} finally {
// 关闭连接
JDBCUtilsByDruid.close(resultSet, preparedStatement, conn);
}
}
// 验证用户登录
public boolean existUsernameAndPassword(String username, String password) {
PreparedStatement preparedStatement = null;
ResultSet resultSet = null;
Connection conn = null;
try {
// 获取连接
conn = JDBCUtilsByDruid.getConnection();
// 预处理方式
preparedStatement = conn.prepareStatement("SELECT 1 FROM tb_user WHERE `name` = ? AND `password` = ?");
// 设置第一个问号的参数值
preparedStatement.setString(1, username);
// 设置第二个问号的参数值
preparedStatement.setString(2, password);
// 执行查询
resultSet = preparedStatement.executeQuery();
// 如果查询到一条记录,则说明用户存在
return resultSet.next();
} catch (SQLException e) {
e.printStackTrace();
} finally {
// 关闭连接
JDBCUtilsByDruid.close(resultSet, preparedStatement, conn);
}
return false;
}
}
在 src/servlet 下创建 treatZhuCe.java
@WebServlet(urlPatterns = {"/treatZhuCe"})
public class treatZhuCe extends HttpServlet {
private UserDAO userDAO = new UserDAO();
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
// 设置字符集避免乱码
req.setCharacterEncoding("UTF-8");
// 获取参数
String username = req.getParameter("username");
String password = req.getParameter("password");
String confirmPassword = req.getParameter("confirmPassword");
String info;
if (username == null || username.isEmpty() || password == null || password.isEmpty() || confirmPassword == null || confirmPassword.isEmpty()) {
info = "用户名或密码为空";
} else if (!password.trim().equals(confirmPassword)) {
info = "两次密码不一致";
} else if (userDAO.existUsername(username)) {
// 判断是否在数据库中已存在
info = "用户已存在,注册失败";
} else {
// 注册
userDAO.insert(username, password);
info = "您好!" + username + "注册成功!";
}
req.setAttribute("info", info);
req.getRequestDispatcher("/zhuCeResult.jsp").forward(req, resp);
}
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
doGet(req, resp);
}
}
在 src/servlet 下创建 treatDengLu.java
@WebServlet(urlPatterns = {"/treatDengLu"})
public class treatDengLu extends HttpServlet {
private final UserDAO userDAO = new UserDAO();
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
// 设置字符集避免乱码
req.setCharacterEncoding("UTF-8");
// 获取参数
String username = req.getParameter("username");
String password = req.getParameter("password");
String info;
if (username == null || username.isEmpty() || password == null || password.isEmpty()) {
info = "用户名或密码为空";
} else if (userDAO.existUsernameAndPassword(username, password)) {
req.getSession().setAttribute("user", new UserBean(username, password));
info = "你好," + username + " 登陆成功";
} else {
info = "用户名或密码错误";
}
req.setAttribute("info", info);
req.getRequestDispatcher("/dengLuResult.jsp").forward(req, resp);
}
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
doGet(req, resp);
}
}
如果重复注册相同用户名:
传统的JDBC数据库连接使用 DriverManager 连接的时候都要将 Connection 加载到内存中再验证IP地址,用户名和密码。需要数据库连接的时候就向数据库要求一个,频繁的进行数据库连接操作将占用很多的系统资源,容易造成服务器崩溃。每一次数据库连接,使用完后都得断开,如果程序出现异常而未能关闭,将导致数据库内存泄漏,最终将导致重启数据库。使用数据库连接池技术可以得到一定的安全性保证与性能提升。