feat: 专利信息开发
This commit is contained in:
parent
666c95855b
commit
31d2d04a46
File diff suppressed because it is too large
Load Diff
|
|
@ -5,6 +5,7 @@ export * from './tech-resources'
|
||||||
export * from './system'
|
export * from './system'
|
||||||
export * from './dashboard'
|
export * from './dashboard'
|
||||||
export * from './upload'
|
export * from './upload'
|
||||||
|
export * from './patent'
|
||||||
|
|
||||||
// 导出请求方法
|
// 导出请求方法
|
||||||
export { get, post, put, del } from './request'
|
export { get, post, put, del } from './request'
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,202 @@
|
||||||
|
// src/api/patent.ts
|
||||||
|
|
||||||
|
// 专利信息接口 (对应 patent 表和 patent_talent 关联表)
|
||||||
|
export interface Patent {
|
||||||
|
id: string
|
||||||
|
patentName: string
|
||||||
|
patentNumber: string
|
||||||
|
patentType: string // 专利类型
|
||||||
|
applicationTime: string
|
||||||
|
authorizationTime?: string | null // 允许为空
|
||||||
|
patentStatus: string // 专利状态
|
||||||
|
status?: number
|
||||||
|
flag: number
|
||||||
|
createTime: string
|
||||||
|
updateTime: string
|
||||||
|
createBy?: string
|
||||||
|
updateBy?: string
|
||||||
|
|
||||||
|
// 关联的跨表字段(前端展示用)
|
||||||
|
talentId?: string
|
||||||
|
talentName?: string
|
||||||
|
}
|
||||||
|
|
||||||
|
// 分页查询参数
|
||||||
|
export interface PatentPageParams {
|
||||||
|
pageNum: number
|
||||||
|
pageSize: number
|
||||||
|
patentName?: string
|
||||||
|
patentNumber?: string
|
||||||
|
patentType?: string
|
||||||
|
talentName?: string
|
||||||
|
}
|
||||||
|
|
||||||
|
// 新增/更新参数
|
||||||
|
export interface PatentFormData {
|
||||||
|
id?: string
|
||||||
|
talentId: string // 关联人才
|
||||||
|
patentName: string
|
||||||
|
patentNumber: string
|
||||||
|
patentType: string
|
||||||
|
applicationTime: string
|
||||||
|
authorizationTime?: string | null
|
||||||
|
patentStatus: string
|
||||||
|
}
|
||||||
|
|
||||||
|
// 注意:这里不加 export,防止和 index.ts 里其他文件的同名接口冲突
|
||||||
|
interface ApiResponse<T = unknown> {
|
||||||
|
code: number
|
||||||
|
message: string
|
||||||
|
data: T
|
||||||
|
}
|
||||||
|
|
||||||
|
interface PageResponse<T> {
|
||||||
|
records: T[]
|
||||||
|
total: number
|
||||||
|
size: number
|
||||||
|
current: number
|
||||||
|
pages: number
|
||||||
|
}
|
||||||
|
|
||||||
|
// ==================== Mock 数据 ====================
|
||||||
|
const mockPatents: Patent[] = [
|
||||||
|
{
|
||||||
|
id: '1',
|
||||||
|
talentId: '1',
|
||||||
|
talentName: '张伟',
|
||||||
|
patentName: '一种基于深度学习的图像识别方法及系统',
|
||||||
|
patentNumber: 'CN202110123456.7',
|
||||||
|
patentType: 'INVENTION',
|
||||||
|
applicationTime: '2021-03-15 00:00:00',
|
||||||
|
authorizationTime: '2022-08-20 00:00:00',
|
||||||
|
patentStatus: 'AUTHORIZED',
|
||||||
|
status: 1,
|
||||||
|
flag: 0,
|
||||||
|
createTime: '2024-01-01 10:00:00',
|
||||||
|
updateTime: '2024-01-15 14:30:00',
|
||||||
|
createBy: 'admin',
|
||||||
|
updateBy: 'admin'
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: '2',
|
||||||
|
talentId: '2',
|
||||||
|
talentName: '李娜',
|
||||||
|
patentName: '一种新型散热计算机机箱',
|
||||||
|
patentNumber: 'CN202220987654.1',
|
||||||
|
patentType: 'UTILITY_MODEL',
|
||||||
|
applicationTime: '2022-05-10 00:00:00',
|
||||||
|
authorizationTime: null,
|
||||||
|
patentStatus: 'APPLYING',
|
||||||
|
status: 1,
|
||||||
|
flag: 0,
|
||||||
|
createTime: '2024-01-02 09:00:00',
|
||||||
|
updateTime: '2024-01-16 11:20:00',
|
||||||
|
createBy: 'admin',
|
||||||
|
updateBy: 'admin'
|
||||||
|
}
|
||||||
|
]
|
||||||
|
|
||||||
|
let mockIdCounter = 3
|
||||||
|
const mockDelay = () => new Promise(resolve => setTimeout(resolve, 300))
|
||||||
|
|
||||||
|
export async function getPatentPage(params: PatentPageParams) {
|
||||||
|
await mockDelay()
|
||||||
|
let filteredData = [...mockPatents]
|
||||||
|
|
||||||
|
if (params.patentName) {
|
||||||
|
filteredData = filteredData.filter(item => item.patentName.includes(params.patentName!))
|
||||||
|
}
|
||||||
|
if (params.patentNumber) {
|
||||||
|
filteredData = filteredData.filter(item => item.patentNumber.includes(params.patentNumber!))
|
||||||
|
}
|
||||||
|
if (params.patentType) {
|
||||||
|
filteredData = filteredData.filter(item => item.patentType === params.patentType)
|
||||||
|
}
|
||||||
|
if (params.talentName) {
|
||||||
|
filteredData = filteredData.filter(item => item.talentName?.includes(params.talentName!))
|
||||||
|
}
|
||||||
|
|
||||||
|
filteredData.sort((a, b) => b.applicationTime.localeCompare(a.applicationTime))
|
||||||
|
|
||||||
|
const start = (params.pageNum - 1) * params.pageSize
|
||||||
|
const end = start + params.pageSize
|
||||||
|
const records = filteredData.slice(start, end)
|
||||||
|
|
||||||
|
return {
|
||||||
|
data: {
|
||||||
|
code: 200,
|
||||||
|
message: '查询成功',
|
||||||
|
data: {
|
||||||
|
records,
|
||||||
|
total: filteredData.length,
|
||||||
|
size: params.pageSize,
|
||||||
|
current: params.pageNum,
|
||||||
|
pages: Math.ceil(filteredData.length / params.pageSize)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export async function getPatentDetail(id: string) {
|
||||||
|
await mockDelay()
|
||||||
|
const patent = mockPatents.find(item => item.id === id)
|
||||||
|
if (patent) {
|
||||||
|
return { data: { code: 200, message: '查询成功', data: patent } }
|
||||||
|
} else {
|
||||||
|
return { data: { code: 404, message: '未找到该专利', data: null } }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export async function addPatent(data: PatentFormData) {
|
||||||
|
await mockDelay()
|
||||||
|
const newPatent: Patent = {
|
||||||
|
...data,
|
||||||
|
id: String(mockIdCounter++),
|
||||||
|
flag: 0,
|
||||||
|
createTime: new Date().toISOString().replace('T', ' ').substring(0, 19),
|
||||||
|
updateTime: new Date().toISOString().replace('T', ' ').substring(0, 19),
|
||||||
|
createBy: 'admin',
|
||||||
|
updateBy: 'admin',
|
||||||
|
talentName: '关联人才' // Mock时简单占位
|
||||||
|
} as Patent
|
||||||
|
mockPatents.unshift(newPatent)
|
||||||
|
return { data: { code: 200, message: '新增成功', data: null } }
|
||||||
|
}
|
||||||
|
|
||||||
|
export async function updatePatent(data: PatentFormData) {
|
||||||
|
await mockDelay()
|
||||||
|
const index = mockPatents.findIndex(item => item.id === data.id)
|
||||||
|
if (index !== -1) {
|
||||||
|
mockPatents[index] = {
|
||||||
|
...mockPatents[index],
|
||||||
|
...data,
|
||||||
|
updateTime: new Date().toISOString().replace('T', ' ').substring(0, 19),
|
||||||
|
updateBy: 'admin'
|
||||||
|
}
|
||||||
|
return { data: { code: 200, message: '修改成功', data: null } }
|
||||||
|
} else {
|
||||||
|
return { data: { code: 404, message: '未找到该专利', data: null } }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export async function deletePatent(id: string) {
|
||||||
|
await mockDelay()
|
||||||
|
const index = mockPatents.findIndex(item => item.id === id)
|
||||||
|
if (index !== -1) {
|
||||||
|
mockPatents.splice(index, 1)
|
||||||
|
return { data: { code: 200, message: '删除成功', data: null } }
|
||||||
|
} else {
|
||||||
|
return { data: { code: 404, message: '未找到该专利', data: null } }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export async function batchDeletePatent(ids: string[]) {
|
||||||
|
await mockDelay()
|
||||||
|
ids.forEach(id => {
|
||||||
|
const index = mockPatents.findIndex(item => item.id === id)
|
||||||
|
if (index !== -1) {
|
||||||
|
mockPatents.splice(index, 1)
|
||||||
|
}
|
||||||
|
})
|
||||||
|
return { data: { code: 200, message: '批量删除成功', data: null } }
|
||||||
|
}
|
||||||
|
|
@ -218,6 +218,26 @@ const routes: Array<RouteRecordRaw> = [
|
||||||
path: 'talent-resume/view/:id',
|
path: 'talent-resume/view/:id',
|
||||||
name: 'admin-talent-resume-view',
|
name: 'admin-talent-resume-view',
|
||||||
component: () => import('@/views/admin/tech-resources/talent-resume-form.vue')
|
component: () => import('@/views/admin/tech-resources/talent-resume-form.vue')
|
||||||
|
},
|
||||||
|
{
|
||||||
|
path: 'tech-patents',
|
||||||
|
name: 'TechPatents',
|
||||||
|
component: () => import('@/views/admin/tech-resources/tech-patent.vue'),
|
||||||
|
},
|
||||||
|
{
|
||||||
|
path: 'tech-patents/create',
|
||||||
|
name: 'TechPatentsCreate',
|
||||||
|
component: () => import('@/views/admin/tech-resources/tech-patent-form.vue'),
|
||||||
|
},
|
||||||
|
{
|
||||||
|
path: 'tech-patents/edit/:id',
|
||||||
|
name: 'TechPatentsEdit',
|
||||||
|
component: () => import('@/views/admin/tech-resources/tech-patent-form.vue'),
|
||||||
|
},
|
||||||
|
{
|
||||||
|
path: 'tech-patents/view/:id',
|
||||||
|
name: 'TechPatentsView',
|
||||||
|
component: () => import('@/views/admin/tech-resources/tech-patent-form.vue'),
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,139 @@
|
||||||
|
<template>
|
||||||
|
<div class="tech-patents-form-container">
|
||||||
|
<el-card>
|
||||||
|
<template #header>
|
||||||
|
<div class="card-header">
|
||||||
|
<span>{{ isView ? '查看' : (formData.id ? '编辑' : '新增') }}专利</span>
|
||||||
|
<el-button @click="handleBack">返回</el-button>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<el-form ref="formRef" :model="formData" :rules="rules" label-width="120px" :disabled="isView">
|
||||||
|
<el-row :gutter="20">
|
||||||
|
<el-col :span="12">
|
||||||
|
<el-form-item label="关联人才" prop="talentId">
|
||||||
|
<el-select v-model="formData.talentId" placeholder="请选择发明人" style="width: 100%" filterable>
|
||||||
|
<el-option v-for="t in talentList" :key="t.id" :label="t.name" :value="t.id" />
|
||||||
|
</el-select>
|
||||||
|
</el-form-item>
|
||||||
|
</el-col>
|
||||||
|
<el-col :span="12">
|
||||||
|
<el-form-item label="专利名称" prop="patentName">
|
||||||
|
<el-input v-model="formData.patentName" placeholder="请输入专利名称" />
|
||||||
|
</el-form-item>
|
||||||
|
</el-col>
|
||||||
|
</el-row>
|
||||||
|
|
||||||
|
<el-row :gutter="20">
|
||||||
|
<el-col :span="12">
|
||||||
|
<el-form-item label="专利号" prop="patentNumber">
|
||||||
|
<el-input v-model="formData.patentNumber" placeholder="请输入专利号" />
|
||||||
|
</el-form-item>
|
||||||
|
</el-col>
|
||||||
|
<el-col :span="12">
|
||||||
|
<el-form-item label="专利类型" prop="patentType">
|
||||||
|
<el-select v-model="formData.patentType" placeholder="请选择类型" style="width: 100%">
|
||||||
|
<el-option label="发明专利" value="INVENTION" />
|
||||||
|
<el-option label="实用新型" value="UTILITY_MODEL" />
|
||||||
|
<el-option label="外观设计" value="DESIGN" />
|
||||||
|
</el-select>
|
||||||
|
</el-form-item>
|
||||||
|
</el-col>
|
||||||
|
</el-row>
|
||||||
|
|
||||||
|
<el-row :gutter="20">
|
||||||
|
<el-col :span="12">
|
||||||
|
<el-form-item label="申请时间" prop="applicationTime">
|
||||||
|
<el-date-picker v-model="formData.applicationTime" type="datetime" value-format="YYYY-MM-DD HH:mm:ss" style="width: 100%" />
|
||||||
|
</el-form-item>
|
||||||
|
</el-col>
|
||||||
|
<el-col :span="12">
|
||||||
|
<el-form-item label="授权时间" prop="authorizationTime">
|
||||||
|
<el-date-picker v-model="formData.authorizationTime" type="datetime" value-format="YYYY-MM-DD HH:mm:ss" style="width: 100%" clearable />
|
||||||
|
</el-form-item>
|
||||||
|
</el-col>
|
||||||
|
</el-row>
|
||||||
|
|
||||||
|
<el-form-item label="专利状态" prop="patentStatus">
|
||||||
|
<el-select v-model="formData.patentStatus" style="width: 300px">
|
||||||
|
<el-option label="申请中" value="APPLYING" />
|
||||||
|
<el-option label="已授权" value="AUTHORIZED" />
|
||||||
|
<el-option label="已失效" value="INVALID" />
|
||||||
|
</el-select>
|
||||||
|
</el-form-item>
|
||||||
|
|
||||||
|
<el-form-item v-if="!isView">
|
||||||
|
<el-button type="primary" @click="handleSubmit" :loading="submitting">提交</el-button>
|
||||||
|
<el-button @click="handleBack">取消</el-button>
|
||||||
|
</el-form-item>
|
||||||
|
</el-form>
|
||||||
|
</el-card>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script setup lang="ts">
|
||||||
|
import { ref, reactive, onMounted } from 'vue'
|
||||||
|
import { useRoute, useRouter } from 'vue-router'
|
||||||
|
import { ElMessage } from 'element-plus'
|
||||||
|
import type { FormInstance, FormRules } from 'element-plus'
|
||||||
|
import { getPatentDetail, addPatent, updatePatent, type PatentFormData } from '@/api/patent'
|
||||||
|
|
||||||
|
defineOptions({ name: 'TechPatentsForm' })
|
||||||
|
|
||||||
|
const router = useRouter()
|
||||||
|
const route = useRoute()
|
||||||
|
const formRef = ref<FormInstance>()
|
||||||
|
const submitting = ref(false)
|
||||||
|
const isView = ref(false)
|
||||||
|
|
||||||
|
const talentList = ref([
|
||||||
|
{ id: '1', name: '张伟' }, { id: '2', name: '李娜' }, { id: '3', name: '王强' }
|
||||||
|
])
|
||||||
|
|
||||||
|
const formData = reactive<PatentFormData>({
|
||||||
|
talentId: '', patentName: '', patentNumber: '', patentType: 'INVENTION',
|
||||||
|
patentStatus: 'APPLYING', applicationTime: '', authorizationTime: ''
|
||||||
|
})
|
||||||
|
|
||||||
|
const rules: FormRules = {
|
||||||
|
talentId: [{ required: true, message: '请选择关联人才', trigger: 'change' }],
|
||||||
|
patentName: [{ required: true, message: '请输入专利名称', trigger: 'blur' }],
|
||||||
|
patentNumber: [{ required: true, message: '请输入专利号', trigger: 'blur' }],
|
||||||
|
applicationTime: [{ required: true, message: '请选择申请时间', trigger: 'change' }]
|
||||||
|
}
|
||||||
|
|
||||||
|
const loadDetail = async (id: string) => {
|
||||||
|
try {
|
||||||
|
const { data } = await getPatentDetail(id)
|
||||||
|
if (data.code === 200) Object.assign(formData, data.data)
|
||||||
|
} catch (error) { ElMessage.error('加载失败') }
|
||||||
|
}
|
||||||
|
|
||||||
|
const handleSubmit = async () => {
|
||||||
|
if (!formRef.value) return
|
||||||
|
await formRef.value.validate(async (valid) => {
|
||||||
|
if (valid) {
|
||||||
|
submitting.value = true
|
||||||
|
try {
|
||||||
|
const apiFunc = formData.id ? updatePatent : addPatent
|
||||||
|
const { data } = await apiFunc(formData)
|
||||||
|
if (data.code === 200) { ElMessage.success('操作成功'); handleBack() }
|
||||||
|
} catch (error) { ElMessage.error('操作失败') }
|
||||||
|
finally { submitting.value = false }
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
const handleBack = () => router.push('/admin/tech-patents')
|
||||||
|
|
||||||
|
onMounted(() => {
|
||||||
|
const id = route.params.id as string
|
||||||
|
isView.value = route.path.includes('/view/')
|
||||||
|
if (id) loadDetail(id)
|
||||||
|
})
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
.tech-patents-form-container { padding: 20px; }
|
||||||
|
.card-header { display: flex; justify-content: space-between; align-items: center; }
|
||||||
|
</style>
|
||||||
|
|
@ -0,0 +1,137 @@
|
||||||
|
<template>
|
||||||
|
<div class="tech-patents-container">
|
||||||
|
<el-card>
|
||||||
|
<el-form :inline="true" :model="searchForm" class="search-form">
|
||||||
|
<el-form-item label="专利名称">
|
||||||
|
<el-input v-model="searchForm.patentName" placeholder="请输入专利名称" clearable />
|
||||||
|
</el-form-item>
|
||||||
|
<el-form-item label="专利号">
|
||||||
|
<el-input v-model="searchForm.patentNumber" placeholder="请输入专利号" clearable />
|
||||||
|
</el-form-item>
|
||||||
|
<el-form-item label="发明人">
|
||||||
|
<el-input v-model="searchForm.talentName" placeholder="请输入关联人才" clearable />
|
||||||
|
</el-form-item>
|
||||||
|
<el-form-item>
|
||||||
|
<el-button type="primary" @click="handleSearch">查询</el-button>
|
||||||
|
<el-button @click="handleReset">重置</el-button>
|
||||||
|
</el-form-item>
|
||||||
|
</el-form>
|
||||||
|
|
||||||
|
<div class="toolbar">
|
||||||
|
<el-button type="primary" @click="handleAdd">新增</el-button>
|
||||||
|
<el-button type="danger" :disabled="selectedIds.length === 0" @click="handleBatchDelete">批量删除</el-button>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<el-table :data="tableData" style="width: 100%" @selection-change="handleSelectionChange" v-loading="loading">
|
||||||
|
<el-table-column type="selection" width="55" />
|
||||||
|
<el-table-column prop="patentName" label="专利名称" min-width="200" show-overflow-tooltip />
|
||||||
|
<el-table-column prop="patentNumber" label="专利号" width="160" />
|
||||||
|
<el-table-column prop="talentName" label="发明人" width="120" />
|
||||||
|
<el-table-column label="申请时间" width="120">
|
||||||
|
<template #default="{ row }">
|
||||||
|
{{ formatDate(row.applicationTime) }}
|
||||||
|
</template>
|
||||||
|
</el-table-column>
|
||||||
|
<el-table-column label="授权时间" width="120">
|
||||||
|
<template #default="{ row }">
|
||||||
|
{{ formatDate(row.authorizationTime) || '-' }}
|
||||||
|
</template>
|
||||||
|
</el-table-column>
|
||||||
|
<el-table-column label="操作" width="180" fixed="right">
|
||||||
|
<template #default="{ row }">
|
||||||
|
<el-button link type="primary" @click="handleView(row)">查看</el-button>
|
||||||
|
<el-button link type="primary" @click="handleEdit(row)">编辑</el-button>
|
||||||
|
<el-button link type="danger" @click="handleDelete(row)">删除</el-button>
|
||||||
|
</template>
|
||||||
|
</el-table-column>
|
||||||
|
</el-table>
|
||||||
|
|
||||||
|
<el-pagination
|
||||||
|
v-model:current-page="pagination.pageNum"
|
||||||
|
v-model:page-size="pagination.pageSize"
|
||||||
|
:page-sizes="[10, 20, 50, 100]"
|
||||||
|
:total="pagination.total"
|
||||||
|
layout="total, sizes, prev, pager, next, jumper"
|
||||||
|
@size-change="handleSizeChange"
|
||||||
|
@current-change="handleCurrentChange"
|
||||||
|
class="pagination"
|
||||||
|
/>
|
||||||
|
</el-card>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script setup lang="ts">
|
||||||
|
import { ref, reactive, onMounted } from 'vue'
|
||||||
|
import { useRouter } from 'vue-router'
|
||||||
|
import { ElMessage, ElMessageBox } from 'element-plus'
|
||||||
|
import {
|
||||||
|
getPatentPage, deletePatent, batchDeletePatent, type Patent, type PatentPageParams
|
||||||
|
} from '@/api/patent'
|
||||||
|
|
||||||
|
defineOptions({ name: 'TechPatents' })
|
||||||
|
|
||||||
|
const router = useRouter()
|
||||||
|
const searchForm = reactive<Partial<PatentPageParams>>({ patentName: '', patentNumber: '', talentName: '' })
|
||||||
|
const pagination = reactive({ pageNum: 1, pageSize: 10, total: 0 })
|
||||||
|
const tableData = ref<Patent[]>([])
|
||||||
|
const loading = ref(false)
|
||||||
|
const selectedIds = ref<string[]>([])
|
||||||
|
|
||||||
|
const formatDate = (dateStr?: string | null) => {
|
||||||
|
if (!dateStr) return ''
|
||||||
|
return dateStr.substring(0, 10)
|
||||||
|
}
|
||||||
|
|
||||||
|
const loadData = async () => {
|
||||||
|
loading.value = true
|
||||||
|
try {
|
||||||
|
const params = { pageNum: pagination.pageNum, pageSize: pagination.pageSize, ...searchForm }
|
||||||
|
const { data } = await getPatentPage(params)
|
||||||
|
if (data.code === 200) {
|
||||||
|
tableData.value = data.data.records
|
||||||
|
pagination.total = data.data.total
|
||||||
|
}
|
||||||
|
} catch (error) {
|
||||||
|
ElMessage.error('加载失败')
|
||||||
|
} finally {
|
||||||
|
loading.value = false
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
const handleSearch = () => { pagination.pageNum = 1; loadData() }
|
||||||
|
const handleReset = () => { Object.assign(searchForm, { patentName: '', patentNumber: '', talentName: '' }); handleSearch() }
|
||||||
|
|
||||||
|
// 注意这里的跳转路径,全都是 tech-patents 相关的
|
||||||
|
const handleAdd = () => router.push('/admin/tech-patents/create')
|
||||||
|
const handleView = (row: Patent) => router.push(`/admin/tech-patents/view/${row.id}`)
|
||||||
|
const handleEdit = (row: Patent) => router.push(`/admin/tech-patents/edit/${row.id}`)
|
||||||
|
|
||||||
|
const handleDelete = async (row: Patent) => {
|
||||||
|
try {
|
||||||
|
await ElMessageBox.confirm('确定要删除该专利吗?', '提示', { type: 'warning' })
|
||||||
|
const { data } = await deletePatent(row.id)
|
||||||
|
if (data.code === 200) { ElMessage.success('删除成功'); loadData() }
|
||||||
|
} catch (e) { /* catch cancel */ }
|
||||||
|
}
|
||||||
|
|
||||||
|
const handleBatchDelete = async () => {
|
||||||
|
try {
|
||||||
|
await ElMessageBox.confirm('确定要删除选中记录吗?', '提示', { type: 'warning' })
|
||||||
|
const { data } = await batchDeletePatent(selectedIds.value)
|
||||||
|
if (data.code === 200) { ElMessage.success('删除成功'); selectedIds.value = []; loadData() }
|
||||||
|
} catch (e) { /* catch cancel */ }
|
||||||
|
}
|
||||||
|
|
||||||
|
const handleSelectionChange = (selection: Patent[]) => { selectedIds.value = selection.map(item => item.id) }
|
||||||
|
const handleSizeChange = () => loadData()
|
||||||
|
const handleCurrentChange = () => loadData()
|
||||||
|
|
||||||
|
onMounted(() => loadData())
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
.tech-patents-container { padding: 20px; }
|
||||||
|
.search-form { margin-bottom: 20px; }
|
||||||
|
.toolbar { margin-bottom: 20px; }
|
||||||
|
.pagination { margin-top: 20px; justify-content: flex-end; }
|
||||||
|
</style>
|
||||||
Loading…
Reference in New Issue