Merge pull request #1053 from SuanmoSuanyangTechnology/feature/knowledgeBase_zy
feat(web): add csv template
This commit is contained in:
1
web/src/assets/csv_template.csv
Normal file
1
web/src/assets/csv_template.csv
Normal file
@@ -0,0 +1 @@
|
|||||||
|
Q A
|
||||||
|
@@ -951,7 +951,8 @@ export const en = {
|
|||||||
feishuFolderToken: 'Folder Token',
|
feishuFolderToken: 'Folder Token',
|
||||||
feishuFolderTokenRequired: 'Please enter Folder Token',
|
feishuFolderTokenRequired: 'Please enter Folder Token',
|
||||||
feishuFolderTokenPlaceholder: 'Enter your Feishu Folder Token',
|
feishuFolderTokenPlaceholder: 'Enter your Feishu Folder Token',
|
||||||
}
|
},
|
||||||
|
csvTemplate: 'Click to download CSV template',
|
||||||
},
|
},
|
||||||
api: {
|
api: {
|
||||||
pageTitle: 'Memory library IAP document',
|
pageTitle: 'Memory library IAP document',
|
||||||
|
|||||||
@@ -438,7 +438,8 @@ export const zh = {
|
|||||||
feishuFolderToken: '文件夹 Token',
|
feishuFolderToken: '文件夹 Token',
|
||||||
feishuFolderTokenRequired: '请输入文件夹 Token',
|
feishuFolderTokenRequired: '请输入文件夹 Token',
|
||||||
feishuFolderTokenPlaceholder: '请输入您的飞书文件夹 Token',
|
feishuFolderTokenPlaceholder: '请输入您的飞书文件夹 Token',
|
||||||
}
|
},
|
||||||
|
csvTemplate: '点击下载 CSV 模板',
|
||||||
},
|
},
|
||||||
application: {
|
application: {
|
||||||
searchPlaceholder: '搜索应用',
|
searchPlaceholder: '搜索应用',
|
||||||
|
|||||||
@@ -596,111 +596,121 @@ const CreateDataset = () => {
|
|||||||
</div> }
|
</div> }
|
||||||
<div className='rb:bg-white rb:rounded-xl rb:flex-1 rb:mt-3'>
|
<div className='rb:bg-white rb:rounded-xl rb:flex-1 rb:mt-3'>
|
||||||
|
|
||||||
{current === 0 && (
|
{current === 0 && (<>
|
||||||
<div className='rb:flex rb:w-full rb:p-6'>
|
<div className='rb:flex rb:w-full rb:p-6'>
|
||||||
{source && (source === 'local' || source === 'csv') && (
|
{source && (source === 'local' || source === 'csv') && (
|
||||||
<UploadFiles
|
<UploadFiles
|
||||||
ref={uploadRef}
|
ref={uploadRef}
|
||||||
isCanDrag={true}
|
isCanDrag={true}
|
||||||
fileSize={100}
|
fileSize={100}
|
||||||
multiple={source !== 'csv'}
|
multiple={source !== 'csv'}
|
||||||
maxCount={source === 'csv' ? 1 : 99}
|
maxCount={source === 'csv' ? 1 : 99}
|
||||||
fileType={source === 'csv' ? csvFileType : fileType}
|
fileType={source === 'csv' ? csvFileType : fileType}
|
||||||
customRequest={handleUpload}
|
customRequest={handleUpload}
|
||||||
onChange={(fileList) => {
|
onChange={(fileList) => {
|
||||||
console.log('File list changed:', fileList);
|
console.log('File list changed:', fileList);
|
||||||
}}
|
}}
|
||||||
onRemove={async (file) => {
|
onRemove={async (file) => {
|
||||||
// 如果文件正在上传,取消上传
|
// 如果文件正在上传,取消上传
|
||||||
const fileUid = file.uid;
|
const fileUid = file.uid;
|
||||||
const abortController = abortControllersRef.current.get(fileUid);
|
const abortController = abortControllersRef.current.get(fileUid);
|
||||||
if (abortController) {
|
if (abortController) {
|
||||||
abortController.abort();
|
abortController.abort();
|
||||||
abortControllersRef.current.delete(fileUid);
|
abortControllersRef.current.delete(fileUid);
|
||||||
console.log('Upload cancelled:', (file as any).name);
|
console.log('Upload cancelled:', (file as any).name);
|
||||||
// 取消上传后直接返回 true,允许移除文件
|
// 取消上传后直接返回 true,允许移除文件
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Only delete server file when file upload was successful (has response.id)
|
// Only delete server file when file upload was successful (has response.id)
|
||||||
if (file.response?.id) {
|
if (file.response?.id) {
|
||||||
try {
|
try {
|
||||||
await deleteDocument(file.response.id);
|
await deleteDocument(file.response.id);
|
||||||
setRechunkFileIds(prev => prev.filter(id => id !== file.response.id));
|
setRechunkFileIds(prev => prev.filter(id => id !== file.response.id));
|
||||||
console.log('Server file deleted:', file.response.id);
|
console.log('Server file deleted:', file.response.id);
|
||||||
return true;
|
return true;
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
console.error('Failed to delete file:', error);
|
console.error('Failed to delete file:', error);
|
||||||
messageApi.error(t('common.deleteFailed') || 'Failed to delete file');
|
messageApi.error(t('common.deleteFailed') || 'Failed to delete file');
|
||||||
return false; // Don't remove file when deletion fails
|
return false; // Don't remove file when deletion fails
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Also allow removal in other cases (such as failed uploads)
|
// Also allow removal in other cases (such as failed uploads)
|
||||||
return true;
|
return true;
|
||||||
}} />
|
}}
|
||||||
)}
|
/>
|
||||||
{source && source === 'link' && (
|
)}
|
||||||
<div className='rb:flex rb:w-full rb:flex-col rb:mt-10 rb:px-40'>
|
{source && source === 'link' && (
|
||||||
|
<div className='rb:flex rb:w-full rb:flex-col rb:mt-10 rb:px-40'>
|
||||||
|
|
||||||
<div className='rb:text-sm rb:font-medium rb:text-gray-800 rb:mb-3'>
|
<div className='rb:text-sm rb:font-medium rb:text-gray-800 rb:mb-3'>
|
||||||
{t('knowledgeBase.webLink')}
|
{t('knowledgeBase.webLink')}
|
||||||
</div>
|
|
||||||
<TextArea rows={6} placeholder={t('knowledgeBase.webLinkPlaceholder')} />
|
|
||||||
<div className='rb:text-sm rb:text-gray-500 rb:mt-3'>
|
|
||||||
{t('knowledgeBase.webLinkDesc',{count: 5})}
|
|
||||||
</div>
|
|
||||||
<div className='rb:text-sm rb:font-medium rb:text-gray-800 rb:mt-10 rb:mb-3'>
|
|
||||||
{t('knowledgeBase.selectorTutorial')}
|
|
||||||
</div>
|
|
||||||
<Input className='rb:w-full' placeholder={t('knowledgeBase.webLinkPlaceholder')}/>
|
|
||||||
</div>
|
</div>
|
||||||
|
<TextArea rows={6} placeholder={t('knowledgeBase.webLinkPlaceholder')} />
|
||||||
|
<div className='rb:text-sm rb:text-gray-500 rb:mt-3'>
|
||||||
|
{t('knowledgeBase.webLinkDesc',{count: 5})}
|
||||||
|
</div>
|
||||||
|
<div className='rb:text-sm rb:font-medium rb:text-gray-800 rb:mt-10 rb:mb-3'>
|
||||||
|
{t('knowledgeBase.selectorTutorial')}
|
||||||
|
</div>
|
||||||
|
<Input className='rb:w-full' placeholder={t('knowledgeBase.webLinkPlaceholder')}/>
|
||||||
|
</div>
|
||||||
)}
|
)}
|
||||||
{source && source === 'text' && (
|
{source && source === 'text' && (
|
||||||
<div className='rb:flex rb:w-full rb:flex-col rb:mt-10 rb:px-20'>
|
<div className='rb:flex rb:w-full rb:flex-col rb:mt-10 rb:px-20'>
|
||||||
<Form
|
<Form
|
||||||
form={form}
|
form={form}
|
||||||
layout="vertical"
|
layout="vertical"
|
||||||
onValuesChange={() => {
|
onValuesChange={() => {
|
||||||
// 检查表单字段是否都已填写
|
// 检查表单字段是否都已填写
|
||||||
const values = form.getFieldsValue();
|
const values = form.getFieldsValue();
|
||||||
const isValid = !!(values.title?.trim() && values.content?.trim());
|
const isValid = !!(values.title?.trim() && values.content?.trim());
|
||||||
setTextFormValid(isValid);
|
setTextFormValid(isValid);
|
||||||
}}
|
}}
|
||||||
|
>
|
||||||
|
<Form.Item
|
||||||
|
name="title"
|
||||||
|
label={t('knowledgeBase.title')}
|
||||||
|
rules={[{ required: true, message: t('knowledgeBase.pleaseEnterTitle') }]}
|
||||||
>
|
>
|
||||||
<Form.Item
|
<Input placeholder={t('knowledgeBase.pleaseEnterTitle')} />
|
||||||
name="title"
|
</Form.Item>
|
||||||
label={t('knowledgeBase.title')}
|
|
||||||
rules={[{ required: true, message: t('knowledgeBase.pleaseEnterTitle') }]}
|
|
||||||
>
|
|
||||||
<Input placeholder={t('knowledgeBase.pleaseEnterTitle')} />
|
|
||||||
</Form.Item>
|
|
||||||
|
|
||||||
<Form.Item
|
<Form.Item
|
||||||
name="content"
|
name="content"
|
||||||
label={t('knowledgeBase.customContent')}
|
label={t('knowledgeBase.customContent')}
|
||||||
rules={[{ required: true, message: t('knowledgeBase.pleaseEnterContent') }]}
|
rules={[{ required: true, message: t('knowledgeBase.pleaseEnterContent') }]}
|
||||||
>
|
>
|
||||||
<Input.TextArea
|
<Input.TextArea
|
||||||
placeholder={t('knowledgeBase.pleaseEnterContent')}
|
placeholder={t('knowledgeBase.pleaseEnterContent')}
|
||||||
rows={8}
|
rows={8}
|
||||||
showCount
|
showCount
|
||||||
maxLength={5000}
|
maxLength={5000}
|
||||||
/>
|
/>
|
||||||
</Form.Item>
|
</Form.Item>
|
||||||
</Form>
|
</Form>
|
||||||
{/* <div className='rb:text-sm rb:font-medium rb:text-gray-800 rb:mb-3'>
|
{/* <div className='rb:text-sm rb:font-medium rb:text-gray-800 rb:mb-3'>
|
||||||
{t('knowledgeBase.customText')}
|
{t('knowledgeBase.customText')}
|
||||||
</div>
|
|
||||||
<Input className='rb:w-full' placeholder={t('knowledgeBase.webLinkPlaceholder')}/>
|
|
||||||
<div className='rb:text-sm rb:font-medium rb:text-gray-800 rb:mt-10 rb:mb-3'>
|
|
||||||
{t('knowledgeBase.customContent')}
|
|
||||||
</div>
|
|
||||||
<TextArea rows={6} placeholder={t('knowledgeBase.webLinkPlaceholder')} /> */}
|
|
||||||
</div>
|
</div>
|
||||||
|
<Input className='rb:w-full' placeholder={t('knowledgeBase.webLinkPlaceholder')}/>
|
||||||
|
<div className='rb:text-sm rb:font-medium rb:text-gray-800 rb:mt-10 rb:mb-3'>
|
||||||
|
{t('knowledgeBase.customContent')}
|
||||||
|
</div>
|
||||||
|
<TextArea rows={6} placeholder={t('knowledgeBase.webLinkPlaceholder')} /> */}
|
||||||
|
</div>
|
||||||
)}
|
)}
|
||||||
</div>
|
</div>
|
||||||
)}
|
{source === 'csv' &&
|
||||||
|
<a
|
||||||
|
href="@/assets/csv_template.csv"
|
||||||
|
download="csv_template.csv"
|
||||||
|
className='rb:mx-6 rb:text-sm rb:font-medium rb:text-gray-800 rb:-mt-6!'
|
||||||
|
>
|
||||||
|
{t('knowledgeBase.csvTemplate')}
|
||||||
|
</a>
|
||||||
|
}
|
||||||
|
</>)}
|
||||||
|
|
||||||
{current === 1 && (
|
{current === 1 && (
|
||||||
<div className='rb:flex rb:flex-col rb:mt-10 rb:px-40'>
|
<div className='rb:flex rb:flex-col rb:mt-10 rb:px-40'>
|
||||||
|
|||||||
Reference in New Issue
Block a user