Compare commits

..

14 Commits
5.9 ... master

Author SHA1 Message Date
HuskyOo c38bdc3ffe 文件上传修改 2023-03-09 16:22:07 +08:00
HuskyOo 828dcd0510 办事指南添加部门查询 2022-06-10 09:03:51 +08:00
HuskyOo a8eb29a2d7 修改 2022-05-24 14:51:07 +08:00
HuskyOo a0b3d62482 导出和条件搜索 2022-05-23 17:10:08 +08:00
HuskyOo 36fc52b119 结算添加积分清单 特约商户添加字段 2022-05-19 16:06:13 +08:00
HuskyOo 8a20a9e026 图标添加 2022-05-19 09:34:27 +08:00
HuskyOo 4fe93e1f77 积分结算添加条件搜索和导出 2022-05-13 16:24:04 +08:00
HuskyOo 6e8c0cd37e 工单管理添加扣分操作 一些页面添加字段 2022-05-13 15:05:58 +08:00
HuskyOo 30b0d587af 积分活动管理 2022-05-13 15:04:18 +08:00
HuskyOo 79bd7a92e7 结算积分 2022-05-12 11:41:01 +08:00
HuskyOo 09c4fb088d 积分流水 积分结算 2022-05-12 10:23:02 +08:00
HuskyOo c6e8e6f2e3 特约商户添加筛选 2022-05-12 10:22:10 +08:00
HuskyOo 046bf46262 右边菜单修改 2022-05-12 10:20:11 +08:00
HuskyOo 688a2d9ab1 积分规则管理 特约商户管理 左边菜单栏修改 2022-05-10 10:10:23 +08:00
24 changed files with 2733 additions and 418 deletions

View File

@ -4,8 +4,8 @@ ENV = 'development'
# base api # base api
#VUE_APP_BASE_API = '/dev-api' #VUE_APP_BASE_API = '/dev-api'
#VUE_APP_BASE_API = 'http://app.rt.xianci.info/' #VUE_APP_BASE_API = 'http://app.rt.xianci.info/'
VUE_APP_BASE_API = 'http://office.xianci.info:18904/' # VUE_APP_BASE_API = 'http://office.xianci.info:18904/'
#VUE_APP_BASE_API = 'http://api.rt.myntv.cn/' VUE_APP_BASE_API = 'https://api.rt.rtrmt.cn/'
# base url # base url
VUE_APP_BASE_URL = 'http://admin.rt.xianci.info' VUE_APP_BASE_URL = 'http://admin.rt.xianci.info'

BIN
convenience-prod.zip Normal file

Binary file not shown.

View File

@ -114,3 +114,16 @@ export function leaderTVData(data) {
data data
}) })
} }
/**
* LeaderTv
* @param {*} data
* @returns
*/
export function leaderDeal(data) {
return request({
url: '/api/convenience/v2/services/leaderDeal',
method: 'post',
data
})
}

View File

@ -0,0 +1,89 @@
import request from '@/utils/request'
export function list(params) {
return request({
url: '/api/convenience/fingertipIntegral/list',
method: 'get',
params
})
}
export function add(data) {
return request({
url: '/api/convenience/fingertipIntegral',
method: 'post',
data
})
}
export function del(params) {
return request({
url: '/api/convenience/fingertipIntegral',
method: 'DELETE',
params
})
}
export function recordList(data) {
return request({
url: '/api/convenience/fingertipIntegral/recordList',
method: 'post',
data
})
}
export function settlementList(data) {
return request({
url: '/api/convenience/fingertipIntegral/settlementList',
method: 'post',
data
})
}
export function settlementDeal(data) {
return request({
url: '/api/convenience/fingertipIntegral/settlementDeal',
method: 'post',
data
})
}
export function activityList(data) {
return request({
url: '/api/convenience/fingertipIntegralActivity/list',
method: 'post',
data
})
}
export function activityUpdate(data) {
return request({
url: '/api/convenience/fingertipIntegralActivity',
method: 'post',
data
})
}
export function activityInfo(params) {
return request({
url: '/api/convenience/fingertipIntegralActivity/info',
method: 'get',
params
})
}
export function activityDel(params) {
return request({
url: '/api/convenience/fingertipIntegralActivity',
method: 'DELETE',
params
})
}
export function settlementRecordList(params) {
return request({
url: '/api/convenience/fingertipIntegral/settlementRecordList',
method: 'get',
params
})
}

View File

@ -0,0 +1,25 @@
import request from '@/utils/request'
export function speciallyBusinessList(data) {
return request({
url: '/api/convenience/speciallyBusiness/fixServ/speciallyBusinessList',
method: 'post',
data
})
}
export function list(data) {
return request({
url: '/api/convenience/speciallyBusiness/fixServ/list',
method: 'post',
data
})
}
export function speciallyBusinessSet(data) {
return request({
url: '/api/convenience/speciallyBusiness/fixServ/speciallyBusinessSet',
method: 'post',
data
})
}

View File

@ -1,4 +1,4 @@
import request from "@/utils/request"; import request from '@/utils/request'
/** /**
* 通讯录 * 通讯录
@ -26,8 +26,21 @@ export function staffList(data) {
*/ */
export function info(data) { export function info(data) {
return request({ return request({
url: "/api/convenience/v2/staff/info", url: '/api/convenience/v2/staff/info',
method: "get", method: 'get',
params: data params: data
}); })
}
/**
* 文件上传
* @param data
*/
export function upload(data) {
return request({
url: '/api/common/upload/upload',
method: 'post',
headers: { 'Content-Type': 'multipart/form-data' },
data
})
} }

View File

@ -20,6 +20,8 @@
import OSS from '@/utils/aliOSS' import OSS from '@/utils/aliOSS'
import UUID from 'uuidjs' import UUID from 'uuidjs'
import { upload } from '@/api/staff'
export default { export default {
props: { props: {
value: { value: {
@ -58,10 +60,18 @@ export default {
const suffix = item.name.substr(item.name.lastIndexOf('.')+1) const suffix = item.name.substr(item.name.lastIndexOf('.')+1)
const fileName = UUID.generate() + '.' + suffix const fileName = UUID.generate() + '.' + suffix
item.name = fileName item.name = fileName
OSS(item.raw, fileName).then(res => {
this.$emit('input', 'http://storage.myntv.cn/'+res.name) const formData = new FormData()
item.url = 'http://storage.myntv.cn/'+res.name formData.append('file', item.raw, fileName)
upload(formData).then(res => {
console.log(res)
// OSS(item.raw, fileName).then(res => {
// this.$emit('input', 'http://storage.myntv.cn/'+res.name)
// item.url = 'http://storage.myntv.cn/'+res.name
this.$emit('input', res.d)
item.url = res.d
item.status = 'success' item.status = 'success'
const list = fileList.filter(item => item.status === 'success').map(item => item.url) const list = fileList.filter(item => item.status === 'success').map(item => item.url)
console.log(list); console.log(list);
@ -70,13 +80,17 @@ export default {
} }
}) })
} else { } else {
// const suffix = file.name.split('.')[0] const suffix = file.name.split('.')[0]
const suffix = item.name.substr(item.name.lastIndexOf('.')+1)
const fileName = UUID.generate() + '.' + suffix const fileName = UUID.generate() + '.' + suffix
file.name = fileName file.name = fileName
this.fileList = [file] this.fileList = [file]
OSS(file.raw, fileName).then(res => {
this.$emit('input', 'http://storage.myntv.cn/'+res.name) const formData = new FormData()
formData.append('file', file.raw, fileName)
upload(formData).then(res => {
// OSS(file.raw, fileName).then(res => {
// this.$emit('input', 'http://storage.myntv.cn/'+res.name)
this.$emit('input', res.d)
}) })
} }
}, },

View File

@ -41,6 +41,8 @@ import { Loading } from 'element-ui'
import OSS from '@/utils/aliOSS' import OSS from '@/utils/aliOSS'
import UUID from 'uuidjs' import UUID from 'uuidjs'
import { upload } from '@/api/staff'
export default { export default {
components: { Preview }, components: { Preview },
props: { props: {
@ -178,8 +180,13 @@ export default {
file = item file = item
}) })
const suffix = file.name.split('.')[1] const suffix = file.name.split('.')[1]
OSS(file, UUID.generate() + '.' + suffix).then(res => {
resolve(res.url) const form = new FormData()
form.append('file', file)
upload(form).then(res => {
// OSS(file, UUID.generate() + '.' + suffix).then(res => {
// resolve(res.url)
resolve(res.d)
loadingInstance.close() loadingInstance.close()
}).catch(() => { }).catch(() => {
console.log('文件上传失败!') console.log('文件上传失败!')

View File

@ -32,7 +32,7 @@
:style="{ width: width + 'px', height: height + 'px' }" :style="{ width: width + 'px', height: height + 'px' }"
@mouseenter="mouseEnter" @mouseenter="mouseEnter"
@mouseleave="mouseLeave" @mouseleave="mouseLeave"
/> >
<i <i
v-else v-else
class="el-icon-plus avatar-uploader-icon" class="el-icon-plus avatar-uploader-icon"
@ -101,7 +101,7 @@
</el-upload> </el-upload>
<!-- 多图片预览弹窗 --> <!-- 多图片预览弹窗 -->
<el-dialog :visible.sync="dialogVisible" append-to-body> <el-dialog :visible.sync="dialogVisible" append-to-body>
<img width="100%" :src="dialogImageUrl" alt="" /> <img width="100%" :src="dialogImageUrl" alt="">
</el-dialog> </el-dialog>
<!-- 剪裁组件弹窗 --> <!-- 剪裁组件弹窗 -->
<el-dialog <el-dialog
@ -121,13 +121,15 @@
</div> </div>
</template> </template>
<script> <script>
import Cropper from "@/components/uploader/cropper"; import Cropper from '@/components/uploader/cropper'
// import axios from 'axios' // import axios from 'axios'
import OSS from "@/utils/aliOSS"; import OSS from '@/utils/aliOSS'
import UUID from "uuidjs"; import UUID from 'uuidjs'
import { upload } from '@/api/staff'
export default { export default {
name: "Uploader", name: 'Uploader',
components: { components: {
Cropper Cropper
}, },
@ -135,7 +137,7 @@ export default {
targetUrl: { targetUrl: {
// //
type: String, type: String,
default: "http://120.77.82.246:6789/api/postUpLoadFiles" default: 'http://120.77.82.246:6789/api/postUpLoadFiles'
}, },
multiple: { multiple: {
// //
@ -144,12 +146,12 @@ export default {
}, },
initUrl: { initUrl: {
// //
default: "" default: ''
}, },
fixedNumber: { fixedNumber: {
// //
default: function() { default: function() {
return [3, 1]; return [3, 1]
} }
}, },
news: { news: {
@ -169,66 +171,66 @@ export default {
}, },
data() { data() {
return { return {
file: "", // file: '', //
imageUrl: "", // imageUrl: '', //
dialogImageUrl: "", // dialogImageUrl: '', //
uploadList: [], // uploadList: [], //
reupload: true, // "" reupload: true, // ""
dialogVisible: false, // dialogVisible: false, //
cropperModel: false, // cropperModel: false, //
reuploadWidth: this.height * 0.7 // reuploadWidth: this.height * 0.7 //
}; }
}, },
watch: { watch: {
initUrl: function(val) { initUrl: function(val) {
// //
console.info("watch"); console.info('watch')
console.info(val); console.info(val)
if (val) { if (val) {
if (typeof this.initUrl === "string") { if (typeof this.initUrl === 'string') {
this.imageUrl = val; this.imageUrl = val
} else { } else {
this.uploadList = this.formatImgArr(val); this.uploadList = this.formatImgArr(val)
} }
} else { } else {
this.imageUrl = ""; this.imageUrl = ''
this.uploadList = []; this.uploadList = []
} }
} }
}, },
updated() { updated() {
if (this.$refs.vueCropper) { if (this.$refs.vueCropper) {
this.$refs.vueCropper.Update(); this.$refs.vueCropper.Update()
} }
}, },
mounted() { mounted() {
if (typeof this.initUrl === "string") { if (typeof this.initUrl === 'string') {
this.imageUrl = this.initUrl; this.imageUrl = this.initUrl
} else { } else {
this.uploadList = this.formatImgArr(this.initUrl); this.uploadList = this.formatImgArr(this.initUrl)
} }
}, },
methods: { methods: {
/** **************************** multiple多图情况 **************************************/ /** **************************** multiple多图情况 **************************************/
handlePreview(file) { handlePreview(file) {
// //
this.dialogImageUrl = file.url; this.dialogImageUrl = file.url
this.dialogVisible = true; this.dialogVisible = true
}, },
handleRemove(file, fileList) { handleRemove(file, fileList) {
// //
this.uploadList = fileList; this.uploadList = fileList
this.$emit("imgupload", this.formatImgArr(this.uploadList)); this.$emit('imgupload', this.formatImgArr(this.uploadList))
}, },
handlePicRemove(file) { handlePicRemove(file) {
this.imageUrl = ""; this.imageUrl = ''
this.$emit("imgupload", this.imageUrl); this.$emit('imgupload', this.imageUrl)
}, },
consoleFL(file, fileList) { consoleFL(file, fileList) {
// //
this.cropperModel = true; this.cropperModel = true
this.file = file; this.file = file
this.uploadList = fileList; this.uploadList = fileList
}, },
/** **********************************************************************************/ /** **********************************************************************************/
@ -236,28 +238,28 @@ export default {
handlePreviewSingle(file) { handlePreviewSingle(file) {
// //
// this.dialogImageUrl = this.file.url // this.dialogImageUrl = this.file.url
this.dialogImageUrl = this.imageUrl; this.dialogImageUrl = this.imageUrl
this.dialogVisible = true; this.dialogVisible = true
}, },
mouseEnter() { mouseEnter() {
// //
this.$refs.reupload.style.display = "block"; this.$refs.reupload.style.display = 'block'
if (this.$refs.failUpload.style.display === "block") { if (this.$refs.failUpload.style.display === 'block') {
this.$refs.failUpload.style.display = "none"; this.$refs.failUpload.style.display = 'none'
} }
this.$refs.singleImg.style.opacity = "0.6"; this.$refs.singleImg.style.opacity = '0.6'
}, },
mouseLeave() { mouseLeave() {
// //
this.$refs.reupload.style.display = "none"; this.$refs.reupload.style.display = 'none'
this.$refs.singleImg.style.opacity = "1"; this.$refs.singleImg.style.opacity = '1'
}, },
handleCrop(file, files) { handleCrop(file, files) {
file.url = URL.createObjectURL(file.raw); file.url = URL.createObjectURL(file.raw)
// console.log(file) // console.log(file)
// //
this.cropperModel = true; this.cropperModel = true
this.file = file; this.file = file
// this.imageUrl = file.url // this.imageUrl = file.url
}, },
/** **********************************************************************************/ /** **********************************************************************************/
@ -266,70 +268,85 @@ export default {
// upload // upload
if (!this.multiple) { if (!this.multiple) {
// //
this.$refs.uploading.style.display = "block"; this.$refs.uploading.style.display = 'block'
} }
// const formData = new FormData() // const formData = new FormData()
// formData.append('file', data, '123.png') // formData.append('file', data, '123.png')
// axios.defaults.withCredentials = false // axios.defaults.withCredentials = false
// axios.post(this.targetUrl, formData, { headers: { 'Content-Type': 'multipart/form-data' }}).then(res => { // axios.post(this.targetUrl, formData, { headers: { 'Content-Type': 'multipart/form-data' }}).then(res => {
const name = UUID.generate() + ".png"; const name = UUID.generate() + '.png'
OSS(data, name).then(res => {
const formData = new FormData()
formData.append('file', data, name)
upload(formData).then(res => {
// OSS(data, name).then(res => {
if (!this.multiple) { if (!this.multiple) {
// //
this.$refs.uploading.style.display = "none"; this.$refs.uploading.style.display = 'none'
} }
// console.log(res) // console.log(res)
if (res.res.status === 200) { // if (res.res.status === 200) {
// //
const currentPic = res.url; const currentPic = res.d
if (this.multiple) { if (this.multiple) {
this.uploadList.pop(); this.uploadList.pop()
this.uploadList.push({ this.uploadList.push({
url: currentPic, url: currentPic,
uid: "111" uid: '111'
}); })
// console.log(this.formatImgArr(this.uploadList)) // console.log(this.formatImgArr(this.uploadList))
this.$emit("imgupload", this.formatImgArr(this.uploadList)); this.$emit('imgupload', this.formatImgArr(this.uploadList))
} else {
this.$emit("imgupload", currentPic);
}
} else { } else {
this.$message({ this.$emit('imgupload', currentPic)
type: "warning",
message: "上传失败!"
});
//
if (!this.multiple) {
this.$refs.failUpload.style.display = "block";
} else {
this.uploadList.pop();
}
} }
}); // } else {
this.cropperModel = false; // this.$message({
// type: "warning",
// message: "!"
// });
// //
// if (!this.multiple) {
// this.$refs.failUpload.style.display = "block";
// } else {
// this.uploadList.pop();
// }
// }
}).catch(() => {
this.$message({
type: 'warning',
message: '上传失败!'
})
//
if (!this.multiple) {
this.$refs.failUpload.style.display = 'block'
} else {
this.uploadList.pop()
}
})
this.cropperModel = false
}, },
formatImgArr(arr) { formatImgArr(arr) {
// console.log(arr); // console.log(arr);
if (arr) { if (arr) {
const result = arr.map((item, index) => { const result = arr.map((item, index) => {
if (typeof item === "string") { if (typeof item === 'string') {
return { return {
url: item, url: item,
uid: `index${index}` uid: `index${index}`
}; }
} else { } else {
return item.url; return item.url
} }
}); })
return result; return result
} }
}, },
beforeClose(done) { beforeClose(done) {
this.uploadList.pop(); this.uploadList.pop()
this.cropperModel = false; this.cropperModel = false
} }
} }
}; }
</script> </script>
<style> <style>
.avatar-uploader .el-upload { .avatar-uploader .el-upload {

View File

@ -1,24 +1,24 @@
<script> <script>
export default { export default {
name: "MenuItem", name: 'MenuItem',
functional: true, functional: true,
props: { props: {
icon: { icon: {
type: String, type: String,
default: "" default: ''
}, },
title: { title: {
type: String, type: String,
default: "" default: ''
} }
}, },
render(h, context) { render(h, context) {
const { icon, title } = context.props; const { icon, title } = context.props
const vnodes = []; const vnodes = []
if (icon) { if (icon) {
if (icon.includes("el-icon")) { if (icon.includes('el-icon')) {
vnodes.push(<i class={[icon, "sub-el-icon"]} />); vnodes.push(<i class={[icon, 'sub-el-icon']} />)
// icon_menu_statistical // icon_menu_statistical
} else { } else {
vnodes.push( vnodes.push(
@ -28,25 +28,26 @@ export default {
// > // >
// <svg-icon icon-class={icon} /> // <svg-icon icon-class={icon} />
// </div> // </div>
<i class={["icon_menu_" + icon, "icon_menu"]}></i> <i class={['icon_menu_' + icon, 'icon_menu']}></i>
); )
// vnodes.push(<svg-icon icon-class={icon}/>) // vnodes.push(<svg-icon icon-class={icon}/>)
} }
} }
if (title) { if (title) {
vnodes.push(<span slot="title">{title}</span>); vnodes.push(<span slot='title'>{title}</span>)
} }
return vnodes; return vnodes
} }
}; }
</script> </script>
<style scoped> <style scoped>
.icon_menu { .icon_menu {
display: inline-block; display: inline-block;
width: 53px; width: 30px;
height: 53px; height: 30px;
margin-right: 17px;
/* background: url('./img/icon_home.png')no-repeat; */ /* background: url('./img/icon_home.png')no-repeat; */
background-size: cover !important; background-size: cover !important;
} }
@ -68,6 +69,15 @@ export default {
.icon_menu_townRanking { .icon_menu_townRanking {
background: url("./img/icon_twonRanking.png") no-repeat; background: url("./img/icon_twonRanking.png") no-repeat;
} }
.icon_menu_dept {
background: url("./img/icon_dept.png") no-repeat;
}
.icon_menu_speciallyBusiness {
background: url("./img/icon_speciallyBusiness.png") no-repeat;
}
.icon_menu_fingertipIntegral {
background: url("./img/icon_fingertipIntegral.png") no-repeat;
}
.sub-el-icon { .sub-el-icon {
color: currentColor; color: currentColor;
width: 1em; width: 1em;

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.8 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.8 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.6 KiB

View File

@ -58,10 +58,22 @@ export default {
</script> </script>
<style> <style>
.el-menu-item { .el-menu-item {
height: 153px; height: 80px;
justify-content: center;
display: flex; display: flex;
flex-direction: column;
align-items: center; align-items: center;
font-size: 16px;
}
.el-submenu__title{
height: 80px;
display: flex;
align-items: center;
font-size: 16px;
}
.el-submenu .el-menu-item {
height: 40px;
padding-left: 65px !important;
}
.el-submenu__title i {
color: #fff;
} }
</style> </style>

View File

@ -7,10 +7,10 @@ Vue.use(Router)
import Layout from '@/layout' import Layout from '@/layout'
/* Router Modules */ /* Router Modules */
import componentsRouter from './modules/components' // import componentsRouter from './modules/components'
import chartsRouter from './modules/charts' // import chartsRouter from './modules/charts'
import tableRouter from './modules/table' // import tableRouter from './modules/table'
import nestedRouter from './modules/nested' // import nestedRouter from './modules/nested'
/** /**
* Note: sub-menu only appear when route children.length >= 1 * Note: sub-menu only appear when route children.length >= 1
@ -373,7 +373,7 @@ export const asyncRoutes = [
redirect: '/dept/list', redirect: '/dept/list',
meta: { meta: {
title: '县级部门管理', title: '县级部门管理',
icon: 'townRanking', icon: 'dept',
roles: ['SSS'] roles: ['SSS']
}, },
hidden: false, hidden: false,
@ -384,7 +384,7 @@ export const asyncRoutes = [
name: 'DeptList', name: 'DeptList',
meta: { meta: {
title: '部门列表', title: '部门列表',
icon: 'townRanking', icon: 'dept',
affix: true, affix: true,
parentTitle: '县级部门管理' parentTitle: '县级部门管理'
} }
@ -395,7 +395,7 @@ export const asyncRoutes = [
name: 'DeptStaff', name: 'DeptStaff',
meta: { meta: {
title: '人员列表', title: '人员列表',
icon: 'townRanking', icon: 'dept',
affix: true, affix: true,
parentTitle: '县级部门管理' parentTitle: '县级部门管理'
}, },
@ -403,6 +403,118 @@ export const asyncRoutes = [
} }
] ]
}, },
{
path: '/fingertipIntegral',
component: Layout,
name: 'FingertipIntegral',
redirect: '/fingertipIntegral/list',
meta: {
title: '积分管理',
icon: 'fingertipIntegral',
roles: ['SSS']
},
hidden: false,
children: [
{
path: 'list',
component: () => import('@/views/fingertipIntegral/list'),
name: 'FingertipIntegralList',
meta: {
title: '规则列表',
affix: true,
parentTitle: '规则列表'
}
},
{
path: 'recordList',
component: () => import('@/views/fingertipIntegral/recordList'),
name: 'FingertipIntegralRecordList',
meta: {
title: '积分流水',
affix: true,
parentTitle: '积分流水'
}
},
{
path: 'settlementList',
component: () => import('@/views/fingertipIntegral/settlementList'),
name: 'FingertipIntegralSettlementList',
meta: {
title: '积分结算',
affix: true,
parentTitle: '积分结算'
}
},
{
path: 'activityList',
component: () => import('@/views/fingertipIntegral/activity/list'),
name: 'FingertipIntegralActivityList',
meta: {
title: '活动列表',
affix: true,
parentTitle: '活动列表'
}
},
{
path: 'activityCreate',
component: () => import('@/views/fingertipIntegral/activity/detail'),
name: 'FingertipIntegralActivityCreate',
meta: {
title: '创建活动',
affix: true,
parentTitle: '创建活动'
},
hidden: true
},
{
path: 'activityDetail',
component: () => import('@/views/fingertipIntegral/activity/detail'),
name: 'FingertipIntegralActivityDetail',
meta: {
title: '活动详情',
affix: true,
parentTitle: '活动详情'
},
hidden: true
},
{
path: 'activityChange',
component: () => import('@/views/fingertipIntegral/activity/detail'),
name: 'FingertipIntegralActivityChange',
meta: {
title: '活动修改',
affix: true,
parentTitle: '活动修改'
},
hidden: true
}
]
},
{
path: '/speciallyBusiness',
component: Layout,
name: 'SpeciallyBusiness',
redirect: '/speciallyBusiness/list',
meta: {
title: '特约商户管理',
icon: 'speciallyBusiness',
roles: ['SSS']
},
hidden: false,
children: [
{
path: 'list',
component: () => import('@/views/speciallyBusiness/list'),
name: 'speciallyBusinessList',
meta: {
title: '商户列表',
icon: 'speciallyBusiness',
affix: true,
parentTitle: '特约商户管理'
}
}
]
},
// { // {
// path: '/permission', // path: '/permission',
// component: Layout, // component: Layout,

View File

@ -14,18 +14,18 @@ $menuText:#ffffff;
// $menuActiveText:#409EFF; // $menuActiveText:#409EFF;
$menuActiveText:#ffffff; $menuActiveText:#ffffff;
// $subMenuActiveText:#f4f4f5; // https://github.com/ElemeFE/element/issues/12951 // $subMenuActiveText:#f4f4f5; // https://github.com/ElemeFE/element/issues/12951
$subMenuActiveText:#5d94ff; $subMenuActiveText:#ffffff;
// $menuBg:#304156; // $menuBg:#304156;
$menuBg:#4081ff; $menuBg:#4081ff;
// $menuHover:#263445; // $menuHover:#263445;
$menuHover:#5d94ff; $menuHover:#5d94ff;
$subMenuBg:#1f2d3d; $subMenuBg:#4081ff;
$subMenuHover:#001528; $subMenuHover:#5d94ff;
// $sideBarWidth: 210px; $sideBarWidth: 230px;
$sideBarWidth: 150px; // $sideBarWidth: 150px;
// the :export directive is the magic sauce for webpack // the :export directive is the magic sauce for webpack
// https://www.bluematador.com/blog/how-to-share-variables-between-js-and-sass // https://www.bluematador.com/blog/how-to-share-variables-between-js-and-sass

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,103 @@
<template>
<div class="app-container">
<el-form
ref="convenienceForm"
style="width:680px"
:model="form"
:rules="rules"
:disabled="pageQuery.type === 'detail'"
label-width="80px"
class="el-form"
>
<el-form-item label="标题" prop="title">
<el-input
v-model="form.title"
placeholder="请输入"
/>
</el-form-item>
<el-form-item label="简介" prop="introduction">
<el-input
v-model="form.introduction"
type="textarea"
placeholder="请输入"
/>
</el-form-item>
<el-form-item label="图片" prop="images">
<template v-if="pageQuery.type === 'detail'">
<el-image v-for="item of form.images" :key="item" :src="item" />
</template>
<CutUploadImage v-else :disabled="pageQuery.type === 'detail'" :init-url="form.images" multiple @imgupload="imgUpload" />
</el-form-item>
<el-form-item label="内容" prop="content">
<UEditor v-model="form.content" :disabled="pageQuery.type === 'detail'" />
</el-form-item>
<el-form-item v-if="pageQuery.type !== 'detail'">
<el-button type="primary" @click="handleAdd">提交</el-button>
</el-form-item>
</el-form>
</div>
</template>
<script>
import { activityUpdate, activityInfo } from '@/api/fingertipIntegral'
import UEditor from '@/components/UEditor'
import CutUploadImage from '@/components/cutUploadImage'
export default {
components: { UEditor, CutUploadImage },
data() {
return {
pageQuery: {
type: undefined,
id: undefined
},
form: {
active: true,
audioImage: undefined,
audioUrl: undefined,
content: undefined,
images: [],
introduction: undefined,
show: true,
subtitle: undefined,
title: undefined,
videoUrl: undefined
},
rules: {
title: [{ required: true, message: '请输入', trigger: 'change' }]
}
}
},
created() {
this.pageQuery = this.$route.query
if (this.pageQuery.id) this.getInfo()
},
methods: {
getInfo() {
activityInfo({ id: this.pageQuery.id }).then(res => {
console.log(res)
this.form = res.d
})
},
imgUpload(e) {
this.form.images = e
},
handleAdd() {
this.$refs.convenienceForm.validate(valid => {
if (valid) {
const form = this.form
activityUpdate(form).then(res => {
this.$message({
type: 'success',
message: '操作成功!'
})
this.$router.back()
})
}
})
}
}
}
</script>
<style scope></style>

View File

@ -0,0 +1,235 @@
<template>
<div class="app-container">
<div class="filter-container">
<el-input
v-model="listQuery.title"
style="width:200px;margin-right:10px"
class="filter-item"
placeholder="请输入标题"
clearable
/>
<!-- <el-select v-model="listQuery.source" clearable class="filter-item" placeholder="请选择积分来源">
<el-option v-for="item of sourceOptions" :key="item.value" v-bind="item" />
</el-select> -->
<el-button
type="primary"
style="margin-left:10px"
@click="handleSearch"
>搜索</el-button>
</div>
<el-button
type="primary"
size="mini"
style="margin-bottom:20px"
@click="handleAdd"
>新增活动</el-button>
<el-table v-loading="loading" :data="list" border style="width: 100%">
<el-table-column label="标题" prop="title" />
<el-table-column label="简介" prop="introduction" />
<el-table-column label="图片" prop="images">
<template v-if="scope.row.images && scope.row.images.length" slot-scope="scope">
<el-image
style="width: 100px; height: 100px"
:src="scope.row.images[0]"
:preview-src-list="scope.row.images"
/>
</template>
</el-table-column>
<el-table-column label="创建时间">
<template slot-scope="scope">
<span>{{
scope.row.createDate | parseTime("{y}-{m}-{d} {h}:{i}:{s}")
}}</span>
</template>
</el-table-column>
<el-table-column label="操作" fixed="right" align="center" width="280px">
<template slot-scope="scope">
<el-button
size="mini"
type="primary"
round
style="font-size:14px;padding:10px 20px"
@click="handleDetail(scope.row)"
>查看详情</el-button>
<el-button
size="mini"
type="primary"
round
style="font-size:14px;padding:10px 20px"
@click="handleUpdate(scope.row)"
>编辑</el-button>
<el-button
size="mini"
type="danger"
round
style="font-size:14px;padding:10px 20px"
@click="handleDel(scope.row)"
>删除</el-button>
</template>
</el-table-column>
</el-table>
<pagination
v-if="total > 0"
:total="total"
:page.sync="listQuery.lastPageIndex"
:limit.sync="listQuery.size"
@pagination="getList"
/>
</div>
</template>
<script>
import Pagination from '@/components/Pagination'
import { activityList, activityDel } from '@/api/fingertipIntegral'
export default {
components: { Pagination },
filters: {
optionsFilter(value, options = []) {
const findItem = options.find((option) => option.value === value)
if (findItem) {
return findItem.label
}
return ''
}
},
data() {
return {
loading: false,
total: 0,
listQuery: {
lastPageIndex: 1,
size: 10,
title: undefined
},
list: undefined,
sourceOptions: [
{
value: 'REAL_NAME_AUTHENTICATION',
label: '实名认证'
},
{
value: 'HANDLING',
label: '处理办件'
},
{
value: 'APPLY',
label: '申请办件'
},
{
value: 'TIMEOUT',
label: '超期办件扣分'
},
{
value: 'VERY_SATISFIED',
label: '非常满意得分'
},
{
value: 'NEGATIVE_COMMENT',
label: '差评扣分'
},
{
value: 'READ',
label: '阅读'
},
{
value: 'SEND_A_CIRCLE_OF_FRIENDS',
label: '发朋友圈'
},
{
value: 'CONSUMPTION',
label: '消费'
},
{
value: 'MERCHANT_SETTLEMENT',
label: '商户结算'
},
{
value: 'POINT_REFUND',
label: '积分回退'
},
{
value: 'REGULATORY_PUNISHMENT_AND_REWARD',
label: '监管惩罚'
},
{
value: 'SPECIAL_WORK_TYPE',
label: '特殊工单类型奖励积分(医保卫生)'
}
]
}
},
watch: {
'listQuery.lastPageIndex': {
handler(val) {
this.getList()
},
deep: true // true
}
},
created() {
this.getList()
},
methods: {
getList() {
this.loading = true
activityList(this.listQuery).then(res => {
this.list = res.d.records
this.total = res.d.total
// this.pageSize = res.d.pageSize
this.loading = false
}).catch(() => {
this.loading = false
})
},
handleDel(item) {
this.$confirm('此操作将永久删除, 是否继续?', '提示', {
confirmButtonText: '确定',
cancelButtonText: '取消',
type: 'warning'
}).then(() => {
activityDel({ id: item.id }).then(() => {
this.$message({
type: 'success',
message: '删除成功!'
})
this.getList()
})
})
},
handleAdd() {
this.$router.push({
path: '/fingertipIntegral/activityCreate'
})
},
handleUpdate(item) {
this.$router.push({
path: '/fingertipIntegral/activityChange',
query: {
id: item.id
}
})
},
handleDetail(item) {
this.$router.push({
path: '/fingertipIntegral/activityDetail',
query: {
type: 'detail',
id: item.id
}
})
},
handleSearch() {
const { listQuery } = this
this.listQuery.lastPageIndex = 1
Object.keys(listQuery).forEach(key => {
if (listQuery[key] === '') listQuery[key] = undefined
})
this.getList()
}
}
}
</script>
<style></style>

View File

@ -0,0 +1,429 @@
<template>
<div class="app-container">
<el-button
type="primary"
size="mini"
style="margin-bottom:20px"
@click="handleAdd()"
>新增规则</el-button>
<el-table :data="list" border style="width: 100%">
<el-table-column label="规则名称" prop="name" />
<el-table-column label="规则类型" prop="ruleType">
<template slot-scope="scope">
<span>{{
scope.row.ruleType | optionsFilter(ruleTypeOptions)
}}</span>
</template>
</el-table-column>
<el-table-column label="创建时间">
<template slot-scope="scope">
<span>{{
scope.row.createDate | parseTime("{y}-{m}-{d} {h}:{i}:{s}")
}}</span>
</template>
</el-table-column>
<el-table-column label="最后更新时间">
<template slot-scope="scope">
<span>{{
scope.row.lastUpdateDate | parseTime("{y}-{m}-{d} {h}:{i}:{s}")
}}</span>
</template>
</el-table-column>
<el-table-column label="操作" fixed="right" align="center" width="280px">
<template slot-scope="scope">
<el-button
size="mini"
type="primary"
round
style="font-size:14px;padding:10px 20px"
@click="handleAdd(scope.row)"
>编辑</el-button>
<el-button
size="mini"
type="danger"
round
style="font-size:14px;padding:10px 20px"
@click="handleDel(scope.row)"
>删除</el-button>
</template>
</el-table-column>
</el-table>
<pagination
v-if="total > 0"
:total="total"
:page.sync="listQuery.lastPageIndex"
:limit.sync="listQuery.size"
@pagination="getList"
/>
<el-dialog
class="dialog"
:title="diaTitle"
append-to-body
center
width="604px"
:visible.sync="diaVisible"
:close-on-click-modal="false"
:close-on-press-escape="false"
:close="closeDia"
>
<div class="preview-container">
<el-form
ref="form"
label-position="left"
label-width="150px"
:rules="rules"
:model="form"
>
<el-form-item label="规则名称" prop="name">
<el-input
v-model="form.name"
placeholder="请输入"
/>
</el-form-item>
<el-form-item label="规则类型" prop="ruleType">
<el-select v-model="form.ruleType">
<el-option v-for="item of ruleTypeOptions" :key="item.value" :label="item.label" :value="item.value" />
</el-select>
</el-form-item>
<el-form-item v-if="form.ruleType === 'TEMPORARY'" label="生效时间" prop="dateRange">
<el-date-picker
v-model="form.dateRange"
type="datetimerange"
range-separator="至"
start-placeholder="开始日期"
end-placeholder="结束日期"
/>
</el-form-item>
<el-form-item label="行政区域" prop="regionIds">
<el-cascader
v-model="form.regionIds"
class="filter-item"
style="width:240px"
:options="regions"
:props="{ checkStrictly: true }"
placeholder="行政区域"
clearable
/>
</el-form-item>
<el-form-item label="是否适用于子级区域" prop="all">
<el-radio v-model="form.all" :label="true"></el-radio>
<el-radio v-model="form.all" :label="false"></el-radio>
</el-form-item>
<el-form-item v-if="form.ruleType === 'FINAL'" label="商户结算具体要求" prop="specialBusinessContent">
<el-input
v-model="form.specialBusinessContent"
type="textarea"
placeholder="请输入"
/>
</el-form-item>
<el-form-item v-if="form.ruleType === 'FINAL'" label="商户结算积分最低限额" prop="specialBusinessMin">
<el-input
v-model="form.specialBusinessMin"
type="number"
placeholder="请输入"
/>
</el-form-item>
<el-form-item label="申请办件积分" prop="apply">
<el-input
v-model="form.apply"
type="number"
placeholder="请输入"
/>
</el-form-item>
<el-form-item label="处理办件积分" prop="handling">
<el-input
v-model="form.handling"
type="number"
placeholder="请输入"
/>
</el-form-item>
<el-form-item label="差评扣分(负数)" prop="negativeComment">
<el-input
v-model="form.negativeComment"
type="number"
placeholder="请输入"
/>
</el-form-item>
<el-form-item label="阅读" prop="read">
<el-input
v-model="form.read"
type="number"
placeholder="请输入"
/>
</el-form-item>
<el-form-item label="实名认证积分" prop="realNameAuthentication">
<el-input
v-model="form.realNameAuthentication"
type="number"
placeholder="请输入"
/>
</el-form-item>
<el-form-item label="发朋友圈" prop="sendACircleOfFriends">
<el-input
v-model="form.sendACircleOfFriends"
type="number"
placeholder="请输入"
/>
</el-form-item>
<el-form-item label="特殊工单类型奖励积分(医保卫生)" prop="specialWorkType">
<el-input
v-model="form.specialWorkType"
type="number"
placeholder="请输入"
/>
</el-form-item>
<el-form-item label="超期办件扣分(负数)" prop="timeOut">
<el-input
v-model="form.timeOut"
type="number"
placeholder="请输入"
/>
</el-form-item>
<el-form-item label="非常满意得分" prop="verySatisfied">
<el-input
v-model="form.verySatisfied"
type="number"
placeholder="请输入"
/>
</el-form-item>
</el-form>
</div>
<span slot="footer" class="dialog-footer">
<el-button type="default" @click="closeDia">取消</el-button>
<el-button type="primary" @click="submitForm">提交</el-button>
</span>
</el-dialog>
</div>
</template>
<script>
import Pagination from '@/components/Pagination'
import { list, add, del } from '@/api/fingertipIntegral'
import { getRegions } from '@/api/region'
export default {
components: { Pagination },
filters: {
optionsFilter(value, options = []) {
const findItem = options.find((option) => option.value === value)
if (findItem) {
return findItem.label
}
return ''
}
},
data() {
return {
total: 0,
listQuery: {
lastPageIndex: 1,
// params: {},
size: 10
},
list: undefined,
diaTitle: '',
diaVisible: false,
form: {
name: undefined,
ruleType: 'FINAL',
regionIds: undefined,
all: false,
dateRange: undefined,
apply: undefined,
handling: undefined,
negativeComment: undefined,
read: undefined,
realNameAuthentication: undefined,
sendACircleOfFriends: undefined,
specialWorkType: undefined,
timeOut: undefined,
verySatisfied: undefined,
specialBusinessContent: undefined,
specialBusinessMin: undefined
},
rules: {
name: [{ required: true, message: '请输入', trigger: 'change' }],
ruleType: [{ required: true, message: '请选择', trigger: 'change' }],
regionIds: [{ required: true, message: '请选择', trigger: 'change' }],
all: [{ required: true, message: '请选择', trigger: 'change' }],
dateRange: [{ required: true, message: '请选择', trigger: 'change' }],
specialBusinessContent: [{ required: true, message: '请输入', trigger: 'change' }],
specialBusinessMin: [{ required: true, message: '请输入', trigger: 'change' }]
},
ruleTypeOptions: [
{
label: '长期规则',
value: 'FINAL'
},
{
label: '临时规则',
value: 'TEMPORARY'
}
],
regions: []
}
},
watch: {
'listQuery.lastPageIndex': {
handler(val) {
this.getList()
},
deep: true // true
}
},
created() {
this.getRegions()
this.getList()
},
methods: {
getList() {
list(this.listQuery).then(res => {
// console.log(res);
this.list = res.d
this.total = res.d.total
this.pageSize = res.d.pageSize
// if (!res.d.lastPageIndex) {
// this.listQuery.lastPageIndex;
// }
})
},
getRegions() {
getRegions().then(res => {
const tempData = res.d
const countyArr = [] // ,1
tempData.map(county => {
const countyObj = {
value: county.root.id,
label: county.root.name,
disabled: !county.root.check,
children: []
}
countyArr.push(countyObj)
county.node.map(town => {
const townObj = {
value: town.root.id,
label: town.root.name,
disabled: !town.root.check,
children: []
}
countyObj.children.push(townObj)
town.node.map(country => {
townObj.children.push({
value: country.root.id,
label: country.root.name,
disabled: !country.root.check
})
})
})
})
this.regions = countyArr
})
},
handleAdd(item) {
if (item) {
this.diaTitle = '编辑规则'
const tmpItem = JSON.parse(JSON.stringify(item))
const { regionIds, startDate, endDate } = tmpItem
tmpItem.regionIds = regionIds.split(',')
if (startDate || endDate) {
tmpItem.dateRange = [new Date(startDate * 1000), new Date(endDate * 1000)]
}
this.form = tmpItem
} else {
this.diaTitle = '新增规则'
this.form = {
name: undefined,
ruleType: 'FINAL',
regionIds: undefined,
all: false,
dateRange: undefined,
apply: undefined,
handling: undefined,
negativeComment: undefined,
read: undefined,
realNameAuthentication: undefined,
sendACircleOfFriends: undefined,
specialWorkType: undefined,
timeOut: undefined,
verySatisfied: undefined,
specialBusinessContent: undefined,
specialBusinessMin: undefined
}
}
this.$nextTick(() => {
const formEl = this.$refs['form']
if (formEl) formEl.clearValidate()
this.diaVisible = true
})
},
submitForm() {
// console.log(this.form)
// return
this.$refs['form'].validate((valid) => {
if (valid) {
const { dateRange } = this.form
const form = JSON.parse(JSON.stringify(this.form))
const { regionIds = [] } = form
form.regionIds = regionIds.join(',')
if (dateRange) {
form.startDate = dateRange[0].getTime() / 1000
form.endDate = dateRange[1].getTime() / 1000
}
add(form).then(() => {
this.$message({
type: 'success',
message: '操作成功!'
})
this.closeDia()
this.getList()
})
}
})
},
handleDel(item) {
this.$confirm('此操作将永久删除, 是否继续?', '提示', {
confirmButtonText: '确定',
cancelButtonText: '取消',
type: 'warning'
}).then(() => {
del({ id: item.id }).then(() => {
this.$message({
type: 'success',
message: '删除成功!'
})
this.getList()
})
})
},
jumpStaff(item) {
const { name, id } = item
this.$router.push({
path: '/dept/staff',
query: {
name,
id
}
})
},
closeDia() {
this.diaVisible = false
}
}
}
</script>
<style></style>

View File

@ -0,0 +1,58 @@
export const sourceOptions = [
{
value: 'REAL_NAME_AUTHENTICATION',
label: '实名认证'
},
{
value: 'HANDLING',
label: '处理办件'
},
{
value: 'APPLY',
label: '申请办件'
},
{
value: 'TIMEOUT',
label: '超期办件扣分'
},
{
value: 'VERY_SATISFIED',
label: '非常满意得分'
},
{
value: 'NEGATIVE_COMMENT',
label: '差评扣分'
},
{
value: 'READ',
label: '阅读'
},
{
value: 'SEND_A_CIRCLE_OF_FRIENDS',
label: '发朋友圈'
},
{
value: 'CONSUMPTION',
label: '消费'
},
{
value: 'MERCHANT_SETTLEMENT',
label: '商户结算'
},
{
value: 'POINT_REFUND',
label: '积分回退'
},
{
value: 'REGULATORY_PUNISHMENT_AND_REWARD',
label: '监管惩罚'
},
{
value: 'SPECIAL_WORK_TYPE',
label: '特殊工单类型奖励积分'
},
{
value: 'TITLE_EVALUATION',
label: '称号评比'
}
]

View File

@ -0,0 +1,238 @@
<template>
<div class="app-container">
<div class="filter-container">
<!-- <el-input
v-model="listQuery.keyword"
style="width:200px;margin-right:10px"
class="filter-item"
placeholder="请输入关键字"
clearable
/> -->
<el-select v-model="listQuery.source" clearable class="filter-item" style="margin-right: 10px" placeholder="请选择积分来源">
<el-option v-for="item of sourceOptions" :key="item.value" v-bind="item" />
</el-select>
<el-date-picker
v-model="listQuery.dateArr"
type="datetimerange"
class="filter-item"
style="margin-right: 10px"
range-separator="至"
start-placeholder="开始日期"
end-placeholder="结束日期"
value-format="timestamp"
align="right"
clearable
/>
<el-cascader
v-model="listQuery.regionIds"
class="filter-item"
style="width:240px"
:options="regions"
:props="{ checkStrictly: true }"
placeholder="行政区域"
clearable
/>
<el-button
type="primary"
style="margin-left:10px"
@click="handleSearch"
>搜索</el-button>
<el-button
:loading="exportLoading"
icon="el-icon-download"
type="primary"
style="margin-left:10px"
@click="handleExport"
>导出</el-button>
</div>
<el-table :data="list" border style="width: 100%">
<el-table-column label="用户名" prop="residentInformation.name" />
<el-table-column label="积分来源" prop="source">
<template slot-scope="scope">
<span>{{
scope.row.source | optionsFilter(sourceOptions)
}}</span>
</template>
</el-table-column>
<el-table-column label="获取积分数" prop="num" />
<el-table-column label="获取时间">
<template slot-scope="scope">
<span>{{
scope.row.createDate | parseTime("{y}-{m}-{d} {h}:{i}:{s}")
}}</span>
</template>
</el-table-column>
</el-table>
<pagination
v-if="total > 0"
:total="total"
:page.sync="listQuery.lastPageIndex"
:limit.sync="listQuery.size"
@pagination="getList"
/>
</div>
</template>
<script>
import Pagination from '@/components/Pagination'
import { recordList } from '@/api/fingertipIntegral'
import { getRegions } from '@/api/region'
import { sourceOptions } from './options'
export default {
components: { Pagination },
filters: {
optionsFilter(value, options = []) {
const findItem = options.find((option) => option.value === value)
if (findItem) {
return findItem.label
}
return ''
}
},
data() {
return {
total: 0,
listQuery: {
lastPageIndex: 1,
// params: {},
size: 10,
category: undefined,
id: undefined,
innerCategory: undefined,
keyword: undefined,
source: undefined,
status: undefined,
userId: undefined,
dateArr: [],
regionIds: []
},
list: undefined,
regionSearchVal: undefined,
regions: [],
exportLoading: false,
sourceOptions
}
},
watch: {
'listQuery.lastPageIndex': {
handler(val) {
this.getList()
},
deep: true // true
}
},
created() {
this.getList()
this.getRegions()
},
methods: {
getList() {
const listQuery = JSON.parse(JSON.stringify(this.listQuery))
const { dateArr, regionIds } = listQuery
if (dateArr) {
listQuery.startDate = dateArr[0] / 1000
listQuery.endDate = dateArr[1] / 1000
}
listQuery.regionIds = regionIds.join(',')
recordList(listQuery).then(res => {
this.list = res.d.records
this.total = res.d.total
// this.pageSize = res.d.pageSize
})
},
getRegions() {
getRegions().then(res => {
const tempData = res.d
const countyArr = [] // ,1
tempData.map(county => {
const countyObj = {
value: county.root.id,
label: county.root.name,
disabled: !county.root.check,
children: []
}
countyArr.push(countyObj)
county.node.map(town => {
const townObj = {
value: town.root.id,
label: town.root.name,
disabled: !town.root.check,
children: []
}
countyObj.children.push(townObj)
town.node.map(country => {
townObj.children.push({
value: country.root.id,
label: country.root.name,
disabled: !country.root.check
})
})
})
})
this.regions = countyArr
})
},
handleExport() {
const that = this
import('@/vendor/Export2Excel').then(excel => {
const tHeader = ['用户名', '积分来源', '获取积分数', '获取时间']
const filterVal = ['residentInformation.name', 'source', 'num', 'createDate']
this.exportLoading = true
const listQuery = JSON.parse(JSON.stringify(this.listQuery))
const { dateArr, regionIds } = listQuery
if (dateArr) {
listQuery.startDate = dateArr[0] / 1000
listQuery.endDate = dateArr[1] / 1000
}
listQuery.regionIds = regionIds.join(',')
listQuery.size = 999999
recordList(listQuery).then(res => {
setTimeout(() => {
this.exportLoading = false
}, 3000)
const data = that.formatJson(filterVal, res.d.records)
excel.export_json_to_excel({
header: tHeader,
data: data,
filename: '积分流水'
})
})
})
},
formatJson(filterVal, jsonData) {
return jsonData.map(v =>
filterVal.map(j => {
let value
if (j === 'createDate') {
value = this.$options.filters['parseTime'](v[j])
} else if (j === 'residentInformation.name') {
value = v['residentInformation']['name']
} else if (j === 'source') {
value = this.$options.filters['optionsFilter'](v[j], sourceOptions)
} else {
value = v[j]
}
// if (!value && value !== 0) value = "N/A";
return value
})
)
},
handleSearch() {
const { listQuery } = this
this.listQuery.lastPageIndex = 1
Object.keys(listQuery).forEach(key => {
if (listQuery[key] === '') listQuery[key] = undefined
})
this.getList()
}
}
}
</script>
<style></style>

View File

@ -0,0 +1,410 @@
<template>
<div class="app-container">
<div class="filter-container">
<!-- <el-input
v-model="listQuery.keyword"
style="width:200px;margin-right:10px"
class="filter-item"
placeholder="请输入关键字"
clearable
/> -->
<el-select v-model="listQuery.settlementStatus" clearable class="filter-item" style="width:200px;margin-right:10px" placeholder="请选择结算状态">
<el-option v-for="item of settlementStatusOptions" :key="item.value" v-bind="item" />
</el-select>
<el-select v-model="listQuery.dealStatus" clearable class="filter-item" style="width:200px;margin-right:10px" placeholder="请选择已处理状态">
<el-option v-for="item of dealStatusOptions" :key="item.value" v-bind="item" />
</el-select>
<el-date-picker
v-model="listQuery.dateArr"
type="datetimerange"
class="filter-item"
range-separator="至"
start-placeholder="开始日期"
end-placeholder="结束日期"
value-format="timestamp"
align="right"
clearable
/>
<el-button
type="primary"
style="margin-left:10px"
@click="handleSearch"
>搜索</el-button>
<el-button
:loading="exportLoading"
icon="el-icon-download"
type="primary"
style="margin-left:10px"
@click="handleExport"
>导出</el-button>
</div>
<el-table v-loading="loading" :data="list" border style="width: 100%">
<el-table-column label="用户名" prop="residentInformation.name" />
<el-table-column label="店名" prop="residentInformation.speciallyBusinessInfo.name" />
<el-table-column label="结算积分数" prop="num" />
<el-table-column label="积分兑换金额(元)" prop="money" />
<el-table-column label="提交时间">
<template slot-scope="scope">
<span>{{
scope.row.createDate | parseTime("{y}-{m}-{d} {h}:{i}:{s}")
}}</span>
</template>
</el-table-column>
<el-table-column label="结算状态">
<template slot-scope="scope">
<span>{{
scope.row.settlementStatus | optionsFilter(settlementStatusOptions)
}}</span>
</template>
</el-table-column>
<el-table-column label="已处理状态">
<template slot-scope="scope">
<span>{{
scope.row.dealStatus | optionsFilter(dealStatusOptions)
}}</span>
</template>
</el-table-column>
<el-table-column label="处理备注" prop="remark" />
<el-table-column label="发票状态">
<template slot-scope="scope">
<span>{{
scope.row.invoiceStatus | optionsFilter(invoiceStatusOptions)
}}</span>
</template>
</el-table-column>
<el-table-column label="操作" width="300px" fixed="right" align="center">
<template slot-scope="scope">
<el-button
v-if="scope.row.invoiceStatus == '1' && scope.row.dealStatus == null"
type="primary"
size="mini"
style="font-size:12px;padding:10px 20px"
@click="handleEdit(scope.row)"
>处理</el-button>
<el-button
v-if="scope.row.invoiceStatus != '1'"
type="success"
size="mini"
style="font-size:12px;padding:10px 20px;border-radius:21px"
@click="handleDelivery(scope.row)"
>收到发票</el-button>
<el-button
v-if="scope.row.dealStatus != '1'"
type="primary"
size="mini"
style="font-size:12px;padding:10px 20px"
@click="handleRExport(scope.row)"
>导出结算积分</el-button>
</template>
</el-table-column>
</el-table>
<pagination
v-if="total > 0"
:total="total"
:page.sync="listQuery.lastPageIndex"
:limit.sync="listQuery.size"
@pagination="getList"
/>
<el-dialog
class="dialog"
title="积分结算"
append-to-body
center
width="364px"
:visible.sync="diaVisible"
:close-on-click-modal="false"
:close-on-press-escape="false"
:close="closeDia"
>
<div class="preview-container">
<el-form
ref="form"
label-position="left"
label-width="100px"
:rules="rules"
:model="form"
>
<el-form-item label="结算状态" prop="dealStatus">
<el-radio v-model="form.dealStatus" :label="0">兑换</el-radio>
<el-radio v-model="form.dealStatus" :label="1">不兑换</el-radio>
</el-form-item>
<el-form-item label="备注" prop="remark">
<el-input
v-model="form.remark"
type="textarea"
placeholder="请输入"
/>
</el-form-item>
</el-form>
</div>
<span slot="footer" class="dialog-footer">
<el-button type="default" @click="closeDia">取消</el-button>
<el-button type="primary" @click="submitForm">提交</el-button>
</span>
</el-dialog>
</div>
</template>
<script>
import Pagination from '@/components/Pagination'
import { settlementList, settlementDeal, settlementRecordList } from '@/api/fingertipIntegral'
import { sourceOptions } from './options'
export default {
components: { Pagination },
filters: {
optionsFilter(value, options = []) {
const findItem = options.find((option) => option.value === value)
if (findItem) {
return findItem.label
}
return ''
}
},
data() {
return {
total: 0,
listQuery: {
lastPageIndex: 1,
size: 10,
category: undefined,
dealStatus: undefined,
endDate: undefined,
id: undefined,
innerCategory: undefined,
keyword: undefined,
settlementStatus: undefined,
startDate: undefined,
status: undefined,
dateArr: []
},
list: undefined,
exportLoading: false,
settlementStatusOptions: [
{
label: '待处理',
value: '0'
},
{
label: '已处理',
value: '1'
}
],
dealStatusOptions: [
{
label: '兑换',
value: '0'
},
{
label: '不兑换',
value: '1'
}
],
invoiceStatusOptions: [
{
label: '未收',
value: '0'
},
{
label: '已收',
value: '1'
}
],
diaVisible: false,
form: {
dealStatus: 0,
remark: undefined
},
rules: {
dealStatus: [{ required: true, message: '请选择', trigger: 'change' }]
}
}
},
watch: {
'listQuery.lastPageIndex': {
handler(val) {
this.getList()
},
deep: true // true
}
},
created() {
this.getList()
},
methods: {
getList() {
const listQuery = JSON.parse(JSON.stringify(this.listQuery))
const { dateArr } = listQuery
if (dateArr) {
listQuery.startDate = dateArr[0] / 1000
listQuery.endDate = dateArr[1] / 1000
}
this.loading = true
settlementList(listQuery).then(res => {
this.loading = false
this.list = res.d.records
this.total = res.d.total
// this.pageSize = res.d.pageSize
}).catch(() => {
this.loading = false
})
},
handleEdit(item) {
this.form = {
id: item.id,
dealStatus: 0,
remark: undefined,
invoiceStatus: item.invoiceStatus
}
this.$nextTick(() => {
const formEl = this.$refs['form']
if (formEl) formEl.clearValidate()
this.diaVisible = true
})
},
submitForm() {
this.$refs['form'].validate((valid) => {
if (valid) {
settlementDeal(this.form).then(() => {
this.$message({
type: 'success',
message: '操作成功!'
})
this.closeDia()
this.getList()
})
}
})
},
closeDia() {
this.diaVisible = false
},
handleExport() {
const that = this
import('@/vendor/Export2Excel').then(excel => {
const tHeader = ['用户名', '店名', '结算积分数', '积分兑换金额(元)', '提交时间', '结算状态', '已处理状态', '处理备注', '发票状态']
const filterVal = ['residentInformation.name', 'residentInformation.speciallyBusinessInfo.name', 'num', 'money', 'createDate', 'settlementStatus', 'dealStatus', 'remark', 'invoiceStatus']
this.exportLoading = true
const listQuery = JSON.parse(JSON.stringify(this.listQuery))
const { dateArr } = listQuery
if (dateArr) {
listQuery.startDate = dateArr[0] / 1000
listQuery.endDate = dateArr[1] / 1000
}
listQuery.size = 999999
settlementList(listQuery).then(res => {
setTimeout(() => {
this.exportLoading = false
}, 3000)
const data = that.formatJson(filterVal, res.d.records)
excel.export_json_to_excel({
header: tHeader,
data: data,
filename: '结算记录'
})
})
})
},
formatJson(filterVal, jsonData) {
return jsonData.map(v =>
filterVal.map(j => {
let value
if (j === 'invoiceStatus' || j === 'dealStatus' || j === 'settlementStatus') {
value = this.$options.filters['optionsFilter'](v[j], this[`${j}Options`])
} else if (j === 'createDate') {
value = this.$options.filters['parseTime'](v[j])
} else if (j === 'residentInformation.name') {
value = v['residentInformation']['name']
} else if (j === 'residentInformation.speciallyBusinessInfo.name') {
value = v['residentInformation']['speciallyBusinessInfo']['name']
} else {
value = v[j]
}
// if (!value && value !== 0) value = "N/A";
return value
})
)
},
handleRExport(item) {
const that = this
import('@/vendor/Export2Excel').then(excel => {
const tHeader = ['商户姓名', '日期', '群众姓名', '积分数量', '积分兑换金额(元)', '积分交易备注']
const filterVal = ['businessName', 'createDate', 'massesName', 'num', 'money', 'remark']
this.loading = true
// const listQuery = JSON.parse(JSON.stringify(this.listQuery))
// const { dateArr } = listQuery
// if (dateArr) {
// listQuery.startDate = dateArr[0] / 1000
// listQuery.endDate = dateArr[1] / 1000
// }
// listQuery.size = 999999
settlementRecordList({ id: item.id }).then(res => {
setTimeout(() => {
this.loading = false
}, 3000)
const data = that.formatDJson(filterVal, res.d)
excel.export_json_to_excel({
header: tHeader,
data: data,
filename: '积分清单'
})
}).catch(() => {
this.loading = false
})
})
},
formatDJson(filterVal, jsonData) {
return jsonData.map(v =>
filterVal.map(j => {
let value
if (j === 'createDate') {
value = this.$options.filters['parseTime'](v[j])
} else if (j === 'source') {
value = this.$options.filters['optionsFilter'](v[j], sourceOptions)
} else {
value = v[j]
}
// if (!value && value !== 0) value = "N/A";
return value
})
)
},
handleDelivery(item) {
this.$confirm('是否收到发票?', '提示', {
confirmButtonText: '确定',
cancelButtonText: '取消',
type: 'warning'
}).then(() => {
settlementDeal({
id: item.id,
dealStatus: item.dealStatus,
invoiceStatus: 1
}).then(() => {
this.$message({
type: 'success',
message: '操作成功!'
})
this.getList()
})
})
},
handleSearch() {
const { listQuery } = this
this.listQuery.lastPageIndex = 1
Object.keys(listQuery).forEach(key => {
if (listQuery[key] === '') listQuery[key] = undefined
})
this.getList()
}
}
}
</script>
<style></style>

View File

@ -0,0 +1,496 @@
<template>
<div class="app-container">
<div class="filter-container">
<el-input
v-model="listQuery.params.name"
style="width:200px;margin-right:10px"
class="filter-item"
placeholder="姓名"
clearable
/>
<el-input
v-model="listQuery.params.phone"
style="width:200px;margin-right:10px"
class="filter-item"
placeholder="手机号"
clearable
/>
<el-input
v-model="listQuery.params.idCard"
style="width:200px;margin-right:10px"
class="filter-item"
placeholder="身份证号"
clearable
/>
<el-cascader
v-model="regionSearchVal"
class="filter-item"
style="width:240px"
:options="regions"
:props="{ checkStrictly: true }"
placeholder="行政区域"
clearable
/>
<el-checkbox
v-model="isStaff"
style="margin-left:10px"
@change="handleIsStaff"
>是否是便民工作人员</el-checkbox>
<el-button
type="primary"
style="margin-left:10px"
@click="handleSearch"
>搜索</el-button>
</div>
<!-- <el-button
type="primary"
size="mini"
style="margin-bottom:20px"
@click="handleAdd()"
>新增规则</el-button> -->
<el-tabs v-model="activeName" @tab-click="handleClick">
<el-tab-pane label="待添加列表" name="first" />
<el-tab-pane label="已添加列表" name="second" />
</el-tabs>
<el-table v-loading="loading" :data="list" border style="width: 100%">
<el-table-column prop="name" label="姓名" width="100">
<template slot-scope="scope">
{{ scope.row.name }}
</template>
</el-table-column>
<el-table-column prop="nameZ" label="姓名(藏语)" width="180">
<template slot-scope="scope">
{{ scope.row.nameZ }}
</template>
</el-table-column>
<el-table-column prop="phone" label="手机号" width="120">
<template slot-scope="scope">
{{ scope.row.phone }}
</template>
</el-table-column>
<el-table-column prop="phone" label="身份证号" width="200">
<template slot-scope="scope">
{{ scope.row.idCard }}
</template>
</el-table-column>
<el-table-column prop="phone" label="是否是便民工作人员" width="150">
<template slot-scope="scope">
{{ scope.row.isConvenience ? "是" : "否" }}
</template>
</el-table-column>
<el-table-column prop="phone" label="所属行政区域">
<template slot-scope="scope">
{{
scope.row.permanentResidenceRegion +
(scope.row.permanentResidenceTown
? "-" + scope.row.permanentResidenceTown
: "") +
(scope.row.permanentResidenceTownShip
? "-" + scope.row.permanentResidenceTownShip
: "")
}}
</template>
</el-table-column>
<el-table-column label="操作" fixed="right" align="center">
<template slot-scope="scope">
<el-button
v-if="activeName === 'first'"
size="mini"
type="primary"
round
style="font-size:14px;padding:10px 20px"
@click="handleAdd(scope.row, 'add')"
>添加</el-button>
<el-button
v-if="activeName === 'second'"
size="mini"
type="primary"
round
style="font-size:14px;padding:10px 20px"
@click="handleAdd(scope.row, 'edit')"
>编辑</el-button>
<el-button
v-if="activeName === 'second'"
size="mini"
type="danger"
round
style="font-size:14px;padding:10px 20px"
@click="handleDel(scope.row)"
>移除</el-button>
</template>
</el-table-column>
</el-table>
<pagination
v-if="total > 0"
:total="total"
:page.sync="listQuery.lastPageIndex"
:limit.sync="listQuery.size"
@pagination="getList"
/>
<el-dialog
class="dialog"
:title="diaTitle"
append-to-body
center
width="604px"
:visible.sync="diaVisible"
:close-on-click-modal="false"
:close-on-press-escape="false"
:close="closeDia"
>
<div class="preview-container">
<el-form
ref="form"
label-position="left"
label-width="150px"
:rules="rules"
:model="form"
>
<el-form-item label="商户名称" prop="name">
<el-input
v-model="form.name"
placeholder="请输入"
/>
</el-form-item>
<el-form-item label="商户名称(藏文)" prop="nameZ">
<el-input
v-model="form.nameZ"
placeholder="请输入"
/>
</el-form-item>
<el-form-item label="商户图片" prop="images">
<CutUploadImage :init-url="form.images" multiple @imgupload="UploadCbk" />
</el-form-item>
<el-form-item label="营业执照" prop="businessLicense">
<CutUploadImage :init-url="form.businessLicense" @imgupload="bUploadCbk" />
</el-form-item>
<el-form-item label="商户地址" prop="address">
<el-input
v-model="form.address"
placeholder="请输入"
/>
</el-form-item>
<el-form-item label="商户地址(藏文)" prop="addressZ">
<el-input
v-model="form.addressZ"
placeholder="请输入"
/>
</el-form-item>
<el-form-item label="商户介绍" prop="introduce">
<el-input
v-model="form.introduce"
placeholder="请输入"
/>
</el-form-item>
<el-form-item label="商户介绍(藏文)" prop="introduceZ">
<el-input
v-model="form.introduceZ"
placeholder="请输入"
/>
</el-form-item>
<el-form-item label="兑换规则" prop="rule">
<el-input
v-model="form.rule"
placeholder="请输入"
/>
</el-form-item>
<el-form-item label="兑换规则(藏文)" prop="ruleZ">
<el-input
v-model="form.ruleZ"
placeholder="请输入"
/>
</el-form-item>
</el-form>
</div>
<span slot="footer" class="dialog-footer">
<el-button type="default" @click="closeDia">取消</el-button>
<el-button type="primary" @click="submitForm">提交</el-button>
</span>
</el-dialog>
</div>
</template>
<script>
import Pagination from '@/components/Pagination'
import CutUploadImage from '@/components/cutUploadImage'
import { list, speciallyBusinessList, speciallyBusinessSet } from '@/api/speciallyBusiness'
import { getRegions } from '@/api/region'
export default {
components: { Pagination, CutUploadImage },
filters: {
optionsFilter(value, options = []) {
const findItem = options.find((option) => option.value === value)
if (findItem) {
return findItem.label
}
return ''
}
},
data() {
return {
loading: false,
total: 0,
listQuery: {
lastPageIndex: 1,
size: 10,
params: {
name: undefined,
phone: undefined,
idCard: undefined,
isConvenience: undefined
}
},
list: undefined,
listMethod: list,
activeName: 'first',
diaTitle: '',
diaVisible: false,
form: {
name: undefined,
nameZ: undefined,
images: [],
businessLicense: undefined,
address: undefined,
addressZ: undefined,
introduce: undefined,
introduceZ: undefined,
rule: undefined,
ruleZ: undefined
},
rules: {
name: [{ required: true, message: '请输入', trigger: 'change' }],
ruleType: [{ required: true, message: '请选择', trigger: 'change' }],
regionIds: [{ required: true, message: '请选择', trigger: 'change' }],
all: [{ required: true, message: '请选择', trigger: 'change' }],
dateRange: [{ required: true, message: '请选择', trigger: 'change' }]
},
ruleTypeOptions: [
{
label: '长期规则',
value: 'FINAL'
},
{
label: '临时规则',
value: 'TEMPORARY'
}
],
regions: [],
isStaff: undefined,
regionSearchVal: undefined
}
},
watch: {
'listQuery.lastPageIndex': {
handler(val) {
this.getList()
},
deep: true // true
}
},
created() {
this.getRegions()
this.getList()
},
methods: {
getList() {
this.loading = true
this.listMethod(this.listQuery).then(res => {
// console.log(res);
this.list = res.d.list
this.total = res.d.total
this.pageSize = res.d.pageSize
this.loading = false
// if (!res.d.lastPageIndex) {
// this.listQuery.lastPageIndex;
// }
}).catch(() => {
this.loading = false
})
},
handleClick() {
const { activeName } = this
// console.log(activeName)
switch (activeName) {
case 'first':
this.listMethod = list
break
default:
this.listMethod = speciallyBusinessList
}
this.listQuery.lastPageIndex = 1
this.getList()
},
getRegions() {
getRegions().then(res => {
const tempData = res.d
const countyArr = [] // ,1
tempData.map(county => {
const countyObj = {
value: county.root.name,
label: county.root.name,
disabled: !county.root.check,
children: []
}
countyArr.push(countyObj)
county.node.map(town => {
const townObj = {
value: town.root.name,
label: town.root.name,
disabled: !town.root.check,
children: []
}
countyObj.children.push(townObj)
town.node.map(country => {
townObj.children.push({
value: country.root.name,
label: country.root.name,
disabled: !country.root.check
})
})
})
})
this.regions = countyArr
})
},
handleAdd(item, type) {
if (type === 'edit') {
this.diaTitle = '编辑'
const tmpItem = JSON.parse(JSON.stringify(item.speciallyBusinessInfo))
tmpItem.id = item.id
this.form = tmpItem
} else if (type === 'add') {
this.diaTitle = '添加'
this.form = {
id: item.id,
name: undefined,
nameZ: undefined,
images: [],
businessLicense: undefined,
address: undefined,
addressZ: undefined,
introduce: undefined,
introduceZ: undefined,
rule: undefined,
ruleZ: undefined
}
}
this.$nextTick(() => {
const formEl = this.$refs['form']
if (formEl) formEl.clearValidate()
this.diaVisible = true
})
},
submitForm() {
// console.log(this.form)
// return
this.$refs['form'].validate((valid) => {
if (valid) {
const form = JSON.parse(JSON.stringify(this.form))
speciallyBusinessSet([{
id: form.id,
add: true,
speciallyBusinessInfo: form
}]).then(() => {
this.$message({
type: 'success',
message: '操作成功!'
})
this.closeDia()
this.getList()
})
}
})
},
handleDel(item) {
this.$confirm('是否移除?', '提示', {
confirmButtonText: '确定',
cancelButtonText: '取消',
type: 'warning'
}).then(() => {
speciallyBusinessSet([{
id: item.id,
add: false
}]).then(() => {
this.$message({
type: 'success',
message: '操作成功!'
})
this.getList()
})
})
},
UploadCbk(data) {
this.form.images = data
},
bUploadCbk(data) {
this.form.businessLicense = data
},
// jumpStaff(item) {
// const { name, id } = item
// this.$router.push({
// path: '/dept/staff',
// query: {
// name,
// id
// }
// })
// },
closeDia() {
this.diaVisible = false
},
handleIsStaff(val) {
if (val === false) {
this.listQuery.params.isConvenience === undefined
const temp = Object.assign({}, this.listQuery)
temp.params.isConvenience === undefined
this.listQuery = temp
}
},
handleSearch() {
this.listQuery.params.isConvenience = this.isStaff ? true : undefined
if (this.regionSearchVal) {
switch (this.regionSearchVal.length) {
case 1:
this.listQuery.params.PermanentResidenceRegion = this.regionSearchVal[0]
this.listQuery.params.PermanentResidenceTown = undefined
this.listQuery.params.PermanentResidenceTownShip = undefined
break
case 2:
this.listQuery.params.PermanentResidenceTown = this.regionSearchVal[1]
this.listQuery.params.PermanentResidenceRegion = undefined
this.listQuery.params.PermanentResidenceTownShip = undefined
break
case 3:
this.listQuery.params.PermanentResidenceTownShip = this.regionSearchVal[2]
this.listQuery.params.PermanentResidenceRegion = undefined
this.listQuery.params.PermanentResidenceTown = undefined
break
default:
this.listQuery.params.PermanentResidenceRegion = undefined
this.listQuery.params.PermanentResidenceTown = undefined
this.listQuery.params.PermanentResidenceTownShip = undefined
break
}
}
this.getList()
}
}
}
</script>
<style></style>