尚硅谷书城项目-基于Java

0.需求分析

画出数据库的ER图

在这里插入图片描述

1.新建项目-登录功能实现

1.1创建各个POJO类

在这里插入图片描述

1.2配置xml文件

 <?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd"
         version="4.0">
    <context-param>
        <param-name>view-prefix</param-name>
        <param-value>/WEB-INF/pages/</param-value>
    </context-param>
    <context-param>
        <param-name>view-suffix</param-name>
        <param-value>.html</param-value>
    </context-param>
    <context-param>
        <param-name>contextConfigLocation</param-name>
        <param-value>applicationContext.xml</param-value>
    </context-param>
</web-app>

在这里插入图片描述
如图pages在WEB-INF中的pages文件的user下,所以在配置xml文件时,前缀view-prefix就是/WEB-INF/pages/,后缀依然是.html
而在配置服务器运行时打开的URL就是在这里插入图片描述

1.3 配置applicationContext.xml

<beans>

    <bean id="page" class="com.atguigu.myssm.myspringmvc.PageController"/>
</beans>

1.4 配置login.html文件

<!DOCTYPE html>
<html xmlns:th="http://www.thymeleaf.org">
  <head>
    <meta charset="UTF-8">
    <title>尚硅谷会员登录页面</title>
    <link type="text/css" rel="stylesheet" th:href="@{/static/css/style.css}">
  </head>
  <body>
    <div id="login_header">
      <a href="../index.html">
        <img class="logo_img" alt="" th:src="@{/static/img/logo.gif}">
      </a>
    </div>

    <div class="login_banner">
      <div id="l_content">
        <span class="login_word">欢迎登录</span>
      </div>

      <div id="content">
        <div class="login_form">
          <div class="login_box">
            <div class="tit">
              <h1>尚硅谷会员</h1>
            </div>
            <div class="msg_cont">
              <b></b>
              <span class="errorMsg">请输入用户名和密码</span>
            </div>
            <div class="form">
            这里变成 th:th:action="@{/user.do}" method="post"
             <form th:action="@{/user.do}" method="post">
             还需添加一个隐藏域,用于调用
                <input type="hidden" name="operate" value="login">
                <label>用户名称:</label>
                <input class="itxt" type="text" placeholder="请输入用户名" autocomplete="off" tabindex="1" name="uname" id="username">
                <br>
                <br>
                <label>用户密码:</label>
                <input class="itxt" type="password" placeholder="请输入密码" autocomplete="off" tabindex="1" name="pwd" id="password">
                <br>
                <br>
                <input type="submit" value="登录" id="sub_btn">
              </form>
              <div class="tit">
                <a href="regist.html">立即注册</a>
              </div>
            </div>
          </div>
        </div>
      </div>
    </div>
    <div id="bottom">
      <span>
        尚硅谷书城.Copyright ©2015
      </span>
    </div>
  </body>
</html>

1.5编写Controller层的UserController

如果要编写UserController层的,实现用户的功能。
先从底层的DAO层开始做起,先创建UserDAO接口,我们现在是实现登录功能,所以只需先添加一个getUser方法。

public interface UserDAO {
    User getUser(String uname, String pwd);
}

再创建它的实现类UserDAOImpl,同样的,实现登录功能,那么我们就查询数据库中是否有这条数据

public class UserDAOImpl extends BaseDAO<User> implements UserDAO {
    @Override
    public User getUser(String uname, String pwd) {
        return load("select * from t_user where uname like ?,and pwd like ?",uname,pwd);
    }
}

之后我们在Service层中处理登录的需求,

public interface UserService {
    User getUser(String uname,String pwd);
}
public class UserServiceImpl implements UserService {
    private UserDAO userDAO;
    @Override
    public User getUser(String uname, String pwd) {
        return userDAO.getUser(uname, pwd);
    }
}

接着在UserController中调用登录所需要实现的操作

public class UserController {
    private UserService userService;
    public String login(String uname, String pwd, HttpSession session){

        User user =userService.getUser(uname,pwd);
        return "index";
    }
}

继续在applicationContext.xml中进行注入


<beans>
    <bean id="page" class="com.atguigu.myssm.myspringmvc.PageController"/>


    <!-- DAO -->
    <bean id="userDAO" class="com.atguigu.book.dao.Impl.UserDAOImpl"/>

    <!-- Service -->
    <bean id="userService" class="com.atguigu.book.service.Impl.UserServiceImpl">
        <property name="userDAO" ref="userDAO" />
    </bean>

    <!-- controller -->
    <bean id="user" class="com.atguigu.book.controller.UserController">
        <property name="userService" ref="userService" />
    </bean>


</beans>

2.首页展示图书列表

书城预览图
如图展示的图书列表

2.1创建BookDAO层以及DAO层的实现类

public interface BookDAO {
    List<Book> getBookList();
}
public class BookDAOImpl extends BaseDAO<Book> implements BookDAO {

    @Override
    public List<Book> getBookList() {
        return executeQuery("select * from t_book");
    }
}

2.2创建BookService以及BookService的实现类

public interface BookService {
    List<Book> getBookList();
}
public class BookServiceImpl implements BookService {

    private BookDAO bookDAO;
    @Override
    public List<Book> getBookList() {
        return bookDAO.getBookList();
    }
}

那么此时我们就可以写BookService类来调用BookService的实现方法了,但是在书城的使用中,登录成功后,页面需要跳转到书城首页面,所以我们需要对UserController进行改进,改进如下

public class UserController {
    private UserService userService;
    public String login(String uname, String pwd, HttpSession session){

        User user =userService.getUser(uname,pwd);
        if (user != null) {
            session.setAttribute("currUser",user);
            //如果登录成功,跳转到书城首页面
            return "redirect:book.do?operate=index";//如若此时operate=index没有写,那么还是会跳转到index,因为在Dispatcher中定义了如果operate值为空,那么默认跳转到index
        }
		//如果登录失败,还是登录页面
        return "user/login";
    }
}

配置.xml文件

<beans>
    <bean id="page" class="com.atguigu.myssm.myspringmvc.PageController"/>


    <!-- DAO -->
    <bean id="userDAO" class="com.atguigu.book.dao.Impl.UserDAOImpl"/>
    <bean id="bookDAO" class="com.atguigu.book.dao.Impl.BookDAOImpl"/>
    
    <!-- Service -->
    <bean id="userService" class="com.atguigu.book.service.Impl.UserServiceImpl">
        <property name="userDAO" ref="userDAO" />
    </bean>
    <bean id="bookService" class="com.atguigu.book.service.Impl.BookServiceImpl">
        <property name="bookDAO" ref="bookDAO" />
    </bean>

    <!-- controller -->
    <bean id="user" class="com.atguigu.book.controller.UserController">
        <property name="userService" ref="userService" />
    </bean>
    <bean id="book" class="com.atguigu.book.controller.BookController">
        <property name="bookService" ref="bookService" />
    </bean>


</beans>

既然成功跳转到index页面,那么我们就要对index页面进行改造,使之成为上面的书城列表样式

<div class="list-content">
              <div class="list-item" th:each="book : ${session.bookList}" th:object="${book}">
                <img th:src="@{|/static/uploads/*{bookImg}|}" alt="">
                <p th:text="|书名:*{bookName}|">书名:活着</p>
                <p th:text="|作者:*{author}|">作者:余华</p>
                <p th:text="|价格:¥*{price}|">价格:¥66.6</p>
                <p th:text="|销量:*{salCount}|">销量:230</p>
                <p th:text="|库存:*{bookCount}|">库存:1000</p>
                <button>加入购物车</button>
              </div>

登陆后界面如图所示:
在这里插入图片描述

3.添加图书到购物车中

3.1登录后右上角登录状态的显示

登录前为:
在这里插入图片描述

<div class="topbar-right" th:if="${session.currUser==null}">
            <a href="user/login.html" class="login">登录</a>
            <a href="user/regist.html" class="register">注册</a>
            <a href="cart/cart.html" class="cart iconfont icon-gouwuche">
              购物车
              <div class="cart-num">3</div>
            </a>
            <a href="manager/book_manager.html" class="admin">后台管理</a>
          </div>

登录后为:
在这里插入图片描述

 <div class="topbar-right" th:unless="${session.currUser==null}">
            <!--          登录后风格-->
            <span>欢迎你<b th:text="${session.currUser.uname}">张总</b></span>-->
            <a href="#" class="register">注销</a>
            <a href="pages/cart/cart.jsp" class="cart iconfont icon-gouwuche" >
              购物车
              <div class="cart-num">3</div>
            </a>
            <a href="./pages/manager/book_manager.html" class="admin">后台管理</a>
          </div>

3.2添加图书到购物车中

3.2.1点击时,调用js方法addCart

<div class="list-item" th:each="book : ${session.bookList}" th:object="${book}">
                <img th:src="@{|/static/uploads/*{bookImg}|}" alt="">
                <p th:text="|书名:*{bookName}|">书名:活着</p>
                <p th:text="|作者:*{author}|">作者:余华</p>
                <p th:text="|价格:¥*{price}|">价格:¥66.6</p>
                <p th:text="|销量:*{salCount}|">销量:230</p>
                <p th:text="|库存:*{bookCount}|">库存:1000</p>
                <button th:onclick="|addCart(*{id})|">加入购物车</button>
              </div>

JS方法:

function addCart(bookId) {
        window.location.href = 'cart.do?operate=addCart&bookId=' + bookId;
}

其中cart.do意义为需要有对应的CartController,operate=addCart是为了在CartController中得有一个addCart的方法,bookId=bookId是在addController中得有一个参数为bookId。

3.2.2创建CartController类,分析业务逻辑:

														将制定的图书添加到当前用户的购物车中
       													 1.如果当前用户的购物车中已经存在这个图书了,那么将购物车的图书的数量+1
       													 2.否则,在我的购物车中新增这个图书的CartItem,数量是1

3.2.3 创建CartItemDAO接口并实现此方法

public interface CartItemDAO {
    void addCartItem(CartItem cartItem);
    void updateCartItem(CartItem cartItem);
}
public class CartItemDAOImpl extends BaseDAO<CartItem> implements CartItemDAO {
    @Override
    public void addCartItem(CartItem cartItem) {
        executeUpdate("insert into t_cart values(0,?,?,?)",cartItem.getBook(),cartItem.getBuyCount(),cartItem.getUserBean().getId());
    }

    @Override
    public void updateCartItem(CartItem cartItem) {
        executeUpdate("update t_cart set buyCount = ? where id = ?",cartItem.getBuyCount(),cartItem.getId());
    }
}

3.2.4 创建CartItemService接口及其实现方法

public interface CartItemService {
    void addCartItem(CartItem cartItem);
    void updateCartItem(CartItem cartItem);
    void addOrUpdateCartItem(CartItem cartItem, Cart cart);
}

那么此时CartController中的1.如果当前用户的购物车中已经存在这个图书了,那么将购物车的图书的数量+1
2.否则,在我的购物车中新增这个图书的CartItem,数量是1
被封装到ServiceImpl中,在开发过程中,发现如果有POJO类中有一个Cart购物车实体类的话,对于代码的简洁性,降低冗余性都有好处,(因为在封装图书的数量加1和新增图书的详情封装到一个方法时,必须要有一个Cart实体)所以我们加入Cart类:

public class Cart {
    private Map<Integer,CartItem> cartItemMap;      //购物车中购物车项的集合,Map集合中的Key是Book的id,用来判断如果添加的图书的id等于key中的Integer,那么就用add方法,而不是update
    private Integer totalCount;                     // 购物车中购物项的数量,请注意,是几项,而不是几件
    private Double totalMoney;                      //购物车的总金额

    public Cart() {
    }

    public Map<Integer, CartItem> getCartItemMap() {
        return cartItemMap;
    }

    public void setCartItemMap(Map<Integer, CartItem> cartItemMap) {
        this.cartItemMap = cartItemMap;
    }

    public Integer getTotalCount() {
        totalCount = 0 ;
        if (cartItemMap != null && cartItemMap.size() > 0) {
            totalCount = cartItemMap.size();
        }
        return totalCount;
    }

    public void setTotalCount(Integer totalCount) {
        this.totalCount = totalCount;
    }

    public Double getTotalMoney() {
        totalMoney = 0.0;
        if (cartItemMap != null && cartItemMap.size() > 0) {
            Set<Map.Entry<Integer, CartItem>> entries = cartItemMap.entrySet();//entrySet就是entrySet是java中的Map接口的一个方法,用于返回映射中包含的键-值对的Set视图。如若不熟练可使用values
            for (Map.Entry<Integer,CartItem> cartItemEntry : entries) {
                CartItem cartItem = cartItemEntry.getValue();//getValue就是从Map.Entry<Integer,CartItem>中获取得到cartItem
                 totalMoney += cartItem.getBook().getPrice() * cartItem.getBuyCount();
            }
        }
        return totalMoney;
    }

    public void setTotalMoney(Double totalMoney) {
        this.totalMoney = totalMoney;
    }
}
public class CartItemServiceImpl implements CartItemService {
    private CartItemDAO cartItemDAO;
    @Override
    public void addCartItem(CartItem cartItem) {
        cartItemDAO.addCartItem(cartItem);
    }

    @Override
    public void updateCartItem(CartItem cartItem) {
        cartItemDAO.updateCartItem(cartItem);
    }

    @Override
    public void addOrUpdateCartItem(CartItem cartItem, Cart cart) {
        //判断当前用户的<购物车>是否有这本书的CartItem,有 则 update,没有 则 add
        if (cart != null) {
            Map<Integer, CartItem> cartItemMap = cart.getCartItemMap();
            if (cartItemMap == null) {
                cartItemMap = new HashMap<>();
            }
            if (cartItemMap.containsKey(cartItem.getBook().getId())){//获取主键,看是否包含此书
                CartItem cartItemTemp = cartItemMap.get(cartItem.getBook().getId());//如果包含
                cartItemTemp.setBuyCount(cartItemTemp.getBuyCount() + 1);
                updateCartItem(cartItemTemp);
            }else {
                addCartItem(cartItem);
            }
        }else {//没有购物车的情况
            addCartItem(cartItem);
        }
    }
}

DAO层,Service层都完成后,该到Controller层,继续补全CarterController

public class CartController {
    private CartItemService cartItemService;
    public String addCart(Integer bookId){
            //将指定的图书添加到当前用户的购物车中
            //1.如果当前用户的购物车中已经存在这个图书了,那么将购物车的图书的数量+1
            //2.否则,在我的购物车中新增这个图书的CartItem,数量是1
        //cartItemService.addOrUpdateCartItem(cartitem,cart);
    }
}

但是当我们在考虑补全CartController时,cartItemService.addOrUpdateCartItem(cartitem,cart);中的cartitem和cart从哪里获取?
重新思考业务逻辑时,对于用户没有登录时,也能直接访问首页,首页中也有购物车的选项

3.2.5 (插曲)用户未登录和登录状态下右上角都有购物车栏

照例从DAO层开始做起:
在这里插入图片描述
实现此方法:
在这里插入图片描述
Service中实现业务逻辑的调用:
在这里插入图片描述
具体的实现方法:
在这里插入图片描述
上图写完后,就要回到Controller层写了,那么在未登录和登录时都要能够显示完整的功能,所以购物车CartItemService就要放在UserController中,
在这里插入图片描述
需要注意的时,我们在初创User类时,里面并没有Cart属性,所以还得到User中添加上Cart属性并且添加get和set方法
在这里插入图片描述

3.2.6在CartController中 将指定的图书添加到当前用户的购物车中

完成上面一步插曲之后,我们继续将指定的图书添加到当前用户的购物车中,
在这里插入图片描述
在applicationContext.xml中注入配置

<beans>
    <bean id="page" class="com.atguigu.myssm.myspringmvc.PageController"/>


    <!-- DAO -->
    <bean id="userDAO" class="com.atguigu.book.dao.Impl.UserDAOImpl"/>
    <bean id="bookDAO" class="com.atguigu.book.dao.Impl.BookDAOImpl"/>
    <bean id="cartItemDAO" class="com.atguigu.book.dao.Impl.CartItemDAOImpl"/>


    <!-- Service -->
    <bean id="userService" class="com.atguigu.book.service.Impl.UserServiceImpl">
        <property name="userDAO" ref="userDAO" />
    </bean>
    <bean id="bookService" class="com.atguigu.book.service.Impl.BookServiceImpl">
        <property name="bookDAO" ref="bookDAO" />
    </bean>
    <bean id="cartItemService" class="com.atguigu.book.service.Impl.CartItemServiceImpl">
        <property name="cartItemDAO" ref="cartItemDAO"/>
    </bean>

    <!-- controller -->
    <bean id="user" class="com.atguigu.book.controller.UserController">
        <property name="userService" ref="userService" />
        <property name="cartItemService" ref="cartItemService"/>
    </bean>
    <bean id="book" class="com.atguigu.book.controller.BookController">
        <property name="bookService" ref="bookService" />
    </bean>
    <bean id="cart" class="com.atguigu.book.controller.CartController">
        <property name="cartItemService" ref="cartItemService"/>
    </bean>

</beans>

到这一步,我们完成了添加图书到购物者的功能,Debug运行,如果报异常,在完成添加或者更新图书的方法处添加断点进行debug即可。
下一步开发展示购物车详情页面。

4.展示购物车详情页面

本业务逻辑为:在首页点击加入购物车后,跳转到购物车的界面 ,那么我们在CartController中添加index方法
在这里插入图片描述
对cart.html进行动态渲染

<!DOCTYPE html>
<html lang="en" xmlns:th="http://www.thymeleaf.org">
  <head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
    <link rel="stylesheet" th:href="@{/static/css/minireset.css}">
    <link rel="stylesheet" th:href="@{/static/css/common.css}">
    <link rel="stylesheet" th:href="@{/static/css/cart.css}">
  </head>
  <body>
    <div class="header">
      <div class="w">
        <div class="header-left">
          <a th:href="@{/index.html}">
            <img src="../../static/img/logo.gif" alt=""></a>
          <h1>我的购物车</h1>
        </div>
        <div class="header-right">
          <h3>欢迎<span th:text="${session.currUser.uname}">张总</span>光临尚硅谷书城</h3>
          <div class="order"><a href="../order/order.html">我的订单</a></div>
          <div class="destory"><a href="../index.html">注销</a></div>
          <div class="gohome">
            <a href="../index.html">返回</a>
          </div>
        </div>
      </div>
    </div>
    <div class="list">
      <div class="w">
        <table>
          <thead>
            <tr>
              <th>图片</th>
              <th>商品名称</th>
              <th>数量</th>
              <th>单价</th>
              <th>金额</th>
              <th>操作</th>
            </tr>
          </thead>
          <tbody>
            <tr th:each="cartItem : ${session.currUser.cart.cartItemMap.values()}">
              <td>
                <img th:src="@{|/static/uploads/${cartItem.book.bookImg}|}" alt="">
              </td>
              <td th:text="${cartItem.book.bookName}">活着</td>
              <td>
                <span class="count">-</span>
                <input class="count-num" type="text" th:value="${cartItem.buyCount}">
                <span class="count">+</span>
              </td>
              <td th:text="${cartItem.book.price}">36.8</td>
              <td th:text="${cartItem.book.price * cartItem.buyCount}">36.8</td>
              <td><a href="">删除</a></td>
            </tr>
          </tbody>
        </table>
        <div class="footer">
          <div class="footer-left">
            <a href="#" class="clear-cart">清空购物车</a>
            <a href="#">继续购物</a>
          </div>
          <div class="footer-right">
            <div><span th:text="${session.currUser.cart.totalBookCount}">3</span>件商品</div>
            <div class="total-price">总金额<span th:text="${session.currUser.cart.totalMoney}">99.9</span></div>
            <a class="pay" href="checkout.html">去结账</a>
          </div>
        </div>
      </div>
    </div>
    <div class="bottom">
      <div class="w">
        <div class="top">
          <ul>
            <li>
              <a href="">
                <img src="../../static/img/bottom1.png" alt="">
                <span>大咖级讲师亲自授课</span>
              </a>
            </li>
            <li>
              <a href="">
                <img src="../../static/img/bottom.png" alt="">
                <span>课程为学员成长持续赋能</span>
              </a>
            </li>
            <li>
              <a href="">
                <img src="../../static/img/bottom2.png" alt="">
                <span>学员真是情况大公开</span>
              </a>
            </li>
          </ul>
        </div>
        <div class="content">
          <dl>
            <dt>关于尚硅谷</dt>
            <dd>教育理念</dd>
            <!-- <dd>名师团队</dd>
            <dd>学员心声</dd> -->
          </dl>
          <dl>
            <dt>资源下载</dt>
            <dd>视频下载</dd>
            <!-- <dd>资料下载</dd>
            <dd>工具下载</dd> -->
          </dl>
          <dl>
            <dt>加入我们</dt>
            <dd>招聘岗位</dd>
            <!-- <dd>岗位介绍</dd>
            <dd>招贤纳师</dd> -->
          </dl>
          <dl>
            <dt>联系我们</dt>
            <dd>http://www.atguigu.com</dd>
            <dd></dd>
          </dl>
        </div>
      </div>
      <div class="down">
        尚硅谷书城.Copyright ©2015
      </div>
    </div>
  </body>
</html>

运行后,添加商品到购物车中,跳转到的页面情况如下:在这里插入图片描述
报错信息:org.thymeleaf.exceptions.TemplateProcessingException: Exception evaluating OGNL expression: “session.currUser.cart.totalMoney” (template: “cart/cart” - line 66, col 47)
进行Debug,在Cart中的getTotalMoney处打上断点,往下一步步调试可在控制台看到
在这里插入图片描述
为什么会只是查到了book的ID呢?因为CartController在调用CartService时,CartServiceImpl中的getCart方法,在这里插入图片描述
此方法调用cartItemDAO.getCartItemsList时,
在这里插入图片描述

仅仅是得到了cartIteam的id,buyCount,book(外键为书的id),以及Userbean。
所以 为了得到完成的CartItem属性(包括id,buyCount,UserBean以及Book(book包括了书名,作者,售价,书籍图片等等)),我们在CartItemService接口中添加新的方法:在这里插入图片描述
实现此方法:
在这里插入图片描述
在BookService层中实现getBook业务逻辑的方法
在这里插入图片描述
在这里插入图片描述
在DAO层中实现对getBook的具体操作
在这里插入图片描述
如此步骤执行完成以后,CartController中就得到了完整的属性,
在这里插入图片描述
随后我们在applicationContext.xml中注入属性即可。
功能展示:在这里插入图片描述

5.结账功能

先分析完成结账功能所需要的功能:

  1. 订单表(Order)添加一条记录(订单记录,集成了所有的订单项
  2. 订单详情表(OrderItem)添加n条记录(OrderItem类中的属性)
  3. 购物车项表(Cart)中需要删除对应的n条记录(删除购物车中的购物车项)
    注:n为用户购物车的购物车项数量
    创建DAO层,完成结账功能,需要有两个DAO类,添加到数据库中不同的表中,一个添加到订单表中,另一个添加到订单详情表中
    在这里插入图片描述
public class OrderDAOImpl extends BaseDAO<OrderBean> implements OrderDAO {
 @Override
 public void addOrderBean(OrderBean orderBean) {
     int orderBeanId = executeUpdate("insert into t_order values(0,?,?,?,?,?)",orderBean.getOrderNo(),orderBean.getOrderDate(),orderBean.getOrderMoney(),orderBean.getOrderStatus(),orderBean.getUSER());
     orderBean.setId(orderBeanId);
     //在BaseDAO中执行insert操作会返回一个值。
     //思考:为什么要设置orderBeanId的值
 }
}

在这里插入图片描述

public class OrderItemDAOImpl extends BaseDAO<OrderItem> implements OrderItemDAO {
    //订单详情表添加n条记录
    @Override
    public void addOrderItem(OrderItem orderItem) {
        executeUpdate("insert into t_order_detail values (0,?,?,?)",orderItem.getBook().getId(),orderItem.getBuyCount(),orderItem.getOrderBean().getId());
    }
}

完成DAO层的创建后,我们进行Service层的创建
在这里插入图片描述
在这里插入图片描述
在初次开发时,我们往订单详情表中添加记录,但是请注意,此时的orderBean中的OrderItem是空的(如下图)!所以无法添加到订单详情表中
在这里插入图片描述
那么解决的思维为:从User类得到的Cart类,再从Cart类中得到cartItemMap,用foreach遍历得出购物车中的数据对应订单详情表的每个数据,然后用DAO方法添加到数据库中
在这里插入图片描述
然后Debug
在这里插入图片描述
点击去结账后,跳转回index首页
在这里插入图片描述
到数据库中查看
在这里插入图片描述
在这里插入图片描述
均已完成各自的功能。
出现的错误
后来检查时发现,数据库中的订单钱数返回为0,经过Debug之后,发现是在OrderController中
在这里插入图片描述
改完后的代码:
在这里插入图片描述
在这里插入图片描述

6.我的订单-计算订单数量

在索引界面点击购物车后,进入购物车界面
在这里插入图片描述
在这里插入图片描述

去index.html中将购物车的超链接跳转地址改动到CartConteoller中的index方法即可
在这里插入图片描述
cart.do就是意味着跳转到CartController中,operate默认的就是index(因为在myssm中写了如果operate为空,那么默认赋值operate为index)。
完成此功能后,我们还需点击购物车后右上角的我的订单跳转到我的订单页面在这里插入图片描述
点击进入:在这里插入图片描述
为了能有如图的功能,我们在OrderController添加getOrderList方法,
在这里插入图片描述
并且在执行完成后跳转到我的订单页面。
那按照惯例,我们从DAO层的开发开始,创建getOrderBeanList方法并实现在这里插入图片描述
在这里插入图片描述

接着在Service层创建方法并实现
在这里插入图片描述
在这里插入图片描述
然后补全OrderController中的方法
在这里插入图片描述
retuen到order.html中后,我们需要对order中的代码用thymeleaf进行更改
在这里插入图片描述
其实此时对于数据库的第三范式来说这一步并不规范,但是为了提高开发速度,我们只能这么做,要不然另一种方法太繁琐。
在这里插入图片描述
如图在Order表中创建了一列,那么我们在POJO类中需要完善属性
在这里插入图片描述
所以在往数据库中的Order表中添加数据时,还多需要添加一个orderBookCount,那么我们对OrderDAOImpl中的addOrderBean方法进行修改

public class OrderDAOImpl extends BaseDAO<OrderBean> implements OrderDAO {
    @Override
    public void addOrderBean(OrderBean orderBean) {
        int orderBeanId = executeUpdate("insert into t_order values(0,?,?,?,?,?,?)",orderBean.getOrderNo(),orderBean.getOrderDate(),orderBean.getOrderMoney(),orderBean.getOrderStatus(),orderBean.getUSER().getId(),orderBean.getUSER().getCart().getTotalBookCount());
        orderBean.setId(orderBeanId);
        //在BaseDAO中执行insert操作会返回一个值。
        //思考:为什么要设置orderBeanId的值
    }

    @Override
    public List<OrderBean> getOrderBeanList(User user) {
        return executeQuery("select * from t_order where USER=?",user.getId());
    }
}

那么此时在getOrderBeanList中就可以得到完整的数据了,在order.html中添加
在这里插入图片描述
这下就得到了完整的订单表
在这里插入图片描述

7.编辑购物车

功能说明:在购物车中点击"+" 和"-" 号能够对购买的书籍数量进行更改
在这里插入图片描述

6.1在cart.html中进行修改

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

6.2在CartController中补全editCart方法

在这里插入图片描述

8.金额精度问题

在这里插入图片描述
在商品的单价后有小数后,会出现如此的问题,这是因为数据类型为Double的原因,要解决此问题:link

7.1解决商品的金额显示问题

在CartItem类中声明属性:
在这里插入图片描述
xj的get方法:
在这里插入图片描述
接着将前端cart.html的小计的值改为cartItem.xj即可
在这里插入图片描述

7.2解决总金额的显示问题

在Cart中对着原有的getTotalMoney进行修改:
在这里插入图片描述
完成上述两步骤后,购物车中的金额显示bug得以解决
在这里插入图片描述

9.合法用户验证过滤器的添加

在com.atguigu下创建一个包z_book.filters中创建一个类SessionFilters

**@WebFilter(urlPatterns = {"*.do","*.html"},
        initParams = {
            @WebInitParam(name = "bai",
                    value = "/pro24/page.do?operate=page&page=user/login,/pro24/user.do?null")
        }
)
public class SessionFilter implements Filter {
    List<String> baiList = null;
    @Override
    public void init(FilterConfig filterConfig) throws ServletException {
        String bai = filterConfig.getInitParameter("bai");
        String[] baiArr = bai.split(",");
        baiList = Arrays.asList(baiArr);
    }

    @Override
    public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
        HttpServletRequest request = (HttpServletRequest)servletRequest;
        HttpServletResponse response = (HttpServletResponse) servletResponse;

        //
        //System.out.println("request.getRequestURI() = " + request.getRequestURI());
        //System.out.println("request.getQueryString() = " + request.getQueryString());


        String uri = request.getRequestURI();
        String queryString = request.getQueryString();
        String str = uri + "?" + queryString;
        if (baiList.contains(str)) {
            filterChain.doFilter(request,response);
        }else {
            HttpSession session = request.getSession();
            Object currUserObj = session.getAttribute("currUser");

            if (currUserObj == null) {
                response.sendRedirect("page.do?operate=page&page=user/login");
            }else {
                filterChain.doFilter(request,response);
            }
        }
    }

    @Override
    public void destroy() {

    }
}

10.验证码

11.注册页面的表单认证

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值