pyegeria 5.4.0.23__py3-none-any.whl → 5.4.0.25__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.
Files changed (54) hide show
  1. commands/cat/debug_log +7967 -465
  2. commands/cat/debug_log.2025-08-15_09-14-07_444802.zip +0 -0
  3. commands/cat/debug_log.2025-08-16_10-21-59_388912.zip +0 -0
  4. commands/cat/debug_log.2025-08-17_11-34-27_981852.zip +0 -0
  5. commands/cat/dr_egeria_md.py +36 -6
  6. commands/cat/logs/pyegeria.log +3 -135
  7. md_processing/.DS_Store +0 -0
  8. md_processing/__init__.py +12 -6
  9. md_processing/data/commands.json +8523 -2234
  10. md_processing/dr_egeria_inbox/gov_def.md +76 -18
  11. md_processing/dr_egeria_inbox/img.png +0 -0
  12. md_processing/dr_egeria_inbox/product.md +185 -24
  13. md_processing/dr_egeria_outbox/.obsidian/workspace.json +5 -5
  14. md_processing/dr_egeria_outbox/monday/processed-2025-08-19 07:05-product.md +426 -0
  15. md_processing/dr_egeria_outbox/monday/processed-2025-08-19 07:56-product.md +212 -0
  16. md_processing/dr_egeria_outbox/monday/processed-2025-08-19 09:43-product.md +201 -0
  17. md_processing/dr_egeria_outbox/tuesday/processed-2025-08-19 10:55-product.md +209 -0
  18. md_processing/md_commands/governance_officer_commands.py +247 -178
  19. md_processing/md_commands/product_manager_commands.py +730 -580
  20. md_processing/md_processing_utils/common_md_proc_utils.py +170 -12
  21. md_processing/md_processing_utils/common_md_utils.py +126 -28
  22. md_processing/md_processing_utils/extraction_utils.py +2 -2
  23. md_processing/md_processing_utils/md_processing_constants.py +14 -10
  24. pyegeria/.DS_Store +0 -0
  25. pyegeria/__init__.py +1 -1
  26. pyegeria/_client_new.py +61 -12
  27. pyegeria/_exceptions_new.py +6 -0
  28. pyegeria/_output_formats.py +42 -2
  29. pyegeria/collection_manager.py +79 -14
  30. pyegeria/{data_designer_omvs.py → data_designer.py} +1171 -1675
  31. pyegeria/glossary_browser.py +1259 -0
  32. pyegeria/{glossary_manager_omvs.py → glossary_manager.py} +1181 -1099
  33. pyegeria/governance_officer.py +1 -3
  34. pyegeria/load_config.py +1 -1
  35. pyegeria/models.py +37 -4
  36. pyegeria/output_formatter.py +2 -1
  37. pyegeria/project_manager.py +1952 -0
  38. pyegeria/utils.py +5 -2
  39. {pyegeria-5.4.0.23.dist-info → pyegeria-5.4.0.25.dist-info}/METADATA +1 -1
  40. {pyegeria-5.4.0.23.dist-info → pyegeria-5.4.0.25.dist-info}/RECORD +43 -44
  41. md_processing/dr_egeria_outbox/friday/processed-2025-07-18 15:00-product.md +0 -62
  42. md_processing/dr_egeria_outbox/friday/processed-2025-07-18 15:13-product.md +0 -62
  43. md_processing/dr_egeria_outbox/friday/processed-2025-07-20 13:23-product.md +0 -47
  44. md_processing/dr_egeria_outbox/friday/processed-2025-08-01 11:55-data_test3.md +0 -503
  45. md_processing/dr_egeria_outbox/monday/processed-2025-07-14 12:38-data_designer_out.md +0 -663
  46. md_processing/dr_egeria_outbox/monday/processed-2025-07-21 10:52-generated_help_report.md +0 -2744
  47. md_processing/dr_egeria_outbox/monday/processed-2025-07-21 18:38-collections.md +0 -62
  48. md_processing/dr_egeria_outbox/monday/processed-2025-08-01 11:34-gov_def.md +0 -444
  49. md_processing/dr_egeria_outbox/processed-2025-08-03 16:05-glossary_list.md +0 -37
  50. pyegeria/glossary_browser_omvs.py +0 -3840
  51. pyegeria/governance_officer_omvs.py +0 -2367
  52. {pyegeria-5.4.0.23.dist-info → pyegeria-5.4.0.25.dist-info}/LICENSE +0 -0
  53. {pyegeria-5.4.0.23.dist-info → pyegeria-5.4.0.25.dist-info}/WHEEL +0 -0
  54. {pyegeria-5.4.0.23.dist-info → pyegeria-5.4.0.25.dist-info}/entry_points.txt +0 -0
@@ -0,0 +1,1952 @@
1
+ """
2
+ PDX-License-Identifier: Apache-2.0
3
+ Copyright Contributors to the ODPi Egeria project.
4
+
5
+ Create, maintain and explore projects.
6
+ https://egeria-project.org/concepts/project
7
+
8
+ """
9
+
10
+ import asyncio
11
+ import inspect
12
+ from datetime import datetime
13
+ from typing import Optional, Annotated, Literal, Union
14
+
15
+ from loguru import logger
16
+ from pydantic import ValidationError, Field, HttpUrl
17
+
18
+ from pyegeria._exceptions_new import PyegeriaInvalidParameterException
19
+ from pyegeria._globals import NO_ELEMENTS_FOUND, NO_GUID_RETURNED, NO_MEMBERS_FOUND
20
+ from pyegeria._output_formats import select_output_format_set, get_output_format_type_match
21
+ from pyegeria.load_config import get_app_config
22
+ from pyegeria.models import (SearchStringRequestBody, FilterRequestBody, GetRequestBody, NewElementRequestBody,
23
+ ReferenceableProperties, InitialClassifications, TemplateRequestBody,
24
+ UpdateElementRequestBody, UpdateStatusRequestBody, NewRelationshipRequestBody,
25
+ DeleteRequestBody, UpdateRelationshipRequestBody, ResultsRequestBody,
26
+ get_defined_field_values, PyegeriaModel)
27
+ from pyegeria.output_formatter import (generate_output,
28
+ _extract_referenceable_properties, populate_columns_from_properties,
29
+ get_required_relationships)
30
+ from pyegeria._client_new import Client2
31
+ from pyegeria.utils import body_slimmer, dynamic_catch
32
+
33
+
34
+ app_settings = get_app_config()
35
+ EGERIA_LOCAL_QUALIFIER = app_settings.User_Profile.egeria_local_qualifier
36
+ from pyegeria._globals import NO_ELEMENTS_FOUND, NO_PROJECTS_FOUND
37
+
38
+ class ProjectManager(Client2):
39
+ """
40
+ Create and manage projects. Projects may be organized in a hierarchy.
41
+ See https://egeria-project.org/types/1/0130-Projects
42
+
43
+ Attributes:
44
+
45
+ server_name: str
46
+ The name of the View Server to connect to.
47
+ platform_url : str
48
+ URL of the server platform to connect to
49
+ user_id : str
50
+ The identity of the user calling the method - this sets a default optionally used by the methods
51
+ when the user doesn't pass the user_id on a method call.
52
+ user_pwd: str
53
+ The password associated with the user_id. Defaults to None
54
+ """
55
+
56
+ def __init__(
57
+ self,
58
+ view_server: str,
59
+ platform_url: str,
60
+ user_id: str,
61
+ user_pwd: str = None,
62
+ token: str = None,
63
+ ):
64
+ self.view_server = view_server
65
+ self.platform_url = platform_url
66
+ self.user_id = user_id
67
+ self.user_pwd = user_pwd
68
+ self.project_command_base: str = (
69
+ f"/api/open-metadata/project-manager/metadata-elements"
70
+ )
71
+ Client.__init__(self, view_server, platform_url, user_id, user_pwd, token)
72
+
73
+ #
74
+ # Retrieving Projects= Information - https://egeria-project.org/concepts/project
75
+ #
76
+ async def _async_get_linked_projects(
77
+ self,
78
+ parent_guid: str,
79
+ project_status: str = None,
80
+ effective_time: str = None,
81
+ start_from: int = 0,
82
+ page_size: int = None,
83
+ ) -> list | str:
84
+ """Returns the list of projects that are linked off of the supplied element. Any relationship will do.
85
+ The request body is optional, but if supplied acts as a filter on project status. Async version.
86
+
87
+ Parameters
88
+ ----------
89
+ parent_guid: str
90
+ The identity of the parent to find linked projects from.
91
+ project_status: str, optional
92
+ Optionally, filter results by project status.
93
+ effective_time: str, optional
94
+ Time at which to query for projects. Time format is "YYYY-MM-DDTHH:MM:SS" (ISO 8601).
95
+
96
+ start_from: int, [default=0], optional
97
+ When multiple pages of results are available, the page number to start from.
98
+ page_size: int, [default=None]
99
+ The number of items to return in a single page. If not specified, the default will be taken from
100
+ the class instance.
101
+ Returns
102
+ -------
103
+ List | str
104
+
105
+ A list of projects linked off of the supplied element filtered by project status and effective time.
106
+
107
+ Raises
108
+ ------
109
+
110
+ InvalidParameterException
111
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
112
+ PropertyServerException
113
+ Raised by the server when an issue arises in processing a valid request
114
+ NotAuthorizedException
115
+ The principle specified by the user_id does not have authorization for the requested action
116
+
117
+ """
118
+
119
+ if page_size is None:
120
+ page_size = self.page_size
121
+
122
+ body = {
123
+ "filter": project_status,
124
+ "effectiveTime": effective_time,
125
+ }
126
+ body_s = body_slimmer(body)
127
+ url = (
128
+ f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/project-manager/"
129
+ f"metadata-elements/{parent_guid}/projects?startFrom={start_from}&pageSize={page_size}"
130
+ )
131
+
132
+ resp = await self._async_make_request("POST", url, body_s)
133
+ return resp.json().get("elements", "No linked projects found")
134
+
135
+ def get_linked_projects(
136
+ self,
137
+ parent_guid: str,
138
+ project_status: str = None,
139
+ effective_time: str = None,
140
+ start_from: int = 0,
141
+ page_size: int = None,
142
+ ) -> list | str:
143
+ """Returns the list of projects that are linked off of the supplied element. Any relationship will do.
144
+ The request body is optional, but if supplied acts as a filter on project status.
145
+
146
+ Parameters
147
+ ----------
148
+ parent_guid: str
149
+ The identity of the parent to find linked projects from
150
+ project_status: str, optional
151
+ Optionally, filter results by project status.
152
+ effective_time: str, optional
153
+ Time at which to query for projects. Time format is "YYYY-MM-DDTHH:MM:SS" (ISO 8601).
154
+
155
+ start_from: int, [default=0], optional
156
+ When multiple pages of results are available, the page number to start from.
157
+ page_size: int, [default=None]
158
+ The number of items to return in a single page. If not specified, the default will be taken from
159
+ the class instance.
160
+ Returns
161
+ -------
162
+ List | str
163
+
164
+ A list of projects linked off of the supplied element filtered by project status and effective time.
165
+
166
+ Raises
167
+ ------
168
+
169
+ InvalidParameterException
170
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
171
+ PropertyServerException
172
+ Raised by the server when an issue arises in processing a valid request
173
+ NotAuthorizedException
174
+ The principle specified by the user_id does not have authorization for the requested action
175
+
176
+ """
177
+ loop = asyncio.get_event_loop()
178
+ resp = loop.run_until_complete(
179
+ self._async_get_linked_projects(
180
+ parent_guid,
181
+ project_status,
182
+ effective_time,
183
+ start_from,
184
+ page_size,
185
+ )
186
+ )
187
+ return resp
188
+
189
+ async def _async_get_classified_projects(
190
+ self,
191
+ project_classification: str,
192
+ effective_time: str = None,
193
+ start_from: int = 0,
194
+ page_size: int = None,
195
+ ) -> list | str:
196
+ """Returns the list of projects with a particular classification. The name of the classification is
197
+ supplied in the request body. Examples of these classifications include StudyProject, PersonalProject,
198
+ Campaign or Task. There is also GlossaryProject and GovernanceProject. Async version.
199
+
200
+ Parameters
201
+ ----------
202
+ project_classification: str
203
+ The project classification to search for.
204
+ effective_time: str, optional
205
+ Time at which to query for projects. Time format is "YYYY-MM-DDTHH:MM:SS" (ISO 8601).
206
+
207
+ start_from: int, [default=0], optional
208
+ When multiple pages of results are available, the page number to start from.
209
+ page_size: int, [default=None]
210
+ The number of items to return in a single page. If not specified, the default will be taken from
211
+ the class instance.
212
+ Returns
213
+ -------
214
+ List | str
215
+
216
+ A list of projects filtered by project classification, and effective time.
217
+
218
+ Raises
219
+ ------
220
+
221
+ InvalidParameterException
222
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
223
+ PropertyServerException
224
+ Raised by the server when an issue arises in processing a valid request
225
+ NotAuthorizedException
226
+ The principle specified by the user_id does not have authorization for the requested action
227
+
228
+ """
229
+
230
+ if page_size is None:
231
+ page_size = self.page_size
232
+
233
+ body = {
234
+ "filter": project_classification,
235
+ "effectiveTime": effective_time,
236
+ }
237
+ body_s = body_slimmer(body)
238
+ url = (
239
+ f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/project-manager/"
240
+ f"projects/by-classifications?startFrom={start_from}&pageSize={page_size}"
241
+ )
242
+
243
+ resp = await self._async_make_request("POST", url, body_s)
244
+ return resp.json()
245
+
246
+ def get_classified_projects(
247
+ self,
248
+ project_classification: str,
249
+ effective_time: str = None,
250
+ start_from: int = 0,
251
+ page_size: int = None,
252
+ ) -> list | str:
253
+ """Returns the list of projects with a particular classification. The name of the classification is
254
+ supplied in the request body. Examples of these classifications include StudyProject, PersonalProject,
255
+ Campaign or Task. There is also GlossaryProject and GovernanceProject.
256
+
257
+ Parameters
258
+ ----------
259
+ project_classification: str
260
+ The project classification to search for.
261
+ effective_time: str, optional
262
+ Time at which to query for projects. Time format is "YYYY-MM-DDTHH:MM:SS" (ISO 8601).
263
+
264
+ start_from: int, [default=0], optional
265
+ When multiple pages of results are available, the page number to start from.
266
+ page_size: int, [default=None]
267
+ The number of items to return in a single page. If not specified, the default will be taken from
268
+ the class instance.
269
+ Returns
270
+ -------
271
+ List | str
272
+
273
+ A list of projects filtered by project classification, and effective time.
274
+
275
+ Raises
276
+ ------
277
+
278
+ InvalidParameterException
279
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
280
+ PropertyServerException
281
+ Raised by the server when an issue arises in processing a valid request
282
+ NotAuthorizedException
283
+ The principle specified by the user_id does not have authorization for the requested action
284
+
285
+ """
286
+ loop = asyncio.get_event_loop()
287
+ resp = loop.run_until_complete(
288
+ self._async_get_classified_projects(
289
+ project_classification,
290
+ effective_time,
291
+ start_from,
292
+ page_size,
293
+ )
294
+ )
295
+ return resp
296
+
297
+ async def _async_get_project_team(
298
+ self,
299
+ project_guid: str,
300
+ team_role: str = None,
301
+ effective_time: str = None,
302
+ start_from: int = 0,
303
+ page_size: int = None,
304
+ ) -> list | str:
305
+ """Returns the list of actors that are linked off of the project. This includes the project managers.
306
+ The optional request body allows a teamRole to be specified as a filter. To filter out the project managers,
307
+ specify ProjectManagement as the team role. See https://egeria-project.org/concepts/project for details.
308
+ Async version.
309
+
310
+ Parameters
311
+ ----------
312
+ project_guid: str
313
+ The identity of the project to return team information about.
314
+ team_role: str, optional
315
+ team role to filter on. Project managers would be "ProjectManagement".
316
+ effective_time: str, optional
317
+ Time at which to query the team role. Time format is "YYYY-MM-DDTHH:MM:SS" (ISO 8601).
318
+
319
+ start_from: int, [default=0], optional
320
+ When multiple pages of results are available, the page number to start from.
321
+ page_size: int, [default=None]
322
+ The number of items to return in a single page. If not specified, the default will be taken from
323
+ the class instance.
324
+
325
+ Returns
326
+ -------
327
+ list | str
328
+ The list of actors linked off the project, including project managers Returns a string if none found.
329
+
330
+ Raises
331
+ ------
332
+ InvalidParameterException
333
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values.
334
+ PropertyServerException
335
+ Raised by the server when an issue arises in processing a valid request.
336
+ NotAuthorizedException
337
+ The principle specified by the user_id does not have authorization for the requested action.
338
+ Notes
339
+ -----
340
+ """
341
+
342
+ if page_size is None:
343
+ page_size = self.page_size
344
+
345
+ body = {effective_time: effective_time, "filter": team_role}
346
+ body_s = body_slimmer(body)
347
+ url = (
348
+ f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/project-manager/projects/"
349
+ f"{project_guid}/team?startFrom={start_from}&pageSize={page_size}"
350
+ )
351
+
352
+ resp = await self._async_make_request("POST", url, body_s)
353
+
354
+ result = resp.json().get("elements", NO_ELEMENTS_FOUND)
355
+ return result
356
+
357
+ def get_project_team(
358
+ self,
359
+ project_guid: str,
360
+ team_role: str = None,
361
+ effective_time: str = None,
362
+ start_from: int = 0,
363
+ page_size: int = None,
364
+ ) -> list | str:
365
+ """Returns the list of actors that are linked off of the project. This includes the project managers.
366
+ The optional request body allows a teamRole to be specified as a filter. To filter out the project managers,
367
+ specify ProjectManagement as the team role. See https://egeria-project.org/concepts/project for details.
368
+ Async version.
369
+
370
+ Parameters
371
+ ----------
372
+ project_guid: str
373
+ The identity of the project to return team information about.
374
+ team_role: str, optional
375
+ team role to filter on. Project managers would be "ProjectManagement".
376
+ effective_time: str, optional
377
+ Time at which to query the team role. Time format is "YYYY-MM-DDTHH:MM:SS" (ISO 8601).
378
+
379
+ start_from: int, [default=0], optional
380
+ When multiple pages of results are available, the page number to start from.
381
+ page_size: int, [default=None]
382
+ The number of items to return in a single page. If not specified, the default will be taken from
383
+ the class instance.
384
+
385
+ Returns
386
+ -------
387
+ list | str
388
+ The list of actors linked off the project, including project managers Returns a string if none found.
389
+
390
+ Raises
391
+ ------
392
+ InvalidParameterException
393
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values.
394
+ PropertyServerException
395
+ Raised by the server when an issue arises in processing a valid request.
396
+ NotAuthorizedException
397
+ The principle specified by the user_id does not have authorization for the requested action.
398
+ Notes
399
+ -----
400
+ """
401
+ loop = asyncio.get_event_loop()
402
+ resp = loop.run_until_complete(
403
+ self._async_get_project_team(
404
+ project_guid,
405
+ team_role,
406
+ effective_time,
407
+ start_from,
408
+ page_size,
409
+ )
410
+ )
411
+ return resp
412
+
413
+ async def _async_find_projects(
414
+ self,
415
+ search_string: str,
416
+ effective_time: str = None,
417
+ starts_with: bool = False,
418
+ ends_with: bool = False,
419
+ ignore_case: bool = False,
420
+ start_from: int = 0,
421
+ page_size: int = None,
422
+ ) -> list | str:
423
+ """Returns the list of projects matching the search string.
424
+ The search string is located in the request body and is interpreted as a plain string.
425
+ The request parameters, startsWith, endsWith and ignoreCase can be used to allow a fuzzy search.
426
+ Async version.
427
+
428
+ Parameters
429
+ ----------
430
+ search_string: str,
431
+ Search string to use to find matching projects. If the search string is '*' then all projects returned.
432
+ effective_time: str, [default=None], optional
433
+ Effective time of the query. If not specified will default to any time.
434
+
435
+ starts_with : bool, [default=False], optional
436
+ Starts with the supplied string.
437
+ ends_with : bool, [default=False], optional
438
+ Ends with the supplied string
439
+ ignore_case : bool, [default=False], optional
440
+ Ignore case when searching
441
+ start_from: int, [default=0], optional
442
+ When multiple pages of results are available, the page number to start from.
443
+ page_size: int, [default=None]
444
+ The number of items to return in a single page. If not specified, the default will be taken from
445
+ the class instance.
446
+ Returns
447
+ -------
448
+ List | str
449
+
450
+ A list of projects matching the search string. Returns a string if none found.
451
+
452
+ Raises
453
+ ------
454
+
455
+ InvalidParameterException
456
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
457
+ PropertyServerException
458
+ Raised by the server when an issue arises in processing a valid request
459
+ NotAuthorizedException
460
+ The principle specified by the user_id does not have authorization for the requested action
461
+
462
+ """
463
+
464
+ if page_size is None:
465
+ page_size = self.page_size
466
+ starts_with_s = str(starts_with).lower()
467
+ ends_with_s = str(ends_with).lower()
468
+ ignore_case_s = str(ignore_case).lower()
469
+
470
+ validate_search_string(search_string)
471
+
472
+ if search_string == "*":
473
+ search_string = None
474
+
475
+ body = {
476
+ "filter": search_string,
477
+ "effective_time": effective_time,
478
+ }
479
+ body_s = body_slimmer(body)
480
+ url = (
481
+ f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/project-manager/projects/"
482
+ f"by-search-string?startFrom={start_from}&pageSize={page_size}&startsWith={starts_with_s}&"
483
+ f"endsWith={ends_with_s}&ignoreCase={ignore_case_s}"
484
+ )
485
+
486
+ resp = await self._async_make_request("POST", url, body_s)
487
+ return resp.json().get("elements", NO_ELEMENTS_FOUND)
488
+
489
+ def find_projects(
490
+ self,
491
+ search_string: str,
492
+ effective_time: str = None,
493
+ starts_with: bool = False,
494
+ ends_with: bool = False,
495
+ ignore_case: bool = False,
496
+ start_from: int = 0,
497
+ page_size: int = None,
498
+ ) -> list | str:
499
+ """Returns the list of projects matching the search string.
500
+ The search string is located in the request body and is interpreted as a plain string.
501
+ The request parameters, startsWith, endsWith and ignoreCase can be used to allow a fuzzy search.
502
+
503
+ Parameters
504
+ ----------
505
+ search_string: str,
506
+ Search string to use to find matching projects. If the search string is '*' then all projects returned.
507
+ effective_time: str, [default=None], optional
508
+ Effective time of the query. If not specified will default to any time.
509
+
510
+ starts_with : bool, [default=False], optional
511
+ Starts with the supplied string.
512
+ ends_with : bool, [default=False], optional
513
+ Ends with the supplied string
514
+ ignore_case : bool, [default=False], optional
515
+ Ignore case when searching
516
+ start_from: int, [default=0], optional
517
+ When multiple pages of results are available, the page number to start from.
518
+ page_size: int, [default=None]
519
+ The number of items to return in a single page. If not specified, the default will be taken from
520
+ the class instance.
521
+ Returns
522
+ -------
523
+ List | str
524
+
525
+ A list of projects matching the search string. Returns a string if none found.
526
+
527
+ Raises
528
+ ------
529
+
530
+ InvalidParameterException
531
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
532
+ PropertyServerException
533
+ Raised by the server when an issue arises in processing a valid request
534
+ NotAuthorizedException
535
+ The principle specified by the user_id does not have authorization for the requested action
536
+
537
+ """
538
+ loop = asyncio.get_event_loop()
539
+ resp = loop.run_until_complete(
540
+ self._async_find_projects(
541
+ search_string,
542
+ effective_time,
543
+ starts_with,
544
+ ends_with,
545
+ ignore_case,
546
+ start_from,
547
+ page_size,
548
+ )
549
+ )
550
+
551
+ return resp
552
+
553
+ async def _async_get_projects_by_name(
554
+ self,
555
+ name: str,
556
+ effective_time: str = None,
557
+ start_from: int = 0,
558
+ page_size: int = None,
559
+ ) -> list | str:
560
+ """Returns the list of projects with a particular name. Async version.
561
+
562
+ Parameters
563
+ ----------
564
+ name: str,
565
+ name to use to find matching collections.
566
+ effective_time: str, [default=None], optional
567
+ Effective time of the query. If not specified will default to any time. ISO 8601 format.
568
+
569
+ start_from: int, [default=0], optional
570
+ When multiple pages of results are available, the page number to start from.
571
+ page_size: int, [default=None]
572
+ The number of items to return in a single page. If not specified, the default will be taken from
573
+ the class instance.
574
+ Returns
575
+ -------
576
+ List | str
577
+
578
+ A list of collections match matching the name. Returns a string if none found.
579
+
580
+ Raises
581
+ ------
582
+
583
+ InvalidParameterException
584
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
585
+ PropertyServerException
586
+ Raised by the server when an issue arises in processing a valid request
587
+ NotAuthorizedException
588
+ The principle specified by the user_id does not have authorization for the requested action
589
+
590
+ """
591
+
592
+ if page_size is None:
593
+ page_size = self.page_size
594
+
595
+ validate_search_string(name)
596
+
597
+ body = {
598
+ "filter": name,
599
+ "effective_time": effective_time,
600
+ }
601
+ body_s = body_slimmer(body)
602
+ url = (
603
+ f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/project-manager/projects/"
604
+ f"by-name?startFrom={start_from}&pageSize={page_size}"
605
+ )
606
+
607
+ resp = await self._async_make_request("POST", url, body_s)
608
+ return resp.json().get("elements", NO_PROJECTS_FOUND)
609
+
610
+ def get_projects_by_name(
611
+ self,
612
+ name: str,
613
+ effective_time: str = None,
614
+ start_from: int = 0,
615
+ page_size: int = None,
616
+ ) -> list | str:
617
+ """Returns the list of projects with a particular name.
618
+
619
+ Parameters
620
+ ----------
621
+ name: str,
622
+ name to use to find matching collections.
623
+ effective_time: str, [default=None], optional
624
+ Effective time of the query. If not specified will default to any time. ISO 8601 format.
625
+
626
+ start_from: int, [default=0], optional
627
+ When multiple pages of results are available, the page number to start from.
628
+ page_size: int, [default=None]
629
+ The number of items to return in a single page. If not specified, the default will be taken from
630
+ the class instance.
631
+ Returns
632
+ -------
633
+ List | str
634
+
635
+ A list of collections match matching the name. Returns a string if none found.
636
+
637
+ Raises
638
+ ------
639
+
640
+ InvalidParameterException
641
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
642
+ PropertyServerException
643
+ Raised by the server when an issue arises in processing a valid request
644
+ NotAuthorizedException
645
+ The principle specified by the user_id does not have authorization for the requested action
646
+
647
+ """
648
+ loop = asyncio.get_event_loop()
649
+ resp = loop.run_until_complete(
650
+ self._async_get_projects_by_name(
651
+ name, effective_time, start_from, page_size
652
+ )
653
+ )
654
+
655
+ return resp
656
+
657
+ async def _async_get_project_by_guid(
658
+ self,
659
+ project_guid: str,
660
+ effective_time: str = None,
661
+ ) -> dict | str:
662
+ """Return the properties of a specific project. Async version.
663
+
664
+ Parameters
665
+ ----------
666
+ project_guid: str,
667
+ unique identifier of the project.
668
+ effective_time: str, [default=None], optional
669
+ Effective time of the query. If not specified will default to any time. Time in ISO8601 format is assumed.
670
+
671
+
672
+ Returns
673
+ -------
674
+ dict | str
675
+
676
+ A JSON dict representing the specified project. Returns a string if none found.
677
+
678
+ Raises
679
+ ------
680
+
681
+ InvalidParameterException
682
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
683
+ PropertyServerException
684
+ Raised by the server when an issue arises in processing a valid request
685
+ NotAuthorizedException
686
+ The principle specified by the user_id does not have authorization for the requested action
687
+
688
+ """
689
+
690
+ validate_guid(project_guid)
691
+ body = {
692
+ "effective_time": effective_time,
693
+ }
694
+ url = f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/project-manager/projects/{project_guid}"
695
+
696
+ resp = await self._async_make_request("GET", url, body)
697
+ return resp.json().get('element',NO_ELEMENTS_FOUND)
698
+
699
+ def get_project_by_guid(self, project_guid: str, effective_time: str = None) -> dict | str:
700
+ """Return the properties of a specific project.
701
+
702
+ Parameters
703
+ ----------
704
+ project_guid: str,
705
+ unique identifier of the project.
706
+ effective_time: str, [default=None], optional
707
+ Effective time of the query. If not specified will default to any time. Time in ISO8601 format is assumed.
708
+
709
+
710
+ Returns
711
+ -------
712
+ dict | str
713
+
714
+ A JSON dict representing the specified project. Returns a string if none found.
715
+
716
+ Raises
717
+ ------
718
+
719
+ InvalidParameterException
720
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
721
+ PropertyServerException
722
+ Raised by the server when an issue arises in processing a valid request
723
+ NotAuthorizedException
724
+ The principle specified by the user_id does not have authorization for the requested action
725
+
726
+ """
727
+ loop = asyncio.get_event_loop()
728
+ resp = loop.run_until_complete(
729
+ self._async_get_project_by_guid(project_guid, effective_time)
730
+ )
731
+
732
+ return resp
733
+
734
+ async def _async_get_project_graph(
735
+ self,
736
+ project_guid: str,
737
+ effective_time: str = None,
738
+ ) -> dict | str:
739
+ """Return the mermaid graph of a specific project. Async version.
740
+
741
+ Parameters
742
+ ----------
743
+ project_guid: str,
744
+ unique identifier of the project.
745
+ effective_time: str, [default=None], optional
746
+ Effective time of the query. If not specified will default to any time. Time in ISO8601 format is assumed.
747
+
748
+
749
+ Returns
750
+ -------
751
+ str
752
+
753
+ A mermaid markdown string representing the graph of the project.
754
+ Raises
755
+ ------
756
+
757
+ InvalidParameterException
758
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
759
+ PropertyServerException
760
+ Raised by the server when an issue arises in processing a valid request
761
+ NotAuthorizedException
762
+ The principle specified by the user_id does not have authorization for the requested action
763
+
764
+ """
765
+
766
+ validate_guid(project_guid)
767
+ body = {
768
+ "effective_time": effective_time,
769
+ }
770
+ url = f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/project-manager/projects/{project_guid}/graph"
771
+
772
+ resp = await self._async_make_request("GET", url, body)
773
+ return resp.json().get('element',NO_ELEMENTS_FOUND)
774
+
775
+ def get_project_graph(self, project_guid: str, effective_time: str = None) -> dict | str:
776
+ """Return the mermaid graph of a specific project.
777
+
778
+ Parameters
779
+ ----------
780
+ project_guid: str,
781
+ unique identifier of the project.
782
+ effective_time: str, [default=None], optional
783
+ Effective time of the query. If not specified will default to any time. Time in ISO8601 format is assumed.
784
+
785
+
786
+ Returns
787
+ -------
788
+ str
789
+
790
+ A mermaid markdown string representing the graph of the project.
791
+ Raises
792
+ ------
793
+
794
+ InvalidParameterException
795
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
796
+ PropertyServerException
797
+ Raised by the server when an issue arises in processing a valid request
798
+ NotAuthorizedException
799
+ The principle specified by the user_id does not have authorization for the requested action
800
+
801
+ """
802
+ loop = asyncio.get_event_loop()
803
+ resp = loop.run_until_complete(
804
+ self._async_get_project_graph(project_guid, effective_time)
805
+ )
806
+
807
+ return resp
808
+
809
+
810
+ #
811
+ # Create project methods
812
+ #
813
+ async def _async_create_project_w_body(
814
+ self,
815
+ body: dict,
816
+ classification: str = None,
817
+ ) -> str:
818
+ """Create project: https://egeria-project.org/concepts/project Async version.
819
+
820
+ Parameters
821
+ ----------.
822
+ body: dict
823
+ A dict representing the details of the project to create.
824
+ classification: str, optional
825
+ An optional project classification. See https://egeria-project.org/types/1/0130-Projects for values.
826
+ view_server: str, optional, defaults to None
827
+ The name of the server to configure. If not provided, the server name associated with the
828
+ instance is used.
829
+
830
+ Returns
831
+ -------
832
+ str - the guid of the created project
833
+
834
+ Raises
835
+ ------
836
+ InvalidParameterException
837
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
838
+ PropertyServerException
839
+ Raised by the server when an issue arises in processing a valid request
840
+ NotAuthorizedException
841
+ The principle specified by the user_id does not have authorization for the requested action
842
+ Notes
843
+ -----
844
+
845
+ Body structure like:
846
+ {
847
+ "anchorGUID" : "anchor GUID, if set then isOwnAnchor=false",
848
+ "isOwnAnchor" : False,
849
+ "parentGUID" : "parent GUID, if set, set all parameters beginning 'parent'",
850
+ "parentRelationshipTypeName" : "open metadata type name",
851
+ "parentAtEnd1": True,
852
+ "projectProperties": {
853
+ "class" : "ProjectProperties",
854
+ "qualifiedName": "Must provide a unique name here",
855
+ "identifier" : "Add business identifier",
856
+ "name" : "Add display name here",
857
+ "description" : "Add description of the project here",
858
+ "projectStatus": "Add appropriate valid value for type",
859
+ "projectPhase" : "Add appropriate valid value for phase",
860
+ "projectHealth" : "Add appropriate valid value for health",
861
+ "startDate" : "date/time",
862
+ "plannedEndDate" : "date/time"
863
+ }
864
+ }
865
+
866
+ """
867
+
868
+ if classification is None:
869
+ url = f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/project-manager/projects"
870
+ else:
871
+ url = (
872
+ f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/project-manager/projects?"
873
+ f"classificationName={classification}"
874
+ )
875
+ body_s = body_slimmer(body)
876
+ resp = await self._async_make_request("POST", url, body_s)
877
+ return resp.json().get("guid", "No GUID returned")
878
+
879
+ def create_project_w_body(
880
+ self,
881
+ body: dict,
882
+ classification: str = None,
883
+ ) -> str:
884
+ """Create project: https://egeria-project.org/concepts/project
885
+
886
+ Parameters
887
+ ----------.
888
+ body: dict
889
+ A dict representing the details of the project to create.
890
+ classification: str, optional
891
+ An optional project classification. See https://egeria-project.org/types/1/0130-Projects for values.
892
+ view_server: str, optional, defaults to None
893
+ The name of the server to configure. If not provided, the server name associated with the instance
894
+ is used.
895
+
896
+ Returns
897
+ -------
898
+ str - the guid of the created collection
899
+
900
+ Raises
901
+ ------
902
+ InvalidParameterException
903
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
904
+ PropertyServerException
905
+ Raised by the server when an issue arises in processing a valid request
906
+ NotAuthorizedException
907
+ The principle specified by the user_id does not have authorization for the requested action
908
+
909
+ Notes
910
+ -----
911
+ Body structure like:
912
+ {
913
+ "anchorGUID" : "anchor GUID, if set then isOwnAnchor=false",
914
+ "isOwnAnchor" : False,
915
+ "parentGUID" : "parent GUID, if set, set all parameters beginning 'parent'",
916
+ "parentRelationshipTypeName" : "open metadata type name",
917
+ "parentAtEnd1": True,
918
+ "projectProperties": {
919
+ "class" : "ProjectProperties",
920
+ "qualifiedName": "Must provide a unique name here",
921
+ "identifier" : "Add business identifier",
922
+ "name" : "Add display name here",
923
+ "description" : "Add description of the project here",
924
+ "projectStatus": "Add appropriate valid value for type",
925
+ "projectPhase" : "Add appropriate valid value for phase",
926
+ "projectHealth" : "Add appropriate valid value for health",
927
+ "startDate" : "date/time",
928
+ "plannedEndDate" : "date/time"
929
+ }
930
+ }
931
+
932
+ """
933
+ loop = asyncio.get_event_loop()
934
+ resp = loop.run_until_complete(
935
+ self._async_create_project_w_body(body, classification)
936
+ )
937
+ return resp
938
+
939
+ async def _async_create_project(
940
+ self,
941
+ anchor_guid: str,
942
+ parent_guid: str,
943
+ parent_relationship_type_name: str,
944
+ parent_at_end1: bool,
945
+ display_name: str,
946
+ description: str,
947
+ classification_name: str = None,
948
+ identifier: str = None,
949
+ is_own_anchor: bool = False,
950
+ project_status: str = None,
951
+ project_phase: str = None,
952
+ project_health: str = None,
953
+ start_date: str = None,
954
+ planned_end_date: str = None,
955
+ ) -> str:
956
+ """Create Project: https://egeria-project.org/concepts/project Async version.
957
+
958
+ Parameters
959
+ ----------
960
+ classification_name: str, optional
961
+ Type of project to create; "PersonalProject", "Campaign", etc. If not provided, project will not
962
+ be classified.
963
+ anchor_guid: str
964
+ The unique identifier of the element that should be the anchor for the new element. Set to null if no
965
+ anchor, or if this collection is to be its own anchor.
966
+ parent_guid: str
967
+ The optional unique identifier for an element that should be connected to the newly created element.
968
+ If this property is specified, parentRelationshipTypeName must also be specified
969
+ parent_relationship_type_name: str
970
+ The name of the relationship, if any, that should be established between the new element and the parent
971
+ element. Examples could be "ResourceList".
972
+ parent_at_end1: bool
973
+ Identifies which end any parent entity sits on the relationship.
974
+ display_name: str
975
+ The display name of the element. Will also be used as the basis of the qualified_name.
976
+ description: str
977
+ A description of the collection.
978
+ identifier: str
979
+ A project identifier.
980
+ is_own_anchor: bool, optional, defaults to False
981
+ Indicates if the collection should be classified as its own anchor or not.
982
+ project_status: str, optional
983
+ The project status
984
+ project_phase: str, optional
985
+ Project phase as defined in valid values
986
+ project_health: str, optional
987
+ Project health as defined in valid values
988
+ start_date: str, optional, defaults to None
989
+ Start date of the project in ISO 8601 string format.
990
+ planned_end_date: str, optional, defaults to None
991
+ Planned completion date in ISO 8601 string format.
992
+
993
+
994
+ Returns
995
+ -------
996
+ str - the guid of the created project
997
+
998
+ Raises
999
+ ------
1000
+ InvalidParameterException
1001
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
1002
+ PropertyServerException
1003
+ Raised by the server when an issue arises in processing a valid request
1004
+ NotAuthorizedException
1005
+ The principle specified by the user_id does not have authorization for the requested action
1006
+
1007
+ """
1008
+
1009
+ if parent_guid is None:
1010
+ is_own_anchor = False
1011
+
1012
+ if classification_name is None:
1013
+ url = f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/project-manager/projects"
1014
+ else:
1015
+ url = (
1016
+ f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/project-manager/projects?"
1017
+ f"classificationName={classification_name}"
1018
+ )
1019
+
1020
+ body = {
1021
+ "anchorGUID": anchor_guid,
1022
+ "isOwnAnchor": str(is_own_anchor).lower(),
1023
+ "parentGUID": parent_guid,
1024
+ "parentRelationshipTypeName": parent_relationship_type_name,
1025
+ "parentAtEnd1": str(parent_at_end1).lower(),
1026
+ "projectProperties": {
1027
+ "class": "ProjectProperties",
1028
+ "qualifiedName": f"{classification_name}-{display_name}-{time.asctime()}",
1029
+ "identifier": identifier,
1030
+ "name": display_name,
1031
+ "description": description,
1032
+ "projectStatus": project_status,
1033
+ "projectPhase": project_phase,
1034
+ "projectHealth": project_health,
1035
+ "startDate": start_date,
1036
+ "plannedEndDate": planned_end_date,
1037
+ },
1038
+ }
1039
+ body_s = body_slimmer(body)
1040
+ resp = await self._async_make_request("POST", url, body_s)
1041
+ return resp.json().get("guid", "No GUID returned")
1042
+
1043
+ def create_project(
1044
+ self,
1045
+ anchor_guid: str,
1046
+ parent_guid: str,
1047
+ parent_relationship_type_name: str,
1048
+ parent_at_end1: bool,
1049
+ display_name: str,
1050
+ description: str,
1051
+ classification_name: str,
1052
+ identifier: str = None,
1053
+ is_own_anchor: bool = False,
1054
+ project_status: str = None,
1055
+ project_phase: str = None,
1056
+ project_health: str = None,
1057
+ start_date: str = None,
1058
+ planned_end_date: str = None,
1059
+ ) -> str:
1060
+ """Create Project: https://egeria-project.org/concepts/project
1061
+
1062
+ Parameters
1063
+ ----------
1064
+ classification_name: str
1065
+ Type of project to create; "PersonalProject", "Campaign", etc. If not provided, the project will not
1066
+ have a project classification.
1067
+ anchor_guid: str
1068
+ The unique identifier of the element that should be the anchor for the new element. Set to null if no
1069
+ anchor, or if this collection is to be its own anchor.
1070
+ parent_guid: str
1071
+ The optional unique identifier for an element that should be connected to the newly created element.
1072
+ If this property is specified, parentRelationshipTypeName must also be specified
1073
+ parent_relationship_type_name: str
1074
+ The name of the relationship, if any, that should be established between the new element and the parent
1075
+ element. Examples could be "ResourceList".
1076
+ parent_at_end1: bool
1077
+ Identifies which end any parent entity sits on the relationship.
1078
+ display_name: str
1079
+ The display name of the element. Will also be used as the basis of the qualified_name.
1080
+ description: str
1081
+ A description of the collection.
1082
+ identifier: str
1083
+ A project identifier.
1084
+ is_own_anchor: bool, optional, defaults to False
1085
+ Indicates if the collection should be classified as its own anchor or not.
1086
+ project_status: str, optional
1087
+ The project status
1088
+ project_phase: str, optional
1089
+ Project phase as defined in valid values
1090
+ project_health: str, optional
1091
+ Project health as defined in valid values
1092
+ start_date: str, optional, defaults to None
1093
+ Start date of the project in ISO 8601 string format.
1094
+ planned_end_date: str, optional, defaults to None
1095
+ Planned completion date in ISO 8601 string format.
1096
+
1097
+
1098
+ Returns
1099
+ -------
1100
+ str - the guid of the created project
1101
+
1102
+ Raises
1103
+ ------
1104
+ InvalidParameterException
1105
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
1106
+ PropertyServerException
1107
+ Raised by the server when an issue arises in processing a valid request
1108
+ NotAuthorizedException
1109
+ The principle specified by the user_id does not have authorization for the requested action
1110
+
1111
+ """
1112
+ loop = asyncio.get_event_loop()
1113
+ resp = loop.run_until_complete(
1114
+ self._async_create_project(
1115
+ anchor_guid,
1116
+ parent_guid,
1117
+ parent_relationship_type_name,
1118
+ parent_at_end1,
1119
+ display_name,
1120
+ description,
1121
+ classification_name,
1122
+ identifier,
1123
+ is_own_anchor,
1124
+ project_status,
1125
+ project_phase,
1126
+ project_health,
1127
+ start_date,
1128
+ planned_end_date,
1129
+ )
1130
+ )
1131
+ return resp
1132
+
1133
+ async def _async_create_project_task(
1134
+ self,
1135
+ project_guid: str,
1136
+ display_name: str,
1137
+ identifier: str = None,
1138
+ description: str = None,
1139
+ project_status: str = None,
1140
+ project_phase: str = None,
1141
+ project_health: str = None,
1142
+ start_date: str = None,
1143
+ planned_end_date: str = None,
1144
+ ) -> str:
1145
+ """Create a new project with the Task classification and link it to a project. Async version.
1146
+
1147
+ Parameters
1148
+ ----------
1149
+ project_guid: str
1150
+ The unique identifier of the project to create the task for (the parent).
1151
+ display_name: str
1152
+ The display name of the element. Will also be used as the basis of the qualified_name.
1153
+ identifier: str
1154
+ A project identifier.
1155
+ description: str
1156
+ A description of the collection.
1157
+ project_status: str, optional, defaults to "OTHER"
1158
+ The project status
1159
+ project_phase: str, optional
1160
+ Project phase as defined in valid values
1161
+ project_health: str, optional
1162
+ Project health as defined in valid values
1163
+ start_date: str, optional, defaults to None
1164
+ Start date of the project in ISO 8601 string format.
1165
+ planned_end_date: str, optional, defaults to None
1166
+ Planned completion date in ISO 8601 string format.
1167
+
1168
+ Returns
1169
+ -------
1170
+ str - the guid of the created project task
1171
+
1172
+ Raises
1173
+ ------
1174
+ InvalidParameterException
1175
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
1176
+ PropertyServerException
1177
+ Raised by the server when an issue arises in processing a valid request
1178
+ NotAuthorizedException
1179
+ The principle specified by the user_id does not have authorization for the requested action
1180
+
1181
+ """
1182
+
1183
+ url = (
1184
+ f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/project-manager/projects/"
1185
+ f"{project_guid}/task"
1186
+ )
1187
+
1188
+ body = {
1189
+ "class": "ProjectProperties",
1190
+ "qualifiedName": f"task-{display_name}-{time.asctime()}",
1191
+ "identifier": identifier,
1192
+ "name": display_name,
1193
+ "description": description,
1194
+ "projectStatus": project_status,
1195
+ "projectPhase": project_phase,
1196
+ "projectHealth": project_health,
1197
+ "startDate": start_date,
1198
+ "plannedEndDate": planned_end_date,
1199
+ }
1200
+ body_s = body_slimmer(body)
1201
+ resp = await self._async_make_request("POST", url, body_s)
1202
+ return resp.json().get("guid", "No GUID Returned")
1203
+
1204
+ def create_project_task(
1205
+ self,
1206
+ project_guid: str,
1207
+ display_name: str,
1208
+ identifier: str = None,
1209
+ description: str = None,
1210
+ project_status: str = None,
1211
+ project_phase: str = None,
1212
+ project_health: str = None,
1213
+ start_date: str = None,
1214
+ planned_end_date: str = None,
1215
+ ) -> str:
1216
+ """Create a new project with the Task classification and link it to a project.
1217
+
1218
+ Parameters
1219
+ ----------
1220
+ project_guid: str
1221
+ The unique identifier of the project to create the task for.The parent.
1222
+ display_name: str
1223
+ The display name of the element. Will also be used as the basis of the qualified_name.
1224
+ identifier: str
1225
+ A project identifier.
1226
+ description: str
1227
+ A description of the collection.
1228
+ project_status: str, optional, defaults to "OTHER"
1229
+ The project status
1230
+ project_phase: str, optional
1231
+ Project phase as defined in valid values
1232
+ project_health: str, optional
1233
+ Project health as defined in valid values
1234
+ start_date: str, optional, defaults to None
1235
+ Start date of the project in ISO 8601 string format.
1236
+ planned_end_date: str, optional, defaults to None
1237
+ Planned completion date in ISO 8601 string format.
1238
+
1239
+ Returns
1240
+ -------
1241
+ str - the guid of the created project task
1242
+
1243
+ Raises
1244
+ ------
1245
+ InvalidParameterException
1246
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
1247
+ PropertyServerException
1248
+ Raised by the server when an issue arises in processing a valid request
1249
+ NotAuthorizedException
1250
+ The principle specified by the user_id does not have authorization for the requested action
1251
+
1252
+ """
1253
+ loop = asyncio.get_event_loop()
1254
+ resp = loop.run_until_complete(
1255
+ self._async_create_project_task(
1256
+ project_guid,
1257
+ display_name,
1258
+ identifier,
1259
+ description,
1260
+ project_status,
1261
+ project_phase,
1262
+ project_health,
1263
+ start_date,
1264
+ planned_end_date,
1265
+ )
1266
+ )
1267
+ return resp
1268
+
1269
+ async def _async_create_project_from_template(
1270
+ self,
1271
+ body: dict,
1272
+ ) -> str:
1273
+ """Create a new metadata element to represent a project using an existing metadata element as a template.
1274
+ The template defines additional classifications and relationships that should be added to the new project.
1275
+ Async version.
1276
+
1277
+ Parameters
1278
+ ----------
1279
+
1280
+ body: dict
1281
+ A dict representing the details of the collection to create.
1282
+
1283
+
1284
+ Returns
1285
+ -------
1286
+ str - the guid of the created project.
1287
+
1288
+ Raises
1289
+ ------
1290
+ InvalidParameterException
1291
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
1292
+ PropertyServerException
1293
+ Raised by the server when an issue arises in processing a valid request
1294
+ NotAuthorizedException
1295
+ The principle specified by the user_id does not have authorization for the requested action
1296
+
1297
+ Notes
1298
+ -----
1299
+ JSON Structure looks like:
1300
+ {
1301
+ "class": "TemplateRequestBody",
1302
+ "anchorGUID": "anchor GUID, if set then isOwnAnchor=false",
1303
+ "isOwnAnchor": false,
1304
+ "parentGUID": "parent GUID, if set, set all parameters beginning 'parent'",
1305
+ "parentRelationshipTypeName": "open metadata type name",
1306
+ "parentAtEnd1": true,
1307
+ "templateGUID": "template GUID",
1308
+ "replacementProperties": {
1309
+ "class": "ElementProperties",
1310
+ "propertyValueMap" : {
1311
+ "propertyName" : {
1312
+ "class": "PrimitiveTypePropertyValue",
1313
+ "typeName": "string",
1314
+ "primitiveTypeCategory" : "OM_PRIMITIVE_TYPE_STRING",
1315
+ "primitiveValue" : "value of property"
1316
+ }
1317
+ }
1318
+ },
1319
+ "placeholderPropertyValues" : {
1320
+ "placeholderProperty1Name" : "property1Value",
1321
+ "placeholderProperty2Name" : "property2Value"
1322
+ }
1323
+ }
1324
+
1325
+
1326
+ """
1327
+
1328
+ url = f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/project-manager/projects/from-template"
1329
+ body_s = body_slimmer(body)
1330
+ resp = await self._async_make_request("POST", url, body_s)
1331
+ return resp.json().get("guid", "No GUID Returned")
1332
+
1333
+ def create_project_from_template(
1334
+ self,
1335
+ body: dict,
1336
+ ) -> str:
1337
+ """Create a new metadata element to represent a project using an existing metadata element as a template.
1338
+ The template defines additional classifications and relationships that should be added to the new project.
1339
+
1340
+ Parameters
1341
+ ----------
1342
+
1343
+ body: dict
1344
+ A dict representing the details of the collection to create.
1345
+
1346
+
1347
+ Returns
1348
+ -------
1349
+ str - the guid of the created project.
1350
+
1351
+ Raises
1352
+ ------
1353
+ InvalidParameterException
1354
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
1355
+ PropertyServerException
1356
+ Raised by the server when an issue arises in processing a valid request
1357
+ NotAuthorizedException
1358
+ The principle specified by the user_id does not have authorization for the requested action
1359
+
1360
+ Notes
1361
+ -----
1362
+ JSON Structure looks like:
1363
+ {
1364
+ "class": "TemplateRequestBody",
1365
+ "anchorGUID": "anchor GUID, if set then isOwnAnchor=false",
1366
+ "isOwnAnchor": false,
1367
+ "parentGUID": "parent GUID, if set, set all parameters beginning 'parent'",
1368
+ "parentRelationshipTypeName": "open metadata type name",
1369
+ "parentAtEnd1": true,
1370
+ "templateGUID": "template GUID",
1371
+ "replacementProperties": {
1372
+ "class": "ElementProperties",
1373
+ "propertyValueMap" : {
1374
+ "propertyName" : {
1375
+ "class": "PrimitiveTypePropertyValue",
1376
+ "typeName": "string",
1377
+ "primitiveTypeCategory" : "OM_PRIMITIVE_TYPE_STRING",
1378
+ "primitiveValue" : "value of property"
1379
+ }
1380
+ }
1381
+ },
1382
+ "placeholderPropertyValues" : {
1383
+ "placeholderProperty1Name" : "property1Value",
1384
+ "placeholderProperty2Name" : "property2Value"
1385
+ }
1386
+ }
1387
+ """
1388
+ loop = asyncio.get_event_loop()
1389
+ resp = loop.run_until_complete(self._async_create_project_from_template(body))
1390
+ return resp
1391
+
1392
+ async def _async_update_project(
1393
+ self,
1394
+ project_guid: str,
1395
+ qualified_name: str = None,
1396
+ identifier: str = None,
1397
+ display_name: str = None,
1398
+ description: str = None,
1399
+ project_status: str = None,
1400
+ project_phase: str = None,
1401
+ project_health: str = None,
1402
+ start_date: str = None,
1403
+ planned_end_date: str = None,
1404
+ replace_all_props: bool = False,
1405
+ ) -> None:
1406
+ """Update the properties of a project. Async Version.
1407
+
1408
+ Parameters
1409
+ ----------
1410
+ project_guid: str
1411
+ Unique identifier for the project.
1412
+ qualified_name: str, optional, defaults to None
1413
+ The unique identifier of the project.
1414
+ identifier: str
1415
+ A project identifier.
1416
+ display_name: str
1417
+ The display name of the element. Will also be used as the basis of the qualified_name.
1418
+ description: str
1419
+ A description of the collection.
1420
+ project_status: str, optional
1421
+ The project status
1422
+ project_phase: str, optional
1423
+ Project phase as defined in valid values
1424
+ project_health: str, optional
1425
+ Project health as defined in valid values
1426
+ start_date: str, optional, defaults to None
1427
+ Start date of the project in ISO 8601 string format.
1428
+ planned_end_date: str, optional, defaults to None
1429
+ Planned completion date in ISO 8601 string format.
1430
+ replace_all_props: bool, optional, defaults to False
1431
+ If True, then all the properties of the project will be replaced with the specified properties.
1432
+
1433
+ Returns
1434
+ -------
1435
+ str - the guid of the created project task
1436
+
1437
+ Raises
1438
+ ------
1439
+ InvalidParameterException
1440
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
1441
+ PropertyServerException
1442
+ Raised by the server when an issue arises in processing a valid request
1443
+ NotAuthorizedException
1444
+ The principle specified by the user_id does not have authorization for the requested action
1445
+ """
1446
+
1447
+ replace_all_props_s = str(replace_all_props).lower()
1448
+ url = (
1449
+ f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/project-manager/projects/{project_guid}/"
1450
+ f"update?replaceAllProperties={replace_all_props_s}"
1451
+ )
1452
+
1453
+ body = {
1454
+ "class": "ProjectProperties",
1455
+ "qualifiedName": qualified_name,
1456
+ "identifier": identifier,
1457
+ "name": display_name,
1458
+ "description": description,
1459
+ "projectStatus": project_status,
1460
+ "projectPhase": project_phase,
1461
+ "projectHealth": project_health,
1462
+ "startDate": start_date,
1463
+ "plannedEndDate": planned_end_date,
1464
+ }
1465
+ body_s = body_slimmer(body)
1466
+ await self._async_make_request("POST", url, body_s)
1467
+ return
1468
+
1469
+ def update_project(
1470
+ self,
1471
+ project_guid: str,
1472
+ qualified_name: str = None,
1473
+ identifier: str = None,
1474
+ display_name: str = None,
1475
+ description: str = None,
1476
+ project_status: str = None,
1477
+ project_phase: str = None,
1478
+ project_health: str = None,
1479
+ start_date: str = None,
1480
+ planned_end_date: str = None,
1481
+ replace_all_props: bool = False,
1482
+ ) -> None:
1483
+ """Update the properties of a project.
1484
+
1485
+ Parameters
1486
+ ----------
1487
+ project_guid: str
1488
+ Unique identifier for the project.
1489
+ qualified_name: str, optional, defaults to None
1490
+ The unique identifier of the project.
1491
+ identifier: str
1492
+ A project identifier.
1493
+ display_name: str
1494
+ The display name of the element. Will also be used as the basis of the qualified_name.
1495
+ description: str
1496
+ A description of the collection.
1497
+ project_status: str, optional
1498
+ The project status
1499
+ project_phase: str, optional
1500
+ Project phase as defined in valid values
1501
+ project_health: str, optional
1502
+ Project health as defined in valid values
1503
+ start_date: str, optional, defaults to None
1504
+ Start date of the project in ISO 8601 string format.
1505
+ planned_end_date: str, optional, defaults to None
1506
+ Planned completion date in ISO 8601 string format.
1507
+ replace_all_props: bool, optional, defaults to False
1508
+ If True, then all the properties of the project will be replaced with the specified properties.
1509
+
1510
+ Returns
1511
+ -------
1512
+ str - the guid of the created project task
1513
+
1514
+ Raises
1515
+ ------
1516
+ InvalidParameterException
1517
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
1518
+ PropertyServerException
1519
+ Raised by the server when an issue arises in processing a valid request
1520
+ NotAuthorizedException
1521
+ The principle specified by the user_id does not have authorization for the requested action
1522
+ """
1523
+ loop = asyncio.get_event_loop()
1524
+ loop.run_until_complete(
1525
+ self._async_update_project(
1526
+ project_guid,
1527
+ qualified_name,
1528
+ identifier,
1529
+ display_name,
1530
+ description,
1531
+ project_status,
1532
+ project_phase,
1533
+ project_health,
1534
+ start_date,
1535
+ planned_end_date,
1536
+ replace_all_props,
1537
+ )
1538
+ )
1539
+ return
1540
+
1541
+ async def _async_delete_project(
1542
+ self,
1543
+ project_guid: str, cascade: bool = False
1544
+ ) -> None:
1545
+ """Delete a project. It is detected from all parent elements. Async version
1546
+
1547
+ Parameters
1548
+ ----------
1549
+ project_guid: str
1550
+ The guid of the project to update.
1551
+ cascade: bool, optional, defaults to False
1552
+ If true, then all anchored elements will be deleted.
1553
+
1554
+ Returns
1555
+ -------
1556
+ Nothing
1557
+
1558
+ Raises
1559
+ ------
1560
+ InvalidParameterException
1561
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
1562
+ PropertyServerException
1563
+ Raised by the server when an issue arises in processing a valid request
1564
+ NotAuthorizedException
1565
+ The principle specified by the user_id does not have authorization for the requested action
1566
+
1567
+ """
1568
+ cascade_s = str(cascade).lower()
1569
+ url = (
1570
+ f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/project-manager/projects/"
1571
+ f"{project_guid}/delete?cascadedDelete={cascade_s}"
1572
+ )
1573
+
1574
+ body = {"class": "NullRequestBody"}
1575
+
1576
+ await self._async_make_request("POST", url, body)
1577
+ return
1578
+
1579
+ def delete_project(
1580
+ self,
1581
+ project_guid: str, cascade: bool = False
1582
+ ) -> None:
1583
+ """Delete a project. It is detected from all parent elements.
1584
+
1585
+ Parameters
1586
+ ----------
1587
+ project_guid: str
1588
+ The guid of the collection to update.
1589
+ cascade: bool, optional, defaults to False
1590
+ If true, then all anchored elements will be deleted.
1591
+
1592
+
1593
+ cascade: bool, optional, defaults to False
1594
+ If true, then all anchored elements will be deleted.
1595
+ Returns
1596
+ -------
1597
+ Nothing
1598
+
1599
+ Raises
1600
+ ------
1601
+
1602
+ InvalidParameterException
1603
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
1604
+ PropertyServerException
1605
+ Raised by the server when an issue arises in processing a valid request
1606
+ NotAuthorizedException
1607
+ The principle specified by the user_id does not have authorization for the requested action
1608
+
1609
+ """
1610
+ loop = asyncio.get_event_loop()
1611
+ loop.run_until_complete(self._async_delete_project(project_guid, cascade))
1612
+ return
1613
+
1614
+ async def _async_add_to_project_team(
1615
+ self,
1616
+ project_guid: str,
1617
+ actor_guid: str,
1618
+ team_role: str = None,
1619
+ effective_from: str = None,
1620
+ effective_to: str = None,
1621
+ ) -> None:
1622
+ """Add an actor to a project. The request body is optional. If supplied, it contains the name of the role that
1623
+ the actor plays in the project. Async version.
1624
+
1625
+ Parameters
1626
+ ----------
1627
+ project_guid: str
1628
+ identity of the project to update.
1629
+ actor_guid: str
1630
+ identity of the actor to add.
1631
+ team_role: str, optional, defaults to None
1632
+ Name of the role the actor plays in the project.
1633
+ effective_from: str, optional, defaults to None
1634
+ Date at which the actor becomes active in the project. Date format is ISO 8601 string format.
1635
+ effective_to: str, optional, defaults to None
1636
+ Date at which the actor is no longer active in the project. Date format is ISO 8601 string format.
1637
+
1638
+ Returns
1639
+ -------
1640
+ None
1641
+
1642
+ Raises
1643
+ ------
1644
+
1645
+ InvalidParameterException
1646
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
1647
+ PropertyServerException
1648
+ Raised by the server when an issue arises in processing a valid request
1649
+ NotAuthorizedException
1650
+ The principle specified by the user_id does not have authorization for the requested action
1651
+
1652
+ """
1653
+
1654
+ url = (
1655
+ f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/project-manager/projects/{project_guid}/"
1656
+ f"members/{actor_guid}/attach"
1657
+ )
1658
+ body = {
1659
+ "class": "ProjectTeamProperties",
1660
+ "teamRole": team_role,
1661
+ "effectiveFrom": effective_from,
1662
+ "effectiveTo": effective_to,
1663
+ }
1664
+ body_s = body_slimmer(body)
1665
+ if body_s is None:
1666
+ await self._async_make_request("POST", url)
1667
+ else:
1668
+ await self._async_make_request("POST", url, body_s)
1669
+ return
1670
+
1671
+ def add_to_project_team(
1672
+ self,
1673
+ project_guid: str,
1674
+ actor_guid: str,
1675
+ team_role: str = None,
1676
+ effective_from: str = None,
1677
+ effective_to: str = None,
1678
+ ) -> None:
1679
+ """Add an actor to a project. The request body is optional. If supplied, it contains the name of the role that
1680
+ the actor plays in the project.
1681
+
1682
+ Parameters
1683
+ ----------
1684
+ project_guid: str
1685
+ identity of the project to update.
1686
+ actor_guid: str
1687
+ identity of the actor to add.
1688
+ team_role: str, optional, defaults to None
1689
+ Name of the role the actor plays in the project.
1690
+ effective_from: str, optional, defaults to None
1691
+ Date at which the actor becomes active in the project. Date format is ISO 8601 string format.
1692
+ effective_to: str, optional, defaults to None
1693
+ Date at which the actor is no longer active in the project. Date format is ISO 8601 string format.
1694
+
1695
+ Returns
1696
+ -------
1697
+ None
1698
+
1699
+ Raises
1700
+ ------
1701
+
1702
+ InvalidParameterException
1703
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
1704
+ PropertyServerException
1705
+ Raised by the server when an issue arises in processing a valid request
1706
+ NotAuthorizedException
1707
+ The principle specified by the user_id does not have authorization for the requested action
1708
+
1709
+ """
1710
+ loop = asyncio.get_event_loop()
1711
+ loop.run_until_complete(
1712
+ self._async_add_to_project_team(
1713
+ project_guid,
1714
+ actor_guid,
1715
+ team_role,
1716
+ effective_from,
1717
+ effective_to,
1718
+ )
1719
+ )
1720
+ return
1721
+
1722
+ async def _async_remove_from_project_team(
1723
+ self,
1724
+ project_guid: str,
1725
+ actor_guid: str,
1726
+ ) -> None:
1727
+ """Remove an actor from a project. Async version.
1728
+
1729
+ Parameters
1730
+ ----------
1731
+ project_guid: str
1732
+ identity of the project to remove members from.
1733
+ actor_guid: str
1734
+ identity of the actor to remove.
1735
+
1736
+ Returns
1737
+ -------
1738
+ None
1739
+
1740
+ Raises
1741
+ ------
1742
+
1743
+ InvalidParameterException
1744
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
1745
+ PropertyServerException
1746
+ Raised by the server when an issue arises in processing a valid request
1747
+ NotAuthorizedException
1748
+ The principle specified by the user_id does not have authorization for the requested action
1749
+
1750
+ """
1751
+
1752
+ url = (
1753
+ f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/project-manager/projects/{project_guid}/"
1754
+ f"members/{actor_guid}/detach"
1755
+ )
1756
+
1757
+ body = {"class": "NullRequestBody"}
1758
+ await self._async_make_request("POST", url, body)
1759
+ return
1760
+
1761
+ def remove_from_project_team(
1762
+ self,
1763
+ project_guid: str,
1764
+ actor_guid: str,
1765
+ ) -> None:
1766
+ """Remove an actor from a project.
1767
+
1768
+ Parameters
1769
+ ----------
1770
+ project_guid: str
1771
+ identity of the project.
1772
+ actor_guid: str
1773
+ identity of the actor to remove.
1774
+
1775
+ Returns
1776
+ -------
1777
+ None
1778
+
1779
+ Raises
1780
+ ------
1781
+
1782
+ InvalidParameterException
1783
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
1784
+ PropertyServerException
1785
+ Raised by the server when an issue arises in processing a valid request
1786
+ NotAuthorizedException
1787
+ The principle specified by the user_id does not have authorization for the requested action
1788
+
1789
+ """
1790
+ loop = asyncio.get_event_loop()
1791
+ loop.run_until_complete(
1792
+ self._async_remove_from_project_team(project_guid, actor_guid)
1793
+ )
1794
+ return
1795
+
1796
+ async def _async_setup_project_management_role(
1797
+ self,
1798
+ project_guid: str,
1799
+ project_role_guid: str,
1800
+ ) -> None:
1801
+ """Create a ProjectManagement relationship between a project and a person role to show that anyone appointed to
1802
+ the role is a member of the project. Async version.
1803
+
1804
+ Parameters
1805
+ ----------
1806
+ project_guid: str
1807
+ identity of the project.
1808
+ project_role_guid: str
1809
+ guid of the role to assign to the project.
1810
+
1811
+
1812
+ Returns
1813
+ -------
1814
+ None
1815
+
1816
+ Raises
1817
+ ------
1818
+
1819
+ InvalidParameterException
1820
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
1821
+ PropertyServerException
1822
+ Raised by the server when an issue arises in processing a valid request
1823
+ NotAuthorizedException
1824
+ The principle specified by the user_id does not have authorization for the requested action
1825
+
1826
+ """
1827
+
1828
+ url = (
1829
+ f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/project-manager/projects/{project_guid}/"
1830
+ f"project-management-roles/{project_role_guid}/attach"
1831
+ )
1832
+
1833
+ body = {"class": "NullRequestBody"}
1834
+ await self._async_make_request("POST", url, body)
1835
+ return
1836
+
1837
+ def setup_project_management_role(
1838
+ self,
1839
+ project_guid: str,
1840
+ project_role_guid: str,
1841
+ ) -> None:
1842
+ """Create a ProjectManagement relationship between a project and a person role to show that anyone appointed to
1843
+ the role is a member of the project. Async version.
1844
+
1845
+ Parameters
1846
+ ----------
1847
+ project_guid: str
1848
+ identity of the project.
1849
+ project_role_guid: str
1850
+ guid of the role to assign to the project.
1851
+
1852
+
1853
+ Returns
1854
+ -------
1855
+ None
1856
+
1857
+ Raises
1858
+ ------
1859
+
1860
+ InvalidParameterException
1861
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
1862
+ PropertyServerException
1863
+ Raised by the server when an issue arises in processing a valid request
1864
+ NotAuthorizedException
1865
+ The principle specified by the user_id does not have authorization for the requested action
1866
+
1867
+ """
1868
+ loop = asyncio.get_event_loop()
1869
+ loop.run_until_complete(
1870
+ self._async_setup_project_management_role(project_guid, project_role_guid)
1871
+ )
1872
+ return
1873
+
1874
+ async def _async_clear_project_management_role(
1875
+ self,
1876
+ project_guid: str,
1877
+ project_role_guid: str,
1878
+ ) -> None:
1879
+ """Remove a ProjectManagement relationship between a project and a person role. Async version.
1880
+
1881
+ Parameters
1882
+ ----------
1883
+ project_guid: str
1884
+ identity of the project.
1885
+ project_role_guid: str
1886
+ guid of the role to assign to the project.
1887
+
1888
+
1889
+ Returns
1890
+ -------
1891
+ None
1892
+
1893
+ Raises
1894
+ ------
1895
+
1896
+ InvalidParameterException
1897
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
1898
+ PropertyServerException
1899
+ Raised by the server when an issue arises in processing a valid request
1900
+ NotAuthorizedException
1901
+ The principle specified by the user_id does not have authorization for the requested action
1902
+
1903
+ """
1904
+
1905
+ url = (
1906
+ f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/project-manager/projects/{project_guid}/"
1907
+ f"project-management-roles/{project_role_guid}/detach"
1908
+ )
1909
+
1910
+ body = {"class": "NullRequestBody"}
1911
+ await self._async_make_request("POST", url, body)
1912
+ return
1913
+
1914
+ def clear_project_management_role(
1915
+ self,
1916
+ project_guid: str,
1917
+ project_role_guid: str,
1918
+ ) -> None:
1919
+ """Clear a ProjectManagement relationship between a project and a person role.
1920
+
1921
+ Parameters
1922
+ ----------
1923
+ project_guid: str
1924
+ identity of the project.
1925
+ project_role_guid: str
1926
+ guid of the role to assign to the project.
1927
+
1928
+
1929
+ Returns
1930
+ -------
1931
+ None
1932
+
1933
+ Raises
1934
+ ------
1935
+
1936
+ InvalidParameterException
1937
+ If the client passes incorrect parameters on the request - such as bad URLs or invalid values
1938
+ PropertyServerException
1939
+ Raised by the server when an issue arises in processing a valid request
1940
+ NotAuthorizedException
1941
+ The principle specified by the user_id does not have authorization for the requested action
1942
+
1943
+ """
1944
+ loop = asyncio.get_event_loop()
1945
+ loop.run_until_complete(
1946
+ self._async_clear_project_management_role(project_guid, project_role_guid)
1947
+ )
1948
+ return
1949
+
1950
+
1951
+ if __name__ == "__main__":
1952
+ print("Main-Project Manager")