@openeo/js-client 2.5.1 → 2.7.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/LICENSE +201 -201
- package/README.md +94 -84
- package/openeo.d.ts +310 -72
- package/openeo.js +5412 -5191
- package/openeo.min.js +1 -1
- package/package.json +72 -70
- package/src/authprovider.js +147 -138
- package/src/baseentity.js +162 -162
- package/src/basicprovider.js +69 -48
- package/src/browser.js +168 -168
- package/src/builder/builder.js +400 -400
- package/src/builder/formula.js +211 -211
- package/src/builder/node.js +268 -268
- package/src/builder/parameter.js +144 -144
- package/src/builder/tapdigit.js +489 -489
- package/src/capabilities.js +274 -220
- package/src/connection.js +1290 -1211
- package/src/env.js +16 -6
- package/src/filetypes.js +111 -111
- package/src/job.js +323 -322
- package/src/logs.js +109 -68
- package/src/node.js +168 -168
- package/src/oidcprovider.js +387 -375
- package/src/openeo.js +137 -138
- package/src/pages.js +349 -0
- package/src/service.js +222 -221
- package/src/typedefs.js +271 -243
- package/src/userfile.js +128 -128
- package/src/userprocess.js +166 -166
package/src/connection.js
CHANGED
|
@@ -1,1211 +1,1290 @@
|
|
|
1
|
-
const Environment = require('./env');
|
|
2
|
-
const Utils = require('@openeo/js-commons/src/utils');
|
|
3
|
-
const ProcessRegistry = require('@openeo/js-commons/src/processRegistry');
|
|
4
|
-
const axios = require('axios')
|
|
5
|
-
const StacMigrate = require('@radiantearth/stac-migrate');
|
|
6
|
-
|
|
7
|
-
const AuthProvider = require('./authprovider');
|
|
8
|
-
const BasicProvider = require('./basicprovider');
|
|
9
|
-
const OidcProvider = require('./oidcprovider');
|
|
10
|
-
|
|
11
|
-
const Capabilities = require('./capabilities');
|
|
12
|
-
const FileTypes = require('./filetypes');
|
|
13
|
-
const UserFile = require('./userfile');
|
|
14
|
-
const Job = require('./job');
|
|
15
|
-
const UserProcess = require('./userprocess');
|
|
16
|
-
const Service = require('./service');
|
|
17
|
-
|
|
18
|
-
const Builder = require('./builder/builder');
|
|
19
|
-
const BuilderNode = require('./builder/node');
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
*
|
|
45
|
-
*
|
|
46
|
-
* @
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
*
|
|
52
|
-
*
|
|
53
|
-
* @
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
*
|
|
59
|
-
*
|
|
60
|
-
* @
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
*
|
|
66
|
-
*
|
|
67
|
-
* @
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
*
|
|
73
|
-
*
|
|
74
|
-
* @
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
*
|
|
80
|
-
*
|
|
81
|
-
* @
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
*
|
|
87
|
-
*
|
|
88
|
-
* @
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
*
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
*
|
|
169
|
-
*
|
|
170
|
-
* @
|
|
171
|
-
*/
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
*
|
|
179
|
-
*
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
*
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
*
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
|
|
212
|
-
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
*
|
|
223
|
-
*
|
|
224
|
-
*
|
|
225
|
-
*
|
|
226
|
-
*
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
*
|
|
238
|
-
*
|
|
239
|
-
*
|
|
240
|
-
*
|
|
241
|
-
* @
|
|
242
|
-
* @
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
*
|
|
250
|
-
*
|
|
251
|
-
*
|
|
252
|
-
*
|
|
253
|
-
* @
|
|
254
|
-
* @
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
|
|
281
|
-
|
|
282
|
-
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
}
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
|
|
301
|
-
|
|
302
|
-
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
|
|
311
|
-
|
|
312
|
-
|
|
313
|
-
|
|
314
|
-
|
|
315
|
-
*
|
|
316
|
-
*
|
|
317
|
-
*
|
|
318
|
-
*
|
|
319
|
-
*
|
|
320
|
-
*
|
|
321
|
-
*
|
|
322
|
-
*
|
|
323
|
-
* @
|
|
324
|
-
* @
|
|
325
|
-
* @
|
|
326
|
-
*/
|
|
327
|
-
|
|
328
|
-
|
|
329
|
-
|
|
330
|
-
|
|
331
|
-
|
|
332
|
-
|
|
333
|
-
|
|
334
|
-
|
|
335
|
-
|
|
336
|
-
|
|
337
|
-
|
|
338
|
-
|
|
339
|
-
|
|
340
|
-
|
|
341
|
-
|
|
342
|
-
|
|
343
|
-
|
|
344
|
-
|
|
345
|
-
|
|
346
|
-
*
|
|
347
|
-
*
|
|
348
|
-
|
|
349
|
-
|
|
350
|
-
|
|
351
|
-
|
|
352
|
-
|
|
353
|
-
|
|
354
|
-
|
|
355
|
-
|
|
356
|
-
|
|
357
|
-
|
|
358
|
-
|
|
359
|
-
|
|
360
|
-
|
|
361
|
-
|
|
362
|
-
|
|
363
|
-
|
|
364
|
-
|
|
365
|
-
|
|
366
|
-
|
|
367
|
-
|
|
368
|
-
|
|
369
|
-
|
|
370
|
-
|
|
371
|
-
|
|
372
|
-
|
|
373
|
-
*
|
|
374
|
-
*
|
|
375
|
-
* @
|
|
376
|
-
* @param {string}
|
|
377
|
-
* @returns {Promise
|
|
378
|
-
* @throws {Error}
|
|
379
|
-
* @see Connection#listProcesses
|
|
380
|
-
*/
|
|
381
|
-
async
|
|
382
|
-
|
|
383
|
-
|
|
384
|
-
|
|
385
|
-
|
|
386
|
-
|
|
387
|
-
|
|
388
|
-
|
|
389
|
-
|
|
390
|
-
|
|
391
|
-
|
|
392
|
-
|
|
393
|
-
|
|
394
|
-
|
|
395
|
-
|
|
396
|
-
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
|
|
400
|
-
|
|
401
|
-
|
|
402
|
-
|
|
403
|
-
|
|
404
|
-
|
|
405
|
-
|
|
406
|
-
|
|
407
|
-
|
|
408
|
-
|
|
409
|
-
|
|
410
|
-
|
|
411
|
-
|
|
412
|
-
|
|
413
|
-
|
|
414
|
-
|
|
415
|
-
|
|
416
|
-
|
|
417
|
-
|
|
418
|
-
|
|
419
|
-
|
|
420
|
-
|
|
421
|
-
|
|
422
|
-
|
|
423
|
-
|
|
424
|
-
|
|
425
|
-
|
|
426
|
-
|
|
427
|
-
|
|
428
|
-
|
|
429
|
-
|
|
430
|
-
|
|
431
|
-
|
|
432
|
-
|
|
433
|
-
|
|
434
|
-
|
|
435
|
-
|
|
436
|
-
|
|
437
|
-
|
|
438
|
-
|
|
439
|
-
|
|
440
|
-
|
|
441
|
-
|
|
442
|
-
|
|
443
|
-
|
|
444
|
-
|
|
445
|
-
|
|
446
|
-
|
|
447
|
-
|
|
448
|
-
|
|
449
|
-
|
|
450
|
-
|
|
451
|
-
|
|
452
|
-
|
|
453
|
-
|
|
454
|
-
*
|
|
455
|
-
*
|
|
456
|
-
*
|
|
457
|
-
*
|
|
458
|
-
*
|
|
459
|
-
*
|
|
460
|
-
* @
|
|
461
|
-
|
|
462
|
-
|
|
463
|
-
|
|
464
|
-
|
|
465
|
-
|
|
466
|
-
|
|
467
|
-
|
|
468
|
-
|
|
469
|
-
|
|
470
|
-
|
|
471
|
-
|
|
472
|
-
|
|
473
|
-
|
|
474
|
-
|
|
475
|
-
|
|
476
|
-
|
|
477
|
-
|
|
478
|
-
|
|
479
|
-
|
|
480
|
-
*
|
|
481
|
-
*
|
|
482
|
-
*
|
|
483
|
-
*
|
|
484
|
-
*
|
|
485
|
-
* @
|
|
486
|
-
* @see
|
|
487
|
-
*/
|
|
488
|
-
|
|
489
|
-
|
|
490
|
-
|
|
491
|
-
|
|
492
|
-
|
|
493
|
-
|
|
494
|
-
|
|
495
|
-
|
|
496
|
-
|
|
497
|
-
|
|
498
|
-
|
|
499
|
-
|
|
500
|
-
}
|
|
501
|
-
|
|
502
|
-
/**
|
|
503
|
-
*
|
|
504
|
-
*
|
|
505
|
-
*
|
|
506
|
-
*
|
|
507
|
-
* @
|
|
508
|
-
|
|
509
|
-
|
|
510
|
-
|
|
511
|
-
|
|
512
|
-
|
|
513
|
-
|
|
514
|
-
|
|
515
|
-
|
|
516
|
-
|
|
517
|
-
|
|
518
|
-
|
|
519
|
-
|
|
520
|
-
*
|
|
521
|
-
*
|
|
522
|
-
*
|
|
523
|
-
|
|
524
|
-
|
|
525
|
-
|
|
526
|
-
|
|
527
|
-
|
|
528
|
-
|
|
529
|
-
|
|
530
|
-
|
|
531
|
-
*
|
|
532
|
-
*
|
|
533
|
-
* @param {
|
|
534
|
-
*/
|
|
535
|
-
|
|
536
|
-
|
|
537
|
-
|
|
538
|
-
|
|
539
|
-
|
|
540
|
-
|
|
541
|
-
|
|
542
|
-
*
|
|
543
|
-
|
|
544
|
-
|
|
545
|
-
|
|
546
|
-
|
|
547
|
-
|
|
548
|
-
|
|
549
|
-
*
|
|
550
|
-
*
|
|
551
|
-
|
|
552
|
-
|
|
553
|
-
|
|
554
|
-
|
|
555
|
-
|
|
556
|
-
|
|
557
|
-
|
|
558
|
-
|
|
559
|
-
|
|
560
|
-
|
|
561
|
-
|
|
562
|
-
|
|
563
|
-
|
|
564
|
-
|
|
565
|
-
|
|
566
|
-
|
|
567
|
-
|
|
568
|
-
|
|
569
|
-
|
|
570
|
-
|
|
571
|
-
|
|
572
|
-
|
|
573
|
-
|
|
574
|
-
|
|
575
|
-
*
|
|
576
|
-
*
|
|
577
|
-
* @param {
|
|
578
|
-
|
|
579
|
-
|
|
580
|
-
|
|
581
|
-
|
|
582
|
-
|
|
583
|
-
|
|
584
|
-
|
|
585
|
-
|
|
586
|
-
|
|
587
|
-
|
|
588
|
-
|
|
589
|
-
this.
|
|
590
|
-
|
|
591
|
-
|
|
592
|
-
|
|
593
|
-
|
|
594
|
-
|
|
595
|
-
*
|
|
596
|
-
*
|
|
597
|
-
*
|
|
598
|
-
*
|
|
599
|
-
*
|
|
600
|
-
*
|
|
601
|
-
|
|
602
|
-
|
|
603
|
-
|
|
604
|
-
|
|
605
|
-
|
|
606
|
-
|
|
607
|
-
|
|
608
|
-
|
|
609
|
-
|
|
610
|
-
|
|
611
|
-
|
|
612
|
-
|
|
613
|
-
|
|
614
|
-
|
|
615
|
-
|
|
616
|
-
|
|
617
|
-
|
|
618
|
-
|
|
619
|
-
|
|
620
|
-
|
|
621
|
-
|
|
622
|
-
|
|
623
|
-
*
|
|
624
|
-
*
|
|
625
|
-
* @
|
|
626
|
-
* @
|
|
627
|
-
|
|
628
|
-
|
|
629
|
-
|
|
630
|
-
|
|
631
|
-
|
|
632
|
-
|
|
633
|
-
|
|
634
|
-
*
|
|
635
|
-
*
|
|
636
|
-
*
|
|
637
|
-
*
|
|
638
|
-
* @
|
|
639
|
-
|
|
640
|
-
|
|
641
|
-
|
|
642
|
-
|
|
643
|
-
|
|
644
|
-
|
|
645
|
-
|
|
646
|
-
|
|
647
|
-
|
|
648
|
-
|
|
649
|
-
|
|
650
|
-
|
|
651
|
-
|
|
652
|
-
|
|
653
|
-
|
|
654
|
-
|
|
655
|
-
|
|
656
|
-
*
|
|
657
|
-
*
|
|
658
|
-
* @
|
|
659
|
-
* @
|
|
660
|
-
* @
|
|
661
|
-
*/
|
|
662
|
-
|
|
663
|
-
|
|
664
|
-
|
|
665
|
-
|
|
666
|
-
|
|
667
|
-
*
|
|
668
|
-
*
|
|
669
|
-
*
|
|
670
|
-
*
|
|
671
|
-
* @
|
|
672
|
-
* @
|
|
673
|
-
* @
|
|
674
|
-
|
|
675
|
-
|
|
676
|
-
|
|
677
|
-
|
|
678
|
-
|
|
679
|
-
|
|
680
|
-
|
|
681
|
-
|
|
682
|
-
}
|
|
683
|
-
|
|
684
|
-
|
|
685
|
-
|
|
686
|
-
|
|
687
|
-
|
|
688
|
-
|
|
689
|
-
|
|
690
|
-
|
|
691
|
-
|
|
692
|
-
*
|
|
693
|
-
*
|
|
694
|
-
|
|
695
|
-
|
|
696
|
-
|
|
697
|
-
|
|
698
|
-
|
|
699
|
-
|
|
700
|
-
|
|
701
|
-
|
|
702
|
-
|
|
703
|
-
|
|
704
|
-
|
|
705
|
-
|
|
706
|
-
|
|
707
|
-
|
|
708
|
-
|
|
709
|
-
|
|
710
|
-
|
|
711
|
-
|
|
712
|
-
|
|
713
|
-
|
|
714
|
-
|
|
715
|
-
|
|
716
|
-
|
|
717
|
-
|
|
718
|
-
|
|
719
|
-
|
|
720
|
-
|
|
721
|
-
|
|
722
|
-
|
|
723
|
-
|
|
724
|
-
|
|
725
|
-
|
|
726
|
-
|
|
727
|
-
|
|
728
|
-
|
|
729
|
-
|
|
730
|
-
|
|
731
|
-
|
|
732
|
-
|
|
733
|
-
|
|
734
|
-
|
|
735
|
-
|
|
736
|
-
|
|
737
|
-
|
|
738
|
-
|
|
739
|
-
|
|
740
|
-
|
|
741
|
-
|
|
742
|
-
|
|
743
|
-
|
|
744
|
-
|
|
745
|
-
*
|
|
746
|
-
*
|
|
747
|
-
* @
|
|
748
|
-
* @param {
|
|
749
|
-
* @returns {Promise<UserProcess
|
|
750
|
-
* @throws {Error}
|
|
751
|
-
*/
|
|
752
|
-
async
|
|
753
|
-
|
|
754
|
-
return await
|
|
755
|
-
}
|
|
756
|
-
|
|
757
|
-
/**
|
|
758
|
-
*
|
|
759
|
-
*
|
|
760
|
-
* @
|
|
761
|
-
* @
|
|
762
|
-
|
|
763
|
-
|
|
764
|
-
|
|
765
|
-
|
|
766
|
-
|
|
767
|
-
|
|
768
|
-
|
|
769
|
-
|
|
770
|
-
|
|
771
|
-
*
|
|
772
|
-
*
|
|
773
|
-
*
|
|
774
|
-
*
|
|
775
|
-
|
|
776
|
-
|
|
777
|
-
|
|
778
|
-
|
|
779
|
-
|
|
780
|
-
|
|
781
|
-
|
|
782
|
-
|
|
783
|
-
|
|
784
|
-
|
|
785
|
-
|
|
786
|
-
|
|
787
|
-
|
|
788
|
-
|
|
789
|
-
|
|
790
|
-
|
|
791
|
-
|
|
792
|
-
|
|
793
|
-
|
|
794
|
-
|
|
795
|
-
|
|
796
|
-
|
|
797
|
-
|
|
798
|
-
|
|
799
|
-
|
|
800
|
-
|
|
801
|
-
|
|
802
|
-
|
|
803
|
-
|
|
804
|
-
|
|
805
|
-
|
|
806
|
-
|
|
807
|
-
|
|
808
|
-
|
|
809
|
-
|
|
810
|
-
}
|
|
811
|
-
|
|
812
|
-
|
|
813
|
-
|
|
814
|
-
|
|
815
|
-
|
|
816
|
-
|
|
817
|
-
|
|
818
|
-
|
|
819
|
-
|
|
820
|
-
|
|
821
|
-
|
|
822
|
-
|
|
823
|
-
|
|
824
|
-
|
|
825
|
-
|
|
826
|
-
|
|
827
|
-
|
|
828
|
-
|
|
829
|
-
|
|
830
|
-
|
|
831
|
-
|
|
832
|
-
|
|
833
|
-
|
|
834
|
-
|
|
835
|
-
|
|
836
|
-
|
|
837
|
-
|
|
838
|
-
|
|
839
|
-
|
|
840
|
-
|
|
841
|
-
|
|
842
|
-
|
|
843
|
-
|
|
844
|
-
|
|
845
|
-
|
|
846
|
-
|
|
847
|
-
|
|
848
|
-
|
|
849
|
-
|
|
850
|
-
|
|
851
|
-
|
|
852
|
-
|
|
853
|
-
*
|
|
854
|
-
*
|
|
855
|
-
*
|
|
856
|
-
*
|
|
857
|
-
|
|
858
|
-
|
|
859
|
-
|
|
860
|
-
|
|
861
|
-
|
|
862
|
-
|
|
863
|
-
|
|
864
|
-
|
|
865
|
-
|
|
866
|
-
|
|
867
|
-
|
|
868
|
-
|
|
869
|
-
|
|
870
|
-
|
|
871
|
-
|
|
872
|
-
|
|
873
|
-
|
|
874
|
-
|
|
875
|
-
|
|
876
|
-
*
|
|
877
|
-
*
|
|
878
|
-
* @
|
|
879
|
-
* @param {
|
|
880
|
-
* @returns {Promise<Job
|
|
881
|
-
* @throws {Error}
|
|
882
|
-
*/
|
|
883
|
-
async
|
|
884
|
-
|
|
885
|
-
|
|
886
|
-
|
|
887
|
-
|
|
888
|
-
|
|
889
|
-
|
|
890
|
-
|
|
891
|
-
|
|
892
|
-
|
|
893
|
-
|
|
894
|
-
|
|
895
|
-
|
|
896
|
-
|
|
897
|
-
|
|
898
|
-
|
|
899
|
-
|
|
900
|
-
|
|
901
|
-
|
|
902
|
-
|
|
903
|
-
|
|
904
|
-
|
|
905
|
-
*
|
|
906
|
-
*
|
|
907
|
-
* @
|
|
908
|
-
* @param {string}
|
|
909
|
-
* @returns {Promise<Job>} The batch job.
|
|
910
|
-
* @throws {Error}
|
|
911
|
-
*/
|
|
912
|
-
async
|
|
913
|
-
|
|
914
|
-
|
|
915
|
-
|
|
916
|
-
|
|
917
|
-
|
|
918
|
-
|
|
919
|
-
|
|
920
|
-
|
|
921
|
-
|
|
922
|
-
|
|
923
|
-
|
|
924
|
-
|
|
925
|
-
|
|
926
|
-
|
|
927
|
-
|
|
928
|
-
|
|
929
|
-
|
|
930
|
-
|
|
931
|
-
|
|
932
|
-
|
|
933
|
-
|
|
934
|
-
|
|
935
|
-
|
|
936
|
-
|
|
937
|
-
|
|
938
|
-
*
|
|
939
|
-
*
|
|
940
|
-
|
|
941
|
-
|
|
942
|
-
|
|
943
|
-
|
|
944
|
-
|
|
945
|
-
|
|
946
|
-
|
|
947
|
-
*
|
|
948
|
-
*
|
|
949
|
-
* @
|
|
950
|
-
* @
|
|
951
|
-
* @
|
|
952
|
-
|
|
953
|
-
|
|
954
|
-
|
|
955
|
-
|
|
956
|
-
|
|
957
|
-
|
|
958
|
-
|
|
959
|
-
|
|
960
|
-
|
|
961
|
-
|
|
962
|
-
|
|
963
|
-
|
|
964
|
-
|
|
965
|
-
|
|
966
|
-
|
|
967
|
-
|
|
968
|
-
|
|
969
|
-
|
|
970
|
-
|
|
971
|
-
|
|
972
|
-
|
|
973
|
-
|
|
974
|
-
|
|
975
|
-
|
|
976
|
-
|
|
977
|
-
*
|
|
978
|
-
*
|
|
979
|
-
* @
|
|
980
|
-
* @param {
|
|
981
|
-
* @
|
|
982
|
-
* @
|
|
983
|
-
|
|
984
|
-
|
|
985
|
-
|
|
986
|
-
|
|
987
|
-
|
|
988
|
-
|
|
989
|
-
|
|
990
|
-
|
|
991
|
-
|
|
992
|
-
|
|
993
|
-
|
|
994
|
-
|
|
995
|
-
|
|
996
|
-
|
|
997
|
-
|
|
998
|
-
|
|
999
|
-
|
|
1000
|
-
|
|
1001
|
-
|
|
1002
|
-
|
|
1003
|
-
|
|
1004
|
-
|
|
1005
|
-
|
|
1006
|
-
|
|
1007
|
-
|
|
1008
|
-
|
|
1009
|
-
*
|
|
1010
|
-
*
|
|
1011
|
-
* @
|
|
1012
|
-
* @
|
|
1013
|
-
|
|
1014
|
-
|
|
1015
|
-
|
|
1016
|
-
|
|
1017
|
-
|
|
1018
|
-
|
|
1019
|
-
|
|
1020
|
-
|
|
1021
|
-
|
|
1022
|
-
|
|
1023
|
-
|
|
1024
|
-
|
|
1025
|
-
*
|
|
1026
|
-
*
|
|
1027
|
-
* @
|
|
1028
|
-
* @
|
|
1029
|
-
|
|
1030
|
-
|
|
1031
|
-
|
|
1032
|
-
|
|
1033
|
-
|
|
1034
|
-
|
|
1035
|
-
|
|
1036
|
-
|
|
1037
|
-
|
|
1038
|
-
|
|
1039
|
-
|
|
1040
|
-
|
|
1041
|
-
|
|
1042
|
-
|
|
1043
|
-
|
|
1044
|
-
|
|
1045
|
-
|
|
1046
|
-
|
|
1047
|
-
|
|
1048
|
-
|
|
1049
|
-
|
|
1050
|
-
|
|
1051
|
-
|
|
1052
|
-
|
|
1053
|
-
|
|
1054
|
-
|
|
1055
|
-
|
|
1056
|
-
|
|
1057
|
-
|
|
1058
|
-
|
|
1059
|
-
|
|
1060
|
-
|
|
1061
|
-
|
|
1062
|
-
|
|
1063
|
-
|
|
1064
|
-
|
|
1065
|
-
|
|
1066
|
-
|
|
1067
|
-
|
|
1068
|
-
|
|
1069
|
-
|
|
1070
|
-
|
|
1071
|
-
|
|
1072
|
-
|
|
1073
|
-
|
|
1074
|
-
|
|
1075
|
-
|
|
1076
|
-
|
|
1077
|
-
|
|
1078
|
-
|
|
1079
|
-
|
|
1080
|
-
|
|
1081
|
-
|
|
1082
|
-
|
|
1083
|
-
|
|
1084
|
-
|
|
1085
|
-
|
|
1086
|
-
|
|
1087
|
-
|
|
1088
|
-
|
|
1089
|
-
|
|
1090
|
-
*
|
|
1091
|
-
*
|
|
1092
|
-
|
|
1093
|
-
|
|
1094
|
-
|
|
1095
|
-
|
|
1096
|
-
|
|
1097
|
-
|
|
1098
|
-
|
|
1099
|
-
|
|
1100
|
-
|
|
1101
|
-
|
|
1102
|
-
|
|
1103
|
-
|
|
1104
|
-
|
|
1105
|
-
|
|
1106
|
-
|
|
1107
|
-
|
|
1108
|
-
*
|
|
1109
|
-
*
|
|
1110
|
-
* @
|
|
1111
|
-
* @
|
|
1112
|
-
* @param {string}
|
|
1113
|
-
* @
|
|
1114
|
-
* @
|
|
1115
|
-
|
|
1116
|
-
|
|
1117
|
-
|
|
1118
|
-
|
|
1119
|
-
|
|
1120
|
-
|
|
1121
|
-
|
|
1122
|
-
|
|
1123
|
-
|
|
1124
|
-
|
|
1125
|
-
|
|
1126
|
-
|
|
1127
|
-
|
|
1128
|
-
|
|
1129
|
-
*
|
|
1130
|
-
*
|
|
1131
|
-
* @
|
|
1132
|
-
|
|
1133
|
-
|
|
1134
|
-
|
|
1135
|
-
|
|
1136
|
-
|
|
1137
|
-
|
|
1138
|
-
|
|
1139
|
-
|
|
1140
|
-
|
|
1141
|
-
|
|
1142
|
-
|
|
1143
|
-
|
|
1144
|
-
|
|
1145
|
-
|
|
1146
|
-
|
|
1147
|
-
*
|
|
1148
|
-
*
|
|
1149
|
-
*
|
|
1150
|
-
*
|
|
1151
|
-
*
|
|
1152
|
-
*
|
|
1153
|
-
*
|
|
1154
|
-
*
|
|
1155
|
-
|
|
1156
|
-
|
|
1157
|
-
|
|
1158
|
-
|
|
1159
|
-
|
|
1160
|
-
|
|
1161
|
-
|
|
1162
|
-
|
|
1163
|
-
|
|
1164
|
-
|
|
1165
|
-
|
|
1166
|
-
|
|
1167
|
-
|
|
1168
|
-
|
|
1169
|
-
|
|
1170
|
-
|
|
1171
|
-
|
|
1172
|
-
|
|
1173
|
-
|
|
1174
|
-
|
|
1175
|
-
|
|
1176
|
-
|
|
1177
|
-
|
|
1178
|
-
|
|
1179
|
-
|
|
1180
|
-
|
|
1181
|
-
|
|
1182
|
-
|
|
1183
|
-
|
|
1184
|
-
|
|
1185
|
-
|
|
1186
|
-
|
|
1187
|
-
|
|
1188
|
-
|
|
1189
|
-
|
|
1190
|
-
|
|
1191
|
-
|
|
1192
|
-
|
|
1193
|
-
|
|
1194
|
-
|
|
1195
|
-
|
|
1196
|
-
|
|
1197
|
-
|
|
1198
|
-
|
|
1199
|
-
|
|
1200
|
-
|
|
1201
|
-
|
|
1202
|
-
|
|
1203
|
-
|
|
1204
|
-
|
|
1205
|
-
|
|
1206
|
-
|
|
1207
|
-
}
|
|
1208
|
-
|
|
1209
|
-
|
|
1210
|
-
|
|
1211
|
-
|
|
1
|
+
const Environment = require('./env');
|
|
2
|
+
const Utils = require('@openeo/js-commons/src/utils');
|
|
3
|
+
const ProcessRegistry = require('@openeo/js-commons/src/processRegistry');
|
|
4
|
+
const axios = require('axios');
|
|
5
|
+
const StacMigrate = require('@radiantearth/stac-migrate');
|
|
6
|
+
|
|
7
|
+
const AuthProvider = require('./authprovider');
|
|
8
|
+
const BasicProvider = require('./basicprovider');
|
|
9
|
+
const OidcProvider = require('./oidcprovider');
|
|
10
|
+
|
|
11
|
+
const Capabilities = require('./capabilities');
|
|
12
|
+
const FileTypes = require('./filetypes');
|
|
13
|
+
const UserFile = require('./userfile');
|
|
14
|
+
const Job = require('./job');
|
|
15
|
+
const UserProcess = require('./userprocess');
|
|
16
|
+
const Service = require('./service');
|
|
17
|
+
|
|
18
|
+
const Builder = require('./builder/builder');
|
|
19
|
+
const BuilderNode = require('./builder/node');
|
|
20
|
+
const { CollectionPages, ItemPages, JobPages, ProcessPages, ServicePages, UserFilePages } = require('./pages');
|
|
21
|
+
|
|
22
|
+
const CONFORMANCE_RELS = [
|
|
23
|
+
'conformance',
|
|
24
|
+
'http://www.opengis.net/def/rel/ogc/1.0/conformance'
|
|
25
|
+
];
|
|
26
|
+
|
|
27
|
+
/**
|
|
28
|
+
* A connection to a back-end.
|
|
29
|
+
*/
|
|
30
|
+
class Connection {
|
|
31
|
+
|
|
32
|
+
/**
|
|
33
|
+
* Creates a new Connection.
|
|
34
|
+
*
|
|
35
|
+
* @param {string} baseUrl - The versioned URL or the back-end instance.
|
|
36
|
+
* @param {Options} [options={}] - Additional options for the connection.
|
|
37
|
+
* @param {?string} [url=null] - User-provided URL of the backend connected to.
|
|
38
|
+
*/
|
|
39
|
+
constructor(baseUrl, options = {}, url = null) {
|
|
40
|
+
/**
|
|
41
|
+
* User-provided URL of the backend connected to.
|
|
42
|
+
*
|
|
43
|
+
* `null` if not given and the connection was directly made to a versioned instance of the back-end.
|
|
44
|
+
*
|
|
45
|
+
* @protected
|
|
46
|
+
* @type {string | null}
|
|
47
|
+
*/
|
|
48
|
+
this.url = url;
|
|
49
|
+
/**
|
|
50
|
+
* The versioned URL or the back-end instance.
|
|
51
|
+
*
|
|
52
|
+
* @protected
|
|
53
|
+
* @type {string}
|
|
54
|
+
*/
|
|
55
|
+
this.baseUrl = Utils.normalizeUrl(baseUrl);
|
|
56
|
+
/**
|
|
57
|
+
* Auth Provider cache
|
|
58
|
+
*
|
|
59
|
+
* @protected
|
|
60
|
+
* @type {Array.<AuthProvider> | null}
|
|
61
|
+
*/
|
|
62
|
+
this.authProviderList = null;
|
|
63
|
+
/**
|
|
64
|
+
* Current auth provider
|
|
65
|
+
*
|
|
66
|
+
* @protected
|
|
67
|
+
* @type {AuthProvider | null}
|
|
68
|
+
*/
|
|
69
|
+
this.authProvider = null;
|
|
70
|
+
/**
|
|
71
|
+
* Capability cache
|
|
72
|
+
*
|
|
73
|
+
* @protected
|
|
74
|
+
* @type {Capabilities | null}
|
|
75
|
+
*/
|
|
76
|
+
this.capabilitiesObject = null;
|
|
77
|
+
/**
|
|
78
|
+
* Listeners for events.
|
|
79
|
+
*
|
|
80
|
+
* @protected
|
|
81
|
+
* @type {object.<string|Function>}
|
|
82
|
+
*/
|
|
83
|
+
this.listeners = {};
|
|
84
|
+
/**
|
|
85
|
+
* Additional options for the connection.
|
|
86
|
+
*
|
|
87
|
+
* @protected
|
|
88
|
+
* @type {Options}
|
|
89
|
+
*/
|
|
90
|
+
this.options = options;
|
|
91
|
+
/**
|
|
92
|
+
* Process cache
|
|
93
|
+
*
|
|
94
|
+
* @protected
|
|
95
|
+
* @type {ProcessRegistry}
|
|
96
|
+
*/
|
|
97
|
+
this.processes = new ProcessRegistry([], Boolean(options.addNamespaceToProcess));
|
|
98
|
+
this.processes.listeners.push((...args) => this.emit('processesChanged', ...args));
|
|
99
|
+
}
|
|
100
|
+
|
|
101
|
+
/**
|
|
102
|
+
* Initializes the connection by requesting the capabilities.
|
|
103
|
+
*
|
|
104
|
+
* @async
|
|
105
|
+
* @protected
|
|
106
|
+
* @returns {Promise<Capabilities>} Capabilities
|
|
107
|
+
* @throws {Error}
|
|
108
|
+
*/
|
|
109
|
+
async init() {
|
|
110
|
+
const response = await this._get('/');
|
|
111
|
+
const data = Object.assign({}, response.data);
|
|
112
|
+
data.links = this.makeLinksAbsolute(data.links, response);
|
|
113
|
+
|
|
114
|
+
if (!Array.isArray(data.conformsTo) && Array.isArray(data.links)) {
|
|
115
|
+
const conformanceLink = this._getLinkHref(data.links, CONFORMANCE_RELS);
|
|
116
|
+
if (conformanceLink) {
|
|
117
|
+
const response2 = await this._get(conformanceLink);
|
|
118
|
+
if (Utils.isObject(response2.data) && Array.isArray(response2.data.conformsTo)) {
|
|
119
|
+
data.conformsTo = response2.data.conformsTo;
|
|
120
|
+
}
|
|
121
|
+
}
|
|
122
|
+
}
|
|
123
|
+
|
|
124
|
+
this.capabilitiesObject = new Capabilities(data);
|
|
125
|
+
return this.capabilitiesObject;
|
|
126
|
+
}
|
|
127
|
+
|
|
128
|
+
/**
|
|
129
|
+
* Refresh the cache for processes.
|
|
130
|
+
*
|
|
131
|
+
* @async
|
|
132
|
+
* @protected
|
|
133
|
+
* @returns {Promise}
|
|
134
|
+
*/
|
|
135
|
+
async refreshProcessCache() {
|
|
136
|
+
if (this.processes.count() === 0) {
|
|
137
|
+
return;
|
|
138
|
+
}
|
|
139
|
+
const promises = this.processes.namespaces().map(namespace => {
|
|
140
|
+
let fn = () => Promise.resolve();
|
|
141
|
+
if (namespace === 'user') {
|
|
142
|
+
const userProcesses = this.processes.namespace('user');
|
|
143
|
+
if (!this.isAuthenticated()) {
|
|
144
|
+
fn = () => (this.processes.remove(null, 'user') ? Promise.resolve() : Promise.reject(new Error("Can't clear user processes")));
|
|
145
|
+
}
|
|
146
|
+
else if (this.capabilities().hasFeature('listUserProcesses')) {
|
|
147
|
+
fn = () => this.listUserProcesses(userProcesses);
|
|
148
|
+
}
|
|
149
|
+
}
|
|
150
|
+
else if (this.capabilities().hasFeature('listProcesses')) {
|
|
151
|
+
fn = () => this.listProcesses(namespace);
|
|
152
|
+
}
|
|
153
|
+
return fn().catch(error => console.warn(`Could not update processes for namespace '${namespace}' due to an error: ${error.message}`));
|
|
154
|
+
});
|
|
155
|
+
return await Promise.all(promises);
|
|
156
|
+
}
|
|
157
|
+
|
|
158
|
+
/**
|
|
159
|
+
* Returns the URL of the versioned back-end instance currently connected to.
|
|
160
|
+
*
|
|
161
|
+
* @returns {string} The versioned URL or the back-end instance.
|
|
162
|
+
*/
|
|
163
|
+
getBaseUrl() {
|
|
164
|
+
return this.baseUrl;
|
|
165
|
+
}
|
|
166
|
+
|
|
167
|
+
/**
|
|
168
|
+
* Returns the user-provided URL of the back-end currently connected to.
|
|
169
|
+
*
|
|
170
|
+
* @returns {string} The URL or the back-end.
|
|
171
|
+
*/
|
|
172
|
+
getUrl() {
|
|
173
|
+
return this.url || this.baseUrl;
|
|
174
|
+
}
|
|
175
|
+
|
|
176
|
+
/**
|
|
177
|
+
* Returns the capabilities of the back-end.
|
|
178
|
+
*
|
|
179
|
+
* @returns {Capabilities} Capabilities
|
|
180
|
+
*/
|
|
181
|
+
capabilities() {
|
|
182
|
+
return this.capabilitiesObject;
|
|
183
|
+
}
|
|
184
|
+
|
|
185
|
+
/**
|
|
186
|
+
* List the supported output file formats.
|
|
187
|
+
*
|
|
188
|
+
* @async
|
|
189
|
+
* @returns {Promise<FileTypes>} A response compatible to the API specification.
|
|
190
|
+
* @throws {Error}
|
|
191
|
+
*/
|
|
192
|
+
async listFileTypes() {
|
|
193
|
+
const response = await this._get('/file_formats');
|
|
194
|
+
return new FileTypes(response.data);
|
|
195
|
+
}
|
|
196
|
+
|
|
197
|
+
/**
|
|
198
|
+
* List the supported secondary service types.
|
|
199
|
+
*
|
|
200
|
+
* @async
|
|
201
|
+
* @returns {Promise<object.<string, ServiceType>>} A response compatible to the API specification.
|
|
202
|
+
* @throws {Error}
|
|
203
|
+
*/
|
|
204
|
+
async listServiceTypes() {
|
|
205
|
+
const response = await this._get('/service_types');
|
|
206
|
+
return response.data;
|
|
207
|
+
}
|
|
208
|
+
|
|
209
|
+
/**
|
|
210
|
+
* List the supported UDF runtimes.
|
|
211
|
+
*
|
|
212
|
+
* @async
|
|
213
|
+
* @returns {Promise<object.<string, UdfRuntime>>} A response compatible to the API specification.
|
|
214
|
+
* @throws {Error}
|
|
215
|
+
*/
|
|
216
|
+
async listUdfRuntimes() {
|
|
217
|
+
const response = await this._get('/udf_runtimes');
|
|
218
|
+
return response.data;
|
|
219
|
+
}
|
|
220
|
+
|
|
221
|
+
/**
|
|
222
|
+
* List all collections available on the back-end.
|
|
223
|
+
*
|
|
224
|
+
* The collections returned always comply to the latest STAC version (currently 1.0.0).
|
|
225
|
+
* This function adds a self link to the response if not present.
|
|
226
|
+
*
|
|
227
|
+
* @async
|
|
228
|
+
* @returns {Promise<Collections>} A response compatible to the API specification.
|
|
229
|
+
* @throws {Error}
|
|
230
|
+
*/
|
|
231
|
+
async listCollections() {
|
|
232
|
+
const pages = this.paginateCollections(null);
|
|
233
|
+
return await pages.nextPage([], false);
|
|
234
|
+
}
|
|
235
|
+
|
|
236
|
+
/**
|
|
237
|
+
* Paginate through the collections available on the back-end.
|
|
238
|
+
*
|
|
239
|
+
* The collections returned always comply to the latest STAC version (currently 1.0.0).
|
|
240
|
+
*
|
|
241
|
+
* @param {?number} [limit=50] - The number of collections per request/page as integer. If `null`, requests all collections.
|
|
242
|
+
* @returns {CollectionPages} A paged list of collections.
|
|
243
|
+
*/
|
|
244
|
+
paginateCollections(limit = 50) {
|
|
245
|
+
return new CollectionPages(this, limit);
|
|
246
|
+
}
|
|
247
|
+
|
|
248
|
+
/**
|
|
249
|
+
* Get further information about a single collection.
|
|
250
|
+
*
|
|
251
|
+
* The collection returned always complies to the latest STAC version (currently 1.0.0).
|
|
252
|
+
*
|
|
253
|
+
* @async
|
|
254
|
+
* @param {string} collectionId - Collection ID to request further metadata for.
|
|
255
|
+
* @returns {Promise<Collection>} - A response compatible to the API specification.
|
|
256
|
+
* @throws {Error}
|
|
257
|
+
*/
|
|
258
|
+
async describeCollection(collectionId) {
|
|
259
|
+
const response = await this._get('/collections/' + collectionId);
|
|
260
|
+
if (response.data.stac_version) {
|
|
261
|
+
return StacMigrate.collection(response.data);
|
|
262
|
+
}
|
|
263
|
+
else {
|
|
264
|
+
return response.data;
|
|
265
|
+
}
|
|
266
|
+
}
|
|
267
|
+
|
|
268
|
+
/**
|
|
269
|
+
* Paginate through items for a specific collection.
|
|
270
|
+
*
|
|
271
|
+
* May not be available for all collections.
|
|
272
|
+
*
|
|
273
|
+
* The items returned always comply to the latest STAC version (currently 1.0.0).
|
|
274
|
+
*
|
|
275
|
+
* @async
|
|
276
|
+
* @param {string} collectionId - Collection ID to request items for.
|
|
277
|
+
* @param {?Array.<number>} [spatialExtent=null] - Limits the items to the given bounding box in WGS84:
|
|
278
|
+
* 1. Lower left corner, coordinate axis 1
|
|
279
|
+
* 2. Lower left corner, coordinate axis 2
|
|
280
|
+
* 3. Upper right corner, coordinate axis 1
|
|
281
|
+
* 4. Upper right corner, coordinate axis 2
|
|
282
|
+
* @param {?Array} [temporalExtent=null] - Limits the items to the specified temporal interval.
|
|
283
|
+
* The interval has to be specified as an array with exactly two elements (start, end) and
|
|
284
|
+
* each must be either an RFC 3339 compatible string or a Date object.
|
|
285
|
+
* Also supports open intervals by setting one of the boundaries to `null`, but never both.
|
|
286
|
+
* @param {?number} [limit=null] - The amount of items per request/page as integer. If `null` (default), the back-end decides.
|
|
287
|
+
* @returns {Promise<ItemPages>} A response compatible to the API specification.
|
|
288
|
+
* @throws {Error}
|
|
289
|
+
*/
|
|
290
|
+
listCollectionItems(collectionId, spatialExtent = null, temporalExtent = null, limit = null) {
|
|
291
|
+
let params = {};
|
|
292
|
+
if (Array.isArray(spatialExtent)) {
|
|
293
|
+
params.bbox = spatialExtent.join(',');
|
|
294
|
+
}
|
|
295
|
+
if (Array.isArray(temporalExtent)) {
|
|
296
|
+
params.datetime = temporalExtent
|
|
297
|
+
.map(e => {
|
|
298
|
+
if (e instanceof Date) {
|
|
299
|
+
return e.toISOString();
|
|
300
|
+
}
|
|
301
|
+
else if (typeof e === 'string') {
|
|
302
|
+
return e;
|
|
303
|
+
}
|
|
304
|
+
return '..'; // Open date range
|
|
305
|
+
})
|
|
306
|
+
.join('/');
|
|
307
|
+
}
|
|
308
|
+
if (limit > 0) {
|
|
309
|
+
params.limit = limit;
|
|
310
|
+
}
|
|
311
|
+
return new ItemPages(this, collectionId, params, limit);
|
|
312
|
+
}
|
|
313
|
+
|
|
314
|
+
/**
|
|
315
|
+
* Normalisation of the namespace to a value that is compatible with the OpenEO specs - EXPERIMENTAL.
|
|
316
|
+
*
|
|
317
|
+
* This is required to support UDP that are shared as public. These can only be executed with providing the full URL
|
|
318
|
+
* (e.g. https://<backend>/processes/<namespace>/<process_id>) as the namespace value in the processing graph. For other
|
|
319
|
+
* parts of the API (such as the listing of the processes, only the name of the namespace is required.
|
|
320
|
+
*
|
|
321
|
+
* This function will extract the short name of the namespace from a shareable URL.
|
|
322
|
+
*
|
|
323
|
+
* @protected
|
|
324
|
+
* @param {?string} namespace - Namespace of the process
|
|
325
|
+
* @returns {?string}
|
|
326
|
+
*/
|
|
327
|
+
normalizeNamespace(namespace) {
|
|
328
|
+
// The pattern in https://github.com/Open-EO/openeo-api/pull/348 doesn't include the double colon yet - the regexp may change in the future
|
|
329
|
+
const matches = namespace.match( /^https?:\/\/.*\/processes\/(@?[\w\-.~:]+)\/?/i);
|
|
330
|
+
return matches && matches.length > 1 ? matches[1] : namespace;
|
|
331
|
+
}
|
|
332
|
+
|
|
333
|
+
/**
|
|
334
|
+
* List all processes available on the back-end.
|
|
335
|
+
*
|
|
336
|
+
* Requests pre-defined processes by default.
|
|
337
|
+
* Set the namespace parameter to request processes from a specific namespace.
|
|
338
|
+
*
|
|
339
|
+
* Note: The list of namespaces can be retrieved by calling `listProcesses` without a namespace given.
|
|
340
|
+
* The namespaces are then listed in the property `namespaces`.
|
|
341
|
+
*
|
|
342
|
+
* This function adds a self link to the response if not present.
|
|
343
|
+
*
|
|
344
|
+
* @async
|
|
345
|
+
* @param {?string} [namespace=null] - Namespace of the processes (default to `null`, i.e. pre-defined processes). EXPERIMENTAL!
|
|
346
|
+
* @returns {Promise<Processes>} - A response compatible to the API specification.
|
|
347
|
+
* @throws {Error}
|
|
348
|
+
*/
|
|
349
|
+
async listProcesses(namespace = null) {
|
|
350
|
+
const pages = this.paginateProcesses(namespace);
|
|
351
|
+
return await pages.nextPage([], false);
|
|
352
|
+
}
|
|
353
|
+
|
|
354
|
+
/**
|
|
355
|
+
* Paginate through the processes available on the back-end.
|
|
356
|
+
*
|
|
357
|
+
* Requests pre-defined processes by default.
|
|
358
|
+
* Set the namespace parameter to request processes from a specific namespace.
|
|
359
|
+
*
|
|
360
|
+
* Note: The list of namespaces can be retrieved by calling `listProcesses` without a namespace given.
|
|
361
|
+
* The namespaces are then listed in the property `namespaces`.
|
|
362
|
+
*
|
|
363
|
+
* @param {?string} [namespace=null] - Namespace of the processes (default to `null`, i.e. pre-defined processes). EXPERIMENTAL!
|
|
364
|
+
* @param {?number} [limit=50] - The number of processes per request/page as integer. If `null`, requests all processes.
|
|
365
|
+
* @returns {ProcessPages} A paged list of processes.
|
|
366
|
+
*/
|
|
367
|
+
paginateProcesses(namespace = null, limit = 50) {
|
|
368
|
+
return new ProcessPages(this, limit, namespace);
|
|
369
|
+
}
|
|
370
|
+
|
|
371
|
+
/**
|
|
372
|
+
* Get information about a single process.
|
|
373
|
+
*
|
|
374
|
+
* @async
|
|
375
|
+
* @param {string} processId - Collection ID to request further metadata for.
|
|
376
|
+
* @param {?string} [namespace=null] - Namespace of the process (default to `null`, i.e. pre-defined processes). EXPERIMENTAL!
|
|
377
|
+
* @returns {Promise<?Process>} - A single process as object, or `null` if none is found.
|
|
378
|
+
* @throws {Error}
|
|
379
|
+
* @see Connection#listProcesses
|
|
380
|
+
*/
|
|
381
|
+
async describeProcess(processId, namespace = null) {
|
|
382
|
+
if (!namespace) {
|
|
383
|
+
namespace = 'backend';
|
|
384
|
+
}
|
|
385
|
+
if (namespace === 'backend') {
|
|
386
|
+
await this.listProcesses();
|
|
387
|
+
}
|
|
388
|
+
else {
|
|
389
|
+
const response = await this._get(`/processes/${this.normalizeNamespace(namespace)}/${processId}`);
|
|
390
|
+
if (!Utils.isObject(response.data) || typeof response.data.id !== 'string') {
|
|
391
|
+
throw new Error('Invalid response received for process');
|
|
392
|
+
}
|
|
393
|
+
this.processes.add(response.data, namespace);
|
|
394
|
+
}
|
|
395
|
+
return this.processes.get(processId, namespace);
|
|
396
|
+
}
|
|
397
|
+
|
|
398
|
+
/**
|
|
399
|
+
* Returns an object to simply build user-defined processes based upon pre-defined processes.
|
|
400
|
+
*
|
|
401
|
+
* @async
|
|
402
|
+
* @param {string} id - A name for the process.
|
|
403
|
+
* @returns {Promise<Builder>}
|
|
404
|
+
* @throws {Error}
|
|
405
|
+
* @see Connection#listProcesses
|
|
406
|
+
*/
|
|
407
|
+
async buildProcess(id) {
|
|
408
|
+
await this.listProcesses();
|
|
409
|
+
return new Builder(this.processes, null, id);
|
|
410
|
+
}
|
|
411
|
+
|
|
412
|
+
/**
|
|
413
|
+
* List all authentication methods supported by the back-end.
|
|
414
|
+
*
|
|
415
|
+
* @async
|
|
416
|
+
* @returns {Promise<Array.<AuthProvider>>} An array containing all supported AuthProviders (including all OIDC providers and HTTP Basic).
|
|
417
|
+
* @throws {Error}
|
|
418
|
+
* @see AuthProvider
|
|
419
|
+
*/
|
|
420
|
+
async listAuthProviders() {
|
|
421
|
+
if (this.authProviderList !== null) {
|
|
422
|
+
return this.authProviderList;
|
|
423
|
+
}
|
|
424
|
+
|
|
425
|
+
this.authProviderList = [];
|
|
426
|
+
const cap = this.capabilities();
|
|
427
|
+
|
|
428
|
+
// Add OIDC providers
|
|
429
|
+
if (cap.hasFeature('authenticateOIDC')) {
|
|
430
|
+
const res = await this._get('/credentials/oidc');
|
|
431
|
+
const oidcFactory = this.getOidcProviderFactory();
|
|
432
|
+
if (Utils.isObject(res.data) && Array.isArray(res.data.providers) && typeof oidcFactory === 'function') {
|
|
433
|
+
for(let i in res.data.providers) {
|
|
434
|
+
const obj = oidcFactory(res.data.providers[i]);
|
|
435
|
+
if (obj instanceof AuthProvider) {
|
|
436
|
+
this.authProviderList.push(obj);
|
|
437
|
+
}
|
|
438
|
+
}
|
|
439
|
+
}
|
|
440
|
+
}
|
|
441
|
+
|
|
442
|
+
// Add Basic provider
|
|
443
|
+
if (cap.hasFeature('authenticateBasic')) {
|
|
444
|
+
this.authProviderList.push(new BasicProvider(this));
|
|
445
|
+
}
|
|
446
|
+
|
|
447
|
+
return this.authProviderList;
|
|
448
|
+
}
|
|
449
|
+
|
|
450
|
+
/**
|
|
451
|
+
* This function is meant to create the OIDC providers used for authentication.
|
|
452
|
+
*
|
|
453
|
+
* The function gets passed a single argument that contains the
|
|
454
|
+
* provider information as provided by the API, e.g. having the properties
|
|
455
|
+
* `id`, `issuer`, `title` etc.
|
|
456
|
+
*
|
|
457
|
+
* The function must return an instance of AuthProvider or any derived class.
|
|
458
|
+
* May return `null` if the instance can't be created.
|
|
459
|
+
*
|
|
460
|
+
* @callback oidcProviderFactoryFunction
|
|
461
|
+
* @param {object.<string, *>} providerInfo - The provider information as provided by the API, having the properties `id`, `issuer`, `title` etc.
|
|
462
|
+
* @returns {AuthProvider | null}
|
|
463
|
+
*/
|
|
464
|
+
|
|
465
|
+
/**
|
|
466
|
+
* Sets a factory function that creates custom OpenID Connect provider instances.
|
|
467
|
+
*
|
|
468
|
+
* You only need to call this if you have implemented a new AuthProvider based
|
|
469
|
+
* on the AuthProvider interface (or OIDCProvider class), e.g. to use a
|
|
470
|
+
* OIDC library other than oidc-client-js.
|
|
471
|
+
*
|
|
472
|
+
* @param {?oidcProviderFactoryFunction} [providerFactoryFunc=null]
|
|
473
|
+
* @see AuthProvider
|
|
474
|
+
*/
|
|
475
|
+
setOidcProviderFactory(providerFactoryFunc) {
|
|
476
|
+
this.oidcProviderFactory = providerFactoryFunc;
|
|
477
|
+
}
|
|
478
|
+
|
|
479
|
+
/**
|
|
480
|
+
* Get the OpenID Connect provider factory.
|
|
481
|
+
*
|
|
482
|
+
* Returns `null` if OIDC is not supported by the client or an instance
|
|
483
|
+
* can't be created for whatever reason.
|
|
484
|
+
*
|
|
485
|
+
* @returns {oidcProviderFactoryFunction | null}
|
|
486
|
+
* @see AuthProvider
|
|
487
|
+
*/
|
|
488
|
+
getOidcProviderFactory() {
|
|
489
|
+
if (typeof this.oidcProviderFactory === 'function') {
|
|
490
|
+
return this.oidcProviderFactory;
|
|
491
|
+
}
|
|
492
|
+
else {
|
|
493
|
+
if (OidcProvider.isSupported()) {
|
|
494
|
+
return providerInfo => new OidcProvider(this, providerInfo);
|
|
495
|
+
}
|
|
496
|
+
else {
|
|
497
|
+
return null;
|
|
498
|
+
}
|
|
499
|
+
}
|
|
500
|
+
}
|
|
501
|
+
|
|
502
|
+
/**
|
|
503
|
+
* Authenticates with username and password against a back-end supporting HTTP Basic Authentication.
|
|
504
|
+
*
|
|
505
|
+
* DEPRECATED in favor of using `listAuthProviders` and `BasicProvider`.
|
|
506
|
+
*
|
|
507
|
+
* @async
|
|
508
|
+
* @deprecated
|
|
509
|
+
* @param {string} username
|
|
510
|
+
* @param {string} password
|
|
511
|
+
* @see BasicProvider
|
|
512
|
+
* @see Connection#listAuthProviders
|
|
513
|
+
*/
|
|
514
|
+
async authenticateBasic(username, password) {
|
|
515
|
+
const basic = new BasicProvider(this);
|
|
516
|
+
await basic.login(username, password);
|
|
517
|
+
}
|
|
518
|
+
|
|
519
|
+
/**
|
|
520
|
+
* Returns whether the user is authenticated (logged in) at the back-end or not.
|
|
521
|
+
*
|
|
522
|
+
* @returns {boolean} `true` if authenticated, `false` if not.
|
|
523
|
+
*/
|
|
524
|
+
isAuthenticated() {
|
|
525
|
+
return (this.authProvider !== null);
|
|
526
|
+
}
|
|
527
|
+
|
|
528
|
+
/**
|
|
529
|
+
* Emits the given event.
|
|
530
|
+
*
|
|
531
|
+
* @protected
|
|
532
|
+
* @param {string} event
|
|
533
|
+
* @param {...*} args
|
|
534
|
+
*/
|
|
535
|
+
emit(event, ...args) {
|
|
536
|
+
if (typeof this.listeners[event] === 'function') {
|
|
537
|
+
this.listeners[event](...args);
|
|
538
|
+
}
|
|
539
|
+
}
|
|
540
|
+
|
|
541
|
+
/**
|
|
542
|
+
* Registers a listener with the given event.
|
|
543
|
+
*
|
|
544
|
+
* Currently supported:
|
|
545
|
+
* - authProviderChanged(provider): Raised when the auth provider has changed.
|
|
546
|
+
* - tokenChanged(token): Raised when the access token has changed.
|
|
547
|
+
* - processesChanged(type, data, namespace): Raised when the process registry has changed (i.e. a process was added, updated or deleted).
|
|
548
|
+
*
|
|
549
|
+
* @param {string} event
|
|
550
|
+
* @param {Function} callback
|
|
551
|
+
*/
|
|
552
|
+
on(event, callback) {
|
|
553
|
+
this.listeners[event] = callback;
|
|
554
|
+
}
|
|
555
|
+
|
|
556
|
+
/**
|
|
557
|
+
* Removes a listener from the given event.
|
|
558
|
+
*
|
|
559
|
+
* @param {string} event
|
|
560
|
+
*/
|
|
561
|
+
off(event) {
|
|
562
|
+
delete this.listeners[event];
|
|
563
|
+
}
|
|
564
|
+
|
|
565
|
+
/**
|
|
566
|
+
* Returns the AuthProvider.
|
|
567
|
+
*
|
|
568
|
+
* @returns {AuthProvider | null}
|
|
569
|
+
*/
|
|
570
|
+
getAuthProvider() {
|
|
571
|
+
return this.authProvider;
|
|
572
|
+
}
|
|
573
|
+
|
|
574
|
+
/**
|
|
575
|
+
* Sets the AuthProvider.
|
|
576
|
+
*
|
|
577
|
+
* @param {AuthProvider} provider
|
|
578
|
+
*/
|
|
579
|
+
setAuthProvider(provider) {
|
|
580
|
+
if (provider === this.authProvider) {
|
|
581
|
+
return;
|
|
582
|
+
}
|
|
583
|
+
if (provider instanceof AuthProvider) {
|
|
584
|
+
this.authProvider = provider;
|
|
585
|
+
}
|
|
586
|
+
else {
|
|
587
|
+
this.authProvider = null;
|
|
588
|
+
}
|
|
589
|
+
this.emit('authProviderChanged', this.authProvider);
|
|
590
|
+
// Update process cache on auth changes: https://github.com/Open-EO/openeo-js-client/issues/55
|
|
591
|
+
this.refreshProcessCache();
|
|
592
|
+
}
|
|
593
|
+
|
|
594
|
+
/**
|
|
595
|
+
* Sets the authentication token for the connection.
|
|
596
|
+
*
|
|
597
|
+
* This creates a new custom `AuthProvider` with the given details and returns it.
|
|
598
|
+
* After calling this function you can make requests against the API.
|
|
599
|
+
*
|
|
600
|
+
* This is NOT recommended to use. Only use if you know what you are doing.
|
|
601
|
+
* It is recommended to authenticate through `listAuthProviders` or related functions.
|
|
602
|
+
*
|
|
603
|
+
* @param {string} type - The authentication type, e.g. `basic` or `oidc`.
|
|
604
|
+
* @param {string} providerId - The provider identifier. For OIDC the `id` of the provider.
|
|
605
|
+
* @param {string} token - The actual access token as given by the authentication method during the login process.
|
|
606
|
+
* @returns {AuthProvider}
|
|
607
|
+
*/
|
|
608
|
+
setAuthToken(type, providerId, token) {
|
|
609
|
+
const provider = new AuthProvider(type, this, {
|
|
610
|
+
id: providerId,
|
|
611
|
+
title: "Custom",
|
|
612
|
+
description: ""
|
|
613
|
+
});
|
|
614
|
+
provider.setToken(token);
|
|
615
|
+
this.setAuthProvider(provider);
|
|
616
|
+
return provider;
|
|
617
|
+
}
|
|
618
|
+
|
|
619
|
+
/**
|
|
620
|
+
* Get information about the authenticated user.
|
|
621
|
+
*
|
|
622
|
+
* Updates the User ID if available.
|
|
623
|
+
*
|
|
624
|
+
* @async
|
|
625
|
+
* @returns {Promise<UserAccount>} A response compatible to the API specification.
|
|
626
|
+
* @throws {Error}
|
|
627
|
+
*/
|
|
628
|
+
async describeAccount() {
|
|
629
|
+
const response = await this._get('/me');
|
|
630
|
+
return response.data;
|
|
631
|
+
}
|
|
632
|
+
|
|
633
|
+
/**
|
|
634
|
+
* List all files from the user workspace.
|
|
635
|
+
*
|
|
636
|
+
* @async
|
|
637
|
+
* @returns {Promise<ResponseArray.<UserFile>>} A list of files.
|
|
638
|
+
* @throws {Error}
|
|
639
|
+
*/
|
|
640
|
+
async listFiles() {
|
|
641
|
+
const pages = this.paginateFiles(null);
|
|
642
|
+
return await pages.nextPage();
|
|
643
|
+
}
|
|
644
|
+
|
|
645
|
+
/**
|
|
646
|
+
* Paginate through the files from the user workspace.
|
|
647
|
+
*
|
|
648
|
+
* @param {?number} [limit=50] - The number of files per request/page as integer. If `null`, requests all files.
|
|
649
|
+
* @returns {ServicePages} A paged list of files.
|
|
650
|
+
*/
|
|
651
|
+
paginateFiles(limit = 50) {
|
|
652
|
+
return new UserFilePages(this, limit);
|
|
653
|
+
}
|
|
654
|
+
|
|
655
|
+
/**
|
|
656
|
+
* A callback that is executed on upload progress updates.
|
|
657
|
+
*
|
|
658
|
+
* @callback uploadStatusCallback
|
|
659
|
+
* @param {number} percentCompleted - The percent (0-100) completed.
|
|
660
|
+
* @param {UserFile} file - The file object corresponding to the callback.
|
|
661
|
+
*/
|
|
662
|
+
|
|
663
|
+
/**
|
|
664
|
+
* Uploads a file to the user workspace.
|
|
665
|
+
* If a file with the name exists, overwrites it.
|
|
666
|
+
*
|
|
667
|
+
* This method has different behaviour depending on the environment.
|
|
668
|
+
* In a nodeJS environment the source must be a path to a file as string.
|
|
669
|
+
* In a browser environment the source must be an object from a file upload form.
|
|
670
|
+
*
|
|
671
|
+
* @async
|
|
672
|
+
* @param {*} source - The source, see method description for details.
|
|
673
|
+
* @param {?string} [targetPath=null] - The target path on the server, relative to the user workspace. Defaults to the file name of the source file.
|
|
674
|
+
* @param {?uploadStatusCallback} [statusCallback=null] - Optionally, a callback that is executed on upload progress updates.
|
|
675
|
+
* @param {?AbortController} [abortController=null] - An AbortController object that can be used to cancel the upload process.
|
|
676
|
+
* @returns {Promise<UserFile>}
|
|
677
|
+
* @throws {Error}
|
|
678
|
+
*/
|
|
679
|
+
async uploadFile(source, targetPath = null, statusCallback = null, abortController = null) {
|
|
680
|
+
if (targetPath === null) {
|
|
681
|
+
targetPath = Environment.fileNameForUpload(source);
|
|
682
|
+
}
|
|
683
|
+
const file = await this.getFile(targetPath);
|
|
684
|
+
return await file.uploadFile(source, statusCallback, abortController);
|
|
685
|
+
}
|
|
686
|
+
|
|
687
|
+
/**
|
|
688
|
+
* Opens a (existing or non-existing) file without reading any information or creating a new file at the back-end.
|
|
689
|
+
*
|
|
690
|
+
* @async
|
|
691
|
+
* @param {string} path - Path to the file, relative to the user workspace.
|
|
692
|
+
* @returns {Promise<UserFile>} A file.
|
|
693
|
+
* @throws {Error}
|
|
694
|
+
*/
|
|
695
|
+
async getFile(path) {
|
|
696
|
+
return new UserFile(this, path);
|
|
697
|
+
}
|
|
698
|
+
|
|
699
|
+
/**
|
|
700
|
+
* Takes a UserProcess, BuilderNode or a plain object containing process nodes
|
|
701
|
+
* and converts it to an API compliant object.
|
|
702
|
+
*
|
|
703
|
+
* @param {UserProcess|BuilderNode|object.<string, *>} process - Process to be normalized.
|
|
704
|
+
* @param {object.<string, *>} additional - Additional properties to be merged with the resulting object.
|
|
705
|
+
* @returns {object.<string, *>}
|
|
706
|
+
* @protected
|
|
707
|
+
*/
|
|
708
|
+
_normalizeUserProcess(process, additional = {}) {
|
|
709
|
+
if (process instanceof UserProcess) {
|
|
710
|
+
process = process.toJSON();
|
|
711
|
+
}
|
|
712
|
+
else if (process instanceof BuilderNode) {
|
|
713
|
+
process.result = true;
|
|
714
|
+
process = process.parent.toJSON();
|
|
715
|
+
}
|
|
716
|
+
else if (Utils.isObject(process) && !Utils.isObject(process.process_graph)) {
|
|
717
|
+
process = {
|
|
718
|
+
process_graph: process
|
|
719
|
+
};
|
|
720
|
+
}
|
|
721
|
+
return Object.assign({}, additional, {process: process});
|
|
722
|
+
}
|
|
723
|
+
|
|
724
|
+
/**
|
|
725
|
+
* Validates a user-defined process at the back-end.
|
|
726
|
+
*
|
|
727
|
+
* @async
|
|
728
|
+
* @param {Process} process - User-defined process to validate.
|
|
729
|
+
* @returns {Promise<ValidationResult>} errors - A list of API compatible error objects. A valid process returns an empty list.
|
|
730
|
+
* @throws {Error}
|
|
731
|
+
*/
|
|
732
|
+
async validateProcess(process) {
|
|
733
|
+
const response = await this._post('/validation', this._normalizeUserProcess(process).process);
|
|
734
|
+
if (Array.isArray(response.data.errors)) {
|
|
735
|
+
const errors = response.data.errors;
|
|
736
|
+
errors['federation:backends'] = Array.isArray(response.data['federation:missing']) ? response.data['federation:missing'] : [];
|
|
737
|
+
return errors;
|
|
738
|
+
}
|
|
739
|
+
else {
|
|
740
|
+
throw new Error("Invalid validation response received.");
|
|
741
|
+
}
|
|
742
|
+
}
|
|
743
|
+
|
|
744
|
+
/**
|
|
745
|
+
* List all user-defined processes of the authenticated user.
|
|
746
|
+
*
|
|
747
|
+
* @async
|
|
748
|
+
* @param {Array.<UserProcess>} [oldProcesses=[]] - A list of existing user-defined processes to update.
|
|
749
|
+
* @returns {Promise<ResponseArray.<UserProcess>>} A list of user-defined processes.
|
|
750
|
+
* @throws {Error}
|
|
751
|
+
*/
|
|
752
|
+
async listUserProcesses(oldProcesses = []) {
|
|
753
|
+
const pages = this.paginateUserProcesses(null);
|
|
754
|
+
return await pages.nextPage(oldProcesses);
|
|
755
|
+
}
|
|
756
|
+
|
|
757
|
+
/**
|
|
758
|
+
* Paginates through the user-defined processes of the authenticated user.
|
|
759
|
+
*
|
|
760
|
+
* @param {?number} [limit=50] - The number of processes per request/page as integer. If `null`, requests all processes.
|
|
761
|
+
* @returns {ProcessPages} A paged list of user-defined processes.
|
|
762
|
+
*/
|
|
763
|
+
paginateUserProcesses(limit = 50) {
|
|
764
|
+
return this.paginateProcesses('user', limit);
|
|
765
|
+
}
|
|
766
|
+
|
|
767
|
+
/**
|
|
768
|
+
* Creates a new stored user-defined process at the back-end.
|
|
769
|
+
*
|
|
770
|
+
* @async
|
|
771
|
+
* @param {string} id - Unique identifier for the process.
|
|
772
|
+
* @param {Process} process - A user-defined process.
|
|
773
|
+
* @returns {Promise<UserProcess>} The new user-defined process.
|
|
774
|
+
* @throws {Error}
|
|
775
|
+
*/
|
|
776
|
+
async setUserProcess(id, process) {
|
|
777
|
+
const pg = new UserProcess(this, id);
|
|
778
|
+
return await pg.replaceUserProcess(process);
|
|
779
|
+
}
|
|
780
|
+
|
|
781
|
+
/**
|
|
782
|
+
* Get all information about a user-defined process.
|
|
783
|
+
*
|
|
784
|
+
* @async
|
|
785
|
+
* @param {string} id - Identifier of the user-defined process.
|
|
786
|
+
* @returns {Promise<UserProcess>} The user-defined process.
|
|
787
|
+
* @throws {Error}
|
|
788
|
+
*/
|
|
789
|
+
async getUserProcess(id) {
|
|
790
|
+
const pg = new UserProcess(this, id);
|
|
791
|
+
return await pg.describeUserProcess();
|
|
792
|
+
}
|
|
793
|
+
|
|
794
|
+
/**
|
|
795
|
+
* Executes a process synchronously and returns the result as the response.
|
|
796
|
+
*
|
|
797
|
+
* Please note that requests can take a very long time of several minutes or even hours.
|
|
798
|
+
*
|
|
799
|
+
* @async
|
|
800
|
+
* @param {Process} process - A user-defined process.
|
|
801
|
+
* @param {?string} [plan=null] - The billing plan to use for this computation.
|
|
802
|
+
* @param {?number} [budget=null] - The maximum budget allowed to spend for this computation.
|
|
803
|
+
* @param {?AbortController} [abortController=null] - An AbortController object that can be used to cancel the processing request.
|
|
804
|
+
* @param {object.<string, *>} [additional={}] - Other parameters to pass for the batch job, e.g. `log_level`.
|
|
805
|
+
* @returns {Promise<SyncResult>} - An object with the data and some metadata.
|
|
806
|
+
*/
|
|
807
|
+
async computeResult(process, plan = null, budget = null, abortController = null, additional = {}) {
|
|
808
|
+
const requestBody = this._normalizeUserProcess(
|
|
809
|
+
process,
|
|
810
|
+
Object.assign({}, additional, {
|
|
811
|
+
plan: plan,
|
|
812
|
+
budget: budget
|
|
813
|
+
})
|
|
814
|
+
);
|
|
815
|
+
const response = await this._post('/result', requestBody, Environment.getResponseType(), abortController);
|
|
816
|
+
const syncResult = {
|
|
817
|
+
data: response.data,
|
|
818
|
+
costs: null,
|
|
819
|
+
type: null,
|
|
820
|
+
logs: []
|
|
821
|
+
};
|
|
822
|
+
|
|
823
|
+
if (typeof response.headers['openeo-costs'] === 'number') {
|
|
824
|
+
syncResult.costs = response.headers['openeo-costs'];
|
|
825
|
+
}
|
|
826
|
+
|
|
827
|
+
if (typeof response.headers['content-type'] === 'string') {
|
|
828
|
+
syncResult.type = response.headers['content-type'];
|
|
829
|
+
}
|
|
830
|
+
|
|
831
|
+
const links = Array.isArray(response.headers.link) ? response.headers.link : [response.headers.link];
|
|
832
|
+
for(let link of links) {
|
|
833
|
+
if (typeof link !== 'string') {
|
|
834
|
+
continue;
|
|
835
|
+
}
|
|
836
|
+
const logs = link.match(/^<([^>]+)>;\s?rel="monitor"/i);
|
|
837
|
+
if (Array.isArray(logs) && logs.length > 1) {
|
|
838
|
+
try {
|
|
839
|
+
const logsResponse = await this._get(logs[1]);
|
|
840
|
+
if (Utils.isObject(logsResponse.data) && Array.isArray(logsResponse.data.logs)) {
|
|
841
|
+
syncResult.logs = logsResponse.data.logs;
|
|
842
|
+
}
|
|
843
|
+
} catch(error) {
|
|
844
|
+
console.warn(error);
|
|
845
|
+
}
|
|
846
|
+
}
|
|
847
|
+
}
|
|
848
|
+
|
|
849
|
+
return syncResult;
|
|
850
|
+
}
|
|
851
|
+
|
|
852
|
+
/**
|
|
853
|
+
* Executes a process synchronously and downloads to result the given path.
|
|
854
|
+
*
|
|
855
|
+
* Please note that requests can take a very long time of several minutes or even hours.
|
|
856
|
+
*
|
|
857
|
+
* This method has different behaviour depending on the environment.
|
|
858
|
+
* If a NodeJs environment, writes the downloaded file to the target location on the file system.
|
|
859
|
+
* In a browser environment, offers the file for downloading using the specified name (folders are not supported).
|
|
860
|
+
*
|
|
861
|
+
* @async
|
|
862
|
+
* @param {Process} process - A user-defined process.
|
|
863
|
+
* @param {string} targetPath - The target, see method description for details.
|
|
864
|
+
* @param {?string} [plan=null] - The billing plan to use for this computation.
|
|
865
|
+
* @param {?number} [budget=null] - The maximum budget allowed to spend for this computation.
|
|
866
|
+
* @param {?AbortController} [abortController=null] - An AbortController object that can be used to cancel the processing request.
|
|
867
|
+
* @throws {Error}
|
|
868
|
+
*/
|
|
869
|
+
async downloadResult(process, targetPath, plan = null, budget = null, abortController = null) {
|
|
870
|
+
const response = await this.computeResult(process, plan, budget, abortController);
|
|
871
|
+
// @ts-ignore
|
|
872
|
+
await Environment.saveToFile(response.data, targetPath);
|
|
873
|
+
}
|
|
874
|
+
|
|
875
|
+
/**
|
|
876
|
+
* List all batch jobs of the authenticated user.
|
|
877
|
+
*
|
|
878
|
+
* @async
|
|
879
|
+
* @param {Array.<Job>} [oldJobs=[]] - A list of existing jobs to update.
|
|
880
|
+
* @returns {Promise<ResponseArray.<Job>>} A list of jobs.
|
|
881
|
+
* @throws {Error}
|
|
882
|
+
*/
|
|
883
|
+
async listJobs(oldJobs = []) {
|
|
884
|
+
const pages = this.paginateJobs(null);
|
|
885
|
+
const firstPage = await pages.nextPage(oldJobs);
|
|
886
|
+
return firstPage;
|
|
887
|
+
}
|
|
888
|
+
|
|
889
|
+
/**
|
|
890
|
+
* Paginate through the batch jobs of the authenticated user.
|
|
891
|
+
*
|
|
892
|
+
* @param {?number} [limit=50] - The number of jobs per request/page as integer. If `null`, requests all jobs.
|
|
893
|
+
* @returns {JobPages} A paged list of jobs.
|
|
894
|
+
*/
|
|
895
|
+
paginateJobs(limit = 50) {
|
|
896
|
+
return new JobPages(this, limit);
|
|
897
|
+
}
|
|
898
|
+
|
|
899
|
+
/**
|
|
900
|
+
* Creates a new batch job at the back-end.
|
|
901
|
+
*
|
|
902
|
+
* @async
|
|
903
|
+
* @param {Process} process - A user-define process to execute.
|
|
904
|
+
* @param {?string} [title=null] - A title for the batch job.
|
|
905
|
+
* @param {?string} [description=null] - A description for the batch job.
|
|
906
|
+
* @param {?string} [plan=null] - The billing plan to use for this batch job.
|
|
907
|
+
* @param {?number} [budget=null] - The maximum budget allowed to spend for this batch job.
|
|
908
|
+
* @param {object.<string, *>} [additional={}] - Other parameters to pass for the batch job, e.g. `log_level`.
|
|
909
|
+
* @returns {Promise<Job>} The stored batch job.
|
|
910
|
+
* @throws {Error}
|
|
911
|
+
*/
|
|
912
|
+
async createJob(process, title = null, description = null, plan = null, budget = null, additional = {}) {
|
|
913
|
+
additional = Object.assign({}, additional, {
|
|
914
|
+
title: title,
|
|
915
|
+
description: description,
|
|
916
|
+
plan: plan,
|
|
917
|
+
budget: budget
|
|
918
|
+
});
|
|
919
|
+
const requestBody = this._normalizeUserProcess(process, additional);
|
|
920
|
+
const response = await this._post('/jobs', requestBody);
|
|
921
|
+
if (typeof response.headers['openeo-identifier'] !== 'string') {
|
|
922
|
+
throw new Error("Response did not contain a Job ID. Job has likely been created, but may not show up yet.");
|
|
923
|
+
}
|
|
924
|
+
const job = new Job(this, response.headers['openeo-identifier']).setAll(requestBody);
|
|
925
|
+
if (this.capabilities().hasFeature('describeJob')) {
|
|
926
|
+
return await job.describeJob();
|
|
927
|
+
}
|
|
928
|
+
else {
|
|
929
|
+
return job;
|
|
930
|
+
}
|
|
931
|
+
}
|
|
932
|
+
|
|
933
|
+
/**
|
|
934
|
+
* Get all information about a batch job.
|
|
935
|
+
*
|
|
936
|
+
* @async
|
|
937
|
+
* @param {string} id - Batch Job ID.
|
|
938
|
+
* @returns {Promise<Job>} The batch job.
|
|
939
|
+
* @throws {Error}
|
|
940
|
+
*/
|
|
941
|
+
async getJob(id) {
|
|
942
|
+
const job = new Job(this, id);
|
|
943
|
+
return await job.describeJob();
|
|
944
|
+
}
|
|
945
|
+
|
|
946
|
+
/**
|
|
947
|
+
* List all secondary web services of the authenticated user.
|
|
948
|
+
*
|
|
949
|
+
* @async
|
|
950
|
+
* @param {Array.<Service>} [oldServices=[]] - A list of existing services to update.
|
|
951
|
+
* @returns {Promise<ResponseArray.<Job>>} A list of services.
|
|
952
|
+
* @throws {Error}
|
|
953
|
+
*/
|
|
954
|
+
async listServices(oldServices = []) {
|
|
955
|
+
const pages = this.paginateServices(null);
|
|
956
|
+
return await pages.nextPage(oldServices);
|
|
957
|
+
}
|
|
958
|
+
|
|
959
|
+
/**
|
|
960
|
+
* Paginate through the secondary web services of the authenticated user.
|
|
961
|
+
*
|
|
962
|
+
* @param {?number} [limit=50] - The number of services per request/page as integer. If `null` (default), requests all services.
|
|
963
|
+
* @returns {ServicePages} A paged list of services.
|
|
964
|
+
*/
|
|
965
|
+
paginateServices(limit = 50) {
|
|
966
|
+
return new ServicePages(this, limit);
|
|
967
|
+
}
|
|
968
|
+
|
|
969
|
+
/**
|
|
970
|
+
* Creates a new secondary web service at the back-end.
|
|
971
|
+
*
|
|
972
|
+
* @async
|
|
973
|
+
* @param {Process} process - A user-defined process.
|
|
974
|
+
* @param {string} type - The type of service to be created (see `Connection.listServiceTypes()`).
|
|
975
|
+
* @param {?string} [title=null] - A title for the service.
|
|
976
|
+
* @param {?string} [description=null] - A description for the service.
|
|
977
|
+
* @param {boolean} [enabled=true] - Enable the service (`true`, default) or not (`false`).
|
|
978
|
+
* @param {object.<string, *>} [configuration={}] - Configuration parameters to pass to the service.
|
|
979
|
+
* @param {?string} [plan=null] - The billing plan to use for this service.
|
|
980
|
+
* @param {?number} [budget=null] - The maximum budget allowed to spend for this service.
|
|
981
|
+
* @param {object.<string, *>} [additional={}] - Other parameters to pass for the service, e.g. `log_level`.
|
|
982
|
+
* @returns {Promise<Service>} The stored service.
|
|
983
|
+
* @throws {Error}
|
|
984
|
+
*/
|
|
985
|
+
async createService(process, type, title = null, description = null, enabled = true, configuration = {}, plan = null, budget = null, additional = {}) {
|
|
986
|
+
const requestBody = this._normalizeUserProcess(process, Object.assign({
|
|
987
|
+
title: title,
|
|
988
|
+
description: description,
|
|
989
|
+
type: type,
|
|
990
|
+
enabled: enabled,
|
|
991
|
+
configuration: configuration,
|
|
992
|
+
plan: plan,
|
|
993
|
+
budget: budget
|
|
994
|
+
}, additional));
|
|
995
|
+
const response = await this._post('/services', requestBody);
|
|
996
|
+
if (typeof response.headers['openeo-identifier'] !== 'string') {
|
|
997
|
+
throw new Error("Response did not contain a Service ID. Service has likely been created, but may not show up yet.");
|
|
998
|
+
}
|
|
999
|
+
const service = new Service(this, response.headers['openeo-identifier']).setAll(requestBody);
|
|
1000
|
+
if (this.capabilities().hasFeature('describeService')) {
|
|
1001
|
+
return service.describeService();
|
|
1002
|
+
}
|
|
1003
|
+
else {
|
|
1004
|
+
return service;
|
|
1005
|
+
}
|
|
1006
|
+
}
|
|
1007
|
+
|
|
1008
|
+
/**
|
|
1009
|
+
* Get all information about a secondary web service.
|
|
1010
|
+
*
|
|
1011
|
+
* @async
|
|
1012
|
+
* @param {string} id - Service ID.
|
|
1013
|
+
* @returns {Promise<Service>} The service.
|
|
1014
|
+
* @throws {Error}
|
|
1015
|
+
*/
|
|
1016
|
+
async getService(id) {
|
|
1017
|
+
const service = new Service(this, id);
|
|
1018
|
+
return await service.describeService();
|
|
1019
|
+
}
|
|
1020
|
+
|
|
1021
|
+
/**
|
|
1022
|
+
* Get the a link with the given rel type.
|
|
1023
|
+
*
|
|
1024
|
+
* @protected
|
|
1025
|
+
* @param {Array.<Link>} links - An array of links.
|
|
1026
|
+
* @param {string|Array.<string>} rel - Relation type(s) to find.
|
|
1027
|
+
* @returns {string | null}
|
|
1028
|
+
* @throws {Error}
|
|
1029
|
+
*/
|
|
1030
|
+
_getLinkHref(links, rel) {
|
|
1031
|
+
if (!Array.isArray(rel)) {
|
|
1032
|
+
rel = [rel];
|
|
1033
|
+
}
|
|
1034
|
+
if (Array.isArray(links)) {
|
|
1035
|
+
const link = links.find(l => Utils.isObject(l) && rel.includes(l.rel) && typeof l.href === 'string');
|
|
1036
|
+
if (link) {
|
|
1037
|
+
return link.href;
|
|
1038
|
+
}
|
|
1039
|
+
}
|
|
1040
|
+
return null;
|
|
1041
|
+
}
|
|
1042
|
+
|
|
1043
|
+
/**
|
|
1044
|
+
* Makes all links in the list absolute.
|
|
1045
|
+
*
|
|
1046
|
+
* @param {Array.<Link>} links - An array of links.
|
|
1047
|
+
* @param {?string|AxiosResponse} [base=null] - The base url to use for relative links, or an response to derive the url from.
|
|
1048
|
+
* @returns {Array.<Link>}
|
|
1049
|
+
*/
|
|
1050
|
+
makeLinksAbsolute(links, base = null) {
|
|
1051
|
+
if (!Array.isArray(links)) {
|
|
1052
|
+
return links;
|
|
1053
|
+
}
|
|
1054
|
+
let baseUrl = null;
|
|
1055
|
+
if (Utils.isObject(base) && base.headers && base.config && base.request) { // AxiosResponse
|
|
1056
|
+
baseUrl = base.config.baseURL + base.config.url;
|
|
1057
|
+
}
|
|
1058
|
+
else if (typeof base !== 'string') {
|
|
1059
|
+
baseUrl = this._getLinkHref(links, 'self');
|
|
1060
|
+
}
|
|
1061
|
+
else {
|
|
1062
|
+
baseUrl = base;
|
|
1063
|
+
}
|
|
1064
|
+
if (!baseUrl) {
|
|
1065
|
+
return links;
|
|
1066
|
+
}
|
|
1067
|
+
return links.map((link) => {
|
|
1068
|
+
if (!Utils.isObject(link) || typeof link.href !== 'string') {
|
|
1069
|
+
return link;
|
|
1070
|
+
}
|
|
1071
|
+
try {
|
|
1072
|
+
const url = new URL(link.href, baseUrl);
|
|
1073
|
+
return Object.assign({}, link, {href: url.toString()});
|
|
1074
|
+
} catch(error) {
|
|
1075
|
+
return link;
|
|
1076
|
+
}
|
|
1077
|
+
});
|
|
1078
|
+
}
|
|
1079
|
+
|
|
1080
|
+
/**
|
|
1081
|
+
* Sends a GET request.
|
|
1082
|
+
*
|
|
1083
|
+
* @protected
|
|
1084
|
+
* @async
|
|
1085
|
+
* @param {string} path
|
|
1086
|
+
* @param {object.<string, *>} query
|
|
1087
|
+
* @param {string} responseType - Response type according to axios, defaults to `json`.
|
|
1088
|
+
* @param {?AbortController} [abortController=null] - An AbortController object that can be used to cancel the request.
|
|
1089
|
+
* @returns {Promise<AxiosResponse>}
|
|
1090
|
+
* @throws {Error}
|
|
1091
|
+
* @see https://github.com/axios/axios#request-config
|
|
1092
|
+
*/
|
|
1093
|
+
async _get(path, query, responseType, abortController = null) {
|
|
1094
|
+
return await this._send({
|
|
1095
|
+
method: 'get',
|
|
1096
|
+
responseType: responseType,
|
|
1097
|
+
url: path,
|
|
1098
|
+
// Timeout for capabilities requests as they are used for a quick first discovery to check whether the server is a openEO back-end.
|
|
1099
|
+
// Without timeout connecting with a wrong server url may take forever.
|
|
1100
|
+
timeout: path === '/' ? 5000 : 0,
|
|
1101
|
+
params: query
|
|
1102
|
+
}, abortController);
|
|
1103
|
+
}
|
|
1104
|
+
|
|
1105
|
+
/**
|
|
1106
|
+
* Sends a POST request.
|
|
1107
|
+
*
|
|
1108
|
+
* @protected
|
|
1109
|
+
* @async
|
|
1110
|
+
* @param {string} path
|
|
1111
|
+
* @param {*} body
|
|
1112
|
+
* @param {string} responseType - Response type according to axios, defaults to `json`.
|
|
1113
|
+
* @param {?AbortController} [abortController=null] - An AbortController object that can be used to cancel the request.
|
|
1114
|
+
* @returns {Promise<AxiosResponse>}
|
|
1115
|
+
* @throws {Error}
|
|
1116
|
+
* @see https://github.com/axios/axios#request-config
|
|
1117
|
+
*/
|
|
1118
|
+
async _post(path, body, responseType, abortController = null) {
|
|
1119
|
+
const options = {
|
|
1120
|
+
method: 'post',
|
|
1121
|
+
responseType: responseType,
|
|
1122
|
+
url: path,
|
|
1123
|
+
data: body
|
|
1124
|
+
};
|
|
1125
|
+
return await this._send(options, abortController);
|
|
1126
|
+
}
|
|
1127
|
+
|
|
1128
|
+
/**
|
|
1129
|
+
* Sends a PUT request.
|
|
1130
|
+
*
|
|
1131
|
+
* @protected
|
|
1132
|
+
* @async
|
|
1133
|
+
* @param {string} path
|
|
1134
|
+
* @param {*} body
|
|
1135
|
+
* @returns {Promise<AxiosResponse>}
|
|
1136
|
+
* @throws {Error}
|
|
1137
|
+
*/
|
|
1138
|
+
async _put(path, body) {
|
|
1139
|
+
return await this._send({
|
|
1140
|
+
method: 'put',
|
|
1141
|
+
url: path,
|
|
1142
|
+
data: body
|
|
1143
|
+
});
|
|
1144
|
+
}
|
|
1145
|
+
|
|
1146
|
+
/**
|
|
1147
|
+
* Sends a PATCH request.
|
|
1148
|
+
*
|
|
1149
|
+
* @protected
|
|
1150
|
+
* @async
|
|
1151
|
+
* @param {string} path
|
|
1152
|
+
* @param {*} body
|
|
1153
|
+
* @returns {Promise<AxiosResponse>}
|
|
1154
|
+
* @throws {Error}
|
|
1155
|
+
*/
|
|
1156
|
+
async _patch(path, body) {
|
|
1157
|
+
return await this._send({
|
|
1158
|
+
method: 'patch',
|
|
1159
|
+
url: path,
|
|
1160
|
+
data: body
|
|
1161
|
+
});
|
|
1162
|
+
}
|
|
1163
|
+
|
|
1164
|
+
/**
|
|
1165
|
+
* Sends a DELETE request.
|
|
1166
|
+
*
|
|
1167
|
+
* @protected
|
|
1168
|
+
* @async
|
|
1169
|
+
* @param {string} path
|
|
1170
|
+
* @returns {Promise<AxiosResponse>}
|
|
1171
|
+
* @throws {Error}
|
|
1172
|
+
*/
|
|
1173
|
+
async _delete(path) {
|
|
1174
|
+
return await this._send({
|
|
1175
|
+
method: 'delete',
|
|
1176
|
+
url: path
|
|
1177
|
+
});
|
|
1178
|
+
}
|
|
1179
|
+
|
|
1180
|
+
/**
|
|
1181
|
+
* Downloads data from a URL.
|
|
1182
|
+
*
|
|
1183
|
+
* May include authorization details where required.
|
|
1184
|
+
*
|
|
1185
|
+
* @param {string} url - An absolute or relative URL to download data from.
|
|
1186
|
+
* @param {boolean} authorize - Send authorization details (`true`) or not (`false`).
|
|
1187
|
+
* @returns {Promise<Stream.Readable|Blob>} - Returns the data as `Stream` in NodeJS environments or as `Blob` in browsers
|
|
1188
|
+
* @throws {Error}
|
|
1189
|
+
*/
|
|
1190
|
+
async download(url, authorize) {
|
|
1191
|
+
const result = await this._send({
|
|
1192
|
+
method: 'get',
|
|
1193
|
+
responseType: Environment.getResponseType(),
|
|
1194
|
+
url: url,
|
|
1195
|
+
authorization: authorize
|
|
1196
|
+
});
|
|
1197
|
+
return result.data;
|
|
1198
|
+
}
|
|
1199
|
+
|
|
1200
|
+
/**
|
|
1201
|
+
* Get the authorization header for requests.
|
|
1202
|
+
*
|
|
1203
|
+
* @protected
|
|
1204
|
+
* @returns {object.<string, string>}
|
|
1205
|
+
*/
|
|
1206
|
+
_getAuthHeaders() {
|
|
1207
|
+
const headers = {};
|
|
1208
|
+
if (this.isAuthenticated()) {
|
|
1209
|
+
headers.Authorization = 'Bearer ' + this.authProvider.getToken();
|
|
1210
|
+
}
|
|
1211
|
+
return headers;
|
|
1212
|
+
}
|
|
1213
|
+
|
|
1214
|
+
/**
|
|
1215
|
+
* Sends a HTTP request.
|
|
1216
|
+
*
|
|
1217
|
+
* Options mostly conform to axios,
|
|
1218
|
+
* see {@link https://github.com/axios/axios#request-config}.
|
|
1219
|
+
*
|
|
1220
|
+
* Automatically sets a baseUrl and the authorization information.
|
|
1221
|
+
* Default responseType is `json`.
|
|
1222
|
+
*
|
|
1223
|
+
* Tries to smoothly handle error responses by providing an object for all response types,
|
|
1224
|
+
* instead of Streams or Blobs for non-JSON response types.
|
|
1225
|
+
*
|
|
1226
|
+
* @protected
|
|
1227
|
+
* @async
|
|
1228
|
+
* @param {object.<string, *>} options
|
|
1229
|
+
* @param {?AbortController} [abortController=null] - An AbortController object that can be used to cancel the request.
|
|
1230
|
+
* @returns {Promise<AxiosResponse>}
|
|
1231
|
+
* @throws {Error}
|
|
1232
|
+
* @see https://github.com/axios/axios
|
|
1233
|
+
*/
|
|
1234
|
+
async _send(options, abortController = null) {
|
|
1235
|
+
options.baseURL = this.baseUrl;
|
|
1236
|
+
if (typeof options.authorization === 'undefined' || options.authorization === true) {
|
|
1237
|
+
if (!options.headers) {
|
|
1238
|
+
options.headers = {};
|
|
1239
|
+
}
|
|
1240
|
+
Object.assign(options.headers, this._getAuthHeaders());
|
|
1241
|
+
}
|
|
1242
|
+
if (!options.responseType) {
|
|
1243
|
+
options.responseType = 'json';
|
|
1244
|
+
}
|
|
1245
|
+
if (abortController) {
|
|
1246
|
+
options.signal = abortController.signal;
|
|
1247
|
+
}
|
|
1248
|
+
|
|
1249
|
+
try {
|
|
1250
|
+
let response = await axios(options);
|
|
1251
|
+
const capabilities = this.capabilities();
|
|
1252
|
+
if (capabilities) {
|
|
1253
|
+
response = capabilities.migrate(response);
|
|
1254
|
+
}
|
|
1255
|
+
return response;
|
|
1256
|
+
} catch(error) {
|
|
1257
|
+
if (axios.isCancel(error)) {
|
|
1258
|
+
throw error;
|
|
1259
|
+
}
|
|
1260
|
+
const checkContentType = type => (typeof type === 'string' && type.indexOf('/json') !== -1);
|
|
1261
|
+
const enrichError = (origin, response) => {
|
|
1262
|
+
if (typeof response.message === 'string') {
|
|
1263
|
+
origin.message = response.message;
|
|
1264
|
+
}
|
|
1265
|
+
origin.code = typeof response.code === 'string' ? response.code : "";
|
|
1266
|
+
origin.id = response.id;
|
|
1267
|
+
origin.links = Array.isArray(response.links) ? response.links : [];
|
|
1268
|
+
return origin;
|
|
1269
|
+
};
|
|
1270
|
+
if (Utils.isObject(error.response) && Utils.isObject(error.response.data) && (checkContentType(error.response.data.type) || (Utils.isObject(error.response.headers) && checkContentType(error.response.headers['content-type'])))) {
|
|
1271
|
+
// JSON error responses are Blobs and streams if responseType is set as such, so convert to JSON if required.
|
|
1272
|
+
// See: https://github.com/axios/axios/issues/815
|
|
1273
|
+
if (options.responseType === Environment.getResponseType()) {
|
|
1274
|
+
try {
|
|
1275
|
+
const errorResponse = await Environment.handleErrorResponse(error);
|
|
1276
|
+
throw enrichError(error, errorResponse);
|
|
1277
|
+
} catch (error2) {
|
|
1278
|
+
console.error(error2);
|
|
1279
|
+
}
|
|
1280
|
+
}
|
|
1281
|
+
else {
|
|
1282
|
+
throw enrichError(error, error.response.data);
|
|
1283
|
+
}
|
|
1284
|
+
}
|
|
1285
|
+
throw error;
|
|
1286
|
+
}
|
|
1287
|
+
}
|
|
1288
|
+
}
|
|
1289
|
+
|
|
1290
|
+
module.exports = Connection;
|