feat: 完善平台总后台模块
This commit is contained in:
40
frontend/platform_admin/src/views/shared/CrudListPage.vue
Normal file
40
frontend/platform_admin/src/views/shared/CrudListPage.vue
Normal file
@@ -0,0 +1,40 @@
|
||||
<template>
|
||||
<a-card :title="title" :bordered="false">
|
||||
<template #extra><a-space><a-button @click="load">刷新</a-button><a-button type="primary" @click="openCreate">新建</a-button></a-space></template>
|
||||
<a-table :data="list" :loading="loading" :pagination="false" row-key="identity">
|
||||
<template #columns>
|
||||
<a-table-column title="业务标识" data-index="identity" :width="220" ellipsis tooltip />
|
||||
<a-table-column v-for="field in fields" :key="field.key" :title="field.label" :data-index="field.key" ellipsis tooltip />
|
||||
<a-table-column title="状态" data-index="status" :width="100"><template #cell="{ record }"><a-tag :color="record.status === 'enabled' ? 'green' : 'orange'">{{ record.status }}</a-tag></template></a-table-column>
|
||||
<a-table-column title="操作" :width="210" fixed="right"><template #cell="{ record }"><a-space><a-button size="mini" @click="openDetail(record)">详情</a-button><a-button size="mini" @click="openEdit(record)">编辑</a-button><a-button size="mini" @click="changeStatus(record)">{{ record.status === 'enabled' ? '停用' : '启用' }}</a-button></a-space></template></a-table-column>
|
||||
</template>
|
||||
</a-table>
|
||||
<div class="pagination"><a-pagination :total="total" :current="page" :page-size="pageSize" show-total @change="changePage" /></div>
|
||||
</a-card>
|
||||
<a-drawer :visible="formVisible" :title="editingIdentity ? `编辑${title}` : `新建${title}`" :width="480" @cancel="formVisible = false" @ok="save">
|
||||
<a-form :model="form" layout="vertical"><a-form-item v-for="field in fields" :key="field.key" :label="field.label" :required="field.required"><a-input v-model="form[field.key]" :placeholder="`请输入${field.label}`" /></a-form-item></a-form>
|
||||
</a-drawer>
|
||||
<a-drawer :visible="detailVisible" title="详情" :width="540" @cancel="detailVisible = false"><a-descriptions :column="1" bordered><a-descriptions-item v-for="(value, key) in detail" :key="String(key)" :label="String(key)">{{ value ?? '-' }}</a-descriptions-item></a-descriptions></a-drawer>
|
||||
</template>
|
||||
|
||||
<script setup lang="ts">
|
||||
import { Message } from '@arco-design/web-vue';
|
||||
import { onMounted, reactive, ref } from 'vue';
|
||||
import { resourceApi } from '@/api/resource';
|
||||
|
||||
type Field = { key: string; label: string; required?: boolean };
|
||||
type Row = Record<string, any>;
|
||||
const props = defineProps<{ title: string; resource: string; fields: Field[] }>();
|
||||
const loading = ref(false); const page = ref(1); const pageSize = 20; const total = ref(0); const list = ref<Row[]>([]);
|
||||
const formVisible = ref(false); const detailVisible = ref(false); const editingIdentity = ref(''); const form = reactive<Row>({}); const detail = ref<Row>({});
|
||||
function resetForm(data?: Row) { props.fields.forEach((field) => { form[field.key] = data?.[field.key] ?? ''; }); }
|
||||
async function load() { loading.value = true; try { const result = await resourceApi.list<Row>(props.resource, page.value, pageSize); list.value = result.list; total.value = result.total; } catch (error) { Message.error((error as Error).message); } finally { loading.value = false; } }
|
||||
function openCreate() { editingIdentity.value = ''; resetForm(); formVisible.value = true; }
|
||||
function openEdit(row: Row) { editingIdentity.value = row.identity; resetForm(row); formVisible.value = true; }
|
||||
function openDetail(row: Row) { detail.value = row; detailVisible.value = true; }
|
||||
async function save() { if (props.fields.some((field) => field.required && !form[field.key])) { Message.warning('请填写必填字段'); return; } try { if (editingIdentity.value) await resourceApi.update(props.resource, editingIdentity.value, form); else await resourceApi.create(props.resource, form); Message.success('保存成功'); formVisible.value = false; await load(); } catch (error) { Message.error((error as Error).message); } }
|
||||
async function changeStatus(row: Row) { try { await resourceApi.updateStatus(props.resource, row.identity, row.status === 'enabled' ? 'disabled' : 'enabled'); await load(); } catch (error) { Message.error((error as Error).message); } }
|
||||
async function changePage(next: number) { page.value = next; await load(); }
|
||||
onMounted(load);
|
||||
</script>
|
||||
<style scoped lang="less">.pagination { display: flex; justify-content: flex-end; margin-top: 16px; }</style>
|
||||
Reference in New Issue
Block a user