一:准备工作
1:test文件夹(里面有所需的页面资源),我完成的是在里面添加增删改查操作
2:myeclipse(版本没什么要求) eclipse也行 jdk
3:数据库 MySQL
4:需要了解到的知识点:
servlet
EL与JSTL表达式
项目的基本框架搭建(javaweb经典三层框架)
5:在myeclipse中建立对应的包结构
二:项目的基本框架搭建
所谓三层框架分别为表述层(WEB层)、业务逻辑层()、数据访问层()。
web层(action):包含JSP和Servlet等与web相关的内容,负责与浏览器的响应和请求;
业务层(service):只关心业务逻辑;
数据层(dao):封装了对数据库的访问细节,数据操作类;
关系:web层依赖业务层 业务层依赖数据层(这个关系很重要)
ps:除了以上三层框架是我们在写一个javaweb项目必须的外,还需要一个实体类(entity)。
三:实现数据库的连接
需要在MySQL中创建所需数据库,并将表建好。
DROP TABLE IF EXISTS tb_subject
;
CREATE TABLE tb_subject
(subjectID
int(10) unsigned NOT NULL AUTO_INCREMENT COMMENT ‘试题编号’,subjectTitle
varchar(100) NOT NULL COMMENT ‘试题题目’,subjectOptionA
varchar(40) NOT NULL COMMENT ‘A选项’,subjectOptionB
varchar(40) NOT NULL COMMENT ‘B选项’,subjectOptionC
varchar(40) NOT NULL COMMENT ‘C选项’,subjectOptionD
varchar(40) NOT NULL COMMENT ‘D选项’,subjectAnswer
varchar(40) NOT NULL COMMENT ‘正确答案’,subjectParse
text NOT NULL COMMENT ‘试题解析’,
PRIMARY KEY (subjectID
)
) ENGINE=InnoDB AUTO_INCREMENT=2 DEFAULT CHARSET=utf8;
连接数据库
在dao下新建一个DBConn类用来处理对数据进行连接。 这是MySQL的连接方式
package dao;
import java.sql.*;
public class DBConn {
static Connection conn = null;
//连接数据库,返回Connection conn;
public static Connection getConn () {
String driverClassName = "com.mysql.jdbc.Driver";
String url = "jdbc:mysql://localhost:3306/db_examsystem";
String username = "root";
String password = "123";
try {
Class.forName(driverClassName);
conn = DriverManager.getConnection(url, username, password);
} catch (Exception e) {
e.printStackTrace();
}
return conn;
}
}
四:建立实体类
在entity包下创建Subject实体类(实体类中的对象对应数据库表中的字段数据)
package entity;
public class Subject {
private int subjectID;
private String subjectTitle;
private String subjectOptionA;
private String subjectOptionB;
private String subjectOptionC;
private String subjectOptionD;
private String subjectAnswer;
private String subjectParse;
public int getSubjectID() {
return subjectID;
}
public void setSubjectID(int subjectID) {
this.subjectID = subjectID;
}
public String getSubjectTitle() {
return subjectTitle;
}
public void setSubjectTitle(String subjectTitle) {
this.subjectTitle = subjectTitle;
}
public String getSubjectOptionA() {
return subjectOptionA;
}
public void setSubjectOptionA(String subjectOptionA) {
this.subjectOptionA = subjectOptionA;
}
public String getSubjectOptionB() {
return subjectOptionB;
}
public void setSubjectOptionB(String subjectOptionB) {
this.subjectOptionB = subjectOptionB;
}
public String getSubjectOptionC() {
return subjectOptionC;
}
public void setSubjectOptionC(String subjectOptionC) {
this.subjectOptionC = subjectOptionC;
}
public String getSubjectOptionD() {
return subjectOptionD;
}
public void setSubjectOptionD(String subjectOptionD) {
this.subjectOptionD = subjectOptionD;
}
public String getSubjectAnswer() {
return subjectAnswer;
}
public void setSubjectAnswer(String subjectAnswer) {
this.subjectAnswer = subjectAnswer;
}
public String getSubjectParse() {
return subjectParse;
}
public void setSubjectParse(String subjectParse) {
this.subjectParse = subjectParse;
}
}
五:实现增删改查方法
创建方法类,这里有两种方法
1:在dao包中创建一个StudentDao接口,里面写增删改查的方法,再在dao中创建StudentDaoImpl类来实现接口,并实现之中的方法。
StudentDao接口:
package dao;
import java.util.List;
import entity.Subject;
public interface SubjectDao {
/*
* 1.添加数据
* 2.查看数据,返回信息
* 3.修改
* 4.删除
*
* */
public boolean add(Subject subject);
public List<Subject> selectall();
public boolean update(String subjectTitle,String subjectOptionA,String subjectOptionB,
String subjectOptionC,String subjectOptionD,String subjectAnswer,String subjectParse);
public boolean delete(int subjectID);
public List<Subject> selectByID(String string);
}
StudentDaoImpl类(包含增删改查操作):
```java
package dao;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;
import com.mysql.jdbc.Connection;
import entity.Subject;
public class SubjectDaoImpl implements SubjectDao {
Connection conn = (Connection) DBConn.getConn();
@Override
public boolean add(Subject subject) {
boolean flag = false;
try {
String sql="insert tb_subject values('"+subject.getSubjectID()+"','"
+subject.getSubjectTitle()+"','"
+subject.getSubjectOptionA()+"','"
+subject.getSubjectOptionB()+"','"
+subject.getSubjectOptionC()+"','"
+subject.getSubjectOptionD()+"','"
+subject.getSubjectAnswer()+"','"
+subject.getSubjectParse()+"')";
PreparedStatement pstmt = conn.prepareStatement(sql);
int i = pstmt.executeUpdate();
pstmt.close();
conn.close();
if(i>0) {
flag = true;
}
} catch (SQLException e) {
e.printStackTrace();
}
return flag;
}
@Override
public List<Subject> selectall() {
List<Subject> list = new ArrayList<Subject>();
try {
String sql = "select * from tb_subject";
PreparedStatement pstmt = conn.prepareStatement(sql);
ResultSet rs = pstmt.executeQuery();
while(rs.next()) {
Subject subject = new Subject();
subject.setSubjectID(rs.getInt("subjectID"));
subject.setSubjectTitle(rs.getString("subjectTitle"));
subject.setSubjectOptionA(rs.getString("subjectOptionA"));
subject.setSubjectOptionB(rs.getString("subjectOptionB"));
subject.setSubjectOptionC(rs.getString("subjectOptionC"));
subject.setSubjectOptionD(rs.getString("subjectOptionD"));
subject.setSubjectAnswer(rs.getString("subjectAnswer"));
subject.setSubjectParse(rs.getString("subjectParse"));
list.add(subject);
}
rs.close();
pstmt.close();
conn.close();
} catch (SQLException e) {
e.printStackTrace();
}
return list;
}
@Override
public List<Subject> selectByID(String subjectID) {
List<Subject> list = new ArrayList<Subject>();
try {
String sql = "select * from tb_subject where subjectID=?";
PreparedStatement pstmt = conn.prepareStatement(sql);
pstmt.setString(1,subjectID );
ResultSet rs = pstmt.executeQuery();
while(rs.next()) {
Subject subject = new Subject();
subject.setSubjectID(rs.getInt("subjectID"));
subject.setSubjectTitle(rs.getString("subjectTitle"));
subject.setSubjectOptionA(rs.getString("subjectOptionA"));
subject.setSubjectOptionB(rs.getString("subjectOptionB"));
subject.setSubjectOptionC(rs.getString("subjectOptionC"));
subject.setSubjectOptionD(rs.getString("subjectOptionD"));
subject.setSubjectAnswer(rs.getString("subjectAnswer"));
subject.setSubjectParse(rs.getString("subjectParse"));
list.add(subject);
}
rs.close();
pstmt.close();
conn.close();
} catch (SQLException e) {
e.printStackTrace();
}
return list;
}
@Override
public boolean update( String subjectTitle,
String subjectOptionA, String subjectOptionB,
String subjectOptionC, String subjectOptionD, String subjectAnswer,
String subjectParse) {
boolean flag = false;
try {
String sql = "update tb_subject set subjectOptionA = '"+subjectOptionA+"',subjectOptionB = '"+subjectOptionB+"',subjectOptionC = '"+subjectOptionC+
"',subjectOptionD = '"+subjectOptionD+"',subjectAnswer = '"+subjectAnswer+"',subjectParse = '"+subjectParse+"' where subjectTitle = '"+subjectTitle+"'";
PreparedStatement pstmt = conn.prepareStatement(sql);
int i = pstmt.executeUpdate();
pstmt.close();
conn.close();
if(i>0)flag = true;
} catch (SQLException e) {
e.printStackTrace();
}
return flag;
}
@Override
public boolean delete(int subjectID) {
boolean flag = false;
try {
String sql = "delete from tb_subject where subjectID = '"+subjectID+"'";
PreparedStatement pstmt = conn.prepareStatement(sql);
int i = pstmt.executeUpdate();
pstmt.close();
conn.close();
if(i>0) flag = true;
} catch (SQLException e) {
System.out.println("删除失败!");
e.printStackTrace();
}
return flag;
}
}
2:在service包中创建StudentService类,在dao包中创建StudentDao类来实现StudentService类中的方法。(具体操作以后更新)
六:实现servlet和对应jsp(html)页面
Servlet有两种方式创建,一种手工创建。另一种程序自动生成。前者自己创建java类,实现Servlet具体内容,然后需要去WEB_INF下的web.xml去配置servlet . 而后者则直接由程序替我们配置好了Servlet
1:增
创建SubjectAddServlet
```java
package action;
import java.io.IOException;
import java.io.PrintWriter;
import java.sql.SQLException;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import dao.SubjectDao;
import dao.SubjectDaoImpl;
import entity.Subject;
public class SubjectServlet extends HttpServlet {
@Override
protected void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
request.setCharacterEncoding("utf-8");
response.setContentType("text/html;charset=utf-8");
String subjectTitle=request.getParameter("subjectTitle");
String subjectOptionA=request.getParameter("subjectOptionA");
String subjectOptionB=request.getParameter("subjectOptionB");
String subjectOptionC=request.getParameter("subjectOptionC");
String subjectOptionD=request.getParameter("subjectOptionD");
String subjectAnswer=request.getParameter("subjectAnswer");
String subjectParse=request.getParameter("subjectParse");
Subject Subject =new Subject();
Subject.setSubjectTitle(subjectTitle);
Subject.setSubjectOptionA(subjectOptionA);
Subject.setSubjectOptionB(subjectOptionB);
Subject.setSubjectOptionC(subjectOptionC);
Subject.setSubjectOptionD(subjectOptionD);
Subject.setSubjectAnswer(subjectAnswer);
Subject.setSubjectParse(subjectParse);
SubjectDao sd = new SubjectDaoImpl();
try{
sd.add(Subject);
}catch(Exception e){
System.out.println("添加失败");
e.printStackTrace();
}
}
}
注意:
ps:因为在设计数据库中我们设置的subjectID为自增长,所以这里添加数据的时候不用添加subjectID这一字段。
request.getParameterr(“xxx”):
request.getParameter(“name”);//得到request域的参数信息(得到jsp页面传过来的参数)
getParameter表示接收参数,参数为页面提交的参数,包括:表单提交的参数、URL重写(就是xxx?id=1中的id)传的参数等,因此这个并没有设置参数的方法(没有setParameter),而且接收参数返回的不是Object,而是String类型
subjectAdd页面部分
<div id="addSubjectForm" align="center"><!--录入试题表单-->
<form action="SubjectAddServlet" method="post">
<table border="0" cellspacing="10" cellpadding="0">
<tr>
<td colspan="2"><FONT color="red"><s:actionerror/></FONT></td>
</tr>
<tr>
<td>试题题目:</td>
<td><input type="text" name="subjectTitle" size="80" ></td>
</tr>
<tr>
<td>选项A:</td>
<td><input type="text" name="subjectOptionA" size="20" ></td>
</tr>
<tr>
<td>选项B:</td>
<td><input type="text" name="subjectOptionB" size="20" ></td>
</tr>
<tr>
<td>选项C:</td>
<td><input type="text" name="subjectOptionC" size="20" ></td>
</tr>
<tr>
<td>选项D:</td>
<td><input type="text" name="subjectOptionD" size="20" ></td>
</tr>
<tr>
<td>答案:</td>
<td>
<input name="subjectAnswer" type="radio" value="A" checked>A
<input name="subjectAnswer" type="radio" value="B">B
<input name="subjectAnswer" type="radio" value="C">C
<input name="subjectAnswer" type="radio" value="D">D
</td>
</tr>
<tr>
<td valign="top">试题解析:</td>
<td>
<textarea name="subjectParse" cols="76" rows="10"></textarea>
</td>
</tr>
<tr>
<td colspan="2"><div align="center">
<input type="submit" value="录入">
<input type="reset" value="重置">
</div>
</td>
</tr>
</table>
</form>
注意:
action=“SubjectAddServlet”为SubjectAddServlet在web.xml中的URL目录
当在servlet中完成的操作需要获取页面表单等的数据时,需要在页面中指向对应的servlet。
2:删
创建SubjectDeleteServlet
package action;
import java.io.IOException;
import java.io.PrintWriter;
import java.util.List;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import dao.SubjectDao;
import dao.SubjectDaoImpl;
import entity.Subject;
public class SubjectDeleteServlet extends HttpServlet {
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
doPost(request, response);
}
@Override
protected void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
request.setCharacterEncoding("utf-8");
response.setContentType("text/html;charset=utf-8");
String subjejctID = (String) request.getParameter("subjectID");
int userSubjectID = Integer.parseInt(subjejctID);
SubjectDao sd = new SubjectDaoImpl();
sd.delete(userSubjectID);
}
}
注意:doGet(),doPost()
当需要获取页面中的数据时,用doPost。
当用到URL重写(就是xxx?id=1中的id)传的参数时,用doGet()。
或者是把具体方法写到doPost中,在doGet()方法中调用doPost方法。
subjectDelete.jsp部分页面
<div id="manageSubject" align="center"><!--删除试题-->
<table width="95%" cellspacing="10">
<tr align="center">
<td>试题编号</td>
<td>试题标题</td>
<td>正确答案</td>
<td>查看试题</td>
</tr>
<c:forEach var="s" items="${list }">
<tr align="center">
<td>${s.subjectID }</td>
<td align="left">${s.subjectTitle }</td>
<td>${s.subjectAnswer }</td>
<td><a href="SubjectShowServlet?subjectID=${s.subjectID }">查看</a></td>
<td><a href="SubjectDeleteServlet?subjectID=${s.subjectID }">删除</a></td>
</tr>
</c:forEach>
</table>
</div>
注意:
删除页面和查询页面是公用一个页面
${list }:EL表达式 获取request域中名为list的值
页面使用的到JSTL表达式 即c标签。使用c标签需要引入头文件<%@ taglib prefix=“c” uri=“http://java.sun.com/jsp/jstl/core”%> 。
需要注意的的是El标签配合JSTl标签的使用,<c:forEach var=“s” items="{list }
而且当指定别名后var=“s” ,别名可以随便起,为了方便一般是小写类名命名。
C标签内遍历的属性也是需要用${ }获取。此时别名s即为当前集合中的Subject对象,想得到属性只需要用 ${ s.属性名 } 即可
3:改
创建SubjectUpdateServlet
package action;
import java.io.IOException;
import java.io.PrintWriter;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import dao.SubjectDao;
import dao.SubjectDaoImpl;
import entity.Subject;
public class SubjectUpdateServlet extends HttpServlet {
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
doPost(request, response);
}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
request.setCharacterEncoding("utf-8");
response.setContentType("text/html;charset=utf-8");
String subjectID = request.getParameter("subjectID");
String subjectTitle=request.getParameter("subjectTitle");
String subjectOptionA=request.getParameter("subjectOptionA");
String subjectOptionB=request.getParameter("subjectOptionB");
String subjectOptionC=request.getParameter("subjectOptionC");
String subjectOptionD=request.getParameter("subjectOptionD");
String subjectAnswer=request.getParameter("subjectAnswer");
String subjectParse=request.getParameter("subjectParse");
SubjectDao sd = new SubjectDaoImpl();
try{
sd.update( subjectTitle, subjectOptionA, subjectOptionB, subjectOptionC,
subjectOptionD, subjectAnswer, subjectParse);
}catch(Exception e) {
System.out.println("修改失败!");
e.printStackTrace();
}
}
}
注意:
request.getParameter("")获取页面参数
<div id="updateSubjectForm" align="center"><!--更新试题表单-->
<form action="SubjectUpdateServlet" method="post">
<table border="0" cellspacing="10" cellpadding="0">
<tr>
<td colspan="2"><s:actionmessage/></td>
</tr>
<tr>
<td>试题题目:</td>
<td>
<input name="subjectID" type="hidden" >
<input name="subjectTitle" type="text" size="80" >
</td>
</tr>
<tr>
<td>选项A:</td>
<td><input type="text" name="subjectOptionA" size="20" ></td>
</tr>
<tr>
<td>选项B:</td>
<td><input type="text" name="subjectOptionB" size="20" ></td>
</tr>
<tr>
<td>选项C:</td>
<td><input type="text" name="subjectOptionC" size="20" ></td>
</tr>
<tr>
<td>选项D:</td>
<td><input type="text" name="subjectOptionD" size="20" ></td>
</tr>
<tr>
<td>答案:</td>
<td>
<input type="text" name="subjectAnswer" size="20" value="">
</td>
</tr>
<tr>
<td valign="top">答案解析:</td>
<td>
<textarea name="subjectParse" cols="76" rows="10" ></textarea>
</td>
</tr>
<tr>
<td colspan="2"><div align="center">
<input type="submit" value="更新">
<input type="reset" value="重置">
</div>
</td>
</tr>
</table>
</form>
</div>
注意:
action=“SubjectUpdateServlet”为SubjectUpdateServlet在web.xml中的URL目录
当在servlet中完成的操作需要获取页面表单等的数据时,需要在页面中指向对应的servlet。
4:查
这里需要完成两个查询(查询返回列表;查询返回列表详细)
查询返回列表
创建SubjectListServlet:
package action;
import java.io.IOException;
import java.io.PrintWriter;
import java.util.List;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import dao.SubjectDao;
import dao.SubjectDaoImpl;
import entity.Subject;
public class SubjectListServlet extends HttpServlet {
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
request.setCharacterEncoding("utf-8");
response.setContentType("text/html;charset=utf-8");
SubjectDao sd = new SubjectDaoImpl();
List<Subject> list = sd.selectall();
request.setAttribute("list", list);
request.getRequestDispatcher("/subjectList.jsp").forward(request, response);//转发到指定页面
}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
doGet(request, response);
}
}
注意:当不需要页面的参数时,页面由servlet引出
转发(request.getRequestDispatcher().forward();)和重定向(response.sendRedirect();)区别:
(1).重定向的执行过程:Web服务器向浏览器发送一个http响应–》浏览器接受此响应后再发送一个新的http请求到服务器–》服务器根据此请求寻找资源并发送给浏览器。它可以重定向到任意URL,不能共享request范围内的数据。
(2).重定向是在客户端发挥作用,通过新的地址实现页面转向。
(3).重定向是通过浏览器重新请求地址,在地址栏中可以显示转向后的地址。
(4).转发过程:Web服务器调用内部方法在容器内部完成请求和转发动作–》将目标资源发送给浏览器,它只能在同一个Web应用中使用,可以共享request范围内的数据。
(5).转发是在服务器端发挥作用,通过forward()方法将提交信息在多个页面间进行传递。
(6).转发是在服务器内部控制权的转移,客户端浏览器的地址栏不会显示出转向后的地址。
subjectList.jsp部分页面:
<div id="manageSubject" align="center"><!--查看试题-->
<table width="95%" cellspacing="10">
<tr align="center">
<td>试题编号</td>
<td>试题标题</td>
<td>正确答案</td>
<td>查看试题</td>
</tr>
<c:forEach var="u" items="${list }">
<tr align="center">
<td>${u.subjectID }</td>
<td align="left">${u.subjectTitle }</td>
<td>${u.subjectAnswer }</td>
<td><a href="SubjectShowServlet?subjectID=${u.subjectID }">查看</a></td>
<td><a href="SubjectDeleteServlet?subjectID=${u.subjectID }">删除</a></td>
</tr>
</c:forEach>
</table>
</div>
注意:
这里的顺序是,先访问的是SubjectListServlet,在转发到此页面,此页面的查看和删除又通过对应的servlet来实现对应的功能。
查询返回列表详细
创建SubjectShowServlet:
package action;
import java.io.IOException;
import java.io.PrintWriter;
import java.util.List;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import dao.SubjectDao;
import dao.SubjectDaoImpl;
import entity.Subject;
public class SubjectShowServlet extends HttpServlet {
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
request.setCharacterEncoding("utf-8");
response.setContentType("text/html;charset=utf-8");
SubjectDao sd = new SubjectDaoImpl();
List<Subject> list = sd.selectByID(request.getParameter("subjectID"));
request.setAttribute("list", list);
request.getRequestDispatcher("/subjectShow.jsp").forward(request, response);
}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
doGet(request, response);
}
}
注意:
这个查询方法需要通过限制条件subjectID来查询,不然显示出来的是所有的数据
subjectShow.jsp部分页面
<div id="showSubject" align="center"><!--显示试题-->
<table border="0" cellspacing="10" cellpadding="0">
<c:forEach var="u" items="${list }">
<tr>
<td>试题编号:</td>
<td>${u.subjectID }</td>
</tr>
<tr>
<td>试题题目:</td>
<td>${u.subjectTitle }</td>
</tr>
<tr>
<td>选项A:</td>
<td>${u.subjectOptionA }</td>
</tr>
<tr>
<td>选项B:</td>
<td>${u.subjectOptionB }</td>
</tr>
<tr>
<td>选项C:</td>
<td>${u.subjectOptionC }</td>
</tr>
<tr>
<td>选项D:</td>
<td>${u.subjectOptionD }</td>
</tr>
<tr>
<td>答案:</td>
<td>${u.subjectAnswer }</td>
</tr>
<tr>
<td valign="top">答案解析:</td>
<td valign="top">${u.subjectParse }</td>
</tr>
</c:forEach>
</table>
</div>
注意:
页面同样运用的是EL和jstl表达式
七:总结
在学习的道路上,一昧的看视频是没有用的,当看完一个阶段的视频后,要对该阶段写一个小项目,这样才能将视频中的知识点融会贯通。
项目源码(页面):点击打开链接
建议保留页面相关代码,servlet及jsp相关代码自己敲。
来源:CSDN
作者:人工智能小博士
链接:https://blog.csdn.net/weixin_40877900/article/details/104296334