书城管理系统(Java web 案例)
前言:
刚开始学Java Web,自己写的一个JSP小项目分享一下:
一、技术点
1、客户端:html、css、JavaScript、JQuery
http://ip:port/工程路径/资源路径
后端处理结果响应在客户端,解析展示在前端页面
2、JavaEE 项目的三层架构
Web层:Servlet程序、SpringMVC
(1) 获取请求参数,封装成为Bean对象
(2) 调用Service层处理业务
(3) 响应数据给客户端,请求转发/重定向
Service业务层:Spring
(1) 处理业务逻辑
(2) 调用持久层保存到数据库
DAO持久层:JDBC、DbUtils、Mybatis、HIbernate
负责与数据库交互,CRUD操作;增删改查
3、数据库:MySQL、Oracle、Sql Server
4、MVC 概念
MVC 全称:Model 模型、 View 视图、 Controller 控制器。
MVC 最早出现在 JavaEE 三层中的 Web 层,它可以有效的指导 Web 层的代码如何有效分离,单独工作。
(1) Model 模型:将与业务逻辑相关的数据封装为具体的 JavaBean 类,其中不掺杂任何与数据处理相关的代码 — JavaBean/domain/entity/pojo。
(2) View 视图:只负责数据和界面的显示,不接受任何与显示数据无关的代码,便于程序员和美工的分工合作 — JSP/HTML。
(3) Controller 控制器:只负责接收请求,调用业务层的代码处理请求,然后派发页面,是一个“调度者”的角色 —Servlet,转到某个页面,或者是重定向到某个页面。
二、用户注册和登陆
1、表单验证
(1) 验证用户名:必须由字母,数字下划线组成,并且长度为 5 到 12 位
(2) 验证密码:必须由字母,数字下划线组成,并且长度为 5 到 12 位
(3) 验证确认密码:和密码相同
(4) 邮箱验证:xxxxx@xxx.com
(5) 验证码:使用谷歌 kaptcha 生成图片验证码,判断验证码输入是否正确
2、用户注册
(1) 访问注册页面
(2) 填写注册信息,提交给服务器
(3) 服务器应该保存用户
(4) 当用户已经存在,提示用户注册失败,用户名已存在
(5) 当用户不存在,返回注册成功信息
3、用户登陆
(1) 访问登陆页面
(2) 填写用户名密码后提交
(3) 服务器判断用户是否存在
(4) 如果登陆失败,返回用户名或者密码错误信息
(5) 如果登录成功,返回登陆成功信息
三、创建书城需要的数据库和表
drop database if exists book;
create database book;
use book;
create table t_user(
`id` int primary key auto_increment,
`username` varchar(20) not null unique,
`password` varchar(32) not null,
`email` varchar(200),
`power` int
);
insert into t_user(`username`,`password`,`email`,`power`) values('admin','admin','admin@atanhui.com',2);
select * from t_user;
create table t_book(
`id` int primary key auto_increment,
`name` varchar(100),
`price` decimal(11,2),
`author` varchar(100),
`sales` int,
`stock` int,
`img_path` varchar(200) );
insert into t_book(`id` , `name` , `author` , `price` , `sales` , `stock` , `img_path`)
values(null , 'java 从入门到放弃' , '华仔' , 80 , 9999 , 9 , 'static/img/default.jpg');
create table t_order(
`order_id` varchar(50) primary key,
`create_time` datetime,
`price` decimal(11,2),
`status` int,
`user_id` int,
foreign key(`user_id`) references t_user(`id`)
);
create table t_order_item(
`id` int primary key auto_increment,
`name` varchar(100), `count` int,
`price` decimal(11,2),
`total_price` decimal(11,2),
`order_id` varchar(50),
foreign key(`order_id`)
references t_order(`order_id`)
);
四、编写数据库表对应的 JavaBean 对象
1、编写用户模块的 JavaBean
User.java
package com.atanhui.pojo;
public class User {
private Integer id;
private String username;
private String password;
private String email;
private Integer power
2、编写图书模块的 JavaBean
Book.java
package com.atanhui.pojo;
import java.math.BigDecimal;
public class Book {
private Integer id;
private String name;
private String author;
private BigDecimal price;
private Integer sales;
private Integer stock;
private String img_path = "static/img/default.jpg";
3、分页模型 Page 的抽取
package com.atanhui.pojo;
import java.util.List;
// page是分页的模型对象,<T>是具体的模块的javaBean类
public class Page<T> {
public static final Integer PAGE_SIZE = 4;
private String url;
// 当前页码
private Integer pageNo;
// 总页码
private Integer pageTotal;
// 页面大小
private Integer pageSize = PAGE_SIZE;
// 总记录数
private Integer pageTotalCount;
// 当前页面数据
private List<T> items;
4、编写购物车模块的 JavaBean
Cart.java
package com.atanhui.pojo;
import java.math.BigDecimal;
import java.util.*;
public class Cart {
// key 商品编号 value 商品信息
// map集合
private Map<Integer, CartItem> items = new LinkedHashMap<Integer, CartItem>();
// 添加商品项
public void addItem(CartItem cartItem) {
// 查看购物车中是否已经添加过此商品,如果已经添加,则数量更新,如果没有添加过,直接加入购物车即可
CartItem cartItem1 = items.get(cartItem.getId());
if (cartItem1 == null) {
// 之前没有添加此商品
items.put(cartItem.getId(), cartItem);
} else {
// 已经添加过此商品
cartItem1.setCount(cartItem1.getCount() + 1); // 数量累加
cartItem1.setTotalPrice(cartItem1.getTotalPrice().add(cartItem1.getPrice())); // 更新总金额
}
}
// 删除商品项
public void deleteItem(Integer id) {
items.remove(id);
}
// 清空购物车
public void clear() {
items.clear();
}
// 修改商品数量
public void updateCount(Integer id, Integer count) {
// 先查看购物车中是否有此商品
CartItem cartItem = items.get(id);
if (cartItem != null) {
// 如果商品存在,更新商品数量
cartItem.setCount(count);
cartItem.setTotalPrice(cartItem.getPrice().multiply(new BigDecimal(count)));
}
}
@Override
public String toString() {
return "Cart{" +
"totalCount=" + getTotalCount() +
", totalPrice=" + getTotalPrice() +
", items=" + items +
'}';
}
public Integer getTotalCount() {
Integer totalCount = 0;
// 方案一 遍历map集合 键值对 <key, value>
for (Map.Entry<Integer, CartItem> entry : items.entrySet()) {
CartItem cartItem = entry.getValue();
totalCount = cartItem.getCount() + totalCount;
}
return totalCount;
}
public BigDecimal getTotalPrice() {
BigDecimal totalPrice = new BigDecimal(0);
// 方案二 遍历map集合的value
for (CartItem cartItem : items.values()) {
totalPrice = cartItem.getTotalPrice().add(totalPrice);
}
return totalPrice;
}
public Map<Integer, CartItem> getItems() {
return items;
}
public void setItems(Map<Integer, CartItem> items) {
this.items = items;
}
public Cart(Map<Integer, CartItem> items) {
this.items = items;
}
public Cart() {
}
}
5、编写订单模块的 JavaBean
Order.java
package com.atanhui.pojo;
import java.math.BigDecimal;
import java.util.Date;
// 订单
public class Order {
private String orderId;
private Date createTime;
// 0 表示未发货;1 表示已发货;2 表示已签收
private BigDecimal price;
private Integer status = 0;
private Integer userId;
OrderItem.java
package com.atanhui.pojo;
import java.math.BigDecimal;
// 订单项
public class OrderItem {
private Integer id;
private String name;
private Integer count;
private BigDecimal price;
private BigDecimal totalPrice;
private String orderId;
五、编写工具类
1、编写 JdbcUtils 工具类
JdbcUtils.java
package com.atanhui.utils;
import com.alibaba.druid.pool.DruidDataSource;
import com.alibaba.druid.pool.DruidDataSourceFactory;
import java.io.InputStream;
import java.sql.Connection;
import java.util.Properties;
public class JdbcUtils {
// 数据库连接池
private static DruidDataSource dataSource;
private static ThreadLocal<Connection> conns = new ThreadLocal<Connection>();
static {
try {
Properties properties = new Properties();
// 读取jdbc.properties属性加载配置文件
InputStream inputStream = JdbcUtils.class.getClassLoader().getResourceAsStream("jdbc.properties");
// 从流中加载数据
properties.load(inputStream);
// 创建 数据库连接池
dataSource = (DruidDataSource) DruidDataSourceFactory.createDataSource(properties);
} catch (Exception e) {
e.printStackTrace();
}
}
/*
* 如果返回null,说明获取连接失败,有值就是获取连接成功
* 获取数据库连接池中的连接
*/
public static Connection getConnection(){
Connection conn = conns.get();
if (conn == null) {
try {
conn = dataSource.getConnection(); // 从数据库连接池中获取连接
conns.set(conn); // 保存到threadlocal对象中,用于后面的jdbc操作使用
conn.setAutoCommit(false); // 设置手动管理事务
} catch (Exception e) {
e.printStackTrace();
}
}
return conn;
}
/*
* 提交事务,关闭连接,放回数据连接池
*/
public static void commitAndClose(){
Connection conn = conns.get();
if (conn != null) { // 如果不等于null,说明之前使用过,操作过数据库
try {
conn.commit(); // 提交事务
} catch (Exception e) {
e.printStackTrace();
} finally {
try {
conn.close(); // 关闭连接
} catch (Exception e) {
e.printStackTrace();
}
}
}
// 一定要执行remove操作,否则会出错,因为Tomcat服务器底层使用了线程池技术
conns.remove();
}
/*
* 回滚事务,关闭连接,放回数据库连接池
*/
public static void rollbackAndClose(){
Connection conn = conns.get();
if (conn != null) { // 如果不等于null,说明之前使用过,操作过数据库
try {
conn.rollback(); // 回滚事务
} catch (Exception e) {
e.printStackTrace();
} finally {
try {
conn.close(); // 关闭连接
} catch (Exception e) {
e.printStackTrace();
}
}
}
// 一定要执行remove操作,否则会出错,因为Tomcat服务器底层使用了线程池技术
conns.remove();
}
}
2、编写 WebUtils 工具类
WebUtils.java
package com.atanhui.utils;
import org.apache.commons.beanutils.BeanUtils;
import java.util.Map;
public class WebUtils {
public static <T> T copyParamToBean(Map value, T bean) {
try {
System.out.println("注入之前"+bean);
// 把所有请求req的参数注入到JavaBean属性中
BeanUtils.populate(bean, value);
System.out.println("注入之后"+bean);
} catch (Exception e) {
e.printStackTrace();
}
return bean;
}
// 将字符串转化成为int类型的数据
public static int parseInt(String strInt, int defaultValve) {
try {
return Integer.parseInt(strInt);
} catch (NumberFormatException e) {
// e.printStackTrace();
}
return defaultValve;
}
public static void parseInt(String status) {
}
}
六、编写 Dao 层
1、抽取 BaseDao 程序
BaseDAO.java
package com.atanhui.dao.impl;
import com.atanhui.utils.JdbcUtils;
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.Connection;
import java.sql.SQLException;
import java.util.List;
public abstract class BaseDAO {
// DBUtils操作数据库
private QueryRunner queryRunner = new QueryRunner();
// update方法 用来执行insert update delete语句
// 如果return返回-1,说明执行失败,返回其他,表示返回影响的行数
public int update(String sql, Object...args) {
System.out.println("baseDAO程序在【" + Thread.currentThread().getName() + "】线程中");
Connection conn = JdbcUtils.getConnection();
try {
return queryRunner.update(conn, sql, args);
} catch (SQLException e) {
e.printStackTrace();
// 捕获异常,向外抛出异常
throw new RuntimeException(e);
}
}
// 查询一条javaBean的sql语句
// type 返回对象类型,sql 执行的sql语句,args sql对应的参数值,<T> 返回的类型的泛型
public <T> T queryForOne(Class<T> type, String sql, Object...args) {
Connection conn = JdbcUtils.getConnection();
try {
return queryRunner.query(conn, sql, new BeanHandler<T>(type), args);
} catch (Exception e) {
e.printStackTrace();
throw new RuntimeException(e);
}
}
// 查询多条javaBean的sql语句
// type 返回对象类型,sql 执行的sql语句,args sql对应的参数值,<T> 返回的类型的泛型
public <T> List<T> queryForList(Class<T> type, String sql, Object...args) {
Connection conn = JdbcUtils.getConnection();
try {
return queryRunner.query(conn, sql, new BeanListHandler<T>(type), args);
} catch (Exception e) {
e.printStackTrace();
throw new RuntimeException(e);
}
}
// 执行返回一行一列的sql语句
// sql 执行sql的语句,args sql对应的参数值
public Object queryForSingleValue(String sql, Object...args) {
Connection conn = JdbcUtils.getConnection();
try {
return queryRunner.query(conn, sql, new ScalarHandler(), args);
} catch (SQLException e) {
e.printStackTrace();
throw new RuntimeException(e);
}
}
}
2、编写用户模块的 Dao 和测试 Dao
UserDAOImpl.java
package com.atanhui.dao.impl;
import com.atanhui.dao.UserDAO;
import com.atanhui.pojo.User;
import java.util.List;
public class UserDAOImpl extends BaseDAO implements UserDAO {
@Override
public User queryUserByUsername(String username) {
String sql = "select id,username,password,email,power from t_user where username=?";
return queryForOne(User.class, sql, username);
}
@Override
public int saveUser(User user) {
String sql = "insert into t_user(username,password,email,power) values(?,?,?,?)";
return update(sql, user.getUsername(),user.getPassword(),user.getEmail(),user.getPower());
}
@Override
public User queryUserByUsernameAndPassword(String username, String password) {
String sql = "select id,username,password,email,power from t_user where username=? and password=?";
return queryForOne(User.class, sql, username, password);
}
@Override
public List<User> queryUser() {
String sql = "select id,username,password,email,power from t_user";
return queryForList(User.class, sql);
}
@Override
public int updateUser(User user) {
String sql = "update t_user set username=?, password=?, email=?, power=? where id=?";
return update(sql, user.getUsername(), user.getPassword(), user.getEmail(), user.getPower(), user.getId());
}
@Override
public int deleteUserById(Integer id) {
String sql = "delete from t_user where id=?";
return update(sql, id);
}
@Override
public User queryUserById(Integer id) {
String sql = "select id,username,password,email,power from t_user where id=?";
return queryForOne(User.class, sql, id);
}
@Override
public Integer queryForPageTotalCount() {
String sql = "select count(*) from t_user ";
Number count = (Number)queryForSingleValue(sql);
return count.intValue();
}
@Override
public List<User> queryForPageItems(int begin, int pageSize) {
String sql = "select id,username,password,email,power from t_user limit ? , ?";
return queryForList(User.class, sql, begin, pageSize);
}
}
3、编写图书模块的 Dao 和测试 Dao
BookDAOImpl.java
package com.atanhui.dao.impl;
import com.atanhui.dao.BookDAO;
import com.atanhui.pojo.Book;
import java.util.List;
public class BookDAOImpl extends BaseDAO implements BookDAO {
@Override
public int addBook(Book book) {
String sql = "insert into t_book(`name`, `author`, `price`, `sales`, `stock`, `img_path`) values(?,?,?,?,?,?)";
return update(sql, book.getName(),book.getAuthor(),book.getPrice(),book.getSales(),book.getStock(),book.getImg_path());
}
@Override
public int deleteBookById(Integer id) {
String sql = "delete from t_book where id=?";
return update(sql, id);
}
@Override
public int updateBook(Book book) {
System.out.println("bookDAO程序在【" + Thread.currentThread().getName() + "】线程中");
String sql = "update t_book set `name`=?, `author`=?, `price`=?, `sales`=?, `stock`=?, `img_path`=? where id=?";
return update(sql, book.getName(), book.getAuthor(), book.getPrice(), book.getSales(), book.getStock(), book.getImg_path(), book.getId());
}
@Override
public Book queryBookById(Integer id) {
String sql = "select `id`, `name`, `author`, `price`, `sales`, `stock`, `img_path` from t_book where id=?";
return queryForOne(Book.class, sql, id);
}
@Override
public List<Book> queryBooks() {
String sql = "select `id`, `name`, `author`, `price`, `sales`, `stock`, `img_path` from t_book";
return queryForList(Book.class, sql);
}
@Override
public Integer queryForPageTotalCount() {
String sql = "select count(*) from t_book ";
Number count = (Number)queryForSingleValue(sql);
return count.intValue();
}
@Override
public List<Book> queryForPageItems(int begin, int pageSize) {
String sql = "select `id`, `name`, `author`, `price`, `sales`, `stock`, `img_path` from t_book limit ? , ?";
return queryForList(Book.class, sql, begin, pageSize);
}
@Override
public Integer queryForPageTotalCountByPrice(int min, int max) {
String sql = "select count(*) from t_book where price between ? and ? ";
Number count = (Number)queryForSingleValue(sql, min, max);
return count.intValue();
}
@Override
public List<Book> queryForPageItemsByPrice(int begin, int pageSize, int min, int max) {
String sql = "select `id`, `name`, `author`, `price`, `sales`, `stock`, `img_path` from t_book where price between ? and ? order by price limit ? , ?";
return queryForList(Book.class, sql, min, max, begin, pageSize);
}
}
4、编写订单模块的 Dao 和测试 Dao
OrderDAOImpl.java
package com.atanhui.dao.impl;
import com.atanhui.dao.OrderDAO;
import com.atanhui.pojo.Order;
import java.util.List;
public class OrderDAOImpl extends BaseDAO implements OrderDAO {
@Override
public int saveOrder(Order order) {
System.out.println("orderDAO程序在【" + Thread.currentThread().getName() + "】线程中");
String sql = "insert into t_order(`order_id`, `create_time`, `price`, `status`, `user_id`) values(?, ?, ?, ?, ?)";
int update = update(sql, order.getOrderId(), order.getCreateTime(), order.getPrice(), order.getStatus(), order.getUserId());
return update;
}
@Override
public List<Order> queryOrder() {
String sql = "select `order_id` orderId, `create_time` createTime, `price`, `status`, `user_id` userId from t_order";
return queryForList(Order.class, sql);
}
@Override
public int changeOrderStatus(String orderId, Integer status) {
String sql = "update t_order set `status`=? where `order_id`=?";
return update(sql, status, orderId);
}
@Override
public List<Order> queryOrderByUserId(Integer userId) {
String sql = "select `order_id` orderId, `create_time` createTime, `price`, `status`, `user_id` userId from t_order where `user_id`=?";
return queryForList(Order.class, sql, userId);
}
}
OrderItemDAOImpl.java
package com.atanhui.dao.impl;
import com.atanhui.dao.OrderItemDAO;
import com.atanhui.pojo.OrderItem;
import java.util.List;
public class OrderItemDAOImpl extends BaseDAO implements OrderItemDAO {
@Override
public int saveOrderItem(OrderItem orderItem) {
System.out.println("orderItemDAO程序在【" + Thread.currentThread().getName() + "】线程中");
String sql = "insert into t_order_item(`name`, `count`, `price`, `total_price`, `order_id`) values(?, ?, ?, ?, ?)";
int update = update(sql, orderItem.getName(), orderItem.getCount(), orderItem.getPrice(), orderItem.getTotalPrice(), orderItem.getOrderId());
return update;
}
@Override
public List<OrderItem> queryOrderItemByOrderId(String orderId) {
String sql = "select `name`, `count`, `price`, `total_price` totalPrice, `order_id` orderId from t_order_item where order_id=?";
return queryForList(OrderItem.class, sql, orderId);
}
}
七、编写 Service 层
1、编写用户模块的 Service 和测试 Service
UserServiceImpl.java
package com.atanhui.service;
import com.atanhui.dao.UserDAO;
import com.atanhui.dao.impl.UserDAOImpl;
import com.atanhui.pojo.Page;
import com.atanhui.pojo.User;
import com.atanhui.service.UserService;
import java.util.List;
public class UserServiceImpl implements UserService {
private UserDAO userDAO = new UserDAOImpl();
@Override
public int registUser(User user) {
return userDAO.saveUser(user);
}
@Override
public User login(User user) {
return userDAO.queryUserByUsernameAndPassword(user.getUsername(),user.getPassword());
}
@Override
public boolean existsUsername(String username) {
if (userDAO.queryUserByUsername(username)==null) {
// 等于null,说明没查到,没查到表示可用
return false;
} else {
return true;
}
}
@Override
public int updateUser(User user) {
return userDAO.updateUser(user);
}
@Override
public int deleteUserById(Integer id) {
return userDAO.deleteUserById(id);
}
@Override
public User queryUserById(Integer id) {
return userDAO.queryUserById(id);
}
@Override
public List<User> queryUser() {
return userDAO.queryUser();
}
@Override
public Page<User> page(int pageNo, int pageSize) {
Page<User> page = new Page<User>();
page.setPageSize(pageSize);
Integer pageTotalCount = userDAO.queryForPageTotalCount();
page.setPageTotalCount(pageTotalCount);
int pageTotal = pageTotalCount / pageSize;
if (pageTotalCount%pageSize > 0){
pageTotal++;
}
page.setPageTotal(pageTotal);
page.setPageNo(pageNo);
int begin = (pageNo-1)*page.getPageSize();
List<User> items = userDAO.queryForPageItems(begin, pageSize);
page.setItems(items);
return page;
}
}
2、编写图书模块的 Service 和测试 Service
BookServiceImpl.java
package com.atanhui.service.impl;
import com.atanhui.dao.BookDAO;
import com.atanhui.dao.impl.BookDAOImpl;
import com.atanhui.pojo.Book;
import com.atanhui.pojo.Page;
import com.atanhui.service.BookService;
import java.util.List;
public class BookServiceImpl implements BookService {
// service 依赖于 dao
private BookDAO bookDAO = new BookDAOImpl();
@Override
public void addBook(Book book) {
bookDAO.addBook(book);
}
@Override
public void deleteBookById(Integer id) {
bookDAO.deleteBookById(id);
}
@Override
public void updateBook(Book book) {
bookDAO.updateBook(book);
}
@Override
public Book queryBookById(Integer id) {
return bookDAO.queryBookById(id);
}
@Override
public List<Book> queryBooks() {
return bookDAO.queryBooks();
}
@Override
public Page<Book> page(int pageNo, int pageSize) {
Page<Book> page = new Page<Book>();
page.setPageSize(pageSize);
// 求总记录数
Integer pageTotalCount = bookDAO.queryForPageTotalCount();
page.setPageTotalCount(pageTotalCount);
// 求总页码
int pageTotal = pageTotalCount / pageSize;
if (pageTotalCount%pageSize > 0){
pageTotal++;
}
page.setPageTotal(pageTotal);
// 设置 当前页码,页面大小
page.setPageNo(pageNo);
// 当前页面数据
int begin = (pageNo-1)*page.getPageSize();
List<Book> items = bookDAO.queryForPageItems(begin, pageSize);
page.setItems(items);
return page;
}
@Override
public Page<Book> pageByPrice(int pageNo, int pageSize, int min, int max) {
Page<Book> page = new Page<Book>();
page.setPageSize(pageSize);
// 求总记录数
Integer pageTotalCount = bookDAO.queryForPageTotalCountByPrice(min, max);
page.setPageTotalCount(pageTotalCount);
// 求总页码
int pageTotal = pageTotalCount / pageSize;
if (pageTotalCount%pageSize > 0){
pageTotal++;
}
page.setPageTotal(pageTotal);
// 设置 当前页码,页面大小
page.setPageNo(pageNo);
// 当前页面数据
int begin = (pageNo-1)*page.getPageSize();
List<Book> items = bookDAO.queryForPageItemsByPrice(begin, pageSize, min, max);
page.setItems(items);
return page;
}
}
3、编写订单模块的 Service 和测试 Service
OrderServiceImpl.java
ackage com.atanhui.service.impl;
import com.atanhui.dao.BookDAO;
import com.atanhui.dao.OrderDAO;
import com.atanhui.dao.OrderItemDAO;
import com.atanhui.dao.impl.BookDAOImpl;
import com.atanhui.dao.impl.OrderDAOImpl;
import com.atanhui.dao.impl.OrderItemDAOImpl;
import com.atanhui.pojo.*;
import com.atanhui.service.OrderService;
import java.util.Date;
import java.util.List;
public class OrderServiceImpl implements OrderService {
private OrderDAO orderDAO = new OrderDAOImpl();
private OrderItemDAO orderItemDAO = new OrderItemDAOImpl();
private BookDAO bookDAO = new BookDAOImpl();
@Override
public String createOrder(Cart cart, Integer id) {
System.out.println("orderService程序在【" + Thread.currentThread().getName() + "】线程中");
// 订单号唯一性
String orderId = System.currentTimeMillis()+""+id;
// 创建一个订单对象
Order order = new Order(orderId, new Date(), cart.getTotalPrice(), 0, id);
orderDAO.saveOrder(order);
// int i = 15 / 0;
// 遍历购物车中每一个商品项转换成订单项保存到数据库中
for (CartItem value : cart.getItems().values()) {
// 获取每一个购物车中的商品项 转换成每一个订单项
OrderItem orderItem = new OrderItem(null, value.getName(), value.getCount(), value.getPrice(), value.getTotalPrice(), orderId);
// 保存订单项到数据库
orderItemDAO.saveOrderItem(orderItem);
// 更新库存 销量
Book book = bookDAO.queryBookById(value.getId());
book.setSales(book.getSales()+value.getCount());
book.setStock(book.getStock()-value.getCount());
bookDAO.updateBook(book);
}
// 清空购物车
cart.clear();
return orderId;
}
@Override
public List<Order> showAllOrder() {
return orderDAO.queryOrder();
}
@Override
public int sendOrder(String orderId) {
return orderDAO.changeOrderStatus(orderId, 1);
}
@Override
public List<OrderItem> showOrderDetail(String orderId) {
return orderItemDAO.queryOrderItemByOrderId(orderId);
}
@Override
public List<Order> showMyOrders(Integer userId) {
return orderDAO.queryOrderByUserId(userId);
}
@Override
public int receiverOrder(String orderId) {
return orderDAO.changeOrderStatus(orderId, 2);
}
}
八、编写 web 层
1、抽取 BaseServlet 程序
BaseServlet.java
package com.atanhui.web;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.lang.reflect.Method;
public abstract class BaseServlet extends HttpServlet {
protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
req.setCharacterEncoding("utf-8");
resp.setContentType("text/html;charset=utf-8");
String action = req.getParameter("action");
try {
Method method = this.getClass().getDeclaredMethod(action, HttpServletRequest.class, HttpServletResponse.class);
method.invoke(this, req, resp);
} catch (Exception e) {
e.printStackTrace();
throw new RuntimeException(e); // 吧异常抛给FIlter
}
}
}
2、编写用户模块的 Web 层,和页面联调测试
UserServlet.java
package com.atanhui.web;
import com.atanhui.pojo.Page;
import com.atanhui.pojo.User;
import com.atanhui.service.UserService;
import com.atanhui.service.impl.UserServiceImpl;
import com.atanhui.utils.WebUtils;
import com.google.gson.Gson;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
public class UserServlet extends BaseServlet {
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
req.setCharacterEncoding("utf-8");
resp.setContentType("text/html;charset=utf-8");
super.doPost(req, resp);
}
private UserService userService = new UserServiceImpl();
// 查看所有用户
protected void showAllUsers(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
List<User> users = userService.queryUser();
req.setAttribute("users", users);
req.getRequestDispatcher("/pages/manager/user_manager.jsp").forward(req, resp);
}
protected void page(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
// 获取请求的参数
int pageNo = WebUtils.parseInt(req.getParameter("pageNo"), 1);
int pageSize = WebUtils.parseInt(req.getParameter("pageSize"), Page.PAGE_SIZE);
Page<User> page = userService.page(pageNo, pageSize);
page.setUrl("manager/userServlet?action=page");
req.setAttribute("page", page);
req.getRequestDispatcher("/pages/manager/user_manager.jsp").forward(req, resp);
}
protected void deleteUser(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
int id = WebUtils.parseInt(req.getParameter("id"), 0);
userService.deleteUserById(id);
resp.sendRedirect(req.getContextPath()+"/manager/userServlet?action=page&pageNo="+req.getParameter("pageNo"));
}
protected void getUser(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
int id = WebUtils.parseInt(req.getParameter("id"), 0);
User user = userService.queryUserById(id);
req.setAttribute("user", user);
req.getRequestDispatcher("/pages/manager/user_edit.jsp").forward(req, resp);
}
protected void updateUser(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
User user = WebUtils.copyParamToBean(req.getParameterMap(), new User());
userService.updateUser(user);
resp.sendRedirect(req.getContextPath()+"/manager/userServlet?action=page&pageNo="+req.getParameter("pageNo"));
}
protected void addUser(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
// *********
int pageNo = WebUtils.parseInt(req.getParameter("pageTotal"), 0);
pageNo = pageNo + 1;
User user = WebUtils.copyParamToBean(req.getParameterMap(), new User());
userService.registUser(user);
resp.sendRedirect(req.getContextPath()+"/manager/userServlet?action=page&pageNo="+pageNo);
}
protected void ajaxExistsUsername(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
// 获取请求的参数
String username = req.getParameter("username");
// 调用userService.existsUsername(username)
boolean existsUsername = userService.existsUsername(username);
// 把返回的结果封装成为map对象
Map<String, Object> resultMap = new HashMap<>();
resultMap.put("existsUsername", existsUsername);
Gson gson = new Gson();
String json = gson.toJson(resultMap);
resp.getWriter().write(json);
}
}
用户分页查询
用户添加
用户修改
用户删除
3、编写图书模块的 Web 层,和页面联调测试
BookServlet.java
package com.atanhui.web;
import com.atanhui.pojo.Book;
import com.atanhui.pojo.Page;
import com.atanhui.service.BookService;
import com.atanhui.service.impl.BookServiceImpl;
import com.atanhui.utils.WebUtils;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.util.List;
public class BookServlet extends BaseServlet {
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
req.setCharacterEncoding("utf-8");
resp.setContentType("text/html;charset=utf-8");
super.doPost(req, resp);
}
private BookService bookService = new BookServiceImpl();
// 处理分页功能
protected void page(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
// 1 获取请求的参数
int pageNo = WebUtils.parseInt(req.getParameter("pageNo"), 1);
int pageSize = WebUtils.parseInt(req.getParameter("pageSize"), Page.PAGE_SIZE);
// 2 调用BookService.page(pageNo, pageSize)返回page对象
Page<Book> page = bookService.page(pageNo, pageSize);
page.setUrl("manager/bookServlet?action=page");
// 3 保存page对象到request域中
req.setAttribute("page", page);
// 4 请求转发到page/manager/book_manager.jsp页面
req.getRequestDispatcher("/pages/manager/book_manager.jsp").forward(req, resp);
}
protected void add(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
// System.out.println(req.getParameter("name")); *****
int pageNo = WebUtils.parseInt(req.getParameter("pageTotal"), 0);
Book book = WebUtils.copyParamToBean(req.getParameterMap(), new Book());
bookService.addBook(book);
// 重定向
resp.sendRedirect(req.getContextPath()+"/manager/bookServlet?action=page&pageNo="+pageNo);
}
protected void delete(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
// 获取请求参数
String id = (String) req.getParameter("id");
int i = WebUtils.parseInt(id, 0);
// 调用bookService.deleteBookById()
bookService.deleteBookById(i);
// 重定向回图书列表管理页面
resp.sendRedirect(req.getContextPath()+"/manager/bookServlet?action=page&pageNo="+req.getParameter("pageNo"));
}
protected void getBook(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
// 获取请求的参数,图书编号
String id = req.getParameter("id");
int i = WebUtils.parseInt(id, 0);
// 调用bookService.queryBookById查询图书
Book book = bookService.queryBookById(i);
// 保存图书到request域中
req.setAttribute("book", book);
// 请求转发到 pages/manager/book_edit.jsp页面
req.getRequestDispatcher("/pages/manager/book_edit.jsp").forward(req, resp);
}
protected void update(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
// 获取请求的参数=对象成为Book对象
Book book = WebUtils.copyParamToBean(req.getParameterMap(), new Book());
// 调用BookService.updateBook(),修改图书
bookService.updateBook(book);
// 重定向回图书列表管理页面
// 地址: /工程名/manager/bookService?action=list
resp.sendRedirect(req.getContextPath()+"/manager/bookServlet?action=page&pageNo="+req.getParameter("pageNo"));
}
protected void list(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
// 通过BookService查询全部图书
List<Book> books = bookService.queryBooks();
// 把全部图书保存到request域中
req.setAttribute("books", books);
// 请求转发到/pages/manager/book_manager.jsp页面
req.getRequestDispatcher("/pages/manager/book_manager.jsp").forward(req, resp);
}
}
图书分页查询
图书添加
图书修改
图书删除
4、编写购物车模块的 Web 层,和页面联调测试
CartServlet.java
package com.atanhui.web;
import com.atanhui.pojo.Book;
import com.atanhui.pojo.Cart;
import com.atanhui.pojo.CartItem;
import com.atanhui.service.BookService;
import com.atanhui.service.impl.BookServiceImpl;
import com.atanhui.utils.WebUtils;
import com.google.gson.Gson;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.util.HashMap;
import java.util.Map;
public class CartServlet extends BaseServlet {
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
req.setCharacterEncoding("utf-8");
resp.setContentType("text/html;charset=utf-8");
super.doPost(req, resp);
}
BookService bookService = new BookServiceImpl();
protected void AjaxaddItem(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
// 获取商品编号
int id = WebUtils.parseInt(req.getParameter("id"), 0);
// 调用 bookService.queryBookById(id) Book
Book book = bookService.queryBookById(id);
// 把book对象转换成cartItem
CartItem cartItem = new CartItem(book.getId(), book.getName(), 1, book.getPrice(), book.getPrice());
// 获取session中的购物车对象cart
Cart cart = (Cart) req.getSession().getAttribute("cart");
if (cart == null) {
cart = new Cart();
req.getSession().setAttribute("cart", cart);
}
// 调用cart.addItem(cartItem) 添加购物车
cart.addItem(cartItem);
// 返回购物车中总商品数量和最后一个添加的商品名称
Map<String, Object> resultmap = new HashMap<String, Object>();
resultmap.put("lastName", cartItem.getName());
resultmap.put("totalCount", cart.getTotalCount());
Gson gson = new Gson();
String resultmapJson = gson.toJson(resultmap);
resp.getWriter().write(resultmapJson);
}
// 加入购物车
protected void addItem(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
// 获取请求的参数,商品编号
int id = WebUtils.parseInt(req.getParameter("id"), 0);
// 调用bookService.queryBookById(id) 得到图书的信息
Book book = bookService.queryBookById(id);
// 把图书信息转化成为cartItem商品项
CartItem cartItem = new CartItem(book.getId(), book.getName(), 1, book.getPrice(), book.getPrice());
// 调用Cart.addItem(cartItem),添加商品项
Cart cart = (Cart) req.getSession().getAttribute("cart");
if (cart == null) {
cart = new Cart();
req.getSession().setAttribute("cart", cart);
}
cart.addItem(cartItem);
// 最后一个添加的商品名称 添加到session域中
req.getSession().setAttribute("lastName", cartItem.getName());
// 重定向回到原来的商品列表页面
// Referer 请求头Referer
// 重定向 不支持request域 数据共享
resp.sendRedirect(req.getHeader("Referer"));
}
// 删除商品项
protected void deleteItem(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
// 获取商品编号
int id = WebUtils.parseInt(req.getParameter("id"), 0);
Cart cart = (Cart) req.getSession().getAttribute("cart");
if (cart != null) {
cart.deleteItem(id);
}
// 重定向为购物车原来展示页面
resp.sendRedirect(req.getHeader("Referer"));
}
// 清空购物车
protected void clear(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
// 获取购物车对象
Cart cart = (Cart)req.getSession().getAttribute("cart");
// 判断购物车是否为空?
if (cart != null) {
cart.clear();
resp.sendRedirect(req.getHeader("Referer"));
}
}
// 修改商品数量
protected void updateCount(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
// 获取商品编号,商品数量
int id = WebUtils.parseInt(req.getParameter("id"), 0);
int count = WebUtils.parseInt(req.getParameter("count"), 0);
// 获取Cart购物车对象
Cart cart = (Cart) req.getSession().getAttribute("cart");
// 判断购物车是否为空
if (cart != null){
// 更新购物车
cart.updateCount(id, count);
resp.sendRedirect(req.getHeader("Referer"));
}
}
}
加入购物车
删除商品项
清空购物车
修改商品数量
5、编写订单模块的 web 层和页面联调
OrderServlet.java
package com.atanhui.web;
import com.atanhui.pojo.*;
import com.atanhui.service.OrderService;
import com.atanhui.service.UserService;
import com.atanhui.service.impl.OrderServiceImpl;
import com.atanhui.service.impl.UserServiceImpl;
import com.atanhui.utils.WebUtils;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import java.io.IOException;
import java.util.List;
public class OrderServlet extends BaseServlet{
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
req.setCharacterEncoding("utf-8");
resp.setContentType("text/html;charset=utf-8");
super.doPost(req, resp);
}
OrderService orderService = new OrderServiceImpl();
UserService userService = new UserServiceImpl();
// 生成订单
protected void createOrder(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
// 获取cart购物车对象
HttpSession session = req.getSession();
Cart cart = (Cart)session.getAttribute("cart");
// 获取用户UseId
User LoginUser = (User)session.getAttribute("user");
if (LoginUser!=null) {
System.out.println("orderServlet程序在【" + Thread.currentThread().getName() + "】线程中");
String orderId = orderService.createOrder(cart, LoginUser.getId());
session.setAttribute("orderId", orderId);
// 重定向/pages/cart/checkout.jsp
resp.sendRedirect(req.getContextPath() + "/pages/cart/checkout.jsp");
} else {
req.getRequestDispatcher("/pages/user/login.jsp").forward(req, resp);
}
}
// 查看所有订单
protected void showAllOrders(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
List<Order> orders = orderService.showAllOrder();
req.setAttribute("orders", orders);
req.getRequestDispatcher("/pages/manager/order_manager.jsp").forward(req, resp);
}
// 查看我的订单
protected void showMyOrders(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
User LoginUser = (User)req.getSession().getAttribute("user");
if(LoginUser!=null) {
List<Order> myOrders = orderService.showMyOrders(LoginUser.getId());
req.setAttribute("myOrders", myOrders);
req.getRequestDispatcher("/pages/order/order.jsp").forward(req, resp);
} else {
req.getRequestDispatcher("/pages/user/login.jsp").forward(req, resp);
}
}
protected void showOrderDetail(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
String orderId = req.getParameter("orderId");
List<OrderItem> orderItems = orderService.showOrderDetail(orderId);
req.setAttribute("orderItems", orderItems);
req.getRequestDispatcher("/pages/order/order_detail.jsp").forward(req, resp);
}
protected void receiverOrSignOrRefundOrder(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
String orderId = req.getParameter("orderId");
int status = WebUtils.parseInt(req.getParameter("status"), 0);
if (status==0) {
int send = orderService.sendOrder(orderId);
} else if (status==1) {
int receiver = orderService.receiverOrder(orderId);
} else {
}
resp.sendRedirect(req.getHeader("Referer"));
}
}
生成订单
查看所有订单
查看订单详情