DAO(數據訪問對象)設計模式——JSP的應用(使用PostgreSQL數據庫)

DAO(數據訪問對象)

程序的標準架構爲:html

客戶層(Client)-> 顯示層(jsp/servlet)-> 業務層(BO) -> 數據層(BAO) -> 資源層(DataBase)java

項目Gitee地址:https://gitee.com/hcflyambation/daoprojectgit

1,組成部分(Java命名規範)

  • 1,DatabaseConnection: 專門負責數據庫打開和關閉操做的類;(xxx.dbc.DatabaseConnection)
  • 2,VO:主要由屬性、setter、geter組成,VO類中的屬性與表中的字段相對應。(xxx.vo.Xxx)
  • 3,DAO: 主要定義操做的接口,定義一系列的數據庫的原子性操做,如,增刪改查。(xxx.dao.XxxDAO)
  • 4,Impl:DAO接口的真實實現類,完成具體的數據庫操做,可是不負責數據庫的打開和關閉。(xxx.dao.impl.XxxDAOImpl)
  • 5,Proxy:代理實現類,主要完成數據庫的打開和關閉,而且調用真實實現類對象的操做。(xxx.dao.proxy.XxxDAOProxy)
  • 6,Factory:工廠類,經過工廠類得到一個DAO的實例化對象。(xxx.factory.DAOFactory)

2,DAO的實例開發

項目結構:程序員

特別要注意的是:當啓動web程序時,請將依賴的jar(postgresql-42.2.19.jar放入WEB-INF/lib/下,否則會檢測不到)web

JAR必須直接放在web項目的/ WEB-INF / lib文件夾中,而不用項目屬性中的Build Path.該文件夾是webapp運行時類路徑的標準部分sql

2.1,數據庫腳本創建(使用PostgreSQL)

數據庫名爲:jsp數據庫

create table emp (
    empno int  primary key,
    ename varchar(10),
    job varchar(9),
    hiredate date,
    sal decimal
);

2.2,編寫與數據庫對應的OV類(Emp.java)

package com.hcfly.vo;

import java.math.BigDecimal;
import java.util.Date;

public class Emp {
	private int empno;
	private String ename;
	private String job;
	private Date hiredate;
	private float sal;
	
	public int getEmpno() {
		return empno;
	}
	public void setEmpno(int empno) {
		this.empno = empno;
	}
	public String getEname() {
		return ename;
	}
	public void setEname(String ename) {
		this.ename = ename;
	}
	public String getJob() {
		return job;
	}
	public void setJob(String job) {
		this.job = job;
	}
	public Date getHiredate() {
		return hiredate;
	}
	public void setHiredate(Date hiredate) {
		this.hiredate = hiredate;
	}
	public float getSal() {
		return sal;
	}
	public void setSal(float sal) {
		this.sal = sal;
	}
}

2.3, 編寫數據庫鏈接類(DatabaseConnection.java)

這個地方能夠將DatabaseConnection抽象爲一個接口,而且用不一樣的數據庫訪問類去實現它,來達到通用的水平。apache

package com.hcfly.dbc;

import java.sql.Connection;
import java.sql.DriverManager;

public class DatabaseConnection {
	// 數據庫鏈接類
	private static final String DBDRIVER = "org.postgresql.Driver";
	private static final String DBURL = "jdbc:postgresql://localhost/jsp";
	private static final String DBUSER = "postgres";
	private static final String DBPASSWORD = "miaomiao";
	private Connection connection = null;
	
	public DatabaseConnection() throws Exception{
		try {
			Class.forName(DBDRIVER);
			this.connection = DriverManager.getConnection(DBURL, DBUSER, DBPASSWORD);
//			System.out.println("鏈接成功");
		} catch (Exception e) {
			throw e;
			// TODO: handle exception
		}
	
	}
	
	public Connection getConnection() {
		return this.connection;
	}
	
	public void close() throws Exception {
		if(this.connection != null) {
			try {
				this.connection.close();
			} catch (Exception e) {
				throw e;
				// TODO: handle exception
			}
		}
	}

}

2.4,定義DAO操做標準(IEmpDAO.java)

package com.hcfly.dao;

import java.util.List;

import com.hcfly.vo.Emp;

public interface IEmpDAO { // 定義DAO操做
	/**
	 * 定義DAO的標準操做
	 * 
	 */
	public boolean doCreate(Emp emp) throws Exception;
	/**
	 * @param emp要增長的數據對象
	 */
	public List<Emp> findAll(String keyWord) throws Exception;
	/**
	 * 根據查詢關鍵字進行搜索
	 */
	public Emp findById(int empno) throws Exception;

}

2.5,真實主題實現類(EmpDAOImpl.java)

package com.hcfly.dao.impl;

import java.sql.Connection;
import java.sql.Date;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.util.ArrayList;
import java.util.List;

import com.hcfly.dao.IEmpDAO;
import com.hcfly.vo.Emp;

public class EmpDAOImpl implements IEmpDAO{
	/**
	 * 真實主題類
	 */
	private Connection connection = null;
	private PreparedStatement pstmt = null;
	
	public EmpDAOImpl(Connection connection) {
		// 獲取數據庫鏈接
		this.connection = connection;
	}

	@Override
	public boolean doCreate(Emp emp) throws Exception {
		boolean flag = false;
		String sql = "INSERT INTO emp (empno, ename, job, hiredate, sal) VALUES (?,?,?,?,?)";
		this.pstmt = this.connection.prepareStatement(sql);
		this.pstmt.setInt(1, emp.getEmpno());
		this.pstmt.setString(2, emp.getEname());
		this.pstmt.setString(3, emp.getJob());
		this.pstmt.setDate(4, new Date(emp.getHiredate().getTime()));
		this.pstmt.setFloat(5, emp.getSal());
		
		if(this.pstmt.executeUpdate() > 0) {	// 更新記錄行數大於1
			flag = true;
		}
		this.pstmt.close();
		return flag;
	}

	@Override
	public List<Emp> findAll(String keyWord) throws Exception {
		
		List<Emp> all = new ArrayList<Emp>();
		String sql = "SELECT empno, ename, job, hiredate, sal FROM emp WHERE ename LIKE ? OR job LIKE ?";
		this.pstmt = this.connection.prepareStatement(sql);
		this.pstmt.setString(1, "%"+keyWord +"%");
		this.pstmt.setString(2, "%"+keyWord +"%");
		ResultSet rSet = this.pstmt.executeQuery();
		Emp emp = null;
		while (rSet.next()) {
			emp = new Emp();
			emp.setEmpno(rSet.getInt("empno"));
			emp.setEname(rSet.getString("ename"));
			emp.setHiredate(rSet.getDate("hiredate"));
			emp.setJob(rSet.getString("job"));
			emp.setSal(rSet.getFloat("sal"));
			all.add(emp);
			
		}
		this.pstmt.close();
		// TODO Auto-generated method stub
		return all;
	}

	@Override
	public Emp findById(int empno) throws Exception {
		String sql = "SELECT empno, ename, job, hiredate, sal FROM emp WHERE empno=?";
		this.pstmt = this.connection.prepareStatement(sql);
		this.pstmt.setInt(1, empno);
		ResultSet rSet = this.pstmt.executeQuery();
		Emp emp = null;
		if(rSet.next()) {
			emp = new Emp();
			emp.setEmpno(rSet.getInt("empno"));
			emp.setEname(rSet.getString("ename"));
			emp.setHiredate(rSet.getDate("hiredate"));
			emp.setJob(rSet.getString("job"));
			emp.setSal(rSet.getFloat("sal"));
		}
		this.pstmt.close();
		// TODO Auto-generated method stub
		return emp;
	}

}

2.5,代理主題實現類(IEmpDAOProxy.java)

package com.hcfly.dao.proxy;

import java.util.List;

import com.hcfly.dao.IEmpDAO;
import com.hcfly.dao.impl.EmpDAOImpl;
import com.hcfly.dbc.DatabaseConnection;
import com.hcfly.vo.Emp;

public class EmpDAOProxy implements IEmpDAO{
	/**
	 * 代理主題實現類
	 */
	
	private DatabaseConnection dbc = null;
	private IEmpDAO dao = null;
	
	public EmpDAOProxy() throws Exception{
		this.dbc = new DatabaseConnection(); // 鏈接到數據庫
		this.dao = new EmpDAOImpl(this.dbc.getConnection());
	}

	@Override
	public boolean doCreate(Emp emp) throws Exception {
		boolean flag = false;
		
		try {
			if(this.dao.findById(emp.getEmpno()) == null) {
				flag = this.dao.doCreate(emp);
			}
		} catch (Exception e) {
			throw e;
		}finally {	
			this.dbc.close();	// 不管是否成功,將鏈接關閉
		}
		// TODO Auto-generated method stub
		return flag;
	}

	@Override
	public List<Emp> findAll(String keyWord) throws Exception {
		List<Emp> all = null;
		try {
			all = this.dao.findAll(keyWord);
		} catch (Exception e) {
			throw e;
		} finally {
			this.dbc.close();
		}
		return all;
	}

	@Override
	public Emp findById(int empno) throws Exception {
		Emp emp = null;
		try {
			emp = this.dao.findById(empno);
		} catch (Exception e) {
			throw e;
		}finally {
			this.dbc.close();
		}
		return emp;
	}

}

2.6,DAO工廠類(DAOFactory.java)

package com.hcfly.factory;

import com.hcfly.dao.IEmpDAO;
import com.hcfly.dao.proxy.EmpDAOProxy;

public class DAOFactory {
	/**
	 * 工廠類
	 * @return
	 * @throws Exception
	 */
	public static IEmpDAO getIEmpDAOInstance() throws Exception{
		return new EmpDAOProxy();
	}
}

2.7,測試類(TestDAOInsert.java)

package com.hcfly.dao.test;

import java.util.Date;

import com.hcfly.factory.DAOFactory;
import com.hcfly.vo.Emp;

public class TestDAOInsert {

	public static void main(String[] args) throws Exception{
		// TODO Auto-generated method stub
		Emp emp = null;
		for(int x = 0; x < 5; x++) {
			emp = new Emp();
			emp.setEmpno(1000+x);
			emp.setEname("張憨憨" + x);
			emp.setJob("程序員 - " + x);
			emp.setHiredate(new Date());
			emp.setSal(500 * x);
//			DAOFactory.getIEmpDAOInstance().doCreate(emp);
			
		}
		System.out.println(DAOFactory.getIEmpDAOInstance().findById(1001));

	}

}

2.8,總結

DAO 只是提供了一個數據的操做平臺,無論在Application仍是Web程序中,此DAO程序都不用作修改。架構

3,DAO的web使用實例(開發工具爲Ecplise,若是要運行,請先配置數據庫)

從註冊頁面提交信息給數據庫,而後讀出來,展現到表格中。app

3.1, 登陸註冊頁面(增長數據表單)(emp_insert.jsp)

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>註冊</title>
</head>
<body>
    <form action="emp_insert_do.jsp" method="post" >
        僱員編號:<input type="text" name="empno" id=""><br/>
        僱員姓名:<input type="text" name="ename" id=""><br/>
        僱員職位:<input type="text" name="job" id=""><br/>
        僱員日期:<input type="text" name="hiredate" id=""><br/>
        僱員工資:<input type="text" name="sal" id=""><br/>
        <input type="submit" value="註冊">
        <input type="reset" value="重置">
    </form>
    <a href="emp_list.jsp">跳轉到列表頁面</a>
</body>
</html>

3.2, 處理數據頁面(emp_insert_do.jsp)

<%@page import="com.hcfly.factory.DAOFactory"%>
<%@page import="java.text.SimpleDateFormat"%>
<%@page import="com.hcfly.vo.Emp"%>
<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>處理表單</title>
<%request.setCharacterEncoding("utf-8"); 
	response.setHeader("refresh", "3;URL=emp_list.jsp");	// 設置跳轉時間爲3秒
%>
</head>
<body>
<%
Emp emp = new Emp();
emp.setEmpno(Integer.parseInt(request.getParameter("empno")));
emp.setEname(request.getParameter("ename"));
emp.setJob(request.getParameter("job"));
emp.setHiredate(new SimpleDateFormat("yyyy-MM-dd").parse(request.getParameter("hiredate")));
emp.setSal(Float.parseFloat(request.getParameter("sal")));
try{
	if(DAOFactory.getIEmpDAOInstance().doCreate(emp)){
		out.print("<h3>僱員信息添加成功!</h3>");
	}else{
		out.print("<h3>僱員信息添加失敗!</h3>");
	}
}catch(Exception e){
	e.printStackTrace();
}

%>
<h3>3秒後跳轉到列表頁</h3>
</body>
</html>

3.3,列表頁面(emp_list.jsp)

<%@page import="com.hcfly.vo.Emp"%>
<%@page import="java.util.List"%>
<%@page import="org.apache.jasper.tagplugins.jstl.core.Catch"%>
<%@page import="java.util.Iterator"%>
<%@page import="com.hcfly.factory.DAOFactory"%>
<%@page import="java.util.Dictionary"%>
<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>列表</title>
<% request.setCharacterEncoding("utf-8"); %>
</head>
<body>
<%
	try{
		String keyWord = request.getParameter("kw");
		if(keyWord == null){
			keyWord = "";
		}
		List<Emp> all = DAOFactory.getIEmpDAOInstance().findAll(keyWord);
		Iterator<Emp> iter = all.iterator();
	
%>
<center>
        <form action="" method="post">
            <input type="text" name="kw">
            <input type="submit" value="查詢">

        </form>
        <table border="1" width="80%">
            <tr>
                <td>僱員編號:</td>
                <td>僱員姓名:</td>
                <td>僱員工做:</td>
                <td>僱員工資:</td>
                <td>僱員日期:</td>
            </tr>
            <% while(iter.hasNext()){
            	Emp emp = iter.next();
            	
            	%>
            <tr>
                <td><%= emp.getEmpno() %></td>
                <td><%= emp.getEname() %></td>
                <td><%= emp.getJob() %></td>
                <td><%= emp.getSal() %></td>
                <td><%= emp.getHiredate() %></td>
            </tr>
            <%
            }
            %>
        </table>
        
        <a href="emp_insert.jsp">跳轉到插入頁面</a>

    </center>
    <%
    }catch(Exception e){
    	e.printStackTrace();
    }
    %>
</body>
</html>

3.4,結果展現

3.4.1 數據庫

3.4.2,註冊界面

3.4.3,列表頁面

相關文章
相關標籤/搜索