balibabu
fix: filter knowledge list by keywords and clear the selected file list after the file is uploaded successfully and add ellipsis pattern to chunk list (#628)
8e109c7
| import { useFetchChunkList } from '@/hooks/chunkHooks'; | |
| import { useDeleteChunkByIds } from '@/hooks/knowledgeHook'; | |
| import type { PaginationProps } from 'antd'; | |
| import { Divider, Flex, Pagination, Space, Spin, message } from 'antd'; | |
| import classNames from 'classnames'; | |
| import { useCallback, useEffect, useState } from 'react'; | |
| import { useDispatch, useSearchParams, useSelector } from 'umi'; | |
| import ChunkCard from './components/chunk-card'; | |
| import CreatingModal from './components/chunk-creating-modal'; | |
| import ChunkToolBar from './components/chunk-toolbar'; | |
| import DocumentPreview from './components/document-preview/preview'; | |
| import { | |
| useChangeChunkTextMode, | |
| useHandleChunkCardClick, | |
| useSelectChunkListLoading, | |
| useSelectDocumentInfo, | |
| } from './hooks'; | |
| import { ChunkModelState } from './model'; | |
| import { useTranslation } from 'react-i18next'; | |
| import styles from './index.less'; | |
| const Chunk = () => { | |
| const dispatch = useDispatch(); | |
| const chunkModel: ChunkModelState = useSelector( | |
| (state: any) => state.chunkModel, | |
| ); | |
| const [selectedChunkIds, setSelectedChunkIds] = useState<string[]>([]); | |
| const [searchParams] = useSearchParams(); | |
| const { data = [], total, pagination } = chunkModel; | |
| const loading = useSelectChunkListLoading(); | |
| const documentId: string = searchParams.get('doc_id') || ''; | |
| const [chunkId, setChunkId] = useState<string | undefined>(); | |
| const { removeChunk } = useDeleteChunkByIds(); | |
| const documentInfo = useSelectDocumentInfo(); | |
| const { handleChunkCardClick, selectedChunkId } = useHandleChunkCardClick(); | |
| const isPdf = documentInfo.type === 'pdf'; | |
| const { t } = useTranslation(); | |
| const { changeChunkTextMode, textMode } = useChangeChunkTextMode(); | |
| const getChunkList = useFetchChunkList(); | |
| const handleEditChunk = useCallback( | |
| (chunk_id?: string) => { | |
| setChunkId(chunk_id); | |
| dispatch({ | |
| type: 'chunkModel/setIsShowCreateModal', | |
| payload: true, | |
| }); | |
| }, | |
| [dispatch], | |
| ); | |
| const onPaginationChange: PaginationProps['onShowSizeChange'] = ( | |
| page, | |
| size, | |
| ) => { | |
| setSelectedChunkIds([]); | |
| dispatch({ | |
| type: 'chunkModel/setPagination', | |
| payload: { | |
| current: page, | |
| pageSize: size, | |
| }, | |
| }); | |
| getChunkList(); | |
| }; | |
| const selectAllChunk = useCallback( | |
| (checked: boolean) => { | |
| setSelectedChunkIds(checked ? data.map((x) => x.chunk_id) : []); | |
| }, | |
| [data], | |
| ); | |
| const handleSingleCheckboxClick = useCallback( | |
| (chunkId: string, checked: boolean) => { | |
| setSelectedChunkIds((previousIds) => { | |
| const idx = previousIds.findIndex((x) => x === chunkId); | |
| const nextIds = [...previousIds]; | |
| if (checked && idx === -1) { | |
| nextIds.push(chunkId); | |
| } else if (!checked && idx !== -1) { | |
| nextIds.splice(idx, 1); | |
| } | |
| return nextIds; | |
| }); | |
| }, | |
| [], | |
| ); | |
| const showSelectedChunkWarning = useCallback(() => { | |
| message.warning(t('message.pleaseSelectChunk')); | |
| }, [t]); | |
| const handleRemoveChunk = useCallback(async () => { | |
| if (selectedChunkIds.length > 0) { | |
| const resCode: number = await removeChunk(selectedChunkIds, documentId); | |
| if (resCode === 0) { | |
| setSelectedChunkIds([]); | |
| } | |
| } else { | |
| showSelectedChunkWarning(); | |
| } | |
| }, [selectedChunkIds, documentId, removeChunk, showSelectedChunkWarning]); | |
| const switchChunk = useCallback( | |
| async (available?: number, chunkIds?: string[]) => { | |
| let ids = chunkIds; | |
| if (!chunkIds) { | |
| ids = selectedChunkIds; | |
| if (selectedChunkIds.length === 0) { | |
| showSelectedChunkWarning(); | |
| return; | |
| } | |
| } | |
| const resCode: number = await dispatch<any>({ | |
| type: 'chunkModel/switch_chunk', | |
| payload: { | |
| chunk_ids: ids, | |
| available_int: available, | |
| doc_id: documentId, | |
| }, | |
| }); | |
| if (!chunkIds && resCode === 0) { | |
| getChunkList(); | |
| } | |
| }, | |
| [ | |
| dispatch, | |
| documentId, | |
| getChunkList, | |
| selectedChunkIds, | |
| showSelectedChunkWarning, | |
| ], | |
| ); | |
| useEffect(() => { | |
| getChunkList(); | |
| return () => { | |
| dispatch({ | |
| type: 'chunkModel/resetFilter', // TODO: need to reset state uniformly | |
| }); | |
| }; | |
| }, [dispatch, getChunkList]); | |
| return ( | |
| <> | |
| <div className={styles.chunkPage}> | |
| <ChunkToolBar | |
| getChunkList={getChunkList} | |
| selectAllChunk={selectAllChunk} | |
| createChunk={handleEditChunk} | |
| removeChunk={handleRemoveChunk} | |
| checked={selectedChunkIds.length === data.length} | |
| switchChunk={switchChunk} | |
| changeChunkTextMode={changeChunkTextMode} | |
| ></ChunkToolBar> | |
| <Divider></Divider> | |
| <Flex flex={1} gap={'middle'}> | |
| <Flex | |
| vertical | |
| className={isPdf ? styles.pagePdfWrapper : styles.pageWrapper} | |
| > | |
| <Spin spinning={loading} className={styles.spin} size="large"> | |
| <div className={styles.pageContent}> | |
| <Space | |
| direction="vertical" | |
| size={'middle'} | |
| className={classNames(styles.chunkContainer, { | |
| [styles.chunkOtherContainer]: !isPdf, | |
| })} | |
| > | |
| {data.map((item) => ( | |
| <ChunkCard | |
| item={item} | |
| key={item.chunk_id} | |
| editChunk={handleEditChunk} | |
| checked={selectedChunkIds.some( | |
| (x) => x === item.chunk_id, | |
| )} | |
| handleCheckboxClick={handleSingleCheckboxClick} | |
| switchChunk={switchChunk} | |
| clickChunkCard={handleChunkCardClick} | |
| selected={item.chunk_id === selectedChunkId} | |
| textMode={textMode} | |
| ></ChunkCard> | |
| ))} | |
| </Space> | |
| </div> | |
| </Spin> | |
| <div className={styles.pageFooter}> | |
| <Pagination | |
| responsive | |
| showLessItems | |
| showQuickJumper | |
| showSizeChanger | |
| onChange={onPaginationChange} | |
| pageSize={pagination.pageSize} | |
| pageSizeOptions={[10, 30, 60, 90]} | |
| current={pagination.current} | |
| size={'small'} | |
| total={total} | |
| /> | |
| </div> | |
| </Flex> | |
| {isPdf && ( | |
| <section className={styles.documentPreview}> | |
| <DocumentPreview | |
| selectedChunkId={selectedChunkId} | |
| ></DocumentPreview> | |
| </section> | |
| )} | |
| </Flex> | |
| </div> | |
| <CreatingModal doc_id={documentId} chunkId={chunkId} /> | |
| </> | |
| ); | |
| }; | |
| export default Chunk; | |