Skip to content

Commit

Permalink
fix(fs/s3): throw error if upload >50GB
Browse files Browse the repository at this point in the history
  • Loading branch information
fbeauchamp authored and julien-f committed Oct 23, 2023
1 parent 1fac792 commit 9e66753
Show file tree
Hide file tree
Showing 2 changed files with 25 additions and 2 deletions.
25 changes: 23 additions & 2 deletions @xen-orchestra/fs/src/s3.js
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ import { getApplyMd5BodyChecksumPlugin } from '@aws-sdk/middleware-apply-body-ch
import { Agent as HttpAgent } from 'http'
import { Agent as HttpsAgent } from 'https'
import { createLogger } from '@xen-orchestra/log'
import { PassThrough, pipeline } from 'stream'
import { PassThrough, Transform, pipeline } from 'stream'
import { parse } from 'xo-remote-parser'
import copyStreamToBuffer from './_copyStreamToBuffer.js'
import guessAwsRegion from './_guessAwsRegion.js'
Expand Down Expand Up @@ -224,17 +224,38 @@ export default class S3Handler extends RemoteHandlerAbstract {
}

async _outputStream(path, input, { validator }) {
// S3 storage is limited to 10K part, each part is limited to 5GB. And the total upload must be smaller than 5TB
// a bigger partSize increase the memory consumption of aws/lib-storage exponentially
const MAX_PART = 10000
const PART_SIZE = 5 * 1024 * 1024
const MAX_SIZE = MAX_PART * PART_SIZE

// ensure we don't try to upload a stream to big for this partSize
let readCounter = 0
const streamCutter = new Transform({
transform(chunk, encoding, callback) {
readCounter += chunk.length
if (readCounter > MAX_SIZE) {
callback(new Error(`read ${readCounter} bytes, maximum size allowed is ${MAX_SIZE} `))
} else {
callback(null, chunk)
}
},
})

// Workaround for "ReferenceError: ReadableStream is not defined"
// https://github.com/aws/aws-sdk-js-v3/issues/2522
const Body = new PassThrough()
pipeline(input, Body, () => {})
pipeline(input, streamCutter, Body, () => {})

const upload = new Upload({
client: this.#s3,
params: {
...this.#createParams(path),
Body,
},
partSize: PART_SIZE,
leavePartsOnError: false,
})

await upload.done()
Expand Down
2 changes: 2 additions & 0 deletions CHANGELOG.unreleased.md
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,8 @@
<!--packages-start-->

- @xen-orchestra/backups patch
- @xen-orchestra/fs patch
- @xen-orchestra/mixins minor
- @xen-orchestra/xapi minor
- xo-server minor
Expand Down

0 comments on commit 9e66753

Please sign in to comment.