@aws-amplify/storage 4.4.23 → 4.4.24-unstable.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/aws-amplify-storage.js +84 -121
- package/dist/aws-amplify-storage.js.map +1 -1
- package/dist/aws-amplify-storage.min.js +1 -1
- package/dist/aws-amplify-storage.min.js.map +1 -1
- package/lib/providers/AWSS3ProviderManagedUpload.d.ts +1 -3
- package/lib/providers/AWSS3ProviderManagedUpload.js +66 -86
- package/lib/providers/AWSS3ProviderManagedUpload.js.map +1 -1
- package/lib-esm/providers/AWSS3ProviderManagedUpload.d.ts +1 -3
- package/lib-esm/providers/AWSS3ProviderManagedUpload.js +66 -86
- package/lib-esm/providers/AWSS3ProviderManagedUpload.js.map +1 -1
- package/package.json +3 -3
- package/src/providers/AWSS3ProviderManagedUpload.ts +75 -89
|
@@ -58,8 +58,8 @@ export class AWSS3ProviderManagedUpload {
|
|
|
58
58
|
private params: PutObjectRequest = null;
|
|
59
59
|
private opts = null;
|
|
60
60
|
private completedParts: CompletedPart[] = [];
|
|
61
|
-
private cancel = false;
|
|
62
61
|
private s3client: S3Client;
|
|
62
|
+
private uploadId = null;
|
|
63
63
|
|
|
64
64
|
// Progress reporting
|
|
65
65
|
private bytesUploaded = 0;
|
|
@@ -74,79 +74,87 @@ export class AWSS3ProviderManagedUpload {
|
|
|
74
74
|
}
|
|
75
75
|
|
|
76
76
|
public async upload() {
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
const parts: Part[] = this.createParts();
|
|
94
|
-
for (
|
|
95
|
-
let start = 0;
|
|
96
|
-
start < numberOfPartsToUpload;
|
|
97
|
-
start += this.queueSize
|
|
98
|
-
) {
|
|
99
|
-
/** This first block will try to cancel the upload if the cancel
|
|
100
|
-
* request came before any parts uploads have started.
|
|
101
|
-
**/
|
|
102
|
-
await this.checkIfUploadCancelled(uploadId);
|
|
103
|
-
|
|
104
|
-
// Upload as many as `queueSize` parts simultaneously
|
|
105
|
-
await this.uploadParts(
|
|
106
|
-
uploadId,
|
|
107
|
-
parts.slice(start, start + this.queueSize)
|
|
77
|
+
try {
|
|
78
|
+
this.body = await this.validateAndSanitizeBody(this.params.Body);
|
|
79
|
+
this.totalBytesToUpload = this.byteLength(this.body);
|
|
80
|
+
if (this.totalBytesToUpload <= this.minPartSize) {
|
|
81
|
+
// Multipart upload is not required. Upload the sanitized body as is
|
|
82
|
+
this.params.Body = this.body;
|
|
83
|
+
const putObjectCommand = new PutObjectCommand(this.params);
|
|
84
|
+
return this.s3client.send(putObjectCommand);
|
|
85
|
+
} else {
|
|
86
|
+
// Step 1: Initiate the multi part upload
|
|
87
|
+
this.uploadId = await this.createMultiPartUpload();
|
|
88
|
+
|
|
89
|
+
// Step 2: Upload chunks in parallel as requested
|
|
90
|
+
const numberOfPartsToUpload = Math.ceil(
|
|
91
|
+
this.totalBytesToUpload / this.minPartSize
|
|
108
92
|
);
|
|
109
93
|
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
94
|
+
const parts: Part[] = this.createParts();
|
|
95
|
+
for (
|
|
96
|
+
let start = 0;
|
|
97
|
+
start < numberOfPartsToUpload;
|
|
98
|
+
start += this.queueSize
|
|
99
|
+
) {
|
|
100
|
+
|
|
101
|
+
// Upload as many as `queueSize` parts simultaneously
|
|
102
|
+
await this.uploadParts(
|
|
103
|
+
this.uploadId,
|
|
104
|
+
parts.slice(start, start + this.queueSize)
|
|
105
|
+
);
|
|
106
|
+
}
|
|
115
107
|
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
108
|
+
parts.map(part => {
|
|
109
|
+
this.removeEventListener(part);
|
|
110
|
+
});
|
|
119
111
|
|
|
120
|
-
|
|
121
|
-
|
|
112
|
+
// Step 3: Finalize the upload such that S3 can recreate the file
|
|
113
|
+
return await this.finishMultiPartUpload(this.uploadId);
|
|
114
|
+
}
|
|
115
|
+
} catch (error) {
|
|
116
|
+
// if any error is thrown, call cleanup
|
|
117
|
+
await this.cleanup(this.uploadId);
|
|
118
|
+
logger.error('Error. Cancelling the multipart upload.');
|
|
119
|
+
throw error;
|
|
122
120
|
}
|
|
123
121
|
}
|
|
124
122
|
|
|
125
123
|
private createParts(): Part[] {
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
124
|
+
try {
|
|
125
|
+
const parts: Part[] = [];
|
|
126
|
+
for (let bodyStart = 0; bodyStart < this.totalBytesToUpload; ) {
|
|
127
|
+
const bodyEnd = Math.min(
|
|
128
|
+
bodyStart + this.minPartSize,
|
|
129
|
+
this.totalBytesToUpload
|
|
130
|
+
);
|
|
131
|
+
parts.push({
|
|
132
|
+
bodyPart: this.body.slice(bodyStart, bodyEnd),
|
|
133
|
+
partNumber: parts.length + 1,
|
|
134
|
+
emitter: new events.EventEmitter(),
|
|
135
|
+
_lastUploadedBytes: 0,
|
|
136
|
+
});
|
|
137
|
+
bodyStart += this.minPartSize;
|
|
138
|
+
}
|
|
139
|
+
return parts;
|
|
140
|
+
} catch (error) {
|
|
141
|
+
logger.error(error);
|
|
142
|
+
throw error;
|
|
139
143
|
}
|
|
140
|
-
return parts;
|
|
141
144
|
}
|
|
142
145
|
|
|
143
146
|
private async createMultiPartUpload() {
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
147
|
+
try {
|
|
148
|
+
const createMultiPartUploadCommand = new CreateMultipartUploadCommand(
|
|
149
|
+
this.params
|
|
150
|
+
);
|
|
151
|
+
const response = await this.s3client.send(createMultiPartUploadCommand);
|
|
152
|
+
logger.debug(response.UploadId);
|
|
153
|
+
return response.UploadId;
|
|
154
|
+
} catch (error) {
|
|
155
|
+
logger.error(error);
|
|
156
|
+
throw error;
|
|
157
|
+
}
|
|
150
158
|
}
|
|
151
159
|
|
|
152
160
|
/**
|
|
@@ -191,11 +199,9 @@ export class AWSS3ProviderManagedUpload {
|
|
|
191
199
|
}
|
|
192
200
|
} catch (error) {
|
|
193
201
|
logger.error(
|
|
194
|
-
'
|
|
195
|
-
error
|
|
202
|
+
'Error happened while uploading a part. Cancelling the multipart upload'
|
|
196
203
|
);
|
|
197
|
-
|
|
198
|
-
return;
|
|
204
|
+
throw error;
|
|
199
205
|
}
|
|
200
206
|
}
|
|
201
207
|
|
|
@@ -211,31 +217,11 @@ export class AWSS3ProviderManagedUpload {
|
|
|
211
217
|
const data = await this.s3client.send(completeUploadCommand);
|
|
212
218
|
return data.Key;
|
|
213
219
|
} catch (error) {
|
|
214
|
-
logger.error(
|
|
215
|
-
|
|
216
|
-
error
|
|
217
|
-
);
|
|
218
|
-
this.cancelUpload();
|
|
219
|
-
return;
|
|
220
|
+
logger.error('Error happened while finishing the upload.');
|
|
221
|
+
throw error;
|
|
220
222
|
}
|
|
221
223
|
}
|
|
222
224
|
|
|
223
|
-
private async checkIfUploadCancelled(uploadId: string) {
|
|
224
|
-
if (this.cancel) {
|
|
225
|
-
let errorMessage = 'Upload was cancelled.';
|
|
226
|
-
try {
|
|
227
|
-
await this.cleanup(uploadId);
|
|
228
|
-
} catch (error) {
|
|
229
|
-
errorMessage += ` ${error.message}`;
|
|
230
|
-
}
|
|
231
|
-
throw new Error(errorMessage);
|
|
232
|
-
}
|
|
233
|
-
}
|
|
234
|
-
|
|
235
|
-
public cancelUpload() {
|
|
236
|
-
this.cancel = true;
|
|
237
|
-
}
|
|
238
|
-
|
|
239
225
|
private async cleanup(uploadId: string) {
|
|
240
226
|
// Reset this's state
|
|
241
227
|
this.body = null;
|
|
@@ -255,7 +241,7 @@ export class AWSS3ProviderManagedUpload {
|
|
|
255
241
|
const data = await this.s3client.send(new ListPartsCommand(input));
|
|
256
242
|
|
|
257
243
|
if (data && data.Parts && data.Parts.length > 0) {
|
|
258
|
-
throw new Error('
|
|
244
|
+
throw new Error('Multipart upload clean up failed.');
|
|
259
245
|
}
|
|
260
246
|
}
|
|
261
247
|
|