供应商

This commit is contained in:
孙景学
2025-06-24 10:52:30 +08:00
parent f24a87a15c
commit c1267c8228
116 changed files with 16058 additions and 1 deletions

View File

@ -0,0 +1,120 @@
import React, { useEffect, useState } from 'react';
import { Table } from 'antd';
import type { ColumnsType, TablePaginationConfig } from 'antd/es/table';
import { bank } from '../services';
import { useIntl } from 'umi';
interface BankInfo {
id: string;
interbankNumber: string;
bank: string;
accountName: string;
account: string;
currency: string;
nation: string;
province: string;
city: string;
updateTime: string;
}
// 表格头部
const columns: ColumnsType<BankInfo> = [
{
title: 'page.workbench.bank.index',
dataIndex: 'index',
key: 'index',
width: 80,
align: 'center',
render: (_: any, __: any, index: number) => index + 1
},
{
title: 'page.workbench.bank.interbankNumber',
dataIndex: 'interbankNumber',
key: 'interbankNumber',
},
{
title: 'page.workbench.bank.bank',
dataIndex: 'bank',
key: 'bank',
},
{
title: 'page.workbench.bank.accountName',
dataIndex: 'accountName',
key: 'accountName',
},
{
title: 'page.workbench.bank.account',
dataIndex: 'account',
key: 'account',
},
{
title: 'page.workbench.bank.currency',
dataIndex: 'currency',
key: 'currency',
},
{
title: 'page.workbench.bank.nation',
dataIndex: 'nation',
key: 'nation',
},
{
title: 'page.workbench.bank.province',
dataIndex: 'province',
key: 'province',
},
{
title: 'page.workbench.bank.city',
dataIndex: 'city',
key: 'city',
},
{
title: 'page.workbench.bank.updateTime',
dataIndex: 'updateTime',
key: 'updateTime',
},
];
const BankInfoTab: React.FC = () => {
//双语
const intl = useIntl();
//列表渲染数据
const [data, setData] = useState<BankInfo[]>([]);
//列表加载
const [loading, setLoading] = useState(false);
//列表分页
const [pagination, setPagination] = useState<TablePaginationConfig>({ current: 1, pageSize: 10, total: 0 });
//列表方法
const getList = async (page: number = 1, pageSize: number = 10) => {
setLoading(true);
try {
const { code, data, total } = await bank({page, pageSize});
if (code === 200) {
setData(data);
setPagination({ current: page, pageSize, total });
}
} finally {
setLoading(false);
}
};
//初始化
useEffect(() => {
getList();
}, []);
return (
<div style={{ padding: '0 30px 0 0' }}>
<Table
rowKey="id"
className="custom-table"
columns={columns.map(column => ({
...column,
title: intl.formatMessage({ id: column.title as string })
}))}
dataSource={data}
pagination={pagination}
loading={loading}
onChange={(pagination) => getList(pagination.current!, pagination.pageSize!)}
/>
</div>
);
};
export default BankInfoTab;

View File

@ -0,0 +1,106 @@
import React, { useEffect, useState } from 'react';
import { Descriptions } from 'antd';
import { coscoSupplier } from '../services';
import { useIntl } from 'umi';
const BaseInfoTab: React.FC = () => {
const intl = useIntl();
const [registerInfo, setRegisterInfo] = useState<any>({ base: {} });
const fetchData = async () => {
const res = await coscoSupplier({});
if (res.code === 200) {
setRegisterInfo(res.data);
}
};
useEffect(() => {
//供应商信息
fetchData()
}, []);
if (!registerInfo?.base) return <div>{intl.formatMessage({ id: 'component.globalModal.loading' })}...</div>;
return (
<div style={{ padding: '0 30px 0 0' }}>
<Descriptions
bordered
column={2}
size="middle"
style={{ background: '#fff', padding: '16px 0 0' }}
>
{registerInfo.base.supplierType === 'dvs' && (
<Descriptions.Item label={intl.formatMessage({ id: 'component.globalModal.supplierIdentityType' })}>
{intl.formatMessage({ id: 'component.globalModal.domesticEnterprise' })}
</Descriptions.Item>
)}
<Descriptions.Item label={intl.formatMessage({ id: 'component.globalModal.enterpriseName' })}>
{registerInfo.base.name}
</Descriptions.Item>
<Descriptions.Item label={intl.formatMessage({ id: 'component.globalModal.enterpriseEnglishName' })}>
{registerInfo.base.nameEn}
</Descriptions.Item>
{registerInfo.base.supplierType !== 'dvs' && (
<>
<Descriptions.Item label={intl.formatMessage({ id: 'component.globalModal.foreignCountryRegion' })}>
{registerInfo.base.nation}
</Descriptions.Item>
<Descriptions.Item label={intl.formatMessage({ id: 'component.globalModal.foreignVAT' })}>
{registerInfo.base.vat}
</Descriptions.Item>
<Descriptions.Item label={intl.formatMessage({ id: 'component.globalModal.foreignTaxpayerId' })}>
{registerInfo.base.taxpayerId}
</Descriptions.Item>
<Descriptions.Item label={intl.formatMessage({ id: 'component.globalModal.foreignCurrency' })}>
{registerInfo.base.currency}
</Descriptions.Item>
</>
)}
<Descriptions.Item label={intl.formatMessage({ id: 'component.globalModal.creditCode' })}>
{registerInfo.base.socialCreditCode}
</Descriptions.Item>
<Descriptions.Item label={intl.formatMessage({ id: 'component.globalModal.businessScope' })}>
{registerInfo.base.range}
</Descriptions.Item>
<Descriptions.Item label={intl.formatMessage({ id: 'component.globalModal.registerAddress' })}>
{registerInfo.base.regAddress}
</Descriptions.Item>
<Descriptions.Item label={intl.formatMessage({ id: 'component.globalModal.officeAddress' })}>
{registerInfo.base.workAddress}
</Descriptions.Item>
<Descriptions.Item label={intl.formatMessage({ id: 'component.globalModal.parentCompanyInfo' })}>
{registerInfo.base.parentCompanyInvestor}
</Descriptions.Item>
<Descriptions.Item label={intl.formatMessage({ id: 'component.globalModal.legalPerson' })}>
{registerInfo.base.legalPerson}
</Descriptions.Item>
<Descriptions.Item label={intl.formatMessage({ id: 'component.globalModal.idCardNumber' })}>
{registerInfo.base.idCard}
</Descriptions.Item>
<Descriptions.Item label={intl.formatMessage({ id: 'component.globalModal.registeredCapital' })}>
{registerInfo.base.capital}
</Descriptions.Item>
<Descriptions.Item label={intl.formatMessage({ id: 'component.globalModal.supplierType' })}>
{registerInfo.base.enterpriseType}
</Descriptions.Item>
<Descriptions.Item label={intl.formatMessage({ id: 'component.globalModal.contactName' })}>
{registerInfo.base.contactsName}
</Descriptions.Item>
<Descriptions.Item label={intl.formatMessage({ id: 'component.globalModal.contactMobile' })}>
{registerInfo.base.contactsPhone}
</Descriptions.Item>
<Descriptions.Item label={intl.formatMessage({ id: 'component.globalModal.contactIdType' })}>
{registerInfo.base.contactsType}
</Descriptions.Item>
<Descriptions.Item label={intl.formatMessage({ id: 'component.globalModal.contactEmail' })}>
{registerInfo.base.contactsEmail}
</Descriptions.Item>
<Descriptions.Item label={intl.formatMessage({ id: 'component.globalModal.contactPhone' })}>
{registerInfo.base.telephone}
</Descriptions.Item>
</Descriptions>
</div>
);
};
export default BaseInfoTab;

View File

@ -0,0 +1,117 @@
import React, { useEffect, useState } from 'react';
import { Table } from 'antd';
import type { ColumnsType, TablePaginationConfig } from 'antd/es/table';
import { coscoSupplier } from '../services';
import { useIntl } from 'umi';
// 联系人信息接口
interface Contact {
id: string;
name: string;
department: string;
position: string;
mobile: string;
phone: string;
email: string;
updateTime: string;
}
const ContactsInfoTab: React.FC = () => {
const intl = useIntl();
const [data, setData] = useState<Contact[]>([]);
const [pagination, setPagination] = useState<TablePaginationConfig>({
current: 1,
pageSize: 10,
total: 0,
});
const [loading, setLoading] = useState(false);
const fetchContacts = async (page: number = 1, pageSize: number = 10) => {
setLoading(true);
try {
const res = await coscoSupplier(page);
if (res.code === 200) {
setData(res.contacts || []);
setPagination({
current: page,
pageSize,
total: res.totalContacts || (res.contacts?.length || 0),
});
}
} finally {
setLoading(false);
}
};
useEffect(() => {
fetchContacts();
}, []);
const handleTableChange = (pagination: TablePaginationConfig) => {
fetchContacts(pagination.current!, pagination.pageSize!);
};
const columns: ColumnsType<Contact> = [
{
title: intl.formatMessage({ id: 'page.workbench.contacts.index' }),
dataIndex: 'index',
key: 'index',
width: 60,
align: 'center',
render: (_: any, __: any, index: number) =>
(pagination.current! - 1) * pagination.pageSize! + index + 1,
},
{
title: intl.formatMessage({ id: 'page.workbench.contacts.name' }),
dataIndex: 'name',
key: 'name',
},
{
title: intl.formatMessage({ id: 'page.workbench.contacts.department' }),
dataIndex: 'department',
key: 'department',
},
{
title: intl.formatMessage({ id: 'page.workbench.contacts.position' }),
dataIndex: 'position',
key: 'position',
},
{
title: intl.formatMessage({ id: 'page.workbench.contacts.mobile' }),
dataIndex: 'mobile',
key: 'mobile',
},
{
title: intl.formatMessage({ id: 'page.workbench.contacts.phone' }),
dataIndex: 'phone',
key: 'phone',
},
{
title: intl.formatMessage({ id: 'page.workbench.contacts.email' }),
dataIndex: 'email',
key: 'email',
},
{
title: intl.formatMessage({ id: 'page.workbench.contacts.updateTime' }),
dataIndex: 'updateTime',
key: 'updateTime',
},
];
return (
<div style={{ padding: '0 30px 0 0' }}>
<Table
className="custom-table"
columns={columns}
dataSource={data}
rowKey="id"
loading={loading}
pagination={pagination}
onChange={handleTableChange}
bordered
/>
</div>
);
};
export default ContactsInfoTab;

View File

@ -0,0 +1,83 @@
import React, { useEffect, useState } from 'react';
import { Table } from 'antd';
import type { ColumnsType, TablePaginationConfig } from 'antd/es/table';
import { invoice } from '../services';
import { useIntl } from 'umi';
interface InvoiceInfo {
id: string;
taxpayerType: string;
taxpayerCode: string;
head: string;
address: string;
phone: string;
bank: string;
account: string;
updateTime: string;
certificateUrl: string;
}
const columns: ColumnsType<InvoiceInfo> = [
{ title: 'page.workbench.invoice.index', dataIndex: 'index', width: 80, key: 'index', render: (_: any, __: any, index: number) => index + 1 },
{ title: 'page.workbench.invoice.taxpayerType', dataIndex: 'taxpayerType' },
{ title: 'page.workbench.invoice.taxpayerCode', dataIndex: 'taxpayerCode' },
{ title: 'page.workbench.invoice.head', dataIndex: 'head' },
{ title: 'page.workbench.invoice.address', dataIndex: 'address' },
{ title: 'page.workbench.invoice.phone', dataIndex: 'phone' },
{ title: 'page.workbench.invoice.bank', dataIndex: 'bank' },
{ title: 'page.workbench.invoice.account', dataIndex: 'account' },
{ title: 'page.workbench.invoice.updateTime', dataIndex: 'updateTime' },
{
title: 'page.workbench.invoice.qualificationCertificate',
width:'180px',
dataIndex: 'qualificationCertificate',
render: (val: string) => (val ? <a href={val} target="_blank" rel="noreferrer"></a> : '-'),
},
];
const InvoiceTab: React.FC = () => {
//语言切换
const intl = useIntl();
//列表渲染数据
const [data, setData] = useState<InvoiceInfo[]>([]);
//列表加载
const [loading, setLoading] = useState(false);
//列表分页
const [pagination, setPagination] = useState<TablePaginationConfig>({ current: 1, pageSize: 10, total: 0 });
//列表方法
const getList = async (page = 1, pageSize = 10) => {
setLoading(true);
try {
const { code, data, total } = await invoice({page, pageSize});
if (code === 200) {
setData(data);
setPagination({ current: page, pageSize, total });
}
} finally {
setLoading(false);
}
};
//初始化
useEffect(() => {
getList();
}, []);
return (
<div style={{ padding: '0 30px 0 0' }}>
<Table
className="custom-table"
rowKey="id"
columns={columns.map(column => ({
...column,
title: intl.formatMessage({ id: column.title as string })
}))}
dataSource={data}
pagination={pagination}
loading={loading}
onChange={(pagination) => getList(pagination.current!, pagination.pageSize!)}
/>
</div>
);
};
export default InvoiceTab;

View File

@ -0,0 +1,74 @@
import React, { useEffect, useState } from 'react';
import { Table } from 'antd';
import type { ColumnsType } from 'antd/es/table';
import { coscoSupplier } from '../services';
import { useIntl } from 'umi';
interface AttachmentItem {
id: string;
fileName: string;
fileType: string;
uploadTime: string;
uploader: string;
fileUrl: string;
}
const OtherAttachmentsTab: React.FC = () => {
const intl = useIntl();
const [data, setData] = useState<AttachmentItem[]>([]);
const [loading, setLoading] = useState(false);
useEffect(() => {
setLoading(true);
coscoSupplier(1).then((res: any) => {
setLoading(false);
if (res.code === 200) {
setData(res.otherAttachments || []);
}
});
}, []);
const columns: ColumnsType<AttachmentItem> = [
{
title: intl.formatMessage({ id: 'page.workbench.attachments.index' }),
render: (_: any, __: any, index: number) => index + 1,
width: 60,
},
{
title: intl.formatMessage({ id: 'page.workbench.attachments.fileName' }),
dataIndex: 'fileName',
},
{
title: intl.formatMessage({ id: 'page.workbench.attachments.fileType' }),
dataIndex: 'fileType',
},
{
title: intl.formatMessage({ id: 'page.workbench.attachments.uploadTime' }),
dataIndex: 'uploadTime',
},
{
title: intl.formatMessage({ id: 'page.workbench.attachments.uploader' }),
dataIndex: 'uploader',
},
{
title: intl.formatMessage({ id: 'page.workbench.attachments.action' }),
dataIndex: 'fileUrl',
render: (val: string) => (val ? <a href={val} target="_blank" rel="noreferrer"></a> : '-'),
},
];
return (
<div style={{ padding: '0 30px 0 0' }}>
<Table
className="custom-table"
rowKey="id"
columns={columns}
dataSource={data}
loading={loading}
pagination={{ pageSize: 10 }}
/>
</div>
);
};
export default OtherAttachmentsTab;

View File

@ -0,0 +1,75 @@
import React, { useEffect, useState } from 'react';
import { Table } from 'antd';
import type { ColumnsType, TablePaginationConfig } from 'antd/es/table';
import { qualifications } from '../services';
import { useIntl } from 'umi';
interface Qualification {
id: string;
certificateType: string;
name: string;
code: string;
typeLevel: string;
authority: string;
dateTime: string;
termOfValidity: string;
updateTime: string;
}
// 列表头部信息
const columns: ColumnsType<Qualification> = [
{ title: 'page.workbench.certificateType', dataIndex: 'certificateType' },
{ title: 'page.workbench.certificateName', dataIndex: 'name' },
{ title: 'page.workbench.certificateCode', dataIndex: 'code' },
{ title: 'page.workbench.typeLevel', dataIndex: 'typeLevel' },
{ title: 'page.workbench.authority', dataIndex: 'authority' },
{ title: 'page.workbench.dateTime', dataIndex: 'dateTime' },
{ title: 'page.workbench.termOfValidity', dataIndex: 'termOfValidity' },
{ title: 'page.workbench.updateTime', dataIndex: 'updateTime' },
];
const QualificationTab: React.FC = () => {
//语言切换
const intl = useIntl();
//列表渲染数据
const [data, setData] = useState<Qualification[]>([]);
//列表加载
const [loading, setLoading] = useState(false);
//列表分页
const [pagination, setPagination] = useState<TablePaginationConfig>({ current: 1, pageSize: 10, total: 0 });
//列表方法
const getList = async (page = 1, pageSize = 10) => {
setLoading(true);
try {
const { code, data, total } = await qualifications({page, pageSize});
if (code === 200) {
setData(data);
setPagination({ current: page, pageSize, total });
}
} finally {
setLoading(false);
}
};
//初始化
useEffect(() => {
getList();
}, []);
return (
<div style={{ padding: '0 30px 0 0' }}>
<Table
rowKey="id"
className="custom-table"
columns={columns.map(column => ({
...column,
title: intl.formatMessage({ id: column.title as string })
}))}
dataSource={data}
pagination={pagination}
loading={loading}
onChange={(pagination) => getList(pagination.current!, pagination.pageSize!)}
/>
</div>
);
};
export default QualificationTab;