Sfoglia il codice sorgente

Merge branch 'master' into kitchenmanage

tmp
zhaoy 9 mesi fa
parent
commit
e07665510e
9 ha cambiato i file con 4 aggiunte e 946 eliminazioni
  1. +0
    -7
      config/routes.js
  2. +2
    -2
      src/pages/device/deviceInfo/components/CreateForm.jsx
  3. +0
    -216
      src/pages/device/deviceInfo/components/DeviceFood.jsx
  4. +0
    -195
      src/pages/device/deviceInfo/components/StockMaterial.jsx
  5. +0
    -151
      src/pages/device/deviceInfo/components/StockMaterialForm.jsx
  6. +2
    -24
      src/pages/device/deviceInfo/index.jsx
  7. +0
    -67
      src/pages/device/devicepush/components/PushFrom.jsx
  8. +0
    -254
      src/pages/device/devicepush/index.jsx
  9. +0
    -30
      src/pages/device/devicepush/services.js

+ 0
- 7
config/routes.js Vedi File

@@ -190,13 +190,6 @@ export default [
component: './device/productmanage',
access: 'k14',
},
{
name: '设备数据下发',
icon: 'smile',
path: '/device/devicepush',
component: './device/devicepush',
access: 'k14',
},
// {
// name: '设备工艺信息',
// icon: 'smile',


+ 2
- 2
src/pages/device/deviceInfo/components/CreateForm.jsx Vedi File

@@ -117,12 +117,12 @@ const CreateForm = (props) => {
)}
/>
</Form.Item>
<Form.Item label={'支持功能'} name="technologyOrBom" rules={[{ required: true }]}>
{/* <Form.Item label={'支持功能'} name="technologyOrBom" rules={[{ required: true }]}>
<Radio.Group onChange={onChange} value={value}>
<Radio value={0}>工艺</Radio>
<Radio value={1}>配方</Radio>
</Radio.Group>
</Form.Item>
</Form.Item> */}
<Form.Item>
<Button type="primary" htmlType="submit">
保存


+ 0
- 216
src/pages/device/deviceInfo/components/DeviceFood.jsx Vedi File

@@ -1,216 +0,0 @@
import { Modal, message, Space, Popconfirm,Button } from 'antd';
import React, { useState, useRef, useEffect } from 'react';
import ProTable from '@ant-design/pro-table';
import { AddDeviceGood, GetByDeviceGoods, getFoodMenuList,PushDeviceGoods } from '../services';

const DeviceFood = (props) => {
const actionRef = useRef();
/**
* 当前选中的商品
*/
const [selectedRowKeys, setSelectedRowKeys] = useState([]);
const [isFirst, setIsFirst] = useState(true);
// 菜谱列表
const [foodMenuList, setFoodMenuList] = useState([]);
const [foodMenuId, setFoodMenuId] = useState('');

const columns = [
{
title: '菜谱列表',
dataIndex: 'foodMenuId',
valueType: 'treeSelect',
hideInTable: true,
fieldProps: {
options: foodMenuList,
value: foodMenuId,
onChange: (value) => {
setFoodMenuId(value);
}
}
},
{
title: '商品id',
dataIndex: 'goodsId',
tip: '规则名称是唯一的 key',
hideInSearch: true,
hideInTable: true,
},
{
title: '商品名称',
dataIndex: 'goodsName',
},
];

/**
* 为设备添加商品
*/
const handleOk = async () => {
if (!props.device?.id) return;
const foodss = [];
selectedRowKeys.forEach(item => {
foodss.push({
foodId: item
});
});
const response = await AddDeviceGood({
foodss,
deviceId: props.device.id
});
if (response.data) {
message.success("设备商品更新成功!");
props.onOk();
} else {
message.error(JSON.stringify(response.errors) || "上架失败");
}
}

/**
* 获取菜谱列表
*/
const onFetchFoodMenu = async () => {
const response = await getFoodMenuList();
if (response.statusCode === 200 && response.data.length > 0) {
setFoodMenuId(response.data[0].value);
setFoodMenuList(response.data);
}
}

useEffect(() => {
onFetchFoodMenu();
}, []);

useEffect(() => {
if (actionRef.current) {
actionRef.current.reload();
}
}, [foodMenuId]);

return (
<Modal
width={900}
bodyStyle={{ padding: '32px 40px 48px' }}
destroyOnClose
title={`【${props.device.deviceName}】绑定商品`}
visible={props.open}
onCancel={() => props.onCancel()}
onOk={handleOk}
maskClosable={false}
>
<ProTable
actionRef={actionRef}
rowKey="goodsId"
pagination={{ defaultPageSize: 10 }}
params={{
deviceId: props.device.id,
}}
toolBarRender={() => [
<Popconfirm
type="primary"
key="primary-async"
title="确认同步吗?"
okText="是"
cancelText="否"
onConfirm={async () => {
console.log(props.device.id)
const response = await PushDeviceGoods(props.device.id);
if (response.data) {
message.success('同步成功!');
actionRef.current.reload();
} else {
message.error(response.errors || '同步失败!');
}
}}
>
<Button
type="primary"
key="primary"
>
同步商品到设备
</Button>
</Popconfirm>,
]}
//数据绑定
request={async (params) => {
if (!foodMenuId) return [];
const response = await GetByDeviceGoods({
...params,
foolMenuId: foodMenuId,
storeId: props.device.orgId,
foodName: params.goodsName || ""
});
if (response.statusCode === 200) {
if (response.data.total>0) {
const set = new Set([...selectedRowKeys, ...response.data.data.checkedIds]);
const setArray = [];
set.forEach(item => {
setArray.push(item);
});
setSelectedRowKeys(setArray);
}else{
setSelectedRowKeys([])
}
return {
data: response.data?.data?.data || [],
success: true,
total: response.data.total,
};
} else {
return []
}
}}
columns={columns}
rowSelection={{
type: 'checkbox',
selectedRowKeys,
onSelect: (record, selected) => {
const tempArray = [...selectedRowKeys];
const findIndex = tempArray.findIndex(item => item === record.goodsId);
if (selected) {
findIndex < 0 && tempArray.push(record.goodsId);
} else {
findIndex > -1 && tempArray.splice(findIndex, 1);
}
setSelectedRowKeys(tempArray);
},
onSelectAll: (selected, selectedRows, changeRows) => {
const tempArray = [...selectedRowKeys];
if (selected) {
selectedRows.forEach(item => {
if (!item) return;
const findIndex = tempArray.findIndex(fItem => fItem === item.goodsId);
if (findIndex < 0) {
tempArray.push(item.goodsId);
}
});
} else {
changeRows.forEach(item => {
const findIndex = tempArray.findIndex(fItem => fItem === item.goodsId);
if (findIndex > -1) {
tempArray.splice(findIndex, 1);
}
});
}
setSelectedRowKeys(tempArray);
}
}}
tableAlertOptionRender={() => {
return (
<Space size={16}>
<Popconfirm
title="此操作会取消所有选中项,确定要取消吗?"
onConfirm={() => setSelectedRowKeys([])}
okText="确定"
cancelText="取消"
>
<a>取消选择</a>
</Popconfirm>
</Space>
);
}}
/>
</Modal>
);
};

export default DeviceFood;

+ 0
- 195
src/pages/device/deviceInfo/components/StockMaterial.jsx Vedi File

@@ -1,195 +0,0 @@
import { Modal, message, Popconfirm, Button } from 'antd';
import React, { useEffect, useState, useRef } from 'react';
import ProTable from '@ant-design/pro-table';
import { GetDeviceStorePage, removeSingleStockAdjust, PushStockAsync, CheckStockAdjust } from '../services';
import StockMaterialForm from "./StockMaterialForm";
import { PlusOutlined } from '@ant-design/icons';

const StockMaterial = (props) => {
const actionRef = useRef();

// 是否展示库存弹窗
const [showStockForm, setShowStockForm] = useState(false);
// 当前操作的库存
const [currStock, setCurrStock] = useState();

const columns = [
{
title: '主键',
dataIndex: 'id',
hideInSearch: true,
hideInTable: true,
tip: '规则名称是唯一的 key',
},
{
title: '物料',
dataIndex: 'batching_Name',
valueType: 'textarea',
},
{
title: '数量',
dataIndex: 'batching_Count',
valueType: 'textarea',
},
{
title: '库位',
dataIndex: 'batching_Loc',
},
{
title: '操作',
dataIndex: 'option',
valueType: 'option',
render: (_, record) => [
<a
key="config"
onClick={() => {
setCurrStock(record);
setShowStockForm(true);
}}
>
修改
</a>,
<Popconfirm
type="primary"
key="primary"
title="确认删除吗?"
okText="是"
cancelText="否"
onConfirm={() => handleDelete(record)}
>
<a href="#">删除</a>
</Popconfirm>,
],
},
];

const handleOk = () => {
props.onOk();
}

/**
* 删除库存原料
* @param {*} record
*/
const handleDelete = async (record) => {
const response = await removeSingleStockAdjust(record.id);
if (response.data) {
message.success('删除成功');
actionRef.current.reload();
} else {
message.error('删除失败,请重试');
}
}

useEffect(() => {

}, []);

return (
<Modal
width={700}
destroyOnClose
title={`【${props.device.deviceName}】库存原料`}
visible={props.open}
onCancel={() => props.onCancel()}
onOk={handleOk}
maskClosable={false}
>
<ProTable
actionRef={actionRef}
rowKey="id"
search={false}
params={{
deviceId: props.device.id,
}}
toolBarRender={() => [
<Popconfirm
type="primary"
key="primary-async-time"
title="获取实时库存会覆盖本次补货数据"
okText="是"
cancelText="否"
onConfirm={async () => {
const response = await CheckStockAdjust(props.device.id);
if (response.data) {
message.success('获取实时库存会成功!');
actionRef.current.reload();
} else {
message.error(response.errors || '获取实时库存会失败!');
}
}}
>
<Button
type="primary"
key="primary"
>
获取实时库存
</Button>
</Popconfirm>,
<Popconfirm
type="primary"
key="primary-async"
title="确认同步吗?"
okText="是"
cancelText="否"
onConfirm={async () => {
const response = await PushStockAsync(props.device.id);
if (response.data) {
message.success('同步成功!');
actionRef.current.reload();
} else {
message.error(response.errors || '同步失败!');
}
}}
>
<Button
type="primary"
key="primary"
>
同步库存
</Button>
</Popconfirm>,
<Button
type="primary"
key="primary"
onClick={() => {
setCurrStock(undefined);
setShowStockForm(true);
}}
>
<PlusOutlined /> 新增库存原料
</Button>
]}
request={async (params) => {
const response = await GetDeviceStorePage(params);
if (response.statusCode === 200) {
return {
data: response.data.data,
success: true,
total: response.data.total,
};
}
return [];
}}
columns={columns}
/>

{
showStockForm && <StockMaterialForm
device={props.device}
stockMaterial={currStock}
open={showStockForm}
onOk={() => {
setShowStockForm(false);
actionRef.current.reload();
}}
onCancel={() => setShowStockForm(false)}
>

</StockMaterialForm>
}
</Modal>
);
};

export default StockMaterial;

+ 0
- 151
src/pages/device/deviceInfo/components/StockMaterialForm.jsx Vedi File

@@ -1,151 +0,0 @@
import { Modal, message, Form, Input, Select, InputNumber, Button, Popconfirm } from 'antd';
import React, { useEffect, useState } from 'react';
import { AddStoreBatchingStocAsync, UpdateStoreBatchingStocAsync, getloc, GetBatchingAsync } from '../services';
const key = 'message';

/**
* 更新
* @param {*} props
* @returns
*/
const StockMaterialForm = (props) => {

const [form] = Form.useForm();
// 位置信息
const [loc, setloc] = useState([]);
const [batchingList, setBatchingList] = useState([]);

const handleOk = async () => {
const formData = await form.validateFields();
formData.DeviceId = props.device.id;
if (formData.id) {
await UpdateStoreBatchingStocAsync(formData).then((r) => {
message.destroy(key);
if (r.data) {
message.success('修改成功');
props.onOk();
} else {
message.error('修改失败' + r.errors);
}
});
} else {
await AddStoreBatchingStocAsync(formData).then((r) => {
message.destroy(key);
if (r.data) {
message.success('添加成功');
props.onOk();
} else {
message.error('添加失败' + r.errors);
}
});
}
}

/**
* 获取设备位置信息
*/
const onFetchLoc = async () => {
getloc(props.device.deviceTypeKey).then((data) => {
setloc(data.data);
});
}

/**
* 获取原料列表
*/
const getBatchingAsync = async () => {
GetBatchingAsync({ DeviceId: props.device.id }).then((data) => {
setBatchingList(data.data);
});
}

useEffect(() => {
if (props.stockMaterial?.id) {
form.setFieldsValue(props.stockMaterial);
}
onFetchLoc();
getBatchingAsync();
}, []);


return (
<Modal
width={700}
destroyOnClose
title={`${props.stockMaterial?.id ? '编辑' + props.stockMaterial.batching_Name : '新增'}`}
visible={props.open}
onCancel={props.onCancel}
onOk={handleOk}
footer={[
<Button key="back" onClick={props.onCancel}>
取消
</Button>,
<Popconfirm
title="点击同步库存或重启设备后生效!!!"
onConfirm={handleOk}
okText="确定"
cancelText="取消"
>
<Button key="submit" type="primary">
确定
</Button>
</Popconfirm>
]}
>
<Form
layout="vertical"
preserve={false}
form={form}
>
<Form.Item name="id" hidden={true}>
<Input />
</Form.Item>
<Form.Item
name="batching_Id"
label="原料名称"
rules={[{ required: true, message: '请选择原料名称' }]}
>
<Select placeholder="请选择原料名称" showSearch
optionFilterProp="children"
filterOption={(input, option) =>
option.children.toLowerCase().indexOf(input.toLowerCase()) >= 0
}>
{batchingList?.map((item, index) => {
return (
<Select.Option index={index} value={item.id} key={item.id}>
{item.name}
</Select.Option>
);
})}
</Select>
</Form.Item>
<Form.Item
name="batching_Loc"
label="库存位置"
rules={[{ required: true }]}
defaultValue="0"
>
<Select placeholder="请选择库存位置" >
{loc?.map((item, index) => {
return (
<Select.Option index={index} value={item.loc} key={item.loc}>
{item.loc}
</Select.Option>
);
})}
</Select>
</Form.Item>
<Form.Item
name="batching_Count"
label="原料数量"
rules={[{ required: true }]}
defaultValue="0"
>
<InputNumber style={{ width: '100%' }} min={0} placeholder="请输入原料数量" />
</Form.Item>
</Form>
</Modal>
);
};

export default StockMaterialForm;

+ 2
- 24
src/pages/device/deviceInfo/index.jsx Vedi File

@@ -17,8 +17,7 @@ import {
GoodsTemplateExport,
} from './services';
import { gettree } from '../../org/orgamange/service';
import DeviceFood from './components/DeviceFood';
import StockMaterial from './components/StockMaterial';

import { values } from 'lodash';
const key = 'message';

@@ -31,12 +30,7 @@ const GoodsTypeManage = () => {
const [OrgListArray, setOrgListArray] = useState([]);
const [dicDataAny, setDicDataAny] = useState([]);
const [dicData, setDicData] = useState([]);
const [DeviceVesionData, setDeviceVesionData] = useState([]);
const [deviceVersion, setDeviceVersion] = useState([]);
// 是否显示 设备商品弹窗
const [deviceFoodModal, setDeviceFoodModal] = useState();
// 是否显示 库存物料弹窗
const [stockModal, setStockModal] = useState(false);
/** 新建/更新窗口的弹窗 */
const [createModalVisible, handleModalVisible] = useState(false);
/** 分布更新窗口的弹窗 */
@@ -431,23 +425,7 @@ const handleRemove = async (selectedRows) => {
deviceVersions={deviceVersion}
values={currentRow || {}}
/>
{deviceFoodModal && (
<DeviceFood
open={deviceFoodModal}
device={currentRow}
onOk={() => setDeviceFoodModal(false)}
onCancel={() => setDeviceFoodModal(false)}
></DeviceFood>
)}

{stockModal && (
<StockMaterial
open={stockModal}
device={currentRow}
onOk={() => setStockModal(false)}
onCancel={() => setStockModal(false)}
></StockMaterial>
)}
</PageContainer>
);
};


+ 0
- 67
src/pages/device/devicepush/components/PushFrom.jsx Vedi File

@@ -1,67 +0,0 @@
import React, { useState, useEffect,useRef } from 'react';
import { Modal, Row, Col, Checkbox, Select} from 'antd';
import {
GetDeviceList,
} from '../services';
const PushFrom = (props) => {
const [deviceData, setdeviceData] = useState([]);
useEffect(() => {
console.log(props.values)
GetDeviceList().then((r)=>{
var data=r.data.map(x=>{
return {value:x.id,label:x.name}
})
setdeviceData(data)
})
},[props.values])
const handleChange=()=>{

}
const onChangedata=()=>{

}
return (
<Modal
title={'下发数据'}
width={640}
visible={props.createModalVisible}
bodyStyle={{ padding: '32px 40px 1px 48px' }}
okText="保存"
cancelText="取消"
onOk={() => {
}}
onCancel={() => {
props.onCancel();
}}
destroyOnClose
>
<Row gutter={26}>
<Col lg={24} md={24} sm={24}>
选择设备:
<Select
mode="multiple"
allowClear
style={{width: '60%'}}
placeholder="请选择要下发设备"
onChange={handleChange}
options={deviceData}
/>
</Col>
</Row>
<Row gutter={26}>
<Col span={24}>
选择数据:
<Checkbox.Group defaultValue={['1','2']} onChange={onChangedata} >
<Checkbox value="1">商品</Checkbox><a style={{marginLeft:2,marginRight:30}}>【选择商品】</a>
<Checkbox value="2">物料 </Checkbox><a style={{marginLeft:2,marginRight:30}}>【选择物料】</a>
<Checkbox value="3">工艺</Checkbox><a style={{marginLeft:2,marginRight:30}}>【选择工艺】</a>
<Checkbox value="4">配方</Checkbox><a style={{marginLeft:2,marginRight:30}}>【选择配方】</a>
</Checkbox.Group>
</Col>
</Row>
</Modal>
);
};

export default PushFrom;

+ 0
- 254
src/pages/device/devicepush/index.jsx Vedi File

@@ -1,254 +0,0 @@
import { PlusOutlined } from '@ant-design/icons';
import { Button, message, Input, Drawer, Popconfirm } from 'antd';
import React, { useState, useRef, useEffect } from 'react';
import { PageContainer, FooterToolbar } from '@ant-design/pro-layout';
import ProTable from '@ant-design/pro-table';
import ProDescriptions from '@ant-design/pro-descriptions';
import PushFrom from './components/PushFrom';

import {
GetDevicePushRecodePage,
DevicePushRecodeDelete
} from './services';



const DevicePush = () => {
/** 新建/更新窗口的弹窗 */
const [createModalVisible, handleModalVisible] = useState(false);
/** 分布更新窗口的弹窗 */
const [showDetail, setShowDetail] = useState(false);
const actionRef = useRef();
const [currentRow, setCurrentRow] = useState();
const [selectedRowsState, setSelectedRows] = useState([]);
/** 国际化修改 */
useEffect(() => {
}, []);

/**
* 批量删除
*
* @param selectedRows
*/
const handleRemove = async (selectedRows) => {
const hide = message.loading('正在删除');
if (!selectedRows) return true;
await DevicePushRecodeDelete(selectedRows.map((row) => row.id)).then((r) => {
if (r.succeeded) {
message.success('删除成功');
actionRef.current.reload();
} else {
message.error(r.errors);
}
});
hide();
return true;
};
const columns = [
{
title: '主键',
dataIndex: 'id',
hideInSearch: true,
hideInTable: true,
tip: '规则名称是唯一的 key',
render: (dom, entity) => {
return (
<a
onClick={() => {
setCurrentRow(entity);
setShowDetail(true);
}}
>
{dom}
</a>
);
},
},
{
title: '下发设备',
dataIndex: 'deviceName',
valueType: 'textarea',
ellipsis: true,
},

{
title: '下发数据',
dataIndex: 'type',
ellipsis: true,
valueEnum: {
1: {
text: '商品',
},
2: {
text: '物料',
},
3: {
text: '工艺',
},
4: {
text: '配方',
},
},
},
{
title: '下发时间',
dataIndex: 'ceateAt',
hideInSearch: true,
},
{
title: '操作',
dataIndex: 'option',
valueType: 'option',
render: (_, record) => [
<a
key="config"
onClick={() => {
handleModalVisible(true);
setCurrentRow(record);
}}
>
下发详情
</a>,
<Popconfirm
type="primary"
key="primary"
title="确认删除吗?"
okText="是"
cancelText="否"
onConfirm={async () => {
await DeleteGoodsType(record.id).then((r) => {
if (r.succeeded) {
message.success('删除成功');
actionRef.current.reload();
} else {
message.error(r.errors);
}
});
}}
onCancel={() => {}}
>
<a href="#">删除</a>
</Popconfirm>,
],
},
];

return (
<PageContainer host header={{
title: '',
breadcrumb: {},
}}>
<ProTable
headerTitle=""
actionRef={actionRef}
rowKey="id"
pagination={{ defaultPageSize: 10 }}
search={{
labelWidth: 120,
}}
toolBarRender={() => [
<Button
type="primary"
key="primary"
onClick={() => {
handleModalVisible(true);
}}
>
<PlusOutlined /> 下发数据
</Button>,
]}
request={async (params) => {
var goodsData = [];
var total = 0;
await GetDevicePushRecodePage(params).then((r) => {
goodsData = r.data.data;
total = r.data.total;
});
return {
data: goodsData,
success: true,
total: total,
};
}}
columns={columns}
rowSelection={{
onChange: (_, selectedRows) => {
setSelectedRows(selectedRows);
},
}}
/>
{selectedRowsState?.length > 0 && (
<FooterToolbar
extra={
<div>
已选择{' '}
<a
style={{
fontWeight: 600,
}}
>
{selectedRowsState.length}
</a>{' '}
项 &nbsp;&nbsp;
{/* <span>
服务调用次数总计 {selectedRowsState.reduce((pre, item) => pre + item.id, 0)} 万
</span> */}
</div>
}
>
<Button
onClick={async () => {
await handleRemove(selectedRowsState);
setSelectedRows([]);
actionRef.current?.reloadAndRest?.();
}}
>
删除
</Button>
{/* <Button type="primary">批量审批</Button> */}
</FooterToolbar>
)}

<PushFrom
onFinish={async (value) => {
}}
onCancel={() => {
handleModalVisible(false);
setCurrentRow(undefined);
}}
createModalVisible={createModalVisible}
values={currentRow || {}}
/>

<Drawer
width={600}
visible={showDetail}
onClose={() => {
setCurrentRow(undefined);
setShowDetail(false);
}}
closable={false}
>
{currentRow?.name && (
<ProDescriptions
column={2}
title={currentRow?.name}
request={async () => ({
data: currentRow || {},
})}
params={{
id: currentRow?.name,
}}
columns={columns}
/>
)}
</Drawer>
</PageContainer>
);
};

export default DevicePush;

+ 0
- 30
src/pages/device/devicepush/services.js Vedi File

@@ -1,30 +0,0 @@
import { request } from 'umi';
export async function GetDevicePushRecodePage(data) {
return request(`/saasstore/api/devicepushrecode/page`, {
method: 'POST',
data: data,
});
}
export async function DevicePushRecodeAdd(data) {
return request(`/saasstore/api/devicepushrecode/add`, {
method: 'POST',
data: data,
});
}
export async function DevicePushRecodeUpdate(data) {
return request(`/saasstore/api/devicepushrecode/update`, {
method: 'POST',
data: data,
});
}
export async function DevicePushRecodeDelete(data) {
return request(`/saasstore/api/devicepushrecode/delete`, {
method: 'POST',
data: data,
});
}
export async function GetDeviceList() {
return request(`/saasbase/api/device/list`, {
method: 'GET',
});
}

Caricamento…
Annulla
Salva