forked from yoone/WEB
1
0
Fork 0
WEB/src/pages/Stock/Transfer/index.tsx

716 lines
21 KiB
TypeScript

import { productcontrollerSearchproducts } from '@/servers/api/product';
import {
stockcontrollerCanceltransfer,
stockcontrollerCreatetransfer,
stockcontrollerGetallstockpoints,
stockcontrollerGetpurchaseorder,
stockcontrollerGettransfers,
stockcontrollerLosttransfer,
stockcontrollerReceivetransfer,
stockcontrollerUpdatetransfer,
} from '@/servers/api/stock';
import { EditOutlined, PlusOutlined } from '@ant-design/icons';
import {
ActionType,
DrawerForm,
PageContainer,
ProColumns,
ProForm,
ProFormDatePicker,
ProFormDependency,
ProFormDigit,
ProFormList,
ProFormSelect,
ProFormText,
ProFormTextArea,
ProTable,
} from '@ant-design/pro-components';
import { App, Button, Divider, Form, Popconfirm } from 'antd';
import { useRef } from 'react';
const TransferPage: React.FC = () => {
const { message } = App.useApp();
const actionRef = useRef<ActionType>();
const columns: ProColumns[] = [
{
title: '订单编号',
dataIndex: 'orderNumber',
},
{
title: '源仓库',
dataIndex: 'sourceStockPointName',
hideInSearch: true,
},
{
title: '目标仓库',
dataIndex: 'destStockPointName',
hideInSearch: true,
},
{
title: '状态',
dataIndex: 'status',
hideInSearch: true,
render(_, record) {
if (record.isLost) return '已丢失';
if (record.isCancel) return '已取消';
if (record.isArrived) return '已到达';
return '运输中';
},
},
{
title: '数量',
hideInSearch: true,
render(_, record) {
return record?.items?.reduce?.((cur, next) => {
return cur + next.quantity;
}, 0);
},
},
{
title: '备注',
dataIndex: 'note',
hideInSearch: true,
},
{
title: '到货时间',
dataIndex: 'arriveAt',
valueType: 'dateTime',
hideInSearch: true,
},
{
title: '发货时间',
dataIndex: 'sendAt',
valueType: 'dateTime',
hideInSearch: true,
},
{
title: '操作',
dataIndex: 'option',
valueType: 'option',
render: (_, record) => (
<>
{!record.isCancel && !record.isArrived && !record.isLost ? (
<>
<UpdateForm tableRef={actionRef} values={record} />
<Divider type="vertical" />
<Popconfirm
title="入库"
description="确认已到达?"
onConfirm={async () => {
try {
const { success, message: errMsg } =
await stockcontrollerReceivetransfer({
id: record.id as number,
});
if (!success) {
throw new Error(errMsg);
}
actionRef.current?.reload();
} catch (error: any) {
message.error(error.message);
}
}}
>
<Button type="primary"></Button>
</Popconfirm>
<Divider type="vertical" />
<Popconfirm
title="丢失"
description="确认该批货已丢失?"
onConfirm={async () => {
try {
const { success, message: errMsg } =
await stockcontrollerLosttransfer({
id: record.id as number,
});
if (!success) {
throw new Error(errMsg);
}
actionRef.current?.reload();
} catch (error: any) {
message.error(error.message);
}
}}
>
<Button type="primary"></Button>
</Popconfirm>
<Divider type="vertical" />
<Popconfirm
title="取消"
description="确认取消?"
onConfirm={async () => {
try {
const { success, message: errMsg } =
await stockcontrollerCanceltransfer({
id: record.id as number,
});
if (!success) {
throw new Error(errMsg);
}
actionRef.current?.reload();
} catch (error: any) {
message.error(error.message);
}
}}
>
<Button type="primary" danger>
</Button>
</Popconfirm>
</>
) : (
<DetailForm tableRef={actionRef} values={record} />
)}
</>
),
},
];
return (
<PageContainer ghost>
<ProTable
headerTitle="查询表格"
actionRef={actionRef}
rowKey="id"
request={async (params) => {
const { data, success } = await stockcontrollerGettransfers(params);
return {
total: data?.total || 0,
data: data?.items || [],
success,
};
}}
columns={columns}
toolBarRender={() => [<CreateForm tableRef={actionRef} />]}
/>
</PageContainer>
);
};
const CreateForm: React.FC<{
tableRef: React.MutableRefObject<ActionType | undefined>;
}> = ({ tableRef }) => {
const { message } = App.useApp();
const [form] = Form.useForm();
return (
<DrawerForm
title="新建"
trigger={
<Button type="primary">
<PlusOutlined />
</Button>
}
form={form}
autoFocusFirstInput
layout="vertical"
drawerProps={{
destroyOnHidden: true,
}}
onFinish={async ({ orderNumber, ...values }) => {
try {
const { success, message: errMsg } =
await stockcontrollerCreatetransfer(values);
if (!success) {
throw new Error(errMsg);
}
tableRef.current?.reload();
message.success('提交成功');
return true;
} catch (error: any) {
message.error(error.message);
}
}}
>
<ProFormDatePicker
name="sendAt"
label="发货时间"
rules={[{ required: true, message: '请选择发货时间' }]}
/>
<ProFormSelect
request={async () => {
try {
const { data } = await stockcontrollerGetallstockpoints();
return (
data?.map((item) => {
return {
label: item.name,
value: item.id,
};
}) || []
);
} catch (error) {
return [];
}
}}
name="sourceStockPointId"
label="源仓库"
width="lg"
placeholder="请选择仓库"
rules={[{ required: true, message: '请选择源仓库' }]}
/>
<ProFormSelect
request={async () => {
try {
const { data } = await stockcontrollerGetallstockpoints();
return (
data?.map((item) => {
return {
label: item.name,
value: item.id,
};
}) || []
);
} catch (error) {
return [];
}
}}
name="destStockPointId"
label="目标仓库"
width="lg"
placeholder="请选择仓库"
rules={[{ required: true, message: '请选择源目标仓库' }]}
/>
<ProFormTextArea name="note" label="备注" />
<ProFormText
name={'orderNumber'}
addonAfter={
<Button
onClick={async () => {
const orderNumber = await form.getFieldValue('orderNumber');
const { data } = await stockcontrollerGetpurchaseorder({
orderNumber,
});
form.setFieldsValue({
items: data?.map(
(item: { productName: string; sku: string }) => ({
...item,
sku: {
label: item.productName,
value: item.sku,
},
}),
),
});
}}
>
</Button>
}
/>
<ProFormDependency name={['items']}>
{({ items }) => {
return (
'数量:' +
(items?.reduce?.((acc, cur) => acc + cur.quantity, 0) || 0)
);
}}
</ProFormDependency>
<ProFormList
name="items"
label="产品"
rules={[
{
required: true,
message: '至少需要一个商品',
validator: (_, value) =>
value && value.length > 0
? Promise.resolve()
: Promise.reject('至少需要一个商品'),
},
]}
creatorButtonProps={{ children: '新增', size: 'large' }}
wrapperCol={{ span: 24 }}
>
{(fields, idx, { remove }) => (
<div key={idx}>
<ProFormSelect
request={async ({ keyWords }) => {
if (keyWords.length < 2) return [];
try {
const { data } = await productcontrollerSearchproducts({
name: keyWords,
});
return (
data?.map((item) => {
return {
label: `${item.name} - ${item.nameCn}`,
value: item.sku,
};
}) || []
);
} catch (error) {
return [];
}
}}
name="sku"
label={'产品' + (idx + 1)}
width="lg"
placeholder="请选择产品"
tooltip="至少输入3个字符"
fieldProps={{
showSearch: true,
}}
transform={(value) => {
return value?.value || value;
}}
debounceTime={300} // 防抖,减少请求频率
rules={[{ required: true, message: '请选择产品' }]}
onChange={(_, option) => {
form.setFieldValue(
['items', fields.key, 'productName'],
option.title,
);
}}
/>
<ProFormText name={'productName'} label="产品名称" hidden={true} />
<ProFormDigit
name="quantity"
label="数量"
placeholder="请输入数量"
rules={[{ required: true, message: '请输入数量' }]}
fieldProps={{
precision: 0,
}}
/>
</div>
)}
</ProFormList>
</DrawerForm>
);
};
const UpdateForm: React.FC<{
tableRef: React.MutableRefObject<ActionType | undefined>;
values: API.UpdatePurchaseOrderDTO & {
id: number;
};
}> = ({ tableRef, values }) => {
const { message } = App.useApp();
const [form] = Form.useForm();
const initialValues = {
...values,
items: values?.items?.map((item: API.PurchaseOrderItem) => ({
...item,
sku: {
label: item.productName,
value: item.sku,
},
})),
};
return (
<DrawerForm<API.UpdatePurchaseOrderDTO>
title="编辑"
form={form}
initialValues={initialValues}
trigger={
<Button type="primary">
<EditOutlined />
</Button>
}
autoFocusFirstInput
drawerProps={{
destroyOnHidden: true,
}}
onFinish={async (values) => {
try {
const { success, message: errMsg } =
await stockcontrollerUpdatetransfer(
{ id: initialValues.id },
values,
);
if (!success) {
throw new Error(errMsg);
}
message.success('提交成功');
tableRef.current?.reload();
return true;
} catch (error: any) {
message.error(error.message);
}
}}
>
<ProFormSelect
readonly
request={async () => {
try {
const { data } = await stockcontrollerGetallstockpoints();
return (
data?.map((item) => {
return {
label: item.name,
value: item.id,
};
}) || []
);
} catch (error) {
return [];
}
}}
name="sourceStockPointId"
label="源仓库"
width="lg"
placeholder="请选择仓库"
rules={[{ required: true, message: '请选择源仓库' }]}
/>
<ProFormSelect
request={async () => {
try {
const { data } = await stockcontrollerGetallstockpoints();
return (
data?.map((item) => {
return {
label: item.name,
value: item.id,
};
}) || []
);
} catch (error) {
return [];
}
}}
name="destStockPointId"
label="目标仓库"
width="lg"
placeholder="请选择仓库"
rules={[{ required: true, message: '请选择源目标仓库' }]}
/>
<ProFormTextArea name="note" label="备注" />
<ProFormDependency name={['items']}>
{({ items }) => {
return '数量:' + items?.reduce?.((acc, cur) => acc + cur.quantity, 0);
}}
</ProFormDependency>
<ProFormList
name="items"
label="产品"
rules={[
{
required: true,
message: '至少需要一个商品',
validator: (_, value) =>
value && value.length > 0
? Promise.resolve()
: Promise.reject('至少需要一个商品'),
},
]}
creatorButtonProps={{ children: '新增', size: 'large' }}
wrapperCol={{ span: 24 }}
>
{(fields, idx, { remove }) => (
<div key={idx}>
<ProFormSelect
request={async ({ keyWords }) => {
if (keyWords.length < 2) return [];
try {
const { data } = await productcontrollerSearchproducts({
name: keyWords,
});
return (
data?.map((item) => {
return {
label: `${item.name} - ${item.nameCn}`,
value: item.sku,
};
}) || []
);
} catch (error) {
return [];
}
}}
name="sku"
label={'产品' + (idx + 1)}
width="lg"
placeholder="请选择产品"
tooltip="至少输入3个字符"
fieldProps={{
showSearch: true,
}}
transform={(value) => {
return value?.value || value;
}}
debounceTime={300} // 防抖,减少请求频率
rules={[{ required: true, message: '请选择产品' }]}
onChange={(_, option) => {
form.setFieldValue(
['items', fields.key, 'productName'],
option.title,
);
}}
/>
<ProFormText name={'productName'} label="产品名称" hidden={true} />
<ProFormDigit
name="quantity"
label="数量"
placeholder="请输入数量"
rules={[{ required: true, message: '请输入数量' }]}
fieldProps={{
precision: 0,
}}
/>
</div>
)}
</ProFormList>
</DrawerForm>
);
};
const DetailForm: React.FC<{
tableRef: React.MutableRefObject<ActionType | undefined>;
values: Record<string, any>;
}> = ({ tableRef, values }) => {
const { message } = App.useApp();
const [form] = Form.useForm();
const initialValues = {
...values,
items: values?.items?.map((item: { productName: string; sku: string }) => ({
...item,
sku: {
label: item.productName,
value: item.sku,
},
})),
};
return (
<DrawerForm
title="详情"
form={form}
initialValues={initialValues}
trigger={<Button type="primary"></Button>}
autoFocusFirstInput
drawerProps={{
destroyOnHidden: true,
}}
readonly={true}
layout="vertical"
>
<ProFormText
name="orderNumber"
label="订单编号"
placeholder="请输入订单编号"
width={'lg'}
rules={[{ required: true, message: '请输入订单编号' }]}
/>
<ProFormSelect
request={async () => {
try {
const { data } = await stockcontrollerGetallstockpoints();
return (
data?.map((item) => {
return {
label: item.name,
value: item.id,
};
}) || []
);
} catch (error) {
return [];
}
}}
name="sourceStockPointId"
label="源仓库"
width="lg"
placeholder="请选择仓库"
rules={[{ required: true, message: '请选择源仓库' }]}
/>
<ProFormSelect
request={async () => {
try {
const { data } = await stockcontrollerGetallstockpoints();
return (
data?.map((item) => {
return {
label: item.name,
value: item.id,
};
}) || []
);
} catch (error) {
return [];
}
}}
name="destStockPointId"
label="目标仓库"
width="lg"
placeholder="请选择仓库"
rules={[{ required: true, message: '请选择源目标仓库' }]}
/>
<ProFormTextArea name="note" label="备注" />
<ProFormList<API.PurchaseOrderItem>
name="items"
rules={[
{
required: true,
message: '至少需要一个商品',
validator: (_, value) =>
value && value.length > 0
? Promise.resolve()
: Promise.reject('至少需要一个商品'),
},
]}
creatorButtonProps={{ children: '新增', size: 'large' }}
wrapperCol={{ span: 24 }}
>
{(fields, idx, { remove }) => (
<div key={idx}>
<ProForm.Group>
<ProFormSelect
request={async ({ keyWords }) => {
if (keyWords.length < 2) return [];
try {
const { data } = await productcontrollerSearchproducts({
name: keyWords,
});
return (
data?.map((item) => {
return {
label: `${item.name} - ${item.nameCn}`,
value: item.sku,
};
}) || []
);
} catch (error) {
return [];
}
}}
name="sku"
label="产品"
width="lg"
placeholder="请选择产品"
tooltip="至少输入3个字符"
fieldProps={{
showSearch: true,
}}
transform={(value) => {
return value?.value || value;
}}
debounceTime={300} // 防抖,减少请求频率
rules={[{ required: true, message: '请选择产品' }]}
onChange={(_, option) => {
form.setFieldValue(
['items', fields.key, 'productName'],
option?.title,
);
}}
/>
<ProFormText name="productName" label="产品名称" hidden={true} />
<ProFormDigit
name="quantity"
label="数量"
placeholder="请输入数量"
rules={[{ required: true, message: '请输入数量' }]}
fieldProps={{
precision: 0,
}}
/>
</ProForm.Group>
</div>
)}
</ProFormList>
</DrawerForm>
);
};
export default TransferPage;