Browse Source

优化结构

element-plus-release
Nick930826 2 years ago
parent
commit
1f164c67fc
  1. 8515
      package-lock.json
  2. 2
      src/App.vue
  3. 8
      src/components/Header.vue
  4. 2
      src/main.js
  5. 136
      src/views/Account.vue
  6. 386
      src/views/AddGood.vue
  7. 241
      src/views/Category.vue
  8. 125
      src/views/Good.vue
  9. 142
      src/views/Guest.vue
  10. 212
      src/views/Index.vue
  11. 208
      src/views/IndexConfig.vue
  12. 17
      src/views/Introduce.vue
  13. 83
      src/views/Login.vue
  14. 280
      src/views/Order.vue
  15. 8
      src/views/Swiper.vue
  16. 2
      vite.config.js
  17. 7967
      yarn.lock

8515
package-lock.json
File diff suppressed because it is too large
View File

2
src/App.vue

@ -220,7 +220,7 @@ export default {
text-decoration: none;
}
.el-pagination {
text-align: center;
justify-content: center;
margin-top: 20px;
}
.el-popper__arrow {

8
src/components/Header.vue

@ -1,7 +1,7 @@
<template>
<div class="header">
<div class="left">
<i v-if="hasBack" class="el-icon-back" @click="back"></i>
<i-back v-if="hasBack" width="14" height="14" class="el-icon-back" @click="back" />
<span style="font-size: 20px">{{ name }}</span>
</div>
<div class="right">
@ -81,13 +81,17 @@ export default {
<style scoped>
.header {
height: 50px;
height: 52px;
border-bottom: 1px solid #e9e9e9;
display: flex;
justify-content: space-between;
align-items: center;
padding: 0 20px;
}
.left {
display: flex;
align-items: center;
}
.el-icon-back {
border: 1px solid #e9e9e9;
padding: 4px;

2
src/main.js

@ -46,7 +46,7 @@ app.config.globalProperties.$filters = {
}
}
console.log('ElIconModules', ElIconModules)
// console.log('ElIconModules', ElIconModules)
function transElIconName (iconName) {
return 'i' + iconName.replace(/[A-Z]/g,(match)=> '-' + match.toLowerCase())

136
src/views/Account.vue

@ -1,11 +1,11 @@
<template>
<el-card class="account-container">
<el-form :model="nameForm" :rules="rules" ref="nameRef" label-width="80px" label-position="right" class="demo-ruleForm">
<el-form :model="nameForm" :rules="state.rules" ref="nameRef" label-width="80px" label-position="right" class="demo-ruleForm">
<el-form-item label="登录名:" prop="loginName">
<el-input style="width: 200px" v-model="nameForm.loginName"></el-input>
<el-input style="width: 200px" v-model="state.nameForm.loginName"></el-input>
</el-form-item>
<el-form-item label="昵称:" prop="nickName">
<el-input style="width: 200px" v-model="nameForm.nickName"></el-input>
<el-input style="width: 200px" v-model="state.nameForm.nickName"></el-input>
</el-form-item>
<el-form-item>
<el-button type="danger" @click="submitName">确认修改</el-button>
@ -13,12 +13,12 @@
</el-form>
</el-card>
<el-card class="account-container">
<el-form :model="passForm" :rules="rules" ref="passRef" label-width="80px" label-position="right" class="demo-ruleForm">
<el-form :model="passForm" :rules="state.rules" ref="passRef" label-width="80px" label-position="right" class="demo-ruleForm">
<el-form-item label="原密码:" prop="oldpass">
<el-input style="width: 200px" v-model="passForm.oldpass"></el-input>
<el-input style="width: 200px" v-model="state.passForm.oldpass"></el-input>
</el-form-item>
<el-form-item label="新密码:" prop="newpass">
<el-input style="width: 200px" v-model="passForm.newpass"></el-input>
<el-input style="width: 200px" v-model="state.passForm.newpass"></el-input>
</el-form-item>
<el-form-item>
<el-button type="danger" @click="submitPass">确认修改</el-button>
@ -27,82 +27,70 @@
</el-card>
</template>
<script>
<script setup>
import { onMounted, reactive, ref, toRefs } from 'vue'
import axios from '@/utils/axios'
import { ElMessage } from 'element-plus'
import md5 from 'js-md5'
export default {
name: 'Account',
setup() {
const nameRef = ref(null)
const passRef = ref(null)
const state = reactive({
user: null,
nameForm: {
loginName: '',
nickName: ''
},
passForm: {
oldpass: '',
newpass: ''
},
rules: {
loginName: [
{ required: 'true', message: '登录名不能为空', trigger: ['change'] }
],
nickName: [
{ required: 'true', message: '昵称不能为空', trigger: ['change'] }
],
oldpass: [
{ required: 'true', message: '原密码不能为空', trigger: ['change'] }
],
newpass: [
{ required: 'true', message: '新密码不能为空', trigger: ['change'] }
]
},
})
onMounted(() => {
axios.get('/adminUser/profile').then(res => {
state.user = res
state.nameForm.loginName = res.loginUserName
state.nameForm.nickName = res.nickName
})
})
const submitName = () => {
nameRef.value.validate((vaild) => {
if (vaild) {
axios.put('/adminUser/name', {
loginUserName: state.nameForm.loginName,
nickName: state.nameForm.nickName
}).then(() => {
ElMessage.success('修改成功')
window.location.reload()
})
}
const nameRef = ref(null)
const passRef = ref(null)
const state = reactive({
user: null,
nameForm: {
loginName: '',
nickName: ''
},
passForm: {
oldpass: '',
newpass: ''
},
rules: {
loginName: [
{ required: 'true', message: '登录名不能为空', trigger: ['change'] }
],
nickName: [
{ required: 'true', message: '昵称不能为空', trigger: ['change'] }
],
oldpass: [
{ required: 'true', message: '原密码不能为空', trigger: ['change'] }
],
newpass: [
{ required: 'true', message: '新密码不能为空', trigger: ['change'] }
]
},
})
onMounted(() => {
axios.get('/adminUser/profile').then(res => {
state.user = res
state.nameForm.loginName = res.loginUserName
state.nameForm.nickName = res.nickName
})
})
const submitName = () => {
nameRef.value.validate((vaild) => {
if (vaild) {
axios.put('/adminUser/name', {
loginUserName: state.nameForm.loginName,
nickName: state.nameForm.nickName
}).then(() => {
ElMessage.success('修改成功')
window.location.reload()
})
}
const submitPass = () => {
passRef.value.validate((vaild) => {
if (vaild) {
axios.put('/adminUser/password', {
originalPassword: md5(state.passForm.oldpass),
newPassword: md5(state.passForm.newpass)
}).then(() => {
ElMessage.success('修改成功')
window.location.reload()
})
}
})
}
const submitPass = () => {
passRef.value.validate((vaild) => {
if (vaild) {
axios.put('/adminUser/password', {
originalPassword: md5(state.passForm.oldpass),
newPassword: md5(state.passForm.newpass)
}).then(() => {
ElMessage.success('修改成功')
window.location.reload()
})
}
return {
...toRefs(state),
nameRef,
passRef,
submitName,
submitPass
}
}
})
}
</script>

386
src/views/AddGood.vue

@ -1,30 +1,30 @@
<template>
<div class="add">
<el-card class="add-container">
<el-form :model="goodForm" :rules="rules" ref="goodRef" label-width="100px" class="goodForm">
<el-form :model="state.goodForm" :rules="rules" ref="goodRef" label-width="100px" class="goodForm">
<el-form-item required label="商品分类">
<el-cascader :placeholder="defaultCate" style="width: 300px" :props="category" @change="handleChangeCate"></el-cascader>
<el-cascader :placeholder="state.defaultCate" style="width: 300px" :props="state.category" @change="handleChangeCate"></el-cascader>
</el-form-item>
<el-form-item label="商品名称" prop="goodsName">
<el-input style="width: 300px" v-model="goodForm.goodsName" placeholder="请输入商品名称"></el-input>
<el-input style="width: 300px" v-model="state.goodForm.goodsName" placeholder="请输入商品名称"></el-input>
</el-form-item>
<el-form-item label="商品简介" prop="goodsIntro">
<el-input style="width: 300px" type="textarea" v-model="goodForm.goodsIntro" placeholder="请输入商品简介(100字)"></el-input>
<el-input style="width: 300px" type="textarea" v-model="state.goodForm.goodsIntro" placeholder="请输入商品简介(100字)"></el-input>
</el-form-item>
<el-form-item label="商品价格" prop="originalPrice">
<el-input type="number" min="0" style="width: 300px" v-model="goodForm.originalPrice" placeholder="请输入商品价格"></el-input>
<el-input type="number" min="0" style="width: 300px" v-model="state.goodForm.originalPrice" placeholder="请输入商品价格"></el-input>
</el-form-item>
<el-form-item label="商品售卖价" prop="sellingPrice">
<el-input type="number" min="0" style="width: 300px" v-model="goodForm.sellingPrice" placeholder="请输入商品售价"></el-input>
<el-input type="number" min="0" style="width: 300px" v-model="state.goodForm.sellingPrice" placeholder="请输入商品售价"></el-input>
</el-form-item>
<el-form-item label="商品库存" prop="stockNum">
<el-input type="number" min="0" style="width: 300px" v-model="goodForm.stockNum" placeholder="请输入商品库存"></el-input>
<el-input type="number" min="0" style="width: 300px" v-model="state.goodForm.stockNum" placeholder="请输入商品库存"></el-input>
</el-form-item>
<el-form-item label="商品标签" prop="tag">
<el-input style="width: 300px" v-model="goodForm.tag" placeholder="请输入商品小标签"></el-input>
<el-input style="width: 300px" v-model="state.goodForm.tag" placeholder="请输入商品小标签"></el-input>
</el-form-item>
<el-form-item label="上架状态" prop="goodsSellStatus">
<el-radio-group v-model="goodForm.goodsSellStatus">
<el-radio-group v-model="state.goodForm.goodsSellStatus">
<el-radio label="0">上架</el-radio>
<el-radio label="1">下架</el-radio>
</el-radio-group>
@ -32,17 +32,17 @@
<el-form-item required label="商品主图" prop="goodsCoverImg">
<el-upload
class="avatar-uploader"
:action="uploadImgServer"
:action="state.uploadImgServer"
accept="jpg,jpeg,png"
:headers="{
token: token
token: state.token
}"
:show-file-list="false"
:before-upload="handleBeforeUpload"
:on-success="handleUrlSuccess"
>
<img style="width: 100px; height: 100px; border: 1px solid #e9e9e9;" v-if="goodForm.goodsCoverImg" :src="goodForm.goodsCoverImg" class="avatar">
<i v-else class="el-icon-plus avatar-uploader-icon"></i>
<img style="width: 100px; height: 100px; border: 1px solid #e9e9e9;" v-if="state.goodForm.goodsCoverImg" :src="state.goodForm.goodsCoverImg" class="avatar">
<i-plus v-else width='40' height='40' />
</el-upload>
</el-form-item>
<el-form-item label="详情内容">
@ -56,207 +56,194 @@
</div>
</template>
<script>
<script setup>
import { reactive, ref, toRefs, onMounted, onBeforeUnmount, getCurrentInstance } from 'vue'
import WangEditor from 'wangeditor'
import axios from '@/utils/axios'
import { ElMessage } from 'element-plus'
import { useRoute, useRouter } from 'vue-router'
import { localGet, uploadImgServer, uploadImgsServer, hasEmoji } from '@/utils'
export default {
name: 'AddGood',
setup() {
const { proxy } = getCurrentInstance()
console.log('proxy', proxy)
const editor = ref(null)
const goodRef = ref(null)
const route = useRoute()
const router = useRouter()
const { id } = route.query
const state = reactive({
uploadImgServer,
token: localGet('token') || '',
id: id,
defaultCate: '',
goodForm: {
goodsName: '',
goodsIntro: '',
originalPrice: '',
sellingPrice: '',
stockNum: '',
goodsSellStatus: '0',
goodsCoverImg: '',
tag: ''
},
rules: {
goodsCoverImg: [
{ required: 'true', message: '请上传主图', trigger: ['change'] }
],
goodsName: [
{ required: 'true', message: '请填写商品名称', trigger: ['change'] }
],
originalPrice: [
{ required: 'true', message: '请填写商品价格', trigger: ['change'] }
],
sellingPrice: [
{ required: 'true', message: '请填写商品售价', trigger: ['change'] }
],
stockNum: [
{ required: 'true', message: '请填写商品库存', trigger: ['change'] }
],
},
categoryId: '',
category: {
lazy: true,
lazyLoad(node, resolve) {
const { level = 0, value } = node
axios.get('/categories', {
params: {
pageNumber: 1,
pageSize: 1000,
categoryLevel: level + 1,
parentId: value || 0
}
}).then(res => {
const list = res.list
const nodes = list.map(item => ({
value: item.categoryId,
label: item.categoryName,
leaf: level > 1
}))
resolve(nodes)
})
}
}
})
let instance
onMounted(() => {
instance = new WangEditor(editor.value)
instance.config.showLinkImg = false
instance.config.showLinkImgAlt = false
instance.config.showLinkImgHref = false
instance.config.uploadImgMaxSize = 2 * 1024 * 1024 // 2M
instance.config.uploadFileName = 'file'
instance.config.uploadImgHeaders = {
token: state.token
}
//
instance.config.uploadImgHooks = {
//
// { errno: 0, data: [...] } 使 customInsert
customInsert: function(insertImgFn, result) {
console.log('result', result)
// result
// insertImgFn src
if (result.data && result.data.length) {
result.data.forEach(item => insertImgFn(item))
}
}
}
instance.config.uploadImgServer = uploadImgsServer
Object.assign(instance.config, {
onchange() {
console.log('change')
},
})
instance.create()
if (id) {
axios.get(`/goods/${id}`).then(res => {
const { goods, firstCategory, secondCategory, thirdCategory } = res
state.goodForm = {
goodsName: goods.goodsName,
goodsIntro: goods.goodsIntro,
originalPrice: goods.originalPrice,
sellingPrice: goods.sellingPrice,
stockNum: goods.stockNum,
goodsSellStatus: String(goods.goodsSellStatus),
goodsCoverImg: proxy.$filters.prefix(goods.goodsCoverImg),
tag: goods.tag,
categoryId: goods.goodsCategoryId
}
state.categoryId = goods.goodsCategoryId
state.defaultCate = `${firstCategory.categoryName}/${secondCategory.categoryName}/${thirdCategory.categoryName}`
if (instance) {
// html
instance.txt.html(goods.goodsDetailContent)
const { proxy } = getCurrentInstance()
console.log('proxy', proxy)
const editor = ref(null)
const goodRef = ref(null)
const route = useRoute()
const router = useRouter()
const { id } = route.query
const state = reactive({
uploadImgServer,
token: localGet('token') || '',
id: id,
defaultCate: '',
goodForm: {
goodsName: '',
goodsIntro: '',
originalPrice: '',
sellingPrice: '',
stockNum: '',
goodsSellStatus: '0',
goodsCoverImg: '',
tag: ''
},
rules: {
goodsCoverImg: [
{ required: 'true', message: '请上传主图', trigger: ['change'] }
],
goodsName: [
{ required: 'true', message: '请填写商品名称', trigger: ['change'] }
],
originalPrice: [
{ required: 'true', message: '请填写商品价格', trigger: ['change'] }
],
sellingPrice: [
{ required: 'true', message: '请填写商品售价', trigger: ['change'] }
],
stockNum: [
{ required: 'true', message: '请填写商品库存', trigger: ['change'] }
],
},
categoryId: '',
category: {
lazy: true,
lazyLoad(node, resolve) {
const { level = 0, value } = node
axios.get('/categories', {
params: {
pageNumber: 1,
pageSize: 1000,
categoryLevel: level + 1,
parentId: value || 0
}
}).then(res => {
const list = res.list
const nodes = list.map(item => ({
value: item.categoryId,
label: item.categoryName,
leaf: level > 1
}))
resolve(nodes)
})
}
}
})
let instance
onMounted(() => {
instance = new WangEditor(editor.value)
instance.config.showLinkImg = false
instance.config.showLinkImgAlt = false
instance.config.showLinkImgHref = false
instance.config.uploadImgMaxSize = 2 * 1024 * 1024 // 2M
instance.config.uploadFileName = 'file'
instance.config.uploadImgHeaders = {
token: state.token
}
//
instance.config.uploadImgHooks = {
//
// { errno: 0, data: [...] } 使 customInsert
customInsert: function(insertImgFn, result) {
console.log('result', result)
// result
// insertImgFn src
if (result.data && result.data.length) {
result.data.forEach(item => insertImgFn(item))
}
}
}
instance.config.uploadImgServer = uploadImgsServer
Object.assign(instance.config, {
onchange() {
console.log('change')
},
})
onBeforeUnmount(() => {
instance.destroy()
instance = null
})
const submitAdd = () => {
goodRef.value.validate((vaild) => {
if (vaild) {
// post
let httpOption = axios.post
let params = {
goodsCategoryId: state.categoryId,
goodsCoverImg: state.goodForm.goodsCoverImg,
goodsDetailContent: instance.txt.html(),
goodsIntro: state.goodForm.goodsIntro,
goodsName: state.goodForm.goodsName,
goodsSellStatus: state.goodForm.goodsSellStatus,
originalPrice: state.goodForm.originalPrice,
sellingPrice: state.goodForm.sellingPrice,
stockNum: state.goodForm.stockNum,
tag: state.goodForm.tag
}
if (hasEmoji(params.goodsIntro) || hasEmoji(params.goodsName) || hasEmoji(params.tag) || hasEmoji(params.goodsDetailContent)) {
ElMessage.error('不要输入表情包,再输入就打死你个龟孙儿~')
return
}
if (params.goodsName.length > 128) {
ElMessage.error('商品名称不能超过128个字符')
return
}
if (params.goodsIntro.length > 200) {
ElMessage.error('商品简介不能超过200个字符')
return
}
if (params.tag.length > 16) {
ElMessage.error('商品标签不能超过16个字符')
return
}
console.log('params', params)
if (id) {
params.goodsId = id
// 使 put
httpOption = axios.put
}
httpOption('/goods', params).then(() => {
ElMessage.success(id ? '修改成功' : '添加成功')
router.push({ path: '/good' })
})
instance.create()
if (id) {
axios.get(`/goods/${id}`).then(res => {
const { goods, firstCategory, secondCategory, thirdCategory } = res
state.goodForm = {
goodsName: goods.goodsName,
goodsIntro: goods.goodsIntro,
originalPrice: goods.originalPrice,
sellingPrice: goods.sellingPrice,
stockNum: goods.stockNum,
goodsSellStatus: String(goods.goodsSellStatus),
goodsCoverImg: proxy.$filters.prefix(goods.goodsCoverImg),
tag: goods.tag,
categoryId: goods.goodsCategoryId
}
state.categoryId = goods.goodsCategoryId
state.defaultCate = `${firstCategory.categoryName}/${secondCategory.categoryName}/${thirdCategory.categoryName}`
if (instance) {
// html
instance.txt.html(goods.goodsDetailContent)
}
})
}
const handleBeforeUpload = (file) => {
const sufix = file.name.split('.')[1] || ''
if (!['jpg', 'jpeg', 'png'].includes(sufix)) {
ElMessage.error('请上传 jpg、jpeg、png 格式的图片')
return false
})
onBeforeUnmount(() => {
instance.destroy()
instance = null
})
const submitAdd = () => {
goodRef.value.validate((vaild) => {
if (vaild) {
// post
let httpOption = axios.post
let params = {
goodsCategoryId: state.categoryId,
goodsCoverImg: state.goodForm.goodsCoverImg,
goodsDetailContent: instance.txt.html(),
goodsIntro: state.goodForm.goodsIntro,
goodsName: state.goodForm.goodsName,
goodsSellStatus: state.goodForm.goodsSellStatus,
originalPrice: state.goodForm.originalPrice,
sellingPrice: state.goodForm.sellingPrice,
stockNum: state.goodForm.stockNum,
tag: state.goodForm.tag
}
if (hasEmoji(params.goodsIntro) || hasEmoji(params.goodsName) || hasEmoji(params.tag) || hasEmoji(params.goodsDetailContent)) {
ElMessage.error('不要输入表情包,再输入就打死你个龟孙儿~')
return
}
if (params.goodsName.length > 128) {
ElMessage.error('商品名称不能超过128个字符')
return
}
if (params.goodsIntro.length > 200) {
ElMessage.error('商品简介不能超过200个字符')
return
}
if (params.tag.length > 16) {
ElMessage.error('商品标签不能超过16个字符')
return
}
console.log('params', params)
if (id) {
params.goodsId = id
// 使 put
httpOption = axios.put
}
httpOption('/goods', params).then(() => {
ElMessage.success(id ? '修改成功' : '添加成功')
router.push({ path: '/good' })
})
}
})
}
const handleBeforeUpload = (file) => {
console.log('file', file)
const sufix = file.name.split('.')[1] || ''
if (!['jpg', 'jpeg', 'png'].includes(sufix)) {
ElMessage.error('请上传 jpg、jpeg、png 格式的图片')
return false
}
const handleUrlSuccess = (val) => {
state.goodForm.goodsCoverImg = val.data || ''
}
const handleChangeCate = (val) => {
state.categoryId = val[2] || 0
}
return {
...toRefs(state),
goodRef,
submitAdd,
handleBeforeUpload,
handleUrlSuccess,
editor,
handleChangeCate
}
}
}
const handleUrlSuccess = (val) => {
state.goodForm.goodsCoverImg = val.data || ''
}
const handleChangeCate = (val) => {
state.categoryId = val[2] || 0
}
</script>
<style scoped>
@ -272,6 +259,9 @@ export default {
height: 100px;
color: #ddd;
font-size: 30px;
border: 1px solid #e9e9e9;
text-align: center;
line-height: 116px;
}
.avatar-uploader-icon {
display: block;

241
src/views/Category.vue

@ -2,21 +2,23 @@
<el-card class="category-container">
<template #header>
<div class="header">
<el-button type="primary" size="small" icon="el-icon-plus" @click="handleAdd">增加</el-button>
<el-button type="primary" @click="handleAdd"><i-plus width='14' /> 增加</el-button>
<el-popconfirm
title="确定删除吗?"
@confirm="handleDelete"
confirm-button-text="确定"
cancel-button-text="取消"
>
<template #reference>
<el-button type="danger" size="small" icon="el-icon-delete">批量删除</el-button>
<el-button type="danger"><i-delete width='14' /> 批量删除</el-button>
</template>
</el-popconfirm>
</div>
</template>
<el-table
v-loading="loading"
v-loading="state.loading"
ref="multipleTable"
:data="tableData"
:data="state.tableData"
tooltip-effect="dark"
style="width: 100%"
@selection-change="handleSelectionChange">
@ -52,6 +54,8 @@
<el-popconfirm
title="确定删除吗?"
@confirm="handleDeleteOne(scope.row.categoryId)"
confirm-button-text="确定"
cancel-button-text="取消"
>
<template #reference>
<a style="cursor: pointer">删除</a>
@ -64,145 +68,124 @@
<el-pagination
background
layout="prev, pager, next"
:total="total"
:page-size="pageSize"
:current-page="currentPage"
:total="state.total"
:page-size="state.pageSize"
:current-page="state.currentPage"
@current-change="changePage"
/>
</el-card>
<DialogAddCategory ref='addGood' :reload="getCategory" :type="type" :level="level" :parent_id="parent_id" />
<DialogAddCategory ref='addGood' :reload="getCategory" :type="state.type" :level="state.level" :parent_id="state.parent_id" />
</template>
<script>
<script setup>
import { onMounted, onUnmounted, reactive, ref, toRefs } from 'vue'
import { useRoute, useRouter } from 'vue-router'
import { ElMessage } from 'element-plus'
import DialogAddCategory from '@/components/DialogAddCategory.vue'
import axios from '@/utils/axios'
export default {
name: 'Category',
components: {
DialogAddCategory
},
setup() {
const multipleTable = ref(null)
const addGood = ref(null)
const router = useRouter()
const route = useRoute()
const state = reactive({
loading: false,
tableData: [], //
multipleSelection: [], //
total: 0, //
currentPage: 1, //
pageSize: 10, //
type: 'add', //
level: 1,
parent_id: 0
})
onMounted(() => {
getCategory()
})
onUnmounted(() => {
unwatch()
})
const unwatch = router.afterEach((to) => {
if (['category', 'level2', 'level3'].includes(to.name)) {
getCategory()
}
})
//
const getCategory = () => {
const { level = 1, parent_id = 0 } = route.query
state.loading = true
axios.get('/categories', {
params: {
pageNumber: state.currentPage,
pageSize: state.pageSize,
categoryLevel: level,
parentId: parent_id
}
}).then(res => {
state.tableData = res.list
state.total = res.totalCount
state.currentPage = res.currPage
state.loading = false
state.level = level
state.parentId = parent_id
})
}
//
const handleAdd = () => {
state.type = 'add'
addGood.value.open()
}
//
const handleEdit = (id) => {
state.type = 'edit'
addGood.value.open(id)
}
//
const handleSelectionChange = (val) => {
state.multipleSelection = val
}
//
const handleDelete = () => {
if (!state.multipleSelection.length) {
ElMessage.error('请选择项')
return
}
axios.delete('/categories', {
data: {
ids: state.multipleSelection.map(i => i.categoryId)
}
}).then(() => {
ElMessage.success('删除成功')
getCategory()
})
}
//
const handleDeleteOne = (id) => {
axios.delete('/categories', {
data: {
ids: [id]
}
}).then(() => {
ElMessage.success('删除成功')
getCategory()
})
}
const changePage = (val) => {
state.currentPage = val
getCategory()
const multipleTable = ref(null)
const addGood = ref(null)
const router = useRouter()
const route = useRoute()
const state = reactive({
loading: false,
tableData: [], //
multipleSelection: [], //
total: 0, //
currentPage: 1, //
pageSize: 10, //
type: 'add', //
level: 1,
parent_id: 0
})
onMounted(() => {
getCategory()
})
onUnmounted(() => {
unwatch()
})
const unwatch = router.afterEach((to) => {
if (['category', 'level2', 'level3'].includes(to.name)) {
getCategory()
}
})
//
const getCategory = () => {
const { level = 1, parent_id = 0 } = route.query
state.loading = true
axios.get('/categories', {
params: {
pageNumber: state.currentPage,
pageSize: state.pageSize,
categoryLevel: level,
parentId: parent_id
}
const handleNext = (item) => {
const levelNumber = item.categoryLevel + 1
if (levelNumber == 4) {
ElMessage.error('没有下一级')
return
}
router.push({
name: `level${levelNumber}`,
query: {
level: levelNumber,
parent_id: item.categoryId
}
})
}).then(res => {
state.tableData = res.list
state.total = res.totalCount
state.currentPage = res.currPage
state.loading = false
state.level = level
state.parentId = parent_id
})
}
//
const handleAdd = () => {
state.type = 'add'
addGood.value.open()
}
//
const handleEdit = (id) => {
state.type = 'edit'
addGood.value.open(id)
}
//
const handleSelectionChange = (val) => {
state.multipleSelection = val
}
//
const handleDelete = () => {
if (!state.multipleSelection.length) {
ElMessage.error('请选择项')
return
}
axios.delete('/categories', {
data: {
ids: state.multipleSelection.map(i => i.categoryId)
}
return {
...toRefs(state),
multipleTable,
handleSelectionChange,
addGood,
handleAdd,
handleEdit,
handleDelete,
handleDeleteOne,
getCategory,
changePage,
handleNext
}).then(() => {
ElMessage.success('删除成功')
getCategory()
})
}
//
const handleDeleteOne = (id) => {
axios.delete('/categories', {
data: {
ids: [id]
}
}).then(() => {
ElMessage.success('删除成功')
getCategory()
})
}
const changePage = (val) => {
state.currentPage = val
getCategory()
}
const handleNext = (item) => {
const levelNumber = item.categoryLevel + 1
if (levelNumber == 4) {
ElMessage.error('没有下一级')
return
}
router.push({
name: `level${levelNumber}`,
query: {
level: levelNumber,
parent_id: item.categoryId
}
})
}
</script>

125
src/views/Good.vue

@ -2,13 +2,13 @@
<el-card class="good-container">
<template #header>
<div class="header">
<el-button type="primary" size="small" icon="el-icon-plus" @click="handleAdd">新增商品</el-button>
<el-button type="primary" @click="handleAdd"><i-plus width='14' /> 新增商品</el-button>
</div>
</template>
<el-table
v-loading="loading"
v-loading="state.loading"
ref="multipleTable"
:data="tableData"
:data="state.tableData"
tooltip-effect="dark"
style="width: 100%"
@selection-change="handleSelectionChange">
@ -73,83 +73,68 @@
<el-pagination
background
layout="prev, pager, next"
:total="total"
:page-size="pageSize"
:current-page="currentPage"
:total="state.total"
:page-size="state.pageSize"
:current-page="state.currentPage"
@current-change="changePage"
/>
</el-card>
</template>
<script>
<script setup>
import { onMounted, reactive, ref, toRefs } from 'vue'
import axios from '@/utils/axios'
import { ElMessage } from 'element-plus'
import { useRouter } from 'vue-router'
export default {
name: 'Good',
setup() {
const multipleTable = ref(null)
const router = useRouter()
const state = reactive({
loading: false,
tableData: [], //
multipleSelection: [], //
total: 0, //
currentPage: 1, //
pageSize: 10 //
})
onMounted(() => {
getGoodList()
})
//
const getGoodList = () => {
state.loading = true
axios.get('/goods/list', {
params: {
pageNumber: state.currentPage,
pageSize: state.pageSize
}
}).then(res => {
state.tableData = res.list
state.total = res.totalCount
state.currentPage = res.currPage
state.loading = false
})
const multipleTable = ref(null)
const router = useRouter()
const state = reactive({
loading: false,
tableData: [], //
multipleSelection: [], //
total: 0, //
currentPage: 1, //
pageSize: 10 //
})
onMounted(() => {
getGoodList()
})
//
const getGoodList = () => {
state.loading = true
axios.get('/goods/list', {
params: {
pageNumber: state.currentPage,
pageSize: state.pageSize
}
const handleAdd = () => {
router.push({ path: '/add' })
}
const handleEdit = (id) => {
router.push({ path: '/add', query: { id } })
}
//
const handleSelectionChange = (val) => {
state.multipleSelection = val
}
const changePage = (val) => {
state.currentPage = val
getGoodList()
}
const handleStatus = (id, status) => {
axios.put(`/goods/status/${status}`, {
ids: id ? [id] : []
}).then(() => {
ElMessage.success('修改成功')
getGoodList()
})
}
return {
...toRefs(state),
multipleTable,
handleSelectionChange,
handleAdd,
handleEdit,
getGoodList,
changePage,
handleStatus
}
}
}).then(res => {
state.tableData = res.list
state.total = res.totalCount
state.currentPage = res.currPage
state.loading = false
})
}
const handleAdd = () => {
router.push({ path: '/add' })
}
const handleEdit = (id) => {
router.push({ path: '/add', query: { id } })
}
//
const handleSelectionChange = (val) => {
state.multipleSelection = val
}
const changePage = (val) => {
state.currentPage = val
getGoodList()
}
const handleStatus = (id, status) => {
axios.put(`/goods/status/${status}`, {
ids: id ? [id] : []
}).then(() => {
ElMessage.success('修改成功')
getGoodList()
})
}
</script>

142
src/views/Guest.vue

@ -2,14 +2,14 @@
<el-card class="guest-container">
<template #header>
<div class="header">
<el-button type="primary" size="small" icon="el-icon-plus" @click="handleSolve">解除禁用</el-button>
<el-button type="danger" size="small" icon="el-icon-delete" @click="handleForbid">禁用账户</el-button>
<el-button type="primary" @click="handleSolve">解除禁用</el-button>
<el-button type="danger" @click="handleForbid">禁用账户</el-button>
</div>
</template>
<el-table
v-loading="loading"
v-loading="state.loading"
ref="multipleTable"
:data="tableData"
:data="state.tableData"
tooltip-effect="dark"
style="width: 100%"
@selection-change="handleSelectionChange">
@ -71,90 +71,76 @@
<el-pagination
background
layout="prev, pager, next"
:total="total"
:page-size="pageSize"
:current-page="currentPage"
:total="state.total"
:page-size="state.pageSize"
:current-page="state.currentPage"
@current-change="changePage"
/>
</el-card>
</template>
<script>
<script setup>
import { onMounted, reactive, ref, toRefs } from 'vue'
import axios from '@/utils/axios'
import { ElMessage } from 'element-plus'
export default {
name: 'Guest',
setup() {
const multipleTable = ref(null)
const state = reactive({
loading: false,
tableData: [], //
multipleSelection: [], //
total: 0, //
currentPage: 1, //
pageSize: 10 //
})
onMounted(() => {
getGuestList()
})
//
const getGuestList = () => {
state.loading = true
axios.get('/users', {
params: {
pageNumber: state.currentPage,
pageSize: state.pageSize
}
}).then(res => {
state.tableData = res.list
state.total = res.totalCount
state.currentPage = res.currPage
state.loading = false
})
}
//
const handleSelectionChange = (val) => {
state.multipleSelection = val
}
const changePage = (val) => {
state.currentPage = val
getGuestList()
}
const handleSolve = () => {
if (!state.multipleSelection.length) {
ElMessage.error('请选择项')
return
}
axios.put(`/users/0`, {
ids: state.multipleSelection.map(item => item.userId)
}).then(() => {
ElMessage.success('解除成功')
getGuestList()
})
}
const handleForbid = () => {
if (!state.multipleSelection.length) {
ElMessage.error('请选择项')
return
}
axios.put(`/users/1`, {
ids: state.multipleSelection.map(item => item.userId)
}).then(() => {
ElMessage.success('禁用成功')
getGuestList()
})
}
return {
...toRefs(state),
multipleTable,
handleSelectionChange,
getGuestList,
changePage,
handleSolve,
handleForbid
const multipleTable = ref(null)
const state = reactive({
loading: false,
tableData: [], //
multipleSelection: [], //
total: 0, //
currentPage: 1, //
pageSize: 10 //
})
onMounted(() => {
getGuestList()
})
//
const getGuestList = () => {
state.loading = true
axios.get('/users', {
params: {
pageNumber: state.currentPage,
pageSize: state.pageSize
}
}).then(res => {
state.tableData = res.list
state.total = res.totalCount
state.currentPage = res.currPage
state.loading = false
})
}
//
const handleSelectionChange = (val) => {
state.multipleSelection = val
}
const changePage = (val) => {
state.currentPage = val
getGuestList()
}
const handleSolve = () => {
if (!state.multipleSelection.length) {
ElMessage.error('请选择项')
return
}
axios.put(`/users/0`, {
ids: state.multipleSelection.map(item => item.userId)
}).then(() => {
ElMessage.success('解除成功')
getGuestList()
})
}
const handleForbid = () => {
if (!state.multipleSelection.length) {
ElMessage.error('请选择项')
return
}
axios.put(`/users/1`, {
ids: state.multipleSelection.map(item => item.userId)
}).then(() => {
ElMessage.success('禁用成功')
getGuestList()
})
}
</script>

212
src/views/Index.vue

@ -30,125 +30,119 @@
</el-card>
</template>
<script>
<script setup>
import { onMounted, onUnmounted } from 'vue'
let myChart = null
export default {
name: 'Index',
setup() {
onMounted(() => {
if (window.echarts) {
// domecharts
myChart = window.echarts.init(document.getElementById('zoom'))
onMounted(() => {
if (window.echarts) {
// domecharts
myChart = window.echarts.init(document.getElementById('zoom'))
//
const option = {
title: {
text: '系统折线图'
//
const option = {
title: {
text: '系统折线图'
},
tooltip: {
trigger: 'axis',
axisPointer: {
type: 'cross',
label: {
backgroundColor: '#6a7985'
}
}
},
legend: {
data: ['新增注册', '付费用户', '活跃用户', '订单数', '当日总收入']
},
toolbox: {
feature: {
saveAsImage: {}
}
},
grid: {
left: '3%',
right: '4%',
bottom: '3%',
containLabel: true
},
xAxis: [
{
type: 'category',
boundaryGap: false,
data: ['2021-03-11', '2021-03-12', '2021-03-13', '2021-03-14', '2021-03-15', '2021-03-16', '2021-03-17']
}
],
yAxis: [
{
type: 'value'
}
],
series: [
{
name: '新增注册',
type: 'line',
stack: '总量',
areaStyle: {},
emphasis: {
focus: 'series'
},
data: [120, 132, 101, 134, 90, 230, 210]
},
{
name: '付费用户',
type: 'line',
stack: '总量',
areaStyle: {},
emphasis: {
focus: 'series'
},
tooltip: {
trigger: 'axis',
axisPointer: {
type: 'cross',
label: {
backgroundColor: '#6a7985'
}
}
data: [220, 182, 191, 234, 290, 330, 310]
},
{
name: '活跃用户',
type: 'line',
stack: '总量',
areaStyle: {},
emphasis: {
focus: 'series'
},
legend: {
data: ['新增注册', '付费用户', '活跃用户', '订单数', '当日总收入']
data: [150, 232, 201, 154, 190, 330, 410]
},
{
name: '订单数',
type: 'line',
stack: '总量',
areaStyle: {},
emphasis: {
focus: 'series'
},
toolbox: {
feature: {
saveAsImage: {}
}
data: [320, 332, 301, 334, 390, 330, 320]
},
{
name: '当日总收入',
type: 'line',
stack: '总量',
label: {
show: true,
position: 'top'
},
grid: {
left: '3%',
right: '4%',
bottom: '3%',
containLabel: true
areaStyle: {},
emphasis: {
focus: 'series'
},
xAxis: [
{
type: 'category',
boundaryGap: false,
data: ['2021-03-11', '2021-03-12', '2021-03-13', '2021-03-14', '2021-03-15', '2021-03-16', '2021-03-17']
}
],
yAxis: [
{
type: 'value'
}
],
series: [
{
name: '新增注册',
type: 'line',
stack: '总量',
areaStyle: {},
emphasis: {
focus: 'series'
},
data: [120, 132, 101, 134, 90, 230, 210]
},
{
name: '付费用户',
type: 'line',
stack: '总量',
areaStyle: {},
emphasis: {
focus: 'series'
},
data: [220, 182, 191, 234, 290, 330, 310]
},
{
name: '活跃用户',
type: 'line',
stack: '总量',
areaStyle: {},
emphasis: {
focus: 'series'
},
data: [150, 232, 201, 154, 190, 330, 410]
},
{
name: '订单数',
type: 'line',
stack: '总量',
areaStyle: {},
emphasis: {
focus: 'series'
},
data: [320, 332, 301, 334, 390, 330, 320]
},
{
name: '当日总收入',
type: 'line',
stack: '总量',
label: {
show: true,
position: 'top'
},
areaStyle: {},
emphasis: {
focus: 'series'
},
data: [820, 932, 901, 934, 1290, 1330, 1320]
}
]
data: [820, 932, 901, 934, 1290, 1330, 1320]
}
]
}
// 使
myChart.setOption(option)
}
})
onUnmounted(() => {
myChart.dispose()
})
}
}
// 使
myChart.setOption(option)
}
})
onUnmounted(() => {
myChart.dispose()
})
</script>
<style scoped>

208
src/views/IndexConfig.vue

@ -2,21 +2,23 @@
<el-card class="index-container">
<template #header>
<div class="header">
<el-button type="primary" size="small" icon="el-icon-plus" @click="handleAdd">增加</el-button>
<el-button type="primary" @click="handleAdd"><i-plus width='14' /> 增加</el-button>
<el-popconfirm
title="确定删除吗?"
@confirm="handleDelete"
confirm-button-text="确定"
cancel-button-text="取消"
>
<template #reference>
<el-button type="danger" size="small" icon="el-icon-delete">批量删除</el-button>
<el-button type="danger"><i-delete width='14' /> 批量删除</el-button>
</template>
</el-popconfirm>
</div>
</template>
<el-table
v-loading="loading"
v-loading="state.loading"
ref="multipleTable"
:data="tableData"
:data="state.tableData"
tooltip-effect="dark"
style="width: 100%"
@selection-change="handleSelectionChange">
@ -63,6 +65,8 @@
<el-popconfirm
title="确定删除吗?"
@confirm="handleDeleteOne(scope.row.configId)"
confirmButtonText='确定'
cancelButtonText='取消'
>
<template #reference>
<a style="cursor: pointer">删除</a>
@ -75,16 +79,16 @@
<el-pagination
background
layout="prev, pager, next"
:total="total"
:page-size="pageSize"
:current-page="currentPage"
:total="state.total"
:page-size="state.pageSize"
:current-page="state.currentPage"
@current-change="changePage"
/>
</el-card>
<DialogAddGood ref='addGood' :reload="getIndexConfig" :type="type" :configType="configType" />
<DialogAddGood ref='addGood' :reload="getIndexConfig" :type="state.type" :configType="state.configType" />
</template>
<script>
<script setup>
import { onMounted, onUnmounted, reactive, ref, toRefs } from 'vue'
import { ElMessage } from 'element-plus'
import DialogAddGood from '@/components/DialogAddGood.vue'
@ -96,111 +100,91 @@ const configTypeMap = {
new: 4,
recommend: 5
}
export default {
name: 'Hot',
components: {
DialogAddGood
},
setup() {
const router = useRouter()
const route = useRoute()
const multipleTable = ref(null)
const addGood = ref(null)
const state = reactive({
loading: false,
tableData: [], //
multipleSelection: [], //
total: 0, //
currentPage: 1, //
pageSize: 10, //
type: 'add', //
configType: 3 // 3-() 4-()线 5-()
})
//
const unwatch = router.beforeEach((to) => {
if (['hot', 'new', 'recommend'].includes(to.name)) {
state.configType = configTypeMap[to.name]
state.currentPage = 1
getIndexConfig()
}
})
//
onMounted(() => {
state.configType = configTypeMap[route.name]
getIndexConfig()
})
onUnmounted(() => {
unwatch()
})
//
const getIndexConfig = () => {
state.loading = true
axios.get('/indexConfigs', {
params: {
pageNumber: state.currentPage,
pageSize: state.pageSize,
configType: state.configType
}
}).then(res => {
state.tableData = res.list
state.total = res.totalCount
state.currentPage = res.currPage
state.loading = false
})
}
//
const handleAdd = () => {
state.type = 'add'
addGood.value.open()
}
//
const handleEdit = (id) => {
state.type = 'edit'
addGood.value.open(id)
}
//
const handleSelectionChange = (val) => {
state.multipleSelection = val
}
//
const handleDelete = () => {
if (!state.multipleSelection.length) {
ElMessage.error('请选择项')
return
}
axios.post('/indexConfigs/delete', {
ids: state.multipleSelection.map(i => i.configId)
}).then(() => {
ElMessage.success('删除成功')
getIndexConfig()
})
}
//
const handleDeleteOne = (id) => {
axios.post('/indexConfigs/delete', {
ids: [id]
}).then(() => {
ElMessage.success('删除成功')
getIndexConfig()
})
}
const changePage = (val) => {
state.currentPage = val
getIndexConfig()
}
return {
...toRefs(state),
multipleTable,
handleSelectionChange,
addGood,
handleAdd,
handleEdit,
handleDelete,
handleDeleteOne,
getIndexConfig,
changePage
const router = useRouter()
const route = useRoute()
const multipleTable = ref(null)
const addGood = ref(null)
const state = reactive({
loading: false,
tableData: [], //
multipleSelection: [], //
total: 0, //
currentPage: 1, //
pageSize: 10, //
type: 'add', //
configType: 3 // 3-() 4-()线 5-()
})
//
const unwatch = router.beforeEach((to) => {
if (['hot', 'new', 'recommend'].includes(to.name)) {
state.configType = configTypeMap[to.name]
state.currentPage = 1
getIndexConfig()
}
})
//
onMounted(() => {
state.configType = configTypeMap[route.name]
getIndexConfig()
})
onUnmounted(() => {
unwatch()
})
//
const getIndexConfig = () => {
state.loading = true
axios.get('/indexConfigs', {
params: {
pageNumber: state.currentPage,
pageSize: state.pageSize,
configType: state.configType
}
}).then(res => {
state.tableData = res.list
state.total = res.totalCount
state.currentPage = res.currPage
state.loading = false
})
}
//
const handleAdd = () => {
state.type = 'add'
addGood.value.open()
}
//
const handleEdit = (id) => {
state.type = 'edit'
addGood.value.open(id)
}
//
const handleSelectionChange = (val) => {
state.multipleSelection = val
}
//
const handleDelete = () => {
if (!state.multipleSelection.length) {
ElMessage.error('请选择项')
return
}
axios.post('/indexConfigs/delete', {
ids: state.multipleSelection.map(i => i.configId)
}).then(() => {
ElMessage.success('删除成功')
getIndexConfig()
})
}
//
const handleDeleteOne = (id) => {
axios.post('/indexConfigs/delete', {
ids: [id]
}).then(() => {
ElMessage.success('删除成功')
getIndexConfig()
})
}
const changePage = (val) => {
state.currentPage = val
getIndexConfig()
}
</script>

17
src/views/Introduce.vue

@ -73,19 +73,10 @@
</el-card>
</template>
<script>
export default {
name: 'Introduce',
setup() {
const goJuejin = () => {
console.log('goJuejin')
window.open('https://juejin.cn/book/6933939264455442444', 'target')
}
return {
goJuejin
}
}
<script setup>
const goJuejin = () => {
console.log('goJuejin')
window.open('https://juejin.cn/book/6933939264455442444', 'target')
}
</script>
<style scoped>

83
src/views/Login.vue

@ -8,17 +8,17 @@
<div class="tips">Vue3.0 后台管理系统</div>
</div>
</div>
<el-form label-position="top" :rules="rules" :model="ruleForm" ref="loginForm" class="login-form">
<el-form label-position="top" :rules="state.rules" :model="state.ruleForm" ref="loginForm" class="login-form">
<el-form-item label="账号" prop="username">
<el-input type="text" v-model.trim="ruleForm.username" autocomplete="off"></el-input>
<el-input type="text" v-model.trim="state.ruleForm.username" autocomplete="off"></el-input>
</el-form-item>
<el-form-item label="密码" prop="password">
<el-input type="password" v-model.trim="ruleForm.password" autocomplete="off"></el-input>
<el-input type="password" v-model.trim="state.ruleForm.password" autocomplete="off"></el-input>
</el-form-item>
<el-form-item>
<div style="color: #333">登录表示您已同意<a>服务条款</a></div>
<el-button style="width: 100%" type="primary" @click="submitForm">立即登录</el-button>
<el-checkbox v-model="checked" @change="!checked">下次自动登录</el-checkbox>
<el-checkbox v-model="state.checked" @change="!checked">下次自动登录</el-checkbox>
</el-form-item>
</el-form>
</div>
@ -30,51 +30,40 @@ import axios from '@/utils/axios'
import md5 from 'js-md5'
import { reactive, ref, toRefs } from 'vue'
import { localSet } from '@/utils'
export default {
name: 'Login',
setup() {
const loginForm = ref(null)
const state = reactive({
ruleForm: {
username: '',
password: ''
},
checked: true,
rules: {
username: [
{ required: 'true', message: '账户不能为空', trigger: 'blur' }
],
password: [
{ required: 'true', message: '密码不能为空', trigger: 'blur' }
]
}
})
const submitForm = async () => {
loginForm.value.validate((valid) => {
if (valid) {
axios.post('/adminUser/login', {
userName: state.ruleForm.username || '',
passwordMd5: md5(state.ruleForm.password)
}).then(res => {
localSet('token', res)
window.location.href = '/'
})
} else {
console.log('error submit!!')
return false;
}
const loginForm = ref(null)
const state = reactive({
ruleForm: {
username: '',
password: ''
},
checked: true,
rules: {
username: [
{ required: 'true', message: '账户不能为空', trigger: 'blur' }
],
password: [
{ required: 'true', message: '密码不能为空', trigger: 'blur' }
]
}
})
const submitForm = async () => {
loginForm.value.validate((valid) => {
if (valid) {
axios.post('/adminUser/login', {
userName: state.ruleForm.username || '',
passwordMd5: md5(state.ruleForm.password)
}).then(res => {
localSet('token', res)
window.location.href = '/'
})
} else {
console.log('error submit!!')
return false;
}
const resetForm = () => {
loginForm.value.resetFields();
}
return {
...toRefs(state),
loginForm,
submitForm,
resetForm
}
}
})
}
const resetForm = () => {
loginForm.value.resetFields();
}
</script>

280
src/views/Order.vue

@ -7,10 +7,9 @@
placeholder="请输入订单号"
v-model="orderNo"
@change="handleOption"
size="small"
clearable
/>
<el-select @change="handleOption" v-model="orderStatus" size="small" style="width: 200px; margin-right: 10px">
<el-select @change="handleOption" v-model="orderStatus" style="width: 200px; margin-right: 10px">
<el-option
v-for="item in options"
:key="item.value"
@ -19,14 +18,14 @@
/>
</el-select>
<!-- <el-button type="primary" size="small" icon="el-icon-edit">修改订单</el-button> -->
<el-button type="primary" size="small" icon="el-icon-s-home" @click="handleConfig()">配货完成</el-button>
<el-button type="primary" size="small" icon="el-icon-s-home" @click="handleSend()">出库</el-button>
<el-button type="danger" size="small" icon="el-icon-delete" @click="handleClose()">关闭订单</el-button>
<el-button type="primary" @click="handleConfig()"><i-document-checked width="16" />配货完成</el-button>
<el-button type="primary" @click="handleSend()"><i-van width="16" />出库</el-button>
<el-button type="danger" @click="handleClose()"><i-document-delete width="16" /> 关闭订单</el-button>
</div>
</template>
<el-table
v-loading="loading"
:data="tableData"
v-loading="state.loading"
:data="state.tableData"
tooltip-effect="dark"
style="width: 100%"
@selection-change="handleSelectionChange">
@ -75,6 +74,8 @@
v-if="scope.row.orderStatus == 1"
title="确定配货完成吗?"
@confirm="handleConfig(scope.row.orderId)"
confirm-button-text="确定"
cancel-button-text="取消"
>
<template #reference>
<a style="cursor: pointer; margin-right: 10px">配货完成</a>
@ -84,6 +85,8 @@
v-if="scope.row.orderStatus == 2"
title="确定出库吗?"
@confirm="handleSend(scope.row.orderId)"
confirm-button-text="确定"
cancel-button-text="取消"
>
<template #reference>
<a style="cursor: pointer; margin-right: 10px">出库</a>
@ -106,158 +109,143 @@
<el-pagination
background
layout="prev, pager, next"
:total="total"
:page-size="pageSize"
:current-page="currentPage"
:total="state.total"
:page-size="state.pageSize"
:current-page="state.currentPage"
@current-change="changePage"
/>
</el-card>
</template>
<script>
<script setup>
import { onMounted, reactive, ref, toRefs } from 'vue'
import { ElMessage } from 'element-plus'
import axios from '@/utils/axios'
export default {
name: 'Order',
setup() {
const state = reactive({
loading: false,
tableData: [], //
multipleSelection: [], //
total: 0, //
currentPage: 1, //
pageSize: 10, //
orderNo: '', //
orderStatus: '', //
options: [{
value: '',
label: '全部'
}, {
value: 0,
label: '待支付'
}, {
value: 1,
label: '已支付'
}, {
value: 2,
label: '配货完成'
}, {
value: 3,
label: '出库成功'
}, {
value: 4,
label: '交易成功'
}, {
value: -1,
label: '手动关闭'
}, {
value: -2,
label: '超时关闭'
}, {
value: -3,
label: '商家关闭'
}]
})
onMounted(() => {
getOrderList()
})
//
const getOrderList = () => {
state.loading = true
axios.get('/orders', {
params: {
pageNumber: state.currentPage,
pageSize: state.pageSize,
orderNo: state.orderNo,
orderStatus: state.orderStatus
}
}).then(res => {
state.tableData = res.list
state.total = res.totalCount
state.currentPage = res.currPage
state.loading = false
})
const state = reactive({
loading: false,
tableData: [], //
multipleSelection: [], //
total: 0, //
currentPage: 1, //
pageSize: 10, //
orderNo: '', //
orderStatus: '', //
options: [{
value: '',
label: '全部'
}, {
value: 0,
label: '待支付'
}, {
value: 1,
label: '已支付'
}, {
value: 2,
label: '配货完成'
}, {
value: 3,
label: '出库成功'
}, {
value: 4,
label: '交易成功'
}, {
value: -1,
label: '手动关闭'
}, {
value: -2,
label: '超时关闭'
}, {
value: -3,
label: '商家关闭'
}]
})
onMounted(() => {
getOrderList()
})
//
const getOrderList = () => {
state.loading = true
axios.get('/orders', {
params: {
pageNumber: state.currentPage,
pageSize: state.pageSize,
orderNo: state.orderNo,
orderStatus: state.orderStatus
}
const handleOption = () => {
state.currentPage = 1
getOrderList()
}
//
const handleSelectionChange = (val) => {
state.multipleSelection = val
}
const changePage = (val) => {
state.currentPage = val
getOrderList()
}
const handleConfig = (id) => {
console.log('id', id)
let params
if (id) {
params = [id]
} else {
if (!state.multipleSelection.length) {
console.log('state.multipleSelection', state.multipleSelection.length)
ElMessage.error('请选择项')
return
}
params = state.multipleSelection.map(i => i.orderId)
}
axios.put('/orders/checkDone', {
ids: params
}).then(() => {
ElMessage.success('配货成功')
getOrderList()
})
}
const handleSend = (id) => {
let params
if (id) {
params = [id]
} else {
if (!state.multipleSelection.length) {
ElMessage.error('请选择项')
return
}
params = state.multipleSelection.map(i => i.orderId)
}
axios.put('/orders/checkOut', {
ids: params
}).then(() => {
ElMessage.success('出库成功')
getOrderList()
})
}).then(res => {
state.tableData = res.list
state.total = res.totalCount
state.currentPage = res.currPage
state.loading = false
})
}
const handleOption = () => {
state.currentPage = 1
getOrderList()
}
//
const handleSelectionChange = (val) => {
state.multipleSelection = val
}
const changePage = (val) => {
state.currentPage = val
getOrderList()
}
const handleConfig = (id) => {
console.log('id', id)
let params
if (id) {
params = [id]
} else {
if (!state.multipleSelection.length) {
console.log('state.multipleSelection', state.multipleSelection.length)
ElMessage.error('请选择项')
return
}
const handleClose = (id) => {
let params
if (id) {
params = [id]
} else {
if (!state.multipleSelection.length) {
ElMessage.error('请选择项')
return
}
params = state.multipleSelection.map(i => i.orderId)
}
axios.put('/orders/close', {
ids: params
}).then(() => {
ElMessage.success('关闭成功')
getOrderList()
})
params = state.multipleSelection.map(i => i.orderId)
}
axios.put('/orders/checkDone', {
ids: params
}).then(() => {
ElMessage.success('配货成功')
getOrderList()
})
}
const handleSend = (id) => {
let params
if (id) {
params = [id]
} else {
if (!state.multipleSelection.length) {
ElMessage.error('请选择项')
return
}
return {
...toRefs(state),
handleSelectionChange,
getOrderList,
changePage,
handleOption,
handleConfig,
handleSend,
handleClose
params = state.multipleSelection.map(i => i.orderId)
}
axios.put('/orders/checkOut', {
ids: params
}).then(() => {
ElMessage.success('出库成功')
getOrderList()
})
}
const handleClose = (id) => {
let params
if (id) {
params = [id]
} else {
if (!state.multipleSelection.length) {
ElMessage.error('请选择项')
return
}
params = state.multipleSelection.map(i => i.orderId)
}
axios.put('/orders/close', {
ids: params
}).then(() => {
ElMessage.success('关闭成功')
getOrderList()
})
}
</script>

8
src/views/Swiper.vue

@ -2,13 +2,15 @@
<el-card class="swiper-container">
<template #header>
<div class="header">
<el-button type="primary" size="small" icon="el-icon-plus" @click="handleAdd">增加</el-button>
<el-button type="primary" @click="handleAdd"><i-plus width='14' /> 增加</el-button>
<el-popconfirm
title="确定删除吗?"
@confirm="handleDelete"
confirm-button-text="确定"
cancel-button-text="取消"
>
<template #reference>
<el-button type="danger" size="small" icon="el-icon-delete">批量删除</el-button>
<el-button type="danger"><i-delete width='14' /> 批量删除</el-button>
</template>
</el-popconfirm>
</div>
@ -59,6 +61,8 @@
<el-popconfirm
title="确定删除吗?"
@confirm="handleDeleteOne(scope.row.carouselId)"
confirm-button-text="确定"
cancel-button-text="取消"
>
<template #reference>
<a style="cursor: pointer">删除</a>

2
vite.config.js

@ -3,6 +3,7 @@ import vue from '@vitejs/plugin-vue'
import AutoImport from 'unplugin-auto-import/vite'
import Components from 'unplugin-vue-components/vite'
import { ElementPlusResolver } from 'unplugin-vue-components/resolvers'
import ElementPlus from 'unplugin-element-plus/vite' // 不加这个配置,ElMessage出不来
import path from 'path'
const baseUrl = {
@ -25,6 +26,7 @@ export default ({ mode }) => defineConfig({
importStyle: 'sass'
})],
}),
ElementPlus()
],
base: baseUrl[mode],
resolve: {

7967
yarn.lock
File diff suppressed because it is too large
View File

Loading…
Cancel
Save