54 lines
1.4 KiB
Go
54 lines
1.4 KiB
Go
package infra
|
|
|
|
import (
|
|
"fmt"
|
|
"io"
|
|
"mime"
|
|
"os"
|
|
"path/filepath"
|
|
"strings"
|
|
"time"
|
|
)
|
|
|
|
// FileSaveDisk escribe el contenido de data en baseDir con un nombre unico generado a
|
|
// partir de filename original. Crea baseDir si no existe.
|
|
//
|
|
// Retorna el UploadedFile con la metadata y la ruta completa en disco. El campo
|
|
// ContentType se infiere de la extension via mime.TypeByExtension; si la app necesita
|
|
// validacion mas estricta, debe usar FileValidateType antes y/o sobreescribir el campo.
|
|
func FileSaveDisk(baseDir string, filename string, data io.Reader) (UploadedFile, error) {
|
|
if err := os.MkdirAll(baseDir, 0o755); err != nil {
|
|
return UploadedFile{}, fmt.Errorf("file_save_disk: mkdir %s: %w", baseDir, err)
|
|
}
|
|
|
|
stored := FileUniqueName(filename)
|
|
dst := filepath.Join(baseDir, stored)
|
|
|
|
f, err := os.Create(dst)
|
|
if err != nil {
|
|
return UploadedFile{}, fmt.Errorf("file_save_disk: create %s: %w", dst, err)
|
|
}
|
|
defer f.Close()
|
|
|
|
n, err := io.Copy(f, data)
|
|
if err != nil {
|
|
_ = os.Remove(dst)
|
|
return UploadedFile{}, fmt.Errorf("file_save_disk: copy: %w", err)
|
|
}
|
|
|
|
ext := strings.ToLower(filepath.Ext(stored))
|
|
ct := mime.TypeByExtension(ext)
|
|
if ct == "" {
|
|
ct = "application/octet-stream"
|
|
}
|
|
|
|
return UploadedFile{
|
|
Filename: filename,
|
|
StoredName: stored,
|
|
Size: n,
|
|
ContentType: ct,
|
|
Path: dst,
|
|
CreatedAt: time.Now().UTC(),
|
|
}, nil
|
|
}
|