update media processing (#244)

This commit is contained in:
tobi 2021-09-23 11:13:11 +02:00 committed by GitHub
parent 7e6350b448
commit ddfd83d0fb
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
8 changed files with 63 additions and 81 deletions

View file

@ -187,9 +187,9 @@ func (suite *MediaCreateTestSuite) TestStatusCreatePOSTImageHandlerSuccessful()
Aspect: 1.7777778, Aspect: 1.7777778,
}, },
Small: model.MediaDimensions{ Small: model.MediaDimensions{
Width: 256, Width: 512,
Height: 144, Height: 288,
Size: "256x144", Size: "512x288",
Aspect: 1.7777778, Aspect: 1.7777778,
}, },
Focus: model.MediaFocus{ Focus: model.MediaFocus{
@ -197,7 +197,7 @@ func (suite *MediaCreateTestSuite) TestStatusCreatePOSTImageHandlerSuccessful()
Y: 0.5, Y: 0.5,
}, },
}, attachmentReply.Meta) }, attachmentReply.Meta)
assert.Equal(suite.T(), "LjCZnlvyRkRn_NvzRjWF?urqV@f9", attachmentReply.Blurhash) assert.Equal(suite.T(), "LjBzUo#6RQR._NvzRjWF?urqV@a$", attachmentReply.Blurhash)
assert.NotEmpty(suite.T(), attachmentReply.ID) assert.NotEmpty(suite.T(), attachmentReply.ID)
assert.NotEmpty(suite.T(), attachmentReply.URL) assert.NotEmpty(suite.T(), attachmentReply.URL)
assert.NotEmpty(suite.T(), attachmentReply.PreviewURL) assert.NotEmpty(suite.T(), attachmentReply.PreviewURL)

View file

@ -65,7 +65,7 @@ func (suite *AttachmentTestSuite) TestDereferenceAttachmentOK() {
suite.Equal(2071680, attachment.FileMeta.Original.Size) suite.Equal(2071680, attachment.FileMeta.Original.Size)
suite.Equal(1245, attachment.FileMeta.Original.Height) suite.Equal(1245, attachment.FileMeta.Original.Height)
suite.Equal(1664, attachment.FileMeta.Original.Width) suite.Equal(1664, attachment.FileMeta.Original.Width)
suite.Equal("LwQ9yKRP_4t8t7RjWBt7%hozM_ay", attachment.Blurhash) suite.Equal("LwP?p=aK_4%N%MRjWXt7%hozM_a}", attachment.Blurhash)
suite.Equal(gtsmodel.ProcessingStatusProcessed, attachment.Processing) suite.Equal(gtsmodel.ProcessingStatusProcessed, attachment.Processing)
suite.NotEmpty(attachment.File.Path) suite.NotEmpty(attachment.File.Path)
suite.Equal(attachmentContentType, attachment.File.ContentType) suite.Equal(attachmentContentType, attachment.File.ContentType)
@ -91,7 +91,7 @@ func (suite *AttachmentTestSuite) TestDereferenceAttachmentOK() {
suite.Equal(2071680, dbAttachment.FileMeta.Original.Size) suite.Equal(2071680, dbAttachment.FileMeta.Original.Size)
suite.Equal(1245, dbAttachment.FileMeta.Original.Height) suite.Equal(1245, dbAttachment.FileMeta.Original.Height)
suite.Equal(1664, dbAttachment.FileMeta.Original.Width) suite.Equal(1664, dbAttachment.FileMeta.Original.Width)
suite.Equal("LwQ9yKRP_4t8t7RjWBt7%hozM_ay", dbAttachment.Blurhash) suite.Equal("LwP?p=aK_4%N%MRjWXt7%hozM_a}", dbAttachment.Blurhash)
suite.Equal(gtsmodel.ProcessingStatusProcessed, dbAttachment.Processing) suite.Equal(gtsmodel.ProcessingStatusProcessed, dbAttachment.Processing)
suite.NotEmpty(dbAttachment.File.Path) suite.NotEmpty(dbAttachment.File.Path)
suite.Equal(attachmentContentType, dbAttachment.File.ContentType) suite.Equal(attachmentContentType, dbAttachment.File.ContentType)

View file

@ -120,7 +120,7 @@ func (mh *mediaHandler) processHeaderOrAvi(imageBytes []byte, contentType string
AccountID: accountID, AccountID: accountID,
Description: "", Description: "",
ScheduledStatusID: "", ScheduledStatusID: "",
Blurhash: original.blurhash, Blurhash: small.blurhash,
Processing: 2, Processing: 2,
File: gtsmodel.File{ File: gtsmodel.File{
Path: originalPath, Path: originalPath,

View file

@ -55,7 +55,7 @@ func (mh *mediaHandler) processImageAttachment(data []byte, minAttachment *gtsmo
return nil, errors.New("media type unrecognized") return nil, errors.New("media type unrecognized")
} }
small, err = deriveThumbnail(clean, contentType, 256, 256) small, err = deriveThumbnail(clean, contentType, 512, 512)
if err != nil { if err != nil {
return nil, fmt.Errorf("error deriving thumbnail: %s", err) return nil, fmt.Errorf("error deriving thumbnail: %s", err)
} }
@ -109,7 +109,7 @@ func (mh *mediaHandler) processImageAttachment(data []byte, minAttachment *gtsmo
AccountID: minAttachment.AccountID, AccountID: minAttachment.AccountID,
Description: minAttachment.Description, Description: minAttachment.Description,
ScheduledStatusID: minAttachment.ScheduledStatusID, ScheduledStatusID: minAttachment.ScheduledStatusID,
Blurhash: original.blurhash, Blurhash: small.blurhash,
Processing: 2, Processing: 2,
File: gtsmodel.File{ File: gtsmodel.File{
Path: originalPath, Path: originalPath,

Binary file not shown.

Before

Width:  |  Height:  |  Size: 753 KiB

After

Width:  |  Height:  |  Size: 263 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 29 KiB

After

Width:  |  Height:  |  Size: 24 KiB

View file

@ -156,23 +156,12 @@ func deriveGif(b []byte, extension string) (*imageAndMeta, error) {
size := width * height size := width * height
aspect := float64(width) / float64(height) aspect := float64(width) / float64(height)
bh, err := blurhash.Encode(4, 3, g.Image[0])
if err != nil || bh == "" {
return nil, err
}
out := &bytes.Buffer{}
if err := gif.EncodeAll(out, g); err != nil {
return nil, err
}
return &imageAndMeta{ return &imageAndMeta{
image: out.Bytes(), image: b,
width: width, width: width,
height: height, height: height,
size: size, size: size,
aspect: aspect, aspect: aspect,
blurhash: bh,
}, nil }, nil
} }
@ -200,25 +189,12 @@ func deriveImage(b []byte, contentType string) (*imageAndMeta, error) {
size := width * height size := width * height
aspect := float64(width) / float64(height) aspect := float64(width) / float64(height)
bh, err := blurhash.Encode(4, 3, i)
if err != nil {
return nil, err
}
out := &bytes.Buffer{}
if err := jpeg.Encode(out, i, &jpeg.Options{
Quality: 100,
}); err != nil {
return nil, err
}
return &imageAndMeta{ return &imageAndMeta{
image: out.Bytes(), image: b,
width: width, width: width,
height: height, height: height,
size: size, size: size,
aspect: aspect, aspect: aspect,
blurhash: bh,
}, nil }, nil
} }
@ -257,9 +233,15 @@ func deriveThumbnail(b []byte, contentType string, x uint, y uint) (*imageAndMet
size := width * height size := width * height
aspect := float64(width) / float64(height) aspect := float64(width) / float64(height)
tiny := resize.Thumbnail(32, 32, thumb, resize.NearestNeighbor)
bh, err := blurhash.Encode(4, 3, tiny)
if err != nil {
return nil, err
}
out := &bytes.Buffer{} out := &bytes.Buffer{}
if err := jpeg.Encode(out, thumb, &jpeg.Options{ if err := jpeg.Encode(out, thumb, &jpeg.Options{
Quality: 100, Quality: 75,
}); err != nil { }); err != nil {
return nil, err return nil, err
} }
@ -269,6 +251,7 @@ func deriveThumbnail(b []byte, contentType string, x uint, y uint) (*imageAndMet
height: height, height: height,
size: size, size: size,
aspect: aspect, aspect: aspect,
blurhash: bh,
}, nil }, nil
} }

View file

@ -23,7 +23,6 @@
"testing" "testing"
"github.com/sirupsen/logrus" "github.com/sirupsen/logrus"
"github.com/stretchr/testify/assert"
"github.com/stretchr/testify/suite" "github.com/stretchr/testify/suite"
) )
@ -64,82 +63,82 @@ func (suite *MediaUtilTestSuite) TearDownTest() {
func (suite *MediaUtilTestSuite) TestParseContentTypeOK() { func (suite *MediaUtilTestSuite) TestParseContentTypeOK() {
f, err := ioutil.ReadFile("./test/test-jpeg.jpg") f, err := ioutil.ReadFile("./test/test-jpeg.jpg")
assert.Nil(suite.T(), err) suite.NoError(err)
ct, err := parseContentType(f) ct, err := parseContentType(f)
assert.Nil(suite.T(), err) suite.NoError(err)
assert.Equal(suite.T(), "image/jpeg", ct) suite.Equal("image/jpeg", ct)
} }
func (suite *MediaUtilTestSuite) TestParseContentTypeNotOK() { func (suite *MediaUtilTestSuite) TestParseContentTypeNotOK() {
f, err := ioutil.ReadFile("./test/test-corrupted.jpg") f, err := ioutil.ReadFile("./test/test-corrupted.jpg")
assert.Nil(suite.T(), err) suite.NoError(err)
ct, err := parseContentType(f) ct, err := parseContentType(f)
assert.NotNil(suite.T(), err) suite.NotNil(err)
assert.Equal(suite.T(), "", ct) suite.Equal("", ct)
assert.Equal(suite.T(), "filetype unknown", err.Error()) suite.Equal("filetype unknown", err.Error())
} }
func (suite *MediaUtilTestSuite) TestRemoveEXIF() { func (suite *MediaUtilTestSuite) TestRemoveEXIF() {
// load and validate image // load and validate image
b, err := ioutil.ReadFile("./test/test-with-exif.jpg") b, err := ioutil.ReadFile("./test/test-with-exif.jpg")
assert.Nil(suite.T(), err) suite.NoError(err)
// clean it up and validate the clean version // clean it up and validate the clean version
clean, err := purgeExif(b) clean, err := purgeExif(b)
assert.Nil(suite.T(), err) suite.NoError(err)
// compare it to our stored sample // compare it to our stored sample
sampleBytes, err := ioutil.ReadFile("./test/test-without-exif.jpg") sampleBytes, err := ioutil.ReadFile("./test/test-without-exif.jpg")
assert.Nil(suite.T(), err) suite.NoError(err)
assert.EqualValues(suite.T(), sampleBytes, clean) suite.EqualValues(sampleBytes, clean)
} }
func (suite *MediaUtilTestSuite) TestDeriveImageFromJPEG() { func (suite *MediaUtilTestSuite) TestDeriveImageFromJPEG() {
// load image // load image
b, err := ioutil.ReadFile("./test/test-jpeg.jpg") b, err := ioutil.ReadFile("./test/test-jpeg.jpg")
assert.Nil(suite.T(), err) suite.NoError(err)
// clean it up and validate the clean version // clean it up and validate the clean version
imageAndMeta, err := deriveImage(b, "image/jpeg") imageAndMeta, err := deriveImage(b, "image/jpeg")
assert.Nil(suite.T(), err) suite.NoError(err)
assert.Equal(suite.T(), 1920, imageAndMeta.width) suite.Equal(1920, imageAndMeta.width)
assert.Equal(suite.T(), 1080, imageAndMeta.height) suite.Equal(1080, imageAndMeta.height)
assert.Equal(suite.T(), 1.7777777777777777, imageAndMeta.aspect) suite.Equal(1.7777777777777777, imageAndMeta.aspect)
assert.Equal(suite.T(), 2073600, imageAndMeta.size) suite.Equal(2073600, imageAndMeta.size)
assert.Equal(suite.T(), "LjCZnlvyRkRn_NvzRjWF?urqV@f9", imageAndMeta.blurhash)
// assert that the final image is what we would expect // assert that the final image is what we would expect
sampleBytes, err := ioutil.ReadFile("./test/test-jpeg-processed.jpg") sampleBytes, err := ioutil.ReadFile("./test/test-jpeg-processed.jpg")
assert.Nil(suite.T(), err) suite.NoError(err)
assert.EqualValues(suite.T(), sampleBytes, imageAndMeta.image) suite.EqualValues(sampleBytes, imageAndMeta.image)
} }
func (suite *MediaUtilTestSuite) TestDeriveThumbnailFromJPEG() { func (suite *MediaUtilTestSuite) TestDeriveThumbnailFromJPEG() {
// load image // load image
b, err := ioutil.ReadFile("./test/test-jpeg.jpg") b, err := ioutil.ReadFile("./test/test-jpeg.jpg")
assert.Nil(suite.T(), err) suite.NoError(err)
// clean it up and validate the clean version // clean it up and validate the clean version
imageAndMeta, err := deriveThumbnail(b, "image/jpeg", 256, 256) imageAndMeta, err := deriveThumbnail(b, "image/jpeg", 512, 512)
assert.Nil(suite.T(), err) suite.NoError(err)
assert.Equal(suite.T(), 256, imageAndMeta.width) suite.Equal(512, imageAndMeta.width)
assert.Equal(suite.T(), 144, imageAndMeta.height) suite.Equal(288, imageAndMeta.height)
assert.Equal(suite.T(), 1.7777777777777777, imageAndMeta.aspect) suite.Equal(1.7777777777777777, imageAndMeta.aspect)
assert.Equal(suite.T(), 36864, imageAndMeta.size) suite.Equal(147456, imageAndMeta.size)
suite.Equal("LjBzUo#6RQR._NvzRjWF?urqV@a$", imageAndMeta.blurhash)
sampleBytes, err := ioutil.ReadFile("./test/test-jpeg-thumbnail.jpg") sampleBytes, err := ioutil.ReadFile("./test/test-jpeg-thumbnail.jpg")
assert.Nil(suite.T(), err) suite.NoError(err)
assert.EqualValues(suite.T(), sampleBytes, imageAndMeta.image) suite.EqualValues(sampleBytes, imageAndMeta.image)
} }
func (suite *MediaUtilTestSuite) TestSupportedImageTypes() { func (suite *MediaUtilTestSuite) TestSupportedImageTypes() {
ok := SupportedImageType("image/jpeg") ok := SupportedImageType("image/jpeg")
assert.True(suite.T(), ok) suite.True(ok)
ok = SupportedImageType("image/bmp") ok = SupportedImageType("image/bmp")
assert.False(suite.T(), ok) suite.False(ok)
} }
func TestMediaUtilTestSuite(t *testing.T) { func TestMediaUtilTestSuite(t *testing.T) {