簡體   English   中英

node.js將imagemagick的輸出上傳到AWS S3

[英]node.js uploading output of imagemagick to AWS S3

我在使用imagemagick操縱圖像並將其上傳到S3時遇到問題。 生成的對象大小不同(較大),似乎已損壞。 如果我做一個中間步驟,然后先將輸出保存到本地tmp文件中並讀回,然后上傳結果,一切似乎都很好。 此代碼無效。

im.resize({
    srcData: imageObject.Body,
    width: variant.width,
    height: variant.height,
    customArgs: ['-auto-orient']
}, function(err, stdout, stderr) {
    if (err) {
        // This resize completed successfully
        log.err('Failed calling imageMagick, bail out', err);
        callback(err);
        return;
    }

    var fileName = cfg.aws.s3.uploadDir +
                    photo.imageId + '/' +
                    variant.width + 'x' + variant.height + '.jpg';
    log.info('Storing image at S3 ' + fileName);
    //fs.writeFileSync('/tmp/xxx.jpg', stdout, 'binary');
    //stdout = fs.readFileSync('/tmp/xxx.jpg');
    var x = new Buffer(stdout);
    console.log(x);
    s3.putObject(
        {
            Bucket: cfg.aws.s3.bucket,
            Key: fileName,
            Body: x,
            ContentType: 'image/jpeg',
            ACL: 'public-read'
        },
        function(err, data) {
            if (err) {
                // Failed saving to S3
                log.error('Failed saving to S3', err);
            }

            callback(err);
        }
    );
});

取消注釋fileWriteSync和fileReadSync,它可以正常工作。

在兩種情況下,console.log(x)命令的輸出:BAD:

緩沖區c3 bf c3 98 c3 bf c3 a0 00 10 4a 46 49 46 00 01 01 01 00 01 00 01 00 00 c3 bf c3 9b 00 43 00 06 04 05 06 05 04 06 06 05 06 07 07 06 08 0a 10 0a 0a 09 09 ...>

好:

緩沖區ff d8 ff e0 00 10 4a 46 49 46 00 01 01 01 00 01 00 01 00 00 ff db 00 43 00 06 04 05 06 05 04 06 06 05 06 07 07 06 08 0a 10 0a 0a 0a 09 09 0a 14 0e 0f 0c 10 ...>

如您所見,好的文件是正確的jpeg,壞的文件包含類似的序列,例如4a 46 49 46 = JFIF,但是有些字節已關閉,並且有移位,在壞的情況下,整個文件會增加大約20% 。

與編碼有關? 我已經嘗試了幾件事,但此時我迷路了。

謝謝!

更新#1:顯然,它與UTF編碼有關,但我仍然不完全了解這種情況下發生的情況。 顯然,c3 bf c3 98 c3 bf c3 a0 00 10 4a 46 49 46 00 01是以下內容的UTF編碼:

U+00FF LATIN SMALL LETTER Y WITH DIAERESIS character (ÿ)
U+00D8 LATIN CAPITAL LETTER O WITH STROKE character (Ø)
U+00FF LATIN SMALL LETTER Y WITH DIAERESIS character (ÿ)
U+00E0 LATIN SMALL LETTER A WITH GRAVE character (à)
U+0000 <control> character
U+0010 <control> character
U+004A LATIN CAPITAL LETTER J character
U+0046 LATIN CAPITAL LETTER F character
U+0049 LATIN CAPITAL LETTER I character
U+0046 LATIN CAPITAL LETTER F character
U+0000 <control> character
U+0001 <control> character

當FF D8 FF ..正是我所期望的。

我知道如何使代碼在沒有臨時文件的情況下工作(用var x = new Buffer(stdout)替換var x = new Buffer(stdout,'binary')

但是我仍然不能說我完全理解這里發生了什么,這應該在沒有Buffer()包裝的情況下進行,哪個組件有問題? ImageMagick的? 緩沖?

顯然這是很晚了,但是我本人只是遇到了這個問題,這就是我的工作方式。

ImageMagick.resize(params, function(err, stdout, stderr) {
    // Handle errors

    // Save the output of imagemagick to S3
    S3.putObject({
        Bucket: bucketName,
        Key: fileName,
        Body:  new Buffer(stdout, "binary")
    }).promise().then(function(data){
      // Success
    }).catch(function(err){
      // Error
    });
});

關鍵在於: new Buffer(stdout, "binary") 如果您不知道響應是否為緩沖區,則可以使用Buffer.isBuffer方法並執行以下操作:

var body = ( Buffer.isBuffer(stdout) ? stdout : new Buffer(stdout, "binary") );

不知道OP是否解決了問題,但是我也遇到了類似的問題,其中上傳到S3的圖像大於原始文件。 您能告訴我stdout包含什么(即,它是原始字節流嗎?)

我通過將Body:參數設置為使用base64編碼的緩沖區而不是二進制緩沖區來解決該問題。 我不完全確定為什么這可以解決問題,但我懷疑這與以下問題有關:

當需要對二進制數據進行編碼時,通常需要使用Base64編碼方案,該二進制數據需要通過旨在處理文本數據的媒體進行存儲和傳輸。 這是為了確保數據在傳輸過程中保持不變。

來源: MDN

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM