@uploadcare/upload-client 4.3.0 → 5.0.0
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/README.md +15 -1
- package/dist/index.browser.js +187 -151
- package/dist/index.node.js +87 -57
- package/dist/index.react-native.js +187 -151
- package/dist/types.d.ts +32 -17
- package/package.json +4 -4
package/dist/index.browser.js
CHANGED
|
@@ -27,11 +27,118 @@ const onCancel = (signal, callback) => {
|
|
|
27
27
|
}
|
|
28
28
|
};
|
|
29
29
|
|
|
30
|
+
function isObject(o) {
|
|
31
|
+
return Object.prototype.toString.call(o) === '[object Object]';
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
const SEPARATOR = /\W|_/g;
|
|
35
|
+
function camelizeString(text) {
|
|
36
|
+
return text
|
|
37
|
+
.split(SEPARATOR)
|
|
38
|
+
.map((word, index) => word.charAt(0)[index > 0 ? 'toUpperCase' : 'toLowerCase']() +
|
|
39
|
+
word.slice(1))
|
|
40
|
+
.join('');
|
|
41
|
+
}
|
|
42
|
+
function camelizeArrayItems(array, { ignoreKeys } = { ignoreKeys: [] }) {
|
|
43
|
+
if (!Array.isArray(array)) {
|
|
44
|
+
return array;
|
|
45
|
+
}
|
|
46
|
+
return array.map((item) => camelizeKeys(item, { ignoreKeys }));
|
|
47
|
+
}
|
|
48
|
+
function camelizeKeys(source, { ignoreKeys } = { ignoreKeys: [] }) {
|
|
49
|
+
if (Array.isArray(source)) {
|
|
50
|
+
return camelizeArrayItems(source, { ignoreKeys });
|
|
51
|
+
}
|
|
52
|
+
if (!isObject(source)) {
|
|
53
|
+
return source;
|
|
54
|
+
}
|
|
55
|
+
const result = {};
|
|
56
|
+
for (const key of Object.keys(source)) {
|
|
57
|
+
let value = source[key];
|
|
58
|
+
if (ignoreKeys.includes(key)) {
|
|
59
|
+
result[key] = value;
|
|
60
|
+
continue;
|
|
61
|
+
}
|
|
62
|
+
if (isObject(value)) {
|
|
63
|
+
value = camelizeKeys(value, { ignoreKeys });
|
|
64
|
+
}
|
|
65
|
+
else if (Array.isArray(value)) {
|
|
66
|
+
value = camelizeArrayItems(value, { ignoreKeys });
|
|
67
|
+
}
|
|
68
|
+
result[camelizeString(key)] = value;
|
|
69
|
+
}
|
|
70
|
+
return result;
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
/**
|
|
74
|
+
* setTimeout as Promise.
|
|
75
|
+
*
|
|
76
|
+
* @param {number} ms Timeout in milliseconds.
|
|
77
|
+
*/
|
|
78
|
+
const delay = (ms) => new Promise((resolve) => setTimeout(resolve, ms));
|
|
79
|
+
|
|
80
|
+
function getUserAgent$1({ libraryName, libraryVersion, userAgent, publicKey = '', integration = '' }) {
|
|
81
|
+
const languageName = 'JavaScript';
|
|
82
|
+
if (typeof userAgent === 'string') {
|
|
83
|
+
return userAgent;
|
|
84
|
+
}
|
|
85
|
+
if (typeof userAgent === 'function') {
|
|
86
|
+
return userAgent({
|
|
87
|
+
publicKey,
|
|
88
|
+
libraryName,
|
|
89
|
+
libraryVersion,
|
|
90
|
+
languageName,
|
|
91
|
+
integration
|
|
92
|
+
});
|
|
93
|
+
}
|
|
94
|
+
const mainInfo = [libraryName, libraryVersion, publicKey]
|
|
95
|
+
.filter(Boolean)
|
|
96
|
+
.join('/');
|
|
97
|
+
const additionInfo = [languageName, integration].filter(Boolean).join('; ');
|
|
98
|
+
return `${mainInfo} (${additionInfo})`;
|
|
99
|
+
}
|
|
100
|
+
|
|
101
|
+
const defaultOptions = {
|
|
102
|
+
factor: 2,
|
|
103
|
+
time: 100
|
|
104
|
+
};
|
|
105
|
+
function retrier(fn, options = defaultOptions) {
|
|
106
|
+
let attempts = 0;
|
|
107
|
+
function runAttempt(fn) {
|
|
108
|
+
const defaultDelayTime = Math.round(options.time * options.factor ** attempts);
|
|
109
|
+
const retry = (ms) => delay(ms ?? defaultDelayTime).then(() => {
|
|
110
|
+
attempts += 1;
|
|
111
|
+
return runAttempt(fn);
|
|
112
|
+
});
|
|
113
|
+
return fn({
|
|
114
|
+
attempt: attempts,
|
|
115
|
+
retry
|
|
116
|
+
});
|
|
117
|
+
}
|
|
118
|
+
return runAttempt(fn);
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
class UploadcareNetworkError extends Error {
|
|
122
|
+
constructor(progressEvent) {
|
|
123
|
+
super();
|
|
124
|
+
this.name = 'UploadcareNetworkError';
|
|
125
|
+
this.message = 'Network error';
|
|
126
|
+
Object.setPrototypeOf(this, UploadcareNetworkError.prototype);
|
|
127
|
+
this.originalProgressEvent = progressEvent;
|
|
128
|
+
}
|
|
129
|
+
}
|
|
130
|
+
|
|
30
131
|
const request = ({ method, url, data, headers = {}, signal, onProgress }) => new Promise((resolve, reject) => {
|
|
31
132
|
const xhr = new XMLHttpRequest();
|
|
32
133
|
const requestMethod = method?.toUpperCase() || 'GET';
|
|
33
134
|
let aborted = false;
|
|
34
|
-
|
|
135
|
+
/**
|
|
136
|
+
* Force synchronous flag to be off
|
|
137
|
+
* Some chrome versions gets `InvalidAccessError` error when we set `responseType`
|
|
138
|
+
* See https://xhr.spec.whatwg.org/#synchronous-flag
|
|
139
|
+
* and https://bugs.chromium.org/p/chromium/issues/detail?id=1346628
|
|
140
|
+
*/
|
|
141
|
+
xhr.open(requestMethod, url, true);
|
|
35
142
|
if (headers) {
|
|
36
143
|
Object.entries(headers).forEach((entry) => {
|
|
37
144
|
const [key, value] = entry;
|
|
@@ -86,11 +193,11 @@ const request = ({ method, url, data, headers = {}, signal, onProgress }) => new
|
|
|
86
193
|
});
|
|
87
194
|
}
|
|
88
195
|
};
|
|
89
|
-
xhr.onerror = () => {
|
|
196
|
+
xhr.onerror = (progressEvent) => {
|
|
90
197
|
if (aborted)
|
|
91
198
|
return;
|
|
92
199
|
// only triggers if the request couldn't be made at all
|
|
93
|
-
reject(new
|
|
200
|
+
reject(new UploadcareNetworkError(progressEvent));
|
|
94
201
|
};
|
|
95
202
|
if (onProgress && typeof onProgress === 'function') {
|
|
96
203
|
xhr.upload.onprogress = (event) => {
|
|
@@ -221,7 +328,7 @@ const buildSearchParams = (query) => {
|
|
|
221
328
|
};
|
|
222
329
|
const getUrl = (base, path, query) => {
|
|
223
330
|
const url = new URL(base);
|
|
224
|
-
url.pathname = path;
|
|
331
|
+
url.pathname = (url.pathname + path).replace('//', '/');
|
|
225
332
|
if (query) {
|
|
226
333
|
url.search = buildSearchParams(query);
|
|
227
334
|
}
|
|
@@ -237,109 +344,18 @@ const defaultSettings = {
|
|
|
237
344
|
baseURL: 'https://upload.uploadcare.com',
|
|
238
345
|
maxContentLength: 50 * 1024 * 1024,
|
|
239
346
|
retryThrottledRequestMaxTimes: 1,
|
|
347
|
+
retryNetworkErrorMaxTimes: 3,
|
|
240
348
|
multipartMinFileSize: 25 * 1024 * 1024,
|
|
241
349
|
multipartChunkSize: 5 * 1024 * 1024,
|
|
242
350
|
multipartMinLastPartSize: 1024 * 1024,
|
|
243
351
|
maxConcurrentRequests: 4,
|
|
244
|
-
multipartMaxAttempts: 3,
|
|
245
352
|
pollingTimeoutMilliseconds: 10000,
|
|
246
353
|
pusherKey: '79ae88bd931ea68464d9'
|
|
247
354
|
};
|
|
248
355
|
const defaultContentType = 'application/octet-stream';
|
|
249
356
|
const defaultFilename = 'original';
|
|
250
357
|
|
|
251
|
-
var version = '
|
|
252
|
-
|
|
253
|
-
function isObject(o) {
|
|
254
|
-
return Object.prototype.toString.call(o) === '[object Object]';
|
|
255
|
-
}
|
|
256
|
-
|
|
257
|
-
const SEPARATOR = /\W|_/g;
|
|
258
|
-
function camelizeString(text) {
|
|
259
|
-
return text
|
|
260
|
-
.split(SEPARATOR)
|
|
261
|
-
.map((word, index) => word.charAt(0)[index > 0 ? 'toUpperCase' : 'toLowerCase']() +
|
|
262
|
-
word.slice(1))
|
|
263
|
-
.join('');
|
|
264
|
-
}
|
|
265
|
-
function camelizeArrayItems(array, { ignoreKeys } = { ignoreKeys: [] }) {
|
|
266
|
-
if (!Array.isArray(array)) {
|
|
267
|
-
return array;
|
|
268
|
-
}
|
|
269
|
-
return array.map((item) => camelizeKeys(item, { ignoreKeys }));
|
|
270
|
-
}
|
|
271
|
-
function camelizeKeys(source, { ignoreKeys } = { ignoreKeys: [] }) {
|
|
272
|
-
if (Array.isArray(source)) {
|
|
273
|
-
return camelizeArrayItems(source, { ignoreKeys });
|
|
274
|
-
}
|
|
275
|
-
if (!isObject(source)) {
|
|
276
|
-
return source;
|
|
277
|
-
}
|
|
278
|
-
const result = {};
|
|
279
|
-
for (const key of Object.keys(source)) {
|
|
280
|
-
let value = source[key];
|
|
281
|
-
if (ignoreKeys.includes(key)) {
|
|
282
|
-
result[key] = value;
|
|
283
|
-
continue;
|
|
284
|
-
}
|
|
285
|
-
if (isObject(value)) {
|
|
286
|
-
value = camelizeKeys(value, { ignoreKeys });
|
|
287
|
-
}
|
|
288
|
-
else if (Array.isArray(value)) {
|
|
289
|
-
value = camelizeArrayItems(value, { ignoreKeys });
|
|
290
|
-
}
|
|
291
|
-
result[camelizeString(key)] = value;
|
|
292
|
-
}
|
|
293
|
-
return result;
|
|
294
|
-
}
|
|
295
|
-
|
|
296
|
-
/**
|
|
297
|
-
* setTimeout as Promise.
|
|
298
|
-
*
|
|
299
|
-
* @param {number} ms Timeout in milliseconds.
|
|
300
|
-
*/
|
|
301
|
-
const delay = (ms) => new Promise((resolve) => setTimeout(resolve, ms));
|
|
302
|
-
|
|
303
|
-
function getUserAgent$1({ libraryName, libraryVersion, userAgent, publicKey = '', integration = '' }) {
|
|
304
|
-
const languageName = 'JavaScript';
|
|
305
|
-
if (typeof userAgent === 'string') {
|
|
306
|
-
return userAgent;
|
|
307
|
-
}
|
|
308
|
-
if (typeof userAgent === 'function') {
|
|
309
|
-
return userAgent({
|
|
310
|
-
publicKey,
|
|
311
|
-
libraryName,
|
|
312
|
-
libraryVersion,
|
|
313
|
-
languageName,
|
|
314
|
-
integration
|
|
315
|
-
});
|
|
316
|
-
}
|
|
317
|
-
const mainInfo = [libraryName, libraryVersion, publicKey]
|
|
318
|
-
.filter(Boolean)
|
|
319
|
-
.join('/');
|
|
320
|
-
const additionInfo = [languageName, integration].filter(Boolean).join('; ');
|
|
321
|
-
return `${mainInfo} (${additionInfo})`;
|
|
322
|
-
}
|
|
323
|
-
|
|
324
|
-
const defaultOptions = {
|
|
325
|
-
factor: 2,
|
|
326
|
-
time: 100
|
|
327
|
-
};
|
|
328
|
-
function retrier(fn, options = defaultOptions) {
|
|
329
|
-
let attempts = 0;
|
|
330
|
-
function runAttempt(fn) {
|
|
331
|
-
const defaultDelayTime = Math.round(options.time * options.factor ** attempts);
|
|
332
|
-
const retry = (ms) => delay(ms ?? defaultDelayTime).then(() => {
|
|
333
|
-
attempts += 1;
|
|
334
|
-
return runAttempt(fn);
|
|
335
|
-
});
|
|
336
|
-
return fn({
|
|
337
|
-
attempt: attempts,
|
|
338
|
-
retry
|
|
339
|
-
});
|
|
340
|
-
}
|
|
341
|
-
return runAttempt(fn);
|
|
342
|
-
}
|
|
358
|
+
var version = '5.0.0';
|
|
343
359
|
|
|
344
360
|
const LIBRARY_NAME = 'UploadcareUploadClient';
|
|
345
361
|
const LIBRARY_VERSION = version;
|
|
@@ -352,20 +368,26 @@ function getUserAgent(options) {
|
|
|
352
368
|
}
|
|
353
369
|
|
|
354
370
|
const REQUEST_WAS_THROTTLED_CODE = 'RequestThrottledError';
|
|
355
|
-
const
|
|
371
|
+
const DEFAULT_THROTTLED_TIMEOUT = 15000;
|
|
372
|
+
const DEFAULT_NETWORK_ERROR_TIMEOUT = 1000;
|
|
356
373
|
function getTimeoutFromThrottledRequest(error) {
|
|
357
374
|
const { headers } = error || {};
|
|
358
375
|
return ((headers &&
|
|
359
376
|
Number.parseInt(headers['x-throttle-wait-seconds']) * 1000) ||
|
|
360
|
-
|
|
377
|
+
DEFAULT_THROTTLED_TIMEOUT);
|
|
361
378
|
}
|
|
362
|
-
function
|
|
379
|
+
function retryIfFailed(fn, options) {
|
|
380
|
+
const { retryThrottledRequestMaxTimes, retryNetworkErrorMaxTimes } = options;
|
|
363
381
|
return retrier(({ attempt, retry }) => fn().catch((error) => {
|
|
364
382
|
if ('response' in error &&
|
|
365
383
|
error?.code === REQUEST_WAS_THROTTLED_CODE &&
|
|
366
|
-
attempt <
|
|
384
|
+
attempt < retryThrottledRequestMaxTimes) {
|
|
367
385
|
return retry(getTimeoutFromThrottledRequest(error));
|
|
368
386
|
}
|
|
387
|
+
if (error instanceof UploadcareNetworkError &&
|
|
388
|
+
attempt < retryNetworkErrorMaxTimes) {
|
|
389
|
+
return retry((attempt + 1) * DEFAULT_NETWORK_ERROR_TIMEOUT);
|
|
390
|
+
}
|
|
369
391
|
throw error;
|
|
370
392
|
}));
|
|
371
393
|
}
|
|
@@ -378,8 +400,8 @@ function getStoreValue(store) {
|
|
|
378
400
|
* Performs file uploading request to Uploadcare Upload API.
|
|
379
401
|
* Can be canceled and has progress.
|
|
380
402
|
*/
|
|
381
|
-
function base(file, { publicKey, fileName, contentType, baseURL = defaultSettings.baseURL, secureSignature, secureExpire, store, signal, onProgress, source = 'local', integration, userAgent, retryThrottledRequestMaxTimes = defaultSettings.retryThrottledRequestMaxTimes, metadata }) {
|
|
382
|
-
return
|
|
403
|
+
function base(file, { publicKey, fileName, contentType, baseURL = defaultSettings.baseURL, secureSignature, secureExpire, store, signal, onProgress, source = 'local', integration, userAgent, retryThrottledRequestMaxTimes = defaultSettings.retryThrottledRequestMaxTimes, retryNetworkErrorMaxTimes = defaultSettings.retryNetworkErrorMaxTimes, metadata }) {
|
|
404
|
+
return retryIfFailed(() => request({
|
|
383
405
|
method: 'POST',
|
|
384
406
|
url: getUrl(baseURL, '/base/', {
|
|
385
407
|
jsonerrors: 1
|
|
@@ -410,7 +432,7 @@ function base(file, { publicKey, fileName, contentType, baseURL = defaultSetting
|
|
|
410
432
|
else {
|
|
411
433
|
return response;
|
|
412
434
|
}
|
|
413
|
-
}), retryThrottledRequestMaxTimes);
|
|
435
|
+
}), { retryNetworkErrorMaxTimes, retryThrottledRequestMaxTimes });
|
|
414
436
|
}
|
|
415
437
|
|
|
416
438
|
var TypeEnum;
|
|
@@ -421,8 +443,8 @@ var TypeEnum;
|
|
|
421
443
|
/**
|
|
422
444
|
* Uploading files from URL.
|
|
423
445
|
*/
|
|
424
|
-
function fromUrl(sourceUrl, { publicKey, baseURL = defaultSettings.baseURL, store, fileName, checkForUrlDuplicates, saveUrlForRecurrentUploads, secureSignature, secureExpire, source = 'url', signal, integration, userAgent, retryThrottledRequestMaxTimes = defaultSettings.retryThrottledRequestMaxTimes, metadata }) {
|
|
425
|
-
return
|
|
446
|
+
function fromUrl(sourceUrl, { publicKey, baseURL = defaultSettings.baseURL, store, fileName, checkForUrlDuplicates, saveUrlForRecurrentUploads, secureSignature, secureExpire, source = 'url', signal, integration, userAgent, retryThrottledRequestMaxTimes = defaultSettings.retryThrottledRequestMaxTimes, retryNetworkErrorMaxTimes = defaultSettings.retryNetworkErrorMaxTimes, metadata }) {
|
|
447
|
+
return retryIfFailed(() => request({
|
|
426
448
|
method: 'POST',
|
|
427
449
|
headers: {
|
|
428
450
|
'X-UC-User-Agent': getUserAgent({ publicKey, integration, userAgent })
|
|
@@ -449,7 +471,7 @@ function fromUrl(sourceUrl, { publicKey, baseURL = defaultSettings.baseURL, stor
|
|
|
449
471
|
else {
|
|
450
472
|
return response;
|
|
451
473
|
}
|
|
452
|
-
}), retryThrottledRequestMaxTimes);
|
|
474
|
+
}), { retryNetworkErrorMaxTimes, retryThrottledRequestMaxTimes });
|
|
453
475
|
}
|
|
454
476
|
|
|
455
477
|
var Status;
|
|
@@ -466,8 +488,8 @@ const isErrorResponse = (response) => {
|
|
|
466
488
|
/**
|
|
467
489
|
* Checking upload status and working with file tokens.
|
|
468
490
|
*/
|
|
469
|
-
function fromUrlStatus(token, { publicKey, baseURL = defaultSettings.baseURL, signal, integration, userAgent, retryThrottledRequestMaxTimes = defaultSettings.retryThrottledRequestMaxTimes } = {}) {
|
|
470
|
-
return
|
|
491
|
+
function fromUrlStatus(token, { publicKey, baseURL = defaultSettings.baseURL, signal, integration, userAgent, retryThrottledRequestMaxTimes = defaultSettings.retryThrottledRequestMaxTimes, retryNetworkErrorMaxTimes = defaultSettings.retryNetworkErrorMaxTimes } = {}) {
|
|
492
|
+
return retryIfFailed(() => request({
|
|
471
493
|
method: 'GET',
|
|
472
494
|
headers: publicKey
|
|
473
495
|
? {
|
|
@@ -491,14 +513,14 @@ function fromUrlStatus(token, { publicKey, baseURL = defaultSettings.baseURL, si
|
|
|
491
513
|
else {
|
|
492
514
|
return response;
|
|
493
515
|
}
|
|
494
|
-
}), retryThrottledRequestMaxTimes);
|
|
516
|
+
}), { retryNetworkErrorMaxTimes, retryThrottledRequestMaxTimes });
|
|
495
517
|
}
|
|
496
518
|
|
|
497
519
|
/**
|
|
498
520
|
* Create files group.
|
|
499
521
|
*/
|
|
500
|
-
function group(uuids, { publicKey, baseURL = defaultSettings.baseURL, jsonpCallback, secureSignature, secureExpire, signal, source, integration, userAgent, retryThrottledRequestMaxTimes = defaultSettings.retryThrottledRequestMaxTimes }) {
|
|
501
|
-
return
|
|
522
|
+
function group(uuids, { publicKey, baseURL = defaultSettings.baseURL, jsonpCallback, secureSignature, secureExpire, signal, source, integration, userAgent, retryThrottledRequestMaxTimes = defaultSettings.retryThrottledRequestMaxTimes, retryNetworkErrorMaxTimes = defaultSettings.retryNetworkErrorMaxTimes }) {
|
|
523
|
+
return retryIfFailed(() => request({
|
|
502
524
|
method: 'POST',
|
|
503
525
|
headers: {
|
|
504
526
|
'X-UC-User-Agent': getUserAgent({ publicKey, integration, userAgent })
|
|
@@ -521,14 +543,14 @@ function group(uuids, { publicKey, baseURL = defaultSettings.baseURL, jsonpCallb
|
|
|
521
543
|
else {
|
|
522
544
|
return response;
|
|
523
545
|
}
|
|
524
|
-
}), retryThrottledRequestMaxTimes);
|
|
546
|
+
}), { retryNetworkErrorMaxTimes, retryThrottledRequestMaxTimes });
|
|
525
547
|
}
|
|
526
548
|
|
|
527
549
|
/**
|
|
528
550
|
* Get info about group.
|
|
529
551
|
*/
|
|
530
|
-
function groupInfo(id, { publicKey, baseURL = defaultSettings.baseURL, signal, source, integration, userAgent, retryThrottledRequestMaxTimes = defaultSettings.retryThrottledRequestMaxTimes }) {
|
|
531
|
-
return
|
|
552
|
+
function groupInfo(id, { publicKey, baseURL = defaultSettings.baseURL, signal, source, integration, userAgent, retryThrottledRequestMaxTimes = defaultSettings.retryThrottledRequestMaxTimes, retryNetworkErrorMaxTimes = defaultSettings.retryNetworkErrorMaxTimes }) {
|
|
553
|
+
return retryIfFailed(() => request({
|
|
532
554
|
method: 'GET',
|
|
533
555
|
headers: {
|
|
534
556
|
'X-UC-User-Agent': getUserAgent({ publicKey, integration, userAgent })
|
|
@@ -548,14 +570,14 @@ function groupInfo(id, { publicKey, baseURL = defaultSettings.baseURL, signal, s
|
|
|
548
570
|
else {
|
|
549
571
|
return response;
|
|
550
572
|
}
|
|
551
|
-
}), retryThrottledRequestMaxTimes);
|
|
573
|
+
}), { retryThrottledRequestMaxTimes, retryNetworkErrorMaxTimes });
|
|
552
574
|
}
|
|
553
575
|
|
|
554
576
|
/**
|
|
555
577
|
* Returns a JSON dictionary holding file info.
|
|
556
578
|
*/
|
|
557
|
-
function info(uuid, { publicKey, baseURL = defaultSettings.baseURL, signal, source, integration, userAgent, retryThrottledRequestMaxTimes = defaultSettings.retryThrottledRequestMaxTimes }) {
|
|
558
|
-
return
|
|
579
|
+
function info(uuid, { publicKey, baseURL = defaultSettings.baseURL, signal, source, integration, userAgent, retryThrottledRequestMaxTimes = defaultSettings.retryThrottledRequestMaxTimes, retryNetworkErrorMaxTimes = defaultSettings.retryNetworkErrorMaxTimes }) {
|
|
580
|
+
return retryIfFailed(() => request({
|
|
559
581
|
method: 'GET',
|
|
560
582
|
headers: {
|
|
561
583
|
'X-UC-User-Agent': getUserAgent({ publicKey, integration, userAgent })
|
|
@@ -575,14 +597,14 @@ function info(uuid, { publicKey, baseURL = defaultSettings.baseURL, signal, sour
|
|
|
575
597
|
else {
|
|
576
598
|
return response;
|
|
577
599
|
}
|
|
578
|
-
}), retryThrottledRequestMaxTimes);
|
|
600
|
+
}), { retryThrottledRequestMaxTimes, retryNetworkErrorMaxTimes });
|
|
579
601
|
}
|
|
580
602
|
|
|
581
603
|
/**
|
|
582
604
|
* Start multipart uploading.
|
|
583
605
|
*/
|
|
584
|
-
function multipartStart(size, { publicKey, contentType, fileName, multipartChunkSize = defaultSettings.multipartChunkSize, baseURL = '', secureSignature, secureExpire, store, signal, source = 'local', integration, userAgent, retryThrottledRequestMaxTimes = defaultSettings.retryThrottledRequestMaxTimes, metadata }) {
|
|
585
|
-
return
|
|
606
|
+
function multipartStart(size, { publicKey, contentType, fileName, multipartChunkSize = defaultSettings.multipartChunkSize, baseURL = '', secureSignature, secureExpire, store, signal, source = 'local', integration, userAgent, retryThrottledRequestMaxTimes = defaultSettings.retryThrottledRequestMaxTimes, retryNetworkErrorMaxTimes = defaultSettings.retryNetworkErrorMaxTimes, metadata }) {
|
|
607
|
+
return retryIfFailed(() => request({
|
|
586
608
|
method: 'POST',
|
|
587
609
|
url: getUrl(baseURL, '/multipart/start/', { jsonerrors: 1 }),
|
|
588
610
|
headers: {
|
|
@@ -611,14 +633,14 @@ function multipartStart(size, { publicKey, contentType, fileName, multipartChunk
|
|
|
611
633
|
response.parts = Object.keys(response.parts).map((key) => response.parts[key]);
|
|
612
634
|
return response;
|
|
613
635
|
}
|
|
614
|
-
}), retryThrottledRequestMaxTimes);
|
|
636
|
+
}), { retryThrottledRequestMaxTimes, retryNetworkErrorMaxTimes });
|
|
615
637
|
}
|
|
616
638
|
|
|
617
639
|
/**
|
|
618
640
|
* Complete multipart uploading.
|
|
619
641
|
*/
|
|
620
|
-
function multipartUpload(part, url, { signal, onProgress }) {
|
|
621
|
-
return request({
|
|
642
|
+
function multipartUpload(part, url, { signal, onProgress, retryThrottledRequestMaxTimes = defaultSettings.retryThrottledRequestMaxTimes, retryNetworkErrorMaxTimes = defaultSettings.retryNetworkErrorMaxTimes }) {
|
|
643
|
+
return retryIfFailed(() => request({
|
|
622
644
|
method: 'PUT',
|
|
623
645
|
url,
|
|
624
646
|
data: part,
|
|
@@ -635,14 +657,17 @@ function multipartUpload(part, url, { signal, onProgress }) {
|
|
|
635
657
|
});
|
|
636
658
|
return result;
|
|
637
659
|
})
|
|
638
|
-
.then(({ status }) => ({ code: status }))
|
|
660
|
+
.then(({ status }) => ({ code: status })), {
|
|
661
|
+
retryThrottledRequestMaxTimes,
|
|
662
|
+
retryNetworkErrorMaxTimes
|
|
663
|
+
});
|
|
639
664
|
}
|
|
640
665
|
|
|
641
666
|
/**
|
|
642
667
|
* Complete multipart uploading.
|
|
643
668
|
*/
|
|
644
|
-
function multipartComplete(uuid, { publicKey, baseURL = defaultSettings.baseURL, source = 'local', signal, integration, userAgent, retryThrottledRequestMaxTimes = defaultSettings.retryThrottledRequestMaxTimes }) {
|
|
645
|
-
return
|
|
669
|
+
function multipartComplete(uuid, { publicKey, baseURL = defaultSettings.baseURL, source = 'local', signal, integration, userAgent, retryThrottledRequestMaxTimes = defaultSettings.retryThrottledRequestMaxTimes, retryNetworkErrorMaxTimes = defaultSettings.retryNetworkErrorMaxTimes }) {
|
|
670
|
+
return retryIfFailed(() => request({
|
|
646
671
|
method: 'POST',
|
|
647
672
|
url: getUrl(baseURL, '/multipart/complete/', { jsonerrors: 1 }),
|
|
648
673
|
headers: {
|
|
@@ -662,7 +687,7 @@ function multipartComplete(uuid, { publicKey, baseURL = defaultSettings.baseURL,
|
|
|
662
687
|
else {
|
|
663
688
|
return response;
|
|
664
689
|
}
|
|
665
|
-
}), retryThrottledRequestMaxTimes);
|
|
690
|
+
}), { retryThrottledRequestMaxTimes, retryNetworkErrorMaxTimes });
|
|
666
691
|
}
|
|
667
692
|
|
|
668
693
|
class UploadcareFile {
|
|
@@ -729,7 +754,7 @@ const poll = ({ check, interval = DEFAULT_INTERVAL, signal }) => new Promise((re
|
|
|
729
754
|
timeoutId = setTimeout(tick, 0);
|
|
730
755
|
});
|
|
731
756
|
|
|
732
|
-
function isReadyPoll({ file, publicKey, baseURL, source, integration, userAgent, retryThrottledRequestMaxTimes, signal, onProgress }) {
|
|
757
|
+
function isReadyPoll({ file, publicKey, baseURL, source, integration, userAgent, retryThrottledRequestMaxTimes, retryNetworkErrorMaxTimes, signal, onProgress }) {
|
|
733
758
|
return poll({
|
|
734
759
|
check: (signal) => info(file, {
|
|
735
760
|
publicKey,
|
|
@@ -738,7 +763,8 @@ function isReadyPoll({ file, publicKey, baseURL, source, integration, userAgent,
|
|
|
738
763
|
source,
|
|
739
764
|
integration,
|
|
740
765
|
userAgent,
|
|
741
|
-
retryThrottledRequestMaxTimes
|
|
766
|
+
retryThrottledRequestMaxTimes,
|
|
767
|
+
retryNetworkErrorMaxTimes
|
|
742
768
|
}).then((response) => {
|
|
743
769
|
if (response.isReady) {
|
|
744
770
|
return response;
|
|
@@ -750,7 +776,7 @@ function isReadyPoll({ file, publicKey, baseURL, source, integration, userAgent,
|
|
|
750
776
|
});
|
|
751
777
|
}
|
|
752
778
|
|
|
753
|
-
const uploadDirect = (file, { publicKey, fileName, baseURL, secureSignature, secureExpire, store, contentType, signal, onProgress, source, integration, userAgent, retryThrottledRequestMaxTimes, baseCDN, metadata }) => {
|
|
779
|
+
const uploadDirect = (file, { publicKey, fileName, baseURL, secureSignature, secureExpire, store, contentType, signal, onProgress, source, integration, userAgent, retryThrottledRequestMaxTimes, retryNetworkErrorMaxTimes, baseCDN, metadata }) => {
|
|
754
780
|
return base(file, {
|
|
755
781
|
publicKey,
|
|
756
782
|
fileName,
|
|
@@ -765,6 +791,7 @@ const uploadDirect = (file, { publicKey, fileName, baseURL, secureSignature, sec
|
|
|
765
791
|
integration,
|
|
766
792
|
userAgent,
|
|
767
793
|
retryThrottledRequestMaxTimes,
|
|
794
|
+
retryNetworkErrorMaxTimes,
|
|
768
795
|
metadata
|
|
769
796
|
})
|
|
770
797
|
.then(({ file }) => {
|
|
@@ -776,6 +803,7 @@ const uploadDirect = (file, { publicKey, fileName, baseURL, secureSignature, sec
|
|
|
776
803
|
integration,
|
|
777
804
|
userAgent,
|
|
778
805
|
retryThrottledRequestMaxTimes,
|
|
806
|
+
retryNetworkErrorMaxTimes,
|
|
779
807
|
onProgress,
|
|
780
808
|
signal
|
|
781
809
|
});
|
|
@@ -963,7 +991,7 @@ const preconnect = (key) => {
|
|
|
963
991
|
getPusher(key).connect();
|
|
964
992
|
};
|
|
965
993
|
|
|
966
|
-
function pollStrategy({ token, publicKey, baseURL, integration, userAgent, retryThrottledRequestMaxTimes, onProgress, signal }) {
|
|
994
|
+
function pollStrategy({ token, publicKey, baseURL, integration, userAgent, retryThrottledRequestMaxTimes, retryNetworkErrorMaxTimes, onProgress, signal }) {
|
|
967
995
|
return poll({
|
|
968
996
|
check: (signal) => fromUrlStatus(token, {
|
|
969
997
|
publicKey,
|
|
@@ -971,6 +999,7 @@ function pollStrategy({ token, publicKey, baseURL, integration, userAgent, retry
|
|
|
971
999
|
integration,
|
|
972
1000
|
userAgent,
|
|
973
1001
|
retryThrottledRequestMaxTimes,
|
|
1002
|
+
retryNetworkErrorMaxTimes,
|
|
974
1003
|
signal
|
|
975
1004
|
}).then((response) => {
|
|
976
1005
|
switch (response.status) {
|
|
@@ -1121,7 +1150,7 @@ const uploadFromUrl = (sourceUrl, { publicKey, fileName, baseURL, baseCDN, check
|
|
|
1121
1150
|
}))
|
|
1122
1151
|
.then((fileInfo) => new UploadcareFile(fileInfo, { baseCDN }));
|
|
1123
1152
|
|
|
1124
|
-
const uploadFromUploaded = (uuid, { publicKey, fileName, baseURL, signal, onProgress, source, integration, userAgent, retryThrottledRequestMaxTimes, baseCDN }) => {
|
|
1153
|
+
const uploadFromUploaded = (uuid, { publicKey, fileName, baseURL, signal, onProgress, source, integration, userAgent, retryThrottledRequestMaxTimes, retryNetworkErrorMaxTimes, baseCDN }) => {
|
|
1125
1154
|
return info(uuid, {
|
|
1126
1155
|
publicKey,
|
|
1127
1156
|
baseURL,
|
|
@@ -1129,7 +1158,8 @@ const uploadFromUploaded = (uuid, { publicKey, fileName, baseURL, signal, onProg
|
|
|
1129
1158
|
source,
|
|
1130
1159
|
integration,
|
|
1131
1160
|
userAgent,
|
|
1132
|
-
retryThrottledRequestMaxTimes
|
|
1161
|
+
retryThrottledRequestMaxTimes,
|
|
1162
|
+
retryNetworkErrorMaxTimes
|
|
1133
1163
|
})
|
|
1134
1164
|
.then((fileInfo) => new UploadcareFile(fileInfo, { baseCDN, fileName }))
|
|
1135
1165
|
.then((result) => {
|
|
@@ -1201,18 +1231,15 @@ const runWithConcurrency = (concurrency, tasks) => {
|
|
|
1201
1231
|
});
|
|
1202
1232
|
};
|
|
1203
1233
|
|
|
1204
|
-
const
|
|
1234
|
+
const uploadPart = (chunk, url, { publicKey, onProgress, signal, integration, retryThrottledRequestMaxTimes, retryNetworkErrorMaxTimes }) => multipartUpload(chunk, url, {
|
|
1205
1235
|
publicKey,
|
|
1206
1236
|
onProgress,
|
|
1207
1237
|
signal,
|
|
1208
|
-
integration
|
|
1209
|
-
|
|
1210
|
-
|
|
1211
|
-
|
|
1212
|
-
|
|
1213
|
-
throw error;
|
|
1214
|
-
}));
|
|
1215
|
-
const uploadMultipart = (file, { publicKey, fileName, fileSize, baseURL, secureSignature, secureExpire, store, signal, onProgress, source, integration, userAgent, retryThrottledRequestMaxTimes, contentType, multipartChunkSize = defaultSettings.multipartChunkSize, maxConcurrentRequests = defaultSettings.maxConcurrentRequests, multipartMaxAttempts = defaultSettings.multipartMaxAttempts, baseCDN, metadata }) => {
|
|
1238
|
+
integration,
|
|
1239
|
+
retryThrottledRequestMaxTimes,
|
|
1240
|
+
retryNetworkErrorMaxTimes
|
|
1241
|
+
});
|
|
1242
|
+
const uploadMultipart = (file, { publicKey, fileName, fileSize, baseURL, secureSignature, secureExpire, store, signal, onProgress, source, integration, userAgent, retryThrottledRequestMaxTimes, retryNetworkErrorMaxTimes, contentType, multipartChunkSize = defaultSettings.multipartChunkSize, maxConcurrentRequests = defaultSettings.maxConcurrentRequests, baseCDN, metadata }) => {
|
|
1216
1243
|
const size = fileSize || getFileSize(file);
|
|
1217
1244
|
let progressValues;
|
|
1218
1245
|
const createProgressHandler = (totalChunks, chunkIdx) => {
|
|
@@ -1246,18 +1273,20 @@ const uploadMultipart = (file, { publicKey, fileName, fileSize, baseURL, secureS
|
|
|
1246
1273
|
integration,
|
|
1247
1274
|
userAgent,
|
|
1248
1275
|
retryThrottledRequestMaxTimes,
|
|
1276
|
+
retryNetworkErrorMaxTimes,
|
|
1249
1277
|
metadata
|
|
1250
1278
|
})
|
|
1251
1279
|
.then(({ uuid, parts }) => {
|
|
1252
1280
|
const getChunk = prepareChunks(file, size, multipartChunkSize);
|
|
1253
1281
|
return Promise.all([
|
|
1254
1282
|
uuid,
|
|
1255
|
-
runWithConcurrency(maxConcurrentRequests, parts.map((url, index) => () =>
|
|
1283
|
+
runWithConcurrency(maxConcurrentRequests, parts.map((url, index) => () => uploadPart(getChunk(index), url, {
|
|
1256
1284
|
publicKey,
|
|
1257
1285
|
onProgress: createProgressHandler(parts.length, index),
|
|
1258
1286
|
signal,
|
|
1259
1287
|
integration,
|
|
1260
|
-
|
|
1288
|
+
retryThrottledRequestMaxTimes,
|
|
1289
|
+
retryNetworkErrorMaxTimes
|
|
1261
1290
|
})))
|
|
1262
1291
|
]);
|
|
1263
1292
|
})
|
|
@@ -1267,7 +1296,8 @@ const uploadMultipart = (file, { publicKey, fileName, fileSize, baseURL, secureS
|
|
|
1267
1296
|
source,
|
|
1268
1297
|
integration,
|
|
1269
1298
|
userAgent,
|
|
1270
|
-
retryThrottledRequestMaxTimes
|
|
1299
|
+
retryThrottledRequestMaxTimes,
|
|
1300
|
+
retryNetworkErrorMaxTimes
|
|
1271
1301
|
}))
|
|
1272
1302
|
.then((fileInfo) => {
|
|
1273
1303
|
if (fileInfo.isReady) {
|
|
@@ -1282,6 +1312,7 @@ const uploadMultipart = (file, { publicKey, fileName, fileSize, baseURL, secureS
|
|
|
1282
1312
|
integration,
|
|
1283
1313
|
userAgent,
|
|
1284
1314
|
retryThrottledRequestMaxTimes,
|
|
1315
|
+
retryNetworkErrorMaxTimes,
|
|
1285
1316
|
onProgress,
|
|
1286
1317
|
signal
|
|
1287
1318
|
});
|
|
@@ -1293,7 +1324,7 @@ const uploadMultipart = (file, { publicKey, fileName, fileSize, baseURL, secureS
|
|
|
1293
1324
|
/**
|
|
1294
1325
|
* Uploads file from provided data.
|
|
1295
1326
|
*/
|
|
1296
|
-
function uploadFile(data, { publicKey, fileName, baseURL = defaultSettings.baseURL, secureSignature, secureExpire, store, signal, onProgress, source, integration, userAgent, retryThrottledRequestMaxTimes, contentType, multipartMinFileSize, multipartChunkSize,
|
|
1327
|
+
function uploadFile(data, { publicKey, fileName, baseURL = defaultSettings.baseURL, secureSignature, secureExpire, store, signal, onProgress, source, integration, userAgent, retryThrottledRequestMaxTimes, retryNetworkErrorMaxTimes, contentType, multipartMinFileSize, multipartChunkSize, maxConcurrentRequests, baseCDN = defaultSettings.baseCDN, checkForUrlDuplicates, saveUrlForRecurrentUploads, pusherKey, metadata }) {
|
|
1297
1328
|
if (isFileData(data)) {
|
|
1298
1329
|
const fileSize = getFileSize(data);
|
|
1299
1330
|
if (isMultipart(fileSize, multipartMinFileSize)) {
|
|
@@ -1301,7 +1332,6 @@ function uploadFile(data, { publicKey, fileName, baseURL = defaultSettings.baseU
|
|
|
1301
1332
|
publicKey,
|
|
1302
1333
|
contentType,
|
|
1303
1334
|
multipartChunkSize,
|
|
1304
|
-
multipartMaxAttempts,
|
|
1305
1335
|
fileName,
|
|
1306
1336
|
baseURL,
|
|
1307
1337
|
secureSignature,
|
|
@@ -1314,6 +1344,7 @@ function uploadFile(data, { publicKey, fileName, baseURL = defaultSettings.baseU
|
|
|
1314
1344
|
userAgent,
|
|
1315
1345
|
maxConcurrentRequests,
|
|
1316
1346
|
retryThrottledRequestMaxTimes,
|
|
1347
|
+
retryNetworkErrorMaxTimes,
|
|
1317
1348
|
baseCDN,
|
|
1318
1349
|
metadata
|
|
1319
1350
|
});
|
|
@@ -1332,6 +1363,7 @@ function uploadFile(data, { publicKey, fileName, baseURL = defaultSettings.baseU
|
|
|
1332
1363
|
integration,
|
|
1333
1364
|
userAgent,
|
|
1334
1365
|
retryThrottledRequestMaxTimes,
|
|
1366
|
+
retryNetworkErrorMaxTimes,
|
|
1335
1367
|
baseCDN,
|
|
1336
1368
|
metadata
|
|
1337
1369
|
});
|
|
@@ -1353,6 +1385,7 @@ function uploadFile(data, { publicKey, fileName, baseURL = defaultSettings.baseU
|
|
|
1353
1385
|
integration,
|
|
1354
1386
|
userAgent,
|
|
1355
1387
|
retryThrottledRequestMaxTimes,
|
|
1388
|
+
retryNetworkErrorMaxTimes,
|
|
1356
1389
|
pusherKey,
|
|
1357
1390
|
metadata
|
|
1358
1391
|
});
|
|
@@ -1368,6 +1401,7 @@ function uploadFile(data, { publicKey, fileName, baseURL = defaultSettings.baseU
|
|
|
1368
1401
|
integration,
|
|
1369
1402
|
userAgent,
|
|
1370
1403
|
retryThrottledRequestMaxTimes,
|
|
1404
|
+
retryNetworkErrorMaxTimes,
|
|
1371
1405
|
baseCDN
|
|
1372
1406
|
});
|
|
1373
1407
|
}
|
|
@@ -1423,7 +1457,7 @@ const isUrlArray = (data) => {
|
|
|
1423
1457
|
return true;
|
|
1424
1458
|
};
|
|
1425
1459
|
|
|
1426
|
-
function uploadFileGroup(data, { publicKey, fileName, baseURL = defaultSettings.baseURL, secureSignature, secureExpire, store, signal, onProgress, source, integration, userAgent, retryThrottledRequestMaxTimes, contentType, multipartChunkSize = defaultSettings.multipartChunkSize, baseCDN = defaultSettings.baseCDN, jsonpCallback }) {
|
|
1460
|
+
function uploadFileGroup(data, { publicKey, fileName, baseURL = defaultSettings.baseURL, secureSignature, secureExpire, store, signal, onProgress, source, integration, userAgent, retryThrottledRequestMaxTimes, retryNetworkErrorMaxTimes, contentType, multipartChunkSize = defaultSettings.multipartChunkSize, baseCDN = defaultSettings.baseCDN, jsonpCallback }) {
|
|
1427
1461
|
if (!isFileDataArray(data) && !isUrlArray(data) && !isUuidArray(data)) {
|
|
1428
1462
|
throw new TypeError(`Group uploading from "${data}" is not supported`);
|
|
1429
1463
|
}
|
|
@@ -1460,6 +1494,7 @@ function uploadFileGroup(data, { publicKey, fileName, baseURL = defaultSettings.
|
|
|
1460
1494
|
integration,
|
|
1461
1495
|
userAgent,
|
|
1462
1496
|
retryThrottledRequestMaxTimes,
|
|
1497
|
+
retryNetworkErrorMaxTimes,
|
|
1463
1498
|
contentType,
|
|
1464
1499
|
multipartChunkSize,
|
|
1465
1500
|
baseCDN
|
|
@@ -1475,7 +1510,8 @@ function uploadFileGroup(data, { publicKey, fileName, baseURL = defaultSettings.
|
|
|
1475
1510
|
source,
|
|
1476
1511
|
integration,
|
|
1477
1512
|
userAgent,
|
|
1478
|
-
retryThrottledRequestMaxTimes
|
|
1513
|
+
retryThrottledRequestMaxTimes,
|
|
1514
|
+
retryNetworkErrorMaxTimes
|
|
1479
1515
|
})
|
|
1480
1516
|
.then((groupInfo) => new UploadcareGroup(groupInfo, files))
|
|
1481
1517
|
.then((group) => {
|
|
@@ -1548,4 +1584,4 @@ class UploadClient {
|
|
|
1548
1584
|
}
|
|
1549
1585
|
}
|
|
1550
1586
|
|
|
1551
|
-
export { UploadClient, UploadClientError, UploadcareFile, UploadcareGroup, base, fromUrl, fromUrlStatus, getUserAgent$1 as getUserAgent, group, groupInfo, info, multipartComplete, multipartStart, multipartUpload, uploadDirect, uploadFile, uploadFileGroup, uploadFromUploaded, uploadFromUrl, uploadMultipart };
|
|
1587
|
+
export { UploadClient, UploadClientError, UploadcareFile, UploadcareGroup, UploadcareNetworkError, base, fromUrl, fromUrlStatus, getUserAgent$1 as getUserAgent, group, groupInfo, info, multipartComplete, multipartStart, multipartUpload, uploadDirect, uploadFile, uploadFileGroup, uploadFromUploaded, uploadFromUrl, uploadMultipart };
|