@meginhufr/brua-cli 0.1.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/openapi.json ADDED
@@ -0,0 +1,3459 @@
1
+ {
2
+ "openapi": "3.0.4",
3
+ "info": {
4
+ "title": "Brua API",
5
+ "description": "Brua serves images and animations to apps and web pages. Your systems use this API to create assets and upload their\nsources, to put versions in change sets that people review and merge, and, when a frozen snapshot is wanted, to read\nwhat the current release serves. Apps and pages read released assets straight from the edge by id (`/assets/{org}/{id}.json`)\nand need neither a key nor this API.\n\n**Authentication.** Send a project's API key as `X-Api-Key`. An admin creates keys in the back office's settings or with\n`POST /v1/projects/{project}/api-keys`; a key has the scopes `delivery:read` (reading assets), `assets:write` (creating\nassets, uploading, change sets) or `admin` (keys and settings). Merging a change set into prod is done by a person.\n\n**Errors** have one shape on every endpoint, `{ \"error\": \"<code>\", \"id\": \"<what it is about>\" }`, with `errors` per\nfield on `validation_failed`. Fields that are null are left out of responses, and new fields may appear at any time.",
6
+ "version": "v1"
7
+ },
8
+ "paths": {
9
+ "/v1/projects/{project}/api-keys": {
10
+ "post": {
11
+ "tags": [
12
+ "API keys"
13
+ ],
14
+ "summary": "Creates a key for a system. The full key is in this response only (SPEC.md 13.2).",
15
+ "operationId": "ApiKeys.Create",
16
+ "parameters": [
17
+ {
18
+ "name": "project",
19
+ "in": "path",
20
+ "description": "The project's id, as in its URLs in the back office; a project also reads its organization's libraries through its own id.",
21
+ "required": true,
22
+ "schema": {
23
+ "type": "string"
24
+ }
25
+ }
26
+ ],
27
+ "requestBody": {
28
+ "content": {
29
+ "application/json": {
30
+ "schema": {
31
+ "$ref": "#/components/schemas/CreateApiKeyRequest"
32
+ }
33
+ },
34
+ "text/json": {
35
+ "schema": {
36
+ "$ref": "#/components/schemas/CreateApiKeyRequest"
37
+ }
38
+ },
39
+ "application/*+json": {
40
+ "schema": {
41
+ "$ref": "#/components/schemas/CreateApiKeyRequest"
42
+ }
43
+ }
44
+ }
45
+ },
46
+ "responses": {
47
+ "201": {
48
+ "description": "Created",
49
+ "content": {
50
+ "application/json": {
51
+ "schema": {
52
+ "$ref": "#/components/schemas/CreatedApiKeyDto"
53
+ }
54
+ }
55
+ }
56
+ },
57
+ "400": {
58
+ "description": "The body is invalid: `validation_failed`, with the messages per field in `errors`.",
59
+ "content": {
60
+ "application/json": {
61
+ "schema": {
62
+ "$ref": "#/components/schemas/ErrorDto"
63
+ }
64
+ }
65
+ }
66
+ },
67
+ "401": {
68
+ "description": "No key or token, or an invalid or revoked one."
69
+ },
70
+ "403": {
71
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
72
+ "content": {
73
+ "application/json": {
74
+ "schema": {
75
+ "$ref": "#/components/schemas/ErrorDto"
76
+ }
77
+ }
78
+ }
79
+ }
80
+ },
81
+ "security": [
82
+ {
83
+ "ApiKey": [ ]
84
+ }
85
+ ]
86
+ },
87
+ "get": {
88
+ "tags": [
89
+ "API keys"
90
+ ],
91
+ "summary": "The project's keys with when each was last used; secrets are never shown again.",
92
+ "operationId": "ApiKeys.List",
93
+ "parameters": [
94
+ {
95
+ "name": "project",
96
+ "in": "path",
97
+ "description": "The project's id, as in its URLs in the back office; a project also reads its organization's libraries through its own id.",
98
+ "required": true,
99
+ "schema": {
100
+ "type": "string"
101
+ }
102
+ }
103
+ ],
104
+ "responses": {
105
+ "200": {
106
+ "description": "OK",
107
+ "content": {
108
+ "application/json": {
109
+ "schema": {
110
+ "type": "array",
111
+ "items": {
112
+ "$ref": "#/components/schemas/ApiKeyDto"
113
+ }
114
+ }
115
+ }
116
+ }
117
+ },
118
+ "401": {
119
+ "description": "No key or token, or an invalid or revoked one."
120
+ },
121
+ "403": {
122
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
123
+ "content": {
124
+ "application/json": {
125
+ "schema": {
126
+ "$ref": "#/components/schemas/ErrorDto"
127
+ }
128
+ }
129
+ }
130
+ }
131
+ },
132
+ "security": [
133
+ {
134
+ "ApiKey": [ ]
135
+ }
136
+ ]
137
+ }
138
+ },
139
+ "/v1/projects/{project}/api-keys/{id}": {
140
+ "delete": {
141
+ "tags": [
142
+ "API keys"
143
+ ],
144
+ "summary": "Revokes a key; requests with it fail from the next one.",
145
+ "operationId": "ApiKeys.Revoke",
146
+ "parameters": [
147
+ {
148
+ "name": "project",
149
+ "in": "path",
150
+ "description": "The project's id, as in its URLs in the back office; a project also reads its organization's libraries through its own id.",
151
+ "required": true,
152
+ "schema": {
153
+ "type": "string"
154
+ }
155
+ },
156
+ {
157
+ "name": "id",
158
+ "in": "path",
159
+ "description": "The key's id.",
160
+ "required": true,
161
+ "schema": {
162
+ "type": "string",
163
+ "format": "uuid"
164
+ }
165
+ }
166
+ ],
167
+ "responses": {
168
+ "204": {
169
+ "description": "No Content"
170
+ },
171
+ "404": {
172
+ "description": "Not Found",
173
+ "content": {
174
+ "application/json": {
175
+ "schema": {
176
+ "$ref": "#/components/schemas/ErrorDto"
177
+ }
178
+ }
179
+ }
180
+ },
181
+ "401": {
182
+ "description": "No key or token, or an invalid or revoked one."
183
+ },
184
+ "403": {
185
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
186
+ "content": {
187
+ "application/json": {
188
+ "schema": {
189
+ "$ref": "#/components/schemas/ErrorDto"
190
+ }
191
+ }
192
+ }
193
+ }
194
+ },
195
+ "security": [
196
+ {
197
+ "ApiKey": [ ]
198
+ }
199
+ ]
200
+ }
201
+ },
202
+ "/v1/projects/{project}/assets": {
203
+ "get": {
204
+ "tags": [
205
+ "Assets"
206
+ ],
207
+ "summary": "Every asset in the project, newest first, with thumbnails of its newest processed version.",
208
+ "operationId": "Assets.List",
209
+ "parameters": [
210
+ {
211
+ "name": "project",
212
+ "in": "path",
213
+ "description": "The project's id, as in its URLs in the back office; a project also reads its organization's libraries through its own id.",
214
+ "required": true,
215
+ "schema": {
216
+ "type": "string"
217
+ }
218
+ }
219
+ ],
220
+ "responses": {
221
+ "200": {
222
+ "description": "OK",
223
+ "content": {
224
+ "application/json": {
225
+ "schema": {
226
+ "type": "array",
227
+ "items": {
228
+ "$ref": "#/components/schemas/AssetSummaryDto"
229
+ }
230
+ }
231
+ }
232
+ }
233
+ },
234
+ "401": {
235
+ "description": "No key or token, or an invalid or revoked one."
236
+ },
237
+ "403": {
238
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
239
+ "content": {
240
+ "application/json": {
241
+ "schema": {
242
+ "$ref": "#/components/schemas/ErrorDto"
243
+ }
244
+ }
245
+ }
246
+ }
247
+ },
248
+ "security": [
249
+ {
250
+ "ApiKey": [ ]
251
+ }
252
+ ]
253
+ },
254
+ "post": {
255
+ "tags": [
256
+ "Assets"
257
+ ],
258
+ "summary": "Creates an asset with a first draft version.",
259
+ "operationId": "Assets.Create",
260
+ "parameters": [
261
+ {
262
+ "name": "project",
263
+ "in": "path",
264
+ "description": "The project's id, as in its URLs in the back office; a project also reads its organization's libraries through its own id.",
265
+ "required": true,
266
+ "schema": {
267
+ "type": "string"
268
+ }
269
+ }
270
+ ],
271
+ "requestBody": {
272
+ "content": {
273
+ "application/json": {
274
+ "schema": {
275
+ "$ref": "#/components/schemas/CreateAssetRequest"
276
+ }
277
+ },
278
+ "text/json": {
279
+ "schema": {
280
+ "$ref": "#/components/schemas/CreateAssetRequest"
281
+ }
282
+ },
283
+ "application/*+json": {
284
+ "schema": {
285
+ "$ref": "#/components/schemas/CreateAssetRequest"
286
+ }
287
+ }
288
+ }
289
+ },
290
+ "responses": {
291
+ "201": {
292
+ "description": "Created",
293
+ "content": {
294
+ "application/json": {
295
+ "schema": {
296
+ "$ref": "#/components/schemas/AssetVersionDto"
297
+ }
298
+ }
299
+ }
300
+ },
301
+ "400": {
302
+ "description": "Bad Request",
303
+ "content": {
304
+ "application/json": {
305
+ "schema": {
306
+ "$ref": "#/components/schemas/ErrorDto"
307
+ }
308
+ }
309
+ }
310
+ },
311
+ "409": {
312
+ "description": "Conflict",
313
+ "content": {
314
+ "application/json": {
315
+ "schema": {
316
+ "$ref": "#/components/schemas/ErrorDto"
317
+ }
318
+ }
319
+ }
320
+ },
321
+ "401": {
322
+ "description": "No key or token, or an invalid or revoked one."
323
+ },
324
+ "403": {
325
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
326
+ "content": {
327
+ "application/json": {
328
+ "schema": {
329
+ "$ref": "#/components/schemas/ErrorDto"
330
+ }
331
+ }
332
+ }
333
+ }
334
+ },
335
+ "security": [
336
+ {
337
+ "ApiKey": [ ]
338
+ }
339
+ ]
340
+ }
341
+ },
342
+ "/v1/projects/{project}/assets/{id}/versions": {
343
+ "get": {
344
+ "tags": [
345
+ "Assets"
346
+ ],
347
+ "summary": "The asset's versions, newest first, with alt text, variant types and thumbnails.",
348
+ "operationId": "Assets.Versions",
349
+ "parameters": [
350
+ {
351
+ "name": "project",
352
+ "in": "path",
353
+ "description": "The project's id, as in its URLs in the back office; a project also reads its organization's libraries through its own id.",
354
+ "required": true,
355
+ "schema": {
356
+ "type": "string"
357
+ }
358
+ },
359
+ {
360
+ "name": "id",
361
+ "in": "path",
362
+ "description": "The asset's id.",
363
+ "required": true,
364
+ "schema": {
365
+ "type": "string"
366
+ }
367
+ }
368
+ ],
369
+ "responses": {
370
+ "200": {
371
+ "description": "OK",
372
+ "content": {
373
+ "application/json": {
374
+ "schema": {
375
+ "$ref": "#/components/schemas/AssetDetailDto"
376
+ }
377
+ }
378
+ }
379
+ },
380
+ "404": {
381
+ "description": "Not Found",
382
+ "content": {
383
+ "application/json": {
384
+ "schema": {
385
+ "$ref": "#/components/schemas/ErrorDto"
386
+ }
387
+ }
388
+ }
389
+ },
390
+ "401": {
391
+ "description": "No key or token, or an invalid or revoked one."
392
+ },
393
+ "403": {
394
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
395
+ "content": {
396
+ "application/json": {
397
+ "schema": {
398
+ "$ref": "#/components/schemas/ErrorDto"
399
+ }
400
+ }
401
+ }
402
+ }
403
+ },
404
+ "security": [
405
+ {
406
+ "ApiKey": [ ]
407
+ }
408
+ ]
409
+ },
410
+ "post": {
411
+ "tags": [
412
+ "Assets"
413
+ ],
414
+ "summary": "Starts the next draft version of an existing asset.",
415
+ "operationId": "Assets.CreateVersion",
416
+ "parameters": [
417
+ {
418
+ "name": "project",
419
+ "in": "path",
420
+ "description": "The project's id, as in its URLs in the back office; a project also reads its organization's libraries through its own id.",
421
+ "required": true,
422
+ "schema": {
423
+ "type": "string"
424
+ }
425
+ },
426
+ {
427
+ "name": "id",
428
+ "in": "path",
429
+ "description": "The asset's id.",
430
+ "required": true,
431
+ "schema": {
432
+ "type": "string"
433
+ }
434
+ }
435
+ ],
436
+ "requestBody": {
437
+ "content": {
438
+ "application/json": {
439
+ "schema": {
440
+ "$ref": "#/components/schemas/CreateVersionRequest"
441
+ }
442
+ },
443
+ "text/json": {
444
+ "schema": {
445
+ "$ref": "#/components/schemas/CreateVersionRequest"
446
+ }
447
+ },
448
+ "application/*+json": {
449
+ "schema": {
450
+ "$ref": "#/components/schemas/CreateVersionRequest"
451
+ }
452
+ }
453
+ }
454
+ },
455
+ "responses": {
456
+ "201": {
457
+ "description": "Created",
458
+ "content": {
459
+ "application/json": {
460
+ "schema": {
461
+ "$ref": "#/components/schemas/AssetVersionDto"
462
+ }
463
+ }
464
+ }
465
+ },
466
+ "404": {
467
+ "description": "Not Found",
468
+ "content": {
469
+ "application/json": {
470
+ "schema": {
471
+ "$ref": "#/components/schemas/ErrorDto"
472
+ }
473
+ }
474
+ }
475
+ },
476
+ "409": {
477
+ "description": "Conflict",
478
+ "content": {
479
+ "application/json": {
480
+ "schema": {
481
+ "$ref": "#/components/schemas/ErrorDto"
482
+ }
483
+ }
484
+ }
485
+ },
486
+ "400": {
487
+ "description": "The body is invalid: `validation_failed`, with the messages per field in `errors`.",
488
+ "content": {
489
+ "application/json": {
490
+ "schema": {
491
+ "$ref": "#/components/schemas/ErrorDto"
492
+ }
493
+ }
494
+ }
495
+ },
496
+ "401": {
497
+ "description": "No key or token, or an invalid or revoked one."
498
+ },
499
+ "403": {
500
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
501
+ "content": {
502
+ "application/json": {
503
+ "schema": {
504
+ "$ref": "#/components/schemas/ErrorDto"
505
+ }
506
+ }
507
+ }
508
+ }
509
+ },
510
+ "security": [
511
+ {
512
+ "ApiKey": [ ]
513
+ }
514
+ ]
515
+ }
516
+ },
517
+ "/v1/projects/{project}/assets/{id}": {
518
+ "delete": {
519
+ "tags": [
520
+ "Assets"
521
+ ],
522
+ "summary": "Deletes an asset that isn't in prod: its versions, files and entries in every release and change set go, so no rollback brings it back, and a merged change set that held nothing else goes with it (SPEC.md 10).",
523
+ "description": "`asset_live` while it is in prod: take it out in a change set first. `asset_in_review` while a submitted or approved change set holds it, with that change set's name as the id: send it back first.",
524
+ "operationId": "Assets.Delete",
525
+ "parameters": [
526
+ {
527
+ "name": "project",
528
+ "in": "path",
529
+ "description": "The project's id, as in its URLs in the back office; a project also reads its organization's libraries through its own id.",
530
+ "required": true,
531
+ "schema": {
532
+ "type": "string"
533
+ }
534
+ },
535
+ {
536
+ "name": "id",
537
+ "in": "path",
538
+ "description": "The asset's id.",
539
+ "required": true,
540
+ "schema": {
541
+ "type": "string"
542
+ }
543
+ }
544
+ ],
545
+ "responses": {
546
+ "204": {
547
+ "description": "No Content"
548
+ },
549
+ "404": {
550
+ "description": "Not Found",
551
+ "content": {
552
+ "application/json": {
553
+ "schema": {
554
+ "$ref": "#/components/schemas/ErrorDto"
555
+ }
556
+ }
557
+ }
558
+ },
559
+ "409": {
560
+ "description": "Conflict",
561
+ "content": {
562
+ "application/json": {
563
+ "schema": {
564
+ "$ref": "#/components/schemas/ErrorDto"
565
+ }
566
+ }
567
+ }
568
+ },
569
+ "401": {
570
+ "description": "No key or token, or an invalid or revoked one."
571
+ },
572
+ "403": {
573
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
574
+ "content": {
575
+ "application/json": {
576
+ "schema": {
577
+ "$ref": "#/components/schemas/ErrorDto"
578
+ }
579
+ }
580
+ }
581
+ }
582
+ },
583
+ "security": [
584
+ {
585
+ "ApiKey": [ ]
586
+ }
587
+ ]
588
+ },
589
+ "get": {
590
+ "tags": [
591
+ "Assets"
592
+ ],
593
+ "summary": "The delivery API: the asset's version in the current release as an AssetResponse, a snapshot to embed (SPEC.md 5.2).",
594
+ "description": "`not_found` when there is no such asset, `not_released` when none of its versions is live. Apps and pages that hold the id read the same object from the edge instead, at `/assets/{org}/{id}.json`, with no key.",
595
+ "operationId": "Assets.Get",
596
+ "parameters": [
597
+ {
598
+ "name": "project",
599
+ "in": "path",
600
+ "description": "The project, or one that reads the asset's library.",
601
+ "required": true,
602
+ "schema": {
603
+ "type": "string"
604
+ }
605
+ },
606
+ {
607
+ "name": "id",
608
+ "in": "path",
609
+ "description": "The asset's id.",
610
+ "required": true,
611
+ "schema": {
612
+ "type": "string"
613
+ }
614
+ },
615
+ {
616
+ "name": "Accept-Language",
617
+ "in": "header",
618
+ "description": "The languages wanted, in order; the alt text and language-specific files follow the first one the project has (SPEC.md 5.5).",
619
+ "schema": {
620
+ "type": "string"
621
+ }
622
+ },
623
+ {
624
+ "name": "Asset-Change-Set",
625
+ "in": "header",
626
+ "description": "An open change set's id: the response is the current release with it applied, for previews (SPEC.md 21.3).",
627
+ "schema": {
628
+ "type": "string"
629
+ }
630
+ }
631
+ ],
632
+ "responses": {
633
+ "200": {
634
+ "description": "OK",
635
+ "headers": {
636
+ "Asset-Release": {
637
+ "description": "The release that answered, such as 12, or shared@3 for a library's asset.",
638
+ "schema": {
639
+ "type": "string"
640
+ }
641
+ },
642
+ "Content-Language": {
643
+ "description": "The language the alt text and files are in.",
644
+ "schema": {
645
+ "type": "string"
646
+ }
647
+ },
648
+ "Vary": {
649
+ "description": "The request headers the response depends on; cache by them.",
650
+ "schema": {
651
+ "type": "string"
652
+ }
653
+ }
654
+ },
655
+ "content": {
656
+ "application/json": {
657
+ "schema": {
658
+ "$ref": "#/components/schemas/AssetResponse"
659
+ }
660
+ }
661
+ }
662
+ },
663
+ "404": {
664
+ "description": "Not Found",
665
+ "content": {
666
+ "application/json": {
667
+ "schema": {
668
+ "$ref": "#/components/schemas/ErrorDto"
669
+ }
670
+ }
671
+ }
672
+ },
673
+ "401": {
674
+ "description": "No key or token, or an invalid or revoked one."
675
+ },
676
+ "403": {
677
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
678
+ "content": {
679
+ "application/json": {
680
+ "schema": {
681
+ "$ref": "#/components/schemas/ErrorDto"
682
+ }
683
+ }
684
+ }
685
+ }
686
+ },
687
+ "security": [
688
+ {
689
+ "ApiKey": [ ]
690
+ }
691
+ ]
692
+ }
693
+ },
694
+ "/v1/projects/{project}/assets/{id}/versions/{version}": {
695
+ "delete": {
696
+ "tags": [
697
+ "Assets"
698
+ ],
699
+ "summary": "Deletes a version that isn't in prod: its files and entries in every release and change set go, and its number is never given out again (SPEC.md 10).",
700
+ "description": "`version_live` while it is in prod. `version_in_review` while a submitted or approved change set holds it, with that change set's name as the id. `only_version` for an asset's last version: delete the asset instead.",
701
+ "operationId": "Assets.DeleteVersion",
702
+ "parameters": [
703
+ {
704
+ "name": "project",
705
+ "in": "path",
706
+ "description": "The project's id, as in its URLs in the back office; a project also reads its organization's libraries through its own id.",
707
+ "required": true,
708
+ "schema": {
709
+ "type": "string"
710
+ }
711
+ },
712
+ {
713
+ "name": "id",
714
+ "in": "path",
715
+ "description": "The asset's id.",
716
+ "required": true,
717
+ "schema": {
718
+ "type": "string"
719
+ }
720
+ },
721
+ {
722
+ "name": "version",
723
+ "in": "path",
724
+ "description": "The version number, from 1.",
725
+ "required": true,
726
+ "schema": {
727
+ "type": "integer",
728
+ "format": "int32"
729
+ }
730
+ }
731
+ ],
732
+ "responses": {
733
+ "204": {
734
+ "description": "No Content"
735
+ },
736
+ "404": {
737
+ "description": "Not Found",
738
+ "content": {
739
+ "application/json": {
740
+ "schema": {
741
+ "$ref": "#/components/schemas/ErrorDto"
742
+ }
743
+ }
744
+ }
745
+ },
746
+ "409": {
747
+ "description": "Conflict",
748
+ "content": {
749
+ "application/json": {
750
+ "schema": {
751
+ "$ref": "#/components/schemas/ErrorDto"
752
+ }
753
+ }
754
+ }
755
+ },
756
+ "401": {
757
+ "description": "No key or token, or an invalid or revoked one."
758
+ },
759
+ "403": {
760
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
761
+ "content": {
762
+ "application/json": {
763
+ "schema": {
764
+ "$ref": "#/components/schemas/ErrorDto"
765
+ }
766
+ }
767
+ }
768
+ }
769
+ },
770
+ "security": [
771
+ {
772
+ "ApiKey": [ ]
773
+ }
774
+ ]
775
+ },
776
+ "get": {
777
+ "tags": [
778
+ "Assets"
779
+ ],
780
+ "summary": "The version's slots: which source files its preset needs, and which are uploaded (SPEC.md 9.1). Poll it after completing an upload until the status is \"Ready\" or \"Failed\".",
781
+ "operationId": "Assets.GetVersion",
782
+ "parameters": [
783
+ {
784
+ "name": "project",
785
+ "in": "path",
786
+ "description": "The project's id, as in its URLs in the back office; a project also reads its organization's libraries through its own id.",
787
+ "required": true,
788
+ "schema": {
789
+ "type": "string"
790
+ }
791
+ },
792
+ {
793
+ "name": "id",
794
+ "in": "path",
795
+ "description": "The asset's id.",
796
+ "required": true,
797
+ "schema": {
798
+ "type": "string"
799
+ }
800
+ },
801
+ {
802
+ "name": "version",
803
+ "in": "path",
804
+ "description": "The version number, from 1.",
805
+ "required": true,
806
+ "schema": {
807
+ "type": "integer",
808
+ "format": "int32"
809
+ }
810
+ }
811
+ ],
812
+ "responses": {
813
+ "200": {
814
+ "description": "OK",
815
+ "content": {
816
+ "application/json": {
817
+ "schema": {
818
+ "$ref": "#/components/schemas/AssetVersionDto"
819
+ }
820
+ }
821
+ }
822
+ },
823
+ "404": {
824
+ "description": "Not Found",
825
+ "content": {
826
+ "application/json": {
827
+ "schema": {
828
+ "$ref": "#/components/schemas/ErrorDto"
829
+ }
830
+ }
831
+ }
832
+ },
833
+ "401": {
834
+ "description": "No key or token, or an invalid or revoked one."
835
+ },
836
+ "403": {
837
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
838
+ "content": {
839
+ "application/json": {
840
+ "schema": {
841
+ "$ref": "#/components/schemas/ErrorDto"
842
+ }
843
+ }
844
+ }
845
+ }
846
+ },
847
+ "security": [
848
+ {
849
+ "ApiKey": [ ]
850
+ }
851
+ ]
852
+ }
853
+ },
854
+ "/v1/projects/{project}/assets/{id}/versions/{version}/slots/{slot}/upload-url": {
855
+ "post": {
856
+ "tags": [
857
+ "Assets"
858
+ ],
859
+ "summary": "Returns a presigned URL to PUT one slot's source file to.",
860
+ "description": "Slots are named like `dark.still.source` or `nb.light.still.source` (SPEC.md 9.1). The slot must be one the preset has (`slot_not_in_preset`) and the version still a draft (`version_not_draft`). PUT the bytes to the URL with the file's Content-Type, then complete the slot.",
861
+ "operationId": "Assets.RequestSlotUpload",
862
+ "parameters": [
863
+ {
864
+ "name": "project",
865
+ "in": "path",
866
+ "description": "The project's id, as in its URLs in the back office; a project also reads its organization's libraries through its own id.",
867
+ "required": true,
868
+ "schema": {
869
+ "type": "string"
870
+ }
871
+ },
872
+ {
873
+ "name": "id",
874
+ "in": "path",
875
+ "description": "The asset's id.",
876
+ "required": true,
877
+ "schema": {
878
+ "type": "string"
879
+ }
880
+ },
881
+ {
882
+ "name": "version",
883
+ "in": "path",
884
+ "description": "The version number, from 1.",
885
+ "required": true,
886
+ "schema": {
887
+ "type": "integer",
888
+ "format": "int32"
889
+ }
890
+ },
891
+ {
892
+ "name": "slot",
893
+ "in": "path",
894
+ "description": "The slot, such as any.still.source, dark.still.source or nb.light.still.source (SPEC.md 9.1).",
895
+ "required": true,
896
+ "schema": {
897
+ "type": "string"
898
+ }
899
+ }
900
+ ],
901
+ "responses": {
902
+ "200": {
903
+ "description": "OK",
904
+ "content": {
905
+ "application/json": {
906
+ "schema": {
907
+ "$ref": "#/components/schemas/SourceUploadDto"
908
+ }
909
+ }
910
+ }
911
+ },
912
+ "404": {
913
+ "description": "Not Found",
914
+ "content": {
915
+ "application/json": {
916
+ "schema": {
917
+ "$ref": "#/components/schemas/ErrorDto"
918
+ }
919
+ }
920
+ }
921
+ },
922
+ "409": {
923
+ "description": "Conflict",
924
+ "content": {
925
+ "application/json": {
926
+ "schema": {
927
+ "$ref": "#/components/schemas/ErrorDto"
928
+ }
929
+ }
930
+ }
931
+ },
932
+ "401": {
933
+ "description": "No key or token, or an invalid or revoked one."
934
+ },
935
+ "403": {
936
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
937
+ "content": {
938
+ "application/json": {
939
+ "schema": {
940
+ "$ref": "#/components/schemas/ErrorDto"
941
+ }
942
+ }
943
+ }
944
+ }
945
+ },
946
+ "security": [
947
+ {
948
+ "ApiKey": [ ]
949
+ }
950
+ ]
951
+ }
952
+ },
953
+ "/v1/projects/{project}/assets/{id}/versions/{version}/slots/{slot}/complete": {
954
+ "post": {
955
+ "tags": [
956
+ "Assets"
957
+ ],
958
+ "summary": "Confirms a slot's file is uploaded. Processing starts when every required slot is.",
959
+ "description": "`upload_not_requested` when no upload URL was asked for, `source_missing` when nothing was PUT to it.",
960
+ "operationId": "Assets.CompleteSlotUpload",
961
+ "parameters": [
962
+ {
963
+ "name": "project",
964
+ "in": "path",
965
+ "description": "The project's id, as in its URLs in the back office; a project also reads its organization's libraries through its own id.",
966
+ "required": true,
967
+ "schema": {
968
+ "type": "string"
969
+ }
970
+ },
971
+ {
972
+ "name": "id",
973
+ "in": "path",
974
+ "description": "The asset's id.",
975
+ "required": true,
976
+ "schema": {
977
+ "type": "string"
978
+ }
979
+ },
980
+ {
981
+ "name": "version",
982
+ "in": "path",
983
+ "description": "The version number, from 1.",
984
+ "required": true,
985
+ "schema": {
986
+ "type": "integer",
987
+ "format": "int32"
988
+ }
989
+ },
990
+ {
991
+ "name": "slot",
992
+ "in": "path",
993
+ "description": "The slot, such as any.still.source, dark.still.source or nb.light.still.source (SPEC.md 9.1).",
994
+ "required": true,
995
+ "schema": {
996
+ "type": "string"
997
+ }
998
+ }
999
+ ],
1000
+ "responses": {
1001
+ "202": {
1002
+ "description": "Accepted",
1003
+ "content": {
1004
+ "application/json": {
1005
+ "schema": {
1006
+ "$ref": "#/components/schemas/AssetVersionDto"
1007
+ }
1008
+ }
1009
+ }
1010
+ },
1011
+ "404": {
1012
+ "description": "Not Found",
1013
+ "content": {
1014
+ "application/json": {
1015
+ "schema": {
1016
+ "$ref": "#/components/schemas/ErrorDto"
1017
+ }
1018
+ }
1019
+ }
1020
+ },
1021
+ "409": {
1022
+ "description": "Conflict",
1023
+ "content": {
1024
+ "application/json": {
1025
+ "schema": {
1026
+ "$ref": "#/components/schemas/ErrorDto"
1027
+ }
1028
+ }
1029
+ }
1030
+ },
1031
+ "401": {
1032
+ "description": "No key or token, or an invalid or revoked one."
1033
+ },
1034
+ "403": {
1035
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
1036
+ "content": {
1037
+ "application/json": {
1038
+ "schema": {
1039
+ "$ref": "#/components/schemas/ErrorDto"
1040
+ }
1041
+ }
1042
+ }
1043
+ }
1044
+ },
1045
+ "security": [
1046
+ {
1047
+ "ApiKey": [ ]
1048
+ }
1049
+ ]
1050
+ }
1051
+ },
1052
+ "/v1/projects/{project}/assets/{id}/versions/{version}/source/upload-url": {
1053
+ "post": {
1054
+ "tags": [
1055
+ "Assets"
1056
+ ],
1057
+ "summary": "Shorthand for the single slot of a flexible asset, any.still.source.",
1058
+ "operationId": "Assets.RequestSourceUpload",
1059
+ "parameters": [
1060
+ {
1061
+ "name": "project",
1062
+ "in": "path",
1063
+ "description": "The project's id, as in its URLs in the back office; a project also reads its organization's libraries through its own id.",
1064
+ "required": true,
1065
+ "schema": {
1066
+ "type": "string"
1067
+ }
1068
+ },
1069
+ {
1070
+ "name": "id",
1071
+ "in": "path",
1072
+ "description": "The asset's id.",
1073
+ "required": true,
1074
+ "schema": {
1075
+ "type": "string"
1076
+ }
1077
+ },
1078
+ {
1079
+ "name": "version",
1080
+ "in": "path",
1081
+ "description": "The version number, from 1.",
1082
+ "required": true,
1083
+ "schema": {
1084
+ "type": "integer",
1085
+ "format": "int32"
1086
+ }
1087
+ }
1088
+ ],
1089
+ "responses": {
1090
+ "200": {
1091
+ "description": "OK",
1092
+ "content": {
1093
+ "application/json": {
1094
+ "schema": {
1095
+ "$ref": "#/components/schemas/SourceUploadDto"
1096
+ }
1097
+ }
1098
+ }
1099
+ },
1100
+ "404": {
1101
+ "description": "Not Found",
1102
+ "content": {
1103
+ "application/json": {
1104
+ "schema": {
1105
+ "$ref": "#/components/schemas/ErrorDto"
1106
+ }
1107
+ }
1108
+ }
1109
+ },
1110
+ "409": {
1111
+ "description": "Conflict",
1112
+ "content": {
1113
+ "application/json": {
1114
+ "schema": {
1115
+ "$ref": "#/components/schemas/ErrorDto"
1116
+ }
1117
+ }
1118
+ }
1119
+ },
1120
+ "401": {
1121
+ "description": "No key or token, or an invalid or revoked one."
1122
+ },
1123
+ "403": {
1124
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
1125
+ "content": {
1126
+ "application/json": {
1127
+ "schema": {
1128
+ "$ref": "#/components/schemas/ErrorDto"
1129
+ }
1130
+ }
1131
+ }
1132
+ }
1133
+ },
1134
+ "security": [
1135
+ {
1136
+ "ApiKey": [ ]
1137
+ }
1138
+ ]
1139
+ }
1140
+ },
1141
+ "/v1/projects/{project}/assets/{id}/versions/{version}/source/complete": {
1142
+ "post": {
1143
+ "tags": [
1144
+ "Assets"
1145
+ ],
1146
+ "summary": "Shorthand for completing the single slot of a flexible asset.",
1147
+ "operationId": "Assets.CompleteSourceUpload",
1148
+ "parameters": [
1149
+ {
1150
+ "name": "project",
1151
+ "in": "path",
1152
+ "description": "The project's id, as in its URLs in the back office; a project also reads its organization's libraries through its own id.",
1153
+ "required": true,
1154
+ "schema": {
1155
+ "type": "string"
1156
+ }
1157
+ },
1158
+ {
1159
+ "name": "id",
1160
+ "in": "path",
1161
+ "description": "The asset's id.",
1162
+ "required": true,
1163
+ "schema": {
1164
+ "type": "string"
1165
+ }
1166
+ },
1167
+ {
1168
+ "name": "version",
1169
+ "in": "path",
1170
+ "description": "The version number, from 1.",
1171
+ "required": true,
1172
+ "schema": {
1173
+ "type": "integer",
1174
+ "format": "int32"
1175
+ }
1176
+ }
1177
+ ],
1178
+ "responses": {
1179
+ "202": {
1180
+ "description": "Accepted",
1181
+ "content": {
1182
+ "application/json": {
1183
+ "schema": {
1184
+ "$ref": "#/components/schemas/AssetVersionDto"
1185
+ }
1186
+ }
1187
+ }
1188
+ },
1189
+ "404": {
1190
+ "description": "Not Found",
1191
+ "content": {
1192
+ "application/json": {
1193
+ "schema": {
1194
+ "$ref": "#/components/schemas/ErrorDto"
1195
+ }
1196
+ }
1197
+ }
1198
+ },
1199
+ "409": {
1200
+ "description": "Conflict",
1201
+ "content": {
1202
+ "application/json": {
1203
+ "schema": {
1204
+ "$ref": "#/components/schemas/ErrorDto"
1205
+ }
1206
+ }
1207
+ }
1208
+ },
1209
+ "401": {
1210
+ "description": "No key or token, or an invalid or revoked one."
1211
+ },
1212
+ "403": {
1213
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
1214
+ "content": {
1215
+ "application/json": {
1216
+ "schema": {
1217
+ "$ref": "#/components/schemas/ErrorDto"
1218
+ }
1219
+ }
1220
+ }
1221
+ }
1222
+ },
1223
+ "security": [
1224
+ {
1225
+ "ApiKey": [ ]
1226
+ }
1227
+ ]
1228
+ }
1229
+ },
1230
+ "/v1/projects/{project}/assets/{id}/versions/{version}/submit": {
1231
+ "post": {
1232
+ "tags": [
1233
+ "Assets"
1234
+ ],
1235
+ "summary": "Adds a processed version to a change set, or to a new one with just this change (SPEC.md 21.1).",
1236
+ "description": "`version_not_ready` until processing has finished.",
1237
+ "operationId": "Assets.SubmitVersion",
1238
+ "parameters": [
1239
+ {
1240
+ "name": "project",
1241
+ "in": "path",
1242
+ "description": "The project's id, as in its URLs in the back office; a project also reads its organization's libraries through its own id.",
1243
+ "required": true,
1244
+ "schema": {
1245
+ "type": "string"
1246
+ }
1247
+ },
1248
+ {
1249
+ "name": "id",
1250
+ "in": "path",
1251
+ "description": "The asset's id.",
1252
+ "required": true,
1253
+ "schema": {
1254
+ "type": "string"
1255
+ }
1256
+ },
1257
+ {
1258
+ "name": "version",
1259
+ "in": "path",
1260
+ "description": "The version number, from 1.",
1261
+ "required": true,
1262
+ "schema": {
1263
+ "type": "integer",
1264
+ "format": "int32"
1265
+ }
1266
+ }
1267
+ ],
1268
+ "requestBody": {
1269
+ "content": {
1270
+ "application/json": {
1271
+ "schema": {
1272
+ "$ref": "#/components/schemas/SubmitVersionRequest"
1273
+ }
1274
+ },
1275
+ "text/json": {
1276
+ "schema": {
1277
+ "$ref": "#/components/schemas/SubmitVersionRequest"
1278
+ }
1279
+ },
1280
+ "application/*+json": {
1281
+ "schema": {
1282
+ "$ref": "#/components/schemas/SubmitVersionRequest"
1283
+ }
1284
+ }
1285
+ }
1286
+ },
1287
+ "responses": {
1288
+ "200": {
1289
+ "description": "OK",
1290
+ "content": {
1291
+ "application/json": {
1292
+ "schema": {
1293
+ "$ref": "#/components/schemas/ChangeSetDto"
1294
+ }
1295
+ }
1296
+ }
1297
+ },
1298
+ "404": {
1299
+ "description": "Not Found",
1300
+ "content": {
1301
+ "application/json": {
1302
+ "schema": {
1303
+ "$ref": "#/components/schemas/ErrorDto"
1304
+ }
1305
+ }
1306
+ }
1307
+ },
1308
+ "409": {
1309
+ "description": "Conflict",
1310
+ "content": {
1311
+ "application/json": {
1312
+ "schema": {
1313
+ "$ref": "#/components/schemas/ErrorDto"
1314
+ }
1315
+ }
1316
+ }
1317
+ },
1318
+ "400": {
1319
+ "description": "The body is invalid: `validation_failed`, with the messages per field in `errors`.",
1320
+ "content": {
1321
+ "application/json": {
1322
+ "schema": {
1323
+ "$ref": "#/components/schemas/ErrorDto"
1324
+ }
1325
+ }
1326
+ }
1327
+ },
1328
+ "401": {
1329
+ "description": "No key or token, or an invalid or revoked one."
1330
+ },
1331
+ "403": {
1332
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
1333
+ "content": {
1334
+ "application/json": {
1335
+ "schema": {
1336
+ "$ref": "#/components/schemas/ErrorDto"
1337
+ }
1338
+ }
1339
+ }
1340
+ }
1341
+ },
1342
+ "security": [
1343
+ {
1344
+ "ApiKey": [ ]
1345
+ }
1346
+ ]
1347
+ }
1348
+ },
1349
+ "/v1/projects/{project}/change-sets": {
1350
+ "get": {
1351
+ "tags": [
1352
+ "Change sets"
1353
+ ],
1354
+ "summary": "The project's change sets, newest first, merged ones included.",
1355
+ "operationId": "ChangeSets.List",
1356
+ "parameters": [
1357
+ {
1358
+ "name": "project",
1359
+ "in": "path",
1360
+ "description": "The project's id, as in its URLs in the back office; a project also reads its organization's libraries through its own id.",
1361
+ "required": true,
1362
+ "schema": {
1363
+ "type": "string"
1364
+ }
1365
+ }
1366
+ ],
1367
+ "responses": {
1368
+ "200": {
1369
+ "description": "OK",
1370
+ "content": {
1371
+ "application/json": {
1372
+ "schema": {
1373
+ "type": "array",
1374
+ "items": {
1375
+ "$ref": "#/components/schemas/ChangeSetDto"
1376
+ }
1377
+ }
1378
+ }
1379
+ }
1380
+ },
1381
+ "401": {
1382
+ "description": "No key or token, or an invalid or revoked one."
1383
+ },
1384
+ "403": {
1385
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
1386
+ "content": {
1387
+ "application/json": {
1388
+ "schema": {
1389
+ "$ref": "#/components/schemas/ErrorDto"
1390
+ }
1391
+ }
1392
+ }
1393
+ }
1394
+ },
1395
+ "security": [
1396
+ {
1397
+ "ApiKey": [ ]
1398
+ }
1399
+ ]
1400
+ },
1401
+ "post": {
1402
+ "tags": [
1403
+ "Change sets"
1404
+ ],
1405
+ "summary": "Opens an empty change set to add changes to.",
1406
+ "operationId": "ChangeSets.Create",
1407
+ "parameters": [
1408
+ {
1409
+ "name": "project",
1410
+ "in": "path",
1411
+ "description": "The project's id, as in its URLs in the back office; a project also reads its organization's libraries through its own id.",
1412
+ "required": true,
1413
+ "schema": {
1414
+ "type": "string"
1415
+ }
1416
+ }
1417
+ ],
1418
+ "requestBody": {
1419
+ "content": {
1420
+ "application/json": {
1421
+ "schema": {
1422
+ "$ref": "#/components/schemas/CreateChangeSetRequest"
1423
+ }
1424
+ },
1425
+ "text/json": {
1426
+ "schema": {
1427
+ "$ref": "#/components/schemas/CreateChangeSetRequest"
1428
+ }
1429
+ },
1430
+ "application/*+json": {
1431
+ "schema": {
1432
+ "$ref": "#/components/schemas/CreateChangeSetRequest"
1433
+ }
1434
+ }
1435
+ }
1436
+ },
1437
+ "responses": {
1438
+ "201": {
1439
+ "description": "Created",
1440
+ "content": {
1441
+ "application/json": {
1442
+ "schema": {
1443
+ "$ref": "#/components/schemas/ChangeSetDto"
1444
+ }
1445
+ }
1446
+ }
1447
+ },
1448
+ "400": {
1449
+ "description": "The body is invalid: `validation_failed`, with the messages per field in `errors`.",
1450
+ "content": {
1451
+ "application/json": {
1452
+ "schema": {
1453
+ "$ref": "#/components/schemas/ErrorDto"
1454
+ }
1455
+ }
1456
+ }
1457
+ },
1458
+ "401": {
1459
+ "description": "No key or token, or an invalid or revoked one."
1460
+ },
1461
+ "403": {
1462
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
1463
+ "content": {
1464
+ "application/json": {
1465
+ "schema": {
1466
+ "$ref": "#/components/schemas/ErrorDto"
1467
+ }
1468
+ }
1469
+ }
1470
+ }
1471
+ },
1472
+ "security": [
1473
+ {
1474
+ "ApiKey": [ ]
1475
+ }
1476
+ ]
1477
+ }
1478
+ },
1479
+ "/v1/projects/{project}/change-sets/{id}": {
1480
+ "get": {
1481
+ "tags": [
1482
+ "Change sets"
1483
+ ],
1484
+ "summary": "The change set with its diff against prod, including conflicts.",
1485
+ "operationId": "ChangeSets.Get",
1486
+ "parameters": [
1487
+ {
1488
+ "name": "project",
1489
+ "in": "path",
1490
+ "description": "The project's id, as in its URLs in the back office; a project also reads its organization's libraries through its own id.",
1491
+ "required": true,
1492
+ "schema": {
1493
+ "type": "string"
1494
+ }
1495
+ },
1496
+ {
1497
+ "name": "id",
1498
+ "in": "path",
1499
+ "description": "The change set's id.",
1500
+ "required": true,
1501
+ "schema": {
1502
+ "type": "string"
1503
+ }
1504
+ }
1505
+ ],
1506
+ "responses": {
1507
+ "200": {
1508
+ "description": "OK",
1509
+ "content": {
1510
+ "application/json": {
1511
+ "schema": {
1512
+ "$ref": "#/components/schemas/ChangeSetDto"
1513
+ }
1514
+ }
1515
+ }
1516
+ },
1517
+ "404": {
1518
+ "description": "Not Found",
1519
+ "content": {
1520
+ "application/json": {
1521
+ "schema": {
1522
+ "$ref": "#/components/schemas/ErrorDto"
1523
+ }
1524
+ }
1525
+ }
1526
+ },
1527
+ "401": {
1528
+ "description": "No key or token, or an invalid or revoked one."
1529
+ },
1530
+ "403": {
1531
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
1532
+ "content": {
1533
+ "application/json": {
1534
+ "schema": {
1535
+ "$ref": "#/components/schemas/ErrorDto"
1536
+ }
1537
+ }
1538
+ }
1539
+ }
1540
+ },
1541
+ "security": [
1542
+ {
1543
+ "ApiKey": [ ]
1544
+ }
1545
+ ]
1546
+ },
1547
+ "delete": {
1548
+ "tags": [
1549
+ "Change sets"
1550
+ ],
1551
+ "summary": "Deletes a change set that hasn't merged. The versions in it stay with their assets.",
1552
+ "description": "`change_set_merged` once it has merged: a merged change set is part of the release history.",
1553
+ "operationId": "ChangeSets.Delete",
1554
+ "parameters": [
1555
+ {
1556
+ "name": "project",
1557
+ "in": "path",
1558
+ "description": "The project's id, as in its URLs in the back office; a project also reads its organization's libraries through its own id.",
1559
+ "required": true,
1560
+ "schema": {
1561
+ "type": "string"
1562
+ }
1563
+ },
1564
+ {
1565
+ "name": "id",
1566
+ "in": "path",
1567
+ "description": "The change set's id.",
1568
+ "required": true,
1569
+ "schema": {
1570
+ "type": "string"
1571
+ }
1572
+ }
1573
+ ],
1574
+ "responses": {
1575
+ "204": {
1576
+ "description": "No Content"
1577
+ },
1578
+ "404": {
1579
+ "description": "Not Found",
1580
+ "content": {
1581
+ "application/json": {
1582
+ "schema": {
1583
+ "$ref": "#/components/schemas/ErrorDto"
1584
+ }
1585
+ }
1586
+ }
1587
+ },
1588
+ "409": {
1589
+ "description": "Conflict",
1590
+ "content": {
1591
+ "application/json": {
1592
+ "schema": {
1593
+ "$ref": "#/components/schemas/ErrorDto"
1594
+ }
1595
+ }
1596
+ }
1597
+ },
1598
+ "401": {
1599
+ "description": "No key or token, or an invalid or revoked one."
1600
+ },
1601
+ "403": {
1602
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
1603
+ "content": {
1604
+ "application/json": {
1605
+ "schema": {
1606
+ "$ref": "#/components/schemas/ErrorDto"
1607
+ }
1608
+ }
1609
+ }
1610
+ }
1611
+ },
1612
+ "security": [
1613
+ {
1614
+ "ApiKey": [ ]
1615
+ }
1616
+ ]
1617
+ }
1618
+ },
1619
+ "/v1/projects/{project}/change-sets/{id}/changes": {
1620
+ "post": {
1621
+ "tags": [
1622
+ "Change sets"
1623
+ ],
1624
+ "summary": "Points an asset at a version, or takes it out of the release when version is null.",
1625
+ "description": "Only while the change set is open (`change_set_not_open`) and the version is processed (`version_not_ready`).",
1626
+ "operationId": "ChangeSets.AddChange",
1627
+ "parameters": [
1628
+ {
1629
+ "name": "project",
1630
+ "in": "path",
1631
+ "description": "The project's id, as in its URLs in the back office; a project also reads its organization's libraries through its own id.",
1632
+ "required": true,
1633
+ "schema": {
1634
+ "type": "string"
1635
+ }
1636
+ },
1637
+ {
1638
+ "name": "id",
1639
+ "in": "path",
1640
+ "description": "The change set's id.",
1641
+ "required": true,
1642
+ "schema": {
1643
+ "type": "string"
1644
+ }
1645
+ }
1646
+ ],
1647
+ "requestBody": {
1648
+ "content": {
1649
+ "application/json": {
1650
+ "schema": {
1651
+ "$ref": "#/components/schemas/AddChangeRequest"
1652
+ }
1653
+ },
1654
+ "text/json": {
1655
+ "schema": {
1656
+ "$ref": "#/components/schemas/AddChangeRequest"
1657
+ }
1658
+ },
1659
+ "application/*+json": {
1660
+ "schema": {
1661
+ "$ref": "#/components/schemas/AddChangeRequest"
1662
+ }
1663
+ }
1664
+ }
1665
+ },
1666
+ "responses": {
1667
+ "200": {
1668
+ "description": "OK",
1669
+ "content": {
1670
+ "application/json": {
1671
+ "schema": {
1672
+ "$ref": "#/components/schemas/ChangeSetDto"
1673
+ }
1674
+ }
1675
+ }
1676
+ },
1677
+ "404": {
1678
+ "description": "Not Found",
1679
+ "content": {
1680
+ "application/json": {
1681
+ "schema": {
1682
+ "$ref": "#/components/schemas/ErrorDto"
1683
+ }
1684
+ }
1685
+ }
1686
+ },
1687
+ "409": {
1688
+ "description": "Conflict",
1689
+ "content": {
1690
+ "application/json": {
1691
+ "schema": {
1692
+ "$ref": "#/components/schemas/ErrorDto"
1693
+ }
1694
+ }
1695
+ }
1696
+ },
1697
+ "400": {
1698
+ "description": "The body is invalid: `validation_failed`, with the messages per field in `errors`.",
1699
+ "content": {
1700
+ "application/json": {
1701
+ "schema": {
1702
+ "$ref": "#/components/schemas/ErrorDto"
1703
+ }
1704
+ }
1705
+ }
1706
+ },
1707
+ "401": {
1708
+ "description": "No key or token, or an invalid or revoked one."
1709
+ },
1710
+ "403": {
1711
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
1712
+ "content": {
1713
+ "application/json": {
1714
+ "schema": {
1715
+ "$ref": "#/components/schemas/ErrorDto"
1716
+ }
1717
+ }
1718
+ }
1719
+ }
1720
+ },
1721
+ "security": [
1722
+ {
1723
+ "ApiKey": [ ]
1724
+ }
1725
+ ]
1726
+ }
1727
+ },
1728
+ "/v1/projects/{project}/change-sets/{id}/submit": {
1729
+ "post": {
1730
+ "tags": [
1731
+ "Change sets"
1732
+ ],
1733
+ "summary": "Sends the change set for review.",
1734
+ "description": "`change_set_empty` when it has no changes.",
1735
+ "operationId": "ChangeSets.Submit",
1736
+ "parameters": [
1737
+ {
1738
+ "name": "project",
1739
+ "in": "path",
1740
+ "description": "The project's id, as in its URLs in the back office; a project also reads its organization's libraries through its own id.",
1741
+ "required": true,
1742
+ "schema": {
1743
+ "type": "string"
1744
+ }
1745
+ },
1746
+ {
1747
+ "name": "id",
1748
+ "in": "path",
1749
+ "description": "The change set's id.",
1750
+ "required": true,
1751
+ "schema": {
1752
+ "type": "string"
1753
+ }
1754
+ }
1755
+ ],
1756
+ "responses": {
1757
+ "200": {
1758
+ "description": "OK",
1759
+ "content": {
1760
+ "application/json": {
1761
+ "schema": {
1762
+ "$ref": "#/components/schemas/ChangeSetDto"
1763
+ }
1764
+ }
1765
+ }
1766
+ },
1767
+ "404": {
1768
+ "description": "Not Found",
1769
+ "content": {
1770
+ "application/json": {
1771
+ "schema": {
1772
+ "$ref": "#/components/schemas/ErrorDto"
1773
+ }
1774
+ }
1775
+ }
1776
+ },
1777
+ "409": {
1778
+ "description": "Conflict",
1779
+ "content": {
1780
+ "application/json": {
1781
+ "schema": {
1782
+ "$ref": "#/components/schemas/ErrorDto"
1783
+ }
1784
+ }
1785
+ }
1786
+ },
1787
+ "401": {
1788
+ "description": "No key or token, or an invalid or revoked one."
1789
+ },
1790
+ "403": {
1791
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
1792
+ "content": {
1793
+ "application/json": {
1794
+ "schema": {
1795
+ "$ref": "#/components/schemas/ErrorDto"
1796
+ }
1797
+ }
1798
+ }
1799
+ }
1800
+ },
1801
+ "security": [
1802
+ {
1803
+ "ApiKey": [ ]
1804
+ }
1805
+ ]
1806
+ }
1807
+ },
1808
+ "/v1/projects/{project}/change-sets/{id}/approve": {
1809
+ "post": {
1810
+ "tags": [
1811
+ "Change sets"
1812
+ ],
1813
+ "summary": "Approves a submitted change set, by a person other than its author.",
1814
+ "description": "`own_change_set` when the author tries, unless the project's review policy allows self-approval.",
1815
+ "operationId": "ChangeSets.Approve",
1816
+ "parameters": [
1817
+ {
1818
+ "name": "project",
1819
+ "in": "path",
1820
+ "description": "The project's id, as in its URLs in the back office; a project also reads its organization's libraries through its own id.",
1821
+ "required": true,
1822
+ "schema": {
1823
+ "type": "string"
1824
+ }
1825
+ },
1826
+ {
1827
+ "name": "id",
1828
+ "in": "path",
1829
+ "description": "The change set's id.",
1830
+ "required": true,
1831
+ "schema": {
1832
+ "type": "string"
1833
+ }
1834
+ }
1835
+ ],
1836
+ "responses": {
1837
+ "200": {
1838
+ "description": "OK",
1839
+ "content": {
1840
+ "application/json": {
1841
+ "schema": {
1842
+ "$ref": "#/components/schemas/ChangeSetDto"
1843
+ }
1844
+ }
1845
+ }
1846
+ },
1847
+ "404": {
1848
+ "description": "Not Found",
1849
+ "content": {
1850
+ "application/json": {
1851
+ "schema": {
1852
+ "$ref": "#/components/schemas/ErrorDto"
1853
+ }
1854
+ }
1855
+ }
1856
+ },
1857
+ "409": {
1858
+ "description": "Conflict",
1859
+ "content": {
1860
+ "application/json": {
1861
+ "schema": {
1862
+ "$ref": "#/components/schemas/ErrorDto"
1863
+ }
1864
+ }
1865
+ }
1866
+ },
1867
+ "401": {
1868
+ "description": "No key or token, or an invalid or revoked one."
1869
+ },
1870
+ "403": {
1871
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
1872
+ "content": {
1873
+ "application/json": {
1874
+ "schema": {
1875
+ "$ref": "#/components/schemas/ErrorDto"
1876
+ }
1877
+ }
1878
+ }
1879
+ }
1880
+ },
1881
+ "security": [
1882
+ {
1883
+ "ApiKey": [ ]
1884
+ }
1885
+ ]
1886
+ }
1887
+ },
1888
+ "/v1/projects/{project}/change-sets/{id}/merge": {
1889
+ "post": {
1890
+ "tags": [
1891
+ "Change sets"
1892
+ ],
1893
+ "summary": "Merges an approved change set into a new release now, or at a scheduled time.",
1894
+ "description": "Refused while an asset is in conflict (`conflicts`, with the asset ids) and when another merge got there first (`concurrent_release`). Merging is done by a person: keys cannot approve or merge.",
1895
+ "operationId": "ChangeSets.Merge",
1896
+ "parameters": [
1897
+ {
1898
+ "name": "project",
1899
+ "in": "path",
1900
+ "description": "The project's id, as in its URLs in the back office; a project also reads its organization's libraries through its own id.",
1901
+ "required": true,
1902
+ "schema": {
1903
+ "type": "string"
1904
+ }
1905
+ },
1906
+ {
1907
+ "name": "id",
1908
+ "in": "path",
1909
+ "description": "The change set's id.",
1910
+ "required": true,
1911
+ "schema": {
1912
+ "type": "string"
1913
+ }
1914
+ }
1915
+ ],
1916
+ "requestBody": {
1917
+ "content": {
1918
+ "application/json": {
1919
+ "schema": {
1920
+ "$ref": "#/components/schemas/MergeRequest"
1921
+ }
1922
+ },
1923
+ "text/json": {
1924
+ "schema": {
1925
+ "$ref": "#/components/schemas/MergeRequest"
1926
+ }
1927
+ },
1928
+ "application/*+json": {
1929
+ "schema": {
1930
+ "$ref": "#/components/schemas/MergeRequest"
1931
+ }
1932
+ }
1933
+ }
1934
+ },
1935
+ "responses": {
1936
+ "200": {
1937
+ "description": "OK",
1938
+ "content": {
1939
+ "application/json": {
1940
+ "schema": {
1941
+ "$ref": "#/components/schemas/ChangeSetDto"
1942
+ }
1943
+ }
1944
+ }
1945
+ },
1946
+ "404": {
1947
+ "description": "Not Found",
1948
+ "content": {
1949
+ "application/json": {
1950
+ "schema": {
1951
+ "$ref": "#/components/schemas/ErrorDto"
1952
+ }
1953
+ }
1954
+ }
1955
+ },
1956
+ "409": {
1957
+ "description": "Conflict",
1958
+ "content": {
1959
+ "application/json": {
1960
+ "schema": {
1961
+ "$ref": "#/components/schemas/ErrorDto"
1962
+ }
1963
+ }
1964
+ }
1965
+ },
1966
+ "400": {
1967
+ "description": "The body is invalid: `validation_failed`, with the messages per field in `errors`.",
1968
+ "content": {
1969
+ "application/json": {
1970
+ "schema": {
1971
+ "$ref": "#/components/schemas/ErrorDto"
1972
+ }
1973
+ }
1974
+ }
1975
+ },
1976
+ "401": {
1977
+ "description": "No key or token, or an invalid or revoked one."
1978
+ },
1979
+ "403": {
1980
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
1981
+ "content": {
1982
+ "application/json": {
1983
+ "schema": {
1984
+ "$ref": "#/components/schemas/ErrorDto"
1985
+ }
1986
+ }
1987
+ }
1988
+ }
1989
+ },
1990
+ "security": [
1991
+ {
1992
+ "ApiKey": [ ]
1993
+ }
1994
+ ]
1995
+ }
1996
+ },
1997
+ "/v1/projects/{project}/change-sets/{id}/withdraw": {
1998
+ "post": {
1999
+ "tags": [
2000
+ "Change sets"
2001
+ ],
2002
+ "summary": "Takes a submitted or approved change set back to open, so editors can change it again; a scheduled merge is cancelled.",
2003
+ "description": "`change_set_merged` once it has merged, `change_set_open` when there is nothing to withdraw.",
2004
+ "operationId": "ChangeSets.Withdraw",
2005
+ "parameters": [
2006
+ {
2007
+ "name": "project",
2008
+ "in": "path",
2009
+ "description": "The project's id, as in its URLs in the back office; a project also reads its organization's libraries through its own id.",
2010
+ "required": true,
2011
+ "schema": {
2012
+ "type": "string"
2013
+ }
2014
+ },
2015
+ {
2016
+ "name": "id",
2017
+ "in": "path",
2018
+ "description": "The change set's id.",
2019
+ "required": true,
2020
+ "schema": {
2021
+ "type": "string"
2022
+ }
2023
+ }
2024
+ ],
2025
+ "responses": {
2026
+ "200": {
2027
+ "description": "OK",
2028
+ "content": {
2029
+ "application/json": {
2030
+ "schema": {
2031
+ "$ref": "#/components/schemas/ChangeSetDto"
2032
+ }
2033
+ }
2034
+ }
2035
+ },
2036
+ "404": {
2037
+ "description": "Not Found",
2038
+ "content": {
2039
+ "application/json": {
2040
+ "schema": {
2041
+ "$ref": "#/components/schemas/ErrorDto"
2042
+ }
2043
+ }
2044
+ }
2045
+ },
2046
+ "409": {
2047
+ "description": "Conflict",
2048
+ "content": {
2049
+ "application/json": {
2050
+ "schema": {
2051
+ "$ref": "#/components/schemas/ErrorDto"
2052
+ }
2053
+ }
2054
+ }
2055
+ },
2056
+ "401": {
2057
+ "description": "No key or token, or an invalid or revoked one."
2058
+ },
2059
+ "403": {
2060
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
2061
+ "content": {
2062
+ "application/json": {
2063
+ "schema": {
2064
+ "$ref": "#/components/schemas/ErrorDto"
2065
+ }
2066
+ }
2067
+ }
2068
+ }
2069
+ },
2070
+ "security": [
2071
+ {
2072
+ "ApiKey": [ ]
2073
+ }
2074
+ ]
2075
+ }
2076
+ },
2077
+ "/v1/projects/{project}/change-sets/{id}/resolve": {
2078
+ "post": {
2079
+ "tags": [
2080
+ "Change sets"
2081
+ ],
2082
+ "summary": "Settles a conflict for one asset: keep \"mine\" (this change set's version) or \"prod\".",
2083
+ "operationId": "ChangeSets.Resolve",
2084
+ "parameters": [
2085
+ {
2086
+ "name": "project",
2087
+ "in": "path",
2088
+ "description": "The project's id, as in its URLs in the back office; a project also reads its organization's libraries through its own id.",
2089
+ "required": true,
2090
+ "schema": {
2091
+ "type": "string"
2092
+ }
2093
+ },
2094
+ {
2095
+ "name": "id",
2096
+ "in": "path",
2097
+ "description": "The change set's id.",
2098
+ "required": true,
2099
+ "schema": {
2100
+ "type": "string"
2101
+ }
2102
+ }
2103
+ ],
2104
+ "requestBody": {
2105
+ "content": {
2106
+ "application/json": {
2107
+ "schema": {
2108
+ "$ref": "#/components/schemas/ResolveConflictRequest"
2109
+ }
2110
+ },
2111
+ "text/json": {
2112
+ "schema": {
2113
+ "$ref": "#/components/schemas/ResolveConflictRequest"
2114
+ }
2115
+ },
2116
+ "application/*+json": {
2117
+ "schema": {
2118
+ "$ref": "#/components/schemas/ResolveConflictRequest"
2119
+ }
2120
+ }
2121
+ }
2122
+ },
2123
+ "responses": {
2124
+ "200": {
2125
+ "description": "OK",
2126
+ "content": {
2127
+ "application/json": {
2128
+ "schema": {
2129
+ "$ref": "#/components/schemas/ChangeSetDto"
2130
+ }
2131
+ }
2132
+ }
2133
+ },
2134
+ "404": {
2135
+ "description": "Not Found",
2136
+ "content": {
2137
+ "application/json": {
2138
+ "schema": {
2139
+ "$ref": "#/components/schemas/ErrorDto"
2140
+ }
2141
+ }
2142
+ }
2143
+ },
2144
+ "409": {
2145
+ "description": "Conflict",
2146
+ "content": {
2147
+ "application/json": {
2148
+ "schema": {
2149
+ "$ref": "#/components/schemas/ErrorDto"
2150
+ }
2151
+ }
2152
+ }
2153
+ },
2154
+ "400": {
2155
+ "description": "The body is invalid: `validation_failed`, with the messages per field in `errors`.",
2156
+ "content": {
2157
+ "application/json": {
2158
+ "schema": {
2159
+ "$ref": "#/components/schemas/ErrorDto"
2160
+ }
2161
+ }
2162
+ }
2163
+ },
2164
+ "401": {
2165
+ "description": "No key or token, or an invalid or revoked one."
2166
+ },
2167
+ "403": {
2168
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
2169
+ "content": {
2170
+ "application/json": {
2171
+ "schema": {
2172
+ "$ref": "#/components/schemas/ErrorDto"
2173
+ }
2174
+ }
2175
+ }
2176
+ }
2177
+ },
2178
+ "security": [
2179
+ {
2180
+ "ApiKey": [ ]
2181
+ }
2182
+ ]
2183
+ }
2184
+ },
2185
+ "/v1/projects/{project}": {
2186
+ "get": {
2187
+ "tags": [
2188
+ "Projects"
2189
+ ],
2190
+ "summary": "The project's name and languages, for clients such as the Figma plugin and pipelines that need to know which languages alt text takes.",
2191
+ "operationId": "Projects.Get",
2192
+ "parameters": [
2193
+ {
2194
+ "name": "project",
2195
+ "in": "path",
2196
+ "description": "The project's id, as in its URLs in the back office; a project also reads its organization's libraries through its own id.",
2197
+ "required": true,
2198
+ "schema": {
2199
+ "type": "string"
2200
+ }
2201
+ }
2202
+ ],
2203
+ "responses": {
2204
+ "200": {
2205
+ "description": "OK",
2206
+ "content": {
2207
+ "application/json": {
2208
+ "schema": {
2209
+ "$ref": "#/components/schemas/ProjectDto"
2210
+ }
2211
+ }
2212
+ }
2213
+ },
2214
+ "404": {
2215
+ "description": "Not Found",
2216
+ "content": {
2217
+ "application/json": {
2218
+ "schema": {
2219
+ "$ref": "#/components/schemas/ErrorDto"
2220
+ }
2221
+ }
2222
+ }
2223
+ },
2224
+ "401": {
2225
+ "description": "No key or token, or an invalid or revoked one."
2226
+ },
2227
+ "403": {
2228
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
2229
+ "content": {
2230
+ "application/json": {
2231
+ "schema": {
2232
+ "$ref": "#/components/schemas/ErrorDto"
2233
+ }
2234
+ }
2235
+ }
2236
+ }
2237
+ },
2238
+ "security": [
2239
+ {
2240
+ "ApiKey": [ ]
2241
+ }
2242
+ ]
2243
+ }
2244
+ },
2245
+ "/v1/projects/{project}/releases": {
2246
+ "get": {
2247
+ "tags": [
2248
+ "Releases"
2249
+ ],
2250
+ "summary": "Release history, newest (prod) first.",
2251
+ "operationId": "Releases.List",
2252
+ "parameters": [
2253
+ {
2254
+ "name": "project",
2255
+ "in": "path",
2256
+ "description": "The project's id, as in its URLs in the back office; a project also reads its organization's libraries through its own id.",
2257
+ "required": true,
2258
+ "schema": {
2259
+ "type": "string"
2260
+ }
2261
+ }
2262
+ ],
2263
+ "responses": {
2264
+ "200": {
2265
+ "description": "OK",
2266
+ "content": {
2267
+ "application/json": {
2268
+ "schema": {
2269
+ "type": "array",
2270
+ "items": {
2271
+ "$ref": "#/components/schemas/ReleaseDto"
2272
+ }
2273
+ }
2274
+ }
2275
+ }
2276
+ },
2277
+ "401": {
2278
+ "description": "No key or token, or an invalid or revoked one."
2279
+ },
2280
+ "403": {
2281
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
2282
+ "content": {
2283
+ "application/json": {
2284
+ "schema": {
2285
+ "$ref": "#/components/schemas/ErrorDto"
2286
+ }
2287
+ }
2288
+ }
2289
+ }
2290
+ },
2291
+ "security": [
2292
+ {
2293
+ "ApiKey": [ ]
2294
+ }
2295
+ ]
2296
+ }
2297
+ },
2298
+ "/v1/projects/{project}/releases/{number}/restore": {
2299
+ "post": {
2300
+ "tags": [
2301
+ "Releases"
2302
+ ],
2303
+ "summary": "Rolls prod back to release `number`'s contents, as a new release (SPEC.md 21.5).",
2304
+ "operationId": "Releases.Restore",
2305
+ "parameters": [
2306
+ {
2307
+ "name": "project",
2308
+ "in": "path",
2309
+ "description": "The project's id, as in its URLs in the back office; a project also reads its organization's libraries through its own id.",
2310
+ "required": true,
2311
+ "schema": {
2312
+ "type": "string"
2313
+ }
2314
+ },
2315
+ {
2316
+ "name": "number",
2317
+ "in": "path",
2318
+ "description": "The release number.",
2319
+ "required": true,
2320
+ "schema": {
2321
+ "type": "integer",
2322
+ "format": "int32"
2323
+ }
2324
+ }
2325
+ ],
2326
+ "responses": {
2327
+ "200": {
2328
+ "description": "OK",
2329
+ "content": {
2330
+ "application/json": {
2331
+ "schema": {
2332
+ "$ref": "#/components/schemas/ReleaseDto"
2333
+ }
2334
+ }
2335
+ }
2336
+ },
2337
+ "404": {
2338
+ "description": "Not Found",
2339
+ "content": {
2340
+ "application/json": {
2341
+ "schema": {
2342
+ "$ref": "#/components/schemas/ErrorDto"
2343
+ }
2344
+ }
2345
+ }
2346
+ },
2347
+ "401": {
2348
+ "description": "No key or token, or an invalid or revoked one."
2349
+ },
2350
+ "403": {
2351
+ "description": "The key lacks the scope, or the person has no role in the project that allows this; with a body when a rule refused it, such as `owners_only`.",
2352
+ "content": {
2353
+ "application/json": {
2354
+ "schema": {
2355
+ "$ref": "#/components/schemas/ErrorDto"
2356
+ }
2357
+ }
2358
+ }
2359
+ }
2360
+ },
2361
+ "security": [
2362
+ {
2363
+ "ApiKey": [ ]
2364
+ }
2365
+ ]
2366
+ }
2367
+ }
2368
+ },
2369
+ "components": {
2370
+ "schemas": {
2371
+ "AddChangeRequest": {
2372
+ "required": [
2373
+ "asset"
2374
+ ],
2375
+ "type": "object",
2376
+ "properties": {
2377
+ "asset": {
2378
+ "type": "string",
2379
+ "description": "The asset's id."
2380
+ },
2381
+ "version": {
2382
+ "type": "integer",
2383
+ "description": "A processed version, or null to remove the asset from the release.",
2384
+ "format": "int32",
2385
+ "nullable": true
2386
+ }
2387
+ },
2388
+ "additionalProperties": false,
2389
+ "description": "Points an asset at a version, or takes it out of the release when Brua.Shared.DTOs.AddChangeRequest.Version is null."
2390
+ },
2391
+ "ApiKeyDto": {
2392
+ "required": [
2393
+ "createdAt",
2394
+ "id",
2395
+ "name",
2396
+ "prefix",
2397
+ "scopes"
2398
+ ],
2399
+ "type": "object",
2400
+ "properties": {
2401
+ "id": {
2402
+ "type": "string",
2403
+ "description": "The key's id, for revoking it."
2404
+ },
2405
+ "name": {
2406
+ "type": "string",
2407
+ "description": "The system it is for."
2408
+ },
2409
+ "prefix": {
2410
+ "type": "string",
2411
+ "description": "The part of the key that identifies it, brua_{prefix}."
2412
+ },
2413
+ "scopes": {
2414
+ "type": "array",
2415
+ "items": {
2416
+ "type": "string"
2417
+ },
2418
+ "description": "What it may do."
2419
+ },
2420
+ "createdAt": {
2421
+ "type": "string",
2422
+ "description": "When it was created.",
2423
+ "format": "date-time"
2424
+ },
2425
+ "lastUsedAt": {
2426
+ "type": "string",
2427
+ "description": "When a request last used it.",
2428
+ "format": "date-time",
2429
+ "nullable": true
2430
+ },
2431
+ "revokedAt": {
2432
+ "type": "string",
2433
+ "description": "When it was revoked, if it was.",
2434
+ "format": "date-time",
2435
+ "nullable": true
2436
+ }
2437
+ },
2438
+ "additionalProperties": false,
2439
+ "description": "A key as listed for admins: the secret is never shown again, only its prefix (SPEC.md 13.2)."
2440
+ },
2441
+ "AssetDetailDto": {
2442
+ "required": [
2443
+ "createdAt",
2444
+ "id",
2445
+ "sizing",
2446
+ "versions"
2447
+ ],
2448
+ "type": "object",
2449
+ "properties": {
2450
+ "id": {
2451
+ "type": "string",
2452
+ "description": "The asset's id."
2453
+ },
2454
+ "sizing": {
2455
+ "type": "string",
2456
+ "description": "\"flexible\" (a width ladder) or \"fixed\" (a designed size at @1x–@3x); every version keeps it."
2457
+ },
2458
+ "liveVersion": {
2459
+ "type": "integer",
2460
+ "description": "The version in prod; left out when none is released.",
2461
+ "format": "int32",
2462
+ "nullable": true
2463
+ },
2464
+ "createdAt": {
2465
+ "type": "string",
2466
+ "description": "When the asset was created.",
2467
+ "format": "date-time"
2468
+ },
2469
+ "versions": {
2470
+ "type": "array",
2471
+ "items": {
2472
+ "$ref": "#/components/schemas/VersionDetailDto"
2473
+ },
2474
+ "description": "Every version, newest first."
2475
+ },
2476
+ "library": {
2477
+ "type": "string",
2478
+ "description": "The shared library the asset lives in, when it isn't the project's own.",
2479
+ "nullable": true
2480
+ }
2481
+ },
2482
+ "additionalProperties": false,
2483
+ "description": "An asset and all its versions, newest first, for the back office. The asset itself is an id and a\nBrua.Shared.DTOs.AssetDetailDto.Sizing; each version says which conditions have their own files. Brua.Shared.DTOs.AssetDetailDto.Library names the\nshared library the asset lives in when it isn't the project's own; it is changed there (SPEC.md 22.4)."
2484
+ },
2485
+ "AssetResponse": {
2486
+ "required": [
2487
+ "alt",
2488
+ "height",
2489
+ "id",
2490
+ "url",
2491
+ "variants",
2492
+ "version",
2493
+ "width"
2494
+ ],
2495
+ "type": "object",
2496
+ "properties": {
2497
+ "id": {
2498
+ "type": "string",
2499
+ "description": "The asset's id, unique in the organization."
2500
+ },
2501
+ "version": {
2502
+ "type": "integer",
2503
+ "description": "The version the response describes: the one in the current release, unless a version was asked for.",
2504
+ "format": "int32"
2505
+ },
2506
+ "url": {
2507
+ "type": "string",
2508
+ "description": "The single URL: the edge negotiates format, density, color scheme and language from the request."
2509
+ },
2510
+ "width": {
2511
+ "type": "integer",
2512
+ "description": "The width in CSS pixels at 1x.",
2513
+ "format": "int32"
2514
+ },
2515
+ "height": {
2516
+ "type": "integer",
2517
+ "description": "The height in CSS pixels at 1x.",
2518
+ "format": "int32"
2519
+ },
2520
+ "alt": {
2521
+ "type": "string",
2522
+ "description": "The alt text in the resolved language; empty for a decorative asset."
2523
+ },
2524
+ "lang": {
2525
+ "type": "string",
2526
+ "description": "The alt text's language, when the asset has one.",
2527
+ "nullable": true
2528
+ },
2529
+ "variants": {
2530
+ "type": "array",
2531
+ "items": {
2532
+ "$ref": "#/components/schemas/AssetVariantDto"
2533
+ },
2534
+ "description": "Every file of the version for the resolved language, each with the conditions it is for."
2535
+ }
2536
+ },
2537
+ "additionalProperties": false,
2538
+ "description": "The asset contract from SPEC.md section 5: the HTML picture model as JSON.\nOptional fields are null and left out of the JSON."
2539
+ },
2540
+ "AssetSummaryDto": {
2541
+ "required": [
2542
+ "decorative",
2543
+ "id",
2544
+ "latestStatus",
2545
+ "latestVersion",
2546
+ "preset",
2547
+ "previews"
2548
+ ],
2549
+ "type": "object",
2550
+ "properties": {
2551
+ "id": {
2552
+ "type": "string",
2553
+ "description": "The asset's id."
2554
+ },
2555
+ "preset": {
2556
+ "type": "string",
2557
+ "description": "\"flexible\", \"fixed\" or \"animated\"."
2558
+ },
2559
+ "latestVersion": {
2560
+ "type": "integer",
2561
+ "description": "The newest version's number.",
2562
+ "format": "int32"
2563
+ },
2564
+ "latestStatus": {
2565
+ "type": "string",
2566
+ "description": "The newest version's status: \"Draft\", \"Processing\", \"Ready\" or \"Failed\"."
2567
+ },
2568
+ "liveVersion": {
2569
+ "type": "integer",
2570
+ "description": "The version in prod; left out when none is released.",
2571
+ "format": "int32",
2572
+ "nullable": true
2573
+ },
2574
+ "width": {
2575
+ "type": "integer",
2576
+ "description": "The newest processed version's width in CSS pixels.",
2577
+ "format": "int32",
2578
+ "nullable": true
2579
+ },
2580
+ "height": {
2581
+ "type": "integer",
2582
+ "description": "The newest processed version's height in CSS pixels.",
2583
+ "format": "int32",
2584
+ "nullable": true
2585
+ },
2586
+ "alt": {
2587
+ "type": "string",
2588
+ "description": "The newest version's alt text in the project's first language.",
2589
+ "nullable": true
2590
+ },
2591
+ "decorative": {
2592
+ "type": "boolean",
2593
+ "description": "Whether the asset is decorative."
2594
+ },
2595
+ "previews": {
2596
+ "type": "array",
2597
+ "items": {
2598
+ "$ref": "#/components/schemas/PreviewDto"
2599
+ },
2600
+ "description": "Thumbnails of the newest processed version."
2601
+ },
2602
+ "library": {
2603
+ "type": "string",
2604
+ "description": "The shared library the asset lives in, when it isn't the project's own.",
2605
+ "nullable": true
2606
+ },
2607
+ "liveUrl": {
2608
+ "type": "string",
2609
+ "description": "The single URL of the version in prod.",
2610
+ "nullable": true
2611
+ }
2612
+ },
2613
+ "additionalProperties": false,
2614
+ "description": "One asset in the back office's list, with its newest version and the version in prod. Brua.Shared.DTOs.AssetSummaryDto.Library names\nthe shared library the asset lives in when it isn't the project's own (SPEC.md 22). Brua.Shared.DTOs.AssetSummaryDto.LiveUrl is the\nsingle URL of the version in prod."
2615
+ },
2616
+ "AssetVariantDto": {
2617
+ "required": [
2618
+ "type",
2619
+ "url"
2620
+ ],
2621
+ "type": "object",
2622
+ "properties": {
2623
+ "type": {
2624
+ "type": "string",
2625
+ "description": "The file's media type."
2626
+ },
2627
+ "url": {
2628
+ "type": "string",
2629
+ "description": "The file's URL on the edge, immutable."
2630
+ },
2631
+ "prefersColorScheme": {
2632
+ "type": "string",
2633
+ "description": "\"light\" or \"dark\" when the file is for one scheme; left out when it serves both.",
2634
+ "nullable": true
2635
+ },
2636
+ "prefersReducedMotion": {
2637
+ "type": "string",
2638
+ "description": "\"reduce\" on the still of an animation.",
2639
+ "nullable": true
2640
+ },
2641
+ "lang": {
2642
+ "type": "string",
2643
+ "description": "The language the file is for; left out for language-neutral files.",
2644
+ "nullable": true
2645
+ },
2646
+ "scale": {
2647
+ "type": "integer",
2648
+ "description": "The density of a fixed-size file: 1, 2 or 3.",
2649
+ "format": "int32",
2650
+ "nullable": true
2651
+ },
2652
+ "pixelWidth": {
2653
+ "type": "integer",
2654
+ "description": "The width of a flexible file in pixels.",
2655
+ "format": "int32",
2656
+ "nullable": true
2657
+ }
2658
+ },
2659
+ "additionalProperties": false,
2660
+ "description": "One file of a version. Value fields are strings, not closed enums, so new values never break a client (SPEC.md 14)."
2661
+ },
2662
+ "AssetVersionDto": {
2663
+ "required": [
2664
+ "id",
2665
+ "status",
2666
+ "version"
2667
+ ],
2668
+ "type": "object",
2669
+ "properties": {
2670
+ "id": {
2671
+ "type": "string",
2672
+ "description": "The asset's id."
2673
+ },
2674
+ "version": {
2675
+ "type": "integer",
2676
+ "description": "The version number, from 1.",
2677
+ "format": "int32"
2678
+ },
2679
+ "status": {
2680
+ "type": "string",
2681
+ "description": "\"Draft\" until every required slot is uploaded, \"Processing\", then \"Ready\" or \"Failed\"."
2682
+ },
2683
+ "slots": {
2684
+ "type": "array",
2685
+ "items": {
2686
+ "$ref": "#/components/schemas/SlotDto"
2687
+ },
2688
+ "description": "The source files the preset needs and which are uploaded.",
2689
+ "nullable": true
2690
+ },
2691
+ "failureCode": {
2692
+ "type": "string",
2693
+ "description": "Why processing failed, such as \"wrong_proportions\" (SPEC.md 9.2).",
2694
+ "nullable": true
2695
+ },
2696
+ "failureDetail": {
2697
+ "type": "string",
2698
+ "description": "The failure in words.",
2699
+ "nullable": true
2700
+ }
2701
+ },
2702
+ "additionalProperties": false,
2703
+ "description": "A version while it is made: its slots, and whether processing has finished (SPEC.md 9)."
2704
+ },
2705
+ "ChangeDto": {
2706
+ "required": [
2707
+ "asset",
2708
+ "conflict",
2709
+ "kind"
2710
+ ],
2711
+ "type": "object",
2712
+ "properties": {
2713
+ "asset": {
2714
+ "type": "string",
2715
+ "description": "The asset's id."
2716
+ },
2717
+ "kind": {
2718
+ "type": "string",
2719
+ "description": "\"set\" (a version goes live) or \"remove\" (the asset leaves the release)."
2720
+ },
2721
+ "fromVersion": {
2722
+ "type": "integer",
2723
+ "description": "The version in prod; left out when the asset isn't released yet.",
2724
+ "format": "int32",
2725
+ "nullable": true
2726
+ },
2727
+ "toVersion": {
2728
+ "type": "integer",
2729
+ "description": "The version the change set carries; left out for a removal.",
2730
+ "format": "int32",
2731
+ "nullable": true
2732
+ },
2733
+ "conflict": {
2734
+ "type": "boolean",
2735
+ "description": "True when prod changed after the change was added; resolve it before merging."
2736
+ },
2737
+ "proportionChange": {
2738
+ "$ref": "#/components/schemas/ProportionChangeDto"
2739
+ },
2740
+ "coverageChange": {
2741
+ "$ref": "#/components/schemas/CoverageChangeDto"
2742
+ }
2743
+ },
2744
+ "additionalProperties": false,
2745
+ "description": "One asset in a change set's diff: from its prod version to the change set's (SPEC.md 21.3).\nBrua.Shared.DTOs.ChangeDto.ProportionChange is set when the new version has another shape than the one in prod, and\nBrua.Shared.DTOs.ChangeDto.CoverageChange when other conditions have their own files (appearances, languages, an animation)."
2746
+ },
2747
+ "ChangeSetDto": {
2748
+ "required": [
2749
+ "changes",
2750
+ "createdAt",
2751
+ "id",
2752
+ "name",
2753
+ "status"
2754
+ ],
2755
+ "type": "object",
2756
+ "properties": {
2757
+ "id": {
2758
+ "type": "string",
2759
+ "description": "The change set's id."
2760
+ },
2761
+ "name": {
2762
+ "type": "string",
2763
+ "description": "What it is for, such as \"Spring campaign\"."
2764
+ },
2765
+ "status": {
2766
+ "type": "string",
2767
+ "description": "\"open\", \"inreview\", \"approved\" or \"merged\"."
2768
+ },
2769
+ "createdAt": {
2770
+ "type": "string",
2771
+ "description": "When it was opened.",
2772
+ "format": "date-time"
2773
+ },
2774
+ "createdBy": {
2775
+ "type": "string",
2776
+ "description": "Who opened it: an email, or \"key:{name}\" for a system.",
2777
+ "nullable": true
2778
+ },
2779
+ "approvedBy": {
2780
+ "type": "string",
2781
+ "description": "Who approved it.",
2782
+ "nullable": true
2783
+ },
2784
+ "mergeAt": {
2785
+ "type": "string",
2786
+ "description": "When a scheduled merge happens.",
2787
+ "format": "date-time",
2788
+ "nullable": true
2789
+ },
2790
+ "mergedRelease": {
2791
+ "type": "integer",
2792
+ "description": "The release it became.",
2793
+ "format": "int32",
2794
+ "nullable": true
2795
+ },
2796
+ "changes": {
2797
+ "type": "array",
2798
+ "items": {
2799
+ "$ref": "#/components/schemas/ChangeDto"
2800
+ },
2801
+ "description": "Its diff against prod, one entry per asset."
2802
+ },
2803
+ "readBy": {
2804
+ "type": "integer",
2805
+ "description": "For a library: how many projects a merge reaches. Left out for a project.",
2806
+ "format": "int32",
2807
+ "nullable": true
2808
+ }
2809
+ },
2810
+ "additionalProperties": false,
2811
+ "description": "A change set: versions that go live together once reviewed (SPEC.md 21)."
2812
+ },
2813
+ "CoverageChangeDto": {
2814
+ "required": [
2815
+ "fromColorSchemes",
2816
+ "fromLanguages",
2817
+ "fromPreset",
2818
+ "toColorSchemes",
2819
+ "toLanguages",
2820
+ "toPreset"
2821
+ ],
2822
+ "type": "object",
2823
+ "properties": {
2824
+ "fromPreset": {
2825
+ "type": "string",
2826
+ "description": "The preset in prod."
2827
+ },
2828
+ "toPreset": {
2829
+ "type": "string",
2830
+ "description": "The new preset."
2831
+ },
2832
+ "fromColorSchemes": {
2833
+ "type": "string",
2834
+ "description": "The color schemes in prod: \"any\", \"any-dark\" or \"both\"."
2835
+ },
2836
+ "toColorSchemes": {
2837
+ "type": "string",
2838
+ "description": "The new color schemes."
2839
+ },
2840
+ "fromLanguages": {
2841
+ "type": "string",
2842
+ "description": "The languages in prod: \"none\", \"optional\" or \"required\"."
2843
+ },
2844
+ "toLanguages": {
2845
+ "type": "string",
2846
+ "description": "The new languages."
2847
+ }
2848
+ },
2849
+ "additionalProperties": false,
2850
+ "description": "Which conditions have their own files before and after a change, when that differs: a dark-mode user gets the one\ndesign where there was a dark file, every language gets the same image, a still plays where an animation did, or\nthe other way round."
2851
+ },
2852
+ "CreateApiKeyRequest": {
2853
+ "required": [
2854
+ "name",
2855
+ "scopes"
2856
+ ],
2857
+ "type": "object",
2858
+ "properties": {
2859
+ "name": {
2860
+ "type": "string",
2861
+ "description": "The system the key is for, such as \"gift-service\"; shown wherever the key's actions are."
2862
+ },
2863
+ "scopes": {
2864
+ "type": "array",
2865
+ "items": {
2866
+ "type": "string"
2867
+ },
2868
+ "description": "\"delivery:read\" (reading assets) and \"assets:write\" (creating assets, uploading, change sets); \"admin\" for keys and settings."
2869
+ }
2870
+ },
2871
+ "additionalProperties": false,
2872
+ "description": "Body of `POST …/api-keys`."
2873
+ },
2874
+ "CreateAssetRequest": {
2875
+ "required": [
2876
+ "decorative",
2877
+ "id",
2878
+ "preset"
2879
+ ],
2880
+ "type": "object",
2881
+ "properties": {
2882
+ "id": {
2883
+ "type": "string",
2884
+ "description": "The asset's id: lowercase letters, digits and dashes, unique in the organization, and the contract with every consumer."
2885
+ },
2886
+ "preset": {
2887
+ "type": "string",
2888
+ "description": "\"flexible\", \"fixed\" or \"animated\" (SPEC.md 4)."
2889
+ },
2890
+ "alt": {
2891
+ "type": "object",
2892
+ "additionalProperties": {
2893
+ "type": "string"
2894
+ },
2895
+ "description": "Alt text per project language; required in every language unless the asset is decorative.",
2896
+ "nullable": true
2897
+ },
2898
+ "decorative": {
2899
+ "type": "boolean",
2900
+ "description": "True for an asset that carries no meaning, which screen readers then skip."
2901
+ },
2902
+ "width": {
2903
+ "type": "integer",
2904
+ "description": "The designed width in CSS pixels, for fixed and animated assets.",
2905
+ "format": "int32",
2906
+ "nullable": true
2907
+ },
2908
+ "height": {
2909
+ "type": "integer",
2910
+ "description": "The designed height in CSS pixels, for fixed and animated assets.",
2911
+ "format": "int32",
2912
+ "nullable": true
2913
+ },
2914
+ "colorSchemes": {
2915
+ "type": "string",
2916
+ "description": "\"any\", \"any-dark\" or \"both\".",
2917
+ "nullable": true
2918
+ },
2919
+ "stillFit": {
2920
+ "type": "string",
2921
+ "description": "\"match\" or \"fill\".",
2922
+ "nullable": true
2923
+ },
2924
+ "languages": {
2925
+ "type": "string",
2926
+ "description": "\"none\", \"optional\" or \"required\".",
2927
+ "nullable": true
2928
+ },
2929
+ "scales": {
2930
+ "type": "string",
2931
+ "description": "\"single\" or \"individual\".",
2932
+ "nullable": true
2933
+ }
2934
+ },
2935
+ "additionalProperties": false,
2936
+ "description": "Body of `POST /v1/projects/{project}/assets`. Brua.Shared.DTOs.CreateAssetRequest.StillFit is \"match\" (default: stills must have the\ndesigned proportions) or \"fill\" (stills are scaled and center-cropped to the designed size). Brua.Shared.DTOs.CreateAssetRequest.Languages\nis \"none\" (default), \"optional\" (some languages have their own files, slots `{lang}.{scheme}.{motion}.source`)\nor \"required\" (every project language has its own). Brua.Shared.DTOs.CreateAssetRequest.ColorSchemes is \"any\", \"any-dark\" (a default plus a dark\noverride) or \"both\". Brua.Shared.DTOs.CreateAssetRequest.Scales is \"single\" (default: one still source) or \"individual\" (fixed sizing: a still per\nscale in slots such as `light.still@2x`, @2x and @3x required, @1x made from @2x when left out)."
2937
+ },
2938
+ "CreateChangeSetRequest": {
2939
+ "required": [
2940
+ "name"
2941
+ ],
2942
+ "type": "object",
2943
+ "properties": {
2944
+ "name": {
2945
+ "type": "string",
2946
+ "description": "What the change set is for."
2947
+ }
2948
+ },
2949
+ "additionalProperties": false,
2950
+ "description": "Body of `POST …/change-sets`."
2951
+ },
2952
+ "CreateVersionRequest": {
2953
+ "type": "object",
2954
+ "properties": {
2955
+ "alt": {
2956
+ "type": "object",
2957
+ "additionalProperties": {
2958
+ "type": "string"
2959
+ },
2960
+ "description": "New alt text per project language.",
2961
+ "nullable": true
2962
+ },
2963
+ "decorative": {
2964
+ "type": "boolean",
2965
+ "description": "Whether the asset is decorative from this version on.",
2966
+ "nullable": true
2967
+ },
2968
+ "stillFit": {
2969
+ "type": "string",
2970
+ "description": "\"match\" or \"fill\".",
2971
+ "nullable": true
2972
+ },
2973
+ "preset": {
2974
+ "type": "string",
2975
+ "description": "\"flexible\", \"fixed\" or \"animated\", of the asset's sizing.",
2976
+ "nullable": true
2977
+ },
2978
+ "width": {
2979
+ "type": "integer",
2980
+ "description": "The designed width in CSS pixels, for fixed and animated versions.",
2981
+ "format": "int32",
2982
+ "nullable": true
2983
+ },
2984
+ "height": {
2985
+ "type": "integer",
2986
+ "description": "The designed height in CSS pixels, for fixed and animated versions.",
2987
+ "format": "int32",
2988
+ "nullable": true
2989
+ },
2990
+ "colorSchemes": {
2991
+ "type": "string",
2992
+ "description": "\"any\", \"any-dark\" or \"both\".",
2993
+ "nullable": true
2994
+ },
2995
+ "languages": {
2996
+ "type": "string",
2997
+ "description": "\"none\", \"optional\" or \"required\".",
2998
+ "nullable": true
2999
+ },
3000
+ "scales": {
3001
+ "type": "string",
3002
+ "description": "\"single\" or \"individual\".",
3003
+ "nullable": true
3004
+ }
3005
+ },
3006
+ "additionalProperties": false,
3007
+ "description": "Body of `POST …/assets/{id}/versions`. A version decides which conditions have their own files: its preset,\ncolor schemes, languages, scales and designed size can all differ from the version before, both ways (one file where\nthere were eight, or dark and languages added). Only the sizing stays: a flexible asset's versions are flexible, a\nfixed one's fixed or animated. Everything left out, the alt text and Brua.Shared.DTOs.CreateVersionRequest.StillFit included, is copied from\nthe newest version."
3008
+ },
3009
+ "CreatedApiKeyDto": {
3010
+ "required": [
3011
+ "id",
3012
+ "key",
3013
+ "name",
3014
+ "scopes"
3015
+ ],
3016
+ "type": "object",
3017
+ "properties": {
3018
+ "id": {
3019
+ "type": "string",
3020
+ "description": "The key's id, for revoking it."
3021
+ },
3022
+ "name": {
3023
+ "type": "string",
3024
+ "description": "The system it is for."
3025
+ },
3026
+ "key": {
3027
+ "type": "string",
3028
+ "description": "The key, `brua_{prefix}_{secret}`: send it as `X-Api-Key`. Store it now; it is never shown again."
3029
+ },
3030
+ "scopes": {
3031
+ "type": "array",
3032
+ "items": {
3033
+ "type": "string"
3034
+ },
3035
+ "description": "What it may do."
3036
+ }
3037
+ },
3038
+ "additionalProperties": false,
3039
+ "description": "The full key is returned only here, once."
3040
+ },
3041
+ "ErrorDto": {
3042
+ "required": [
3043
+ "error"
3044
+ ],
3045
+ "type": "object",
3046
+ "properties": {
3047
+ "error": {
3048
+ "type": "string",
3049
+ "description": "A code to act on, such as \"not_found\", \"not_released\", \"validation_failed\" or \"conflicts\"."
3050
+ },
3051
+ "id": {
3052
+ "type": "string",
3053
+ "description": "What the error is about, such as the asset id or the change set.",
3054
+ "nullable": true
3055
+ },
3056
+ "errors": {
3057
+ "type": "object",
3058
+ "additionalProperties": {
3059
+ "type": "array",
3060
+ "items": {
3061
+ "type": "string"
3062
+ }
3063
+ },
3064
+ "description": "For \"validation_failed\": the messages per field.",
3065
+ "nullable": true
3066
+ }
3067
+ },
3068
+ "additionalProperties": false,
3069
+ "description": "Every error, on every endpoint (SPEC.md 5.2)."
3070
+ },
3071
+ "MergeRequest": {
3072
+ "type": "object",
3073
+ "properties": {
3074
+ "at": {
3075
+ "type": "string",
3076
+ "description": "When to merge; left out, now.",
3077
+ "format": "date-time",
3078
+ "nullable": true
3079
+ }
3080
+ },
3081
+ "additionalProperties": false,
3082
+ "description": "Body of `POST …/change-sets/{id}/merge`."
3083
+ },
3084
+ "PreviewDto": {
3085
+ "required": [
3086
+ "transparent",
3087
+ "url"
3088
+ ],
3089
+ "type": "object",
3090
+ "properties": {
3091
+ "colorScheme": {
3092
+ "type": "string",
3093
+ "description": "\"light\" or \"dark\"; left out when the still serves both.",
3094
+ "nullable": true
3095
+ },
3096
+ "url": {
3097
+ "type": "string",
3098
+ "description": "The thumbnail's URL on the edge."
3099
+ },
3100
+ "transparent": {
3101
+ "type": "boolean",
3102
+ "description": "Whether the still has an alpha channel, so it is shown on a checkerboard."
3103
+ },
3104
+ "lang": {
3105
+ "type": "string",
3106
+ "description": "The language the still is for; left out for language-neutral files.",
3107
+ "nullable": true
3108
+ }
3109
+ },
3110
+ "additionalProperties": false,
3111
+ "description": "A small still of a version for thumbnails; Brua.Shared.DTOs.PreviewDto.ColorScheme is null when it serves both and\nBrua.Shared.DTOs.PreviewDto.Lang is null for language-neutral files. Brua.Shared.DTOs.PreviewDto.Transparent is set when the still has an alpha channel."
3112
+ },
3113
+ "ProjectDto": {
3114
+ "required": [
3115
+ "allowSelfApproval",
3116
+ "languages",
3117
+ "name",
3118
+ "slug"
3119
+ ],
3120
+ "type": "object",
3121
+ "properties": {
3122
+ "slug": {
3123
+ "type": "string",
3124
+ "description": "The project's id in URLs."
3125
+ },
3126
+ "name": {
3127
+ "type": "string",
3128
+ "description": "The project's name."
3129
+ },
3130
+ "languages": {
3131
+ "type": "array",
3132
+ "items": {
3133
+ "type": "string"
3134
+ },
3135
+ "description": "The project's languages as BCP 47 tags, first one the default; alt text is required in each."
3136
+ },
3137
+ "allowSelfApproval": {
3138
+ "type": "boolean",
3139
+ "description": "Whether authors may approve their own change sets, from the review policy (SPEC.md 6.2)."
3140
+ }
3141
+ },
3142
+ "additionalProperties": false,
3143
+ "description": "A project's settings that clients need, such as the languages alt text is required in."
3144
+ },
3145
+ "ProportionChangeDto": {
3146
+ "required": [
3147
+ "fromHeight",
3148
+ "fromWidth",
3149
+ "toHeight",
3150
+ "toWidth"
3151
+ ],
3152
+ "type": "object",
3153
+ "properties": {
3154
+ "fromWidth": {
3155
+ "type": "integer",
3156
+ "description": "The width in prod.",
3157
+ "format": "int32"
3158
+ },
3159
+ "fromHeight": {
3160
+ "type": "integer",
3161
+ "description": "The height in prod.",
3162
+ "format": "int32"
3163
+ },
3164
+ "toWidth": {
3165
+ "type": "integer",
3166
+ "description": "The new width.",
3167
+ "format": "int32"
3168
+ },
3169
+ "toHeight": {
3170
+ "type": "integer",
3171
+ "description": "The new height.",
3172
+ "format": "int32"
3173
+ }
3174
+ },
3175
+ "additionalProperties": false,
3176
+ "description": "The sizes a change moves an asset between, when their proportions differ: what a layout built for the old shape gets."
3177
+ },
3178
+ "ReleaseDto": {
3179
+ "required": [
3180
+ "assetCount",
3181
+ "createdAt",
3182
+ "note",
3183
+ "number"
3184
+ ],
3185
+ "type": "object",
3186
+ "properties": {
3187
+ "number": {
3188
+ "type": "integer",
3189
+ "description": "The release number, counting up; the highest is prod.",
3190
+ "format": "int32"
3191
+ },
3192
+ "createdAt": {
3193
+ "type": "string",
3194
+ "description": "When it went live.",
3195
+ "format": "date-time"
3196
+ },
3197
+ "note": {
3198
+ "type": "string",
3199
+ "description": "What made it, such as the merged change set or a restore."
3200
+ },
3201
+ "changeSetId": {
3202
+ "type": "string",
3203
+ "description": "The change set it merged, if any.",
3204
+ "nullable": true
3205
+ },
3206
+ "assetCount": {
3207
+ "type": "integer",
3208
+ "description": "How many assets it serves.",
3209
+ "format": "int32"
3210
+ }
3211
+ },
3212
+ "additionalProperties": false,
3213
+ "description": "One release: what prod served from this number on (SPEC.md 21.4)."
3214
+ },
3215
+ "ResolveConflictRequest": {
3216
+ "required": [
3217
+ "asset",
3218
+ "keep"
3219
+ ],
3220
+ "type": "object",
3221
+ "properties": {
3222
+ "asset": {
3223
+ "type": "string",
3224
+ "description": "The asset in conflict."
3225
+ },
3226
+ "keep": {
3227
+ "type": "string",
3228
+ "description": "\"mine\" or \"prod\"."
3229
+ }
3230
+ },
3231
+ "additionalProperties": false,
3232
+ "description": "Brua.Shared.DTOs.ResolveConflictRequest.Keep is \"mine\" (the change set's version) or \"prod\"."
3233
+ },
3234
+ "SlotDto": {
3235
+ "required": [
3236
+ "name",
3237
+ "required",
3238
+ "status"
3239
+ ],
3240
+ "type": "object",
3241
+ "properties": {
3242
+ "name": {
3243
+ "type": "string",
3244
+ "description": "The slot, such as `any.still.source`, `dark.still.source` or `nb.light.still.source`."
3245
+ },
3246
+ "status": {
3247
+ "type": "string",
3248
+ "description": "\"empty\" or \"uploaded\"."
3249
+ },
3250
+ "contentType": {
3251
+ "type": "string",
3252
+ "description": "The uploaded file's media type.",
3253
+ "nullable": true
3254
+ },
3255
+ "required": {
3256
+ "type": "boolean",
3257
+ "description": "Whether processing waits for this slot."
3258
+ }
3259
+ },
3260
+ "additionalProperties": false,
3261
+ "description": "One source file of a version and whether it's uploaded (SPEC.md 9.1); optional slots are per-language extras."
3262
+ },
3263
+ "SourceUploadDto": {
3264
+ "required": [
3265
+ "expiresAt",
3266
+ "method",
3267
+ "uploadUrl"
3268
+ ],
3269
+ "type": "object",
3270
+ "properties": {
3271
+ "uploadUrl": {
3272
+ "type": "string",
3273
+ "description": "PUT the file's bytes here, with its Content-Type; no Brua key is needed."
3274
+ },
3275
+ "method": {
3276
+ "type": "string",
3277
+ "description": "\"PUT\"."
3278
+ },
3279
+ "expiresAt": {
3280
+ "type": "string",
3281
+ "description": "When the URL stops working; ask for a new one after that.",
3282
+ "format": "date-time"
3283
+ }
3284
+ },
3285
+ "additionalProperties": false,
3286
+ "description": "Where to upload a version's source file, with a presigned PUT URL."
3287
+ },
3288
+ "SubmitVersionRequest": {
3289
+ "type": "object",
3290
+ "properties": {
3291
+ "changeSet": {
3292
+ "type": "string",
3293
+ "description": "The open change set to add the version to; left out, a new one is opened for it.",
3294
+ "nullable": true
3295
+ }
3296
+ },
3297
+ "additionalProperties": false,
3298
+ "description": "Body of `POST …/versions/{version}/submit`."
3299
+ },
3300
+ "VersionDetailDto": {
3301
+ "required": [
3302
+ "alt",
3303
+ "colorSchemes",
3304
+ "decorative",
3305
+ "languages",
3306
+ "preset",
3307
+ "previews",
3308
+ "scales",
3309
+ "status",
3310
+ "stillFit",
3311
+ "types",
3312
+ "url",
3313
+ "variantCount",
3314
+ "variants",
3315
+ "version"
3316
+ ],
3317
+ "type": "object",
3318
+ "properties": {
3319
+ "version": {
3320
+ "type": "integer",
3321
+ "description": "The version number.",
3322
+ "format": "int32"
3323
+ },
3324
+ "status": {
3325
+ "type": "string",
3326
+ "description": "\"Draft\", \"Processing\", \"Ready\" or \"Failed\"."
3327
+ },
3328
+ "failureCode": {
3329
+ "type": "string",
3330
+ "description": "Why processing failed, such as \"wrong_proportions\".",
3331
+ "nullable": true
3332
+ },
3333
+ "failureDetail": {
3334
+ "type": "string",
3335
+ "description": "The failure in words.",
3336
+ "nullable": true
3337
+ },
3338
+ "width": {
3339
+ "type": "integer",
3340
+ "description": "The width in CSS pixels, once processed.",
3341
+ "format": "int32",
3342
+ "nullable": true
3343
+ },
3344
+ "height": {
3345
+ "type": "integer",
3346
+ "description": "The height in CSS pixels, once processed.",
3347
+ "format": "int32",
3348
+ "nullable": true
3349
+ },
3350
+ "decorative": {
3351
+ "type": "boolean",
3352
+ "description": "Whether the version is decorative."
3353
+ },
3354
+ "stillFit": {
3355
+ "type": "string",
3356
+ "description": "\"match\" or \"fill\"."
3357
+ },
3358
+ "preset": {
3359
+ "type": "string",
3360
+ "description": "\"flexible\", \"fixed\" or \"animated\"."
3361
+ },
3362
+ "colorSchemes": {
3363
+ "type": "string",
3364
+ "description": "\"any\", \"any-dark\" or \"both\"."
3365
+ },
3366
+ "languages": {
3367
+ "type": "string",
3368
+ "description": "\"none\", \"optional\" or \"required\"."
3369
+ },
3370
+ "scales": {
3371
+ "type": "string",
3372
+ "description": "\"single\" or \"individual\"."
3373
+ },
3374
+ "designWidth": {
3375
+ "type": "integer",
3376
+ "description": "The designed width of a fixed or animated version.",
3377
+ "format": "int32",
3378
+ "nullable": true
3379
+ },
3380
+ "designHeight": {
3381
+ "type": "integer",
3382
+ "description": "The designed height of a fixed or animated version.",
3383
+ "format": "int32",
3384
+ "nullable": true
3385
+ },
3386
+ "alt": {
3387
+ "type": "object",
3388
+ "additionalProperties": {
3389
+ "type": "string"
3390
+ },
3391
+ "description": "Alt text per language."
3392
+ },
3393
+ "types": {
3394
+ "type": "array",
3395
+ "items": {
3396
+ "type": "string"
3397
+ },
3398
+ "description": "The media types the version has files in."
3399
+ },
3400
+ "variantCount": {
3401
+ "type": "integer",
3402
+ "description": "How many files were generated.",
3403
+ "format": "int32"
3404
+ },
3405
+ "previews": {
3406
+ "type": "array",
3407
+ "items": {
3408
+ "$ref": "#/components/schemas/PreviewDto"
3409
+ },
3410
+ "description": "Thumbnails per scheme and language."
3411
+ },
3412
+ "variants": {
3413
+ "type": "array",
3414
+ "items": {
3415
+ "$ref": "#/components/schemas/AssetVariantDto"
3416
+ },
3417
+ "description": "Every generated file with the conditions it is for."
3418
+ },
3419
+ "url": {
3420
+ "type": "string",
3421
+ "description": "The version's single URL."
3422
+ }
3423
+ },
3424
+ "additionalProperties": false,
3425
+ "description": "One version with its alt text, thumbnails and every generated file (Brua.Shared.DTOs.VersionDetailDto.Variants, with delivery URLs).\nBrua.Shared.DTOs.VersionDetailDto.Preset, Brua.Shared.DTOs.VersionDetailDto.ColorSchemes, Brua.Shared.DTOs.VersionDetailDto.Languages, Brua.Shared.DTOs.VersionDetailDto.Scales and the designed\nsize are the version's own: the next version may change them. Brua.Shared.DTOs.VersionDetailDto.Url is the version's single URL, which\nthe edge negotiates (SPEC.md 5.3)."
3426
+ }
3427
+ },
3428
+ "securitySchemes": {
3429
+ "ApiKey": {
3430
+ "type": "apiKey",
3431
+ "description": "A project's API key, brua_{prefix}_{secret}, from an admin.",
3432
+ "name": "X-Api-Key",
3433
+ "in": "header"
3434
+ }
3435
+ }
3436
+ },
3437
+ "tags": [
3438
+ {
3439
+ "name": "Assets",
3440
+ "description": "Creating assets and uploading their sources (SPEC.md 9), and the delivery API: what the current release serves (5.2)."
3441
+ },
3442
+ {
3443
+ "name": "Change sets",
3444
+ "description": "Versions that go live together once a person has reviewed them (SPEC.md 21)."
3445
+ },
3446
+ {
3447
+ "name": "Releases",
3448
+ "description": "What prod has served, release by release, and rolling back (SPEC.md 21.4)."
3449
+ },
3450
+ {
3451
+ "name": "API keys",
3452
+ "description": "Keys for systems: created by an admin, shown once, revoked when a system goes (SPEC.md 13.2)."
3453
+ },
3454
+ {
3455
+ "name": "Projects",
3456
+ "description": "The project a key belongs to: its name and the languages alt text is required in."
3457
+ }
3458
+ ]
3459
+ }