mirror of https://github.com/langgenius/dify.git
test(web): cover VisionFile normalization branches
This commit is contained in:
parent
c7256e6891
commit
5be09d8df1
|
|
@ -4,7 +4,13 @@ import type { VisionFile } from '@/types/app'
|
|||
import type { FileResponse } from '@/types/workflow'
|
||||
import { describe, expect, it } from 'vitest'
|
||||
import { TransferMethod } from '@/types/app'
|
||||
import { addFileInfos, sortAgentSorts } from '../index'
|
||||
import {
|
||||
addFileInfos,
|
||||
getVisionFileMimeType,
|
||||
getVisionFileName,
|
||||
getVisionFileSupportType,
|
||||
sortAgentSorts,
|
||||
} from '../index'
|
||||
|
||||
describe('tools/utils', () => {
|
||||
const createFileEntity = (overrides: Partial<FileEntity>): FileEntity => ({
|
||||
|
|
@ -54,6 +60,46 @@ describe('tools/utils', () => {
|
|||
})
|
||||
})
|
||||
|
||||
describe('VisionFile helpers', () => {
|
||||
it.each([
|
||||
['image', 'image/png'],
|
||||
['video', 'video/mp4'],
|
||||
['audio', 'audio/mpeg'],
|
||||
['application/pdf', 'application/pdf'],
|
||||
['document', 'application/octet-stream'],
|
||||
['unknown', 'application/octet-stream'],
|
||||
])('returns %s mime type as %s', (fileType, expectedMimeType) => {
|
||||
expect(getVisionFileMimeType(fileType)).toBe(expectedMimeType)
|
||||
})
|
||||
|
||||
it.each([
|
||||
['image', 'image'],
|
||||
['video', 'video'],
|
||||
['audio', 'audio'],
|
||||
['document', 'document'],
|
||||
['image/png', 'image'],
|
||||
['video/mp4', 'video'],
|
||||
['audio/mpeg', 'audio'],
|
||||
['application/pdf', 'document'],
|
||||
['application/json', 'document'],
|
||||
] as const)('returns %s support type as %s', (fileType, expectedSupportType) => {
|
||||
expect(getVisionFileSupportType(fileType)).toBe(expectedSupportType)
|
||||
})
|
||||
|
||||
it('extracts the file name from URLs with query params', () => {
|
||||
expect(getVisionFileName('https://example.com/generated.png?signature=1', 'image')).toBe('generated.png')
|
||||
})
|
||||
|
||||
it.each([
|
||||
['image', 'generated_image.png'],
|
||||
['video', 'generated_video.mp4'],
|
||||
['audio', 'generated_audio.mp3'],
|
||||
['document', 'generated_file.bin'],
|
||||
] as const)('returns a fallback file name for %s URLs without a file segment', (supportFileType, expectedFileName) => {
|
||||
expect(getVisionFileName('https://example.com/', supportFileType)).toBe(expectedFileName)
|
||||
})
|
||||
})
|
||||
|
||||
describe('addFileInfos', () => {
|
||||
it('returns null/undefined input as-is', () => {
|
||||
expect(addFileInfos(null as unknown as ThoughtItem[], [])).toBeNull()
|
||||
|
|
@ -131,6 +177,30 @@ describe('tools/utils', () => {
|
|||
}))
|
||||
})
|
||||
|
||||
it('matches VisionFile payloads by upload_file_id when id is missing', () => {
|
||||
const visionFile: VisionFile = {
|
||||
type: 'document',
|
||||
transfer_method: TransferMethod.remote_url,
|
||||
url: 'https://example.com/',
|
||||
upload_file_id: 'upload-vision-fallback',
|
||||
}
|
||||
|
||||
const items = [{ id: '1', files: ['upload-vision-fallback'] }] as unknown as ThoughtItem[]
|
||||
|
||||
const result = addFileInfos(items, [visionFile])
|
||||
const messageFiles = (result[0] as ThoughtItem & { message_files: FileEntity[] }).message_files
|
||||
|
||||
expect(messageFiles).toHaveLength(1)
|
||||
expect(messageFiles[0]).toEqual(expect.objectContaining({
|
||||
id: 'upload-vision-fallback',
|
||||
name: 'generated_file.bin',
|
||||
type: 'application/octet-stream',
|
||||
transferMethod: TransferMethod.remote_url,
|
||||
supportFileType: 'document',
|
||||
uploadedId: 'upload-vision-fallback',
|
||||
}))
|
||||
})
|
||||
|
||||
it('returns items without files unchanged', () => {
|
||||
const items = [
|
||||
{ id: '1' },
|
||||
|
|
|
|||
|
|
@ -32,6 +32,7 @@ export const sortAgentSorts = (list: ThoughtItem[]) => {
|
|||
|
||||
type AgentThoughtHistoryFile = FileResponse & { id: string }
|
||||
type AgentThoughtMessageFile = FileEntity | VisionFile | AgentThoughtHistoryFile
|
||||
type VisionFileSupportType = 'image' | 'video' | 'audio' | 'document'
|
||||
|
||||
const isFileEntity = (file: AgentThoughtMessageFile): file is FileEntity => {
|
||||
return 'transferMethod' in file
|
||||
|
|
@ -41,7 +42,7 @@ const isAgentThoughtHistoryFile = (file: AgentThoughtMessageFile): file is Agent
|
|||
return 'filename' in file && 'mime_type' in file
|
||||
}
|
||||
|
||||
const getVisionFileMimeType = (fileType: string) => {
|
||||
export const getVisionFileMimeType = (fileType: string) => {
|
||||
if (fileType.includes('/'))
|
||||
return fileType
|
||||
|
||||
|
|
@ -57,35 +58,25 @@ const getVisionFileMimeType = (fileType: string) => {
|
|||
}
|
||||
}
|
||||
|
||||
const getVisionFileSupportType = (fileType: string) => {
|
||||
export const getVisionFileSupportType = (fileType: string): VisionFileSupportType => {
|
||||
if (fileType.includes('/')) {
|
||||
const [mainType, subType] = fileType.split('/')
|
||||
if (mainType === 'image')
|
||||
return 'image'
|
||||
if (mainType === 'video')
|
||||
return 'video'
|
||||
if (mainType === 'audio')
|
||||
return 'audio'
|
||||
if (subType === 'pdf')
|
||||
return 'document'
|
||||
const [mainType] = fileType.split('/')
|
||||
if (['image', 'video', 'audio'].includes(mainType))
|
||||
return mainType as 'image' | 'video' | 'audio'
|
||||
return 'document'
|
||||
}
|
||||
|
||||
switch (fileType) {
|
||||
case 'image':
|
||||
return 'image'
|
||||
case 'video':
|
||||
return 'video'
|
||||
case 'audio':
|
||||
return 'audio'
|
||||
case 'document':
|
||||
return 'document'
|
||||
return fileType
|
||||
default:
|
||||
return 'document'
|
||||
}
|
||||
}
|
||||
|
||||
const getVisionFileName = (url: string, supportFileType: string) => {
|
||||
export const getVisionFileName = (url: string, supportFileType: VisionFileSupportType) => {
|
||||
const fileName = url.split('/').pop()?.split('?')[0]
|
||||
if (fileName)
|
||||
return fileName
|
||||
|
|
|
|||
Loading…
Reference in New Issue