import { SessionWithTokens, authOptions } from "@/config/authConfig"; import { getServerSession } from "next-auth"; import { headers } from "next/headers"; import { redirect } from "next/navigation"; export interface searchParamsProps { searchParams: { [key: string]: string | string[] | undefined }; } export class ServerFetchError extends Error { public readonly response: Response | undefined; constructor(message?: string, response?: Response) { super(message); this.response = response; Object.setPrototypeOf(this, ServerFetchError.prototype); } } export const serverFetch: typeof fetch = async (input, init) => { // eslint-disable-next-line @typescript-eslint/no-explicit-any const session = await getServerSession(authOptions); const accessToken = session?.accessToken; console.log(accessToken); return fetch(input, { ...init, headers: { ...init?.headers, ...(accessToken ? { Authorization: `Bearer ${accessToken}`, Accept: "application/json, application/vnd.openxmlformats-officedocument.spreadsheetml.sheet, multipart/form-data", } : {}), }, }); }; type FetchParams = Parameters; export async function serverFetchJson(...args: FetchParams) { const response = await serverFetch(...args); if (response.ok) { return response.json() as T; } else { const errorText = await response.text() switch (response.status) { case 401: signOutUser(); case 422: throw new ServerFetchError( JSON.parse(errorText).error, response ); default: console.error(errorText); throw new ServerFetchError( "Something went wrong fetching data in server.", response ); } } } export async function serverFetchWithNoContent(...args: FetchParams) { const response = await serverFetch(...args); if (response.ok) { return response.status; // 204 No Content, e.g. for delete data } else { switch (response.status) { case 401: signOutUser(); default: console.error(await response.text()); throw Error("Something went wrong fetching data in server."); } } } export async function serverFetchString(...args: FetchParams) { const response = await serverFetch(...args); if (response.ok) { return response.text() as T; } else { switch (response.status) { case 401: signOutUser(); default: console.error(await response.text()); throw new ServerFetchError( "Something went wrong fetching data in server.", response, ); } } } export async function serverFetchBlob(...args: FetchParams) { const response = await serverFetch(...args); if (response.ok) { const body = response.body; // console.log(body) // console.log(body?.tee()[0].getReader()) const reader = body?.getReader(); let finalUInt8Array = new Uint8Array(); let done = false; while (!done) { const read = await reader?.read(); // version 1 if (read?.done) { done = true; } else { const tempUInt8Array = new Uint8Array( finalUInt8Array.length + read?.value.length!, ); tempUInt8Array.set(finalUInt8Array); tempUInt8Array.set(read?.value!, finalUInt8Array.length); finalUInt8Array = new Uint8Array(tempUInt8Array.length!); finalUInt8Array.set(tempUInt8Array); // console.log("1", finalUInt8Array) } } // version 2 & return bodyRead // const bodyRead = reader?.read().then(function processText({ done, value }): any { // // Result objects contain two properties: // // done - true if the stream has already given you all its data. // // value - some data. Always undefined when done is true. // if (done) { // console.log("Stream complete"); // return { filename: response.headers.get("filename"), blobValue: finalUInt8Array } as T;; // } // // value for fetch streams is a Uint8Array // finalUInt8Array = new Uint8Array(value.length) // finalUInt8Array.set(value) // console.log(finalUInt8Array) // // Read some more, and call this function again // return reader.read().then(processText); // }) // const bodyValue = bodyRead?.value // const blob = await response.blob() // const blobText = await blob.text(); // const blobType = await blob.type; // console.log(bodyReader) // console.log("2", finalUInt8Array) // console.log(bodyValue) return { filename: response.headers.get("filename"), blobValue: finalUInt8Array, } as T; } else { switch (response.status) { case 401: signOutUser(); default: console.error(await response.text()); throw Error("Something went wrong fetching data in server."); } } } export const signOutUser = () => { const headersList = headers(); const referer = headersList.get("referer"); redirect( `/logout${referer ? `?callbackUrl=${encodeURIComponent(referer)}` : ""}`, ); };