import { ApiClientError } from "@/shared/api/http-client" import { configuredBackendUrl } from "@/lib/backend-url" const MAX_RESTORE_BYTES = 512 * 1024 * 1024 function trimBaseUrl(baseUrl: string): string { return baseUrl.replace(/\/$/, "") } function resolveDatabaseApiUrl(baseUrl: string, path: string): string { if (configuredBackendUrl().kind === "same-origin") { return path } return `${trimBaseUrl(baseUrl)}${path}` } function parseFilename(contentDisposition: string | null, fallback: string): string { if (!contentDisposition) return fallback const utfMatch = /filename\*=UTF-8''([^;]+)/i.exec(contentDisposition) if (utfMatch?.[1]) { try { return decodeURIComponent(utfMatch[1]) } catch { return utfMatch[1] } } const plainMatch = /filename="([^"]+)"/i.exec(contentDisposition) if (plainMatch?.[1]) return plainMatch[1] return fallback } export async function downloadSystemDatabaseBackup( baseUrl: string, ): Promise<{ blob: Blob; filename: string }> { const res = await fetch(resolveDatabaseApiUrl(baseUrl, "/api/system/database/backup")) if (!res.ok) { const payload = await res.json().catch(() => undefined) const msg = typeof payload === "object" && payload !== null && "error" in payload && typeof (payload as { error?: unknown }).error === "string" ? (payload as { error: string }).error : res.statusText throw new ApiClientError(msg, res.status, payload) } const blob = await res.blob() const filename = parseFilename(res.headers.get("Content-Disposition"), "mikrotik-manager.db") return { blob, filename } } export async function restoreSystemDatabaseBackup(baseUrl: string, file: File): Promise { if (file.size > MAX_RESTORE_BYTES) { throw new ApiClientError( `Файл больше ${MAX_RESTORE_BYTES / (1024 * 1024)} МБ — уменьшите бэкап или обратитесь к администратору`, 413, ) } const body = await file.arrayBuffer() const res = await fetch(resolveDatabaseApiUrl(baseUrl, "/api/system/database/restore"), { method: "POST", headers: { "Content-Type": "application/octet-stream" }, body, }) if (!res.ok) { const payload = await res.json().catch(() => undefined) const msg = typeof payload === "object" && payload !== null && "error" in payload && typeof (payload as { error?: unknown }).error === "string" ? (payload as { error: string }).error : res.statusText throw new ApiClientError(msg, res.status, payload) } }