1、简介
1.1、背景
开发中,同一套Java代码是无法操作不同的关系型数据库,因为每一个关系型数据库的底层实现细节都不一样。如果这样,假如在业务开发阶段使用的是MySQL数据库,而上线时公司最终选用oracle数据库,则需要对代码进行大批量修改,这显然行不通。
因此Java开发人员更希望做到的是同一套Java代码操作不同的关系型数据库。sun公司就指定了一套标准接口(JDBC),JDBC中定义了所有操作关系型数据库的规则。
接口是无法直接使用的,我们需要使用接口的实现类,而这套实现类(称之为:驱动)就由各自的数据库厂商给出。
简单来说:在开发中我们使用的是java语言,那么势必要通过java语言操作数据库中的数据,势必要用Java操作不同的数据库管理系统,所以需要JDBC!
1.2、概念
JDBC(Java Database Connectivity)是Java程序用于访问关系数据库的API。通过标准的接口和类来管理数据库连接和执行SQL语句,可以用于连接不同类型的数据库管理系统(DBMS),如MySQL、Oracle、SQL Server等。这使得Java程序员可以快速、方便地与各种关系数据库进行交互。
2、JDBC的优点
各数据库厂商使用相同的接口,Java代码不需要针对不同数据库分别开发,可随时替换底层数据库,访问数据库的Java代码基本不变 。
以后编写操作数据库的代码只需要面向JDBC(接口),操作哪个关系型数据库就需要导入该数据库的驱动包,如需要操作MySQL数据库,就需要在项目中导入MySQL数据库的驱动包。
3、JDBC操作步骤
3.1、代码步骤
①创建工程,导入驱动jar包
②注册驱动->Class.forName("com.mysql.jdbc.Driver");
③获取连接->Connection connection = DriverManager.getConnection(url, username, password);
Java代码需要发送SQL给MySQL服务端,就需要先建立连接
(如果是连接本地root数据库,要记得开启本地的MySQL服务)
(在后面的技术中,主要使用的是连接池的方式获取Connection连接)
④定义SQL语句->String sql = "update…" ;
⑤获取执行SQL对象(执行SQL语句需要SQL执行对象,而这个执行对象就是Statement对象) ->
->Statement statement = connection.createStatement();
⑥执行SQL->statement.executeUpdate(sql);
ResultSet resultSet = statement.executeQuery(sql);
⑦处理返回结果 while (resultSet.next()) {...}
⑧释放资源connection.close();
3.2、操作演示
1、导包
把mysql的jar包放到lib目录下
添加到项目依赖中,MySQL驱动包才能正常使用。
有拓展的符号那就证明添加成功了。
3.2、MVC三层架构
MVC(Model View Controller)是软件工程中的一种软件架构模式,它把软件系统分为模型、视图和控制器三个基本部分。用一种业务逻辑、数据、界面显示分离的方法组织代码,将业务逻辑聚集到一个部件里面,在改进和个性化定制界面及用户交互的同时,不需要重新编写业务逻辑。
M:Model,模型。 JavaBean
- 完成具体的业务操作,如:查询数据库,封装对象
V:view视图。JSP、HTML等来进行数据展示
C:Controller控制器。
Servlet
-
获取View的请求
-
调用模型将数据交给视图进行展示
接下来的项目将会围绕着三层架构去写相应的功能。
4、项目实例
4.1、Dao层
新建数据库(MySQL)
创建表
封装数据库连接操作
package com.org.utils;
import java.sql.*;
import java.util.Properties;
/***
* 封装数据库连接操作
*/
public class DBUtils {
private static String driver;
private static String user;
private static String password;
private static String url;
static {
//获取配置信息
Properties p = ReadFileDemo2.readFile2("file/db.properties");
driver = (String)p.get("driver");
user = (String)p.get("user");
password = (String)p.get("password");
url = (String)p.get("url");
try {
Class.forName(driver);
} catch (ClassNotFoundException e) {
e.printStackTrace();
}
}
public static Connection getConnection(){
try {
//加载驱动
Connection connection = DriverManager.getConnection(url, user, password);
return connection;
} catch (Exception e) {
e.printStackTrace();
}
return null;
}
//关闭数据库连接
public static void closeDB(Connection connection, PreparedStatement ps, ResultSet rs){
if (rs != null){
try {
rs.close();
} catch (SQLException e) {
e.printStackTrace();
}
}
if (ps != null){
try {
ps.close();
} catch (SQLException e) {
e.printStackTrace();
}
}
if (connection != null){
try {
connection.close();
} catch (SQLException e) {
e.printStackTrace();
}
}
}
}
User类
package com.org.domain;
import java.util.Date;
/**
* 封装User
*/
public class User {
private String username;
private String password;
private String gender;
private String hobby;
private String address;
private String remark;
public User() {
}
public User(String username, String password, String gender, String hobby, String address, String remark) {
this.username = username;
this.password = password;
this.gender = gender;
this.hobby = hobby;
this.address = address;
this.remark = remark;
}
//获取getter和setter方法
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 getGender() {
return gender;
}
public void setGender(String gender) {
this.gender = gender;
}
public String getHobby() {
return hobby;
}
public void setHobby(String hobby) {
this.hobby = hobby;
}
public String getAddress() {
return address;
}
public void setAddress(String address) {
this.address = address;
}
public String getRemark() {
return remark;
}
public void setRemark(String remark) {
this.remark = remark;
}
//获取toString方法
@Override
public String toString() {
return "User{" +
"username='" + username + '\'' +
", password='" + password + '\'' +
", gender='" + gender + '\'' +
", hobby='" + hobby + '\'' +
", address='" + address + '\'' +
", remark='" + remark + '\'' +
'}';
}
}
UserDao类:User对数据库的连接等操作
package com.org.dao;
import com.org.domain.User;
import com.org.utils.DBUtils;
import sun.security.x509.DNSName;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;
public class UserDao {
//根据用户名和密码查询用户
public boolean findUserByUserNameAndPassword(String username,String password){
//连接数据库
Connection connection = DBUtils.getConnection();
String sql = "select id from user where username = ? AND password = ?";
PreparedStatement ps = null;
ResultSet rs = null;
boolean flag = false;
try {
ps = connection.prepareStatement(sql);
ps.setString(1,username);
ps.setString(2,password);
rs = ps.executeQuery();
while(rs.next()){
if (rs.getInt(1)>0){
flag = true;
}
}
} catch (SQLException e) {
e.printStackTrace();
}
DBUtils.closeDB(connection,ps,rs);
return flag;
}
//根据用户名查询用户
public boolean findUserByName(String username){
//连接数据库
Connection connection = DBUtils.getConnection();
String sql = "select id fromm user where username = ?";
PreparedStatement ps = null;
ResultSet rs = null;
boolean flag = false;
try {
ps = connection.prepareStatement(sql);
ps.setString(1,username);
rs = ps.executeQuery();
while(rs.next()){
if (rs.getInt(1)>0){
flag = true;
}
}
} catch (SQLException e) {
e.printStackTrace();
}
DBUtils.closeDB(connection,ps,rs);
return false;
}
//添加用户
public int addUser(User user){
//连接数据库
Connection connection = DBUtils.getConnection();
String sql = "INSERT INTO USER(username,password,gender,hobby,address,remark) VALUE (?,?,?,?,?,?)";
PreparedStatement ps = null;
try {
ps = connection.prepareStatement(sql);
ps.setString(1,user.getUsername());
ps.setString(2,user.getPassword());
ps.setString(3,user.getGender());
ps.setString(4,user.getHobby());
ps.setString(5,user.getAddress());
ps.setString(6,user.getRemark());
int i = ps.executeUpdate();
return i;
} catch (SQLException e) {
e.printStackTrace();
}
DBUtils.closeDB(connection,ps,null);
return 0;
}
}
4.2、Service层
Userservice:处理User业务
package com.org.service;
import com.org.dao.UserDao;
import com.org.domain.User;
import java.util.ArrayList;
import java.util.List;
/**
* 处理User业务
*/
public class UserService {
/**
* 注册用户
* (0代表注册失败,1代表注册成功,2代表用户存在)
*/
//登录
public boolean login(String username,String password){
UserDao userDao = new UserDao();
boolean flag = userDao.findUserByUserNameAndPassword(username, password);
return flag;
}
//注册
public int register(User user){
UserDao userDao = new UserDao();
boolean flag = userDao.findUserByName(user.getUsername());
int state = 0;
if (flag){
state = 2;
}else {
int i = userDao.addUser(user);
if (i > 0){
state = 1;
}else {
state = 0;
}
}
return state;
}
}
4.3、Controller层
UserController:调用方法实现业务
package com.org.controller;
import com.org.domain.User;
import com.org.service.UserService;
import com.org.utils.ArrayToString;
import com.org.validate.ValidateDemo;
import org.apache.commons.beanutils.BeanUtils;
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.lang.reflect.InvocationTargetException;
import java.net.URLEncoder;
import java.util.Map;
@WebServlet("/UserController")
public class UserController extends HttpServlet{
@Override
protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
//查询所有用户
UserService service = new UserService();
service.select();
String userAction = req.getParameter("userAction");
//登录
if ("login".equals(userAction)){
User user = new User();
try {
BeanUtils.populate(user,req.getParameterMap());
Map<String, String> error = ValidateDemo.validateUser(user);
if (error.isEmpty()){
UserService userService = new UserService();
boolean flag = userService.login(user.getUsername(),user.getPassword());
if (flag){
resp.sendRedirect("index.jsp?username="+ URLEncoder.encode(user.getUsername(),"utf-8"));
}else{
req.setAttribute("fail","登陆失败!");
req.getRequestDispatcher("login2.jsp").forward(req,resp);
}
}else {
req.setAttribute("error",error);
req.getRequestDispatcher("login2.jsp").forward(req,resp);
}
} catch (IllegalAccessException e) {
e.printStackTrace();
} catch (InvocationTargetException e) {
e.printStackTrace();
}
}
//注册
if ("register".equals(userAction)){
User user = new User();
try {
BeanUtils.populate(user,req.getParameterMap());
user.setHobby(ArrayToString.arraytostring(req.getParameterValues("hobby")));
} catch (IllegalAccessException e) {
e.printStackTrace();
} catch (InvocationTargetException e) {
e.printStackTrace();
}
//验证数据
Map<String, String> error = ValidateDemo.validateUser(user);
if (error.isEmpty()){
UserService userService = new UserService();
int register = userService.register(user);
if (register == 0){
resp.sendRedirect("/servlet/registerfail.jsp");
}
if (register == 1){
resp.sendRedirect("/servlet/success.jsp");
}
if (register == 2){
resp.sendRedirect("/servlet/register.jsp?registerfail="+URLEncoder.encode("该用户已存在!","utf-8"));
}
}else{
req.setAttribute("error",error);
req.getRequestDispatcher("register.jsp").forward(req,resp);
}
}
}
}
4.4、建立网页
4.4.1、注册界面(register.jsp)
<%@ page import="java.util.HashMap" %><%--
Created by IntelliJ IDEA.
User: Nine06
Date: 2023/9/21
Time: 11:54
To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title></title>
</head>
<body>
<%
HashMap<String,String> error = (HashMap<String, String>)request.getAttribute("error");
String fail = request.getParameter("fail");
%>
<div>
<div style="text-align: center"><%=fail==null?"":fail%></div>
<form action="UserController" method="post">
<input type="hidden" value="register" name="userAction">
<table border="1px" width="30%" height="500px" align="center">
<tr align="center">
<td colspan="2">注册</td>
</tr>
<tr>
<td>用户名:</td><td><input type="text" name="username"><span style="color: red;"><%=error==null?"":error.get("username")==null?"":error.get("username")%></span></td>
</tr>
<tr>
<td>密码:</td><td><input type="password" name="password"><span style="color: red;"><%=error==null?"":error.get("password")==null?"":error.get("password")%></span></td>
</tr>
<%--<tr>--%>
<%--<td>出生日期:</td>--%>
<%--<td>--%>
<%--<input type="text" name="birthday">--%>
<%--</td>--%>
<%--</tr>--%>
<tr>
<td>性别:</td>
<td>
<input type="radio" name="gender" value="male">男
<input type="radio" name="gender" value="female">女
</td>
</tr>
<tr>
<td>爱好:</td>
<td>
<input type="checkbox" name="hobby" value="篮球">篮球
<input type="checkbox" name="hobby" value="足球">足球
<input type="checkbox" name="hobby" value="羽毛球">羽毛球
</td>
</tr>
<tr>
<td>地址:</td>
<td>
<select name="address">
<option value="成都">成都</option>
<option value="绵阳">绵阳</option>
<option value="达州">达州</option>
</select>
</td>
</tr>
<tr>
<td>备注:</td>
<td><textarea cols="30" rows="10" name="remark"></textarea></td>
</tr>
<tr>
<td colspan="2" align="center">
<input type="submit" value="登录" >
<input type="reset" value="重置" >
</td>
</tr>
</table>
</form>
</div>
</body>
</html>
4.4.2、登录界面(login2.jsp)
<%@ page import="java.util.HashMap" %><%--
Created by IntelliJ IDEA.
User: Nine06
Date: 2023/9/27
Time: 10:32
To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>Title</title>
</head>
<body>
<%
HashMap<String,String> error = (HashMap<String, String>)request.getAttribute("error");
String registerfail = (String) request.getAttribute("registerfail");
%>
<form action="UserController" method="post">
<input type="hidden" value="login" name="userAction">
<table border="1" cellpadding="0" cellspacing="0" align="center">
<tr><th>登录</th></tr>
<tr><td>账号:<input type="text" name="username"><span style="color: red;"><%=registerfail==null?"":registerfail%><%=error==null?"":error.get("username")==null?"":error.get("username")%></span></td></tr>
<tr><td>密码:<input type="password" name="password"><span style="color: red;"><%=error==null?"":error.get("password")==null?"":error.get("password")%></span></td></tr>
<tr><td colspan="2" align="center"><input type="submit" value="登录">
<input type="reset" value="重置">
</td></tr>
</table>
</form>
</body>
</html>
4.4.3、首页(index.jsp)
<%--
Created by IntelliJ IDEA.
User: Nine06
Date: 2023/9/19
Time: 10:27
To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>Title</title>
</head>
<body>
<%--转发 --%>
<%--欢迎<%=request.getAttribute("username")%>登录成功!!!--%>
<%--重定向--%>
欢迎<%=request.getParameter("username")%>登录成功!!!<br>
<a href="userinfo.jsp">查询更多用户</a>
</body>
</html>
4.4.4、注册成功页面(success.jsp)
<%--
Created by IntelliJ IDEA.
User: Nine06
Date: 2023/9/21
Time: 15:36
To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>Title</title>
</head>
<body>
<h1>注册成功!!!</h1><a href="login2.jsp">登录</a>
</body>
</html>
4.4.5、注册失败页面(registerfail.jsp)
<%--
Created by IntelliJ IDEA.
User: Nine06
Date: 2023/9/21
Time: 15:30
To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>Title</title>
</head>
<body>
<H1>注册失败!!!</H1><a href="register.jsp">返回</a>
</body>
</html>
4.5、运行页面
注册界面
注册成功
登陆界面
登录成功
数据库数据接收成功
运行完成。