diff --git a/packages/http/file.go b/packages/http/file.go index b3dfd61..8aebee4 100644 --- a/packages/http/file.go +++ b/packages/http/file.go @@ -1,6 +1,10 @@ package http import ( + "crypto/sha256" + "go-socket/packages/globals" + "go-socket/packages/minio" + "io" "net/http" "go-socket/packages/convertions" @@ -29,4 +33,41 @@ func HandleFileUpload(response http.ResponseWriter, request *http.Request) { return } + request.Body = http.MaxBytesReader(response, request.Body, int64(globals.MaxPostWithFileBytes)) + multipartReader, err := request.MultipartReader() + if err != nil { + http.Error(response, "expected multipart form", 400) + return + } + + for { + part, err := multipartReader.NextPart() + if err == io.EOF { + http.Error(response, "bad request", 400) + return + } + + if part.FileName() == "" { + part.Close() + continue + } + + if len(part.FileName()) != sha256.Size { + part.Close() + http.Error(response, "filename must be sha256 of whole file", 400) + return + } + + err = minio.Upload(ctx, part.FileName(), part, -1, part.Header.Get("Content-Type"), user.Id) + if err != nil { + http.Error(response, "upload failed", http.StatusInternalServerError) + return + } + part.Close() + + if err != nil { + http.Error(response, "upload failed", 500) + return + } + } } diff --git a/packages/minio/minio.go b/packages/minio/minio.go index 6396dba..8b2877b 100644 --- a/packages/minio/minio.go +++ b/packages/minio/minio.go @@ -65,7 +65,7 @@ func MinInit() { } -func upload(ctx context.Context, key string, body io.Reader, size int64, contentType string, uploader uuid.UUID) error { +func Upload(ctx context.Context, key string, body io.Reader, size int64, contentType string, uploader uuid.UUID) error { _, err := minClient.PutObject(ctx, globals.FileStorageBucketName, key, body, size, minio.PutObjectOptions{ ContentType: contentType, @@ -82,3 +82,11 @@ func getDownloadUrl(ctx context.Context, key string) (*url.URL, error) { u, err := minClient.PresignedGetObject(ctx, globals.FileStorageBucketName, key, globals.FileDownloadLinkTtl, nil) return u, err } + +func DoesExist(ctx context.Context, key string) bool { + _, err := minClient.GetObject(ctx, globals.FileStorageBucketName, key, minio.GetObjectOptions{}) + if err != nil { + return false + } + return true +}