Commit 86655bf0 authored by 前端-钟卫鹏's avatar 前端-钟卫鹏

Merge branch 'dev-srm' of http://10.0.0.22:3000/lingxi/lingxi-business-paltform into dev-srm

parents ae76195d 2368dfa9
......@@ -37,30 +37,77 @@ export const purchaseBidRoute = [
component: '@/pages/transaction/purchaseAbility/purchaseBid/readyAdd/add',
hideInMenu: true
},
// 修改采购竞价单
{
path: '/memberCenter/procurementAbility/purchaseBid/readyAdd/modify',
name: '修改采购竞价单',
component: '@/pages/transaction/purchaseAbility/purchaseBid/readyAdd/add',
hideInMenu: true
},
// 待新增采购竞价单详情
{
path: '/memberCenter/procurementAbility/purchaseBid/readyAdd/detail',
name: '待新增采购竞价单详情',
component: '@/pages/transaction/purchaseAbility/purchaseBid/search/detail',
hideInMenu: true,
noMargin: true,
},
// 待审核采购竞价单(一级)
{
path: '/memberCenter/procurementAbility/purchaseBid/readyExamineOne',
name: '待审核采购竞价单(一级)',
component: '@/pages/transaction/purchaseAbility/purchaseBid/readyExamineOne'
},
// 待审核采购竞价单(一级)详情
{
path: '/memberCenter/procurementAbility/purchaseBid/readyExamineOne/detail',
name: '待审核采购竞价单(一级)详情',
component: '@/pages/transaction/purchaseAbility/purchaseBid/search/detail',
hideInMenu: true,
noMargin: true,
},
// 待审核采购竞价单(二级)
{
path: '/memberCenter/procurementAbility/purchaseBid/readyExamineTwo',
name: '待审核采购竞价单(二级)',
component: '@/pages/transaction/purchaseAbility/purchaseBid/readyExamineTwo'
},
// 待审核采购竞价单(二级)详情
{
path: '/memberCenter/procurementAbility/purchaseBid/readyExamineTwo/detail',
name: '待审核采购竞价单(二级)详情',
component: '@/pages/transaction/purchaseAbility/purchaseBid/search/detail',
hideInMenu: true,
noMargin: true,
},
// 待提交采购竞价单
{
path: '/memberCenter/procurementAbility/purchaseBid/readySubmit',
name: '待提交采购竞价单',
component: '@/pages/transaction/purchaseAbility/purchaseBid/readySubmit'
},
// 待提交采购竞价单详情
{
path: '/memberCenter/procurementAbility/purchaseBid/readySubmit/detail',
name: '待提交采购竞价单详情',
component: '@/pages/transaction/purchaseAbility/purchaseBid/search/detail',
hideInMenu: true,
noMargin: true,
},
// 待审核竞价报名
{
path: '/memberCenter/procurementAbility/purchaseBid/readyExamineSignUp',
name: '待审核竞价报名',
component: '@/pages/transaction/purchaseAbility/purchaseBid/readyExamineSignUp'
},
// 待审核竞价报名详情
{
path: '/memberCenter/procurementAbility/purchaseBid/readyExamineSignUp/detail',
name: '待审核竞价报名详情',
component: '@/pages/transaction/purchaseAbility/purchaseBid/search/detail',
hideInMenu: true,
noMargin: true,
},
// 待竞价
{
path: '/memberCenter/procurementAbility/purchaseBid/readyBid',
......@@ -75,30 +122,70 @@ export const purchaseBidRoute = [
hideInMenu: true,
noMargin: true,
},
// 待竞价详情
{
path: '/memberCenter/procurementAbility/purchaseBid/readyBid/detail',
name: '待竞价详情',
component: '@/pages/transaction/purchaseAbility/purchaseBid/search/detail',
hideInMenu: true,
noMargin: true,
},
// 待提交审核竞价结果
{
path: '/memberCenter/procurementAbility/purchaseBid/readySubmitExamineResult',
name: '待提交审核竞价结果',
component: '@/pages/transaction/purchaseAbility/purchaseBid/readySubmitExamineResult'
},
// 待提交审核竞价结果详情
{
path: '/memberCenter/procurementAbility/purchaseBid/readySubmitExamineResult/detail',
name: '待提交审核竞价结果详情',
component: '@/pages/transaction/purchaseAbility/purchaseBid/search/detail',
hideInMenu: true,
noMargin: true,
},
// 待审核竞价结果(一级)
{
path: '/memberCenter/procurementAbility/purchaseBid/readyExamineResultOne',
name: '待审核竞价结果(一级)',
component: '@/pages/transaction/purchaseAbility/purchaseBid/readyExamineResultOne'
},
// 待审核竞价结果(一级)详情
{
path: '/memberCenter/procurementAbility/purchaseBid/readyExamineResultOne/detail',
name: '待审核竞价结果(一级)详情',
component: '@/pages/transaction/purchaseAbility/purchaseBid/search/detail',
hideInMenu: true,
noMargin: true,
},
// 待审核竞价结果(二级)
{
path: '/memberCenter/procurementAbility/purchaseBid/readyExamineResultTwo',
name: '待审核竞价结果(二级)',
component: '@/pages/transaction/purchaseAbility/purchaseBid/readyExamineResultTwo'
},
// 待审核竞价结果(二级)详情
{
path: '/memberCenter/procurementAbility/purchaseBid/readyExamineResultTwo/detail',
name: '待审核竞价结果(二级)详情',
component: '@/pages/transaction/purchaseAbility/purchaseBid/search/detail',
hideInMenu: true,
noMargin: true,
},
// 待审核竞价结果
{
path: '/memberCenter/procurementAbility/purchaseBid/readyConfirm',
name: '待审核竞价结果',
component: '@/pages/transaction/purchaseAbility/purchaseBid/readyConfirm'
},
// 待审核竞价结果详情
{
path: '/memberCenter/procurementAbility/purchaseBid/readyConfirm/detail',
name: '待审核竞价结果详情',
component: '@/pages/transaction/purchaseAbility/purchaseBid/search/detail',
hideInMenu: true,
noMargin: true,
},
]
},
]
......@@ -436,6 +436,7 @@ const Details = (props: any) => {
fontSize: '14px',
color: '#909399',
}}
onClick={() => history.goBack()}
/>
<span
style={{
......
......@@ -53,11 +53,6 @@ const AddInfo = (props: any) => {
/* 付款阶段 */
const [payPlanList, setpayPlanList] = useState<any>([]);
/* 选中设置值 */
// const tag = [
// { name: '账期(默认)', Index: 1 },
// { name: '现结', Index: 2 },
// { name: '月结', Index: 3 },
// ]
const [Index, setIndex] = useState<number>(1)
const columnsList: any = [
{
......@@ -119,7 +114,6 @@ const AddInfo = (props: any) => {
const basic = basics;
basics[key] = e;
setBasics(basic);
console.log(e, key);
}
/* 确认回显数据 */
const Confirm = () => {
......@@ -145,6 +139,7 @@ const AddInfo = (props: any) => {
basicsData.contractId = selectRow.id;
basicsData.payParam = res.data.payPlanList[0].payParam
info.startTime = selectRow.startTime;
basicsData.applyAmount = res.data.payPlanList[0].payAmount;
setapplyAmount(res.data.payPlanList[0].payAmount)
info.status = "同意签订合同";
setpayPlanList(res.data.payPlanList)
......@@ -157,7 +152,8 @@ const AddInfo = (props: any) => {
tagList.push({
name: item.payWay == 1 ? '账期' : item.payWay == 2 ? '月结' : '现结',
payParam: item.payParam,
Index: index + 1
Index: index + 1,
id: item.id,
})
})
setTag(tagList)
......@@ -210,8 +206,32 @@ const AddInfo = (props: any) => {
})
})
}
return (
/* 切换请款金额 */
const onSelect = (e) => {
setBasicsKey(e)
}
/* 切换 给对应的赋值 */
const setBasicsKey = (id: string) => {
let key: any = {};
payPlanList.some((item: any, index: number) => {
item.Index = index + 1;
if (item.id == id) {
key = item
}
})
console.log(key);
const basicsData = basics;
basicsData.applyAmount = key.payAmount;
basicsData.payWay = key.payWay;
basicsData.payPlanId = key.id;
basicsData.expectPayTime = moment(key.expectPayTime),
basicsData.payRatio = key.payRatio;
setBasics(basicsData)
setIndex(key.Index);
attrValueForm.setFieldsValue(basicsData);
}
return (
<div>
<Form
form={attrValueForm}
......@@ -281,7 +301,7 @@ const AddInfo = (props: any) => {
initialValue={basics.payPlanId}
labelCol={{ span: 4 }} wrapperCol={{ span: 18 }}>
<Select
// onChange={(e) => onSelectChange(e)}
onChange={(e) => onSelect(e)}
>
{
payPlanList.map(item => (
......@@ -335,7 +355,7 @@ const AddInfo = (props: any) => {
{
tag.map((item: any) => {
return (
<span className={item.Index == Index ? styles.tative : styles.tag} onClick={() => setIndex(item.Index)}>{item.name}</span>
<span className={item.Index == Index ? styles.tative : styles.tag} onClick={() => setBasicsKey(item.id)}>{item.name}</span>
)
})
}
......
......@@ -221,7 +221,7 @@ const QueryList = () => {
useStateFilterSearchLinkageEffect(
$,
actions,
'orderNo',
'contractNo',
FORM_FILTER_PATH,
);
},
......
......@@ -162,7 +162,7 @@ const addList = () => {
/* 修改 */
const edit = (record) => {
history.push(`/memberCenter/contract/manage/add/addList/contracAdd?sourceType=${record.sourceType}&id=${record.id}`)
history.push(`/memberCenter/contract/manage/add/addList/editing?contractId=${record.id}`)
}
/* 提交审核 */
......
import React, { useState, useEffect, forwardRef } from 'react';
import { Button, Input, Select, DatePicker, Form, Drawer } from 'antd'
import { PublicApi } from '@/services/api';
import moment from 'moment';
const { Option } = Select;
const { RangePicker } = DatePicker;
const Information = (props: any) => {
const { currentRef, basic } = props;
const [attrValueForm] = Form.useForm();
/**
* @param {{basicsVO}} 表单数据集合
* */
useEffect(() => {
console.log(basic)
attrValueForm.setFieldsValue(basic)
}, [basic])
useEffect(() => {
currentRef.current = {
get: () => new Promise((resolve: any) => {
attrValueForm.validateFields().then(res => {
resolve({
state: true,
name: 'basic',
data: res
})
}).catch(error => {
if (error && error.errorFields) {
}
})
})
}
})
const rangeConfig = {
rules: [{ type: 'array' as const, required: true, message: ' 请选择开始或者结束时间' }],
};
return (
<div>
<Form
form={attrValueForm}
name="edit_infomation"
layout="horizontal"
labelAlign="left"
colon={false}
autoComplete="off"
>
<Form.Item
label="合同编号"
labelAlign="left"
name="contractNo"
labelCol={{ span: 2 }}
wrapperCol={{ span: 8 }}
initialValue={basic.contractNo}
rules={[
{
required: true,
message: '请输入合同编号',
},
]}
>
{/* disabled */}
<Input placeholder='请输入合同编号' disabled />
</Form.Item>
<Form.Item
label="合同摘要"
labelAlign="left"
name="contractAbstract"
labelCol={{ span: 2 }}
wrapperCol={{ span: 8 }}
rules={[
{
required: true,
message: '请输入合同摘要',
},
]}
>
<Input placeholder='请输入合同摘要' />
</Form.Item>
<Form.Item
label="寻源类型"
labelAlign="left"
name="sourceType"
labelCol={{ span: 2 }}
wrapperCol={{ span: 8 }}
initialValue={basic.sourceType}
rules={[
{
required: true,
message: '请选择寻源类型',
},
]}
>
<Select disabled>
<Option value="1" >采购询价</Option>
<Option value="2" >采购招标</Option>
<Option value="3" >采购竞价</Option>
</Select>
</Form.Item>
<Form.Item
label="合同有效期"
labelAlign="left"
labelCol={{ span: 2 }}
wrapperCol={{ span: 8 }}
name="range-picker"
{...rangeConfig}
>
<RangePicker style={{ width: '100%' }} />
</Form.Item>
<Form.Item
label="对应单据"
labelAlign="left"
labelCol={{ span: 2 }}
name="sourceNo"
initialValue={basic.sourceNo ? basic.sourceNo : ''}
wrapperCol={{ span: 8 }}
>
<Input placeholder='最长60个字符,30个汉字' disabled />
</Form.Item>
<Form.Item
label="授标会员"
labelAlign="left"
labelCol={{ span: 2 }}
name="partyBName"
initialValue={basic.partyBName ? basic.partyBName : ''}
wrapperCol={{ span: 8 }}
rules={[
{
required: true,
message: '请选择授标会员',
},
]}
>
<Input placeholder='最长60个字符,30个汉字' disabled />
</Form.Item>
<Form.Item
label="授标金额"
labelAlign="left"
labelCol={{ span: 2 }}
wrapperCol={{ span: 8 }}
>
<p>{basic.totalAmount ? `¥${basic.totalAmount}` : ''}</p>
</Form.Item>
</Form>
</div>
)
}
export default forwardRef(Information)
import React, { useState, useRef, useEffect } from 'react'
import { Button, Card, Tabs, Form } from 'antd'
import { PageHeaderWrapper } from '@ant-design/pro-layout'
import { PublicApi } from '@/services/api';
import { history } from 'umi'
import Information from './components/information'
import {
SaveOutlined,
} from '@ant-design/icons'
const { TabPane } = Tabs;
const Editing: React.FC<{}> = (props: any) => {
const {
location: {
query: {
contractId, // 寻源类型
} } } = props;
const currentBasic = useRef<any>({});
const purchaseMate = useRef<any>([])
const payPlan = useRef<any>([])
const contractText = useRef<any>({})
/**
* @param name tag标签名
* @param components 显示内容
*/
const [basic, setbasic] = useState<any>({});
const [purchaseMaterielList, setpurchaseMaterielList] = useState<any>({})
const [payPlanList, setpayPlanList] = useState<any>([]);
const TabList = [
{
name: '基本信息',
components:
<Information currentRef={currentBasic} basic={basic} />
},
{
name: '采购物料',
components:
2
},
{
name: '付款计划',
components:
3
},
{ name: '合同文本', components: 5 },
]
useEffect(() => {
PublicApi.getContractManageGetDetail({ contractId }).then(res => {
if (res.code === 1000) {
console.log(res);
const { basics } = res.data;
basic.sourceType = String(basic.sourceType);
console.log(basics.sourceType)
setbasic(basics)
}
})
console.log(contractId);
}, [])
return (
<PageHeaderWrapper
title="新建合同"
extra={[
<Button key="1" type="primary" icon={<SaveOutlined />} > 保存</Button>
]}
>
<Card>
<Tabs defaultActiveKey="0" type="card" size="small">
{
TabList.map((item, index) => (
<TabPane tab={item.name} key={index}>
{item.components}
</TabPane>
))
}
</Tabs>
</Card>
</PageHeaderWrapper>
)
}
export default Editing;
......@@ -283,7 +283,7 @@ export const userchema: any = {
export const QueryListSchema: ISchema = {
type: 'object',
properties: {
orderNo: {
contractNo: {
type: 'string',
"x-component": 'SearchFilter',
'x-component-props': {
......
......@@ -4,10 +4,10 @@ import { CaretDownOutlined, CaretUpOutlined } from '@ant-design/icons';
const areaItem = (props: any) => {
const { data } = props;
const [showMore, setShowMore] = useState<any>(false);
// const showDataSource = showMore ? data['inviteTenderAreaList'] : [...data['inviteTenderAreaList']].splice(0, 3)
const showDataSource = useMemo(() => {
return showMore ? data['inviteTenderAreaList'] : [...data['inviteTenderAreaList']].splice(0, 3)
}, [showMore, data])
const showDataSource = showMore ? data : [...data].splice(0, 3)
// const showDataSource = useMemo(() => {
// return showMore ? data : [...data].splice(0, 3)
// }, [showMore, data])
const toogleMore = () => {
setShowMore(!showMore);
......@@ -15,11 +15,11 @@ const areaItem = (props: any) => {
return (
<>
{showDataSource.map((_item, _i) => <p key={`address${_i}`}>{_item.provinceName + '/' + (_item.cityName || '')}</p>)}
{showDataSource.map((_item, _i) => <p key={`address${_i}`}>{_item.province + '/' + (_item.city || '')}</p>)}
{
data.length > 3 &&
<p onClick={toogleMore} style={{ cursor: 'pointer' }} className="commonPickColor">
展开{showMore ? <CaretDownOutlined /> : <CaretUpOutlined />}
{showMore ? '收起' : '展开'}{showMore ? <CaretUpOutlined /> : <CaretDownOutlined />}
</p>
}
</>
......
......@@ -38,9 +38,9 @@ const BidCommonLayout: React.FC<BidCommonLayoutProps> = (props: any) => {
case 'text':
return data.extra
case 'area':
return <AreaItem />
return <AreaItem data={data.extra} />
case 'files':
return <FilesItem />
return <FilesItem files={data.extra} />
}
}
const _returnChild = (child, key) => {
......@@ -80,23 +80,23 @@ const BidCommonLayout: React.FC<BidCommonLayoutProps> = (props: any) => {
return (<Row gutter={[8, 8]}>
{effect.map((item, index) => (
<Col span={5} key={`effect_msg_${index}`}>
<MsgItem itemIndex={index} />
<MsgItem data={item} rank={index} />
</Col>
))}
</Row>)
} else if (layoutType === 'result') {
return (
<Row gutter={[8, 8]}>
{effect.map((item, index) => (
{effect?.list?.map((item, index) => (
<Col span={5} key={`effect_result_${index}`}>
<ResultItem itemIndex={index} checkDetailFunc={checkDetailFunc} />
<ResultItem detail={item} itemIndex={index} checkDetailFunc={checkDetailFunc} />
</Col>
))}
<Col span={24}>
<Divider dashed style={{ color: '#EBECF0' }} />
<div className={selfStyles.baseItem}>
<h5 className={selfStyles.label}>授标意见: </h5>
<h5 className={selfStyles.content}>最低价中标</h5>
<h5 className={selfStyles.content}>{effect.signUpIdea}</h5>
</div>
<div className={selfStyles.baseItem}>
<h5 className={selfStyles.label}>附件: </h5>
......
......@@ -5,39 +5,41 @@ import { LinkOutlined } from '@ant-design/icons';
import styles from './index.less';
export interface MsgItemPrpos {
itemIndex: number,
detail?: any
rank?: number,
data?: any,
}
const MsgItem: React.FC<MsgItemPrpos> = (props: any) => {
const { itemIndex, detial } = props;
const { data, rank } = props;
const rankNumber = Number(rank) + 1;
return (
<div key={`msgItem_key_${itemIndex}`} className={styles.msgItem}>
<div className={styles.msgItem}>
<div className={styles.msgItemRow}>
<div className={styles.badge}>1</div>
<div className={styles.title}>广州白马皮具交易中心</div>
<div className={styles.badge}>{rankNumber}</div>
<div className={styles.title}>{data.memberName}</div>
</div>
<div className={styles.msgItemRow}><div className={styles.label}>联系人姓名:</div><div className={styles.title}>小王</div></div>
<div className={styles.msgItemRow}><div className={styles.label}>联系人手机:</div><div className={styles.title}>185 2929 6758</div></div>
<div className={styles.msgItemRow}><div className={styles.label}>电子邮箱:</div><div className={styles.title}>kuaimeizheng@qq.com</div></div>
<div className={styles.msgItemRow}><div className={styles.label}>联系地址:</div>{<Tooltip placement="top" title={'广东省广州市海珠区新港东路168…'}>
<div className={styles.title}>广东省广州市海珠区新港东路168…</div>
<div className={styles.msgItemRow}><div className={styles.label}>联系人姓名:</div><div className={styles.title}>{data.contacts}</div></div>
<div className={styles.msgItemRow}><div className={styles.label}>联系人手机:</div><div className={styles.title}>{data.tel}</div></div>
<div className={styles.msgItemRow}><div className={styles.label}>电子邮箱:</div><div className={styles.title}>{data.mail}</div></div>
<div className={styles.msgItemRow}><div className={styles.label}>联系地址:</div>{<Tooltip placement="top" title={data.address}>
<div className={styles.title}>{data.address}</div>
</Tooltip>}</div>
<div className={styles.msgItemRow}>
<div className={styles.label}>报名文件:</div>
<div className={styles.files}>
<Typography.Link
style={{ display: 'block', paddingBottom: '8px' }}
target="_blank"
>
<LinkOutlined />营业执照.pdf
</Typography.Link>
<Typography.Link
style={{ display: 'block', paddingBottom: '8px' }}
target="_blank"
>
<LinkOutlined />报名信息.doc
</Typography.Link>
{data.enclosureUrls && data.enclosureUrls.map((item, index) => {
return (
<Typography.Link
style={{ display: 'block', paddingBottom: '8px' }}
target="_blank"
href={item.url}
key={`Typography_${item.name}_${index}`}
>
<LinkOutlined />{item.name}
</Typography.Link>
)
})}
</div>
</div>
</div>
......
......@@ -15,10 +15,11 @@ export interface ResultItemPrpos {
}
const ResultItem: React.FC<ResultItemPrpos> = (props: any) => {
const { itemIndex, detial, checkDetailFunc } = props;
const { itemIndex, detail, checkDetailFunc } = props;
const _returnBadge = (number) => {
switch (number) {
const _number = Number(number)+1;
switch (_number) {
case 1:
return <img src={level1} alt='第一名' />;
case 2:
......@@ -26,22 +27,22 @@ const ResultItem: React.FC<ResultItemPrpos> = (props: any) => {
case 3:
return <img src={level3} alt='第三名' />;
default:
return <div className={styles.badge}>number</div>
return <div className={styles.badge}>{_number}</div>
}
}
return (
<div key={`msgItem_key_${itemIndex}`} className={styles.resultItem}>
<img src={winBig} alt="授标" className={styles.resultItemWinBid}/>
{detail.isAward && <img src={winBig} alt="授标" className={styles.resultItemWinBid}/>}
<div className={styles.resultItemRow}>
<div className={styles.title}>广州白马皮具交易中心{_returnBadge(1)}</div>
<div className={styles.title}>{detail.memberName}{_returnBadge(detail.purchaseRanking)}</div>
</div>
<div className={styles.resultItemRow}>
<div className={styles.money}>¥900.00<span>(含税)</span></div>
<div className={styles.money}>¥{detail.price}<span>(含税)</span></div>
<Button type='link' onClick={checkDetailFunc}>查看报价明细</Button>
</div>
<Divider dashed style={{ color: '#EBECF0', margin: '6px 0' }} />
<div className={styles.resultItemRow}><div className={styles.label}>联系人姓名:</div><div className={styles.title}>小王</div></div>
<div className={styles.resultItemRow}><div className={styles.label}>联系人手机:</div><div className={styles.title}>185 2929 6758</div></div>
<div className={styles.resultItemRow}><div className={styles.label}>联系人姓名:</div><div className={styles.title}>{detail.contacts}</div></div>
<div className={styles.resultItemRow}><div className={styles.label}>联系人手机:</div><div className={styles.title}>{detail.tel}</div></div>
</div>
)
}
......
......@@ -25,11 +25,13 @@ const TextStyle = {
}
export interface DemandLayoutIProps {
storeList?: any
storeList?: any,
title?: string
}
const DemandLayout: React.FC<DemandLayoutIProps> = (props: any) => {
const { storeList } = props;
const { storeList, title } = props;
console.log(title)
const context = useContext(Context);
const columns = [
......@@ -109,7 +111,7 @@ const DemandLayout: React.FC<DemandLayoutIProps> = (props: any) => {
title='需求对接'
>
<div className={style.list}>
<h5 className={style.listLable} style={{ flex: '0 0 100px' }}>发布方式</h5>
<h5 className={style.listLable} style={{ flex: '0 0 100px' }}>{title}</h5>
<h5 className={style.listContent}>{TYPE[context.type]}</h5>
</div>
{context.type === 1
......@@ -138,4 +140,9 @@ const DemandLayout: React.FC<DemandLayoutIProps> = (props: any) => {
</Card>
)
}
DemandLayout.defaultProps = {
title: '发布方式'
}
export default DemandLayout;
......@@ -206,7 +206,7 @@ const ModalOperate: React.FC<IProps> = (props: any) => {
}}
>
{modalNode()}
{(modalType === 'audit' || modalType === 'abandon')
{(modalType === 'audit' || modalType === 'abandon' || modalType === 'discard')
&& (<Field
title={modalText}
name={modalType === 'audit' ? 'auditOpinion' : 'reason'}
......
......@@ -8,6 +8,9 @@ import NiceForm from '@/components/NiceForm';
import { createFormActions, FormEffectHooks } from '@formily/antd';
import { useStateFilterSearchLinkageEffect } from '@/formSchema/effects/useFilterSearch';
import { searchSelectGetSelectCategoryOptionEffect } from '@/pages/transaction/effect/index';
import { useLinkageUtils } from '@/utils/formEffectUtils';
const { onFormMount$ } = FormEffectHooks
import {
PurchaseDemandSchema,
PurchaseDemandPublicSchema,
......@@ -20,13 +23,13 @@ import {
CONFIRMOFFERSUBMITAPRICE_SCHEMA,
CONFIRMOFFERAUDIT_SCHEMA,
} from '../../schema';
import {
import {
PURCHASEBIDORDER_SCHEMA,
PURCHASEBIDREADYADD_SCHEMA,
PURCHASEBIDOSIGNUP_SCHEMA,
} from '../../schema/purchaseBid';
import {
import {
ONLINEBIDORDER_SCHEMA,
ONLINEBIDREADYBID_SCHEMA,
ONLINEBIDREADYSIGN_SCHEMA,
......@@ -37,26 +40,28 @@ interface Iprops {
fetchRowkeys?(e: any),
controllerBtns?: React.ReactNode,
schemaType?:
'PurchaseDemand' |
'PurchaseDemandPublic' |
'INQUIRYDEMANDORDER_SCHEMA' |
'INQUIRYWAITORDER_SCHEMA' |
'OFFERDEMANDSERAH_SCHEMA' |
'OFFERSERAH_SCHEMA' |
'OFFERSERAHAUDIT_SCHEMA' |
'CONFIRMOFFERSERAH_SCHEMA' |
'CONFIRMOFFERSUBMITAPRICE_SCHEMA' |
'CONFIRMOFFERAUDIT_SCHEMA' |
'PURCHASEBIDORDER_SCHEMA' |
'PURCHASEBIDREADYADD_SCHEMA' |
'PURCHASEBIDOSIGNUP_SCHEMA' |
'ONLINEBIDORDER_SCHEMA' |
'ONLINEBIDREADYBID_SCHEMA' |
'ONLINEBIDREADYSIGN_SCHEMA'
'PurchaseDemand' |
'PurchaseDemandPublic' |
'INQUIRYDEMANDORDER_SCHEMA' |
'INQUIRYWAITORDER_SCHEMA' |
'OFFERDEMANDSERAH_SCHEMA' |
'OFFERSERAH_SCHEMA' |
'OFFERSERAHAUDIT_SCHEMA' |
'CONFIRMOFFERSERAH_SCHEMA' |
'CONFIRMOFFERSUBMITAPRICE_SCHEMA' |
'CONFIRMOFFERAUDIT_SCHEMA' |
'PURCHASEBIDORDER_SCHEMA' |
'PURCHASEBIDREADYADD_SCHEMA' |
'PURCHASEBIDOSIGNUP_SCHEMA' |
'ONLINEBIDORDER_SCHEMA' |
'ONLINEBIDREADYBID_SCHEMA' |
'ONLINEBIDREADYSIGN_SCHEMA'
columns: ColumnType<any>[],
effects?: string,
selectedRow?: boolean,
reload?: any,
externalStatusFetch?: any,
interiorStatusFetch?: any,
}
const formActions = createFormActions();
const Table: React.FC<Iprops> = (props: any) => {
......@@ -68,7 +73,9 @@ const Table: React.FC<Iprops> = (props: any) => {
controllerBtns,
selectedRow,
reload,
fetchRowkeys
fetchRowkeys,
externalStatusFetch,
interiorStatusFetch
} = props;
const tableRef = useRef<any>({});
/** Schema */
......@@ -138,6 +145,21 @@ const Table: React.FC<Iprops> = (props: any) => {
tableRef.current.reload(values)
}
const useBusinessEffects = () => {
const linkage = useLinkageUtils();
onFormMount$().subscribe(() => {
externalStatusFetch && externalStatusFetch().then(res => {
const _enum = res.data.map((item) => {return { label: item.name, value: item.satatus }})
linkage.enum('externalState',_enum)
})
interiorStatusFetch && interiorStatusFetch().then(res => {
const _enum = res.data.map((item) => {return { label: item.name, value: item.satatus }})
linkage.enum('interiorState',_enum)
})
})
}
return (
<PageHeaderWrapper>
<Card>
......@@ -157,6 +179,7 @@ const Table: React.FC<Iprops> = (props: any) => {
FormEffectHooks.onFieldChange$('category').subscribe(state => {
searchSelectGetSelectCategoryOptionEffect(actions, 'category')
})
useBusinessEffects();
}}
schema={
schemaType && SchemaRender()
......
......@@ -31,8 +31,15 @@ const TabFormErrors = (props) => {
}
const AddForm = () => {
const { id, number } = history.location.query;
const {
query: {
id,
number
},
pathname, } = history.location;
const { memberId, memberRoleId, name } = JSON.parse(localStorage.getItem('auth'));
const [path] = useState(pathname.split('/')[pathname.split('/').length - 1]);
console.log(path)
/** 基本信息 */
const [basic, setBasic] = useState<any>({});
/** 添加采购物料 */
......@@ -76,14 +83,14 @@ const AddForm = () => {
memberRoleId,
memberName: name,
details: basicRef.data.details,
isAreas : basicRef.data.isAreas,
isAreas: basicRef.data.isAreas,
areas: basicRef.data.areas,
...materialRef.data,
...conditionRef.data,
...demandRef.data,
...ruleRef.data,
...requirementRef.data,
urls : [...fileRef.data]
urls: [...fileRef.data]
}
let res: {
code: number,
......@@ -123,11 +130,13 @@ const AddForm = () => {
current: '1',
pageSize: '1',
}
PublicApi.getPurchasePurchaseInquiryDetails(parmas).then((res: any) => {
PublicApi.getPurchaseBiddingDetails(parmas).then((res: any) => {
if (res.code === 1000) {
const params: GetPurchasePurchaseInquiryDetailsResponse = res.data;
const basicInfo: GetPurchasePurchaseInquiryDetailsResponse = { ...basic };
const materialInfo: GetPurchasePurchaseInquiryDetailsResponse = { ...material };
const rulesInfo: GetPurchasePurchaseInquiryDetailsResponse = { ...rules };
const requirementInfo: GetPurchasePurchaseInquiryDetailsResponse = { ...requirement };
const conditionInfo: GetPurchasePurchaseInquiryDetailsResponse = { ...condition };
const demandInfo: GetPurchasePurchaseInquiryDetailsResponse = { ...demand };
basicInfo.details = params.details;
......@@ -139,16 +148,35 @@ const AddForm = () => {
cityCode: '',
city: ''
}];
basicInfo.memberName = params.memberName;
basicInfo.purchaseInquiryNo = params.purchaseInquiryNo;
basicInfo.memberName = params.createMemberName;
basicInfo.biddingNo = params.biddingNo;
basicInfo.createTime = params.createTime;
basicInfo.externalState = params.externalState
basicInfo.externalState = params.externalState;
basicInfo.externalStateName = params.externalStateName;
basicInfo.interiorState = params.interiorState;
basicInfo.interiorStateName = params.interiorStateName;
setBasic(basicInfo);
materialInfo.materielMode = params.materielMode;
materialInfo.materiels = params.materiels;
setMaterial(materialInfo);
conditionInfo.deliveryTime = params.deliveryTime;
rulesInfo.biddingStartTime = params.biddingStartTime;
rulesInfo.biddingEndTime = params.biddingEndTime;
rulesInfo.isStartingPrice = params.isStartingPrice;
rulesInfo.isTargetPrice = params.isTargetPrice;
rulesInfo.isMinPrice = params.isMinPrice;
rulesInfo.isOpenPurchase = params.isOpenPurchase;
rulesInfo.isOpenRanking = params.isOpenRanking;
rulesInfo.startingPrice = params.startingPrice;
rulesInfo.targetPrice = params.targetPrice;
rulesInfo.allowPurchaseCount = params.allowPurchaseCount;
rulesInfo.minPrice = params.minPrice;
setRules(rulesInfo);
requirementInfo.startSignUp = params.startSignUp;
requirementInfo.endSignUp = params.endSignUp;
requirementInfo.demand = params.demand;
requirementInfo.demandUrls = params.demandUrls;
setRequirement(requirementInfo);
conditionInfo.deliver = params.deliver;
conditionInfo.offerEndTime = params.offerEndTime;
conditionInfo.address = params.address;
conditionInfo.addressId = params.addressId;
......@@ -163,10 +191,12 @@ const AddForm = () => {
demandInfo.shopIds = params.shopIds;
demandInfo.demandMembers = params.demandMembers;
setDemand(demandInfo);
setfile([...params.urls]);
}
})
}
}, [id, number])
return (
<PageHeaderWrapper
onBack={() => history.goBack()}
......
......@@ -305,19 +305,19 @@ const BasicInfo: React.FC<Iprops> = (props: any) => {
label='竞价单号'
name='purchaseInquiryNo'
>
<Text strong>{(fetchdata && fetchdata.purchaseInquiryNo) && fetchdata.purchaseInquiryNo}</Text>
<Text strong>{(fetchdata && fetchdata.biddingNo) && fetchdata.biddingNo}</Text>
</Form.Item>
<Form.Item
label='外部状态'
name='externalState'
>
<Text type="warning" strong>{(fetchdata && fetchdata.externalState) && BID_EXTERNALSTATE[fetchdata.externalState]}</Text>
<Text type="warning" strong>{(fetchdata && fetchdata.externalState) && fetchdata.externalStateName}</Text>
</Form.Item>
<Form.Item
label='内部状态'
name='interiorState'
>
<Text type="warning" strong>{(fetchdata && fetchdata.interiorState) && BID_INTERNALSTATE[fetchdata.interiorState]}</Text>
<Text type="warning" strong>{(fetchdata && fetchdata.interiorState) && fetchdata.interiorStateName}</Text>
</Form.Item>
</Form>
</>
......
......@@ -74,6 +74,11 @@ const BidRules: React.FC<Iprops> = (props: any) => {
}, [])
useEffect(() => {
fetchdata.isStartingPrice != undefined && setIsStartingPrice(!!fetchdata.isStartingPrice);
fetchdata.isTargetPrice != undefined && setIsTargetPrice(!!fetchdata.isTargetPrice);
fetchdata.isMinPrice != undefined && setIsMinPrice(!!fetchdata.isMinPrice);
setIsOpenPurchase(!!fetchdata.isOpenPurchase);
setIsOpenRanking(!!fetchdata.isOpenRanking);
form.setFieldsValue({
biddingTime: [fetchdata.biddingStartTime ? moment(fetchdata.biddingStartTime) : '', fetchdata.biddingEndTime ? moment(fetchdata.biddingEndTime) : ''],
isStartingPrice: !!fetchdata.isStartingPrice,
......@@ -90,8 +95,8 @@ const BidRules: React.FC<Iprops> = (props: any) => {
const onCheckboxChange = (e: { target: { checked: boolean } }, func: Function, name?: string) => {
func(e.target.checked);
if(!e.target.checked && name){
form.setFieldsValue({[`${name}`] : ''})
if (!e.target.checked && name) {
form.setFieldsValue({ [`${name}`]: '' })
}
};
......@@ -127,12 +132,12 @@ const BidRules: React.FC<Iprops> = (props: any) => {
name='startingPrice'
className={styles.hidden}
rules={[{
required: true,
required: isStartingPrice ? true : false,
message: '请输入起拍价',
type: 'number',
whitespace: true,
transform(value) {
if(value){
if (value) {
return parseFloat(value)
}
},
......@@ -160,12 +165,12 @@ const BidRules: React.FC<Iprops> = (props: any) => {
name='targetPrice'
className={styles.hidden}
rules={[{
required: true,
required: isTargetPrice ? true : false,
message: '请输入目标价',
type: 'number',
whitespace: true,
transform(value) {
if(value){
if (value) {
return parseFloat(value)
}
},
......@@ -193,12 +198,12 @@ const BidRules: React.FC<Iprops> = (props: any) => {
label=" "
className={styles.hidden}
rules={[{
required: true,
required: isMinPrice ? true : false,
message: '请输入最小价差',
type: 'number',
whitespace: true,
transform(value) {
if(value){
if (value) {
return parseFloat(value)
}
},
......@@ -225,7 +230,7 @@ const BidRules: React.FC<Iprops> = (props: any) => {
whitespace: true,
pattern: new RegExp(/^[1-9]\d*$/, "g"),
transform(value) {
if(value){
if (value) {
return parseInt(value);
}
},
......
......@@ -20,7 +20,7 @@ export interface IProps {
const File: React.FC<IProps> = (props) => {
const { fetchdata, currentRef } = props;
const [form] = Form.useForm();
const [files, setFiles] = useState([]);
const [files, setFiles] = useState(fetchdata || []);
const [loading, setloading] = useState(false);
/**判断文件类型和大小 */
const beforeDocUpload = (file: any) => {
......@@ -51,11 +51,12 @@ const File: React.FC<IProps> = (props) => {
arr.splice(index, 1);
setFiles(arr);
}
// useEffect(() => {
// if (Object.keys(editData).length > 0) {
// setFiles(editData.enclosureUrls)
// }
// }, [editData])
useEffect(() => {
if (fetchdata.length > 0) {
setFiles(fetchdata)
}
}, [fetchdata])
useEffect(() => {
currentRef.current = {
......
......@@ -28,7 +28,7 @@ const ReadyAdd = () => {
dataIndex: 'biddingNo',
render: (text: any, record: any) => (
<Space direction='vertical'>
<EyePreview url={`/memberCenter/procurementAbility/offter/addOffter/view?id=${record.id}&number=${text}`}>{text}</EyePreview>
<EyePreview url={`/memberCenter/procurementAbility/purchaseBid/readyAdd/detail?id=${record.id}&number=${text}`}>{text}</EyePreview>
<Text type='secondary'>{record.details}</Text>
</Space>
)
......@@ -70,107 +70,94 @@ const ReadyAdd = () => {
</Button>
</Popconfirm>
<Dropdown overlay={() => (
<Menu onClick={(e) => handleMenuClick(e, record.id)}>
<Menu.Item key="1">
修改
</Menu.Item>
<Menu.Item key="2">
删除
</Menu.Item>
<Menu onClick={(e) => handleMenuClick(e, record)}>
<Menu.Item key="1">编辑</Menu.Item>
<Menu.Item key="2">删除</Menu.Item>
</Menu>
)}>
<Button type='link'>更多<CaretDownOutlined /></Button>
</Dropdown>
{/* <Button
onClick={() => history.push(`/memberCenter/procurementAbility/offter/edit?id=${record.id}&number=${record.quotedPriceNo}`)}
type='link'
>修改</Button>
<Popconfirm title="确定要删除吗?" okText="是" cancelText="否" onConfirm={() => fetchDeleteBatch(record.id)}>
<Button type='link'>
删除
</Button>
</Popconfirm> */}
</>
}
</>
}];
const handleMenuClick = (e: any, id: number) => {
if(e.key === 1){
}else{
fetchDeleteBatch(id);
const handleMenuClick = (e: any, record: any) => {
if (e.key === '1') {
history.push(`/memberCenter/procurementAbility/purchaseBid/readyAdd/modify?id=${record.id}&number=${record.biddingNo}`)
} else {
fetchDeleteBatch(record.id);
}
}
/** 批量审核 */
const fetchSubmitBatch = async (id?: number) => {
let res = null;
if (id) {
res = await PublicApi.postPurchaseBiddingExamine({ id });
} else {
res = await PublicApi.postPurchaseBiddingExamineBatch({ ids: rowkeys });
}
if (res.code === 1000) {
ref.current.reload();
setRowKeys([])
}
}
/**
* 删除或批量删除
* @type: 1: 单个删除, 2: 批量删除
* */
const fetchDeleteBatch = async (id?: number) => {
let res = null;
if (id) {
res = await PublicApi.postPurchaseBiddingDelete({ id });
} else {
res = await PublicApi.postPurchaseBiddingDeleteBatch({ ids: rowkeys });
/** 批量审核 */
const fetchSubmitBatch = async (id?: number) => {
let res = null;
if (id) {
res = await PublicApi.postPurchaseBiddingExamine({ id });
} else {
res = await PublicApi.postPurchaseBiddingExamineBatch({ ids: rowkeys });
}
if (res.code === 1000) {
ref.current.reload();
setRowKeys([])
}
}
if (res.code === 1000) {
ref.current.reload();
setRowKeys([])
/**
* 删除或批量删除
* @type: 1: 单个删除, 2: 批量删除
* */
const fetchDeleteBatch = async (id?: number) => {
let res = null;
if (id) {
res = await PublicApi.postPurchaseBiddingDelete({ id });
} else {
res = await PublicApi.postPurchaseBiddingDeleteBatch({ ids: rowkeys });
}
if (res.code === 1000) {
ref.current.reload();
setRowKeys([])
}
}
}
return (
<Table
selectedRow
reload={ref}
fetchRowkeys={(e) => setRowKeys(e)}
schemaType="PURCHASEBIDREADYADD_SCHEMA"
columns={columns}
effects="biddingNo"
fetch={PublicApi.getPurchaseBiddingAwaitNewList}
controllerBtns={
<Row>
<Col span={24}>
<Space size={16}>
<Button
onClick={() => history.push('/memberCenter/procurementAbility/purchaseBid/readyAdd/add')}
type="primary"
icon={<PlusOutlined />}
>
新建
return (
<Table
selectedRow
reload={ref}
fetchRowkeys={(e) => setRowKeys(e)}
schemaType="PURCHASEBIDREADYADD_SCHEMA"
columns={columns}
effects="biddingNo"
fetch={PublicApi.getPurchaseBiddingAwaitNewList}
controllerBtns={
<Row>
<Col span={24}>
<Space size={16}>
<Button
onClick={() => history.push('/memberCenter/procurementAbility/purchaseBid/readyAdd/add')}
type="primary"
icon={<PlusOutlined />}
>
新建
</Button>
<Button
onClick={() => fetchSubmitBatch()}
disabled={rowkeys.length === 0}
>
批量提交审核
<Button
onClick={() => fetchSubmitBatch()}
disabled={rowkeys.length === 0}
>
批量提交审核
</Button>
<Button
onClick={() => fetchDeleteBatch()}
disabled={rowkeys.length === 0}
>
批量删除
<Button
onClick={() => fetchDeleteBatch()}
disabled={rowkeys.length === 0}
>
批量删除
</Button>
</Space>
</Col>
</Row>
}
/>
)
</Space>
</Col>
</Row>
}
/>
)
}
export default ReadyAdd
......@@ -26,13 +26,13 @@ const ReadyBid = () => {
dataIndex: 'id',
key: 'id',
render: (t, r, i) => ++i
}, {
}, {
title: '竞价单号/摘要',
key: 'biddingNo',
dataIndex: 'biddingNo',
render: (text: any, record: any) => (
<Space direction='vertical'>
<EyePreview url={`/memberCenter/procurementAbility/offter/addOffter/view?id=${record.id}&number=${text}`}>{text}</EyePreview>
<EyePreview url={`/memberCenter/procurementAbility/purchaseBid/readyBid/detail?id=${record.id}&number=${text}`}>{text}</EyePreview>
<Text type='secondary'>{record.details}</Text>
</Space>
)
......
......@@ -36,7 +36,7 @@ const ReadyConfirm = () => {
dataIndex: 'biddingNo',
render: (text: any, record: any) => (
<Space direction='vertical'>
<EyePreview url={`/memberCenter/procurementAbility/offter/addOffter/view?id=${record.id}&number=${text}`}>{text}</EyePreview>
<EyePreview url={`/memberCenter/procurementAbility/purchaseBid/readyConfirm/detail?id=${record.id}&number=${text}`}>{text}</EyePreview>
<Text type='secondary'>{record.details}</Text>
</Space>
)
......
......@@ -32,7 +32,7 @@ const ReadyExamineOne = () => {
dataIndex: 'biddingNo',
render: (text: any, record: any) => (
<Space direction='vertical'>
<EyePreview url={`/memberCenter/procurementAbility/offter/addOffter/view?id=${record.id}&number=${text}`}>{text}</EyePreview>
<EyePreview url={`/memberCenter/procurementAbility/purchaseBid/readyExamineOne/detail?id=${record.id}&number=${text}`}>{text}</EyePreview>
<Text type='secondary'>{record.details}</Text>
</Space>
)
......
......@@ -30,7 +30,7 @@ const ReadyExamineResultOne = () => {
dataIndex: 'biddingNo',
render: (text: any, record: any) => (
<Space direction='vertical'>
<EyePreview url={`/memberCenter/procurementAbility/offter/addOffter/view?id=${record.id}&number=${text}`}>{text}</EyePreview>
<EyePreview url={`/memberCenter/procurementAbility/purchaseBid/readyExamineResultOne/detail?id=${record.id}&number=${text}`}>{text}</EyePreview>
<Text type='secondary'>{record.details}</Text>
</Space>
)
......
......@@ -31,7 +31,7 @@ const ReadyExamineResultTwo = () => {
dataIndex: 'biddingNo',
render: (text: any, record: any) => (
<Space direction='vertical'>
<EyePreview url={`/memberCenter/procurementAbility/offter/addOffter/view?id=${record.id}&number=${text}`}>{text}</EyePreview>
<EyePreview url={`/memberCenter/procurementAbility/purchaseBid/readyExamineResultTwo/detail?id=${record.id}&number=${text}`}>{text}</EyePreview>
<Text type='secondary'>{record.details}</Text>
</Space>
)
......
......@@ -35,7 +35,7 @@ const ReadyExamineSignUp = () => {
dataIndex: 'biddingNo',
render: (text: any, record: any) => (
<Space direction='vertical'>
<EyePreview url={`/memberCenter/procurementAbility/offter/addOffter/view?id=${record.id}&number=${text}`}>{text}</EyePreview>
<EyePreview url={`/memberCenter/procurementAbility/purchaseBid/readyExamineSignUp/detail?id=${record.id}&number=${text}`}>{text}</EyePreview>
<Text type='secondary'>{record.details}</Text>
</Space>
)
......
......@@ -31,7 +31,7 @@ const ReadyExamineTwo = () => {
dataIndex: 'biddingNo',
render: (text: any, record: any) => (
<Space direction='vertical'>
<EyePreview url={`/memberCenter/procurementAbility/offter/addOffter/view?id=${record.id}&number=${text}`}>{text}</EyePreview>
<EyePreview url={`/memberCenter/procurementAbility/purchaseBid/readyExamineTwo/detail?id=${record.id}&number=${text}`}>{text}</EyePreview>
<Text type='secondary'>{record.details}</Text>
</Space>
)
......
......@@ -28,7 +28,7 @@ const ReadySubmit = () => {
dataIndex: 'biddingNo',
render: (text: any, record: any) => (
<Space direction='vertical'>
<EyePreview url={`/memberCenter/procurementAbility/offter/addOffter/view?id=${record.id}&number=${text}`}>{text}</EyePreview>
<EyePreview url={`/memberCenter/procurementAbility/purchaseBid/readySubmit/detail?id=${record.id}&number=${text}`}>{text}</EyePreview>
<Text type='secondary'>{record.details}</Text>
</Space>
)
......@@ -62,14 +62,14 @@ const ReadySubmit = () => {
key: 'operate',
dataIndex: 'operate',
align: 'center',
render: (text: any, record: any) => <Button onClick={() => {fetchSubmitBatch(record.id)}} type='link'>提交</Button>
render: (text: any, record: any) => <Button onClick={() => { fetchSubmitBatch(record.id) }} type='link'>提交</Button>
}];
/** 批量审核 */
const fetchSubmitBatch = async (id?: number) => {
let res = null;
if (id) {
res = await PublicApi.postPurchaseBiddingSubmit({ id,state: 1 });
res = await PublicApi.postPurchaseBiddingSubmit({ id, state: 1 });
} else {
res = await PublicApi.postPurchaseBiddingSubmitBatch({ ids: rowkeys });
}
......
......@@ -31,7 +31,7 @@ const ReadySubmitExamineResult = () => {
dataIndex: 'biddingNo',
render: (text: any, record: any) => (
<Space direction='vertical'>
<EyePreview url={`/memberCenter/procurementAbility/offter/addOffter/view?id=${record.id}&number=${text}`}>{text}</EyePreview>
<EyePreview url={`/memberCenter/procurementAbility/purchaseBid/readySubmitExamineResult/detail?id=${record.id}&number=${text}`}>{text}</EyePreview>
<Text type='secondary'>{record.details}</Text>
</Space>
)
......
......@@ -72,6 +72,7 @@ const Search = () => {
<>
<Button
type='link'
disabled={record.externalState === -1}
onClick={() => {
setId(record.id);
setVisible(true);
......@@ -96,6 +97,8 @@ const Search = () => {
effects="biddingNo"
fetch={PublicApi.getPurchaseBiddingList}
reload={ref}
externalStatusFetch={PublicApi.getPurchaseBiddingExternalStatus}
interiorStatusFetch={PublicApi.getPurchaseBiddingInteriorStatus}
/>
<ModalOperate
id={id}
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment