客户信息管理系统2—客户信息的增加(一)
四、系统具体的功能实现:
1、功能一: 客户信息的增加
(1)添加的流程
(2)客户信息添加过程中,防止表单F5刷新重复提交.
令牌机制 ,在访问JSP页面时,生成令牌号,将令牌号保存在Session中,同时将令牌号放入form的隐藏字段。在提交form 后,令牌号也会提交,在服务器端用请求中令牌号与Session中令牌号 比较,如果一致,说明请求有效,使用Session令牌号后,删除。
如果客户端提交令牌号 与 服务器端令牌号 不一致,说明非法请求(重复提交 )
详细看博文:防止表单重复刷新
(3)引入 jquery的日历控件:
即:点击生日输入框,即跳出日历,让客户进行选择年,月,日
本系统日历空间的js,css,图片代码结构
具体的js和css,以及图片,可以自己在网上下载:
http://sc.chinaz.com/jiaoben/170930414770.htm【但是,这个和我的js,css代码不同,效果类似】
引入日历控件写法
同时, 还需要 为 input输入项 生日 添加 一个 id=”birthday”
(4)如何去掉Myeclipse对JS等文件的验证
参考文章:如何去掉Myeclipse对JS等文件的验证
网址:
https://jingyan.baidu.com/article/ca41422fe094251eae99ede7.html
(5)实现代码
1.1代码组成
Customers + addCustomer.jsp+ CustomersServlet + CustomersService + CustomersDao+ CustomersDaoImplement + DaoFactory+dao.properties(dao相关配置文件)+
JdbcUtils(工具类) +c3p0-config.xml(连接池配置文件)
1.2代码功能介绍
【1】JdbcUtils(工具类) +c3p0-config.xml(连接池配置文件): JdbcUtils类,用于从c3p0中获取连接和得到数据库连接池的数据源
【2】Customers :是实体类,封装客户的信息
【3】addCustomer.jsp 是添加客户信息的页面
【4】CustomersServlet(web层): 是接收添加客户信息的页面传递过来的参数,并调用业务层:CustomersService的insert方法去执行添加客户信息操作,并把添加是否成功的信息返回给客户端
【5】CustomersService(业务层):是负责业务的处理,并把要操作的数据传递给dao层
【6】CustomersDao(dao层接口)+ CustomersDaoImplement(到层接口实现类) + DaoFactory(dao层工厂)++dao.properties(配置文件):
其中不直接写dao类的目的,而是写dao接口,然后再写dao接口的实现类,并写个dao工厂类:目的是为了解耦合操作
1.3解耦合介绍
解耦合
new对象—>工厂的静态方法【接口+配置文件+反射技术】
读取配置文件,得到对象实例。
好处:增强扩展性,方便代码的书写和维护
应用场景:某个模块不会写,可以自己定义一个接口,然后外包给其它人去实现,利用解耦合技术,然后集成进来实现好接口的类,再进行修改下配置文件,即可达成目的。
1.4代码详细
1.4.1 Customers(实体类)
packagecom.zhku.jsj144.zk.domain;
importjava.sql.Date;
//importjava.util.Date;
public class Customers {
private String id;
private String name;
private String gender;
private Date birthday;//特殊:Date类型
private String email;
private String cellphone;
private String preference;
private String type;
private String description;
public String getId() {
return id;
}
public void setId(String id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getGender() {
return gender;
}
public void setGender(String gender) {
this.gender = gender;
}
public Date getBirthday() {
return birthday;
}
public void setBirthday(Date birthday) {
this.birthday = birthday;
}
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
public String getCellphone() {
return cellphone;
}
public void setCellphone(String cellphone) {
this.cellphone = cellphone;
}
public String getPreference() {
return preference;
}
public void setPreference(String preference) {
this.preference = preference;
}
public String getType() {
return type;
}
public void setType(String type) {
this.type = type;
}
public String getDescription() {
return description;
}
public void setDescription(String description){
this.description = description;
}
@Override
public String toString() {
return "Customers [id=" + id + "]";
}
}
1.4.2 addCustomer.jsp(添加客户信息的页面)
<%@ page language="java" import="java.util.*"
contentType="text/html;charset=utf-8" pageEncoding="UTF-8"%>
<%
String path = request.getContextPath();
String basePath = request.getScheme() + "://"
+ request.getServerName() + ":" + request.getServerPort()
+ path + "/";
%>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
<head>
<base href="<%=basePath%>">
<title>My JSP 'addCustomer.jsp' starting page</title>
<meta http-equiv="pragma" content="no-cache">
<meta http-equiv="cache-control" content="no-cache">
<meta http-equiv="expires" content="0">
<meta http-equiv="keywords" content="keyword1,keyword2,keyword3">
<meta http-equiv="description" content="This is my page">
<!-- 路径问题:此种是错误的 -->
<!-- <script type="text/javascript" src="/js/jquery-1.7.1.min.js"></script> -->
<script type="text/javascript" src="js/jquery-1.7.1.min.js"></script>
<script type="text/javascript" src="js/jquery-ui-1.8.18.custom.min.js"></script>
<link href="css/jquery-ui-1.8.18.custom.css" rel="stylesheet" type="text/css"/>
<script type="text/javascript">
$(function(){
$("#birthday").datepicker({
minDate: new Date(1980, 0, 01),
maxDate: new Date(2020, 11, 31),
yearRange :'-40:+30',
changeMonth: true,
changeYear: true,
dateFormat: 'yy-mm-dd'
});
});
</script>
</head>
<h3>客户信息添加的页面</h3>
<body>
<!-- <font color="red">${msg }</font> -->
<%
//生成一个唯一的串
String token = UUID.randomUUID().toString();
session.setAttribute("token_session", token);//设置session
%>
<form action="${pageContext.request.contextPath }/CustomersServlet"
method="post">
<!-- <form action="/customer_system/CustomersServlet" method="post"> -->
<table>
<tr>
<td>名字</td>
<td><input type="text" name="name">
<!-- 设置token 的隐藏数值 -->
<input type="hidden" name="token" value="${token_session }">
</td>
</tr>
<tr>
<td>性别</td>
<td><input type="radio" name="gender" value="男">男 <input
type="radio" name="gender" value="女">女</td>
</tr>
<tr>
<td>生日</td>
<td><input type="text" name="birthday" id="birthday"></td>
</tr>
<tr>
<td>手机</td>
<td><input type="text" name="cellphone"></td>
</tr>
<tr>
<td>电子邮件</td>
<td><input type="text" name="email"></td>
</tr>
<tr>
<td>客户爱好</td>
<td><input type="checkbox" name="preference" value="上班">上班
<input type="checkbox" name="preference" value="工作">工作 <input
type="checkbox" name="preference" value="学习">学习 <input
type="checkbox" name="preference" value="睡觉">睡觉</td>
</tr>
<tr>
<td>客户类型</td>
<td><select name="type">
<option value="vip">vip</option>
<option value="黄金vip">黄金vip</option>
<option value="普通用户">普通用户</option>
<option value="超级vip">超级vip</option>
</select></td>
</tr>
<tr>
<td>备注</td>
<td><textarea rows="5" cols="30" name="description"></textarea></td>
</tr>
<tr>
<td colspan="2"><input type="submit" value="提交">
<input type="reset" value="重置"></td>
</tr>
</table>
</form>
</body>
</html>
1.4.3 CustomersServlet(web层)
package com.zhku.jsj144.zk.web;
import java.io.IOException;
import java.util.Arrays;
import java.util.Date;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.apache.commons.beanutils.BeanUtils;
import org.apache.commons.beanutils.ConvertUtils;
import org.apache.commons.beanutils.locale.converters.DateLocaleConverter;
import com.zhku.jsj144.zk.domain.Customers;
import com.zhku.jsj144.zk.service.CustomersService;
//添加客户信息
public class CustomersServlet extends HttpServlet {
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp)
throws ServletException, IOException {
//解决乱码问题
req.setCharacterEncoding("utf-8");
resp.setCharacterEncoding("text/html;charset=utf-8");
//防表单刷新的判断代码
//关键:带过来的参数值不会改变,但是带过来的session值被移除后就改变了,
//因此,通过对比参数值和session值,就可以知道是不是重复提交表单了
//注意:虽然一开始参数值token和session值session_token来源相同,
//但是,参数值一旦被保存,则不会改变,不论来源的值有什么变化,都不会改变。
//而session值则不同,一旦被移除后,则变为null,也因此可以通过对比参数和session值,从而知道表单是否刷新
//获得 带过来的隐藏域 中的值
String token = req.getParameter("token");
//获得之前存在 session 域 中的token 值
String token_session = (String) req.getSession().getAttribute("token_session");
req.getSession().removeAttribute("token_session");//移除session
//这样,第二次在访问同一个表单的时候,token_session的值就会为空
if(token!=null)
System.out.println("token:"+token);
if(token_session!=null)
System.out.println("token_session:"+token_session);
if(token==null||!token.equals(token_session)){
//就认为 是 重复刷新 提交 表单数据
req.setAttribute("msg", " 你在重复提交表单");
req.getRequestDispatcher("/failure.jsp").forward(req, resp);
return ;
}
Customers customers=new Customers();//对象
CustomersService customersService=new CustomersService();
//beanutils可以将属性类型自动转换成javaBean里的属性类型(只限于8种基本数据类型)
//想要将复杂类型的属性转换成其他型则需要注册一个转换器来实现
//转换器
// ConvertUtils.register(new DateLocaleConverter(), Date.class);
// String date=req.getParameter("birthday");
//1.获得传递过来的参数,进行封装【利用工具封装】
try {
BeanUtils.populate(customers, req.getParameterMap());//把获取到的参数封装到customers中
System.out.println(customers);
//对于爱好preference是多个值,那么使用beanutils封装时,会丢失数据,需要手动处理
String[] values=req.getParameterValues("preference");
if(values!=null){
String preference=Arrays.toString(values);//将数组变为字符串[上班,工作]
//进一步处理:将 [上班,工作] ---> 上班,工作
preference=preference.substring(1, preference.length()-1);
customers.setPreference(preference);//设置爱好
}
// System.out.println(customers.getName()+":"+customers.getGender());
//2.调用CustomersServervice的inser方法
int count = customersService.insert(customers);
//3.根据插入的结果情况,从而跳转不同的页面
if(count==1){
req.setAttribute("msg", " 恭喜你,注册成功");
req.getRequestDispatcher("/success.jsp").forward(req, resp);
}
else{
// req.getSession().setAttribute("msg", "注册失败,请重新注册");
// resp.sendRedirect("/customer_system/addCustomer.jsp");
req.setAttribute("msg", " 注册失败,请重新注册");
req.getRequestDispatcher("/failure.jsp").forward(req, resp);
}
} catch (Exception e) {
e.printStackTrace();
}
}
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp)
throws ServletException, IOException {
doGet(req, resp);
}
}
项目详细代码资源:
本人的github项目地址
https://github.com/Forever99/customer_system