完善用户管理和客户管理,新增平台管理(素材管理),忽略src文件夹语法检查(因为这个真烦,而且每次重载还费时,忽略后快多了)

This commit is contained in:
Double-_-Z 2025-07-11 16:32:35 +08:00
parent 5fe4fa3589
commit 5424a94fa5
7 changed files with 329 additions and 25 deletions

View File

@ -2,3 +2,5 @@ build/*.js
src/assets
public
dist
views
src

View File

@ -0,0 +1,27 @@
import request from '@/utils/request'
export function add(data) {
return request({
url: 'api/article',
method: 'post',
data
})
}
export function del(ids) {
return request({
url: 'api/article',
method: 'delete',
data: ids
})
}
export function edit(data) {
return request({
url: 'api/article',
method: 'put',
data
})
}
export default { add, edit, del }

View File

@ -0,0 +1,27 @@
import request from '@/utils/request'
export function add(data) {
return request({
url: 'api/material',
method: 'post',
data
})
}
export function del(ids) {
return request({
url: 'api/material',
method: 'delete',
data: ids
})
}
export function edit(data) {
return request({
url: 'api/material',
method: 'put',
data
})
}
export default { add, edit, del }

View File

@ -0,0 +1,10 @@
<template>
<div>
123
</div>
</template>
<script>
export default {
name: 'Article'
}
</script>

View File

@ -0,0 +1,225 @@
<template>
<div class="app-container">
<!--工具栏-->
<div class="head-container">
<div>
<!-- 搜索 -->
<el-input
v-model="query.name"
clearable
size="small"
placeholder="输入素材名称"
style="width: 200px;"
class="filter-item"
@keyup.enter.native="crud.toQuery"
/>
<rrOperation />
<el-button v-permission="permission.add" class="filter-item" size="mini" type="primary"
icon="el-icon-plus" @click="crud.toAdd">
新增{{ crud.title }}
</el-button>
</div>
</div>
<!--表单渲染-->
<el-dialog append-to-body :before-close="crud.cancelCU" :visible.sync="crud.status.cu > 0"
:title="crud.status.title" width="400px" @close="uploadDisabled = false;">
<el-form v-loading="loading" ref="form" :model="form" :rules="rules" size="small" label-width="80px">
<el-row :gutter="10">
<el-col :xs="24" :sm="24" :md="24" :lg="24" :xl="24" class="mb20">
<el-form-item label="名称" prop="name">
<el-input v-model="form.name" placeholder="请输入名称"/>
</el-form-item>
</el-col>
<el-col :xs="24" :sm="24" :md="24" :lg="24" :xl="24" class="mb20">
<el-form-item label="素材类型" prop="type">
<el-select v-model="form.type" placeholder="请选择素材类型" clearable>
<el-option v-for="item in dict.material_type" :key="item.id" :label="item.label" :value="item.value" />
</el-select>
</el-form-item>
</el-col>
<el-col :xs="24" :sm="24" :md="24" :lg="24" :xl="24" class="mb20">
<el-form-item label="素材资源" prop="files">
<el-upload ref="uploadRef" action="#" list-type="picture-card" :class="{ disabled: uploadDisabled }"
:limit="1" :file-list="form.files" :on-change="handleChange" :auto-upload="false">
<div style="display: flex;flex-direction: column;align-items: center;justify-content: center;margin-top: -20px;">
<i class="el-icon-plus" style="font-size: 30px;" />
<span style="margin: 5px 0 -20px;line-height: 20px">上传</span>
</div>
<template #file="{ file }">
<div>
<img class="el-upload-list__item-thumbnail" :src="file.url" alt="">
<span class="el-upload-list__item-actions">
<span class="el-upload-list__item-preview" @click="handlePictureCardPreview(file)">
<i class="el-icon-zoom-in" />
</span>
<span class="el-upload-list__item-delete" @click="handleRemove(file)">
<i class="el-icon-delete" />
</span>
</span>
</div>
</template>
</el-upload>
<el-dialog append-to-body :visible.sync="dialogVisible" top="20vh">
<div><img :src="dialogImageUrl" style="width: 100%" alt="Preview Image"></div>
</el-dialog>
</el-form-item>
</el-col>
<el-col :xs="24" :sm="24" :md="24" :lg="24" :xl="24" class="mb20">
<el-form-item label="跳转链接">
<el-input v-model="form.link" type="url" placeholder="请输入跳转链接"/>
</el-form-item>
</el-col>
<el-col :xs="24" :sm="24" :md="24" :lg="24" :xl="24" class="mb20">
<el-form-item label="排序号" prop="sort">
<el-input-number v-model="form.sort" controls-position="right" :min="1" placeholder="请输入排序号"/>
</el-form-item>
</el-col>
</el-row>
</el-form>
<div slot="footer" class="dialog-footer" style="margin-top: -30px;">
<el-button type="text" @click="crud.cancelCU">取消</el-button>
<el-button :loading="crud.status.cu === 2" type="primary" @click="crud.submitCU">新增</el-button>
</div>
</el-dialog>
<!--表格渲染-->
<el-table ref="table" v-loading="crud.loading" :data="crud.data" style="width: 100%;">
<el-table-column :show-overflow-tooltip="true" prop="name" label="素材名称" />
<el-table-column :show-overflow-tooltip="true" prop="url" label="素材资源">
<template slot-scope="scope">
<el-image v-if="scope.row.type == '轮播图'" style="width: 100px;height: 100px;" :src="scope.row.url" :preview-src-list="[scope.row.url]"></el-image>
<video controls width="100px" height="100px" :src="scope.row.url" v-else preload="meta" />
</template>
</el-table-column>
<el-table-column :show-overflow-tooltip="true" prop="type" label="素材类型" />
<el-table-column :show-overflow-tooltip="true" prop="link" label="跳转地址">
<template slot-scope="scope">
<el-link :href="scope.row.link" target="_blank">{{ scope.row.link }}</el-link>
</template>
</el-table-column>
<el-table-column :show-overflow-tooltip="true" prop="sort" label="排序号" align="center" />
<el-table-column :show-overflow-tooltip="true" prop="createTime" label="创建时间" />
<el-table-column v-if="checkPer(['admin', 'material:edit', 'material:del'])" label="操作" align="center"
fixed="right">
<template slot-scope="scope">
<udOperation :data="scope.row" :permission="permission" />
</template>
</el-table-column>
</el-table>
<!--分页组件-->
<pagination />
</div>
</template>
<script>
import crudMaterial from '@/api/platform/material'
import CRUD, { presenter, header, form, crud } from '@crud/crud'
import rrOperation from '@crud/RR.operation'
import udOperation from '@crud/UD.operation'
import pagination from '@crud/Pagination'
const defaultForm = { name: null, url: null, type: null, link: null, sort: null, files: [] }
export default {
name: 'Material',
components: { rrOperation, pagination, udOperation },
//
dicts: ['material_type'],
cruds() {
return CRUD({ title: '素材', url: 'api/material', crudMethod: { ...crudMaterial }, optShow: { add: true, reset: true }})
},
mixins: [presenter(), header(), form(defaultForm), crud()],
data() {
return {
permission: {
add: ['admin', 'material:add'],
edit: ['admin', 'material:edit'],
del: ['admin', 'material:del']
},
uploadDisabled: false,
dialogVisible: false,
loading: false,
dialogImageUrl: '',
rules: {
name: [
{ required: true, message: '请输入名称', trigger: 'blur' },
],
type: [
{ required: true, message: '请选择素材类型', trigger: 'change' },
],
files: [
{ required: true, message: '请上传文件', trigger: 'change' },
],
sort: [
{ required: true, message: '请输入排序号', trigger: 'blur', type: 'number' }
],
}
}
},
created() {
this.crud.data = [{ id: 1, name: '景区', type: '轮播图', url: 'https://huyun120.cn/fd/health/img/%E7%BB%84%20319@2x.f0767b46.png', link: 'http://baidu.com', sort: 1, createTime: '2020-01-01 00:00:00' },
{ id: 1, name: '景区', type: '宣传视频', url: 'https://huyun120.cn/dfs/group1/M00/03/F4/wKgKPWhbuNiATUQYAE51rnUVITc628.mp4', link: '', sort: 2, createTime: '2020-01-01 00:00:00' }
]
this.crud.resetDataStatus()
},
methods: {
//
handlePictureCardPreview(file, uploadFiles) {
this.dialogImageUrl = file.url
this.dialogVisible = true
},
//
handleRemove(file, uploadFiles) {
this.$refs['uploadRef'].clearFiles()
this.form.url = null
this.form.files = [];
this.uploadDisabled = false
console.log(this.form)
},
//
handleChange(file, uploadFiles) {
if (file.raw.type === 'image/png' || file.raw.type === 'image/jpeg' || file.raw.type === 'image/jpg' || file.raw.type === 'image/gif') {
this.loading = true
this.form.files = uploadFiles
this.uploadDisabled = true
try {
// const formdata = new FormData();
// formdata.append('file', file.raw);
// let res = await photoApi.uploadFile(formdata);
// if(res?.success){
// this.form.url = res.data.path;
this.$message.success('图片上传成功!')
this.loading = false
console.log(this.form)
// }else{
// this.$message.error('');
// }
} catch (error) {
this.loading = false
this.$message.error('图片上传失败!')
}
} else {
this.$confirm('图片的格式不正确,请重新选择!', '提示', {
confirmButtonText: '确定',
type: 'warning'
})
uploadFiles.pop()
this.uploadDisabled = false
}
},
}
}
</script>
<style scoped lang="scss">
::v-deep .el-select,::v-deep .el-input-number{
width: 100%;
}
::v-deep .el-upload--picture-card,::v-deep .el-upload-list__item{
width: 110px !important;
height: 110px !important;
display: flex;
align-items: center;
justify-content: center;
}
::v-deep .disabled{
.el-upload--picture-card{
display: none;
}
}
</style>

View File

@ -59,22 +59,33 @@
<!--表格渲染-->
<el-table ref="table" v-loading="crud.loading" :data="crud.data" style="width: 100%;">
<el-table-column :show-overflow-tooltip="true" prop="nickName" label="姓名" />
<el-table-column :show-overflow-tooltip="true" prop="gender" label="性别" />
<el-table-column :show-overflow-tooltip="true" prop="gender" label="性别">
<template slot-scope="scope">
<el-tag size="medium" v-if="Number(scope.row.gender) === 0"></el-tag>
<el-tag size="medium" v-else type="danger"></el-tag>
</template>
</el-table-column>
<el-table-column :show-overflow-tooltip="true" prop="phone" label="手机号" />
<el-table-column :show-overflow-tooltip="true" prop="userType" label="用户类型" />
<el-table-column :show-overflow-tooltip="true" prop="createTime" label="创建时间" />
<el-table-column :show-overflow-tooltip="true" prop="enable" label="用户状态" />
<el-table-column v-if="checkPer(['admin', 'customer:enable', 'customer:del'])" label="操作" width="115" align="center"
<el-table-column :show-overflow-tooltip="true" prop="enable" label="用户状态">
<template slot-scope="scope">
<el-tag size="medium" v-if="Number(scope.row.enable) === 1" type="success">启用</el-tag>
<el-tag size="medium" v-else type="danger">停用</el-tag>
</template>
</el-table-column>
<el-table-column v-if="checkPer(['admin', 'customer:enable', 'customer:del'])" label="操作" align="center"
fixed="right">
<template slot-scope="scope">
<el-button v-permission="permission.enable" size="mini" type="primary" icon="el-icon-folder" @click.stop="toEnable(scope.row)">{{ scope.row.enable ? '停用' : '启用' }}</el-button>
<el-button v-permission="permission.enable" size="mini" :type="Number(scope.row.enable) === 1 ?'info':'primary'"
@click.stop="toEnable(scope.row)">{{ Number(scope.row.enable) === 1 ? '停用' : '启用' }}</el-button>
<el-popover v-model="pop" v-permission="permission.del" placement="top" width="180" trigger="manual" @show="pop = false" @hide="pop = false">
<p>确定删除本条数据吗</p>
<div style="text-align: right; margin: 0">
<el-button size="mini" type="text" @click="pop = false;crud.cancelDelete(scope.row)">取消</el-button>
<el-button :loading="crud.dataStatus[crud.getDataId(scope.row)].delete === 2" type="primary" size="mini" @click="crud.doDelete(scope.row)">确定</el-button>
</div>
<el-button slot="reference" type="danger" icon="el-icon-delete" size="mini" @click.stop="pop = true">删除</el-button>
<el-button slot="reference" type="danger" size="mini" @click.stop="pop = true">删除</el-button>
</el-popover>
</template>
</el-table-column>
@ -123,10 +134,10 @@ export default {
],
rules: {
gender: [
{ required: true, message: '请选择性别', trigger: 'blur' },
{ required: true, message: '请选择性别', trigger: 'change' },
],
userType: [
{ required: true, message: '请选择用户类型', trigger: 'blur' },
{ required: true, message: '请选择用户类型', trigger: 'change' },
],
nickName: [
{ required: true, message: '请输入姓名', trigger: 'blur' },
@ -137,6 +148,16 @@ export default {
],
}
}
},
created() {
this.crud.data.push({ id: 1, nickName: '测试', gender: 0, phone: '12345678901', userType: '普通用户', enable: 1, createTime: '2020-01-01' })
this.crud.resetDataStatus()
},
methods: {
// /
toEnable(row){
row.enable = Number(row.enable) === 1 ? 0 : 1;
}
}
}
</script>

View File

@ -54,7 +54,8 @@
<!-- <crudOperation :permission="permission" /> -->
</div>
<!--表单渲染-->
<el-dialog append-to-body :before-close="crud.cancelCU" :visible.sync="crud.status.cu > 0" :title="crud.status.title">
<el-dialog append-to-body :before-close="crud.cancelCU" :visible.sync="crud.status.cu > 0" :title="crud.status.title"
@close="uploadDisabled = false;">
<el-form ref="form" v-loading="loading" :model="form" :rules="rules" size="small" label-width="80px">
<el-row :gutter="10">
<el-col :xs="24" :sm="24" :md="12" :lg="8" :xl="6" class="mb20">
@ -148,14 +149,14 @@
</el-form-item>
</el-col>
<el-col :xs="24" :sm="24" :md="12" :lg="8" :xl="6" class="mb20">
<el-form-item label="飞行资质附件" prop="intelligenceFile" label-width="100px">
<el-form-item label="飞行资质附件" prop="files" label-width="120px">
<el-upload
ref="uploadRef"
action="#"
list-type="picture-card"
:class="{ disabled: uploadDisabled }"
:limit="1"
:file-list="fileList"
:file-list="form.files"
:on-change="handleChange"
:auto-upload="false"
>
@ -248,7 +249,7 @@ import '@riophae/vue-treeselect/dist/vue-treeselect.css'
import { LOAD_CHILDREN_OPTIONS } from '@riophae/vue-treeselect'
let userRoles = []
let userJobs = []
const defaultForm = { id: null, username: null, nickName: null, enabled: 'false', password: null, phone: null, area: null, spot: null, role: null, intelligence: null, intelligenceFile: null, roles: [] }
const defaultForm = { id: null, username: null, nickName: null, enabled: 'false', password: null, phone: null, area: null, spot: null, role: null, intelligence: null, intelligenceFile: null, files: [], roles: [] }
export default {
name: 'User',
components: { Treeselect, crudOperation, rrOperation, udOperation, pagination, DateRangePicker },
@ -279,7 +280,6 @@ export default {
edit: ['admin', 'user:edit'],
del: ['admin', 'user:del']
},
fileList: [],
uploadDisabled: false,
dialogVisible: false,
loading: false,
@ -305,18 +305,10 @@ export default {
intelligence: [
{ required: true, message: '飞行资质不能为空', trigger: 'blur' }
],
files: [
{ required: true, message: '请上传资质文件', trigger: 'change' }
],
role: [
// {
// validator: (rule, value, callback) => {
// value = this.jobDatas
// if (!value || value.length === 0) {
// callback(new Error(''))
// } else {
// callback()
// }
// },
// trigger: 'change'
// },
{ required: true, message: '角色不能为空', trigger: 'blur' }
]
}
@ -352,6 +344,7 @@ export default {
handleRemove(file, uploadFiles) {
this.$refs['uploadRef'].clearFiles()
this.form.intelligenceFile = null
this.form.files = [];
this.uploadDisabled = false
console.log(this.form)
},
@ -359,7 +352,7 @@ export default {
handleChange(file, uploadFiles) {
if (file.raw.type === 'image/png' || file.raw.type === 'image/jpeg' || file.raw.type === 'image/jpg' || file.raw.type === 'image/gif') {
this.loading = true
this.fileList = uploadFiles
this.form.files = uploadFiles
this.uploadDisabled = true
try {
// const formdata = new FormData();
@ -530,7 +523,6 @@ export default {
changeEnabled(data, val) {
this.$confirm('此操作将 "' + this.dict.label.user_status[val] + '" ' + data.username + ', 是否继续?', '提示', {
confirmButtonText: '确定',
cancelButtonText: '取消',
type: 'warning'
}).then(() => {
crudUser.edit(data).then(res => {