100 lines
2.8 KiB
TypeScript
100 lines
2.8 KiB
TypeScript
'use server';
|
|
import { env } from '@/lib/env';
|
|
import axios from 'axios';
|
|
import { z } from 'zod';
|
|
|
|
// Crear instancia de Axios con la URL base validada
|
|
const fetchApi = axios.create({
|
|
baseURL: env.API_URL,
|
|
});
|
|
|
|
// Interceptor para incluir el token automáticamente en las peticiones
|
|
// ESTE INTERCEPTOR ESTÁ BIEN PARA EL RESTO DE LAS PETICIONES AUTENTICADAS
|
|
fetchApi.interceptors.request.use(async (config: any) => {
|
|
try {
|
|
// console.log("Solicitando autenticación...");
|
|
|
|
const { auth } = await import('@/lib/auth'); // Importación dinámica
|
|
const session = await auth();
|
|
const token = session?.access_token;
|
|
|
|
if (token) {
|
|
config.headers.Authorization = `Bearer ${token}`;
|
|
}
|
|
|
|
// **Importante:** Si el body es FormData, elimina el Content-Type para que Axios lo configure automáticamente.
|
|
if (config.data instanceof FormData) {
|
|
delete config.headers['Content-Type'];
|
|
} else {
|
|
config.headers['Content-Type'] = 'application/json';
|
|
}
|
|
|
|
return config;
|
|
} catch (error) {
|
|
console.error('Error al obtener el token de autenticación para el interceptor:', error);
|
|
// IMPORTANTE: Si ocurre un error aquí, es mejor rechazar la promesa
|
|
// para que la solicitud no se envíe sin autorización.
|
|
return Promise.reject(error);
|
|
}
|
|
});
|
|
|
|
// safeFetchApi sigue siendo útil para el resto de las llamadas que requieren autenticación
|
|
export const safeFetchApi = async <T extends z.ZodSchema<any>>(
|
|
schema: T,
|
|
url: string,
|
|
method: 'GET' | 'POST' | 'PUT' | 'PATCH' | 'DELETE' = 'GET',
|
|
data?: any,
|
|
): Promise<
|
|
[{ type: string; message: string; details?: any } | null, z.infer<T> | null]
|
|
> => {
|
|
try {
|
|
const response = await fetchApi({
|
|
method,
|
|
url,
|
|
data,
|
|
});
|
|
|
|
const parsed = schema.safeParse(response.data);
|
|
|
|
if (!parsed.success) {
|
|
console.error('Validation Error Details:', {
|
|
errors: parsed.error.errors,
|
|
receivedData: response.data,
|
|
expectedSchema: schema,
|
|
data: response.data.data,
|
|
});
|
|
return [
|
|
{
|
|
type: 'VALIDATION_ERROR',
|
|
message: 'Validation error',
|
|
details: parsed.error.errors,
|
|
},
|
|
null,
|
|
];
|
|
}
|
|
|
|
return [null, parsed.data];
|
|
} catch (error: any) {
|
|
const errorDetails = {
|
|
status: error.response?.status,
|
|
statusText: error.response?.statusText,
|
|
message: error.message,
|
|
url: error.config?.url,
|
|
method: error.config?.method,
|
|
requestData: error.config?.data,
|
|
responseData: error.response?.data,
|
|
headers: error.config?.headers,
|
|
};
|
|
|
|
return [
|
|
{
|
|
type: 'API_ERROR',
|
|
message: error.response?.data?.message || 'Unknown API error',
|
|
details: errorDetails,
|
|
},
|
|
null,
|
|
];
|
|
}
|
|
};
|
|
|
|
export { fetchApi }; |