2025-04-22 22:40:01 -07:00
|
|
|
import type { CoreAssistantMessage, CoreToolMessage, UIMessage } from 'ai';
|
2024-11-15 12:18:17 -05:00
|
|
|
import { type ClassValue, clsx } from 'clsx';
|
2024-10-30 16:01:24 +05:30
|
|
|
import { twMerge } from 'tailwind-merge';
|
2025-04-21 10:26:58 -07:00
|
|
|
import type { Document } from '@/lib/db/schema';
|
2025-05-13 19:01:28 -07:00
|
|
|
import { ChatSDKError, type ErrorCode } from './errors';
|
2024-10-15 10:50:50 +05:30
|
|
|
|
2023-05-19 12:33:56 -04:00
|
|
|
export function cn(...inputs: ClassValue[]) {
|
2024-10-11 18:00:22 +05:30
|
|
|
return twMerge(clsx(inputs));
|
2023-05-19 12:33:56 -04:00
|
|
|
}
|
|
|
|
|
|
2024-10-11 18:00:22 +05:30
|
|
|
export const fetcher = async (url: string) => {
|
2025-05-13 19:01:28 -07:00
|
|
|
const response = await fetch(url);
|
|
|
|
|
|
|
|
|
|
if (!response.ok) {
|
|
|
|
|
const { code, cause } = await response.json();
|
|
|
|
|
throw new ChatSDKError(code as ErrorCode, cause);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
return response.json();
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
export async function fetchWithErrorHandlers(
|
|
|
|
|
input: RequestInfo | URL,
|
|
|
|
|
init?: RequestInit,
|
|
|
|
|
) {
|
|
|
|
|
try {
|
|
|
|
|
const response = await fetch(input, init);
|
2024-03-14 20:00:52 +03:00
|
|
|
|
2025-05-13 19:01:28 -07:00
|
|
|
if (!response.ok) {
|
|
|
|
|
const { code, cause } = await response.json();
|
|
|
|
|
throw new ChatSDKError(code as ErrorCode, cause);
|
|
|
|
|
}
|
2024-03-19 04:37:30 +03:00
|
|
|
|
2025-05-13 19:01:28 -07:00
|
|
|
return response;
|
|
|
|
|
} catch (error: unknown) {
|
|
|
|
|
if (typeof navigator !== 'undefined' && !navigator.onLine) {
|
|
|
|
|
throw new ChatSDKError('offline:chat');
|
|
|
|
|
}
|
2024-03-19 04:37:30 +03:00
|
|
|
|
2024-10-11 18:00:22 +05:30
|
|
|
throw error;
|
2024-03-19 04:37:30 +03:00
|
|
|
}
|
2025-05-13 19:01:28 -07:00
|
|
|
}
|
2024-08-24 23:23:37 -05:00
|
|
|
|
2024-10-11 18:00:22 +05:30
|
|
|
export function getLocalStorage(key: string) {
|
2024-10-30 16:01:24 +05:30
|
|
|
if (typeof window !== 'undefined') {
|
|
|
|
|
return JSON.parse(localStorage.getItem(key) || '[]');
|
2024-10-11 18:00:22 +05:30
|
|
|
}
|
|
|
|
|
return [];
|
2024-08-24 23:23:37 -05:00
|
|
|
}
|
|
|
|
|
|
2024-10-11 18:00:22 +05:30
|
|
|
export function generateUUID(): string {
|
2024-11-15 12:18:17 -05:00
|
|
|
return 'xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx'.replace(/[xy]/g, (c) => {
|
2024-10-11 18:00:22 +05:30
|
|
|
const r = (Math.random() * 16) | 0;
|
2024-10-30 16:01:24 +05:30
|
|
|
const v = c === 'x' ? r : (r & 0x3) | 0x8;
|
2024-10-11 18:00:22 +05:30
|
|
|
return v.toString(16);
|
|
|
|
|
});
|
2024-08-24 23:23:37 -05:00
|
|
|
}
|
2024-10-15 10:50:50 +05:30
|
|
|
|
2025-01-28 18:51:04 +05:30
|
|
|
type ResponseMessageWithoutId = CoreToolMessage | CoreAssistantMessage;
|
|
|
|
|
type ResponseMessage = ResponseMessageWithoutId & { id: string };
|
|
|
|
|
|
2025-03-16 18:42:29 -07:00
|
|
|
export function getMostRecentUserMessage(messages: Array<UIMessage>) {
|
2024-11-05 17:15:51 +03:00
|
|
|
const userMessages = messages.filter((message) => message.role === 'user');
|
|
|
|
|
return userMessages.at(-1);
|
|
|
|
|
}
|
|
|
|
|
|
2024-11-01 15:31:54 +05:30
|
|
|
export function getDocumentTimestampByIndex(
|
|
|
|
|
documents: Array<Document>,
|
2024-11-15 13:00:15 -05:00
|
|
|
index: number,
|
2024-11-01 15:31:54 +05:30
|
|
|
) {
|
|
|
|
|
if (!documents) return new Date();
|
|
|
|
|
if (index > documents.length) return new Date();
|
|
|
|
|
|
|
|
|
|
return documents[index].createdAt;
|
|
|
|
|
}
|
2025-03-16 18:42:29 -07:00
|
|
|
|
|
|
|
|
export function getTrailingMessageId({
|
|
|
|
|
messages,
|
|
|
|
|
}: {
|
|
|
|
|
messages: Array<ResponseMessage>;
|
|
|
|
|
}): string | null {
|
|
|
|
|
const trailingMessage = messages.at(-1);
|
|
|
|
|
|
|
|
|
|
if (!trailingMessage) return null;
|
|
|
|
|
|
|
|
|
|
return trailingMessage.id;
|
|
|
|
|
}
|
2025-05-02 16:45:26 -07:00
|
|
|
|
|
|
|
|
export function sanitizeText(text: string) {
|
|
|
|
|
return text.replace('<has_function_call>', '');
|
|
|
|
|
}
|