BookStore主要是采用servlet以及JSP编写的。再次做一下简单的总结。
1. 将请求参数封装成对象的方法
使用beanUtils将请求参数封装为对象
- 导入jar包
commons-beanutils-1.9.4.jar
commons-logging-1.2.jar - 编写以下方法即可
public static<T> T params2bean(HttpServletRequest request, T t){
// 方法一:稍微有点复杂
// 通过反射得到参数对象的所有属性值
Field[] fields = t.getClass().getDeclaredFields();
// 遍历所有属性值,并为属性赋值且封装到对象中
for (Field field : fields) {
String name = field.getName();
String value = request.getParameter(name);
try {
BeanUtils.setProperty(t,name,value);
} catch (IllegalAccessException e) {
e.printStackTrace();
} catch (InvocationTargetException e) {
e.printStackTrace();
}
}
/*
// 方法二:死活行不通
// 获取所有的请求参数封装到map集合中
Map parameterMap = request.getParameterMap();
try {
// 调用BeanUtils工具类的populate方法即可
BeanUtils.populate(t, parameterMap);
} catch (IllegalAccessException e) {
e.printStackTrace();
} catch (InvocationTargetException e) {
e.printStackTrace();
}*/
return t;
}
2. 在同一个servlet调用不同的方法
创建一个BaseServlet类,作为今后创建servlet的所有父类,BaseServlet类有doGet();以及doPost();方法。
doPost();方法设置好获取前端传过来的隐藏对象的方法,通过反射调用相应的方法。
/**
* 使用反射处理前台传过来的参数,调用响应的方法
* @param request
* @param response
* @throws ServletException
* @throws IOException
*/
@Override
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
// 防止中文乱码
request.setCharacterEncoding("UTF-8");
String method = request.getParameter("method");
try {
// 通过反射,找到要调用的方法
Method methodReflect = this.getClass().getDeclaredMethod(method,HttpServletRequest.class,HttpServletResponse.class);
// 将方法的权限放大
methodReflect.setAccessible(true);
// 调用这个方法(谁要调用,这个方法的参数列表)
methodReflect.invoke(this,request,response);
} catch (Exception e) {
e.printStackTrace();
}
}
3. 页面数据的分页
3.1. 首先创建一个Page的model类
page.java的类中封装着页面分页的所有信息
// 当前是第几页,用户传过来的
private int pageNo;
// 总页数,通过总记录数/每页显示的个数 计算得出
private int allPage;
// 总记录数,通过获取数据库中数据的数量 得出
private int allCount;
// 每一页在数据库中开始查找的索引,通过当前的页数以及每页显示的数量计算得出
// index = (pageNo - 1) * pageSize
private int index;
// 每页显示多少数据,用户传过来的,此处默认显示4个数据
private int pageSize = 4;
// 转发时动态的url,主要是用于分页功能的抽取使用,使跳转页面时有动态的链接
private String url;
// 每页显示的对象信息
private List<T> pageList;
// 是否有上一页
private boolean hasPre;
// 是否有下一页
private boolean hasNext;
page.java的model类,即以上属性的声明及setXxx方法以及getXxx()等方法
import java.util.List;
public class Page<T> {
// 当前是第几页,用户传过来的
private int pageNo;
// 总页数,通过总记录数/每页显示的个数 计算得出
private int allPage;
// 总记录数,通过获取数据库中数据的数量 得出
private int allCount;
// 每一页在数据库中开始查找的索引,通过当前的页数以及每页显示的数量计算得出
// index = (pageNo - 1) * pageSize
private int index;
// 每页显示多少数据,用户传过来的,此处默认显示4个数据
private int pageSize = 4;
// 转发时动态的url,主要是用于分页功能的抽取使用,使跳转页面时有动态的链接
private String url;
// 每页显示的对象信息
private List<T> pageList;
// 是否有上一页
private boolean hasPre;
// 是否有下一页
private boolean hasNext;
public int getPageNo() {
return pageNo;
}
public void setPageNo(int pageNo) {
pageNo = pageNo > 1 ? pageNo : 1;
pageNo = pageNo < getAllPage() ? pageNo : getAllPage();
this.pageNo = pageNo;
}
public void setAllPage(int allPage) {
this.allPage = allPage;
}
public int getAllPage() {
// 总页数=总记录数/每页显示的记录数;
// 判断 总记录数%每页显示的记录数 是否等于0来判断是否需要加1
allPage = allCount / pageSize;
if (allCount % pageSize != 0){
allPage++;
}
return allPage;
}
public int getAllCount() {
return allCount;
}
public void setAllCount(int allCount) {
this.allCount = allCount;
}
public int getIndex() {
// 在数据库中开始的索引页=(当前页-1)*每页的数量
int i = (pageNo - 1) * pageSize;
// 如果用户请求第0页的话,需要进行一次判断
if(i < 0){
i = 0;
}
return i;
}
public int getpageSize() {
return pageSize;
}
public void setpageSize(int pageSize) {
this.pageSize = pageSize;
}
public String getUrl() {
return url;
}
public void setUrl(String url) {
this.url = url;
}
public List<T> getPageList() {
return pageList;
}
public void setPageList(List<T> pageList) {
this.pageList = pageList;
}
public boolean isHasPre() {
// 判断当前页是否大于第一页,大于第一页说明有上一页
return pageNo > 1;
}
public boolean isHasNext() {
// 判断当前页是否小于总页数,小于总页数说明有下一页
return pageNo < getAllPage();
}
public Page() {
}
public Page(int pageNo, int allPage, int allCount, int index, int pageSize, String url, List<T> pageList, boolean hasPre, boolean hasNext) {
this.pageNo = pageNo;
this.allPage = allPage;
this.allCount = allCount;
this.index = index;
this.pageSize = pageSize;
this.url = url;
this.pageList = pageList;
this.hasPre = hasPre;
this.hasNext = hasNext;
}
@Override
public String toString() {
return "Page{" +
"pageNo=" + pageNo +
", allPage=" + allPage +
", allCount=" + allCount +
", index=" + index +
", pageSize=" + pageSize +
", url='" + url + '\'' +
", pageList=" + pageList +
", hasPre=" + hasPre +
", hasNext=" + hasNext +
'}';
}
}
3.2. Controller层以及Service层
controller主要是为页面的跳转
service主要是为页面的page对象设置值
dao层作为持久化对象层,获取数据库中的数据
3.3. View层的按钮抽取
下列是抽取出来的分页按钮,具体如下图所示
<%@ page contentType="text/html;charset=UTF-8" language="java" pageEncoding="utf-8" %>
<script type="text/javascript">
$(function () {
$("#gotoPage").click(function (){
var gotoPageNo = $("#pn_input").val();
window.location.href = "${requestScope.pageList.url}&pageNo="+gotoPageNo;
});
});
</script>
<div id="page_nav">
<!-- 页码大于首页才显示 -->
<c:if test="${requestScope.pageList.pageNo > 1}">
<a href="${requestScope.pageList.url}&pageNo=1">首页</a>
</c:if>
<c:if test="${requestScope.pageList.hasPre}">
<a href="${requestScope.pageList.url}&pageNo=${requestScope.pageList.pageNo-1}">上一页</a>
</c:if>
<!-- 页码输出的开始 -->
<c:choose>
<%-- 当页数小于5时 --%>
<c:when test="${requestScope.pageList.allPage <= 5}">
<c:set var="begin" value="1" scope="page"></c:set>
<c:set var="end" value="${requestScope.pageList.allPage}" scope="page"></c:set>
</c:when>
<%-- 当页数大于5时 --%>
<c:when test="${requestScope.pageList.allPage > 5}">
<c:choose>
<%-- 当页码小于3 --%>
<c:when test="${requestScope.pageList.pageNo <= 3}">
<c:set var="begin" value="1" scope="page"></c:set>
<c:set var="end" value="5" scope="page"></c:set>
</c:when>
<%-- 当页码大于等于页数-2时 --%>
<c:when test="${requestScope.pageList.pageNo >= requestScope.pageList.allPage-2}">
<c:set var="begin" value="${requestScope.pageList.allPage-4}" scope="page"></c:set>
<c:set var="end" value="${requestScope.pageList.allPage}" scope="page"></c:set>
</c:when>
<%-- 当页码大于3,小于页数减2时--%>
<c:otherwise>
<c:set var="begin" value="${requestScope.pageList.pageNo-2}" scope="page"></c:set>
<c:set var="end" value="${requestScope.pageList.pageNo+2}" scope="page"></c:set>
</c:otherwise>
</c:choose>
</c:when>
</c:choose>
<c:forEach begin="${pageScope.begin}" var="i" end="${pageScope.end}">
<!-- 是当前页的话就不加链接 -->
<c:if test="${i == requestScope.pageList.pageNo}">
【${requestScope.pageList.pageNo}】
</c:if>
<!-- 不是当前页的话就加链接 -->
<c:if test="${i != requestScope.pageList.pageNo}">
<a href="${requestScope.pageList.url}&pageNo=${i}">${i}</a>
</c:if>
</c:forEach>
<c:if test="${requestScope.pageList.hasNext}">
<a href="${requestScope.pageList.url}&pageNo=${requestScope.pageList.pageNo+1}">下一页</a>
</c:if>
<!-- 页码小于末页才显示 -->
<c:if test="${requestScope.pageList.pageNo < requestScope.pageList.allPage}">
<a href="${requestScope.pageList.url}&pageNo=${requestScope.pageList.allPage}">末页</a>
</c:if>
共${requestScope.pageList.allPage}页,
${requestScope.pageList.allCount}条记录
到第<input value="${requestScope.pageList.pageNo}" name="pn" id="pn_input"/>页
<input type="button" value="确定" id="gotoPage">
</div>