[原创]java WEB学习笔记26:MVC案例完整实践(part 7)---修改的设计和实现
本博客为原创:综合 尚硅谷(http://www.atguigu.com)的系统教程(深表感谢)和 网络上的现有资源(博客,文档,图书等),资源的出处我会标明
本博客的目的:①总结自己的学习过程,相当于学习笔记 ②将自己的经验分享给大家,相互学习,互相交流,不可商用
内容难免出现问题,欢迎指正,交流,探讨,可以留言,也可以通过以下方式联系。
本人互联网技术爱好者,互联网技术发烧友
微博:伊直都在0221
QQ:951226918
-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
1.修改操作的思路:先显示页面,修改字段,提交表单,修改完成
1)index.jsp 查询
2)查询结果 中的 Update 超链接 <a href="editeCustomer.do?id=<%=customer.getId()%>">Update</a>
3)servlet 中的editeCustomer 通过 传入的 id号 进行查询 ,返回结果保存到 customer对象 ,转发到updatecustomer.jsp
4)在 updatecustomer.jsp 页面中显示所要修改的字段
5)填写提交字段 ,提交到 servlet中的 updateCustomer.do 中
6)先验证 name是否可以,若不可以,则通过转发的方式返回错误提示信息;若可以,则将提交的字段,封装为一个Customer对象,调用customerDAO.update(customer)方法处理更新
2.关键代码
1)index.jsp
1 <%@ page language="java" contentType="text/html; charset=UTF-8"
2 pageEncoding="UTF-8"%>
3
4 <%@ page import="com.jsaon.mvcapp.domain.Customer" %>
5 <%@ page import="java.util.List" %>
6
7 <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
8 <html>
9 <head>
10 <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
11 <title>mve_index</title>
12
13 <!-- 加入 jquery 库 -->
14 <script type="text/javascript" src="scripts/jquery-1.7.2.js"></script>
15 <script type="text/javascript">
16 $(function(){
17 //1.为删除操作添加 click事件
18 $(".delete").click(function(){
19 //2.获取a标签的父节点td,再获取td的父标签tr,再找到第二个td标签,也就是name节点,最后获取那么name节点的文本值
20 var content = $(this).parent().parent().find("td:eq(1)").text();
21 //3.确认。'是'则处理删除操作,'否'则不处理
22 var flag = confirm("确定要删除" + content + "的用户么?");
23 return flag;
24
25 });
26 });
27
28 </script>
29 </head>
30 <body>
31
32 <form action="query.do" method="post">
33 <table>
34 <tr>
35 <td>CustomerName:</td>
36 <td><input type="text" name="name"/></td>
37 </tr>
38 <tr>
39 <td>Address:</td>
40 <td><input type="text" name="address"/></td>
41 </tr>
42 <tr>
43 <td>Phone:</td>
44 <td><input type="text" name="phone"/></td>
45 </tr>
46 <tr>
47 <td><input type="submit" value="Query"/></td>
48 <td><a href="newcustomer.jsp">Add New Customer</a></td>
49 </tr>
50 </table>
51 </form>
52 <br><br>
53
54 <%
55 List<Customer> lists = (List<Customer>)request.getAttribute("list");
56 if(lists != null && lists.size() > 0 ){
57 %>
58 <hr>
59 <br><br>
60
61 <table border="1" cellpadding="10" cellspacing="0">
62 <tr>
63 <th>ID</th>
64 <th>CustomerName</th>
65 <th>Address</th>
66 <th>Phone</th>
67 <th>Update\Delete</th>
68 </tr>
69
70 <%
71 for(Customer customer : lists){
72 %>
73 <tr>
74 <td><%= customer.getId() %></td>
75 <td><%= customer.getName() %></td>
76 <td><%= customer.getAddress() %></td>
77 <td><%= customer.getPhone() %></td>
78 <td>
79 <a href="editeCustomer.do?id=<%=customer.getId()%>">Update</a>
80 <a href="deleteCustomer.do?id=<%= customer.getId() %>" class="delete">Delete</a>
81 </td>
82 </tr>
83
84 <%
85 }
86 %>
87
88
89 </table>
90 <%
91 }
92 %>
93
94 </body>
95 </html>
2)updatecustomer.jsp
1 <%@page import="com.jsaon.mvcapp.domain.Customer"%> 2 <%@ page language="java" contentType="text/html; charset=UTF-8" 3 pageEncoding="UTF-8"%> 4 <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd"> 5 <html> 6 <head> 7 <meta http-equiv="Content-Type" content="text/html; charset=UTF-8"> 8 <title>updatecustomer</title> 9 </head> 10 <body> 11 <%--可以用来回显 <%= request.getParameter("name") %> 若为空 则赋为 空串儿 ; 反之 ,赋原值 --%> 12 13 <h2><font color="red"><%=request.getAttribute("message") == null ? "" : request.getAttribute("message")%></font></h2> 14 15 <% 16 // 此步骤 避免了 nullPointerException 异常 ,即 从sevlet中未获取到 customer 17 String id = null; 18 String oldName = null; 19 String name = null; 20 String address = null; 21 String phone = null; 22 Customer customer = (Customer)request.getAttribute("customer"); 23 if(customer != null){ 24 //当从sevlet中的 updateCustomer 方法返回的customer 不为空,就用customer填充字段 25 id = customer.getId() + ""; 26 oldName = customer.getName(); 27 name = customer.getName(); 28 address = customer.getAddress(); 29 phone = customer.getPhone(); 30 } else{ 31 //customer 为空,则 id,oldName 为 32 id = request.getParameter("id"); 33 oldName = request.getParameter("oldName"); 34 name = request.getParameter("oldName"); 35 // address,phone 为请求参数, 通过转发 获取 36 address = request.getParameter("address"); 37 phone = request.getParameter("phone"); 38 39 } 40 %> 41 42 43 <form action="updateCustomer.do" method="post"> 44 <input type="hidden" name="id" value="<%= id %>"/> 45 <input type="hidden" name="oldName" value="<%= oldName %>"/> 46 <table> 47 <tr> 48 <td>CustomerName:</td> 49 <td><input type="text" name="name" 50 value="<%= name %>"/></td> 51 </tr> 52 <tr> 53 <td>Address:</td> 54 <td><input type="text" name="address" 55 value="<%= address %>"/></td> 56 </tr> 57 <tr> 58 <td>Phone:</td> 59 <td><input type="text" name="phone" 60 value="<%= phone %>"/></td> 61 </tr> 62 <tr> 63 <td colspan="2"><input type="submit" value="submit"/></td> 64 </tr> 65 </table> 66 </form> 67 68 </body> 69 </html>
3 )CustomerServlet2.java updateCustomer() , editeCustomer()
注意: updateCustomer 中的验证
1 private void updateCustomer(HttpServletRequest request, HttpServletResponse response)
2 throws ServletException, IOException {
3 System.out.println("update");
4 request.setCharacterEncoding("UTF-8");
5
6 //1.获取请求信息:id,name,address,phone,oldName
7
8 //1.1 隐藏域的 值
9 String idStr = request.getParameter("id");
10 String oldNameStr = request.getParameter("oldName");
11
12 //1.2 提交的值
13 String nameStr = request.getParameter("name");
14 String addressStr = request.getParameter("address");
15 String phoneStr = request.getParameter("phone");
16
17 //2.验证name 是否可用
18 //通过equalsIgnoreCase() 方式 避免了 大小写的问题。equals 方法区分大小写, 而数据库SQL 不区分大小写
19 if(!oldNameStr.equalsIgnoreCase(nameStr)){
20 //2.1 先比较name 和 oldName 是否相同,若相同,说明name 可用
21 //2.2 若不相同,则调用CustomerDAO 的getCostomerWithName(String name) 获取 name 在数据库中是否存在
22 long rel = customerDAO.getCountWithName(nameStr);
23 //2.2.1 若存在,则返回值大于 0,则响应 updatecustomer.jsp 页面:通过转发的方式
24 if(rel > 0){
25 // 进行回显字符串,在request 中放入一个属性 message:用户名 name
26 // 回显:updatecustomer.jsp 的表单值可以回显
27 // value="<%= request.getParameter("name") == null ? "" : request.getParameter("name") %>" 进行回显
28 // 注意:name 显示的是 oldName,而address 和 phone 显示的是新的
29 request.setAttribute("message", "用户名 " + nameStr + " 已经被占用了,请重新选择!");
30 //2.2.2 存在,要求在updatecustomer.jsp 页面显示一条消息:用户名 name 已经被占用了,请重新选择
31 request.getRequestDispatcher("/updatecustomer.jsp").forward(request,response);
32 // 2.2.3 结束方法:return
33 return;
34 }
35 }
36
37 //3.通过验证后,则将表单封装为一个Customer 对象 customer
38 Customer customer = new Customer(nameStr, addressStr, phoneStr);
39 customer.setId(Integer.parseInt(idStr));
40
41 //4.调用CustomerDAO 的save(Customer customer) 执行更新操作
42 customerDAO.update(customer);
43
44 //5.重定向到 query.do
45 response.sendRedirect("query.do");
46
47 }
48
49 private void editeCustomer(HttpServletRequest request,
50 HttpServletResponse response) throws ServletException, IOException {
51 System.out.println("edit");
52 String forwardPath = "/error.jsp";
53 //1. 获取请求参数id
54 String idStr = request.getParameter("id");
55 int id = Integer.parseInt(idStr);
56 try {
57 //2. 调用CustomerDAO 的get(id) 方法,获取 和id 对应的Customer 对象
58 Customer customer = customerDAO.get(id);
59 if(customer != null){
60 forwardPath ="/updatecustomer.jsp";
61 //3. 将 customer 放入 request 中
62 request.setAttribute("customer", customer);
63 }
64 } catch (Exception e) {}
65 //4. 响应updatecustomer.jsp 页面: 转发的形式
66 request.getRequestDispatcher(forwardPath).forward(request, response);
67
68 }
4)error.jsp
1 <%@ page language="java" contentType="text/html; charset=UTF-8"
2 pageEncoding="UTF-8"%>
3 <!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
4 <html>
5 <head>
6 <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
7 <title>error page</title>
8 </head>
9 <body>
10 <h1> 页面出错了</h1>
11 </body>
12 </html>
5)CustomerDAO 中的 update() 的声明
1 //更新操作
2 public void update(Customer customer);
6)CustomerDAOJdbcImpl 中 update 的实现
1 @Override
2 public void update(Customer customer) {
3 String sql = "UPDATE customers SET name = ?, address = ?, phone = ? WHERE id = ?";
4 update(sql, customer.getName(), customer.getAddress(), customer.getPhone(), customer.getId());
5 }
总结:
1.表单的回显(了解):
<td><input type="text" name="name"
value="<%= request.getParameter("name") == null ? "" : request.getParameter("name") %>"/></td>
2.验证
1)id一般都使用 隐藏域 <input type="hidden" name="id" value="<%= id %>"/>
2)修改中的复杂验证,若某一字段在数据库表中不允许重复的解决方案
①在表单中使用隐藏域保存该字段的原始信息值:<input type="hidden" name="oldName" value="<%= oldName %>"/>
②同时在Servlet 中同时获取原始值和新提交的值:若一致,则通过;若不 一致,则用使用新提交的值去查询数据库表。返回有记录,则提示错误信息或者页面;范围无记录,则可以执行修改
1 if(!oldNameStr.equalsIgnoreCase(nameStr)){
2 20 //2.1 先比较name 和 oldName 是否相同,若相同,说明name 可用
3 21 //2.2 若不相同,则调用CustomerDAO 的getCostomerWithName(String name) 获取 name 在数据库中是否存在
4 22 long rel = customerDAO.getCountWithName(nameStr);
5 23 //2.2.1 若存在,则返回值大于 0,则响应 updatecustomer.jsp 页面:通过转发的方式
6 24 if(rel > 0){
7 25 // 进行回显字符串,在request 中放入一个属性 message:用户名 name
8 26 // 回显:updatecustomer.jsp 的表单值可以回显
9 27 // value="<%= request.getParameter("name") == null ? "" : request.getParameter("name") %>" 进行回显
10 28 // 注意:name 显示的是 oldName,而address 和 phone 显示的是新的
11 29 request.setAttribute("message", "用户名 " + nameStr + " 已经被占用了,请重新选择!");
12 30 //2.2.2 存在,要求在updatecustomer.jsp 页面显示一条消息:用户名 name 已经被占用了,请重新选择
13 31 request.getRequestDispatcher("/updatecustomer.jsp").forward(request,response);
14 32 // 2.2.3 结束方法:return
15 33 return;
16 34 }
17 35 }
3)在修改状态下,若验证没有通过,表单的回显问题。通用的原则
不允许重复的字段要给予提示,但字段中的显示旧的字段值,允许修改,则改为新的字段的值。通过Ajax 会有更好的用户体验。
3.response.sendRedirect()方法可以防止表单的重复提交