Appearance
Subida de avatar de agente (S3 presign)
El panel no envía el binario al endpoint de agentes. El flujo es:
- Presign —
POST /storage/documents/uploadcon el body validado poruploadDocumentSchema(name,size,contentType,fileRouteType). Para avatares se usafileRouteType: AVATAR(FileRouteTypeen@repo/schemas). - S3 — Se arma un
FormDatacon todas las entradas defieldsy, al final,formData.set('file', file). Se hacePOSTa laurlconXMLHttpRequest+send(formData)(cuerpo multipart, no JSON; no fijarContent-Typea mano). No usar elapiClientde Axios para esta petición (evitar cabeceras de auth). - Agente — Tras un upload correcto, se toma la
keydesdefields.keyy se envía encreateAgent/updateAgentcomoavatar. La API es la que resuelve dominio + key para las respuestas con URL pública.
Implementación de referencia: storage-documents.service.ts y helpers en s3-presigned-upload.ts. El diálogo de crear/editar agente sube solo si el usuario eligió un archivo nuevo (avatarFile en el formulario); en edición, si no hay archivo nuevo, no se envía avatar en el PATCH para no sobrescribir con una URL de preview.
Para mostrar avatares cuando la API devuelve solo la key S3, el panel usa VITE_PUBLIC_STORAGE_URL (origen del bucket público, sin / final) y resolvePublicStorageObjectUrl en public-storage-url.ts. Ver apps/panel/.env.example.