在csdn上记一次自己的课程设计过程(已经实习两个月了、感觉这个很容易做。支付可能需要多花点时间、):

在此框架基础之上权限认证管理设置成功:https://blog.csdn.net/weixin_43304253/article/details/121111530
动态搜索书籍信息(包括在一定价格范围内查询):https://blog.csdn.net/weixin_43304253/article/details/120920214
课程名称:企业项目实训II
设计题目:大学当图书商城

已知技术参数和设计要求:

1.问题描述(功能要求):
1.1 顾客端
1)注册登录:游客可浏览所有图书,只有注册用户才能添加购物车、下订单购买、评论;
2)图书分类浏览:图书分三个层级进行分类浏览;
3)动态搜索图书:可以按书名、作者、出版社及价格范围进行搜索,搜索的图书分页显示;
4)图书详情:可从图书列表中进一步看到图书的详细信息,包括书号、书名、作者、出版社、印次、内容简介等信息;
5)添加并管理购物车:登录用户可以选择图书加入到购物车,并可对购物车的图书进行增删改查的操作;
6)下订单:登录用户可对图书进行下订单,同时可查看订单当前的状态,订单状态包括待付款(模拟)、待发货(模拟)、待收货(模拟)、待评论;
7)模拟支付:所有注册用户都有一个余额钱包,可模拟充值,充值记录保存下来并可查看,利用余额钱包进行付款。或者使用支付宝的模拟支付接口进行支付;
8)商品评论:购买完图书后进行评价,给一个1-5等级及相应的评论内容。
1.2商家
1)商家注册登录:注册信息包括商家名称,商家地址、经营类型、注册资金、log图片等基本信息,刚注册的商家处于未审核状态,只有等待区域运营方审核后才能正常登录。区域运营方由管理员在后台直接添加;
2)商家管理自家商品:可对商品进行相应的增、删、改、查的操作;
3)商家管理自家店铺:商家可根据平台提供的模板,对店铺进行管理;
4)商家管理订单:商家可对顾客下的订单进行相应的操作,如查看订单、发货(模拟)、查看评论。

  1. 运行环境要求:
    (1)客户端:
    Windows操作系统
    浏览器
    (2)服务器:
    windows操作系统
    Tomcat 服务器
    MySQL 数据库服务器

  2. 技术要求:
    (1)需求分析规格说明书与用例规约
    (2)系统数据库设计,时序图,类图
    (3)系统采用SSM框架技术,完整编码(采用spring boot和vue)
    (4)为保证系统安全性,要求用到日志
    (5)在必要地方使用事务技术
    (6)在必要地方使用2个以上设计模式

设计工作量:
8周

工作计划:
共安排8周时间进行集中实训,软件开发步骤如下,
第1-2周:需求分析、数据库设计、系统设计
第3-7周:编码
第8周:系统测试、答辩、撰写设计说明书

工作进展:在开始编辑这篇文章的时候、距离课程设计已经过了两个周(本人在实习、只能抽出空闲时间来写和周六、周日的时间)现在这个系统的后台逻辑几乎都实现了、还有支付功能未实现。前端页面的美化后来进一步处理吧。

目前的目录结构、后续还需要改进


1、搭建框架
(我花了一天的时间将整个项目的框架搭建起来、使用spring boot整合mybatis、thymeleaf和shiro)
使用spring boot是真的爽到上天、spring简直就是配置地狱。

  • 整合mybatis的目的是简化sql的编写管理
  • 整合thymeleaf的目的是数据的交互
  • 整合shiro的目的是简化权限认证以及授权…

使用到的maven依赖

    <dependencies><!--整合shirosubject:用户security manager:管理所有的用户realm:连接数据库--><dependency><groupId>org.apache.shiro</groupId><artifactId>shiro-spring</artifactId><version>1.4.1</version></dependency><dependency><groupId>com.github.theborakompanioni</groupId><artifactId>thymeleaf-extras-shiro</artifactId><version>2.0.0</version></dependency><!--整合mybatis--><!-- https://mvnrepository.com/artifact/org.mybatis.spring.boot/mybatis-spring-boot-starter --><dependency><groupId>org.mybatis.spring.boot</groupId><artifactId>mybatis-spring-boot-starter</artifactId><version>2.1.0</version></dependency><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-web</artifactId></dependency><!--   JDBC--><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-jdbc</artifactId></dependency><!--  Mysql--><dependency><groupId>mysql</groupId><artifactId>mysql-connector-java</artifactId><scope>runtime</scope></dependency><dependency><groupId>com.alibaba</groupId><artifactId>druid</artifactId><version>1.1.6</version></dependency><!-- 导入页面依赖<dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-thymeleaf</artifactId></dependency>    --><!--        thymeleaf,都是基于3.x开发的--><dependency><groupId>org.thymeleaf</groupId><artifactId>thymeleaf-spring5</artifactId></dependency><dependency><groupId>org.thymeleaf.extras</groupId><artifactId>thymeleaf-extras-java8time</artifactId></dependency><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-test</artifactId><scope>test</scope></dependency><!--        简化set和get方法--><dependency><groupId>org.projectlombok</groupId><artifactId>lombok</artifactId><version>1.16.10</version><scope>provided</scope></dependency><!--        导入日志依赖--><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter</artifactId><exclusions><exclusion><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-logging</artifactId></exclusion></exclusions></dependency><!-- 日志文件 --><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-log4j</artifactId><version>1.3.8.RELEASE</version></dependency><!-- 分页插件 --><dependency><groupId>com.github.pagehelper</groupId><artifactId>pagehelper-spring-boot-starter</artifactId><version>1.2.5</version></dependency></dependencies>

2、接下来就是编写相应的代码(太简单了、几乎是无脑操作)

随便展示一个书籍的操作、从前台页面到后端代码的编写

先看效果图

前端页面代码


<!DOCTYPE html>
<html lang="en" xmlns:th="http://www.thymeleaf.org">
<head><meta charset="UTF-8"><title>书籍列表</title><!-- 新 Bootstrap 核心 CSS 文件 --><link href="https://cdn.staticfile.org/twitter-bootstrap/3.3.7/css/bootstrap.min.css" rel="stylesheet"></head>
<body><div class="container"><!--导航栏部分--><nav class="navbar navbar-inverse"><div class="container-fluid"><!-- Brand and toggle get grouped for better mobile display --><div class="navbar-header"><a class="navbar-brand" href="#">书籍商城</a></div><div class="collapse navbar-collapse" id="bs-example-navbar-collapse-1"><ul class="nav navbar-nav"><li><a th:href="@{/customer/toCustomerIndex}">个人信息</a></li><li><a href="#">购买记录</a></li><li><a href="#">购物车</a></li><li><a th:href="@{/book/bookList}">书籍商城</a></li></ul></div><!-- /.navbar-collapse --></div><!-- /.container-fluid --></nav><hr><div class="row "><form  th:action="@{/book/bookList}" style="float: left"><div class="col-md-2"><input type="text" name="queryBookName" class="form-control" placeholder="书籍名"></div><div class="col-md-2" ><input type="text" name="queryBookAuthor" class="form-control" placeholder="作者名"></div><div class="col-md-2" ><input type="text" name="queryBookAddress" class="form-control" placeholder="出版社"></div><div class="col-md-4" ><div class="col-row"><div class="col-md-5"><input type="text" name="minPrice" class="form-control" placeholder="最低价格"></div><div class="col-md-1"><span><strong>:</strong></span></div><div class="col-md-5"><input type="text" name="maxPrice" class="form-control" placeholder="最高价格"></div></div></div><input type="submit" value="查询" class="btn btn-primary"></form></div>
<hr><div class="row clearfix"><div class="col-md-12 column"><table class="table table-hover table-striped"><thead><tr>
<!--                    <th>书籍编号</th>--><th>书籍名称</th><th>书籍作者</th><th>书籍价格</th><th>书籍出版社</th><th>操作</th></tr></thead><!--查询书籍处理--><tbody><tr th:each="book:${bookList}">
<!--                    <td  th:text="${book.getBookId()}">编号</td>--><td th:text="${book.getBookName()}">书名</td><td th:text="${book.getBookAuthor()}">作者</td><td th:text="${book.getPrice()}"></td><td th:text="${book.getAddress()}">出版社</td><td><a  th:href="@{/book/todetail(bookId=${book.getBookId()})}" >详情</a>&nbsp;&nbsp;|&nbsp;&nbsp;<a  th:href="@{/shop/addshop(bookId=${book.getBookId()})}" >加入购物车</a></td></tr></tbody></table><div class="col-md-3"><a class="btn btn-primary" th:href="@{/book/bookList}">返回查询首页</a></div><div class="col-md-5"><p ><strong>当前</strong> <span th:text="${pageInfo.pageNum}"></span><strong> 页,总 </strong><span th:text="${pageInfo.pages}"></span><strong> 页,共</strong> <span th:text="${pageInfo.total}"></span><strong> 条记录</strong></p></div><div class="col-md-4"><div class="row"><div class="col-md-12"><a class="btn btn-primary" th:href="@{/book/bookList}">首页</a><a class="btn btn-primary" th:href="@{/book/bookList(pageNum=${pageInfo.hasPreviousPage}?${pageInfo.prePage}:1)}">上一页</a><a class="btn btn-primary" th:href="@{/book/bookList(pageNum=${pageInfo.hasNextPage}?${pageInfo.nextPage}:${pageInfo.pages})}">下一页</a><a class="btn btn-primary" th:href="@{/book/bookList(pageNum=${pageInfo.pages})}">尾页</a></div></div></div></div></div></div>
</body>
</html>

编写的书籍实体类

(没有使用lombox、失去了Java的灵魂、不喜欢用)

package com.example.zheng.pojo;public class Books {private String bookId;private String bookName;private String bookAuthor;private Double price;private String address;private String impression;private String introduce;//新增这两个字段的原因,将前台传入的价格范围封装、在编写sql语句的时候动态替换价格参数private Double minPrice;//最小价格private Double maxPrice;//最大价格public Books(String bookId, String bookName, String bookAuthor, Double price, String address, String impression, String introduce, Double minPrice, Double maxPrice) {this.bookId = bookId;this.bookName = bookName;this.bookAuthor = bookAuthor;this.price = price;this.address = address;this.impression = impression;this.introduce = introduce;this.minPrice = minPrice;this.maxPrice = maxPrice;}public Double getPrice() {return price;}public void setPrice(Double price) {this.price = price;}public Double getMinPrice() {return minPrice;}public void setMinPrice(Double minPrice) {this.minPrice = minPrice;}public Double getMaxPrice() {return maxPrice;}public void setMaxPrice(Double maxPrice) {this.maxPrice = maxPrice;}public Books() { }public String getBookId() {return bookId;}public void setBookId(String bookId) {this.bookId = bookId;}public String getBookName() {return bookName;}public void setBookName(String bookName) {this.bookName = bookName;}public String getBookAuthor() {return bookAuthor;}public void setBookAuthor(String bookAuthor) {this.bookAuthor = bookAuthor;}public String getAddress() {return address;}public void setAddress(String address) {this.address = address;}public String getImpression() {return impression;}public void setImpression(String impression) {this.impression = impression;}public String getIntroduce() {return introduce;}public void setIntroduce(String introduce) {this.introduce = introduce;}
}

controller层

(这里的传输数据可以使用其他的方式ajax等等、我这里是暂时走通前后端。后期会进一步改造)

package com.example.zheng.controller;import com.example.zheng.pojo.Books;
import com.example.zheng.service.BooksService;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;import java.util.List;@Controller
public class BooksController {@AutowiredBooksService booksService;@RequestMapping("/book/bookList")public String bookList(@RequestParam(defaultValue = "1",value = "pageNum") Integer pageNum,Double minPrice,Double maxPrice, String queryBookAuthor, String queryBookAddress, String queryBookName, Model model){PageHelper.startPage(pageNum,10);Books books =new Books();books.setBookAuthor(queryBookAuthor);books.setBookName(queryBookName);books.setAddress(queryBookAddress);books.setMinPrice(minPrice);books.setMaxPrice(maxPrice);try {List<Books> list = booksService.queryBookList(books);PageInfo<Books> pageInfo = new PageInfo<Books>(list);model.addAttribute("pageInfo",pageInfo);if(list == null){model.addAttribute("error","书籍列表为空");}else{model.addAttribute("bookList",list);}} catch (Exception e) {e.printStackTrace();}return "allBook";}@RequestMapping("/book/todetail")public String bookDetail(String bookId,Model model){try {Books books = booksService.queryBookById(bookId);if(books == null){model.addAttribute("error","查询书籍详细信息失败");}else{model.addAttribute("books",books);}} catch (Exception e) {e.printStackTrace();}return "bookDetail";}}

service层

package com.example.zheng.service;import com.example.zheng.pojo.Books;import java.util.List;public interface BooksService {/*** 查询图书*/public List<Books> queryBookList(Books books);/*** 查询书籍的详细信息通过书籍编号*/public Books queryBookById(String bookId);
}

实现类

package com.example.zheng.service.impl;import com.example.zheng.mapper.BooksMapper;
import com.example.zheng.pojo.Books;
import com.example.zheng.service.BooksService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;import java.util.List;@Service
public class BooksServiceImpl implements BooksService {@AutowiredBooksMapper booksMapper;//查询所有书籍@Overridepublic List<Books> queryBookList(Books books) {return booksMapper.queryBookList(books);}//根据id查询具体书籍信息@Overridepublic Books queryBookById(String bookId) {return booksMapper.queryBookById(bookId);}
}

Dao层

package com.example.zheng.mapper;import com.example.zheng.pojo.Books;
import org.apache.ibatis.annotations.Mapper;
import org.springframework.stereotype.Repository;import java.util.List;@Mapper    //这个注解表示这个是mybatis的mapeper
@Repository
public interface BooksMapper {/*** 查询图书*/public List<Books> queryBookList(Books books);/*** 查询书籍的详细信息通过书籍编号*/public Books queryBookById(String id);}

sql语句

<?xml version="1.0" encoding="UTF8"?>
<!DOCTYPE mapperPUBLIC "-//mybatis.org//DTD Config 3.0//EN""http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.example.zheng.mapper.BooksMapper"><select id="queryBookList" parameterType="com.example.zheng.pojo.Books" resultType="com.example.zheng.pojo.Books">select * from bookss<where>1=1<if test="bookName != null and bookName != ''">And bookName =#{bookName}</if><if test="bookAuthor != null and bookAuthor != ''">And bookAuthor =#{bookAuthor}</if><if test="address != null and address !=''">And address =#{address}</if><if test="minPrice !=null and minPrice !=''">And price > #{minPrice}<if test="maxPrice !=null and maxPrice !=''">And price &lt; #{maxPrice}</if></if></where></select><select id="queryBookById" resultType="com.example.zheng.pojo.Books">select * from bookss where bookId=#{bookId}</select></mapper>

差不多整个流程就是这样。大差不差。

在开发中遇到的问题以及解决的办法?

一、在整合框架的时候遇到的奇葩问题:

1、跳转到指定页面出现问题?必须要在properties中配置,这样的目的是,说白了是个视图解析器。和我以前写的不一样,这个也太简单了
2、必须在pom依赖中添加试图解析的依赖。
3、图片路径的问题,添加static则不显示图片,这个是相对路径,找不出来。就很离谱。解决方法:把static删除,然后重启idea。
4、@Controller。跳转到指定页面中要使用这个注解,另外一个出现问题

二、使用thymeleaf在进行传输数据的时候遇到的奇葩

这里需要注意的是,怎样获取当前书籍的主键、以及怎样将这个主键传递到controller层对应的方法中。将这个主键作为查询条件。
解决的方法:<a th:href="@{/book/todetail(bookId=${book.getBookId()})}" >详情</a>
这个方法是thymleaf特有的传输形式

1、改进书籍展示的信息、将书籍编号隐藏。只给顾客展示、书名、作者、出版社、价格


解决办法:1、首先是想到隐藏该列信息、但是没能成功。2、直接将该列信息代码删除、在点击详情需要根据改行的图书主键搜索数据库。由于当前的对象中,已经包含该图书的所有信息。可以直接拿来使用。当前行图书主键存在的意义不是很大。

三、实现在一定价格区间内搜索图书。

遇到的问题:编写的问题sql语句中的价格参数是变动的。不能将其写死在sql中。

解决办法:直接在前端页面设置两个输入框,用来接受数据。同时在实体类书籍中添加最大价格和最小价格两个属性、将前端的数据封装到实体类中,然后将数据直接传输到sql中。

遇到的问题:在新增两个属性后、查询不到数据、爆空指针异常。

经过分析发现、在实体类中书籍的价格应使用Double而不是double.idea没有给我报错、离谱。这种错误我也是醉了。我还真找了好一会。

遇到的问题:获得了参数、在写入sql中,<号不能使用。总是爆红、上网搜索、需要使用转移字符:&lt;

四、遇到的问题? 怎样将查询到的用户权限放入shiro中、进行接下来的认证。

解决办法:将查询到的用户
已经查询到当前用户具有的权限

 //授权@Overrideprotected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principalCollection) {System.out.println("执行了授权");//拿到当前登录的这个对象Subject subject = SecurityUtils.getSubject();Customer currentCustomer = (Customer) subject.getPrincipal();//拿到对象//设置当前用户的权限SimpleAuthorizationInfo info = new SimpleAuthorizationInfo();//设置集合Collection<String> perStringCollection = new HashSet<String>();//已经查询到当前用户具有的权限Set<Roles> permissionSet =rolesService.queryRoles(currentCustomer.getUsercount());for(Roles perm : permissionSet){//将每一个当前用户的权限加入perStringCollection.add(perm.getAuthName());}info.addStringPermissions(perStringCollection);return info;}

五、根据登录用户、在查询购物车的时候、查询当前用户的购物车。在购买商品的时候加入到当前用户的购物车中

主要的代码是:

Customer parent = (Customer) SecurityUtils.getSubject().getPrincipal();

待编辑

springboot+bootstrap实现图书商城管理(大三下学期课程设计)相关推荐

  1. 计算机专业大三上学期课程,武汉工程大学邮电与信息工程学院计算机专业大三下学期课程安排...

    技校网专门为您推荐的类似问题答案 问题1: 四川大学锦江学院机械工程系数控专业大三下学期要学哪些课程 你去学校的校网查啊,里面有各种安排的.每个学校都有啊.不过是在学分制系统里,我不是这个学校的所以进 ...

  2. 基于设计模式的绘图程序设计(大二下学期课程设计)

    课程名称:设计模式课程设计 设计题目:基于设计模式的绘图程序设计 源代码 源代码保存地址:http://t.csdn.cn/5LwZO 1.需求分析 该系统是一个画图程序,我们要用设计模式的思想来设计 ...

  3. JSP+servlet+mybatis+layui服装库存管理系统(大三上学期课程设计)

    阿西吧.自从学会使用框架.再看以前写的.我真的是要死了.项目用的还不是maven.整理项目能给我搞死.更要命的是这个项目还是用eclipse写的.数据库还是SQL server.阿西吧 这个系统代码不 ...

  4. 2017年上半年总结:大三下学期,马上大四,马上要毕业了.

    2017年上半年总结:大三下学期,马上大四,马上要毕业了. 当这学期马上结束了,想起要写今年上半年的总结了,写下标题才猛然惊起,我已结束大三,下学期就大四了啊? --不可思议且平淡的大三end 回忆这 ...

  5. 谈谈大三下学期找实习的经历(宇视科技 亚信联创 网新恒天 虹软)

    本人是浙江工业大学大三软件工程专业的学生,大学在校期间做过几个项目,参加过一些比赛,个人主要往Java开发这一方面发展,现在5月下旬刚好要去找相应的企业进行实习,分享一下自己的笔试面试经历,与君共勉! ...

  6. 【Unity学习笔记】大三下学期 射击类小游戏制作

    虽然大二寒假做过一次,但已经快忘光光了.. 所以这次要认真记录一下知识点! //0415更新 新添实现敌机生成.单例模式添加音乐特效等 //0408更新 总共实现了背景轮播.控制飞机走动.发射子弹的功 ...

  7. 大三下学期第四周总结

    今天是蓝桥杯省赛的比赛日子,但是考场却发生机器无端蓝屏,重启十几次无果.浪费了两个多小时,组委会最终延时40分组左右.这次考试感觉很郁闷.根本无法写题.对于自己来说,今年无缘省三.也可惜了近一个月的算 ...

  8. 大三下学期十一周总结

    时间总是在不经意间流逝,不知不觉,学期已经进入到了11周末.大学生涯马上就要落下帷幕了.本周在找工作方面毫无进展,只剩下普元一家.尽量努力,事在人为.学长在这方面也劝我全力去准备秋招,一心学习.我这方 ...

  9. 大三下学期第一周总结

    本周以是开学第一周了,在生活方面,生活琐事确实变多了起来.每天上课,看着老师熟悉的面庞,如履春风.感觉学习没有那么多的陌生恐惧.学习是一方面,身体锻炼不能落下.一周至少保证三小时及其以上的运动.身体是 ...

最新文章

  1. 导出页面div中的图
  2. 随记一个C的毫秒级群PING
  3. halcon 将数据保存到excel_Python保存数据到Excel文件的多个sheet
  4. java 对象列表_Java中的对象列表
  5. 前端多次点击button_对于防止按钮重复点击的尝试详解
  6. UVALive 4212 Candy
  7. android7.0+关闭wifi连接CA验证
  8. AlbertTransformerEncoder
  9. [Liferay6.2]Liferay Dynamic Query API示例
  10. c最简单的编程语言,世界上最简单的中文编程语言
  11. HBuilderX ios打包失败(已解决)
  12. 【赖世雄音标】——元音
  13. 工程项目管理系统-专注项目数字化管理-工程管理
  14. 瑞利信号公式(级联信道,多信道之和,多个瑞利信号之和,概率密度函数)
  15. 我在华清的嵌入式课程笔记(至2020.7.5)
  16. 用python玩转数据作业答案_大学mooc用Python玩转数据课后答案
  17. 在做嵌入式开发的时候难免手抖,IAR软件窗口恢复操作
  18. LinkSpark日报|人工智能资料库
  19. 全新WayOS 配置文件保存工具支持蓝色界面路由版本
  20. Python学习随记 ————随机抽号器(一)

热门文章

  1. 51单片机实现智能报警器
  2. SGU 103 Traffic Lights (最短路)
  3. echarts 地图,3D echarts地图,echarts飞线,echarts福建地图
  4. 6000端口有毒,谷歌浏览器访问不到
  5. 这样画三角形的内心很方便,数学老师必会技能!
  6. 李德仁院士:数字孪生助推我国智能交通、数字交通快速发展
  7. 衢州希尔顿逸林酒店开业;雅高集团全球首家铂翎汇臻选奢华酒店落户贵阳 | 全球旅报...
  8. Excel更改引用方式在绝对引用与相对引用之间快速切换
  9. 裸辞25k鹅厂工作,待在家里全职接单,一个月我挣了多少?
  10. 迅睿CMS 集成栏目页