import axios, { AxiosInstance, AxiosRequestConfig, AxiosResponse } from "axios"; import { FileDocument, FolderDocument } from "@/types"; import MY_TOKEN_KEY from "./get-cookie-name"; export interface ApiResponse { ok: boolean; data?: T; message?: string; error?: string; } export interface PaginationInfo { page: number; limit: number; total: number; pages: number; } export interface FileListResponse { ok?: boolean; files: FileDocument[]; pagination: PaginationInfo; } export interface FolderTreeResponse { ok?: boolean; tree: FolderDocument[]; } // Original API instance (keep for backward compatibility) export const api = axios.create({ baseURL: `/api`, headers: { cache: "no-store", }, }); export const apiServer = axios.create({ baseURL: process.env.NEXT_APP_API_URL as string, headers: { cache: "no-store", }, }); api.interceptors.request.use( async (config) => { // get the token from cookies const cookie_name = MY_TOKEN_KEY(); const token = document.cookie .split("; ") .find((row) => row.startsWith(`${cookie_name}=`)) ?.split("=")[1]; if (token) { config.headers.Authorization = `Bearer ${token}`; } return config; }, (error) => { // Handle the error return Promise.reject(error); } ); // Enhanced API client class class ApiClient { private client: AxiosInstance; constructor() { this.client = api; // Use the existing configured instance } // Generic HTTP methods async get(url: string, config?: AxiosRequestConfig): Promise> { return this.client.get(url, config); } async post(url: string, data?: unknown, config?: AxiosRequestConfig): Promise> { return this.client.post(url, data, config); } async put(url: string, data?: unknown, config?: AxiosRequestConfig): Promise> { return this.client.put(url, data, config); } async patch(url: string, data?: unknown, config?: AxiosRequestConfig): Promise> { return this.client.patch(url, data, config); } async delete(url: string, config?: AxiosRequestConfig): Promise> { return this.client.delete(url, config); } // File-specific methods async getFiles( projectId: string, options?: { folderId?: string; type?: string; search?: string; limit?: number; page?: number; } ): Promise> { const params = new URLSearchParams(); if (options?.folderId) params.append('folderId', options.folderId); if (options?.type) params.append('type', options.type); if (options?.search) params.append('search', options.search); if (options?.limit) params.append('limit', options.limit.toString()); if (options?.page) params.append('page', options.page.toString()); return this.get(`/projects/${projectId}/files?${params.toString()}`); } async getFile(projectId: string, fileId: string, includeVersions?: boolean): Promise> { const params = includeVersions ? '?includeVersions=true' : ''; return this.get(`/projects/${projectId}/files/${fileId}${params}`); } async createFile(projectId: string, fileData: { name: string; content: string; type: string; parentFolderId?: string; metadata?: Record; }): Promise> { return this.post(`/projects/${projectId}/files`, fileData); } async updateFile(projectId: string, fileId: string, fileData: { content?: string; name?: string; metadata?: Record; changeDescription?: string; }): Promise> { return this.put(`/projects/${projectId}/files/${fileId}`, fileData); } async deleteFile(projectId: string, fileId: string): Promise> { return this.delete(`/projects/${projectId}/files/${fileId}`); } // Folder-specific methods async getFolders( projectId: string, options?: { parentFolderId?: string; includeFiles?: boolean; tree?: boolean; } ): Promise> { const params = new URLSearchParams(); if (options?.parentFolderId) params.append('parentFolderId', options.parentFolderId); if (options?.includeFiles) params.append('includeFiles', 'true'); if (options?.tree) params.append('tree', 'true'); return this.get(`/projects/${projectId}/folders?${params.toString()}`); } async createFolder(projectId: string, folderData: { name: string; parentFolderId?: string; metadata?: Record; }): Promise> { return this.post(`/projects/${projectId}/folders`, folderData); } // AI-specific methods async generateFiles(projectId: string, data: { prompt: string; model?: string; provider?: string; projectType?: string; framework?: string; includeFiles?: string[]; parentFolderId?: string; }): Promise> { return this.post(`/projects/${projectId}/generate-files`, data); } async generateWithGemini(data: { model: string; prompt?: string; systemInstruction?: string; messages?: Array<{ role: string; content: string }>; config?: Record; stream?: boolean; }): Promise> { return this.post('/ai/gemini', data); } async generateWithOpenRouter(data: { model: string; prompt?: string; systemInstruction?: string; messages?: Array<{ role: string; content: string }>; config?: Record; stream?: boolean; }): Promise> { return this.post('/ai/openrouter', data); } } // Export enhanced API client instance export const apiClient = new ApiClient();