Files
dify/web/app/components/workflow/skill/viewer/read-only-file-preview.tsx
Novice 499d237b7e fix: pass all CI quality checks - ESLint, TypeScript, basedpyright, pyrefly, lint-imports
Frontend:
- Migrate deprecated imports: modal→dialog, toast→ui/toast, tooltip→tooltip-plus,
  portal-to-follow-elem→portal-to-follow-elem-plus, select→ui/select, confirm→alert-dialog
- Replace next/* with @/next/* wrapper modules
- Convert TypeScript enums to const objects (erasable-syntax-only)
- Replace all `any` types with `unknown` or specific types in workflow types
- Fix unused vars, react-hooks-extra, react-refresh/only-export-components
- Extract InteractionMode to separate module, tool-block commands to commands.ts

Backend:
- Fix pyrefly errors: type narrowing, null guards, getattr patterns
- Remove unused TYPE_CHECKING imports in LLM node
- Add ignore_imports entries to .importlinter for dify_graph boundary violations

Made-with: Cursor
2026-03-24 10:54:58 +08:00

99 lines
2.6 KiB
TypeScript

'use client'
import * as React from 'react'
import Loading from '@/app/components/base/loading'
import dynamic from '@/next/dynamic'
import { useFetchTextContent } from '../hooks/use-fetch-text-content'
import { useFileTypeInfo } from '../hooks/use-file-type-info'
import { getFileLanguage } from '../utils/file-utils'
import MediaFilePreview from './media-file-preview'
import UnsupportedFileDownload from './unsupported-file-download'
const ReadOnlyCodePreview = dynamic(
() => import('./read-only-code-preview'),
{ ssr: false, loading: () => <Loading type="area" /> },
)
const ReadOnlyMarkdownPreview = dynamic(
() => import('./read-only-markdown-preview'),
{ ssr: false, loading: () => <Loading type="area" /> },
)
const SQLiteFilePreview = dynamic(
() => import('./sqlite-file-preview'),
{ ssr: false, loading: () => <Loading type="area" /> },
)
const PdfFilePreview = dynamic(
() => import('./pdf-file-preview'),
{ ssr: false, loading: () => <Loading type="area" /> },
)
type ReadOnlyFilePreviewProps = {
downloadUrl: string
fileName: string
extension?: string | null
fileSize?: number | null
}
const ReadOnlyFilePreview = ({
downloadUrl,
fileName,
extension,
fileSize,
}: ReadOnlyFilePreviewProps) => {
const fileNode = React.useMemo(
() => ({ name: fileName, extension }),
[fileName, extension],
)
const { isMarkdown, isCodeOrText, isImage, isVideo, isPdf, isSQLite, isPreviewable } = useFileTypeInfo(fileNode)
const isTextFile = isPreviewable && (isMarkdown || isCodeOrText)
const { data: textContent, isLoading: isTextLoading } = useFetchTextContent(
isTextFile ? downloadUrl : undefined,
)
if (!isPreviewable) {
return (
<UnsupportedFileDownload
name={fileName}
size={fileSize ?? undefined}
downloadUrl={downloadUrl}
/>
)
}
if (isTextFile && isTextLoading)
return <Loading type="area" />
if (isMarkdown)
return <ReadOnlyMarkdownPreview value={textContent ?? ''} />
if (isCodeOrText) {
return (
<ReadOnlyCodePreview
value={textContent ?? ''}
language={getFileLanguage(fileName)}
/>
)
}
if (isImage || isVideo)
return <MediaFilePreview type={isImage ? 'image' : 'video'} src={downloadUrl} />
if (isSQLite)
return <SQLiteFilePreview downloadUrl={downloadUrl} />
if (isPdf)
return <PdfFilePreview downloadUrl={downloadUrl} />
return (
<UnsupportedFileDownload
name={fileName}
size={fileSize ?? undefined}
downloadUrl={downloadUrl}
/>
)
}
export default React.memo(ReadOnlyFilePreview)