工作流

pull/781/head
zy 2025-04-29 00:15:39 +08:00
parent cd23457490
commit 5c0e4096f8
8 changed files with 79 additions and 30 deletions

View File

@ -125,6 +125,11 @@ export const getRemindContractCount = async () => {
return await request.get({ url: '/crm/contract/remind-count' }) return await request.get({ url: '/crm/contract/remind-count' })
} }
// 合作主主体
export const getOrg = async (params) => {
return await request.get({ url: '/system/organizations/page', params })
}
// ==================== 子表CRM 合同产品关联) ==================== // ==================== 子表CRM 合同产品关联) ====================
// 获得CRM 合同产品关联列表 // 获得CRM 合同产品关联列表

View File

@ -557,11 +557,12 @@ const remainingRouter: AppRouteRecordRaw[] = [
component: () => import('@/views/crm/billtemplate/BillTemplateForm.vue') component: () => import('@/views/crm/billtemplate/BillTemplateForm.vue')
}, },
{ {
path: 'business/quotationAdd', path: 'quotation/QuotationForm',
name: 'QuotationAdd', name: 'QuotationAdd',
meta: { meta: {
title: '方案报价新增', title: '方案报价新增',
noCache: true, noCache: true,
canTo: true,
hidden: true, hidden: true,
activeMenu: '/crm/quotation' activeMenu: '/crm/quotation'
}, },
@ -579,11 +580,12 @@ const remainingRouter: AppRouteRecordRaw[] = [
component: () => import('@/views/crm/quotation/QuotationForm.vue') component: () => import('@/views/crm/quotation/QuotationForm.vue')
}, },
{ {
path: 'business/quotationDetail', path: 'quotation/quotationDetail',
name: 'QuotationDetail', name: 'QuotationDetail',
meta: { meta: {
title: '方案报价详情', title: '方案报价详情',
noCache: true, noCache: true,
canTo: true,
hidden: true, hidden: true,
activeMenu: '/crm/quotation' activeMenu: '/crm/quotation'
}, },
@ -645,11 +647,12 @@ const remainingRouter: AppRouteRecordRaw[] = [
component: () => import('@/views/crm/contract/ContractChange.vue') component: () => import('@/views/crm/contract/ContractChange.vue')
}, },
{ {
path: 'contract/detail/:id', path: 'contract/detail/index',
name: 'CrmContractDetail', name: 'CrmContractDetail',
meta: { meta: {
title: '合同详情', title: '合同详情',
noCache: true, noCache: true,
canTo: true,
hidden: true, hidden: true,
activeMenu: '/crm/contract' activeMenu: '/crm/contract'
}, },

View File

@ -8,16 +8,17 @@
label-width="120px" label-width="120px"
> >
<el-row> <el-row>
<el-col :span="8">
<el-form-item label="合同编号" prop="no">
<el-input v-model="formData.no" placeholder="请输入合同编号" />
</el-form-item>
</el-col>
<el-col :span="8"> <el-col :span="8">
<el-form-item label="合同名称" prop="name"> <el-form-item label="合同名称" prop="name">
<el-input v-model="formData.name" placeholder="请输入合同名称" /> <el-input v-model="formData.name" placeholder="请输入合同名称" />
</el-form-item> </el-form-item>
</el-col> </el-col>
<el-col :span="8" v-if="formType">
<el-form-item label="合同编号" prop="no">
<el-input v-model="formData.no" placeholder="请输入合同编号" />
</el-form-item>
</el-col>
</el-row> </el-row>
<el-row> <el-row>
@ -264,7 +265,7 @@
<el-form-item label="合作主体" prop="partnerCompanyId"> <el-form-item label="合作主体" prop="partnerCompanyId">
<el-select v-model="formData.partnerCompanyId" placeholder="请选择合作主体" disabled > <el-select v-model="formData.partnerCompanyId" placeholder="请选择合作主体" disabled >
<el-option <el-option
v-for="dict in deptList" v-for="dict in orgList"
:key="dict.id" :key="dict.id"
:label="dict.name" :label="dict.name"
:value="dict.id" :value="dict.id"
@ -378,11 +379,14 @@ import ContractProductForm from '@/views/crm/contract/components/ContractProduct
import ContractAAuthorizedCompanyForm from './components/ContractAAuthorizedCompanyForm.vue' import ContractAAuthorizedCompanyForm from './components/ContractAAuthorizedCompanyForm.vue'
import ContractAAuthorizedPersonForm from './components/ContractAAuthorizedPersonForm.vue' import ContractAAuthorizedPersonForm from './components/ContractAAuthorizedPersonForm.vue'
import ContractBAuthorizedPersonForm from './components/ContractBAuthorizedPersonForm.vue' import ContractBAuthorizedPersonForm from './components/ContractBAuthorizedPersonForm.vue'
import { propTypes } from '@/utils/propTypes'
const { t } = useI18n() // const { t } = useI18n() //
const message = useMessage() // const message = useMessage() //
const { proxy }: any = getCurrentInstance(); const { proxy }: any = getCurrentInstance();
const props = defineProps({
id: propTypes.number.def(undefined)
})
const dialogVisible = ref(false) // const dialogVisible = ref(false) //
const dialogTitle = ref('') // const dialogTitle = ref('') //
const formLoading = ref(false) // 12 const formLoading = ref(false) // 12
@ -436,6 +440,7 @@ const userOptions = ref<UserApi.UserVO[]>([]) // 用户列表
const customerList = ref([]) // const customerList = ref([]) //
const quotationList = ref<QuotationVO[]>([]) const quotationList = ref<QuotationVO[]>([])
const contactList = ref<ContactApi.ContactVO[]>([]) const contactList = ref<ContactApi.ContactVO[]>([])
const orgList = ref([])
/** 子表的表单 */ /** 子表的表单 */
const subTabsName = ref('product') const subTabsName = ref('product')
@ -626,7 +631,7 @@ const getContactOptions = computed(() =>
const route = useRoute(); const route = useRoute();
onMounted(async () => { onMounted(async () => {
formType.value = route.query.id; formType.value = props.id || route.query.id
if (formType.value) open(formType.value) if (formType.value) open(formType.value)
@ -643,5 +648,10 @@ onMounted(async () => {
// } // }
// //
contactList.value = await ContactApi.getSimpleContactList() contactList.value = await ContactApi.getSimpleContactList()
const data = await ContractApi.getOrg({
pageNo: 1,
pageSize: 1000
})
orgList.value = data.list
}); });
</script> </script>

View File

@ -65,9 +65,10 @@ import PermissionList from '@/views/crm/permission/components/PermissionList.vue
import FollowUpList from '@/views/crm/followup/index.vue' import FollowUpList from '@/views/crm/followup/index.vue'
import ReceivableList from '@/views/crm/receivable/components/ReceivableList.vue' import ReceivableList from '@/views/crm/receivable/components/ReceivableList.vue'
import ReceivablePlanList from '@/views/crm/receivable/plan/components/ReceivablePlanList.vue' import ReceivablePlanList from '@/views/crm/receivable/plan/components/ReceivablePlanList.vue'
import { propTypes } from '@/utils/propTypes'
defineOptions({ name: 'CrmContractDetail' }) defineOptions({ name: 'CrmContractDetail' })
const props = defineProps<{ id?: number }>()
const route = useRoute() const route = useRoute()
const message = useMessage() const message = useMessage()
@ -75,7 +76,9 @@ const contractId = ref(0) // 编号
const loading = ref(true) // const loading = ref(true) //
const contract = ref<ContractApi.ContractVO>({} as ContractApi.ContractVO) // const contract = ref<ContractApi.ContractVO>({} as ContractApi.ContractVO) //
const permissionListRef = ref<InstanceType<typeof PermissionList>>() // Ref const permissionListRef = ref<InstanceType<typeof PermissionList>>() // Ref
const props = defineProps({
id: propTypes.number.def(undefined)
})
/** 编辑 */ /** 编辑 */
const formRef = ref() const formRef = ref()
const openForm = (type: string, id?: number) => { const openForm = (type: string, id?: number) => {
@ -127,7 +130,7 @@ const close = () => {
/** 初始化 */ /** 初始化 */
onMounted(async () => { onMounted(async () => {
const id = props.id || route.params.id const id = props.id || route.query.id
if (!id) { if (!id) {
message.warning('参数错误,合同不能为空!') message.warning('参数错误,合同不能为空!')
close() close()

View File

@ -82,7 +82,7 @@
<el-table-column align="center" fixed="left" label="合同编号" prop="no" width="180" /> <el-table-column align="center" fixed="left" label="合同编号" prop="no" width="180" />
<el-table-column align="center" fixed="left" label="合同名称" prop="name" width="160"> <el-table-column align="center" fixed="left" label="合同名称" prop="name" width="160">
<template #default="scope"> <template #default="scope">
<el-link :underline="false" type="primary" @click="openDetail(scope.row.id)"> <el-link :underline="false" type="primary" @click="openDetail(scope.row)">
{{ scope.row.name }} {{ scope.row.name }}
</el-link> </el-link>
</template> </template>
@ -229,17 +229,17 @@
<el-button <el-button
v-else v-else
link link
v-hasPermi="['crm:contract:update']" v-hasPermi="['crm:customer-suggestion:query']"
type="primary" type="primary"
@click="handleProcessDetail(scope.row)" @click="handleProcessDetail(scope.row)"
> >
查看审批 进度
</el-button> </el-button>
<el-button <el-button
v-hasPermi="['crm:contract:query']" v-hasPermi="['crm:contract:query']"
link link
type="primary" type="primary"
@click="openDetail(scope.row.id)" @click="openDetail(scope.row)"
> >
详情 详情
</el-button> </el-button>
@ -327,6 +327,7 @@ const resetQuery = () => {
/** 添加/修改操作 */ /** 添加/修改操作 */
const formRef = ref() const formRef = ref()
const router = useRouter() //
const openFormEdit = (row: Object) => { const openFormEdit = (row: Object) => {
@ -340,8 +341,8 @@ const openFormDetail = (row: Object) => {
push({ name: 'CrmContractDetail', query: { id: row.id } }) push({ name: 'CrmContractDetail', query: { id: row.id } })
} }
const handleChange = (row: Object) => { const handleChange = (row) => {
push({ name: 'CrmContractChange', query: { id: row.id } }) router.push({ name: 'CrmContractChange', query: { id: row.id } })
} }
@ -382,19 +383,19 @@ const handleSubmit = async (row: ContractApi.ContractVO) => {
} }
/** 查看审批 */ /** 查看审批 */
const handleProcessDetail = (row: ContractApi.ContractVO) => { const handleProcessDetail = (row) => {
push({ name: 'BpmProcessInstanceDetail', query: { id: row.processInstanceId } }) router.push({ name: 'BpmProcessInstanceDetail', query: { id: row.processInstanceId } })
} }
/** 打开合同详情 */ /** 打开合同详情 */
const { push } = useRouter() const { push } = useRouter()
const openDetail = (id: number) => { const openDetail = (row) => {
push({ name: 'CrmContractDetail', params: { id } }) router.push({ name: 'CrmContractDetail', query: { id: row.id } })
} }
/** 打开客户详情 */ /** 打开客户详情 */
const openCustomerDetail = (id: number) => { const openCustomerDetail = (id: number) => {
push({ name: 'CrmCustomerDetail', params: { id } }) router.push({ name: 'CrmCustomerDetail', query: { id } })
} }
/** 打开联系人详情 */ /** 打开联系人详情 */

View File

@ -361,6 +361,7 @@ import * as UserApi from '@/api/system/user'
import * as DeptApi from '@/api/system/dept' import * as DeptApi from '@/api/system/dept'
import * as BusinessApi from '@/api/crm/business' import * as BusinessApi from '@/api/crm/business'
import { erpPriceMultiply, erpPriceInputFormatter } from '@/utils' import { erpPriceMultiply, erpPriceInputFormatter } from '@/utils'
import { propTypes } from '@/utils/propTypes'
/** CRM 方案报价 表单 */ /** CRM 方案报价 表单 */
defineOptions({ name: 'QuotationForm' }) defineOptions({ name: 'QuotationForm' })
@ -375,7 +376,9 @@ const deptTree = ref() // 部门树形结构
const deptList = ref() // const deptList = ref() //
const invoiceTemplateList = ref([]) const invoiceTemplateList = ref([])
const props = defineProps({
id: propTypes.number.def(undefined)
})
const dialogVisible = ref(false) // const dialogVisible = ref(false) //
const dialogTitle = ref('') // const dialogTitle = ref('') //
const formLoading = ref(false) // 12 const formLoading = ref(false) // 12
@ -590,8 +593,7 @@ const resetForm = () => {
const route = useRoute(); const route = useRoute();
onMounted(async () => { onMounted(async () => {
formType.value = route.query.id; formType.value = props.id
if (formType.value) open(formType.value) if (formType.value) open(formType.value)
// //

View File

@ -142,7 +142,7 @@
<el-form-item label="合作主体" prop="partnerCompanyId"> <el-form-item label="合作主体" prop="partnerCompanyId">
<el-select v-model="formData.partnerCompanyId" placeholder="请选择合作主体" @change="onPartnerChange"> <el-select v-model="formData.partnerCompanyId" placeholder="请选择合作主体" @change="onPartnerChange">
<el-option <el-option
v-for="dict in deptList" v-for="dict in orgList"
:key="dict.id" :key="dict.id"
:label="dict.name" :label="dict.name"
:value="dict.id" :value="dict.id"
@ -360,6 +360,7 @@ import { QuotationApi, QuotationVO } from '@/api/crm/quotation'
import { defaultProps, handleTree } from '@/utils/tree' import { defaultProps, handleTree } from '@/utils/tree'
import { BillTemplateApi, BillTemplateVO } from '@/api/crm/billtemplate' import { BillTemplateApi, BillTemplateVO } from '@/api/crm/billtemplate'
import QuotationProductForm from './components/QuotationProductForm.vue' import QuotationProductForm from './components/QuotationProductForm.vue'
import * as ContractApi from '@/api/crm/contract'
import * as CustomerApi from '@/api/crm/customer' import * as CustomerApi from '@/api/crm/customer'
import * as UserApi from '@/api/system/user' import * as UserApi from '@/api/system/user'
import * as DeptApi from '@/api/system/dept' import * as DeptApi from '@/api/system/dept'
@ -376,6 +377,7 @@ const templateOptions = ref([])
const businessList = ref([]) const businessList = ref([])
const deptTree = ref() // const deptTree = ref() //
const deptList = ref() // const deptList = ref() //
const orgList = ref([])
const invoiceTemplateList = ref([]) const invoiceTemplateList = ref([])
const { proxy }: any = getCurrentInstance(); const { proxy }: any = getCurrentInstance();
@ -619,5 +621,10 @@ onMounted(async () => {
businessList.value = await BusinessApi.getSimpleBusinessList() businessList.value = await BusinessApi.getSimpleBusinessList()
// //
deptTree.value = handleTree(await DeptApi.getSimpleDeptList()) deptTree.value = handleTree(await DeptApi.getSimpleDeptList())
const org = await ContractApi.getOrg({
pageNo: 1,
pageSize: 1000
})
orgList.value = org.list
}); });
</script> </script>

View File

@ -154,6 +154,14 @@
> >
编辑 编辑
</el-button> </el-button>
<el-button
v-hasPermi="['crm:customer-suggestion:query']"
link
type="primary"
@click="handleProcessDetail(scope.row)"
>
进度
</el-button>
<el-button <el-button
link link
type="danger" type="danger"
@ -246,7 +254,7 @@ const openFormAdd = () => {
const openFormDetail = (row: Object) => { const openFormDetail = (row: Object) => {
push({ name: 'QuotationDetail', query: { id: row.id, customerId: row.customerId } }) router.push({ name: 'QuotationDetail', query: { id: row.id } })
} }
/** 删除按钮操作 */ /** 删除按钮操作 */
@ -262,6 +270,16 @@ const handleDelete = async (id: number) => {
} catch {} } catch {}
} }
/** 审批进度 */
const router = useRouter() //
const handleProcessDetail = (row) => {
router.push({
name: 'BpmProcessInstanceDetail',
query: {
id: row.processInstanceId
}
})
}
/** 导出按钮操作 */ /** 导出按钮操作 */
const handleExport = async () => { const handleExport = async () => {
try { try {