redblack-python-sdk 0.1.0__py3-none-any.whl
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.
- redblack/__init__.py +105 -0
- redblack/_generated/__init__.py +39 -0
- redblack/_generated/contract.py +212 -0
- redblack/_generated/operation_specs.py +5115 -0
- redblack/_version.py +4 -0
- redblack/auth.py +352 -0
- redblack/client.py +512 -0
- redblack/config.py +576 -0
- redblack/downloads.py +410 -0
- redblack/errors.py +483 -0
- redblack/models/__init__.py +105 -0
- redblack/models/base.py +150 -0
- redblack/models/generated.py +11736 -0
- redblack/odata.py +75 -0
- redblack/pagination.py +184 -0
- redblack/polling.py +163 -0
- redblack/py.typed +1 -0
- redblack/raw.py +102 -0
- redblack/resources/__init__.py +65 -0
- redblack/resources/_base.py +212 -0
- redblack/resources/_collections.py +80 -0
- redblack/resources/_exports.py +215 -0
- redblack/resources/accounts.py +132 -0
- redblack/resources/cash_actions.py +260 -0
- redblack/resources/equivalents.py +144 -0
- redblack/resources/households.py +138 -0
- redblack/resources/orders.py +118 -0
- redblack/resources/restrictions.py +146 -0
- redblack/resources/review_sets.py +889 -0
- redblack/resources/securities.py +175 -0
- redblack/resources/tasks.py +291 -0
- redblack/resources/users.py +88 -0
- redblack/response.py +118 -0
- redblack/transport.py +606 -0
- redblack_python_sdk-0.1.0.dist-info/METADATA +151 -0
- redblack_python_sdk-0.1.0.dist-info/RECORD +38 -0
- redblack_python_sdk-0.1.0.dist-info/WHEEL +5 -0
- redblack_python_sdk-0.1.0.dist-info/top_level.txt +1 -0
|
@@ -0,0 +1,889 @@
|
|
|
1
|
+
"""Review-set reads, order-add sessions, and order-release sessions."""
|
|
2
|
+
|
|
3
|
+
from __future__ import annotations
|
|
4
|
+
|
|
5
|
+
from collections.abc import Iterator, Mapping, Sequence
|
|
6
|
+
from dataclasses import dataclass
|
|
7
|
+
from threading import Event
|
|
8
|
+
from typing import Any, Literal, overload
|
|
9
|
+
|
|
10
|
+
from ..models import (
|
|
11
|
+
OrderAddCancelResult,
|
|
12
|
+
OrderAddResult,
|
|
13
|
+
OrderAddSession,
|
|
14
|
+
OrderAddSessionItem,
|
|
15
|
+
OrderCreate,
|
|
16
|
+
OrderCreateResult,
|
|
17
|
+
PendingOrder,
|
|
18
|
+
ReleaseError,
|
|
19
|
+
ReleaseValidationResult,
|
|
20
|
+
ReviewSet,
|
|
21
|
+
ReviewSetReleaseSession,
|
|
22
|
+
)
|
|
23
|
+
from ..models.generated import (
|
|
24
|
+
ReviewSetsCancelReleaseResponse200,
|
|
25
|
+
ReviewSetsCancelReleaseResponse202,
|
|
26
|
+
)
|
|
27
|
+
from ..odata import DEFAULT_PAGE_SIZE, ODataQuery
|
|
28
|
+
from ..pagination import Page, Paginator
|
|
29
|
+
from ..polling import Poller, PollOutcome
|
|
30
|
+
from ._base import (
|
|
31
|
+
ApiResponseProtocol,
|
|
32
|
+
ClientProtocol,
|
|
33
|
+
HttpInfoMode,
|
|
34
|
+
Resource,
|
|
35
|
+
body_mapping,
|
|
36
|
+
body_value,
|
|
37
|
+
enum_value,
|
|
38
|
+
read_member,
|
|
39
|
+
require_positive_identifier,
|
|
40
|
+
)
|
|
41
|
+
from ._exports import WorkflowProtocolError
|
|
42
|
+
|
|
43
|
+
|
|
44
|
+
def _optional_boolean(name: str, value: bool | None) -> None:
|
|
45
|
+
if value is not None and not isinstance(value, bool):
|
|
46
|
+
raise TypeError(f"{name} must be a boolean")
|
|
47
|
+
|
|
48
|
+
|
|
49
|
+
def _set_optional_boolean(body: dict[str, Any], wire_name: str, value: bool | None) -> None:
|
|
50
|
+
_optional_boolean(wire_name, value)
|
|
51
|
+
if value is None:
|
|
52
|
+
return
|
|
53
|
+
if wire_name in body and body[wire_name] != value:
|
|
54
|
+
raise ValueError(f"{wire_name} conflicts with the request body")
|
|
55
|
+
body[wire_name] = value
|
|
56
|
+
|
|
57
|
+
|
|
58
|
+
def _validate_versioned_id(value: object) -> dict[str, int]:
|
|
59
|
+
item = body_mapping(value)
|
|
60
|
+
identifier = item.get("id")
|
|
61
|
+
row_version = item.get("rowVersion", item.get("row_version"))
|
|
62
|
+
if isinstance(identifier, bool) or not isinstance(identifier, int):
|
|
63
|
+
raise TypeError("order id must be an integer")
|
|
64
|
+
require_positive_identifier("order id", identifier)
|
|
65
|
+
if isinstance(row_version, bool) or not isinstance(row_version, int):
|
|
66
|
+
raise TypeError("rowVersion must be an integer")
|
|
67
|
+
if row_version < 0:
|
|
68
|
+
raise ValueError("rowVersion must be greater than or equal to zero")
|
|
69
|
+
return {"id": identifier, "rowVersion": row_version}
|
|
70
|
+
|
|
71
|
+
|
|
72
|
+
@dataclass(frozen=True, slots=True)
|
|
73
|
+
class ReleaseCriteria:
|
|
74
|
+
"""Validated release target selection using RedBlack FilterMode values."""
|
|
75
|
+
|
|
76
|
+
mode: int
|
|
77
|
+
filter: str | None = None
|
|
78
|
+
ids: tuple[object, ...] | None = None
|
|
79
|
+
|
|
80
|
+
def __post_init__(self) -> None:
|
|
81
|
+
if isinstance(self.mode, bool) or not isinstance(self.mode, int):
|
|
82
|
+
raise TypeError("release criteria mode must be an integer")
|
|
83
|
+
if self.mode not in {0, 1, 2}:
|
|
84
|
+
raise ValueError("release criteria mode must be 0, 1, or 2")
|
|
85
|
+
if self.mode == 0:
|
|
86
|
+
if not isinstance(self.filter, str) or not self.filter.strip():
|
|
87
|
+
raise ValueError("Filtered release criteria requires a filter")
|
|
88
|
+
if self.ids is not None:
|
|
89
|
+
raise ValueError("Filtered release criteria must not include ids")
|
|
90
|
+
elif self.mode == 1:
|
|
91
|
+
if self.filter is not None:
|
|
92
|
+
raise ValueError("Specific release criteria must not include a filter")
|
|
93
|
+
if not self.ids:
|
|
94
|
+
raise ValueError("Specific release criteria requires ids")
|
|
95
|
+
if len(self.ids) > 500:
|
|
96
|
+
raise ValueError("Specific release criteria is limited to 500 ids")
|
|
97
|
+
for item in self.ids:
|
|
98
|
+
_validate_versioned_id(item)
|
|
99
|
+
elif self.filter is not None or self.ids is not None:
|
|
100
|
+
raise ValueError("All release criteria must not include filter or ids")
|
|
101
|
+
|
|
102
|
+
@classmethod
|
|
103
|
+
def filtered(cls, filter: str) -> ReleaseCriteria:
|
|
104
|
+
return cls(mode=0, filter=filter)
|
|
105
|
+
|
|
106
|
+
@classmethod
|
|
107
|
+
def specific(cls, ids: Sequence[object]) -> ReleaseCriteria:
|
|
108
|
+
return cls(mode=1, ids=tuple(ids))
|
|
109
|
+
|
|
110
|
+
@classmethod
|
|
111
|
+
def all(cls) -> ReleaseCriteria:
|
|
112
|
+
"""Explicitly target all pending orders in the review set."""
|
|
113
|
+
|
|
114
|
+
return cls(mode=2)
|
|
115
|
+
|
|
116
|
+
def to_wire(self) -> dict[str, Any]:
|
|
117
|
+
if self.mode == 0:
|
|
118
|
+
return {"mode": 0, "filter": self.filter, "ids": None}
|
|
119
|
+
if self.mode == 1:
|
|
120
|
+
return {
|
|
121
|
+
"mode": 1,
|
|
122
|
+
"filter": None,
|
|
123
|
+
"ids": [_validate_versioned_id(item) for item in self.ids or ()],
|
|
124
|
+
}
|
|
125
|
+
return {"mode": 2, "filter": None, "ids": None}
|
|
126
|
+
|
|
127
|
+
|
|
128
|
+
def _normalize_criteria(value: ReleaseCriteria | Mapping[str, object]) -> dict[str, Any]:
|
|
129
|
+
if isinstance(value, ReleaseCriteria):
|
|
130
|
+
return value.to_wire()
|
|
131
|
+
body = body_mapping(value)
|
|
132
|
+
raw_mode = body.get("mode")
|
|
133
|
+
if isinstance(raw_mode, bool) or not isinstance(raw_mode, int):
|
|
134
|
+
raise TypeError("release criteria mode must be an integer")
|
|
135
|
+
raw_ids = body.get("ids")
|
|
136
|
+
ids: tuple[object, ...] | None
|
|
137
|
+
if raw_ids is None:
|
|
138
|
+
ids = None
|
|
139
|
+
elif isinstance(raw_ids, Sequence) and not isinstance(raw_ids, str | bytes | bytearray):
|
|
140
|
+
ids = tuple(raw_ids)
|
|
141
|
+
else:
|
|
142
|
+
raise TypeError("release criteria ids must be a sequence")
|
|
143
|
+
return ReleaseCriteria(
|
|
144
|
+
mode=raw_mode,
|
|
145
|
+
filter=body.get("filter"),
|
|
146
|
+
ids=ids,
|
|
147
|
+
).to_wire()
|
|
148
|
+
|
|
149
|
+
|
|
150
|
+
@dataclass(slots=True)
|
|
151
|
+
class OrderAddSessionHandle:
|
|
152
|
+
_client: ClientProtocol
|
|
153
|
+
review_set_id: int
|
|
154
|
+
session_id: int
|
|
155
|
+
latest: OrderAddSession | None = None
|
|
156
|
+
|
|
157
|
+
def __post_init__(self) -> None:
|
|
158
|
+
require_positive_identifier("review_set_id", self.review_set_id)
|
|
159
|
+
require_positive_identifier("session_id", self.session_id)
|
|
160
|
+
|
|
161
|
+
@property
|
|
162
|
+
def _path(self) -> dict[str, int]:
|
|
163
|
+
return {
|
|
164
|
+
"reviewSetId": self.review_set_id,
|
|
165
|
+
"sessionId": self.session_id,
|
|
166
|
+
}
|
|
167
|
+
|
|
168
|
+
def _refresh_with_timeout(self, timeout_budget: float | None) -> OrderAddSession:
|
|
169
|
+
if timeout_budget is None:
|
|
170
|
+
return self.refresh()
|
|
171
|
+
response = self._client.request(
|
|
172
|
+
"ReviewSets_GetOrderAddSession",
|
|
173
|
+
path_params=self._path,
|
|
174
|
+
timeout_budget=timeout_budget,
|
|
175
|
+
)
|
|
176
|
+
self.latest = response.data
|
|
177
|
+
return response.data
|
|
178
|
+
|
|
179
|
+
def refresh(self) -> OrderAddSession:
|
|
180
|
+
response = self._client.request("ReviewSets_GetOrderAddSession", path_params=self._path)
|
|
181
|
+
self.latest = response.data
|
|
182
|
+
return response.data
|
|
183
|
+
|
|
184
|
+
status = refresh
|
|
185
|
+
|
|
186
|
+
@staticmethod
|
|
187
|
+
def _classify(value: object) -> PollOutcome:
|
|
188
|
+
status = enum_value(value, "session_status", "sessionStatus")
|
|
189
|
+
if status == 3:
|
|
190
|
+
return PollOutcome.SUCCEEDED
|
|
191
|
+
if status == 19:
|
|
192
|
+
return PollOutcome.NEEDS_INPUT
|
|
193
|
+
if status in {4, 5, 20}:
|
|
194
|
+
return PollOutcome.FAILED
|
|
195
|
+
return PollOutcome.PENDING
|
|
196
|
+
|
|
197
|
+
def wait(
|
|
198
|
+
self,
|
|
199
|
+
*,
|
|
200
|
+
timeout: float | None = 300.0,
|
|
201
|
+
poll_interval: float = 1.0,
|
|
202
|
+
max_interval: float = 30.0,
|
|
203
|
+
stop_event: Event | None = None,
|
|
204
|
+
raise_on_failure: bool = True,
|
|
205
|
+
) -> OrderAddSession:
|
|
206
|
+
return Poller(
|
|
207
|
+
refresh=self.refresh,
|
|
208
|
+
classify=self._classify,
|
|
209
|
+
refresh_with_timeout=self._refresh_with_timeout,
|
|
210
|
+
).wait(
|
|
211
|
+
timeout=timeout,
|
|
212
|
+
poll_interval=poll_interval,
|
|
213
|
+
max_interval=max_interval,
|
|
214
|
+
stop_event=stop_event,
|
|
215
|
+
raise_on_failure=raise_on_failure,
|
|
216
|
+
)
|
|
217
|
+
|
|
218
|
+
def results(
|
|
219
|
+
self,
|
|
220
|
+
*,
|
|
221
|
+
filter: str | None = None,
|
|
222
|
+
order_by: str | None = None,
|
|
223
|
+
top: int | None = None,
|
|
224
|
+
skip: int | None = None,
|
|
225
|
+
count: bool | None = None,
|
|
226
|
+
) -> Page[OrderAddResult]:
|
|
227
|
+
query = ODataQuery(filter=filter, order_by=order_by, top=top, skip=skip, count=count)
|
|
228
|
+
response = self._client.request(
|
|
229
|
+
"ReviewSets_QueryOrderAddSessionResults",
|
|
230
|
+
path_params=self._path,
|
|
231
|
+
query=query.to_params(),
|
|
232
|
+
)
|
|
233
|
+
return Page.from_data(response.data, query=query, http=response.http)
|
|
234
|
+
|
|
235
|
+
def iter_results(
|
|
236
|
+
self,
|
|
237
|
+
*,
|
|
238
|
+
filter: str | None = None,
|
|
239
|
+
order_by: str | None = None,
|
|
240
|
+
count: bool | None = None,
|
|
241
|
+
start_skip: int = 0,
|
|
242
|
+
page_size: int = DEFAULT_PAGE_SIZE,
|
|
243
|
+
max_items: int | None = None,
|
|
244
|
+
) -> Iterator[OrderAddResult]:
|
|
245
|
+
base = ODataQuery(filter=filter, order_by=order_by, count=count, skip=start_skip)
|
|
246
|
+
return Paginator(
|
|
247
|
+
fetch_page=lambda query: self.results(
|
|
248
|
+
filter=query.filter,
|
|
249
|
+
order_by=query.order_by,
|
|
250
|
+
top=query.top,
|
|
251
|
+
skip=query.skip,
|
|
252
|
+
count=query.count,
|
|
253
|
+
),
|
|
254
|
+
query=base,
|
|
255
|
+
page_size=page_size,
|
|
256
|
+
max_items=max_items,
|
|
257
|
+
).iter_items()
|
|
258
|
+
|
|
259
|
+
def cancel(self) -> OrderAddCancelResult:
|
|
260
|
+
response = self._client.request("ReviewSets_CancelOrderAddSession", path_params=self._path)
|
|
261
|
+
return response.data
|
|
262
|
+
|
|
263
|
+
@property
|
|
264
|
+
def has_failures(self) -> bool:
|
|
265
|
+
error_count = read_member(self.latest, "error_count", "errorCount")
|
|
266
|
+
return (
|
|
267
|
+
isinstance(error_count, int) and not isinstance(error_count, bool) and error_count > 0
|
|
268
|
+
)
|
|
269
|
+
|
|
270
|
+
|
|
271
|
+
@dataclass(slots=True)
|
|
272
|
+
class ReleaseSessionHandle:
|
|
273
|
+
_client: ClientProtocol
|
|
274
|
+
review_set_id: int
|
|
275
|
+
session_id: int
|
|
276
|
+
latest: object | None = None
|
|
277
|
+
|
|
278
|
+
def __post_init__(self) -> None:
|
|
279
|
+
require_positive_identifier("review_set_id", self.review_set_id)
|
|
280
|
+
require_positive_identifier("session_id", self.session_id)
|
|
281
|
+
|
|
282
|
+
@property
|
|
283
|
+
def _path(self) -> dict[str, int]:
|
|
284
|
+
return {
|
|
285
|
+
"reviewSetId": self.review_set_id,
|
|
286
|
+
"sessionId": self.session_id,
|
|
287
|
+
}
|
|
288
|
+
|
|
289
|
+
def _refresh_with_timeout(self, timeout_budget: float | None) -> ReviewSetReleaseSession:
|
|
290
|
+
if timeout_budget is None:
|
|
291
|
+
return self.refresh()
|
|
292
|
+
response = self._client.request(
|
|
293
|
+
"ReviewSets_GetReleaseSession",
|
|
294
|
+
path_params=self._path,
|
|
295
|
+
timeout_budget=timeout_budget,
|
|
296
|
+
)
|
|
297
|
+
self.latest = response.data
|
|
298
|
+
return response.data
|
|
299
|
+
|
|
300
|
+
def refresh(self) -> ReviewSetReleaseSession:
|
|
301
|
+
response = self._client.request("ReviewSets_GetReleaseSession", path_params=self._path)
|
|
302
|
+
self.latest = response.data
|
|
303
|
+
return response.data
|
|
304
|
+
|
|
305
|
+
status = refresh
|
|
306
|
+
|
|
307
|
+
@staticmethod
|
|
308
|
+
def _classify(value: object) -> PollOutcome:
|
|
309
|
+
status = enum_value(value, "session_status", "sessionStatus")
|
|
310
|
+
if status == 5:
|
|
311
|
+
return PollOutcome.SUCCEEDED
|
|
312
|
+
if status in {6, 7}:
|
|
313
|
+
return PollOutcome.FAILED
|
|
314
|
+
return PollOutcome.PENDING
|
|
315
|
+
|
|
316
|
+
def wait(
|
|
317
|
+
self,
|
|
318
|
+
*,
|
|
319
|
+
timeout: float | None = 300.0,
|
|
320
|
+
poll_interval: float = 1.0,
|
|
321
|
+
max_interval: float = 30.0,
|
|
322
|
+
stop_event: Event | None = None,
|
|
323
|
+
raise_on_failure: bool = True,
|
|
324
|
+
) -> ReviewSetReleaseSession:
|
|
325
|
+
return Poller(
|
|
326
|
+
refresh=self.refresh,
|
|
327
|
+
classify=self._classify,
|
|
328
|
+
refresh_with_timeout=self._refresh_with_timeout,
|
|
329
|
+
).wait(
|
|
330
|
+
timeout=timeout,
|
|
331
|
+
poll_interval=poll_interval,
|
|
332
|
+
max_interval=max_interval,
|
|
333
|
+
stop_event=stop_event,
|
|
334
|
+
raise_on_failure=raise_on_failure,
|
|
335
|
+
)
|
|
336
|
+
|
|
337
|
+
def validation_results(
|
|
338
|
+
self,
|
|
339
|
+
*,
|
|
340
|
+
filter: str | None = None,
|
|
341
|
+
order_by: str | None = None,
|
|
342
|
+
top: int | None = None,
|
|
343
|
+
skip: int | None = None,
|
|
344
|
+
count: bool | None = None,
|
|
345
|
+
) -> Page[ReleaseValidationResult]:
|
|
346
|
+
query = ODataQuery(filter=filter, order_by=order_by, top=top, skip=skip, count=count)
|
|
347
|
+
response = self._client.request(
|
|
348
|
+
"ReviewSets_QueryReleaseValidationResults",
|
|
349
|
+
path_params=self._path,
|
|
350
|
+
query=query.to_params(),
|
|
351
|
+
)
|
|
352
|
+
return Page.from_data(response.data, query=query, http=response.http)
|
|
353
|
+
|
|
354
|
+
def errors(
|
|
355
|
+
self,
|
|
356
|
+
*,
|
|
357
|
+
filter: str | None = None,
|
|
358
|
+
order_by: str | None = None,
|
|
359
|
+
top: int | None = None,
|
|
360
|
+
skip: int | None = None,
|
|
361
|
+
count: bool | None = None,
|
|
362
|
+
) -> Page[ReleaseError]:
|
|
363
|
+
query = ODataQuery(filter=filter, order_by=order_by, top=top, skip=skip, count=count)
|
|
364
|
+
response = self._client.request(
|
|
365
|
+
"ReviewSets_QueryReleaseResults",
|
|
366
|
+
path_params=self._path,
|
|
367
|
+
query=query.to_params(),
|
|
368
|
+
)
|
|
369
|
+
# The documented 204 success deliberately becomes an empty Page.
|
|
370
|
+
return Page.from_data(response.data, query=query, http=response.http)
|
|
371
|
+
|
|
372
|
+
def cancel(
|
|
373
|
+
self,
|
|
374
|
+
) -> ReviewSetsCancelReleaseResponse200 | ReviewSetsCancelReleaseResponse202:
|
|
375
|
+
response = self._client.request("ReviewSets_CancelRelease", path_params=self._path)
|
|
376
|
+
self.latest = response.data
|
|
377
|
+
return response.data
|
|
378
|
+
|
|
379
|
+
@property
|
|
380
|
+
def has_failures(self) -> bool:
|
|
381
|
+
stats = read_member(self.latest, "release_stats", "releaseStats")
|
|
382
|
+
failed = read_member(stats, "failed")
|
|
383
|
+
return isinstance(failed, int) and not isinstance(failed, bool) and failed > 0
|
|
384
|
+
|
|
385
|
+
|
|
386
|
+
class ReviewSetsResource(Resource[HttpInfoMode]):
|
|
387
|
+
OPERATION_IDS = frozenset(
|
|
388
|
+
{
|
|
389
|
+
"ReviewSets_Query",
|
|
390
|
+
"ReviewSetsPendingOrders_Query",
|
|
391
|
+
"ReviewSets_CreateOrder",
|
|
392
|
+
"ReviewSets_CreateOrderAddSession",
|
|
393
|
+
"ReviewSets_GetOrderAddSession",
|
|
394
|
+
"ReviewSets_QueryOrderAddSessionResults",
|
|
395
|
+
"ReviewSets_CancelOrderAddSession",
|
|
396
|
+
"ReviewSets_ReleaseOrders",
|
|
397
|
+
"ReviewSets_GetReleaseSession",
|
|
398
|
+
"ReviewSets_QueryReleaseValidationResults",
|
|
399
|
+
"ReviewSets_QueryReleaseResults",
|
|
400
|
+
"ReviewSets_CancelRelease",
|
|
401
|
+
}
|
|
402
|
+
)
|
|
403
|
+
|
|
404
|
+
def _collection(
|
|
405
|
+
self,
|
|
406
|
+
operation_id: str,
|
|
407
|
+
*,
|
|
408
|
+
path_params: Mapping[str, object] | None = None,
|
|
409
|
+
filter: str | None = None,
|
|
410
|
+
order_by: str | None = None,
|
|
411
|
+
top: int | None = None,
|
|
412
|
+
skip: int | None = None,
|
|
413
|
+
count: bool | None = None,
|
|
414
|
+
) -> Page[Any] | ApiResponseProtocol[Page[Any]]:
|
|
415
|
+
return self._page(
|
|
416
|
+
operation_id,
|
|
417
|
+
path_params=path_params,
|
|
418
|
+
odata=ODataQuery(
|
|
419
|
+
filter=filter,
|
|
420
|
+
order_by=order_by,
|
|
421
|
+
top=top,
|
|
422
|
+
skip=skip,
|
|
423
|
+
count=count,
|
|
424
|
+
),
|
|
425
|
+
)
|
|
426
|
+
|
|
427
|
+
@overload
|
|
428
|
+
def list(
|
|
429
|
+
self: ReviewSetsResource[Literal[False]],
|
|
430
|
+
*,
|
|
431
|
+
filter: str | None = None,
|
|
432
|
+
order_by: str | None = None,
|
|
433
|
+
top: int | None = None,
|
|
434
|
+
skip: int | None = None,
|
|
435
|
+
count: bool | None = None,
|
|
436
|
+
) -> Page[ReviewSet]: ...
|
|
437
|
+
|
|
438
|
+
@overload
|
|
439
|
+
def list(
|
|
440
|
+
self: ReviewSetsResource[Literal[True]],
|
|
441
|
+
*,
|
|
442
|
+
filter: str | None = None,
|
|
443
|
+
order_by: str | None = None,
|
|
444
|
+
top: int | None = None,
|
|
445
|
+
skip: int | None = None,
|
|
446
|
+
count: bool | None = None,
|
|
447
|
+
) -> ApiResponseProtocol[Page[ReviewSet]]: ...
|
|
448
|
+
|
|
449
|
+
def list(
|
|
450
|
+
self,
|
|
451
|
+
*,
|
|
452
|
+
filter: str | None = None,
|
|
453
|
+
order_by: str | None = None,
|
|
454
|
+
top: int | None = None,
|
|
455
|
+
skip: int | None = None,
|
|
456
|
+
count: bool | None = None,
|
|
457
|
+
) -> Page[ReviewSet] | ApiResponseProtocol[Page[ReviewSet]]:
|
|
458
|
+
return self._collection(
|
|
459
|
+
"ReviewSets_Query",
|
|
460
|
+
filter=filter,
|
|
461
|
+
order_by=order_by,
|
|
462
|
+
top=top,
|
|
463
|
+
skip=skip,
|
|
464
|
+
count=count,
|
|
465
|
+
)
|
|
466
|
+
|
|
467
|
+
@overload
|
|
468
|
+
def list_pending_orders(
|
|
469
|
+
self: ReviewSetsResource[Literal[False]],
|
|
470
|
+
review_set_id: int,
|
|
471
|
+
*,
|
|
472
|
+
filter: str | None = None,
|
|
473
|
+
order_by: str | None = None,
|
|
474
|
+
top: int | None = None,
|
|
475
|
+
skip: int | None = None,
|
|
476
|
+
count: bool | None = None,
|
|
477
|
+
) -> Page[PendingOrder]: ...
|
|
478
|
+
|
|
479
|
+
@overload
|
|
480
|
+
def list_pending_orders(
|
|
481
|
+
self: ReviewSetsResource[Literal[True]],
|
|
482
|
+
review_set_id: int,
|
|
483
|
+
*,
|
|
484
|
+
filter: str | None = None,
|
|
485
|
+
order_by: str | None = None,
|
|
486
|
+
top: int | None = None,
|
|
487
|
+
skip: int | None = None,
|
|
488
|
+
count: bool | None = None,
|
|
489
|
+
) -> ApiResponseProtocol[Page[PendingOrder]]: ...
|
|
490
|
+
|
|
491
|
+
def list_pending_orders(
|
|
492
|
+
self,
|
|
493
|
+
review_set_id: int,
|
|
494
|
+
*,
|
|
495
|
+
filter: str | None = None,
|
|
496
|
+
order_by: str | None = None,
|
|
497
|
+
top: int | None = None,
|
|
498
|
+
skip: int | None = None,
|
|
499
|
+
count: bool | None = None,
|
|
500
|
+
) -> Page[PendingOrder] | ApiResponseProtocol[Page[PendingOrder]]:
|
|
501
|
+
require_positive_identifier("review_set_id", review_set_id)
|
|
502
|
+
return self._collection(
|
|
503
|
+
"ReviewSetsPendingOrders_Query",
|
|
504
|
+
path_params={"reviewSetId": review_set_id},
|
|
505
|
+
filter=filter,
|
|
506
|
+
order_by=order_by,
|
|
507
|
+
top=top,
|
|
508
|
+
skip=skip,
|
|
509
|
+
count=count,
|
|
510
|
+
)
|
|
511
|
+
|
|
512
|
+
@overload
|
|
513
|
+
def create_order(
|
|
514
|
+
self: ReviewSetsResource[Literal[False]],
|
|
515
|
+
review_set_id: int,
|
|
516
|
+
order: OrderCreate | Mapping[str, object],
|
|
517
|
+
*,
|
|
518
|
+
ignore_warnings: bool | None = None,
|
|
519
|
+
) -> OrderCreateResult: ...
|
|
520
|
+
|
|
521
|
+
@overload
|
|
522
|
+
def create_order(
|
|
523
|
+
self: ReviewSetsResource[Literal[True]],
|
|
524
|
+
review_set_id: int,
|
|
525
|
+
order: OrderCreate | Mapping[str, object],
|
|
526
|
+
*,
|
|
527
|
+
ignore_warnings: bool | None = None,
|
|
528
|
+
) -> ApiResponseProtocol[OrderCreateResult]: ...
|
|
529
|
+
|
|
530
|
+
def create_order(
|
|
531
|
+
self,
|
|
532
|
+
review_set_id: int,
|
|
533
|
+
order: OrderCreate | Mapping[str, object],
|
|
534
|
+
*,
|
|
535
|
+
ignore_warnings: bool | None = None,
|
|
536
|
+
) -> OrderCreateResult | ApiResponseProtocol[OrderCreateResult]:
|
|
537
|
+
require_positive_identifier("review_set_id", review_set_id)
|
|
538
|
+
payload = body_mapping(order)
|
|
539
|
+
_set_optional_boolean(payload, "ignoreWarnings", ignore_warnings)
|
|
540
|
+
response = self._request(
|
|
541
|
+
"ReviewSets_CreateOrder",
|
|
542
|
+
path_params={"reviewSetId": review_set_id},
|
|
543
|
+
json=payload,
|
|
544
|
+
)
|
|
545
|
+
return self._finish(response, response.data)
|
|
546
|
+
|
|
547
|
+
@overload
|
|
548
|
+
def start_order_add(
|
|
549
|
+
self: ReviewSetsResource[Literal[False]],
|
|
550
|
+
review_set_id: int,
|
|
551
|
+
orders: Sequence[OrderAddSessionItem | Mapping[str, object]],
|
|
552
|
+
*,
|
|
553
|
+
ignore_warnings: bool | None = None,
|
|
554
|
+
) -> OrderAddSessionHandle: ...
|
|
555
|
+
|
|
556
|
+
@overload
|
|
557
|
+
def start_order_add(
|
|
558
|
+
self: ReviewSetsResource[Literal[True]],
|
|
559
|
+
review_set_id: int,
|
|
560
|
+
orders: Sequence[OrderAddSessionItem | Mapping[str, object]],
|
|
561
|
+
*,
|
|
562
|
+
ignore_warnings: bool | None = None,
|
|
563
|
+
) -> ApiResponseProtocol[OrderAddSessionHandle]: ...
|
|
564
|
+
|
|
565
|
+
def start_order_add(
|
|
566
|
+
self,
|
|
567
|
+
review_set_id: int,
|
|
568
|
+
orders: Sequence[OrderAddSessionItem | Mapping[str, object]],
|
|
569
|
+
*,
|
|
570
|
+
ignore_warnings: bool | None = None,
|
|
571
|
+
) -> OrderAddSessionHandle | ApiResponseProtocol[OrderAddSessionHandle]:
|
|
572
|
+
require_positive_identifier("review_set_id", review_set_id)
|
|
573
|
+
if isinstance(orders, str | bytes | bytearray):
|
|
574
|
+
raise TypeError("orders must be a sequence of order requests")
|
|
575
|
+
order_values = list(orders)
|
|
576
|
+
if not 1 <= len(order_values) <= 500:
|
|
577
|
+
raise ValueError("orders must contain between 1 and 500 entries")
|
|
578
|
+
payload: dict[str, Any] = {"orders": [body_value(order) for order in order_values]}
|
|
579
|
+
_set_optional_boolean(payload, "ignoreWarnings", ignore_warnings)
|
|
580
|
+
response = self._request(
|
|
581
|
+
"ReviewSets_CreateOrderAddSession",
|
|
582
|
+
path_params={"reviewSetId": review_set_id},
|
|
583
|
+
json=payload,
|
|
584
|
+
)
|
|
585
|
+
session_id = read_member(response.data, "id")
|
|
586
|
+
if isinstance(session_id, bool) or not isinstance(session_id, int):
|
|
587
|
+
raise WorkflowProtocolError("order-add create response omitted integer id")
|
|
588
|
+
handle = OrderAddSessionHandle(
|
|
589
|
+
self._client,
|
|
590
|
+
review_set_id,
|
|
591
|
+
session_id,
|
|
592
|
+
latest=response.data,
|
|
593
|
+
)
|
|
594
|
+
return self._finish(response, handle)
|
|
595
|
+
|
|
596
|
+
@overload
|
|
597
|
+
def get_order_add_session(
|
|
598
|
+
self: ReviewSetsResource[Literal[False]], review_set_id: int, session_id: int
|
|
599
|
+
) -> OrderAddSessionHandle: ...
|
|
600
|
+
|
|
601
|
+
@overload
|
|
602
|
+
def get_order_add_session(
|
|
603
|
+
self: ReviewSetsResource[Literal[True]], review_set_id: int, session_id: int
|
|
604
|
+
) -> ApiResponseProtocol[OrderAddSessionHandle]: ...
|
|
605
|
+
|
|
606
|
+
def get_order_add_session(
|
|
607
|
+
self, review_set_id: int, session_id: int
|
|
608
|
+
) -> OrderAddSessionHandle | ApiResponseProtocol[OrderAddSessionHandle]:
|
|
609
|
+
require_positive_identifier("review_set_id", review_set_id)
|
|
610
|
+
require_positive_identifier("session_id", session_id)
|
|
611
|
+
response = self._request(
|
|
612
|
+
"ReviewSets_GetOrderAddSession",
|
|
613
|
+
path_params={"reviewSetId": review_set_id, "sessionId": session_id},
|
|
614
|
+
)
|
|
615
|
+
handle = OrderAddSessionHandle(
|
|
616
|
+
self._client, review_set_id, session_id, latest=response.data
|
|
617
|
+
)
|
|
618
|
+
return self._finish(response, handle)
|
|
619
|
+
|
|
620
|
+
@overload
|
|
621
|
+
def list_order_add_results(
|
|
622
|
+
self: ReviewSetsResource[Literal[False]],
|
|
623
|
+
review_set_id: int,
|
|
624
|
+
session_id: int,
|
|
625
|
+
*,
|
|
626
|
+
filter: str | None = None,
|
|
627
|
+
order_by: str | None = None,
|
|
628
|
+
top: int | None = None,
|
|
629
|
+
skip: int | None = None,
|
|
630
|
+
count: bool | None = None,
|
|
631
|
+
) -> Page[OrderAddResult]: ...
|
|
632
|
+
|
|
633
|
+
@overload
|
|
634
|
+
def list_order_add_results(
|
|
635
|
+
self: ReviewSetsResource[Literal[True]],
|
|
636
|
+
review_set_id: int,
|
|
637
|
+
session_id: int,
|
|
638
|
+
*,
|
|
639
|
+
filter: str | None = None,
|
|
640
|
+
order_by: str | None = None,
|
|
641
|
+
top: int | None = None,
|
|
642
|
+
skip: int | None = None,
|
|
643
|
+
count: bool | None = None,
|
|
644
|
+
) -> ApiResponseProtocol[Page[OrderAddResult]]: ...
|
|
645
|
+
|
|
646
|
+
def list_order_add_results(
|
|
647
|
+
self,
|
|
648
|
+
review_set_id: int,
|
|
649
|
+
session_id: int,
|
|
650
|
+
*,
|
|
651
|
+
filter: str | None = None,
|
|
652
|
+
order_by: str | None = None,
|
|
653
|
+
top: int | None = None,
|
|
654
|
+
skip: int | None = None,
|
|
655
|
+
count: bool | None = None,
|
|
656
|
+
) -> Page[OrderAddResult] | ApiResponseProtocol[Page[OrderAddResult]]:
|
|
657
|
+
require_positive_identifier("review_set_id", review_set_id)
|
|
658
|
+
require_positive_identifier("session_id", session_id)
|
|
659
|
+
return self._collection(
|
|
660
|
+
"ReviewSets_QueryOrderAddSessionResults",
|
|
661
|
+
path_params={"reviewSetId": review_set_id, "sessionId": session_id},
|
|
662
|
+
filter=filter,
|
|
663
|
+
order_by=order_by,
|
|
664
|
+
top=top,
|
|
665
|
+
skip=skip,
|
|
666
|
+
count=count,
|
|
667
|
+
)
|
|
668
|
+
|
|
669
|
+
@overload
|
|
670
|
+
def cancel_order_add_session(
|
|
671
|
+
self: ReviewSetsResource[Literal[False]], review_set_id: int, session_id: int
|
|
672
|
+
) -> OrderAddCancelResult: ...
|
|
673
|
+
|
|
674
|
+
@overload
|
|
675
|
+
def cancel_order_add_session(
|
|
676
|
+
self: ReviewSetsResource[Literal[True]], review_set_id: int, session_id: int
|
|
677
|
+
) -> ApiResponseProtocol[OrderAddCancelResult]: ...
|
|
678
|
+
|
|
679
|
+
def cancel_order_add_session(
|
|
680
|
+
self, review_set_id: int, session_id: int
|
|
681
|
+
) -> OrderAddCancelResult | ApiResponseProtocol[OrderAddCancelResult]:
|
|
682
|
+
require_positive_identifier("review_set_id", review_set_id)
|
|
683
|
+
require_positive_identifier("session_id", session_id)
|
|
684
|
+
response = self._request(
|
|
685
|
+
"ReviewSets_CancelOrderAddSession",
|
|
686
|
+
path_params={"reviewSetId": review_set_id, "sessionId": session_id},
|
|
687
|
+
)
|
|
688
|
+
return self._finish(response, response.data)
|
|
689
|
+
|
|
690
|
+
@overload
|
|
691
|
+
def start_release(
|
|
692
|
+
self: ReviewSetsResource[Literal[False]],
|
|
693
|
+
review_set_id: int,
|
|
694
|
+
*,
|
|
695
|
+
criteria: ReleaseCriteria | Mapping[str, object],
|
|
696
|
+
skip_validation: bool | None = None,
|
|
697
|
+
ignore_approval_warnings: bool | None = None,
|
|
698
|
+
allow_partial_release: bool | None = None,
|
|
699
|
+
) -> ReleaseSessionHandle: ...
|
|
700
|
+
|
|
701
|
+
@overload
|
|
702
|
+
def start_release(
|
|
703
|
+
self: ReviewSetsResource[Literal[True]],
|
|
704
|
+
review_set_id: int,
|
|
705
|
+
*,
|
|
706
|
+
criteria: ReleaseCriteria | Mapping[str, object],
|
|
707
|
+
skip_validation: bool | None = None,
|
|
708
|
+
ignore_approval_warnings: bool | None = None,
|
|
709
|
+
allow_partial_release: bool | None = None,
|
|
710
|
+
) -> ApiResponseProtocol[ReleaseSessionHandle]: ...
|
|
711
|
+
|
|
712
|
+
def start_release(
|
|
713
|
+
self,
|
|
714
|
+
review_set_id: int,
|
|
715
|
+
*,
|
|
716
|
+
criteria: ReleaseCriteria | Mapping[str, object],
|
|
717
|
+
skip_validation: bool | None = None,
|
|
718
|
+
ignore_approval_warnings: bool | None = None,
|
|
719
|
+
allow_partial_release: bool | None = None,
|
|
720
|
+
) -> ReleaseSessionHandle | ApiResponseProtocol[ReleaseSessionHandle]:
|
|
721
|
+
require_positive_identifier("review_set_id", review_set_id)
|
|
722
|
+
payload: dict[str, Any] = {"criteria": _normalize_criteria(criteria)}
|
|
723
|
+
_set_optional_boolean(payload, "skipValidation", skip_validation)
|
|
724
|
+
_set_optional_boolean(payload, "ignoreApprovalWarnings", ignore_approval_warnings)
|
|
725
|
+
_set_optional_boolean(payload, "allowPartialRelease", allow_partial_release)
|
|
726
|
+
response = self._request(
|
|
727
|
+
"ReviewSets_ReleaseOrders",
|
|
728
|
+
path_params={"reviewSetId": review_set_id},
|
|
729
|
+
json=payload,
|
|
730
|
+
)
|
|
731
|
+
session_id = read_member(response.data, "id")
|
|
732
|
+
if isinstance(session_id, bool) or not isinstance(session_id, int):
|
|
733
|
+
raise WorkflowProtocolError("release create response omitted integer id")
|
|
734
|
+
handle = ReleaseSessionHandle(
|
|
735
|
+
self._client,
|
|
736
|
+
review_set_id,
|
|
737
|
+
session_id,
|
|
738
|
+
latest=response.data,
|
|
739
|
+
)
|
|
740
|
+
return self._finish(response, handle)
|
|
741
|
+
|
|
742
|
+
@overload
|
|
743
|
+
def get_release_session(
|
|
744
|
+
self: ReviewSetsResource[Literal[False]], review_set_id: int, session_id: int
|
|
745
|
+
) -> ReleaseSessionHandle: ...
|
|
746
|
+
|
|
747
|
+
@overload
|
|
748
|
+
def get_release_session(
|
|
749
|
+
self: ReviewSetsResource[Literal[True]], review_set_id: int, session_id: int
|
|
750
|
+
) -> ApiResponseProtocol[ReleaseSessionHandle]: ...
|
|
751
|
+
|
|
752
|
+
def get_release_session(
|
|
753
|
+
self, review_set_id: int, session_id: int
|
|
754
|
+
) -> ReleaseSessionHandle | ApiResponseProtocol[ReleaseSessionHandle]:
|
|
755
|
+
require_positive_identifier("review_set_id", review_set_id)
|
|
756
|
+
require_positive_identifier("session_id", session_id)
|
|
757
|
+
response = self._request(
|
|
758
|
+
"ReviewSets_GetReleaseSession",
|
|
759
|
+
path_params={"reviewSetId": review_set_id, "sessionId": session_id},
|
|
760
|
+
)
|
|
761
|
+
handle = ReleaseSessionHandle(self._client, review_set_id, session_id, latest=response.data)
|
|
762
|
+
return self._finish(response, handle)
|
|
763
|
+
|
|
764
|
+
@overload
|
|
765
|
+
def list_release_validation_results(
|
|
766
|
+
self: ReviewSetsResource[Literal[False]],
|
|
767
|
+
review_set_id: int,
|
|
768
|
+
session_id: int,
|
|
769
|
+
*,
|
|
770
|
+
filter: str | None = None,
|
|
771
|
+
order_by: str | None = None,
|
|
772
|
+
top: int | None = None,
|
|
773
|
+
skip: int | None = None,
|
|
774
|
+
count: bool | None = None,
|
|
775
|
+
) -> Page[ReleaseValidationResult]: ...
|
|
776
|
+
|
|
777
|
+
@overload
|
|
778
|
+
def list_release_validation_results(
|
|
779
|
+
self: ReviewSetsResource[Literal[True]],
|
|
780
|
+
review_set_id: int,
|
|
781
|
+
session_id: int,
|
|
782
|
+
*,
|
|
783
|
+
filter: str | None = None,
|
|
784
|
+
order_by: str | None = None,
|
|
785
|
+
top: int | None = None,
|
|
786
|
+
skip: int | None = None,
|
|
787
|
+
count: bool | None = None,
|
|
788
|
+
) -> ApiResponseProtocol[Page[ReleaseValidationResult]]: ...
|
|
789
|
+
|
|
790
|
+
def list_release_validation_results(
|
|
791
|
+
self,
|
|
792
|
+
review_set_id: int,
|
|
793
|
+
session_id: int,
|
|
794
|
+
*,
|
|
795
|
+
filter: str | None = None,
|
|
796
|
+
order_by: str | None = None,
|
|
797
|
+
top: int | None = None,
|
|
798
|
+
skip: int | None = None,
|
|
799
|
+
count: bool | None = None,
|
|
800
|
+
) -> Page[ReleaseValidationResult] | ApiResponseProtocol[Page[ReleaseValidationResult]]:
|
|
801
|
+
require_positive_identifier("review_set_id", review_set_id)
|
|
802
|
+
require_positive_identifier("session_id", session_id)
|
|
803
|
+
return self._collection(
|
|
804
|
+
"ReviewSets_QueryReleaseValidationResults",
|
|
805
|
+
path_params={"reviewSetId": review_set_id, "sessionId": session_id},
|
|
806
|
+
filter=filter,
|
|
807
|
+
order_by=order_by,
|
|
808
|
+
top=top,
|
|
809
|
+
skip=skip,
|
|
810
|
+
count=count,
|
|
811
|
+
)
|
|
812
|
+
|
|
813
|
+
@overload
|
|
814
|
+
def list_release_errors(
|
|
815
|
+
self: ReviewSetsResource[Literal[False]],
|
|
816
|
+
review_set_id: int,
|
|
817
|
+
session_id: int,
|
|
818
|
+
*,
|
|
819
|
+
filter: str | None = None,
|
|
820
|
+
order_by: str | None = None,
|
|
821
|
+
top: int | None = None,
|
|
822
|
+
skip: int | None = None,
|
|
823
|
+
count: bool | None = None,
|
|
824
|
+
) -> Page[ReleaseError]: ...
|
|
825
|
+
|
|
826
|
+
@overload
|
|
827
|
+
def list_release_errors(
|
|
828
|
+
self: ReviewSetsResource[Literal[True]],
|
|
829
|
+
review_set_id: int,
|
|
830
|
+
session_id: int,
|
|
831
|
+
*,
|
|
832
|
+
filter: str | None = None,
|
|
833
|
+
order_by: str | None = None,
|
|
834
|
+
top: int | None = None,
|
|
835
|
+
skip: int | None = None,
|
|
836
|
+
count: bool | None = None,
|
|
837
|
+
) -> ApiResponseProtocol[Page[ReleaseError]]: ...
|
|
838
|
+
|
|
839
|
+
def list_release_errors(
|
|
840
|
+
self,
|
|
841
|
+
review_set_id: int,
|
|
842
|
+
session_id: int,
|
|
843
|
+
*,
|
|
844
|
+
filter: str | None = None,
|
|
845
|
+
order_by: str | None = None,
|
|
846
|
+
top: int | None = None,
|
|
847
|
+
skip: int | None = None,
|
|
848
|
+
count: bool | None = None,
|
|
849
|
+
) -> Page[ReleaseError] | ApiResponseProtocol[Page[ReleaseError]]:
|
|
850
|
+
require_positive_identifier("review_set_id", review_set_id)
|
|
851
|
+
require_positive_identifier("session_id", session_id)
|
|
852
|
+
return self._collection(
|
|
853
|
+
"ReviewSets_QueryReleaseResults",
|
|
854
|
+
path_params={"reviewSetId": review_set_id, "sessionId": session_id},
|
|
855
|
+
filter=filter,
|
|
856
|
+
order_by=order_by,
|
|
857
|
+
top=top,
|
|
858
|
+
skip=skip,
|
|
859
|
+
count=count,
|
|
860
|
+
)
|
|
861
|
+
|
|
862
|
+
@overload
|
|
863
|
+
def cancel_release(
|
|
864
|
+
self: ReviewSetsResource[Literal[False]], review_set_id: int, session_id: int
|
|
865
|
+
) -> ReviewSetsCancelReleaseResponse200 | ReviewSetsCancelReleaseResponse202: ...
|
|
866
|
+
|
|
867
|
+
@overload
|
|
868
|
+
def cancel_release(
|
|
869
|
+
self: ReviewSetsResource[Literal[True]], review_set_id: int, session_id: int
|
|
870
|
+
) -> ApiResponseProtocol[
|
|
871
|
+
ReviewSetsCancelReleaseResponse200 | ReviewSetsCancelReleaseResponse202
|
|
872
|
+
]: ...
|
|
873
|
+
|
|
874
|
+
def cancel_release(
|
|
875
|
+
self, review_set_id: int, session_id: int
|
|
876
|
+
) -> (
|
|
877
|
+
ReviewSetsCancelReleaseResponse200
|
|
878
|
+
| ReviewSetsCancelReleaseResponse202
|
|
879
|
+
| ApiResponseProtocol[
|
|
880
|
+
ReviewSetsCancelReleaseResponse200 | ReviewSetsCancelReleaseResponse202
|
|
881
|
+
]
|
|
882
|
+
):
|
|
883
|
+
require_positive_identifier("review_set_id", review_set_id)
|
|
884
|
+
require_positive_identifier("session_id", session_id)
|
|
885
|
+
response = self._request(
|
|
886
|
+
"ReviewSets_CancelRelease",
|
|
887
|
+
path_params={"reviewSetId": review_set_id, "sessionId": session_id},
|
|
888
|
+
)
|
|
889
|
+
return self._finish(response, response.data)
|