我正在从他们各自的URL下载2个PNG图像,然后使用pixelmatch比较它们并生成第三张图像。
然后我试图将第三张图片上传到S3存储桶,但我很挣扎。 代码如下。
promise1和promise2分别是获得png1和png2的两个调用。 下面使用的dimensions1数组是在promise1创建的。 PNG是pngjs包。
const promArr = [promise1, promise2]; Promise.all(promArr).then(() => { const diff = new PNG({ width: dimensions1[0], height: dimensions1[1] }); const pix = pixelmatch(png1.data, png2.data, diff.data, dimensions1[0], dimensions1[1], { threshold: 0.1 }); const size = dimensions1[0] * dimensions1[1]; diff.pack().pipe(fs.createWriteStream(`/tmp/${targetHash}.png`)); const percentage = ((pix / size) * 100); const fileBuffer = fs.readFileSync(`/tmp/${targetHash}.png`); const s3 = new AWS.S3(); s3.putObject({ ACL: 'public-read', Key: targetFilename, Body: fileBuffer, Bucket: targetBucket, ContentType: 'image/png', }, (err) => { if (err) { console.warn(err); cb(err); } else { cb(null, { percentage, hash: `${targetFilename}`, key: `${targetFilename}`, bucket: targetBucket, url: `${event.stageVariables.endpoint}${targetFilename}`, }); } return; }); }) .catch((err) => { console.warn(`error: ${err}`); cb(err); });这会返回一个指向mac的报告为空的图像的URL。 这表明我有一个异步问题。
我也尝试传递diff.pack()作为正文,并得到错误: Cannot determine length of [object Object] 。 我在这里找到了关于这个错误的讨论。
我感觉真的很接近解决方案,但我并没有完全达到目标。 谁能帮忙? 谢谢
I'm downloading 2 png images from their respective URLs then using pixelmatch to compare them and generate a 3rd image.
I'm then trying to upload the third image to an S3 bucket but I'm struggling. Code follows.
promise1 and promise2 are the two calls to get png1 and png2 respectively. The dimensions1 array used below is created in promise1. PNG is the pngjs package.
const promArr = [promise1, promise2]; Promise.all(promArr).then(() => { const diff = new PNG({ width: dimensions1[0], height: dimensions1[1] }); const pix = pixelmatch(png1.data, png2.data, diff.data, dimensions1[0], dimensions1[1], { threshold: 0.1 }); const size = dimensions1[0] * dimensions1[1]; diff.pack().pipe(fs.createWriteStream(`/tmp/${targetHash}.png`)); const percentage = ((pix / size) * 100); const fileBuffer = fs.readFileSync(`/tmp/${targetHash}.png`); const s3 = new AWS.S3(); s3.putObject({ ACL: 'public-read', Key: targetFilename, Body: fileBuffer, Bucket: targetBucket, ContentType: 'image/png', }, (err) => { if (err) { console.warn(err); cb(err); } else { cb(null, { percentage, hash: `${targetFilename}`, key: `${targetFilename}`, bucket: targetBucket, url: `${event.stageVariables.endpoint}${targetFilename}`, }); } return; }); }) .catch((err) => { console.warn(`error: ${err}`); cb(err); });This returns a URL to the image which Preview on mac reports to be empty. This suggests to me that I have an async issue.
I have also tried passing diff.pack() as the body and got the error: Cannot determine length of [object Object]. I found a discussion of this error here.
I feel really close to a solution but I'm not quite getting there. Can anyone help? Thank you
最满意答案
见下面的解决方案 这是一个异步问题。 从这里采取笔记。 一旦创建临时文件的管道已经完成s3的东西开始。 注意这里提到的createReadStream的使用。
const promArr = [promise1, promise2]; Promise.all(promArr).then(() => { const diff = new PNG({ width: dimensions1[0], height: dimensions1[1] }); const pix = pixelmatch(png1.data, png2.data, diff.data, dimensions1[0], dimensions1[1], { threshold: 0.1 }); const size = dimensions1[0] * dimensions1[1]; const percentage = ((pix / size) * 100); diff.pack().pipe(fs.createWriteStream(`/tmp/${targetHash}.png`).on('finish', () => { const fileBuffer = fs.createReadStream(`/tmp/${targetHash}.png`); const s3 = new AWS.S3(); s3.putObject({ ACL: 'public-read', Key: targetFilename, Body: fileBuffer, Bucket: targetBucket, ContentType: 'image/png', }, (err) => { if (err) { console.warn(err); cb(err); } else { cb(null, { percentage, hash: `${targetFilename}`, key: `${targetFilename}`, bucket: targetBucket, url: `${event.stageVariables.endpoint}${targetFilename}`, }); } return; }); })); }) .catch((err) => { console.warn(`error: ${err}`); cb(err); });我并不完全满意于写入tmp然后再读出来,但它似乎是现在处理aws-sdk限制的最简单方法。
See solution below. It was an async issue. Took notes from here. Once the pipe to create the temporary file has finished the s3 stuff kicks off. NB the use of createReadStream which is mentioned here.
const promArr = [promise1, promise2]; Promise.all(promArr).then(() => { const diff = new PNG({ width: dimensions1[0], height: dimensions1[1] }); const pix = pixelmatch(png1.data, png2.data, diff.data, dimensions1[0], dimensions1[1], { threshold: 0.1 }); const size = dimensions1[0] * dimensions1[1]; const percentage = ((pix / size) * 100); diff.pack().pipe(fs.createWriteStream(`/tmp/${targetHash}.png`).on('finish', () => { const fileBuffer = fs.createReadStream(`/tmp/${targetHash}.png`); const s3 = new AWS.S3(); s3.putObject({ ACL: 'public-read', Key: targetFilename, Body: fileBuffer, Bucket: targetBucket, ContentType: 'image/png', }, (err) => { if (err) { console.warn(err); cb(err); } else { cb(null, { percentage, hash: `${targetFilename}`, key: `${targetFilename}`, bucket: targetBucket, url: `${event.stageVariables.endpoint}${targetFilename}`, }); } return; }); })); }) .catch((err) => { console.warn(`error: ${err}`); cb(err); });I'm not completely happy with writing to tmp then reading back out again but it seems to be the easiest way of dealing with aws-sdk limitations for now.
更多推荐
发布评论