Skip to content

Commit aa59cf0

Browse files
committed
fix: precompute total body size
1 parent 6b7fed2 commit aa59cf0

1 file changed

Lines changed: 34 additions & 15 deletions

File tree

lib/CloudConvert.ts

Lines changed: 34 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -89,35 +89,53 @@ export class UploadFile {
8989
this.filename = name;
9090
this.fileSize = size;
9191
}
92-
byteCount() {
93-
return this.fileSize;
94-
}
9592
add(key: string, value: unknown) {
9693
this.attributes.push([key, value]);
9794
}
98-
async *stream(boundary: string) {
95+
toMultiPart(boundary: string): {
96+
size: number;
97+
stream: AsyncIterable<Uint8Array>;
98+
} {
9999
const enc = new TextEncoder();
100+
const prefix: Uint8Array[] = [];
101+
const suffix: Uint8Array[] = [];
102+
100103
// Start multipart/form-data protocol
101-
yield enc.encode(`--${boundary}\r\n`);
104+
prefix.push(enc.encode(`--${boundary}\r\n`));
102105
// Send all attributes
103106
const separator = enc.encode(`\r\n--${boundary}\r\n`);
104107
let first = true;
105108
for (const [key, value] of this.attributes) {
106109
if (value == null) continue;
107-
if (!first) yield separator;
108-
yield enc.encode(
109-
`content-disposition:form-data;name="${key}"\r\n\r\n${value}`
110+
if (!first) prefix.push(separator);
111+
prefix.push(
112+
enc.encode(
113+
`content-disposition:form-data;name="${key}"\r\n\r\n${value}`
114+
)
110115
);
111116
first = false;
112117
}
113118
// Send file
114-
if (!first) yield separator;
115-
yield enc.encode(
116-
`content-disposition:form-data;name="file";filename=${this.filename}\r\ncontent-type:application/octet-stream\r\n\r\n`
119+
if (!first) prefix.push(separator);
120+
prefix.push(
121+
enc.encode(
122+
`content-disposition:form-data;name="file";filename=${this.filename}\r\ncontent-type:application/octet-stream\r\n\r\n`
123+
)
117124
);
118-
yield* this.data;
125+
const data = this.data;
119126
// End multipart/form-data protocol
120-
yield enc.encode(`\r\n--${boundary}--\r\n`);
127+
suffix.push(enc.encode(`\r\n--${boundary}--\r\n`));
128+
129+
const size =
130+
prefix.reduce((sum, arr) => sum + arr.byteLength, 0) +
131+
this.fileSize +
132+
suffix.reduce((sum, arr) => sum + arr.byteLength, 0);
133+
async function* concat() {
134+
yield* prefix;
135+
yield* data;
136+
yield* suffix;
137+
}
138+
return { size, stream: concat() };
121139
}
122140
}
123141

@@ -279,10 +297,11 @@ function prepareParameters(
279297
const boundary = `----------${Array.from(Array(32))
280298
.map(() => Math.random().toString(36)[2] || 0)
281299
.join('')}`;
300+
const { size, stream } = data.toMultiPart(boundary);
282301
return {
283-
contentLength: data.byteCount().toString(),
302+
contentLength: size.toString(),
284303
contentType: `multipart/form-data; boundary=${boundary}`,
285-
body: asyncIterableToReadableStream(data.stream(boundary))
304+
body: asyncIterableToReadableStream(stream)
286305
};
287306
}
288307

0 commit comments

Comments
 (0)