58 lines
1.6 KiB
Go
58 lines
1.6 KiB
Go
package infra
|
|
|
|
import (
|
|
"net/http"
|
|
)
|
|
|
|
// UploadHandler retorna un http.HandlerFunc completo para multipart upload. Compone
|
|
// internamente UploadParse + FileValidateType + FileSaveDisk segun cfg.
|
|
//
|
|
// Comportamiento:
|
|
// - Parsea el multipart con maxSize = cfg.MaxFileSize.
|
|
// - Para cada archivo: valida tipo por magic bytes contra cfg.AllowedTypes,
|
|
// guarda en cfg.BaseDir con FileSaveDisk, sobreescribe ContentType con el
|
|
// MIME real detectado.
|
|
// - Responde 200 con JSON `{"files": [UploadedFile, ...]}`.
|
|
// - Errores: 400 si el parse falla, 415 si algun archivo es de tipo no permitido,
|
|
// 500 si falla el guardado.
|
|
func UploadHandler(cfg StorageConfig) http.HandlerFunc {
|
|
return func(w http.ResponseWriter, r *http.Request) {
|
|
files, err := UploadParse(r, cfg.MaxFileSize)
|
|
if err != nil {
|
|
HTTPErrorResponse(w, HTTPError{
|
|
Status: http.StatusBadRequest,
|
|
Code: "parse_error",
|
|
Message: err.Error(),
|
|
})
|
|
return
|
|
}
|
|
|
|
var saved []UploadedFile
|
|
for _, pf := range files {
|
|
mime, ok := FileValidateType(pf.Header, cfg.AllowedTypes)
|
|
if !ok {
|
|
HTTPErrorResponse(w, HTTPError{
|
|
Status: http.StatusUnsupportedMediaType,
|
|
Code: "invalid_type",
|
|
Message: "tipo no permitido: " + mime,
|
|
})
|
|
return
|
|
}
|
|
|
|
uploaded, err := FileSaveDisk(cfg.BaseDir, pf.Filename, pf.Content)
|
|
if err != nil {
|
|
HTTPErrorResponse(w, HTTPError{
|
|
Status: http.StatusInternalServerError,
|
|
Code: "save_error",
|
|
Message: err.Error(),
|
|
})
|
|
return
|
|
}
|
|
uploaded.ContentType = mime
|
|
saved = append(saved, uploaded)
|
|
}
|
|
|
|
HTTPJSONResponse(w, http.StatusOK, map[string]any{"files": saved})
|
|
}
|
|
}
|