<script setup lang="ts">
import type { VbenFormProps } from '#/adapter/form';
import type { VxeGridProps } from '#/adapter/vxe-table';

import { computed, nextTick, onMounted, ref, watch } from 'vue';
import { useRoute } from 'vue-router';

import { Page } from '@vben/common-ui';

import { useDebounceFn } from '@vueuse/core';

import { useVbenVxeGrid } from '#/adapter/vxe-table';
import {
  postTreeModelDeviceDataInfoPage,
} from '#/api-client';
import { $t } from '#/locales';

import { generateDynamicColumns } from './dynamicColumns';
import { querySchema } from './schema';

defineOptions({
  name: 'DeviceData',
});

// 格式化日期为 yyyy-MM-dd HH:mm:ss 格式
const formatDate = (date: Date | string) => {
  if (!date) return undefined;

  const d = new Date(date);
  if (isNaN(d.getTime())) return undefined;

  const year = d.getFullYear();
  const month = String(d.getMonth() + 1).padStart(2, '0');
  const day = String(d.getDate()).padStart(2, '0');
  const hours = String(d.getHours()).padStart(2, '0');
  const minutes = String(d.getMinutes()).padStart(2, '0');
  const seconds = String(d.getSeconds()).padStart(2, '0');

  return `${year}-${month}-${day} ${hours}:${minutes}:${seconds}`;
};

const route = useRoute();
const { IoTDataType, DeviceAddress } = route.query;

// 动态列定义
const dynamicColumns = ref<any[]>([]);

// 固定列定义（基础列，始终显示）- 基于 IoTDBTreeModelDeviceDataDto 类型
const fixedBaseColumns = [
  { title: '序号', type: 'seq', width: 50, field: 'seq', slots: {} },
  {
    field: 'TimestampStr',
    title: $t('abp.IoTDBBase.Timestamps'),
    minWidth: 150,
    showOverflow: true,
    slots: {},
  },
  {
    field: 'FormattedTimestamps',
    title: $t('abp.IoTDBBase.FormattedTimestamps'),
    minWidth: 150,
    showOverflow: true,
    slots: {},
  },
  {
    field: 'IoTDataType',
    title: $t('abp.IoTDBBase.IoTDataType'),
    minWidth: 150,
    showOverflow: true,
    slots: {},
  },
  {
    field: 'DeviceAddress',
    title: $t('abp.IoTDBBase.DeviceAddress'),
    minWidth: 150,
    showOverflow: true,
    slots: {},
  },
  {
    field: 'SubDevice',
    title: $t('abp.IoTDBBase.SubDevice'),
    minWidth: 150,
    showOverflow: true,
    slots: {},
  },
];

// 合并固定列和动态列 - 使用计算属性确保响应式
const allColumns = computed(() => {
  const columns = [...fixedBaseColumns];

  // 安全地添加动态列
  if (dynamicColumns.value && Array.isArray(dynamicColumns.value)) {
    const validDynamicColumns = dynamicColumns.value
      .filter((col) => col && typeof col === 'object' && col.field && col.title)
      .map((col) => ({
        ...col,
        slots: col.slots || {}, // 确保每个列都有slots属性
      }));
    columns.push(...validDynamicColumns);
  }

  return columns;
});

// 表格是否已初始化
const isGridInitialized = ref(false);
// 是否正在初始化，用于防止重复查询
const isInitializing = ref(false);

// 设备下拉自动选中真实路径时会连续触发多次表单值变化（原值 → 清空 → 完整路径），
// 用防抖把这些变化合并为一次查询，并在执行时读取“最终”表单值，
// 避免多次并发查询竞态导致空结果覆盖有数据结果。
// 记录上一次实际发起查询的条件签名，避免“自动选中触发”与“初始化兜底触发”
// 在同一完整路径下重复投递 DeviceDataInfoPage（两次都带数据、但纯属多余）。
const lastReloadSig = ref<string>('');
const debouncedReload = useDebounceFn(async () => {
  if (!gridApi?.formApi) {
    return;
  }
  const values = await gridApi.formApi.getValues();
  if (values.DeviceAddress && values.IoTDataType) {
    const sig = [
      values.IoTDataType,
      values.DeviceAddress,
      values.StartCreationTime,
      values.EndCreationTime,
    ].join('|');
    if (sig === lastReloadSig.value) {
      return;
    }
    lastReloadSig.value = sig;
    gridApi.reload(values);
  }
}, 200);

const formOptions: VbenFormProps = {
  schema: querySchema.value,
  initialValues: {
    IoTDataType: IoTDataType as string,
    DeviceAddress: DeviceAddress as string,
  },
  // 禁用表单值变化时自动提交，使用自定义处理函数
  submitOnChange: false,
  // 添加表单值变化的处理函数
  handleValuesChange: async (values, changedFields) => {
    // IoTDataType 变化时：清空 DeviceAddress，但不触发数据查询。
    // 初始化回填期间跳过，避免把路由带来的预设设备地址联动清空。
    if (changedFields.includes('IoTDataType')) {
      if (isInitializing.value) {
        return;
      }
      const currentValues = await gridApi.formApi.getValues();
      if (currentValues.DeviceAddress) {
        await gridApi.formApi.setFieldValue('DeviceAddress', undefined);
      }
      return;
    }

    // DeviceAddress 变化时：只要同时有 IoTDataType 就触发数据查询（防抖合并连续变化）。
    // 注意：此处不受初始化拦截——设备下拉异步自动选中真实设备标识（完整树路径）后，正是靠这里触发 DeviceDataInfoPage 查询。
    if (changedFields.includes('DeviceAddress')) {
      debouncedReload();
      return;
    }

    // 其他字段变化（时间范围）：初始化期间跳过
    if (isInitializing.value) {
      return;
    }
    const relevantFields = new Set([
      'EndCreationTime',
      'StartCreationTime',
    ]);
    const hasRelevantChange = changedFields.some((field) =>
      relevantFields.has(field),
    );

    if (hasRelevantChange) {
      debouncedReload();
    }
  },
};

const gridOptions: VxeGridProps<any> = {
  checkboxConfig: {
    highlight: true,
    labelField: 'name',
  },
  columns: fixedBaseColumns, // 初始化时只使用基础固定列
  height: 'auto',
  keepSource: true,
  // 确保分页功能正常工作
  pager: true,
  pagerConfig: {
    currentPage: 1,
    pageSize: 20,
  },
  toolbarConfig: {
    custom: true,
  },
  customConfig: {
    storage: true,
  },
  // 添加调试配置
  showOverflow: true,
  showHeaderOverflow: true,
  proxyConfig: {
    // 关闭挂载时的自动查询：初始表单里的设备地址是路由带来的“原始地址”，
    // 直接作为 DevicePath 查询必然 204；真正的查询由设备下拉自动选中真实树路径后经防抖触发。
    autoLoad: false,
    ajax: {
      query: async ({ page, sorts, filters }, formValues) => {
        // 确保page参数存在
        if (!page) {
          return { items: [], totalCount: 0 };
        }

        // 获取当前表单值
        const currentFormValues =
          formValues ||
          (gridApi?.formApi ? await gridApi.formApi.getValues() : {}) ||
          {};

        // 如果表单中没有DeviceAddress，但有路由参数，使用路由参数
        if (!currentFormValues.DeviceAddress && DeviceAddress) {
          currentFormValues.DeviceAddress = DeviceAddress as string;
        }

        // 如果表单中没有IoTDataType，但有路由参数，使用路由参数
        if (!currentFormValues.IoTDataType && IoTDataType) {
          currentFormValues.IoTDataType = IoTDataType as string;
        }

        // 条件检查：只有同时有 IoTDataType 和 DeviceAddress 才发起查询
        if (!currentFormValues.IoTDataType || !currentFormValues.DeviceAddress) {
          console.log('跳过查询：缺少必要参数', {
            IoTDataType: currentFormValues.IoTDataType,
            DeviceAddress: currentFormValues.DeviceAddress,
          });
          return { items: [], totalCount: 0 };
        }

        // 处理筛选字段
        const ioTDataTypeValue = currentFormValues.IoTDataType;

        // 调试：打印表单值和路由参数
        console.log('表单值:', currentFormValues);
        console.log('路由参数:', { IoTDataType, DeviceAddress });

        // 处理日期范围参数
        const startCreationTime = currentFormValues.StartCreationTime
          ? formatDate(currentFormValues.StartCreationTime)
          : undefined;
        const endCreationTime = currentFormValues.EndCreationTime
          ? formatDate(currentFormValues.EndCreationTime)
          : undefined;

        // 获取选中的设备地址
        const deviceAddress = currentFormValues.DeviceAddress || '';

        // 如果表单中没有DeviceAddress，但有路由参数，使用路由参数
        const finalDeviceAddress = deviceAddress || (DeviceAddress as string);

        try {
          // 调试：打印请求参数
          console.log('API请求参数:', {
            pageIndex: page.currentPage,
            pageSize: page.pageSize,
            DevicePath: finalDeviceAddress,
            IoTDataType: ioTDataTypeValue,
            StartCreationTime: startCreationTime,
            EndCreationTime: endCreationTime,
          });

          const { data } = await postTreeModelDeviceDataInfoPage({
            body: {
              pageIndex: page.currentPage,
              pageSize: page.pageSize,
              DevicePath: finalDeviceAddress,
              IoTDataType: ioTDataTypeValue || undefined,
              StartCreationTime: startCreationTime || undefined,
              EndCreationTime: endCreationTime || undefined,
            },
          });

          // 简化处理逻辑，直接使用接口返回的数据
          if (data?.items && data.items.length > 0) {
            try {
              // 动态生成列定义
              const generatedColumns = generateDynamicColumns(data.items);

              // 更新动态列
              dynamicColumns.value = generatedColumns;

              // 使用setState更新整个gridOptions，确保列定义能够正确更新
              await nextTick();
              if (gridApi && gridApi.setState) {
                gridApi.setState({
                  gridOptions: {
                    ...gridOptions,
                    columns: allColumns.value,
                    // 保持分页配置
                    pager: true,
                    pagerConfig: gridOptions.pagerConfig,
                  },
                });
              }
            } catch (error) {
              console.error('更新列定义时出错:', error);
              // 如果列更新失败，使用空数组
              dynamicColumns.value = [];
            }

            // 直接使用接口返回的totalCount
            const result = {
              items: data.items || [],
              totalCount: data.totalCount || 0,
            };

            return result;
          }
          return {
            items: [],
            totalCount: 0,
          };
        } catch (error) {
          console.error('API调用出错:', error);
          throw error;
        }
      },
    },
  },
};

const [Grid, gridApi] = useVbenVxeGrid({ formOptions, gridOptions });

// 监听分页器状态变化
watch(
  () => gridApi?.pagerApi?.pageSize,
  (newSize, oldSize) => {
    if (newSize !== oldSize && oldSize && !isInitializing.value) {
      // 重置到第一页
      gridApi.pagerApi.currentPage = 1;
      // 触发数据重新加载
      gridApi.reload();
    }
  },
);

// 监听当前页变化
watch(
  () => gridApi?.pagerApi?.currentPage,
  (newPage, oldPage) => {
    if (newPage !== oldPage && oldPage && !isInitializing.value) {
      // 触发数据重新加载
      gridApi.reload();
    }
  },
);

// 初始化函数
const initializeGrid = async () => {
  try {
    // 设置初始化标志
    isInitializing.value = true;

    // 标记表格已初始化
    isGridInitialized.value = true;

    // 更新表格列定义
    if (gridApi && gridApi.setState) {
      await nextTick();
      gridApi.setState({
        gridOptions: {
          ...gridOptions,
          columns: allColumns.value,
          // 保持分页配置
          pager: true,
          pagerConfig: gridOptions.pagerConfig,
        },
      });
    }

    // 如果有路由参数，自动触发查询
    if (IoTDataType || DeviceAddress) {
      // 延迟一下确保表格已完全初始化
      setTimeout(async () => {
        if (gridApi && gridApi.formApi) {
          // 确保表单值正确设置
          const currentValues = await gridApi.formApi.getValues();
          const updatedValues = { ...currentValues };

          if (!currentValues.DeviceAddress && DeviceAddress) {
            updatedValues.DeviceAddress = DeviceAddress as string;
          }

          if (!currentValues.IoTDataType && IoTDataType) {
            updatedValues.IoTDataType = IoTDataType as string;
          }

          // 回填路由带来的数据类型与设备地址（触发数据类型选择、设备下拉按类型/地址加载）
          await gridApi.formApi.setValues(updatedValues);
          // 等待表单值更新完成
          await nextTick();

          isInitializing.value = false;

          // 兜底触发一次查询（防抖，执行时读取最终表单值）：覆盖“设备下拉未产生地址变更”的情况；
          // 与自动选中引发的变更查询共用同一防抖，合并为单次查询，避免并发竞态。
          debouncedReload();
        } else {
          isInitializing.value = false;
        }
      }, 300);
    } else {
      // 如果没有路由参数，直接清除初始化标志
      isInitializing.value = false;
    }
  } catch (error) {
    console.error('初始化表格失败:', error);
    isInitializing.value = false;
  }
};

// 监听路由参数变化，当有路由参数时自动触发查询
watch(
  () => [IoTDataType, DeviceAddress],
  async (newValues, oldValues) => {
    // 如果正在初始化，不触发额外的查询
    if (isInitializing.value || !isGridInitialized.value) {
      return;
    }

    // 只有当路由参数真正发生变化时才触发查询
    const hasChanged =
      oldValues &&
      (newValues[0] !== oldValues[0] || newValues[1] !== oldValues[1]);

    if (hasChanged && newValues.some(Boolean) && gridApi) {
      // 延迟一下确保表单值已经设置
      setTimeout(() => {
        gridApi.reload();
      }, 100);
    }
  },
  { immediate: false }, // 改为false，避免立即触发
);

// 页面初始化时，延迟初始化表格
onMounted(async () => {
  // 延迟初始化，确保VXE表格组件已完全挂载
  setTimeout(async () => {
    await initializeGrid();
  }, 100);
});
</script>

<template>
  <Page auto-content-height>
    <Grid />
  </Page>
</template>
