<template>
  <div class="gl-page-content-grey">
    <div class="content">
      <FileTree
        ref="fileTreeRef"
        :api="dataListDirApi"
        :params="{ dirType: DIR_TYPE.KNOWLEDGE }"
        @choseNode="choseNodeFun"
        @updateNav="updateNavFun"
      >
        <template #options>
          <el-button :icon="Plus" class="options" type="primary" @click="appendFun({})">
            {{ $t('知识库.新增') }}
          </el-button>
        </template>
        <template #treeAction="{ data, }">
          <div>
            <el-button type="primary" link @click.stop="appendFun(data)">
              <el-icon>
                <FolderAdd />
              </el-icon>
            </el-button>
            <el-button type="primary" link @click.stop="updateFun(data)">
              <el-icon>
                <EditPen />
              </el-icon>
            </el-button>
            <el-popconfirm
              :title="$t('知识库.确认删除')"
              :cancelButtonText="$t('通用.取消')"
              :confirmButtonText="$t('通用.确定')"
              @confirm="removeFun(data)"
            >
              <template #reference>
                <el-button type="danger" link>
                  <el-icon>
                    <Delete />
                  </el-icon>
                </el-button>
              </template>
            </el-popconfirm>
          </div>
        </template>
        <template #table>
          <TableSearch
            v-if="searchItems.length > 0"
            ref="tableSearchRef"
            :searchItems="searchItems"
            @search="searchFun"
            @reset="resetFun"
          />
          <BaseTable
            ref="baseTableRef"
            tableName="SIMULATION_KNOWLEDGE"
            :api="apiName"
            :params="searchParams"
            showIndex
            :actionsWidth="200"
            :actionList="actionList"
            @cell-dblclick="onCellDblclickFun"
            :exportApi="dataExportKnowledgeListApi"
            :exportFileName="$t('知识库.知识库列表')"
            :exportDict="{
              approvalStatus: 'KNOWLEDGE_APPROVE_STATUS'
            }"
            :exportParams="{
              ...searchParams,
              parentDirId: currentFolder?.id || ''
            }"
          >
            <template #leftOptions>
              <div>
                <el-button :icon="DArrowLeft" @click="backFun" :disabled="navList.length <= 1">{{ $t('通用.返回上一级')
                }}</el-button>
                <el-button type="primary" :icon="Plus" @click="openModalFun" :disabled="!currentFolder">
                  {{ $t('知识库.上传') }}
                </el-button>
              </div>
            </template>
            <template #originalName="{ row }">
              <el-icon v-if="row.dataType === 1">
                <Folder />
              </el-icon>
              <el-icon v-else>
                <Document />
              </el-icon>
              {{ row.originalName }}
            </template>
            <template #fileSize="{ row }">
              {{ formatFileSize(row.fileSize) }}
            </template>
            <template #approvalStatus="{ row, column }">
              <template v-if="row.dataType === 2">
                <el-button type="primary" link @click="openProcessFun(row)" v-if='row[column.field] === "pending"'>
                  {{ KNOWLEDGE_APPROVE_STATUS.O[row[column.field]] }}
                </el-button>
                <el-button type="primary" link @click="openProcessFun(row)" v-else>
                  {{ $t('知识库.审批完成') }}
                </el-button>
              </template>
            </template>
            <template #approveType="{ row, column }">
              <el-button v-if="row.dataType === 2" type="primary" link @click="openProcessFun(row)"> {{
                KNOWLEDGE_APPROVE_TYPE.O[row[column.field]] }}</el-button>
            </template>
          </BaseTable>
        </template>
      </FileTree>
    </div>
    <ApprovalProcess v-model="processVisible" :flowId="currentRow?.cidFlowId" />
    <knowledgeDetailModal
      v-model="visible"
      :detail="currentRow"
      :folder="currentFolder"
      :tableName="TABLE_NAME.SIMULATION_KNOWLEDGE"
      @confirm="onConfirmFun"
    />
    <folderModal
      v-model="folderModalVisible"
      :detail="currentFolder"
      :mode="currentFolderMode"
      @confirm="onFolderConfirmFun"
    />
    <FilePreview v-model="previewVisible" :fileId="currentRow?.id" />
  </div>
</template>

<script lang="ts" setup>
import { computed, h, ref, watchEffect, type Ref } from 'vue';
import { DArrowLeft, Plus } from '@element-plus/icons-vue';
import BaseTable from '@/components/common/table/baseTable.vue';
import FileTree from '@/components/common/fileTree/index.vue';
import knowledgeDetailModal from './components/knowledgeDetailModal.vue';
import folderModal from './components/folderDetailModal.vue';
import { dataCreateDirApi, dataListDirApi, dataRenameDirApi, dataUploadFilesApi, dataDelDirApi, dataQueryDirApi, dataFileSearchApi, dataDelFileApi, dataUpdateFileApi, batchAddFileInfoApi, dataExportKnowledgeListApi } from '@/api/data/data';
import { ElMessage, ElMessageBox } from 'element-plus';
import type { RenderContentContext } from 'element-plus';
import { formatFileSize } from '@/utils/file';
import TableSearch from '@/components/common/table/tableSearch.vue';
import { cloneDeep } from 'lodash-es';
import { DIR_TYPE } from '@/utils/enum/data.ts';
import ApproveList from '@/components/common/approveList/index.vue';
import { useDict } from '@/utils/useDict';
import ApprovalProcess from '@/components/common/approvalProcess/index.vue';
import i18n from '@/utils/i18n';
import FilePreview from '@/components/common/filePreview/index.vue';
import emitter from '@/utils/eventBus';
import { TABLE_NAME } from '@/utils/enum/tableName';
import { downloadFileById } from '@/utils/file';

const { KNOWLEDGE_APPROVE_STATUS, KNOWLEDGE_APPROVE_TYPE } = useDict('KNOWLEDGE_APPROVE_STATUS', 'KNOWLEDGE_APPROVE_TYPE');
type Data = RenderContentContext['data']
const fileTreeRef = ref<any>();
const baseTableRef = ref<any>();
const navList = ref<any>([]);
const currentFolder = ref();
const memoryFolder = ref();
const currentFolderMode: Ref<'add' | 'edit'> = ref('add');
const choseNodeFun = (data: Data) => {
  isSearching.value = false;
  currentFolder.value = data;
  memoryFolder.value = currentFolder.value;
};

const updateNavFun = (data: any) => {
  navList.value = data;
};

const backFun = () => {
  fileTreeRef.value.backFun();
};

const searchItems = ref<any[]>([
  { title: '名称', key: 'fileName', inputMode: 'input' },
  {
    title: '上传人', key: 'uploadUserId', inputMode: 'userSelectMultiple',
  },

]);
const folderModalVisible = ref(false);
const appendFun = (data: Data) => {
  currentFolder.value = data;
  currentFolderMode.value = 'add';
  folderModalVisible.value = true;

};
const updateFun = (data: Data) => {
  currentFolder.value = data;
  currentFolderMode.value = 'edit';
  folderModalVisible.value = true;

};
const removeFun = async (data: Data) => {
  const req = {
    delDirId: data.id,
  };
  const res: any = await dataDelDirApi(req);
  if (res.code === 200) {
    refreshTreeAfterModifyOrRemove(data);
    ElMessage.success(res.message);
  } else {
    ElMessage.error(res.message);
  }
};
const refreshTreeRoot = () => {
  fileTreeRef.value?.reloadFun();
  baseTableRef.value?.resetFun();
};
const refreshTreeOpenDir = (dirId: number) => {
  fileTreeRef.value?.openDirFun(dirId);
  baseTableRef.value?.resetFun();
};
const refreshTreeAfterAdd = (parentNode?: any | null) => {
  if (parentNode && typeof parentNode.id === 'number') {
    refreshTreeOpenDir(parentNode.id);
  } else {
    refreshTreeRoot();
  }
};
const isTopLevel = (node: any) => {
  if (!node || !node.objectKey) return false;
  const key = String(node.objectKey).replace(/\/$/, '');
  const parts = key.split('/');
  return parts.length === 2;
};
const refreshTreeAfterModifyOrRemove = (node?: any | null) => {
  if (isTopLevel(node)) {
    refreshTreeRoot();
  } else {
    refreshTreeOpenDir(node.parentId);
  }

};
const isSearching = ref(false);
const searchParams = ref<any>({
  fileId: currentFolder.value?.id || '',

});

const actionList = computed(() => {
  return [
    {
      title: i18n?.global?.t('通用.预览'),
      type: 'primary',
      click: (row: any) => {
        previewFileFun(row);
      },
      hide: (row: any) => {
        return row.dataType !== 2;
      },
    },
    {
      title: i18n?.global?.t('通用.下载'),
      type: 'primary',
      click: (row: any) => {
        downloadFileById(row.id);
      },
      hide: (row: any) => {
        return row.dataType !== 2;
      },
    },
    {
      title: i18n?.global?.t('通用.编辑'),
      type: 'primary',
      click: (row: any) => {
        editFileFun(row);
      },
      hide: (row: any) => {
        return row.dataType !== 2 || row.approvalStatus === 'pending';
      },
    },
    {
      title: i18n?.global?.t('通用.删除'),
      type: 'danger',
      click: (row: any) => {
        delFileFun(row);
      },
      hide: (row: any) => {
        return row.dataType !== 2 || row.approvalStatus === 'pending';
      },
    },
  ];

});
const searchFun = (data: object) => {
  isSearching.value = true;
  if (!memoryFolder.value && currentFolder.value) {
    memoryFolder.value = currentFolder.value;
    currentFolder.value = null;
  }
  searchParams.value = cloneDeep(data);
  searchParams.value.searchType = 1;
  searchParams.value.parentDirId = memoryFolder.value?.id || '';
};
const resetFun = (data: object) => {
  isSearching.value = false;
  currentFolder.value = memoryFolder.value;
  searchParams.value = cloneDeep(data);
  searchParams.value.fileId = currentFolder.value?.id || '';
};
const refreshTableFun = async () => {
  baseTableRef.value?.resetFun();
};
const onFolderConfirmFun = async (formData: any) => {
  if (currentFolderMode.value === 'add') {
    const req = {
      dirType: DIR_TYPE.KNOWLEDGE,
      parDirId: currentFolder.value?.id,
      dirName: formData.name,
      type: 0,
    };
    const res: any = await dataCreateDirApi(req);
    if (res.code === 200) {
      refreshTreeAfterAdd(currentFolder.value);
      folderModalVisible.value = false;
      ElMessage.success(res.message);
    }

  } else if (currentFolderMode.value === 'edit') {
    const req = {
      dirId: currentFolder.value.id,
      oldName: currentFolder.value.originalName,
      newName: formData.name,
      type: 0,
    };
    const res: any = await dataRenameDirApi(req);
    if (res.code === 200) {
      refreshTreeAfterModifyOrRemove(currentFolder.value);
      folderModalVisible.value = false;
      ElMessage.success(res.message);
    }

  }
};
const visible = ref(false);
const currentRow = ref();
const openModalFun = () => {
  visible.value = true;
  currentRow.value = null;
};
const onConfirmFun = async (formData: any) => {
  const req = {
    ...currentRow.value,
    templateId: formData.templateId,
    templateName: formData.templateName,
    file: formData.file.raw,
    fileName: formData.file.name,
    size: formData.file.size,
    projectName: formData.projectName,
    path: currentFolder.value.objectKey,
    dirId: currentFolder.value.id,
    chunk: 0,
    remarks: formData.remarks,
    projectId: formData.projectId,
    chunkTotal: 0,
    encryptKey: null,
    type: 0,
    analysisDirectionId: formData.analysisDirectionId,
  };
  let res: any;
  if (currentRow.value && currentRow.value.id) {
    res = await dataUpdateFileApi(req);
  } else {
    const req = {
      sourceFiles: formData.file,
      uploadTaskId: new Date().getTime(),
      dirId: currentFolder.value.id,
      projectId: formData.projectId,
      analysisDirectionId: formData.analysisDirectionId,
      templateId: formData.templateId,
      templateName: formData.templateName,
      remarks: formData.remarks,
      type: 0,
    };
    res = await batchAddFileInfoApi(req);
    if (res.code === 200) {
      res.data.forEach((item: any, index: number) => {
        emitter.emit('ADD_UPLOAD_FILE', {
          file: formData.originalName[index].raw, // 文件对象
          data: { // 接口返回的文件目录信息，包括配置信息
            ...item,
            isApprove: 1, // 0否 1是
            taskType: 2, // 2知识库
          },
        });
      });
    }
  }
  if (res.code === 200) {
    visible.value = false;
    refreshTableFun();
    ElMessage.success(res.message);
  }

};
const previewVisible = ref(false);
const previewFileFun = (row: any) => {
  currentRow.value = row;
  previewVisible.value = true;
};

const editFileFun = (row: any) => {
  currentRow.value = row;
  visible.value = true;
};
const delFileFun = async (row: any) => {
  const templateId = ref('');
  const templateName = ref('');
  ElMessageBox({
    title: i18n?.global?.t('通用.审核模版'),
    showCancelButton: true,
    showConfirmButton: true,
    confirmButtonText: i18n?.global?.t('通用.确定'),
    cancelButtonText: i18n?.global?.t('通用.取消'),
    message: () =>
      h(ApproveList, {
        modelValue: templateId.value,
        'onChange': (val: any) => {
          templateName.value = val.label;
          templateId.value = val.value;
        },
      }),
  }).then(async () => {
    if (!templateId.value) {
      ElMessage.error(i18n?.global?.t('通用.请选择审核模版'));
      return;
    }
    const req = {
      templateId: templateId.value,
      templateName: templateName.value,
      delFileId: row.id,
    };
    const res: any = await dataDelFileApi(req);
    if (res.code === 200) {
      refreshTableFun();
      ElMessage.success(res.message);
    }
  });

};
const onCellDblclickFun = (e: any) => {
  if (e.row.dataType === 1) {
    fileTreeRef.value?.openDirFun(e.row.id);
  }
};
const apiName: any = ref(null);
watchEffect(() => {
  if (currentFolder.value && currentFolder.value.id && !isSearching.value) {
    searchParams.value.fileId = currentFolder.value?.id || '';
    apiName.value = dataQueryDirApi;
  } else if (isSearching.value) {
    apiName.value = dataFileSearchApi;
  } else {
    apiName.value = null;
  }
});

const processVisible = ref(false);
const openProcessFun = (row: any) => {
  currentRow.value = row;
  processVisible.value = true;
};
</script>

<style lang="scss" scoped>
.gl-page-content-grey {
  height: 100%;
  .content {
    height: 100%;
    .options {
      margin-bottom: var(--margin-small);
    }
  }
}
</style>
