import { api } from "@/src/utils/api"; import { ImageOff } from "lucide-react"; import { MediaReferenceStringSchema, type ParsedMediaReferenceType, } from "@langfuse/shared"; import { ResizableImage } from "@/src/components/ui/resizable-image"; import useProjectIdFromURL from "@/src/hooks/useProjectIdFromURL"; import { type MediaContentType, type MediaReturnType, } from "@/src/features/media/validation"; import { File, Image as ImageIcon, Volume2 } from "lucide-react"; export const LangfuseMediaView = ({ mediaReferenceString, mediaAPIReturnValue, asFileIcon = false, }: { mediaReferenceString?: string | ParsedMediaReferenceType; mediaAPIReturnValue?: MediaReturnType; asFileIcon?: boolean; }) => { let mediaData: { id: string; type: MediaContentType } | null = null; const projectId = useProjectIdFromURL(); if (mediaReferenceString && typeof mediaReferenceString === "string") { const { success, data: parsedTag } = MediaReferenceStringSchema.safeParse(mediaReferenceString); if (success) mediaData = { id: parsedTag.id, type: parsedTag.type as MediaContentType, }; } else if (mediaReferenceString && typeof mediaReferenceString !== "string") { mediaData = { id: mediaReferenceString.id, type: mediaReferenceString.type as MediaContentType, }; } else if (mediaAPIReturnValue) { mediaData = { id: mediaAPIReturnValue.mediaId, type: mediaAPIReturnValue.contentType, }; } if (!mediaData) return (
Invalid Langfuse Media Tag
); const { data } = api.media.getById.useQuery( { mediaId: mediaData.id, projectId: projectId as string, }, { enabled: Boolean(projectId), refetchOnWindowFocus: false, refetchOnMount: false, refetchOnReconnect: false, staleTime: 55 * 60 * 1000, // 55 minutes, s3 links expire after 1 hour }, ); const mediaUrl = data?.url; if (!mediaUrl) return null; if (asFileIcon) { return ; } if (mediaData.type.startsWith("image")) { return (
); } else if (mediaData.type.startsWith("audio")) { return ; } else if (mediaData.type.startsWith("video")) { return ; } else { return ; } }; function FileViewer({ src, contentType, }: { src?: string; contentType: MediaContentType; }) { if (!src) return null; const mimeType = String(contentType); const fileName = src.split("/").pop()?.split("?")[0] || ""; const fileType = mimeType.split("/")[0]; const fileExtension = mimeType.split("/")[1]?.toUpperCase() || "FILE"; const openInNewTab = () => { window.open(src, "_blank", "noopener,noreferrer"); }; return ( ); } function AudioPlayer({ src }: { src?: string }) { if (!src) return null; return ( ); } function VideoPlayer({ src }: { src?: string }) { if (!src) return null; return ( ); }