<template>
  <Spin v-if="metadata.properties?.length" :spinning="loading">
    <Card :bordered="false" borderStyle="padding: 0">
      <template #extra>
        <Space>
          <Button @click="visible = true">批量映射</Button>
          <Button type="primary" @click="onSave">保存</Button>
        </Space>
      </template>
      <Form ref="formRef" :model="modelRef">
        <Table :dataSource="modelRef.dataSource" :columns="columns">
          <template #headerCell="{ column }">
            <template v-if="column.key === 'collectorId'">
              采集器
              <Tooltip title="数据采集中配置的真实物理设备">
                <AIcon type="QuestionCircleOutlined" />
              </Tooltip>
            </template>
          </template>
          <template #bodyCell="{ column, record, index }">
            <template v-if="column.dataIndex === 'channelId'">
              <FormItem :name="['dataSource', index, 'channelId']">
                <Select
                  style="width: 100%"
                  v-model:value="record[column.dataIndex]"
                  placeholder="请选择"
                  allowClear
                  :filter-option="filterOption"
                  :options="channelList"
                  @select="
                    (_, option) => {
                      record.provider = option.provider;
                    }
                  "
                />
              </FormItem>
            </template>
            <template v-if="column.dataIndex === 'collectorId'">
              <FormItem
                :name="['dataSource', index, 'collectorId']"
                :rules="[
                  {
                    required: !!record.channelId,
                    message: '请选择采集器'
                  }
                ]"
              >
                <MSelect v-model="record[column.dataIndex]" :id="record.channelId" type="COLLECTOR" />
              </FormItem>
            </template>
            <template v-if="column.dataIndex === 'pointId'">
              <FormItem
                :name="['dataSource', index, 'pointId']"
                :rules="[
                  {
                    required: !!record.channelId,
                    message: '请选择点位'
                  }
                ]"
              >
                <MSelect v-model="record[column.dataIndex]" :id="record.collectorId" type="POINT" />
              </FormItem>
            </template>
            <template v-if="column.dataIndex === 'id'">
              <Badge v-if="record[column.dataIndex]" status="success" text="已绑定" />
              <Badge v-else status="error" text="未绑定" />
            </template>
            <template v-if="column.key === 'action'">
              <Tooltip title="解绑">
                <Popconfirm title="确认解绑" :disabled="!record.id" @confirm="unbind(record.id)">
                  <Button type="link" :disabled="!record.id"><AIcon type="icon-jiebang" /></Button>
                </Popconfirm>
              </Tooltip>
            </template>
          </template>
        </Table>
      </Form>
    </Card>
    <PatchMapping
      :deviceId="instanceStore.current.id"
      v-if="visible"
      @close="visible = false"
      @save="onPatchBind"
      :type="provider"
      :metaData="modelRef.dataSource"
    />
  </Spin>
  <Card v-else :bordered="false" borderStyle="padding: 0">
    <JEmpty description="暂无数据，请配置物模型" style="margin: 10% 0" />
  </Card>
</template>

<script lang="ts" setup>
  import { ref, reactive, onMounted, toRaw } from 'vue';
  import { useInstanceStore } from '@jdlinker/func';
  import { queryMapping, saveMapping, removeMapping, queryChannelNoPaging } from '../../../../../../api/device/instance';
  import MSelect from '../MSelect.vue';
  import PatchMapping from './PatchMapping.vue';
  import { onlyMessage } from '@jdlinker/utils';
  import { JEmpty } from '@jdlinker/ui';
  import {
    Spin,
    Card,
    Space,
    Tooltip,
    Table,
    Form,
    FormItem,
    Button,
    AIcon,
    Select,
    Badge,
    Popconfirm
  } from 'linker-ui-components';

  const columns = [
    {
      title: '名称',
      dataIndex: 'metadataName',
      key: 'metadataName',
      width: '20%'
    },
    {
      title: '通道',
      dataIndex: 'channelId',
      key: 'channelId',
      width: '20%'
    },
    {
      title: '采集器',
      dataIndex: 'collectorId',
      key: 'collectorId',
      width: '20%'
    },
    {
      title: '点位',
      key: 'pointId',
      dataIndex: 'pointId',
      width: '20%'
    },
    {
      title: '状态',
      key: 'id',
      dataIndex: 'id',
      width: '10%'
    },
    {
      title: '操作',
      key: 'action',
      width: '10%'
    }
  ];

  const filterOption = (input: string, option: any) => {
    return option.label.toLowerCase().indexOf(input.toLowerCase()) >= 0;
  };

  const props = defineProps({
    provider: {
      type: String,
      default: 'MODBUS_TCP'
    }
  });

  const instanceStore = useInstanceStore();
  const metadata = JSON.parse(instanceStore.current?.metadata || '{}');
  const loading = ref<boolean>(false);
  const channelList = ref([]);

  const modelRef = reactive({
    dataSource: []
  });

  const formRef = ref();
  const visible = ref<boolean>(false);

  const getChannel = async () => {
    const resp: any = await queryChannelNoPaging({
      paging: false
      // terms: [
      //     {
      //         terms: [
      //             {
      //                 column: 'provider',
      //                 value: props.provider,
      //             },
      //         ],
      //     },
      // ],
    });
    if (resp.code === 200) {
      channelList.value = resp.result?.map((item: any) => ({
        label: item.name,
        value: item.id,
        provider: item.provider
      }));
    }
  };

  const handleSearch = async () => {
    loading.value = true;
    getChannel();
    const _metadata =
      metadata.properties?.map?.((item: any) => ({
        metadataId: item.id,
        metadataName: `${item.name}(${item.id})`,
        metadataType: 'property',
        name: item.name
      })) || [];
    if (_metadata && _metadata.length) {
      const resp: any = await queryMapping('device', instanceStore.current.id);
      if (resp.code === 200) {
        const array = resp.result.reduce((x: any, y: any) => {
          const metadataId = _metadata.find((item: any) => item.metadataId === y.metadataId);
          if (metadataId) {
            Object.assign(metadataId, y);
          } else {
            x.push(y);
          }
          return x;
        }, _metadata);
        modelRef.dataSource = array;
      }
    }
    loading.value = false;
  };

  const unbind = async (id: string) => {
    if (id) {
      const resp = await removeMapping('device', instanceStore.current.id, [id]);
      if (resp.code === 200) {
        onlyMessage('操作成功！');
        handleSearch();
      }
    }
  };

  const onPatchBind = () => {
    visible.value = false;
    handleSearch();
  };

  onMounted(() => {
    handleSearch();
  });

  const onSave = () => {
    formRef.value
      .validate()
      .then(async () => {
        const arr = toRaw(modelRef).dataSource.filter((i: any) => i.channelId);
        if (arr && arr.length !== 0) {
          const resp = await saveMapping(instanceStore.current.id, props.provider, arr);
          if (resp.code === 200) {
            onlyMessage('操作成功！');
            handleSearch();
          }
        }
      })
      .catch((err: any) => {
        console.log('error', err);
      });
  };
</script>

<style lang="less" scoped>
  :deep(.ant-form-item) {
    margin: 0 !important;
  }
</style>
