位置: IT常识 - 正文

SpringBoot+Vue实现在线商城系统

编辑:rootadmin
SpringBoot+Vue实现在线商城系统 该项目开始是要求我们使用JavaWeb(java+jsp+servlet+MySQL+jdbc+css+js+jQuery)实现,但我学过一丢丢的框架,就改用了SpringBoot+Vue实现。

推荐整理分享SpringBoot+Vue实现在线商城系统,希望有所帮助,仅作参考,欢迎阅读内容。

文章相关热门搜索词:,内容如对您有帮助,希望把文章链接给更多的朋友!

注意!!!!!代码中的serverIp我设置的我服务器的IP,所以不在服务器上面应该是localhost!!!!!!!!

在线商城项目演示视频:https://www.bilibili.com/video/BV1kY41117DH/

目录

1. 产品介绍

2. 产品面向的用户群体

3. 产品的范围

4. 产品中的角色

5. 产品的功能需求

5.1 功能性需求分类

5.2功能层次结构图

6. 产品的非功能性需求

6.1 用户界面需求

6.2 软硬件环境需求

6.3 产品质量需求

数据库设计:

前台页面:

在线商城首页:

​编辑

首页Home.vue源代码:

 商品详情页:

​编辑 源代码Detail.Vue

我的购物车: 

我的订单:

返回数据:

个人信息:

 源代码Person.vue

联系商家:

 后台页面:

核心代码: 

1.UserController

2.TokenUtils 

3.CartController

4.EchartsController

5.FileController

6.MybatisPlusConfig

7.Constants

1. 产品介绍

对于网上商城,其最大好处是要能给用户带来最大的便捷,这种便捷不仅体现在网络之外的物流、商品的折扣等,更要体现在进行网络操作时的易用性,能够模拟用户的购物行为,营造一种尽量真实、贴切的用户购物过程。所以,在设计网络商城时,最重要的就是完成“用户功能”。其次,对众多商品、订单、用户信息的网络管理,对于网站经营者的经营效率的意义,也是不言而喻的,这些则可以称为“管理功能”。

2. 产品面向的用户群体

本系统主要面向系统管理员和普通用户。

(1)系统管理员:订单管理、用户管理、商品管理等。

(2)普通用户:主要使用的业务模块包括系统登录、注册、购买商品、查询订单。

3. 产品的范围

本项目主要分为系统设置模块、用户管理模块、商品管理模块、购买商品管理模块、订单管理模块。

4. 产品中的角色

角色名称

职责描述

普通用户

注册,登录,添加购物车,商品付款

管理员

登录,注册,商品信息管理,用户信息管理

5. 产品的功能需求5.1 功能性需求分类

功能类别

功能名称

描述

用户管理

个人信息管理

管理用户的个人信息

用户管理

管理已存在用户

商品管理

增加商品

对商城的商品进行添加

删除商品

删除商城的在架商品

订单管理

订单详情管理

对订单进行处理,对已付款的订单进行发货,对发货的商品进行收货

订单支付

支付当前未付款的订单

查看商品

查看该笔订单的商品信息

购物车管理

添加购物车

添加商品到购物车

删除购物车

删除当前购物车内的商品

商品结算

结算购物车的商品

5.2功能层次结构图

6. 产品的非功能性需求6.1 用户界面需求

需求名称

详细要求

整体风格

以蓝色为主色调

兼容性

能在主流浏览器(火狐、谷歌、IE8+、360浏览器)上运行

6.2 软硬件环境需求

需求名称

详细要求

开发语言

Java或.NET

SpringBoot+Vue实现在线商城系统

运行环境

Jdk1.6+或.NET Framework 3.5以上

数据库

Mysql5.0或者SqlServer 2005以上

操作系统

Windows Server2008

6.3 产品质量需求

主要质量属性

详细要求

正确性

无数据计算错误,无流程错误

健壮性

程序出错后,系统能正常捕获异常,不会导致程序终止运行

可靠性

系统支持7*24无间断运行,不会因系统功能的复杂运算而导致系统崩溃

性能、效率

数据请求在0.2S内返回

易用性

功能使用,操作简单,避免繁琐的逻辑设定

清晰性

功能结果及名称清晰,避免用户误解

安全性

用户必须成功登陆后,根据权限才可使用对应的功能

可扩展性

提供良好的系统接口,支持后续功能的开发扩展

兼容性

兼容主流浏览器(火狐、谷歌、IE8+、360浏览器)

可移植性

能较好部署到其他版本的Windows操作系统上

数据库设计:

1.1 数据库系统:

SQL Server 2008 / My SQL,服务器为MySQL8.0版本

1.2 设计工具:

Enterprise Architect

1.3连接工具:

Navicat、服务器为1核(vCPU) 2 GiB

前台页面:在线商城首页:

 

首页Home.vue源代码:<template> <div class="base"> <div style="background-color: #545c64; width: 1510px"> <el-menu background-color="#545c64" text-color="#fff" active-text-color="#ffd04b" class="el-menu-demo" mode="horizontal"> <el-menu-item index="/home" @click="$router.push('/home')">在线商城首页</el-menu-item> <el-menu-item index="1" > <a href="https://www.jd.com" target="_blank" style="text-decoration: none">商城官网</a></el-menu-item> <el-menu-item index="/front/cart" @click="$router.push('/front/cart')">我的购物车<i class="el-icon-shopping-cart-1"/></el-menu-item> <el-menu-item index="/front/orders" @click="$router.push('/front/orders')">我的订单<i class="el-icon-truck"/></el-menu-item><!-- <el-menu-item index="/user" @click="$router.push('/user')" v-if="user.role == 1">后台管理</el-menu-item>--> <!-- <el-submenu index="7" v-if="user.role == 1">--> <!-- <template slot="title">后台管理</template>--> <!-- <el-menu-item index="/user" @click="$router.push('/user')">用户管理</el-menu-item>--> <!-- <el-menu-item index="/goods" @click="$router.push('/goods')">商品管理</el-menu-item>--> <!-- <el-menu-item index="/cart" @click="$router.push('/cart')">购物车管理</el-menu-item>--> <!-- <el-menu-item index="/orders" @click="$router.push('/orders')">订单管理</el-menu-item>--> <!-- </el-submenu>--> <div style="float: right; display: flex"> <el-menu-item index="/login" @click="$router.push('/login')">登录/注册</el-menu-item><!-- <el-menu-item index="/register" @click="$router.push('/login')">退出商城</el-menu-item>--><!-- <el-menu-item index="/front/person" @click="$router.push('/front/person')">{{ user.nickname }}</el-menu-item>--> <el-submenu index="7"> <template slot="title">{{ user.nickname }}</template> <el-menu-item index="/front/person" @click="$router.push('/front/person')">个人信息</el-menu-item> <el-menu-item index="/login" @click="$router.push('/login')">退出</el-menu-item> </el-submenu> </div> </el-menu> </div> <el-card style="height: 80px; background-color: white"> <el-input style="width: 600px; margin-left: 400px" placeholder="请输入你要查询的商品" clearable v-model="name" size="big"></el-input><!-- <el-input style="width: 200px; margin-left: 10px" placeholder="请输入用户名" clearable suffix-icon="el-icon-user" v-model="username" ></el-input>--> <el-button type="primary" style="margin-left: 5px" @click="load" size="big"><i class="el-icon-search" />搜索</el-button> </el-card> <div style="width: 1500px; height: 410px; display: flex"> <div style="width: 300px; text-align: right; padding-right: 10px; background-color: whitesmoke; margin: 10px 0 0"> <ul style="margin: 10px 0; font-weight: inherit; font-size: 18px; color: #545c64"> <li style="margin-top: 10px; cursor: pointer">手机</li> <li style="margin-top: 20px; cursor: pointer">电脑</li> <li style="margin-top: 20px; cursor: pointer">家装</li> <li style="margin-top: 20px; cursor: pointer">医药</li> <li style="margin-top: 20px; cursor: pointer">女装</li> <li style="margin-top: 20px; cursor: pointer">男装</li> <li style="margin-top: 20px; cursor: pointer">美妆</li> <li style="margin-top: 20px; cursor: pointer">食品</li> </ul> </div> <!-- 轮播图--> <div style="flex: 1; margin: 10px 0 0 "> <span class="demonstration"></span> <el-carousel trigger="click" height="400px"> <el-carousel-item v-for="item in list" :key="item"> <img :src="item.img" > </el-carousel-item> </el-carousel> </div> </div> <div style="width: 100px; height: 50px; text-align: center; margin:25px 0 0 710px"> <a style="font-size: 28px; font-weight: bold; padding-top: 100px">手机</a> </div> <div style="margin: 10px 60px; background-color: whitesmoke; height: 640px; width: 1400px; "> <el-row :gutter="12" > <el-col :span="4" v-for="item in tableData" :key="item.id"> <div class="phone"> <img :src="item.url" alt="" @click="$router.push('/detail?id=' + item.id)" style="width: 140px; height: 140px; margin-top: 5px; margin-left: 2px; cursor: pointer"> <div class="refer" @click="$router.push('/detail?id=' + item.id)"><b>{{item.refer}}</b></div> <div class="goodsName" @click="$router.push('/detail?id=' + item.id)">{{item.name}}</div> <div class="price" @click="$router.push('/detail?id=' + item.id)">¥{{item.price}}</div> </div> </el-col> </el-row> </div> <div style="padding: 10px 0 0 50px"> <el-pagination @size-change="handleSizeChange" @current-change="handleCurrentChange" :current-page="pageNum" :page-sizes="[ 5, 10, 15]" :page-size="pageSize" layout="total, prev, pager, next" :total="total"> </el-pagination> </div><!-- <div style="width: 100%; height: 50px; margin-top: 50px">--><!-- <a style="font-size: 28px; font-weight: bold; margin-left: 730px">电脑</a>--><!-- </div>--><!-- <div style="margin: 10px 60px; background-color: whitesmoke; height: 640px; width: 1400px; ">--><!-- <el-row :gutter="10" >--><!-- <el-col :span="4" v-for="item in tableData" :key="item.id">--><!-- <div class="phone">--><!-- <img :src="item.url" alt="" @click="$router.push('/detail?id=' + item.id)" style="width: 170px; height: 170px; margin-top: 5px; margin-left: 3px; cursor: pointer">--><!-- <div class="refer" @click="$router.push('/detail?id=' + item.id)"><b>{{item.refer}}</b></div>--><!-- <div class="goodsName" @click="$router.push('/detail?id=' + item.id)">{{item.name}}</div>--><!-- <div class="price" @click="$router.push('/detail?id=' + item.id)">¥{{item.price}}</div>--><!-- </div>--><!-- </el-col>--><!-- </el-row>--><!-- </div>--><!-- <div style="width: 100%; height: 50px; margin-top: 50px">--><!-- <a style="font-size: 28px; font-weight: bold; margin-left: 705px">电脑外设</a>--><!-- </div>--><!-- <div style="margin: 10px 60px; background-color: whitesmoke; height: 640px; width: 1400px; ">--><!-- <el-row :gutter="10" >--><!-- <el-col :span="4" v-for="item in tableData" :key="item.id">--><!-- <div class="phone">--><!-- <img :src="item.url" alt="" @click="$router.push('/detail?id=' + item.id)" style="width: 170px; height: 170px; margin-top: 5px; margin-left: 3px; cursor: pointer">--><!-- <div class="refer" @click="$router.push('/detail?id=' + item.id)"><b>{{item.refer}}</b></div>--><!-- <div class="goodsName" @click="$router.push('/detail?id=' + item.id)">{{item.name}}</div>--><!-- <div class="price" @click="$router.push('/detail?id=' + item.id)">¥{{item.price}}</div>--><!-- </div>--><!-- </el-col>--><!-- </el-row>--><!-- </div>--><!-- <div style="width: 100%; height: 50px; margin-top: 50px">--><!-- <a style="font-size: 28px; font-weight: bold; margin-left: 705px">电脑配件</a>--><!-- </div>--><!-- <div style="margin: 10px 60px; background-color: whitesmoke; height: 640px; width: 1400px; ">--><!-- <el-row :gutter="10" >--><!-- <el-col :span="4" v-for="item in tableData" :key="item.id">--><!-- <div class="phone">--><!-- <img :src="item.url" alt="" @click="$router.push('/detail?id=' + item.id)" style="width: 170px; height: 170px; margin-top: 5px; margin-left: 3px; cursor: pointer">--><!-- <div class="refer" @click="$router.push('/detail?id=' + item.id)"><b>{{item.refer}}</b></div>--><!-- <div class="goodsName" @click="$router.push('/detail?id=' + item.id)">{{item.name}}</div>--><!-- <div class="price" @click="$router.push('/detail?id=' + item.id)">¥{{item.price}}</div>--><!-- </div>--><!-- </el-col>--><!-- </el-row>--><!-- </div>--> <div style="width: 100%; height: 250px; margin-top: 80px"> <div style="height: 250px;width: 1510px; background-color: #545c64"> <h3 style="margin-left: 705px; font-size: 28px; color: white">合作伙伴</h3> <img src="src/assets/images/footer/facebook.png" alt="" style="width: 30px; height: 30px; margin-left: 665px"> <img src="src/assets/images/footer/推特.png" alt="" style="width: 30px; height: 30px; margin-left: 10px"> <img src="src/assets/images/footer/telegram.png" alt="" style="width: 30px; height: 30px; margin-left: 10px"> <img src="src/assets/images/footer/xbox.png" alt="" style="width: 30px; height: 30px; margin-left: 10px"> <img src="src/assets/images/footer/Youtube.png" alt="" style="width: 30px; height: 30px; margin-left: 10px"> <div style="margin-top: 15px"> <a style="margin-left: 280px; font-size: 16px; color: white">商城 | 游戏 | 政企服务 | 集团隐私政策 | 公司儿童信息保护规则 | 商城隐私政策 | 商城用户协议 | 问题反馈 | Select Location</a> </div> <div style="margin-top: 10px"> <a style="margin-left: 315px;font-size: 16px; color: white"> 互联网ICP备案:沪ICP备13002172号-3 沪-非经营性-2016-0143 营业性演出许可证 沪市文演(经)00-2253 | </a> </div> </div> </div> </div></template><script>export default { name: "Home", components: {}, data() { return { tableData: [], total: 0, pageNum: 1, pageSize: 10, name: "", user: localStorage.getItem("user") ? JSON.parse(localStorage.getItem("user")) : {}, list:[ {img:require('../../assets/images/Carousel/img.png')}, {img:require('../../assets/images/Carousel/img_1.png')}, {img:require('../../assets/images/Carousel/img_2.png')}, {img:require('../../assets/images/Carousel/img_3.png')}, {img:require('../../assets/images/Carousel/img_4.png')}, ] } }, created() { this.load() }, methods: { load: function () { this.request.get("/goods/page", { params: { pageNum: this.pageNum, pageSize: this.pageSize, name: this.name, } }).then(res => { this.tableData = res.data.records this.total = res.data.total }) }, home() { this.$router.push("/") }, handleSizeChange(pageSize) { console.log(pageSize) this.pageSize = pageSize this.load() }, handleCurrentChange(pageNum) { console.log(pageNum) this.pageNum = pageNum this.load() }, }}</script><style scoped>li:hover { color: orangered;}.goodsName { font-size: 14px; text-align: center; cursor: pointer}.price { font-size: 16px; font-weight: bold; color: orangered; cursor: pointer;}.refer { padding: 2px; cursor: pointer; /*margin-top: 5px;*/ overflow: hidden; display: -webkit-box; -webkit-line-clamp: 2; -webkit-box-orient: vertical;}.base { margin: 0px; padding: 0px;}img { width: 100%; height: 100%;}.phone { background-color: white; padding-bottom: 10px; font-size: 16px; text-align: center; width: 160px; height: 150px; transition: all 0.8s; margin: 60px 16px;}.box~.phone{ margin-left: 30px;}.box0 img{ width: 170px; height: 170px;}.phone:hover{ transform: scale(1.08);}</style> 商品详情页: 源代码Detail.Vue<template> <div style="padding: 10px 0"> <el-card style="width: 1100px; margin-left: 200px"> <div style="display: flex"> <div style="width: 350px"> <el-image :src="goods.url" :preview-src-list="[goods.url]" style="width: 80%; position: center; margin-top: 30px"></el-image> </div> <div style="flex: 1; padding-left: 50px"> <div class="goodsName">{{ goods.name }}</div> <div class="refer">{{ goods.refer }}</div> <div class="price">¥{{ goods.price }}</div> <div class="refer" style="margin-top: 10px;">库存{{ goods.num }}台</div> <div class="goodsName"> <el-input-number size="big" v-model="form.number" :min="1" :max="100" label="数量"></el-input-number> </div> <div class="goodsName" ><!-- <template v-slot="scope">--> <el-button class="addCar" size="big" @click="buy(scope.row.id)"><i class="el-icon-bank-card"/> 直接购买</el-button> <el-button class="addCar" size="big" v-on:click="addCart"><i class="el-icon-shopping-cart-1" /> 加入购物车</el-button><!-- </template>--> </div> <a size="big" @click="chat" style="float: left; color: #DF3033; cursor: pointer; padding-left: 10px">联系商家</a> </div> </div> </el-card> </div></template><script>import {serverIp} from "../../../public/config";const baseUrl = `http://${serverIp}:9090`export default { name: "Detail", data() { return { id: this.$route.query.id, goods: {}, form: {number: 1}, user: localStorage.getItem("user") ? JSON.parse(localStorage.getItem("user")) : {} } }, created() { this.load() }, methods: { load() { this.request.get("/goods/" + this.id).then(res => { this.goods = res.data }) }, chat() { this.$router.push("/im") }, addCart() { if (!this.user.username) { this.$message.warning("请登录后操作") return } this.form.goodsId = this.goods.id //商品ID this.request.post("/cart", this.form).then(res => { if (res.code === '200') { this.$message.success("加入购物车成功") } else { this.$message.error(res.msg) } }) }, buy(goodsId) { fetch(baseUrl + '/api/buy?goodsId=' + goodsId, { headers: { 'Content-Type': 'application/json;charset=utf-8' }, method: 'POST' }).then(res => res.json()).then(res => { if (res) { this.$message.success("下单成功") this.load() } else { this.$message.error("下单失败") } }) } }}</script><style scoped>.addCar { padding: 10px; /*margin-left: 10px;*/ width: 140px; height: 45px; background-color: #DF3033; color: white; font-weight: bold; font-size: 18px}.goodsName { padding: 10px; font-size: 22px; font-weight: bold;}.refer { padding: 10px; font-size: 16px; font-weight: bold}.price { height: 60px; padding: 15px 10px 10px 20px; background-color: #FCE5E5; color: orangered; font-weight: bold; margin-left: 10px; margin-top: 10px; font-size: 24px;}</style>我的购物车: 

可以勾选商品进行计算价格,然后进行商品结算 去订单页面付款,也可以选择删除购物车里面的商品。

我的订单:

可以查看自己的订单的商品,设置5s时间自动关闭。支付使用支付宝沙箱支付,对于已经支付的订单无法二次支付,即使支付也会报错,对于已支付的订单也不能进行取消。

返回数据:

支付宝进行回调信息存储到数据库,后台可以接收信息。 

进行支付之后,后台可以对订单进行发货,用户在我的订单里面也可以看见订单状态是否发货,从而进行收货操作。

个人信息:

 源代码Person.vue<template> <el-card style="width: 500px; margin-left: 50px"> <el-form label-width="80px" size="small"> <el-form-item label="用户名"> <el-input v-model="form.username" disabled autocomplete="off"></el-input> </el-form-item> <el-form-item label="昵称"> <el-input v-model="form.nickname" autocomplete="off"></el-input> </el-form-item> <el-form-item label="性别"> <el-input v-model="form.sex" autocomplete="off"></el-input> </el-form-item> <el-form-item label="邮箱"> <el-input v-model="form.email" autocomplete="off"></el-input> </el-form-item> <el-form-item label="电话"> <el-input v-model="form.phone" autocomplete="off"></el-input> </el-form-item> <el-form-item label="地址"> <el-input type="textarea" v-model="form.address" autocomplete="off"></el-input> </el-form-item> <el-form-item> <el-button type="primary" @click="save">保 存</el-button> <el-button type="primary" @click="sign" disabled><i class="el-icon-location" />定位</el-button> <el-button type="success" @click="return1" style="float: right">返回主页</el-button> </el-form-item> </el-form> </el-card></template><script>export default { name: "Person", data() { return { form: {}, user: localStorage.getItem("user") ? JSON.parse(localStorage.getItem("user")) : {} } }, mounted() { // 获取地理位置 var geolocation = new BMapGL.Geolocation(); geolocation.getCurrentPosition(function(r){ if(this.getStatus() == BMAP_STATUS_SUCCESS){ const province = r.address.province const city = r.address.city localStorage.setItem("address", province + city) } }); }, created() { this.request.get("/user/username/" + this.user.username).then(res => { if (res.code === '200') { this.form = res.data } }) }, methods: { sign() { const address = localStorage.getItem("address") const username = this.user.username this.request.post("/user", { user: username, address: address }).then(res => { if (res.code === '200') { this.$message.success("获取成功") } else { this.$message.error(res.msg) } }) }, save() { this.request.post("/user", this.form).then(res => { if (res.data) { this.$message.success("保存成功") } else { this.$message.error("保存失败") } }) }, return1() { this.$router.push("/") } }}</script><style></style>联系商家:

此功能可以参考我的另外一篇文章:(2条消息) SpringBoot实现简易聊天室_慕言要努力的博客-CSDN博客

 后台页面:

核心代码: 1.UserControllerimport cn.hutool.core.util.StrUtil;import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;import com.baomidou.mybatisplus.extension.plugins.pagination.Page;import com.example.demo.common.Constants;import com.example.demo.common.Result;import com.example.demo.controller.dto.UserDTO;import com.example.demo.entity.User;import com.example.demo.service.IUserService;import com.example.demo.utils.TokenUtils;import org.springframework.web.bind.annotation.*;import javax.annotation.Resource;import java.util.List;@CrossOrigin@RestController@RequestMapping("/user")public class UserController { @Resource private IUserService userService; @PostMapping("/login") public Result login(@RequestBody UserDTO userDTO) { String username = userDTO.getUsername(); String password = userDTO.getPassword(); if (StrUtil.isBlank(username) || StrUtil.isBlank(password)) { return Result.error(Constants.CODE_400,"参数错误"); } UserDTO dto = userService.login(userDTO); return Result.success(dto); } @PostMapping("/register") public Result register(@RequestBody UserDTO userDTO) { String username = userDTO.getUsername(); String password = userDTO.getPassword(); if (StrUtil.isBlank(username) || StrUtil.isBlank(password)) { return Result.error(Constants.CODE_400,"参数错误"); } return Result.success(userService.register(userDTO)); } //新增或者更新 @PostMapping public Result save(@RequestBody User user) { return Result.success(userService.saveOrUpdate(user)); } //删除 @DeleteMapping("/{id}") public Result delete(@PathVariable Integer id) { return Result.success(userService.removeById(id)); } @PostMapping("/del/batch") public Result deleteBatch(@RequestBody List<Integer> ids) {//批量删除 return Result.success(userService.removeByIds(ids)); } // //查询所有数据// @GetMapping// public Result findAll() {// return Result.success(userService.list());// }// @GetMapping("/{id}") public Result findOne(@PathVariable Integer id) { return Result.success(userService.getById(id)); } @GetMapping("/username/{username}") public Result findOne(@PathVariable String username) { QueryWrapper<User> queryWrapper = new QueryWrapper<>(); queryWrapper.eq("username", username); return Result.success(userService.getOne(queryWrapper)); } @GetMapping("/page") public Result findPage(@RequestParam Integer pageNum, @RequestParam Integer pageSize, @RequestParam(defaultValue = "") String username) { QueryWrapper<User> queryWrapper = new QueryWrapper<>(); queryWrapper.orderByDesc("id"); if (!"".equals(username)) { queryWrapper.like("username", username); } return Result.success(userService.page(new Page<>(pageNum, pageSize), queryWrapper)); }}2.TokenUtils import cn.hutool.core.date.DateUtil;import cn.hutool.core.util.StrUtil;import com.auth0.jwt.JWT;import com.auth0.jwt.algorithms.Algorithm;import com.example.demo.entity.User;import com.example.demo.service.IUserService;import org.springframework.stereotype.Component;import org.springframework.web.context.request.RequestContextHolder;import org.springframework.web.context.request.ServletRequestAttributes;import javax.annotation.PostConstruct;import javax.annotation.Resource;import javax.servlet.http.HttpServletRequest;import java.util.Date;@Componentpublic class TokenUtils { private static IUserService staticUserService; @Resource private IUserService userService; @PostConstruct public void setUserService() { staticUserService = userService; } /** * 生成token * * @return */ public static String genToken(String userId, String sign) { return JWT.create().withAudience(userId) // 将 user id 保存到 token 里面,作为载荷 .withExpiresAt(DateUtil.offsetHour(new Date(), 2)) // 2小时后token过期 .sign(Algorithm.HMAC256(sign)); // 以 password 作为 token 的密钥 } /** * 获取当前登录的用户信息 * * @return user对象 */ public static User getCurrentUser() { try { HttpServletRequest request = ((ServletRequestAttributes) RequestContextHolder.getRequestAttributes()).getRequest(); String token = request.getHeader("token"); if (StrUtil.isNotBlank(token)) { String userId = JWT.decode(token).getAudience().get(0); return staticUserService.getById(Integer.valueOf(userId)); } } catch (Exception e) { return null; } return null; }}3.CartControllerimport com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;import com.baomidou.mybatisplus.extension.plugins.pagination.Page;import com.example.demo.common.Result;import com.example.demo.entity.Cart;import com.example.demo.entity.User;import com.example.demo.mapper.CartMapper;import com.example.demo.service.ICartService;import com.example.demo.utils.TokenUtils;import org.springframework.web.bind.annotation.*;import javax.annotation.Resource;import java.util.List;@CrossOrigin@RestController@RequestMapping("/cart")public class CartController { @Resource private ICartService cartService; @Resource private CartMapper cartMapper; //新增或者更新 @PostMapping public Result save(@RequestBody Cart cart) { Integer userId = TokenUtils.getCurrentUser().getId(); //相同商品进行处理 Integer goodsId = cart.getGoodsId(); QueryWrapper<Cart> queryWrapper = new QueryWrapper<>(); queryWrapper.eq("goods_id", goodsId); queryWrapper.eq("user_id", userId); Cart db = cartService.getOne(queryWrapper); if (db != null) {// db.setNumber(db.getNumber() + cart.getNumber()); db.setNumber(db.getNumber() + cart.getNumber()); cartService.updateById(db); return Result.success(); } //新增或更新 if (cart.getId() == null) { cart.setUserId(userId); } cartService.saveOrUpdate(cart); return Result.success(); } @PostMapping("/number/{id}/{number}") public Result updateNum(@PathVariable Integer id, @PathVariable Integer number) { cartMapper.updateNum(number, id); return Result.success(); } //删除 @DeleteMapping("/{id}") public Result delete(@PathVariable Integer id) { return Result.success(cartService.removeById(id)); } @PostMapping("/del/batch") public Result deleteBatch(@RequestBody List<Integer> ids) {//批量删除 return Result.success(cartService.removeByIds(ids)); } //查询所有数据 @GetMapping public Result findAll() { return Result.success(cartService.list()); } @GetMapping("/{id}") public Result findOne(@PathVariable Integer id) { return Result.success(cartService.getById(id)); }// @GetMapping("/id/{id}")// public Result findOne(@PathVariable String userId) {// QueryWrapper<Cart> queryWrapper = new QueryWrapper<>();// queryWrapper.eq("userId", userId);// return Result.success(cartService.getOne(queryWrapper));// } @GetMapping("/page") public Result findPage(@RequestParam Integer pageNum, @RequestParam Integer pageSize, @RequestParam(defaultValue = "") String name) { User currentUser = TokenUtils.getCurrentUser(); Integer userId = currentUser.getId(); String role = currentUser.getRole(); return Result.success(cartMapper.page(new Page<>(pageNum, pageSize), userId, role, name)); }}4.EchartsControllerimport cn.hutool.core.collection.CollUtil;import cn.hutool.core.date.DateUtil;import cn.hutool.core.date.Quarter;import com.example.demo.common.Result;import com.example.demo.entity.User;import com.example.demo.service.IUserService;import org.springframework.beans.factory.annotation.Autowired;import org.springframework.web.bind.annotation.GetMapping;import org.springframework.web.bind.annotation.RequestMapping;import org.springframework.web.bind.annotation.RestController;import java.util.Date;import java.util.HashMap;import java.util.List;import java.util.Map;@RestController@RequestMapping("/echarts")public class EchartsController { @Autowired private IUserService userService; @GetMapping("/example") public Result get() { Map<String, Object> map = new HashMap<>(); map.put("x", CollUtil.newArrayList("Mon", "Tue", "Wed", "Thu", "Fri", "Sat", "Sun")); map.put("y", CollUtil.newArrayList(150, 230, 224, 218, 135, 147, 260)); return Result.success(map); } @GetMapping("/members") public Result members() { List<User> list = userService.list(); int q1 = 0; //第一季度 int q2 = 0; //第二季度 int q3 = 0; //第三季度 int q4 = 0; //第四季度 for (User user : list) { Date createTime = user.getCreateTime(); Quarter quarter = DateUtil.quarterEnum(createTime); switch (quarter) { case Q1: q1 += 1; break; case Q2: q2 += 1; break; case Q3: q3 += 1; break; case Q4: q4 += 1; break; default: break; } } return Result.success(CollUtil.newArrayList(q1, q2, q3, q4)); }}5.FileControllerimport cn.hutool.core.io.FileUtil;import cn.hutool.core.util.IdUtil;import cn.hutool.core.util.StrUtil;import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;import com.example.demo.entity.Files;import com.example.demo.entity.Goods;import com.example.demo.mapper.FileMapper;import com.example.demo.mapper.GoodsMapper;import org.springframework.beans.factory.annotation.Value;import org.springframework.web.bind.annotation.*;import org.springframework.web.multipart.MultipartFile;import javax.annotation.Resource;import javax.servlet.ServletOutputStream;import javax.servlet.http.HttpServletResponse;import java.io.File;import java.io.IOException;import java.net.URLEncoder;import java.util.List;@RestController@RequestMapping("/file")public class FileController { @Value("${files.upload.path}") private String fileUploadPath; @Value("${server.ip}") private String serverIp; @Resource private FileMapper fileMapper; @Resource private GoodsMapper goodsMapper; @PostMapping("/upload") public String upload(@RequestParam MultipartFile file) throws IOException { String originalFilename = file.getOriginalFilename(); String type = FileUtil.extName(originalFilename); long size = file.getSize(); //定义一个文件的唯一标识码// String uuid = IdUtil.fastSimpleUUID();// String fileUUID = uuid + StrUtil.DOT + type;// File uploadFile = new File(fileUploadPath + fileUUID); //先存储到磁盘 File parentFile = new File(fileUploadPath);// File parentFile = uploadFile.getParentFile(); //判断目录是否存在,不存在就新建 if (!parentFile.exists()) { parentFile.mkdirs(); } String uuid = IdUtil.fastSimpleUUID(); String fileUUID = uuid + StrUtil.DOT + type; File uploadFile = new File(fileUploadPath + fileUUID); file.transferTo(uploadFile); String url = "http://" + serverIp + ":9090/file/" + fileUUID; //存储到数据库 Files saveFile = new Files(); Goods goods = new Goods(); saveFile.setName(originalFilename); saveFile.setType(type); saveFile.setSize(size/1024); saveFile.setUrl(url); goods.setUrl(url); fileMapper.insert(saveFile); goodsMapper.insert(goods); return url;// String md5 = SecureUtil.md5(file.getInputStream());// Files files = getFileByMd5(md5);//// String url;// if (files != null) {// url = files.getUrl();// } else {// file.transferTo(uploadFile);// url = "http://localhost:9090/file/" + fileUUID;// }// //存储到数据库// Files saveFile = new Files();// saveFile.setName(originalFilename);// saveFile.setType(type);// saveFile.setSize(size/1024);// saveFile.setUrl(url);// saveFile.setMd5(md5);// fileMapper.insert(saveFile);// return url; } @GetMapping("/{fileUUID}") public void download(@PathVariable String fileUUID, HttpServletResponse response) throws IOException { // 根据文件的唯一标识码获取文件 File uploadFile = new File(fileUploadPath + fileUUID); // 设置输出流的格式 ServletOutputStream os = response.getOutputStream(); response.addHeader("Content-Disposition", "attachment;filename=" + URLEncoder.encode(fileUUID, "UTF-8")); response.setContentType("application/octet-stream"); // 读取文件的字节流 os.write(FileUtil.readBytes(uploadFile)); os.flush(); os.close(); } /** * 通过文件的md5查询文件 * @param md5 * @return */ private Files getFileByMd5(String md5) { // 查询文件的md5是否存在 QueryWrapper<Files> queryWrapper = new QueryWrapper<>(); queryWrapper.eq("md5", md5); List<Files> filesList = fileMapper.selectList(queryWrapper); return filesList.size() == 0 ? null : filesList.get(0); }}6.MybatisPlusConfigimport com.baomidou.mybatisplus.annotation.DbType;import com.baomidou.mybatisplus.extension.plugins.MybatisPlusInterceptor;import com.baomidou.mybatisplus.extension.plugins.inner.PaginationInnerInterceptor;import org.mybatis.spring.annotation.MapperScan;import org.springframework.context.annotation.Bean;import org.springframework.context.annotation.Configuration;@Configuration@MapperScan("com.example.demo.mapper")public class MybatisPlusConfig { /** * 分页插件 */ @Bean public MybatisPlusInterceptor mybatisPlusInterceptor() { MybatisPlusInterceptor interceptor = new MybatisPlusInterceptor(); interceptor.addInnerInterceptor(new PaginationInnerInterceptor(DbType.MYSQL)); return interceptor; }}7.Constantspublic interface Constants { String CODE_200 = "200"; //成功 String CODE_400 = "400"; //参数不足 String CODE_401 = "401"; //权限不足 String CODE_500 = "500"; //系统错误 String CODE_600 = "600"; //其他业务异常}

完结撒花,对于在线商城这个项目呢,肯定还会有很多的优化,这个项目我也有2个版本,就是服务器上面的和不是服务器上面的,但是基本上都差不多。基本功能呢也都能实现, 只是跟商业的比起来肯定差点意思啦。各位小伙伴觉得笔者写的还不错,就多多点赞,需要源码的也可以私信我哦,看见信息第一时间回复大家。记得点赞关注!!!!

本文链接地址:https://www.jiuchutong.com/zhishi/299516.html 转载请保留说明!

上一篇:OpenAI Translator | 基于ChatGPT API全局翻译润色解析插件

下一篇:动态内存的开辟(动态内存管理)

  • 迅雷云盘在哪打开(迅雷云盘在哪找)

    迅雷云盘在哪打开(迅雷云盘在哪找)

  • 钉钉怎么查看打卡记录(钉钉怎么查看打卡距离)

    钉钉怎么查看打卡记录(钉钉怎么查看打卡距离)

  • 苹果耳机降噪模式怎么切换(苹果耳机降噪模式原理)

    苹果耳机降噪模式怎么切换(苹果耳机降噪模式原理)

  • vivo x50屏幕尺寸是多大(vivox50手机屏幕多少寸)

    vivo x50屏幕尺寸是多大(vivox50手机屏幕多少寸)

  • 抖音作品为什么要置顶(抖音作品为什么看不到浏览的人)

    抖音作品为什么要置顶(抖音作品为什么看不到浏览的人)

  • pr导出的时候encoder未安装(pr导出字幕不见了)

    pr导出的时候encoder未安装(pr导出字幕不见了)

  • 华为手机美颜怎么开(华为手机美颜怎么弄)

    华为手机美颜怎么开(华为手机美颜怎么弄)

  • 华为屏幕保修时间多久(华为屏幕保修时间查询)

    华为屏幕保修时间多久(华为屏幕保修时间查询)

  • 拼多多618是什么意思(拼多多618商品是正品吗)

    拼多多618是什么意思(拼多多618商品是正品吗)

  • 荣耀x10什么时候上市(荣耀x10什么时候出pro)

    荣耀x10什么时候上市(荣耀x10什么时候出pro)

  • 微信登录失败3-1是什么意思(微信登录失败该应用未获得微信登录的权限)

    微信登录失败3-1是什么意思(微信登录失败该应用未获得微信登录的权限)

  • 苹果手机压tp是什么意思(iphone 压tp)

    苹果手机压tp是什么意思(iphone 压tp)

  • 电脑可以用手机耳机听吗(电脑可以用手机当音响吗)

    电脑可以用手机耳机听吗(电脑可以用手机当音响吗)

  • hg261gu是千兆猫吗(hg226g是千兆猫吗)

    hg261gu是千兆猫吗(hg226g是千兆猫吗)

  • 无法保持通话什么意思(为什么无法保持通话)

    无法保持通话什么意思(为什么无法保持通话)

  • 华为录屏画质不好怎么办(华为录制屏幕不清晰)

    华为录屏画质不好怎么办(华为录制屏幕不清晰)

  • 笔记本电脑打开后不显示桌面黑屏(笔记本电脑打开软件总是弹出一个是或否)

    笔记本电脑打开后不显示桌面黑屏(笔记本电脑打开软件总是弹出一个是或否)

  • 电视盒子有什么用(电视盒子有什么好玩的游戏)

    电视盒子有什么用(电视盒子有什么好玩的游戏)

  • 电脑切屏键是什么(电脑切屏是哪个快捷键)

    电脑切屏键是什么(电脑切屏是哪个快捷键)

  • airpods pro 怎么充电(airpodspro怎么充电对电池好)

    airpods pro 怎么充电(airpodspro怎么充电对电池好)

  • 想要电影中的一段怎么剪辑(有一个电影里面是什么)

    想要电影中的一段怎么剪辑(有一个电影里面是什么)

  • 喜马拉雅怎么退订vip(喜马拉雅怎么退出粉丝团)

    喜马拉雅怎么退订vip(喜马拉雅怎么退出粉丝团)

  • wps文字超链接怎么做(wps文字超链接怎么打开)

    wps文字超链接怎么做(wps文字超链接怎么打开)

  • uki好友都是附近的吗(uki有附近人吗)

    uki好友都是附近的吗(uki有附近人吗)

  • 抖音怎么设置别人看不到我的粉丝(抖音怎么设置别人下载不了我的作品)

    抖音怎么设置别人看不到我的粉丝(抖音怎么设置别人下载不了我的作品)

  • 京东购买记录在哪里看(京东买东西记录在哪里查看)

    京东购买记录在哪里看(京东买东西记录在哪里查看)

  • 荣耀v20出厂有钢化膜吗(荣耀v20机身)

    荣耀v20出厂有钢化膜吗(荣耀v20机身)

  • 微信朋友圈显示非对方朋友是什么意思(微信朋友圈显示不全)

    微信朋友圈显示非对方朋友是什么意思(微信朋友圈显示不全)

  • 为什么app下载不了(为什么app下载不需要密码)

    为什么app下载不了(为什么app下载不需要密码)

  • qq画画功能在哪里(qq画画图片大全)

    qq画画功能在哪里(qq画画图片大全)

  • 恶搞,vbs+bat实现随机位置无限弹窗(恶搞代码vbs教程)

    恶搞,vbs+bat实现随机位置无限弹窗(恶搞代码vbs教程)

  • 正常工资薪金包括年终奖吗
  • 房产税计入管理费用了,汇算清缴怎么调
  • 服务业费用有哪些
  • 利息收入交所得税吗
  • 卷式发票是什么样的
  • 加计抵减的税额多长时间
  • 套期工具是资产还是负债
  • 如何在房产证上加父母名字
  • 旅游的合同
  • 无形资产资本化加计扣除可抵扣暂时性差异
  • 耕地占用税滞纳金是否能减免
  • 终止合同后原合同怎么处理
  • 房地产企业销售未完工产品预计毛利率
  • 企业收到预收账款,能不能给购买方开具发票
  • 外贸公司的出口清单
  • 堤围内的土地性质
  • 财务人员最重要的三点
  • 电子商务平台支付的区别
  • 代开专用发票缴纳的增值税需要计提吗?
  • 水利行政事业性收费收入会计分录
  • 关于增值税若干问题的探讨
  • 产权转移书据有哪些
  • 商贸公司开办费用
  • 固定资产清理的借方
  • 个体户能给自己交五险吗
  • win10内存完整性不兼容的驱动程序
  • 在windows7的
  • php数组函数输出《咏雪》里有多少"片"字
  • igfxext.exe
  • php字符串定义
  • 其他应收款贷方表示什么
  • 所得税费用怎么计算公式
  • 员工的通讯费怎么报销
  • 进价金额核算法例题
  • Vision Transformer 模型详解
  • 融资租赁增值税税目
  • 月末结转本年利润吗
  • php判断用户是否登录
  • java 日志系统
  • opengl环境光参数
  • 怎么安装vue-cli脚手架
  • 辅助生产车间工人工资计入
  • 扣供应商货款怎么入账
  • 个体工商户季度超过9万怎么交税
  • 会计准则中规范性的内容
  • 特许权使用费计入无形资产吗
  • 租入的房子再出租用交房产税吗?
  • 代金券抵帐怎么退款
  • 长期待摊的分录
  • 非限定性净资产是什么意思
  • 展位费按多少税率
  • ipv6文件
  • wrsvn.exe是什么
  • xpkw
  • dos命令提示符窗口怎么打开
  • ubuntu下安装deb文件
  • WIN10系统崩溃如何自救?
  • win8.1应用
  • linux下时间同步的两种方法分享
  • win7如何查看电脑主板型号
  • linux中病毒了怎么处理
  • 控制台报错是前端问题吗
  • js动态表格可修改表格数据
  • perl判断字符串相等
  • nodejs与springboot结合
  • js中的垃圾回收机制有哪些方法
  • python简易
  • javascript的dom
  • canvas的原理
  • python搜索功能
  • 二级联动什么意思
  • android 进程通信
  • JavaScript isPrototypeOf和hasOwnProperty使用区别
  • 国家税务总局令第43号公告
  • 申报参保时间怎么填
  • 动车票电子发票如何获取
  • 税务局无编制人员工资
  • 如何在国税电子税务平台为员工办理定制社保卡
  • 广告行业税率6%包含的内容
  • 乡村振兴与文化遗产保护研究
  • 免责声明:网站部分图片文字素材来源于网络,如有侵权,请及时告知,我们会第一时间删除,谢谢! 邮箱:opceo@qq.com

    鄂ICP备2023003026号

    网站地图: 企业信息 工商信息 财税知识 网络常识 编程技术

    友情链接: 武汉网站建设