feat: metadata panel

This commit is contained in:
Joel 2025-02-19 18:38:29 +08:00
parent b568947e00
commit 10fccd2b3f
6 changed files with 165 additions and 6 deletions

View File

@ -21,7 +21,7 @@ import Input from '@/app/components/base/input'
import { ApiConnectionMod } from '@/app/components/base/icons/src/vender/solid/development'
import CheckboxWithLabel from '@/app/components/datasets/create/website/base/checkbox-with-label'
// import DatasetMetadataDrawer from '@/app/components/datasets/metadata/dataset-metadata-drawer'
import NoData from '@/app/components/datasets/metadata/metadata-document/no-data'
import MetaDataDocument from '@/app/components/datasets/metadata/metadata-document'
// Services
import { fetchDatasetApiBaseUrl } from '@/service/datasets'
@ -92,8 +92,8 @@ const Container = () => {
return (
<div ref={containerRef} className='grow relative flex flex-col bg-background-body overflow-y-auto scroll-container'>
<div className='flex justify-end mt-[300px]'>
<NoData onStart={() => { }} />
<div className='flex justify-end mt-[300px] mr-[100px]'>
<MetaDataDocument />
{/* <SelectMetadataModal trigger={<Button className='w-[200px]'>select</Button>} onSave={(data) => { console.log(data) }} />
<CreateModal trigger={<Button className='w-[200px]'>add</Button>} hasBack onSave={(data) => { console.log(data) }} />
<Button className='flex w-[200px]' size="medium" onClick={() => setShowExternalApiPanel(true)}>

View File

@ -7,17 +7,20 @@ import { InputNumber } from '@/app/components/base/input-number'
import cn from '@/utils/classnames'
type Props = {
className?: string
type: DataType
value: any
onChange: (value: any) => void
}
const InputCombined: FC<Props> = ({
className: configClassName,
type,
value,
onChange,
}) => {
const className = 'grow p-0.5 h-6 text-xs'
// TODO: configClassName...
const className = cn('grow p-0.5 h-6 text-xs', configClassName)
if (type === DataType.time)
return <div className='grow text-xs'>Datepicker placeholder</div>

View File

@ -0,0 +1,26 @@
'use client'
import type { FC } from 'react'
import React from 'react'
type Props = {
label: string
children: React.ReactNode
}
const Field: FC<Props> = ({
label,
children,
}) => {
return (
<div className='flex items-start space-x-2'>
<div className='shrink-0 flex w-[128px] truncate pt-1 h-6 items-center text-text-tertiary system-xs-medium'>
{label}
</div>
<div className='shrink-0 w-[244px]'>
{children}
</div>
</div>
)
}
export default React.memo(Field)

View File

@ -0,0 +1,61 @@
'use client'
import type { FC } from 'react'
import React, { useState } from 'react'
import { DataType, type MetadataItemWithValue } from '../types'
import InfoGroup from './info-group'
import NoData from './no-data'
import Button from '@/app/components/base/button'
import { RiEditLine } from '@remixicon/react'
import { useTranslation } from 'react-i18next'
const MetadataDocument: FC = () => {
const { t } = useTranslation()
const [isEdit, setIsEdit] = useState(false)
const [list, setList] = useState<MetadataItemWithValue[]>([
{
id: '1',
name: 'Doc type',
value: 'PDF',
type: DataType.string,
},
{
id: '2',
name: 'Title',
value: 'PDF',
type: DataType.string,
},
])
const hasData = list.length > 0
return (
<div>
{hasData ? (
<InfoGroup
title='Metadata'
titleTooltip='Metadata serves as a critical filter that enhances the accuracy and relevance of information retrieval. You can modify and add metadata for this document here.'
list={list}
headerRight={isEdit ? <div>Save</div> : <Button variant='ghost' onClick={() => setIsEdit(true)}>
<RiEditLine className='size-3.5 text-text-tertiary cursor-pointer' />
<div>{t('common.operation.edit')}</div>
</Button>}
isEdit={isEdit}
onChange={(item) => {
const newList = list.map(i => (i.name === item.name ? item : i))
setList(newList)
}}
onDelete={(item) => {
const newList = list.filter(i => i.name !== item.name)
setList(newList)
}}
onAdd={() => {
}}
/>
) : (
<NoData onStart={() => { }} />
)}
</div>
)
}
export default React.memo(MetadataDocument)

View File

@ -0,0 +1,66 @@
'use client'
import type { FC } from 'react'
import React from 'react'
import type { MetadataItemWithValue } from '../types'
import Field from './field'
import InputCombined from '../edit-metadata-batch/input-combined'
import { RiDeleteBinLine } from '@remixicon/react'
import Tooltip from '@/app/components/base/tooltip'
type Props = {
title: string
titleTooltip?: string
headerRight?: React.ReactNode
list: MetadataItemWithValue[]
isEdit?: boolean
onChange?: (item: MetadataItemWithValue) => void
onDelete?: (item: MetadataItemWithValue) => void
onAdd?: (item: MetadataItemWithValue) => void
}
const InfoGroup: FC<Props> = ({
title,
titleTooltip,
headerRight,
list,
isEdit,
onChange,
onDelete,
onAdd,
}) => {
return (
<div>
<div className='flex items-center justify-between'>
<div className='flex items-center space-x-1'>
<div className='system-xs-medium text-text-secondary'>{title}</div>
{titleTooltip && (
<Tooltip popupContent={titleTooltip} />
)}
</div>
{headerRight}
{/* <div className='flex px-1.5 rounded-md hover:bg-components-button-tertiary-bg-hover items-center h-6 space-x-1 cursor-pointer' onClick={() => setIsEdit(true)}>
</div> */}
</div>
<div className='space-y-1'>
{list.map((item, i) => (
<Field key={item.id || `${i}`} label={item.name}>
{isEdit ? (
<div className='flex items-center space-x-0.5'>
<InputCombined
className='h-6'
type={item.type}
value={item.value}
onChange={value => onChange?.({ ...item, value })}
/>
<div className='shrink-0 p-1 rounded-md text-text-tertiary hover:text-text-destructive hover:bg-state-destructive-hover cursor-pointer'>
<RiDeleteBinLine className='size-4' />
</div>
</div>
) : (<div className='system-xs-regular text-text-secondary'>{item.value}</div>)}
</Field>
))}
</div>
</div>
)
}
export default React.memo(InfoGroup)

View File

@ -10,6 +10,10 @@ export type MetadataItem = {
name: string
}
export type MetadataItemWithValue = MetadataItem & {
value: string | number
}
export type MetadataItemWithValueLength = MetadataItem & {
valueLength: number
}
@ -17,8 +21,7 @@ export enum UpdateType {
changeValue = 'changeValue',
delete = 'delete',
}
export type MetadataItemWithEdit = MetadataItem & {
value: string | number
export type MetadataItemWithEdit = MetadataItemWithValue & {
isMultipleValue?: boolean
isUpdated?: boolean
updateType?: UpdateType