- 收敛 easyflow-ui-admin 的 lint、格式和类型问题 - 修正 demo 页面与管理端前端构建失败点 - 验证 pnpm lint 与 pnpm build 均已通过
261 lines
6.3 KiB
Vue
261 lines
6.3 KiB
Vue
<script setup lang="ts">
|
|
import { computed, ref } from 'vue';
|
|
import { useRoute } from 'vue-router';
|
|
|
|
import { $t } from '@easyflow/locales';
|
|
|
|
import { Back } from '@element-plus/icons-vue';
|
|
import { ElButton, ElMessage, ElStep, ElSteps } from 'element-plus';
|
|
|
|
import { api } from '#/api/request';
|
|
import ComfirmImportDocument from '#/views/ai/documentCollection/ComfirmImportDocument.vue';
|
|
import ImportKnowledgeFileContainer from '#/views/ai/documentCollection/ImportKnowledgeFileContainer.vue';
|
|
import SegmenterDoc from '#/views/ai/documentCollection/SegmenterDoc.vue';
|
|
import SplitterDocPreview from '#/views/ai/documentCollection/SplitterDocPreview.vue';
|
|
|
|
interface UploadFileItem {
|
|
fileName: string;
|
|
filePath: string;
|
|
}
|
|
|
|
interface AnalyzeItem {
|
|
fileName: string;
|
|
filePath: string;
|
|
strategyConfig: Record<string, any>;
|
|
}
|
|
|
|
interface PreviewItem {
|
|
fileName: string;
|
|
previewSessionId: string;
|
|
totalChunks?: number;
|
|
}
|
|
|
|
const emits = defineEmits(['importBack']);
|
|
const route = useRoute();
|
|
const knowledgeId = computed(() => (route.query.id as string) || '');
|
|
|
|
const fileUploadRef = ref<InstanceType<typeof ImportKnowledgeFileContainer>>();
|
|
const segmenterDocRef = ref<InstanceType<typeof SegmenterDoc>>();
|
|
|
|
const activeStep = ref(0);
|
|
const files = ref<UploadFileItem[]>([]);
|
|
const analysisItems = ref<AnalyzeItem[]>([]);
|
|
const previewItems = ref<PreviewItem[]>([]);
|
|
const commitResults = ref<any[]>([]);
|
|
|
|
const analyzing = ref(false);
|
|
const previewing = ref(false);
|
|
const committing = ref(false);
|
|
|
|
const canGoPrevious = computed(() => activeStep.value > 0 && !committing.value);
|
|
|
|
function back() {
|
|
emits('importBack');
|
|
}
|
|
|
|
function getUploadedFiles() {
|
|
return fileUploadRef.value?.getFilesData?.() || [];
|
|
}
|
|
|
|
async function goToNextStep() {
|
|
if (activeStep.value === 0) {
|
|
const currentFiles = getUploadedFiles();
|
|
if (currentFiles.length === 0) {
|
|
ElMessage.error($t('message.uploadFileFirst'));
|
|
return;
|
|
}
|
|
files.value = currentFiles;
|
|
await runAnalyze();
|
|
activeStep.value = 1;
|
|
return;
|
|
}
|
|
|
|
if (activeStep.value === 1) {
|
|
await runPreview();
|
|
activeStep.value = 2;
|
|
return;
|
|
}
|
|
|
|
if (activeStep.value === 2) {
|
|
activeStep.value = 3;
|
|
}
|
|
}
|
|
|
|
function goToPreviousStep() {
|
|
if (!canGoPrevious.value) {
|
|
return;
|
|
}
|
|
activeStep.value -= 1;
|
|
}
|
|
|
|
async function runAnalyze() {
|
|
analyzing.value = true;
|
|
try {
|
|
const res = await api.post('/api/v1/document/import/analyze', {
|
|
files: files.value.map((item) => ({
|
|
fileName: item.fileName,
|
|
filePath: item.filePath,
|
|
})),
|
|
knowledgeId: knowledgeId.value,
|
|
});
|
|
analysisItems.value = res.data?.items || [];
|
|
} finally {
|
|
analyzing.value = false;
|
|
}
|
|
}
|
|
|
|
async function runPreview() {
|
|
const previewRequestItems =
|
|
segmenterDocRef.value?.getPreviewRequestItems?.() || [];
|
|
if (previewRequestItems.length === 0) {
|
|
ElMessage.error($t('documentCollection.importDoc.previewEmpty'));
|
|
return;
|
|
}
|
|
previewing.value = true;
|
|
try {
|
|
const res = await api.post('/api/v1/document/import/preview', {
|
|
files: previewRequestItems,
|
|
knowledgeId: knowledgeId.value,
|
|
});
|
|
previewItems.value = res.data?.items || [];
|
|
commitResults.value = [];
|
|
} finally {
|
|
previewing.value = false;
|
|
}
|
|
}
|
|
|
|
async function confirmImport() {
|
|
if (previewItems.value.length === 0) {
|
|
ElMessage.error($t('documentCollection.importDoc.previewEmpty'));
|
|
return;
|
|
}
|
|
committing.value = true;
|
|
try {
|
|
const res = await api.post('/api/v1/document/import/commit', {
|
|
knowledgeId: knowledgeId.value,
|
|
previewSessionIds: previewItems.value.map(
|
|
(item) => item.previewSessionId,
|
|
),
|
|
});
|
|
commitResults.value = res.data?.results || [];
|
|
if ((res.data?.errorCount || 0) === 0) {
|
|
ElMessage.success($t('documentCollection.splitterDoc.importSuccess'));
|
|
}
|
|
} finally {
|
|
committing.value = false;
|
|
}
|
|
}
|
|
</script>
|
|
|
|
<template>
|
|
<div class="imp-doc-kno-container">
|
|
<div class="imp-doc-header">
|
|
<ElButton :icon="Back" @click="back">
|
|
{{ $t('button.back') }}
|
|
</ElButton>
|
|
</div>
|
|
|
|
<div class="imp-doc-kno-content">
|
|
<div class="step-card">
|
|
<ElSteps :active="activeStep" align-center>
|
|
<ElStep :title="$t('documentCollection.importDoc.fileUpload')" />
|
|
<ElStep
|
|
:title="$t('documentCollection.importDoc.strategyAnalysis')"
|
|
/>
|
|
<ElStep
|
|
:title="$t('documentCollection.importDoc.segmentedPreview')"
|
|
/>
|
|
<ElStep :title="$t('documentCollection.importDoc.confirmImport')" />
|
|
</ElSteps>
|
|
</div>
|
|
|
|
<div class="step-body">
|
|
<ImportKnowledgeFileContainer
|
|
v-if="activeStep === 0"
|
|
ref="fileUploadRef"
|
|
/>
|
|
<SegmenterDoc
|
|
v-else-if="activeStep === 1"
|
|
ref="segmenterDocRef"
|
|
:analysis-items="analysisItems"
|
|
/>
|
|
<SplitterDocPreview
|
|
v-else-if="activeStep === 2"
|
|
:preview-items="previewItems"
|
|
/>
|
|
<ComfirmImportDocument
|
|
v-else
|
|
:preview-items="previewItems"
|
|
:commit-results="commitResults"
|
|
:loading="committing"
|
|
/>
|
|
</div>
|
|
</div>
|
|
|
|
<div class="imp-doc-footer">
|
|
<ElButton v-if="canGoPrevious" @click="goToPreviousStep">
|
|
{{ $t('button.previousStep') }}
|
|
</ElButton>
|
|
<ElButton
|
|
v-if="activeStep < 3"
|
|
type="primary"
|
|
:loading="analyzing || previewing"
|
|
@click="goToNextStep"
|
|
>
|
|
{{ $t('button.nextStep') }}
|
|
</ElButton>
|
|
<ElButton
|
|
v-else
|
|
type="primary"
|
|
:loading="committing"
|
|
:disabled="committing"
|
|
@click="confirmImport"
|
|
>
|
|
{{ $t('button.startImport') }}
|
|
</ElButton>
|
|
</div>
|
|
</div>
|
|
</template>
|
|
|
|
<style scoped>
|
|
.imp-doc-kno-container {
|
|
position: relative;
|
|
display: flex;
|
|
flex-direction: column;
|
|
height: 100%;
|
|
padding: 24px;
|
|
background: var(--el-bg-color);
|
|
border-radius: 16px;
|
|
}
|
|
|
|
.imp-doc-kno-content {
|
|
display: flex;
|
|
flex: 1;
|
|
flex-direction: column;
|
|
gap: 20px;
|
|
padding-top: 16px;
|
|
overflow: auto;
|
|
}
|
|
|
|
.step-card {
|
|
padding: 20px 24px;
|
|
background: var(--el-fill-color-blank);
|
|
border: 1px solid var(--el-border-color-light);
|
|
border-radius: 16px;
|
|
}
|
|
|
|
.step-body {
|
|
flex: 1;
|
|
padding-bottom: 72px;
|
|
}
|
|
|
|
.imp-doc-footer {
|
|
position: absolute;
|
|
right: 24px;
|
|
bottom: 24px;
|
|
display: flex;
|
|
gap: 12px;
|
|
align-items: center;
|
|
}
|
|
</style>
|