databricks-sdk 0.44.0__py3-none-any.whl → 0.45.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.
Potentially problematic release.
This version of databricks-sdk might be problematic. Click here for more details.
- databricks/sdk/__init__.py +123 -115
- databricks/sdk/_base_client.py +112 -88
- databricks/sdk/_property.py +12 -7
- databricks/sdk/_widgets/__init__.py +13 -2
- databricks/sdk/_widgets/default_widgets_utils.py +21 -15
- databricks/sdk/_widgets/ipywidgets_utils.py +47 -24
- databricks/sdk/azure.py +8 -6
- databricks/sdk/casing.py +5 -5
- databricks/sdk/config.py +152 -99
- databricks/sdk/core.py +57 -47
- databricks/sdk/credentials_provider.py +360 -210
- databricks/sdk/data_plane.py +86 -3
- databricks/sdk/dbutils.py +123 -87
- databricks/sdk/environments.py +52 -35
- databricks/sdk/errors/base.py +61 -35
- databricks/sdk/errors/customizer.py +3 -3
- databricks/sdk/errors/deserializer.py +38 -25
- databricks/sdk/errors/details.py +417 -0
- databricks/sdk/errors/mapper.py +1 -1
- databricks/sdk/errors/overrides.py +27 -24
- databricks/sdk/errors/parser.py +26 -14
- databricks/sdk/errors/platform.py +10 -10
- databricks/sdk/errors/private_link.py +24 -24
- databricks/sdk/logger/round_trip_logger.py +28 -20
- databricks/sdk/mixins/compute.py +90 -60
- databricks/sdk/mixins/files.py +815 -145
- databricks/sdk/mixins/jobs.py +201 -20
- databricks/sdk/mixins/open_ai_client.py +26 -20
- databricks/sdk/mixins/workspace.py +45 -34
- databricks/sdk/oauth.py +372 -196
- databricks/sdk/retries.py +14 -12
- databricks/sdk/runtime/__init__.py +34 -17
- databricks/sdk/runtime/dbutils_stub.py +52 -39
- databricks/sdk/service/_internal.py +12 -7
- databricks/sdk/service/apps.py +618 -418
- databricks/sdk/service/billing.py +827 -604
- databricks/sdk/service/catalog.py +6552 -4474
- databricks/sdk/service/cleanrooms.py +550 -388
- databricks/sdk/service/compute.py +5241 -3531
- databricks/sdk/service/dashboards.py +1313 -923
- databricks/sdk/service/files.py +442 -309
- databricks/sdk/service/iam.py +2115 -1483
- databricks/sdk/service/jobs.py +4151 -2588
- databricks/sdk/service/marketplace.py +2210 -1517
- databricks/sdk/service/ml.py +3364 -2255
- databricks/sdk/service/oauth2.py +922 -584
- databricks/sdk/service/pipelines.py +1865 -1203
- databricks/sdk/service/provisioning.py +1435 -1029
- databricks/sdk/service/serving.py +2040 -1278
- databricks/sdk/service/settings.py +2846 -1929
- databricks/sdk/service/sharing.py +2201 -877
- databricks/sdk/service/sql.py +4650 -3103
- databricks/sdk/service/vectorsearch.py +816 -550
- databricks/sdk/service/workspace.py +1330 -906
- databricks/sdk/useragent.py +36 -22
- databricks/sdk/version.py +1 -1
- {databricks_sdk-0.44.0.dist-info → databricks_sdk-0.45.0.dist-info}/METADATA +31 -31
- databricks_sdk-0.45.0.dist-info/RECORD +70 -0
- {databricks_sdk-0.44.0.dist-info → databricks_sdk-0.45.0.dist-info}/WHEEL +1 -1
- databricks_sdk-0.44.0.dist-info/RECORD +0 -69
- {databricks_sdk-0.44.0.dist-info → databricks_sdk-0.45.0.dist-info}/LICENSE +0 -0
- {databricks_sdk-0.44.0.dist-info → databricks_sdk-0.45.0.dist-info}/NOTICE +0 -0
- {databricks_sdk-0.44.0.dist-info → databricks_sdk-0.45.0.dist-info}/top_level.txt +0 -0
databricks/sdk/service/oauth2.py
CHANGED
|
@@ -4,11 +4,12 @@ from __future__ import annotations
|
|
|
4
4
|
|
|
5
5
|
import logging
|
|
6
6
|
from dataclasses import dataclass
|
|
7
|
-
from typing import Dict, Iterator, List, Optional
|
|
7
|
+
from typing import Any, Dict, Iterator, List, Optional
|
|
8
8
|
|
|
9
9
|
from ._internal import _from_dict, _repeated_dict
|
|
10
10
|
|
|
11
|
-
_LOG = logging.getLogger(
|
|
11
|
+
_LOG = logging.getLogger("databricks.sdk")
|
|
12
|
+
|
|
12
13
|
|
|
13
14
|
# all definitions in this file are in alphabetical order
|
|
14
15
|
|
|
@@ -38,35 +39,48 @@ class CreateCustomAppIntegration:
|
|
|
38
39
|
def as_dict(self) -> dict:
|
|
39
40
|
"""Serializes the CreateCustomAppIntegration into a dictionary suitable for use as a JSON request body."""
|
|
40
41
|
body = {}
|
|
41
|
-
if self.confidential is not None:
|
|
42
|
-
|
|
43
|
-
if self.
|
|
44
|
-
|
|
45
|
-
if self.
|
|
42
|
+
if self.confidential is not None:
|
|
43
|
+
body["confidential"] = self.confidential
|
|
44
|
+
if self.name is not None:
|
|
45
|
+
body["name"] = self.name
|
|
46
|
+
if self.redirect_urls:
|
|
47
|
+
body["redirect_urls"] = [v for v in self.redirect_urls]
|
|
48
|
+
if self.scopes:
|
|
49
|
+
body["scopes"] = [v for v in self.scopes]
|
|
50
|
+
if self.token_access_policy:
|
|
51
|
+
body["token_access_policy"] = self.token_access_policy.as_dict()
|
|
46
52
|
if self.user_authorized_scopes:
|
|
47
|
-
body[
|
|
53
|
+
body["user_authorized_scopes"] = [v for v in self.user_authorized_scopes]
|
|
48
54
|
return body
|
|
49
55
|
|
|
50
56
|
def as_shallow_dict(self) -> dict:
|
|
51
57
|
"""Serializes the CreateCustomAppIntegration into a shallow dictionary of its immediate attributes."""
|
|
52
58
|
body = {}
|
|
53
|
-
if self.confidential is not None:
|
|
54
|
-
|
|
55
|
-
if self.
|
|
56
|
-
|
|
57
|
-
if self.
|
|
58
|
-
|
|
59
|
+
if self.confidential is not None:
|
|
60
|
+
body["confidential"] = self.confidential
|
|
61
|
+
if self.name is not None:
|
|
62
|
+
body["name"] = self.name
|
|
63
|
+
if self.redirect_urls:
|
|
64
|
+
body["redirect_urls"] = self.redirect_urls
|
|
65
|
+
if self.scopes:
|
|
66
|
+
body["scopes"] = self.scopes
|
|
67
|
+
if self.token_access_policy:
|
|
68
|
+
body["token_access_policy"] = self.token_access_policy
|
|
69
|
+
if self.user_authorized_scopes:
|
|
70
|
+
body["user_authorized_scopes"] = self.user_authorized_scopes
|
|
59
71
|
return body
|
|
60
72
|
|
|
61
73
|
@classmethod
|
|
62
|
-
def from_dict(cls, d: Dict[str,
|
|
74
|
+
def from_dict(cls, d: Dict[str, Any]) -> CreateCustomAppIntegration:
|
|
63
75
|
"""Deserializes the CreateCustomAppIntegration from a dictionary."""
|
|
64
|
-
return cls(
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
76
|
+
return cls(
|
|
77
|
+
confidential=d.get("confidential", None),
|
|
78
|
+
name=d.get("name", None),
|
|
79
|
+
redirect_urls=d.get("redirect_urls", None),
|
|
80
|
+
scopes=d.get("scopes", None),
|
|
81
|
+
token_access_policy=_from_dict(d, "token_access_policy", TokenAccessPolicy),
|
|
82
|
+
user_authorized_scopes=d.get("user_authorized_scopes", None),
|
|
83
|
+
)
|
|
70
84
|
|
|
71
85
|
|
|
72
86
|
@dataclass
|
|
@@ -84,25 +98,33 @@ class CreateCustomAppIntegrationOutput:
|
|
|
84
98
|
def as_dict(self) -> dict:
|
|
85
99
|
"""Serializes the CreateCustomAppIntegrationOutput into a dictionary suitable for use as a JSON request body."""
|
|
86
100
|
body = {}
|
|
87
|
-
if self.client_id is not None:
|
|
88
|
-
|
|
89
|
-
if self.
|
|
101
|
+
if self.client_id is not None:
|
|
102
|
+
body["client_id"] = self.client_id
|
|
103
|
+
if self.client_secret is not None:
|
|
104
|
+
body["client_secret"] = self.client_secret
|
|
105
|
+
if self.integration_id is not None:
|
|
106
|
+
body["integration_id"] = self.integration_id
|
|
90
107
|
return body
|
|
91
108
|
|
|
92
109
|
def as_shallow_dict(self) -> dict:
|
|
93
110
|
"""Serializes the CreateCustomAppIntegrationOutput into a shallow dictionary of its immediate attributes."""
|
|
94
111
|
body = {}
|
|
95
|
-
if self.client_id is not None:
|
|
96
|
-
|
|
97
|
-
if self.
|
|
112
|
+
if self.client_id is not None:
|
|
113
|
+
body["client_id"] = self.client_id
|
|
114
|
+
if self.client_secret is not None:
|
|
115
|
+
body["client_secret"] = self.client_secret
|
|
116
|
+
if self.integration_id is not None:
|
|
117
|
+
body["integration_id"] = self.integration_id
|
|
98
118
|
return body
|
|
99
119
|
|
|
100
120
|
@classmethod
|
|
101
|
-
def from_dict(cls, d: Dict[str,
|
|
121
|
+
def from_dict(cls, d: Dict[str, Any]) -> CreateCustomAppIntegrationOutput:
|
|
102
122
|
"""Deserializes the CreateCustomAppIntegrationOutput from a dictionary."""
|
|
103
|
-
return cls(
|
|
104
|
-
|
|
105
|
-
|
|
123
|
+
return cls(
|
|
124
|
+
client_id=d.get("client_id", None),
|
|
125
|
+
client_secret=d.get("client_secret", None),
|
|
126
|
+
integration_id=d.get("integration_id", None),
|
|
127
|
+
)
|
|
106
128
|
|
|
107
129
|
|
|
108
130
|
@dataclass
|
|
@@ -116,22 +138,27 @@ class CreatePublishedAppIntegration:
|
|
|
116
138
|
def as_dict(self) -> dict:
|
|
117
139
|
"""Serializes the CreatePublishedAppIntegration into a dictionary suitable for use as a JSON request body."""
|
|
118
140
|
body = {}
|
|
119
|
-
if self.app_id is not None:
|
|
120
|
-
|
|
141
|
+
if self.app_id is not None:
|
|
142
|
+
body["app_id"] = self.app_id
|
|
143
|
+
if self.token_access_policy:
|
|
144
|
+
body["token_access_policy"] = self.token_access_policy.as_dict()
|
|
121
145
|
return body
|
|
122
146
|
|
|
123
147
|
def as_shallow_dict(self) -> dict:
|
|
124
148
|
"""Serializes the CreatePublishedAppIntegration into a shallow dictionary of its immediate attributes."""
|
|
125
149
|
body = {}
|
|
126
|
-
if self.app_id is not None:
|
|
127
|
-
|
|
150
|
+
if self.app_id is not None:
|
|
151
|
+
body["app_id"] = self.app_id
|
|
152
|
+
if self.token_access_policy:
|
|
153
|
+
body["token_access_policy"] = self.token_access_policy
|
|
128
154
|
return body
|
|
129
155
|
|
|
130
156
|
@classmethod
|
|
131
|
-
def from_dict(cls, d: Dict[str,
|
|
157
|
+
def from_dict(cls, d: Dict[str, Any]) -> CreatePublishedAppIntegration:
|
|
132
158
|
"""Deserializes the CreatePublishedAppIntegration from a dictionary."""
|
|
133
|
-
return cls(
|
|
134
|
-
|
|
159
|
+
return cls(
|
|
160
|
+
app_id=d.get("app_id", None), token_access_policy=_from_dict(d, "token_access_policy", TokenAccessPolicy)
|
|
161
|
+
)
|
|
135
162
|
|
|
136
163
|
|
|
137
164
|
@dataclass
|
|
@@ -142,19 +169,54 @@ class CreatePublishedAppIntegrationOutput:
|
|
|
142
169
|
def as_dict(self) -> dict:
|
|
143
170
|
"""Serializes the CreatePublishedAppIntegrationOutput into a dictionary suitable for use as a JSON request body."""
|
|
144
171
|
body = {}
|
|
145
|
-
if self.integration_id is not None:
|
|
172
|
+
if self.integration_id is not None:
|
|
173
|
+
body["integration_id"] = self.integration_id
|
|
146
174
|
return body
|
|
147
175
|
|
|
148
176
|
def as_shallow_dict(self) -> dict:
|
|
149
177
|
"""Serializes the CreatePublishedAppIntegrationOutput into a shallow dictionary of its immediate attributes."""
|
|
150
178
|
body = {}
|
|
151
|
-
if self.integration_id is not None:
|
|
179
|
+
if self.integration_id is not None:
|
|
180
|
+
body["integration_id"] = self.integration_id
|
|
152
181
|
return body
|
|
153
182
|
|
|
154
183
|
@classmethod
|
|
155
|
-
def from_dict(cls, d: Dict[str,
|
|
184
|
+
def from_dict(cls, d: Dict[str, Any]) -> CreatePublishedAppIntegrationOutput:
|
|
156
185
|
"""Deserializes the CreatePublishedAppIntegrationOutput from a dictionary."""
|
|
157
|
-
return cls(integration_id=d.get(
|
|
186
|
+
return cls(integration_id=d.get("integration_id", None))
|
|
187
|
+
|
|
188
|
+
|
|
189
|
+
@dataclass
|
|
190
|
+
class CreateServicePrincipalSecretRequest:
|
|
191
|
+
lifetime: Optional[str] = None
|
|
192
|
+
"""The lifetime of the secret in seconds. If this parameter is not provided, the secret will have a
|
|
193
|
+
default lifetime of 730 days (63072000s)."""
|
|
194
|
+
|
|
195
|
+
service_principal_id: Optional[int] = None
|
|
196
|
+
"""The service principal ID."""
|
|
197
|
+
|
|
198
|
+
def as_dict(self) -> dict:
|
|
199
|
+
"""Serializes the CreateServicePrincipalSecretRequest into a dictionary suitable for use as a JSON request body."""
|
|
200
|
+
body = {}
|
|
201
|
+
if self.lifetime is not None:
|
|
202
|
+
body["lifetime"] = self.lifetime
|
|
203
|
+
if self.service_principal_id is not None:
|
|
204
|
+
body["service_principal_id"] = self.service_principal_id
|
|
205
|
+
return body
|
|
206
|
+
|
|
207
|
+
def as_shallow_dict(self) -> dict:
|
|
208
|
+
"""Serializes the CreateServicePrincipalSecretRequest into a shallow dictionary of its immediate attributes."""
|
|
209
|
+
body = {}
|
|
210
|
+
if self.lifetime is not None:
|
|
211
|
+
body["lifetime"] = self.lifetime
|
|
212
|
+
if self.service_principal_id is not None:
|
|
213
|
+
body["service_principal_id"] = self.service_principal_id
|
|
214
|
+
return body
|
|
215
|
+
|
|
216
|
+
@classmethod
|
|
217
|
+
def from_dict(cls, d: Dict[str, Any]) -> CreateServicePrincipalSecretRequest:
|
|
218
|
+
"""Deserializes the CreateServicePrincipalSecretRequest from a dictionary."""
|
|
219
|
+
return cls(lifetime=d.get("lifetime", None), service_principal_id=d.get("service_principal_id", None))
|
|
158
220
|
|
|
159
221
|
|
|
160
222
|
@dataclass
|
|
@@ -162,6 +224,9 @@ class CreateServicePrincipalSecretResponse:
|
|
|
162
224
|
create_time: Optional[str] = None
|
|
163
225
|
"""UTC time when the secret was created"""
|
|
164
226
|
|
|
227
|
+
expire_time: Optional[str] = None
|
|
228
|
+
"""UTC time when the secret will expire. If the field is not present, the secret does not expire."""
|
|
229
|
+
|
|
165
230
|
id: Optional[str] = None
|
|
166
231
|
"""ID of the secret"""
|
|
167
232
|
|
|
@@ -180,39 +245,57 @@ class CreateServicePrincipalSecretResponse:
|
|
|
180
245
|
def as_dict(self) -> dict:
|
|
181
246
|
"""Serializes the CreateServicePrincipalSecretResponse into a dictionary suitable for use as a JSON request body."""
|
|
182
247
|
body = {}
|
|
183
|
-
if self.create_time is not None:
|
|
184
|
-
|
|
185
|
-
if self.
|
|
186
|
-
|
|
187
|
-
if self.
|
|
188
|
-
|
|
248
|
+
if self.create_time is not None:
|
|
249
|
+
body["create_time"] = self.create_time
|
|
250
|
+
if self.expire_time is not None:
|
|
251
|
+
body["expire_time"] = self.expire_time
|
|
252
|
+
if self.id is not None:
|
|
253
|
+
body["id"] = self.id
|
|
254
|
+
if self.secret is not None:
|
|
255
|
+
body["secret"] = self.secret
|
|
256
|
+
if self.secret_hash is not None:
|
|
257
|
+
body["secret_hash"] = self.secret_hash
|
|
258
|
+
if self.status is not None:
|
|
259
|
+
body["status"] = self.status
|
|
260
|
+
if self.update_time is not None:
|
|
261
|
+
body["update_time"] = self.update_time
|
|
189
262
|
return body
|
|
190
263
|
|
|
191
264
|
def as_shallow_dict(self) -> dict:
|
|
192
265
|
"""Serializes the CreateServicePrincipalSecretResponse into a shallow dictionary of its immediate attributes."""
|
|
193
266
|
body = {}
|
|
194
|
-
if self.create_time is not None:
|
|
195
|
-
|
|
196
|
-
if self.
|
|
197
|
-
|
|
198
|
-
if self.
|
|
199
|
-
|
|
267
|
+
if self.create_time is not None:
|
|
268
|
+
body["create_time"] = self.create_time
|
|
269
|
+
if self.expire_time is not None:
|
|
270
|
+
body["expire_time"] = self.expire_time
|
|
271
|
+
if self.id is not None:
|
|
272
|
+
body["id"] = self.id
|
|
273
|
+
if self.secret is not None:
|
|
274
|
+
body["secret"] = self.secret
|
|
275
|
+
if self.secret_hash is not None:
|
|
276
|
+
body["secret_hash"] = self.secret_hash
|
|
277
|
+
if self.status is not None:
|
|
278
|
+
body["status"] = self.status
|
|
279
|
+
if self.update_time is not None:
|
|
280
|
+
body["update_time"] = self.update_time
|
|
200
281
|
return body
|
|
201
282
|
|
|
202
283
|
@classmethod
|
|
203
|
-
def from_dict(cls, d: Dict[str,
|
|
284
|
+
def from_dict(cls, d: Dict[str, Any]) -> CreateServicePrincipalSecretResponse:
|
|
204
285
|
"""Deserializes the CreateServicePrincipalSecretResponse from a dictionary."""
|
|
205
|
-
return cls(
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
286
|
+
return cls(
|
|
287
|
+
create_time=d.get("create_time", None),
|
|
288
|
+
expire_time=d.get("expire_time", None),
|
|
289
|
+
id=d.get("id", None),
|
|
290
|
+
secret=d.get("secret", None),
|
|
291
|
+
secret_hash=d.get("secret_hash", None),
|
|
292
|
+
status=d.get("status", None),
|
|
293
|
+
update_time=d.get("update_time", None),
|
|
294
|
+
)
|
|
211
295
|
|
|
212
296
|
|
|
213
297
|
@dataclass
|
|
214
298
|
class DeleteCustomAppIntegrationOutput:
|
|
215
|
-
|
|
216
299
|
def as_dict(self) -> dict:
|
|
217
300
|
"""Serializes the DeleteCustomAppIntegrationOutput into a dictionary suitable for use as a JSON request body."""
|
|
218
301
|
body = {}
|
|
@@ -224,14 +307,13 @@ class DeleteCustomAppIntegrationOutput:
|
|
|
224
307
|
return body
|
|
225
308
|
|
|
226
309
|
@classmethod
|
|
227
|
-
def from_dict(cls, d: Dict[str,
|
|
310
|
+
def from_dict(cls, d: Dict[str, Any]) -> DeleteCustomAppIntegrationOutput:
|
|
228
311
|
"""Deserializes the DeleteCustomAppIntegrationOutput from a dictionary."""
|
|
229
312
|
return cls()
|
|
230
313
|
|
|
231
314
|
|
|
232
315
|
@dataclass
|
|
233
316
|
class DeletePublishedAppIntegrationOutput:
|
|
234
|
-
|
|
235
317
|
def as_dict(self) -> dict:
|
|
236
318
|
"""Serializes the DeletePublishedAppIntegrationOutput into a dictionary suitable for use as a JSON request body."""
|
|
237
319
|
body = {}
|
|
@@ -243,14 +325,13 @@ class DeletePublishedAppIntegrationOutput:
|
|
|
243
325
|
return body
|
|
244
326
|
|
|
245
327
|
@classmethod
|
|
246
|
-
def from_dict(cls, d: Dict[str,
|
|
328
|
+
def from_dict(cls, d: Dict[str, Any]) -> DeletePublishedAppIntegrationOutput:
|
|
247
329
|
"""Deserializes the DeletePublishedAppIntegrationOutput from a dictionary."""
|
|
248
330
|
return cls()
|
|
249
331
|
|
|
250
332
|
|
|
251
333
|
@dataclass
|
|
252
334
|
class DeleteResponse:
|
|
253
|
-
|
|
254
335
|
def as_dict(self) -> dict:
|
|
255
336
|
"""Serializes the DeleteResponse into a dictionary suitable for use as a JSON request body."""
|
|
256
337
|
body = {}
|
|
@@ -262,7 +343,7 @@ class DeleteResponse:
|
|
|
262
343
|
return body
|
|
263
344
|
|
|
264
345
|
@classmethod
|
|
265
|
-
def from_dict(cls, d: Dict[str,
|
|
346
|
+
def from_dict(cls, d: Dict[str, Any]) -> DeleteResponse:
|
|
266
347
|
"""Deserializes the DeleteResponse from a dictionary."""
|
|
267
348
|
return cls()
|
|
268
349
|
|
|
@@ -296,34 +377,48 @@ class FederationPolicy:
|
|
|
296
377
|
def as_dict(self) -> dict:
|
|
297
378
|
"""Serializes the FederationPolicy into a dictionary suitable for use as a JSON request body."""
|
|
298
379
|
body = {}
|
|
299
|
-
if self.create_time is not None:
|
|
300
|
-
|
|
301
|
-
if self.
|
|
302
|
-
|
|
303
|
-
if self.
|
|
304
|
-
|
|
380
|
+
if self.create_time is not None:
|
|
381
|
+
body["create_time"] = self.create_time
|
|
382
|
+
if self.description is not None:
|
|
383
|
+
body["description"] = self.description
|
|
384
|
+
if self.name is not None:
|
|
385
|
+
body["name"] = self.name
|
|
386
|
+
if self.oidc_policy:
|
|
387
|
+
body["oidc_policy"] = self.oidc_policy.as_dict()
|
|
388
|
+
if self.uid is not None:
|
|
389
|
+
body["uid"] = self.uid
|
|
390
|
+
if self.update_time is not None:
|
|
391
|
+
body["update_time"] = self.update_time
|
|
305
392
|
return body
|
|
306
393
|
|
|
307
394
|
def as_shallow_dict(self) -> dict:
|
|
308
395
|
"""Serializes the FederationPolicy into a shallow dictionary of its immediate attributes."""
|
|
309
396
|
body = {}
|
|
310
|
-
if self.create_time is not None:
|
|
311
|
-
|
|
312
|
-
if self.
|
|
313
|
-
|
|
314
|
-
if self.
|
|
315
|
-
|
|
397
|
+
if self.create_time is not None:
|
|
398
|
+
body["create_time"] = self.create_time
|
|
399
|
+
if self.description is not None:
|
|
400
|
+
body["description"] = self.description
|
|
401
|
+
if self.name is not None:
|
|
402
|
+
body["name"] = self.name
|
|
403
|
+
if self.oidc_policy:
|
|
404
|
+
body["oidc_policy"] = self.oidc_policy
|
|
405
|
+
if self.uid is not None:
|
|
406
|
+
body["uid"] = self.uid
|
|
407
|
+
if self.update_time is not None:
|
|
408
|
+
body["update_time"] = self.update_time
|
|
316
409
|
return body
|
|
317
410
|
|
|
318
411
|
@classmethod
|
|
319
|
-
def from_dict(cls, d: Dict[str,
|
|
412
|
+
def from_dict(cls, d: Dict[str, Any]) -> FederationPolicy:
|
|
320
413
|
"""Deserializes the FederationPolicy from a dictionary."""
|
|
321
|
-
return cls(
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
|
|
326
|
-
|
|
414
|
+
return cls(
|
|
415
|
+
create_time=d.get("create_time", None),
|
|
416
|
+
description=d.get("description", None),
|
|
417
|
+
name=d.get("name", None),
|
|
418
|
+
oidc_policy=_from_dict(d, "oidc_policy", OidcFederationPolicy),
|
|
419
|
+
uid=d.get("uid", None),
|
|
420
|
+
update_time=d.get("update_time", None),
|
|
421
|
+
)
|
|
327
422
|
|
|
328
423
|
|
|
329
424
|
@dataclass
|
|
@@ -361,50 +456,73 @@ class GetCustomAppIntegrationOutput:
|
|
|
361
456
|
def as_dict(self) -> dict:
|
|
362
457
|
"""Serializes the GetCustomAppIntegrationOutput into a dictionary suitable for use as a JSON request body."""
|
|
363
458
|
body = {}
|
|
364
|
-
if self.client_id is not None:
|
|
365
|
-
|
|
366
|
-
if self.
|
|
367
|
-
|
|
368
|
-
if self.
|
|
369
|
-
|
|
370
|
-
if self.
|
|
371
|
-
|
|
372
|
-
if self.
|
|
373
|
-
|
|
459
|
+
if self.client_id is not None:
|
|
460
|
+
body["client_id"] = self.client_id
|
|
461
|
+
if self.confidential is not None:
|
|
462
|
+
body["confidential"] = self.confidential
|
|
463
|
+
if self.create_time is not None:
|
|
464
|
+
body["create_time"] = self.create_time
|
|
465
|
+
if self.created_by is not None:
|
|
466
|
+
body["created_by"] = self.created_by
|
|
467
|
+
if self.creator_username is not None:
|
|
468
|
+
body["creator_username"] = self.creator_username
|
|
469
|
+
if self.integration_id is not None:
|
|
470
|
+
body["integration_id"] = self.integration_id
|
|
471
|
+
if self.name is not None:
|
|
472
|
+
body["name"] = self.name
|
|
473
|
+
if self.redirect_urls:
|
|
474
|
+
body["redirect_urls"] = [v for v in self.redirect_urls]
|
|
475
|
+
if self.scopes:
|
|
476
|
+
body["scopes"] = [v for v in self.scopes]
|
|
477
|
+
if self.token_access_policy:
|
|
478
|
+
body["token_access_policy"] = self.token_access_policy.as_dict()
|
|
374
479
|
if self.user_authorized_scopes:
|
|
375
|
-
body[
|
|
480
|
+
body["user_authorized_scopes"] = [v for v in self.user_authorized_scopes]
|
|
376
481
|
return body
|
|
377
482
|
|
|
378
483
|
def as_shallow_dict(self) -> dict:
|
|
379
484
|
"""Serializes the GetCustomAppIntegrationOutput into a shallow dictionary of its immediate attributes."""
|
|
380
485
|
body = {}
|
|
381
|
-
if self.client_id is not None:
|
|
382
|
-
|
|
383
|
-
if self.
|
|
384
|
-
|
|
385
|
-
if self.
|
|
386
|
-
|
|
387
|
-
if self.
|
|
388
|
-
|
|
389
|
-
if self.
|
|
390
|
-
|
|
391
|
-
if self.
|
|
486
|
+
if self.client_id is not None:
|
|
487
|
+
body["client_id"] = self.client_id
|
|
488
|
+
if self.confidential is not None:
|
|
489
|
+
body["confidential"] = self.confidential
|
|
490
|
+
if self.create_time is not None:
|
|
491
|
+
body["create_time"] = self.create_time
|
|
492
|
+
if self.created_by is not None:
|
|
493
|
+
body["created_by"] = self.created_by
|
|
494
|
+
if self.creator_username is not None:
|
|
495
|
+
body["creator_username"] = self.creator_username
|
|
496
|
+
if self.integration_id is not None:
|
|
497
|
+
body["integration_id"] = self.integration_id
|
|
498
|
+
if self.name is not None:
|
|
499
|
+
body["name"] = self.name
|
|
500
|
+
if self.redirect_urls:
|
|
501
|
+
body["redirect_urls"] = self.redirect_urls
|
|
502
|
+
if self.scopes:
|
|
503
|
+
body["scopes"] = self.scopes
|
|
504
|
+
if self.token_access_policy:
|
|
505
|
+
body["token_access_policy"] = self.token_access_policy
|
|
506
|
+
if self.user_authorized_scopes:
|
|
507
|
+
body["user_authorized_scopes"] = self.user_authorized_scopes
|
|
392
508
|
return body
|
|
393
509
|
|
|
394
510
|
@classmethod
|
|
395
|
-
def from_dict(cls, d: Dict[str,
|
|
511
|
+
def from_dict(cls, d: Dict[str, Any]) -> GetCustomAppIntegrationOutput:
|
|
396
512
|
"""Deserializes the GetCustomAppIntegrationOutput from a dictionary."""
|
|
397
|
-
return cls(
|
|
398
|
-
|
|
399
|
-
|
|
400
|
-
|
|
401
|
-
|
|
402
|
-
|
|
403
|
-
|
|
404
|
-
|
|
405
|
-
|
|
406
|
-
|
|
407
|
-
|
|
513
|
+
return cls(
|
|
514
|
+
client_id=d.get("client_id", None),
|
|
515
|
+
confidential=d.get("confidential", None),
|
|
516
|
+
create_time=d.get("create_time", None),
|
|
517
|
+
created_by=d.get("created_by", None),
|
|
518
|
+
creator_username=d.get("creator_username", None),
|
|
519
|
+
integration_id=d.get("integration_id", None),
|
|
520
|
+
name=d.get("name", None),
|
|
521
|
+
redirect_urls=d.get("redirect_urls", None),
|
|
522
|
+
scopes=d.get("scopes", None),
|
|
523
|
+
token_access_policy=_from_dict(d, "token_access_policy", TokenAccessPolicy),
|
|
524
|
+
user_authorized_scopes=d.get("user_authorized_scopes", None),
|
|
525
|
+
)
|
|
408
526
|
|
|
409
527
|
|
|
410
528
|
@dataclass
|
|
@@ -417,22 +535,28 @@ class GetCustomAppIntegrationsOutput:
|
|
|
417
535
|
def as_dict(self) -> dict:
|
|
418
536
|
"""Serializes the GetCustomAppIntegrationsOutput into a dictionary suitable for use as a JSON request body."""
|
|
419
537
|
body = {}
|
|
420
|
-
if self.apps:
|
|
421
|
-
|
|
538
|
+
if self.apps:
|
|
539
|
+
body["apps"] = [v.as_dict() for v in self.apps]
|
|
540
|
+
if self.next_page_token is not None:
|
|
541
|
+
body["next_page_token"] = self.next_page_token
|
|
422
542
|
return body
|
|
423
543
|
|
|
424
544
|
def as_shallow_dict(self) -> dict:
|
|
425
545
|
"""Serializes the GetCustomAppIntegrationsOutput into a shallow dictionary of its immediate attributes."""
|
|
426
546
|
body = {}
|
|
427
|
-
if self.apps:
|
|
428
|
-
|
|
547
|
+
if self.apps:
|
|
548
|
+
body["apps"] = self.apps
|
|
549
|
+
if self.next_page_token is not None:
|
|
550
|
+
body["next_page_token"] = self.next_page_token
|
|
429
551
|
return body
|
|
430
552
|
|
|
431
553
|
@classmethod
|
|
432
|
-
def from_dict(cls, d: Dict[str,
|
|
554
|
+
def from_dict(cls, d: Dict[str, Any]) -> GetCustomAppIntegrationsOutput:
|
|
433
555
|
"""Deserializes the GetCustomAppIntegrationsOutput from a dictionary."""
|
|
434
|
-
return cls(
|
|
435
|
-
|
|
556
|
+
return cls(
|
|
557
|
+
apps=_repeated_dict(d, "apps", GetCustomAppIntegrationOutput),
|
|
558
|
+
next_page_token=d.get("next_page_token", None),
|
|
559
|
+
)
|
|
436
560
|
|
|
437
561
|
|
|
438
562
|
@dataclass
|
|
@@ -456,34 +580,48 @@ class GetPublishedAppIntegrationOutput:
|
|
|
456
580
|
def as_dict(self) -> dict:
|
|
457
581
|
"""Serializes the GetPublishedAppIntegrationOutput into a dictionary suitable for use as a JSON request body."""
|
|
458
582
|
body = {}
|
|
459
|
-
if self.app_id is not None:
|
|
460
|
-
|
|
461
|
-
if self.
|
|
462
|
-
|
|
463
|
-
if self.
|
|
464
|
-
|
|
583
|
+
if self.app_id is not None:
|
|
584
|
+
body["app_id"] = self.app_id
|
|
585
|
+
if self.create_time is not None:
|
|
586
|
+
body["create_time"] = self.create_time
|
|
587
|
+
if self.created_by is not None:
|
|
588
|
+
body["created_by"] = self.created_by
|
|
589
|
+
if self.integration_id is not None:
|
|
590
|
+
body["integration_id"] = self.integration_id
|
|
591
|
+
if self.name is not None:
|
|
592
|
+
body["name"] = self.name
|
|
593
|
+
if self.token_access_policy:
|
|
594
|
+
body["token_access_policy"] = self.token_access_policy.as_dict()
|
|
465
595
|
return body
|
|
466
596
|
|
|
467
597
|
def as_shallow_dict(self) -> dict:
|
|
468
598
|
"""Serializes the GetPublishedAppIntegrationOutput into a shallow dictionary of its immediate attributes."""
|
|
469
599
|
body = {}
|
|
470
|
-
if self.app_id is not None:
|
|
471
|
-
|
|
472
|
-
if self.
|
|
473
|
-
|
|
474
|
-
if self.
|
|
475
|
-
|
|
600
|
+
if self.app_id is not None:
|
|
601
|
+
body["app_id"] = self.app_id
|
|
602
|
+
if self.create_time is not None:
|
|
603
|
+
body["create_time"] = self.create_time
|
|
604
|
+
if self.created_by is not None:
|
|
605
|
+
body["created_by"] = self.created_by
|
|
606
|
+
if self.integration_id is not None:
|
|
607
|
+
body["integration_id"] = self.integration_id
|
|
608
|
+
if self.name is not None:
|
|
609
|
+
body["name"] = self.name
|
|
610
|
+
if self.token_access_policy:
|
|
611
|
+
body["token_access_policy"] = self.token_access_policy
|
|
476
612
|
return body
|
|
477
613
|
|
|
478
614
|
@classmethod
|
|
479
|
-
def from_dict(cls, d: Dict[str,
|
|
615
|
+
def from_dict(cls, d: Dict[str, Any]) -> GetPublishedAppIntegrationOutput:
|
|
480
616
|
"""Deserializes the GetPublishedAppIntegrationOutput from a dictionary."""
|
|
481
|
-
return cls(
|
|
482
|
-
|
|
483
|
-
|
|
484
|
-
|
|
485
|
-
|
|
486
|
-
|
|
617
|
+
return cls(
|
|
618
|
+
app_id=d.get("app_id", None),
|
|
619
|
+
create_time=d.get("create_time", None),
|
|
620
|
+
created_by=d.get("created_by", None),
|
|
621
|
+
integration_id=d.get("integration_id", None),
|
|
622
|
+
name=d.get("name", None),
|
|
623
|
+
token_access_policy=_from_dict(d, "token_access_policy", TokenAccessPolicy),
|
|
624
|
+
)
|
|
487
625
|
|
|
488
626
|
|
|
489
627
|
@dataclass
|
|
@@ -496,22 +634,28 @@ class GetPublishedAppIntegrationsOutput:
|
|
|
496
634
|
def as_dict(self) -> dict:
|
|
497
635
|
"""Serializes the GetPublishedAppIntegrationsOutput into a dictionary suitable for use as a JSON request body."""
|
|
498
636
|
body = {}
|
|
499
|
-
if self.apps:
|
|
500
|
-
|
|
637
|
+
if self.apps:
|
|
638
|
+
body["apps"] = [v.as_dict() for v in self.apps]
|
|
639
|
+
if self.next_page_token is not None:
|
|
640
|
+
body["next_page_token"] = self.next_page_token
|
|
501
641
|
return body
|
|
502
642
|
|
|
503
643
|
def as_shallow_dict(self) -> dict:
|
|
504
644
|
"""Serializes the GetPublishedAppIntegrationsOutput into a shallow dictionary of its immediate attributes."""
|
|
505
645
|
body = {}
|
|
506
|
-
if self.apps:
|
|
507
|
-
|
|
646
|
+
if self.apps:
|
|
647
|
+
body["apps"] = self.apps
|
|
648
|
+
if self.next_page_token is not None:
|
|
649
|
+
body["next_page_token"] = self.next_page_token
|
|
508
650
|
return body
|
|
509
651
|
|
|
510
652
|
@classmethod
|
|
511
|
-
def from_dict(cls, d: Dict[str,
|
|
653
|
+
def from_dict(cls, d: Dict[str, Any]) -> GetPublishedAppIntegrationsOutput:
|
|
512
654
|
"""Deserializes the GetPublishedAppIntegrationsOutput from a dictionary."""
|
|
513
|
-
return cls(
|
|
514
|
-
|
|
655
|
+
return cls(
|
|
656
|
+
apps=_repeated_dict(d, "apps", GetPublishedAppIntegrationOutput),
|
|
657
|
+
next_page_token=d.get("next_page_token", None),
|
|
658
|
+
)
|
|
515
659
|
|
|
516
660
|
|
|
517
661
|
@dataclass
|
|
@@ -526,22 +670,25 @@ class GetPublishedAppsOutput:
|
|
|
526
670
|
def as_dict(self) -> dict:
|
|
527
671
|
"""Serializes the GetPublishedAppsOutput into a dictionary suitable for use as a JSON request body."""
|
|
528
672
|
body = {}
|
|
529
|
-
if self.apps:
|
|
530
|
-
|
|
673
|
+
if self.apps:
|
|
674
|
+
body["apps"] = [v.as_dict() for v in self.apps]
|
|
675
|
+
if self.next_page_token is not None:
|
|
676
|
+
body["next_page_token"] = self.next_page_token
|
|
531
677
|
return body
|
|
532
678
|
|
|
533
679
|
def as_shallow_dict(self) -> dict:
|
|
534
680
|
"""Serializes the GetPublishedAppsOutput into a shallow dictionary of its immediate attributes."""
|
|
535
681
|
body = {}
|
|
536
|
-
if self.apps:
|
|
537
|
-
|
|
682
|
+
if self.apps:
|
|
683
|
+
body["apps"] = self.apps
|
|
684
|
+
if self.next_page_token is not None:
|
|
685
|
+
body["next_page_token"] = self.next_page_token
|
|
538
686
|
return body
|
|
539
687
|
|
|
540
688
|
@classmethod
|
|
541
|
-
def from_dict(cls, d: Dict[str,
|
|
689
|
+
def from_dict(cls, d: Dict[str, Any]) -> GetPublishedAppsOutput:
|
|
542
690
|
"""Deserializes the GetPublishedAppsOutput from a dictionary."""
|
|
543
|
-
return cls(apps=_repeated_dict(d,
|
|
544
|
-
next_page_token=d.get('next_page_token', None))
|
|
691
|
+
return cls(apps=_repeated_dict(d, "apps", PublishedAppOutput), next_page_token=d.get("next_page_token", None))
|
|
545
692
|
|
|
546
693
|
|
|
547
694
|
@dataclass
|
|
@@ -553,22 +700,27 @@ class ListFederationPoliciesResponse:
|
|
|
553
700
|
def as_dict(self) -> dict:
|
|
554
701
|
"""Serializes the ListFederationPoliciesResponse into a dictionary suitable for use as a JSON request body."""
|
|
555
702
|
body = {}
|
|
556
|
-
if self.next_page_token is not None:
|
|
557
|
-
|
|
703
|
+
if self.next_page_token is not None:
|
|
704
|
+
body["next_page_token"] = self.next_page_token
|
|
705
|
+
if self.policies:
|
|
706
|
+
body["policies"] = [v.as_dict() for v in self.policies]
|
|
558
707
|
return body
|
|
559
708
|
|
|
560
709
|
def as_shallow_dict(self) -> dict:
|
|
561
710
|
"""Serializes the ListFederationPoliciesResponse into a shallow dictionary of its immediate attributes."""
|
|
562
711
|
body = {}
|
|
563
|
-
if self.next_page_token is not None:
|
|
564
|
-
|
|
712
|
+
if self.next_page_token is not None:
|
|
713
|
+
body["next_page_token"] = self.next_page_token
|
|
714
|
+
if self.policies:
|
|
715
|
+
body["policies"] = self.policies
|
|
565
716
|
return body
|
|
566
717
|
|
|
567
718
|
@classmethod
|
|
568
|
-
def from_dict(cls, d: Dict[str,
|
|
719
|
+
def from_dict(cls, d: Dict[str, Any]) -> ListFederationPoliciesResponse:
|
|
569
720
|
"""Deserializes the ListFederationPoliciesResponse from a dictionary."""
|
|
570
|
-
return cls(
|
|
571
|
-
|
|
721
|
+
return cls(
|
|
722
|
+
next_page_token=d.get("next_page_token", None), policies=_repeated_dict(d, "policies", FederationPolicy)
|
|
723
|
+
)
|
|
572
724
|
|
|
573
725
|
|
|
574
726
|
@dataclass
|
|
@@ -582,22 +734,25 @@ class ListServicePrincipalSecretsResponse:
|
|
|
582
734
|
def as_dict(self) -> dict:
|
|
583
735
|
"""Serializes the ListServicePrincipalSecretsResponse into a dictionary suitable for use as a JSON request body."""
|
|
584
736
|
body = {}
|
|
585
|
-
if self.next_page_token is not None:
|
|
586
|
-
|
|
737
|
+
if self.next_page_token is not None:
|
|
738
|
+
body["next_page_token"] = self.next_page_token
|
|
739
|
+
if self.secrets:
|
|
740
|
+
body["secrets"] = [v.as_dict() for v in self.secrets]
|
|
587
741
|
return body
|
|
588
742
|
|
|
589
743
|
def as_shallow_dict(self) -> dict:
|
|
590
744
|
"""Serializes the ListServicePrincipalSecretsResponse into a shallow dictionary of its immediate attributes."""
|
|
591
745
|
body = {}
|
|
592
|
-
if self.next_page_token is not None:
|
|
593
|
-
|
|
746
|
+
if self.next_page_token is not None:
|
|
747
|
+
body["next_page_token"] = self.next_page_token
|
|
748
|
+
if self.secrets:
|
|
749
|
+
body["secrets"] = self.secrets
|
|
594
750
|
return body
|
|
595
751
|
|
|
596
752
|
@classmethod
|
|
597
|
-
def from_dict(cls, d: Dict[str,
|
|
753
|
+
def from_dict(cls, d: Dict[str, Any]) -> ListServicePrincipalSecretsResponse:
|
|
598
754
|
"""Deserializes the ListServicePrincipalSecretsResponse from a dictionary."""
|
|
599
|
-
return cls(next_page_token=d.get(
|
|
600
|
-
secrets=_repeated_dict(d, 'secrets', SecretInfo))
|
|
755
|
+
return cls(next_page_token=d.get("next_page_token", None), secrets=_repeated_dict(d, "secrets", SecretInfo))
|
|
601
756
|
|
|
602
757
|
|
|
603
758
|
@dataclass
|
|
@@ -615,10 +770,18 @@ class OidcFederationPolicy:
|
|
|
615
770
|
"""The required token issuer, as specified in the 'iss' claim of federated tokens."""
|
|
616
771
|
|
|
617
772
|
jwks_json: Optional[str] = None
|
|
618
|
-
"""The public keys used to validate the signature of federated tokens, in JWKS format.
|
|
619
|
-
|
|
620
|
-
|
|
621
|
-
endpoint
|
|
773
|
+
"""The public keys used to validate the signature of federated tokens, in JWKS format. Most use
|
|
774
|
+
cases should not need to specify this field. If jwks_uri and jwks_json are both unspecified
|
|
775
|
+
(recommended), Databricks automatically fetches the public keys from your issuer’s well known
|
|
776
|
+
endpoint. Databricks strongly recommends relying on your issuer’s well known endpoint for
|
|
777
|
+
discovering public keys."""
|
|
778
|
+
|
|
779
|
+
jwks_uri: Optional[str] = None
|
|
780
|
+
"""URL of the public keys used to validate the signature of federated tokens, in JWKS format. Most
|
|
781
|
+
use cases should not need to specify this field. If jwks_uri and jwks_json are both unspecified
|
|
782
|
+
(recommended), Databricks automatically fetches the public keys from your issuer’s well known
|
|
783
|
+
endpoint. Databricks strongly recommends relying on your issuer’s well known endpoint for
|
|
784
|
+
discovering public keys."""
|
|
622
785
|
|
|
623
786
|
subject: Optional[str] = None
|
|
624
787
|
"""The required token subject, as specified in the subject claim of federated tokens. Must be
|
|
@@ -631,31 +794,48 @@ class OidcFederationPolicy:
|
|
|
631
794
|
def as_dict(self) -> dict:
|
|
632
795
|
"""Serializes the OidcFederationPolicy into a dictionary suitable for use as a JSON request body."""
|
|
633
796
|
body = {}
|
|
634
|
-
if self.audiences:
|
|
635
|
-
|
|
636
|
-
if self.
|
|
637
|
-
|
|
638
|
-
if self.
|
|
797
|
+
if self.audiences:
|
|
798
|
+
body["audiences"] = [v for v in self.audiences]
|
|
799
|
+
if self.issuer is not None:
|
|
800
|
+
body["issuer"] = self.issuer
|
|
801
|
+
if self.jwks_json is not None:
|
|
802
|
+
body["jwks_json"] = self.jwks_json
|
|
803
|
+
if self.jwks_uri is not None:
|
|
804
|
+
body["jwks_uri"] = self.jwks_uri
|
|
805
|
+
if self.subject is not None:
|
|
806
|
+
body["subject"] = self.subject
|
|
807
|
+
if self.subject_claim is not None:
|
|
808
|
+
body["subject_claim"] = self.subject_claim
|
|
639
809
|
return body
|
|
640
810
|
|
|
641
811
|
def as_shallow_dict(self) -> dict:
|
|
642
812
|
"""Serializes the OidcFederationPolicy into a shallow dictionary of its immediate attributes."""
|
|
643
813
|
body = {}
|
|
644
|
-
if self.audiences:
|
|
645
|
-
|
|
646
|
-
if self.
|
|
647
|
-
|
|
648
|
-
if self.
|
|
814
|
+
if self.audiences:
|
|
815
|
+
body["audiences"] = self.audiences
|
|
816
|
+
if self.issuer is not None:
|
|
817
|
+
body["issuer"] = self.issuer
|
|
818
|
+
if self.jwks_json is not None:
|
|
819
|
+
body["jwks_json"] = self.jwks_json
|
|
820
|
+
if self.jwks_uri is not None:
|
|
821
|
+
body["jwks_uri"] = self.jwks_uri
|
|
822
|
+
if self.subject is not None:
|
|
823
|
+
body["subject"] = self.subject
|
|
824
|
+
if self.subject_claim is not None:
|
|
825
|
+
body["subject_claim"] = self.subject_claim
|
|
649
826
|
return body
|
|
650
827
|
|
|
651
828
|
@classmethod
|
|
652
|
-
def from_dict(cls, d: Dict[str,
|
|
829
|
+
def from_dict(cls, d: Dict[str, Any]) -> OidcFederationPolicy:
|
|
653
830
|
"""Deserializes the OidcFederationPolicy from a dictionary."""
|
|
654
|
-
return cls(
|
|
655
|
-
|
|
656
|
-
|
|
657
|
-
|
|
658
|
-
|
|
831
|
+
return cls(
|
|
832
|
+
audiences=d.get("audiences", None),
|
|
833
|
+
issuer=d.get("issuer", None),
|
|
834
|
+
jwks_json=d.get("jwks_json", None),
|
|
835
|
+
jwks_uri=d.get("jwks_uri", None),
|
|
836
|
+
subject=d.get("subject", None),
|
|
837
|
+
subject_claim=d.get("subject_claim", None),
|
|
838
|
+
)
|
|
659
839
|
|
|
660
840
|
|
|
661
841
|
@dataclass
|
|
@@ -685,39 +865,53 @@ class PublishedAppOutput:
|
|
|
685
865
|
def as_dict(self) -> dict:
|
|
686
866
|
"""Serializes the PublishedAppOutput into a dictionary suitable for use as a JSON request body."""
|
|
687
867
|
body = {}
|
|
688
|
-
if self.app_id is not None:
|
|
689
|
-
|
|
690
|
-
if self.
|
|
868
|
+
if self.app_id is not None:
|
|
869
|
+
body["app_id"] = self.app_id
|
|
870
|
+
if self.client_id is not None:
|
|
871
|
+
body["client_id"] = self.client_id
|
|
872
|
+
if self.description is not None:
|
|
873
|
+
body["description"] = self.description
|
|
691
874
|
if self.is_confidential_client is not None:
|
|
692
|
-
body[
|
|
693
|
-
if self.name is not None:
|
|
694
|
-
|
|
695
|
-
if self.
|
|
875
|
+
body["is_confidential_client"] = self.is_confidential_client
|
|
876
|
+
if self.name is not None:
|
|
877
|
+
body["name"] = self.name
|
|
878
|
+
if self.redirect_urls:
|
|
879
|
+
body["redirect_urls"] = [v for v in self.redirect_urls]
|
|
880
|
+
if self.scopes:
|
|
881
|
+
body["scopes"] = [v for v in self.scopes]
|
|
696
882
|
return body
|
|
697
883
|
|
|
698
884
|
def as_shallow_dict(self) -> dict:
|
|
699
885
|
"""Serializes the PublishedAppOutput into a shallow dictionary of its immediate attributes."""
|
|
700
886
|
body = {}
|
|
701
|
-
if self.app_id is not None:
|
|
702
|
-
|
|
703
|
-
if self.
|
|
887
|
+
if self.app_id is not None:
|
|
888
|
+
body["app_id"] = self.app_id
|
|
889
|
+
if self.client_id is not None:
|
|
890
|
+
body["client_id"] = self.client_id
|
|
891
|
+
if self.description is not None:
|
|
892
|
+
body["description"] = self.description
|
|
704
893
|
if self.is_confidential_client is not None:
|
|
705
|
-
body[
|
|
706
|
-
if self.name is not None:
|
|
707
|
-
|
|
708
|
-
if self.
|
|
894
|
+
body["is_confidential_client"] = self.is_confidential_client
|
|
895
|
+
if self.name is not None:
|
|
896
|
+
body["name"] = self.name
|
|
897
|
+
if self.redirect_urls:
|
|
898
|
+
body["redirect_urls"] = self.redirect_urls
|
|
899
|
+
if self.scopes:
|
|
900
|
+
body["scopes"] = self.scopes
|
|
709
901
|
return body
|
|
710
902
|
|
|
711
903
|
@classmethod
|
|
712
|
-
def from_dict(cls, d: Dict[str,
|
|
904
|
+
def from_dict(cls, d: Dict[str, Any]) -> PublishedAppOutput:
|
|
713
905
|
"""Deserializes the PublishedAppOutput from a dictionary."""
|
|
714
|
-
return cls(
|
|
715
|
-
|
|
716
|
-
|
|
717
|
-
|
|
718
|
-
|
|
719
|
-
|
|
720
|
-
|
|
906
|
+
return cls(
|
|
907
|
+
app_id=d.get("app_id", None),
|
|
908
|
+
client_id=d.get("client_id", None),
|
|
909
|
+
description=d.get("description", None),
|
|
910
|
+
is_confidential_client=d.get("is_confidential_client", None),
|
|
911
|
+
name=d.get("name", None),
|
|
912
|
+
redirect_urls=d.get("redirect_urls", None),
|
|
913
|
+
scopes=d.get("scopes", None),
|
|
914
|
+
)
|
|
721
915
|
|
|
722
916
|
|
|
723
917
|
@dataclass
|
|
@@ -725,6 +919,9 @@ class SecretInfo:
|
|
|
725
919
|
create_time: Optional[str] = None
|
|
726
920
|
"""UTC time when the secret was created"""
|
|
727
921
|
|
|
922
|
+
expire_time: Optional[str] = None
|
|
923
|
+
"""UTC time when the secret will expire. If the field is not present, the secret does not expire."""
|
|
924
|
+
|
|
728
925
|
id: Optional[str] = None
|
|
729
926
|
"""ID of the secret"""
|
|
730
927
|
|
|
@@ -740,31 +937,48 @@ class SecretInfo:
|
|
|
740
937
|
def as_dict(self) -> dict:
|
|
741
938
|
"""Serializes the SecretInfo into a dictionary suitable for use as a JSON request body."""
|
|
742
939
|
body = {}
|
|
743
|
-
if self.create_time is not None:
|
|
744
|
-
|
|
745
|
-
if self.
|
|
746
|
-
|
|
747
|
-
if self.
|
|
940
|
+
if self.create_time is not None:
|
|
941
|
+
body["create_time"] = self.create_time
|
|
942
|
+
if self.expire_time is not None:
|
|
943
|
+
body["expire_time"] = self.expire_time
|
|
944
|
+
if self.id is not None:
|
|
945
|
+
body["id"] = self.id
|
|
946
|
+
if self.secret_hash is not None:
|
|
947
|
+
body["secret_hash"] = self.secret_hash
|
|
948
|
+
if self.status is not None:
|
|
949
|
+
body["status"] = self.status
|
|
950
|
+
if self.update_time is not None:
|
|
951
|
+
body["update_time"] = self.update_time
|
|
748
952
|
return body
|
|
749
953
|
|
|
750
954
|
def as_shallow_dict(self) -> dict:
|
|
751
955
|
"""Serializes the SecretInfo into a shallow dictionary of its immediate attributes."""
|
|
752
956
|
body = {}
|
|
753
|
-
if self.create_time is not None:
|
|
754
|
-
|
|
755
|
-
if self.
|
|
756
|
-
|
|
757
|
-
if self.
|
|
957
|
+
if self.create_time is not None:
|
|
958
|
+
body["create_time"] = self.create_time
|
|
959
|
+
if self.expire_time is not None:
|
|
960
|
+
body["expire_time"] = self.expire_time
|
|
961
|
+
if self.id is not None:
|
|
962
|
+
body["id"] = self.id
|
|
963
|
+
if self.secret_hash is not None:
|
|
964
|
+
body["secret_hash"] = self.secret_hash
|
|
965
|
+
if self.status is not None:
|
|
966
|
+
body["status"] = self.status
|
|
967
|
+
if self.update_time is not None:
|
|
968
|
+
body["update_time"] = self.update_time
|
|
758
969
|
return body
|
|
759
970
|
|
|
760
971
|
@classmethod
|
|
761
|
-
def from_dict(cls, d: Dict[str,
|
|
972
|
+
def from_dict(cls, d: Dict[str, Any]) -> SecretInfo:
|
|
762
973
|
"""Deserializes the SecretInfo from a dictionary."""
|
|
763
|
-
return cls(
|
|
764
|
-
|
|
765
|
-
|
|
766
|
-
|
|
767
|
-
|
|
974
|
+
return cls(
|
|
975
|
+
create_time=d.get("create_time", None),
|
|
976
|
+
expire_time=d.get("expire_time", None),
|
|
977
|
+
id=d.get("id", None),
|
|
978
|
+
secret_hash=d.get("secret_hash", None),
|
|
979
|
+
status=d.get("status", None),
|
|
980
|
+
update_time=d.get("update_time", None),
|
|
981
|
+
)
|
|
768
982
|
|
|
769
983
|
|
|
770
984
|
@dataclass
|
|
@@ -779,25 +993,27 @@ class TokenAccessPolicy:
|
|
|
779
993
|
"""Serializes the TokenAccessPolicy into a dictionary suitable for use as a JSON request body."""
|
|
780
994
|
body = {}
|
|
781
995
|
if self.access_token_ttl_in_minutes is not None:
|
|
782
|
-
body[
|
|
996
|
+
body["access_token_ttl_in_minutes"] = self.access_token_ttl_in_minutes
|
|
783
997
|
if self.refresh_token_ttl_in_minutes is not None:
|
|
784
|
-
body[
|
|
998
|
+
body["refresh_token_ttl_in_minutes"] = self.refresh_token_ttl_in_minutes
|
|
785
999
|
return body
|
|
786
1000
|
|
|
787
1001
|
def as_shallow_dict(self) -> dict:
|
|
788
1002
|
"""Serializes the TokenAccessPolicy into a shallow dictionary of its immediate attributes."""
|
|
789
1003
|
body = {}
|
|
790
1004
|
if self.access_token_ttl_in_minutes is not None:
|
|
791
|
-
body[
|
|
1005
|
+
body["access_token_ttl_in_minutes"] = self.access_token_ttl_in_minutes
|
|
792
1006
|
if self.refresh_token_ttl_in_minutes is not None:
|
|
793
|
-
body[
|
|
1007
|
+
body["refresh_token_ttl_in_minutes"] = self.refresh_token_ttl_in_minutes
|
|
794
1008
|
return body
|
|
795
1009
|
|
|
796
1010
|
@classmethod
|
|
797
|
-
def from_dict(cls, d: Dict[str,
|
|
1011
|
+
def from_dict(cls, d: Dict[str, Any]) -> TokenAccessPolicy:
|
|
798
1012
|
"""Deserializes the TokenAccessPolicy from a dictionary."""
|
|
799
|
-
return cls(
|
|
800
|
-
|
|
1013
|
+
return cls(
|
|
1014
|
+
access_token_ttl_in_minutes=d.get("access_token_ttl_in_minutes", None),
|
|
1015
|
+
refresh_token_ttl_in_minutes=d.get("refresh_token_ttl_in_minutes", None),
|
|
1016
|
+
)
|
|
801
1017
|
|
|
802
1018
|
|
|
803
1019
|
@dataclass
|
|
@@ -821,37 +1037,47 @@ class UpdateCustomAppIntegration:
|
|
|
821
1037
|
def as_dict(self) -> dict:
|
|
822
1038
|
"""Serializes the UpdateCustomAppIntegration into a dictionary suitable for use as a JSON request body."""
|
|
823
1039
|
body = {}
|
|
824
|
-
if self.integration_id is not None:
|
|
825
|
-
|
|
826
|
-
if self.
|
|
827
|
-
|
|
1040
|
+
if self.integration_id is not None:
|
|
1041
|
+
body["integration_id"] = self.integration_id
|
|
1042
|
+
if self.redirect_urls:
|
|
1043
|
+
body["redirect_urls"] = [v for v in self.redirect_urls]
|
|
1044
|
+
if self.scopes:
|
|
1045
|
+
body["scopes"] = [v for v in self.scopes]
|
|
1046
|
+
if self.token_access_policy:
|
|
1047
|
+
body["token_access_policy"] = self.token_access_policy.as_dict()
|
|
828
1048
|
if self.user_authorized_scopes:
|
|
829
|
-
body[
|
|
1049
|
+
body["user_authorized_scopes"] = [v for v in self.user_authorized_scopes]
|
|
830
1050
|
return body
|
|
831
1051
|
|
|
832
1052
|
def as_shallow_dict(self) -> dict:
|
|
833
1053
|
"""Serializes the UpdateCustomAppIntegration into a shallow dictionary of its immediate attributes."""
|
|
834
1054
|
body = {}
|
|
835
|
-
if self.integration_id is not None:
|
|
836
|
-
|
|
837
|
-
if self.
|
|
838
|
-
|
|
839
|
-
if self.
|
|
1055
|
+
if self.integration_id is not None:
|
|
1056
|
+
body["integration_id"] = self.integration_id
|
|
1057
|
+
if self.redirect_urls:
|
|
1058
|
+
body["redirect_urls"] = self.redirect_urls
|
|
1059
|
+
if self.scopes:
|
|
1060
|
+
body["scopes"] = self.scopes
|
|
1061
|
+
if self.token_access_policy:
|
|
1062
|
+
body["token_access_policy"] = self.token_access_policy
|
|
1063
|
+
if self.user_authorized_scopes:
|
|
1064
|
+
body["user_authorized_scopes"] = self.user_authorized_scopes
|
|
840
1065
|
return body
|
|
841
1066
|
|
|
842
1067
|
@classmethod
|
|
843
|
-
def from_dict(cls, d: Dict[str,
|
|
1068
|
+
def from_dict(cls, d: Dict[str, Any]) -> UpdateCustomAppIntegration:
|
|
844
1069
|
"""Deserializes the UpdateCustomAppIntegration from a dictionary."""
|
|
845
|
-
return cls(
|
|
846
|
-
|
|
847
|
-
|
|
848
|
-
|
|
849
|
-
|
|
1070
|
+
return cls(
|
|
1071
|
+
integration_id=d.get("integration_id", None),
|
|
1072
|
+
redirect_urls=d.get("redirect_urls", None),
|
|
1073
|
+
scopes=d.get("scopes", None),
|
|
1074
|
+
token_access_policy=_from_dict(d, "token_access_policy", TokenAccessPolicy),
|
|
1075
|
+
user_authorized_scopes=d.get("user_authorized_scopes", None),
|
|
1076
|
+
)
|
|
850
1077
|
|
|
851
1078
|
|
|
852
1079
|
@dataclass
|
|
853
1080
|
class UpdateCustomAppIntegrationOutput:
|
|
854
|
-
|
|
855
1081
|
def as_dict(self) -> dict:
|
|
856
1082
|
"""Serializes the UpdateCustomAppIntegrationOutput into a dictionary suitable for use as a JSON request body."""
|
|
857
1083
|
body = {}
|
|
@@ -863,7 +1089,7 @@ class UpdateCustomAppIntegrationOutput:
|
|
|
863
1089
|
return body
|
|
864
1090
|
|
|
865
1091
|
@classmethod
|
|
866
|
-
def from_dict(cls, d: Dict[str,
|
|
1092
|
+
def from_dict(cls, d: Dict[str, Any]) -> UpdateCustomAppIntegrationOutput:
|
|
867
1093
|
"""Deserializes the UpdateCustomAppIntegrationOutput from a dictionary."""
|
|
868
1094
|
return cls()
|
|
869
1095
|
|
|
@@ -878,27 +1104,32 @@ class UpdatePublishedAppIntegration:
|
|
|
878
1104
|
def as_dict(self) -> dict:
|
|
879
1105
|
"""Serializes the UpdatePublishedAppIntegration into a dictionary suitable for use as a JSON request body."""
|
|
880
1106
|
body = {}
|
|
881
|
-
if self.integration_id is not None:
|
|
882
|
-
|
|
1107
|
+
if self.integration_id is not None:
|
|
1108
|
+
body["integration_id"] = self.integration_id
|
|
1109
|
+
if self.token_access_policy:
|
|
1110
|
+
body["token_access_policy"] = self.token_access_policy.as_dict()
|
|
883
1111
|
return body
|
|
884
1112
|
|
|
885
1113
|
def as_shallow_dict(self) -> dict:
|
|
886
1114
|
"""Serializes the UpdatePublishedAppIntegration into a shallow dictionary of its immediate attributes."""
|
|
887
1115
|
body = {}
|
|
888
|
-
if self.integration_id is not None:
|
|
889
|
-
|
|
1116
|
+
if self.integration_id is not None:
|
|
1117
|
+
body["integration_id"] = self.integration_id
|
|
1118
|
+
if self.token_access_policy:
|
|
1119
|
+
body["token_access_policy"] = self.token_access_policy
|
|
890
1120
|
return body
|
|
891
1121
|
|
|
892
1122
|
@classmethod
|
|
893
|
-
def from_dict(cls, d: Dict[str,
|
|
1123
|
+
def from_dict(cls, d: Dict[str, Any]) -> UpdatePublishedAppIntegration:
|
|
894
1124
|
"""Deserializes the UpdatePublishedAppIntegration from a dictionary."""
|
|
895
|
-
return cls(
|
|
896
|
-
|
|
1125
|
+
return cls(
|
|
1126
|
+
integration_id=d.get("integration_id", None),
|
|
1127
|
+
token_access_policy=_from_dict(d, "token_access_policy", TokenAccessPolicy),
|
|
1128
|
+
)
|
|
897
1129
|
|
|
898
1130
|
|
|
899
1131
|
@dataclass
|
|
900
1132
|
class UpdatePublishedAppIntegrationOutput:
|
|
901
|
-
|
|
902
1133
|
def as_dict(self) -> dict:
|
|
903
1134
|
"""Serializes the UpdatePublishedAppIntegrationOutput into a dictionary suitable for use as a JSON request body."""
|
|
904
1135
|
body = {}
|
|
@@ -910,27 +1141,27 @@ class UpdatePublishedAppIntegrationOutput:
|
|
|
910
1141
|
return body
|
|
911
1142
|
|
|
912
1143
|
@classmethod
|
|
913
|
-
def from_dict(cls, d: Dict[str,
|
|
1144
|
+
def from_dict(cls, d: Dict[str, Any]) -> UpdatePublishedAppIntegrationOutput:
|
|
914
1145
|
"""Deserializes the UpdatePublishedAppIntegrationOutput from a dictionary."""
|
|
915
1146
|
return cls()
|
|
916
1147
|
|
|
917
1148
|
|
|
918
1149
|
class AccountFederationPolicyAPI:
|
|
919
1150
|
"""These APIs manage account federation policies.
|
|
920
|
-
|
|
1151
|
+
|
|
921
1152
|
Account federation policies allow users and service principals in your Databricks account to securely
|
|
922
1153
|
access Databricks APIs using tokens from your trusted identity providers (IdPs).
|
|
923
|
-
|
|
1154
|
+
|
|
924
1155
|
With token federation, your users and service principals can exchange tokens from your IdP for Databricks
|
|
925
1156
|
OAuth tokens, which can be used to access Databricks APIs. Token federation eliminates the need to manage
|
|
926
1157
|
Databricks secrets, and allows you to centralize management of token issuance policies in your IdP.
|
|
927
1158
|
Databricks token federation is typically used in combination with [SCIM], so users in your IdP are
|
|
928
1159
|
synchronized into your Databricks account.
|
|
929
|
-
|
|
1160
|
+
|
|
930
1161
|
Token federation is configured in your Databricks account using an account federation policy. An account
|
|
931
1162
|
federation policy specifies: * which IdP, or issuer, your Databricks account should accept tokens from *
|
|
932
1163
|
how to determine which Databricks user, or subject, a token is issued for
|
|
933
|
-
|
|
1164
|
+
|
|
934
1165
|
To configure a federation policy, you provide the following: * The required token __issuer__, as specified
|
|
935
1166
|
in the “iss” claim of your tokens. The issuer is an https URL that identifies your IdP. * The allowed
|
|
936
1167
|
token __audiences__, as specified in the “aud” claim of your tokens. This identifier is intended to
|
|
@@ -941,117 +1172,122 @@ class AccountFederationPolicyAPI:
|
|
|
941
1172
|
public keys used to validate the signature of your tokens, in JWKS format. If unspecified (recommended),
|
|
942
1173
|
Databricks automatically fetches the public keys from your issuer’s well known endpoint. Databricks
|
|
943
1174
|
strongly recommends relying on your issuer’s well known endpoint for discovering public keys.
|
|
944
|
-
|
|
1175
|
+
|
|
945
1176
|
An example federation policy is: ``` issuer: "https://idp.mycompany.com/oidc" audiences: ["databricks"]
|
|
946
1177
|
subject_claim: "sub" ```
|
|
947
|
-
|
|
1178
|
+
|
|
948
1179
|
An example JWT token body that matches this policy and could be used to authenticate to Databricks as user
|
|
949
1180
|
`username@mycompany.com` is: ``` { "iss": "https://idp.mycompany.com/oidc", "aud": "databricks", "sub":
|
|
950
1181
|
"username@mycompany.com" } ```
|
|
951
|
-
|
|
1182
|
+
|
|
952
1183
|
You may also need to configure your IdP to generate tokens for your users to exchange with Databricks, if
|
|
953
1184
|
your users do not already have the ability to generate tokens that are compatible with your federation
|
|
954
1185
|
policy.
|
|
955
|
-
|
|
1186
|
+
|
|
956
1187
|
You do not need to configure an OAuth application in Databricks to use token federation.
|
|
957
|
-
|
|
1188
|
+
|
|
958
1189
|
[SCIM]: https://docs.databricks.com/admin/users-groups/scim/index.html"""
|
|
959
1190
|
|
|
960
1191
|
def __init__(self, api_client):
|
|
961
1192
|
self._api = api_client
|
|
962
1193
|
|
|
963
|
-
def create(self,
|
|
964
|
-
*,
|
|
965
|
-
policy: Optional[FederationPolicy] = None,
|
|
966
|
-
policy_id: Optional[str] = None) -> FederationPolicy:
|
|
1194
|
+
def create(self, *, policy: Optional[FederationPolicy] = None, policy_id: Optional[str] = None) -> FederationPolicy:
|
|
967
1195
|
"""Create account federation policy.
|
|
968
|
-
|
|
1196
|
+
|
|
969
1197
|
:param policy: :class:`FederationPolicy` (optional)
|
|
970
1198
|
:param policy_id: str (optional)
|
|
971
1199
|
The identifier for the federation policy. The identifier must contain only lowercase alphanumeric
|
|
972
1200
|
characters, numbers, hyphens, and slashes. If unspecified, the id will be assigned by Databricks.
|
|
973
|
-
|
|
1201
|
+
|
|
974
1202
|
:returns: :class:`FederationPolicy`
|
|
975
1203
|
"""
|
|
976
1204
|
body = policy.as_dict()
|
|
977
1205
|
query = {}
|
|
978
|
-
if policy_id is not None:
|
|
979
|
-
|
|
980
|
-
|
|
981
|
-
|
|
982
|
-
|
|
983
|
-
|
|
984
|
-
|
|
985
|
-
|
|
1206
|
+
if policy_id is not None:
|
|
1207
|
+
query["policy_id"] = policy_id
|
|
1208
|
+
headers = {
|
|
1209
|
+
"Accept": "application/json",
|
|
1210
|
+
"Content-Type": "application/json",
|
|
1211
|
+
}
|
|
1212
|
+
|
|
1213
|
+
res = self._api.do(
|
|
1214
|
+
"POST",
|
|
1215
|
+
f"/api/2.0/accounts/{self._api.account_id}/federationPolicies",
|
|
1216
|
+
query=query,
|
|
1217
|
+
body=body,
|
|
1218
|
+
headers=headers,
|
|
1219
|
+
)
|
|
986
1220
|
return FederationPolicy.from_dict(res)
|
|
987
1221
|
|
|
988
1222
|
def delete(self, policy_id: str):
|
|
989
1223
|
"""Delete account federation policy.
|
|
990
|
-
|
|
1224
|
+
|
|
991
1225
|
:param policy_id: str
|
|
992
1226
|
The identifier for the federation policy.
|
|
993
|
-
|
|
994
|
-
|
|
1227
|
+
|
|
1228
|
+
|
|
995
1229
|
"""
|
|
996
1230
|
|
|
997
|
-
headers = {
|
|
1231
|
+
headers = {
|
|
1232
|
+
"Accept": "application/json",
|
|
1233
|
+
}
|
|
998
1234
|
|
|
999
|
-
self._api.do(
|
|
1000
|
-
|
|
1001
|
-
|
|
1235
|
+
self._api.do(
|
|
1236
|
+
"DELETE", f"/api/2.0/accounts/{self._api.account_id}/federationPolicies/{policy_id}", headers=headers
|
|
1237
|
+
)
|
|
1002
1238
|
|
|
1003
1239
|
def get(self, policy_id: str) -> FederationPolicy:
|
|
1004
1240
|
"""Get account federation policy.
|
|
1005
|
-
|
|
1241
|
+
|
|
1006
1242
|
:param policy_id: str
|
|
1007
1243
|
The identifier for the federation policy.
|
|
1008
|
-
|
|
1244
|
+
|
|
1009
1245
|
:returns: :class:`FederationPolicy`
|
|
1010
1246
|
"""
|
|
1011
1247
|
|
|
1012
|
-
headers = {
|
|
1248
|
+
headers = {
|
|
1249
|
+
"Accept": "application/json",
|
|
1250
|
+
}
|
|
1013
1251
|
|
|
1014
|
-
res = self._api.do(
|
|
1015
|
-
|
|
1016
|
-
|
|
1252
|
+
res = self._api.do(
|
|
1253
|
+
"GET", f"/api/2.0/accounts/{self._api.account_id}/federationPolicies/{policy_id}", headers=headers
|
|
1254
|
+
)
|
|
1017
1255
|
return FederationPolicy.from_dict(res)
|
|
1018
1256
|
|
|
1019
|
-
def list(self,
|
|
1020
|
-
*,
|
|
1021
|
-
page_size: Optional[int] = None,
|
|
1022
|
-
page_token: Optional[str] = None) -> Iterator[FederationPolicy]:
|
|
1257
|
+
def list(self, *, page_size: Optional[int] = None, page_token: Optional[str] = None) -> Iterator[FederationPolicy]:
|
|
1023
1258
|
"""List account federation policies.
|
|
1024
|
-
|
|
1259
|
+
|
|
1025
1260
|
:param page_size: int (optional)
|
|
1026
1261
|
:param page_token: str (optional)
|
|
1027
|
-
|
|
1262
|
+
|
|
1028
1263
|
:returns: Iterator over :class:`FederationPolicy`
|
|
1029
1264
|
"""
|
|
1030
1265
|
|
|
1031
1266
|
query = {}
|
|
1032
|
-
if page_size is not None:
|
|
1033
|
-
|
|
1034
|
-
|
|
1267
|
+
if page_size is not None:
|
|
1268
|
+
query["page_size"] = page_size
|
|
1269
|
+
if page_token is not None:
|
|
1270
|
+
query["page_token"] = page_token
|
|
1271
|
+
headers = {
|
|
1272
|
+
"Accept": "application/json",
|
|
1273
|
+
}
|
|
1035
1274
|
|
|
1036
1275
|
while True:
|
|
1037
|
-
json = self._api.do(
|
|
1038
|
-
|
|
1039
|
-
|
|
1040
|
-
|
|
1041
|
-
|
|
1042
|
-
for v in json['policies']:
|
|
1276
|
+
json = self._api.do(
|
|
1277
|
+
"GET", f"/api/2.0/accounts/{self._api.account_id}/federationPolicies", query=query, headers=headers
|
|
1278
|
+
)
|
|
1279
|
+
if "policies" in json:
|
|
1280
|
+
for v in json["policies"]:
|
|
1043
1281
|
yield FederationPolicy.from_dict(v)
|
|
1044
|
-
if
|
|
1282
|
+
if "next_page_token" not in json or not json["next_page_token"]:
|
|
1045
1283
|
return
|
|
1046
|
-
query[
|
|
1284
|
+
query["page_token"] = json["next_page_token"]
|
|
1047
1285
|
|
|
1048
|
-
def update(
|
|
1049
|
-
|
|
1050
|
-
|
|
1051
|
-
policy: Optional[FederationPolicy] = None,
|
|
1052
|
-
update_mask: Optional[str] = None) -> FederationPolicy:
|
|
1286
|
+
def update(
|
|
1287
|
+
self, policy_id: str, *, policy: Optional[FederationPolicy] = None, update_mask: Optional[str] = None
|
|
1288
|
+
) -> FederationPolicy:
|
|
1053
1289
|
"""Update account federation policy.
|
|
1054
|
-
|
|
1290
|
+
|
|
1055
1291
|
:param policy_id: str
|
|
1056
1292
|
The identifier for the federation policy.
|
|
1057
1293
|
:param policy: :class:`FederationPolicy` (optional)
|
|
@@ -1061,19 +1297,25 @@ class AccountFederationPolicyAPI:
|
|
|
1061
1297
|
should be updated (full replacement). If unspecified, all fields that are set in the policy provided
|
|
1062
1298
|
in the update request will overwrite the corresponding fields in the existing policy. Example value:
|
|
1063
1299
|
'description,oidc_policy.audiences'.
|
|
1064
|
-
|
|
1300
|
+
|
|
1065
1301
|
:returns: :class:`FederationPolicy`
|
|
1066
1302
|
"""
|
|
1067
1303
|
body = policy.as_dict()
|
|
1068
1304
|
query = {}
|
|
1069
|
-
if update_mask is not None:
|
|
1070
|
-
|
|
1071
|
-
|
|
1072
|
-
|
|
1073
|
-
|
|
1074
|
-
|
|
1075
|
-
|
|
1076
|
-
|
|
1305
|
+
if update_mask is not None:
|
|
1306
|
+
query["update_mask"] = update_mask
|
|
1307
|
+
headers = {
|
|
1308
|
+
"Accept": "application/json",
|
|
1309
|
+
"Content-Type": "application/json",
|
|
1310
|
+
}
|
|
1311
|
+
|
|
1312
|
+
res = self._api.do(
|
|
1313
|
+
"PATCH",
|
|
1314
|
+
f"/api/2.0/accounts/{self._api.account_id}/federationPolicies/{policy_id}",
|
|
1315
|
+
query=query,
|
|
1316
|
+
body=body,
|
|
1317
|
+
headers=headers,
|
|
1318
|
+
)
|
|
1077
1319
|
return FederationPolicy.from_dict(res)
|
|
1078
1320
|
|
|
1079
1321
|
|
|
@@ -1084,20 +1326,22 @@ class CustomAppIntegrationAPI:
|
|
|
1084
1326
|
def __init__(self, api_client):
|
|
1085
1327
|
self._api = api_client
|
|
1086
1328
|
|
|
1087
|
-
def create(
|
|
1088
|
-
|
|
1089
|
-
|
|
1090
|
-
|
|
1091
|
-
|
|
1092
|
-
|
|
1093
|
-
|
|
1094
|
-
|
|
1329
|
+
def create(
|
|
1330
|
+
self,
|
|
1331
|
+
*,
|
|
1332
|
+
confidential: Optional[bool] = None,
|
|
1333
|
+
name: Optional[str] = None,
|
|
1334
|
+
redirect_urls: Optional[List[str]] = None,
|
|
1335
|
+
scopes: Optional[List[str]] = None,
|
|
1336
|
+
token_access_policy: Optional[TokenAccessPolicy] = None,
|
|
1337
|
+
user_authorized_scopes: Optional[List[str]] = None,
|
|
1338
|
+
) -> CreateCustomAppIntegrationOutput:
|
|
1095
1339
|
"""Create Custom OAuth App Integration.
|
|
1096
|
-
|
|
1340
|
+
|
|
1097
1341
|
Create Custom OAuth App Integration.
|
|
1098
|
-
|
|
1342
|
+
|
|
1099
1343
|
You can retrieve the custom OAuth app integration via :method:CustomAppIntegration/get.
|
|
1100
|
-
|
|
1344
|
+
|
|
1101
1345
|
:param confidential: bool (optional)
|
|
1102
1346
|
This field indicates whether an OAuth client secret is required to authenticate this client.
|
|
1103
1347
|
:param name: str (optional)
|
|
@@ -1112,108 +1356,135 @@ class CustomAppIntegrationAPI:
|
|
|
1112
1356
|
:param user_authorized_scopes: List[str] (optional)
|
|
1113
1357
|
Scopes that will need to be consented by end user to mint the access token. If the user does not
|
|
1114
1358
|
authorize the access token will not be minted. Must be a subset of scopes.
|
|
1115
|
-
|
|
1359
|
+
|
|
1116
1360
|
:returns: :class:`CreateCustomAppIntegrationOutput`
|
|
1117
1361
|
"""
|
|
1118
1362
|
body = {}
|
|
1119
|
-
if confidential is not None:
|
|
1120
|
-
|
|
1121
|
-
if
|
|
1122
|
-
|
|
1123
|
-
if
|
|
1363
|
+
if confidential is not None:
|
|
1364
|
+
body["confidential"] = confidential
|
|
1365
|
+
if name is not None:
|
|
1366
|
+
body["name"] = name
|
|
1367
|
+
if redirect_urls is not None:
|
|
1368
|
+
body["redirect_urls"] = [v for v in redirect_urls]
|
|
1369
|
+
if scopes is not None:
|
|
1370
|
+
body["scopes"] = [v for v in scopes]
|
|
1371
|
+
if token_access_policy is not None:
|
|
1372
|
+
body["token_access_policy"] = token_access_policy.as_dict()
|
|
1124
1373
|
if user_authorized_scopes is not None:
|
|
1125
|
-
body[
|
|
1126
|
-
headers = {
|
|
1374
|
+
body["user_authorized_scopes"] = [v for v in user_authorized_scopes]
|
|
1375
|
+
headers = {
|
|
1376
|
+
"Accept": "application/json",
|
|
1377
|
+
"Content-Type": "application/json",
|
|
1378
|
+
}
|
|
1127
1379
|
|
|
1128
|
-
res = self._api.do(
|
|
1129
|
-
|
|
1130
|
-
|
|
1131
|
-
|
|
1380
|
+
res = self._api.do(
|
|
1381
|
+
"POST",
|
|
1382
|
+
f"/api/2.0/accounts/{self._api.account_id}/oauth2/custom-app-integrations",
|
|
1383
|
+
body=body,
|
|
1384
|
+
headers=headers,
|
|
1385
|
+
)
|
|
1132
1386
|
return CreateCustomAppIntegrationOutput.from_dict(res)
|
|
1133
1387
|
|
|
1134
1388
|
def delete(self, integration_id: str):
|
|
1135
1389
|
"""Delete Custom OAuth App Integration.
|
|
1136
|
-
|
|
1390
|
+
|
|
1137
1391
|
Delete an existing Custom OAuth App Integration. You can retrieve the custom OAuth app integration via
|
|
1138
1392
|
:method:CustomAppIntegration/get.
|
|
1139
|
-
|
|
1393
|
+
|
|
1140
1394
|
:param integration_id: str
|
|
1141
|
-
|
|
1142
|
-
|
|
1395
|
+
|
|
1396
|
+
|
|
1143
1397
|
"""
|
|
1144
1398
|
|
|
1145
|
-
headers = {
|
|
1399
|
+
headers = {
|
|
1400
|
+
"Accept": "application/json",
|
|
1401
|
+
}
|
|
1146
1402
|
|
|
1147
1403
|
self._api.do(
|
|
1148
|
-
|
|
1149
|
-
f
|
|
1150
|
-
headers=headers
|
|
1404
|
+
"DELETE",
|
|
1405
|
+
f"/api/2.0/accounts/{self._api.account_id}/oauth2/custom-app-integrations/{integration_id}",
|
|
1406
|
+
headers=headers,
|
|
1407
|
+
)
|
|
1151
1408
|
|
|
1152
1409
|
def get(self, integration_id: str) -> GetCustomAppIntegrationOutput:
|
|
1153
1410
|
"""Get OAuth Custom App Integration.
|
|
1154
|
-
|
|
1411
|
+
|
|
1155
1412
|
Gets the Custom OAuth App Integration for the given integration id.
|
|
1156
|
-
|
|
1413
|
+
|
|
1157
1414
|
:param integration_id: str
|
|
1158
1415
|
The OAuth app integration ID.
|
|
1159
|
-
|
|
1416
|
+
|
|
1160
1417
|
:returns: :class:`GetCustomAppIntegrationOutput`
|
|
1161
1418
|
"""
|
|
1162
1419
|
|
|
1163
|
-
headers = {
|
|
1420
|
+
headers = {
|
|
1421
|
+
"Accept": "application/json",
|
|
1422
|
+
}
|
|
1164
1423
|
|
|
1165
1424
|
res = self._api.do(
|
|
1166
|
-
|
|
1167
|
-
f
|
|
1168
|
-
headers=headers
|
|
1425
|
+
"GET",
|
|
1426
|
+
f"/api/2.0/accounts/{self._api.account_id}/oauth2/custom-app-integrations/{integration_id}",
|
|
1427
|
+
headers=headers,
|
|
1428
|
+
)
|
|
1169
1429
|
return GetCustomAppIntegrationOutput.from_dict(res)
|
|
1170
1430
|
|
|
1171
|
-
def list(
|
|
1172
|
-
|
|
1173
|
-
|
|
1174
|
-
|
|
1175
|
-
|
|
1431
|
+
def list(
|
|
1432
|
+
self,
|
|
1433
|
+
*,
|
|
1434
|
+
include_creator_username: Optional[bool] = None,
|
|
1435
|
+
page_size: Optional[int] = None,
|
|
1436
|
+
page_token: Optional[str] = None,
|
|
1437
|
+
) -> Iterator[GetCustomAppIntegrationOutput]:
|
|
1176
1438
|
"""Get custom oauth app integrations.
|
|
1177
|
-
|
|
1439
|
+
|
|
1178
1440
|
Get the list of custom OAuth app integrations for the specified Databricks account
|
|
1179
|
-
|
|
1441
|
+
|
|
1180
1442
|
:param include_creator_username: bool (optional)
|
|
1181
1443
|
:param page_size: int (optional)
|
|
1182
1444
|
:param page_token: str (optional)
|
|
1183
|
-
|
|
1445
|
+
|
|
1184
1446
|
:returns: Iterator over :class:`GetCustomAppIntegrationOutput`
|
|
1185
1447
|
"""
|
|
1186
1448
|
|
|
1187
1449
|
query = {}
|
|
1188
|
-
if include_creator_username is not None:
|
|
1189
|
-
|
|
1190
|
-
if
|
|
1191
|
-
|
|
1450
|
+
if include_creator_username is not None:
|
|
1451
|
+
query["include_creator_username"] = include_creator_username
|
|
1452
|
+
if page_size is not None:
|
|
1453
|
+
query["page_size"] = page_size
|
|
1454
|
+
if page_token is not None:
|
|
1455
|
+
query["page_token"] = page_token
|
|
1456
|
+
headers = {
|
|
1457
|
+
"Accept": "application/json",
|
|
1458
|
+
}
|
|
1192
1459
|
|
|
1193
1460
|
while True:
|
|
1194
|
-
json = self._api.do(
|
|
1195
|
-
|
|
1196
|
-
|
|
1197
|
-
|
|
1198
|
-
|
|
1199
|
-
|
|
1461
|
+
json = self._api.do(
|
|
1462
|
+
"GET",
|
|
1463
|
+
f"/api/2.0/accounts/{self._api.account_id}/oauth2/custom-app-integrations",
|
|
1464
|
+
query=query,
|
|
1465
|
+
headers=headers,
|
|
1466
|
+
)
|
|
1467
|
+
if "apps" in json:
|
|
1468
|
+
for v in json["apps"]:
|
|
1200
1469
|
yield GetCustomAppIntegrationOutput.from_dict(v)
|
|
1201
|
-
if
|
|
1470
|
+
if "next_page_token" not in json or not json["next_page_token"]:
|
|
1202
1471
|
return
|
|
1203
|
-
query[
|
|
1204
|
-
|
|
1205
|
-
def update(
|
|
1206
|
-
|
|
1207
|
-
|
|
1208
|
-
|
|
1209
|
-
|
|
1210
|
-
|
|
1211
|
-
|
|
1472
|
+
query["page_token"] = json["next_page_token"]
|
|
1473
|
+
|
|
1474
|
+
def update(
|
|
1475
|
+
self,
|
|
1476
|
+
integration_id: str,
|
|
1477
|
+
*,
|
|
1478
|
+
redirect_urls: Optional[List[str]] = None,
|
|
1479
|
+
scopes: Optional[List[str]] = None,
|
|
1480
|
+
token_access_policy: Optional[TokenAccessPolicy] = None,
|
|
1481
|
+
user_authorized_scopes: Optional[List[str]] = None,
|
|
1482
|
+
):
|
|
1212
1483
|
"""Updates Custom OAuth App Integration.
|
|
1213
|
-
|
|
1484
|
+
|
|
1214
1485
|
Updates an existing custom OAuth App Integration. You can retrieve the custom OAuth app integration
|
|
1215
1486
|
via :method:CustomAppIntegration/get.
|
|
1216
|
-
|
|
1487
|
+
|
|
1217
1488
|
:param integration_id: str
|
|
1218
1489
|
:param redirect_urls: List[str] (optional)
|
|
1219
1490
|
List of OAuth redirect urls to be updated in the custom OAuth app integration
|
|
@@ -1225,22 +1496,29 @@ class CustomAppIntegrationAPI:
|
|
|
1225
1496
|
:param user_authorized_scopes: List[str] (optional)
|
|
1226
1497
|
Scopes that will need to be consented by end user to mint the access token. If the user does not
|
|
1227
1498
|
authorize the access token will not be minted. Must be a subset of scopes.
|
|
1228
|
-
|
|
1229
|
-
|
|
1499
|
+
|
|
1500
|
+
|
|
1230
1501
|
"""
|
|
1231
1502
|
body = {}
|
|
1232
|
-
if redirect_urls is not None:
|
|
1233
|
-
|
|
1234
|
-
if
|
|
1503
|
+
if redirect_urls is not None:
|
|
1504
|
+
body["redirect_urls"] = [v for v in redirect_urls]
|
|
1505
|
+
if scopes is not None:
|
|
1506
|
+
body["scopes"] = [v for v in scopes]
|
|
1507
|
+
if token_access_policy is not None:
|
|
1508
|
+
body["token_access_policy"] = token_access_policy.as_dict()
|
|
1235
1509
|
if user_authorized_scopes is not None:
|
|
1236
|
-
body[
|
|
1237
|
-
headers = {
|
|
1510
|
+
body["user_authorized_scopes"] = [v for v in user_authorized_scopes]
|
|
1511
|
+
headers = {
|
|
1512
|
+
"Accept": "application/json",
|
|
1513
|
+
"Content-Type": "application/json",
|
|
1514
|
+
}
|
|
1238
1515
|
|
|
1239
1516
|
self._api.do(
|
|
1240
|
-
|
|
1241
|
-
f
|
|
1517
|
+
"PATCH",
|
|
1518
|
+
f"/api/2.0/accounts/{self._api.account_id}/oauth2/custom-app-integrations/{integration_id}",
|
|
1242
1519
|
body=body,
|
|
1243
|
-
headers=headers
|
|
1520
|
+
headers=headers,
|
|
1521
|
+
)
|
|
1244
1522
|
|
|
1245
1523
|
|
|
1246
1524
|
class OAuthPublishedAppsAPI:
|
|
@@ -1251,38 +1529,40 @@ class OAuthPublishedAppsAPI:
|
|
|
1251
1529
|
def __init__(self, api_client):
|
|
1252
1530
|
self._api = api_client
|
|
1253
1531
|
|
|
1254
|
-
def list(
|
|
1255
|
-
|
|
1256
|
-
|
|
1257
|
-
page_token: Optional[str] = None) -> Iterator[PublishedAppOutput]:
|
|
1532
|
+
def list(
|
|
1533
|
+
self, *, page_size: Optional[int] = None, page_token: Optional[str] = None
|
|
1534
|
+
) -> Iterator[PublishedAppOutput]:
|
|
1258
1535
|
"""Get all the published OAuth apps.
|
|
1259
|
-
|
|
1536
|
+
|
|
1260
1537
|
Get all the available published OAuth apps in Databricks.
|
|
1261
|
-
|
|
1538
|
+
|
|
1262
1539
|
:param page_size: int (optional)
|
|
1263
1540
|
The max number of OAuth published apps to return in one page.
|
|
1264
1541
|
:param page_token: str (optional)
|
|
1265
1542
|
A token that can be used to get the next page of results.
|
|
1266
|
-
|
|
1543
|
+
|
|
1267
1544
|
:returns: Iterator over :class:`PublishedAppOutput`
|
|
1268
1545
|
"""
|
|
1269
1546
|
|
|
1270
1547
|
query = {}
|
|
1271
|
-
if page_size is not None:
|
|
1272
|
-
|
|
1273
|
-
|
|
1548
|
+
if page_size is not None:
|
|
1549
|
+
query["page_size"] = page_size
|
|
1550
|
+
if page_token is not None:
|
|
1551
|
+
query["page_token"] = page_token
|
|
1552
|
+
headers = {
|
|
1553
|
+
"Accept": "application/json",
|
|
1554
|
+
}
|
|
1274
1555
|
|
|
1275
1556
|
while True:
|
|
1276
|
-
json = self._api.do(
|
|
1277
|
-
|
|
1278
|
-
|
|
1279
|
-
|
|
1280
|
-
|
|
1281
|
-
for v in json['apps']:
|
|
1557
|
+
json = self._api.do(
|
|
1558
|
+
"GET", f"/api/2.0/accounts/{self._api.account_id}/oauth2/published-apps", query=query, headers=headers
|
|
1559
|
+
)
|
|
1560
|
+
if "apps" in json:
|
|
1561
|
+
for v in json["apps"]:
|
|
1282
1562
|
yield PublishedAppOutput.from_dict(v)
|
|
1283
|
-
if
|
|
1563
|
+
if "next_page_token" not in json or not json["next_page_token"]:
|
|
1284
1564
|
return
|
|
1285
|
-
query[
|
|
1565
|
+
query["page_token"] = json["next_page_token"]
|
|
1286
1566
|
|
|
1287
1567
|
|
|
1288
1568
|
class PublishedAppIntegrationAPI:
|
|
@@ -1293,142 +1573,163 @@ class PublishedAppIntegrationAPI:
|
|
|
1293
1573
|
self._api = api_client
|
|
1294
1574
|
|
|
1295
1575
|
def create(
|
|
1296
|
-
|
|
1297
|
-
|
|
1298
|
-
app_id: Optional[str] = None,
|
|
1299
|
-
token_access_policy: Optional[TokenAccessPolicy] = None) -> CreatePublishedAppIntegrationOutput:
|
|
1576
|
+
self, *, app_id: Optional[str] = None, token_access_policy: Optional[TokenAccessPolicy] = None
|
|
1577
|
+
) -> CreatePublishedAppIntegrationOutput:
|
|
1300
1578
|
"""Create Published OAuth App Integration.
|
|
1301
|
-
|
|
1579
|
+
|
|
1302
1580
|
Create Published OAuth App Integration.
|
|
1303
|
-
|
|
1581
|
+
|
|
1304
1582
|
You can retrieve the published OAuth app integration via :method:PublishedAppIntegration/get.
|
|
1305
|
-
|
|
1583
|
+
|
|
1306
1584
|
:param app_id: str (optional)
|
|
1307
1585
|
App id of the OAuth published app integration. For example power-bi, tableau-deskop
|
|
1308
1586
|
:param token_access_policy: :class:`TokenAccessPolicy` (optional)
|
|
1309
1587
|
Token access policy
|
|
1310
|
-
|
|
1588
|
+
|
|
1311
1589
|
:returns: :class:`CreatePublishedAppIntegrationOutput`
|
|
1312
1590
|
"""
|
|
1313
1591
|
body = {}
|
|
1314
|
-
if app_id is not None:
|
|
1315
|
-
|
|
1316
|
-
|
|
1317
|
-
|
|
1318
|
-
|
|
1319
|
-
|
|
1320
|
-
|
|
1321
|
-
|
|
1592
|
+
if app_id is not None:
|
|
1593
|
+
body["app_id"] = app_id
|
|
1594
|
+
if token_access_policy is not None:
|
|
1595
|
+
body["token_access_policy"] = token_access_policy.as_dict()
|
|
1596
|
+
headers = {
|
|
1597
|
+
"Accept": "application/json",
|
|
1598
|
+
"Content-Type": "application/json",
|
|
1599
|
+
}
|
|
1600
|
+
|
|
1601
|
+
res = self._api.do(
|
|
1602
|
+
"POST",
|
|
1603
|
+
f"/api/2.0/accounts/{self._api.account_id}/oauth2/published-app-integrations",
|
|
1604
|
+
body=body,
|
|
1605
|
+
headers=headers,
|
|
1606
|
+
)
|
|
1322
1607
|
return CreatePublishedAppIntegrationOutput.from_dict(res)
|
|
1323
1608
|
|
|
1324
1609
|
def delete(self, integration_id: str):
|
|
1325
1610
|
"""Delete Published OAuth App Integration.
|
|
1326
|
-
|
|
1611
|
+
|
|
1327
1612
|
Delete an existing Published OAuth App Integration. You can retrieve the published OAuth app
|
|
1328
1613
|
integration via :method:PublishedAppIntegration/get.
|
|
1329
|
-
|
|
1614
|
+
|
|
1330
1615
|
:param integration_id: str
|
|
1331
|
-
|
|
1332
|
-
|
|
1616
|
+
|
|
1617
|
+
|
|
1333
1618
|
"""
|
|
1334
1619
|
|
|
1335
|
-
headers = {
|
|
1620
|
+
headers = {
|
|
1621
|
+
"Accept": "application/json",
|
|
1622
|
+
}
|
|
1336
1623
|
|
|
1337
1624
|
self._api.do(
|
|
1338
|
-
|
|
1339
|
-
f
|
|
1340
|
-
headers=headers
|
|
1625
|
+
"DELETE",
|
|
1626
|
+
f"/api/2.0/accounts/{self._api.account_id}/oauth2/published-app-integrations/{integration_id}",
|
|
1627
|
+
headers=headers,
|
|
1628
|
+
)
|
|
1341
1629
|
|
|
1342
1630
|
def get(self, integration_id: str) -> GetPublishedAppIntegrationOutput:
|
|
1343
1631
|
"""Get OAuth Published App Integration.
|
|
1344
|
-
|
|
1632
|
+
|
|
1345
1633
|
Gets the Published OAuth App Integration for the given integration id.
|
|
1346
|
-
|
|
1634
|
+
|
|
1347
1635
|
:param integration_id: str
|
|
1348
|
-
|
|
1636
|
+
|
|
1349
1637
|
:returns: :class:`GetPublishedAppIntegrationOutput`
|
|
1350
1638
|
"""
|
|
1351
1639
|
|
|
1352
|
-
headers = {
|
|
1640
|
+
headers = {
|
|
1641
|
+
"Accept": "application/json",
|
|
1642
|
+
}
|
|
1353
1643
|
|
|
1354
1644
|
res = self._api.do(
|
|
1355
|
-
|
|
1356
|
-
f
|
|
1357
|
-
headers=headers
|
|
1645
|
+
"GET",
|
|
1646
|
+
f"/api/2.0/accounts/{self._api.account_id}/oauth2/published-app-integrations/{integration_id}",
|
|
1647
|
+
headers=headers,
|
|
1648
|
+
)
|
|
1358
1649
|
return GetPublishedAppIntegrationOutput.from_dict(res)
|
|
1359
1650
|
|
|
1360
|
-
def list(
|
|
1361
|
-
|
|
1362
|
-
|
|
1363
|
-
page_token: Optional[str] = None) -> Iterator[GetPublishedAppIntegrationOutput]:
|
|
1651
|
+
def list(
|
|
1652
|
+
self, *, page_size: Optional[int] = None, page_token: Optional[str] = None
|
|
1653
|
+
) -> Iterator[GetPublishedAppIntegrationOutput]:
|
|
1364
1654
|
"""Get published oauth app integrations.
|
|
1365
|
-
|
|
1655
|
+
|
|
1366
1656
|
Get the list of published OAuth app integrations for the specified Databricks account
|
|
1367
|
-
|
|
1657
|
+
|
|
1368
1658
|
:param page_size: int (optional)
|
|
1369
1659
|
:param page_token: str (optional)
|
|
1370
|
-
|
|
1660
|
+
|
|
1371
1661
|
:returns: Iterator over :class:`GetPublishedAppIntegrationOutput`
|
|
1372
1662
|
"""
|
|
1373
1663
|
|
|
1374
1664
|
query = {}
|
|
1375
|
-
if page_size is not None:
|
|
1376
|
-
|
|
1377
|
-
|
|
1665
|
+
if page_size is not None:
|
|
1666
|
+
query["page_size"] = page_size
|
|
1667
|
+
if page_token is not None:
|
|
1668
|
+
query["page_token"] = page_token
|
|
1669
|
+
headers = {
|
|
1670
|
+
"Accept": "application/json",
|
|
1671
|
+
}
|
|
1378
1672
|
|
|
1379
1673
|
while True:
|
|
1380
|
-
json = self._api.do(
|
|
1381
|
-
|
|
1382
|
-
|
|
1383
|
-
|
|
1384
|
-
|
|
1385
|
-
|
|
1674
|
+
json = self._api.do(
|
|
1675
|
+
"GET",
|
|
1676
|
+
f"/api/2.0/accounts/{self._api.account_id}/oauth2/published-app-integrations",
|
|
1677
|
+
query=query,
|
|
1678
|
+
headers=headers,
|
|
1679
|
+
)
|
|
1680
|
+
if "apps" in json:
|
|
1681
|
+
for v in json["apps"]:
|
|
1386
1682
|
yield GetPublishedAppIntegrationOutput.from_dict(v)
|
|
1387
|
-
if
|
|
1683
|
+
if "next_page_token" not in json or not json["next_page_token"]:
|
|
1388
1684
|
return
|
|
1389
|
-
query[
|
|
1685
|
+
query["page_token"] = json["next_page_token"]
|
|
1390
1686
|
|
|
1391
1687
|
def update(self, integration_id: str, *, token_access_policy: Optional[TokenAccessPolicy] = None):
|
|
1392
1688
|
"""Updates Published OAuth App Integration.
|
|
1393
|
-
|
|
1689
|
+
|
|
1394
1690
|
Updates an existing published OAuth App Integration. You can retrieve the published OAuth app
|
|
1395
1691
|
integration via :method:PublishedAppIntegration/get.
|
|
1396
|
-
|
|
1692
|
+
|
|
1397
1693
|
:param integration_id: str
|
|
1398
1694
|
:param token_access_policy: :class:`TokenAccessPolicy` (optional)
|
|
1399
1695
|
Token access policy to be updated in the published OAuth app integration
|
|
1400
|
-
|
|
1401
|
-
|
|
1696
|
+
|
|
1697
|
+
|
|
1402
1698
|
"""
|
|
1403
1699
|
body = {}
|
|
1404
|
-
if token_access_policy is not None:
|
|
1405
|
-
|
|
1700
|
+
if token_access_policy is not None:
|
|
1701
|
+
body["token_access_policy"] = token_access_policy.as_dict()
|
|
1702
|
+
headers = {
|
|
1703
|
+
"Accept": "application/json",
|
|
1704
|
+
"Content-Type": "application/json",
|
|
1705
|
+
}
|
|
1406
1706
|
|
|
1407
1707
|
self._api.do(
|
|
1408
|
-
|
|
1409
|
-
f
|
|
1708
|
+
"PATCH",
|
|
1709
|
+
f"/api/2.0/accounts/{self._api.account_id}/oauth2/published-app-integrations/{integration_id}",
|
|
1410
1710
|
body=body,
|
|
1411
|
-
headers=headers
|
|
1711
|
+
headers=headers,
|
|
1712
|
+
)
|
|
1412
1713
|
|
|
1413
1714
|
|
|
1414
1715
|
class ServicePrincipalFederationPolicyAPI:
|
|
1415
1716
|
"""These APIs manage service principal federation policies.
|
|
1416
|
-
|
|
1717
|
+
|
|
1417
1718
|
Service principal federation, also known as Workload Identity Federation, allows your automated workloads
|
|
1418
1719
|
running outside of Databricks to securely access Databricks APIs without the need for Databricks secrets.
|
|
1419
1720
|
With Workload Identity Federation, your application (or workload) authenticates to Databricks as a
|
|
1420
1721
|
Databricks service principal, using tokens provided by the workload runtime.
|
|
1421
|
-
|
|
1722
|
+
|
|
1422
1723
|
Databricks strongly recommends using Workload Identity Federation to authenticate to Databricks from
|
|
1423
1724
|
automated workloads, over alternatives such as OAuth client secrets or Personal Access Tokens, whenever
|
|
1424
1725
|
possible. Workload Identity Federation is supported by many popular services, including Github Actions,
|
|
1425
1726
|
Azure DevOps, GitLab, Terraform Cloud, and Kubernetes clusters, among others.
|
|
1426
|
-
|
|
1727
|
+
|
|
1427
1728
|
Workload identity federation is configured in your Databricks account using a service principal federation
|
|
1428
1729
|
policy. A service principal federation policy specifies: * which IdP, or issuer, the service principal is
|
|
1429
1730
|
allowed to authenticate from * which workload identity, or subject, is allowed to authenticate as the
|
|
1430
1731
|
Databricks service principal
|
|
1431
|
-
|
|
1732
|
+
|
|
1432
1733
|
To configure a federation policy, you provide the following: * The required token __issuer__, as specified
|
|
1433
1734
|
in the “iss” claim of workload identity tokens. The issuer is an https URL that identifies the
|
|
1434
1735
|
workload identity provider. * The required token __subject__, as specified in the “sub” claim of
|
|
@@ -1440,129 +1741,143 @@ class ServicePrincipalFederationPolicyAPI:
|
|
|
1440
1741
|
of the workload identity tokens, in JWKS format. If unspecified (recommended), Databricks automatically
|
|
1441
1742
|
fetches the public keys from the issuer’s well known endpoint. Databricks strongly recommends relying on
|
|
1442
1743
|
the issuer’s well known endpoint for discovering public keys.
|
|
1443
|
-
|
|
1744
|
+
|
|
1444
1745
|
An example service principal federation policy, for a Github Actions workload, is: ``` issuer:
|
|
1445
1746
|
"https://token.actions.githubusercontent.com" audiences: ["https://github.com/my-github-org"] subject:
|
|
1446
1747
|
"repo:my-github-org/my-repo:environment:prod" ```
|
|
1447
|
-
|
|
1748
|
+
|
|
1448
1749
|
An example JWT token body that matches this policy and could be used to authenticate to Databricks is: ```
|
|
1449
1750
|
{ "iss": "https://token.actions.githubusercontent.com", "aud": "https://github.com/my-github-org", "sub":
|
|
1450
1751
|
"repo:my-github-org/my-repo:environment:prod" } ```
|
|
1451
|
-
|
|
1752
|
+
|
|
1452
1753
|
You may also need to configure the workload runtime to generate tokens for your workloads.
|
|
1453
|
-
|
|
1754
|
+
|
|
1454
1755
|
You do not need to configure an OAuth application in Databricks to use token federation."""
|
|
1455
1756
|
|
|
1456
1757
|
def __init__(self, api_client):
|
|
1457
1758
|
self._api = api_client
|
|
1458
1759
|
|
|
1459
|
-
def create(
|
|
1460
|
-
|
|
1461
|
-
|
|
1462
|
-
policy: Optional[FederationPolicy] = None,
|
|
1463
|
-
policy_id: Optional[str] = None) -> FederationPolicy:
|
|
1760
|
+
def create(
|
|
1761
|
+
self, service_principal_id: int, *, policy: Optional[FederationPolicy] = None, policy_id: Optional[str] = None
|
|
1762
|
+
) -> FederationPolicy:
|
|
1464
1763
|
"""Create service principal federation policy.
|
|
1465
|
-
|
|
1764
|
+
|
|
1466
1765
|
:param service_principal_id: int
|
|
1467
1766
|
The service principal id for the federation policy.
|
|
1468
1767
|
:param policy: :class:`FederationPolicy` (optional)
|
|
1469
1768
|
:param policy_id: str (optional)
|
|
1470
1769
|
The identifier for the federation policy. The identifier must contain only lowercase alphanumeric
|
|
1471
1770
|
characters, numbers, hyphens, and slashes. If unspecified, the id will be assigned by Databricks.
|
|
1472
|
-
|
|
1771
|
+
|
|
1473
1772
|
:returns: :class:`FederationPolicy`
|
|
1474
1773
|
"""
|
|
1475
1774
|
body = policy.as_dict()
|
|
1476
1775
|
query = {}
|
|
1477
|
-
if policy_id is not None:
|
|
1478
|
-
|
|
1776
|
+
if policy_id is not None:
|
|
1777
|
+
query["policy_id"] = policy_id
|
|
1778
|
+
headers = {
|
|
1779
|
+
"Accept": "application/json",
|
|
1780
|
+
"Content-Type": "application/json",
|
|
1781
|
+
}
|
|
1479
1782
|
|
|
1480
1783
|
res = self._api.do(
|
|
1481
|
-
|
|
1482
|
-
f
|
|
1784
|
+
"POST",
|
|
1785
|
+
f"/api/2.0/accounts/{self._api.account_id}/servicePrincipals/{service_principal_id}/federationPolicies",
|
|
1483
1786
|
query=query,
|
|
1484
1787
|
body=body,
|
|
1485
|
-
headers=headers
|
|
1788
|
+
headers=headers,
|
|
1789
|
+
)
|
|
1486
1790
|
return FederationPolicy.from_dict(res)
|
|
1487
1791
|
|
|
1488
1792
|
def delete(self, service_principal_id: int, policy_id: str):
|
|
1489
1793
|
"""Delete service principal federation policy.
|
|
1490
|
-
|
|
1794
|
+
|
|
1491
1795
|
:param service_principal_id: int
|
|
1492
1796
|
The service principal id for the federation policy.
|
|
1493
1797
|
:param policy_id: str
|
|
1494
1798
|
The identifier for the federation policy.
|
|
1495
|
-
|
|
1496
|
-
|
|
1799
|
+
|
|
1800
|
+
|
|
1497
1801
|
"""
|
|
1498
1802
|
|
|
1499
|
-
headers = {
|
|
1803
|
+
headers = {
|
|
1804
|
+
"Accept": "application/json",
|
|
1805
|
+
}
|
|
1500
1806
|
|
|
1501
1807
|
self._api.do(
|
|
1502
|
-
|
|
1503
|
-
f
|
|
1504
|
-
headers=headers
|
|
1808
|
+
"DELETE",
|
|
1809
|
+
f"/api/2.0/accounts/{self._api.account_id}/servicePrincipals/{service_principal_id}/federationPolicies/{policy_id}",
|
|
1810
|
+
headers=headers,
|
|
1811
|
+
)
|
|
1505
1812
|
|
|
1506
1813
|
def get(self, service_principal_id: int, policy_id: str) -> FederationPolicy:
|
|
1507
1814
|
"""Get service principal federation policy.
|
|
1508
|
-
|
|
1815
|
+
|
|
1509
1816
|
:param service_principal_id: int
|
|
1510
1817
|
The service principal id for the federation policy.
|
|
1511
1818
|
:param policy_id: str
|
|
1512
1819
|
The identifier for the federation policy.
|
|
1513
|
-
|
|
1820
|
+
|
|
1514
1821
|
:returns: :class:`FederationPolicy`
|
|
1515
1822
|
"""
|
|
1516
1823
|
|
|
1517
|
-
headers = {
|
|
1824
|
+
headers = {
|
|
1825
|
+
"Accept": "application/json",
|
|
1826
|
+
}
|
|
1518
1827
|
|
|
1519
1828
|
res = self._api.do(
|
|
1520
|
-
|
|
1521
|
-
f
|
|
1522
|
-
headers=headers
|
|
1829
|
+
"GET",
|
|
1830
|
+
f"/api/2.0/accounts/{self._api.account_id}/servicePrincipals/{service_principal_id}/federationPolicies/{policy_id}",
|
|
1831
|
+
headers=headers,
|
|
1832
|
+
)
|
|
1523
1833
|
return FederationPolicy.from_dict(res)
|
|
1524
1834
|
|
|
1525
|
-
def list(
|
|
1526
|
-
|
|
1527
|
-
|
|
1528
|
-
page_size: Optional[int] = None,
|
|
1529
|
-
page_token: Optional[str] = None) -> Iterator[FederationPolicy]:
|
|
1835
|
+
def list(
|
|
1836
|
+
self, service_principal_id: int, *, page_size: Optional[int] = None, page_token: Optional[str] = None
|
|
1837
|
+
) -> Iterator[FederationPolicy]:
|
|
1530
1838
|
"""List service principal federation policies.
|
|
1531
|
-
|
|
1839
|
+
|
|
1532
1840
|
:param service_principal_id: int
|
|
1533
1841
|
The service principal id for the federation policy.
|
|
1534
1842
|
:param page_size: int (optional)
|
|
1535
1843
|
:param page_token: str (optional)
|
|
1536
|
-
|
|
1844
|
+
|
|
1537
1845
|
:returns: Iterator over :class:`FederationPolicy`
|
|
1538
1846
|
"""
|
|
1539
1847
|
|
|
1540
1848
|
query = {}
|
|
1541
|
-
if page_size is not None:
|
|
1542
|
-
|
|
1543
|
-
|
|
1849
|
+
if page_size is not None:
|
|
1850
|
+
query["page_size"] = page_size
|
|
1851
|
+
if page_token is not None:
|
|
1852
|
+
query["page_token"] = page_token
|
|
1853
|
+
headers = {
|
|
1854
|
+
"Accept": "application/json",
|
|
1855
|
+
}
|
|
1544
1856
|
|
|
1545
1857
|
while True:
|
|
1546
1858
|
json = self._api.do(
|
|
1547
|
-
|
|
1548
|
-
f
|
|
1859
|
+
"GET",
|
|
1860
|
+
f"/api/2.0/accounts/{self._api.account_id}/servicePrincipals/{service_principal_id}/federationPolicies",
|
|
1549
1861
|
query=query,
|
|
1550
|
-
headers=headers
|
|
1551
|
-
|
|
1552
|
-
|
|
1862
|
+
headers=headers,
|
|
1863
|
+
)
|
|
1864
|
+
if "policies" in json:
|
|
1865
|
+
for v in json["policies"]:
|
|
1553
1866
|
yield FederationPolicy.from_dict(v)
|
|
1554
|
-
if
|
|
1867
|
+
if "next_page_token" not in json or not json["next_page_token"]:
|
|
1555
1868
|
return
|
|
1556
|
-
query[
|
|
1557
|
-
|
|
1558
|
-
def update(
|
|
1559
|
-
|
|
1560
|
-
|
|
1561
|
-
|
|
1562
|
-
|
|
1563
|
-
|
|
1869
|
+
query["page_token"] = json["next_page_token"]
|
|
1870
|
+
|
|
1871
|
+
def update(
|
|
1872
|
+
self,
|
|
1873
|
+
service_principal_id: int,
|
|
1874
|
+
policy_id: str,
|
|
1875
|
+
*,
|
|
1876
|
+
policy: Optional[FederationPolicy] = None,
|
|
1877
|
+
update_mask: Optional[str] = None,
|
|
1878
|
+
) -> FederationPolicy:
|
|
1564
1879
|
"""Update service principal federation policy.
|
|
1565
|
-
|
|
1880
|
+
|
|
1566
1881
|
:param service_principal_id: int
|
|
1567
1882
|
The service principal id for the federation policy.
|
|
1568
1883
|
:param policy_id: str
|
|
@@ -1574,84 +1889,103 @@ class ServicePrincipalFederationPolicyAPI:
|
|
|
1574
1889
|
should be updated (full replacement). If unspecified, all fields that are set in the policy provided
|
|
1575
1890
|
in the update request will overwrite the corresponding fields in the existing policy. Example value:
|
|
1576
1891
|
'description,oidc_policy.audiences'.
|
|
1577
|
-
|
|
1892
|
+
|
|
1578
1893
|
:returns: :class:`FederationPolicy`
|
|
1579
1894
|
"""
|
|
1580
1895
|
body = policy.as_dict()
|
|
1581
1896
|
query = {}
|
|
1582
|
-
if update_mask is not None:
|
|
1583
|
-
|
|
1897
|
+
if update_mask is not None:
|
|
1898
|
+
query["update_mask"] = update_mask
|
|
1899
|
+
headers = {
|
|
1900
|
+
"Accept": "application/json",
|
|
1901
|
+
"Content-Type": "application/json",
|
|
1902
|
+
}
|
|
1584
1903
|
|
|
1585
1904
|
res = self._api.do(
|
|
1586
|
-
|
|
1587
|
-
f
|
|
1905
|
+
"PATCH",
|
|
1906
|
+
f"/api/2.0/accounts/{self._api.account_id}/servicePrincipals/{service_principal_id}/federationPolicies/{policy_id}",
|
|
1588
1907
|
query=query,
|
|
1589
1908
|
body=body,
|
|
1590
|
-
headers=headers
|
|
1909
|
+
headers=headers,
|
|
1910
|
+
)
|
|
1591
1911
|
return FederationPolicy.from_dict(res)
|
|
1592
1912
|
|
|
1593
1913
|
|
|
1594
1914
|
class ServicePrincipalSecretsAPI:
|
|
1595
1915
|
"""These APIs enable administrators to manage service principal secrets.
|
|
1596
|
-
|
|
1916
|
+
|
|
1597
1917
|
You can use the generated secrets to obtain OAuth access tokens for a service principal, which can then be
|
|
1598
1918
|
used to access Databricks Accounts and Workspace APIs. For more information, see [Authentication using
|
|
1599
1919
|
OAuth tokens for service principals],
|
|
1600
|
-
|
|
1920
|
+
|
|
1601
1921
|
In addition, the generated secrets can be used to configure the Databricks Terraform Provider to
|
|
1602
1922
|
authenticate with the service principal. For more information, see [Databricks Terraform Provider].
|
|
1603
|
-
|
|
1923
|
+
|
|
1604
1924
|
[Authentication using OAuth tokens for service principals]: https://docs.databricks.com/dev-tools/authentication-oauth.html
|
|
1605
|
-
[Databricks Terraform Provider]: https://github.com/databricks/terraform-provider-databricks/blob/master/docs/index.md#authenticating-with-service-principal
|
|
1925
|
+
[Databricks Terraform Provider]: https://github.com/databricks/terraform-provider-databricks/blob/master/docs/index.md#authenticating-with-service-principal
|
|
1926
|
+
"""
|
|
1606
1927
|
|
|
1607
1928
|
def __init__(self, api_client):
|
|
1608
1929
|
self._api = api_client
|
|
1609
1930
|
|
|
1610
|
-
def create(
|
|
1931
|
+
def create(
|
|
1932
|
+
self, service_principal_id: int, *, lifetime: Optional[str] = None
|
|
1933
|
+
) -> CreateServicePrincipalSecretResponse:
|
|
1611
1934
|
"""Create service principal secret.
|
|
1612
|
-
|
|
1935
|
+
|
|
1613
1936
|
Create a secret for the given service principal.
|
|
1614
|
-
|
|
1937
|
+
|
|
1615
1938
|
:param service_principal_id: int
|
|
1616
1939
|
The service principal ID.
|
|
1617
|
-
|
|
1940
|
+
:param lifetime: str (optional)
|
|
1941
|
+
The lifetime of the secret in seconds. If this parameter is not provided, the secret will have a
|
|
1942
|
+
default lifetime of 730 days (63072000s).
|
|
1943
|
+
|
|
1618
1944
|
:returns: :class:`CreateServicePrincipalSecretResponse`
|
|
1619
1945
|
"""
|
|
1620
|
-
|
|
1621
|
-
|
|
1946
|
+
body = {}
|
|
1947
|
+
if lifetime is not None:
|
|
1948
|
+
body["lifetime"] = lifetime
|
|
1949
|
+
headers = {
|
|
1950
|
+
"Accept": "application/json",
|
|
1951
|
+
"Content-Type": "application/json",
|
|
1952
|
+
}
|
|
1622
1953
|
|
|
1623
1954
|
res = self._api.do(
|
|
1624
|
-
|
|
1625
|
-
f
|
|
1626
|
-
|
|
1955
|
+
"POST",
|
|
1956
|
+
f"/api/2.0/accounts/{self._api.account_id}/servicePrincipals/{service_principal_id}/credentials/secrets",
|
|
1957
|
+
body=body,
|
|
1958
|
+
headers=headers,
|
|
1959
|
+
)
|
|
1627
1960
|
return CreateServicePrincipalSecretResponse.from_dict(res)
|
|
1628
1961
|
|
|
1629
1962
|
def delete(self, service_principal_id: int, secret_id: str):
|
|
1630
1963
|
"""Delete service principal secret.
|
|
1631
|
-
|
|
1964
|
+
|
|
1632
1965
|
Delete a secret from the given service principal.
|
|
1633
|
-
|
|
1966
|
+
|
|
1634
1967
|
:param service_principal_id: int
|
|
1635
1968
|
The service principal ID.
|
|
1636
1969
|
:param secret_id: str
|
|
1637
1970
|
The secret ID.
|
|
1638
|
-
|
|
1639
|
-
|
|
1971
|
+
|
|
1972
|
+
|
|
1640
1973
|
"""
|
|
1641
1974
|
|
|
1642
1975
|
headers = {}
|
|
1643
1976
|
|
|
1644
1977
|
self._api.do(
|
|
1645
|
-
|
|
1646
|
-
f
|
|
1647
|
-
headers=headers
|
|
1978
|
+
"DELETE",
|
|
1979
|
+
f"/api/2.0/accounts/{self._api.account_id}/servicePrincipals/{service_principal_id}/credentials/secrets/{secret_id}",
|
|
1980
|
+
headers=headers,
|
|
1981
|
+
)
|
|
1648
1982
|
|
|
1649
1983
|
def list(self, service_principal_id: int, *, page_token: Optional[str] = None) -> Iterator[SecretInfo]:
|
|
1650
1984
|
"""List service principal secrets.
|
|
1651
|
-
|
|
1985
|
+
|
|
1652
1986
|
List all secrets associated with the given service principal. This operation only returns information
|
|
1653
1987
|
about the secrets themselves and does not include the secret values.
|
|
1654
|
-
|
|
1988
|
+
|
|
1655
1989
|
:param service_principal_id: int
|
|
1656
1990
|
The service principal ID.
|
|
1657
1991
|
:param page_token: str (optional)
|
|
@@ -1661,23 +1995,27 @@ class ServicePrincipalSecretsAPI:
|
|
|
1661
1995
|
previous request. To list all of the secrets for a service principal, it is necessary to continue
|
|
1662
1996
|
requesting pages of entries until the response contains no `next_page_token`. Note that the number
|
|
1663
1997
|
of entries returned must not be used to determine when the listing is complete.
|
|
1664
|
-
|
|
1998
|
+
|
|
1665
1999
|
:returns: Iterator over :class:`SecretInfo`
|
|
1666
2000
|
"""
|
|
1667
2001
|
|
|
1668
2002
|
query = {}
|
|
1669
|
-
if page_token is not None:
|
|
1670
|
-
|
|
2003
|
+
if page_token is not None:
|
|
2004
|
+
query["page_token"] = page_token
|
|
2005
|
+
headers = {
|
|
2006
|
+
"Accept": "application/json",
|
|
2007
|
+
}
|
|
1671
2008
|
|
|
1672
2009
|
while True:
|
|
1673
2010
|
json = self._api.do(
|
|
1674
|
-
|
|
1675
|
-
f
|
|
2011
|
+
"GET",
|
|
2012
|
+
f"/api/2.0/accounts/{self._api.account_id}/servicePrincipals/{service_principal_id}/credentials/secrets",
|
|
1676
2013
|
query=query,
|
|
1677
|
-
headers=headers
|
|
1678
|
-
|
|
1679
|
-
|
|
2014
|
+
headers=headers,
|
|
2015
|
+
)
|
|
2016
|
+
if "secrets" in json:
|
|
2017
|
+
for v in json["secrets"]:
|
|
1680
2018
|
yield SecretInfo.from_dict(v)
|
|
1681
|
-
if
|
|
2019
|
+
if "next_page_token" not in json or not json["next_page_token"]:
|
|
1682
2020
|
return
|
|
1683
|
-
query[
|
|
2021
|
+
query["page_token"] = json["next_page_token"]
|