构建开发环境
导入需要用到的开发包
- servlet-api.jar
- jstl-1.2.jar
- standard-1.1.2.jar
建立程序开发包

设计实体
书籍实体
public class Book { private String id; private String name; private String author; private String description; private double price; public Book(){ } public Book(String id,String name,String author,String description,double price){ this.id=id; this.name=name; this.author=author; this.description=description; this.price=price; } @Override public String toString() { return "Book{" + "id='" + id + '\'' + ", name='" + name + '\'' + ", author='" + author + '\'' + ", description='" + description + '\'' + ", price=" + price + '}'; } 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 getAuthor() { return author; } public void setAuthor(String author) { this.author = author; } public String getDescription() { return description; } public void setDescription(String description) { this.description = description; } public double getPrice() { return price; } public void setPrice(double price) { this.price = price; } }
购物项实体
public class CartItem { private Book book; private int quantity; private double price;//该购物项的价钱等于书的数量*书的单价 public Book getBook() { return book; } public void setBook(Book book) { this.book = book; } public int getQuantity() { return quantity; } public void setQuantity(int quantity) { this.quantity = quantity; } //书的价钱*数量 public double getPrice() { return this.quantity*this.book.getPrice(); } public void setPrice(double price) { this.price = price; } }
购物车实体
public class Cart { //关键字是书籍的id,只是购物项 private Map<String, CartItem> items = new LinkedHashMap<>(); //购物车总价 private double price; //把购物项(用户传递进来的书籍)加入购物车里面,也应该是购物车的功能 public void addBook(Book book) { CartItem cartItem = items.get(book.getId()); //判断购物车是否存在该购物项 if (cartItem == null) { //如果不存在,则创建这个购物项对象 cartItem=new CartItem(); //将用户传递过来的书籍作为购物项 cartItem.setBook(book); //把该购物项的数量设置为1 cartItem.setQuantity(1); //把购物项加入到购物车 items.put(book.getId(),cartItem); }else{ //如果存在该购物项,则将购物项的数量加1 cartItem.setQuantity(cartItem.getQuantity()+1); } } public Map<String, CartItem> getItems() { return items; } public void setItems(Map<String, CartItem> items) { this.items = items; } //购物车的总价就是所有购物项的价钱加起来 public double getPrice() { double totalPrice=0d; if(items!=null){ for(Map.Entry entry:items.entrySet()){ //得到每个购物项 CartItem cartItem = (CartItem)entry.getValue(); //将购物项的钱加起来,就是购物车的总价 totalPrice+=cartItem.getPrice(); } } return totalPrice; } public void setPrice(double price) { this.price = price; } }
数据库
直接用集合模拟数据库
public class BookDB { private static Map<String, Book> map=new LinkedHashMap<>(); static { map.put("1",new Book("1","java","jack","good",75.5)); map.put("2",new Book("2","spring mvc","tom","not good",35.5)); map.put("3",new Book("3","javaweb","jerry","very good",100)); map.put("4",new Book("4","spring boot","john","just so so",50)); } public static Map<String,Book> getAll(){ return map; } }
开发dao
public class BookDao { //获取存放着书籍的Map集合 public Map getAll(){ return BookDB.getAll(); } //根据关键字获取某本书籍 public Book find(String id){ return BookDB.getAll().get(id); } public void buyBook(String id, Cart cart){ Book book = find(id); cart.addBook(book); } public void deleteBook(String id,Cart cart) throws CartNotFoundException{ if(cart==null){ throw new CartNotFoundException("购物车已为空"); } cart.getItems().remove(id); } public void clearCart(Cart cart){ cart.getItems().clear(); } public void updateQuantity(String id,int quantity,Cart cart){ cart.getItems().get(id).setQuantity(quantity); } }
开发service
service层就是对DAO层的一个封装
public class BookService { private BookDao bookDao = new BookDao(); public Map getAll() { return bookDao.getAll(); } public Book find(String id) { return bookDao.find(id); } public void buyBook(String id, Cart cart) { bookDao.buyBook(id, cart); } public void deleteBook(String id, Cart cart) throws CartNotFoundException { bookDao.deleteBook(id, cart); } public void clearCart(Cart cart){ bookDao.clearCart(cart); } public void updateQuantity(String id,int quantity,Cart cart){ bookDao.updateQuantity(id,quantity,cart); } }
开发web
列出所有的书
开发提供JSP页面的Servlet
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { BookServiceDao bookService=new BookServiceImpl(); Map<String, Book> books = bookService.getAll(); request.setAttribute("books",books); request.getRequestDispatcher("/WEB-INF/ListAllBook.jsp").forward(request,response); }
开发显示所有书籍的jsp
<%@ page contentType="text/html;charset=UTF-8" language="java" %> <%@taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %> <html> <head> <title>显示所有的书籍</title> </head> <body> ${pageContext.request.contextPath} <table border="1px"> <tr> <td>书籍编号</td> <td>书名</td> <td>作者</td> <td>描述</td> <td>单价</td> <td>购买</td> </tr> <c:forEach items="${books}" var="me"> <tr> <td>${me.key}</td> <td>${me.value.name}</td> <td>${me.value.author}</td> <td>${me.value.description}</td> <td>${me.value.price}</td> <td><a href="${pageContext.request.contextPath}/BuyServlet?bookId=${me.key}"/>购买 </td> </tr> </c:forEach> </table> </body> </html>
效果:

购买操作
开发处理购买的Servlet
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { //获取得到传递过来的id String id = request.getParameter("bookId"); //把用户想要买的书放到购物上 //用户不单单只有一个,要让购物车上只为当前的用户服务,就需要用到会话跟踪技术了 Cart cart = (Cart) request.getSession().getAttribute("cart"); //如果当前用户还没有点击购买的商品,那么用户的购物车就是空的 if (cart == null) { cart = new Cart(); request.getSession().setAttribute("cart", cart); } //调用BussinessService的方法,实现购买功能 BookService bookService = new BookService(); bookService.buyBook(id, cart); //跳转到购物车显示的页面上 request.getRequestDispatcher("/WEB-INF/ListCart.jsp").forward(request, response); }
购物车的页面
<%@ page contentType="text/html;charset=UTF-8" language="java" %> <%@taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %> <html> <head> <title>购物车页面显示</title> <script type="text/javascript"> function updateQuantity(obj,id,oldValue) { var quantity= obj.value; if(confirm("确定要修改数量?")){ window.location.href="${pageContext.request.contextPath}/UpdateQuantity?bookId="+id+"&quantity="+quantity; }else{ obj.value=oldValue; } } </script> </head> <%--empty函数是判断集合中有没有元素--%> <%--如果购物车没有任何购物项--%> <c:if test="${empty(cart.items)}"> <h1>您还有购买过任何书籍</h1> </c:if> <%--如果购物车有购物项,就显示购物项--%> <c:if test="${!empty(cart.items)}"> <table border="1px"> <tr> <td>书籍编号</td> <td>名称</td> <td>数量</td> <td>小计</td> <td>操作</td> </tr> <c:forEach items="${cart.items}" var="me"> <tr> <td>${me.key}</td> <td>${me.value.book.name}</td> <td><input type="text" value="${me.value.quantity}" onchange="updateQuantity(this,${me.key},${me.value.quantity})"/> </td> <td>${me.value.price}</td> <td><a href="${pageContext.request.contextPath}/DeleteCartBook?bookId=${me.key}">删除</a> </td> </tr> </c:forEach> <tr> <td colspan="2"><a href="${pageContext.request.contextPath}/ClearCart" onclick="return confirm('确定要清空购物车?');">清空购物车</a> </td> <td colspan="2">合计</td> <td>${cart.price}</td> </tr> </table> </c:if> <body> </body> </html>
效果:

删除操作
开发删除功能的Servlet
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { try { //获取得到用户想要删除的那本书的id String id = request.getParameter("bookId"); //获取该用户相对应的购物车对象 Cart cart = (Cart) request.getSession().getAttribute("cart"); //删除购物车的商品 BookService bookService = new BookService(); bookService.deleteBook(id, cart); //删除购物车的商品后,也应该直接跳转回去购物车的显示页面 request.getRequestDispatcher("/WEB-INF/ListCart.jsp").forward(request, response); } catch (CartNotFoundException e) { request.setAttribute("message", "购物车空了"); request.getRequestDispatcher("/WEB-INF/Message.jsp").forward(request, response); } catch (Exception e) { e.printStackTrace(); request.setAttribute("message", "删除出现异常,待会再试"); request.getRequestDispatcher("/WEB-INF/Message.jsp").forward(request, response); } } }
效果:

修改数量
购物车上,数量的值改成输入框,写javascript代码,监控着输入框的变动,如果有变动,就响应事件,将变动的数据传递给服务器,更新数据。(见前面代码)
编写修改数量的Servlet
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { //获取用户想要修改数量的书的id String id=request.getParameter("bookId"); //获取修改的数量 int quantity=Integer.parseInt(request.getParameter("quantity")); //得到当前用户的购物车 Cart cart =(Cart) request.getSession().getAttribute("cart"); //调用BusinessService的方法去修改对应的数据 BookService bookService = new BookService(); bookService.updateQuantity(id,quantity,cart); //修改完再跳转回去购物车的页面中 request.getRequestDispatcher("/WEB-INF/ListCart.jsp").forward(request,response); } }
效果:

清空购物车
首先通过javascript代码询问用户是否要清空,如果要清空就跳转到相对应的Servlet中把购物车的数据清空了。(见前面页面)
开发清空购物车的Servlet
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { //得到用户相对应的购物车 BookService bookService = new BookService(); //调用相对应BusinessService的方法 Cart cart =(Cart) request.getSession().getAttribute("cart"); if(cart==null){ cart=new Cart(); request.getSession().setAttribute("cart",cart); } //清空购物车 bookService.clearCart(cart); request.getRequestDispatcher("/WEB-INF/ListCart.jsp").forward(request,response); } }
效果:

总结:
- 购物车的应该是一个以id作为key,以购物项作为value的一个Map集合。这样在显示商品的时候,就不会重复显示同一种类型的商品。
- 购物项代表该商品,并且应该给予购物项数量和价钱的属性。购物项的价钱应该是数量*单价。
- 购物车应该提供把商品添加到购物车的功能。当然,购物项代表着商品,所以首先要判断该购物车是否有同类的商品,如果有,直接在购物项的数量上加1即可;如果没有,就设置该购物项的属性,并把购物项添加到购物车中。
- 购物车的总价就是所有购物项的总价。
- 无论增删改查购物车的数据,其实就是操作这个集合。
posted on
浙公网安备 33010602011771号