java web 实训 store 功能的介绍

store 商城:

权限管理系统:最少需要五张表,角色,权限、用户 ,用户——角色,权限——角色,

准备工作:

  1. lntellj idea 的软件
  2. jdk 1.8 开发换件
  3. Tomcat (9.0)
  4. MySQL 5.7 版本
  5. 谷歌浏览器
  6. jar 坐标图
<?xml version="1.0" encoding="UTF-8"?>

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
  <modelVersion>4.0.0</modelVersion>

  <groupId>org.example</groupId>
  <artifactId>store</artifactId>
  <version>1.0-SNAPSHOT</version>
  <packaging>war</packaging>

  <name>store Maven Webapp</name>
  <!-- FIXME change it to the project's website -->
  <url>http://www.example.com</url>

  <properties>
    <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
    <maven.compiler.source>1.8</maven.compiler.source>
    <maven.compiler.target>1.8</maven.compiler.target>
  </properties>

  <dependencies>
    <!--单元测试-->
    <dependency>
      <groupId>junit</groupId>
      <artifactId>junit</artifactId>
      <version>4.13</version>
      <scope>test</scope>
    </dependency>

    <!--数据库驱动包-->
    <dependency>
      <groupId>mysql</groupId>
      <artifactId>mysql-connector-java</artifactId>
      <version>5.1.47</version>
    </dependency>

    <!--选择数据源-->
    <dependency>
      <groupId>com.alibaba</groupId>
      <artifactId>druid</artifactId>
      <version>1.1.14</version>
    </dependency>

    <!--导入工具类 : 1.commons-dbutils-->
    <dependency>
      <groupId>commons-dbutils</groupId>
      <artifactId>commons-dbutils</artifactId>
      <version>1.6</version>
    </dependency>

    <dependency>
      <groupId>org.apache.commons</groupId>
      <artifactId>commons-lang3</artifactId>
      <version>3.1</version>
    </dependency>

    <dependency>
      <groupId>commons-beanutils</groupId>
      <artifactId>commons-beanutils</artifactId>
      <version>1.9.2</version>
    </dependency>

    <!-- 依赖包: 日志包-->
    <dependency>
      <groupId>commons-logging</groupId>
      <artifactId>commons-logging</artifactId>
      <version>1.2</version>
    </dependency>

    <!-- 导入 servlet 的坐标-->
    <dependency>
      <groupId>javax.servlet</groupId>
      <artifactId>javax.servlet-api</artifactId>
      <version>4.0.1</version>
    </dependency>

    <dependency>
      <groupId>javax.servlet.jsp</groupId>
      <artifactId>javax.servlet.jsp-api</artifactId>
      <version>2.3.3</version>
    </dependency>

    <!-- 导入标准标签库-->
    <dependency>
      <groupId>org.apache.taglibs</groupId>
      <artifactId>taglibs-standard-impl</artifactId>
      <version>1.2.5</version>
    </dependency>

    <dependency>
      <groupId>org.apache.taglibs</groupId>
      <artifactId>taglibs-standard-spec</artifactId>
      <version>1.2.5</version>
    </dependency>

    <!--文件上传 下载-->
    <dependency>
      <groupId>commons-io</groupId>
      <artifactId>commons-io</artifactId>
      <version>2.5</version>
    </dependency>

    <dependency>
      <groupId>commons-fileupload</groupId>
      <artifactId>commons-fileupload</artifactId>
      <version>1.4</version>
    </dependency>

    <!--  邮箱的依赖   -->
    <dependency>
      <groupId>javax.mail</groupId>
      <artifactId>mail</artifactId>
      <version>1.4.7</version>
    </dependency>
  </dependencies>


</project>

项目的大致运行

java web 实训 store 功能的介绍_第1张图片

store 简绍

这个写的是从用户方面考量所写的一个模拟网上购物的部分功能:
1.网上购物,必须有商品,用户才可以买,
所以可定有一张商品的表,用了商品,用户过来才可以卖,所以肯定用一张用户表,(若用户与商品有某种关系的,就需要另建一张外键关系表把用户和商品链接起来

2。用户必须进入这个网站才可以买东西,应进行注册,然后登陆上用户自己的账号,进入主页,主页什么也有,应用的全部查询,当用户明确自己想要什么,可以进行收搜,采用的通过名字进行查询,名字被赋予的id是唯一的进行查询,或者用户大致收搜,采用模胡查询,由于商品比较多,采用分页展示,应用分页功能,当用户选中商品,加入购物车,具有添加商品的功能呢,或者不需,只是不小心点进了购物车,就具备删除商品,从购物车里减去这个用户不要的商品,当用户选完自己想要的东西,准备付钱的时候,页面,就有单价,数量,总价,商品的图片,等因为用户准确无误的计数出购买所有商品的总价格,一扫描,输入用户自己密码就支付成功,买完东西,或者不需在登陆了,就应该有退出的功能。

分类功能简绍

java web 实训 store 功能的介绍_第2张图片

商品功能的简绍

java web 实训 store 功能的介绍_第3张图片

用户功能简绍

java web 实训 store 功能的介绍_第4张图片

页面功能简绍

java web 实训 store 功能的介绍_第5张图片

代码
一 、 分类

1.分类的实体类

package cn.javabs.store.entity;

/**
 *  类别
 */
public class Category {

    private String cname;  // 名称

    private  Integer cid;  // 编号
    public Category() {
        super();
    }

    public Category(Integer cid, String cname) {
        this.cid = cid;
        this.cname = cname;
    }



    @Override
    public String toString() {
        return "Category{" +
                "cid=" + cid +
                ", cname='" + cname + '\'' +
                '}';
    }

    public Integer getCid() {
        return cid;
    }

    public void setCid(Integer cid) {
        this.cid = cid;
    }

    public String getCname() {
        return cname;
    }

    public void setCname(String cname) {
        this.cname = cname;
    }


}

2.分类dao实现类

package cn.javabs.store.dao.impl;

import cn.javabs.store.dao.CategoryDao;
import cn.javabs.store.entity.Category;
import cn.javabs.store.util.DruidUtil;
import org.apache.commons.dbutils.QueryRunner;
import org.apache.commons.dbutils.handlers.BeanHandler;
import org.apache.commons.dbutils.handlers.BeanListHandler;

import java.sql.SQLException;
import java.util.List;

/**
 *  类别 Dao s实现类
 */
public class CategoryDaoImpl implements CategoryDao {

    /**
     *  准备 QueryRunner
     *  因为 QueryRunner 的参数
     */
  QueryRunner queryRunner =  new QueryRunner(DruidUtil.getDataSource());

    /**
     *  查询全部类目
     *          查询所有是需要两个参数
     *          1.字符串 类型 sql 语句
     *          2. ResultSetHandler (结果集处理器)对象
     *          是一个接口 ,无法new 则无法接口对象
     *          实现类
     *                  BeanListHandler (类)
     *                  需要字节码
     * @return
     */
    @Override
    public List<Category> findAll() {
        try {
            List<Category> list = queryRunner.query("select cid,cname from category ", new BeanListHandler<Category>(Category.class));
            return list;
        } catch (SQLException e) {
            throw new RuntimeException(e);
        }

    }

    /**
     * 指定全部类目
     * @param id
     * @return
     */
    @Override
    public Category findById(Integer id) {

        try {
            Category category = queryRunner.query("select cid,cname from category where cid =? ", new BeanHandler<Category>(Category.class), id);
            return category;
        } catch (SQLException e) {
            throw new RuntimeException(e);
        }

    }

    /**
     * 添加类目
     * @param category
     * @return
     */
    @Override
    public int add(Category category) {
        try {
          int num =  queryRunner.update("insert  into category(cid,cname)value (null,?)",category.getCname());
          return num;
        } catch (SQLException e) {
            throw new RuntimeException(e);
        }

    }

    /**
     * 修改类目
     * @param category
     * @return
     */
    @Override
    public int update(Category category) {
        try {
           int num = queryRunner.update("update category set cname=? where cid=? ",
                   category.getCname(),
                   category.getCid()
                   );
            return num;
        } catch (SQLException e) {
            throw new RuntimeException(e);
        }

    }

    /**
     *  删除类目
     * @param id
     * @return
     */
    @Override
    public int delById(Integer id) {
        try {
            int num = queryRunner.update("delete  from category where cid=?", id);
            return num;
        } catch (SQLException e) {
            throw new RuntimeException(e);
        }

    }
}

  1. 分类的dao
package cn.javabs.store.dao;

import cn.javabs.store.entity.Category;

import java.util.List;

public interface CategoryDao {
    /**
     *  查询全部类目
     * @return
     */
    List<Category> findAll();

    /**
     *  指定查询类目
     * @param id
     * @return
     */
    Category findById(Integer id);

    /**
     * 添加类目
     * @param category
     * @return
     */
    int add(Category category);

    /**
     * 修改类目
     * @param category
     * @return
     */
    int update(Category category);

    /**
     *  删除类目
     * @param id
     * @return
     */
    int delById(Integer id);
}

  1. 分类的service 实现类
package cn.javabs.store.service.impl;

import cn.javabs.store.dao.CategoryDao;
import cn.javabs.store.dao.impl.CategoryDaoImpl;
import cn.javabs.store.entity.Category;
import cn.javabs.store.service.CategoryService;

import java.util.List;

/**
 *  业务逻辑层实现类设计
 */
public class CategoryServiceImpl implements CategoryService {

    // 创建Dao  层的对象进行 此类 调用 dao 类的方法
   CategoryDao categoryDao =new CategoryDaoImpl();


    /**
     * 查询全部类目
     * @return
     */
    @Override
    public List<Category> findAllCategories() {
       List<Category> categoryList= categoryDao.findAll();
        return categoryList;
    }

    /**
     * 指定查询类目
     *
     * @param id
     * @return
     */
    @Override
    public Category findCategoryById(Integer id) {
       Category category = categoryDao.findById(id);
        return category;
    }

    /**
     * 添加类目
     *
     * @param category
     * @return
     */
    @Override
    public int addCategory(Category category) {
       int number = categoryDao.add(category);
        return number;
    }

    /**
     * 修改类目
     *
     * @param category
     * @return
     */
    @Override
    public int editCategory(Category category) {
     int number =  categoryDao.update(category);
        return number;
    }

    /**
     * 删除类目
     *
     * @param id
     * @return
     */
    @Override
    public int delCategory(Integer id) {
      int number = categoryDao.delById(id);
        return number;
    }
}

  1. 分类service
package cn.javabs.store.service;


import cn.javabs.store.entity.Category;

import java.util.List;

/**
 *  类别接口
 */
public interface CategoryService {

    /**
     * 查询全部   List 用的是单列集合 可以存放相同的元素、 存入与取出的顺序一样  ,可以放入相同的数据
     *              set 存取顺序不一样    不可放入相同的数据
     *              数组的大小是固定的
     *              集合是可扩展的
     *      多行数据类型 返回的是 集合(每一个对象是独立的个体,泛型规定返回的类型 对象)
     *
     * @return
     */
   public List<Category> findAllCategories();

    /**
     *  指定查询类目
     * @param id
     * @return
     */
    public Category  findCategoryById(Integer id);

    /**
     * 添加类目
     * @param category
     * @return
     */
    public  int addCategory(Category category);

    /**
     *  修改类目
     * @param category
     * @return
     */
    public int editCategory(Category category);

    /**
     * 删除类目
     * @param id
     * @return
     */
    public  int delCategory(Integer id);
}

分类 Servlet

package cn.javabs.store.servlet;

import cn.javabs.store.entity.Category;
import cn.javabs.store.service.CategoryService;
import cn.javabs.store.service.impl.CategoryServiceImpl;

import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.util.List;

/**
 *  类目的Servlet
 */
@WebServlet( "/categoryServlet")
public class CategoryServlet extends HttpServlet {
    CategoryService categoryService  = new CategoryServiceImpl();

    Category category = new Category();

    public void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
            doGet(request,response);
        }

    public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
         // 设置 编码 解决乱码的问题 通过字符编码过滤器
            //  在 本方法内进行调用如下分类操作的方法
            // 去接受index 。jsp 页面的参数
        String methodName = request.getParameter("methodName");
        if("addCategory".equals(methodName)){
            addCategory(request,response);
        }else if("delCategory".equals(methodName)){
            delCategory(request,response);
        }else if("addCategory".equals(methodName)){
            addCategory(request,response);
        }else if("editCategory".equals(methodName)){
            editCategory(request,response);
        }else if("findAllCategories".equals(methodName)) {
            findAllCategories(request, response);
        }else if("editCategoryView".equals(methodName)){
            editCategoryView(request,response);
        }else {
            System.out.println("方法不存在,请您仔细合查方法");
        }

    }

    /**
     *  数据回显
     * @param request
     * @param response
     * @throws ServletException
     * @throws IOException
     */
    private void editCategoryView(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        String cid = request.getParameter("cid");
        System.out.println("edit");
        int id = Integer.parseInt(cid);
        Category  category = categoryService.findCategoryById(id);
        if (category!=null){
            request.setAttribute("category",category);
            request.getRequestDispatcher("editCategory.jsp").forward(request,response);
        }else {
            response.getWriter().write("修改失败");
        }
//        List categoryList = categoryService.findAllCategories();
//        if(category != null){
//          request.setAttribute("data",category);
//         if (categoryList.size() > 0 && categoryList != null){
//             request.setAttribute("list","categoryList");
//         }
//          request.getRequestDispatcher("categoryList.jsp").forward(request,response);
//      }else {
//          request.setAttribute("data","修改失败");
//          request.getRequestDispatcher("/message.jsp").forward(request,response);
//      }
    }

    /**
     *  查询全部
     * @param request
     * @param response
     * @throws ServletException
     * @throws IOException
     */
    public  void findAllCategories(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        List<Category> categoryList = categoryService.findAllCategories();
        System.out.println("因为查询index.jsp查询的方法,内容是:"+categoryList);
        request.setAttribute("list",categoryList);
        request.getRequestDispatcher("/categoryList.jsp").forward(request,response);
    }

    /**
     *  根据id指定查询
     * @param request
     * @param response
     * @throws ServletException
     * @throws IOException
     */
    public  void findById(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        Category category = categoryService.findCategoryById(2);
        System.out.println(category);

    }

    /**
     * 添加分类
     * @param request
     * @param response
     * @throws ServletException
     * @throws IOException
     */
    public  void addCategory(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
            // 接受参数
        String cname = request.getParameter("cname");
        category.setCid(null);// 数据库自动生成
        category.setCname(cname);
        int rowNumber = categoryService.addCategory(category);
        if(rowNumber >0){
            System.out.println("添加成功");
        }else {
            System.out.println("添加失败");
        }


    }

    /**
     *  修改分类
     * @param request
     * @param response
     * @throws ServletException
     * @throws IOException
     */
    public  void editCategory(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        String cid = request.getParameter("cid");
        String cname = request.getParameter("cname");
        int id = Integer.parseInt(cid);
        category.setCid(id);
        category.setCname(cname);
        int rowNumber = categoryService.editCategory(category);
        if(rowNumber >0){
            System.out.println("修改成功");
            response.getWriter().write("修改成功");
        }else {
            System.out.println("修改失败");
        }

    }

    /**
     *  删除分类
     * @param request
     * @param response
     * @throws ServletException
     * @throws IOException
     */
    public  void delCategory(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {

        String cid = request.getParameter("cid");
        int id = Integer.parseInt(cid);
        int rowNumber = categoryService.delCategory(3);
        if(rowNumber > 0){
            System.out.println("删除成功");
        }else {
            System.out.println("删除失败");
        }

    }
}

<%--
  Created by IntelliJ IDEA.
  User: love
  Date: 2020/5/26
  Time: 9:50
  To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<c:set var="ctx" value="${pageContext.request.contextPath}"></c:set>
<html>
<head>
    <title>分类的列表</title>

</head>
<style>
    a:link{
        text-decoration: none;
        color: black;
    }
    a:hover{
        text-decoration: underline;
        color: red;
    }
    .cate-box{
        margin: 10px auto;
    }
    .add-cate-box{
        text-align: center;
    }
</style>
<body>
        <span class="add-cate-box">
            <form action="${ctx}/categoryServlet?methodName=addCategory" method="post">
                <input type="text" name="cname" placeholder="请填写类别名称..." style="line-height:30px;width: 484px"/>
                <input type="submit" value="添加类目">
            </form>
        </span>
        <span class="add-cate-box">
            <form action="${ctx}/categoryServlet?methodName=editCategory&cid=${data.cid}" method="post">
                <input type="text" name="cname" value="${data.cname}" placeholder="请填写新的类别名称..." style="line-height:30px;width: 484px"/>
                 <input type="submit" value="修改类目">
            </form>
        </span>
    <table class="cate-box" border="1px" width="600px" cellpadding="0" cellspacing="0">
        <thead>
        <tr>
            <th>
                <input type="checkbox">
            </th>
            <th>编号</th>
            <th>名称</th>
            <th>操作</th>
        </tr>
        </thead>
        <c:forEach var="c" items="${list}">
            <tr align="center">
                <td>
                    <input type="checkbox">
                </td>
                <td>${c.cid}</td>
                <td>${c.cname}</td>
                    <td>
                        <a href="${ctx}/categoryServlet?methodName=editCategoryView&cid=${c.cid}">修改</a>
                        <a href="${ctx}/categoryServlet?methodName=delCategory&cid=${c.cid}">删除</a>
                    </td>
            </tr>
        </c:forEach>
    </table>
</body>
</html>

修改分类:

<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<%--
  Created by IntelliJ IDEA.
  User: love
  Date: 2020/5/28
  Time: 22:02
  To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<c:set value="${pageContext.request.contextPath}" var="ctx"></c:set>
<html>
<head>
    <title>修改分类</title>
</head>
<body>
<form action="${ctx}/categoryServlet?methodName=editCategory&cid=${category.cid}" method="post">
    分类名称:<input type="text" name="cname" value="${category.cname}">
    <input type="submit" value="修改">
</form>
</body>
</html>

二 、商品

1.商品的实体类

package cn.javabs.store.entity;

/**
 *  手机的实体类
 */
public class Phone {

    private Integer pid; // 商品编号

    private  String pname;  //  商品名称

    private  String pdescription;  // 商品描述

    private  double price; // 单间

    private  Integer stock; // 库存

    //  商品图片= 商品名称 + 商品路径
    private  String photopath;
    private  String photoName;

    public Phone() {
        super();
    }

    @Override
    public String toString() {
        return "Phone{" +
                "pid=" + pid +
                ", pname='" + pname + '\'' +
                ", pdescription='" + pdescription + '\'' +
                ", price=" + price +
                ", stock=" + stock +
                ", photopath='" + photopath + '\'' +
                ", photoName='" + photoName + '\'' +
                ", category=" + category +
                '}';
    }

    public Phone(Integer pid, String pname, String pdescription, double price, Integer stock, String photopath, String photoName, Category category) {
        this.pid = pid;
        this.pname = pname;
        this.pdescription = pdescription;
        this.price = price;
        this.stock = stock;
        this.photopath = photopath;
        this.photoName = photoName;
        this.category = category;
    }

    public Integer getPid() {
        return pid;
    }

    public void setPid(Integer pid) {
        this.pid = pid;
    }

    public String getPname() {
        return pname;
    }

    public void setPname(String pname) {
        this.pname = pname;
    }

    public String getPdescription() {
        return pdescription;
    }

    public void setPdescription(String pdescription) {
        this.pdescription = pdescription;
    }

    public double getPrice() {
        return price;
    }

    public void setPrice(double price) {
        this.price = price;
    }

    public Integer getStock() {
        return stock;
    }

    public void setStock(Integer stock) {
        this.stock = stock;
    }

    public String getPhotopath() {
        return photopath;
    }

    public void setPhotopath(String photopath) {
        this.photopath = photopath;
    }

    public String getPhotoName() {
        return photoName;
    }

    public void setPhotoName(String photoName) {
        this.photoName = photoName;
    }

    public Category getCategory() {
        return category;
    }

    public void setCategory(Category category) {
        this.category = category;
    }

    private  Category category; // 分类


}

  1. 商品的dao 实体类
package cn.javabs.store.dao.impl;

import cn.javabs.store.dao.PhoneDao;
import cn.javabs.store.entity.Category;
import cn.javabs.store.entity.Phone;
import cn.javabs.store.util.DruidUtil;
import org.apache.commons.dbutils.BasicRowProcessor;
import org.apache.commons.dbutils.QueryRunner;
import org.apache.commons.dbutils.handlers.BeanHandler;
import org.apache.commons.dbutils.handlers.BeanListHandler;
import org.apache.commons.dbutils.handlers.MapListHandler;
import org.apache.commons.dbutils.handlers.ScalarHandler;

import java.sql.SQLException;
import java.util.List;
import java.util.Map;

/**
 *  商品 接口的实现类设计
 */
public class PhoneDaoImpl implements PhoneDao {

    QueryRunner queryRunner = new QueryRunner(DruidUtil.getDataSource());
    /**
     * 添加商品
     *
     * @param phone
     * @return
     */
    @Override
    public int addPhone(Phone phone) {
        try {
            int number = queryRunner.update("insert into phone (pname,pdescription,price,stock,photopath,photoname,cid) values (?,?,?,?,?,?,?) ",
                    phone.getPname(),
                    phone.getPdescription(),
                    phone.getPrice(),
                    phone.getStock(),
                    phone.getPhotopath(),
                    phone.getPhotoName(),
                    phone.getCategory().getCid());
            return number;
        } catch (SQLException e) {
            throw new RuntimeException(e);
        }
    }

    /**
     * 删除商品
     *
     * @param pid
     * @return
     */
    @Override
    public int delPhone(Integer pid) {
        try {
            int number = queryRunner.update("delete  from phone where pid = ?", pid);
            return number;
        } catch (SQLException e) {
            throw new RuntimeException(e);
        }

    }

    /**
     * 修改商品
     *
     * @param phone
     * @return
     */
    @Override
    public int updatePhone(Phone phone) {
        try {
            int number = queryRunner.update("update phone set pname=?,pdescription=?,price=?,stock=?,photopath=?,photoName=?,cid=? where pid=?",
                    phone.getPname(),
                    phone.getPdescription(),
                    phone.getPrice(),
                    phone.getStock(),
                    phone.getPhotopath(),
                    phone.getPhotoName(),
                    phone.getCategory().getCid(),
                    phone.getPid());
            return number;
        } catch (SQLException e) {
            throw new RuntimeException(e);
        }
    }



    /**
     * 指定id 查询
     *
     * @param pid
     * @return
     */
    @Override
    public Phone findPhoneById(Integer pid) {
        try {
            Phone phone = queryRunner.query("select pid,pname,pdescription,price,stock,photopath,photoName,cid from phone where pid=?", new BeanHandler<Phone>(Phone.class), pid);
            return phone;

        }catch (SQLException e) {
            throw new RuntimeException(e);
        }

    }

//    /**
//     * 查询所有商品 (参数有两个)
//     *
//     * @param starIndex
//     * @param pageSize
//     * @return
//     */
//    @Override
//    public List> findPhoneAll(int starIndex, int pageSize) {
//        try {
//            String sql ="select p.*,c.cname from phone,category c where.cid=c.cid limit 10,5";
//            List> list = queryRunner.query(sql, new MapListHandler(new BasicRowProcessor(), starIndex, pageSize));
//            return list;
//        } catch (SQLException e) {
//            throw new RuntimeException(e);
//        }
//    }

    /**
     * 查询所有商品 (参数有两个)
     *
     * @param starIndex
     * @param pageSize
     * @return
     */
    @Override
    public List<Phone> findPhoneAll(int starIndex, int pageSize) {
        try {
            List<Phone>    list = queryRunner.query("select * from  phone limit ?,?", new BeanListHandler<Phone>(Phone.class),starIndex,pageSize);
            return list;
        } catch (SQLException e) {
            throw new RuntimeException(e);
        }

    }


    /**
     * 查询总条数(数据共有几条数据)
     *
     * @return
     */
    @Override
    public int findTotalItems() {
        try {
            Long longNumber = queryRunner.query("select count(*) from phone", new ScalarHandler<>(1));
            int number = longNumber.intValue();
            return number;
        } catch (SQLException e) {
            throw new RuntimeException(e);
        }
    }

    /**
     * 分类分页查询
     *
     * @param startIndex
     * @param pageSize
     * @param cid
     * @return
     */
    @Override
    public List<Phone> findCategoryAndPhoneBYPage(int startIndex, int pageSize, Integer cid) {
        try {
            List<Phone> list = queryRunner.query("select * from  phone where cid = ? limit ?,?",
                    new BeanListHandler<Phone>(Phone.class),cid, startIndex,pageSize);
            return list;
        } catch (SQLException e) {
            throw new RuntimeException(e);
        }
    }


}

3 .商品的dao

package cn.javabs.store.dao;

import cn.javabs.store.entity.Phone;

import java.util.List;

/**
 *  商品接口
 */
public interface PhoneDao {

    /**
     * 添加商品
     *
     * @param phone
     * @return
     */
   int addPhone(Phone phone);

    /**
     * 删除商品
     *
     * @param pid
     * @return
     */
   int delPhone(Integer pid);

    /**
     * 修改商品
     *
     * @param phone
     * @return
     */
    int updatePhone(Phone phone);

    /**
     * 指定id 查询
     *
     * @param pid
     * @return
     */
    Phone findPhoneById(Integer pid);

    /**
     * 查询所有商品 (参数有两个)
     *
     * @param starIndex
     * @param pageSize
     * @return
     */
    List<Phone> findPhoneAll(int starIndex,int pageSize);

    /**
     * 查询总条数(数据共有几条数据)
     *
     * @return
     */
    int findTotalItems();

    /**
     *  分类分页查询
     * @param startIndex
     * @param pageSize
     * @param cid
     * @return
     */
    List<Phone> findCategoryAndPhoneBYPage(int startIndex, int pageSize, Integer cid);
}

4.商品的dao 实现类

package cn.javabs.store.dao.impl;

import cn.javabs.store.dao.PhoneDao;
import cn.javabs.store.entity.Category;
import cn.javabs.store.entity.Phone;
import cn.javabs.store.util.DruidUtil;
import org.apache.commons.dbutils.BasicRowProcessor;
import org.apache.commons.dbutils.QueryRunner;
import org.apache.commons.dbutils.handlers.BeanHandler;
import org.apache.commons.dbutils.handlers.BeanListHandler;
import org.apache.commons.dbutils.handlers.MapListHandler;
import org.apache.commons.dbutils.handlers.ScalarHandler;

import java.sql.SQLException;
import java.util.List;
import java.util.Map;

/**
 *  商品 接口的实现类设计
 */
public class PhoneDaoImpl implements PhoneDao {

    QueryRunner queryRunner = new QueryRunner(DruidUtil.getDataSource());
    /**
     * 添加商品
     *
     * @param phone
     * @return
     */
    @Override
    public int addPhone(Phone phone) {
        try {
            int number = queryRunner.update("insert into phone (pname,pdescription,price,stock,photopath,photoname,cid) values (?,?,?,?,?,?,?) ",
                    phone.getPname(),
                    phone.getPdescription(),
                    phone.getPrice(),
                    phone.getStock(),
                    phone.getPhotopath(),
                    phone.getPhotoName(),
                    phone.getCategory().getCid());
            return number;
        } catch (SQLException e) {
            throw new RuntimeException(e);
        }
    }

    /**
     * 删除商品
     *
     * @param pid
     * @return
     */
    @Override
    public int delPhone(Integer pid) {
        try {
            int number = queryRunner.update("delete  from phone where pid = ?", pid);
            return number;
        } catch (SQLException e) {
            throw new RuntimeException(e);
        }

    }

    /**
     * 修改商品
     *
     * @param phone
     * @return
     */
    @Override
    public int updatePhone(Phone phone) {
        try {
            int number = queryRunner.update("update phone set pname=?,pdescription=?,price=?,stock=?,photopath=?,photoName=?,cid=? where pid=?",
                    phone.getPname(),
                    phone.getPdescription(),
                    phone.getPrice(),
                    phone.getStock(),
                    phone.getPhotopath(),
                    phone.getPhotoName(),
                    phone.getCategory().getCid(),
                    phone.getPid());
            return number;
        } catch (SQLException e) {
            throw new RuntimeException(e);
        }
    }



    /**
     * 指定id 查询
     *
     * @param pid
     * @return
     */
    @Override
    public Phone findPhoneById(Integer pid) {
        try {
            Phone phone = queryRunner.query("select pid,pname,pdescription,price,stock,photopath,photoName,cid from phone where pid=?", new BeanHandler<Phone>(Phone.class), pid);
            return phone;

        }catch (SQLException e) {
            throw new RuntimeException(e);
        }

    }

//    /**
//     * 查询所有商品 (参数有两个)
//     *
//     * @param starIndex
//     * @param pageSize
//     * @return
//     */
//    @Override
//    public List> findPhoneAll(int starIndex, int pageSize) {
//        try {
//            String sql ="select p.*,c.cname from phone,category c where.cid=c.cid limit 10,5";
//            List> list = queryRunner.query(sql, new MapListHandler(new BasicRowProcessor(), starIndex, pageSize));
//            return list;
//        } catch (SQLException e) {
//            throw new RuntimeException(e);
//        }
//    }

    /**
     * 查询所有商品 (参数有两个)
     *
     * @param starIndex
     * @param pageSize
     * @return
     */
    @Override
    public List<Phone> findPhoneAll(int starIndex, int pageSize) {
        try {
            List<Phone>    list = queryRunner.query("select * from  phone limit ?,?", new BeanListHandler<Phone>(Phone.class),starIndex,pageSize);
            return list;
        } catch (SQLException e) {
            throw new RuntimeException(e);
        }

    }


    /**
     * 查询总条数(数据共有几条数据)
     *
     * @return
     */
    @Override
    public int findTotalItems() {
        try {
            Long longNumber = queryRunner.query("select count(*) from phone", new ScalarHandler<>(1));
            int number = longNumber.intValue();
            return number;
        } catch (SQLException e) {
            throw new RuntimeException(e);
        }
    }

    /**
     * 分类分页查询
     *
     * @param startIndex
     * @param pageSize
     * @param cid
     * @return
     */
    @Override
    public List<Phone> findCategoryAndPhoneBYPage(int startIndex, int pageSize, Integer cid) {
        try {
            List<Phone> list = queryRunner.query("select * from  phone where cid = ? limit ?,?",
                    new BeanListHandler<Phone>(Phone.class),cid, startIndex,pageSize);
            return list;
        } catch (SQLException e) {
            throw new RuntimeException(e);
        }
    }


}

  1. 商品的service 实体类
package cn.javabs.store.service.impl;

import cn.javabs.store.commons.Page;
import cn.javabs.store.dao.PhoneDao;
import cn.javabs.store.dao.impl.PhoneDaoImpl;
import cn.javabs.store.entity.Phone;
import cn.javabs.store.service.PhoneService;

import java.util.List;
import java.util.Map;

public class PhoneServiceImpl implements PhoneService {

    //  全局变量 在 类内 方法外,代码块外, 默认值为null  接口不能new 的 ,根本原因是接口里有抽象方法 接口是引用类型 默认值为 null
    PhoneDao phoneDao = new PhoneDaoImpl();

    /**
     * 查询全部
     *
     * @param pageNum 页码
     * @return
     */
    @Override
    public Page findAllPhones(String pageNum) {
        int currentPageNum = 1; // 初始化值为1 当前页是第一页
//        如果说 pageNum = null  判断是否为空,不是空的 才可以进行转化  才执行if 循环语句
        if(pageNum != null) {
            // 1将字符串的类型 页码  PageNum  转换为  整数类型 | “2” -----》2
             currentPageNum = Integer.parseInt(pageNum);
            // 2. 如果一旦为空 ,我们在此重新进行设置一个初始化值 1  表示当前页是第一页
        }
        //  查询一下 数据库内共多少条
         int totalItems = phoneDao.findTotalItems();
        //   为什么可以new  是因为生产了 有参的构造方法  new 就是实力化  开辟了一个空间
        Page page = new Page(totalItems, currentPageNum);

        // 获取 开始索引值(因为Page page 类的构造方法被使用了,可以计算的出索引值多少)
        int startIndex = page.getStartIndex();
       // 获取页多少条数(在 page类中已经被定义的5 条)
        int pageSize = page.getPageSize();

        List<Phone> list = phoneDao.findPhoneAll(startIndex, pageSize);

        page.setRecords(list);

        return page;
    }

    /**
     * 根据商品编码查询商品
     *
     * @param pid
     * @return
     */
    @Override
    public Phone findPhoneById(Integer pid) {
        Phone phone = phoneDao.findPhoneById(pid);
        return phone;
    }

    /**
     * 添加商品
     *
     * @param phone
     * @return
     */
    @Override
    public int addPhone(Phone phone) {
        int num = phoneDao.addPhone(phone);
        return num;
    }

    /**
     * 修改商品
     *
     * @param phone
     * @return
     */
    @Override
    public int editPhone(Phone phone) {
        int num = phoneDao.updatePhone(phone);
        return num;
    }

    /**
     * 删除商品
     *
     * @param pid
     * @return
     */
    @Override
    public int delPhone(Integer pid) {
        int num = phoneDao.delPhone(pid);
        return num;
    }

    /**
     * 分类分页查询
     *
     * @param pageNum
     * @param cid
     * @return
     */
    @Override
    public Page findCategoryAndPhoneBYPage(String pageNum, Integer cid) {
        int currentPageNum = 1; // 初始化值为1 当前页是第一页
//        如果说 pageNum = null  判断是否为空,不是空的 才可以进行转化  才执行if 循环语句
        if(pageNum != null) {
            // 1将字符串的类型 页码  PageNum  转换为  整数类型 | “2” -----》2
            currentPageNum = Integer.parseInt(pageNum);
            // 2. 如果一旦为空 ,我们在此重新进行设置一个初始化值 1  表示当前页是第一页
        }
        //  查询一下 数据库内共多少条
        int totalItems = phoneDao.findTotalItems();
        //   为什么可以new  是因为生产了 有参的构造方法  new 就是实力化  开辟了一个空间
        Page page = new Page(totalItems, currentPageNum);
        System.out.println(page.toString());
        // 获取 开始索引值(因为Page page 类的构造方法被使用了,可以计算的出索引值多少)
        int startIndex = page.getStartIndex();
        // 获取页多少条数(在 page类中已经被定义的5 条)
        int pageSize = page.getPageSize();

        List<Phone> list = phoneDao.findCategoryAndPhoneBYPage(startIndex, pageSize,cid);

        page.setRecords(list);

        return page;
    }
}

  1. 商品的service
package cn.javabs.store.service;

import cn.javabs.store.commons.Page;
import cn.javabs.store.entity.Phone;

import java.util.List;
import java.util.Map;

/**
 *  商品的业务逻辑层设计
 *
 */
public interface PhoneService {

    /**
     *   查询全部
     * @param pageNum  页码
     * @return
     */
    Page findAllPhones(String pageNum);

    /**
     *  根据商品编码查询商品
     * @param pid
     * @return
     */
    Phone findPhoneById(Integer pid);

    /**
     *  添加商品
     * @param phone
     * @return
     */
    int addPhone(Phone phone);

    /**
     *  修改商品
     * @param phone
     * @return
     */
    int  editPhone(Phone phone);

    /**
     *   删除商品
     * @param pid
     * @return
     */
    int  delPhone(Integer pid);

    /**
     *  分类分页查询
     * @param pageNum
     * @param cid
     * @return
     */
    Page  findCategoryAndPhoneBYPage(String pageNum,Integer cid);
}

  1. 商品的Servlet 类
package cn.javabs.store.servlet;

import cn.javabs.store.commons.Page;
import cn.javabs.store.entity.Category;
import cn.javabs.store.entity.Phone;
import cn.javabs.store.execoption.PhoneServletException;
import cn.javabs.store.service.CategoryService;
import cn.javabs.store.service.PhoneService;
import cn.javabs.store.service.impl.CategoryServiceImpl;
import cn.javabs.store.service.impl.PhoneServiceImpl;
import org.apache.commons.beanutils.BeanUtils;
import org.apache.commons.fileupload.FileItem;
import org.apache.commons.fileupload.FileUploadException;
import org.apache.commons.fileupload.disk.DiskFileItemFactory;
import org.apache.commons.fileupload.servlet.ServletFileUpload;
import org.apache.commons.io.FilenameUtils;

import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.File;
import java.io.IOException;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.Iterator;
import java.util.List;
import java.util.UUID;

@WebServlet( "/phoneServlet")
public class PhoneServlet extends HttpServlet {
    CategoryService categoryService = new CategoryServiceImpl();

  PhoneService phoneService = new PhoneServiceImpl();
    public void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
            doGet(request,response);
    }

    public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        String methodName = request.getParameter("methodName");
        if ("findAllPhone".equals(methodName)){
            findAllPhone(request,response);
        }else if ("addPhone".equals(methodName)){
            try {
                addPhone(request,response);
            } catch (Exception e) {
                throw new RuntimeException(e);
            }
        }else if("delAllPhone".equals(methodName)){
            delAllPhone(request,response);
        }else if("editAllPhone".equals(methodName)){
            editAllPhone(request,response);
        }else if("findPhoneById".equals(methodName)){
            findPhoneById(request,response);
        }else if("toAddPhonePage".equals(methodName)){
            toAddPhonePage(request,response);}
        else if("editPhoneView".equals(methodName)){
            editPhoneView(request,response);
        }else {
            System.out.println("请仔细核对方法的单词");
        }
    }

    /**
     *  数据回显
     * @param request
     * @param response
     */
    private void editPhoneView(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {

        String id = request.getParameter("pid");
        int pid = Integer.parseInt(id);
        Phone phone = phoneService.findPhoneById(pid);
        if(phone != null){
            request.setAttribute("categoryLis",phone);
            request.getRequestDispatcher("phoneEdit.jsp").forward(request,response);

        }else {
            request.setAttribute("phone","回显失败");
            request.getRequestDispatcher("phoneEdit.jsp").forward(request,response);
        }
    }

    /**
     * 跳转添加商品的页面
     * @param request
     * @param response
     */
    private void toAddPhonePage(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        List<Category> categories = categoryService.findAllCategories();
        request.setAttribute("categoryList",categories);
            request.getRequestDispatcher("/addPhone.jsp").forward(request,response);
    }

    /**
     * 全部查询 商品
     * @param request
     * @param response
     * @throws ServletException
     * @throws IOException
     */
    public void findAllPhone(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
            //  前台页面传递来一个页面数据
        String pageNum = request.getParameter("pageNum");
            Page page = phoneService.findAllPhones(pageNum);
       page.setUrl("/phoneServlet?methodName=findAllPhone");
        if(page != null){
            request.setAttribute("page",page);
            request.getRequestDispatcher("/phoneList.jsp").forward(request,response);

        }else {
            request.setAttribute("data","查询失败");
            request.getRequestDispatcher("/message.jsp").forward(request,response);
        }

    }

    /**
     *
     * @param request
     * @param response
     * @throws ServletException
     * @throws IOException
     */
    public void findPhoneById(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {

    }

    /**
     *  添加商品
     * @param request
     * @param response
     * @throws ServletException
     * @throws IOException
     */
    public void addPhone(HttpServletRequest request, HttpServletResponse response) throws Exception {
        Phone phone = new Phone();
        boolean isMultipart = ServletFileUpload.isMultipartContent(request);
        DiskFileItemFactory factory = new DiskFileItemFactory();
        ServletFileUpload upload = new ServletFileUpload(factory);
        List<FileItem> items = upload.parseRequest(request);

        Iterator<FileItem> iter = items.iterator();
        while (iter.hasNext()) {
            FileItem item = iter.next();

            if (item.isFormField()) {
                String name = item.getFieldName();
                String value = item.getString(request.getCharacterEncoding());

                BeanUtils.copyProperty(phone,name,value);
            } else {
                String fileName = item.getName();
                System.out.println("原始的filename"+fileName);
//                fileName = UUID.randomUUID().toString()+"."+ FilenameUtils.getExtension(fileName);


                Date date = new Date();
                SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd-HH-mm-ss");
                String newTime = sdf.format(date);
                fileName = newTime+"."+ FilenameUtils.getExtension(fileName);
                System.out.println("使用时间戳改造后fileName"+ fileName);
                String photoPath = getServletContext().getRealPath("/pic");

                File file = new File(photoPath);
                // 如果不存在该文件夹。就创建出来
                if (!file.exists()){
                    file.mkdirs();
                }
                // 将图片的名称放进phone 的对象中去
                phone.setPhotoName(fileName);
                // 将图片的路经放进phone 的对象中去
                phone.setPhotopath(photoPath);

                item.write(new File(photoPath+"/"+fileName));
            }
        }
        Category category = new Category();
        category.setCid(5);
        phone.setCategory(category);
        int number = phoneService.addPhone(phone);
        if (number >0){
            request.setAttribute("data","添加成功");
            request.getRequestDispatcher("message.jsp").forward(request,response);
        }else {
            request.setAttribute("data","添加失败");
            request.getRequestDispatcher("message.jsp").forward(request,response);
        }
        //        Phone phone = new Phone();
//        // 是否是上传 表单
//        boolean multipartContent = ServletFileUpload.isMultipartContent(request);
//        // 如果不是上传的表单将提示语存放在data标记中
//        if(!multipartContent){
//            request.setAttribute("data","哥们你的上传的不是上传表单");
//            // 去message。jsp 这个页面显示数据
//            request.getRequestDispatcher("message.jsp").forward(request,response);
//
//            // 实例化 磁盘文件项目工厂
//            DiskFileItemFactory factory = new DiskFileItemFactory();
//
//            ServletFileUpload servletFileUpload = new ServletFileUpload();
//
//            List fileItems = servletFileUpload.parseRequest(request);
//
//
//            for (FileItem fileItem:fileItems){
//                if (fileItem.isFormField()){ // 是普通表单
//                 // 获取 name 的值
//                    String fieldName = fileItem.getFieldName();// 它将会是 pname/pdescription
//                 // 获取表单的value  的值  (客户输入的值)
//                    String fiedValue = fileItem.getString(request.getCharacterEncoding());
//                    BeanUtils.copyProperty(phone,fiedValue,fieldName);
//
//                    // 第二种写法
//
//                }else {
//                    // 获取到文件名
//                    String fileName = fileItem.getName();
//
//                    String photoPath = getServletContext().getRealPath("/upload");
//
//                    File file = new File(photoPath);
//                    if(!file.exists()){
//                         file.mkdirs();
//                    }
//                    phone.setPhonoName(fileName);
//                    phone.setPhotopath(photoPath);
//
//                    System.out.println("第二个打印商品"+ phone);
//
//                    fileItem.write(new File(photoPath+"/"+fileName));
//                }
//            }
//        }
//        int number = phoneService.addPhone(phone);
//        if(number > 0){
//            request.setAttribute("data","哥们,添加商品成功");
//            request.getRequestDispatcher("message.jsp").forward(request,response);
//        }else {
//            request.setAttribute("data","对不起,亲,你添加失败了");
//            request.getRequestDispatcher("addPhone.jsp").forward(request,response);
//        }


    }

    /**
     *  修改商品
     * @param request
     * @param response
     * @throws ServletException
     * @throws IOException
     */
    public void editAllPhone(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {

        try {
            Phone phone = new Phone();
            String id = request.getParameter("pid");
            int pid = Integer.parseInt(id);
            String pname = request.getParameter("pname");
            boolean isMultipart = ServletFileUpload.isMultipartContent(request);
            DiskFileItemFactory factory = new DiskFileItemFactory();
            ServletFileUpload upload = new ServletFileUpload(factory);
            List<FileItem> items = upload.parseRequest(request);

            Iterator<FileItem> iter = items.iterator();
            while (iter.hasNext()) {
                FileItem item = iter.next();

                if (item.isFormField()) {
                    String name = item.getFieldName();
                    String value = item.getString();
                    phone.setPid(pid);
                    phone.setPname(pname);
                    BeanUtils.copyProperty(phone,name,value);

                } else {
                    String fileName = item.getName();
                    System.out.println("原始的filename"+fileName);
//                    fileName = UUID.randomUUID().toString()+"."+ FilenameUtils.getExtension(fileName);

                    Date date = new Date();
                    SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd-HH-mm-ss");
                    String newTime = sdf.format(date);
                    fileName = newTime+"."+ FilenameUtils.getExtension(fileName);
                    System.out.println("使用时间戳改造后fileName"+ fileName);
                    String photoPath = getServletContext().getRealPath("/pic");

                    File file = new File(photoPath);
                    // 如果不存在该文件夹。就创建出来
                    if (!file.exists()){
                        file.mkdirs();
                    }
                    // 将图片的名称放进phone 的对象中去
                    phone.setPhotoName(fileName);
                    // 将图片的路经放进phone 的对象中去
                    phone.setPhotopath(photoPath);
                    // 将要删除的
                    Category category = new Category();
                    category.setCid(5);
                    phone.setCategory(category);


                    item.write(new File(photoPath+"/"+fileName));
                }
            }
            int number = phoneService.editPhone(phone);
            if (number >0){
                request.setAttribute("data","修改成功");
                request.getRequestDispatcher("message.jsp").forward(request,response);
            }else {
                request.setAttribute("data","修改失败");
                request.getRequestDispatcher("message.jsp").forward(request,response);
            }
        } catch (Exception e) {
            throw new PhoneServletException(e);
        }
    }

    /**
     *  删除商品
     * @param request
     * @param response
     * @throws ServletException
     * @throws IOException
     */
    public void delAllPhone(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        //  1. 会有id 传进来---使用
        String id = request.getParameter("pid");
        int pid = Integer.parseInt(id);

        int number = phoneService.delPhone(pid);
        if(number > 0){
            // 将数据存储到 请求域对象中
            request.setAttribute("data","删除成功");
            request.getRequestDispatcher("message.jsp").forward(request,response);
        }else {
            request.setAttribute("data","删除失败");
            request.getRequestDispatcher("message.jsp").forward(request,response);
        }


    }
}

package cn.javabs.store.dao.impl;

import cn.javabs.store.dao.UserDao;
import cn.javabs.store.entity.User;
import cn.javabs.store.execoption.*;
import cn.javabs.store.util.DruidUtil;
import org.apache.commons.dbutils.QueryRunner;
import org.apache.commons.dbutils.handlers.BeanHandler;
import org.apache.commons.dbutils.handlers.BeanListHandler;
import org.apache.commons.dbutils.handlers.ScalarHandler;

import java.sql.SQLException;
import java.util.List;

/**
 *  用户数据访问层
 */
public class UserDaoImpl implements UserDao {
   QueryRunner queryRunner = new QueryRunner(DruidUtil.getDataSource());

    /**
     * 根据用户id 查询
     * @param id
     * @return
     */
    @Override
    public User getUserById(Integer id) {
        try {
            User user =  queryRunner.query("select *from user where id=?", new BeanHandler<>(User.class),id);
            return user;
        } catch (SQLException e) {
            throw new FindUserException(e);
        }
    }

    /**
     * 注册
     * @param user
     * @return
     */
    @Override
    public int register(User user) {
        String sql ="insert into user(username,password,telephone,email,address,code,actived)values(?,?,?,?,?,?,?)";
        try {
            queryRunner.update(sql,
                    user.getUsername(),
                    user.getPassword(),
                    user.getTelephone(),
                    user.getEmail(),
                    user.getAddress(),
                    user.getCode(),
                    user.isActived());
        } catch (SQLException e) {
            throw new AddUserDaoImplException(e);
        }
        return 0;
    }

    /**
     * 根据激活码激活用户
     * @param code
     * @return
     */
    @Override
    public User findByCode(String code) {
        try {
//            String sql="selcct * from user where  code =?";
//            Class u =User.class;
//            BeanHandler rsh = new BeanHandler<>(u);
//           User user= (User) queryRunner.query(sql,rsh,code);
            return queryRunner.query("select * from user where code = ?",new BeanHandler<User>(User.class),code);
        } catch (SQLException e) {
            throw new UserActiveCodeException(e);
        }
    }

    /**
     * 修改用户
     * @param user
     */
    @Override
    public int update(User user) {
        try {
             return queryRunner.update("update user set username=?,password=?,telephone=?,email=?,address=?,code=?,actived=? where uid=?",
                    user.getUsername(),
                    user.getPassword(),
                    user.getTelephone(),
                    user.getEmail(),
                    user.getAddress(),
                    user.getCode(),
                    user.getAddress(),
                    user.getId());
        } catch (SQLException e) {
            throw new UnsupportedOperationException(e);
        }
    }

    /**
     *  用户登录
     * @param username
     * @param password
     * @return
     */
    @Override
    public User Login(String username, String password) {
        try {
            User user = queryRunner.query("select * from user where username=? and password =?", new BeanHandler<User>(User.class), username, password);
            return user;
        } catch (SQLException e) {
            throw new UserLoginException(e);
        }

    }

    /**
     *  查询共有有多条用户
     * @param pageNum
     * @return
     */
    @Override
    public int findUserTotalItems(String pageNum) {
        try {
          Long num = queryRunner.query("select count (*) from user ",new ScalarHandler<>(1),pageNum);
            int number = num.intValue();
            return number;
        } catch (SQLException e) {
            throw new FindUserException(e);
        }

    }

    /**
     *  查询所有用户(分页)
     * @param startIndex
     * @param pageSize
     * @return
     */
    @Override
    public List<User> findUserByPage(int startIndex, int pageSize) {
        try {
       List<User> userList =   queryRunner.query("select * from user limit ?,?",new BeanListHandler<User>(User.class),startIndex,pageSize);
            return userList;
        } catch (SQLException e) {
            throw new FindAllUserException(e);
        }

    }



    /**
     *根据用户名称进行迷糊查询 分页
     * @param startIndex
     * @param pageSize
     * @param username
     * @return
     */
    @Override
    public List<User> findUseBylikeUsername(int startIndex, int pageSize, String username) {
        try {
            queryRunner.query("select * from where username like ? limit ?,?",
                    new BeanListHandler<User>(User.class),username,startIndex,pageSize);
            return null;
        } catch (SQLException e) {
           throw new FindAllUsersException(e);
        }

    }

    /**
     * 删除用户
     * @param id
     * @return
     */
    @Override
    public int del(Integer id) {
        try {
            int number = queryRunner.update("delete from user where id = ?", id);
            return number;
        } catch (SQLException e) {
            throw new DeleteUserException(e);
        }
    }
}

package cn.javabs.store.dao;

import cn.javabs.store.entity.User;

import java.util.List;

public interface UserDao {

    /**
     * 根据id查询用户
     * @param id
     * @return
     */
    User getUserById(Integer id);

    int register(User user);

    User findByCode(String code);

    /**
     *  修改用户
     * @param user
     */
    int update(User user);

    User Login(String username, String password);

    int findUserTotalItems(String pageNum);

    List<User> findUserByPage(int startIndex, int pageSize);


    /**
     *  根据用户进行模胡查询
     * @param startIndex
     * @param pageSize
     * @param username
     * @return
     */
    List<User> findUseBylikeUsername(int startIndex, int pageSize, String username);

    /**
     * 删除用户
     * @param id
     * @return
     */
    int del(Integer id);
}

package cn.javabs.store.entity;

/**
 * 用户的实体类
 */
public class User {

    private Integer id;
    private String username;
    private String password;
    private String telephone;
    private String email;
    private String address;
    private String code ;// 激活码
    private boolean actived; //是否激活

    public Integer getId() {
        return id;
    }

    public void setId(Integer id) {
        this.id = id;
    }

    public String getUsername() {
        return username;
    }

    public void setUsername(String username) {
        this.username = username;
    }

    public String getPassword() {
        return password;
    }

    public void setPassword(String password) {
        this.password = password;
    }

    public String getTelephone() {
        return telephone;
    }

    public void setTelephone(String telephone) {
        this.telephone = telephone;
    }

    public String getEmail() {
        return email;
    }

    public void setEmail(String email) {
        this.email = email;
    }

    public String getAddress() {
        return address;
    }

    public void setAddress(String address) {
        this.address = address;
    }

    public String getCode() {
        return code;
    }

    public void setCode(String code) {
        this.code = code;
    }

    public boolean isActived() {
        return actived;
    }

    public void setActived(boolean actived) {
        this.actived = actived;
    }

    public boolean getActived() {
        return actived;
    }
}

package cn.javabs.store.service.impl;

import cn.javabs.store.commons.Page;
import cn.javabs.store.dao.UserDao;
import cn.javabs.store.dao.impl.UserDaoImpl;
import cn.javabs.store.entity.User;
import cn.javabs.store.service.UserService;

import java.util.List;

/**
 *  用户的实现类
 */
public class UserServiceImpl implements UserService {
    UserDao userDao = new UserDaoImpl();

    /**
     * 用户注册
     *
     * @param user
     */
    @Override
    public int registerUser(User user) {

      return   userDao.register(user);
    }

    /**
     * 根据激活码激活用户
     *
     * @param code
     */
    @Override
    public User activeUser(String code) {
        User user = userDao.findByCode(code);
        // 表示启动
        user.setActived(true);
        userDao.update(user);// 去修改语句 的状态
        return  user;
    }


    /**
     * 登录
     *
     * @param username
     * @param password
     * @return
     */
    @Override
    public User userLogin(String username, String password) {
        User user = userDao.Login(username, password);
        return user;
    }

    /**
     * 查询所有用户
     *
     * @param pageNum 分页页码
     * @return
     */
    @Override
    public Page findAllUser(String pageNum) {
        int currentPage = 1;
        if (pageNum != null) {
            currentPage = Integer.parseInt(pageNum);
        }
        int totalItem = userDao.findUserTotalItems(pageNum);
        Page page = new Page(currentPage, totalItem);
        int startIndex = page.getStartIndex();
        int pageSize = page.getPageSize();
        List<User> user = userDao.findUserByPage(startIndex, pageSize);
        return page;
    }





    /**
     * 根据用户模胡查询 并进行分页
     *
     * @param username
     * @param pageNum
     * @return
     */
    @Override
    public Page findUserByLikeName(String username, String pageNum) {
       //  初始化 当前的数值 以防Servlet 传递page 为null
        int currentPage =1;
        if(pageNum != null ){
            currentPage = Integer.parseInt(pageNum);
        }
       int  totalItems = userDao.findUserTotalItems(pageNum);
        Page page = new Page(currentPage,totalItems);
        int startIndex = page.getStartIndex();
        int pageSize = page.getPageSize();
        List<User> list = userDao.findUseBylikeUsername(startIndex, pageSize,username);
        page.setRecords(list);
        return page;
    }

    /**
     * 根据id 删除用户
     *
     * @param id
     * @return
     */
    @Override
    public int delUserByid(Integer id) {
       int number = userDao.del(id);
       return number;
    }

    /**
     * 修改用户
     *
     * @param user
     * @return
     */
    @Override
    public int editUser(User user) {
          userDao.update(user);
          return 0;
    }

    /**
     * 根据id查询用户
     *
     * @param id
     * @return
     */
    @Override
    public User getUserById(Integer id) {

        User user = userDao.getUserById(id);
        if (user == null) {
                return null;
            }
            if (!user.isActived()) {
                return null;
            }
            return user;
        }
    }


package cn.javabs.store.service;

import cn.javabs.store.commons.Page;
import cn.javabs.store.entity.User;

/**
 *      用户接口设计
 */
public interface UserService {

    /**
     *  用户注册
     * @param user
     */
    int  registerUser(User user);

    /**
     * 根据激活码激活用户
     * @param code
     */
    User activeUser(String code);

    /**
     *  登录
     * @param username
     * @param password
     * @return
     */
    User userLogin(String username,String password);

    /**
     * 查询所有用户
     * @param pageNum  分页页码
     * @return
     */
    Page findAllUser(String pageNum);


    /**
     * 根据用户模胡查询 并进行分页
     * @param username
     * @param pageNum
     * @return
     */
    Page findUserByLikeName(String username,String pageNum);

    /**
     * 根据id 删除用户
     * @param id
     * @return
     */
    int  delUserByid(Integer id);

    /**
     * 修改用户
     * @param user
     * @return
     */
    int editUser(User user);

    /**
     * 根据id查询用户
     * @param id
     * @return
     */
    User getUserById(Integer id);

}

package cn.javabs.store.servlet;

import cn.javabs.store.entity.Category;
import cn.javabs.store.entity.User;
import cn.javabs.store.service.CategoryService;
import cn.javabs.store.service.UserService;
import cn.javabs.store.service.impl.CategoryServiceImpl;
import cn.javabs.store.service.impl.UserServiceImpl;
import cn.javabs.store.util.MailUtil;
import org.apache.commons.beanutils.BeanUtils;
import org.apache.commons.lang3.StringUtils;

import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import java.io.IOException;
import java.lang.reflect.InvocationTargetException;
import java.util.List;
import java.util.UUID;

import static com.sun.jmx.snmp.EnumRowStatus.active;

@WebServlet( "/userServlet")
public class UserServlet extends HttpServlet {
    UserService userService = new UserServiceImpl();
    User user = new User();
    CategoryService categoryService  =  new CategoryServiceImpl();
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        doGet(request,response);
    }

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        String methodName = request.getParameter("methodName");
        System.out.println(methodName);
        switch (methodName){
            case "register":
                register(request,response);
                break;
            case"active":
                active(request,response);
                break;
            case "login":
                login(request,response);
                break;
            case "logout":
                logout(request,response);
                break;
            case "toLogin":
                toLogin(request,response);
            default:
                System.out.println("写错了方法");
        }
    }

    private void toLogin(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {

        List<Category> allCategories = categoryService.findAllCategories();
        request.setAttribute("categoryList",allCategories);
        request.getRequestDispatcher("login.jsp").forward(request,response);
    }

    /**
     * 注销
     * @param request
     * @param response
     */
    private void logout(HttpServletRequest request, HttpServletResponse response) throws IOException {
        HttpSession session = request.getSession();
        // 通过响应对象完成网页重定向
        session.removeAttribute("USTR");
        session.setAttribute("data","您已注销");
        response.sendRedirect(request.getContextPath());


    }

    /**
     * 登录
     * @param request
     * @param response
     */
    private void login(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        String username = request.getParameter("username");
        String password = request.getParameter("password");
        System.out.println(username+"____"+password);
        User user = userService.userLogin(username, password);
        System.out.println(user);
        if (user != null){
           boolean actived = user.getActived();
           if (actived){
               request.getSession().setAttribute("USER",user);
               response.sendRedirect(request.getContextPath());
           }else {
               request.setAttribute("data","您的账户还为激活,请到邮箱激活");
               String code  =user.getCode();
               MailUtil mailUtil = new MailUtil(user);
               mailUtil.start();
               toLogin(request,response);
           }

        }

//        if(user!=null){
//            if (user.isActived()) {
//                HttpSession session = request.getSession();
//                session.setAttribute("USER", user);
//                response.sendRedirect(request.getContextPath());
//            }else {
//                request.setAttribute("data","您的账户还未激活");
//                request.getRequestDispatcher("message.jsp").forward(request,response);
//            }
//        }else {
//            request.setAttribute("data","没有激活,密码不正确");
//            request.getRequestDispatcher("message.jsp").forward(request,response);
//        }


    }

    /**
     * 激活
     * @param request
     * @param response
     */
    private void active(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        // 获取激活码
        String code = request.getParameter("code");
        System.out.println(code);
        // 如果 不是null  并且不是字符串{并会自动去除空格】
        if (StringUtils.isNotBlank(code)){
         user = userService.activeUser(code);
            if (user != null){
            response.getWriter().write("激活成功,5秒自动转向主页");

            response.setHeader("refresh","5;url="+request.getContextPath());
        }else {
            request.setAttribute("data","激活码不对");
            request.getRequestDispatcher("message.jsp").forward(request,response);
        }

    }
    }

    /**
     * 注册
     * @param request
     * @param response
     */
    private void register(HttpServletRequest request, HttpServletResponse response) {
//        request.getParameter("username");
//        request.getParameter("password");
//        request.getParameter("telephone");
        try {
            BeanUtils.populate(user,request.getParameterMap());
            // 生成激活码 激活码是唯一的 【UUID /时间戳】
            String code = UUID.randomUUID().toString();
            // 将激活码放到 用户对象中去
            user.setCode(code);
            MailUtil mailUtil = new MailUtil(user);
            mailUtil.start();
            // 将user 传递到 UserService

            userService.registerUser(user);
            request.setAttribute("data","注册成功!,已向你的"+user.getUsername()+"邮箱发送了一件激活邮件,请及时点击");
            request.getRequestDispatcher("message.jsp").forward(request,response);
        } catch (Exception e) {
            throw new RuntimeException(e);
        }

    }
}

package cn.javabs.store.servlet;

import cn.javabs.store.commons.Page;
import cn.javabs.store.entity.Cart;
import cn.javabs.store.entity.Category;
import cn.javabs.store.entity.Phone;
import cn.javabs.store.service.CategoryService;
import cn.javabs.store.service.PhoneService;
import cn.javabs.store.service.impl.CategoryServiceImpl;
import cn.javabs.store.service.impl.PhoneServiceImpl;

import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import java.io.IOException;
import java.util.List;

@WebServlet("/clientServlet")
public class ClientServlet extends HttpServlet {

    CategoryService categoryService = new CategoryServiceImpl();

 PhoneService phoneService =   new PhoneServiceImpl();
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        doGet(request,response);
    }

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        String methodName = request.getParameter("methodName");
        switch (methodName){
            case "showIndex":
                showIndex(request,response);
                break;
            case "showCategoryPhones":
                showCategoryPhones(request,response);
               break;
            case "byPhone":
                byPhone(request,response);
                break;
        }
    }

    /**
     * 购买商品
     * @param request
     * @param response
     */
    private void byPhone(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        String id = request.getParameter("pid");
        int pid = Integer.parseInt(id);
       Phone phone = phoneService.findPhoneById(pid);
        HttpSession session = request.getSession();
        Cart cat = (Cart) session.getAttribute("cat");
            if (cat == null){
                Cart cart = new Cart();
                session.setAttribute("cat",cart);
            }
            cat.addPhone(phone);
            request.setAttribute("data","商品已经添加到商品内+");
            request.getRequestDispatcher("message.jsp").forward(request,response);
    }

    /**
     *  根据分页分类查询
     * @param request
     * @param response
     */
    private void showCategoryPhones(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        String pageNum = request.getParameter("pageNum");
        String id = request.getParameter("cid");
        int cid = Integer.parseInt(id);
        Page page = phoneService.findCategoryAndPhoneBYPage(pageNum, cid);
        page.setUrl("/clientServlet?methodName=showCategoryPhonees$cid="+cid);
        List<Category> categoryList = categoryService.findAllCategories();

        request.setAttribute("page",page);
        request.setAttribute("categoryList",categoryList);
        request.getRequestDispatcher("main.jsp").forward(request,response);

    }

    /**
     *  展示页面
     * @param request
     * @param response
     */
    private void showIndex(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        String pageNum = request.getParameter("pageNum");
        // 1.查询所有分类
        List<Category> categoryList = categoryService.findAllCategories();
        // 2.查询商品
        Page page =phoneService.findAllPhones(pageNum);
        page.setUrl("/clientServlet?methodName=showIndex");

        request.setAttribute("categoryList",categoryList);
        request.setAttribute("page",page);
        request.getRequestDispatcher("main.jsp").forward(request,response);


    }
}

package cn.javabs.store.entity;

/**
 * 购物项
 */
public class CartItem {

    private Phone phone;
    private int quantity; //小计数量
    private  double totlPrice; // 小计金额

    public Phone getPhone() {
        return phone;
    }

    public void setPhone(Phone phone) {
        this.phone = phone;
    }

    public int getQuantity() {
        return quantity;
    }

    public void setQuantity(int quantity) {
        this.quantity = quantity;
    }

    /**
     *  获取小计金额
     *      数量 * 单间
     * @return
     */
    public double getTotlPrice() {
        // 获取 商品的单价
        double price = phone.getPrice();
        //  获取小计金额 = 数量 * 单间
        totlPrice =quantity * price;
        return totlPrice;
//        return quantity * totlPrice
    }

    public void setTotlPrice(double totlPrice) {
        this.totlPrice = totlPrice;
    }
}

package cn.javabs.store.entity;

import java.util.HashMap;
import java.util.Map;

public class Cart {
//    private  CartItem cartItem;//购物项
    /**
     *  map 双列集合 存键值对
     *      k  键  对应的
     */
    private Map<Integer,CartItem> item=new HashMap<>();

    public Map<Integer, CartItem> getItem() {
        return item;
    }

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

    /**
     *  获取总数量
     * @return
     */
    public int getTotalQuantity() {
        totalQuantity = 0;
        for (Map.Entry<Integer,CartItem> i:item.entrySet()) {
            totalQuantity = i.getValue().getQuantity() + totalQuantity;
        }

        return totalQuantity;
    }


    public void setTotalQuantity(int totalQuantity) {
        this.totalQuantity = totalQuantity;
    }

    /**
     *   总金额
     * @return
     */
    public double getAmount() {
        amount=0;
        for (Map.Entry<Integer,CartItem> i:item.entrySet()){
            amount = i.getValue().getTotlPrice()+amount;
        }
        return amount;
    }

    public void setAmount(double amount) {
        this.amount = amount;
    }

    private int totalQuantity;// 总数量
    private  double amount; // 总金额

    public  void  addPhone(Phone phone){
        // 获取商品的id
        Integer pid = phone.getPid();
        // 购物项中是否包含的商品id
        if (item.containsKey(pid)){
            // 已经包含(之前以已经加入到购物车内)
            CartItem it = this.item.get(pid); // 在整个表里获取 id
            it.setQuantity(it.getQuantity()+1); // 在原有的商品在加一
        }else {
            // 不包含 (购物项内不包含商品,没有,创建一个就有了)
            CartItem it = new CartItem();
            it.setQuantity(1);
            item.put(pid,it);
        }
    }

}

异常类

package cn.javabs.store.execoption;

import java.sql.SQLException;

public class AddUserDaoImplException extends RuntimeException {

    /**
     * Constructs a new runtime exception with {@code null} as its
     * detail message.  The cause is not initialized, and may subsequently be
     * initialized by a call to {@link #initCause}.
     */
    public AddUserDaoImplException() {
        super();
    }

    /**
     * Constructs a new runtime exception with the specified detail message.
     * The cause is not initialized, and may subsequently be initialized by a
     * call to {@link #initCause}.
     *
     * @param message the detail message. The detail message is saved for
     *                later retrieval by the {@link #getMessage()} method.
     */
    public AddUserDaoImplException(String message) {
        super(message);
    }

    /**
     * Constructs a new runtime exception with the specified detail message and
     * cause.  

Note that the detail message associated with * {@code cause} is not automatically incorporated in * this runtime exception's detail message. * * @param message the detail message (which is saved for later retrieval * by the {@link #getMessage()} method). * @param cause the cause (which is saved for later retrieval by the * {@link #getCause()} method). (A null value is * permitted, and indicates that the cause is nonexistent or * unknown.) * @since 1.4 */ public AddUserDaoImplException(String message, Throwable cause) { super(message, cause); } /** * Constructs a new runtime exception with the specified cause and a * detail message of (cause==null ? null : cause.toString()) * (which typically contains the class and detail message of * cause). This constructor is useful for runtime exceptions * that are little more than wrappers for other throwables. * * @param cause the cause (which is saved for later retrieval by the * {@link #getCause()} method). (A null value is * permitted, and indicates that the cause is nonexistent or * unknown.) * @since 1.4 */ public AddUserDaoImplException(Throwable cause) { super(cause); } /** * Constructs a new runtime exception with the specified detail * message, cause, suppression enabled or disabled, and writable * stack trace enabled or disabled. * * @param message the detail message. * @param cause the cause. (A {@code null} value is permitted, * and indicates that the cause is nonexistent or unknown.) * @param enableSuppression whether or not suppression is enabled * or disabled * @param writableStackTrace whether or not the stack trace should * be writable * @since 1.7 */ protected AddUserDaoImplException(String message, Throwable cause, boolean enableSuppression, boolean writableStackTrace) { super(message, cause, enableSuppression, writableStackTrace); } }

package cn.javabs.store.execoption;

import java.sql.SQLException;

public class DeleteUserException extends RuntimeException {
    /**
     * Constructs a new runtime exception with {@code null} as its
     * detail message.  The cause is not initialized, and may subsequently be
     * initialized by a call to {@link #initCause}.
     */
    public DeleteUserException() {
        super();
    }

    /**
     * Constructs a new runtime exception with the specified detail message.
     * The cause is not initialized, and may subsequently be initialized by a
     * call to {@link #initCause}.
     *
     * @param message the detail message. The detail message is saved for
     *                later retrieval by the {@link #getMessage()} method.
     */
    public DeleteUserException(String message) {
        super(message);
    }

    /**
     * Constructs a new runtime exception with the specified detail message and
     * cause.  

Note that the detail message associated with * {@code cause} is not automatically incorporated in * this runtime exception's detail message. * * @param message the detail message (which is saved for later retrieval * by the {@link #getMessage()} method). * @param cause the cause (which is saved for later retrieval by the * {@link #getCause()} method). (A null value is * permitted, and indicates that the cause is nonexistent or * unknown.) * @since 1.4 */ public DeleteUserException(String message, Throwable cause) { super(message, cause); } /** * Constructs a new runtime exception with the specified cause and a * detail message of (cause==null ? null : cause.toString()) * (which typically contains the class and detail message of * cause). This constructor is useful for runtime exceptions * that are little more than wrappers for other throwables. * * @param cause the cause (which is saved for later retrieval by the * {@link #getCause()} method). (A null value is * permitted, and indicates that the cause is nonexistent or * unknown.) * @since 1.4 */ public DeleteUserException(Throwable cause) { super(cause); } /** * Constructs a new runtime exception with the specified detail * message, cause, suppression enabled or disabled, and writable * stack trace enabled or disabled. * * @param message the detail message. * @param cause the cause. (A {@code null} value is permitted, * and indicates that the cause is nonexistent or unknown.) * @param enableSuppression whether or not suppression is enabled * or disabled * @param writableStackTrace whether or not the stack trace should * be writable * @since 1.7 */ protected DeleteUserException(String message, Throwable cause, boolean enableSuppression, boolean writableStackTrace) { super(message, cause, enableSuppression, writableStackTrace); } }

package cn.javabs.store.execoption;

import java.sql.SQLException;

public class FindAllUserException extends RuntimeException {
    /**
     * Constructs a new runtime exception with {@code null} as its
     * detail message.  The cause is not initialized, and may subsequently be
     * initialized by a call to {@link #initCause}.
     */
    public FindAllUserException() {
        super();
    }

    /**
     * Constructs a new runtime exception with the specified detail message.
     * The cause is not initialized, and may subsequently be initialized by a
     * call to {@link #initCause}.
     *
     * @param message the detail message. The detail message is saved for
     *                later retrieval by the {@link #getMessage()} method.
     */
    public FindAllUserException(String message) {
        super(message);
    }

    /**
     * Constructs a new runtime exception with the specified detail message and
     * cause.  

Note that the detail message associated with * {@code cause} is not automatically incorporated in * this runtime exception's detail message. * * @param message the detail message (which is saved for later retrieval * by the {@link #getMessage()} method). * @param cause the cause (which is saved for later retrieval by the * {@link #getCause()} method). (A null value is * permitted, and indicates that the cause is nonexistent or * unknown.) * @since 1.4 */ public FindAllUserException(String message, Throwable cause) { super(message, cause); } /** * Constructs a new runtime exception with the specified cause and a * detail message of (cause==null ? null : cause.toString()) * (which typically contains the class and detail message of * cause). This constructor is useful for runtime exceptions * that are little more than wrappers for other throwables. * * @param cause the cause (which is saved for later retrieval by the * {@link #getCause()} method). (A null value is * permitted, and indicates that the cause is nonexistent or * unknown.) * @since 1.4 */ public FindAllUserException(Throwable cause) { super(cause); } /** * Constructs a new runtime exception with the specified detail * message, cause, suppression enabled or disabled, and writable * stack trace enabled or disabled. * * @param message the detail message. * @param cause the cause. (A {@code null} value is permitted, * and indicates that the cause is nonexistent or unknown.) * @param enableSuppression whether or not suppression is enabled * or disabled * @param writableStackTrace whether or not the stack trace should * be writable * @since 1.7 */ protected FindAllUserException(String message, Throwable cause, boolean enableSuppression, boolean writableStackTrace) { super(message, cause, enableSuppression, writableStackTrace); } }

package cn.javabs.store.execoption;

import java.sql.SQLException;

public class FindAllUsersException extends RuntimeException{
    /**
     * Constructs a new runtime exception with {@code null} as its
     * detail message.  The cause is not initialized, and may subsequently be
     * initialized by a call to {@link #initCause}.
     */
    public FindAllUsersException() {
        super();
    }

    /**
     * Constructs a new runtime exception with the specified detail message.
     * The cause is not initialized, and may subsequently be initialized by a
     * call to {@link #initCause}.
     *
     * @param message the detail message. The detail message is saved for
     *                later retrieval by the {@link #getMessage()} method.
     */
    public FindAllUsersException(String message) {
        super(message);
    }

    /**
     * Constructs a new runtime exception with the specified detail message and
     * cause.  

Note that the detail message associated with * {@code cause} is not automatically incorporated in * this runtime exception's detail message. * * @param message the detail message (which is saved for later retrieval * by the {@link #getMessage()} method). * @param cause the cause (which is saved for later retrieval by the * {@link #getCause()} method). (A null value is * permitted, and indicates that the cause is nonexistent or * unknown.) * @since 1.4 */ public FindAllUsersException(String message, Throwable cause) { super(message, cause); } /** * Constructs a new runtime exception with the specified cause and a * detail message of (cause==null ? null : cause.toString()) * (which typically contains the class and detail message of * cause). This constructor is useful for runtime exceptions * that are little more than wrappers for other throwables. * * @param cause the cause (which is saved for later retrieval by the * {@link #getCause()} method). (A null value is * permitted, and indicates that the cause is nonexistent or * unknown.) * @since 1.4 */ public FindAllUsersException(Throwable cause) { super(cause); } /** * Constructs a new runtime exception with the specified detail * message, cause, suppression enabled or disabled, and writable * stack trace enabled or disabled. * * @param message the detail message. * @param cause the cause. (A {@code null} value is permitted, * and indicates that the cause is nonexistent or unknown.) * @param enableSuppression whether or not suppression is enabled * or disabled * @param writableStackTrace whether or not the stack trace should * be writable * @since 1.7 */ protected FindAllUsersException(String message, Throwable cause, boolean enableSuppression, boolean writableStackTrace) { super(message, cause, enableSuppression, writableStackTrace); } }

package cn.javabs.store.execoption;

import java.sql.SQLException;

/**
 *  查询共有多少用户
 */
public class FindUserException extends RuntimeException {
    /**
     * Constructs a new runtime exception with {@code null} as its
     * detail message.  The cause is not initialized, and may subsequently be
     * initialized by a call to {@link #initCause}.
     */
    public FindUserException() {
        super();
    }

    /**
     * Constructs a new runtime exception with the specified detail message.
     * The cause is not initialized, and may subsequently be initialized by a
     * call to {@link #initCause}.
     *
     * @param message the detail message. The detail message is saved for
     *                later retrieval by the {@link #getMessage()} method.
     */
    public FindUserException(String message) {
        super(message);
    }

    /**
     * Constructs a new runtime exception with the specified detail message and
     * cause.  

Note that the detail message associated with * {@code cause} is not automatically incorporated in * this runtime exception's detail message. * * @param message the detail message (which is saved for later retrieval * by the {@link #getMessage()} method). * @param cause the cause (which is saved for later retrieval by the * {@link #getCause()} method). (A null value is * permitted, and indicates that the cause is nonexistent or * unknown.) * @since 1.4 */ public FindUserException(String message, Throwable cause) { super(message, cause); } /** * Constructs a new runtime exception with the specified cause and a * detail message of (cause==null ? null : cause.toString()) * (which typically contains the class and detail message of * cause). This constructor is useful for runtime exceptions * that are little more than wrappers for other throwables. * * @param cause the cause (which is saved for later retrieval by the * {@link #getCause()} method). (A null value is * permitted, and indicates that the cause is nonexistent or * unknown.) * @since 1.4 */ public FindUserException(Throwable cause) { super(cause); } /** * Constructs a new runtime exception with the specified detail * message, cause, suppression enabled or disabled, and writable * stack trace enabled or disabled. * * @param message the detail message. * @param cause the cause. (A {@code null} value is permitted, * and indicates that the cause is nonexistent or unknown.) * @param enableSuppression whether or not suppression is enabled * or disabled * @param writableStackTrace whether or not the stack trace should * be writable * @since 1.7 */ protected FindUserException(String message, Throwable cause, boolean enableSuppression, boolean writableStackTrace) { super(message, cause, enableSuppression, writableStackTrace); } }

package cn.javabs.store.execoption;

/**
 * 自定义异常
 */
public class PhoneServletException extends RuntimeException {
    /**
     * Constructs a new runtime exception with {@code null} as its
     * detail message.  The cause is not initialized, and may subsequently be
     * initialized by a call to {@link #initCause}.
     */
    public PhoneServletException() {
        super();
    }

    /**
     * Constructs a new runtime exception with the specified detail message.
     * The cause is not initialized, and may subsequently be initialized by a
     * call to {@link #initCause}.
     *
     * @param message the detail message. The detail message is saved for
     *                later retrieval by the {@link #getMessage()} method.
     */
    public PhoneServletException(String message) {
        super(message);
    }

    /**
     * Constructs a new runtime exception with the specified detail message and
     * cause.  

Note that the detail message associated with * {@code cause} is not automatically incorporated in * this runtime exception's detail message. * * @param message the detail message (which is saved for later retrieval * by the {@link #getMessage()} method). * @param cause the cause (which is saved for later retrieval by the * {@link #getCause()} method). (A null value is * permitted, and indicates that the cause is nonexistent or * unknown.) * @since 1.4 */ public PhoneServletException(String message, Throwable cause) { super(message, cause); } /** * Constructs a new runtime exception with the specified cause and a * detail message of (cause==null ? null : cause.toString()) * (which typically contains the class and detail message of * cause). This constructor is useful for runtime exceptions * that are little more than wrappers for other throwables. * * @param cause the cause (which is saved for later retrieval by the * {@link #getCause()} method). (A null value is * permitted, and indicates that the cause is nonexistent or * unknown.) * @since 1.4 */ public PhoneServletException(Throwable cause) { super(cause); } /** * Constructs a new runtime exception with the specified detail * message, cause, suppression enabled or disabled, and writable * stack trace enabled or disabled. * * @param message the detail message. * @param cause the cause. (A {@code null} value is permitted, * and indicates that the cause is nonexistent or unknown.) * @param enableSuppression whether or not suppression is enabled * or disabled * @param writableStackTrace whether or not the stack trace should * be writable * @since 1.7 */ protected PhoneServletException(String message, Throwable cause, boolean enableSuppression, boolean writableStackTrace) { super(message, cause, enableSuppression, writableStackTrace); } }

package cn.javabs.store.execoption;

import java.sql.SQLException;

/**
 *  
 */
public class UpdateUserDaoImplException extends RuntimeException{
    /**
     * Constructs a new runtime exception with {@code null} as its
     * detail message.  The cause is not initialized, and may subsequently be
     * initialized by a call to {@link #initCause}.
     */
    public UpdateUserDaoImplException() {
        super();
    }

    /**
     * Constructs a new runtime exception with the specified detail message.
     * The cause is not initialized, and may subsequently be initialized by a
     * call to {@link #initCause}.
     *
     * @param message the detail message. The detail message is saved for
     *                later retrieval by the {@link #getMessage()} method.
     */
    public UpdateUserDaoImplException(String message) {
        super(message);
    }

    /**
     * Constructs a new runtime exception with the specified detail message and
     * cause.  

Note that the detail message associated with * {@code cause} is not automatically incorporated in * this runtime exception's detail message. * * @param message the detail message (which is saved for later retrieval * by the {@link #getMessage()} method). * @param cause the cause (which is saved for later retrieval by the * {@link #getCause()} method). (A null value is * permitted, and indicates that the cause is nonexistent or * unknown.) * @since 1.4 */ public UpdateUserDaoImplException(String message, Throwable cause) { super(message, cause); } /** * Constructs a new runtime exception with the specified cause and a * detail message of (cause==null ? null : cause.toString()) * (which typically contains the class and detail message of * cause). This constructor is useful for runtime exceptions * that are little more than wrappers for other throwables. * * @param cause the cause (which is saved for later retrieval by the * {@link #getCause()} method). (A null value is * permitted, and indicates that the cause is nonexistent or * unknown.) * @since 1.4 */ public UpdateUserDaoImplException(Throwable cause) { super(cause); } /** * Constructs a new runtime exception with the specified detail * message, cause, suppression enabled or disabled, and writable * stack trace enabled or disabled. * * @param message the detail message. * @param cause the cause. (A {@code null} value is permitted, * and indicates that the cause is nonexistent or unknown.) * @param enableSuppression whether or not suppression is enabled * or disabled * @param writableStackTrace whether or not the stack trace should * be writable * @since 1.7 */ protected UpdateUserDaoImplException(String message, Throwable cause, boolean enableSuppression, boolean writableStackTrace) { super(message, cause, enableSuppression, writableStackTrace); } }

package cn.javabs.store.execoption;

import java.sql.SQLException;

/**
 * 用户激活码异常
 */
public class UserActiveCodeException extends RuntimeException {

    /**
     * Constructs a new runtime exception with {@code null} as its
     * detail message.  The cause is not initialized, and may subsequently be
     * initialized by a call to {@link #initCause}.
     */
    public UserActiveCodeException() {
        super();
    }

    /**
     * Constructs a new runtime exception with the specified detail message.
     * The cause is not initialized, and may subsequently be initialized by a
     * call to {@link #initCause}.
     *
     * @param message the detail message. The detail message is saved for
     *                later retrieval by the {@link #getMessage()} method.
     */
    public UserActiveCodeException(String message) {
        super(message);
    }

    /**
     * Constructs a new runtime exception with the specified detail message and
     * cause.  

Note that the detail message associated with * {@code cause} is not automatically incorporated in * this runtime exception's detail message. * * @param message the detail message (which is saved for later retrieval * by the {@link #getMessage()} method). * @param cause the cause (which is saved for later retrieval by the * {@link #getCause()} method). (A null value is * permitted, and indicates that the cause is nonexistent or * unknown.) * @since 1.4 */ public UserActiveCodeException(String message, Throwable cause) { super(message, cause); } /** * Constructs a new runtime exception with the specified cause and a * detail message of (cause==null ? null : cause.toString()) * (which typically contains the class and detail message of * cause). This constructor is useful for runtime exceptions * that are little more than wrappers for other throwables. * * @param cause the cause (which is saved for later retrieval by the * {@link #getCause()} method). (A null value is * permitted, and indicates that the cause is nonexistent or * unknown.) * @since 1.4 */ public UserActiveCodeException(Throwable cause) { super(cause); } /** * Constructs a new runtime exception with the specified detail * message, cause, suppression enabled or disabled, and writable * stack trace enabled or disabled. * * @param message the detail message. * @param cause the cause. (A {@code null} value is permitted, * and indicates that the cause is nonexistent or unknown.) * @param enableSuppression whether or not suppression is enabled * or disabled * @param writableStackTrace whether or not the stack trace should * be writable * @since 1.7 */ protected UserActiveCodeException(String message, Throwable cause, boolean enableSuppression, boolean writableStackTrace) { super(message, cause, enableSuppression, writableStackTrace); } }

package cn.javabs.store.execoption;

import java.sql.SQLException;

/**
 * 登录异常
 */
public class UserLoginException extends RuntimeException {
    /**
     * Constructs a new runtime exception with {@code null} as its
     * detail message.  The cause is not initialized, and may subsequently be
     * initialized by a call to {@link #initCause}.
     */
    public UserLoginException() {
        super();
    }

    /**
     * Constructs a new runtime exception with the specified detail message.
     * The cause is not initialized, and may subsequently be initialized by a
     * call to {@link #initCause}.
     *
     * @param message the detail message. The detail message is saved for
     *                later retrieval by the {@link #getMessage()} method.
     */
    public UserLoginException(String message) {
        super(message);
    }

    /**
     * Constructs a new runtime exception with the specified detail message and
     * cause.  

Note that the detail message associated with * {@code cause} is not automatically incorporated in * this runtime exception's detail message. * * @param message the detail message (which is saved for later retrieval * by the {@link #getMessage()} method). * @param cause the cause (which is saved for later retrieval by the * {@link #getCause()} method). (A null value is * permitted, and indicates that the cause is nonexistent or * unknown.) * @since 1.4 */ public UserLoginException(String message, Throwable cause) { super(message, cause); } /** * Constructs a new runtime exception with the specified cause and a * detail message of (cause==null ? null : cause.toString()) * (which typically contains the class and detail message of * cause). This constructor is useful for runtime exceptions * that are little more than wrappers for other throwables. * * @param cause the cause (which is saved for later retrieval by the * {@link #getCause()} method). (A null value is * permitted, and indicates that the cause is nonexistent or * unknown.) * @since 1.4 */ public UserLoginException(Throwable cause) { super(cause); } /** * Constructs a new runtime exception with the specified detail * message, cause, suppression enabled or disabled, and writable * stack trace enabled or disabled. * * @param message the detail message. * @param cause the cause. (A {@code null} value is permitted, * and indicates that the cause is nonexistent or unknown.) * @param enableSuppression whether or not suppression is enabled * or disabled * @param writableStackTrace whether or not the stack trace should * be writable * @since 1.7 */ protected UserLoginException(String message, Throwable cause, boolean enableSuppression, boolean writableStackTrace) { super(message, cause, enableSuppression, writableStackTrace); } }

filter

package cn.javabs.store.filter;

import javax.servlet.*;
import java.io.IOException;

/**
 * 字符编码过滤器
 *          目前的过滤器不能解决 采用get方法提交的汉字乱码问题
 *     1.定义变量:
 *     变量名称:filterConfig
 *     类型: FilterConfig
 *    2.初始化阶段方法: 进行this 调用
 *          this:filterConfig=filterConfig
 *    3.做过滤
 *              去web.xml 获取初始化参数 ending 赋值给ending变量
 *              判断:encoding 是否为空,若为空,则给定义为UTF-8
 *
 *
 *              放行:
 *              chain .dof
 */
public class CharacterEncodingFilter implements Filter {

    private FilterConfig filterConfig;

    /**
     * 初始化阶段
     * @param filterConfig
     * @throws ServletException
     */
    @Override
    public void init(FilterConfig filterConfig) throws ServletException {
            this.filterConfig=filterConfig;
    }

    /**
     *  初始阶段
     *
     * @throws IOException
     * @throws ServletException
     */
    @Override
    public void doFilter(ServletRequest request,  ServletResponse  response, FilterChain  chain) throws IOException, ServletException {
        String encoding =filterConfig.getInitParameter("encoding");
        if(encoding == null){
            encoding = "UTF-8";
        }
        request.setCharacterEncoding("utf-8");
        response.setCharacterEncoding("utf-8");
        response.setContentType("text/html;charset=utf-8");
        chain.doFilter(request,response);
    }

    /**
     *  销毁阶段
     */
    @Override
    public void destroy() {

    }
}

util

package cn.javabs.store.util;

import com.alibaba.druid.pool.DruidDataSourceFactory;

import javax.sql.DataSource;
import java.io.InputStream;
import java.sql.Connection;
import java.sql.SQLException;
import java.util.Properties;

/**
 * 工具类
 */
public class DruidUtil {

    // 1.定义全局变量 ds 类型 DataSource
    private  static DataSource ds;
    // 2. 定义静态代码块
    static {
        try {
            // 2.0 通过反射 db.properties 文件 返回一个io 流文件
            InputStream inputStream = DruidUtil.class.getClassLoader().getResourceAsStream("db.properties");
            // 2.1 找Properties类方法读取(加载)io  流
            // 2.1.1 创建 properties
            Properties p = new Properties();
            // 2.1.2 读取
            p.load(inputStream);
            // 2.2通过核心 [德鲁伊工厂]类创建  数据源 会返回一个 DataSource 类型
            ds = DruidDataSourceFactory.createDataSource(p);
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
    }
        // 3. 定义静态化: 获取数据源 方法 返回值类型为 DataSource
        public static DataSource getDataSource(){
        return ds;
        }

    // 4. 定义静态化: 获取连接  方法  返回值类型 Connection
        private  static Connection getConnection(){
            try {
                // 4.1 返回 ds  调用获取 连接   会有异常  进行抛异常
                return ds.getConnection();
            } catch (SQLException e) {
                throw new RuntimeException(e);
            }
        }
}


package cn.javabs.store.util;

import cn.javabs.store.entity.User;

import javax.mail.Message;
import javax.mail.MessagingException;
import javax.mail.Session;
import javax.mail.Transport;
import javax.mail.internet.InternetAddress;
import javax.mail.internet.MimeMessage;
import java.io.InputStream;
import java.util.Properties;

/**
 * 邮箱的工具类
 */
public class MailUtil extends Thread{
    private User user;


    public MailUtil(User user) {
        this.user = user;
    }
 
    //通过线程发送邮件
    public void run(){
        InputStream is = MailUtil.class.getClassLoader().getResourceAsStream("mail.properties");
        Properties p = new Properties();
        try {
            p.load(is);

            Session session = Session.getInstance(p);
            // 获取MimeMessage对象,通过该对象设置邮件内容
            MimeMessage message = new MimeMessage(session);

            String mailAddress = p.getProperty("mailAddress");


//            String mailContent = p.getProperty("mailContent");
            String username = p.getProperty("username");
            String password = p.getProperty("password");
            // 设置发件邮箱地址
            message.setFrom(new InternetAddress(mailAddress));
            // 设置发送方式  与  客户邮箱地址
            message.setRecipients(Message.RecipientType.TO,user.getEmail());
            // 邮件主题
            message.setSubject("一封来自爱尚手机商城的邮件");
            // 邮件内容
            message.setContent("点我去激活账号,不必回复我了","text/html;charset=utf-8");
            // 设置邮箱用户名和密码
            Transport transport = session.getTransport();
            transport.connect(username,password);
            // 发送,传入信息与收件人
            transport.sendMessage(message,message.getAllRecipients());
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
    }
}

categorysql

# 创建 数据库
create database store;

user store;

create table category(
        cid int primary key auto_increment,
        cname varchar  (50) not  null unique
);


# 手机表
CREATE table phone (
pid int  PRIMARY key  auto_increment,
pname VARCHAR (50) not  null unique,
pdescription VARCHAR(500),
price  DOUBLE,
stock  int  COMMENT '库存',
photoPath VARCHAR(200),
photoName VARCHAR(150),
cid int,
FOREIGN key (cid) REFERENCES  category(cid)

);

# 用户表
CREATE TABLE user(
uid int PRIMARY key  auto_increment,
username VARCHAR (50) not null UNIQUE,
PASSWORD VARCHAR(50) not null,
telephone VARCHAR(30),
email  VARCHAR (80) not NULL UNIQUE,
address VARCHAR(500),
code VARCHAR(50) not NULL,
actived bit(1)

);

<script type="text/javaScript">
    function deOneItem() {
        var sure = confirm("确定删除条数吗?")
        if(sure){
            window.location.herf="${ctx}/phoneServlet?methodName=delPhone&pid="+pid;

        }

    }
      商品图片 <img src="${ctx}/pic/${phone.photoName}"/><br/>

resource
db.properties

# 数据库 的链接信息参数配置 需要更改数据库名称和密码

driverClassName=com.mysql.jdbc.Driver

url=jdbc:mysql://127.0.0.1:3306/store
username=root

password=root

mail.properties

# 1.指定邮件发送协议
mail.transport.protocol=smtp
# 2.指定发件服务器地址,参数是规定的
mail.host=smtp.qq.com
# 3.请求服务器进行身份验证
mail.smtp.auth=true
# “------” 这个地方邮箱号
mailAddress=------@qq.com
# mailSubject=来自爱尚手机商城的邮件

# "------" 邮箱号
username=------
password=
webappp
commons

header.jsp

<%--
  Created by IntelliJ IDEA.
  User: love
  Date: 2020/5/28
  Time: 11:11
  To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>

<html>
<head>
    <title>Title</title>
</head>
<body>

</body>
</html>

page.jsp

<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>

<%--
  Created by IntelliJ IDEA.
  User: love
  Date: 2020/5/27
  Time: 11:10
  To change this template use File | Settings | File Templates.
--%>

<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<c:set value="${pageContext.request.contextPath}" var="cxt"></c:set>
<p align="center">
    第${page.currentPage}/共${page.totalPage}</p>
<p align="center">
    <a href="${cxt}${page.url}&pageNum=${page.prePageNum}">上一页</a>
    <a href="${cxt}${page.url}&pageNum=${page.nextPageNum}">下一页</a>
</p>
<html>
<body>

</body>
</html>

web-INF

addPhone.jsp

<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<%--
  Created by IntelliJ IDEA.
  User: love
  Date: 2020/5/27
  Time: 11:49
  To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<c:set value="${pageContext.request.contextPath}" var="ctx"></c:set>
<html>
<head>
    <title>添加商品页面</title>
</head>
<body>
    <form action="${ctx}/phoneServlet?methodName=addPhone" method="post" enctype="multipart/form-data">
       商品名称 <input type="text" name="pname"/><br/>
       商品描述 <input type="text" name="pdescription"/><br/>
       商品单价 <input type="text" name=price"/><br/>
       商品库存 <input type="text" name="stock"/><br/>
       商品图片 <input type="file" name="phonoName"/><br/>
        <select>
            <c:forEach items="${categoryList}" var="item">
                <option value="${item.cid}">${item.cname}</option>
            </c:forEach>
        </select>
        <input type="submit" value="添加商品">
    </form>
</body>
</html>

categorylist.jsp

<%--
  Created by IntelliJ IDEA.
  User: love
  Date: 2020/5/26
  Time: 9:50
  To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<c:set var="ctx" value="${pageContext.request.contextPath}"></c:set>
<html>
<head>
    <title>分类的列表</title>

</head>
<style>
    a:link{
        text-decoration: none;
        color: black;
    }
    a:hover{
        text-decoration: underline;
        color: red;
    }
    .cate-box{
        margin: 10px auto;
    }
    .add-cate-box{
        text-align: center;
    }
</style>
<body>
        <span class="add-cate-box">
            <form action="${ctx}/categoryServlet?methodName=addCategory" method="post">
                <input type="text" name="cname" placeholder="请填写类别名称..." style="line-height:30px;width: 484px"/>
                <input type="submit" value="添加类目">
            </form>
        </span>
        <span class="add-cate-box">
            <form action="${ctx}/categoryServlet?methodName=editCategory&cid=${data.cid}" method="post">
                <input type="text" name="cname" value="${data.cname}" placeholder="请填写新的类别名称..." style="line-height:30px;width: 484px"/>
                 <input type="submit" value="修改类目">
            </form>
        </span>
    <table class="cate-box" border="1px" width="600px" cellpadding="0" cellspacing="0">
        <thead>
        <tr>
            <th>
                <input type="checkbox">
            </th>
            <th>编号</th>
            <th>名称</th>
            <th>操作</th>
        </tr>
        </thead>
        <c:forEach var="c" items="${list}">
            <tr align="center">
                <td>
                    <input type="checkbox">
                </td>
                <td>${c.cid}</td>
                <td>${c.cname}</td>
                    <td>
                        <a href="${ctx}/categoryServlet?methodName=editCategoryView&cid=${c.cid}">修改</a>
                        <a href="${ctx}/categoryServlet?methodName=delCategory&cid=${c.cid}">删除</a>
                    </td>
            </tr>
        </c:forEach>
    </table>
</body>
</html>

catList.jsp

<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<%--
  Created by IntelliJ IDEA.
  User: love
  Date: 2020/5/29
  Time: 15:50
  To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<c:set var="ctx" value="${pageContext.request.contextPath}"></c:set>
<html>
<head>
    <title>购物车列表页面</title>
</head>
<body>
                        <%-- --%>
<%--    <c:if test="${sessionScope.cat}"></c:if>--%>


<table border="1px" width="600px">
    <tr>
        <th> <input type="checkbox">选择</th>
        <th>名称</th>
        <th>单间</th>
        <th>数量</th>
        <th>小计</th>
        <th>操作</th>
    </tr>
    <c:forEach items="${sessionScope.cart.item}" var="item">
    <tr align="center">
        <td>
            <input type="checkbox">
        </td>
        <td>${item.value.phone.pname}</td>
        <td>${item.value.phone.price}</td>
        <td>${item.value.phone.quantity}</td>
        <td>${item.value.phone. totlPrice}</td>
        <td>
            <a href="/phoneServlet?method=del">删除</a>
        </td>
    </tr>
    <tr center="right">
        <td colspan="6">1 件商品 ,付款金额399<a href="#">去付款</a>
        </td>
    </tr>
    </c:forEach>
</table>

</body>
</html>

editCategory.jsp

在这里插入代码片<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<%--
  Created by IntelliJ IDEA.
  User: love
  Date: 2020/5/28
  Time: 22:02
  To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<c:set value="${pageContext.request.contextPath}" var="ctx"></c:set>
<html>
<head>
    <title>修改分类</title>
</head>
<body>
<form action="${ctx}/categoryServlet?methodName=editCategory&cid=${category.cid}" method="post">
    分类名称:<input type="text" name="cname" value="${category.cname}">
    <input type="submit" value="修改">
</form>
</body>
</html>

index.jsp

<%--
  Created by IntelliJ IDEA.
  User: love
  Date: 2020/5/26
  Time: 9:28
  To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8"  language="java" %>
<html>
<head>
    <title>网页首页</title>
</head>
<body>
<%--        <a href="${pageContext.request.contextPath}/categoryServlet?methodName=findAllCategories">查询所有分类</a>--%>

<jsp:include page="/clientServlet">
    <jsp:param name="methodName" value="showIndex"/>
</jsp:include>

</body>
</html>

login.jsp

<%--
  Created by IntelliJ IDEA.
  User: love
  Date: 2020/5/29
  Time: 14:16
  To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%@ include file="commons/header.jsp"%>
<html>
<head>
    <title>用户登录</title>
</head>
<body>
    <form action="${pageContext.request.contextPath}" method="post">

        用户名: <input type="text" name="username"><br><br/>
      密码: <input type="text" name="password"><br/>
        <input type="submit" value="登录">
    </form>
</body>
</html>

main.jsp

<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<%--
  Created by IntelliJ IDEA.
  User: love
  Date: 2020/5/28
  Time: 8:28
  To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<c:set value="${pageContext.request.contextPath}" var="ctx"></c:set>
<%@include file="commons/header.jsp"%>
<html>
<head>
    <title>商品展示</title>
</head>
<body>
<c:if test="${USER != null}">
    亲爱的,${USER.usernmae},下午好!
    <a href="${ctx}/userServlet?method=logout">退出</a>
    <a href="${ctx}/userServlet?methodName=logout">退出</a>
</c:if>
<c:if test="${USUR == null}">
    赶紧去<A href="${pageContext.request.contextPath}/register.jsp">注册</A>
</c:if>
<center>
<a>所有分类</a>
<c:forEach items="${categoryList}" var="item">
    <a href="${ctx}/clientServlet?methodName=showCategoryPhones&cid=${item.cid}">${item.cname}</a>
</c:forEach>
   <table border="1px" cellspacing="0">
       <tr>
          <c:forEach items="${page.records}" var="item">
              <td>
                  <img src="C:\Users\love\IdeaProjects\store\src\main\webapp\upload\1.jpg" width="47px"/><br/>
                    名称:${item.pname}<br/>
                    描述:${item.pdescription}<br/>
                    单价:${item.price}<br/>
                   库存: ${item.stock}<br/>
                  <a href="${ctx}/clientServlet?methodName=byPhone&pid=${item.pid}">加入购物车</a>
                  <a>查看</a>
              </td>

          </c:forEach>
       </tr>
   </table>
<%--<p>--%>
<%--    第${page.currentPage}/共${page.totalPage}--%>
<%--</p>--%>
<p>
    <jsp:include page="commons/page.jsp"></jsp:include>
</p>
</center>
</body>
</html>

message,jsp

<%--
  Created by IntelliJ IDEA.
  User: love
  Date: 2020/5/27
  Time: 10:55
  To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<c:set var="ctx" value="${pageContext.request.contextPath}"></c:set>
<html>
<head>
    <title>Title</title>
</head>
<style>
        div ul{
            width: 980px;
            list-style: none;
            background-color: burlywood;
        }
    div ul li{
        margin-right: 50px;
        text-align: center;
        float: left;
    }
    h1{
        color: burlywood;
        text-align: center;
    }
</style>
<body>
${data}

<h1>一家手机店</h1>
<div align="center" style="background-color: antiquewhite;">

    <ul>
        <li>
            <a href="${ctx}">首页</a>
        </li>
        <li>
            <a href="${ctx}/login.jsp">登录</a>
        </li>
        <li>
            <a href="${ctx}/clientServlet?methodName=showCategoryPhones">订单</a>
        </li>
        <li>
            <a href="${ctx}/clientServlet?methodName=byphone&pid=${item.pid}">购物车</a>
        </li>
    </ul>
</div>
</body>
</html>

phoneEdit.jsp

<%--
  Created by IntelliJ IDEA.
  User: love
  Date: 2020/5/27
  Time: 10:55
  To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<c:set var="ctx" value="${pageContext.request.contextPath}"></c:set>
<html>
<head>
    <title>Title</title>
</head>
<style>
        div ul{
            width: 980px;
            list-style: none;
            background-color: burlywood;
        }
    div ul li{
        margin-right: 50px;
        text-align: center;
        float: left;
    }
    h1{
        color: burlywood;
        text-align: center;
    }
</style>
<body>
${data}

<h1>一家手机店</h1>
<div align="center" style="background-color: antiquewhite;">

    <ul>
        <li>
            <a href="${ctx}">首页</a>
        </li>
        <li>
            <a href="${ctx}/login.jsp">登录</a>
        </li>
        <li>
            <a href="${ctx}/clientServlet?methodName=showCategoryPhones">订单</a>
        </li>
        <li>
            <a href="${ctx}/clientServlet?methodName=byphone&pid=${item.pid}">购物车</a>
        </li>
    </ul>
</div>
</body>
</html>

phoneList.jsp

<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<%--
  Created by IntelliJ IDEA.
  User: love
  Date: 2020/5/27
  Time: 10:58
  To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<c:set value="${pageContext.request.contextPath}" var="cxt"></c:set>

<html>
<head>
    <title>商品的列表</title>
</head>
<body>
<jsp:include page="message.jsp"></jsp:include><br/>
<div align="center">
<table border="1px" width="600px" cellspacing="0">
        <thead>
        <tr>
<%--            <th><input type="checkbox"></th>--%>
            <th>编号</th>
            <th>名称</th>
            <th>描述</th>
            <th>单价</th>
            <th>创库</th>
            <th>图片</th>
            <th>所属分类</th>
            <th>操作</th>
        </tr>
</thead>
    <tbody>
        <c:forEach items="${page.records}" var="page">
        <tr>
<%--            <td><input type="checkbox"></td>--%>
            <td>${page.pid}</td>
            <td>${page.pname}</td>
            <td>${page.pdescription}</td>
            <td>${page.price}</td>
            <td>${page.stock}</td>
            <td>
                <img src="${page.photopath}/pic/${page.photoName}"/>
            </td>
            <td>${item.category.cname}</td>
           <td>
                <a href="JavaScript:delOneItem('${page.pid}')">删除</a>
                <a href="${cxt}/phoneServlet?methodName=editPhoneView&pid=${page.pid}">修改</a>
           </td>
            <td>
                <a href="${cxt}/phoneServlet?methodName=toAddPhonePage">添加</a>
            </td>
        </tr>
        </c:forEach>
        </tbody>
    </table>
</div>
    <jsp:include page="commons/page.jsp"></jsp:include>
</body>
</html>
<script type="text/javascript">
    function delOneItem(pid) {
        var  sure = confirm("确定删除吗?")
        if (sure){
            window.location.href="${cxt}/phoneServlet?methodName=delAllPhone&pid="+pid;
        }
    }

</script>

register.jsp

<%--
  Created by IntelliJ IDEA.
  User: love
  Date: 2020/5/29
  Time: 11:47
  To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
    <title>用户注册</title>
</head>
<body>
    <br/>
<br/>

<form action="${pageContext.request.contextPath}/userServlet?methodName=register" method="post">
    <table border="20px" cellspacing="20" cellpadding="20" width="600px">
        <tr>
            <td>用户码</td>
            <td>
                <input type="text" name="username"/>
            </td>
        </tr>
        <tr>
            <td>密码</td>
            <td>
                <input type="text" name="password"/>
            </td>
        </tr>
        <tr>
            <td>手机号</td>
            <td>
                <input type="text" name="telephone"/>
            </td>
        </tr>
        <tr>
            <td>电子邮箱</td>
            <td>
                <input type="text" name="email"/>
            </td>
        </tr>
        <tr>
            <td>家庭地址</td>
            <td>
                <input type="text" name="address/">
            </td>
        </tr>

        <tr>
            <td colspan="2">
            <input type="submit" value="注册"/>
            </td>
        </tr>
    </table>
</form>
</body>
</html>

test

java
testCategory
package cn.javabs.store.test;

import cn.javabs.store.entity.Category;
import cn.javabs.store.service.CategoryService;
import cn.javabs.store.service.impl.CategoryServiceImpl;
import org.junit.Test;

import java.util.List;

/**
 * 单元测试
 *      方法书写格式:
 *          1. 必须是public 作为权限修饰符
 *          2. 必须是 void 作为返回值类型关键字
 *          3.方法名称上必须有 @Test
 *          4. 方法名称 :没有硬性要求,但有做到见面
 *          格式:@Test
 *              public void  testFindAllCategories(){
 *
 *              }
 *
 *
 */
public class TestCategory {

    // 创建对象  new
    CategoryService categoryService  = new CategoryServiceImpl();

    /**
     *  查询全部
     */
    @Test
    public void  testFindAllCategories(){
        List<Category> list = categoryService.findAllCategories();
        System.out.println("从数据库查询的类目有"+list);
    }

    /**
     * 指定根据id查询
     */
    @Test
    public void testFindById(){
        Category category = categoryService.findCategoryById(2);
        System.out.println(category);
    }

    /**
     * 添加方法
     */
    @Test
    public void testAddCategory(){
        Category category = new Category(null,"摄像头");// 这是有参的构造方法

        int number = categoryService.addCategory(category);
        System.out.println("数据库插入"+number+"条语句");
    }

    /**
     *  修改方法
     */
    @Test
    public void testEditCategory(){
        Category category = new Category(2, "手机保护壳");
        int number = categoryService.editCategory(category);
        System.out.println("数据修改"+number+"条语句");
    }

    @Test
    public void  testCategoryDel(){
        int number = categoryService.delCategory(1);
        System.out.println("删除"+number+"条数据");
    }
}

testPhone
package cn.javabs.store.test;

import cn.javabs.store.commons.Page;
import cn.javabs.store.dao.PhoneDao;
import cn.javabs.store.dao.impl.PhoneDaoImpl;
import cn.javabs.store.entity.Category;
import cn.javabs.store.entity.Phone;
import cn.javabs.store.service.PhoneService;
import cn.javabs.store.service.impl.PhoneServiceImpl;
import org.junit.Test;

/**
 *  商品的单元测试类
 */
public class TestPhone {
    PhoneService phoneService = new PhoneServiceImpl();
    @Test
    public  void  testFindAllPhone(){


        String pageNum = "1";
        Page page = phoneService.findAllPhones(pageNum);
        System.out.println(page.getRecords());


    }

    /**
     *   根据ID 查询分页
     */
    @Test
    public  void  testFindPhoneById(){
        int pid = 5;
        Phone phone = phoneService.findPhoneById(pid);
        System.out.println(phone);

    }
    @Test
    public void  tessAddPhone(){
        Phone phone = new Phone();
        phone.setPname("小米10");
        phone.setPrice(599.1);
        Category category = new Category();
        category.setCid(3);
        phone.setCategory(category);
        int number = phoneService.addPhone(phone);
        System.out.println("数据插入"+number+"条数据");
    }
    /**
     *  修改商品
     */
    @Test
    public  void  testUpdatePhone(){
        Phone phone = new Phone();
        phone.setPid(10);
        phone.setPname("vivo X9");
        phone.setPrice(2300.00);
        phone.setPdescription("看见你");
        Category category = new Category();
        category.setCid(4);
        phone.setCategory(category);
        int number = phoneService.editPhone(phone);
        System.out.println("数据修改"+number+"条数据");
    }

    /**
     *  删除 商品
     */
    @Test
    public  void  testDeletePhone(){
        int id = 4;
        int number = phoneService.delPhone(id);
        System.out.println("删除了"+number+"条数据");
    }

    @Test
    public void  findAll2(){
        PhoneDao phoneDao = new PhoneDaoImpl();
     int pid = 5;
       Phone phone = phoneService.findPhoneById(pid);
        System.out.println(phone);
    }
}

userTest
package cn.javabs.store.test;

import cn.javabs.store.entity.User;
import cn.javabs.store.service.UserService;
import cn.javabs.store.service.impl.UserServiceImpl;
import org.junit.Test;

public class UserTest {
UserService userService = new UserServiceImpl();

@Test
public  void  registerUserTest(){
    User user = new User();
    user.setUsername("消亡");
    user.setPassword("147268");
    user.setEmail("[email protected]");
    user.setAddress("江南");
    user.setTelephone("18935223401");
    user.setCode("1234");
    userService.registerUser(user);


}

}


结构图
java web 实训 store 功能的介绍_第6张图片java web 实训 store 功能的介绍_第7张图片

你可能感兴趣的:(笔记)