read.go 1.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869
  1. package imagedata
  2. import (
  3. "bytes"
  4. "context"
  5. "io"
  6. "github.com/imgproxy/imgproxy/v3/bufpool"
  7. "github.com/imgproxy/imgproxy/v3/bufreader"
  8. "github.com/imgproxy/imgproxy/v3/config"
  9. "github.com/imgproxy/imgproxy/v3/imagemeta"
  10. "github.com/imgproxy/imgproxy/v3/security"
  11. )
  12. var downloadBufPool *bufpool.Pool
  13. func initRead() {
  14. downloadBufPool = bufpool.New("download", config.Workers, config.DownloadBufferSize)
  15. }
  16. func readAndCheckImage(r io.Reader, contentLength int, secopts security.Options) (*ImageData, error) {
  17. if err := security.CheckFileSize(contentLength, secopts); err != nil {
  18. return nil, err
  19. }
  20. buf := downloadBufPool.Get(contentLength, false)
  21. cancel := func() { downloadBufPool.Put(buf) }
  22. r = security.LimitFileSize(r, secopts)
  23. br := bufreader.New(r, buf)
  24. meta, err := imagemeta.DecodeMeta(br)
  25. if err != nil {
  26. buf.Reset()
  27. cancel()
  28. return nil, wrapError(err)
  29. }
  30. if err = security.CheckDimensions(meta.Width(), meta.Height(), 1, secopts); err != nil {
  31. buf.Reset()
  32. cancel()
  33. return nil, wrapError(err)
  34. }
  35. downloadBufPool.GrowBuffer(buf, contentLength)
  36. if err = br.Flush(); err != nil {
  37. buf.Reset()
  38. cancel()
  39. return nil, wrapError(err)
  40. }
  41. return &ImageData{
  42. Data: buf.Bytes(),
  43. Type: meta.Format(),
  44. cancel: cancel,
  45. }, nil
  46. }
  47. func BorrowBuffer() (*bytes.Buffer, context.CancelFunc) {
  48. buf := downloadBufPool.Get(0, false)
  49. cancel := func() { downloadBufPool.Put(buf) }
  50. return buf, cancel
  51. }