<script setup lang="ts">
import { reactive, ref, onMounted } from 'vue';
import { PageContainer } from '@ant-design-vue/pro-layout';
import { message } from 'ant-design-vue/lib';
import useI18n from '@/hooks/useI18n';
import { RESULT_CODE_SUCCESS } from '@/constants/result-constants';
import {
  getParamConfigTopTab,
  getParamConfigInfoForm,
  updateParamConfigInfo,
  delParamConfigInfo,
  addParamConfigInfo,
} from '@/api/configManage/configParam';
import useNeInfoStore from '@/store/modules/neinfo';
import { toRaw } from 'vue';
import { regExpIPv4, regExpIPv6 } from '@/utils/regular-utils';
import { SizeType } from 'ant-design-vue/lib/config-provider';
import { DataNode } from 'ant-design-vue/lib/tree';
const { t } = useI18n();

/**网元参数 */
let neCascaderOtions = ref<Record<string, any>[]>([]);

/**网元类型选择 type,id */
let neTypeSelect = ref<string[]>(['', '']);

/**对象信息状态类型 */
type TreeStateType = {
  /**网元 loading */
  loading: boolean;
  /**网元配置 tree */
  data: DataNode[];
  /**选择对应Node一级 tree */
  selectNode: Record<string, any>;
  /**选择 loading */
  selectLoading: boolean;
};

let treeState: TreeStateType = reactive({
  loading: true,
  data: [],
  selectNode: {
    topDisplay: '' as string,
    topTag: '' as string,
    method: '' as string,
    //
    title: '' as string,
    key: '' as string,
    type: 'list' as 'list' | 'array',
  },
  selectLoading: true,
});

/**查询可选命令列表 */
function fnSelectConfigNode(_: any, info: any) {
  const { title, key, method } = info.node;
  treeState.selectNode.topDisplay = title;
  treeState.selectNode.topTag = key;
  treeState.selectNode.method = method;
  treeState.selectNode.title = title;
  treeState.selectNode.key = key;
  fnActiveConfigNode(key);
}

/**tab标签栏标签点击监听 */
function fnActiveConfigNode(key: string | number) {
  listState.data = [];
  arrayState.data = [];
  treeState.selectLoading = true;
  if (key !== '#') {
    treeState.selectNode.topTag = key as string;
  }

  // 获取数据
  const neType = neTypeSelect.value[0];
  const neId = neTypeSelect.value[1];
  const topTag = treeState.selectNode.topTag;
  getParamConfigInfoForm(neType, topTag, neId).then(res => {
    if (res.code === RESULT_CODE_SUCCESS && res.data.type) {
      treeState.selectLoading = false;
      treeState.selectNode.topTag = topTag;
      treeState.selectNode.type = res.data.type;
      if (res.data.type === 'list') {
        listState.data = res.data.data;
        listEditClose();
      }
      if (res.data.type === 'array') {
        arrayState.data = res.data.data;
        arrayState.dataRule = res.data.dataRule;

        // 列表数据
        const columnsData: Record<string, any>[] = [];
        for (const v of arrayState.data) {
          const row: Record<string, any> = {};
          for (const item of v.record) {
            row[item.name] = item;
          }
          columnsData.push(row);
        }
        arrayState.columnsData = columnsData;

        // 列表字段
        const columns: Record<string, any>[] = [];
        for (const rule of arrayState.dataRule.record) {
          columns.push({
            title: rule.display,
            dataIndex: rule.name,
            align: 'left',
            width: 5,
          });
        }
        columns.push({
          title: t('common.operate'),
          dataIndex: 'index',
          key: 'index',
          align: 'left',
          fixed: 'right',
          width: 5,
        });
        arrayState.columns = columns;

        arrayEditClose();
      }
    } else {
      message.warning({
        content: t('common.noData'),
        duration: 3,
      });
    }
  });
}

/**查询配置Tag标签 */
function fnGetParamConfigTopTab() {
  const neType = neTypeSelect.value[0];
  if (!neType) {
    message.warning({
      content: t('views.configManage.configParamForm.neTypePleace'),
      duration: 3,
    });
    return;
  }

  treeState.loading = true;
  // 获取数据
  getParamConfigTopTab(neType).then(res => {
    if (res.code === RESULT_CODE_SUCCESS && Array.isArray(res.data)) {
      treeState.data = res.data.map(item => ({
        children: undefined,
        title: item.topDisplay,
        key: item.topTag,
        ...item,
      }));
      treeState.loading = false;
      // 取首个tag
      if (res.data.length > 0) {
        const itemOne = res.data[0];
        treeState.selectNode = {
          title: itemOne.topDisplay,
          key: itemOne.topTag,
          type: 'list',
          ...itemOne,
        };
        fnActiveConfigNode(itemOne.topTag);
      }
    } else {
      message.warning({
        content: t('views.configManage.configParamForm.noConfigData'),
        duration: 3,
      });
    }
  });
}

/**单列表状态类型 */
type ListStateType = {
  /**紧凑型 */
  size: SizeType;
  /**单列记录字段 */
  columns: Record<string, any>[];
  /**单列记录数据 */
  data: Record<string, any>[];
  /**编辑行记录 */
  editRecord: Record<string, any>;
};

/**单列表状态 */
let listState: ListStateType = reactive({
  size: 'middle',
  columns: [
    {
      title: 'Key',
      dataIndex: 'display',
      align: 'left',
      width: '30%',
    },
    {
      title: 'Value',
      dataIndex: 'value',
      align: 'left',
      width: '70%',
    },
  ],
  data: [],
  editRecord: {},
});

/**单列表编辑 */
function listEdit(row: Record<string, any>) {
  listState.editRecord = Object.assign({}, row);
}

/**单列表编辑关闭 */
function listEditClose() {
  listState.editRecord = {};
}

/**单列表编辑确认 */
function listEditOk() {
  const from = toRaw(listState.editRecord);
  // 检查规则
  const [ok, msg] = ruleVerification(from);
  if (!ok) {
    message.warning({
      content: `${msg}`,
      duration: 3,
    });
    return;
  }

  // 发送
  const hide = message.loading({ content: t('common.loading') });
  let data = {
    [from['name']]: from['value'],
  };
  updateParamConfigInfo(
    'list',
    {
      neType: neTypeSelect.value[0],
      neId: neTypeSelect.value[1],
      topTag: treeState.selectNode.topTag,
    },
    data
  )
    .then(res => {
      if (res.code === RESULT_CODE_SUCCESS) {
        message.success({
          content: t('views.configManage.configParamForm.updateValue', {
            num: from['display'],
          }),
          duration: 3,
        });
        // 改变表格数据
        const item = listState.data.filter(
          (item: Record<string, any>) => from['name'] === item['name']
        )[0];
        if (item) {
          Object.assign(item, listState.editRecord);
        }
      } else {
        message.warning({
          content: t('views.configManage.configParamForm.updateValueErr'),
          duration: 3,
        });
      }
    })
    .finally(() => {
      hide();
      listState.editRecord = {};
    });
}

/**多列列表状态类型 */
type ArrayStateType = {
  /**紧凑型 */
  size: SizeType;
  /**多列嵌套记录字段 */
  columns: Record<string, any>[];
  /**多列记录数据 */
  columnsData: Record<string, any>[];
  /**多列嵌套展开key */
  arrayChildExpandKeys: any[];

  /**多列记录数据 */
  data: Record<string, any>[];
  /**多列记录规则 */
  dataRule: Record<string, any>;
};

/**多列列表状态 */
let arrayState: ArrayStateType = reactive({
  size: 'middle',
  columns: [],
  columnsData: [],
  arrayChildExpandKeys: [],
  data: [],
  dataRule: {},
});

/**多列表编辑 */
function arrayEdit(rowIndex: Record<string, any>) {
  const item = arrayState.data.find((s: any) => s.key === rowIndex.value);
  if (!item) return;

  const row: Record<string, any> = {};
  for (const v of item.record) {
    row[v.name] = Object.assign({}, v);
  }

  modalState.from = row;
  modalState.type = 'arrayEdit';
  modalState.title = `${treeState.selectNode.topDisplay} ${item.title}`;
  modalState.key = item.key;
  modalState.data = item.record.filter((v: any) => !Array.isArray(v.array));
  modalState.visible = true;

  // 关闭嵌套
  arrayChildExpandClose();
}

/**多列表编辑关闭 */
function arrayEditClose() {
  arrayChildExpandClose();
  fnModalCancel();
}

/**多列表编辑确认 */
function arrayEditOk(from: Record<string, any>) {
  const loc = from['index']['value'];
  const neType = neTypeSelect.value[0];
  // 遍历提取属性和值
  let data: Record<string, any> = {};
  for (const key in from) {
    // 子嵌套的不插入
    if (from[key]['array']) {
      continue;
    }
    // 检查规则
    const [ok, msg] = ruleVerification(from[key]);
    if (!ok) {
      message.warning({
        content: `${msg}`,
        duration: 3,
      });
      return;
    }
    data[key] = from[key]['value'];
  }

  // 发送
  const hide = message.loading({ content: t('common.loading') });
  updateParamConfigInfo(
    'array',
    {
      neType: neType,
      neId: neTypeSelect.value[1],
      topTag: treeState.selectNode.topTag,
      loc,
    },
    data
  )
    .then(res => {
      if (res.code === RESULT_CODE_SUCCESS) {
        message.success({
          content: t('views.configManage.configParamForm.updateItem', {
            num: modalState.title,
          }),
          duration: 3,
        });
        fnActiveConfigNode('#');
      } else {
        message.warning({
          content: t('views.configManage.configParamForm.updateItemErr'),
          duration: 3,
        });
      }
    })
    .finally(() => {
      hide();
      arrayEditClose();
    });
}

/**多列表删除单行 */
function arrayDelete(rowIndex: Record<string, any>) {
  const index = rowIndex.value;
  delParamConfigInfo({
    neType: neTypeSelect.value[0],
    neId: neTypeSelect.value[1],
    topTag: treeState.selectNode.topTag,
    loc: index,
  }).then(res => {
    if (res.code === RESULT_CODE_SUCCESS) {
      message.success({
        content: t('views.configManage.configParamForm.delItemOk', {
          num: `${treeState.selectNode.topDisplay} Index-${index}`,
        }),
        duration: 2,
      });
      arrayEditClose();
      fnActiveConfigNode('#');
    } else {
      message.error({
        content: `${res.msg}`,
        duration: 2,
      });
    }
  });
}

/**多列表新增单行 */
function arrayAdd() {
  const from = arrayAddInit(arrayState.data, arrayState.dataRule);

  // 处理信息
  const row: Record<string, any> = {};
  for (const v of from.record) {
    if (Array.isArray(v.array)) {
      continue;
    }
    row[v.name] = Object.assign({}, v);
  }

  modalState.from = row;
  modalState.type = 'arrayAdd';
  modalState.title = `${treeState.selectNode.topDisplay} ${from.title}`;
  modalState.key = from.key;
  modalState.data = from.record.filter((v: any) => !Array.isArray(v.array));
  modalState.visible = true;
}

/**多列表新增单行确认 */
function arrayAddOk(from: Record<string, any>) {
  const index = from['index']['value'];
  const neType = neTypeSelect.value[0];
  // 遍历提取属性和值
  let data: Record<string, any> = {};
  for (const key in from) {
    // 子嵌套的不插入
    if (from[key]['array']) {
      continue;
    }
    // 检查规则
    const [ok, msg] = ruleVerification(from[key]);
    if (!ok) {
      message.warning({
        content: `${msg}`,
        duration: 3,
      });
      return;
    }
    data[key] = from[key]['value'];
  }

  // 发送
  const hide = message.loading({ content: t('common.loading') });
  addParamConfigInfo(
    {
      neType: neType,
      neId: neTypeSelect.value[1],
      topTag: treeState.selectNode.topTag,
      loc: index,
    },
    data
  )
    .then(res => {
      if (res.code === RESULT_CODE_SUCCESS) {
        message.success({
          content: t('views.configManage.configParamForm.addItemOk', {
            num: modalState.title,
          }),
          duration: 3,
        });
        fnActiveConfigNode('#');
      } else {
        message.warning({
          content: t('views.configManage.configParamForm.addItemErr'),
          duration: 3,
        });
      }
    })
    .finally(() => {
      hide();
      arrayEditClose();
    });
}

/**多列嵌套列表状态类型 */
type ArrayChildStateType = {
  /**标题 */
  title: string;
  /**层级index */
  loc: string;
  /**紧凑型 */
  size: SizeType;
  /**多列嵌套记录字段 */
  columns: Record<string, any>[];
  /**多列记录数据 */
  columnsData: Record<string, any>[];

  /**多列嵌套记录数据 */
  data: Record<string, any>[];
  /**多列嵌套记录规则 */
  dataRule: Record<string, any>;
};

/**表格状态 */
let arrayChildState: ArrayChildStateType = reactive({
  title: '',
  loc: '',
  size: 'middle',
  columns: [],
  columnsData: [],
  data: [],
  dataRule: {},
});

/**多列表展开嵌套行 */
function arrayChildExpand(
  indexRow: Record<string, any>,
  row: Record<string, any>
) {
  const loc = indexRow.value;
  if (arrayChildState.loc === `${loc}/${row.name}`) {
    arrayChildState.loc = '';
    arrayState.arrayChildExpandKeys = [];
    return;
  }
  arrayChildState.loc = '';
  arrayState.arrayChildExpandKeys = [];
  const from = Object.assign({}, JSON.parse(JSON.stringify(row)));
  // 无数据时
  if (!Array.isArray(from.value)) {
    from.value = [];
  }
  const dataArr = Object.freeze(from.value);
  const ruleArr = Object.freeze(from.array);

  // 列表项数据
  const dataArray: Record<string, any>[] = [];
  for (const item of dataArr) {
    const index = item['index'];
    let record: Record<string, any>[] = [];
    for (const key of Object.keys(item)) {
      // 规则为准
      for (const rule of ruleArr) {
        if (rule['name'] === key) {
          const ruleItem = Object.assign({ optional: 'true' }, rule, {
            value: item[key],
          });
          record.push(ruleItem);
          break;
        }
      }
    }
    // dataArray.push(record);
    dataArray.push({ title: `Index-${index}`, key: index, record });
  }
  arrayChildState.data = dataArray;

  // 无数据时，用于新增
  arrayChildState.dataRule = {
    title: `Index-0`,
    key: 0,
    record: ruleArr,
  };

  // 列表数据
  const columnsData: Record<string, any>[] = [];
  for (const v of arrayChildState.data) {
    const row: Record<string, any> = {};
    for (const item of v.record) {
      row[item.name] = item;
    }
    columnsData.push(row);
  }
  arrayChildState.columnsData = columnsData;

  // 列表字段
  const columns: Record<string, any>[] = [];
  for (const rule of arrayChildState.dataRule.record) {
    columns.push({
      title: rule.display,
      dataIndex: rule.name,
      align: 'left',
      width: 5,
    });
  }
  columns.push({
    title: t('common.operate'),
    dataIndex: 'index',
    key: 'index',
    align: 'left',
    fixed: 'right',
    width: 5,
  });
  arrayChildState.columns = columns;

  // 设置展开key
  arrayState.arrayChildExpandKeys = [indexRow];

  arrayChildState.loc = `${loc}/${from['name']}`;
  // 设置展开列表标题
  arrayChildState.title = `${from['display']}`;
}

/**多列表展开嵌套行 */
function arrayChildExpandClose() {
  arrayChildState.loc = '';
  arrayState.arrayChildExpandKeys = [];
}

/**多列表嵌套行编辑 */
function arrayChildEdit(rowIndex: Record<string, any>) {
  const item = arrayChildState.data.find((s: any) => s.key === rowIndex.value);
  if (!item) return;

  const row: Record<string, any> = {};
  for (const v of item.record) {
    row[v.name] = Object.assign({}, v);
  }

  modalState.from = row;
  modalState.type = 'arrayChildEdit';
  modalState.title = `${arrayChildState.title} ${item.title}`;
  modalState.key = item.key;
  modalState.data = item.record.filter((v: any) => !Array.isArray(v.array));
  modalState.visible = true;
}

/**多列表嵌套行编辑确认 */
function arrayChildEditOk(from: Record<string, any>) {
  const index = from['index']['value'];
  const loc = `${arrayChildState.loc}/${index}`;
  const neType = neTypeSelect.value[0];

  let data: Record<string, any> = {};
  for (const key in from) {
    // 子嵌套的不插入
    if (from[key]['array']) {
      continue;
    }
    // 检查规则
    const [ok, msg] = ruleVerification(from[key]);
    if (!ok) {
      message.warning({
        content: `${msg}`,
        duration: 3,
      });
      return;
    }
    data[key] = from[key]['value'];
  }

  // 发送
  const hide = message.loading({ content: t('common.loading') });
  updateParamConfigInfo(
    'array',
    {
      neType: neType,
      neId: neTypeSelect.value[1],
      topTag: treeState.selectNode.topTag,
      loc,
    },
    data
  )
    .then(res => {
      if (res.code === RESULT_CODE_SUCCESS) {
        message.success({
          content: t('views.configManage.configParamForm.updateItem', {
            num: modalState.title,
          }),
          duration: 3,
        });
        fnActiveConfigNode('#');
      } else {
        message.warning({
          content: t('views.configManage.configParamForm.updateItemErr'),
          duration: 3,
        });
      }
    })
    .finally(() => {
      hide();
      arrayEditClose();
    });
}

/**多列表嵌套行删除单行 */
function arrayChildDelete(rowIndex: Record<string, any>) {
  const index = rowIndex.value;
  const loc = `${arrayChildState.loc}/${index}`;
  delParamConfigInfo({
    neType: neTypeSelect.value[0],
    neId: neTypeSelect.value[1],
    topTag: treeState.selectNode.topTag,
    loc,
  }).then(res => {
    if (res.code === RESULT_CODE_SUCCESS) {
      message.success({
        content: t('views.configManage.configParamForm.delItemOk', {
          num: `${arrayChildState.title} Index-${index}`,
        }),
        duration: 2,
      });
      arrayEditClose();
      fnActiveConfigNode('#');
    } else {
      message.error({
        content: `${res.msg}`,
        duration: 2,
      });
    }
  });
}

/**多列表嵌套行新增单行 */
function arrayChildAdd() {
  const from = arrayAddInit(arrayChildState.data, arrayChildState.dataRule);
  // 处理信息
  const row: Record<string, any> = {};
  for (const v of from.record) {
    if (Array.isArray(v.array)) {
      continue;
    }
    row[v.name] = Object.assign({}, v);
  }

  modalState.from = row;
  modalState.type = 'arrayChildAdd';
  modalState.title = `${arrayChildState.title} ${from.title}`;
  modalState.key = from.key;
  modalState.data = from.record.filter((v: any) => !Array.isArray(v.array));
  modalState.visible = true;
}

/**多列表新增单行确认 */
function arrayChildAddOk(from: Record<string, any>) {
  const index = from['index']['value'];
  const loc = `${arrayChildState.loc}/${index}`;
  const neType = neTypeSelect.value[0];

  let data: Record<string, any> = {};
  for (const key in from) {
    // 子嵌套的不插入
    if (from[key]['array']) {
      continue;
    }
    // 检查规则
    const [ok, msg] = ruleVerification(from[key]);
    if (!ok) {
      message.warning({
        content: `${msg}`,
        duration: 3,
      });
      return;
    }
    data[key] = from[key]['value'];
  }

  // 发送
  const hide = message.loading({ content: t('common.loading') });
  addParamConfigInfo(
    {
      neType: neType,
      neId: neTypeSelect.value[1],
      topTag: treeState.selectNode.topTag,
      loc,
    },
    data
  )
    .then(res => {
      if (res.code === RESULT_CODE_SUCCESS) {
        message.success({
          content: t('views.configManage.configParamForm.addItemOk', {
            num: modalState.title,
          }),
          duration: 3,
        });
        fnActiveConfigNode('#');
      } else {
        message.warning({
          content: t('views.configManage.configParamForm.addItemErr'),
          duration: 3,
        });
      }
    })
    .finally(() => {
      hide();
      arrayEditClose();
    });
}

/**多列表新增行数据初始化 */
function arrayAddInit(data: any[], dataRule: any) {
  const len = data.length;
  let lastItme: Record<string, any> = {};
  let newIndex = 0;
  // 无数据时生成临时记录
  if (len === 0) {
    lastItme = dataRule;
  } else {
    lastItme = data[len - 1];
  }
  const from = Object.assign({}, JSON.parse(JSON.stringify(lastItme)));
  for (const row of from.record) {
    const value = row.value;
    if (row.name === 'index') {
      if (value !== '') {
        newIndex = parseInt(value) + 1;
      }
      if (isNaN(newIndex)) {
        newIndex = 0;
      }
      row.value = newIndex;
      from.key = newIndex;
      from.title = `Index-${newIndex}`;
      continue;
    }
    // 子嵌套的不初始
    if (row.array) {
      row.value = null;
      continue;
    }
    const type = row.type;
    const filter = row.filter;
    switch (type) {
      case 'int':
        if (filter && filter.indexOf('~') !== -1) {
          const filterArr = filter.split('~');
          const minInt = parseInt(filterArr[0]);
          row.value = minInt;
        } else {
          row.value = 0;
        }
        break;
      case 'enum':
        if (filter && filter.indexOf('{') === 0) {
          let filterJson: Record<string, any> = {};
          try {
            filterJson = JSON.parse(filter); //string---json
          } catch (error) {
            console.error(error);
          }

          row.value = Object.keys(filterJson)[0];
        } else {
          row.value = '0';
        }
        break;
      case 'bool':
        if (filter && filter.indexOf('{') === 0) {
          let filterJson: Record<string, any> = {};
          try {
            filterJson = JSON.parse(filter); //string---json
          } catch (error) {
            console.error(error);
          }

          row.value = Object.keys(filterJson)[0];
        } else {
          row.value = false;
        }
        break;
      case 'ipv4':
      case 'ipv6':
      case 'regex':
      default:
        row.value = '';
        break;
    }
  }

  return from;
}

/**规则校验 */
function ruleVerification(row: Record<string, any>): (string | boolean)[] {
  let result = [true, ''];
  const type = row.type;
  const value = row.value;
  const filter = row.filter;
  const display = row.display;

  // 子嵌套的不检查
  if (row.array) {
    return result;
  }

  // 可选的同时没有值不检查
  if (row.optional === 'true' && !value) {
    return result;
  }

  switch (type) {
    case 'int':
      if (filter && filter.indexOf('~') !== -1) {
        const filterArr = filter.split('~');
        const minInt = parseInt(filterArr[0]);
        const maxInt = parseInt(filterArr[1]);
        const valueInt = parseInt(value);
        if (valueInt < minInt || valueInt > maxInt) {
          return [
            false,
            t('views.configManage.configParamForm.requireInt', {
              display,
              filter,
            }),
          ];
        }
      }
      break;
    case 'ipv4':
      if (!regExpIPv4.test(value)) {
        return [
          false,
          t('views.configManage.configParamForm.requireIpv4', { display }),
        ];
      }
      break;
    case 'ipv6':
      if (!regExpIPv6.test(value)) {
        return [
          false,
          t('views.configManage.configParamForm.requireIpv6', { display }),
        ];
      }
      break;
    case 'enum':
      if (filter && filter.indexOf('{') === 1) {
        let filterJson: Record<string, any> = {};
        try {
          filterJson = JSON.parse(filter); //string---json
        } catch (error) {
          console.error(error);
        }

        if (!Object.keys(filterJson).includes(`${value}`)) {
          return [
            false,
            t('views.configManage.configParamForm.requireEnum', { display }),
          ];
        }
      }
      break;
    case 'bool':
      if (filter && filter.indexOf('{') === 1) {
        let filterJson: Record<string, any> = {};
        try {
          filterJson = JSON.parse(filter); //string---json
        } catch (error) {
          console.error(error);
        }

        if (!Object.values(filterJson).includes(`${value}`)) {
          return [
            false,
            t('views.configManage.configParamForm.requireBool', { display }),
          ];
        }
      }
      break;
    case 'string':
      if (filter && filter.indexOf('~') !== -1) {
        try {
          const filterArr = filter.split('~');
          let rule = new RegExp(
            '^\\S{' + filterArr[0] + ',' + filterArr[1] + '}$'
          );
          if (!rule.test(value)) {
            return [
              false,
              t('views.configManage.configParamForm.requireString', {
                display,
              }),
            ];
          }
        } catch (error) {
          console.error(error);
        }
      }

      break;
    case 'regex':
      if (filter) {
        try {
          let regex = new RegExp(filter);
          if (!regex.test(value)) {
            return [
              false,
              t('views.configManage.configParamForm.requireString', {
                display,
              }),
            ];
          }
        } catch (error) {
          console.error(error);
        }
      }
      break;

    default:
      return [
        false,
        t('views.configManage.configParamForm.requireUn', { display }),
      ];
  }
  return result;
}

/**对话框对象信息状态类型 */
type ModalStateType = {
  /**添加框是否显示 */
  visible: boolean;
  /**标题 */
  title: string;
  /**表单数据 */
  from: Record<string, any>;
  /**确定按钮 loading */
  confirmLoading: boolean;
  /**项类型 */
  type: 'arrayAdd' | 'arrayEdit' | 'arrayChildAdd' | 'arrayChildEdit';
  /**项Key */
  key: string | number;
  /**项数据 */
  data: Record<string, any>[];
};

/**对话框对象信息状态 */
let modalState: ModalStateType = reactive({
  visible: false,
  title: 'Item',
  from: {},
  confirmLoading: false,
  type: 'arrayAdd',
  key: '',
  data: [],
});

/**
 * 对话框弹出确认执行函数
 * 进行表达规则校验
 */
function fnModalOk() {
  const from = toRaw(modalState.from);
  if (modalState.type === 'arrayAdd') {
    arrayAddOk(from);
  }
  if (modalState.type === 'arrayEdit') {
    arrayEditOk(from);
  }
  if (modalState.type === 'arrayChildAdd') {
    arrayChildAddOk(from);
  }
  if (modalState.type === 'arrayChildEdit') {
    arrayChildEditOk(from);
  }
}

/**
 * 对话框弹出关闭执行函数
 * 进行表达规则校验
 */
function fnModalCancel() {
  modalState.visible = false;
  modalState.from = {};
  modalState.type = 'arrayAdd';
  modalState.key = '';
  modalState.data = [];
}

onMounted(() => {
  // 获取网元网元列表
  useNeInfoStore()
    .fnNelist()
    .then(res => {
      if (res.code === RESULT_CODE_SUCCESS && Array.isArray(res.data)) {
        if (res.data.length > 0) {
          // 过滤不可用的网元
          neCascaderOtions.value = useNeInfoStore().getNeCascaderOtions.filter(
            (item: any) => {
              return !['OMC'].includes(item.value);
            }
          );
          // 默认选择AMF
          const item = neCascaderOtions.value.find(s => s.value === 'UPF');
          if (item && item.children) {
            const info = item.children[0];
            neTypeSelect.value = [info.neType, info.neId];
          } else {
            const info = neCascaderOtions.value[0].children[0];
            neTypeSelect.value = [info.neType, info.neId];
          }
          fnGetParamConfigTopTab();
        }
      } else {
        message.warning({
          content: t('common.noData'),
          duration: 2,
        });
      }
    });
});
</script>

<template>
  <PageContainer>
    <a-row :gutter="16">
      <a-col :span="6">
        <!-- 网元类型 -->
        <a-card
          size="small"
          :bordered="false"
          :title="t('views.configManage.configParamForm.treeTitle')"
          :loading="treeState.loading"
        >
          <a-form layout="vertical" autocomplete="off">
            <a-form-item name="neId ">
              <a-cascader
                v-model:value="neTypeSelect"
                :options="neCascaderOtions"
                :allow-clear="false"
                @change="fnGetParamConfigTopTab"
              />
            </a-form-item>
            <a-form-item name="listeningPort">
              <a-tree
                :tree-data="treeState.data"
                :selected-keys="[treeState.selectNode.topTag]"
                @select="fnSelectConfigNode"
              >
              </a-tree>
            </a-form-item>
          </a-form>
        </a-card>
      </a-col>
      <a-col :span="18">
        <a-card
          size="small"
          :bordered="false"
          :body-style="{ maxHeight: '650px', 'overflow-y': 'scroll' }"
          :loading="treeState.selectLoading"
        >
          <template #title>
            <a-typography-text strong v-if="treeState.selectNode.topDisplay">
              {{ treeState.selectNode.topDisplay }}
            </a-typography-text>
            <a-typography-text type="danger" v-else>
              {{ t('views.configManage.configParamForm.treeSelectTip') }}
            </a-typography-text>
          </template>
          <template #extra>
            <a-space :size="8" align="center" v-show="!treeState.selectLoading">
              <a-tooltip>
                <template #title>{{ t('common.reloadText') }}</template>
                <a-button
                  type="default"
                  @click.prevent="fnActiveConfigNode('#')"
                >
                  <template #icon>
                    <ReloadOutlined />
                  </template>
                </a-button>
              </a-tooltip>
            </a-space>
          </template>

          <!-- 单列表格列表 -->
          <a-table
            v-if="treeState.selectNode.type === 'list'"
            class="table"
            row-key="name"
            :size="listState.size"
            :columns="listState.columns"
            :data-source="listState.data"
            :pagination="false"
            :bordered="true"
            :scroll="{ x: true }"
          >
            <template #bodyCell="{ column, text, record }">
              <template v-if="column.dataIndex === 'value'">
                <a-tooltip placement="topLeft">
                  <template #title v-if="record.comment">
                    {{ record.comment }}
                  </template>
                  <div class="editable-cell">
                    <div
                      v-if="
                        listState.editRecord['display'] === record['display']
                      "
                      class="editable-cell__input-wrapper"
                    >
                      <a-input-number
                        v-if="record['type'] === 'int'"
                        v-model:value="listState.editRecord['value']"
                        style="width: 100%"
                      ></a-input-number>
                      <a-switch
                        v-else-if="record['type'] === 'bool'"
                        v-model:checked="listState.editRecord['value']"
                        :checked-children="t('common.switch.open')"
                        :un-checked-children="t('common.switch.shut')"
                      ></a-switch>
                      <a-select
                        v-else-if="record['type'] === 'enum'"
                        v-model:value="listState.editRecord['value']"
                        :allow-clear="true"
                        style="width: 100%"
                      >
                        <a-select-option
                          :value="+v"
                          :key="+v"
                          v-for="(k, v) in JSON.parse(record['filter'])"
                        >
                          {{ k }}
                        </a-select-option>
                      </a-select>
                      <a-input
                        v-else
                        v-model:value="listState.editRecord['value']"
                      ></a-input>
                      <a-space :size="16" align="center" direction="horizontal">
                        <a-tooltip placement="bottomRight">
                          <template #title> {{ t('common.ok') }} </template>
                          <a-popconfirm
                            :title="
                              t(
                                'views.configManage.configParamForm.editOkTip',
                                { num: record['display'] }
                              )
                            "
                            placement="topRight"
                            @confirm="listEditOk()"
                          >
                            <a-button
                              type="text"
                              class="editable-cell__icon-edit"
                            >
                              <template #icon><CheckOutlined /></template>
                            </a-button>
                          </a-popconfirm>
                        </a-tooltip>
                        <a-tooltip placement="bottomRight">
                          <template #title>
                            {{ t('common.cancel') }}
                          </template>
                          <a-button
                            type="text"
                            class="editable-cell__icon-edit"
                            @click.prevent="listEditClose()"
                          >
                            <template #icon><CloseOutlined /></template>
                          </a-button>
                        </a-tooltip>
                      </a-space>
                    </div>
                    <div v-else class="editable-cell__text-wrapper">
                      <template v-if="record['type'] === 'enum'">
                        {{ JSON.parse(record['filter'])[text] }}
                      </template>
                      <template v-else>{{ `${text}` || '&nbsp;' }}</template>
                      <EditOutlined
                        class="editable-cell__icon"
                        v-if="record.access !== 'read'"
                        @click="listEdit(record)"
                      />
                    </div>
                  </div>
                </a-tooltip>
              </template>
            </template>
          </a-table>

          <!-- array类型 -->
          <template v-if="treeState.selectNode.type === 'array'">
            <a-table
              class="table"
              row-key="index"
              :columns="treeState.selectNode.method === 'get' ? arrayState.columns.filter((s:any)=>s.key !== 'index') :arrayState.columns"
              :data-source="arrayState.columnsData"
              :size="arrayState.size"
              :pagination="false"
              :bordered="true"
              :scroll="{ x: arrayState.columns.length * 200, y: 450 }"
              :show-expand-column="false"
              v-model:expanded-row-keys="arrayState.arrayChildExpandKeys"
            >
              <!-- 多列新增操作 -->
              <template #title v-if="treeState.selectNode.method !== 'get'">
                <a-button
                  type="primary"
                  @click.prevent="arrayAdd()"
                  size="small"
                >
                  <template #icon> <PlusOutlined /> </template>
                  {{ t('common.addText') }}
                </a-button>
              </template>

              <!-- 多列数据渲染 -->
              <template #bodyCell="{ column, text, record }">
                <template v-if="column.key === 'index'">
                  <a-space :size="16" align="center">
                    <a-tooltip>
                      <template #title>{{ t('common.editText') }}</template>
                      <a-button type="link" @click.prevent="arrayEdit(text)">
                        <template #icon><FormOutlined /></template>
                      </a-button>
                    </a-tooltip>
                    <a-tooltip>
                      <template #title>{{ t('common.deleteText') }}</template>
                      <a-button type="link" @click.prevent="arrayDelete(text)">
                        <template #icon><DeleteOutlined /></template>
                      </a-button>
                    </a-tooltip>
                  </a-space>
                </template>
                <template v-else>
                  <a-tooltip placement="topLeft">
                    <template #title v-if="text.comment">
                      {{ text.comment }}
                    </template>
                    <div class="editable-cell">
                      <template v-if="text.array">
                        <a-button
                          type="default"
                          size="small"
                          @click.prevent="
                            arrayChildExpand(record['index'], text)
                          "
                        >
                          <template #icon><BarsOutlined /></template>
                          {{
                            t('views.configManage.configParamForm.arrayMore')
                          }}
                        </a-button>
                        <!--特殊字段拓展显示-->
                        <span v-if="text.name === 'dnnList'">
                          ({{ text.value.map((s: any) => s.dnn).join() }})
                        </span>
                      </template>

                      <div v-else class="editable-cell__text-wrapper">
                        <template v-if="text['type'] === 'enum'">
                          {{ JSON.parse(text['filter'])[text.value] }}
                        </template>
                        <template v-else>
                          {{ `${text.value}` || '&nbsp;' }}
                        </template>
                      </div>
                    </div>
                  </a-tooltip>
                </template>
              </template>

              <!-- 多列嵌套类型 -->
              <template #expandedRowRender>
                <a-table
                  class="table"
                  row-key="index"
                  :columns="arrayChildState.columns"
                  :data-source="arrayChildState.columnsData"
                  :size="arrayChildState.size"
                  :pagination="false"
                  :bordered="true"
                  :scroll="{
                    x: arrayChildState.columns.length * 200,
                    y: 450,
                  }"
                >
                  <template #title>
                    <a-button
                      type="primary"
                      @click.prevent="arrayChildAdd"
                      size="small"
                    >
                      <template #icon> <PlusOutlined /> </template>
                      {{ t('common.addText') }} {{ arrayChildState.title }}
                    </a-button>
                  </template>
                  <template #bodyCell="{ column, text, record }">
                    <template v-if="column.key === 'index'">
                      <a-space :size="8" align="center">
                        <a-tooltip>
                          <template #title>{{ t('common.editText') }}</template>
                          <a-button
                            type="link"
                            @click.prevent="arrayChildEdit(text)"
                          >
                            <template #icon><FormOutlined /></template>
                          </a-button>
                        </a-tooltip>
                        <a-tooltip>
                          <template #title>{{
                            t('common.deleteText')
                          }}</template>
                          <a-button
                            type="link"
                            @click.prevent="arrayChildDelete(text)"
                          >
                            <template #icon><DeleteOutlined /></template>
                          </a-button>
                        </a-tooltip>
                      </a-space>
                    </template>
                    <template v-else>
                      <a-tooltip placement="topLeft">
                        <template #title v-if="text.comment">
                          {{ text.comment }}
                        </template>
                        <div class="editable-cell">
                          <template v-if="text.array">
                            <a-button type="default" size="small">
                              <template #icon><BarsOutlined /></template>
                              {{
                                t(
                                  'views.configManage.configParamForm.arrayMore'
                                )
                              }}
                            </a-button>
                          </template>

                          <div v-else>
                            <template v-if="text['type'] === 'enum'">
                              {{ JSON.parse(text['filter'])[text.value] }}
                            </template>
                            <template v-else>
                              {{ `${text.value}` || '&nbsp;' }}
                            </template>
                          </div>
                        </div>
                      </a-tooltip>
                    </template>
                  </template>
                </a-table>
              </template>
            </a-table>
          </template>
        </a-card>
      </a-col>
    </a-row>

    <!-- 新增框或修改框 -->
    <a-modal
      width="800px"
      :body-style="{ maxHeight: '650px', 'overflow-y': 'scroll' }"
      :keyboard="false"
      :mask-closable="false"
      :visible="modalState.visible"
      :title="modalState.title"
      :confirm-loading="modalState.confirmLoading"
      @ok="fnModalOk"
      @cancel="fnModalCancel"
    >
      <a-form
        class="form"
        layout="horizontal"
        autocomplete="off"
        :validate-on-rule-change="false"
        :validateTrigger="[]"
      >
        <a-form-item
          v-for="item in modalState.data"
          :label="item.display"
          :name="item.name"
          :required="item.optional === 'false'"
          style="margin-bottom: 2px"
        >
          <a-tooltip placement="topLeft">
            <template #title v-if="item.comment">
              {{ item.comment }}
            </template>
            <div>
              <div
                v-if="
                  !Array.isArray(item.array) &&
                  modalState.from[item.name] !== undefined
                "
              >
                <a-input-number
                  v-if="item['type'] === 'int'"
                  v-model:value="modalState.from[item.name]['value']"
                  :disabled="item.name === 'index'"
                  style="width: 100%"
                ></a-input-number>
                <a-switch
                  v-else-if="item['type'] === 'bool'"
                  v-model:checked="modalState.from[item.name]['value']"
                  :checked-children="t('common.switch.open')"
                  :un-checked-children="t('common.switch.shut')"
                ></a-switch>
                <a-select
                  v-else-if="item['type'] === 'enum'"
                  v-model:value="modalState.from[item.name]['value']"
                  :allow-clear="true"
                  style="width: 100%"
                >
                  <a-select-option
                    :value="+v"
                    :key="+v"
                    v-for="(k, v) in JSON.parse(item['filter'])"
                  >
                    {{ k }}
                  </a-select-option>
                </a-select>
                <a-input
                  v-else
                  v-model:value="modalState.from[item.name]['value']"
                  :disabled="item.name === 'index'"
                ></a-input>
              </div>
              <div v-else>
                {{ `${item.value || '&nbsp;'}` }}
              </div>
            </div>
          </a-tooltip>
        </a-form-item>
      </a-form>
    </a-modal>
  </PageContainer>
</template>

<style lang="less" scoped>
.editable-cell {
  &__icon {
    display: none;
    cursor: pointer;
  }
  &__icon:hover {
    color: var(--ant-primary-color);
  }
  &__icon-edit:hover {
    color: var(--ant-primary-color);
  }
  &__text-wrapper {
    font-size: 16px;
    color: #333;
  }
  &__text-wrapper:hover &__icon {
    display: inline-block;
  }
  &__input-wrapper {
    display: flex;
    justify-content: start;
    align-items: center;
  }
}
</style>
