mirror of
https://github.com/gotenberg/gotenberg.git
synced 2026-08-15 03:42:15 +01:00
Merge commit from fork
Co-authored-by: Jacob Brackett <jbrackett@makenotion.com>
This commit is contained in:
@@ -178,6 +178,12 @@ func newContext(echoCtx echo.Context, logger *slog.Logger, fs *gotenberg.FileSys
|
|||||||
|
|
||||||
return nil, cancel, fmt.Errorf("get multipart form: %w", err)
|
return nil, cancel, fmt.Errorf("get multipart form: %w", err)
|
||||||
}
|
}
|
||||||
|
defer func() {
|
||||||
|
err := form.RemoveAll()
|
||||||
|
if err != nil {
|
||||||
|
logger.ErrorContext(context.Background(), fmt.Sprintf("remove multipart temporary files: %s", err))
|
||||||
|
}
|
||||||
|
}()
|
||||||
|
|
||||||
// This will ensure we do not exceed the body limit.
|
// This will ensure we do not exceed the body limit.
|
||||||
var formValuesSize int64
|
var formValuesSize int64
|
||||||
|
|||||||
@@ -9,6 +9,7 @@ import (
|
|||||||
"mime/multipart"
|
"mime/multipart"
|
||||||
"net/http"
|
"net/http"
|
||||||
"net/http/httptest"
|
"net/http/httptest"
|
||||||
|
"os"
|
||||||
"sync"
|
"sync"
|
||||||
"testing"
|
"testing"
|
||||||
"time"
|
"time"
|
||||||
@@ -73,6 +74,64 @@ func TestNewContext_Cancellation(t *testing.T) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func TestNewContext_RemovesMultipartTemporaryFiles(t *testing.T) {
|
||||||
|
body := new(bytes.Buffer)
|
||||||
|
writer := multipart.NewWriter(body)
|
||||||
|
part, err := writer.CreateFormFile("files", "input.odt")
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("create multipart file: %v", err)
|
||||||
|
}
|
||||||
|
_, err = part.Write(bytes.Repeat([]byte("x"), 1024))
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("write multipart file: %v", err)
|
||||||
|
}
|
||||||
|
err = writer.Close()
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("close multipart writer: %v", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
req := httptest.NewRequest(http.MethodPost, "/forms/libreoffice/convert", body)
|
||||||
|
req.Header.Set("Content-Type", writer.FormDataContentType())
|
||||||
|
err = req.ParseMultipartForm(1)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("parse multipart form: %v", err)
|
||||||
|
}
|
||||||
|
defer func() {
|
||||||
|
_ = req.MultipartForm.RemoveAll()
|
||||||
|
}()
|
||||||
|
|
||||||
|
upload, err := req.MultipartForm.File["files"][0].Open()
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("open disk-backed multipart file: %v", err)
|
||||||
|
}
|
||||||
|
temporaryFile, ok := upload.(*os.File)
|
||||||
|
if !ok {
|
||||||
|
_ = upload.Close()
|
||||||
|
t.Fatal("multipart upload is not disk-backed")
|
||||||
|
}
|
||||||
|
temporaryPath := temporaryFile.Name()
|
||||||
|
err = temporaryFile.Close()
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("close disk-backed multipart file: %v", err)
|
||||||
|
}
|
||||||
|
|
||||||
|
echoCtx := echo.New().NewContext(req, httptest.NewRecorder())
|
||||||
|
logger := slog.New(slog.DiscardHandler)
|
||||||
|
fs := gotenberg.NewFileSystem(new(gotenberg.OsMkdirAll))
|
||||||
|
downloadFromCfg := downloadFromConfig{disable: true}
|
||||||
|
|
||||||
|
_, cancel, err := newContext(echoCtx, logger, fs, 10*time.Second, 0, downloadFromCfg)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("newContext returned error: %v", err)
|
||||||
|
}
|
||||||
|
defer cancel()
|
||||||
|
|
||||||
|
_, err = os.Stat(temporaryPath)
|
||||||
|
if !os.IsNotExist(err) {
|
||||||
|
t.Fatalf("multipart temporary file still exists: %s", temporaryPath)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// Concurrent downloadFrom entries must not race on the shared maps
|
// Concurrent downloadFrom entries must not race on the shared maps
|
||||||
// (ctx.files, ctx.diskToOriginal, ctx.filesByField). Run under -race
|
// (ctx.files, ctx.diskToOriginal, ctx.filesByField). Run under -race
|
||||||
// to catch the data race; without -race a sufficient number of entries
|
// to catch the data race; without -race a sufficient number of entries
|
||||||
|
|||||||
Reference in New Issue
Block a user