我有一个公共AWS S3存储桶,其中包含150个文本文件,每个30kB
。我创建了一个简单的test.js
文件,用于下载这150个文件,并显示第n个文件已成功下载的信息:
const { GetObjectCommand } = require('@aws-sdk/client-s3');
const { S3Client } = require('@aws-sdk/client-s3');
const { range } = require('lodash');
const s3 = new S3Client({
region: 'eu-central-1',
credentials: {
accessKeyId: 'XXXXX',
secretAccessKey: 'XXXXX',
},
});
const test = async () => {
let counter = 0;
await Promise.all(
range(0, 150).map((i) => {
const getCommand = new GetObjectCommand({
Key: `test/testfile${i}.txt`,
Bucket: 'bucketname',
});
return s3.send(getCommand).then(() => {
counter += 1;
console.log(counter, 'downloaded');
});
})
);
console.log('Finish!');
};
test();
问题是下载了第一个50
文件,然后程序停止(没有记录“Finish!”)。100kB
、2MB
、4MB
。在每种情况下,50
文件都有固定的某种限制。
我测试过,当文件大小为15 kB时,这个问题不存在-我在50
文件的每个块之间都有一些中断,但所有文件都下载了。
您知道如何让它下载所有文件吗?
我试图找到与AWS S3有关的一些限制,但我什么也没找到。
我试着玩--max-old-space-size=XXX
,但是没有用。而且看起来也不像是内存问题,因为不同的文件大小有相同的50
文件下载限制。
我试着在第一个0-40
文件和下一个41-80
文件之间添加一些sleep
,但它也卡在了50th
文件上。
1条答案
按热度按时间ruarlubt1#
您正在为150个操作重用同一个S3 Client。虽然在较小的范围内共享一个S3 Client是一个好做法,但一个S3 Client无法同时处理这么多http连接。请注意,默认情况下,aws-sdk-js配置为最多只能处理50个套接字。
我认为你可以通过传递一个自定义的代理来配置S3 Client,但是我不认为这是一个好主意。我从来没有尝试过,但是它可能看起来像这样:
一个更好的解决方案是创建一个promise池,每个promise池一次可以下载一个文件,一旦下载完成就开始下一个。This great solution似乎正是您所需要的: