From e711c834aec2293c53b07efe53e81e3573c289b6 Mon Sep 17 00:00:00 2001
From: 1 <1@123>
Date: 星期三, 01 四月 2026 11:42:44 +0800
Subject: [PATCH] lsh#

---
 rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/OutStockServiceImpl.java                  |   53 
 rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/BasStationTypeServiceImpl.java            |   12 
 rsf-server/src/main/java/com/vincent/rsf/server/ai/tool/RsfWmsStockTools.java                                  |   42 
 rsf-server/src/main/java/com/vincent/rsf/server/manager/entity/MatnrRestrictionWarehouse.java                  |  106 ++
 rsf-server/src/main/java/com/vincent/rsf/server/manager/mapper/BasStationTypeMapper.java                       |   12 
 rsf-server/src/main/java/com/vincent/rsf/server/manager/utils/LocManageUtil.java                               |  113 --
 rsf-server/src/main/java/com/vincent/rsf/server/common/CodeBuilder.java                                        |    4 
 rsf-server/src/main/java/com/vincent/rsf/server/manager/entity/BasContainer.java                               |    4 
 rsf-server/src/main/resources/mapper/manager/BasStationTypeMapper.xml                                          |    5 
 rsf-admin/src/page/basStationType/BasStationTypeEdit.jsx                                                       |  145 ++
 rsf-server/src/main/java/com/vincent/rsf/server/manager/controller/MatnrRestrictionWarehouseController.java    |  110 ++
 rsf-admin/src/page/matnrRestrictionWarehouse/MatnrRestrictionWarehouseList.jsx                                 |  156 ++
 rsf-server/src/main/java/com/vincent/rsf/server/manager/schedules/TaskMissionSchedules.java                    |   25 
 rsf-server/src/main/java/com/vincent/rsf/server/manager/controller/params/GenerateTaskParams.java              |    4 
 rsf-server/src/main/java/com/vincent/rsf/server/manager/service/TaskService.java                               |    2 
 rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/LocItemServiceImpl.java                   |  131 +-
 rsf-server/src/main/java/com/vincent/rsf/server/manager/controller/BasStationTypeController.java               |  110 ++
 rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/MatnrRestrictionWarehouseServiceImpl.java |   12 
 rsf-server/src/main/java/com/vincent/rsf/server/system/entity/TaskPathTemplateMerge.java                       |    7 
 rsf-server/src/main/java/com/vincent/rsf/server/manager/entity/BasStationType.java                             |  188 +++
 rsf-admin/src/page/matnrRestrictionWarehouse/MatnrRestrictionWarehouseCreate.jsx                               |  132 ++
 rsf-server/src/main/java/com/vincent/rsf/server/manager/schedules/AutoRunSchedules.java                        |   44 
 rsf-server/src/main/java/com/vincent/rsf/server/manager/entity/Matnr.java                                      |   16 
 rsf-server/src/main/resources/mapper/manager/MatnrRestrictionWarehouseMapper.xml                               |    5 
 rsf-server/src/main/java/com/vincent/rsf/server/api/controller/mcp/McpController.java                          |    3 
 rsf-admin/src/page/basStationType/BasStationTypeList.jsx                                                       |  170 +++
 rsf-server/src/main/java/com/vincent/rsf/server/manager/mapper/MatnrRestrictionWarehouseMapper.java            |   12 
 rsf-server/src/main/java/com/vincent/rsf/server/manager/schedules/TaskSchedules.java                           |   81 -
 rsf-server/src/main/java/com/vincent/rsf/server/manager/service/BasStationTypeService.java                     |    8 
 rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/DeviceSiteServiceImpl.java                |   25 
 rsf-server/src/main/java/com/vincent/rsf/server/api/service/impl/MobileServiceImpl.java                        |   15 
 rsf-server/src/main/java/com/vincent/rsf/server/api/utils/LocUtils.java                                        |   11 
 rsf-server/src/main/java/com/vincent/rsf/server/manager/enums/TaskType.java                                    |    2 
 rsf-admin/src/page/basStationType/index.jsx                                                                    |   18 
 rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/TaskServiceImpl.java                      |   25 
 rsf-server/src/main/java/com/vincent/rsf/server/manager/utils/WarehouseLocationRetrievalUtil.java              |  534 ++++++++++
 rsf-admin/src/page/matnrRestrictionWarehouse/MatnrRestrictionWarehouseEdit.jsx                                 |  104 +
 rsf-server/src/main/java/com/vincent/rsf/server/manager/controller/params/WaitPakinParam.java                  |    2 
 rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/CheckOrderServiceImpl.java                |   47 
 rsf-server/src/main/java/com/vincent/rsf/server/manager/service/MatnrRestrictionWarehouseService.java          |    8 
 rsf-admin/src/page/basStationType/BasStationTypeCreate.jsx                                                     |  173 +++
 rsf-server/src/main/java/com/vincent/rsf/server/api/service/impl/InBoundServiceImpl.java                       |   30 
 rsf-server/src/main/java/basStationType.sql                                                                    |   31 
 rsf-server/src/main/java/com/vincent/rsf/server/api/service/impl/AgvServiceImpl.java                           |   15 
 rsf-server/src/main/java/com/vincent/rsf/server/manager/entity/BasStation.java                                 |    6 
 rsf-server/src/main/java/com/vincent/rsf/server/api/service/WcsService.java                                    |    1 
 rsf-admin/src/page/matnrRestrictionWarehouse/MatnrRestrictionWarehousePanel.jsx                                |   69 +
 rsf-admin/src/page/matnrRestrictionWarehouse/index.jsx                                                         |   18 
 rsf-server/src/main/java/com/vincent/rsf/server/api/service/impl/WcsServiceImpl.java                           |  178 ++-
 rsf-server/src/main/java/matnrRestrictionWarehouse.sql                                                         |   24 
 rsf-admin/src/page/basStationType/BasStationTypePanel.jsx                                                      |  111 ++
 rsf-server/src/main/java/com/vincent/rsf/server/api/controller/erp/params/TaskInParam.java                     |    3 
 52 files changed, 2,689 insertions(+), 473 deletions(-)

diff --git a/rsf-admin/src/page/basStationType/BasStationTypeCreate.jsx b/rsf-admin/src/page/basStationType/BasStationTypeCreate.jsx
new file mode 100644
index 0000000..fed633d
--- /dev/null
+++ b/rsf-admin/src/page/basStationType/BasStationTypeCreate.jsx
@@ -0,0 +1,173 @@
+import React, { useState, useRef, useEffect, useMemo } from "react";
+import {
+    CreateBase,
+    useTranslate,
+    TextInput,
+    NumberInput,
+    BooleanInput,
+    DateInput,
+    SaveButton,
+    SelectInput,
+    ReferenceInput,
+    ReferenceArrayInput,
+    AutocompleteInput,
+    Toolbar,
+    required,
+    useDataProvider,
+    useNotify,
+    Form,
+    useCreateController,
+} from 'react-admin';
+import {
+    Dialog,
+    DialogActions,
+    DialogContent,
+    DialogTitle,
+    Stack,
+    Grid,
+    Box,
+} from '@mui/material';
+import DialogCloseButton from "../components/DialogCloseButton";
+import StatusSelectInput from "../components/StatusSelectInput";
+import MemoInput from "../components/MemoInput";
+
+const BasStationTypeCreate = (props) => {
+    const { open, setOpen } = props;
+
+    const translate = useTranslate();
+    const notify = useNotify();
+
+    const handleClose = (event, reason) => {
+        if (reason !== "backdropClick") {
+            setOpen(false);
+        }
+    };
+
+    const handleSuccess = async (data) => {
+        setOpen(false);
+        notify('common.response.success');
+    };
+
+    const handleError = async (error) => {
+        notify(error.message || 'common.response.fail', { type: 'error', messageArgs: { _: error.message } });
+    };
+
+    return (
+        <>
+            <CreateBase
+                record={{}}
+                transform={(data) => {
+                    return data;
+                }}
+                mutationOptions={{ onSuccess: handleSuccess, onError: handleError }}
+            >
+                <Dialog
+                    open={open}
+                    onClose={handleClose}
+                    aria-labelledby="form-dialog-title"
+                    fullWidth
+                    disableRestoreFocus
+                    maxWidth="md"   // 'xs' | 'sm' | 'md' | 'lg' | 'xl'
+                >
+                    <Form>
+                        <DialogTitle id="form-dialog-title" sx={{
+                            position: 'sticky',
+                            top: 0,
+                            backgroundColor: 'background.paper',
+                            zIndex: 1000
+                        }}
+                        >
+                            {translate('create.title')}
+                            <Box sx={{ position: 'absolute', top: 8, right: 8, zIndex: 1001 }}>
+                                <DialogCloseButton onClose={handleClose} />
+                            </Box>
+                        </DialogTitle>
+                        <DialogContent sx={{ mt: 2 }}>
+                            <Grid container rowSpacing={2} columnSpacing={2}>
+                                <Grid item xs={6} display="flex" gap={1}>
+                                    <TextInput
+                                        label="table.field.basStationType.stationTypeCode"
+                                        source="stationTypeCode"
+                                        parse={v => v}
+                                        autoFocus
+                                    />
+                                </Grid>
+                                <Grid item xs={6} display="flex" gap={1}>
+                                    <TextInput
+                                        label="table.field.basStationType.stationTypeName"
+                                        source="stationTypeName"
+                                        parse={v => v}
+                                    />
+                                </Grid>
+                                <Grid item xs={6} display="flex" gap={1}>
+                                    <NumberInput
+                                        label="table.field.basStationType.allowFullPalletOut"
+                                        source="allowFullPalletOut"
+                                    />
+                                </Grid>
+                                <Grid item xs={6} display="flex" gap={1}>
+                                    <NumberInput
+                                        label="table.field.basStationType.allowEmptyPalletOut"
+                                        source="allowEmptyPalletOut"
+                                    />
+                                </Grid>
+                                <Grid item xs={6} display="flex" gap={1}>
+                                    <NumberInput
+                                        label="table.field.basStationType.allowPick"
+                                        source="allowPick"
+                                    />
+                                </Grid>
+                                <Grid item xs={6} display="flex" gap={1}>
+                                    <NumberInput
+                                        label="table.field.basStationType.allowFullPalletIn"
+                                        source="allowFullPalletIn"
+                                    />
+                                </Grid>
+                                <Grid item xs={6} display="flex" gap={1}>
+                                    <NumberInput
+                                        label="table.field.basStationType.allowEmptyPalletIn"
+                                        source="allowEmptyPalletIn"
+                                    />
+                                </Grid>
+                                <Grid item xs={6} display="flex" gap={1}>
+                                    <NumberInput
+                                        label="table.field.basStationType.conveyorLine"
+                                        source="conveyorLine"
+                                    />
+                                </Grid>
+                                <Grid item xs={6} display="flex" gap={1}>
+                                    <NumberInput
+                                        label="table.field.basStationType.allowGroundStation"
+                                        source="allowGroundStation"
+                                    />
+                                </Grid>
+                                <Grid item xs={6} display="flex" gap={1}>
+                                    <NumberInput
+                                        label="table.field.basStationType.allowGroundBarcodeStation"
+                                        source="allowGroundBarcodeStation"
+                                    />
+                                </Grid>
+
+                                <Grid item xs={6} display="flex" gap={1}>
+                                    <StatusSelectInput />
+                                </Grid>
+                                <Grid item xs={12} display="flex" gap={1}>
+                                    <Stack direction="column" spacing={1} width={'100%'}>
+                                        <MemoInput />
+                                    </Stack>
+                                </Grid>
+                            </Grid>
+                        </DialogContent>
+                        <DialogActions sx={{ position: 'sticky', bottom: 0, backgroundColor: 'background.paper', zIndex: 1000 }}>
+                            <Toolbar sx={{ width: '100%', justifyContent: 'space-between' }}  >
+                                <SaveButton />
+                            </Toolbar>
+                        </DialogActions>
+                    </Form>
+                </Dialog>
+            </CreateBase>
+        </>
+    )
+}
+
+export default BasStationTypeCreate;
diff --git a/rsf-admin/src/page/basStationType/BasStationTypeEdit.jsx b/rsf-admin/src/page/basStationType/BasStationTypeEdit.jsx
new file mode 100644
index 0000000..654ef16
--- /dev/null
+++ b/rsf-admin/src/page/basStationType/BasStationTypeEdit.jsx
@@ -0,0 +1,145 @@
+import React, { useState, useRef, useEffect, useMemo } from "react";
+import {
+    Edit,
+    SimpleForm,
+    FormDataConsumer,
+    useTranslate,
+    TextInput,
+    NumberInput,
+    BooleanInput,
+    DateInput,
+    SelectInput,
+    ReferenceInput,
+    ReferenceArrayInput,
+    AutocompleteInput,
+    SaveButton,
+    Toolbar,
+    Labeled,
+    NumberField,
+    required,
+    useRecordContext,
+    DeleteButton,
+} from 'react-admin';
+import { useWatch, useFormContext } from "react-hook-form";
+import { Stack, Grid, Box, Typography } from '@mui/material';
+import * as Common from '@/utils/common';
+import { EDIT_MODE, REFERENCE_INPUT_PAGESIZE } from '@/config/setting';
+import EditBaseAside from "../components/EditBaseAside";
+import CustomerTopToolBar from "../components/EditTopToolBar";
+import MemoInput from "../components/MemoInput";
+import StatusSelectInput from "../components/StatusSelectInput";
+
+const FormToolbar = () => {
+    const { getValues } = useFormContext();
+
+    return (
+        <Toolbar sx={{ justifyContent: 'space-between' }}>
+            <SaveButton />
+            <DeleteButton mutationMode="optimistic" />
+        </Toolbar>
+    )
+}
+
+const BasStationTypeEdit = () => {
+    const translate = useTranslate();
+
+    return (
+        <Edit
+            redirect="list"
+            mutationMode={EDIT_MODE}
+            actions={<CustomerTopToolBar />}
+            aside={<EditBaseAside />}
+        >
+            <SimpleForm
+                shouldUnregister
+                warnWhenUnsavedChanges
+                toolbar={<FormToolbar />}
+                mode="onTouched"
+                defaultValues={{}}
+            // validate={(values) => { }}
+            >
+                <Grid container width={{ xs: '100%', xl: '80%' }} rowSpacing={3} columnSpacing={3}>
+                    <Grid item xs={12} md={8}>
+                        <Typography variant="h6" gutterBottom>
+                            {translate('common.edit.title.main')}
+                        </Typography>
+                        <Stack direction='row' gap={2}>
+                            <TextInput
+                                label="table.field.basStationType.stationTypeCode"
+                                source="stationTypeCode"
+                                parse={v => v}
+                                autoFocus
+                            />
+                        </Stack>
+                        <Stack direction='row' gap={2}>
+                            <TextInput
+                                label="table.field.basStationType.stationTypeName"
+                                source="stationTypeName"
+                                parse={v => v}
+                            />
+                        </Stack>
+                        <Stack direction='row' gap={2}>
+                            <NumberInput
+                                label="table.field.basStationType.allowFullPalletOut"
+                                source="allowFullPalletOut"
+                            />
+                        </Stack>
+                        <Stack direction='row' gap={2}>
+                            <NumberInput
+                                label="table.field.basStationType.allowEmptyPalletOut"
+                                source="allowEmptyPalletOut"
+                            />
+                        </Stack>
+                        <Stack direction='row' gap={2}>
+                            <NumberInput
+                                label="table.field.basStationType.allowPick"
+                                source="allowPick"
+                            />
+                        </Stack>
+                        <Stack direction='row' gap={2}>
+                            <NumberInput
+                                label="table.field.basStationType.allowFullPalletIn"
+                                source="allowFullPalletIn"
+                            />
+                        </Stack>
+                        <Stack direction='row' gap={2}>
+                            <NumberInput
+                                label="table.field.basStationType.allowEmptyPalletIn"
+                                source="allowEmptyPalletIn"
+                            />
+                        </Stack>
+                        <Stack direction='row' gap={2}>
+                            <NumberInput
+                                label="table.field.basStationType.conveyorLine"
+                                source="conveyorLine"
+                            />
+                        </Stack>
+                        <Stack direction='row' gap={2}>
+                            <NumberInput
+                                label="table.field.basStationType.allowGroundStation"
+                                source="allowGroundStation"
+                            />
+                        </Stack>
+                        <Stack direction='row' gap={2}>
+                            <NumberInput
+                                label="table.field.basStationType.allowGroundBarcodeStation"
+                                source="allowGroundBarcodeStation"
+                            />
+                        </Stack>
+
+                    </Grid>
+                    <Grid item xs={12} md={4}>
+                        <Typography variant="h6" gutterBottom>
+                            {translate('common.edit.title.common')}
+                        </Typography>
+                        <StatusSelectInput />
+                        <Box mt="2em" />
+                        <MemoInput />
+                    </Grid>
+                </Grid>
+            </SimpleForm>
+        </Edit >
+    )
+}
+
+export default BasStationTypeEdit;
diff --git a/rsf-admin/src/page/basStationType/BasStationTypeList.jsx b/rsf-admin/src/page/basStationType/BasStationTypeList.jsx
new file mode 100644
index 0000000..5cf3ab1
--- /dev/null
+++ b/rsf-admin/src/page/basStationType/BasStationTypeList.jsx
@@ -0,0 +1,170 @@
+import React, { useState, useRef, useEffect, useMemo, useCallback } from "react";
+import { useNavigate } from 'react-router-dom';
+import {
+    List,
+    DatagridConfigurable,
+    SearchInput,
+    TopToolbar,
+    SelectColumnsButton,
+    EditButton,
+    FilterButton,
+    CreateButton,
+    ExportButton,
+    BulkDeleteButton,
+    WrapperField,
+    useRecordContext,
+    useTranslate,
+    useNotify,
+    useListContext,
+    FunctionField,
+    TextField,
+    NumberField,
+    DateField,
+    BooleanField,
+    ReferenceField,
+    TextInput,
+    DateTimeInput,
+    DateInput,
+    SelectInput,
+    NumberInput,
+    ReferenceInput,
+    ReferenceArrayInput,
+    AutocompleteInput,
+    DeleteButton,
+} from 'react-admin';
+import { Box, Typography, Card, Stack } from '@mui/material';
+import { styled } from '@mui/material/styles';
+import BasStationTypeCreate from "./BasStationTypeCreate";
+import BasStationTypePanel from "./BasStationTypePanel";
+import EmptyData from "../components/EmptyData";
+import MyCreateButton from "../components/MyCreateButton";
+import MyExportButton from '../components/MyExportButton';
+import PageDrawer from "../components/PageDrawer";
+import MyField from "../components/MyField";
+import { PAGE_DRAWER_WIDTH, OPERATE_MODE, DEFAULT_PAGE_SIZE } from '@/config/setting';
+import * as Common from '@/utils/common';
+
+const StyledDatagrid = styled(DatagridConfigurable)(({ theme }) => ({
+    '& .css-1vooibu-MuiSvgIcon-root': {
+        height: '.9em'
+    },
+    '& .RaDatagrid-row': {
+        cursor: 'auto'
+    },
+    '& .column-name': {
+    },
+    '& .opt': {
+        width: 200
+    },
+}));
+
+const filters = [
+    <SearchInput source="condition" alwaysOn />,
+    <DateInput label='common.time.after' source="timeStart" alwaysOn />,
+    <DateInput label='common.time.before' source="timeEnd" alwaysOn />,
+
+    <TextInput source="stationTypeCode" label="table.field.basStationType.stationTypeCode" />,
+    <TextInput source="stationTypeName" label="table.field.basStationType.stationTypeName" />,
+    <NumberInput source="allowFullPalletOut" label="table.field.basStationType.allowFullPalletOut" />,
+    <NumberInput source="allowEmptyPalletOut" label="table.field.basStationType.allowEmptyPalletOut" />,
+    <NumberInput source="allowPick" label="table.field.basStationType.allowPick" />,
+    <NumberInput source="allowFullPalletIn" label="table.field.basStationType.allowFullPalletIn" />,
+    <NumberInput source="allowEmptyPalletIn" label="table.field.basStationType.allowEmptyPalletIn" />,
+    <NumberInput source="conveyorLine" label="table.field.basStationType.conveyorLine" />,
+    <NumberInput source="allowGroundStation" label="table.field.basStationType.allowGroundStation" />,
+    <NumberInput source="allowGroundBarcodeStation" label="table.field.basStationType.allowGroundBarcodeStation" />,
+
+    <TextInput label="common.field.memo" source="memo" />,
+    <SelectInput
+        label="common.field.status"
+        source="status"
+        choices={[
+            { id: '1', name: 'common.enums.statusTrue' },
+            { id: '0', name: 'common.enums.statusFalse' },
+        ]}
+        resettable
+    />,
+]
+
+const BasStationTypeList = () => {
+    const translate = useTranslate();
+
+    const [createDialog, setCreateDialog] = useState(false);
+    const [drawerVal, setDrawerVal] = useState(false);
+
+    return (
+        <Box display="flex">
+            <List
+                sx={{
+                    flexGrow: 1,
+                    transition: (theme) =>
+                        theme.transitions.create(['all'], {
+                            duration: theme.transitions.duration.enteringScreen,
+                        }),
+                    marginRight: !!drawerVal ? `${PAGE_DRAWER_WIDTH}px` : 0,
+                }}
+                title={"menu.basStationType"}
+                empty={<EmptyData onClick={() => { setCreateDialog(true) }} />}
+                filters={filters}
+                sort={{ field: "create_time", order: "desc" }}
+                actions={(
+                    <TopToolbar>
+                        <FilterButton />
+                        <MyCreateButton onClick={() => { setCreateDialog(true) }} />
+                        <SelectColumnsButton preferenceKey='basStationType' />
+                        <MyExportButton />
+                    </TopToolbar>
+                )}
+                perPage={DEFAULT_PAGE_SIZE}
+            >
+                <StyledDatagrid
+                    preferenceKey='basStationType'
+                    bulkActionButtons={() => <BulkDeleteButton mutationMode={OPERATE_MODE} />}
+                    rowClick={(id, resource, record) => false}
+                    expand={() => <BasStationTypePanel />}
+                    expandSingle={true}
+                    omit={['id', 'createTime', 'createBy', 'memo']}
+                >
+                    <NumberField source="id" />
+                    <TextField source="stationTypeCode" label="table.field.basStationType.stationTypeCode" />
+                    <TextField source="stationTypeName" label="table.field.basStationType.stationTypeName" />
+                    <NumberField source="allowFullPalletOut" label="table.field.basStationType.allowFullPalletOut" />
+                    <NumberField source="allowEmptyPalletOut" label="table.field.basStationType.allowEmptyPalletOut" />
+                    <NumberField source="allowPick" label="table.field.basStationType.allowPick" />
+                    <NumberField source="allowFullPalletIn" label="table.field.basStationType.allowFullPalletIn" />
+                    <NumberField source="allowEmptyPalletIn" label="table.field.basStationType.allowEmptyPalletIn" />
+                    <NumberField source="conveyorLine" label="table.field.basStationType.conveyorLine" />
+                    <NumberField source="allowGroundStation" label="table.field.basStationType.allowGroundStation" />
+                    <NumberField source="allowGroundBarcodeStation" label="table.field.basStationType.allowGroundBarcodeStation" />
+
+                    <ReferenceField source="updateBy" label="common.field.updateBy" reference="user" link={false} sortable={false}>
+                        <TextField source="nickname" />
+                    </ReferenceField>
+                    <DateField source="updateTime" label="common.field.updateTime" showTime />
+                    <ReferenceField source="createBy" label="common.field.createBy" reference="user" link={false} sortable={false}>
+                        <TextField source="nickname" />
+                    </ReferenceField>
+                    <DateField source="createTime" label="common.field.createTime" showTime />
+                    <BooleanField source="statusBool" label="common.field.status" sortable={false} />
+                    <TextField source="memo" label="common.field.memo" sortable={false} />
+                    <WrapperField cellClassName="opt" label="common.field.opt">
+                        <EditButton sx={{ padding: '1px', fontSize: '.75rem' }} />
+                        <DeleteButton sx={{ padding: '1px', fontSize: '.75rem' }} mutationMode={OPERATE_MODE} />
+                    </WrapperField>
+                </StyledDatagrid>
+            </List>
+            <BasStationTypeCreate
+                open={createDialog}
+                setOpen={setCreateDialog}
+            />
+            <PageDrawer
+                title='BasStationType Detail'
+                drawerVal={drawerVal}
+                setDrawerVal={setDrawerVal}
+            >
+            </PageDrawer>
+        </Box>
+    )
+}
+
+export default BasStationTypeList;
diff --git a/rsf-admin/src/page/basStationType/BasStationTypePanel.jsx b/rsf-admin/src/page/basStationType/BasStationTypePanel.jsx
new file mode 100644
index 0000000..5f19024
--- /dev/null
+++ b/rsf-admin/src/page/basStationType/BasStationTypePanel.jsx
@@ -0,0 +1,111 @@
+import React, { useState, useRef, useEffect, useMemo } from "react";
+import { Box, Card, CardContent, Grid, Typography, Tooltip } from '@mui/material';
+import {
+    useTranslate,
+    useRecordContext,
+} from 'react-admin';
+import PanelTypography from "../components/PanelTypography";
+import * as Common from '@/utils/common'
+
+const BasStationTypePanel = () => {
+    const record = useRecordContext();
+    if (!record) return null;
+    const translate = useTranslate();
+    return (
+        <>
+            <Card sx={{ width: { xs: 300, sm: 500, md: 600, lg: 800 }, margin: 'auto' }}>
+                <CardContent>
+                    <Grid container spacing={2}>
+                        <Grid item xs={12} sx={{ display: 'flex', justifyContent: 'space-between' }}>
+                            <Typography variant="h6" gutterBottom align="left" sx={{
+                                maxWidth: { xs: '100px', sm: '180px', md: '260px', lg: '360px' },
+                                whiteSpace: 'nowrap',
+                                overflow: 'hidden',
+                                textOverflow: 'ellipsis',
+                            }}>
+                                {Common.camelToPascalWithSpaces(translate('table.field.basStationType.id'))}: {record.id}
+                            </Typography>
+                            {/*  inherit, primary, secondary, textPrimary, textSecondary, error */}
+                            <Typography variant="h6" gutterBottom align="right" >
+                                ID: {record.id}
+                            </Typography>
+                        </Grid>
+                    </Grid>
+                    <Grid container spacing={2}>
+                        <Grid item xs={12} container alignContent="flex-end">
+                            <Typography variant="caption" color="textSecondary" sx={{ wordWrap: 'break-word', wordBreak: 'break-all' }}>
+                                {Common.camelToPascalWithSpaces(translate('common.field.memo'))}:{record.memo}
+                            </Typography>
+                        </Grid>
+                    </Grid>
+                    <Box height={20}>&nbsp;</Box>
+                    <Grid container spacing={2}>
+                        <Grid item xs={6}>
+                            <PanelTypography
+                                title="table.field.basStationType.stationTypeCode" 
+                                property={record.stationTypeCode}
+                            />
+                        </Grid>
+                        <Grid item xs={6}>
+                            <PanelTypography
+                                title="table.field.basStationType.stationTypeName" 
+                                property={record.stationTypeName}
+                            />
+                        </Grid>
+                        <Grid item xs={6}>
+                            <PanelTypography
+                                title="table.field.basStationType.allowFullPalletOut" 
+                                property={record.allowFullPalletOut}
+                            />
+                        </Grid>
+                        <Grid item xs={6}>
+                            <PanelTypography
+                                title="table.field.basStationType.allowEmptyPalletOut" 
+                                property={record.allowEmptyPalletOut}
+                            />
+                        </Grid>
+                        <Grid item xs={6}>
+                            <PanelTypography
+                                title="table.field.basStationType.allowPick" 
+                                property={record.allowPick}
+                            />
+                        </Grid>
+                        <Grid item xs={6}>
+                            <PanelTypography
+                                title="table.field.basStationType.allowFullPalletIn" 
+                                property={record.allowFullPalletIn}
+                            />
+                        </Grid>
+                        <Grid item xs={6}>
+                            <PanelTypography
+                                title="table.field.basStationType.allowEmptyPalletIn" 
+                                property={record.allowEmptyPalletIn}
+                            />
+                        </Grid>
+                        <Grid item xs={6}>
+                            <PanelTypography
+                                title="table.field.basStationType.conveyorLine" 
+                                property={record.conveyorLine}
+                            />
+                        </Grid>
+                        <Grid item xs={6}>
+                            <PanelTypography
+                                title="table.field.basStationType.allowGroundStation" 
+                                property={record.allowGroundStation}
+                            />
+                        </Grid>
+                        <Grid item xs={6}>
+                            <PanelTypography
+                                title="table.field.basStationType.allowGroundBarcodeStation" 
+                                property={record.allowGroundBarcodeStation}
+                            />
+                        </Grid>
+
+                    </Grid>
+                </CardContent>
+            </Card >
+        </>
+    );
+};
+
+export default BasStationTypePanel;
diff --git a/rsf-admin/src/page/basStationType/index.jsx b/rsf-admin/src/page/basStationType/index.jsx
new file mode 100644
index 0000000..e4d9ba5
--- /dev/null
+++ b/rsf-admin/src/page/basStationType/index.jsx
@@ -0,0 +1,18 @@
+import React, { useState, useRef, useEffect, useMemo } from "react";
+import {
+    ListGuesser,
+    EditGuesser,
+    ShowGuesser,
+} from "react-admin";
+
+import BasStationTypeList from "./BasStationTypeList";
+import BasStationTypeEdit from "./BasStationTypeEdit";
+
+export default {
+    list: BasStationTypeList,
+    edit: BasStationTypeEdit,
+    show: ShowGuesser,
+    recordRepresentation: (record) => {
+        return `${record.id}`
+    }
+};
diff --git a/rsf-admin/src/page/matnrRestrictionWarehouse/MatnrRestrictionWarehouseCreate.jsx b/rsf-admin/src/page/matnrRestrictionWarehouse/MatnrRestrictionWarehouseCreate.jsx
new file mode 100644
index 0000000..28b42f4
--- /dev/null
+++ b/rsf-admin/src/page/matnrRestrictionWarehouse/MatnrRestrictionWarehouseCreate.jsx
@@ -0,0 +1,132 @@
+import React, { useState, useRef, useEffect, useMemo } from "react";
+import {
+    CreateBase,
+    useTranslate,
+    TextInput,
+    NumberInput,
+    BooleanInput,
+    DateInput,
+    SaveButton,
+    SelectInput,
+    ReferenceInput,
+    ReferenceArrayInput,
+    AutocompleteInput,
+    Toolbar,
+    required,
+    useDataProvider,
+    useNotify,
+    Form,
+    useCreateController,
+} from 'react-admin';
+import {
+    Dialog,
+    DialogActions,
+    DialogContent,
+    DialogTitle,
+    Stack,
+    Grid,
+    Box,
+} from '@mui/material';
+import DialogCloseButton from "../components/DialogCloseButton";
+import StatusSelectInput from "../components/StatusSelectInput";
+import MemoInput from "../components/MemoInput";
+
+const MatnrRestrictionWarehouseCreate = (props) => {
+    const { open, setOpen } = props;
+
+    const translate = useTranslate();
+    const notify = useNotify();
+
+    const handleClose = (event, reason) => {
+        if (reason !== "backdropClick") {
+            setOpen(false);
+        }
+    };
+
+    const handleSuccess = async (data) => {
+        setOpen(false);
+        notify('common.response.success');
+    };
+
+    const handleError = async (error) => {
+        notify(error.message || 'common.response.fail', { type: 'error', messageArgs: { _: error.message } });
+    };
+
+    return (
+        <>
+            <CreateBase
+                record={{}}
+                transform={(data) => {
+                    return data;
+                }}
+                mutationOptions={{ onSuccess: handleSuccess, onError: handleError }}
+            >
+                <Dialog
+                    open={open}
+                    onClose={handleClose}
+                    aria-labelledby="form-dialog-title"
+                    fullWidth
+                    disableRestoreFocus
+                    maxWidth="md"   // 'xs' | 'sm' | 'md' | 'lg' | 'xl'
+                >
+                    <Form>
+                        <DialogTitle id="form-dialog-title" sx={{
+                            position: 'sticky',
+                            top: 0,
+                            backgroundColor: 'background.paper',
+                            zIndex: 1000
+                        }}
+                        >
+                            {translate('create.title')}
+                            <Box sx={{ position: 'absolute', top: 8, right: 8, zIndex: 1001 }}>
+                                <DialogCloseButton onClose={handleClose} />
+                            </Box>
+                        </DialogTitle>
+                        <DialogContent sx={{ mt: 2 }}>
+                            <Grid container rowSpacing={2} columnSpacing={2}>
+                                <Grid item xs={6} display="flex" gap={1}>
+                                    <TextInput
+                                        label="table.field.matnrRestrictionWarehouse.productionLineCode"
+                                        source="productionLineCode"
+                                        parse={v => v}
+                                        autoFocus
+                                    />
+                                </Grid>
+                                <Grid item xs={6} display="flex" gap={1}>
+                                    <TextInput
+                                        label="table.field.matnrRestrictionWarehouse.productionLineName"
+                                        source="productionLineName"
+                                        parse={v => v}
+                                    />
+                                </Grid>
+                                <Grid item xs={6} display="flex" gap={1}>
+                                    <TextInput
+                                        label="table.field.matnrRestrictionWarehouse.matnrRestrictionCode"
+                                        source="matnrRestrictionCode"
+                                        parse={v => v}
+                                    />
+                                </Grid>
+
+                                <Grid item xs={6} display="flex" gap={1}>
+                                    <StatusSelectInput />
+                                </Grid>
+                                <Grid item xs={12} display="flex" gap={1}>
+                                    <Stack direction="column" spacing={1} width={'100%'}>
+                                        <MemoInput />
+                                    </Stack>
+                                </Grid>
+                            </Grid>
+                        </DialogContent>
+                        <DialogActions sx={{ position: 'sticky', bottom: 0, backgroundColor: 'background.paper', zIndex: 1000 }}>
+                            <Toolbar sx={{ width: '100%', justifyContent: 'space-between' }}  >
+                                <SaveButton />
+                            </Toolbar>
+                        </DialogActions>
+                    </Form>
+                </Dialog>
+            </CreateBase>
+        </>
+    )
+}
+
+export default MatnrRestrictionWarehouseCreate;
diff --git a/rsf-admin/src/page/matnrRestrictionWarehouse/MatnrRestrictionWarehouseEdit.jsx b/rsf-admin/src/page/matnrRestrictionWarehouse/MatnrRestrictionWarehouseEdit.jsx
new file mode 100644
index 0000000..ba69099
--- /dev/null
+++ b/rsf-admin/src/page/matnrRestrictionWarehouse/MatnrRestrictionWarehouseEdit.jsx
@@ -0,0 +1,104 @@
+import React, { useState, useRef, useEffect, useMemo } from "react";
+import {
+    Edit,
+    SimpleForm,
+    FormDataConsumer,
+    useTranslate,
+    TextInput,
+    NumberInput,
+    BooleanInput,
+    DateInput,
+    SelectInput,
+    ReferenceInput,
+    ReferenceArrayInput,
+    AutocompleteInput,
+    SaveButton,
+    Toolbar,
+    Labeled,
+    NumberField,
+    required,
+    useRecordContext,
+    DeleteButton,
+} from 'react-admin';
+import { useWatch, useFormContext } from "react-hook-form";
+import { Stack, Grid, Box, Typography } from '@mui/material';
+import * as Common from '@/utils/common';
+import { EDIT_MODE, REFERENCE_INPUT_PAGESIZE } from '@/config/setting';
+import EditBaseAside from "../components/EditBaseAside";
+import CustomerTopToolBar from "../components/EditTopToolBar";
+import MemoInput from "../components/MemoInput";
+import StatusSelectInput from "../components/StatusSelectInput";
+
+const FormToolbar = () => {
+    const { getValues } = useFormContext();
+
+    return (
+        <Toolbar sx={{ justifyContent: 'space-between' }}>
+            <SaveButton />
+            <DeleteButton mutationMode="optimistic" />
+        </Toolbar>
+    )
+}
+
+const MatnrRestrictionWarehouseEdit = () => {
+    const translate = useTranslate();
+
+    return (
+        <Edit
+            redirect="list"
+            mutationMode={EDIT_MODE}
+            actions={<CustomerTopToolBar />}
+            aside={<EditBaseAside />}
+        >
+            <SimpleForm
+                shouldUnregister
+                warnWhenUnsavedChanges
+                toolbar={<FormToolbar />}
+                mode="onTouched"
+                defaultValues={{}}
+            // validate={(values) => { }}
+            >
+                <Grid container width={{ xs: '100%', xl: '80%' }} rowSpacing={3} columnSpacing={3}>
+                    <Grid item xs={12} md={8}>
+                        <Typography variant="h6" gutterBottom>
+                            {translate('common.edit.title.main')}
+                        </Typography>
+                        <Stack direction='row' gap={2}>
+                            <TextInput
+                                label="table.field.matnrRestrictionWarehouse.productionLineCode"
+                                source="productionLineCode"
+                                parse={v => v}
+                                autoFocus
+                            />
+                        </Stack>
+                        <Stack direction='row' gap={2}>
+                            <TextInput
+                                label="table.field.matnrRestrictionWarehouse.productionLineName"
+                                source="productionLineName"
+                                parse={v => v}
+                            />
+                        </Stack>
+                        <Stack direction='row' gap={2}>
+                            <TextInput
+                                label="table.field.matnrRestrictionWarehouse.matnrRestrictionCode"
+                                source="matnrRestrictionCode"
+                                parse={v => v}
+                            />
+                        </Stack>
+
+                    </Grid>
+                    <Grid item xs={12} md={4}>
+                        <Typography variant="h6" gutterBottom>
+                            {translate('common.edit.title.common')}
+                        </Typography>
+                        <StatusSelectInput />
+                        <Box mt="2em" />
+                        <MemoInput />
+                    </Grid>
+                </Grid>
+            </SimpleForm>
+        </Edit >
+    )
+}
+
+export default MatnrRestrictionWarehouseEdit;
diff --git a/rsf-admin/src/page/matnrRestrictionWarehouse/MatnrRestrictionWarehouseList.jsx b/rsf-admin/src/page/matnrRestrictionWarehouse/MatnrRestrictionWarehouseList.jsx
new file mode 100644
index 0000000..60e35ab
--- /dev/null
+++ b/rsf-admin/src/page/matnrRestrictionWarehouse/MatnrRestrictionWarehouseList.jsx
@@ -0,0 +1,156 @@
+import React, { useState, useRef, useEffect, useMemo, useCallback } from "react";
+import { useNavigate } from 'react-router-dom';
+import {
+    List,
+    DatagridConfigurable,
+    SearchInput,
+    TopToolbar,
+    SelectColumnsButton,
+    EditButton,
+    FilterButton,
+    CreateButton,
+    ExportButton,
+    BulkDeleteButton,
+    WrapperField,
+    useRecordContext,
+    useTranslate,
+    useNotify,
+    useListContext,
+    FunctionField,
+    TextField,
+    NumberField,
+    DateField,
+    BooleanField,
+    ReferenceField,
+    TextInput,
+    DateTimeInput,
+    DateInput,
+    SelectInput,
+    NumberInput,
+    ReferenceInput,
+    ReferenceArrayInput,
+    AutocompleteInput,
+    DeleteButton,
+} from 'react-admin';
+import { Box, Typography, Card, Stack } from '@mui/material';
+import { styled } from '@mui/material/styles';
+import MatnrRestrictionWarehouseCreate from "./MatnrRestrictionWarehouseCreate";
+import MatnrRestrictionWarehousePanel from "./MatnrRestrictionWarehousePanel";
+import EmptyData from "../components/EmptyData";
+import MyCreateButton from "../components/MyCreateButton";
+import MyExportButton from '../components/MyExportButton';
+import PageDrawer from "../components/PageDrawer";
+import MyField from "../components/MyField";
+import { PAGE_DRAWER_WIDTH, OPERATE_MODE, DEFAULT_PAGE_SIZE } from '@/config/setting';
+import * as Common from '@/utils/common';
+
+const StyledDatagrid = styled(DatagridConfigurable)(({ theme }) => ({
+    '& .css-1vooibu-MuiSvgIcon-root': {
+        height: '.9em'
+    },
+    '& .RaDatagrid-row': {
+        cursor: 'auto'
+    },
+    '& .column-name': {
+    },
+    '& .opt': {
+        width: 200
+    },
+}));
+
+const filters = [
+    <SearchInput source="condition" alwaysOn />,
+    <DateInput label='common.time.after' source="timeStart" alwaysOn />,
+    <DateInput label='common.time.before' source="timeEnd" alwaysOn />,
+
+    <TextInput source="productionLineCode" label="table.field.matnrRestrictionWarehouse.productionLineCode" />,
+    <TextInput source="productionLineName" label="table.field.matnrRestrictionWarehouse.productionLineName" />,
+    <TextInput source="matnrRestrictionCode" label="table.field.matnrRestrictionWarehouse.matnrRestrictionCode" />,
+
+    <TextInput label="common.field.memo" source="memo" />,
+    <SelectInput
+        label="common.field.status"
+        source="status"
+        choices={[
+            { id: '1', name: 'common.enums.statusTrue' },
+            { id: '0', name: 'common.enums.statusFalse' },
+        ]}
+        resettable
+    />,
+]
+
+const MatnrRestrictionWarehouseList = () => {
+    const translate = useTranslate();
+
+    const [createDialog, setCreateDialog] = useState(false);
+    const [drawerVal, setDrawerVal] = useState(false);
+
+    return (
+        <Box display="flex">
+            <List
+                sx={{
+                    flexGrow: 1,
+                    transition: (theme) =>
+                        theme.transitions.create(['all'], {
+                            duration: theme.transitions.duration.enteringScreen,
+                        }),
+                    marginRight: !!drawerVal ? `${PAGE_DRAWER_WIDTH}px` : 0,
+                }}
+                title={"menu.matnrRestrictionWarehouse"}
+                empty={<EmptyData onClick={() => { setCreateDialog(true) }} />}
+                filters={filters}
+                sort={{ field: "create_time", order: "desc" }}
+                actions={(
+                    <TopToolbar>
+                        <FilterButton />
+                        <MyCreateButton onClick={() => { setCreateDialog(true) }} />
+                        <SelectColumnsButton preferenceKey='matnrRestrictionWarehouse' />
+                        <MyExportButton />
+                    </TopToolbar>
+                )}
+                perPage={DEFAULT_PAGE_SIZE}
+            >
+                <StyledDatagrid
+                    preferenceKey='matnrRestrictionWarehouse'
+                    bulkActionButtons={() => <BulkDeleteButton mutationMode={OPERATE_MODE} />}
+                    rowClick={(id, resource, record) => false}
+                    expand={() => <MatnrRestrictionWarehousePanel />}
+                    expandSingle={true}
+                    omit={['id', 'createTime', 'createBy', 'memo']}
+                >
+                    <NumberField source="id" />
+                    <TextField source="productionLineCode" label="table.field.matnrRestrictionWarehouse.productionLineCode" />
+                    <TextField source="productionLineName" label="table.field.matnrRestrictionWarehouse.productionLineName" />
+                    <TextField source="matnrRestrictionCode" label="table.field.matnrRestrictionWarehouse.matnrRestrictionCode" />
+
+                    <ReferenceField source="updateBy" label="common.field.updateBy" reference="user" link={false} sortable={false}>
+                        <TextField source="nickname" />
+                    </ReferenceField>
+                    <DateField source="updateTime" label="common.field.updateTime" showTime />
+                    <ReferenceField source="createBy" label="common.field.createBy" reference="user" link={false} sortable={false}>
+                        <TextField source="nickname" />
+                    </ReferenceField>
+                    <DateField source="createTime" label="common.field.createTime" showTime />
+                    <BooleanField source="statusBool" label="common.field.status" sortable={false} />
+                    <TextField source="memo" label="common.field.memo" sortable={false} />
+                    <WrapperField cellClassName="opt" label="common.field.opt">
+                        <EditButton sx={{ padding: '1px', fontSize: '.75rem' }} />
+                        <DeleteButton sx={{ padding: '1px', fontSize: '.75rem' }} mutationMode={OPERATE_MODE} />
+                    </WrapperField>
+                </StyledDatagrid>
+            </List>
+            <MatnrRestrictionWarehouseCreate
+                open={createDialog}
+                setOpen={setCreateDialog}
+            />
+            <PageDrawer
+                title='MatnrRestrictionWarehouse Detail'
+                drawerVal={drawerVal}
+                setDrawerVal={setDrawerVal}
+            >
+            </PageDrawer>
+        </Box>
+    )
+}
+
+export default MatnrRestrictionWarehouseList;
diff --git a/rsf-admin/src/page/matnrRestrictionWarehouse/MatnrRestrictionWarehousePanel.jsx b/rsf-admin/src/page/matnrRestrictionWarehouse/MatnrRestrictionWarehousePanel.jsx
new file mode 100644
index 0000000..f962471
--- /dev/null
+++ b/rsf-admin/src/page/matnrRestrictionWarehouse/MatnrRestrictionWarehousePanel.jsx
@@ -0,0 +1,69 @@
+import React, { useState, useRef, useEffect, useMemo } from "react";
+import { Box, Card, CardContent, Grid, Typography, Tooltip } from '@mui/material';
+import {
+    useTranslate,
+    useRecordContext,
+} from 'react-admin';
+import PanelTypography from "../components/PanelTypography";
+import * as Common from '@/utils/common'
+
+const MatnrRestrictionWarehousePanel = () => {
+    const record = useRecordContext();
+    if (!record) return null;
+    const translate = useTranslate();
+    return (
+        <>
+            <Card sx={{ width: { xs: 300, sm: 500, md: 600, lg: 800 }, margin: 'auto' }}>
+                <CardContent>
+                    <Grid container spacing={2}>
+                        <Grid item xs={12} sx={{ display: 'flex', justifyContent: 'space-between' }}>
+                            <Typography variant="h6" gutterBottom align="left" sx={{
+                                maxWidth: { xs: '100px', sm: '180px', md: '260px', lg: '360px' },
+                                whiteSpace: 'nowrap',
+                                overflow: 'hidden',
+                                textOverflow: 'ellipsis',
+                            }}>
+                                {Common.camelToPascalWithSpaces(translate('table.field.matnrRestrictionWarehouse.id'))}: {record.id}
+                            </Typography>
+                            {/*  inherit, primary, secondary, textPrimary, textSecondary, error */}
+                            <Typography variant="h6" gutterBottom align="right" >
+                                ID: {record.id}
+                            </Typography>
+                        </Grid>
+                    </Grid>
+                    <Grid container spacing={2}>
+                        <Grid item xs={12} container alignContent="flex-end">
+                            <Typography variant="caption" color="textSecondary" sx={{ wordWrap: 'break-word', wordBreak: 'break-all' }}>
+                                {Common.camelToPascalWithSpaces(translate('common.field.memo'))}:{record.memo}
+                            </Typography>
+                        </Grid>
+                    </Grid>
+                    <Box height={20}>&nbsp;</Box>
+                    <Grid container spacing={2}>
+                        <Grid item xs={6}>
+                            <PanelTypography
+                                title="table.field.matnrRestrictionWarehouse.productionLineCode" 
+                                property={record.productionLineCode}
+                            />
+                        </Grid>
+                        <Grid item xs={6}>
+                            <PanelTypography
+                                title="table.field.matnrRestrictionWarehouse.productionLineName" 
+                                property={record.productionLineName}
+                            />
+                        </Grid>
+                        <Grid item xs={6}>
+                            <PanelTypography
+                                title="table.field.matnrRestrictionWarehouse.matnrRestrictionCode" 
+                                property={record.matnrRestrictionCode}
+                            />
+                        </Grid>
+
+                    </Grid>
+                </CardContent>
+            </Card >
+        </>
+    );
+};
+
+export default MatnrRestrictionWarehousePanel;
diff --git a/rsf-admin/src/page/matnrRestrictionWarehouse/index.jsx b/rsf-admin/src/page/matnrRestrictionWarehouse/index.jsx
new file mode 100644
index 0000000..9a73a1d
--- /dev/null
+++ b/rsf-admin/src/page/matnrRestrictionWarehouse/index.jsx
@@ -0,0 +1,18 @@
+import React, { useState, useRef, useEffect, useMemo } from "react";
+import {
+    ListGuesser,
+    EditGuesser,
+    ShowGuesser,
+} from "react-admin";
+
+import MatnrRestrictionWarehouseList from "./MatnrRestrictionWarehouseList";
+import MatnrRestrictionWarehouseEdit from "./MatnrRestrictionWarehouseEdit";
+
+export default {
+    list: MatnrRestrictionWarehouseList,
+    edit: MatnrRestrictionWarehouseEdit,
+    show: ShowGuesser,
+    recordRepresentation: (record) => {
+        return `${record.id}`
+    }
+};
diff --git a/rsf-server/src/main/java/basStationType.sql b/rsf-server/src/main/java/basStationType.sql
new file mode 100644
index 0000000..ed1eff5
--- /dev/null
+++ b/rsf-server/src/main/java/basStationType.sql
@@ -0,0 +1,31 @@
+-- save basStationType record
+-- mysql
+insert into `sys_menu` ( `name`, `parent_id`, `route`, `component`, `type`, `sort`, `tenant_id`, `status`) values ( 'menu.basStationType', '0', '/manager/basStationType', 'basStationType', '0' , '0', '1' , '1');
+
+insert into `sys_menu` ( `name`, `parent_id`, `type`, `authority`, `sort`, `tenant_id`, `status`) values ( 'Query 浣滀笟绔欑被鍨�', '', '1', 'manager:basStationType:list', '0', '1', '1');
+insert into `sys_menu` ( `name`, `parent_id`, `type`, `authority`, `sort`, `tenant_id`, `status`) values ( 'Create 浣滀笟绔欑被鍨�', '', '1', 'manager:basStationType:save', '1', '1', '1');
+insert into `sys_menu` ( `name`, `parent_id`, `type`, `authority`, `sort`, `tenant_id`, `status`) values ( 'Update 浣滀笟绔欑被鍨�', '', '1', 'manager:basStationType:update', '2', '1', '1');
+insert into `sys_menu` ( `name`, `parent_id`, `type`, `authority`, `sort`, `tenant_id`, `status`) values ( 'Delete 浣滀笟绔欑被鍨�', '', '1', 'manager:basStationType:remove', '3', '1', '1');
+
+-- locale menu name
+basStationType: 'BasStationType',
+
+-- locale field
+basStationType: {
+    stationTypeCode: "stationTypeCode",
+    stationTypeName: "stationTypeName",
+    allowFullPalletOut: "allowFullPalletOut",
+    allowEmptyPalletOut: "allowEmptyPalletOut",
+    allowPick: "allowPick",
+    allowFullPalletIn: "allowFullPalletIn",
+    allowEmptyPalletIn: "allowEmptyPalletIn",
+    conveyorLine: "conveyorLine",
+    allowGroundStation: "allowGroundStation",
+    allowGroundBarcodeStation: "allowGroundBarcodeStation",
+},
+
+-- ResourceContent
+import basStationType from './basStationType';
+
+case 'basStationType':
+    return basStationType;
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/ai/tool/RsfWmsStockTools.java b/rsf-server/src/main/java/com/vincent/rsf/server/ai/tool/RsfWmsStockTools.java
index 4c09581..f4f84c3 100644
--- a/rsf-server/src/main/java/com/vincent/rsf/server/ai/tool/RsfWmsStockTools.java
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/ai/tool/RsfWmsStockTools.java
@@ -85,28 +85,28 @@
             @ToolParam(required = true, description = "浣滀笟绫诲瀷鍒楄〃") List<String> types,
             @ToolParam(description = "杩斿洖鏉℃暟锛岄粯璁� 20锛屾渶澶� 50") Integer limit) {
         List<String> normalizedTypes = BuiltinToolGovernanceSupport.sanitizeStringList(types, "绔欑偣绫诲瀷鍒楄〃", 10, 32);
-        int finalLimit = BuiltinToolGovernanceSupport.normalizeLimit(limit, 20, 50);
-        List<DeviceSite> sites = deviceSiteService.list(new LambdaQueryWrapper<DeviceSite>()
-                .in(DeviceSite::getType, normalizedTypes)
-                .orderByAsc(DeviceSite::getType)
-                .orderByAsc(DeviceSite::getSite)
-                .last("LIMIT " + finalLimit));
+//        int finalLimit = BuiltinToolGovernanceSupport.normalizeLimit(limit, 20, 50);
+//        List<DeviceSite> sites = deviceSiteService.list(new LambdaQueryWrapper<DeviceSite>()
+//                .in(DeviceSite::getType, normalizedTypes)
+//                .orderByAsc(DeviceSite::getType)
+//                .orderByAsc(DeviceSite::getSite)
+//                .last("LIMIT " + finalLimit));
         List<Map<String, Object>> result = new ArrayList<>();
-        for (DeviceSite site : sites) {
-            Map<String, Object> item = new LinkedHashMap<>();
-            item.put("id", site.getId());
-            item.put("type", site.getType());
-            item.put("site", site.getSite());
-            item.put("name", site.getName());
-            item.put("target", site.getTarget());
-            item.put("label", site.getLabel());
-            item.put("device", site.getDevice());
-            item.put("deviceCode", site.getDeviceCode());
-            item.put("deviceSite", site.getDeviceSite());
-            item.put("channel", site.getChannel());
-            item.put("status", site.getStatus());
-            result.add(item);
-        }
+//        for (DeviceSite site : sites) {
+//            Map<String, Object> item = new LinkedHashMap<>();
+//            item.put("id", site.getId());
+//            item.put("type", site.getType());
+//            item.put("site", site.getSite());
+//            item.put("name", site.getName());
+//            item.put("target", site.getTarget());
+//            item.put("label", site.getLabel());
+//            item.put("device", site.getDevice());
+//            item.put("deviceCode", site.getDeviceCode());
+//            item.put("deviceSite", site.getDeviceSite());
+//            item.put("channel", site.getChannel());
+//            item.put("status", site.getStatus());
+//            result.add(item);
+//        }
         return result;
     }
 }
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/api/controller/erp/params/TaskInParam.java b/rsf-server/src/main/java/com/vincent/rsf/server/api/controller/erp/params/TaskInParam.java
index ea014ed..8ee2efb 100644
--- a/rsf-server/src/main/java/com/vincent/rsf/server/api/controller/erp/params/TaskInParam.java
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/api/controller/erp/params/TaskInParam.java
@@ -25,6 +25,9 @@
     @ApiModelProperty("浠诲姟缂栫爜")
     private String taskCode;
 
+    @ApiModelProperty("搴撳尯ID")
+    private Long areaId;
+
 //    @ApiModelProperty("搴撲綅绫诲瀷")
 //    private String locType;
 
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/api/controller/mcp/McpController.java b/rsf-server/src/main/java/com/vincent/rsf/server/api/controller/mcp/McpController.java
index cf992f1..798de0d 100644
--- a/rsf-server/src/main/java/com/vincent/rsf/server/api/controller/mcp/McpController.java
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/api/controller/mcp/McpController.java
@@ -75,7 +75,8 @@
             longs = JSONArray.parseArray(map.get("type").toString(), String.class);
             map.entrySet().removeIf(next -> next.getKey().equals("type"));
         }
-        List<DeviceSite> list = deviceSiteService.list(new LambdaQueryWrapper<DeviceSite>().in(DeviceSite::getType, longs));
+//        List<DeviceSite> list = deviceSiteService.list(new LambdaQueryWrapper<DeviceSite>().in(DeviceSite::getType, longs));
+        List<DeviceSite> list = deviceSiteService.list(new LambdaQueryWrapper<DeviceSite>());
         return R.ok().add(list);
     }
 
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/api/service/WcsService.java b/rsf-server/src/main/java/com/vincent/rsf/server/api/service/WcsService.java
index e2a432b..cecd6ba 100644
--- a/rsf-server/src/main/java/com/vincent/rsf/server/api/service/WcsService.java
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/api/service/WcsService.java
@@ -11,6 +11,7 @@
     void agvTaskPickUpComplete(TaskInParam param);
 
     InTaskMsgDto getLocNo(TaskInParam param) throws Exception;
+    InTaskMsgDto getLocNoArea(TaskInParam param) throws Exception;
 
     void syncLocsToWms();
 
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/api/service/impl/AgvServiceImpl.java b/rsf-server/src/main/java/com/vincent/rsf/server/api/service/impl/AgvServiceImpl.java
index b2e9abd..d3d6fbc 100644
--- a/rsf-server/src/main/java/com/vincent/rsf/server/api/service/impl/AgvServiceImpl.java
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/api/service/impl/AgvServiceImpl.java
@@ -19,6 +19,7 @@
 import com.vincent.rsf.server.manager.service.impl.DeviceSiteServiceImpl;
 import com.vincent.rsf.server.manager.service.impl.MatnrServiceImpl;
 import com.vincent.rsf.server.manager.utils.LocManageUtil;
+import com.vincent.rsf.server.manager.utils.WarehouseLocationRetrievalUtil;
 import lombok.extern.slf4j.Slf4j;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Service;
@@ -279,12 +280,12 @@
         if (Cools.isEmpty(area)) {
             throw new CoolException("鐩爣搴撳尯涓嶈兘涓虹┖");
         }
-
-        DeviceSite deviceSite = deviceSiteService.getOne(new LambdaQueryWrapper<DeviceSite>()
-                .eq(DeviceSite::getSite, sta)
-                .eq(DeviceSite::getAreaIdEnd, Long.parseLong(area))
-                .eq(DeviceSite::getType, TaskType.TASK_TYPE_IN.type).last("limit 1"));
-        if (Cools.isEmpty(deviceSite)) {
+        boolean isItAvailable = new WarehouseLocationRetrievalUtil().queryPathIsItAvailableInArea(sta, area, waitPakinPda.getBarcode(), "in");
+//        DeviceSite deviceSite = deviceSiteService.getOne(new LambdaQueryWrapper<DeviceSite>()
+//                .eq(DeviceSite::getSite, sta)
+//                .eq(DeviceSite::getAreaIdEnd, Long.parseLong(area))
+//                .eq(DeviceSite::getType, TaskType.TASK_TYPE_IN.type).last("limit 1"));
+        if (!isItAvailable) {
             throw new CoolException("鏃犲彲鐢ㄨ矾寰勶紒锛�");
         }
 
@@ -307,7 +308,7 @@
         }
         String targetLoc = LocManageUtil.getTargetLoc(Long.parseLong(area));
 
-        taskService.generateAGVTasks(waitPakin, targetLoc, sta, deviceSite.getDeviceCode(),loginUserId);
+        taskService.generateAGVTasks(waitPakin, targetLoc, sta,loginUserId,area);
         if (!basStation.getType().equals(0)){
             basStation.setUseStatus(LocStsType.LOC_STS_TYPE_R.type);
         }
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/api/service/impl/InBoundServiceImpl.java b/rsf-server/src/main/java/com/vincent/rsf/server/api/service/impl/InBoundServiceImpl.java
index a6790a1..20b9a6c 100644
--- a/rsf-server/src/main/java/com/vincent/rsf/server/api/service/impl/InBoundServiceImpl.java
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/api/service/impl/InBoundServiceImpl.java
@@ -15,6 +15,7 @@
 import com.vincent.rsf.server.manager.enums.*;
 import com.vincent.rsf.server.manager.service.*;
 import com.vincent.rsf.server.manager.utils.LocManageUtil;
+import com.vincent.rsf.server.manager.utils.WarehouseLocationRetrievalUtil;
 import com.vincent.rsf.server.system.constant.SerialRuleCode;
 import com.vincent.rsf.server.system.utils.SerialRuleUtils;
 import lombok.extern.slf4j.Slf4j;
@@ -214,14 +215,20 @@
 //                throw new CoolException("鏈壘鍒版墍灞炲簱鍖轰俊鎭�");
             }
 
-            DeviceSite deviceSite = deviceSiteService.getOne(new LambdaQueryWrapper<DeviceSite>()
-                    .eq(DeviceSite::getSite, station.getStationName())
-                    .eq(DeviceSite::getAreaIdEnd, warehouseArea.getId())
-                    .eq(DeviceSite::getType, TaskType.TASK_TYPE_EMPTY_IN.type).last("limit 1"));
-            if (Cools.isEmpty(deviceSite)) {
+            boolean isItAvailable = new WarehouseLocationRetrievalUtil().queryPathIsItAvailableInArea(station.getStationName(),  warehouseArea.getId(), param.getContainerNo(), TaskType.TASK_TYPE_EMPTY_IN.type);
+//            DeviceSite deviceSite = deviceSiteService.getOne(new LambdaQueryWrapper<DeviceSite>()
+//                    .eq(DeviceSite::getSite, )
+//                    .eq(DeviceSite::getAreaIdEnd,)
+//                    .eq(DeviceSite::getType, TaskType.TASK_TYPE_EMPTY_IN.type).last("limit 1"));
+//            if (Cools.isEmpty(deviceSite)) {
+//                errorBuilder.append("鏃犲彲鐢ㄨ矾寰�");
+//                continue;
+//                throw new CoolException("鏃犲彲鐢ㄨ矾寰勶紒锛�");
+//            }
+            if (!isItAvailable){
                 errorBuilder.append("鏃犲彲鐢ㄨ矾寰�");
                 continue;
-//                throw new CoolException("鏃犲彲鐢ㄨ矾寰勶紒锛�");
+
             }
 
 //        BasContainer container = basContainerService.getOne(new LambdaUpdateWrapper<BasContainer>()
@@ -244,16 +251,7 @@
             if (StringUtils.isBlank(ruleCode)) {
                 throw new CoolException("缂栫爜閿欒锛氳纭缂栫爜銆孲YS_TASK_CODE銆嶆槸鍚﹀凡鐢熸垚!!");
             }
-            String stationName = null;
-            if (Cools.isEmpty(deviceSite.getDeviceCode())) {
-                stationName = station.getStationName();
-            } else {
-                BasStation stationCode = basStationService.getById(deviceSite.getDeviceCode());
-                stationName = stationCode.getStationName();
-                if (Cools.isEmpty(stationCode)) {
-                    stationName = station.getStationName();
-                }
-            }
+            String stationName = station.getStationName();
             Task task = new Task();
             task.setTaskCode(ruleCode)
                     .setTaskStatus(TaskStsType.MISSION_INITIAL.id)
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/api/service/impl/MobileServiceImpl.java b/rsf-server/src/main/java/com/vincent/rsf/server/api/service/impl/MobileServiceImpl.java
index 6116334..9f14c2d 100644
--- a/rsf-server/src/main/java/com/vincent/rsf/server/api/service/impl/MobileServiceImpl.java
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/api/service/impl/MobileServiceImpl.java
@@ -21,6 +21,7 @@
 import com.vincent.rsf.server.manager.entity.*;
 import com.vincent.rsf.server.manager.mapper.*;
 import com.vincent.rsf.server.manager.service.*;
+import com.vincent.rsf.server.manager.service.impl.BasStationServiceImpl;
 import com.vincent.rsf.server.system.constant.CodeRes;
 import com.vincent.rsf.server.system.constant.GlobalConfigCode;
 import com.vincent.rsf.server.system.constant.SerialRuleCode;
@@ -131,6 +132,7 @@
     private BasContainerService basContainerService;
     @Resource
     private UserRoleService userRoleService;
+    private BasStationServiceImpl basStationService;
 
     /**
      * @return
@@ -1180,11 +1182,12 @@
      */
     @Override
     public R getDeviceSites() {
-        List<DeviceSite> sites = deviceSiteMapper.selectList(new LambdaQueryWrapper<DeviceSite>()
-                .select(DeviceSite::getId, DeviceSite::getSite, DeviceSite::getName)
-                .eq(DeviceSite::getStatus, 1)
-                .groupBy(DeviceSite::getSite, DeviceSite::getId, DeviceSite::getName));
-        return R.ok(sites);
+//        List<DeviceSite> sites = deviceSiteMapper.selectList(new LambdaQueryWrapper<DeviceSite>()
+//                .select(DeviceSite::getId, DeviceSite::getSite, DeviceSite::getName)
+//                .eq(DeviceSite::getStatus, 1)
+//                .groupBy(DeviceSite::getSite, DeviceSite::getId, DeviceSite::getName));
+        List<BasStation> basStationList = basStationService.list(new LambdaQueryWrapper<BasStation>().eq(BasStation::getStatus, 1));
+        return R.ok(basStationList);
     }
 
     /**
@@ -1214,7 +1217,7 @@
         }
         GenerateTaskParams taskParams = new GenerateTaskParams();
         taskParams.setWaitPakins(waitPakins)
-                .setSiteId(Long.parseLong(map.get("site").toString()))
+                .setSiteNo(map.get("siteNo").toString())
                 .setLocCode(map.get("locCode").toString());
         return R.ok(taskService.generateTasks(taskParams, loginUserId));
 
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/api/service/impl/WcsServiceImpl.java b/rsf-server/src/main/java/com/vincent/rsf/server/api/service/impl/WcsServiceImpl.java
index 3a435cf..6d3f168 100644
--- a/rsf-server/src/main/java/com/vincent/rsf/server/api/service/impl/WcsServiceImpl.java
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/api/service/impl/WcsServiceImpl.java
@@ -30,6 +30,7 @@
 import com.vincent.rsf.server.manager.mapper.LocItemMapper;
 import com.vincent.rsf.server.manager.service.*;
 import com.vincent.rsf.server.manager.service.impl.LocServiceImpl;
+import com.vincent.rsf.server.manager.utils.WarehouseLocationRetrievalUtil;
 import com.vincent.rsf.server.system.constant.SerialRuleCode;
 import com.vincent.rsf.server.manager.enums.LocStsType;
 import com.vincent.rsf.server.system.entity.*;
@@ -130,7 +131,7 @@
     public InTaskMsgDto createInTask(TaskInParam param) {
 
         // 楠岃瘉璁惧绔欑偣
-        DeviceSite deviceSite = validateDeviceSite(param);
+//        DeviceSite deviceSite = validateDeviceSite(param);
 
         // 楠岃瘉缁勬嫋鐘舵��
         WaitPakin waitPakin = validateWaitPakin(param.getBarcode());
@@ -148,7 +149,7 @@
 
         // 鍒涘缓骞朵繚瀛樹换鍔�
         Task task = createTask(ruleCode, locNo.getLocNo(), waitPakin.getBarcode(),
-                deviceSite.getDeviceSite(), param.getSourceStaNo().toString(), param.getUser());
+                null, param.getSourceStaNo().toString(), param.getUser());
 
         // 鏇存柊搴撲綅鐘舵��
         updateLocStatus(task.getTargLoc(), waitPakin.getBarcode());
@@ -171,16 +172,16 @@
     /**
      * 楠岃瘉璁惧绔欑偣
      */
-    private DeviceSite validateDeviceSite(TaskInParam param) {
-        DeviceSite deviceSite = deviceSiteService.getOne(new LambdaQueryWrapper<DeviceSite>()
-                .eq(DeviceSite::getSite, param.getSourceStaNo())
-                .eq(DeviceSite::getType, param.getIoType()));
-
-        if (Objects.isNull(deviceSite)) {
-            throw new CoolException("绔欑偣涓嶅瓨鍦紒锛�");
-        }
-        return deviceSite;
-    }
+//    private DeviceSite validateDeviceSite(TaskInParam param) {
+//        DeviceSite deviceSite = deviceSiteService.getOne(new LambdaQueryWrapper<DeviceSite>()
+//                .eq(DeviceSite::getSite, param.getSourceStaNo())
+//                .eq(DeviceSite::getType, param.getIoType()));
+//
+//        if (Objects.isNull(deviceSite)) {
+//            throw new CoolException("绔欑偣涓嶅瓨鍦紒锛�");
+//        }
+//        return deviceSite;
+//    }
 
     /**
      * 楠岃瘉缁勬嫋鐘舵��
@@ -393,6 +394,42 @@
 //        return locNo;
 //    }
     @Override
+    public InTaskMsgDto getLocNoArea(TaskInParam param) throws Exception {
+        String matnr = null;
+        String batch = null;
+        List<WaitPakin> waitPakins = waitPakinService.list(new LambdaQueryWrapper<WaitPakin>().eq(WaitPakin::getBarcode, param.getBarcode()));
+        if (Cools.isEmpty(waitPakins) && param.getIoType().equals(TaskType.TASK_TYPE_IN.type)) {
+            throw new CoolException("鏈壘鍒扮粍鎵樹俊鎭紝璇风粍鎵�");
+        } else if (!Cools.isEmpty(waitPakins)) {
+            matnr = waitPakins.get(0).getCode();
+            batch = waitPakins.get(0).getCode();
+        }
+
+        DeviceBind deviceBind = deviceBindService.getById(LocUtils.getAreaType(param.getSourceStaNo()));
+        if (Cools.isEmpty(deviceBind)) {
+            throw new CoolException("鏁版嵁寮傚父锛岃鑱旂郴绠$悊鍛�===>搴撲綅瑙勫垯鏈煡");
+        }
+        WarehouseAreas warehouseArea = warehouseAreasService.getById(deviceBind.getTypeId());
+        if (Cools.isEmpty(warehouseArea)) {
+            throw new CoolException("鏈壘鍒版墍灞炲簱鍖轰俊鎭�");
+        }
+        LocTypeDto locTypeDto = new LocTypeDto(param);
+        InTaskMsgDto dto = null;
+        //鏍规嵁绔嬪簱绫诲瀷鑾峰彇鑾峰彇搴撲綅
+        if (warehouseArea.getType().equals(WarehType.WAREHOUSE_TYPE_CRN.val)) {
+            //鍫嗗灈鏈�
+            dto = getLocNoCrn(param.getOrgLoc(), deviceBind, warehouseArea.getId(), param.getSourceStaNo(), matnr, batch, locTypeDto, 0, param.getIoType());
+
+        } else if (warehouseArea.getType().equals(WarehType.WAREHOUSE_TYPE_FOUR_DIRECTIONS.val)) {
+            //鍥涘悜搴�
+        } else {
+            //CTU 搴撲互鍙婂叾瀹�
+            dto = getLocNoCtu(deviceBind, warehouseArea.getId(), param.getSourceStaNo(), matnr, batch, locTypeDto, 0, param.getIoType());
+        }
+        return dto;
+    }
+
+    @Override
     public InTaskMsgDto getLocNo(TaskInParam param) throws Exception {
         String matnr = null;
         String batch = null;
@@ -403,13 +440,13 @@
             matnr = waitPakins.get(0).getCode();
             batch = waitPakins.get(0).getCode();
         }
-        List<DeviceSite> deviceSites = deviceSiteService.list(new LambdaQueryWrapper<DeviceSite>()
-                .eq(DeviceSite::getSite, param.getSourceStaNo())
-                .eq(DeviceSite::getType, param.getIoType())
-        );
-        if (Cools.isEmpty(deviceSites)) {
-            throw new CoolException("鏈壘鍒扮珯鐐硅矾寰勪俊鎭�");
-        }
+//        List<DeviceSite> deviceSites = deviceSiteService.list(new LambdaQueryWrapper<DeviceSite>()
+//                .eq(DeviceSite::getSite, param.getSourceStaNo())
+//                .eq(DeviceSite::getType, param.getIoType())
+//        );
+//        if (Cools.isEmpty(deviceSites)) {
+//            throw new CoolException("鏈壘鍒扮珯鐐硅矾寰勪俊鎭�");
+//        }
         DeviceBind deviceBind = deviceBindService.getById(LocUtils.getAreaType(param.getSourceStaNo()));
         if (Cools.isEmpty(deviceBind)) {
             throw new CoolException("鏁版嵁寮傚父锛岃鑱旂郴绠$悊鍛�===>搴撲綅瑙勫垯鏈煡");
@@ -730,40 +767,22 @@
             }
         }
 
-//        // 闈犺繎鎽嗘斁瑙勫垯 --- 绌烘墭 //浜掗�氱増
-//        if (ioType == 10 && deviceBind.getEmptySimilar().equals("1")) {
-//            List<LocMast> locMasts = locMastService.selectList(new EntityWrapper<LocMast>()
-//                    .eq("loc_sts", "D").ge("row1", sRow).le("row1", eRow).eq("whs_type", rowLastnoType.getType().longValue()));
-//            if (!locMasts.isEmpty()) {
-//                for (LocMast loc : locMasts) {
-//                    if (Utils.isShallowLoc(slaveProperties, loc.getLocNo())) {
-//                        continue;
-//                    }
-//                    String shallowLocNo = Utils.getShallowLoc(slaveProperties, loc.getLocNo());
-//                    // 妫�娴嬬洰鏍囧簱浣嶆槸鍚︿负绌哄簱浣�
-//                    LocMast shallowLoc = locMastService.selectById(shallowLocNo);
-//                    if (shallowLoc != null && shallowLoc.getLocSts().equals("O")) {
-//                        if (VersionUtils.locMoveCheckLocTypeComplete(shallowLoc, locTypeDto)) {
-//                            if (basCrnpService.checkSiteError(shallowLoc.getCrnNo(), true)) {
-//                                locMast = shallowLoc;
-//                                crnNo = locMast.getCrnNo();
-//                                break;
-//                            }
-//                        }
-//                    }
-//                }
-//            }
-//        }
-        //鏌ユ壘璺緞
-        DeviceSite deviceSite = deviceSiteService.getOne(new LambdaQueryWrapper<DeviceSite>()
-                .eq(DeviceSite::getType, ioType)
-                .eq(DeviceSite::getSite, sourceStaNo)
-                .eq(DeviceSite::getChannel, channel).last("limit 1")
-        );
-        if (Cools.isEmpty(deviceSite)) {
-            channel = 0;
-        } else {
-            inTaskMsgDto.setStaNo(deviceSite.getDeviceSite());
+
+
+        if (loc != null) {
+            //鏌ユ壘璺緞
+            boolean available = new WarehouseLocationRetrievalUtil().queryPathIsItAvailableInArea(sourceStaNo, loc.getAreaId().toString() ,loc.getBarcode(),"in");
+//            DeviceSite deviceSite = deviceSiteService.getOne(new LambdaQueryWrapper<DeviceSite>()
+//                    .eq(DeviceSite::getType, ioType)
+//                    .eq(DeviceSite::getSite, sourceStaNo)
+//                    .eq(DeviceSite::getChannel, channel).last("limit 1")
+//            );
+            if (!available) {
+                channel = 0;
+                loc = null;
+            } else {
+                inTaskMsgDto.setStaNo(sourceStaNo);
+            }
         }
 
         //鏇存柊褰撳墠鎺�
@@ -891,6 +910,23 @@
                 }
             }
         }
+
+        if (loc != null) {
+            //鏌ユ壘璺緞
+            boolean available = new WarehouseLocationRetrievalUtil().queryPathIsItAvailableInArea(sourceStaNo, loc.getAreaId().toString() ,loc.getBarcode(),"in");
+//            DeviceSite deviceSite = deviceSiteService.getOne(new LambdaQueryWrapper<DeviceSite>()
+//                    .eq(DeviceSite::getType, ioType)
+//                    .eq(DeviceSite::getSite, sourceStaNo)
+//                    .eq(DeviceSite::getChannel, channel).last("limit 1")
+//            );
+            if (!available) {
+                channel = 0;
+                loc = null;
+            } else {
+                inTaskMsgDto.setStaNo(sourceStaNo);
+            }
+        }
+
         //鏌ヨ褰撳墠搴撲綅绫诲瀷绌哄簱浣� 灏忎簬5涓垯locmast = null
         List<Loc> locTypeLocMasts = locService.list(new LambdaQueryWrapper<Loc>()
                 .eq(Loc::getUseStatus, LocStsType.LOC_STS_TYPE_O.type)
@@ -954,18 +990,34 @@
             loc = loc2;
             break;
         }
+
         //鏌ユ壘璺緞
-        DeviceSite deviceSite = deviceSiteService.getOne(new LambdaQueryWrapper<DeviceSite>()
-                .eq(DeviceSite::getType, ioType)
-                .eq(DeviceSite::getSite, sourceStaNo)
-                .eq(!Objects.isNull(loc.getDeviceNo()), DeviceSite::getDeviceCode, loc.getDeviceNo())
-        );
-        if (Cools.isEmpty(deviceSite)) {
-            deviceNo = 0;
-            loc = null;
-        } else {
-            inTaskMsgDto.setStaNo(deviceSite.getDeviceSite());
+        if (loc != null) {
+            //鏌ユ壘璺緞
+            boolean available = new WarehouseLocationRetrievalUtil().queryPathIsItAvailableInArea(sourceStaNo, loc.getAreaId().toString() ,loc.getBarcode(),"in");
+//            DeviceSite deviceSite = deviceSiteService.getOne(new LambdaQueryWrapper<DeviceSite>()
+//                    .eq(DeviceSite::getType, ioType)
+//                    .eq(DeviceSite::getSite, sourceStaNo)
+//                    .eq(DeviceSite::getChannel, channel).last("limit 1")
+//            );
+            if (!available) {
+                deviceNo = 0;
+                loc = null;
+            } else {
+                inTaskMsgDto.setStaNo(sourceStaNo);
+            }
         }
+//        DeviceSite deviceSite = deviceSiteService.getOne(new LambdaQueryWrapper<DeviceSite>()
+//                .eq(DeviceSite::getType, ioType)
+//                .eq(DeviceSite::getSite, sourceStaNo)
+//                .eq(!Objects.isNull(loc.getDeviceNo()), DeviceSite::getDeviceCode, loc.getDeviceNo())
+//        );
+//        if (Cools.isEmpty(deviceSite)) {
+//            deviceNo = 0;
+//            loc = null;
+//        } else {
+//            inTaskMsgDto.setStaNo(deviceSite.getDeviceSite());
+//        }
         // 閫掑綊鏌ヨ
         if (Cools.isEmpty(loc) || !loc.getUseStatus().equals(LocStsType.LOC_STS_TYPE_O.type)) {
             // 褰撳墠宸烽亾鏃犵┖搴撲綅鏃讹紝閫掑綊璋冩暣鑷充笅涓�宸烽亾锛屾绱㈠叏閮ㄥ贩閬撴棤鏋滃悗锛岃烦鍑洪�掑綊
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/api/utils/LocUtils.java b/rsf-server/src/main/java/com/vincent/rsf/server/api/utils/LocUtils.java
index 8557a37..3024b18 100644
--- a/rsf-server/src/main/java/com/vincent/rsf/server/api/utils/LocUtils.java
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/api/utils/LocUtils.java
@@ -346,17 +346,6 @@
 //                }
 //            }
 //        }
-        //鏌ユ壘璺緞
-        DeviceSite deviceSite = deviceSiteService.getOne(new LambdaQueryWrapper<DeviceSite>()
-                .eq(DeviceSite::getType, ioType)
-                .eq(DeviceSite::getSite, sourceStaNo)
-                .eq(DeviceSite::getChannel, channel)
-        );
-        if (Cools.isEmpty(deviceSite)) {
-            channel = 0;
-        } else {
-            inTaskMsgDto.setStaNo(deviceSite.getDeviceSite());
-        }
 
         //鏇存柊褰撳墠鎺�
         deviceBind.setCurrentRow(curRow);
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/common/CodeBuilder.java b/rsf-server/src/main/java/com/vincent/rsf/server/common/CodeBuilder.java
index 24091e7..1b5dba8 100644
--- a/rsf-server/src/main/java/com/vincent/rsf/server/common/CodeBuilder.java
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/common/CodeBuilder.java
@@ -22,8 +22,8 @@
 //        generator.username="sa";
 //        generator.password="Zoneyung@zy56$";
 
-        generator.table = "man_bas_station_area";
-        generator.tableDesc = "鐗╂枡鏉冮檺";
+        generator.table = "man_matnr_restriction_warehouse";
+        generator.tableDesc = "鐗╂枡闄愬埗";
         generator.packagePath = "com.vincent.rsf.server.manager";
 
         generator.build();
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/manager/controller/BasStationTypeController.java b/rsf-server/src/main/java/com/vincent/rsf/server/manager/controller/BasStationTypeController.java
new file mode 100644
index 0000000..c1d3c16
--- /dev/null
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/manager/controller/BasStationTypeController.java
@@ -0,0 +1,110 @@
+package com.vincent.rsf.server.manager.controller;
+
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import com.vincent.rsf.framework.common.Cools;
+import com.vincent.rsf.framework.common.R;
+import com.vincent.rsf.server.common.utils.ExcelUtil;
+import com.vincent.rsf.server.common.annotation.OperationLog;
+import com.vincent.rsf.server.common.domain.BaseParam;
+import com.vincent.rsf.server.common.domain.KeyValVo;
+import com.vincent.rsf.server.common.domain.PageParam;
+import com.vincent.rsf.server.manager.entity.BasStationType;
+import com.vincent.rsf.server.manager.service.BasStationTypeService;
+import com.vincent.rsf.server.system.controller.BaseController;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.security.access.prepost.PreAuthorize;
+import org.springframework.web.bind.annotation.*;
+
+import jakarta.servlet.http.HttpServletResponse;
+import java.util.*;
+
+@RestController
+public class BasStationTypeController extends BaseController {
+
+    @Autowired
+    private BasStationTypeService basStationTypeService;
+
+    @PreAuthorize("hasAuthority('manager:basStationType:list')")
+    @PostMapping("/basStationType/page")
+    public R page(@RequestBody Map<String, Object> map) {
+        BaseParam baseParam = buildParam(map, BaseParam.class);
+        PageParam<BasStationType, BaseParam> pageParam = new PageParam<>(baseParam, BasStationType.class);
+        return R.ok().add(basStationTypeService.page(pageParam, pageParam.buildWrapper(true)));
+    }
+
+    @PreAuthorize("hasAuthority('manager:basStationType:list')")
+    @PostMapping("/basStationType/list")
+    public R list(@RequestBody Map<String, Object> map) {
+        return R.ok().add(basStationTypeService.list());
+    }
+
+    @PreAuthorize("hasAuthority('manager:basStationType:list')")
+    @PostMapping({"/basStationType/many/{ids}", "/basStationTypes/many/{ids}"})
+    public R many(@PathVariable Long[] ids) {
+        return R.ok().add(basStationTypeService.listByIds(Arrays.asList(ids)));
+    }
+
+    @PreAuthorize("hasAuthority('manager:basStationType:list')")
+    @GetMapping("/basStationType/{id}")
+    public R get(@PathVariable("id") Long id) {
+        return R.ok().add(basStationTypeService.getById(id));
+    }
+
+    @PreAuthorize("hasAuthority('manager:basStationType:save')")
+    @OperationLog("Create 浣滀笟绔欑被鍨�")
+    @PostMapping("/basStationType/save")
+    public R save(@RequestBody BasStationType basStationType) {
+//        basStationType.setCreateBy(getLoginUserId());
+//        basStationType.setCreateTime(new Date());
+//        basStationType.setUpdateBy(getLoginUserId());
+//        basStationType.setUpdateTime(new Date());
+//        if (!basStationTypeService.save(basStationType)) {
+//            return R.error("Save Fail");
+//        }
+        return R.ok("Save Success").add(basStationType);
+    }
+
+    @PreAuthorize("hasAuthority('manager:basStationType:update')")
+    @OperationLog("Update 浣滀笟绔欑被鍨�")
+    @PostMapping("/basStationType/update")
+    public R update(@RequestBody BasStationType basStationType) {
+//        basStationType.setUpdateBy(getLoginUserId());
+//        basStationType.setUpdateTime(new Date());
+//        if (!basStationTypeService.updateById(basStationType)) {
+//            return R.error("Update Fail");
+//        }
+        return R.ok("Update Success").add(basStationType);
+    }
+
+    @PreAuthorize("hasAuthority('manager:basStationType:remove')")
+    @OperationLog("Delete 浣滀笟绔欑被鍨�")
+    @PostMapping("/basStationType/remove/{ids}")
+    public R remove(@PathVariable Long[] ids) {
+        if (!basStationTypeService.removeByIds(Arrays.asList(ids))) {
+            return R.error("Delete Fail");
+        }
+        return R.ok("Delete Success").add(ids);
+    }
+
+    @PreAuthorize("hasAuthority('manager:basStationType:list')")
+    @PostMapping("/basStationType/query")
+    public R query(@RequestParam(required = false) String condition) {
+        List<KeyValVo> vos = new ArrayList<>();
+        LambdaQueryWrapper<BasStationType> wrapper = new LambdaQueryWrapper<>();
+        if (!Cools.isEmpty(condition)) {
+            wrapper.like(BasStationType::getId, condition);
+        }
+        basStationTypeService.page(new Page<>(1, 30), wrapper).getRecords().forEach(
+                item -> vos.add(new KeyValVo(item.getId(), item.getId()))
+        );
+        return R.ok().add(vos);
+    }
+
+    @PreAuthorize("hasAuthority('manager:basStationType:list')")
+    @PostMapping("/basStationType/export")
+    public void export(@RequestBody Map<String, Object> map, HttpServletResponse response) throws Exception {
+        ExcelUtil.build(ExcelUtil.create(basStationTypeService.list(), BasStationType.class), response);
+    }
+
+}
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/manager/controller/MatnrRestrictionWarehouseController.java b/rsf-server/src/main/java/com/vincent/rsf/server/manager/controller/MatnrRestrictionWarehouseController.java
new file mode 100644
index 0000000..abc1e28
--- /dev/null
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/manager/controller/MatnrRestrictionWarehouseController.java
@@ -0,0 +1,110 @@
+package com.vincent.rsf.server.manager.controller;
+
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import com.vincent.rsf.framework.common.Cools;
+import com.vincent.rsf.framework.common.R;
+import com.vincent.rsf.server.common.utils.ExcelUtil;
+import com.vincent.rsf.server.common.annotation.OperationLog;
+import com.vincent.rsf.server.common.domain.BaseParam;
+import com.vincent.rsf.server.common.domain.KeyValVo;
+import com.vincent.rsf.server.common.domain.PageParam;
+import com.vincent.rsf.server.manager.entity.MatnrRestrictionWarehouse;
+import com.vincent.rsf.server.manager.service.MatnrRestrictionWarehouseService;
+import com.vincent.rsf.server.system.controller.BaseController;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.security.access.prepost.PreAuthorize;
+import org.springframework.web.bind.annotation.*;
+
+import jakarta.servlet.http.HttpServletResponse;
+import java.util.*;
+
+@RestController
+public class MatnrRestrictionWarehouseController extends BaseController {
+
+    @Autowired
+    private MatnrRestrictionWarehouseService matnrRestrictionWarehouseService;
+
+    @PreAuthorize("hasAuthority('manager:matnrRestrictionWarehouse:list')")
+    @PostMapping("/matnrRestrictionWarehouse/page")
+    public R page(@RequestBody Map<String, Object> map) {
+        BaseParam baseParam = buildParam(map, BaseParam.class);
+        PageParam<MatnrRestrictionWarehouse, BaseParam> pageParam = new PageParam<>(baseParam, MatnrRestrictionWarehouse.class);
+        return R.ok().add(matnrRestrictionWarehouseService.page(pageParam, pageParam.buildWrapper(true)));
+    }
+
+    @PreAuthorize("hasAuthority('manager:matnrRestrictionWarehouse:list')")
+    @PostMapping("/matnrRestrictionWarehouse/list")
+    public R list(@RequestBody Map<String, Object> map) {
+        return R.ok().add(matnrRestrictionWarehouseService.list());
+    }
+
+    @PreAuthorize("hasAuthority('manager:matnrRestrictionWarehouse:list')")
+    @PostMapping({"/matnrRestrictionWarehouse/many/{ids}", "/matnrRestrictionWarehouses/many/{ids}"})
+    public R many(@PathVariable Long[] ids) {
+        return R.ok().add(matnrRestrictionWarehouseService.listByIds(Arrays.asList(ids)));
+    }
+
+    @PreAuthorize("hasAuthority('manager:matnrRestrictionWarehouse:list')")
+    @GetMapping("/matnrRestrictionWarehouse/{id}")
+    public R get(@PathVariable("id") Long id) {
+        return R.ok().add(matnrRestrictionWarehouseService.getById(id));
+    }
+
+    @PreAuthorize("hasAuthority('manager:matnrRestrictionWarehouse:save')")
+    @OperationLog("Create 鐗╂枡闄愬埗")
+    @PostMapping("/matnrRestrictionWarehouse/save")
+    public R save(@RequestBody MatnrRestrictionWarehouse matnrRestrictionWarehouse) {
+        matnrRestrictionWarehouse.setCreateBy(getLoginUserId());
+        matnrRestrictionWarehouse.setCreateTime(new Date());
+        matnrRestrictionWarehouse.setUpdateBy(getLoginUserId());
+        matnrRestrictionWarehouse.setUpdateTime(new Date());
+        if (!matnrRestrictionWarehouseService.save(matnrRestrictionWarehouse)) {
+            return R.error("Save Fail");
+        }
+        return R.ok("Save Success").add(matnrRestrictionWarehouse);
+    }
+
+    @PreAuthorize("hasAuthority('manager:matnrRestrictionWarehouse:update')")
+    @OperationLog("Update 鐗╂枡闄愬埗")
+    @PostMapping("/matnrRestrictionWarehouse/update")
+    public R update(@RequestBody MatnrRestrictionWarehouse matnrRestrictionWarehouse) {
+        matnrRestrictionWarehouse.setUpdateBy(getLoginUserId());
+        matnrRestrictionWarehouse.setUpdateTime(new Date());
+        if (!matnrRestrictionWarehouseService.updateById(matnrRestrictionWarehouse)) {
+            return R.error("Update Fail");
+        }
+        return R.ok("Update Success").add(matnrRestrictionWarehouse);
+    }
+
+    @PreAuthorize("hasAuthority('manager:matnrRestrictionWarehouse:remove')")
+    @OperationLog("Delete 鐗╂枡闄愬埗")
+    @PostMapping("/matnrRestrictionWarehouse/remove/{ids}")
+    public R remove(@PathVariable Long[] ids) {
+        if (!matnrRestrictionWarehouseService.removeByIds(Arrays.asList(ids))) {
+            return R.error("Delete Fail");
+        }
+        return R.ok("Delete Success").add(ids);
+    }
+
+    @PreAuthorize("hasAuthority('manager:matnrRestrictionWarehouse:list')")
+    @PostMapping("/matnrRestrictionWarehouse/query")
+    public R query(@RequestParam(required = false) String condition) {
+        List<KeyValVo> vos = new ArrayList<>();
+        LambdaQueryWrapper<MatnrRestrictionWarehouse> wrapper = new LambdaQueryWrapper<>();
+        if (!Cools.isEmpty(condition)) {
+            wrapper.like(MatnrRestrictionWarehouse::getId, condition);
+        }
+        matnrRestrictionWarehouseService.page(new Page<>(1, 30), wrapper).getRecords().forEach(
+                item -> vos.add(new KeyValVo(item.getId(), item.getId()))
+        );
+        return R.ok().add(vos);
+    }
+
+    @PreAuthorize("hasAuthority('manager:matnrRestrictionWarehouse:list')")
+    @PostMapping("/matnrRestrictionWarehouse/export")
+    public void export(@RequestBody Map<String, Object> map, HttpServletResponse response) throws Exception {
+        ExcelUtil.build(ExcelUtil.create(matnrRestrictionWarehouseService.list(), MatnrRestrictionWarehouse.class), response);
+    }
+
+}
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/manager/controller/params/GenerateTaskParams.java b/rsf-server/src/main/java/com/vincent/rsf/server/manager/controller/params/GenerateTaskParams.java
index a2b5e26..a03fab1 100644
--- a/rsf-server/src/main/java/com/vincent/rsf/server/manager/controller/params/GenerateTaskParams.java
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/manager/controller/params/GenerateTaskParams.java
@@ -27,6 +27,10 @@
     @ApiModelProperty("绔欑偣ID")
     public Long siteId;
 
+    @ApiModelProperty("绔欑偣鍚嶇О")
+    public String siteNo;
+
+
     @ApiModelProperty("搴撲綅缂栫爜")
     public String locCode;
 }
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/manager/controller/params/WaitPakinParam.java b/rsf-server/src/main/java/com/vincent/rsf/server/manager/controller/params/WaitPakinParam.java
index 24f1740..a45f671 100644
--- a/rsf-server/src/main/java/com/vincent/rsf/server/manager/controller/params/WaitPakinParam.java
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/manager/controller/params/WaitPakinParam.java
@@ -13,7 +13,7 @@
 @ApiModel(value = "WaitPakinParam", description = "缁勬嫋鍙傛暟")
 public class WaitPakinParam implements Serializable {
 
-    @ApiModelProperty("鎷栫洏鐮�")
+    @ApiModelProperty("鎵樼洏鐮�")
     private String barcode;
 
     @ApiModelProperty("璺熻釜鐮�")
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/manager/entity/BasContainer.java b/rsf-server/src/main/java/com/vincent/rsf/server/manager/entity/BasContainer.java
index 25b5b78..36d321a 100644
--- a/rsf-server/src/main/java/com/vincent/rsf/server/manager/entity/BasContainer.java
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/manager/entity/BasContainer.java
@@ -52,9 +52,9 @@
     private Long containerType;
 
     /**
-     * 瀹瑰櫒鏉$爜绫诲瀷
+     * 瀹瑰櫒鏉$爜瑙勫垯
      */
-    @ApiModelProperty(value = "瀹瑰櫒鏉$爜绫诲瀷")
+    @ApiModelProperty(value = "瀹瑰櫒鏉$爜瑙勫垯")
     private String codeType;
 
     /**
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/manager/entity/BasStation.java b/rsf-server/src/main/java/com/vincent/rsf/server/manager/entity/BasStation.java
index 34cd75c..2bce886 100644
--- a/rsf-server/src/main/java/com/vincent/rsf/server/manager/entity/BasStation.java
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/manager/entity/BasStation.java
@@ -193,6 +193,12 @@
     @ApiModelProperty(value = "浠撳簱鍚嶇О")
     private String productionLineName;
 
+    /**
+     * 浠撳簱鍚嶇О
+     */
+    @ApiModelProperty(value = "浠撳簱鍚嶇О")
+    private String stationTypeCode;
+
     public BasStation() {
     }
 
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/manager/entity/BasStationType.java b/rsf-server/src/main/java/com/vincent/rsf/server/manager/entity/BasStationType.java
new file mode 100644
index 0000000..89d3b47
--- /dev/null
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/manager/entity/BasStationType.java
@@ -0,0 +1,188 @@
+package com.vincent.rsf.server.manager.entity;
+
+import com.baomidou.mybatisplus.annotation.TableLogic;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableLogic;
+import com.baomidou.mybatisplus.annotation.TableName;
+import com.fasterxml.jackson.annotation.JsonFormat;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import com.vincent.rsf.framework.common.Cools;
+import com.vincent.rsf.framework.common.SpringUtils;
+import com.vincent.rsf.server.system.service.UserService;
+import com.vincent.rsf.server.system.entity.User;
+import org.springframework.format.annotation.DateTimeFormat;
+
+import java.io.Serializable;
+import java.util.Date;
+import java.util.List;
+
+@Data
+@TableName("man_bas_station_type")
+public class BasStationType implements Serializable {
+
+    private static final long serialVersionUID = 1L;
+
+    /**
+     * id
+     */
+    @ApiModelProperty(value= "id")
+    @TableId(value = "id", type = IdType.AUTO)
+    private Long id;
+
+    /**
+     * 缂栫爜
+     */
+    @ApiModelProperty(value= "缂栫爜")
+    private String stationTypeCode;
+
+    /**
+     * 鍚嶇О
+     */
+    @ApiModelProperty(value= "鍚嶇О")
+    private String stationTypeName;
+
+    /**
+     * 鐘舵��
+     */
+    @ApiModelProperty(value= "鐘舵��")
+    private Integer status;
+
+    /**
+     * 鍏ㄦ澘鍑哄簱
+     */
+    @ApiModelProperty(value= "鍏ㄦ澘鍑哄簱")
+    private Integer allowFullPalletOut;
+
+    /**
+     * 绌烘澘鍑哄簱
+     */
+    @ApiModelProperty(value= "绌烘澘鍑哄簱")
+    private Integer allowEmptyPalletOut;
+
+    /**
+     * 鎷i��
+     */
+    @ApiModelProperty(value= "鎷i��")
+    private Integer allowPick;
+
+    /**
+     * 鍏ュ簱
+     */
+    @ApiModelProperty(value= "鍏ュ簱")
+    private Integer allowFullPalletIn;
+
+    /**
+     * 绌烘澘鍏ュ簱
+     */
+    @ApiModelProperty(value= "绌烘澘鍏ュ簱")
+    private Integer allowEmptyPalletIn;
+
+    /**
+     * 杈撻�佺嚎
+     */
+    @ApiModelProperty(value= "杈撻�佺嚎")
+    private Integer conveyorLine;
+
+    /**
+     * 鍦伴潰绔�
+     */
+    @ApiModelProperty(value= "鍦伴潰绔�")
+    private Integer allowGroundStation;
+
+    /**
+     * 鍦伴潰鏉$爜绔�
+     */
+    @ApiModelProperty(value= "鍦伴潰鏉$爜绔�")
+    private Integer allowGroundBarcodeStation;
+
+    @ApiModelProperty(value= "")
+    @TableLogic
+    private Integer deleted;
+
+    @ApiModelProperty(value= "")
+    private Long tenantId;
+
+    @ApiModelProperty(value= "绫诲瀷闆嗗悎")
+    private List<String> taskType;
+
+
+    /**
+     * 娣诲姞浜哄憳
+     */
+    @ApiModelProperty(value= "娣诲姞浜哄憳")
+    private Long createBy;
+
+    /**
+     * 娣诲姞鏃堕棿
+     */
+    @ApiModelProperty(value= "娣诲姞鏃堕棿")
+    @DateTimeFormat(pattern="yyyy-MM-dd HH:mm:ss")
+    @JsonFormat(pattern="yyyy-MM-dd HH:mm:ss",timezone = "GMT+8")
+    private Date createTime;
+
+    /**
+     * 淇敼浜哄憳
+     */
+    @ApiModelProperty(value= "淇敼浜哄憳")
+    private Long updateBy;
+
+    /**
+     * 淇敼鏃堕棿
+     */
+    @ApiModelProperty(value= "淇敼鏃堕棿")
+    @DateTimeFormat(pattern="yyyy-MM-dd HH:mm:ss")
+    @JsonFormat(pattern="yyyy-MM-dd HH:mm:ss",timezone = "GMT+8")
+    private Date updateTime;
+    public BasStationType() {}
+
+    public BasStationType(String stationTypeCode,String stationTypeName,Integer status,Integer allowFullPalletOut,Integer allowEmptyPalletOut,Integer allowPick,Integer allowFullPalletIn,Integer allowEmptyPalletIn,Integer conveyorLine,Integer allowGroundStation,Integer allowGroundBarcodeStation,Integer deleted,Long tenantId) {
+        this.stationTypeCode = stationTypeCode;
+        this.stationTypeName = stationTypeName;
+        this.status = status;
+        this.allowFullPalletOut = allowFullPalletOut;
+        this.allowEmptyPalletOut = allowEmptyPalletOut;
+        this.allowPick = allowPick;
+        this.allowFullPalletIn = allowFullPalletIn;
+        this.allowEmptyPalletIn = allowEmptyPalletIn;
+        this.conveyorLine = conveyorLine;
+        this.allowGroundStation = allowGroundStation;
+        this.allowGroundBarcodeStation = allowGroundBarcodeStation;
+        this.deleted = deleted;
+        this.tenantId = tenantId;
+    }
+
+//    BasStationType basStationType = new BasStationType(
+//            null,    // 缂栫爜
+//            null,    // 鍚嶇О
+//            null,    // 鐘舵��
+//            null,    // 鍏ㄦ澘鍑哄簱
+//            null,    // 绌烘澘鍑哄簱
+//            null,    // 鎷i��
+//            null,    // 鍏ュ簱
+//            null,    // 绌烘澘鍏ュ簱
+//            null,    // 杈撻�佺嚎
+//            null,    // 鍦伴潰绔�
+//            null,    // 鍦伴潰鏉$爜绔�
+//            null,    // 
+//            null    // 
+//    );
+
+
+
+    public Boolean getStatusBool(){
+        if (null == this.status){ return null; }
+        switch (this.status){
+            case 1:
+                return true;
+            case 0:
+                return false;
+            default:
+                return null;
+        }
+    }
+
+}
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/manager/entity/Matnr.java b/rsf-server/src/main/java/com/vincent/rsf/server/manager/entity/Matnr.java
index 9444d95..3bc67ce 100644
--- a/rsf-server/src/main/java/com/vincent/rsf/server/manager/entity/Matnr.java
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/manager/entity/Matnr.java
@@ -5,6 +5,7 @@
 import java.text.SimpleDateFormat;
 import java.util.*;
 
+import com.baomidou.mybatisplus.extension.handlers.JacksonTypeHandler;
 import com.fasterxml.jackson.annotation.JsonFormat;
 import com.vincent.rsf.server.manager.service.BatchRegularService;
 import com.vincent.rsf.server.manager.service.CompanysService;
@@ -29,7 +30,7 @@
 import java.util.Date;
 
 @Data
-@TableName("man_matnr")
+@TableName(value = "man_matnr", autoResultMap = true)
 @Accessors(chain = true)
 @ApiModel(value = "Matnr", description = "鐗╂枡鎵�鏈夊熀纭�灞炴��")
 public class Matnr implements Serializable {
@@ -277,6 +278,19 @@
     private String erpClsId;
 
     /**
+     * 浠撳簱闄愬埗鍚嶇О
+     */
+    @ApiModelProperty(value= "浠撳簱闄愬埗缂栫爜")
+    private String warehouseRestrictionCode;
+
+    /**
+     * 瀹瑰櫒绫诲瀷
+     */
+    @ApiModelProperty(value= "瀹瑰櫒绫诲瀷闆嗗悎")
+    @TableField(typeHandler = JacksonTypeHandler.class)
+    private List<Integer> containerTypes;
+
+    /**
      * 澶囨敞
      */
     @ApiModelProperty(value= "鍒嗙被鍒楄〃")
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/manager/entity/MatnrRestrictionWarehouse.java b/rsf-server/src/main/java/com/vincent/rsf/server/manager/entity/MatnrRestrictionWarehouse.java
new file mode 100644
index 0000000..78ec887
--- /dev/null
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/manager/entity/MatnrRestrictionWarehouse.java
@@ -0,0 +1,106 @@
+package com.vincent.rsf.server.manager.entity;
+
+import com.baomidou.mybatisplus.annotation.*;
+
+import com.baomidou.mybatisplus.annotation.TableLogic;
+import com.baomidou.mybatisplus.extension.handlers.JacksonTypeHandler;
+import com.fasterxml.jackson.annotation.JsonFormat;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import com.vincent.rsf.framework.common.Cools;
+import com.vincent.rsf.framework.common.SpringUtils;
+import com.vincent.rsf.server.system.service.UserService;
+import com.vincent.rsf.server.system.entity.User;
+import org.springframework.format.annotation.DateTimeFormat;
+
+import java.io.Serializable;
+import java.util.Date;
+import java.util.List;
+
+@Data
+@TableName(value = "man_matnr_restriction_warehouse", autoResultMap = true)
+public class MatnrRestrictionWarehouse implements Serializable {
+
+    private static final long serialVersionUID = 1L;
+
+    /**
+     * id
+     */
+    @ApiModelProperty(value= "id")
+    @TableId(value = "id", type = IdType.AUTO)
+    private Long id;
+
+    /**
+     * 浠撳簱缂栫爜
+     */
+    @ApiModelProperty(value= "浠撳簱缂栫爜")
+    @TableField(typeHandler = JacksonTypeHandler.class)
+    private List<Integer> productionLineCode;
+
+    /**
+     * 浠撳簱
+     */
+    @ApiModelProperty(value= "浠撳簱")
+    @TableField(typeHandler = JacksonTypeHandler.class)
+    private List<String> productionLineName;
+
+    /**
+     * 闄愬埗缂栫爜
+     */
+    @ApiModelProperty(value= "闄愬埗缂栫爜")
+    private String matnrRestrictionCode;
+
+    @ApiModelProperty(value= "")
+    private Integer status;
+
+    @ApiModelProperty(value= "")
+    private Long tenantId;
+
+    @ApiModelProperty(value= "")
+    @TableLogic
+    private Integer deleted;
+
+    /**
+     * 娣诲姞浜哄憳
+     */
+    @ApiModelProperty(value= "娣诲姞浜哄憳")
+    private Long createBy;
+
+    /**
+     * 娣诲姞鏃堕棿
+     */
+    @ApiModelProperty(value= "娣诲姞鏃堕棿")
+    @DateTimeFormat(pattern="yyyy-MM-dd HH:mm:ss")
+    @JsonFormat(pattern="yyyy-MM-dd HH:mm:ss",timezone = "GMT+8")
+    private Date createTime;
+
+    /**
+     * 淇敼浜哄憳
+     */
+    @ApiModelProperty(value= "淇敼浜哄憳")
+    private Long updateBy;
+
+    /**
+     * 淇敼鏃堕棿
+     */
+    @ApiModelProperty(value= "淇敼鏃堕棿")
+    @DateTimeFormat(pattern="yyyy-MM-dd HH:mm:ss")
+    @JsonFormat(pattern="yyyy-MM-dd HH:mm:ss",timezone = "GMT+8")
+    private Date updateTime;
+
+    public MatnrRestrictionWarehouse() {}
+
+    public Boolean getStatusBool(){
+        if (null == this.status){ return null; }
+        switch (this.status){
+            case 1:
+                return true;
+            case 0:
+                return false;
+            default:
+                return null;
+        }
+    }
+
+}
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/manager/enums/TaskType.java b/rsf-server/src/main/java/com/vincent/rsf/server/manager/enums/TaskType.java
index f261d38..741dca8 100644
--- a/rsf-server/src/main/java/com/vincent/rsf/server/manager/enums/TaskType.java
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/manager/enums/TaskType.java
@@ -40,6 +40,8 @@
             return TaskType.TASK_TYPE_IN.desc;
         } else if (TaskType.TASK_TYPE_EMPTY_IN.type.equals(type)) {
             return TaskType.TASK_TYPE_EMPTY_IN.desc;
+        } else if (TaskType.TASK_TYPE_LOC_MOVE.type.equals(type)) {
+            return TaskType.TASK_TYPE_LOC_MOVE.desc;
         } else if (TaskType.TASK_TYPE_OUT.type.equals(type)) {
             return TaskType.TASK_TYPE_OUT.desc;
         } else if (TaskType.TASK_TYPE_PICK_IN.type.equals(type)) {
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/manager/mapper/BasStationTypeMapper.java b/rsf-server/src/main/java/com/vincent/rsf/server/manager/mapper/BasStationTypeMapper.java
new file mode 100644
index 0000000..8336995
--- /dev/null
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/manager/mapper/BasStationTypeMapper.java
@@ -0,0 +1,12 @@
+package com.vincent.rsf.server.manager.mapper;
+
+import com.vincent.rsf.server.manager.entity.BasStationType;
+import com.baomidou.mybatisplus.core.mapper.BaseMapper;
+import org.apache.ibatis.annotations.Mapper;
+import org.springframework.stereotype.Repository;
+
+@Mapper
+@Repository
+public interface BasStationTypeMapper extends BaseMapper<BasStationType> {
+
+}
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/manager/mapper/MatnrRestrictionWarehouseMapper.java b/rsf-server/src/main/java/com/vincent/rsf/server/manager/mapper/MatnrRestrictionWarehouseMapper.java
new file mode 100644
index 0000000..2469ab5
--- /dev/null
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/manager/mapper/MatnrRestrictionWarehouseMapper.java
@@ -0,0 +1,12 @@
+package com.vincent.rsf.server.manager.mapper;
+
+import com.vincent.rsf.server.manager.entity.MatnrRestrictionWarehouse;
+import com.baomidou.mybatisplus.core.mapper.BaseMapper;
+import org.apache.ibatis.annotations.Mapper;
+import org.springframework.stereotype.Repository;
+
+@Mapper
+@Repository
+public interface MatnrRestrictionWarehouseMapper extends BaseMapper<MatnrRestrictionWarehouse> {
+
+}
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/manager/schedules/AutoRunSchedules.java b/rsf-server/src/main/java/com/vincent/rsf/server/manager/schedules/AutoRunSchedules.java
index 12add74..e5b357e 100644
--- a/rsf-server/src/main/java/com/vincent/rsf/server/manager/schedules/AutoRunSchedules.java
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/manager/schedules/AutoRunSchedules.java
@@ -14,6 +14,7 @@
 import com.vincent.rsf.server.manager.enums.TaskStsType;
 import com.vincent.rsf.server.manager.enums.TaskType;
 import com.vincent.rsf.server.manager.service.*;
+import com.vincent.rsf.server.manager.utils.WarehouseLocationRetrievalUtil;
 import com.vincent.rsf.server.system.constant.GlobalConfigCode;
 import com.vincent.rsf.server.system.entity.Config;
 import com.vincent.rsf.server.system.service.ConfigService;
@@ -221,32 +222,33 @@
                 });
                 List<BasStation> stations = stationService.list(new LambdaQueryWrapper<BasStation>()
                         .eq(BasStation::getStatus, 1)
-                        .eq(BasStation::getUseStatus, LocStsType.LOC_STS_TYPE_O.type));
+                );
+//                        .eq(BasStation::getUseStatus, LocStsType.LOC_STS_TYPE_O.type)
                 List<String> stationNames = stations.stream().map(BasStation::getStationName).collect(Collectors.toList());
                 if (Cools.isEmpty(stations)) {
                     throw new CoolException("鏃犲彲鐢ㄧ珯鐐癸紒锛�");
                 }
-                DeviceSite deviceSite = deviceSiteService.getOne(new LambdaQueryWrapper<DeviceSite>()
-                        .in(DeviceSite::getSite, stationNames)
-                        .eq(DeviceSite::getType, TaskType.TASK_TYPE_CHECK_OUT.type).last("limit 1"));
-                if (Cools.isEmpty(deviceSite)) {
-                    throw new CoolException("鏃犲彲鐢ㄨ矾寰勶紒锛�");
-                }
-                //鐢熸垚鐩樼偣浠诲姟鍙傛暟
-                LocToTaskParams locToTaskParams = new LocToTaskParams();
-                locToTaskParams.setType(Constants.TASK_TYPE_OUT_CHECK)
-                        .setItems(locItems)
-                        .setSiteNo(deviceSite.getSite())
-                        .setOrgLoc(loc.getCode());
+                for (String stationName : stationNames) {
+                    boolean isItAvailable = new WarehouseLocationRetrievalUtil().queryPathIsItAvailableOutArea(loc.getAreaId(), stationName, loc.getBarcode(), TaskType.TASK_TYPE_CHECK_OUT.type);
+                    if (!isItAvailable) {
+                        continue;
+                    }
+                    //鐢熸垚鐩樼偣浠诲姟鍙傛暟
+                    LocToTaskParams locToTaskParams = new LocToTaskParams();
+                    locToTaskParams.setType(Constants.TASK_TYPE_OUT_CHECK)
+                            .setItems(locItems)
+                            .setSiteNo(stationName)
+                            .setOrgLoc(loc.getCode());
 
-                List<Task> tasks = taskService.list(new LambdaQueryWrapper<Task>().eq(Task::getTargSite, deviceSite.getSite()));
-                if (!tasks.isEmpty()) {
-                    continue;
-                }
-                try {
-                    locItemService.generateTask(TaskResouceType.TASK_RESOUCE_CHECK_TYPE.val, locToTaskParams, getLoginUserId());
-                } catch (Exception e) {
-                    throw new CoolException(e.getMessage());
+                    List<Task> tasks = taskService.list(new LambdaQueryWrapper<Task>().eq(Task::getTargSite, stationName));
+                    if (!tasks.isEmpty()) {
+                        continue;
+                    }
+                    try {
+                        locItemService.generateTask(TaskResouceType.TASK_RESOUCE_CHECK_TYPE.val, locToTaskParams, getLoginUserId());
+                    } catch (Exception e) {
+                        throw new CoolException(e.getMessage());
+                    }
                 }
             }
         }
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/manager/schedules/TaskMissionSchedules.java b/rsf-server/src/main/java/com/vincent/rsf/server/manager/schedules/TaskMissionSchedules.java
index d73e80d..9b14e17 100644
--- a/rsf-server/src/main/java/com/vincent/rsf/server/manager/schedules/TaskMissionSchedules.java
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/manager/schedules/TaskMissionSchedules.java
@@ -13,6 +13,7 @@
 import com.vincent.rsf.server.manager.service.impl.BasStationAreaServiceImpl;
 import com.vincent.rsf.server.manager.service.impl.BasStationServiceImpl;
 import com.vincent.rsf.server.manager.service.impl.DeviceSiteServiceImpl;
+import com.vincent.rsf.server.manager.utils.WarehouseLocationRetrievalUtil;
 import com.vincent.rsf.server.system.constant.GlobalConfigCode;
 import com.vincent.rsf.server.system.entity.*;
 import com.vincent.rsf.server.system.service.ConfigService;
@@ -132,9 +133,21 @@
                 Loc loc2 = locService.getOne(new LambdaQueryWrapper<Loc>().eq(Loc::getCode, task.getOrgLoc()));
                 sou = loc2.getAreaId().toString();
             }
-            List<TaskPathTemplateMerge> taskPathTemplateMergeList = taskPathTemplateMergeService.list(new LambdaQueryWrapper<TaskPathTemplateMerge>().eq(TaskPathTemplateMerge::getSourceType, sou).eq(TaskPathTemplateMerge::getTargetType, end));
+            BasContainer containerByBarcode = new WarehouseLocationRetrievalUtil().getContainerByBarcode(task.getBarcode());
+            List<TaskPathTemplateMerge> taskPathTemplateMergeList = taskPathTemplateMergeService.list(
+                    new LambdaQueryWrapper<TaskPathTemplateMerge>()
+                            .eq(TaskPathTemplateMerge::getSourceType, sou)
+                            .eq(TaskPathTemplateMerge::getTargetType, end)
+                            .apply("container_type != '[]'")  // 涓嶆槸绌烘暟缁�
+                            .apply("JSON_CONTAINS(container_type, {0}) = 1", containerByBarcode.getContainerType().toString())
+            );
             if (Objects.isNull(taskPathTemplateMergeList) || taskPathTemplateMergeList.isEmpty() || !endSign) {
-                List<TaskPathTemplateMerge> list = taskPathTemplateMergeService.list(new LambdaQueryWrapper<TaskPathTemplateMerge>().eq(TaskPathTemplateMerge::getStepSize,1));
+                List<TaskPathTemplateMerge> list = taskPathTemplateMergeService.list(
+                        new LambdaQueryWrapper<TaskPathTemplateMerge>()
+                                .eq(TaskPathTemplateMerge::getStepSize,1)
+                                .apply("container_type != '[]'")  // 涓嶆槸绌烘暟缁�
+                                .apply("JSON_CONTAINS(container_type, {0}) = 1", containerByBarcode.getContainerType().toString())
+                );
                 if (!Cools.isEmpty(list)) {
                     List<String[]> stationList = new ArrayList<>();
                     list.forEach(taskPathTemplate -> {
@@ -196,11 +209,8 @@
                                     if (!siteListRoute.isEmpty()) {
                                         for (String[] siteArray : siteListRoute) {
                                             //鍑哄簱璺緞鎺掓煡
-                                            DeviceSite deviceSite = deviceSiteService.getOne(new LambdaQueryWrapper<DeviceSite>()
-                                                    .eq(DeviceSite::getSite, siteArray[1])
-                                                    .eq(!Objects.isNull(loc.getChannel()),DeviceSite::getChannel, loc.getChannel())
-                                                    .eq(DeviceSite::getType, task.getTaskType()).last("limit 1"),false);
-                                            if (!Objects.isNull(deviceSite)) {
+                                            boolean available = new WarehouseLocationRetrievalUtil().queryPathIsItAvailableOutArea(loc.getAreaId().toString(), siteArray[1], loc.getBarcode(),"out");
+                                            if (available) {
                                                 BasStation basStation = basStationService.getOne(new LambdaQueryWrapper<BasStation>()
                                                         .eq(BasStation::getStationName, siteArray[1])
                                                         .eq(BasStation::getUseStatus, LocStsType.LOC_STS_TYPE_O.type)
@@ -218,7 +228,6 @@
                                 }
                             }
                         }
-
                     }
 //                    System.out.println("浠诲姟锛�"+task.getTaskCode()+"鏌ヨ姝ュ簭涓猴細"+longs);
                 }
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/manager/schedules/TaskSchedules.java b/rsf-server/src/main/java/com/vincent/rsf/server/manager/schedules/TaskSchedules.java
index 2df0126..914d8d2 100644
--- a/rsf-server/src/main/java/com/vincent/rsf/server/manager/schedules/TaskSchedules.java
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/manager/schedules/TaskSchedules.java
@@ -26,6 +26,7 @@
 import com.vincent.rsf.server.manager.entity.*;
 import com.vincent.rsf.server.manager.service.*;
 import com.vincent.rsf.server.manager.service.impl.LocServiceImpl;
+import com.vincent.rsf.server.manager.utils.WarehouseLocationRetrievalUtil;
 import com.vincent.rsf.server.system.constant.GlobalConfigCode;
 import com.vincent.rsf.server.system.constant.SerialRuleCode;
 import com.vincent.rsf.server.system.entity.*;
@@ -179,43 +180,11 @@
                     MissionTaskIssueParam missionTaskIssueParam = new MissionTaskIssueParam(flowStepInstance,subsystemFlowTemplate,flowStepTemplate);
 
                     missionTaskIssueParam.setType(RcsTaskType.getTypeDesc(task.getTaskType()));
-                    boolean souSign = taskInstance.getSourceCode().matches("\\d+");
+                    boolean souSign = new WarehouseLocationRetrievalUtil().retrieveMissionmMergeReservoirAreaIsItAvailable(taskInstance.getSourceCode());
                     if (souSign){
-                        WarehouseAreas warehouseAreas = warehouseAreasService.getById(Long.parseLong(taskInstance.getSourceCode()));
-                        if (Cools.isEmpty(warehouseAreas)){
-                            BasStation basStation = basStationService.getOne(new LambdaQueryWrapper<BasStation>().eq(BasStation::getStationName, taskInstance.getSourceCode()).last("limit 1"));
-                            if (Cools.isEmpty(basStation)){
-                                basStation = basStationService.getOne(new LambdaQueryWrapper<BasStation>()
-                                        .apply("station_alias != '[]'")  // 涓嶆槸绌烘暟缁�
-                                        .apply("JSON_CONTAINS(station_alias, '\"{0}\"') = 1", taskInstance.getSourceCode())
-                                        .eq(BasStation::getDeleted, 0)  // 閫氬父闇�瑕佸姞涓婃湭鍒犻櫎鏉′欢
-                                        .last("LIMIT 1"));
-                            }
-                            if (Cools.isEmpty(basStation)){
-                                flowStepInstance.setRetryTimes(flowStepInstance.getRetryTimes() + 1);
-                                if (flowStepInstance.getRetryTimes()>5){
-                                    flowStepInstance.setStatus((short)4);
-                                    flowStepInstanceService.updateById(flowStepInstance);
-                                    log.error("浠诲姟涓嬪彂澶辫触,婧愮偣鏈煡璇㈠埌锛岄噸璇曟鏁板ぇ浜庣瓑浜庝簲娆★紝鏍囪涓哄け璐ワ紒锛侊紒");
-                                } else {
-                                    flowStepInstanceService.updateById(flowStepInstance);
-                                    log.error("浠诲姟涓嬪彂澶辫触,婧愮偣鏈煡璇㈠埌鐩爣鐐规湭鏌ヨ鍒帮紝绛夊緟閲嶈瘯....");
-                                }
-                                continue;
-                            } else {
-                                missionTaskIssueParam.setSourceCode(basStation.getStationName());
-                            }
-                        } else {
-                            missionTaskIssueParam.setSourceCode(taskInstance.getSourceCode());
-                        }
+                        missionTaskIssueParam.setSourceCode(taskInstance.getSourceCode());
                     } else {
-                        BasStation basStation = basStationService.getOne(new LambdaQueryWrapper<BasStation>().eq(BasStation::getStationName, taskInstance.getSourceCode()).last("limit 1"));
-                        if (Cools.isEmpty(basStation)){
-                            basStation = basStationService.getOne(new LambdaQueryWrapper<BasStation>()
-                                    .apply("station_alias != '[]'")  // 涓嶆槸绌烘暟缁�
-                                    .apply("JSON_CONTAINS(station_alias, '\"{0}\"') = 1", taskInstance.getSourceCode())
-                                    .eq(BasStation::getDeleted, 0)  // 閫氬父闇�瑕佸姞涓婃湭鍒犻櫎鏉′欢
-                                    .last("LIMIT 1"));                            }
+                        BasStation basStation = new WarehouseLocationRetrievalUtil().retrieveMissionmMergeSizeIsItAvailable(taskInstance.getSourceCode());
                         if (Cools.isEmpty(basStation)){
                             flowStepInstance.setRetryTimes(flowStepInstance.getRetryTimes() + 1);
                             if (flowStepInstance.getRetryTimes()>5){
@@ -231,52 +200,20 @@
                             missionTaskIssueParam.setSourceCode(basStation.getStationName());
                         }
                     }
-                    boolean endSign = taskInstance.getTargetCode().matches("\\d+");
+                    boolean endSign = new WarehouseLocationRetrievalUtil().retrieveMissionmMergeReservoirAreaIsItAvailable(taskInstance.getTargetCode());
                     if (endSign){
-                        WarehouseAreas warehouseAreas = warehouseAreasService.getById(Long.parseLong(taskInstance.getTargetCode()));
-                        if (Cools.isEmpty(warehouseAreas)){
-                            BasStation basStation = basStationService.getOne(new LambdaQueryWrapper<BasStation>().eq(BasStation::getStationName, taskInstance.getTargetCode()).last("limit 1"));
-                            if (Cools.isEmpty(basStation)){
-                                basStation = basStationService.getOne(new LambdaQueryWrapper<BasStation>()
-                                        .apply("station_alias != '[]'")  // 涓嶆槸绌烘暟缁�
-                                        .apply("JSON_CONTAINS(station_alias, '\"{0}\"') = 1", taskInstance.getTargetCode())
-                                        .eq(BasStation::getDeleted, 0)  // 閫氬父闇�瑕佸姞涓婃湭鍒犻櫎鏉′欢
-                                        .last("LIMIT 1"));                                }
-                            if (Cools.isEmpty(basStation)){
-                                flowStepInstance.setRetryTimes(flowStepInstance.getRetryTimes() + 1);
-                                if (flowStepInstance.getRetryTimes()>5){
-                                    flowStepInstance.setStatus((short)4);
-                                    flowStepInstanceService.updateById(flowStepInstance);
-                                    log.error("浠诲姟涓嬪彂澶辫触,鐩爣鐐规湭鏌ヨ鍒帮紝閲嶈瘯娆℃暟澶т簬绛変簬浜旀锛屾爣璁颁负澶辫触锛侊紒锛�");
-                                } else {
-                                    flowStepInstanceService.updateById(flowStepInstance);
-                                    log.error("浠诲姟涓嬪彂澶辫触,鐩爣鐐规湭鏌ヨ鍒帮紝绛夊緟閲嶈瘯....");
-                                }
-                                continue;
-                            } else {
-                                missionTaskIssueParam.setTargetCode(basStation.getStationName());
-                            }
-
-                        } else {
-                            missionTaskIssueParam.setTargetCode(taskInstance.getTargetCode());
-                        }
+                        missionTaskIssueParam.setTargetCode(taskInstance.getTargetCode());
                     } else {
-                        BasStation basStation = basStationService.getOne(new LambdaQueryWrapper<BasStation>().eq(BasStation::getStationName, taskInstance.getTargetCode()).last("limit 1"));
-                        if (Cools.isEmpty(basStation)){
-                            basStation = basStationService.getOne(new LambdaQueryWrapper<BasStation>()
-                                    .apply("station_alias != '[]'")  // 涓嶆槸绌烘暟缁�
-                                    .apply("JSON_CONTAINS(station_alias, '\"{0}\"') = 1", taskInstance.getTargetCode())
-                                    .eq(BasStation::getDeleted, 0)  // 閫氬父闇�瑕佸姞涓婃湭鍒犻櫎鏉′欢
-                                    .last("LIMIT 1"));                                  }
+                        BasStation basStation = new WarehouseLocationRetrievalUtil().retrieveMissionmMergeSizeIsItAvailable(taskInstance.getTargetCode());
                         if (Cools.isEmpty(basStation)){
                             flowStepInstance.setRetryTimes(flowStepInstance.getRetryTimes() + 1);
                             if (flowStepInstance.getRetryTimes()>5){
                                 flowStepInstance.setStatus((short)4);
                                 flowStepInstanceService.updateById(flowStepInstance);
-                                log.error("浠诲姟涓嬪彂澶辫触,鐩爣鐐规湭鏌ヨ鍒帮紝閲嶈瘯娆℃暟澶т簬绛変簬浜旀锛屾爣璁颁负澶辫触锛侊紒锛�");
+                                log.error("浠诲姟涓嬪彂澶辫触,婧愮偣鏈煡璇㈠埌锛岄噸璇曟鏁板ぇ浜庣瓑浜庝簲娆★紝鏍囪涓哄け璐ワ紒锛侊紒");
                             } else {
                                 flowStepInstanceService.updateById(flowStepInstance);
-                                log.error("浠诲姟涓嬪彂澶辫触,鐩爣鐐规湭鏌ヨ鍒帮紝绛夊緟閲嶈瘯....");
+                                log.error("浠诲姟涓嬪彂澶辫触,婧愮偣鏈煡璇㈠埌鐩爣鐐规湭鏌ヨ鍒帮紝绛夊緟閲嶈瘯....");
                             }
                             continue;
                         } else {
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/BasStationTypeService.java b/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/BasStationTypeService.java
new file mode 100644
index 0000000..afcfceb
--- /dev/null
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/BasStationTypeService.java
@@ -0,0 +1,8 @@
+package com.vincent.rsf.server.manager.service;
+
+import com.baomidou.mybatisplus.extension.service.IService;
+import com.vincent.rsf.server.manager.entity.BasStationType;
+
+public interface BasStationTypeService extends IService<BasStationType> {
+
+}
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/MatnrRestrictionWarehouseService.java b/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/MatnrRestrictionWarehouseService.java
new file mode 100644
index 0000000..eb9750c
--- /dev/null
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/MatnrRestrictionWarehouseService.java
@@ -0,0 +1,8 @@
+package com.vincent.rsf.server.manager.service;
+
+import com.baomidou.mybatisplus.extension.service.IService;
+import com.vincent.rsf.server.manager.entity.MatnrRestrictionWarehouse;
+
+public interface MatnrRestrictionWarehouseService extends IService<MatnrRestrictionWarehouse> {
+
+}
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/TaskService.java b/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/TaskService.java
index 0eb22b1..fcbbb09 100644
--- a/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/TaskService.java
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/TaskService.java
@@ -14,7 +14,7 @@
 
     R generateFlatWarehouseTasks(WaitPakin waitPakins, String locCode, Long loginUserId);
 
-    R generateAGVTasks(WaitPakin waitPakins, String locCode, String orgSta, String targSite, Long loginUserId);
+    R generateAGVTasks(WaitPakin waitPakins, String locCode, String orgSta, Long loginUserId,String areaId);
 
     void completeTask(List<Task> task) throws Exception;
 
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/BasStationTypeServiceImpl.java b/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/BasStationTypeServiceImpl.java
new file mode 100644
index 0000000..cd516fc
--- /dev/null
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/BasStationTypeServiceImpl.java
@@ -0,0 +1,12 @@
+package com.vincent.rsf.server.manager.service.impl;
+
+import com.vincent.rsf.server.manager.mapper.BasStationTypeMapper;
+import com.vincent.rsf.server.manager.entity.BasStationType;
+import com.vincent.rsf.server.manager.service.BasStationTypeService;
+import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
+import org.springframework.stereotype.Service;
+
+@Service("basStationTypeService")
+public class BasStationTypeServiceImpl extends ServiceImpl<BasStationTypeMapper, BasStationType> implements BasStationTypeService {
+
+}
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/CheckOrderServiceImpl.java b/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/CheckOrderServiceImpl.java
index f8631b8..8067c39 100644
--- a/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/CheckOrderServiceImpl.java
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/CheckOrderServiceImpl.java
@@ -12,6 +12,7 @@
 import com.vincent.rsf.server.manager.entity.*;
 import com.vincent.rsf.server.manager.entity.excel.CheckOrderTemplate;
 import com.vincent.rsf.server.manager.enums.*;
+import com.vincent.rsf.server.manager.mapper.BasStationTypeMapper;
 import com.vincent.rsf.server.manager.mapper.CheckOrderMapper;
 import com.vincent.rsf.server.manager.service.*;
 import com.vincent.rsf.server.system.constant.SerialRuleCode;
@@ -45,6 +46,12 @@
     private LocServiceImpl locService;
     @Autowired
     private TaskItemServiceImpl taskItemService;
+    @Autowired
+    private BasStationTypeMapper basStationTypeMapper;
+    @Autowired
+    private BasStationTypeServiceImpl basStationTypeService;
+    @Autowired
+    private BasStationServiceImpl basStationService;
 
     /**
      * @author Ryan
@@ -212,8 +219,18 @@
     @Override
     public R getSiteNos() {
         List<Integer> list = Arrays.asList(TaskType.TASK_TYPE_CHECK_OUT.type, TaskType.TASK_TYPE_CHECK_IN.type);
-        List<DeviceSite> sites = deviceSiteService.list(new LambdaQueryWrapper<DeviceSite>().in(DeviceSite::getType, list).groupBy(DeviceSite::getSite));
-        return R.ok().add(sites);
+//        List<DeviceSite> sites = deviceSiteService.list(new LambdaQueryWrapper<DeviceSite>().in(DeviceSite::getType, list).groupBy(DeviceSite::getSite));
+        List<BasStationType> basStationTypes = basStationTypeService.list(new LambdaQueryWrapper<BasStationType>().in(BasStationType::getTaskType, list));
+        List<BasStation>  basStations = new ArrayList<>();
+        for (BasStationType basStationType : basStationTypes) {
+            List<BasStation> basStationList = basStationService.list(new LambdaQueryWrapper<BasStation>().eq(BasStation::getStationTypeCode, basStationType.getStationTypeCode()));
+            if (basStationList == null || basStationList.isEmpty()) {
+                continue;
+            }
+            basStations.addAll(basStationList);
+        }
+
+        return R.ok().add(basStations);
     }
 
     /**
@@ -247,16 +264,28 @@
         List<LocItem> locItems = locItemService.listByMatnr(matnrs);
         if (!locItems.isEmpty()) {
             List<Integer> list = Arrays.asList(TaskType.TASK_TYPE_CHECK_OUT.type, TaskType.TASK_TYPE_CHECK_IN.type);
-            DeviceSite deviceSite = deviceSiteService.getOne(new LambdaQueryWrapper<DeviceSite>()
-                    .in(DeviceSite::getType, list)
-                    .groupBy(DeviceSite::getSite)
-                    .last("limit 1"));
-            if (Objects.isNull(deviceSite)) {
-                throw new CoolException("搴撳彛涓嶄负绌猴紒锛�");
+//            DeviceSite deviceSite = deviceSiteService.getOne(new LambdaQueryWrapper<DeviceSite>()
+//                    .in(DeviceSite::getType, list)
+//                    .groupBy(DeviceSite::getSite)
+//                    .last("limit 1"));
+
+            List<BasStationType> basStationTypes = basStationTypeService.list(new LambdaQueryWrapper<BasStationType>().in(BasStationType::getTaskType, list));
+            List<BasStation>  basStations = new ArrayList<>();
+            for (BasStationType basStationType : basStationTypes) {
+                List<BasStation> basStationList = basStationService.list(new LambdaQueryWrapper<BasStation>().eq(BasStation::getStationTypeCode, basStationType.getStationTypeCode()));
+                if (basStationList == null || basStationList.isEmpty()) {
+                    continue;
+                }
+                basStations.addAll(basStationList);
+            }
+            if (basStations.isEmpty()) {
+                throw new CoolException("搴撳彛涓虹┖锛侊紒");
             }
             locItems.forEach(locItem -> {
-                locItem.setSiteNo(deviceSite.getSite());
+                locItem.setSiteNo(basStations.get(0).getStationName());
             });
+
+//            return R.ok().add(basStations);
         }
         return R.ok().add(locItems);
     }
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/DeviceSiteServiceImpl.java b/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/DeviceSiteServiceImpl.java
index 5ddaebe..2204f98 100644
--- a/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/DeviceSiteServiceImpl.java
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/DeviceSiteServiceImpl.java
@@ -37,7 +37,8 @@
     @Transactional(rollbackFor = Exception.class)
     public boolean initSites(DeviceSiteParame param) {
         if (param.getFlagInit() != null && param.getFlagInit() == 1) {
-            List<DeviceSite> list = this.list(new LambdaQueryWrapper<DeviceSite>().select(DeviceSite::getId).last("limit 1"));
+//            List<DeviceSite> list = this.list(new LambdaQueryWrapper<DeviceSite>().select(DeviceSite::getId).last("limit 1"));
+            List<DeviceSite> list = this.list(new LambdaQueryWrapper<DeviceSite>());
             if (!list.isEmpty()) {
                 if (!this.remove(new LambdaQueryWrapper<>())) {
                     throw new CoolException("鍒濆鍖栧け璐ワ細 鍒犻櫎绔欑偣澶辫触锛侊紒");
@@ -81,17 +82,17 @@
                     String targetVal = truncate(row.getTarget().trim(), TARGET_MAX_LENGTH);
                     String commonName = StringUtils.isNotBlank(param.getName()) ? param.getName().trim() : null;
                     String commonLabel = StringUtils.isNotBlank(param.getLabel()) ? param.getLabel().trim() : null;
-                    ds.setType(String.valueOf(typeId))
-                            .setSite(siteName)
-                            .setDevice(param.getDeviceType())
-                            .setDeviceSite(deviceSiteName)
-                            .setTarget(targetVal)
-                            .setDeviceCode(param.getDeviceCode())
-                            .setAreaIdStart(param.getAreaIdStart())
-                            .setAreaIdEnd(param.getAreaIdEnd())
-                            .setChannel(ch)
-                            .setName(commonName != null ? commonName : (deviceSiteName + "-" + siteName + "-" + targetVal + "-" + ch))
-                            .setLabel(commonLabel);
+//                    ds.setType(String.valueOf(typeId))
+//                            .setSite(siteName)
+//                            .setDevice(param.getDeviceType())
+//                            .setDeviceSite(deviceSiteName)
+//                            .setTarget(targetVal)
+//                            .setDeviceCode(param.getDeviceCode())
+////                            .setAreaIdStart(param.getAreaIdStart())
+////                            .setAreaIdEnd(param.getAreaIdEnd())
+//                            .setChannel(ch)
+//                            .setName(commonName != null ? commonName : (deviceSiteName + "-" + siteName + "-" + targetVal + "-" + ch))
+//                            .setLabel(commonLabel);
                     deviceSites.add(ds);
                 }
             }
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/LocItemServiceImpl.java b/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/LocItemServiceImpl.java
index 2bdd486..e6f051c 100644
--- a/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/LocItemServiceImpl.java
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/LocItemServiceImpl.java
@@ -2,6 +2,7 @@
 
 import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
 import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
+import com.vincent.rsf.framework.common.Cools;
 import com.vincent.rsf.framework.exception.CoolException;
 import com.vincent.rsf.server.api.controller.erp.params.TaskInParam;
 import com.vincent.rsf.server.api.entity.dto.InTaskMsgDto;
@@ -18,6 +19,7 @@
 import com.vincent.rsf.server.manager.mapper.WaveMapper;
 import com.vincent.rsf.server.manager.service.*;
 import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
+import com.vincent.rsf.server.manager.utils.WarehouseLocationRetrievalUtil;
 import com.vincent.rsf.server.system.constant.SerialRuleCode;
 import com.vincent.rsf.server.system.utils.SerialRuleUtils;
 import lombok.Synchronized;
@@ -61,6 +63,8 @@
     private CheckDiffService checkDiffService;
     @Autowired
     private CheckDiffItemService checkDiffItemService;
+    @Autowired
+    private WarehouseAreasServiceImpl warehouseAreasService;
 
 
     /**
@@ -112,15 +116,13 @@
                 .setBarcode(loc.getBarcode())
                 .setMemo(map.getMemo());
 
-        if (map.getType().equals(Constants.TASK_TYPE_OUT_STOCK_EMPTY)) {
-                //绌哄鍣ㄥ嚭搴�
-                DeviceSite deviceSite = deviceSiteService.getOne(new LambdaQueryWrapper<DeviceSite>()
-                        .eq(!Objects.isNull(loc.getChannel()), DeviceSite::getChannel, loc.getChannel())
-                        .eq(DeviceSite::getSite, siteNo).eq(DeviceSite::getType, TaskType.TASK_TYPE_EMPTY_OUT.type).last("limit 1"));
-                if (Objects.isNull(deviceSite)) {
-                    throw new CoolException("绔欑偣涓嶆敮鎸佺┖瀹瑰櫒鍑哄簱锛侊紒");
-                }
-                task.setTaskType(TaskType.TASK_TYPE_EMPTY_OUT.type).setWarehType(deviceSite.getDevice());
+        if (map.getType().equals(Constants.TASK_TYPE_OUT_STOCK_EMPTY)) {//绌哄鍣ㄥ嚭搴�
+            boolean available = new WarehouseLocationRetrievalUtil().queryPathIsItAvailableOutArea(loc.getAreaId().toString(), siteNo, loc.getBarcode(),TaskType.TASK_TYPE_EMPTY_OUT.type.toString());
+            if (!available) {
+                throw new CoolException("绔欑偣涓嶆敮鎸佺┖瀹瑰櫒鍑哄簱锛侊紒");
+            }
+            WarehouseAreas warehouseAreas = warehouseAreasService.getById(loc.getAreaId());
+            task.setTaskType(TaskType.TASK_TYPE_EMPTY_OUT.type).setWarehType(warehouseAreas.getType());
         } else {
             throw new CoolException("绌哄鍣ㄥ嚭搴擄紒锛佸叾浠栫被鍨嬫棤鏁堬紝杩涘叆绫诲瀷锛�"+map.getType());
         }
@@ -219,73 +221,45 @@
                     || map.getType().equals(Constants.TASK_TYPE_WAVE_OUT_STOCK)) {
                 if (orgQty.compareTo(outQty) > 0) {
                     //鎷f枡鍑哄簱 -- 鐩樼偣鍑哄簱
-                    DeviceSite deviceSite = deviceSiteService.getOne(new LambdaQueryWrapper<DeviceSite>()
-                            .eq(DeviceSite::getSite, siteNo)
-                            .eq(!Objects.isNull(loc.getChannel()),DeviceSite::getChannel, loc.getChannel())
-                            .eq(DeviceSite::getType, TaskType.TASK_TYPE_PICK_AGAIN_OUT.type).last("limit 1"),false);
-                    if (Objects.isNull(deviceSite)) {
-                        throw new CoolException("绔欑偣涓嶆敮鎸佹嫞鏂欏嚭搴擄紒锛�");
+                    boolean available = new WarehouseLocationRetrievalUtil().queryPathIsItAvailableOutArea(loc.getAreaId().toString(), siteNo, loc.getBarcode(),TaskType.TASK_TYPE_PICK_AGAIN_OUT.type);
+                    if (!available) {
+                        throw new CoolException("绔欑偣涓嶆敮鎸佹瀹瑰櫒鎷i�夊嚭搴擄紒锛�");
                     }
-                    task.setTaskType(TaskType.TASK_TYPE_PICK_AGAIN_OUT.type).setWarehType(deviceSite.getDevice());
+                    WarehouseAreas warehouseAreas = warehouseAreasService.getById(loc.getAreaId());
+                    task.setTaskType(TaskType.TASK_TYPE_PICK_AGAIN_OUT.type).setWarehType(warehouseAreas.getType());
                 } else {
                     if (resouce.equals(TaskResouceType.TASK_RESOUCE_STOCK_NOT_OUT.val)){
                         //鍏ㄦ澘鍑哄簱
-                        DeviceSite deviceSite = deviceSiteService.getOne(new LambdaQueryWrapper<DeviceSite>()
-                                .eq(DeviceSite::getSite, siteNo).eq(DeviceSite::getType, TaskType.TASK_TYPE_CROSS_DOCKING_OUT.type)
-                                .eq(!Objects.isNull(loc.getChannel()), DeviceSite::getChannel, loc.getChannel()).last("limit 1"));
-                        if (Objects.isNull(deviceSite)) {
+                        boolean available = new WarehouseLocationRetrievalUtil().queryPathIsItAvailableOutArea(loc.getAreaId().toString(), siteNo, loc.getBarcode(),TaskType.TASK_TYPE_CROSS_DOCKING_OUT.type);
+                        if (!available) {
                             throw new CoolException("绔欑偣涓嶆敮鎸佽秺搴擄紒锛�");
                         }
-                        task.setTaskType(TaskType.TASK_TYPE_CROSS_DOCKING_OUT.type).setWarehType(deviceSite.getDevice());//瓒婂簱
+                        WarehouseAreas warehouseAreas = warehouseAreasService.getById(loc.getAreaId());
+                        task.setTaskType(TaskType.TASK_TYPE_CROSS_DOCKING_OUT.type).setWarehType(warehouseAreas.getType());//瓒婂簱
                     } else {
                         //鍏ㄦ澘鍑哄簱
-                        DeviceSite deviceSite = deviceSiteService.getOne(new LambdaQueryWrapper<DeviceSite>()
-                                .eq(DeviceSite::getSite, siteNo).eq(DeviceSite::getType, TaskType.TASK_TYPE_OUT.type)
-                                .eq(!Objects.isNull(loc.getChannel()), DeviceSite::getChannel, loc.getChannel()).last("limit 1"));
-                        if (Objects.isNull(deviceSite)) {
+                        boolean available = new WarehouseLocationRetrievalUtil().queryPathIsItAvailableOutArea(loc.getAreaId().toString(), siteNo, loc.getBarcode(),TaskType.TASK_TYPE_OUT.type);
+                        if (!available) {
                             throw new CoolException("绔欑偣涓嶆敮鎸佸叏鏉垮嚭搴擄紒锛�");
                         }
-                        task.setTaskType(TaskType.TASK_TYPE_OUT.type).setWarehType(deviceSite.getDevice());
+                        WarehouseAreas warehouseAreas = warehouseAreasService.getById(loc.getAreaId());
+                        task.setTaskType(TaskType.TASK_TYPE_OUT.type).setWarehType(warehouseAreas.getType());
                     }
 
                 }
             } else if (map.getType().equals(Constants.TASK_TYPE_OUT_CHECK)) {
                 //鐩樼偣鍑哄簱
-                DeviceSite deviceSite = deviceSiteService.getOne(new LambdaQueryWrapper<DeviceSite>()
-                        .eq(!Objects.isNull(loc.getChannel()), DeviceSite::getChannel, loc.getChannel())
-                        .eq(DeviceSite::getSite, siteNo)
-                        .eq(DeviceSite::getType, TaskType.TASK_TYPE_CHECK_OUT.type).last("limit 1"));
-                if (Objects.isNull(deviceSite)) {
+                boolean available = new WarehouseLocationRetrievalUtil().queryPathIsItAvailableOutArea(loc.getAreaId().toString(), siteNo, loc.getBarcode(),TaskType.TASK_TYPE_CHECK_OUT.type);
+                if (!available) {
                     throw new CoolException("褰撳墠绔欑偣涓嶆敮鎸佺洏鐐瑰嚭搴擄紒锛�");
                 }
-                task.setTaskType(TaskType.TASK_TYPE_CHECK_OUT.type).setWarehType(deviceSite.getDevice());
+                WarehouseAreas warehouseAreas = warehouseAreasService.getById(loc.getAreaId());
+                task.setTaskType(TaskType.TASK_TYPE_CHECK_OUT.type).setWarehType(warehouseAreas.getType());
             }
 
             if (taskMapper.insert(task) <= 0) {
                 throw new CoolException("浠诲姟鍒涘缓澶辫触锛侊紒");
             }
-
-//            if (!LocUtils.isShallowLoc(loc.getCode())) {
-//                //鑾峰彇娣卞簱浣嶅搴旀祬搴撲綅
-//                String shallowLoc = LocUtils.getShallowLoc(loc.getCode());
-//                Loc one = locService.getOne(new LambdaQueryWrapper<Loc>().eq(Loc::getCode, shallowLoc));
-//                if (Objects.isNull(one)) {
-//                    throw new CoolException("瀵瑰簲搴撲綅涓嶅瓨鍦紒锛�");
-//                }
-//                Task workTask = taskService.getOne(new LambdaQueryWrapper<Task>().eq(Task::getBarcode, one.getBarcode()));
-//                if (Objects.isNull(workTask)) {
-//                    map.setOrgLoc(one.getCode());
-//                    //浼樺厛鐢熸垚绉诲簱浠诲姟
-//                    if (one.getUseStatus().equals(LocStsType.LOC_STS_TYPE_F.type)) {
-//                        moveTask = genMoveTask(map, loginUserId);
-//                    }
-//                } else {
-//                    workTask.setSort(task.getSort() + 1).setParentId(task.getId());
-//                    if (!taskService.updateById(workTask)) {
-//                        throw new CoolException("浼樺厛绾т慨鏀瑰け璐ワ紒锛�");
-//                    }
-//                }
-//            }
 
             if (!Objects.isNull(moveTask.getId())) {
                 moveTask.setParentId(task.getId()).setSort(moveTask.getSort() + 1);
@@ -465,24 +439,39 @@
         Loc targetLoc;
         if (Objects.isNull(map.getTarLoc()) || StringUtils.isBlank(map.getTarLoc())) {
             //鐩爣搴撲綅涓虹┖锛岃嚜鍔ㄨ幏鍙栨柊搴撲綅
-            DeviceSite deviceSite = deviceSiteService.getOne(new LambdaQueryWrapper<DeviceSite>()
-                    .eq(DeviceSite::getType, TaskType.TASK_TYPE_LOC_MOVE.type)
-                    .eq(!Objects.isNull(orgLoc.getChannel()), DeviceSite::getChannel, orgLoc.getChannel()).last("limit 1"), false);
-            if (Objects.isNull(deviceSite)) {
-                throw new CoolException("绔欑偣淇℃伅涓嶅瓨鍦紒锛�");
+
+            List<String> outWarehouseAreasByReservoirAreaAndContainer = new WarehouseLocationRetrievalUtil().getOutWarehouseAreasByReservoirAreaAndContainer(orgLoc.getAreaId(), orgLoc.getBarcode(), TaskType.TASK_TYPE_LOC_MOVE.type);
+            if (!Cools.isEmpty(outWarehouseAreasByReservoirAreaAndContainer) || outWarehouseAreasByReservoirAreaAndContainer.isEmpty()) {
+                throw new CoolException("鏈壘鍒板彲鐢ㄧ洰鏍囧簱鍖猴紒锛侊紒婧愬簱鍖猴細"+orgLoc.getAreaId());
             }
-            TaskInParam param = new TaskInParam();
-            param.setIoType(TaskType.TASK_TYPE_OUT.type)
-                    .setOrgLoc(map.getOrgLoc())
-                    .setSourceStaNo(deviceSite.getSite())
-                    .setLocType1(Integer.parseInt(orgLoc.getType())
-                    );
-            InTaskMsgDto locNo;
-            try {
-                locNo = wcsService.getLocNo(param);
-            } catch (Exception e) {
-                log.error("<UNK>", e);
-                throw new CoolException(e.getMessage());
+            InTaskMsgDto locNo = null;
+            for (String areaId : outWarehouseAreasByReservoirAreaAndContainer) {
+                List<LocItem> locItems = this.list(new LambdaQueryWrapper<LocItem>().eq(LocItem::getLocCode, orgLoc.getCode()));
+                boolean sign = false;
+                for (LocItem locItem : locItems) {
+                    if (!new WarehouseLocationRetrievalUtil().retrieveMatnrIsItAvailable(areaId, locItem.getMatnrId())){
+                        sign = true;
+                        break;
+                    }
+                }
+                if (sign) {
+                    continue;
+                }
+                TaskInParam param = new TaskInParam();
+                param.setIoType(TaskType.TASK_TYPE_OUT.type)
+                        .setOrgLoc(map.getOrgLoc())
+                        .setAreaId(Long.parseLong(areaId))
+                        .setLocType1(Integer.parseInt(orgLoc.getType())
+                        );
+                try {
+                    locNo = wcsService.getLocNoArea(param);
+                    break;
+                } catch (Exception e) {
+                    log.error("<UNK>", e);
+                }
+            }
+            if (Cools.isEmpty(locNo)){
+                throw new CoolException("绉诲簱鏈壘鍒板彲鐢ㄥ簱浣嶏紒锛侊紒");
             }
             targetLoc = locService.getOne(new LambdaQueryWrapper<Loc>().eq(Loc::getCode, locNo.getLocNo()));
         } else {
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/MatnrRestrictionWarehouseServiceImpl.java b/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/MatnrRestrictionWarehouseServiceImpl.java
new file mode 100644
index 0000000..45456f9
--- /dev/null
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/MatnrRestrictionWarehouseServiceImpl.java
@@ -0,0 +1,12 @@
+package com.vincent.rsf.server.manager.service.impl;
+
+import com.vincent.rsf.server.manager.mapper.MatnrRestrictionWarehouseMapper;
+import com.vincent.rsf.server.manager.entity.MatnrRestrictionWarehouse;
+import com.vincent.rsf.server.manager.service.MatnrRestrictionWarehouseService;
+import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
+import org.springframework.stereotype.Service;
+
+@Service("matnrRestrictionWarehouseService")
+public class MatnrRestrictionWarehouseServiceImpl extends ServiceImpl<MatnrRestrictionWarehouseMapper, MatnrRestrictionWarehouse> implements MatnrRestrictionWarehouseService {
+
+}
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/OutStockServiceImpl.java b/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/OutStockServiceImpl.java
index e4bc088..f5b76c6 100644
--- a/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/OutStockServiceImpl.java
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/OutStockServiceImpl.java
@@ -19,6 +19,7 @@
 import com.vincent.rsf.server.manager.service.*;
 import com.vincent.rsf.server.manager.utils.LocManageUtil;
 import com.vincent.rsf.server.manager.utils.OptimalAlgorithmUtil;
+import com.vincent.rsf.server.manager.utils.WarehouseLocationRetrievalUtil;
 import com.vincent.rsf.server.system.constant.SerialRuleCode;
 import com.vincent.rsf.server.system.utils.SerialRuleUtils;
 import org.apache.commons.lang3.StringUtils;
@@ -78,6 +79,8 @@
     private WaveOrderRelaServiceImpl waveOrderRelaService;
     @Autowired
     private AsnOrderService asnOrderService;
+    @Autowired
+    private BasStationServiceImpl basStationService;
 
 
     /**
@@ -747,12 +750,13 @@
      */
     @Override
     public R getSiteNos() {
-        List<Integer> list = Arrays.asList(TaskType.TASK_TYPE_MERGE_OUT.type,
-                TaskType.TASK_TYPE_OUT.type,
-                TaskType.TASK_TYPE_MERGE_OUT.type,
-                TaskType.TASK_TYPE_PICK_AGAIN_OUT.type);
-        List<DeviceSite> sites = deviceSiteService.list(new LambdaQueryWrapper<DeviceSite>().in(DeviceSite::getType, list).groupBy(DeviceSite::getSite));
-        return R.ok(sites);
+//        List<Integer> list = Arrays.asList(TaskType.TASK_TYPE_MERGE_OUT.type,
+//                TaskType.TASK_TYPE_OUT.type,
+//                TaskType.TASK_TYPE_MERGE_OUT.type,
+//                TaskType.TASK_TYPE_PICK_AGAIN_OUT.type);sites
+//        List<DeviceSite>  = deviceSiteService.list(new LambdaQueryWrapper<DeviceSite>().in(DeviceSite::getType, list).groupBy(DeviceSite::getSite));
+        List<BasStation> basStationList = basStationService.list(new LambdaQueryWrapper<BasStation>().eq(BasStation::getOutAble, true));
+        return R.ok(basStationList);
     }
 
     @Override
@@ -828,24 +832,18 @@
                         OrderOutItemDto orderOutItemDto = new OrderOutItemDto();
 //                        orderOutItemDto.setLocItem(locItem);
                         orderOutItemDto.getLocItemList().add(locItem);
-
-                        List<DeviceSite> deviceSites = deviceSiteService.list(new LambdaQueryWrapper<DeviceSite>()
-                                .eq(DeviceSite::getChannel, loc.getChannel())
-                                .eq(DeviceSite::getType, issued.doubleValue() >= locItem.getAnfme() && itemList.size() == 1 ? TaskType.TASK_TYPE_OUT.type : TaskType.TASK_TYPE_PICK_AGAIN_OUT.type)
-                        );
-
-                        if (!deviceSites.isEmpty()) {
+                        List<String> outboundSiteByReservoirAreaAndContainer = new WarehouseLocationRetrievalUtil().getOutboundSiteByReservoirAreaAndContainer(loc.getAreaId(), loc.getBarcode(),itemList.size() == 1 ? TaskType.TASK_TYPE_OUT.type.toString() : TaskType.TASK_TYPE_PICK_AGAIN_OUT.type.toString());
+                        if (!outboundSiteByReservoirAreaAndContainer.isEmpty()) {
                             List<OrderOutItemDto.staListDto> maps = new ArrayList<>();
-                            for (DeviceSite sta : deviceSites) {
+                            for (String staNo : outboundSiteByReservoirAreaAndContainer) {
                                 OrderOutItemDto.staListDto staListDto = new OrderOutItemDto.staListDto();
-                                staListDto.setStaNo(sta.getSite());
-                                staListDto.setStaName(sta.getSite());
+                                staListDto.setStaNo(staNo);
+                                staListDto.setStaName(staNo);
                                 maps.add(staListDto);
                             }
                             orderOutItemDto.setStaNos(maps);
                             //榛樿鑾峰彇绗竴绔欑偣
-                            DeviceSite deviceSite = deviceSites.stream().findFirst().get();
-                            orderOutItemDto.setSiteNo(deviceSite.getSite());
+                            orderOutItemDto.setSiteNo(outboundSiteByReservoirAreaAndContainer.get(0));
                         }
 
                         list.add(orderOutItemDto);
@@ -918,26 +916,19 @@
                         locItem.setOutQty(issued.doubleValue() >= locItem.getAnfme() ? locItem.getAnfme() : issued.doubleValue());
                         locItem.setBarcode(loc.getBarcode());
                         OrderOutItemDto orderOutItemDto = new OrderOutItemDto();
-//                        orderOutItemDto.setLocItem(locItem);
                         orderOutItemDto.getLocItemList().add(locItem);
-
-                        List<DeviceSite> deviceSites = deviceSiteService.list(new LambdaQueryWrapper<DeviceSite>()
-                                .eq(DeviceSite::getChannel, loc.getChannel())
-                                .eq(DeviceSite::getType, issued.doubleValue() >= locItem.getAnfme() && itemList.size() == 1 ? TaskType.TASK_TYPE_OUT.type : TaskType.TASK_TYPE_PICK_AGAIN_OUT.type)
-                        );
-
-                        if (!deviceSites.isEmpty()) {
+                        List<String> outboundSiteByReservoirAreaAndContainer = new WarehouseLocationRetrievalUtil().getOutboundSiteByReservoirAreaAndContainer(loc.getAreaId(), loc.getBarcode(),itemList.size() == 1 ? TaskType.TASK_TYPE_OUT.type : TaskType.TASK_TYPE_PICK_AGAIN_OUT.type);
+                        if (!outboundSiteByReservoirAreaAndContainer.isEmpty()) {
                             List<OrderOutItemDto.staListDto> maps = new ArrayList<>();
-                            for (DeviceSite sta : deviceSites) {
+                            for (String staNo : outboundSiteByReservoirAreaAndContainer) {
                                 OrderOutItemDto.staListDto staListDto = new OrderOutItemDto.staListDto();
-                                staListDto.setStaNo(sta.getSite());
-                                staListDto.setStaName(sta.getSite());
+                                staListDto.setStaNo(staNo);
+                                staListDto.setStaName(staNo);
                                 maps.add(staListDto);
                             }
                             orderOutItemDto.setStaNos(maps);
                             //榛樿鑾峰彇绗竴绔欑偣
-                            DeviceSite deviceSite = deviceSites.stream().findFirst().get();
-                            orderOutItemDto.setSiteNo(deviceSite.getSite());
+                            orderOutItemDto.setSiteNo(outboundSiteByReservoirAreaAndContainer.get(0));
                         }
 
                         list.add(orderOutItemDto);
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/TaskServiceImpl.java b/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/TaskServiceImpl.java
index 875e6d4..2c4bfe5 100644
--- a/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/TaskServiceImpl.java
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/manager/service/impl/TaskServiceImpl.java
@@ -28,6 +28,7 @@
 import com.vincent.rsf.server.manager.service.*;
 import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
 import com.vincent.rsf.server.manager.utils.LocManageUtil;
+import com.vincent.rsf.server.manager.utils.WarehouseLocationRetrievalUtil;
 import com.vincent.rsf.server.system.constant.GlobalConfigCode;
 import com.vincent.rsf.server.system.constant.SerialRuleCode;
 import com.vincent.rsf.server.manager.enums.LocStsType;
@@ -131,7 +132,7 @@
 
     @Override
     @Transactional(rollbackFor = Exception.class)
-    public synchronized R generateAGVTasks(WaitPakin pakins, String locCode, String orgSta,String targSite, Long loginUserId) {
+    public synchronized R generateAGVTasks(WaitPakin pakins, String locCode, String orgSta, Long loginUserId,String areaId) {
         if (Cools.isEmpty(pakins) || Cools.isEmpty(locCode)) {
             throw new CoolException("鍙傛暟涓嶈兘涓虹┖锛侊紒");
         }
@@ -201,6 +202,10 @@
                 throw new CoolException("浠诲姟鏄庣粏淇濆瓨澶辫触锛侊紒");
             }
             waitPakinItems.forEach(item -> {
+                boolean b = new WarehouseLocationRetrievalUtil().retrieveMatnrIsItAvailable(areaId, item.getMatnrId());
+                if (!b){
+                    throw new CoolException("鍏ュ簱澶辫触锛侊紒鐗╂枡Id:"+item.getMatnrId()+"涓嶆敮鎸佹鐩爣搴撳尯锛�"+areaId);
+                }
                 if (!waitPakinItemService.update(new LambdaUpdateWrapper<WaitPakinItem>()
                         .set(WaitPakinItem::getWorkQty, item.getAnfme())
                         .eq(WaitPakinItem::getId, item.getId()))) {
@@ -307,11 +312,11 @@
             throw new CoolException("鍙傛暟涓嶈兘涓虹┖锛侊紒");
         }
 
-        DeviceSite deviceSite = deviceSiteService.getById(waitPakin.getSiteId());
-        if (Objects.isNull(deviceSite)) {
-            throw new CoolException("绔欑偣涓嶅瓨鍦紒锛�");
-        }
-        DeviceBind deviceBind = deviceBindService.getById(LocUtils.getAreaType(deviceSite.getSite()));
+//        DeviceSite deviceSite = deviceSiteService.getById();
+//        if (Objects.isNull(deviceSite)) {
+//            throw new CoolException("绔欑偣涓嶅瓨鍦紒锛�");
+//        }
+        DeviceBind deviceBind = deviceBindService.getById(LocUtils.getAreaType(waitPakin.getSiteNo()));
         if (Cools.isEmpty(deviceBind)) {
             throw new CoolException("搴撲綅瑙勫垯鏈煡");
         }
@@ -336,7 +341,7 @@
 //            }
 
             //楠岃瘉鍩虹淇℃伅
-            checkStaStatus(pakin.getBarcode(), deviceSite.getSite(),warehouseArea.getId().toString());
+            checkStaStatus(pakin.getBarcode(),waitPakin.getSiteNo(),warehouseArea.getId().toString());
             /**鑾峰彇搴撲綅*/
             String targetLoc = LocManageUtil.getTargetLoc(warehouseArea.getId(), null);
             if (Cools.isEmpty(targetLoc)) {
@@ -355,8 +360,8 @@
                     .setResource(TaskResouceType.TASK_RESOUCE_PAKIN_TYPE.val)
                     .setTargLoc(targetLoc)
                     .setBarcode(pakin.getBarcode())
-                    .setOrgSite(deviceSite.getSite())
-                    .setTargSite(deviceSite.getDeviceSite())
+                    .setOrgSite(waitPakin.getSiteNo())
+                    .setTargSite(waitPakin.getSiteNo())
                     .setCreateBy(loginUserId)
                     .setUpdateBy(loginUserId);
 //            if (!Objects.isNull(waitPakin.getSiteId()) && waitPakin.getSiteId() > 0) {
@@ -380,7 +385,7 @@
                 throw new CoolException("浠诲姟淇濆瓨澶辫触锛侊紒");
             }
             BasStation station = basStationService.getOne(new LambdaQueryWrapper<BasStation>()
-                    .eq(BasStation::getStationName, deviceSite.getSite()));
+                    .eq(BasStation::getStationName, waitPakin.getSiteNo()));
             if (Objects.isNull(station) || !station.getUseStatus().equals(LocStsType.LOC_STS_TYPE_O.type)) {
                 throw new CoolException("绔欑偣涓嶅瓨鍦ㄦ垨绔欑偣涓嶅浜庣┖搴撶姸鎬侊紒锛�");
             }
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/manager/utils/LocManageUtil.java b/rsf-server/src/main/java/com/vincent/rsf/server/manager/utils/LocManageUtil.java
index be0ca00..d999743 100644
--- a/rsf-server/src/main/java/com/vincent/rsf/server/manager/utils/LocManageUtil.java
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/manager/utils/LocManageUtil.java
@@ -88,21 +88,6 @@
         return !Objects.isNull(loc) ? loc.getCode() : null;
     }
 
-
-    /**
-     * @param
-     * @return
-     * @author Ryan
-     * @description 鑾峰彇鐩爣绔欑偣
-     * @time 2025/3/31 09:49
-     */
-    public static String getTargetSite() {
-        //TODO 绔欑偣绛栫暐鍚庣画鎺掓湡
-        DeviceSiteService deviceSite = SpringUtils.getBean(DeviceSiteService.class);
-        DeviceSite loc = deviceSite.getOne(new LambdaQueryWrapper<DeviceSite>().eq(DeviceSite::getStatus, 1), false);
-        return !Objects.isNull(loc) ? loc.getSite() : null;
-    }
-
     /**
      * 鍑哄簱绛栫暐锛�--銆堟晥鐜囦紭鍖栥��
      *
@@ -175,9 +160,7 @@
     public static List<OrderOutItemDto> getOutOrderList(List<WaveToLocParams> params, WaveRule waveRule,String stationId,String locCode) {
         LocService locService = SpringUtils.getBean(LocService.class);
         LocItemService locItemService = SpringUtils.getBean(LocItemService.class);
-        DeviceSiteService deviceSiteService = SpringUtils.getBean(DeviceSiteService.class);
         BasStationAreaService basStationAreaService = SpringUtils.getBean(BasStationAreaService.class);
-//        List<BasStationArea> basStationAreas = basStationAreaService.list(new LambdaQueryWrapper<>());//
         List<Loc> locList = new  ArrayList<>();
         List<OrderOutItemDto> list = new ArrayList<>();
         //涓嶈绔欑偣閲嶅浣跨敤闂
@@ -236,7 +219,7 @@
 //                        orderOutItemDto.setLocItem(locItem);
                         orderOutItemDto.setLoc(loc);
                         orderOutItemDto.getLocItemList().add(locItem);
-                        BasContainer containerType = getContainerType(loc.getBarcode());
+                        BasContainer containerType = new WarehouseLocationRetrievalUtil().getContainerByBarcode(loc.getBarcode());
                         if (Cools.isEmpty(containerType)){
                             continue;
                         }
@@ -328,25 +311,11 @@
                             if (Objects.isNull(basStation)) {
                                 throw new CoolException("缁戝畾绔欓粸涓嶅瓨鍦紒锛�");
                             }
-                            List<DeviceSite> deviceSites = deviceSiteService.list(new LambdaQueryWrapper<DeviceSite>()
-                                    .eq(!Objects.isNull(loc.getChannel()), DeviceSite::getChannel, loc.getChannel())
-                                    .eq(!Objects.isNull(loc.getAreaId()), DeviceSite::getAreaIdStart, loc.getAreaId())
-                                    .eq( DeviceSite::getSite, stationId)
-                                    .eq(DeviceSite::getType, issued.doubleValue() >= locItem.getAnfme() && itemList.size() == 1 ? TaskType.TASK_TYPE_OUT.type : TaskType.TASK_TYPE_PICK_AGAIN_OUT.type)
-                            );
-                            if (!deviceSites.isEmpty()) {
-                                List<OrderOutItemDto.staListDto> maps = new ArrayList<>();
-                                for (DeviceSite sta : deviceSites) {
-                                    OrderOutItemDto.staListDto staListDto = new OrderOutItemDto.staListDto();
-                                    staListDto.setStaNo(sta.getSite());
-                                    staListDto.setStaName(sta.getSite());
-                                    maps.add(staListDto);
-                                }
-                                orderOutItemDto.setStaNos(maps);
-                                orderOutItemDto.setSiteNo(basStation.getStationName());
-                            } else {
-                                throw new CoolException("鏈壘鍒扮鍚堟潯浠剁珯鐐硅矾寰勶紒锛侊紒璇锋鏌ヨ矾寰勭鐞嗭紒锛侊紒");
+                            boolean available = new WarehouseLocationRetrievalUtil().queryPathIsItAvailableOutArea(loc.getAreaId().toString(), stationId, loc.getBarcode(),"out");
+                            if (!available) {
+                                throw new CoolException("鏈壘鍒扮鍚堟潯浠惰矾寰勶紒锛侊紒璇锋鏌ヨ矾寰勯厤缃紒锛侊紒");
                             }
+                            orderOutItemDto.setSiteNo(basStation.getStationName());
 
                             orderOutItemDto.setSource(item.getItemId().toString())
                                     .setTargSiteAreaList(new ArrayList<>())
@@ -355,85 +324,15 @@
 
                             locList.add(loc);
                             issued = issued.subtract(new BigDecimal(locItem.getAnfme().toString()));
-
                         } else {
-                            List<DeviceSite> deviceSites = deviceSiteService.list(new LambdaQueryWrapper<DeviceSite>()
-                                    .eq(!Objects.isNull(loc.getChannel()), DeviceSite::getChannel, loc.getChannel())
-                                    .eq(!Objects.isNull(loc.getAreaId()), DeviceSite::getAreaIdStart, loc.getAreaId())
-                                    .eq(DeviceSite::getType, issued.doubleValue() >= locItem.getAnfme() && itemList.size() == 1 ? TaskType.TASK_TYPE_OUT.type : TaskType.TASK_TYPE_PICK_AGAIN_OUT.type)
-                            );
-
-                            if (!deviceSites.isEmpty()) {
-                                List<OrderOutItemDto.staListDto> maps = new ArrayList<>();
-                                for (DeviceSite sta : deviceSites) {
-                                    OrderOutItemDto.staListDto staListDto = new OrderOutItemDto.staListDto();
-                                    staListDto.setStaNo(sta.getSite());
-                                    staListDto.setStaName(sta.getSite());
-                                    maps.add(staListDto);
-                                }
-                                orderOutItemDto.setStaNos(maps);
-                                //鑾峰彇婊¤冻鏉′欢绔欑偣
-                                Set<String> stationSet = deviceSites.stream().map(DeviceSite::getSite).collect(Collectors.toSet());
-                                //宸蹭娇鐢ㄧ珯鐐�
-                                Set<String> stas = stations.stream().map(BasStation::getStationName).collect(Collectors.toSet());
-                                BasStationService basStationService = SpringUtils.getBean(BasStationService.class);
-                                BasStation basStation = basStationService.getOne(new LambdaQueryWrapper<BasStation>()
-                                        .apply("cross_zone_area != '[]'")  // 涓嶆槸绌烘暟缁�
-                                        .apply("container_type != '[]'")
-                                        .apply("JSON_CONTAINS(cross_zone_area, {0}) = 1", loc.getAreaId().toString())//鍙墽琛屽簱鍖哄尯鍖哄煙id
-                                        .apply("JSON_CONTAINS(container_type, {0}) = 1", containerType.getContainerType().toString())//瀹瑰櫒绫诲瀷
-                                        .eq(BasStation::getUseStatus, LocStsType.LOC_STS_TYPE_O.type)
-                                        .in(BasStation::getStationName, stationSet)
-                                        .notIn(!stas.isEmpty(), BasStation::getStationName, stas)
-                                        .last("LIMIT 1"));
-
-                                if (Objects.isNull(basStation)) {
-                                    throw new CoolException("绔欓粸涓嶅瓨鍦紒锛�");
-                                }
-                                if (basStation.getType()!=0){
-                                    stations.add(basStation);
-                                }
-                                orderOutItemDto.setSiteNo(basStation.getStationName());
-                            } else {
-                                throw new CoolException("鏈壘鍒扮鍚堟潯浠剁珯鐐癸紒锛侊紒璇锋鏌ヨ矾寰勭鐞嗭紒锛侊紒");
-                            }
-
-                            orderOutItemDto.setSource(item.getItemId().toString())
-                                    .setTargSiteAreaList(new ArrayList<>())
-                                    .setSourceId(item.getWaveId().toString());
-                            list.add(orderOutItemDto);
-
-                            locList.add(loc);
-                            issued = issued.subtract(new BigDecimal(locItem.getAnfme().toString()));
+                            throw new CoolException("鏈壘鍒扮鍚堟潯浠跺嚭搴撶珯鐐瑰尯鍩燂紒锛侊紒璇锋鏌ュ簱鍖洪厤缃紒锛侊紒");
                         }
-//                         if (true){
-////                            throw new CoolException("鏈壘鍒扮鍚堟潯浠剁珯鐐癸紒锛侊紒璇锋鏌ュ簱鍖洪厤缃紒锛侊紒");
-//                        }
                     }
                 }
             }
         }
 
         return list;
-    }
-
-
-
-
-    //鏍规嵁鏉$爜鑾峰彇瑙勫垯
-    private static BasContainer getContainerType(String barcode) {
-        BasContainerService basContainerService = SpringUtils.getBean(BasContainerService.class);
-        if (Cools.isEmpty(barcode)) {
-            throw new CoolException("瀹瑰櫒鐮佷笉鑳戒负绌�");
-        }
-        List<BasContainer> containers = basContainerService.list(new LambdaQueryWrapper<>());
-        for (BasContainer container : containers) {
-            String codeType = container.getCodeType();  // 鑾峰彇姝e垯琛ㄨ揪寮�
-            if (barcode.matches(codeType)) {  // 鍒ゆ柇鏉$爜鏄惁绗﹀悎杩欎釜姝e垯
-                return container;
-            }
-        }
-        throw new CoolException("瀹瑰櫒鐮�:"+barcode+"寮傚父==>鏈壘鍒板尮閰嶇殑瑙勫垯");
     }
 
 }
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/manager/utils/WarehouseLocationRetrievalUtil.java b/rsf-server/src/main/java/com/vincent/rsf/server/manager/utils/WarehouseLocationRetrievalUtil.java
new file mode 100644
index 0000000..1e52730
--- /dev/null
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/manager/utils/WarehouseLocationRetrievalUtil.java
@@ -0,0 +1,534 @@
+package com.vincent.rsf.server.manager.utils;
+
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import com.vincent.rsf.framework.common.Cools;
+import com.vincent.rsf.framework.common.SpringUtils;
+import com.vincent.rsf.framework.exception.CoolException;
+import com.vincent.rsf.server.manager.entity.*;
+import com.vincent.rsf.server.manager.service.*;
+import com.vincent.rsf.server.system.entity.TaskPathTemplateMerge;
+import com.vincent.rsf.server.system.service.TaskPathTemplateMergeService;
+import lombok.extern.slf4j.Slf4j;
+import routeR.calculationR.RouteWmsStepFlow;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Objects;
+
+@Slf4j
+public class WarehouseLocationRetrievalUtil {
+
+    private BasStationService basStationService;
+    private WarehouseAreasService warehouseAreasService;
+
+    public WarehouseLocationRetrievalUtil() {
+         basStationService = SpringUtils.getBean(BasStationService.class);
+         warehouseAreasService = SpringUtils.getBean(WarehouseAreasService.class);
+    }
+
+    //鍒ゆ柇鐩爣鏄惁鏄簱鍖�
+    public boolean retrieveMissionmMergeReservoirAreaIsItAvailable(String missionArea) {
+        boolean matches = missionArea.matches("\\d+");
+        if (!matches) {
+            return false;
+        }
+        WarehouseAreas warehouseAreas = warehouseAreasService.getById(Long.parseLong(missionArea));
+        if (Cools.isEmpty(warehouseAreas)){
+            return false;
+        }
+        return true;
+    }
+
+    //鍒ゆ柇鐩爣鏄惁鏄珯鐐�
+    public BasStation retrieveMissionmMergeSizeIsItAvailable(String missionSize) {
+        BasStation basStation = basStationService.getOne(new LambdaQueryWrapper<BasStation>().eq(BasStation::getStationName, missionSize).last("limit 1"));
+        if (Cools.isEmpty(basStation)){
+            basStation = basStationService.getOne(new LambdaQueryWrapper<BasStation>()
+                    .apply("station_alias != '[]'")  // 涓嶆槸绌烘暟缁�
+                    .apply("JSON_CONTAINS(station_alias, '\"{0}\"') = 1", missionSize)
+                    .eq(BasStation::getDeleted, 0)  // 閫氬父闇�瑕佸姞涓婃湭鍒犻櫎鏉′欢
+                    .last("LIMIT 1"));
+        }
+        if (Cools.isEmpty(basStation)){
+            return null;
+        }
+        return basStation;
+    }
+
+    //鏍规嵁鏉$爜鑾峰彇瑙勫垯
+    public BasContainer getContainerByBarcode(String barcode) {
+        if (Cools.isEmpty(barcode)) {
+            throw new CoolException("瀹瑰櫒鐮佷笉鑳戒负绌�");
+        }
+        BasContainerService basContainerService = SpringUtils.getBean(BasContainerService.class);
+        List<BasContainer> containers = basContainerService.list(new LambdaQueryWrapper<>());
+        for (BasContainer container : containers) {
+            String codeType = container.getCodeType();  // 鑾峰彇姝e垯琛ㄨ揪寮�
+            if (barcode.matches(codeType)) {  // 鍒ゆ柇鏉$爜鏄惁绗﹀悎杩欎釜姝e垯
+                return container;
+            }
+        }
+        throw new CoolException("瀹瑰櫒鐮�:"+barcode+"寮傚父==>鏈壘鍒板尮閰嶇殑瑙勫垯");
+    }
+
+    //鏍规嵁鐗╂枡ID鑾峰彇鐗╂枡
+    public Matnr getMatnrByMatnrId(Long matnrId) {
+        if (Cools.isEmpty(matnrId)) {
+            throw new CoolException("鐗╂枡ID涓嶈兘涓虹┖");
+        }
+        MatnrService matnrService = SpringUtils.getBean(MatnrService.class);
+        Matnr matnr = matnrService.selectMatnrById(matnrId);
+        if (matnr == null) {
+            throw new CoolException("鐗╂枡ID:"+matnrId+"寮傚父==>鏈壘鍒板搴旂墿鏂�");
+        }
+        return matnr;
+    }
+
+    //鍒ゆ柇鐗╂枡鏄惁鍙敤姝や粨搴�
+    public boolean retrieveMatnrIsItAvailable(String areaId, Long matnrId) {
+        return retrieveMatnrIsItAvailable(Long.parseLong(areaId),matnrId);
+    }
+    public boolean retrieveMatnrIsItAvailable(Long areaId, Long matnrId) {
+        Matnr matnrByMatnrId = getMatnrByMatnrId(matnrId);
+        if (matnrByMatnrId.getWarehouseRestrictionCode() == null ||  matnrByMatnrId.getWarehouseRestrictionCode().equals("") || matnrByMatnrId.getWarehouseRestrictionCode().equals("all")) {
+            return true;
+        }
+        //鍒ゆ柇鏄惁鍏煎
+        String warehouseRestrictionCode = matnrByMatnrId.getWarehouseRestrictionCode();
+        //鏍规嵁code鑾峰彇
+        MatnrRestrictionWarehouseService matnrRestrictionWarehouseService = SpringUtils.getBean(MatnrRestrictionWarehouseService.class);
+        MatnrRestrictionWarehouse serviceOne = matnrRestrictionWarehouseService.getOne(new LambdaQueryWrapper<MatnrRestrictionWarehouse>().eq(MatnrRestrictionWarehouse::getMatnrRestrictionCode, warehouseRestrictionCode).last("limit 1"));
+        if (Objects.isNull(serviceOne)) {
+            return false;
+        }
+        //鏌ヨarea鏄惁鍦�
+        return serviceOne.getProductionLineCode().contains(areaId.intValue());
+    }
+
+
+    // 鏍规嵁搴撳尯銆佸鍣ㄦ绱㈢鍚堟潯浠剁Щ搴撳簱鍖�
+    public List<String> getOutWarehouseAreasByReservoirAreaAndContainer(Long sourceCode, String barcode,Integer type) {
+        return getOutWarehouseAreasByReservoirAreaAndContainer(sourceCode,barcode,type.toString());
+    }
+    public List<String> getOutWarehouseAreasByReservoirAreaAndContainer(Long sourceCode, String barcode,String type) {
+        List<String> outboundSite = new ArrayList<>();
+        List<String> outboundSiteByReservoirAreaAndContainer = getOutWarehouseAreasByReservoirAreaAndContainer(sourceCode, barcode);
+        for (String areaId : outboundSiteByReservoirAreaAndContainer) {
+            WarehouseAreas warehouseAreas = warehouseAreasService.getById(Long.parseLong(areaId));
+            if (!Cools.isEmpty(warehouseAreas)){
+                outboundSite.add(areaId);
+            }
+        }
+        return outboundSite;
+    }
+
+    // 鏍规嵁搴撳尯銆佸鍣ㄦ绱㈢鍚堟潯浠跺嚭搴撶珯鐐�
+    private List<String> getOutWarehouseAreasByReservoirAreaAndContainer(Long sourceCode, String barcode) {
+        return getTargetTypeByReservoirAreaAndContainer(String.valueOf(sourceCode), barcode,1,false);
+    }
+
+    // 鏍规嵁搴撳尯銆佸鍣ㄦ绱㈢鍚堟潯浠跺嚭搴撶珯鐐�
+    public List<String> getOutboundSiteByReservoirAreaAndContainer(Long sourceCode, String barcode,Integer type) {
+        return getOutboundSiteByReservoirAreaAndContainer(sourceCode,barcode,type.toString());
+    }
+    public List<String> getOutboundSiteByReservoirAreaAndContainer(Long sourceCode, String barcode,String type) {
+        List<String> outboundSite = new ArrayList<>();
+        List<String> outboundSiteByReservoirAreaAndContainer = getOutboundSiteByReservoirAreaAndContainer(sourceCode, barcode);
+        for (String site : outboundSiteByReservoirAreaAndContainer) {
+            BasStation basStation = basStationService.getOne(new LambdaQueryWrapper<BasStation>()
+                    .eq(BasStation::getStationName, site).last("limit 1"));
+            if (!Cools.isEmpty(basStation)){
+                BasStationTypeService basStationTypeService = SpringUtils.getBean(BasStationTypeService.class);
+                BasStationType one = basStationTypeService.getOne(new LambdaQueryWrapper<BasStationType>().eq(BasStationType::getStationTypeCode, basStation.getContainerType()).last("limit 1"));
+                if (!Cools.isEmpty(one)) {
+                    if (one.getTaskType().contains(type)){
+                        outboundSite.add(site);
+                    }
+                }
+            }
+        }
+        return outboundSite;
+    }
+
+    // 鏍规嵁搴撳尯銆佸鍣ㄦ绱㈢鍚堟潯浠跺嚭搴撶珯鐐�
+    private List<String> getOutboundSiteByReservoirAreaAndContainer(Long sourceCode, String barcode) {
+        return getTargetTypeByReservoirAreaAndContainer(String.valueOf(sourceCode), barcode,1,true);
+    }
+
+    // 鏍规嵁搴撳尯銆佸鍣ㄦ绱㈢鍚堟潯浠剁珯鐐规垨搴撳尯
+    private List<String> getTargetTypeByReservoirAreaAndContainer(String code, String barcode,int type,boolean isInOrOut) {
+        List<String> obtainOutboundStations = new ArrayList<>();
+        BasContainer containerByBarcode = getContainerByBarcode(barcode);
+        if (containerByBarcode == null) {
+            log.error("瀹瑰櫒鐮�:"+barcode+"寮傚父==>鏈壘鍒板尮閰嶇殑瑙勫垯");
+            return obtainOutboundStations;
+        }
+        Long containerType = containerByBarcode.getContainerType();
+        TaskPathTemplateMergeService taskPathTemplateMergeService = SpringUtils.getBean(TaskPathTemplateMergeService.class);
+        if (isInOrOut) {//鏍规嵁璧风偣妫�绱㈢粓鐐�
+            List<TaskPathTemplateMerge> taskPathTemplateMergeList = taskPathTemplateMergeService.list(new LambdaQueryWrapper<TaskPathTemplateMerge>()
+                    .eq(TaskPathTemplateMerge::getSourceType, code)
+                    .eq(TaskPathTemplateMerge::getContainerType, containerType)
+            );
+            if (taskPathTemplateMergeList.isEmpty()) {
+                return obtainOutboundStations;
+            }
+            for (TaskPathTemplateMerge taskPathTemplateMerge : taskPathTemplateMergeList) {
+                switch (type){
+                    case 1://绔欑偣
+                        if (retrieveBarcodeIsItAvailableBySite(containerByBarcode,taskPathTemplateMerge.getTargetType())){
+                            obtainOutboundStations.add(taskPathTemplateMerge.getTargetType());
+                        }
+                        break;
+                    case 2://搴撳尯
+                        if (retrieveMissionmMergeReservoirAreaIsItAvailable(taskPathTemplateMerge.getTargetType())){
+                            obtainOutboundStations.add(taskPathTemplateMerge.getTargetType());
+                        }
+                        break;
+                }
+            }
+        } else {//鏍规嵁缁堢偣妫�绱㈣捣鐐�
+            List<TaskPathTemplateMerge> taskPathTemplateMergeList = taskPathTemplateMergeService.list(new LambdaQueryWrapper<TaskPathTemplateMerge>()
+                    .eq(TaskPathTemplateMerge::getTargetType, code)
+                    .eq(TaskPathTemplateMerge::getContainerType, containerType)
+            );
+            if (taskPathTemplateMergeList.isEmpty()) {
+                return obtainOutboundStations;
+            }
+            for (TaskPathTemplateMerge taskPathTemplateMerge : taskPathTemplateMergeList) {
+                switch (type){
+                    case 1://绔欑偣
+                        if (retrieveBarcodeIsItAvailableBySite(containerByBarcode,taskPathTemplateMerge.getSourceType())){
+                            obtainOutboundStations.add(taskPathTemplateMerge.getSourceType());
+                        }
+                        break;
+                    case 2://搴撳尯
+                        if (retrieveMissionmMergeReservoirAreaIsItAvailable(taskPathTemplateMerge.getSourceType())){
+                            obtainOutboundStations.add(taskPathTemplateMerge.getSourceType());
+                        }
+                        break;
+                }
+            }
+        }
+
+        return obtainOutboundStations;
+    }
+
+    // 鏍规嵁绔欑偣妫�绱㈠鍣ㄦ槸鍚﹀彲琛岃嚦姝ょ珯鐐�
+    public boolean retrieveBarcodeIsItAvailableBySite(BasContainer containerByBarcode,BasStation basStation) {
+        if (basStation.getContainerType().contains(containerByBarcode.getContainerType())) {
+            return true;
+        }
+        return false;
+    }
+
+    // 鏍规嵁绔欑偣妫�绱㈠鍣ㄦ槸鍚﹀彲琛岃嚦姝ょ珯鐐�
+    public boolean retrieveBarcodeIsItAvailableBySite(String barcode,BasStation basStation) {
+        BasContainer containerByBarcode = getContainerByBarcode(barcode);
+        if (basStation.getContainerType().contains(containerByBarcode.getContainerType())) {
+            return true;
+        }
+        return false;
+    }
+
+
+    // 鏍规嵁绔欑偣妫�绱㈠鍣ㄦ槸鍚﹀彲琛岃嚦姝ょ珯鐐�
+    public boolean retrieveBarcodeIsItAvailableBySite(BasContainer containerByBarcode,String siteCode) {
+        BasStation basStation = retrieveMissionmMergeSizeIsItAvailable(siteCode);
+        if (Cools.isEmpty(basStation)){
+            return false;
+        }
+        if (basStation.getContainerType().contains(containerByBarcode.getContainerType())) {
+            return true;
+        }
+        return false;
+    }
+
+    // 鏍规嵁绔欑偣妫�绱㈠鍣ㄦ槸鍚﹀彲琛岃嚦姝ょ珯鐐�
+    public boolean retrieveBarcodeIsItAvailableBySite(String barcode,String siteCode) {
+        BasStation basStation = retrieveMissionmMergeSizeIsItAvailable(siteCode);
+        if (Cools.isEmpty(basStation)){
+            return false;
+        }
+        BasContainer containerByBarcode = getContainerByBarcode(barcode);
+        if (basStation.getContainerType().contains(containerByBarcode.getContainerType())) {
+            return true;
+        }
+
+        return false;
+    }
+
+    // 鏍规嵁绔欑偣妫�绱㈠簱鍖烘槸鍚﹀彲鍏ヨ嚦姝ょ珯鐐�
+    public boolean retrieveWarehouseAreasIsItAvailableInBySite(String warehouseCode,BasStation basStation) {
+        // TODO: 瀹炵幇閫昏緫
+
+        return false;
+    }
+
+    // 鏍规嵁绔欑偣妫�绱㈠簱鍖烘槸鍚﹀彲鍏ヨ嚦姝ょ珯鐐�
+    public boolean retrieveWarehouseAreasIsItAvailableInBySite(String warehouseCode,String siteCode) {
+        // TODO: 瀹炵幇閫昏緫
+        return false;
+    }
+
+    // 鏍规嵁绔欑偣妫�绱㈠簱鍖烘槸鍚﹀彲鍑鸿嚦姝ょ珯鐐�
+    public boolean retrieveWarehouseAreasIsItAvailableOutBySite(String warehouseCode,BasStation basStation) {
+        // TODO: 瀹炵幇閫昏緫
+        return false;
+    }
+
+    // 鏍规嵁绔欑偣妫�绱㈠簱鍖烘槸鍚﹀彲鍑鸿嚦姝ょ珯鐐�
+    public boolean retrieveWarehouseAreasIsItAvailableOutBySite(String warehouseCode,String siteCode) {
+        // TODO: 瀹炵幇閫昏緫
+        return false;
+    }
+
+    // 鏍规嵁绔欑偣妫�绱㈢鍚堟潯浠跺簱鍖�
+    public List<String> getWarehouseAreasBySite(String siteCode) {
+        // TODO: 瀹炵幇閫昏緫
+        return null;
+    }
+
+    // 鏍规嵁绔欑偣妫�绱㈢鍚堟潯浠跺鍣�
+    public List<BasContainer> getContainersBySite(String siteCode) {
+        // TODO: 瀹炵幇閫昏緫
+        return null;
+    }
+
+    // 鏍规嵁绔欑偣妫�绱㈢鍚堟潯浠朵换鍔$被鍨�
+    public List<String> getTaskTypesBySite(String siteCode) {
+        // TODO: 瀹炵幇閫昏緫
+        return null;
+    }
+
+    // 鏍规嵁鐗╂枡妫�绱㈢鍚堟潯浠跺簱鍖�
+    public List<String> getWarehouseAreasByMaterial(String materialCode) {
+        // TODO: 瀹炵幇閫昏緫
+        return null;
+    }
+
+    // 鏍规嵁鐗╂枡妫�绱㈢鍚堟潯浠跺鍣�
+    public List<BasContainer> getContainersByMaterial(String materialCode) {
+        // TODO: 瀹炵幇閫昏緫
+        return null;
+    }
+
+    // 鏍规嵁鐗╂枡妫�绱㈢鍚堟潯浠剁珯鐐�
+    public List<String> getSitesByMaterial(String materialCode) {
+        // TODO: 瀹炵幇閫昏緫
+        return null;
+    }
+
+    // 鏍规嵁搴撳尯妫�绱㈢鍚堟潯浠剁珯鐐�
+    public List<String> getSitesByWarehouseArea(String warehouseAreaCode) {
+        // TODO: 瀹炵幇閫昏緫
+        return null;
+    }
+
+    // 鏍规嵁绔欑偣\鐗╂枡妫�绱㈢鍚堟潯浠跺鍣�
+    public List<BasContainer> getContainersBySiteAndMaterial(String siteCode, String materialCode) {
+        // TODO: 瀹炵幇閫昏緫
+        return null;
+    }
+
+    // 鏍规嵁绔欑偣\鐗╂枡妫�绱㈢鍚堟潯浠跺簱鍖�
+    public List<String> getWarehouseAreasBySiteAndMaterial(String siteCode, String materialCode) {
+        // TODO: 瀹炵幇閫昏緫
+        return null;
+    }
+
+    // 鏍规嵁绔欑偣\鐗╂枡妫�绱㈢鍚堟潯浠惰矾寰�
+    public List<String> getPathsBySiteAndMaterial(String siteCode, String materialCode) {
+        // TODO: 瀹炵幇閫昏緫
+        return null;
+    }
+
+    // 鏍规嵁绔欑偣\鐗╂枡妫�绱㈢鍚堟潯浠朵换鍔$被鍨�
+    public List<String> getTaskTypesBySiteAndMaterial(String siteCode, String materialCode) {
+        // TODO: 瀹炵幇閫昏緫
+        return null;
+    }
+
+    // 鏍规嵁绔欑偣\鐗╂枡\瀹瑰櫒妫�绱㈢鍚堟潯浠跺簱鍖�
+    public List<String> getWarehouseAreasBySiteMaterialContainer(String siteCode, String materialCode, String containerType) {
+        // TODO: 瀹炵幇閫昏緫
+        return null;
+    }
+
+    // 鏍规嵁绔欑偣\鐗╂枡\瀹瑰櫒妫�绱㈢鍚堟潯浠朵换鍔$被鍨�
+    public List<String> getTaskTypesBySiteMaterialContainer(String siteCode, String materialCode, String containerType) {
+        // TODO: 瀹炵幇閫昏緫
+        return null;
+    }
+
+    // 鏍规嵁绔欑偣\瀹瑰櫒妫�绱㈢鍚堟潯浠跺鍣�
+    public List<BasContainer> getContainersBySiteAndContainerType(String siteCode, String containerType) {
+        // TODO: 瀹炵幇閫昏緫
+        return null;
+    }
+
+    // 鏍规嵁绔欑偣\瀹瑰櫒妫�绱㈢鍚堟潯浠跺簱鍖�
+    public List<String> getWarehouseAreasBySiteAndContainer(String siteCode, String containerType) {
+        // TODO: 瀹炵幇閫昏緫
+        return null;
+    }
+
+    // 鏍规嵁绔欑偣\瀹瑰櫒妫�绱㈢鍚堟潯浠惰矾寰�
+    public List<String> getPathsBySiteAndContainer(String siteCode, String containerType) {
+        // TODO: 瀹炵幇閫昏緫
+        return null;
+    }
+
+    // 鏍规嵁绔欑偣\瀹瑰櫒妫�绱㈢鍚堟潯浠朵换鍔$被鍨�
+    public List<String> getTaskTypesBySiteAndContainer(String siteCode, String containerType) {
+        // TODO: 瀹炵幇閫昏緫
+        return null;
+    }
+
+    // 鍑哄簱鏍¢獙锛氭牴鎹簮搴撳尯\鐩爣绔欑偣\瀹瑰櫒鍒ゆ柇鏄惁瀛樺湪璺緞
+    public boolean queryPathIsItAvailableOutArea(Long sourceCode, String targetCode, String barcode,Integer type) {
+        return queryPathIsItAvailableOutArea(sourceCode.toString(),targetCode,barcode,type.toString());
+    }
+    public boolean queryPathIsItAvailableOutArea(String sourceCode, String targetCode, String barcode,Integer type) {
+        return queryPathIsItAvailableOutArea(sourceCode,targetCode,barcode,type.toString());
+    }
+    public boolean queryPathIsItAvailableOutArea(String sourceCode, String targetCode, String barcode,String type) {
+        if (queryPathIsItAvailable(sourceCode, targetCode, barcode)){
+            BasStation basStation = basStationService.getOne(new LambdaQueryWrapper<BasStation>()
+                    .eq(BasStation::getStationName, targetCode).last("limit 1"));
+            if (!Cools.isEmpty(basStation)){
+                if (type.equals("in")){
+                    if (basStation.getInAble()==1){
+                        return true;
+                    }
+                } else if (type.equals("out")){
+                    if (basStation.getOutAble()==1){
+                        return true;
+                    }
+                }
+                BasStationTypeService basStationTypeService = SpringUtils.getBean(BasStationTypeService.class);
+                BasStationType one = basStationTypeService.getOne(new LambdaQueryWrapper<BasStationType>().eq(BasStationType::getStationTypeCode, basStation.getContainerType()).last("limit 1"));
+                if (!Cools.isEmpty(one)) {
+                    if (one.getTaskType().contains(type)){
+                        return true;
+                    }
+                    log.error("鐩爣绔欑偣:" + targetCode+" 涓嶆敮鎸佷綔涓氭浠诲姟绫诲瀷锛�"+type);
+                }
+                log.error("鐩爣绔欑偣:" + targetCode+" 涓嶆敮鎸佷綔涓氭浠诲姟绫诲瀷锛�"+type);
+            }
+            log.error("queryPathIsItAvailableInArea: error");
+        }
+        return false;
+    }
+
+    // 鍑哄簱鏍¢獙锛氭牴鎹簮绔欑偣\鐩爣搴撳尯\瀹瑰櫒鍒ゆ柇鏄惁瀛樺湪璺緞
+    public boolean queryPathIsItAvailableInArea(String sourceCode, Long targetCode, String barcode,String type) {
+        return queryPathIsItAvailableInArea(sourceCode,targetCode.toString(),barcode,type);
+    }
+    public boolean queryPathIsItAvailableInArea(String sourceCode, Long targetCode, String barcode,Integer type) {
+        return queryPathIsItAvailableInArea(sourceCode,targetCode.toString(),barcode,type.toString());
+    }
+    public boolean queryPathIsItAvailableInArea(String sourceCode, String targetCode, String barcode,Integer type) {
+        return queryPathIsItAvailableInArea(sourceCode,targetCode,barcode,type.toString());
+    }
+    public boolean queryPathIsItAvailableInArea(String sourceCode, String targetCode, String barcode,String type) {
+        if (queryPathIsItAvailable(sourceCode, targetCode, barcode)){
+            BasStation basStation = basStationService.getOne(new LambdaQueryWrapper<BasStation>()
+                    .eq(BasStation::getStationName, sourceCode).last("limit 1"));
+            if (!Cools.isEmpty(basStation)){
+                if (type.equals("in")){
+                    if (basStation.getInAble()==1){
+                        return true;
+                    }
+                } else if (type.equals("out")){
+                    if (basStation.getOutAble()==1){
+                        return true;
+                    }
+                }
+                BasStationTypeService basStationTypeService = SpringUtils.getBean(BasStationTypeService.class);
+                BasStationType one = basStationTypeService.getOne(new LambdaQueryWrapper<BasStationType>().eq(BasStationType::getStationTypeCode, basStation.getContainerType()).last("limit 1"));
+                if (!Cools.isEmpty(one)) {
+                    if (one.getTaskType().contains(type)){
+                        return true;
+                    }
+                    log.error("褰撳墠绔欑偣:" + sourceCode+" 涓嶆敮鎸佷綔涓氭浠诲姟绫诲瀷锛�"+type);
+                }
+                log.error("褰撳墠绔欑偣:" + sourceCode+" 涓嶆敮鎸佷綔涓氭浠诲姟绫诲瀷锛�"+type);
+            }
+            log.error("queryPathIsItAvailableInArea: error");
+        }
+        return false;
+    }
+
+    // 鏍¢獙锛氭牴鎹捣鐐筡鐩爣鐐筡瀹瑰櫒鍒ゆ柇鏄惁瀛樺湪璺緞
+    private boolean queryPathIsItAvailable(String sourceCode, String targetCode, String barcode) {
+        BasContainer containerByBarcode = getContainerByBarcode(barcode);
+        if (containerByBarcode == null) {
+            return false;
+        }
+        if (retrieveMissionmMergeReservoirAreaIsItAvailable(sourceCode)){
+            BasStation basStation = retrieveMissionmMergeSizeIsItAvailable(targetCode);
+            if (!Cools.isEmpty(basStation)){
+                return queryPathIsItAvailable(sourceCode, targetCode, containerByBarcode);
+            } else {
+                if (retrieveMissionmMergeReservoirAreaIsItAvailable(targetCode)){
+                    return queryPathIsItAvailable(sourceCode, targetCode, containerByBarcode);
+                }
+                log.error("璺緞鏍¢獙锛氭牴鎹捣鐐�:"+sourceCode+"銆佺洰鏍囩偣:"+targetCode+"銆佸鍣ㄨ鍒欙細" +containerByBarcode.getCodeType()+ "鍒ゆ柇鏄惁瀛樺湪璺緞==>缁堢偣绫诲瀷鏈煡锛侊紒锛�");
+            }
+        } else if (retrieveMissionmMergeReservoirAreaIsItAvailable(targetCode)){
+            BasStation basStation = retrieveMissionmMergeSizeIsItAvailable(sourceCode);
+            if (!Cools.isEmpty(basStation)){
+                return queryPathIsItAvailable(sourceCode, targetCode, containerByBarcode);
+            }
+            log.error("璺緞鏍¢獙锛氭牴鎹捣鐐�:"+sourceCode+"銆佺洰鏍囩偣:"+targetCode+"銆佸鍣ㄨ鍒欙細" +containerByBarcode.getCodeType()+ "鍒ゆ柇鏄惁瀛樺湪璺緞==>璧风偣绫诲瀷鏈煡锛侊紒锛�");
+        } else {
+            BasStation basStationS = retrieveMissionmMergeSizeIsItAvailable(sourceCode);
+            BasStation basStationT = retrieveMissionmMergeSizeIsItAvailable(targetCode);
+            if (!Cools.isEmpty(basStationS) &&  !Cools.isEmpty(basStationT)){
+                return queryPathIsItAvailable(sourceCode, targetCode, containerByBarcode);
+            }
+            log.error("璺緞鏍¢獙锛氭牴鎹捣鐐�:"+sourceCode+"銆佺洰鏍囩偣:"+targetCode+"銆佸鍣ㄨ鍒欙細" +containerByBarcode.getCodeType()+ "鍒ゆ柇鏄惁瀛樺湪璺緞==>璧风偣涓庣粓鐐圭被鍨嬫湭鐭ワ紒锛侊紒");
+        }
+        return false;
+    }
+
+
+    // 鏍¢獙锛氭牴鎹捣鐐筡鐩爣鐐筡瀹瑰櫒鍒ゆ柇鏄惁瀛樺湪璺緞
+    private boolean queryPathIsItAvailable(String sourceCode, String targetCode, BasContainer containerByBarcode) {
+        try{
+            TaskPathTemplateMergeService taskPathTemplateMergeService = SpringUtils.getBean(TaskPathTemplateMergeService.class);
+            List<TaskPathTemplateMerge> taskPathTemplateMergeList = taskPathTemplateMergeService.list(new LambdaQueryWrapper<TaskPathTemplateMerge>()
+                    .eq(TaskPathTemplateMerge::getSourceType, sourceCode)
+                    .eq(TaskPathTemplateMerge::getTargetType, targetCode)
+                    .apply("container_type != '[]'")  // 涓嶆槸绌烘暟缁�
+                    .apply("JSON_CONTAINS(container_type, {0}) = 1", containerByBarcode.getContainerType().toString())
+            );
+            if (Objects.isNull(taskPathTemplateMergeList) || taskPathTemplateMergeList.isEmpty()) {
+                List<TaskPathTemplateMerge> list = taskPathTemplateMergeService.list(new LambdaQueryWrapper<TaskPathTemplateMerge>()
+                        .eq(TaskPathTemplateMerge::getStepSize, 1)
+                        .apply("container_type != '[]'")  // 涓嶆槸绌烘暟缁�
+                        .apply("JSON_CONTAINS(container_type, {0}) = 1", containerByBarcode.getContainerType().toString())
+                );
+                if (!Cools.isEmpty(list)) {
+                    List<String[]> stationList = new ArrayList<>();
+                    list.forEach(taskPathTemplate -> {
+                        stationList.add(taskPathTemplate.route());
+                    });
+                    List<Long> longs = RouteWmsStepFlow.routeGet(stationList, targetCode, sourceCode);
+                    if (longs != null && !longs.isEmpty()) {
+                        return true;
+                    }
+                }
+                log.error("璺緞鏍¢獙锛氭牴鎹捣鐐�:"+sourceCode+"銆佺洰鏍囩偣:"+targetCode+"銆佸鍣ㄨ鍒欙細" +containerByBarcode.getCodeType()+ "鍒ゆ柇鏄惁瀛樺湪璺緞==>鏈壘鍒拌矾寰勶紒锛侊紒");
+            } else {
+                return true;
+            }
+        } catch (Exception e) {
+            log.error("璺緞鏍¢獙锛氭牴鎹捣鐐�:"+sourceCode+"銆佺洰鏍囩偣:"+targetCode+"銆佸鍣ㄨ鍒欙細" +containerByBarcode.getCodeType()+ "鍒ゆ柇鏄惁瀛樺湪璺緞==>寮傚父:"+e.getMessage());
+        }
+        return false;
+    }
+
+
+}
diff --git a/rsf-server/src/main/java/com/vincent/rsf/server/system/entity/TaskPathTemplateMerge.java b/rsf-server/src/main/java/com/vincent/rsf/server/system/entity/TaskPathTemplateMerge.java
index 4331b2b..c796aeb 100644
--- a/rsf-server/src/main/java/com/vincent/rsf/server/system/entity/TaskPathTemplateMerge.java
+++ b/rsf-server/src/main/java/com/vincent/rsf/server/system/entity/TaskPathTemplateMerge.java
@@ -197,6 +197,13 @@
     @TableField(typeHandler = JacksonTypeHandler.class)
     private List<String> targetTypeR;
 
+    /**
+     * 瀹瑰櫒绫诲瀷
+     */
+    @ApiModelProperty(value = "瀹瑰櫒绫诲瀷")
+    @TableField(typeHandler = JacksonTypeHandler.class)
+    private List<Integer> containerType;
+
     public TaskPathTemplateMerge() {}
 
     public String getEffectiveTime$(){
diff --git a/rsf-server/src/main/java/matnrRestrictionWarehouse.sql b/rsf-server/src/main/java/matnrRestrictionWarehouse.sql
new file mode 100644
index 0000000..9732d1f
--- /dev/null
+++ b/rsf-server/src/main/java/matnrRestrictionWarehouse.sql
@@ -0,0 +1,24 @@
+-- save matnrRestrictionWarehouse record
+-- mysql
+insert into `sys_menu` ( `name`, `parent_id`, `route`, `component`, `type`, `sort`, `tenant_id`, `status`) values ( 'menu.matnrRestrictionWarehouse', '0', '/manager/matnrRestrictionWarehouse', 'matnrRestrictionWarehouse', '0' , '0', '1' , '1');
+
+insert into `sys_menu` ( `name`, `parent_id`, `type`, `authority`, `sort`, `tenant_id`, `status`) values ( 'Query 鐗╂枡闄愬埗', '', '1', 'manager:matnrRestrictionWarehouse:list', '0', '1', '1');
+insert into `sys_menu` ( `name`, `parent_id`, `type`, `authority`, `sort`, `tenant_id`, `status`) values ( 'Create 鐗╂枡闄愬埗', '', '1', 'manager:matnrRestrictionWarehouse:save', '1', '1', '1');
+insert into `sys_menu` ( `name`, `parent_id`, `type`, `authority`, `sort`, `tenant_id`, `status`) values ( 'Update 鐗╂枡闄愬埗', '', '1', 'manager:matnrRestrictionWarehouse:update', '2', '1', '1');
+insert into `sys_menu` ( `name`, `parent_id`, `type`, `authority`, `sort`, `tenant_id`, `status`) values ( 'Delete 鐗╂枡闄愬埗', '', '1', 'manager:matnrRestrictionWarehouse:remove', '3', '1', '1');
+
+-- locale menu name
+matnrRestrictionWarehouse: 'MatnrRestrictionWarehouse',
+
+-- locale field
+matnrRestrictionWarehouse: {
+    productionLineCode: "productionLineCode",
+    productionLineName: "productionLineName",
+    matnrRestrictionCode: "matnrRestrictionCode",
+},
+
+-- ResourceContent
+import matnrRestrictionWarehouse from './matnrRestrictionWarehouse';
+
+case 'matnrRestrictionWarehouse':
+    return matnrRestrictionWarehouse;
diff --git a/rsf-server/src/main/resources/mapper/manager/BasStationTypeMapper.xml b/rsf-server/src/main/resources/mapper/manager/BasStationTypeMapper.xml
new file mode 100644
index 0000000..42207f7
--- /dev/null
+++ b/rsf-server/src/main/resources/mapper/manager/BasStationTypeMapper.xml
@@ -0,0 +1,5 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
+<mapper namespace="com.vincent.rsf.server.manager.mapper.BasStationTypeMapper">
+
+</mapper>
diff --git a/rsf-server/src/main/resources/mapper/manager/MatnrRestrictionWarehouseMapper.xml b/rsf-server/src/main/resources/mapper/manager/MatnrRestrictionWarehouseMapper.xml
new file mode 100644
index 0000000..535596f
--- /dev/null
+++ b/rsf-server/src/main/resources/mapper/manager/MatnrRestrictionWarehouseMapper.xml
@@ -0,0 +1,5 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
+<mapper namespace="com.vincent.rsf.server.manager.mapper.MatnrRestrictionWarehouseMapper">
+
+</mapper>

--
Gitblit v1.9.1