首页的统计图和票据的状态分标签展示
This commit is contained in:
parent
b840ca4974
commit
f070b02da9
@ -13,8 +13,8 @@ export default mergeConfig(
|
|||||||
},
|
},
|
||||||
proxy: {
|
proxy: {
|
||||||
'/api': {
|
'/api': {
|
||||||
target: 'http://59.110.238.182:8081',
|
target: 'http://106.53.179.133:8081',
|
||||||
// target: 'http://192.168.3.158:8081',
|
// target: 'http://192.168.243.246:8081',
|
||||||
// target: 'http://localhost:5173',
|
// target: 'http://localhost:5173',
|
||||||
changeOrigin: true,
|
changeOrigin: true,
|
||||||
},
|
},
|
||||||
|
@ -3,10 +3,9 @@
|
|||||||
|
|
||||||
<head>
|
<head>
|
||||||
<meta charset="UTF-8" />
|
<meta charset="UTF-8" />
|
||||||
<link rel="shortcut icon" type="image/x-icon"
|
<link rel="icon" href="./src/image/票据服务.png" type="image/x-icon">
|
||||||
href="https://unpkg.byted-static.com/latest/byted/arco-config/assets/favicon.ico">
|
|
||||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||||
<title>中山学院学习平台</title>
|
<title>票据管理系统</title>
|
||||||
</head>
|
</head>
|
||||||
|
|
||||||
<body>
|
<body>
|
||||||
|
@ -13,10 +13,7 @@
|
|||||||
"type:check": "vue-tsc --noEmit --skipLibCheck",
|
"type:check": "vue-tsc --noEmit --skipLibCheck",
|
||||||
"lint-staged": "npx lint-staged",
|
"lint-staged": "npx lint-staged",
|
||||||
"prepare": "husky install",
|
"prepare": "husky install",
|
||||||
|
|
||||||
"start": "npm run dev"
|
"start": "npm run dev"
|
||||||
|
|
||||||
|
|
||||||
},
|
},
|
||||||
"lint-staged": {
|
"lint-staged": {
|
||||||
"*.{js,ts,jsx,tsx}": [
|
"*.{js,ts,jsx,tsx}": [
|
||||||
@ -40,6 +37,8 @@
|
|||||||
"axios": "^0.24.0",
|
"axios": "^0.24.0",
|
||||||
"dayjs": "^1.11.5",
|
"dayjs": "^1.11.5",
|
||||||
"echarts": "^5.4.0",
|
"echarts": "^5.4.0",
|
||||||
|
"exceljs": "^4.4.0",
|
||||||
|
"file-saver": "^2.0.5",
|
||||||
"lodash": "^4.17.21",
|
"lodash": "^4.17.21",
|
||||||
"mitt": "^3.0.0",
|
"mitt": "^3.0.0",
|
||||||
"nprogress": "^0.2.0",
|
"nprogress": "^0.2.0",
|
||||||
@ -50,12 +49,14 @@
|
|||||||
"vue": "^3.2.40",
|
"vue": "^3.2.40",
|
||||||
"vue-echarts": "^6.2.3",
|
"vue-echarts": "^6.2.3",
|
||||||
"vue-i18n": "^9.2.2",
|
"vue-i18n": "^9.2.2",
|
||||||
"vue-router": "^4.0.14"
|
"vue-router": "^4.0.14",
|
||||||
|
"xlsx": "^0.18.5"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@arco-plugins/vite-vue": "^1.4.5",
|
"@arco-plugins/vite-vue": "^1.4.5",
|
||||||
"@commitlint/cli": "^17.1.2",
|
"@commitlint/cli": "^17.1.2",
|
||||||
"@commitlint/config-conventional": "^17.1.0",
|
"@commitlint/config-conventional": "^17.1.0",
|
||||||
|
"@types/file-saver": "^2.0.7",
|
||||||
"@types/lodash": "^4.14.186",
|
"@types/lodash": "^4.14.186",
|
||||||
"@types/mockjs": "^1.0.7",
|
"@types/mockjs": "^1.0.7",
|
||||||
"@types/nprogress": "^0.2.0",
|
"@types/nprogress": "^0.2.0",
|
||||||
|
@ -75,10 +75,12 @@ axios.interceptors.response.use(
|
|||||||
const { response } = error;
|
const { response } = error;
|
||||||
console.log('error', error);
|
console.log('error', error);
|
||||||
|
|
||||||
if (response.status === '401') {
|
if (response.status === 401) {
|
||||||
|
|
||||||
router.push({
|
router.push({
|
||||||
name: 'login',
|
name: 'login',
|
||||||
});
|
});
|
||||||
|
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
Message.error({
|
Message.error({
|
||||||
|
@ -18,8 +18,13 @@ export interface RoleListRecord extends RoleRecord {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// 查询所有的角色列表、
|
// 查询所有的角色列表、
|
||||||
export function queryRoleList() {
|
export function queryRoleList(data: any) {
|
||||||
return axios.get('/api/rest/role');
|
// return axios.get('/api/rest/role',data);
|
||||||
|
return axios({
|
||||||
|
url: '/api/rest/role', // 路径
|
||||||
|
method: 'get',
|
||||||
|
params: data, // 参数
|
||||||
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
// 切换启用状态
|
// 切换启用状态
|
||||||
|
@ -7,7 +7,7 @@ export interface TicketCreateRecord {
|
|||||||
type: string;
|
type: string;
|
||||||
contactEmail: string;
|
contactEmail: string;
|
||||||
companyName: string;
|
companyName: string;
|
||||||
attachId: string;
|
attachId: [];
|
||||||
auditorId: string;
|
auditorId: string;
|
||||||
submit: boolean;
|
submit: boolean;
|
||||||
userId: undefined;
|
userId: undefined;
|
||||||
@ -15,6 +15,9 @@ export interface TicketCreateRecord {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export interface TicketRecord extends TicketCreateRecord {
|
export interface TicketRecord extends TicketCreateRecord {
|
||||||
|
auditor: any;
|
||||||
|
createTime(createTime: any): unknown;
|
||||||
|
deptName: any;
|
||||||
value: any;
|
value: any;
|
||||||
id: undefined;
|
id: undefined;
|
||||||
status: string
|
status: string
|
||||||
@ -83,3 +86,8 @@ export function home(data: any){
|
|||||||
params: data, // 参数
|
params: data, // 参数
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// 首页统计图
|
||||||
|
export function chart(){
|
||||||
|
return axios.get('/api/rest/bill/trend')
|
||||||
|
}
|
@ -29,6 +29,8 @@ export interface PasswordReSetModel {
|
|||||||
|
|
||||||
// 添加用户数据
|
// 添加用户数据
|
||||||
export interface CreateRecord {
|
export interface CreateRecord {
|
||||||
|
value: any;
|
||||||
|
code: any;
|
||||||
|
|
||||||
username: string;
|
username: string;
|
||||||
nickName: string;
|
nickName: string;
|
||||||
@ -107,10 +109,15 @@ export function resetPassword(data: PasswordReSetModel) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// 注册用户
|
// 注册用户
|
||||||
export function create(data: CreateRecord) {
|
export function register(data: CreateRecord) {
|
||||||
return axios.post('/api/rest/user/register', data);
|
return axios.post('/api/rest/user/register', data);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// 新建用户
|
||||||
|
export function create(data: CreateRecord) {
|
||||||
|
return axios.post('/api/rest/user', data);
|
||||||
|
}
|
||||||
|
|
||||||
// 模糊查询用户列表
|
// 模糊查询用户列表
|
||||||
export function queryUserList(params: any) {
|
export function queryUserList(params: any) {
|
||||||
return axios({
|
return axios({
|
||||||
@ -158,6 +165,11 @@ export function deptAudit(id: string,roleId:string){
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// 获取验证码
|
||||||
|
export function code(data: string){
|
||||||
|
return axios.get(`/api/rest/user/send-email?email=${data}`);
|
||||||
|
}
|
||||||
|
|
||||||
export function switchRole(roleId: number) {
|
export function switchRole(roleId: number) {
|
||||||
return axios.patch<UserState>(`/api/user/self/switch-role/${roleId}`);
|
return axios.patch<UserState>(`/api/user/self/switch-role/${roleId}`);
|
||||||
}
|
}
|
||||||
|
@ -1,16 +1,16 @@
|
|||||||
<template>
|
<template>
|
||||||
<a-layout-footer class="footer">Arco Pro</a-layout-footer>
|
<a-layout-footer class="footer"></a-layout-footer>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
<script lang="ts" setup></script>
|
<script lang="ts" setup></script>
|
||||||
|
|
||||||
<style lang="less" scoped>
|
<style lang="less" scoped>
|
||||||
.footer {
|
.footer {
|
||||||
display: flex;
|
display: flex;
|
||||||
align-items: center;
|
align-items: center;
|
||||||
justify-content: center;
|
justify-content: center;
|
||||||
height: 40px;
|
height: 40px;
|
||||||
color: var(--color-text-2);
|
color: var(--color-text-2);
|
||||||
text-align: center;
|
text-align: center;
|
||||||
}
|
}
|
||||||
</style>
|
</style>
|
||||||
|
@ -2,10 +2,7 @@
|
|||||||
<div class="navbar">
|
<div class="navbar">
|
||||||
<div class="left-side">
|
<div class="left-side">
|
||||||
<a-space>
|
<a-space>
|
||||||
<img
|
<img style="height: 24px" alt="logo" src="../../image/票据服务.png" />
|
||||||
alt="logo"
|
|
||||||
src="//p3-armor.byteimg.com/tos-cn-i-49unhts6dw/dfdba5317c0c20ce20e64fac803d52bc.svg~tplv-49unhts6dw-image.image"
|
|
||||||
/>
|
|
||||||
<a-typography-title
|
<a-typography-title
|
||||||
:style="{ margin: 0, fontSize: '18px' }"
|
:style="{ margin: 0, fontSize: '18px' }"
|
||||||
:heading="5"
|
:heading="5"
|
||||||
@ -112,6 +109,9 @@
|
|||||||
|
|
||||||
<li>
|
<li>
|
||||||
<a-dropdown trigger="click">
|
<a-dropdown trigger="click">
|
||||||
|
<a-button style="margin-right: 20px" status="normal">{{
|
||||||
|
userStore.nickName
|
||||||
|
}}</a-button>
|
||||||
<a-avatar
|
<a-avatar
|
||||||
:size="32"
|
:size="32"
|
||||||
:style="{ marginRight: '8px', cursor: 'pointer' }"
|
:style="{ marginRight: '8px', cursor: 'pointer' }"
|
||||||
|
@ -8,7 +8,7 @@
|
|||||||
"menuCollapse": false,
|
"menuCollapse": false,
|
||||||
"footer": true,
|
"footer": true,
|
||||||
"themeColor": "#165DFF",
|
"themeColor": "#165DFF",
|
||||||
"menuWidth": 220,
|
"menuWidth": 200,
|
||||||
"globalSettings": false,
|
"globalSettings": false,
|
||||||
"device": "desktop",
|
"device": "desktop",
|
||||||
"tabBar": false,
|
"tabBar": false,
|
||||||
|
BIN
src/image/票据服务.png
Normal file
BIN
src/image/票据服务.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 3.0 KiB |
@ -9,7 +9,7 @@ const SYSTEM: AppRouteRecordRaw = {
|
|||||||
locale: 'menu.system',
|
locale: 'menu.system',
|
||||||
icon: 'icon-computer',
|
icon: 'icon-computer',
|
||||||
requiresAuth: true,
|
requiresAuth: true,
|
||||||
order: 1,
|
order: 2,
|
||||||
},
|
},
|
||||||
children: [
|
children: [
|
||||||
// {
|
// {
|
||||||
|
@ -9,7 +9,7 @@ const TICKET: AppRouteRecordRaw = {
|
|||||||
locale: 'menu.ticket',
|
locale: 'menu.ticket',
|
||||||
icon: 'icon-folder-add',
|
icon: 'icon-folder-add',
|
||||||
requiresAuth: true,
|
requiresAuth: true,
|
||||||
order: 4,
|
order: 1,
|
||||||
},
|
},
|
||||||
children: [
|
children: [
|
||||||
{
|
{
|
||||||
|
@ -9,7 +9,7 @@ const USER: AppRouteRecordRaw = {
|
|||||||
locale: 'menu.user',
|
locale: 'menu.user',
|
||||||
icon: 'icon-user',
|
icon: 'icon-user',
|
||||||
requiresAuth: true,
|
requiresAuth: true,
|
||||||
order: 7,
|
order: 3,
|
||||||
},
|
},
|
||||||
children: [
|
children: [
|
||||||
// {
|
// {
|
||||||
|
@ -27,8 +27,8 @@ const useRoleStore = defineStore('role', {
|
|||||||
},
|
},
|
||||||
actions: {
|
actions: {
|
||||||
// 获取所有的角色列表
|
// 获取所有的角色列表
|
||||||
async getRoleList() {
|
async getRoleList(params: any) {
|
||||||
return queryRoleList();
|
return queryRoleList(params);
|
||||||
},
|
},
|
||||||
|
|
||||||
async enabledRole(id: string) {
|
async enabledRole(id: string) {
|
||||||
|
@ -11,7 +11,8 @@ import {
|
|||||||
audit,
|
audit,
|
||||||
uploadFile,
|
uploadFile,
|
||||||
attachment,
|
attachment,
|
||||||
home
|
home,
|
||||||
|
chart,
|
||||||
} from '@/api/ticket';
|
} from '@/api/ticket';
|
||||||
import { ticketStore } from './type';
|
import { ticketStore } from './type';
|
||||||
|
|
||||||
@ -61,7 +62,7 @@ const useTicketStore = defineStore('ticket', {
|
|||||||
return update(data);
|
return update(data);
|
||||||
},
|
},
|
||||||
|
|
||||||
async uploadFileTicket(file: any) {
|
async uploadFile(file: any) {
|
||||||
return uploadFile(file);
|
return uploadFile(file);
|
||||||
},
|
},
|
||||||
|
|
||||||
@ -75,7 +76,11 @@ const useTicketStore = defineStore('ticket', {
|
|||||||
|
|
||||||
async getHome(data: any){
|
async getHome(data: any){
|
||||||
return home(data);
|
return home(data);
|
||||||
}
|
},
|
||||||
|
|
||||||
|
async getChart(){
|
||||||
|
return chart();
|
||||||
|
},
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -10,10 +10,12 @@ import {
|
|||||||
enabled,
|
enabled,
|
||||||
remove,
|
remove,
|
||||||
create,
|
create,
|
||||||
|
register,
|
||||||
UserRecord,
|
UserRecord,
|
||||||
update,
|
update,
|
||||||
userDetail,
|
userDetail,
|
||||||
deptAudit
|
deptAudit,
|
||||||
|
code
|
||||||
} from '@/api/user';
|
} from '@/api/user';
|
||||||
import { setToken, clearToken } from '@/utils/auth';
|
import { setToken, clearToken } from '@/utils/auth';
|
||||||
import { removeRouteListener } from '@/utils/route-listener';
|
import { removeRouteListener } from '@/utils/route-listener';
|
||||||
@ -92,11 +94,16 @@ const useUserStore = defineStore('user', {
|
|||||||
return remove(id);
|
return remove(id);
|
||||||
},
|
},
|
||||||
|
|
||||||
// Register user
|
// Create user
|
||||||
async createUser(data: UserRecord) {
|
async createUser(data: UserRecord) {
|
||||||
return create(data);
|
return create(data);
|
||||||
},
|
},
|
||||||
|
|
||||||
|
// register user
|
||||||
|
async registerUser(data: UserRecord) {
|
||||||
|
return register(data);
|
||||||
|
},
|
||||||
|
|
||||||
// Update user
|
// Update user
|
||||||
async updateUser(data: UserRecord) {
|
async updateUser(data: UserRecord) {
|
||||||
return update(data);
|
return update(data);
|
||||||
@ -110,6 +117,10 @@ const useUserStore = defineStore('user', {
|
|||||||
return deptAudit(deptId,roleId)
|
return deptAudit(deptId,roleId)
|
||||||
},
|
},
|
||||||
|
|
||||||
|
async getCode(params: string){
|
||||||
|
return code(params)
|
||||||
|
},
|
||||||
|
|
||||||
logoutCallBack() {
|
logoutCallBack() {
|
||||||
const appStore = useAppStore();
|
const appStore = useAppStore();
|
||||||
this.resetInfo();
|
this.resetInfo();
|
||||||
|
@ -26,6 +26,8 @@ export interface PostData {
|
|||||||
export interface Pagination {
|
export interface Pagination {
|
||||||
page: number;
|
page: number;
|
||||||
size: number;
|
size: number;
|
||||||
|
current: number;
|
||||||
|
total: null | number;
|
||||||
}
|
}
|
||||||
|
|
||||||
export type TimeRanger = [string, string];
|
export type TimeRanger = [string, string];
|
||||||
|
69
src/utils/excel.ts
Normal file
69
src/utils/excel.ts
Normal file
@ -0,0 +1,69 @@
|
|||||||
|
// 新建 @/utils/excel.ts
|
||||||
|
|
||||||
|
import saveAs from 'file-saver'; // https://www.npmjs.com/package/file-saver
|
||||||
|
import ExcelJS from 'exceljs'; // https://github.com/exceljs/exceljs/blob/master/README_zh.md
|
||||||
|
import dayjs from 'dayjs'; // https://dayjs.fenxianglu.cn/
|
||||||
|
import * as XLSX from 'xlsx'; // https://www.npmjs.com/package/xlsx
|
||||||
|
import { Message } from '@arco-design/web-vue'; // https://arco.design/vue/component/message
|
||||||
|
import { FileItem } from '@arco-design/web-vue/es/upload/interfaces'; // arco类型
|
||||||
|
|
||||||
|
export interface DownloadExcelPrams {
|
||||||
|
columns: { title: string, key: string }[];
|
||||||
|
rows: object[];
|
||||||
|
name: string
|
||||||
|
}
|
||||||
|
|
||||||
|
// 导出下载文件
|
||||||
|
export function downloadExcel({ columns, rows, name = '未命名文件' }: DownloadExcelPrams) {
|
||||||
|
|
||||||
|
const workbook = new ExcelJS.Workbook();
|
||||||
|
workbook.creator = 'Start-front';
|
||||||
|
workbook.lastModifiedBy = 'Start-front';
|
||||||
|
workbook.created = new Date(1985, 8, 30);
|
||||||
|
workbook.modified = new Date();
|
||||||
|
workbook.lastPrinted = new Date(2016, 9, 27);
|
||||||
|
|
||||||
|
// 将工作簿添加一个sheet页sheet1
|
||||||
|
const sheet1 = workbook.addWorksheet(name);
|
||||||
|
// 表头数据添加
|
||||||
|
sheet1.columns = columns.map(item => ({
|
||||||
|
header: item.title,
|
||||||
|
key: item.key,
|
||||||
|
width: 20
|
||||||
|
}));
|
||||||
|
// 表格内容添加
|
||||||
|
rows.map(item => sheet1.addRow(item));
|
||||||
|
workbook.xlsx.writeBuffer().then(buffer => {
|
||||||
|
saveAs(
|
||||||
|
new Blob([buffer], { type: 'application/octet-stream' }),
|
||||||
|
`${name}.xlsx`
|
||||||
|
);
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
// 读取文件为json格式
|
||||||
|
export function readExcle(fileItem:FileItem) {
|
||||||
|
console.log('读取文件...',fileItem);
|
||||||
|
return new Promise((resove,reject)=>{
|
||||||
|
try {
|
||||||
|
let workbook:XLSX.Sheet;
|
||||||
|
const reader = new FileReader();
|
||||||
|
reader.readAsBinaryString(fileItem.file as File); // 发起异步请求
|
||||||
|
reader.onload = function(ev){
|
||||||
|
const data = ev.target?.result;
|
||||||
|
workbook = XLSX.read(data, {type: 'binary'});
|
||||||
|
const sheetNames = workbook.SheetNames; // 工作表名称集合
|
||||||
|
sheetNames.forEach((name:string) => {
|
||||||
|
const worksheet = workbook.Sheets[name]; // 只能通过工作表名称来获取指定工作表
|
||||||
|
const jsonres = XLSX.utils.sheet_to_json(worksheet);
|
||||||
|
resove(jsonres)
|
||||||
|
});
|
||||||
|
} // onload
|
||||||
|
} catch (error) {
|
||||||
|
Message.error('读取失败,请选择正确文件');
|
||||||
|
reject(error);
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
@ -1,4 +1,5 @@
|
|||||||
<template>
|
<template>
|
||||||
|
<div style="width: 100%">
|
||||||
<a-grid :cols="24" :row-gap="16" class="panel">
|
<a-grid :cols="24" :row-gap="16" class="panel">
|
||||||
<a-grid-item
|
<a-grid-item
|
||||||
class="panel-col"
|
class="panel-col"
|
||||||
@ -103,12 +104,19 @@
|
|||||||
<a-divider class="panel-border" />
|
<a-divider class="panel-border" />
|
||||||
</a-grid-item>
|
</a-grid-item>
|
||||||
</a-grid>
|
</a-grid>
|
||||||
|
<a-card :bordered="false" v-if="userStore.permissions === 'admin'">
|
||||||
|
<a-space id="TicketEcharts" style="width: 98%; height: 400px"></a-space>
|
||||||
|
</a-card>
|
||||||
|
</div>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
<script lang="ts" setup>
|
<script lang="ts" setup>
|
||||||
|
import { useI18n } from 'vue-i18n';
|
||||||
import { useTicketStore, useUserStore } from '@/store';
|
import { useTicketStore, useUserStore } from '@/store';
|
||||||
import { ref } from 'vue';
|
import { onMounted, ref } from 'vue';
|
||||||
|
import * as echarts from 'echarts';
|
||||||
|
|
||||||
|
const { t } = useI18n();
|
||||||
const ticketStore = useTicketStore();
|
const ticketStore = useTicketStore();
|
||||||
const userStore = useUserStore();
|
const userStore = useUserStore();
|
||||||
const formData = ref({
|
const formData = ref({
|
||||||
@ -118,6 +126,72 @@ const formData = ref({
|
|||||||
pass: undefined,
|
pass: undefined,
|
||||||
});
|
});
|
||||||
|
|
||||||
|
const getEchartData = () => {
|
||||||
|
const res = ticketStore.getChart();
|
||||||
|
console.log('chart', res);
|
||||||
|
};
|
||||||
|
|
||||||
|
onMounted(async () => {
|
||||||
|
const res = await ticketStore.getChart();
|
||||||
|
console.log('chart', res.data);
|
||||||
|
type EChartsOption = echarts.EChartsOption;
|
||||||
|
const chartDom = document.getElementById('TicketEcharts');
|
||||||
|
const myChart = echarts.init(chartDom);
|
||||||
|
const option = {
|
||||||
|
title: {
|
||||||
|
text: t('workplace.chart'),
|
||||||
|
},
|
||||||
|
tooltip: {
|
||||||
|
trigger: 'axis',
|
||||||
|
},
|
||||||
|
legend: {
|
||||||
|
data: [
|
||||||
|
t('workplace.pass'),
|
||||||
|
t('workplace.notPass'),
|
||||||
|
t('workplace.notAudit'),
|
||||||
|
],
|
||||||
|
},
|
||||||
|
grid: {
|
||||||
|
left: '3%',
|
||||||
|
right: '4%',
|
||||||
|
bottom: '3%',
|
||||||
|
containLabel: true,
|
||||||
|
},
|
||||||
|
toolbox: {
|
||||||
|
feature: {
|
||||||
|
saveAsImage: {},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
xAxis: {
|
||||||
|
type: 'category',
|
||||||
|
boundaryGap: false,
|
||||||
|
data: res.data.dates,
|
||||||
|
},
|
||||||
|
yAxis: {
|
||||||
|
type: 'value',
|
||||||
|
},
|
||||||
|
series: [
|
||||||
|
{
|
||||||
|
name: t('workplace.pass'),
|
||||||
|
type: 'line',
|
||||||
|
data: res.data.status2Counts,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: t('workplace.notPass'),
|
||||||
|
type: 'line',
|
||||||
|
data: res.data.status3Counts,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: t('workplace.notAudit'),
|
||||||
|
type: 'line',
|
||||||
|
data: res.data.status1Counts,
|
||||||
|
},
|
||||||
|
],
|
||||||
|
};
|
||||||
|
|
||||||
|
myChart.setOption(option);
|
||||||
|
});
|
||||||
|
|
||||||
const getHomeData = async (params: {
|
const getHomeData = async (params: {
|
||||||
auditorId: number | undefined;
|
auditorId: number | undefined;
|
||||||
userId: number | string | undefined;
|
userId: number | string | undefined;
|
||||||
|
@ -40,4 +40,6 @@ export default {
|
|||||||
'workplace.notPass': 'notPass',
|
'workplace.notPass': 'notPass',
|
||||||
'workplace.notAudit': 'notAudit',
|
'workplace.notAudit': 'notAudit',
|
||||||
'workplace.notFiled': 'notFiled',
|
'workplace.notFiled': 'notFiled',
|
||||||
|
'workplace.total': 'total',
|
||||||
|
'workplace.chart':' Ticket Chart'
|
||||||
};
|
};
|
||||||
|
@ -38,4 +38,6 @@ export default {
|
|||||||
'workplace.notPass': '审核不通过',
|
'workplace.notPass': '审核不通过',
|
||||||
'workplace.notAudit': '待审核',
|
'workplace.notAudit': '待审核',
|
||||||
'workplace.notFiled': '待提交',
|
'workplace.notFiled': '待提交',
|
||||||
|
'workplace.total': '票据总数',
|
||||||
|
'workplace.chart':'票据分析图'
|
||||||
};
|
};
|
||||||
|
@ -94,6 +94,40 @@
|
|||||||
:placeholder="$t('user.info.username.placeholder')"
|
:placeholder="$t('user.info.username.placeholder')"
|
||||||
/>
|
/>
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
|
|
||||||
|
<a-form-item
|
||||||
|
field="email"
|
||||||
|
:label="$t('user.info.email')"
|
||||||
|
:rules="[
|
||||||
|
{
|
||||||
|
required: true,
|
||||||
|
type: 'email',
|
||||||
|
message: t('user.info.email.required'),
|
||||||
|
},
|
||||||
|
]"
|
||||||
|
:validate-trigger="['change', 'input']"
|
||||||
|
>
|
||||||
|
<a-input
|
||||||
|
v-model="formData.email"
|
||||||
|
:placeholder="$t('user.info.emailCode.placeholder')"
|
||||||
|
/>
|
||||||
|
</a-form-item>
|
||||||
|
|
||||||
|
<a-form-item
|
||||||
|
field="phone"
|
||||||
|
:label="$t('user.info.phone')"
|
||||||
|
:rules="[
|
||||||
|
{ required: true, message: t('user.info.phone.required') },
|
||||||
|
{ match: /^1[3-9]\d{9}$/, message: t('user.info.phone.format') },
|
||||||
|
]"
|
||||||
|
:validate-trigger="['change', 'input']"
|
||||||
|
>
|
||||||
|
<a-input
|
||||||
|
v-model="formData.phone"
|
||||||
|
:placeholder="$t('user.info.phone.placeholder')"
|
||||||
|
/>
|
||||||
|
</a-form-item>
|
||||||
|
|
||||||
<a-form-item
|
<a-form-item
|
||||||
field="password"
|
field="password"
|
||||||
:label="$t('user.info.password')"
|
:label="$t('user.info.password')"
|
||||||
@ -111,43 +145,37 @@
|
|||||||
:placeholder="$t('user.info.nickName.placeholder')"
|
:placeholder="$t('user.info.nickName.placeholder')"
|
||||||
/>
|
/>
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
<a-form-item
|
|
||||||
field="phone"
|
|
||||||
:label="$t('user.info.phone')"
|
|
||||||
:rules="[
|
|
||||||
{ required: true, message: t('user.info.phone.required') },
|
|
||||||
{ match: /^1[3-9]\d{9}$/, message: t('user.info.phone.format') },
|
|
||||||
]"
|
|
||||||
:validate-trigger="['change', 'input']"
|
|
||||||
>
|
|
||||||
<a-input
|
|
||||||
v-model="formData.phone"
|
|
||||||
:placeholder="$t('user.info.phone.placeholder')"
|
|
||||||
/>
|
|
||||||
</a-form-item>
|
|
||||||
<a-form-item
|
|
||||||
field="email"
|
|
||||||
:label="$t('user.info.email')"
|
|
||||||
:rules="[
|
|
||||||
{
|
|
||||||
required: true,
|
|
||||||
type: 'email',
|
|
||||||
message: t('user.info.email.required'),
|
|
||||||
},
|
|
||||||
]"
|
|
||||||
:validate-trigger="['change', 'input']"
|
|
||||||
>
|
|
||||||
<a-input
|
|
||||||
v-model="formData.email"
|
|
||||||
:placeholder="$t('user.info.email.placeholder')"
|
|
||||||
/>
|
|
||||||
</a-form-item>
|
|
||||||
<a-form-item field="address" :label="$t('user.info.address')">
|
<a-form-item field="address" :label="$t('user.info.address')">
|
||||||
<a-input
|
<a-input
|
||||||
v-model="formData.address"
|
v-model="formData.address"
|
||||||
:placeholder="$t('user.info.address.placeholder')"
|
:placeholder="$t('user.info.address.placeholder')"
|
||||||
/>
|
/>
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
|
<a-form-item
|
||||||
|
field="code"
|
||||||
|
:label="$t('user.info.code')"
|
||||||
|
:rules="[
|
||||||
|
{
|
||||||
|
required: true,
|
||||||
|
message: t('user.info.code.required'),
|
||||||
|
},
|
||||||
|
]"
|
||||||
|
:validate-trigger="['change', 'input']"
|
||||||
|
>
|
||||||
|
<a-input
|
||||||
|
v-model="formData.code"
|
||||||
|
:placeholder="$t('user.info.code.placeholder')"
|
||||||
|
/>
|
||||||
|
<a-button
|
||||||
|
type="primary"
|
||||||
|
style="margin-left: 50px; margin-right: 50px"
|
||||||
|
@click="getCodeData"
|
||||||
|
:disabled="flag"
|
||||||
|
>发送验证码
|
||||||
|
<div v-if="flag">({{ totalCount }}s)</div>
|
||||||
|
</a-button>
|
||||||
|
</a-form-item>
|
||||||
</a-form>
|
</a-form>
|
||||||
</a-modal>
|
</a-modal>
|
||||||
</template>
|
</template>
|
||||||
@ -179,19 +207,22 @@ const formData = ref<CreateRecord>({
|
|||||||
nickName: '',
|
nickName: '',
|
||||||
password: '',
|
password: '',
|
||||||
phone: '',
|
phone: '',
|
||||||
email: '',
|
email: '@qq.com',
|
||||||
enabled: 'true',
|
enabled: 'true',
|
||||||
address: '',
|
address: '',
|
||||||
deptId: 235,
|
deptId: 235,
|
||||||
roleId: undefined,
|
roleId: undefined,
|
||||||
permissionIds: [],
|
permissionIds: [],
|
||||||
authorities: [],
|
authorities: [],
|
||||||
|
code: '',
|
||||||
});
|
});
|
||||||
|
|
||||||
|
const flag = ref(false);
|
||||||
|
const totalCount = ref(60);
|
||||||
const deptOptions = ref();
|
const deptOptions = ref();
|
||||||
const getDeptData = async () => {
|
const getDeptData = async () => {
|
||||||
const res = await deptList();
|
const res = await deptList();
|
||||||
deptOptions.value = res.data;
|
deptOptions.value = res.data.records;
|
||||||
};
|
};
|
||||||
|
|
||||||
const loginConfig = useStorage('login-config', {
|
const loginConfig = useStorage('login-config', {
|
||||||
@ -207,6 +238,7 @@ const userInfo = reactive({
|
|||||||
password: loginConfig.value.password,
|
password: loginConfig.value.password,
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// 登录
|
||||||
const handleSubmit = async ({
|
const handleSubmit = async ({
|
||||||
// 处理表单提交的异步函数
|
// 处理表单提交的异步函数
|
||||||
errors,
|
errors,
|
||||||
@ -253,23 +285,53 @@ const handleSubmit = async ({
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// 记住密码
|
||||||
const setRememberPassword = (value: boolean) => {
|
const setRememberPassword = (value: boolean) => {
|
||||||
loginConfig.value.rememberPassword = value;
|
loginConfig.value.rememberPassword = value;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// 打开弹窗
|
||||||
const handleClick = () => {
|
const handleClick = () => {
|
||||||
setVisible(true);
|
setVisible(true);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// 关闭弹窗
|
||||||
const handleCancel = async () => {
|
const handleCancel = async () => {
|
||||||
userCreateRef.value?.resetFields();
|
userCreateRef.value?.resetFields();
|
||||||
setVisible(false);
|
setVisible(false);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// 获取验证码
|
||||||
|
const getCodeData = async () => {
|
||||||
|
if (formData.value.email === '') {
|
||||||
|
Message.error({
|
||||||
|
content: t('user.info.email.required'),
|
||||||
|
duration: 5 * 1000,
|
||||||
|
});
|
||||||
|
} else {
|
||||||
|
const res = await userStore.getCode(formData.value.email);
|
||||||
|
if (res.status === 200) {
|
||||||
|
flag.value = true;
|
||||||
|
setInterval(() => {
|
||||||
|
if (totalCount.value !== 0) {
|
||||||
|
totalCount.value = totalCount.value * 1 - 1;
|
||||||
|
}
|
||||||
|
}, 1000);
|
||||||
|
setTimeout(() => {
|
||||||
|
flag.value = false;
|
||||||
|
totalCount.value = 60;
|
||||||
|
}, 60000);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
// 提交注册
|
||||||
const handleOk = async () => {
|
const handleOk = async () => {
|
||||||
const valid = await userCreateRef.value?.validate();
|
const valid = await userCreateRef.value?.validate();
|
||||||
if (!valid) {
|
if (!valid) {
|
||||||
const res = await userStore.createUser(formData.value);
|
// formData.value.username = formData.value.email;
|
||||||
|
const res = await userStore.registerUser(formData.value);
|
||||||
if (res.status === 200) {
|
if (res.status === 200) {
|
||||||
Message.success({
|
Message.success({
|
||||||
content: t('create.sucess'),
|
content: t('create.sucess'),
|
||||||
|
@ -1,32 +1,24 @@
|
|||||||
<template>
|
<template>
|
||||||
<div class="container">
|
<div class="container">
|
||||||
<div class="logo">
|
<div class="logo">
|
||||||
<img
|
<div class="logo-text">Hello Ticket!</div>
|
||||||
alt="logo"
|
|
||||||
src="//p3-armor.byteimg.com/tos-cn-i-49unhts6dw/dfdba5317c0c20ce20e64fac803d52bc.svg~tplv-49unhts6dw-image.image"
|
|
||||||
/>
|
|
||||||
<div class="logo-text">Hello World!</div>
|
|
||||||
</div>
|
</div>
|
||||||
<LoginBanner />
|
<LoginBanner />
|
||||||
<div class="content">
|
<div class="content">
|
||||||
<div class="content-inner">
|
<div class="content-inner">
|
||||||
<LoginForm />
|
<LoginForm />
|
||||||
</div>
|
</div>
|
||||||
<div class="footer">
|
|
||||||
<Footer />
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
<script lang="ts" setup>
|
<script lang="ts" setup>
|
||||||
import Footer from '@/components/footer/index.vue';
|
import LoginBanner from './components/banner.vue';
|
||||||
import LoginBanner from './components/banner.vue';
|
import LoginForm from './components/login-form.vue';
|
||||||
import LoginForm from './components/login-form.vue';
|
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<style lang="less" scoped>
|
<style lang="less" scoped>
|
||||||
.container {
|
.container {
|
||||||
display: flex;
|
display: flex;
|
||||||
height: 100vh;
|
height: 100vh;
|
||||||
|
|
||||||
@ -50,9 +42,9 @@
|
|||||||
bottom: 0;
|
bottom: 0;
|
||||||
width: 100%;
|
width: 100%;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
.logo {
|
.logo {
|
||||||
position: fixed;
|
position: fixed;
|
||||||
top: 24px;
|
top: 24px;
|
||||||
left: 22px;
|
left: 22px;
|
||||||
@ -66,16 +58,16 @@
|
|||||||
color: var(--color-fill-1);
|
color: var(--color-fill-1);
|
||||||
font-size: 20px;
|
font-size: 20px;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
</style>
|
</style>
|
||||||
|
|
||||||
<style lang="less" scoped>
|
<style lang="less" scoped>
|
||||||
// responsive
|
// responsive
|
||||||
@media (max-width: @screen-lg) {
|
@media (max-width: @screen-lg) {
|
||||||
.container {
|
.container {
|
||||||
.banner {
|
.banner {
|
||||||
width: 25%;
|
width: 25%;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
</style>
|
</style>
|
||||||
|
@ -1,11 +1,11 @@
|
|||||||
export default {
|
export default {
|
||||||
'login.form.title': 'ZSC Learning Platform',
|
'login.form.title': 'ZSC Learning Platform',
|
||||||
'login.form.userName.errMsg': 'Username cannot be empty',
|
'login.form.userName.errMsg': 'Username cannot be empty(Email)',
|
||||||
'login.form.password.errMsg': 'Password cannot be empty',
|
'login.form.password.errMsg': 'Password cannot be empty',
|
||||||
'login.form.login.errMsg': 'Login error, refresh and try again',
|
'login.form.login.errMsg': 'Login error, refresh and try again',
|
||||||
'login.form.login.success': 'welcome to use',
|
'login.form.login.success': 'welcome to use',
|
||||||
'login.form.userName.placeholder': 'Username: admin',
|
'login.form.userName.placeholder': 'Username(Email)',
|
||||||
'login.form.password.placeholder': 'Password: admin',
|
'login.form.password.placeholder': 'Password',
|
||||||
'login.form.rememberPassword': 'Remember password',
|
'login.form.rememberPassword': 'Remember password',
|
||||||
'login.form.forgetPassword': 'Forgot password',
|
'login.form.forgetPassword': 'Forgot password',
|
||||||
'login.form.login': 'login',
|
'login.form.login': 'login',
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
export default {
|
export default {
|
||||||
'login.form.title': '中山学院学习平台',
|
'login.form.title': '票据管理系统',
|
||||||
'login.form.userName.errMsg': '用户名不能为空',
|
'login.form.userName.errMsg': '账号不能为空',
|
||||||
'login.form.password.errMsg': '密码不能为空',
|
'login.form.password.errMsg': '密码不能为空',
|
||||||
'login.form.login.errMsg': '登录出错,请刷新重试',
|
'login.form.login.errMsg': '登录出错,请刷新重试',
|
||||||
'login.form.login.success': '欢迎使用',
|
'login.form.login.success': '欢迎使用',
|
||||||
@ -10,11 +10,15 @@ export default {
|
|||||||
'login.form.forgetPassword': '忘记密码',
|
'login.form.forgetPassword': '忘记密码',
|
||||||
'login.form.login': '登录',
|
'login.form.login': '登录',
|
||||||
'login.form.register': '注册账号',
|
'login.form.register': '注册账号',
|
||||||
'login.banner.slogan1': '开箱即用的高质量模板',
|
|
||||||
'login.banner.subSlogan1': '丰富的的页面模板,覆盖大多数典型业务场景',
|
'login.banner.slogan1': '数据查询',
|
||||||
'login.banner.slogan2': '内置了常见问题的解决方案',
|
'login.banner.subSlogan1': '用户可以通过关键词、条件组合等方式进行快速查询和检索',
|
||||||
'login.banner.subSlogan2': '国际化,路由配置,状态管理应有尽有',
|
'login.banner.slogan2': '数据存储',
|
||||||
'login.banner.slogan3': '接入可视化增强工具AUX',
|
'login.banner.subSlogan2': '系统具备强大的数据存储功能,能够将海量数据存储在数据库中',
|
||||||
'login.banner.subSlogan3': '实现灵活的区块式开发',
|
'login.banner.slogan3': '数据输出',
|
||||||
'create.user': '注册用户'
|
'login.banner.subSlogan3': '系统可以将查询和分析结果以表格和图表导出',
|
||||||
|
|
||||||
|
'create.user': '注册用户',
|
||||||
|
'user.info.emailCode.placeholder':'请输入Email(用于获取验证码)',
|
||||||
|
'user.info.email.required':'Email不能为空',
|
||||||
};
|
};
|
||||||
|
@ -1,25 +1,26 @@
|
|||||||
<template>
|
<template>
|
||||||
<a-button v-if="props.isCreate" type="primary" @click="handleClick">
|
<a-button v-if="props.isCreate" type="primary" @click="handleClick">
|
||||||
<template #icon><icon-plus /></template>
|
<template #icon><icon-plus /></template>
|
||||||
{{ modalTitle }}
|
{{ t('create') }}
|
||||||
</a-button>
|
</a-button>
|
||||||
<a-button
|
<a-button
|
||||||
v-if="!props.isCreate"
|
v-if="!props.isCreate"
|
||||||
type="outline"
|
type="outline"
|
||||||
size="small"
|
size="small"
|
||||||
:style="{ marginRight: '10px' }"
|
:style="{ marginRight: '10px', padding: '7px' }"
|
||||||
@click="handleClick"
|
@click="handleClick"
|
||||||
>
|
>
|
||||||
{{ modalTitle }}
|
<template #icon><icon-edit /></template>
|
||||||
|
{{ t('edit') }}
|
||||||
</a-button>
|
</a-button>
|
||||||
<a-modal
|
<a-modal
|
||||||
width="600px"
|
width="700px"
|
||||||
:visible="visible"
|
:visible="visible"
|
||||||
@ok="handleSubmit"
|
@ok="handleSubmit"
|
||||||
@cancel="handleCancel"
|
@cancel="handleCancel"
|
||||||
>
|
>
|
||||||
<template #title>{{ modalTitle }}</template>
|
<template #title>{{ modalTitle }}</template>
|
||||||
<a-form ref="createEditRef" :model="formData" :style="{ width: '500px' }">
|
<a-form ref="createEditRef" :model="formData" :style="{ width: '650px' }">
|
||||||
<a-form-item
|
<a-form-item
|
||||||
field="name"
|
field="name"
|
||||||
:label="$t('dept.info.name')"
|
:label="$t('dept.info.name')"
|
||||||
@ -35,6 +36,7 @@
|
|||||||
<a-textarea
|
<a-textarea
|
||||||
v-model="formData.remark"
|
v-model="formData.remark"
|
||||||
:placeholder="$t('dept.info.remark.placeholder')"
|
:placeholder="$t('dept.info.remark.placeholder')"
|
||||||
|
style="height: 100px"
|
||||||
/>
|
/>
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
</a-form>
|
</a-form>
|
||||||
@ -58,7 +60,7 @@ const props = defineProps({
|
|||||||
});
|
});
|
||||||
const { t } = useI18n();
|
const { t } = useI18n();
|
||||||
const modalTitle = computed(() => {
|
const modalTitle = computed(() => {
|
||||||
return props.isCreate ? t('create') : t('edit');
|
return props.isCreate ? t('createDept') : t('editDept');
|
||||||
});
|
});
|
||||||
const { visible, setVisible } = useVisible(false);
|
const { visible, setVisible } = useVisible(false);
|
||||||
const deptStore = useDeptStore();
|
const deptStore = useDeptStore();
|
||||||
|
@ -1,13 +1,13 @@
|
|||||||
<template>
|
<template>
|
||||||
<div class="container">
|
<div class="container">
|
||||||
<Breadcrumb :items="['menu.system', 'menu.system.dept']" />
|
<Breadcrumb :items="['menu.system', 'menu.system.dept']" />
|
||||||
<a-card class="general-card" :title="$t('menu.list.searchTable')">
|
<a-card class="general-card" title=" ">
|
||||||
<a-row>
|
<a-row>
|
||||||
<a-col :flex="1">
|
<a-col :flex="1">
|
||||||
<a-form
|
<a-form
|
||||||
:model="formModel"
|
:model="formModel"
|
||||||
:label-col-props="{ span: 6 }"
|
:label-col-props="{ span: 6 }"
|
||||||
:wrapper-col-props="{ span: 18 }"
|
:wrapper-col-props="{ span: 12 }"
|
||||||
label-align="right"
|
label-align="right"
|
||||||
>
|
>
|
||||||
<a-row :gutter="16">
|
<a-row :gutter="16">
|
||||||
@ -118,6 +118,8 @@
|
|||||||
:data="renderData"
|
:data="renderData"
|
||||||
:bordered="false"
|
:bordered="false"
|
||||||
:size="size"
|
:size="size"
|
||||||
|
:pagination="false"
|
||||||
|
style="margin-bottom: 40px"
|
||||||
>
|
>
|
||||||
<template #index="{ rowIndex }">
|
<template #index="{ rowIndex }">
|
||||||
{{ rowIndex + 1 }}
|
{{ rowIndex + 1 }}
|
||||||
@ -146,12 +148,28 @@
|
|||||||
type="error"
|
type="error"
|
||||||
@ok="handleDelete(record)"
|
@ok="handleDelete(record)"
|
||||||
>
|
>
|
||||||
<a-button type="primary" size="small" status="danger">
|
<a-button
|
||||||
|
type="primary"
|
||||||
|
size="small"
|
||||||
|
status="danger"
|
||||||
|
style="padding: 7px"
|
||||||
|
>
|
||||||
|
<template #icon><icon-delete /></template>
|
||||||
{{ $t('delete') }}
|
{{ $t('delete') }}
|
||||||
</a-button>
|
</a-button>
|
||||||
</a-popconfirm>
|
</a-popconfirm>
|
||||||
</template>
|
</template>
|
||||||
</a-table>
|
</a-table>
|
||||||
|
<a-pagination
|
||||||
|
style="float: right; position: relative; right: 1px; bottom: 25px"
|
||||||
|
:total="pagination.total"
|
||||||
|
@page-size-change="onSizeChange"
|
||||||
|
:size="size"
|
||||||
|
@change="onPageChange"
|
||||||
|
show-total
|
||||||
|
show-jumper
|
||||||
|
show-page-size
|
||||||
|
/>
|
||||||
</a-card>
|
</a-card>
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
@ -161,6 +179,7 @@ import { computed, ref, watch } from 'vue';
|
|||||||
import { useI18n } from 'vue-i18n';
|
import { useI18n } from 'vue-i18n';
|
||||||
import useLoading from '@/hooks/loading';
|
import useLoading from '@/hooks/loading';
|
||||||
import useTableOption from '@/hooks/table-option';
|
import useTableOption from '@/hooks/table-option';
|
||||||
|
import { Pagination } from '@/types/global';
|
||||||
import type { TableColumnData } from '@arco-design/web-vue/es/table/interface';
|
import type { TableColumnData } from '@arco-design/web-vue/es/table/interface';
|
||||||
import dayjs from 'dayjs';
|
import dayjs from 'dayjs';
|
||||||
import { Message } from '@arco-design/web-vue';
|
import { Message } from '@arco-design/web-vue';
|
||||||
@ -187,6 +206,12 @@ const generateFormModel = () => {
|
|||||||
code: '',
|
code: '',
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
const pagination: Pagination = {
|
||||||
|
page: 1,
|
||||||
|
size: 10,
|
||||||
|
current: 1,
|
||||||
|
total: 10,
|
||||||
|
};
|
||||||
|
|
||||||
const { t } = useI18n();
|
const { t } = useI18n();
|
||||||
const renderData = ref<DeptRecord[]>([]);
|
const renderData = ref<DeptRecord[]>([]);
|
||||||
@ -202,10 +227,16 @@ const columns = computed<TableColumnData[]>(() => [
|
|||||||
{
|
{
|
||||||
title: t('deptTable.columns.name'),
|
title: t('deptTable.columns.name'),
|
||||||
dataIndex: 'name',
|
dataIndex: 'name',
|
||||||
|
sortable: {
|
||||||
|
sortDirections: ['ascend', 'descend'],
|
||||||
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: t('deptTable.columns.id'),
|
title: t('deptTable.columns.id'),
|
||||||
dataIndex: 'id',
|
dataIndex: 'id',
|
||||||
|
sortable: {
|
||||||
|
sortDirections: ['ascend', 'descend'],
|
||||||
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: t('deptTable.columns.remark'),
|
title: t('deptTable.columns.remark'),
|
||||||
@ -215,6 +246,9 @@ const columns = computed<TableColumnData[]>(() => [
|
|||||||
title: t('deptTable.columns.createTime'),
|
title: t('deptTable.columns.createTime'),
|
||||||
dataIndex: 'createTime',
|
dataIndex: 'createTime',
|
||||||
slotName: 'createTime',
|
slotName: 'createTime',
|
||||||
|
sortable: {
|
||||||
|
sortDirections: ['ascend', 'descend'],
|
||||||
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: t('deptTable.columns.enabled'),
|
title: t('deptTable.columns.enabled'),
|
||||||
@ -233,8 +267,11 @@ const fetchData = async (params?: Partial<DeptRecord>) => {
|
|||||||
setLoading(true);
|
setLoading(true);
|
||||||
try {
|
try {
|
||||||
const res = await deptStore.getDeptList(params);
|
const res = await deptStore.getDeptList(params);
|
||||||
const { data } = res;
|
|
||||||
renderData.value = data;
|
renderData.value = res.data.records;
|
||||||
|
pagination.page = res.data.page;
|
||||||
|
pagination.current = res.data.current;
|
||||||
|
pagination.total = res.data.total;
|
||||||
} catch (err) {
|
} catch (err) {
|
||||||
// you can report use errorHandler or other
|
// you can report use errorHandler or other
|
||||||
} finally {
|
} finally {
|
||||||
@ -245,12 +282,26 @@ const fetchData = async (params?: Partial<DeptRecord>) => {
|
|||||||
// 查询
|
// 查询
|
||||||
const search = () => {
|
const search = () => {
|
||||||
fetchData({
|
fetchData({
|
||||||
|
...pagination,
|
||||||
...formModel.value,
|
...formModel.value,
|
||||||
});
|
} as unknown as any);
|
||||||
};
|
};
|
||||||
|
|
||||||
search();
|
search();
|
||||||
|
|
||||||
|
// 分页发生改变
|
||||||
|
const onPageChange = (current: number) => {
|
||||||
|
pagination.page = current;
|
||||||
|
pagination.current = current;
|
||||||
|
search();
|
||||||
|
};
|
||||||
|
|
||||||
|
// 数据条数改变
|
||||||
|
const onSizeChange = (size: number) => {
|
||||||
|
pagination.size = size;
|
||||||
|
search();
|
||||||
|
};
|
||||||
|
|
||||||
// 重置
|
// 重置
|
||||||
const reset = () => {
|
const reset = () => {
|
||||||
formModel.value = generateFormModel();
|
formModel.value = generateFormModel();
|
||||||
|
@ -21,5 +21,9 @@ export default {
|
|||||||
'dept.info.remark': 'Remark',
|
'dept.info.remark': 'Remark',
|
||||||
'dept.info.remark.placeholder': 'Please enter Remark',
|
'dept.info.remark.placeholder': 'Please enter Remark',
|
||||||
|
|
||||||
'Confirm the deletion of this department' :'Confirm the deletion of this department?'
|
'Confirm the deletion of this department' :'Confirm the deletion of this department?',
|
||||||
|
|
||||||
|
// modalTitle
|
||||||
|
'createDept': 'Create Dept',
|
||||||
|
'editDept': 'Edit Dept Info'
|
||||||
};
|
};
|
||||||
|
@ -5,8 +5,8 @@ export default {
|
|||||||
'searchTable.form.deptName.placeholder': '请输入部门名称',
|
'searchTable.form.deptName.placeholder': '请输入部门名称',
|
||||||
|
|
||||||
'deptTable.columns.index': '序号',
|
'deptTable.columns.index': '序号',
|
||||||
'deptTable.columns.name': '区域名称',
|
'deptTable.columns.name': '部门名称',
|
||||||
'deptTable.columns.id': '区域ID',
|
'deptTable.columns.id': '部门ID',
|
||||||
'deptTable.columns.remark': '备注',
|
'deptTable.columns.remark': '备注',
|
||||||
'deptTable.columns.enabled': '是否启用',
|
'deptTable.columns.enabled': '是否启用',
|
||||||
'deptTable.columns.createTime': '创建时间',
|
'deptTable.columns.createTime': '创建时间',
|
||||||
@ -21,5 +21,10 @@ export default {
|
|||||||
'dept.info.remark': '备注',
|
'dept.info.remark': '备注',
|
||||||
'dept.info.remark.placeholder': '请输入备注',
|
'dept.info.remark.placeholder': '请输入备注',
|
||||||
|
|
||||||
'Confirm the deletion of this department' :'确认删除此部门?'
|
'Confirm the deletion of this department' :'确认删除此部门?',
|
||||||
|
|
||||||
|
|
||||||
|
// modalTitle
|
||||||
|
'createDept': '新增部门',
|
||||||
|
'editDept': '修改部门信息'
|
||||||
};
|
};
|
||||||
|
@ -1,25 +1,26 @@
|
|||||||
<template>
|
<template>
|
||||||
<a-button v-if="props.isCreate" type="primary" @click="handleClick">
|
<a-button v-if="props.isCreate" type="primary" @click="handleClick">
|
||||||
<template #icon><icon-plus /></template>
|
<template #icon><icon-plus /></template>
|
||||||
{{ modalTitle }}
|
{{ t('create') }}
|
||||||
</a-button>
|
</a-button>
|
||||||
<a-button
|
<a-button
|
||||||
v-if="!props.isCreate"
|
v-if="!props.isCreate"
|
||||||
type="outline"
|
type="outline"
|
||||||
size="small"
|
size="small"
|
||||||
:style="{ marginRight: '10px' }"
|
:style="{ marginRight: '10px', padding: '7px' }"
|
||||||
@click="handleClick"
|
@click="handleClick"
|
||||||
>
|
>
|
||||||
{{ modalTitle }}
|
<template #icon><icon-edit /></template>
|
||||||
|
{{ t('edit') }}
|
||||||
</a-button>
|
</a-button>
|
||||||
<a-modal
|
<a-modal
|
||||||
width="600px"
|
width="700px"
|
||||||
:visible="visible"
|
:visible="visible"
|
||||||
@ok="handleSubmit"
|
@ok="handleSubmit"
|
||||||
@cancel="handleCancel"
|
@cancel="handleCancel"
|
||||||
>
|
>
|
||||||
<template #title>{{ modalTitle }}</template>
|
<template #title>{{ modalTitle }}</template>
|
||||||
<a-form ref="createEditRef" :model="formData" :style="{ width: '500px' }">
|
<a-form ref="createEditRef" :model="formData" :style="{ width: '650px' }">
|
||||||
<a-form-item
|
<a-form-item
|
||||||
field="name"
|
field="name"
|
||||||
:label="$t('role.info.name')"
|
:label="$t('role.info.name')"
|
||||||
@ -35,7 +36,9 @@
|
|||||||
<a-form-item field="remark" :label="$t('role.info.remark')">
|
<a-form-item field="remark" :label="$t('role.info.remark')">
|
||||||
<a-textarea
|
<a-textarea
|
||||||
v-model="formData.remark"
|
v-model="formData.remark"
|
||||||
|
:show-word-limit="true"
|
||||||
:placeholder="$t('role.info.remark.placeholder')"
|
:placeholder="$t('role.info.remark.placeholder')"
|
||||||
|
style="height: 100px"
|
||||||
/>
|
/>
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
</a-form>
|
</a-form>
|
||||||
@ -60,7 +63,7 @@ const props = defineProps({
|
|||||||
});
|
});
|
||||||
const { t } = useI18n();
|
const { t } = useI18n();
|
||||||
const modalTitle = computed(() => {
|
const modalTitle = computed(() => {
|
||||||
return props.isCreate ? t('create') : t('edit');
|
return props.isCreate ? t('createRole') : t('editRole');
|
||||||
});
|
});
|
||||||
const { visible, setVisible } = useVisible(false);
|
const { visible, setVisible } = useVisible(false);
|
||||||
const createEditRef = ref<FormInstance>();
|
const createEditRef = ref<FormInstance>();
|
||||||
|
@ -1,7 +1,46 @@
|
|||||||
<template>
|
<template>
|
||||||
<div class="container">
|
<div class="container">
|
||||||
<Breadcrumb :items="['menu.system', 'menu.system.role']" />
|
<Breadcrumb :items="['menu.system', 'menu.system.role']" />
|
||||||
<a-card class="general-card" :title="$t('menu.role.list')">
|
<a-card class="general-card" title=" ">
|
||||||
|
<a-row>
|
||||||
|
<a-col :flex="1">
|
||||||
|
<a-form
|
||||||
|
:model="formModel"
|
||||||
|
:label-col-props="{ span: 6 }"
|
||||||
|
:wrapper-col-props="{ span: 12 }"
|
||||||
|
label-align="right"
|
||||||
|
>
|
||||||
|
<a-row :gutter="16">
|
||||||
|
<a-col :span="12">
|
||||||
|
<a-form-item field="title" :label="$t('searchTable.form.name')">
|
||||||
|
<a-input
|
||||||
|
v-model="formModel.name"
|
||||||
|
:placeholder="$t('searchTable.form.name.placeholder')"
|
||||||
|
/>
|
||||||
|
</a-form-item>
|
||||||
|
</a-col>
|
||||||
|
</a-row>
|
||||||
|
</a-form>
|
||||||
|
</a-col>
|
||||||
|
<a-divider style="height: 42px" direction="vertical" />
|
||||||
|
<a-col :flex="'46px'" style="text-align: right">
|
||||||
|
<a-space :size="18">
|
||||||
|
<a-button type="primary" @click="search">
|
||||||
|
<template #icon>
|
||||||
|
<icon-search />
|
||||||
|
</template>
|
||||||
|
{{ $t('searchTable.form.search') }}
|
||||||
|
</a-button>
|
||||||
|
<a-button @click="reset">
|
||||||
|
<template #icon>
|
||||||
|
<icon-refresh />
|
||||||
|
</template>
|
||||||
|
{{ $t('searchTable.form.reset') }}
|
||||||
|
</a-button>
|
||||||
|
</a-space>
|
||||||
|
</a-col>
|
||||||
|
</a-row>
|
||||||
|
<a-divider style="margin-top: 10px" />
|
||||||
<a-row style="margin-bottom: 16px">
|
<a-row style="margin-bottom: 16px">
|
||||||
<a-col :span="12">
|
<a-col :span="12">
|
||||||
<a-space>
|
<a-space>
|
||||||
@ -77,6 +116,7 @@
|
|||||||
:bordered="false"
|
:bordered="false"
|
||||||
:size="size"
|
:size="size"
|
||||||
@page-change="onPageChange"
|
@page-change="onPageChange"
|
||||||
|
style="margin-bottom: 40px"
|
||||||
>
|
>
|
||||||
<template #index="{ rowIndex }">
|
<template #index="{ rowIndex }">
|
||||||
{{ rowIndex + 1 }}
|
{{ rowIndex + 1 }}
|
||||||
@ -105,12 +145,28 @@
|
|||||||
type="error"
|
type="error"
|
||||||
@ok="handleDelete(record)"
|
@ok="handleDelete(record)"
|
||||||
>
|
>
|
||||||
<a-button type="primary" size="small" status="danger">
|
<a-button
|
||||||
|
type="primary"
|
||||||
|
size="small"
|
||||||
|
status="danger"
|
||||||
|
style="padding: 7px"
|
||||||
|
>
|
||||||
|
<template #icon><icon-delete /></template>
|
||||||
{{ $t('delete') }}
|
{{ $t('delete') }}
|
||||||
</a-button>
|
</a-button>
|
||||||
</a-popconfirm>
|
</a-popconfirm>
|
||||||
</template>
|
</template>
|
||||||
</a-table>
|
</a-table>
|
||||||
|
<a-pagination
|
||||||
|
style="float: right; position: relative; right: 1px; bottom: 25px"
|
||||||
|
:total="pagination.total"
|
||||||
|
@page-size-change="onSizeChange"
|
||||||
|
:size="size"
|
||||||
|
@change="onPageChange"
|
||||||
|
show-total
|
||||||
|
show-jumper
|
||||||
|
show-page-size
|
||||||
|
/>
|
||||||
</a-card>
|
</a-card>
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
@ -119,6 +175,7 @@
|
|||||||
import { computed, ref, reactive, watch, nextTick } from 'vue';
|
import { computed, ref, reactive, watch, nextTick } from 'vue';
|
||||||
import { useI18n } from 'vue-i18n';
|
import { useI18n } from 'vue-i18n';
|
||||||
import useLoading from '@/hooks/loading';
|
import useLoading from '@/hooks/loading';
|
||||||
|
import { Pagination } from '@/types/global';
|
||||||
import type { TableColumnData } from '@arco-design/web-vue/es/table/interface';
|
import type { TableColumnData } from '@arco-design/web-vue/es/table/interface';
|
||||||
import { Message } from '@arco-design/web-vue';
|
import { Message } from '@arco-design/web-vue';
|
||||||
import useTableOption from '@/hooks/table-option';
|
import useTableOption from '@/hooks/table-option';
|
||||||
@ -143,6 +200,19 @@ const {
|
|||||||
deepClone,
|
deepClone,
|
||||||
} = useTableOption();
|
} = useTableOption();
|
||||||
const roleStore = useRoleStore();
|
const roleStore = useRoleStore();
|
||||||
|
const generateFormModel = () => {
|
||||||
|
return {
|
||||||
|
name: undefined,
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
const formModel = ref(generateFormModel());
|
||||||
|
const pagination: Pagination = {
|
||||||
|
page: 1,
|
||||||
|
size: 10,
|
||||||
|
current: 1,
|
||||||
|
total: 10,
|
||||||
|
};
|
||||||
|
|
||||||
// 表格头部
|
// 表格头部
|
||||||
const columns = computed<TableColumnData[]>(() => [
|
const columns = computed<TableColumnData[]>(() => [
|
||||||
@ -154,19 +224,21 @@ const columns = computed<TableColumnData[]>(() => [
|
|||||||
{
|
{
|
||||||
title: t('roleTable.columns.name'),
|
title: t('roleTable.columns.name'),
|
||||||
dataIndex: 'name',
|
dataIndex: 'name',
|
||||||
|
sortable: {
|
||||||
|
sortDirections: ['ascend', 'descend'],
|
||||||
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: t('roleTable.columns.remark'),
|
title: t('roleTable.columns.remark'),
|
||||||
dataIndex: 'remark',
|
dataIndex: 'remark',
|
||||||
},
|
},
|
||||||
// {
|
|
||||||
// title: t('roleTable.columns.authorities'),
|
|
||||||
// dataIndex: 'authorities',
|
|
||||||
// },
|
|
||||||
{
|
{
|
||||||
title: t('roleTable.columns.createTime'),
|
title: t('roleTable.columns.createTime'),
|
||||||
dataIndex: 'createTime',
|
dataIndex: 'createTime',
|
||||||
slotName: 'createTime',
|
slotName: 'createTime',
|
||||||
|
sortable: {
|
||||||
|
sortDirections: ['ascend', 'descend'],
|
||||||
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: t('roleTable.columns.enabled'),
|
title: t('roleTable.columns.enabled'),
|
||||||
@ -181,11 +253,15 @@ const columns = computed<TableColumnData[]>(() => [
|
|||||||
]);
|
]);
|
||||||
|
|
||||||
// 获取表格数据
|
// 获取表格数据
|
||||||
const fetchData = async () => {
|
const fetchData = async (params: any) => {
|
||||||
setLoading(true);
|
setLoading(true);
|
||||||
try {
|
try {
|
||||||
const res = await roleStore.getRoleList();
|
const res = await roleStore.getRoleList(params);
|
||||||
renderData.value = res.data;
|
console.log('info', res.data);
|
||||||
|
renderData.value = res.data.records;
|
||||||
|
pagination.page = res.data.page;
|
||||||
|
pagination.current = res.data.current;
|
||||||
|
pagination.total = res.data.total;
|
||||||
} catch (err) {
|
} catch (err) {
|
||||||
// you can report use errorHandler or other
|
// you can report use errorHandler or other
|
||||||
} finally {
|
} finally {
|
||||||
@ -193,7 +269,33 @@ const fetchData = async () => {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
fetchData();
|
// 模糊查询
|
||||||
|
const search = () => {
|
||||||
|
fetchData({
|
||||||
|
...pagination,
|
||||||
|
...formModel.value,
|
||||||
|
} as unknown as any);
|
||||||
|
};
|
||||||
|
|
||||||
|
search();
|
||||||
|
|
||||||
|
// 分页发生改变
|
||||||
|
const onPageChange = (current: number) => {
|
||||||
|
pagination.page = current;
|
||||||
|
pagination.current = current;
|
||||||
|
search();
|
||||||
|
};
|
||||||
|
|
||||||
|
// 数据条数改变
|
||||||
|
const onSizeChange = (size: number) => {
|
||||||
|
pagination.size = size;
|
||||||
|
search();
|
||||||
|
};
|
||||||
|
|
||||||
|
// 重置
|
||||||
|
const reset = () => {
|
||||||
|
formModel.value = generateFormModel();
|
||||||
|
};
|
||||||
|
|
||||||
// 是否启用
|
// 是否启用
|
||||||
const enabledStatus = async (record: string) => {
|
const enabledStatus = async (record: string) => {
|
||||||
@ -220,7 +322,7 @@ const handleDelete = async (record: RoleRecord) => {
|
|||||||
content: t('delete.role.sucess'),
|
content: t('delete.role.sucess'),
|
||||||
duration: 5 * 1000,
|
duration: 5 * 1000,
|
||||||
});
|
});
|
||||||
fetchData();
|
search();
|
||||||
} else {
|
} else {
|
||||||
Message.error({
|
Message.error({
|
||||||
content: t('delete.role.fail'),
|
content: t('delete.role.fail'),
|
||||||
|
@ -14,6 +14,9 @@ export default {
|
|||||||
'delete.role.sucess': 'Delete Role Sucess',
|
'delete.role.sucess': 'Delete Role Sucess',
|
||||||
'delete.role.fail': 'Delete Role Fail',
|
'delete.role.fail': 'Delete Role Fail',
|
||||||
|
|
||||||
|
'searchTable.form.name':'Name',
|
||||||
|
'searchTable.form.name.placeholder':'Please enter Name',
|
||||||
|
|
||||||
'role.info.name': 'Name',
|
'role.info.name': 'Name',
|
||||||
'role.info.name.placeholder': 'Please enter Name',
|
'role.info.name.placeholder': 'Please enter Name',
|
||||||
'role.info.name.required': 'Name is required',
|
'role.info.name.required': 'Name is required',
|
||||||
@ -27,4 +30,9 @@ export default {
|
|||||||
|
|
||||||
'modify.status.sucess':'Modify status sucess',
|
'modify.status.sucess':'Modify status sucess',
|
||||||
'modify.status.fail':'Modify status fail',
|
'modify.status.fail':'Modify status fail',
|
||||||
|
|
||||||
|
|
||||||
|
// modalTitle
|
||||||
|
'createRole': 'Create Role',
|
||||||
|
'editRole': 'Edit Role Info',
|
||||||
};
|
};
|
||||||
|
@ -14,6 +14,9 @@ export default {
|
|||||||
'delete.role.sucess': '删除角色成功',
|
'delete.role.sucess': '删除角色成功',
|
||||||
'delete.role.fail': '删除角色失败',
|
'delete.role.fail': '删除角色失败',
|
||||||
|
|
||||||
|
'searchTable.form.name':'角色名称',
|
||||||
|
'searchTable.form.name.placeholder':'请输入角色名称',
|
||||||
|
|
||||||
'role.info.name': '角色名称',
|
'role.info.name': '角色名称',
|
||||||
'role.info.name.placeholder': '请输入角色名称',
|
'role.info.name.placeholder': '请输入角色名称',
|
||||||
'role.info.name.required': '角色不能为空',
|
'role.info.name.required': '角色不能为空',
|
||||||
@ -27,4 +30,9 @@ export default {
|
|||||||
|
|
||||||
'modify.status.sucess':'修改状态成功',
|
'modify.status.sucess':'修改状态成功',
|
||||||
'modify.status.fail':'修改状态失败',
|
'modify.status.fail':'修改状态失败',
|
||||||
|
|
||||||
|
|
||||||
|
// modalTitle
|
||||||
|
'createRole': '新增角色',
|
||||||
|
'editRole': '修改角色信息'
|
||||||
};
|
};
|
||||||
|
@ -1,26 +1,27 @@
|
|||||||
<template>
|
<template>
|
||||||
<a-button v-if="props.isCreate" type="primary" @click="handleClick">
|
<a-button v-if="props.isCreate" type="primary" @click="handleClick">
|
||||||
<template #icon><icon-plus /></template>
|
<template #icon><icon-plus /></template>
|
||||||
{{ modalTitle }}
|
{{ t('create') }}
|
||||||
</a-button>
|
</a-button>
|
||||||
<a-button
|
<a-button
|
||||||
v-if="!props.isCreate"
|
v-if="!props.isCreate"
|
||||||
type="outline"
|
type="outline"
|
||||||
size="small"
|
size="small"
|
||||||
:style="{ marginRight: '10px' }"
|
:style="{ marginRight: '10px', padding: '7px' }"
|
||||||
@click="handleClick"
|
@click="handleClick"
|
||||||
>
|
>
|
||||||
{{ modalTitle }}
|
<template #icon><icon-edit /></template>
|
||||||
|
{{ t('edit') }}
|
||||||
</a-button>
|
</a-button>
|
||||||
|
|
||||||
<a-modal
|
<a-modal
|
||||||
width="600px"
|
width="700px"
|
||||||
:visible="visible"
|
:visible="visible"
|
||||||
@ok="handleSubmit"
|
@ok="handleSubmit"
|
||||||
@cancel="handleCancel"
|
@cancel="handleCancel"
|
||||||
>
|
>
|
||||||
<template #title>{{ modalTitle }}</template>
|
<template #title>{{ modalTitle }}</template>
|
||||||
<a-form ref="CreateRef" :model="formData" :style="{ width: '500px' }">
|
<a-form ref="CreateRef" :model="formData" :style="{ width: '650px' }">
|
||||||
<a-form-item
|
<a-form-item
|
||||||
field="username"
|
field="username"
|
||||||
:label="$t('user.info.username')"
|
:label="$t('user.info.username')"
|
||||||
@ -42,21 +43,20 @@
|
|||||||
<div v-else>{{ formData.username }}</div>
|
<div v-else>{{ formData.username }}</div>
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
<a-form-item
|
<a-form-item
|
||||||
field="password"
|
field="email"
|
||||||
:label="$t('user.info.password')"
|
:label="$t('user.info.email')"
|
||||||
v-if="isCreate"
|
:rules="[
|
||||||
|
{
|
||||||
|
required: true,
|
||||||
|
type: 'email',
|
||||||
|
message: t('user.info.email.required'),
|
||||||
|
},
|
||||||
|
]"
|
||||||
:validate-trigger="['change', 'input']"
|
:validate-trigger="['change', 'input']"
|
||||||
:rules="[{ required: true, message: t('user.info.password.required') }]"
|
|
||||||
>
|
>
|
||||||
<a-input
|
<a-input
|
||||||
v-model="formData.password"
|
v-model="formData.email"
|
||||||
:placeholder="$t('user.info.password.placeholder')"
|
:placeholder="$t('user.info.email.placeholder')"
|
||||||
/>
|
|
||||||
</a-form-item>
|
|
||||||
<a-form-item field="nickName" :label="$t('user.info.nickName')">
|
|
||||||
<a-input
|
|
||||||
v-model="formData.nickName"
|
|
||||||
:placeholder="$t('user.info.nickName.placeholder')"
|
|
||||||
/>
|
/>
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
<a-form-item
|
<a-form-item
|
||||||
@ -74,22 +74,24 @@
|
|||||||
/>
|
/>
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
<a-form-item
|
<a-form-item
|
||||||
field="email"
|
field="password"
|
||||||
:label="$t('user.info.email')"
|
:label="$t('user.info.password')"
|
||||||
:rules="[
|
v-if="isCreate"
|
||||||
{
|
|
||||||
required: true,
|
|
||||||
type: 'email',
|
|
||||||
message: t('user.info.email.required'),
|
|
||||||
},
|
|
||||||
]"
|
|
||||||
:validate-trigger="['change', 'input']"
|
:validate-trigger="['change', 'input']"
|
||||||
|
:rules="[{ required: true, message: t('user.info.password.required') }]"
|
||||||
>
|
>
|
||||||
<a-input
|
<a-input
|
||||||
v-model="formData.email"
|
v-model="formData.password"
|
||||||
:placeholder="$t('user.info.email.placeholder')"
|
:placeholder="$t('user.info.password.placeholder')"
|
||||||
/>
|
/>
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
|
<a-form-item field="nickName" :label="$t('user.info.nickName')">
|
||||||
|
<a-input
|
||||||
|
v-model="formData.nickName"
|
||||||
|
:placeholder="$t('user.info.nickName.placeholder')"
|
||||||
|
/>
|
||||||
|
</a-form-item>
|
||||||
|
|
||||||
<a-form-item field="address" :label="$t('user.info.address')">
|
<a-form-item field="address" :label="$t('user.info.address')">
|
||||||
<a-input
|
<a-input
|
||||||
v-model="formData.address"
|
v-model="formData.address"
|
||||||
@ -139,11 +141,10 @@
|
|||||||
import { useI18n } from 'vue-i18n';
|
import { useI18n } from 'vue-i18n';
|
||||||
import useVisible from '@/hooks/visible';
|
import useVisible from '@/hooks/visible';
|
||||||
import { computed, PropType, ref } from 'vue';
|
import { computed, PropType, ref } from 'vue';
|
||||||
import { CreateRecord, UserRecord } from '@/api/user';
|
import { CreateRecord } from '@/api/user';
|
||||||
import { FormInstance } from '@arco-design/web-vue/es/form';
|
import { FormInstance } from '@arco-design/web-vue/es/form';
|
||||||
import { queryRoleList } from '@/api/role';
|
import { queryRoleList } from '@/api/role';
|
||||||
import { deptList } from '@/api/dept';
|
import { deptList } from '@/api/dept';
|
||||||
import { computedAsync } from '@vueuse/core';
|
|
||||||
import { Message } from '@arco-design/web-vue';
|
import { Message } from '@arco-design/web-vue';
|
||||||
import { useUserStore } from '@/store';
|
import { useUserStore } from '@/store';
|
||||||
|
|
||||||
@ -155,7 +156,7 @@ const props = defineProps({
|
|||||||
});
|
});
|
||||||
const { t } = useI18n();
|
const { t } = useI18n();
|
||||||
const modalTitle = computed(() => {
|
const modalTitle = computed(() => {
|
||||||
return props.isCreate ? t('create') : t('edit');
|
return props.isCreate ? t('createUser') : t('editUser');
|
||||||
});
|
});
|
||||||
const { visible, setVisible } = useVisible(false);
|
const { visible, setVisible } = useVisible(false);
|
||||||
const checkKeys = ref<number[]>([]);
|
const checkKeys = ref<number[]>([]);
|
||||||
@ -180,32 +181,16 @@ let formDifer = {};
|
|||||||
const userStore = useUserStore();
|
const userStore = useUserStore();
|
||||||
|
|
||||||
// 部门数据
|
// 部门数据
|
||||||
// const deptOptions = computedAsync(async () => {
|
|
||||||
// const { data } = await deptList();
|
|
||||||
// const deptData = data.filter((item: any) => {
|
|
||||||
// return item.enabled !== false;
|
|
||||||
// });
|
|
||||||
// return deptData;
|
|
||||||
// });
|
|
||||||
|
|
||||||
const deptOptions = ref();
|
const deptOptions = ref();
|
||||||
const getDeptData = async () => {
|
const getDeptData = async () => {
|
||||||
const res = await deptList();
|
const res = await deptList();
|
||||||
deptOptions.value = res.data;
|
deptOptions.value = res.data.records;
|
||||||
};
|
};
|
||||||
// 角色数据
|
// 角色数据
|
||||||
// const roleOptions = computedAsync(async () => {
|
|
||||||
// const res = await queryRoleList();
|
|
||||||
// const roleData = res.data.filter((item: any) => {
|
|
||||||
// return item.enabled !== false;
|
|
||||||
// });
|
|
||||||
// return roleData;
|
|
||||||
// });
|
|
||||||
|
|
||||||
const roleOptions = ref();
|
const roleOptions = ref();
|
||||||
const getRoleData = async () => {
|
const getRoleData = async () => {
|
||||||
const res = await queryRoleList();
|
const res = await queryRoleList('');
|
||||||
roleOptions.value = res.data.filter((item: any) => {
|
roleOptions.value = res.data.records.filter((item: any) => {
|
||||||
return item.enabled !== false;
|
return item.enabled !== false;
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
@ -215,7 +200,6 @@ const handleClick = () => {
|
|||||||
getDeptData();
|
getDeptData();
|
||||||
getRoleData();
|
getRoleData();
|
||||||
const userId = props.prem?.id;
|
const userId = props.prem?.id;
|
||||||
|
|
||||||
// 编辑
|
// 编辑
|
||||||
if (!props.isCreate && userId) {
|
if (!props.isCreate && userId) {
|
||||||
formData.value = props.prem;
|
formData.value = props.prem;
|
||||||
@ -242,6 +226,7 @@ const handleSubmit = async () => {
|
|||||||
formData.value.permissionIds = checkKeys.value;
|
formData.value.permissionIds = checkKeys.value;
|
||||||
// 新增
|
// 新增
|
||||||
if (props.isCreate) {
|
if (props.isCreate) {
|
||||||
|
// formData.value.username = formData.value.email;
|
||||||
const res = await userStore.createUser(formData.value);
|
const res = await userStore.createUser(formData.value);
|
||||||
if (res.status === 200) {
|
if (res.status === 200) {
|
||||||
Message.success({
|
Message.success({
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
<template>
|
<template>
|
||||||
<div class="container">
|
<div class="container">
|
||||||
<Breadcrumb :items="['menu.system', 'menu.system.user']" />
|
<Breadcrumb :items="['menu.system', 'menu.system.user']" />
|
||||||
<a-card class="general-card" :title="$t('menu.list.searchTable')">
|
<a-card class="general-card" title=" ">
|
||||||
<a-row>
|
<a-row>
|
||||||
<a-col :flex="1">
|
<a-col :flex="1">
|
||||||
<a-form
|
<a-form
|
||||||
@ -80,15 +80,26 @@
|
|||||||
</a-row>
|
</a-row>
|
||||||
|
|
||||||
<a-divider style="margin-top: 0" />
|
<a-divider style="margin-top: 0" />
|
||||||
<a-row style="margin-bottom: 16px">
|
<a-row>
|
||||||
<a-col :span="12">
|
<a-col :span="12">
|
||||||
<a-space>
|
<a-space>
|
||||||
<UserEdit ref="createUserRef" :is-create="true" @refresh="search" />
|
<UserEdit ref="createUserRef" :is-create="true" @refresh="search" />
|
||||||
</a-space>
|
</a-space>
|
||||||
|
<a-button @click="generateExcel" style="margin-left: 20px">
|
||||||
|
<template #icon>
|
||||||
|
<icon-download size="18" />
|
||||||
|
</template>
|
||||||
|
{{ $t('searchTable.operation.download') }}
|
||||||
|
</a-button>
|
||||||
</a-col>
|
</a-col>
|
||||||
<a-col
|
<a-col
|
||||||
:span="12"
|
:span="12"
|
||||||
style="display: flex; align-items: center; justify-content: end"
|
style="
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: end;
|
||||||
|
padding-bottom: 20px;
|
||||||
|
"
|
||||||
>
|
>
|
||||||
<a-tooltip :content="$t('searchTable.actions.refresh')">
|
<a-tooltip :content="$t('searchTable.actions.refresh')">
|
||||||
<div class="action-icon" @click="search">
|
<div class="action-icon" @click="search">
|
||||||
@ -152,12 +163,15 @@
|
|||||||
<a-table
|
<a-table
|
||||||
row-key="id"
|
row-key="id"
|
||||||
:loading="loading"
|
:loading="loading"
|
||||||
:pagination="pagination"
|
:pagination="false"
|
||||||
:columns="(cloneColumns as TableColumnData[])"
|
:columns="(cloneColumns as TableColumnData[])"
|
||||||
:data="renderData"
|
:data="renderData"
|
||||||
:bordered="false"
|
:bordered="false"
|
||||||
:size="size"
|
:size="size"
|
||||||
@page-change="onPageChange"
|
@page-change="onPageChange"
|
||||||
|
style="margin-bottom: 40px"
|
||||||
|
:filter-icon-align-left="alignLeft"
|
||||||
|
@change="handleSortChange"
|
||||||
>
|
>
|
||||||
<template #index="{ rowIndex }">
|
<template #index="{ rowIndex }">
|
||||||
{{ rowIndex + 1 + (pagination.current - 1) * pagination.size }}
|
{{ rowIndex + 1 + (pagination.current - 1) * pagination.size }}
|
||||||
@ -177,12 +191,12 @@
|
|||||||
:is-create="false"
|
:is-create="false"
|
||||||
@refresh="fetchData"
|
@refresh="fetchData"
|
||||||
/>
|
/>
|
||||||
<!-- <Userc
|
<Userc
|
||||||
ref="editUserRef"
|
ref="editUserRef"
|
||||||
:user="record"
|
:user="record"
|
||||||
:is-create="false"
|
:is-create="false"
|
||||||
@refresh="search"
|
@refresh="search"
|
||||||
/> -->
|
/>
|
||||||
<!-- <a-popconfirm
|
<!-- <a-popconfirm
|
||||||
content="确认删除此用户?"
|
content="确认删除此用户?"
|
||||||
type="error"
|
type="error"
|
||||||
@ -194,22 +208,31 @@
|
|||||||
</a-popconfirm> -->
|
</a-popconfirm> -->
|
||||||
</template>
|
</template>
|
||||||
</a-table>
|
</a-table>
|
||||||
|
<a-pagination
|
||||||
|
style="float: right; position: relative; right: 1px; bottom: 25px"
|
||||||
|
:total="pagination.total"
|
||||||
|
@page-size-change="onSizeChange"
|
||||||
|
:size="size"
|
||||||
|
@change="onPageChange"
|
||||||
|
show-total
|
||||||
|
show-jumper
|
||||||
|
show-page-size
|
||||||
|
/>
|
||||||
</a-card>
|
</a-card>
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
<script lang="ts" setup>
|
<script lang="ts" setup>
|
||||||
import { computed, ref, reactive, watch, nextTick } from 'vue';
|
import { computed, ref, watch } from 'vue';
|
||||||
import { useI18n } from 'vue-i18n';
|
import { useI18n } from 'vue-i18n';
|
||||||
import useLoading from '@/hooks/loading';
|
import useLoading from '@/hooks/loading';
|
||||||
import { UserRecord, UserParams } from '@/api/user';
|
import { UserRecord, UserParams } from '@/api/user';
|
||||||
import { Pagination } from '@/types/global';
|
import { Pagination } from '@/types/global';
|
||||||
import type { SelectOptionData } from '@arco-design/web-vue/es/select/interface';
|
import type { SelectOptionData } from '@arco-design/web-vue/es/select/interface';
|
||||||
import type { TableColumnData } from '@arco-design/web-vue/es/table/interface';
|
import type { TableColumnData } from '@arco-design/web-vue/es/table/interface';
|
||||||
import cloneDeep from 'lodash/cloneDeep';
|
|
||||||
import Sortable from 'sortablejs';
|
|
||||||
import { useUserStore } from '@/store';
|
import { useUserStore } from '@/store';
|
||||||
import { Message } from '@arco-design/web-vue';
|
import { Message } from '@arco-design/web-vue';
|
||||||
|
import { downloadExcel, DownloadExcelPrams } from '@/utils/excel';
|
||||||
import useTableOption from '@/hooks/table-option';
|
import useTableOption from '@/hooks/table-option';
|
||||||
import UserEdit from './components/user-edit.vue';
|
import UserEdit from './components/user-edit.vue';
|
||||||
|
|
||||||
@ -245,13 +268,12 @@ const {
|
|||||||
|
|
||||||
const userStore = useUserStore();
|
const userStore = useUserStore();
|
||||||
|
|
||||||
const basePagination: Pagination = {
|
const pagination: Pagination = {
|
||||||
page: 1,
|
page: 1,
|
||||||
size: 10,
|
size: 10,
|
||||||
|
current: 1,
|
||||||
|
total: null,
|
||||||
};
|
};
|
||||||
const pagination = reactive({
|
|
||||||
...basePagination,
|
|
||||||
});
|
|
||||||
|
|
||||||
const columns = computed<TableColumnData[]>(() => [
|
const columns = computed<TableColumnData[]>(() => [
|
||||||
{
|
{
|
||||||
@ -263,18 +285,30 @@ const columns = computed<TableColumnData[]>(() => [
|
|||||||
{
|
{
|
||||||
title: t('userTable.columns.username'),
|
title: t('userTable.columns.username'),
|
||||||
dataIndex: 'username',
|
dataIndex: 'username',
|
||||||
|
sortable: {
|
||||||
|
sortDirections: ['ascend', 'descend'],
|
||||||
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: t('userTable.columns.phone'),
|
title: t('userTable.columns.phone'),
|
||||||
dataIndex: 'phone',
|
dataIndex: 'phone',
|
||||||
|
sortable: {
|
||||||
|
sortDirections: ['ascend', 'descend'],
|
||||||
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: t('userTable.columns.email'),
|
title: t('userTable.columns.email'),
|
||||||
dataIndex: 'email',
|
dataIndex: 'email',
|
||||||
|
sortable: {
|
||||||
|
sortDirections: ['ascend', 'descend'],
|
||||||
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: t('userTable.columns.nickName'),
|
title: t('userTable.columns.nickName'),
|
||||||
dataIndex: 'nickName',
|
dataIndex: 'nickName',
|
||||||
|
sortable: {
|
||||||
|
sortDirections: ['ascend', 'descend'],
|
||||||
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: t('userTable.columns.address'),
|
title: t('userTable.columns.address'),
|
||||||
@ -311,9 +345,10 @@ const fetchData = async (
|
|||||||
try {
|
try {
|
||||||
const res = await userStore.getUserList(params);
|
const res = await userStore.getUserList(params);
|
||||||
renderData.value = res.data.records;
|
renderData.value = res.data.records;
|
||||||
|
pagination.page = res.data.page;
|
||||||
pagination.current = res.data.current;
|
pagination.current = res.data.current;
|
||||||
pagination.total = res.data.total;
|
pagination.total = res.data.total;
|
||||||
// pagination.size = data.size;
|
pagination.size = res.data.size;
|
||||||
} catch (err) {
|
} catch (err) {
|
||||||
// you can report use errorHandler or other
|
// you can report use errorHandler or other
|
||||||
} finally {
|
} finally {
|
||||||
@ -321,26 +356,58 @@ const fetchData = async (
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// 下载表格
|
||||||
|
const generateExcel = () => {
|
||||||
|
const param: DownloadExcelPrams = {
|
||||||
|
columns: [
|
||||||
|
{ title: '用户名', key: 'username' },
|
||||||
|
{ title: '昵称', key: 'nickName' },
|
||||||
|
{ title: '电话号码', key: 'phone' },
|
||||||
|
{ title: '部门Id', key: 'deptId' },
|
||||||
|
{ title: '角色Id', key: 'roleId' },
|
||||||
|
{ title: 'email', key: 'email' },
|
||||||
|
{ title: '启用状态', key: 'enabled' },
|
||||||
|
],
|
||||||
|
rows: renderData.value,
|
||||||
|
name: '用户表格',
|
||||||
|
};
|
||||||
|
downloadExcel(param);
|
||||||
|
};
|
||||||
|
|
||||||
// 查询
|
// 查询
|
||||||
const search = () => {
|
const search = () => {
|
||||||
fetchData({
|
fetchData({
|
||||||
...basePagination,
|
...pagination,
|
||||||
...formModel.value,
|
...formModel.value,
|
||||||
} as unknown as UserParams);
|
} as unknown as UserParams);
|
||||||
};
|
};
|
||||||
|
|
||||||
// 分页
|
// 分页发生改变
|
||||||
const onPageChange = (current: number) => {
|
const onPageChange = (current: number) => {
|
||||||
fetchData({ ...basePagination, current });
|
pagination.page = current;
|
||||||
|
pagination.current = current;
|
||||||
|
search();
|
||||||
};
|
};
|
||||||
|
|
||||||
fetchData();
|
// 数据条数改变
|
||||||
|
const onSizeChange = (size: number) => {
|
||||||
|
pagination.size = size;
|
||||||
|
search();
|
||||||
|
};
|
||||||
|
|
||||||
|
search();
|
||||||
|
|
||||||
// 重置
|
// 重置
|
||||||
const reset = () => {
|
const reset = () => {
|
||||||
formModel.value = generateFormModel();
|
formModel.value = generateFormModel();
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// 表格内部排序
|
||||||
|
const alignLeft = ref(false);
|
||||||
|
const handleSortChange = (data: any, extra: any, currentDataSource: any) => {
|
||||||
|
console.log('change', data, extra, currentDataSource);
|
||||||
|
};
|
||||||
|
|
||||||
// 是否启用
|
// 是否启用
|
||||||
const enabledStatus = async (record: string) => {
|
const enabledStatus = async (record: string) => {
|
||||||
record.enabled = !record.enabled;
|
record.enabled = !record.enabled;
|
||||||
|
@ -65,4 +65,8 @@ export default {
|
|||||||
'user.info.role.placeholder': 'Please select Role',
|
'user.info.role.placeholder': 'Please select Role',
|
||||||
'user.info.role.required': 'Role is required',
|
'user.info.role.required': 'Role is required',
|
||||||
|
|
||||||
|
|
||||||
|
// modalTitle
|
||||||
|
'createUser': 'Create User',
|
||||||
|
'editUser': 'Edit User Info'
|
||||||
};
|
};
|
||||||
|
@ -16,7 +16,7 @@ export default {
|
|||||||
'searchTable.form.selectDefault': '全部',
|
'searchTable.form.selectDefault': '全部',
|
||||||
'searchTable.operation.create': '新建',
|
'searchTable.operation.create': '新建',
|
||||||
'searchTable.operation.import': '批量导入',
|
'searchTable.operation.import': '批量导入',
|
||||||
'searchTable.operation.download': '下载',
|
'searchTable.operation.download': '导出',
|
||||||
// columns
|
// columns
|
||||||
'userTable.columns.index': '序号',
|
'userTable.columns.index': '序号',
|
||||||
'userTable.columns.nickName': '昵称',
|
'userTable.columns.nickName': '昵称',
|
||||||
@ -64,5 +64,10 @@ export default {
|
|||||||
'user.info.role':'角色',
|
'user.info.role':'角色',
|
||||||
'user.info.role.placeholder': '请选择角色',
|
'user.info.role.placeholder': '请选择角色',
|
||||||
'user.info.role.required': '请选择一个',
|
'user.info.role.required': '请选择一个',
|
||||||
|
'user.info.code':'验证码',
|
||||||
|
'user.info.code.placeholder':'请输入验证码',
|
||||||
|
|
||||||
|
// modalTitle
|
||||||
|
'createUser': '新增用户',
|
||||||
|
'editUser': '修改用户信息'
|
||||||
}
|
}
|
@ -1,33 +1,36 @@
|
|||||||
<template>
|
<template>
|
||||||
|
<!-- 新增 -->
|
||||||
<a-button
|
<a-button
|
||||||
v-permission="['BILL_QUERY']"
|
v-permission="['BILL_QUERY']"
|
||||||
v-if="props.isCreate"
|
v-if="props.isCreate"
|
||||||
type="primary"
|
type="primary"
|
||||||
size="small"
|
size="small"
|
||||||
:style="{ marginRight: '10px' }"
|
|
||||||
@click="handleClick"
|
@click="handleClick"
|
||||||
>
|
>
|
||||||
|
<template #icon><icon-plus /></template>
|
||||||
{{ modalTitle }}
|
{{ modalTitle }}
|
||||||
</a-button>
|
</a-button>
|
||||||
|
|
||||||
|
<!-- 修改 -->
|
||||||
<a-button
|
<a-button
|
||||||
v-permission="['BILL_UPDATE']"
|
v-permission="['BILL_UPDATE']"
|
||||||
v-if="!props.isCreate"
|
v-if="!props.isCreate"
|
||||||
size="small"
|
size="small"
|
||||||
type="primary"
|
type="primary"
|
||||||
:style="{ marginRight: '10px' }"
|
:style="{ marginRight: '10px', padding: '7px' }"
|
||||||
@click="handleClick"
|
@click="handleClick"
|
||||||
>
|
>
|
||||||
|
<template #icon><icon-edit /></template>
|
||||||
{{ modalTitle }}
|
{{ modalTitle }}
|
||||||
</a-button>
|
</a-button>
|
||||||
<a-modal
|
<a-modal
|
||||||
width="600px"
|
width="700px"
|
||||||
:visible="visible"
|
:visible="visible"
|
||||||
:footer="false"
|
:footer="false"
|
||||||
@cancel="handleCancel"
|
@cancel="handleCancel"
|
||||||
>
|
>
|
||||||
<template #title>{{ modalTitle }}</template>
|
<template #title>{{ modalTitle }}</template>
|
||||||
<a-form ref="createEditRef" :model="formData" :style="{ width: '500px' }">
|
<a-form ref="createEditRef" :model="formData" :style="{ width: '650px' }">
|
||||||
<a-form-item
|
<a-form-item
|
||||||
field="companyName"
|
field="companyName"
|
||||||
:label="$t('ticket.info.companyName')"
|
:label="$t('ticket.info.companyName')"
|
||||||
@ -54,18 +57,6 @@
|
|||||||
/>
|
/>
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
|
|
||||||
<a-form-item
|
|
||||||
field="body"
|
|
||||||
:label="$t('ticket.info.body')"
|
|
||||||
:validate-trigger="['change', 'input']"
|
|
||||||
:rules="[{ required: true, message: t('ticket.info.body.required') }]"
|
|
||||||
>
|
|
||||||
<a-textarea
|
|
||||||
v-model="formData.body"
|
|
||||||
:placeholder="$t('ticket.info.body.placeholder')"
|
|
||||||
/>
|
|
||||||
</a-form-item>
|
|
||||||
|
|
||||||
<a-form-item
|
<a-form-item
|
||||||
field="money"
|
field="money"
|
||||||
:label="$t('ticket.info.money')"
|
:label="$t('ticket.info.money')"
|
||||||
@ -105,16 +96,6 @@
|
|||||||
/>
|
/>
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
|
|
||||||
<a-form-item field="attachment" :label="$t('ticket.info.attachment')">
|
|
||||||
<a-upload
|
|
||||||
:file-list="fileList"
|
|
||||||
:custom-request="Onchange"
|
|
||||||
:limit="1"
|
|
||||||
:on-before-remove="removeAttact"
|
|
||||||
v-model="formData.attachId"
|
|
||||||
/>
|
|
||||||
</a-form-item>
|
|
||||||
|
|
||||||
<a-form-item
|
<a-form-item
|
||||||
field="deptId"
|
field="deptId"
|
||||||
:label="$t('ticket.info.dept')"
|
:label="$t('ticket.info.dept')"
|
||||||
@ -159,6 +140,29 @@
|
|||||||
>
|
>
|
||||||
{{ formData.comment }}
|
{{ formData.comment }}
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
|
|
||||||
|
<a-form-item
|
||||||
|
field="body"
|
||||||
|
:label="$t('ticket.info.body')"
|
||||||
|
:validate-trigger="['change', 'input']"
|
||||||
|
:rules="[{ required: true, message: t('ticket.info.body.required') }]"
|
||||||
|
>
|
||||||
|
<a-textarea
|
||||||
|
v-model="formData.body"
|
||||||
|
:placeholder="$t('ticket.info.body.placeholder')"
|
||||||
|
style="height: 100px"
|
||||||
|
/>
|
||||||
|
</a-form-item>
|
||||||
|
|
||||||
|
<a-form-item field="attachment" :label="$t('ticket.info.attachment')">
|
||||||
|
<a-upload
|
||||||
|
:file-list="fileList"
|
||||||
|
:custom-request="Onchange"
|
||||||
|
:limit="5"
|
||||||
|
:on-before-remove="removeAttact"
|
||||||
|
/>
|
||||||
|
</a-form-item>
|
||||||
|
|
||||||
<a-form-item>
|
<a-form-item>
|
||||||
<a-button type="dashed" @click="handleCancel">
|
<a-button type="dashed" @click="handleCancel">
|
||||||
{{ $t('cancel') }}</a-button
|
{{ $t('cancel') }}</a-button
|
||||||
@ -182,10 +186,9 @@
|
|||||||
import { useI18n } from 'vue-i18n';
|
import { useI18n } from 'vue-i18n';
|
||||||
import useVisible from '@/hooks/visible';
|
import useVisible from '@/hooks/visible';
|
||||||
import { computed, PropType, ref } from 'vue';
|
import { computed, PropType, ref } from 'vue';
|
||||||
import { computedAsync } from '@vueuse/core';
|
|
||||||
import { FormInstance } from '@arco-design/web-vue/es/form';
|
import { FormInstance } from '@arco-design/web-vue/es/form';
|
||||||
import { SelectOptionData } from '@arco-design/web-vue/es/select/interface';
|
import { SelectOptionData } from '@arco-design/web-vue/es/select/interface';
|
||||||
import { Message } from '@arco-design/web-vue';
|
import { FileItem, Message } from '@arco-design/web-vue';
|
||||||
import { useTicketStore, useUserStore, useRoleStore } from '@/store';
|
import { useTicketStore, useUserStore, useRoleStore } from '@/store';
|
||||||
import { TicketRecord } from '@/api/ticket';
|
import { TicketRecord } from '@/api/ticket';
|
||||||
import { deptList } from '@/api/dept';
|
import { deptList } from '@/api/dept';
|
||||||
@ -216,7 +219,7 @@ const formData = ref<TicketRecord>({
|
|||||||
type: '',
|
type: '',
|
||||||
contactEmail: '',
|
contactEmail: '',
|
||||||
companyName: '',
|
companyName: '',
|
||||||
attachId: '',
|
attachId: [],
|
||||||
auditorId: '',
|
auditorId: '',
|
||||||
userId: undefined,
|
userId: undefined,
|
||||||
submit: '',
|
submit: '',
|
||||||
@ -228,7 +231,7 @@ const emit = defineEmits(['refresh']);
|
|||||||
const deptOptions = ref();
|
const deptOptions = ref();
|
||||||
const getDeptData = async () => {
|
const getDeptData = async () => {
|
||||||
const res = await deptList();
|
const res = await deptList();
|
||||||
deptOptions.value = res.data;
|
deptOptions.value = res.data.records;
|
||||||
};
|
};
|
||||||
|
|
||||||
const typesOptions = computed<SelectOptionData[]>(() => [
|
const typesOptions = computed<SelectOptionData[]>(() => [
|
||||||
@ -250,8 +253,8 @@ let auiditRoleId = '';
|
|||||||
|
|
||||||
// 获取审核员ID
|
// 获取审核员ID
|
||||||
const getRoleId = async () => {
|
const getRoleId = async () => {
|
||||||
const res = await roleStore.getRoleList();
|
const res = await roleStore.getRoleList('');
|
||||||
res.data.forEach((item: any) => {
|
res.data.records.forEach((item: any) => {
|
||||||
if (item.name === 'auditor') {
|
if (item.name === 'auditor') {
|
||||||
auiditRoleId = item.id;
|
auiditRoleId = item.id;
|
||||||
}
|
}
|
||||||
@ -277,12 +280,13 @@ const optionDept = async (flag: boolean) => {
|
|||||||
|
|
||||||
let formDifer = {};
|
let formDifer = {};
|
||||||
const fileList = ref([]);
|
const fileList = ref([]);
|
||||||
|
const attachList = ref([]);
|
||||||
|
|
||||||
// 上传附件
|
// 上传附件
|
||||||
const Onchange = async (option: any) => {
|
const Onchange = async (option: any) => {
|
||||||
const FormDatas = new FormData();
|
const FormDatas = new FormData();
|
||||||
FormDatas.append('file', option.fileItem.file);
|
FormDatas.append('file', option.fileItem.file);
|
||||||
const res = await ticketStore.uploadFileTicket(FormDatas);
|
const res = await ticketStore.uploadFile(FormDatas);
|
||||||
if (res.status === 200) {
|
if (res.status === 200) {
|
||||||
Message.success({
|
Message.success({
|
||||||
content: t('upload.sucess'),
|
content: t('upload.sucess'),
|
||||||
@ -290,7 +294,10 @@ const Onchange = async (option: any) => {
|
|||||||
});
|
});
|
||||||
res.data.name = res.data.fileName;
|
res.data.name = res.data.fileName;
|
||||||
fileList.value.push(res.data);
|
fileList.value.push(res.data);
|
||||||
formData.value.attachId = res.data.id;
|
console.log('res', res.data.id);
|
||||||
|
attachList.value.push(res.data.id);
|
||||||
|
formData.value.attachId = attachList;
|
||||||
|
console.log('poti', formData.value.attachId);
|
||||||
} else {
|
} else {
|
||||||
Message.error({
|
Message.error({
|
||||||
content: t('upload.fail'),
|
content: t('upload.fail'),
|
||||||
@ -300,8 +307,13 @@ const Onchange = async (option: any) => {
|
|||||||
};
|
};
|
||||||
|
|
||||||
// 删除附件
|
// 删除附件
|
||||||
const removeAttact = () => {
|
const removeAttact = (fileItem: FileItem) => {
|
||||||
fileList.value.pop();
|
console.log('2', fileItem.id, fileList.value, attachList.value);
|
||||||
|
fileList.value = fileList.value.filter((item) => item.id !== fileItem.id);
|
||||||
|
attachList.value = attachList.value.filter((item) => item !== fileItem.id);
|
||||||
|
console.log('3', fileList.value, attachList.value);
|
||||||
|
formData.value.attachId = attachList.value;
|
||||||
|
console.log('3', formData.value.attachId);
|
||||||
};
|
};
|
||||||
|
|
||||||
// 组件被点击时
|
// 组件被点击时
|
||||||
@ -317,12 +329,13 @@ const handleClick = () => {
|
|||||||
// 票据数据
|
// 票据数据
|
||||||
formData.value = res.data;
|
formData.value = res.data;
|
||||||
|
|
||||||
// 附件内容
|
formData.value.attachId.forEach(async (item: any) => {
|
||||||
if (formData.value.attachId) {
|
console.log('item,', item);
|
||||||
const data = await ticketStore.getAttachment(formData.value.attachId);
|
const data = await ticketStore.getAttachment(item);
|
||||||
data.data.name = data.data.fileName;
|
data.data.name = data.data.fileName;
|
||||||
fileList.value.push(data.data);
|
fileList.value.push(data.data);
|
||||||
}
|
});
|
||||||
|
attachList.value = formData.value.attachId;
|
||||||
// 审核员信息
|
// 审核员信息
|
||||||
const auditInfo = await userStore.getUserDetail(
|
const auditInfo = await userStore.getUserDetail(
|
||||||
formData.value.auditorId
|
formData.value.auditorId
|
||||||
@ -389,7 +402,7 @@ const handleOk = async () => {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
createEditRef.value?.resetFields();
|
createEditRef.value?.resetFields();
|
||||||
removeAttact();
|
attachList.value = [];
|
||||||
emit('refresh');
|
emit('refresh');
|
||||||
setVisible(false);
|
setVisible(false);
|
||||||
}
|
}
|
||||||
@ -430,7 +443,8 @@ const handleStorage = async () => {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
createEditRef.value?.resetFields();
|
createEditRef.value?.resetFields();
|
||||||
removeAttact();
|
attachList.value = [];
|
||||||
|
fileList.value = [];
|
||||||
emit('refresh');
|
emit('refresh');
|
||||||
setVisible(false);
|
setVisible(false);
|
||||||
}
|
}
|
||||||
@ -438,7 +452,8 @@ const handleStorage = async () => {
|
|||||||
|
|
||||||
// 关闭
|
// 关闭
|
||||||
const handleCancel = async () => {
|
const handleCancel = async () => {
|
||||||
removeAttact();
|
attachList.value = [];
|
||||||
|
fileList.value = [];
|
||||||
createEditRef.value?.resetFields();
|
createEditRef.value?.resetFields();
|
||||||
setVisible(false);
|
setVisible(false);
|
||||||
};
|
};
|
||||||
|
@ -1,33 +1,37 @@
|
|||||||
<template>
|
<template>
|
||||||
|
<!-- 详情 -->
|
||||||
<a-button
|
<a-button
|
||||||
v-permission="['BILL_QUERY']"
|
v-permission="['BILL_QUERY']"
|
||||||
v-if="props.isDetail"
|
v-if="props.isDetail"
|
||||||
type="outline"
|
type="outline"
|
||||||
size="small"
|
size="small"
|
||||||
:style="{ marginRight: '10px' }"
|
:style="{ marginRight: '10px', padding: '7px' }"
|
||||||
@click="handleClick"
|
@click="handleClick"
|
||||||
>
|
>
|
||||||
|
<template #icon><icon-eye /></template>
|
||||||
{{ modalTitle }}
|
{{ modalTitle }}
|
||||||
</a-button>
|
</a-button>
|
||||||
|
|
||||||
|
<!-- 审核 -->
|
||||||
<a-button
|
<a-button
|
||||||
v-permission="['BILL_AUDIT']"
|
v-permission="['BILL_AUDIT']"
|
||||||
v-if="!props.isDetail"
|
v-if="!props.isDetail"
|
||||||
size="small"
|
size="small"
|
||||||
type="primary"
|
type="primary"
|
||||||
:style="{ marginRight: '10px' }"
|
:style="{ marginRight: '10px', padding: '7px' }"
|
||||||
@click="handleClick"
|
@click="handleClick"
|
||||||
>
|
>
|
||||||
|
<template #icon><icon-search /></template>
|
||||||
{{ modalTitle }}
|
{{ modalTitle }}
|
||||||
</a-button>
|
</a-button>
|
||||||
<a-modal
|
<a-modal
|
||||||
width="600px"
|
width="700px"
|
||||||
:visible="visible"
|
:visible="visible"
|
||||||
@ok="handleSubmit"
|
@ok="handleSubmit"
|
||||||
@cancel="handleCancel"
|
@cancel="handleCancel"
|
||||||
>
|
>
|
||||||
<template #title>{{ modalTitle }}</template>
|
<template #title>{{ modalTitle }}</template>
|
||||||
<a-form ref="createEditRef" :model="formData" :style="{ width: '500px' }">
|
<a-form ref="createEditRef" :model="formData" :style="{ width: '650px' }">
|
||||||
<a-form-item field="companyName" :label="$t('ticket.info.companyName')">
|
<a-form-item field="companyName" :label="$t('ticket.info.companyName')">
|
||||||
<div>
|
<div>
|
||||||
{{ formData.companyName }}
|
{{ formData.companyName }}
|
||||||
@ -70,39 +74,16 @@
|
|||||||
</div>
|
</div>
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
|
|
||||||
<a-form-item field="attachment" :label="$t('ticket.info.attachment')">
|
|
||||||
<a-upload
|
|
||||||
:file-list="fileList"
|
|
||||||
:custom-request="Onchange"
|
|
||||||
:limit="1"
|
|
||||||
:on-before-remove="removeAttact"
|
|
||||||
:show-remove-button="false"
|
|
||||||
v-model="formData.attachId"
|
|
||||||
/>
|
|
||||||
</a-form-item>
|
|
||||||
|
|
||||||
<a-form-item field="deptId" :label="$t('ticket.info.dept')">
|
<a-form-item field="deptId" :label="$t('ticket.info.dept')">
|
||||||
<a-tree-select
|
{{ formData.deptName }}
|
||||||
v-model="formData.deptId"
|
|
||||||
:field-names="{
|
|
||||||
key: 'id',
|
|
||||||
title: 'name',
|
|
||||||
children: 'children',
|
|
||||||
}"
|
|
||||||
:data="deptOptions"
|
|
||||||
disabled
|
|
||||||
style="color: black"
|
|
||||||
/>
|
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
|
|
||||||
|
<!-- 审核员 -->
|
||||||
<a-form-item field="auditorId" :label="$t('ticket.info.auditor')">
|
<a-form-item field="auditorId" :label="$t('ticket.info.auditor')">
|
||||||
<a-select v-model="formData.auditorId" disabled style="color: black">
|
{{ formData.auditor }}
|
||||||
<div v-for="(item, id) in auditorOptions" :key="id">
|
|
||||||
<a-option :value="item.id">{{ item.username }} </a-option>
|
|
||||||
</div>
|
|
||||||
</a-select>
|
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
|
|
||||||
|
<!-- 审核状态 -->
|
||||||
<a-form-item
|
<a-form-item
|
||||||
field="status"
|
field="status"
|
||||||
:label="$t('ticket.info.status')"
|
:label="$t('ticket.info.status')"
|
||||||
@ -112,7 +93,6 @@
|
|||||||
{{ formData.status }}
|
{{ formData.status }}
|
||||||
</div>
|
</div>
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
|
|
||||||
<a-form-item
|
<a-form-item
|
||||||
field="status"
|
field="status"
|
||||||
v-else
|
v-else
|
||||||
@ -121,18 +101,37 @@
|
|||||||
:validate-trigger="['change', 'input']"
|
:validate-trigger="['change', 'input']"
|
||||||
:rules="[{ required: true, message: t('ticket.info.status.required') }]"
|
:rules="[{ required: true, message: t('ticket.info.status.required') }]"
|
||||||
>
|
>
|
||||||
<a-radio-group
|
<a-radio-group v-model="formData.submit" default-value="true">
|
||||||
v-for="i in statusOptions"
|
<a-radio value="true">{{ t('pass') }}</a-radio>
|
||||||
:key="i.value"
|
<a-radio value="false">{{ t('failed') }}</a-radio>
|
||||||
v-model="formData.submit"
|
|
||||||
>
|
|
||||||
<a-radio :value="i.value">{{ i.label }}</a-radio>
|
|
||||||
</a-radio-group>
|
</a-radio-group>
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
|
|
||||||
<a-form-item field="comment" :label="$t('ticket.info.comment')">
|
<!-- 审核意见 -->
|
||||||
<a-textarea v-model="formData.comment" v-if="!props.isDetail" />
|
<a-form-item
|
||||||
<div v-else>{{ formData.comment }} </div>
|
field="comment"
|
||||||
|
:label="$t('ticket.info.comment')"
|
||||||
|
v-if="!props.isDetail"
|
||||||
|
>
|
||||||
|
<a-textarea v-model="formData.comment" style="height: 200px" />
|
||||||
|
</a-form-item>
|
||||||
|
<a-form-item field="comment" :label="$t('ticket.info.comment')" v-else>
|
||||||
|
<div>{{ formData.comment || '无' }}</div>
|
||||||
|
</a-form-item>
|
||||||
|
|
||||||
|
<!-- 附件 -->
|
||||||
|
<a-form-item field="attachment" :label="$t('ticket.info.attachment')">
|
||||||
|
<a-upload
|
||||||
|
:file-list="fileList"
|
||||||
|
:custom-request="Onchange"
|
||||||
|
:limit="5"
|
||||||
|
:disabled="true"
|
||||||
|
:on-before-remove="removeAttact"
|
||||||
|
:show-remove-button="false"
|
||||||
|
v-model="formData.attachId"
|
||||||
|
v-if="fileList.length !== 0"
|
||||||
|
/>
|
||||||
|
<div v-else>无</div>
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
</a-form>
|
</a-form>
|
||||||
</a-modal>
|
</a-modal>
|
||||||
@ -142,7 +141,6 @@
|
|||||||
import { useI18n } from 'vue-i18n';
|
import { useI18n } from 'vue-i18n';
|
||||||
import useVisible from '@/hooks/visible';
|
import useVisible from '@/hooks/visible';
|
||||||
import { computed, PropType, ref } from 'vue';
|
import { computed, PropType, ref } from 'vue';
|
||||||
import { computedAsync } from '@vueuse/core';
|
|
||||||
import { FormInstance } from '@arco-design/web-vue/es/form';
|
import { FormInstance } from '@arco-design/web-vue/es/form';
|
||||||
import { SelectOptionData } from '@arco-design/web-vue/es/select/interface';
|
import { SelectOptionData } from '@arco-design/web-vue/es/select/interface';
|
||||||
import { Message } from '@arco-design/web-vue';
|
import { Message } from '@arco-design/web-vue';
|
||||||
@ -178,8 +176,10 @@ const formData = ref<TicketRecord>({
|
|||||||
companyName: '',
|
companyName: '',
|
||||||
attachId: '',
|
attachId: '',
|
||||||
auditorId: '',
|
auditorId: '',
|
||||||
submit: undefined,
|
submit: true,
|
||||||
comment: '',
|
comment: '',
|
||||||
|
deptName: '',
|
||||||
|
auditor: '',
|
||||||
});
|
});
|
||||||
|
|
||||||
const emit = defineEmits(['refresh']);
|
const emit = defineEmits(['refresh']);
|
||||||
@ -187,15 +187,15 @@ const emit = defineEmits(['refresh']);
|
|||||||
const deptOptions = ref();
|
const deptOptions = ref();
|
||||||
const getDeptData = async () => {
|
const getDeptData = async () => {
|
||||||
const res = await deptList();
|
const res = await deptList();
|
||||||
deptOptions.value = res.data;
|
deptOptions.value = res.data.records;
|
||||||
};
|
};
|
||||||
|
|
||||||
let auiditRoleId = '';
|
let auiditRoleId = '';
|
||||||
|
|
||||||
// 获取审核员ID
|
// 获取审核员ID
|
||||||
const getRoleId = async () => {
|
const getRoleId = async () => {
|
||||||
const res = await roleStore.getRoleList();
|
const res = await roleStore.getRoleList('');
|
||||||
res.data.forEach((item: any) => {
|
res.data.records.forEach((item: any) => {
|
||||||
if (item.name === 'auditor') {
|
if (item.name === 'auditor') {
|
||||||
auiditRoleId = item.id;
|
auiditRoleId = item.id;
|
||||||
}
|
}
|
||||||
@ -216,17 +216,6 @@ const optionDept = async () => {
|
|||||||
auditorOptions.value = res.data.records;
|
auditorOptions.value = res.data.records;
|
||||||
};
|
};
|
||||||
|
|
||||||
const statusOptions = computed<SelectOptionData[]>(() => [
|
|
||||||
{
|
|
||||||
label: t('pass'),
|
|
||||||
value: true,
|
|
||||||
},
|
|
||||||
{
|
|
||||||
label: t('failed'),
|
|
||||||
value: false,
|
|
||||||
},
|
|
||||||
]);
|
|
||||||
|
|
||||||
const fileList = ref([]);
|
const fileList = ref([]);
|
||||||
// 组件被点击时
|
// 组件被点击时
|
||||||
const handleClick = async () => {
|
const handleClick = async () => {
|
||||||
@ -237,18 +226,29 @@ const handleClick = async () => {
|
|||||||
const res = await ticketStore.getDetail(ticketId);
|
const res = await ticketStore.getDetail(ticketId);
|
||||||
// 票据数据
|
// 票据数据
|
||||||
formData.value = res.data;
|
formData.value = res.data;
|
||||||
|
formData.value.submit = 'true';
|
||||||
// 附件内容
|
// 附件内容
|
||||||
if (formData.value.attachId) {
|
formData.value.attachId.forEach(async (item: any) => {
|
||||||
const data = await ticketStore.getAttachment(formData.value.attachId);
|
// console.log('item,', item);
|
||||||
|
const data = await ticketStore.getAttachment(item);
|
||||||
data.data.name = data.data.fileName;
|
data.data.name = data.data.fileName;
|
||||||
fileList.value.push(data.data);
|
fileList.value.push(data.data);
|
||||||
}
|
});
|
||||||
|
|
||||||
// 审核员信息
|
// 审核员信息
|
||||||
const auditInfo = await userStore.getUserDetail(formData.value.auditorId);
|
const auditInfo = await userStore.getUserDetail(formData.value.auditorId);
|
||||||
formData.value.deptId = auditInfo.data.deptId;
|
formData.value.deptId = auditInfo.data.deptId;
|
||||||
optionDept().then(() => {
|
optionDept().then(() => {
|
||||||
|
deptOptions.value.forEach((item: any) => {
|
||||||
|
if (item.id === formData.value.deptId) {
|
||||||
|
formData.value.deptName = item.name;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
auditorOptions.value.forEach((item: any) => {
|
||||||
|
if (item.id === formData.value.auditorId) {
|
||||||
|
formData.value.auditor = item.username;
|
||||||
|
}
|
||||||
|
});
|
||||||
setVisible(true);
|
setVisible(true);
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
@ -271,7 +271,7 @@ const handleSubmit = async () => {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
fileList.value.pop();
|
fileList.value = [];
|
||||||
emit('refresh');
|
emit('refresh');
|
||||||
setVisible(false);
|
setVisible(false);
|
||||||
}
|
}
|
||||||
@ -279,7 +279,7 @@ const handleSubmit = async () => {
|
|||||||
|
|
||||||
// 关闭
|
// 关闭
|
||||||
const handleCancel = async () => {
|
const handleCancel = async () => {
|
||||||
fileList.value.pop();
|
fileList.value = [];
|
||||||
createEditRef.value?.resetFields();
|
createEditRef.value?.resetFields();
|
||||||
setVisible(false);
|
setVisible(false);
|
||||||
};
|
};
|
||||||
|
@ -1,7 +1,18 @@
|
|||||||
<template>
|
<template>
|
||||||
<div class="container">
|
<div class="container">
|
||||||
<Breadcrumb :items="['menu.ticket', 'menu.ticket.manage']" />
|
<Breadcrumb :items="['menu.ticket', 'menu.ticket.manage']" />
|
||||||
<a-card class="general-card" :title="$t('menu.list.searchTable')">
|
<a-card class="general-card">
|
||||||
|
<a-tabs default-active-key="PASS" @change="changeTop">
|
||||||
|
<a-tab-pane key="PASS" :title="t('pass')"> </a-tab-pane>
|
||||||
|
<a-tab-pane key="FAILED" :title="t('failed')"> </a-tab-pane>
|
||||||
|
<a-tab-pane key="EXAMINE" :title="t('unreviewed')"> </a-tab-pane>
|
||||||
|
<a-tab-pane
|
||||||
|
key="SUBMIT"
|
||||||
|
:title="t('drafts')"
|
||||||
|
v-if="userStore.permissions !== 'auditor'"
|
||||||
|
>
|
||||||
|
</a-tab-pane>
|
||||||
|
</a-tabs>
|
||||||
<a-row>
|
<a-row>
|
||||||
<a-col :flex="1">
|
<a-col :flex="1">
|
||||||
<a-form
|
<a-form
|
||||||
@ -11,6 +22,7 @@
|
|||||||
label-align="right"
|
label-align="right"
|
||||||
>
|
>
|
||||||
<a-row :gutter="16">
|
<a-row :gutter="16">
|
||||||
|
<!-- 公司名称 -->
|
||||||
<a-col :span="8">
|
<a-col :span="8">
|
||||||
<a-form-item
|
<a-form-item
|
||||||
field="companyName"
|
field="companyName"
|
||||||
@ -25,6 +37,7 @@
|
|||||||
</a-form-item>
|
</a-form-item>
|
||||||
</a-col>
|
</a-col>
|
||||||
|
|
||||||
|
<!-- 标题 -->
|
||||||
<a-col :span="8">
|
<a-col :span="8">
|
||||||
<a-form-item
|
<a-form-item
|
||||||
field="title"
|
field="title"
|
||||||
@ -36,9 +49,42 @@
|
|||||||
/>
|
/>
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
</a-col>
|
</a-col>
|
||||||
|
|
||||||
|
<!-- 用户 -->
|
||||||
|
<a-col :span="8">
|
||||||
|
<a-form-item
|
||||||
|
field="userName"
|
||||||
|
:label="$t('searchTable.form.userName')"
|
||||||
|
>
|
||||||
|
<a-input
|
||||||
|
v-model="formModel.userName"
|
||||||
|
:placeholder="$t('searchTable.form.committer.placeholder')"
|
||||||
|
/>
|
||||||
|
</a-form-item>
|
||||||
|
</a-col>
|
||||||
</a-row>
|
</a-row>
|
||||||
|
|
||||||
<a-row :gutter="16">
|
<a-row :gutter="16">
|
||||||
|
<!-- 金额 -->
|
||||||
|
<a-col :span="8">
|
||||||
|
<a-form-item
|
||||||
|
field="money"
|
||||||
|
:label="$t('searchTable.form.money')"
|
||||||
|
>
|
||||||
|
<a-input-group>
|
||||||
|
<a-input
|
||||||
|
v-model="formModel.minMoney"
|
||||||
|
:placeholder="$t('searchTable.form.min')"
|
||||||
|
/>
|
||||||
|
<a-input
|
||||||
|
v-model="formModel.maxMoney"
|
||||||
|
:placeholder="$t('searchTable.form.max')"
|
||||||
|
/>
|
||||||
|
</a-input-group>
|
||||||
|
</a-form-item>
|
||||||
|
</a-col>
|
||||||
|
|
||||||
|
<!-- 票据类型 -->
|
||||||
<a-col :span="8">
|
<a-col :span="8">
|
||||||
<a-form-item field="type" :label="$t('searchTable.form.type')">
|
<a-form-item field="type" :label="$t('searchTable.form.type')">
|
||||||
<a-select
|
<a-select
|
||||||
@ -49,15 +95,16 @@
|
|||||||
</a-form-item>
|
</a-form-item>
|
||||||
</a-col>
|
</a-col>
|
||||||
|
|
||||||
|
<!-- 时间 -->
|
||||||
<a-col :span="8">
|
<a-col :span="8">
|
||||||
<a-form-item
|
<a-form-item field="time" :label="$t('searchTable.form.time')">
|
||||||
field="status"
|
<a-range-picker
|
||||||
:label="$t('searchTable.form.status')"
|
v-model="formModel.time"
|
||||||
>
|
style="width: 360px"
|
||||||
<a-select
|
show-time
|
||||||
v-model="formModel.status"
|
@select="onSelect"
|
||||||
:options="statusOptions"
|
value-format="YYYY-MM-DD"
|
||||||
:placeholder="$t('searchTable.form.status.placeholder')"
|
:allow-clear="false"
|
||||||
/>
|
/>
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
</a-col>
|
</a-col>
|
||||||
@ -88,12 +135,19 @@
|
|||||||
<a-col :span="12">
|
<a-col :span="12">
|
||||||
<a-space>
|
<a-space>
|
||||||
<TicketForm
|
<TicketForm
|
||||||
|
v-if="formModel.status === 'SUBMIT'"
|
||||||
ref="createEditRef"
|
ref="createEditRef"
|
||||||
:prem="ticketItem"
|
:prem="formModel"
|
||||||
:is-create="true"
|
:is-create="true"
|
||||||
@refresh="search"
|
@refresh="search"
|
||||||
/>
|
/>
|
||||||
</a-space>
|
</a-space>
|
||||||
|
<a-button @click="generateExcel" style="margin-left: 5px">
|
||||||
|
<template #icon>
|
||||||
|
<icon-download size="16" />
|
||||||
|
</template>
|
||||||
|
{{ $t('searchTable.operation.download') }}
|
||||||
|
</a-button>
|
||||||
</a-col>
|
</a-col>
|
||||||
<a-col
|
<a-col
|
||||||
:span="12"
|
:span="12"
|
||||||
@ -162,10 +216,23 @@
|
|||||||
:columns="(cloneColumns as TableColumnData[])"
|
:columns="(cloneColumns as TableColumnData[])"
|
||||||
:data="renderData"
|
:data="renderData"
|
||||||
:bordered="false"
|
:bordered="false"
|
||||||
:pagination="pagination"
|
:pagination="false"
|
||||||
:size="size"
|
:size="size"
|
||||||
|
:expandable="expandable"
|
||||||
@page-change="onPageChange"
|
@page-change="onPageChange"
|
||||||
|
style="margin-bottom: 40px"
|
||||||
>
|
>
|
||||||
|
<template #expand-row="{ record }">
|
||||||
|
<!-- 下面展示子表格,根据需求对子table进行属性配置 -->
|
||||||
|
<a-descriptions layout="inline-horizontal" :column="1" bordered>
|
||||||
|
<descriptions-item :label="t('ticket.info.contactEmail')">
|
||||||
|
{{ record.contactEmail }}
|
||||||
|
</descriptions-item>
|
||||||
|
<descriptions-item :label="t('ticket.info.body')">
|
||||||
|
{{ record.body }}
|
||||||
|
</descriptions-item>
|
||||||
|
</a-descriptions>
|
||||||
|
</template>
|
||||||
<template #index="{ rowIndex }">
|
<template #index="{ rowIndex }">
|
||||||
{{ rowIndex + 1 + (pagination.current - 1) * pagination.size }}
|
{{ rowIndex + 1 + (pagination.current - 1) * pagination.size }}
|
||||||
</template>
|
</template>
|
||||||
@ -173,6 +240,21 @@
|
|||||||
{{ dayjs(record.createTime).format('YYYY-MM-DD') }}
|
{{ dayjs(record.createTime).format('YYYY-MM-DD') }}
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
|
<template #status="{ record }">
|
||||||
|
<a-button status="success" v-if="record.status === '审核通过'">{{
|
||||||
|
record.status
|
||||||
|
}}</a-button>
|
||||||
|
<a-button status="danger" v-if="record.status === '审核未通过'">{{
|
||||||
|
record.status
|
||||||
|
}}</a-button>
|
||||||
|
<a-button status="normal" v-if="record.status === '待审核'">{{
|
||||||
|
record.status
|
||||||
|
}}</a-button>
|
||||||
|
<a-button status="warning" v-if="record.status === '待提交'">{{
|
||||||
|
record.status
|
||||||
|
}}</a-button>
|
||||||
|
</template>
|
||||||
|
|
||||||
<template #operations="{ record }">
|
<template #operations="{ record }">
|
||||||
<!-- 详情 -->
|
<!-- 详情 -->
|
||||||
<TicketEdit
|
<TicketEdit
|
||||||
@ -210,18 +292,33 @@
|
|||||||
size="small"
|
size="small"
|
||||||
status="danger"
|
status="danger"
|
||||||
v-permission="['BILL_DELETE']"
|
v-permission="['BILL_DELETE']"
|
||||||
|
v-if="
|
||||||
|
record.status === '待提交' || record.status === '审核未通过'
|
||||||
|
"
|
||||||
|
style="padding: 7px"
|
||||||
>
|
>
|
||||||
|
<template #icon><icon-delete /></template>
|
||||||
{{ $t('delete') }}
|
{{ $t('delete') }}
|
||||||
</a-button>
|
</a-button>
|
||||||
</a-popconfirm>
|
</a-popconfirm>
|
||||||
</template>
|
</template>
|
||||||
</a-table>
|
</a-table>
|
||||||
|
<a-pagination
|
||||||
|
style="float: right; position: relative; right: 1px; bottom: 25px"
|
||||||
|
:total="pagination.total"
|
||||||
|
@page-size-change="onSizeChange"
|
||||||
|
:size="size"
|
||||||
|
@change="onPageChange"
|
||||||
|
show-total
|
||||||
|
show-jumper
|
||||||
|
show-page-size
|
||||||
|
/>
|
||||||
</a-card>
|
</a-card>
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
<script lang="ts" setup>
|
<script lang="ts" setup>
|
||||||
import { computed, ref, watch, reactive } from 'vue';
|
import { computed, reactive, ref, watch } from 'vue';
|
||||||
import { useI18n } from 'vue-i18n';
|
import { useI18n } from 'vue-i18n';
|
||||||
import useLoading from '@/hooks/loading';
|
import useLoading from '@/hooks/loading';
|
||||||
import useTableOption from '@/hooks/table-option';
|
import useTableOption from '@/hooks/table-option';
|
||||||
@ -232,6 +329,7 @@ import dayjs from 'dayjs';
|
|||||||
import { Message } from '@arco-design/web-vue';
|
import { Message } from '@arco-design/web-vue';
|
||||||
import { useTicketStore, useUserStore } from '@/store';
|
import { useTicketStore, useUserStore } from '@/store';
|
||||||
import { TicketRecord } from '@/api/ticket';
|
import { TicketRecord } from '@/api/ticket';
|
||||||
|
import { downloadExcel, DownloadExcelPrams } from '@/utils/excel';
|
||||||
import TicketEdit from './components/ticket-edit.vue';
|
import TicketEdit from './components/ticket-edit.vue';
|
||||||
import TicketForm from './components/form-edit.vue';
|
import TicketForm from './components/form-edit.vue';
|
||||||
|
|
||||||
@ -255,13 +353,27 @@ const generateFormModel = () => {
|
|||||||
companyName: '',
|
companyName: '',
|
||||||
title: '',
|
title: '',
|
||||||
type: '',
|
type: '',
|
||||||
status: '',
|
// 默认先展示票据审核通过的
|
||||||
|
status: 'PASS',
|
||||||
|
time: [],
|
||||||
|
userName: '',
|
||||||
|
minMoney: '',
|
||||||
|
maxMoney: '',
|
||||||
|
startTime: '',
|
||||||
|
endTime: '',
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
const { t } = useI18n();
|
const { t } = useI18n();
|
||||||
const renderData = ref<TicketRecord[]>([]);
|
const renderData = ref<TicketRecord[]>([]);
|
||||||
const formModel = ref(generateFormModel());
|
const formModel = ref(generateFormModel());
|
||||||
|
const currentStatus = ref('PASS');
|
||||||
|
|
||||||
|
// 拓展行
|
||||||
|
const expandable = reactive({
|
||||||
|
title: ' ',
|
||||||
|
expandedRowRender: (record: any) => {},
|
||||||
|
});
|
||||||
|
|
||||||
// 表格头部
|
// 表格头部
|
||||||
const columns = computed<TableColumnData[]>(() => [
|
const columns = computed<TableColumnData[]>(() => [
|
||||||
@ -273,6 +385,9 @@ const columns = computed<TableColumnData[]>(() => [
|
|||||||
{
|
{
|
||||||
title: t('ticketTable.columns.companyName'),
|
title: t('ticketTable.columns.companyName'),
|
||||||
dataIndex: 'companyName',
|
dataIndex: 'companyName',
|
||||||
|
sortable: {
|
||||||
|
sortDirections: ['ascend', 'descend'],
|
||||||
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: t('ticketTable.columns.title'),
|
title: t('ticketTable.columns.title'),
|
||||||
@ -281,14 +396,36 @@ const columns = computed<TableColumnData[]>(() => [
|
|||||||
{
|
{
|
||||||
title: t('ticketTable.columns.money'),
|
title: t('ticketTable.columns.money'),
|
||||||
dataIndex: 'money',
|
dataIndex: 'money',
|
||||||
|
sortable: {
|
||||||
|
sortDirections: ['ascend', 'descend'],
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: t('ticketTable.columns.userName'),
|
||||||
|
dataIndex: 'userName',
|
||||||
|
sortable: {
|
||||||
|
sortDirections: ['ascend', 'descend'],
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: t('ticketTable.columns.createTime'),
|
||||||
|
dataIndex: 'createTime',
|
||||||
|
sortable: {
|
||||||
|
sortDirections: ['ascend', 'descend'],
|
||||||
|
},
|
||||||
|
slotName: 'createTime',
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: t('ticketTable.columns.type'),
|
title: t('ticketTable.columns.type'),
|
||||||
dataIndex: 'type',
|
dataIndex: 'type',
|
||||||
|
sortable: {
|
||||||
|
sortDirections: ['ascend', 'descend'],
|
||||||
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: t('ticketTable.columns.status'),
|
title: t('ticketTable.columns.status'),
|
||||||
dataIndex: 'status',
|
dataIndex: 'status',
|
||||||
|
slotName: 'status',
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: t('searchTable.columns.operations'),
|
title: t('searchTable.columns.operations'),
|
||||||
@ -312,39 +449,56 @@ const typesOptions = computed<SelectOptionData[]>(() => [
|
|||||||
},
|
},
|
||||||
]);
|
]);
|
||||||
|
|
||||||
const statusOptions = computed<SelectOptionData[]>(() => [
|
|
||||||
{
|
|
||||||
label: t('unsubmitted'),
|
|
||||||
value: 'SUBMIT',
|
|
||||||
},
|
|
||||||
{
|
|
||||||
label: t('unreviewed'),
|
|
||||||
value: 'EXAMINE',
|
|
||||||
},
|
|
||||||
{
|
|
||||||
label: t('pass'),
|
|
||||||
value: 'PASS',
|
|
||||||
},
|
|
||||||
{
|
|
||||||
label: t('failed'),
|
|
||||||
value: 'FAILED',
|
|
||||||
},
|
|
||||||
]);
|
|
||||||
|
|
||||||
// 基础分页查询的信息
|
// 基础分页查询的信息
|
||||||
const basePagination: Pagination = {
|
const pagination: Pagination = {
|
||||||
page: 1,
|
page: 1,
|
||||||
size: 10,
|
size: 10,
|
||||||
|
current: 1,
|
||||||
|
total: 1,
|
||||||
};
|
};
|
||||||
|
|
||||||
// 映射
|
// 下载表格
|
||||||
const pagination = reactive({
|
const generateExcel = () => {
|
||||||
...basePagination,
|
const param: DownloadExcelPrams = {
|
||||||
});
|
columns: [
|
||||||
|
{ title: '公司', key: 'companyName' },
|
||||||
|
{ title: '标题', key: 'title' },
|
||||||
|
{ title: '金额', key: 'money' },
|
||||||
|
{ title: '内容', key: 'body' },
|
||||||
|
{ title: '联系邮箱', key: 'contactEmail' },
|
||||||
|
{ title: '创建时间', key: 'createTime' },
|
||||||
|
{ title: '类型', key: 'type' },
|
||||||
|
{ title: '审核状态', key: 'status' },
|
||||||
|
],
|
||||||
|
rows: renderData.value,
|
||||||
|
name: '票据表格',
|
||||||
|
};
|
||||||
|
downloadExcel(param);
|
||||||
|
};
|
||||||
|
|
||||||
|
// 时间段选择
|
||||||
|
const onSelect = (dateString: any, date: any) => {
|
||||||
|
formModel.value.startTime = String(dateString[0]);
|
||||||
|
formModel.value.endTime = String(dateString[1]);
|
||||||
|
};
|
||||||
|
|
||||||
|
// 时间段改变
|
||||||
|
const onChange = (dateString: any, date: any) => {
|
||||||
|
formModel.value.startTime = String(dateString[0]);
|
||||||
|
formModel.value.endTime = String(dateString[1]);
|
||||||
|
};
|
||||||
|
|
||||||
// 分页发生改变
|
// 分页发生改变
|
||||||
const onPageChange = (current: number) => {
|
const onPageChange = (current: number) => {
|
||||||
fetchData({ ...basePagination, ...formModel.value, current });
|
pagination.page = current;
|
||||||
|
pagination.current = current;
|
||||||
|
search();
|
||||||
|
};
|
||||||
|
|
||||||
|
// 数据条数改变
|
||||||
|
const onSizeChange = (size: number) => {
|
||||||
|
pagination.size = size;
|
||||||
|
search();
|
||||||
};
|
};
|
||||||
|
|
||||||
// 获取数据
|
// 获取数据
|
||||||
@ -383,22 +537,32 @@ const fetchData = async (params: {
|
|||||||
|
|
||||||
// 模糊查询
|
// 模糊查询
|
||||||
const search = () => {
|
const search = () => {
|
||||||
|
// 删除time
|
||||||
|
const { time, ...auditDate } = formModel.value;
|
||||||
|
|
||||||
fetchData({
|
fetchData({
|
||||||
...basePagination,
|
...pagination,
|
||||||
...formModel.value,
|
...auditDate,
|
||||||
current: '1',
|
|
||||||
} as unknown as any);
|
} as unknown as any);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// 切换标签页
|
||||||
|
const changeTop = (key: any) => {
|
||||||
|
formModel.value.status = key;
|
||||||
|
currentStatus.value = key;
|
||||||
|
search();
|
||||||
|
};
|
||||||
|
|
||||||
search();
|
search();
|
||||||
|
|
||||||
// 重置
|
// 重置
|
||||||
const reset = () => {
|
const reset = () => {
|
||||||
formModel.value = generateFormModel();
|
formModel.value = generateFormModel();
|
||||||
|
formModel.value.status = currentStatus.value;
|
||||||
};
|
};
|
||||||
|
|
||||||
// 删除票据
|
// 删除票据
|
||||||
const handleDelete = async (record) => {
|
const handleDelete = async (record: any) => {
|
||||||
const res = await ticketStore.removeTicket(record.id);
|
const res = await ticketStore.removeTicket(record.id);
|
||||||
if (res.status === 200) {
|
if (res.status === 200) {
|
||||||
Message.success({
|
Message.success({
|
||||||
|
@ -16,10 +16,19 @@ export default {
|
|||||||
'searchTable.form.companyName.placeholder': 'Please enter Company',
|
'searchTable.form.companyName.placeholder': 'Please enter Company',
|
||||||
'searchTable.form.title':'Title',
|
'searchTable.form.title':'Title',
|
||||||
'searchTable.form.title.placeholder': 'Please enter Title',
|
'searchTable.form.title.placeholder': 'Please enter Title',
|
||||||
|
'searchTable.form.money':'Money',
|
||||||
|
'searchTable.form.money.placeholder': 'Please enter Money',
|
||||||
|
'searchTable.form.userName':'UserName',
|
||||||
|
'searchTable.form.userName.placeholder': 'Please enter UserName',
|
||||||
'searchTable.form.type':'Type',
|
'searchTable.form.type':'Type',
|
||||||
'searchTable.form.type.placeholder': 'Please select Type',
|
'searchTable.form.type.placeholder': 'Please select Type',
|
||||||
'searchTable.form.status': 'Status',
|
'searchTable.form.status': 'Status',
|
||||||
'searchTable.form.status.placeholder': 'Please select Status',
|
'searchTable.form.status.placeholder': 'Please select Status',
|
||||||
|
'searchTable.form.time':'Time',
|
||||||
|
'searchTable.form.time.placeholder': 'Please select Time',
|
||||||
|
'searchTable.form.min':'Min money',
|
||||||
|
'searchTable.form.max':'Max money',
|
||||||
|
|
||||||
|
|
||||||
'Confirm the deletion of this ticket': 'Confirm the deletion of this ticket?',
|
'Confirm the deletion of this ticket': 'Confirm the deletion of this ticket?',
|
||||||
|
|
||||||
@ -44,37 +53,39 @@ export default {
|
|||||||
'unreviewed': 'Unreviewed',
|
'unreviewed': 'Unreviewed',
|
||||||
'pass': 'Pass',
|
'pass': 'Pass',
|
||||||
'failed': 'Failed',
|
'failed': 'Failed',
|
||||||
|
'drafts': 'Drafts',
|
||||||
|
|
||||||
"ticket.info.companyName": 'Company',
|
"ticket.info.companyName": 'Company:',
|
||||||
"ticket.info.companyName.required": 'CompanyName is required',
|
"ticket.info.companyName.required": 'CompanyName is required',
|
||||||
"ticket.info.companyName.placeholder": 'Please enter CompanyName',
|
"ticket.info.companyName.placeholder": 'Please enter CompanyName',
|
||||||
"ticket.info.title": 'Title',
|
"ticket.info.title": 'Title:',
|
||||||
"ticket.info.title.required": 'Title is required',
|
"ticket.info.title.required": 'Title is required',
|
||||||
"ticket.info.title.placeholder": 'Please enter Title',
|
"ticket.info.title.placeholder": 'Please enter Title',
|
||||||
"ticket.info.body": 'Content',
|
"ticket.info.body": 'Content:',
|
||||||
"ticket.info.body.required": 'Content is required',
|
"ticket.info.body.required": 'Content is required',
|
||||||
"ticket.info.body.placeholder": 'Please enter Content',
|
"ticket.info.body.placeholder": 'Please enter Content',
|
||||||
"ticket.info.money": 'Money',
|
"ticket.info.money": 'Money:',
|
||||||
"ticket.info.money.required": 'Money is required',
|
"ticket.info.money.required": 'Money is required',
|
||||||
"ticket.info.money.placeholder": 'Please enter Money',
|
"ticket.info.money.placeholder": 'Please enter Money',
|
||||||
"ticket.info.contactEmail": 'Email',
|
"ticket.info.contactEmail": 'Email:',
|
||||||
"ticket.info.createTime": 'CreateTime',
|
"ticket.info.createTime": 'CreateTime:',
|
||||||
"ticket.info.contactEmail.required": 'contactEmail is required',
|
"ticket.info.contactEmail.required": 'contactEmail is required',
|
||||||
"ticket.info.contactEmail.placeholder": 'Please enter contactEmail',
|
"ticket.info.contactEmail.placeholder": 'Please enter contactEmail',
|
||||||
"ticket.info.type": 'Type',
|
"ticket.info.type": 'Type:',
|
||||||
"ticket.info.type.required": 'Type is required',
|
"ticket.info.type.required": 'Type is required',
|
||||||
"ticket.info.type.placeholder": 'Please select Type',
|
"ticket.info.type.placeholder": 'Please select Type',
|
||||||
"ticket.info.attachment": 'Attachment',
|
"ticket.info.attachment": 'Attachment:',
|
||||||
"ticket.info.dept": 'Dept',
|
"ticket.info.dept": 'Dept:',
|
||||||
"ticket.info.dept.required": 'Dept is required',
|
"ticket.info.dept.required": 'Dept is required',
|
||||||
"ticket.info.dept.placeholder": 'Please select Dept',
|
"ticket.info.dept.placeholder": 'Please select Dept',
|
||||||
"ticket.info.auditor": 'Auditor',
|
"ticket.info.auditor": 'Auditor:',
|
||||||
"ticket.info.auditor.required": 'Auditor is required',
|
"ticket.info.auditor.required": 'Auditor is required',
|
||||||
"ticket.info.auditor.placeholder": 'Please select Auditor',
|
"ticket.info.auditor.placeholder": 'Please select Auditor',
|
||||||
"ticket.info.status": 'Status',
|
"ticket.info.status": 'Status:',
|
||||||
"ticket.info.status.required": 'Status is required',
|
"ticket.info.status.required": 'Status is required',
|
||||||
"ticket.info.status.placeholder": 'Please select Status',
|
"ticket.info.status.placeholder": 'Please select Status',
|
||||||
"ticket.info.comment": 'Comment',
|
"ticket.info.comment": 'Comment:',
|
||||||
|
"ticketTable.columns.userName":'userName',
|
||||||
|
|
||||||
'upload.sucess': 'Upload Sucess',
|
'upload.sucess': 'Upload Sucess',
|
||||||
'upload.fail': 'Upload Fail',
|
'upload.fail': 'Upload Fail',
|
||||||
|
@ -15,10 +15,19 @@ export default {
|
|||||||
'searchTable.form.companyName.placeholder': '请输入公司名称',
|
'searchTable.form.companyName.placeholder': '请输入公司名称',
|
||||||
'searchTable.form.title':'标题',
|
'searchTable.form.title':'标题',
|
||||||
'searchTable.form.title.placeholder': '请输入标题',
|
'searchTable.form.title.placeholder': '请输入标题',
|
||||||
|
'searchTable.form.money':'金额',
|
||||||
|
'searchTable.form.money.placeholder': '请输入金额',
|
||||||
|
'searchTable.form.userName':'用户',
|
||||||
|
'searchTable.form.committer.placeholder': '请输入票据提交的用户',
|
||||||
'searchTable.form.type':'类型',
|
'searchTable.form.type':'类型',
|
||||||
'searchTable.form.type.placeholder': '请选择票据类型',
|
'searchTable.form.type.placeholder': '请选择票据类型',
|
||||||
'searchTable.form.status': '状态',
|
'searchTable.form.status': '状态',
|
||||||
'searchTable.form.status.placeholder': '请选择状态',
|
'searchTable.form.status.placeholder': '请选择状态',
|
||||||
|
'searchTable.form.time':'时间',
|
||||||
|
'searchTable.form.time.placeholder': '请选择时间段',
|
||||||
|
'searchTable.form.min':'最小金额',
|
||||||
|
'searchTable.form.max':'最大金额',
|
||||||
|
|
||||||
|
|
||||||
'Confirm the deletion of this ticket': '确定删除此票据?',
|
'Confirm the deletion of this ticket': '确定删除此票据?',
|
||||||
|
|
||||||
@ -43,37 +52,40 @@ export default {
|
|||||||
'unreviewed': '待审核',
|
'unreviewed': '待审核',
|
||||||
'pass': '审核通过',
|
'pass': '审核通过',
|
||||||
'failed': '审核未通过',
|
'failed': '审核未通过',
|
||||||
|
'drafts':'草稿箱',
|
||||||
|
|
||||||
"ticket.info.companyName": '公司',
|
"ticket.info.companyName": '公司:',
|
||||||
"ticket.info.companyName.required": '公司名称不能为空',
|
"ticket.info.companyName.required": '公司名称不能为空',
|
||||||
"ticket.info.companyName.placeholder": '请输入公司名称',
|
"ticket.info.companyName.placeholder": '请输入公司名称',
|
||||||
"ticket.info.title": '标题',
|
"ticket.info.title": '标题:',
|
||||||
"ticket.info.title.required": '标题不能为空',
|
"ticket.info.title.required": '标题不能为空',
|
||||||
"ticket.info.title.placeholder": '请输入标题',
|
"ticket.info.title.placeholder": '请输入标题',
|
||||||
"ticket.info.body": '内容',
|
"ticket.info.body": '内容:',
|
||||||
"ticket.info.body.required": '内容不能为空',
|
"ticket.info.body.required": '内容不能为空',
|
||||||
"ticket.info.body.placeholder": '请输入内容',
|
"ticket.info.body.placeholder": '请输入内容',
|
||||||
"ticket.info.money": '金额',
|
"ticket.info.money": '金额:',
|
||||||
"ticket.info.money.required": '金额不能为空',
|
"ticket.info.money.required": '金额不能为空',
|
||||||
"ticket.info.money.placeholder": '请输入金额',
|
"ticket.info.money.placeholder": '请输入金额',
|
||||||
"ticket.info.contactEmail": '联系邮箱',
|
"ticket.info.contactEmail": '联系邮箱:',
|
||||||
"ticket.info.createTime": '创建时间',
|
"ticket.info.createTime": '创建时间:',
|
||||||
"ticket.info.contactEmail.required": '联系邮箱不能为空',
|
"ticket.info.contactEmail.required": '联系邮箱不能为空',
|
||||||
"ticket.info.contactEmail.placeholder": '请输入联系邮箱',
|
"ticket.info.contactEmail.placeholder": '请输入联系邮箱',
|
||||||
"ticket.info.type": '票据类型',
|
"ticket.info.type": '票据类型:',
|
||||||
"ticket.info.type.required": '票据类型不能为空',
|
"ticket.info.type.required": '票据类型不能为空',
|
||||||
"ticket.info.type.placeholder": '请选择票据类型',
|
"ticket.info.type.placeholder": '请选择票据类型',
|
||||||
"ticket.info.attachment": '附件',
|
"ticket.info.attachment": '附件:',
|
||||||
"ticket.info.dept": '部门',
|
"ticket.info.dept": '部门:',
|
||||||
"ticket.info.dept.required": '部门不能为空',
|
"ticket.info.dept.required": '部门不能为空',
|
||||||
"ticket.info.dept.placeholder": '请选择提交的部门',
|
"ticket.info.dept.placeholder": '请选择提交的部门',
|
||||||
"ticket.info.auditor": '审核员',
|
"ticket.info.auditor": '审核员:',
|
||||||
"ticket.info.auditor.required": '审核员不能为空',
|
"ticket.info.auditor.required": '审核员不能为空',
|
||||||
"ticket.info.auditor.placeholder": '请选择审核员',
|
"ticket.info.auditor.placeholder": '请选择审核员',
|
||||||
"ticket.info.status": '审核状态',
|
"ticket.info.status": '审核状态:',
|
||||||
"ticket.info.status.required": '审核状态不能为空',
|
"ticket.info.status.required": '审核状态不能为空',
|
||||||
"ticket.info.status.placeholder": '请选择审核状态',
|
"ticket.info.status.placeholder": '请选择审核状态',
|
||||||
"ticket.info.comment": '审核意见',
|
"ticket.info.comment": '审核意见:',
|
||||||
|
"ticketTable.columns.userName":'用户',
|
||||||
|
|
||||||
|
|
||||||
'upload.sucess': '上传成功',
|
'upload.sucess': '上传成功',
|
||||||
'upload.fail': '上传失败',
|
'upload.fail': '上传失败',
|
||||||
|
@ -6,7 +6,7 @@
|
|||||||
:label-col-props="{ span: 8 }"
|
:label-col-props="{ span: 8 }"
|
||||||
:wrapper-col-props="{ span: 16 }"
|
:wrapper-col-props="{ span: 16 }"
|
||||||
>
|
>
|
||||||
<a-form-item
|
<!-- <a-form-item
|
||||||
field="oldPassword"
|
field="oldPassword"
|
||||||
:label="$t('userSetting.passwordReset.form.label.oldPassword')"
|
:label="$t('userSetting.passwordReset.form.label.oldPassword')"
|
||||||
:rules="[{ required: true, message: $t('login.form.password.errMsg') }]"
|
:rules="[{ required: true, message: $t('login.form.password.errMsg') }]"
|
||||||
@ -19,7 +19,7 @@
|
|||||||
allow-clear
|
allow-clear
|
||||||
>
|
>
|
||||||
</a-input-password>
|
</a-input-password>
|
||||||
</a-form-item>
|
</a-form-item> -->
|
||||||
|
|
||||||
<a-form-item
|
<a-form-item
|
||||||
field="password"
|
field="password"
|
||||||
|
@ -93,7 +93,7 @@ const fileList = ref<FileItem[]>([file]);
|
|||||||
const Onchange = async (option: any) => {
|
const Onchange = async (option: any) => {
|
||||||
const FormDatas = new FormData();
|
const FormDatas = new FormData();
|
||||||
FormDatas.append('file', option.fileItem.file);
|
FormDatas.append('file', option.fileItem.file);
|
||||||
const res = await ticketStore.uploadFileTicket(FormDatas);
|
const res = await ticketStore.uploadFile(FormDatas);
|
||||||
if (res.status === 200) {
|
if (res.status === 200) {
|
||||||
Message.success({
|
Message.success({
|
||||||
content: t('upload.sucess'),
|
content: t('upload.sucess'),
|
||||||
|
Loading…
Reference in New Issue
Block a user