pyegeria 5.4.3.3__py3-none-any.whl → 5.4.4__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.
- commands/cat/debug_log.2025-09-02_07-44-39_567276.log.zip +0 -0
- commands/cat/debug_log.2025-09-03_07-45-21_986388.log.zip +0 -0
- commands/cat/debug_log.2025-09-04_08-21-58_788009.log.zip +0 -0
- commands/cat/debug_log.2025-09-05_09-37-53_062579.log.zip +0 -0
- commands/cat/list_format_set.py +5 -3
- commands/tech/list_information_supply_chains.py +1 -1
- commands/tech/list_solution_blueprints.py +1 -1
- commands/tech/list_solution_components.py +1 -1
- commands/tech/list_solution_roles.py +1 -1
- md_processing/__init__.py +9 -5
- md_processing/data/commands.json +7182 -1401
- md_processing/data/generated_format_sets.json +4137 -0
- md_processing/data/generated_format_sets.py +51 -0
- md_processing/dr_egeria.py +20 -11
- md_processing/md_commands/data_designer_commands.py +90 -425
- md_processing/md_commands/ext_ref_commands.py +543 -0
- md_processing/md_commands/old_solution_architect_commands.py +1139 -0
- md_processing/md_commands/solution_architect_commands.py +26 -59
- md_processing/md_processing_utils/common_md_utils.py +50 -1
- md_processing/md_processing_utils/debug_log +1 -3
- md_processing/md_processing_utils/dr-egeria-help-2025-09-09T11:10:03.md +3305 -0
- md_processing/md_processing_utils/extraction_utils.py +14 -7
- md_processing/md_processing_utils/gen_format_sets.py +422 -0
- md_processing/md_processing_utils/md_processing_constants.py +20 -2
- pyegeria/__init__.py +1 -1
- pyegeria/_client_new.py +9 -7
- pyegeria/_output_formats.py +278 -3
- pyegeria/collection_manager.py +20 -59
- pyegeria/config.py +10 -1
- pyegeria/data_designer.py +166 -117
- pyegeria/egeria_client.py +1 -1
- pyegeria/egeria_tech_client.py +4 -1
- pyegeria/external_references.py +1794 -0
- pyegeria/glossary_manager.py +71 -85
- pyegeria/governance_officer.py +26 -29
- pyegeria/output_formatter.py +127 -1
- pyegeria/project_manager.py +33 -36
- pyegeria/{solution_architect_omvs.py → solution_architect.py} +733 -873
- {pyegeria-5.4.3.3.dist-info → pyegeria-5.4.4.dist-info}/METADATA +1 -1
- {pyegeria-5.4.3.3.dist-info → pyegeria-5.4.4.dist-info}/RECORD +43 -219
- commands/.DS_Store +0 -0
- commands/cat/.DS_Store +0 -0
- commands/cat/.env +0 -8
- commands/cat/debug_log.2025-08-29_07-07-27_848189.log.zip +0 -0
- commands/cat/debug_log.2025-08-30_21-15-48_528443.log.zip +0 -0
- commands/cat/debug_log.log +0 -6102
- commands/cat/logs/pyegeria.log +0 -90
- commands/cli/debug_log.log +0 -0
- commands/doc/.DS_Store +0 -0
- commands/ops/logs/pyegeria.log +0 -0
- md_processing/.DS_Store +0 -0
- md_processing/.idea/.gitignore +0 -8
- md_processing/.idea/inspectionProfiles/Project_Default.xml +0 -59
- md_processing/.idea/md_processing.iml +0 -15
- md_processing/.idea/modules.xml +0 -8
- md_processing/.idea/sonarlint/issuestore/index.pb +0 -0
- md_processing/.idea/sonarlint/securityhotspotstore/index.pb +0 -0
- md_processing/.idea/vcs.xml +0 -6
- md_processing/.idea/workspace.xml +0 -107
- md_processing/dr_egeria_inbox/Derive-Dr-Gov-Defs.md +0 -8
- md_processing/dr_egeria_inbox/Dr.Egeria Templates.md +0 -873
- md_processing/dr_egeria_inbox/arch_test.md +0 -57
- md_processing/dr_egeria_inbox/archive/dr_egeria_intro.md +0 -254
- md_processing/dr_egeria_inbox/archive/dr_egeria_intro_more_terms.md +0 -696
- md_processing/dr_egeria_inbox/archive/dr_egeria_intro_part1.md +0 -254
- md_processing/dr_egeria_inbox/archive/dr_egeria_intro_part2.md +0 -298
- md_processing/dr_egeria_inbox/archive/dr_egeria_intro_part3.md +0 -608
- md_processing/dr_egeria_inbox/archive/dr_egeria_intro_part4.md +0 -94
- md_processing/dr_egeria_inbox/archive/freddie_intro.md +0 -284
- md_processing/dr_egeria_inbox/archive/freddie_intro_orig.md +0 -275
- md_processing/dr_egeria_inbox/archive/test-term.md +0 -110
- md_processing/dr_egeria_inbox/cat_test.md +0 -100
- md_processing/dr_egeria_inbox/collections.md +0 -39
- md_processing/dr_egeria_inbox/data_designer_debug.log +0 -6
- md_processing/dr_egeria_inbox/data_designer_out.md +0 -60
- md_processing/dr_egeria_inbox/data_designer_search_test.md +0 -11
- md_processing/dr_egeria_inbox/data_field.md +0 -54
- md_processing/dr_egeria_inbox/data_spec.md +0 -77
- md_processing/dr_egeria_inbox/data_spec_test.md +0 -2340
- md_processing/dr_egeria_inbox/data_test.md +0 -179
- md_processing/dr_egeria_inbox/data_test2.md +0 -429
- md_processing/dr_egeria_inbox/data_test3.md +0 -462
- md_processing/dr_egeria_inbox/dr_egeria_data_designer_1.md +0 -124
- md_processing/dr_egeria_inbox/dr_egeria_intro_categories.md +0 -168
- md_processing/dr_egeria_inbox/dr_egeria_intro_part1.md +0 -280
- md_processing/dr_egeria_inbox/dr_egeria_intro_part2.md +0 -318
- md_processing/dr_egeria_inbox/dr_egeria_intro_part3.md +0 -1073
- md_processing/dr_egeria_inbox/dr_egeria_isc1.md +0 -44
- md_processing/dr_egeria_inbox/generated_help_report.md +0 -9
- md_processing/dr_egeria_inbox/generated_help_terms.md +0 -842
- md_processing/dr_egeria_inbox/glossary_list.md +0 -5
- md_processing/dr_egeria_inbox/glossary_search_test.md +0 -40
- md_processing/dr_egeria_inbox/glossary_test1.md +0 -378
- md_processing/dr_egeria_inbox/gov_def.md +0 -718
- md_processing/dr_egeria_inbox/gov_def2.md +0 -447
- md_processing/dr_egeria_inbox/img.png +0 -0
- md_processing/dr_egeria_inbox/output_tests.md +0 -114
- md_processing/dr_egeria_inbox/product.md +0 -211
- md_processing/dr_egeria_inbox/rel.md +0 -8
- md_processing/dr_egeria_inbox/sb.md +0 -119
- md_processing/dr_egeria_inbox/solution-components.md +0 -136
- md_processing/dr_egeria_inbox/solution_blueprints.md +0 -118
- md_processing/dr_egeria_inbox/synonym_test.md +0 -42
- md_processing/dr_egeria_inbox/t2.md +0 -268
- md_processing/dr_egeria_outbox/.DS_Store +0 -0
- md_processing/dr_egeria_outbox/.obsidian/app.json +0 -1
- md_processing/dr_egeria_outbox/.obsidian/appearance.json +0 -1
- md_processing/dr_egeria_outbox/.obsidian/community-plugins.json +0 -7
- md_processing/dr_egeria_outbox/.obsidian/core-plugins.json +0 -33
- md_processing/dr_egeria_outbox/.obsidian/plugins/buttons/main.js +0 -5164
- md_processing/dr_egeria_outbox/.obsidian/plugins/buttons/manifest.json +0 -10
- md_processing/dr_egeria_outbox/.obsidian/plugins/buttons/styles.css +0 -624
- md_processing/dr_egeria_outbox/.obsidian/plugins/calendar/data.json +0 -10
- md_processing/dr_egeria_outbox/.obsidian/plugins/calendar/main.js +0 -4459
- md_processing/dr_egeria_outbox/.obsidian/plugins/calendar/manifest.json +0 -10
- md_processing/dr_egeria_outbox/.obsidian/plugins/obsidian-kanban/data.json +0 -3
- md_processing/dr_egeria_outbox/.obsidian/plugins/obsidian-kanban/main.js +0 -153
- md_processing/dr_egeria_outbox/.obsidian/plugins/obsidian-kanban/manifest.json +0 -11
- md_processing/dr_egeria_outbox/.obsidian/plugins/obsidian-kanban/styles.css +0 -1
- md_processing/dr_egeria_outbox/.obsidian/plugins/obsidian-tasks-plugin/main.js +0 -500
- md_processing/dr_egeria_outbox/.obsidian/plugins/obsidian-tasks-plugin/manifest.json +0 -12
- md_processing/dr_egeria_outbox/.obsidian/plugins/obsidian-tasks-plugin/styles.css +0 -1
- md_processing/dr_egeria_outbox/.obsidian/plugins/templater-obsidian/data.json +0 -38
- md_processing/dr_egeria_outbox/.obsidian/plugins/templater-obsidian/main.js +0 -37
- md_processing/dr_egeria_outbox/.obsidian/plugins/templater-obsidian/manifest.json +0 -11
- md_processing/dr_egeria_outbox/.obsidian/plugins/templater-obsidian/styles.css +0 -220
- md_processing/dr_egeria_outbox/.obsidian/types.json +0 -28
- md_processing/dr_egeria_outbox/.obsidian/workspace.json +0 -270
- md_processing/dr_egeria_outbox/Button Test.md +0 -11
- md_processing/dr_egeria_outbox/Scripts/.DS_Store +0 -0
- md_processing/dr_egeria_outbox/Scripts/sendRest.js +0 -24
- md_processing/dr_egeria_outbox/Templates/sendToApi.md.md +0 -17
- md_processing/dr_egeria_outbox/Untitled.canvas +0 -1
- md_processing/dr_egeria_outbox/monday/processed-2025-09-01 09:26-product.md +0 -210
- md_processing/dr_egeria_outbox/monday/processed-2025-09-01 14:03-product.md +0 -209
- md_processing/dr_egeria_outbox/monday/processed-2025-09-01 14:24-product.md +0 -263
- md_processing/dr_egeria_outbox/monday/processed-2025-09-01 16:03-data_spec_test.md +0 -2374
- md_processing/dr_egeria_outbox/monday/processed-2025-09-01 16:05-data_spec_test.md +0 -2374
- md_processing/dr_egeria_outbox/monday/processed-2025-09-02 08:28-data_spec_test.md +0 -2321
- md_processing/dr_egeria_outbox/monday/processed-2025-09-02 08:37-data_spec_test.md +0 -2304
- md_processing/dr_egeria_outbox/monday/processed-2025-09-02 08:56-data_spec_test.md +0 -2324
- md_processing/dr_egeria_outbox/monday/processed-2025-09-02 09:00-data_spec_test.md +0 -2324
- md_processing/dr_egeria_outbox/processed-2025-08-30 16:56-generated_help_terms.md +0 -795
- md_processing/dr_egeria_outbox/thursday/processed-2025-07-17 15:00-Derive-Dr-Gov-Defs.md +0 -719
- md_processing/dr_egeria_outbox/thursday/processed-2025-07-17 20:13-Derive-Dr-Gov-Defs.md +0 -41
- md_processing/dr_egeria_outbox/thursday/processed-2025-07-17 20:14-Derive-Dr-Gov-Defs.md +0 -33
- md_processing/dr_egeria_outbox/thursday/processed-2025-07-17 20:50-Derive-Dr-Gov-Defs.md +0 -192
- md_processing/dr_egeria_outbox/thursday/processed-2025-07-17 22:08-gov_def2.md +0 -486
- md_processing/dr_egeria_outbox/thursday/processed-2025-07-17 22:10-gov_def2.md +0 -486
- md_processing/dr_egeria_outbox/thursday/processed-2025-07-18 08:53-gov_def2.md +0 -486
- md_processing/dr_egeria_outbox/thursday/processed-2025-07-18 08:54-gov_def2.md +0 -486
- md_processing/dr_egeria_outbox/thursday/processed-2025-07-18 09:03-gov_def2.md +0 -486
- md_processing/dr_egeria_outbox/thursday/processed-2025-07-18 09:06-gov_def2.md +0 -486
- md_processing/dr_egeria_outbox/thursday/processed-2025-07-18 09:10-gov_def2.md +0 -486
- md_processing/dr_egeria_outbox/tuesday/processed-2025-09-02 13:07-gov_def.md +0 -492
- md_processing/dr_egeria_outbox/tuesday/processed-2025-09-02 13:25-gov_def.md +0 -520
- md_processing/dr_egeria_outbox/tuesday/processed-2025-09-02 16:43-gov_def.md +0 -636
- md_processing/dr_egeria_outbox/tuesday/processed-2025-09-02 16:46-gov_def.md +0 -636
- md_processing/family_docs/Data Designer/Create_Data_Class.md +0 -164
- md_processing/family_docs/Data Designer/Create_Data_Dictionary.md +0 -30
- md_processing/family_docs/Data Designer/Create_Data_Field.md +0 -162
- md_processing/family_docs/Data Designer/Create_Data_Specification.md +0 -36
- md_processing/family_docs/Data Designer/Create_Data_Structure.md +0 -38
- md_processing/family_docs/Data Designer/View_Data_Classes.md +0 -78
- md_processing/family_docs/Data Designer/View_Data_Dictionaries.md +0 -78
- md_processing/family_docs/Data Designer/View_Data_Fields.md +0 -78
- md_processing/family_docs/Data Designer/View_Data_Specifications.md +0 -78
- md_processing/family_docs/Data Designer/View_Data_Structures.md +0 -78
- md_processing/family_docs/Data Designer.md +0 -842
- md_processing/family_docs/Digital Product Manager/Add_Member->Collection.md +0 -42
- md_processing/family_docs/Digital Product Manager/Attach_Collection->Resource.md +0 -36
- md_processing/family_docs/Digital Product Manager/Create_Agreement.md +0 -96
- md_processing/family_docs/Digital Product Manager/Create_Data_Sharing_Agreement.md +0 -72
- md_processing/family_docs/Digital Product Manager/Create_DigitalSubscription.md +0 -102
- md_processing/family_docs/Digital Product Manager/Create_Digital_Product.md +0 -134
- md_processing/family_docs/Digital Product Manager/Link_Agreement_Items.md +0 -60
- md_processing/family_docs/Digital Product Manager/Link_Contracts.md +0 -26
- md_processing/family_docs/Digital Product Manager/Link_Digital_Product_-_Digital_Product.md +0 -30
- md_processing/family_docs/Digital Product Manager/Link_Subscribers.md +0 -48
- md_processing/family_docs/Digital Product Manager.md +0 -668
- md_processing/family_docs/Glossary/Attach_Category_Parent.md +0 -18
- md_processing/family_docs/Glossary/Attach_Term-Term_Relationship.md +0 -26
- md_processing/family_docs/Glossary/Create_Category.md +0 -38
- md_processing/family_docs/Glossary/Create_Glossary.md +0 -42
- md_processing/family_docs/Glossary/Create_Term.md +0 -70
- md_processing/family_docs/Glossary.md +0 -206
- md_processing/family_docs/Governance Officer/Create_Business_Imperative.md +0 -106
- md_processing/family_docs/Governance Officer/Create_Certification_Type.md +0 -112
- md_processing/family_docs/Governance Officer/Create_Governance_Approach.md +0 -114
- md_processing/family_docs/Governance Officer/Create_Governance_Obligation.md +0 -114
- md_processing/family_docs/Governance Officer/Create_Governance_Principle.md +0 -114
- md_processing/family_docs/Governance Officer/Create_Governance_Procedure.md +0 -128
- md_processing/family_docs/Governance Officer/Create_Governance_Process.md +0 -122
- md_processing/family_docs/Governance Officer/Create_Governance_Processing_Purpose.md +0 -106
- md_processing/family_docs/Governance Officer/Create_Governance_Responsibility.md +0 -122
- md_processing/family_docs/Governance Officer/Create_Governance_Rule.md +0 -122
- md_processing/family_docs/Governance Officer/Create_Governance_Strategy.md +0 -106
- md_processing/family_docs/Governance Officer/Create_License_Type.md +0 -112
- md_processing/family_docs/Governance Officer/Create_Naming_Standard_Rule.md +0 -122
- md_processing/family_docs/Governance Officer/Create_Regulation_Article.md +0 -106
- md_processing/family_docs/Governance Officer/Create_Regulation_Definition.md +0 -118
- md_processing/family_docs/Governance Officer/Create_Security_Access_Control.md +0 -114
- md_processing/family_docs/Governance Officer/Create_Security_Group.md +0 -120
- md_processing/family_docs/Governance Officer/Create_Service_Level_Objectives.md +0 -122
- md_processing/family_docs/Governance Officer/Create_Threat_Definition.md +0 -106
- md_processing/family_docs/Governance Officer/Link_Governance_Controls.md +0 -32
- md_processing/family_docs/Governance Officer/Link_Governance_Drivers.md +0 -32
- md_processing/family_docs/Governance Officer/Link_Governance_Policies.md +0 -32
- md_processing/family_docs/Governance Officer/View_Governance_Definitions.md +0 -82
- md_processing/family_docs/Governance Officer.md +0 -2412
- md_processing/family_docs/Solution Architect/Create_Information_Supply_Chain.md +0 -70
- md_processing/family_docs/Solution Architect/Create_Solution_Blueprint.md +0 -44
- md_processing/family_docs/Solution Architect/Create_Solution_Component.md +0 -96
- md_processing/family_docs/Solution Architect/Create_Solution_Role.md +0 -66
- md_processing/family_docs/Solution Architect/Link_Information_Supply_Chain_Peers.md +0 -32
- md_processing/family_docs/Solution Architect/Link_Solution_Component_Peers.md +0 -32
- md_processing/family_docs/Solution Architect/View_Information_Supply_Chains.md +0 -32
- md_processing/family_docs/Solution Architect/View_Solution_Blueprints.md +0 -32
- md_processing/family_docs/Solution Architect/View_Solution_Components.md +0 -32
- md_processing/family_docs/Solution Architect/View_Solution_Roles.md +0 -32
- md_processing/family_docs/Solution Architect.md +0 -490
- md_processing/md_commands/old_project_commands.py +0 -164
- md_processing/md_processing_utils/debug_log.log +0 -5580
- md_processing/md_processing_utils/generated_help_terms.md +0 -842
- md_processing/md_processing_utils/logs/pyegeria.log +0 -56
- pyegeria/.DS_Store +0 -0
- pyegeria/___external_references.py +0 -3267
- {pyegeria-5.4.3.3.dist-info → pyegeria-5.4.4.dist-info}/LICENSE +0 -0
- {pyegeria-5.4.3.3.dist-info → pyegeria-5.4.4.dist-info}/WHEEL +0 -0
- {pyegeria-5.4.3.3.dist-info → pyegeria-5.4.4.dist-info}/entry_points.txt +0 -0
@@ -12,13 +12,18 @@ import sys
|
|
12
12
|
from typing import Any, Callable, Dict, List, Optional, Tuple, Union
|
13
13
|
|
14
14
|
from httpx import Response
|
15
|
+
from loguru import logger
|
16
|
+
|
17
|
+
from pyegeria.models import NewElementRequestBody, TemplateRequestBody, UpdateElementRequestBody, \
|
18
|
+
NewRelationshipRequestBody, DeleteRequestBody, UpdateStatusRequestBody, SearchStringRequestBody
|
15
19
|
from pyegeria.output_formatter import make_preamble, make_md_attribute, generate_output, extract_mermaid_only, \
|
16
|
-
extract_basic_dict, MD_SEPARATOR
|
20
|
+
extract_basic_dict, MD_SEPARATOR, populate_common_columns
|
21
|
+
from pyegeria._output_formats import select_output_format_set, get_output_format_type_match
|
17
22
|
from pyegeria import validate_guid
|
18
23
|
from pyegeria.governance_officer import GovernanceOfficer
|
19
|
-
from pyegeria.
|
20
|
-
from pyegeria._globals import NO_ELEMENTS_FOUND
|
21
|
-
from pyegeria.utils import body_slimmer
|
24
|
+
from pyegeria._client_new import Client2, max_paging_size
|
25
|
+
from pyegeria._globals import NO_ELEMENTS_FOUND, NO_GUID_RETURNED
|
26
|
+
from pyegeria.utils import body_slimmer, dynamic_catch
|
22
27
|
from pyegeria._exceptions import (InvalidParameterException)
|
23
28
|
|
24
29
|
sys.path.insert(0, os.path.abspath(os.path.dirname(__file__)))
|
@@ -53,7 +58,7 @@ def base_path(client, view_server: str):
|
|
53
58
|
return f"{client.platform_url}/servers/{view_server}/api/open-metadata/metadata-explorer"
|
54
59
|
|
55
60
|
|
56
|
-
class SolutionArchitect(
|
61
|
+
class SolutionArchitect(Client2):
|
57
62
|
"""SolutionArchitect is a class that extends the Client class. The Solution Architect OMVS provides APIs for
|
58
63
|
searching for architectural elements such as information supply chains, solution blueprints, solution components,
|
59
64
|
and component implementations.
|
@@ -82,7 +87,7 @@ class SolutionArchitect(Client):
|
|
82
87
|
self.user_pwd = user_pwd
|
83
88
|
self.solution_architect_command_root: str = (f"{self.platform_url}/servers/{self.view_server}"
|
84
89
|
f"/api/open-metadata/solution-architect")
|
85
|
-
|
90
|
+
Client2.__init__(self, view_server, platform_url, user_id=user_id, user_pwd=user_pwd, token=token, )
|
86
91
|
self.url_marker = "solution-architect"
|
87
92
|
#
|
88
93
|
# Extract properties functions
|
@@ -220,7 +225,7 @@ class SolutionArchitect(Client):
|
|
220
225
|
else:
|
221
226
|
return []
|
222
227
|
|
223
|
-
def _extract_info_supply_chain_properties(self, element: dict) -> dict:
|
228
|
+
def _extract_info_supply_chain_properties(self, element: dict, columns_struct: dict) -> dict:
|
224
229
|
"""
|
225
230
|
Extract properties from an information supply chain element.
|
226
231
|
|
@@ -230,63 +235,18 @@ class SolutionArchitect(Client):
|
|
230
235
|
Returns:
|
231
236
|
Dictionary with extracted properties
|
232
237
|
"""
|
233
|
-
|
234
|
-
|
235
|
-
|
236
|
-
|
237
|
-
|
238
|
-
|
239
|
-
|
240
|
-
|
241
|
-
|
242
|
-
|
243
|
-
|
244
|
-
|
245
|
-
additional_properties = properties.get("additionalProperties", {})
|
246
|
-
mer = element.get('mermaidGraph', None)
|
247
|
-
|
248
|
-
|
249
|
-
parents = element.get("parents", [])
|
250
|
-
parents_list = []
|
251
|
-
if parents:
|
252
|
-
for sub in parents:
|
253
|
-
sub_rel_label = sub.get('relationshipProperties',{}).get("label", None)
|
254
|
-
sub_qn = sub['relatedElement']['properties']['qualifiedName']
|
255
|
-
sub_lab = f"--> <{sub_rel_label}> -->" if sub_rel_label else ""
|
256
|
-
sub_info = f"{sub_lab} {sub_qn}"
|
257
|
-
parents_list.append(sub_info)
|
258
|
-
|
259
|
-
peer_supply_chains = element.get("links", {})
|
260
|
-
peer_supply_chains_list = []
|
261
|
-
if peer_supply_chains:
|
262
|
-
for peer in peer_supply_chains:
|
263
|
-
peer_supply_chain_qnames = peer['relatedElement']['properties'].get("qualifiedName", "")
|
264
|
-
peer_supply_chain_label = peer['relationshipProperties'].get('label', None)
|
265
|
-
peer_lab = f"==> <{peer_supply_chain_label}> ==>" if peer_supply_chain_label else ""
|
266
|
-
peer_supply_chains_list.append(f"{peer_lab} {peer_supply_chain_qnames}")
|
267
|
-
|
268
|
-
implemented_by = element.get("implementedByList", {})
|
269
|
-
implemented_by_qnames = []
|
270
|
-
if implemented_by:
|
271
|
-
for peer in peer_supply_chains:
|
272
|
-
implemented_by_qnames.append(peer['relatedElement']['properties'].get("qualifiedName", ""))
|
273
|
-
|
274
|
-
return {
|
275
|
-
'GUID': guid,
|
276
|
-
'qualified_name': qualified_name,
|
277
|
-
'display_name': display_name,
|
278
|
-
'description': description,
|
279
|
-
'scope': scope,
|
280
|
-
'purposes': purpose_md,
|
281
|
-
'extended_properties': extended_properties,
|
282
|
-
'additional_properties': additional_properties,
|
283
|
-
'parents_list': parents_list,
|
284
|
-
'links': peer_supply_chains_list,
|
285
|
-
'implemented_by': implemented_by_qnames,
|
286
|
-
'mermaid': mer
|
287
|
-
}
|
288
|
-
|
289
|
-
def _extract_solution_blueprint_properties(self, element: dict) -> dict:
|
238
|
+
# Follow common extractor pattern using populate_common_columns
|
239
|
+
return populate_common_columns(
|
240
|
+
element,
|
241
|
+
columns_struct,
|
242
|
+
include_header=True,
|
243
|
+
include_relationships=True,
|
244
|
+
include_subject_area=True,
|
245
|
+
mermaid_source_key='mermaidGraph',
|
246
|
+
mermaid_dest_key='mermaid'
|
247
|
+
)
|
248
|
+
|
249
|
+
def _extract_solution_blueprint_properties(self, element: dict, columns_struct: dict) -> dict:
|
290
250
|
"""
|
291
251
|
Extract properties from a solution blueprint element.
|
292
252
|
|
@@ -296,34 +256,17 @@ class SolutionArchitect(Client):
|
|
296
256
|
Returns:
|
297
257
|
Dictionary with extracted properties
|
298
258
|
"""
|
299
|
-
|
300
|
-
|
301
|
-
|
302
|
-
|
303
|
-
|
304
|
-
|
305
|
-
|
306
|
-
|
307
|
-
|
308
|
-
|
309
|
-
|
310
|
-
sol_comp_prop = solution_component['solutionComponent']['properties']
|
311
|
-
sol_comp_name = sol_comp_prop.get("displayName", None)
|
312
|
-
sol_comp_desc = sol_comp_prop.get("description", None)
|
313
|
-
solution_components_md += '{' + f" {sol_comp_name}:\t {sol_comp_desc}" + " },\n"
|
314
|
-
mer = f"```mermaid\n\n{element.get('mermaidGraph', None)}\n\n```"
|
315
|
-
|
316
|
-
return {
|
317
|
-
'GUID': guid,
|
318
|
-
'qualified_name': qualified_name,
|
319
|
-
'display_name': display_name,
|
320
|
-
'description': description,
|
321
|
-
'version': version,
|
322
|
-
'solution_components': solution_components_md,
|
323
|
-
'mermaid': mer
|
324
|
-
}
|
325
|
-
|
326
|
-
def _extract_solution_roles_properties(self, element: dict) -> dict:
|
259
|
+
return populate_common_columns(
|
260
|
+
element,
|
261
|
+
columns_struct,
|
262
|
+
include_header=True,
|
263
|
+
include_relationships=True,
|
264
|
+
include_subject_area=True,
|
265
|
+
mermaid_source_key='mermaidGraph',
|
266
|
+
mermaid_dest_key='mermaid'
|
267
|
+
)
|
268
|
+
|
269
|
+
def _extract_solution_roles_properties(self, element: dict, columns_struct: dict) -> dict:
|
327
270
|
"""
|
328
271
|
Extract properties from a solution role element.
|
329
272
|
|
@@ -333,35 +276,15 @@ class SolutionArchitect(Client):
|
|
333
276
|
Returns:
|
334
277
|
Dictionary with extracted properties
|
335
278
|
"""
|
336
|
-
|
337
|
-
|
338
|
-
|
339
|
-
|
340
|
-
|
341
|
-
|
342
|
-
|
343
|
-
|
344
|
-
|
345
|
-
solution_components = element.get('solutionComponents', None)
|
346
|
-
solution_components_md = ""
|
347
|
-
if solution_components:
|
348
|
-
for solution_component in solution_components:
|
349
|
-
sol_comp_prop = solution_component.get('relationshipProperties', None)
|
350
|
-
if sol_comp_prop:
|
351
|
-
sol_comp_name = sol_comp_prop.get("role", None)
|
352
|
-
sol_comp_desc = sol_comp_prop.get("description", None)
|
353
|
-
solution_components_md += "{" + f" {sol_comp_name}:\t {sol_comp_desc}" + " },\n"
|
354
|
-
|
355
|
-
return {
|
356
|
-
'GUID': guid,
|
357
|
-
'qualified_name': qualified_name,
|
358
|
-
'display_name': display_name,
|
359
|
-
'description': description,
|
360
|
-
'role_id': role_id,
|
361
|
-
'scope': scope,
|
362
|
-
'domain_identifier': domain_identifier,
|
363
|
-
'solution_components': solution_components_md
|
364
|
-
}
|
279
|
+
return populate_common_columns(
|
280
|
+
element,
|
281
|
+
columns_struct,
|
282
|
+
include_header=True,
|
283
|
+
include_relationships=True,
|
284
|
+
include_subject_area=True,
|
285
|
+
mermaid_source_key='mermaidGraph',
|
286
|
+
mermaid_dest_key='mermaid'
|
287
|
+
)
|
365
288
|
|
366
289
|
|
367
290
|
|
@@ -548,7 +471,7 @@ class SolutionArchitect(Client):
|
|
548
471
|
else:
|
549
472
|
return []
|
550
473
|
|
551
|
-
def _extract_solution_components_properties(self, element: Union[Dict,List[Dict]]) -> dict:
|
474
|
+
def _extract_solution_components_properties(self, element: Union[Dict,List[Dict]], columns_struct: dict) -> dict:
|
552
475
|
"""
|
553
476
|
Extract properties from a solution component element.
|
554
477
|
|
@@ -559,125 +482,51 @@ class SolutionArchitect(Client):
|
|
559
482
|
Dictionary with extracted properties
|
560
483
|
"""
|
561
484
|
|
562
|
-
|
563
|
-
|
564
|
-
|
565
|
-
|
566
|
-
|
567
|
-
|
568
|
-
|
569
|
-
|
570
|
-
|
571
|
-
extended_props = properties.get("extendedProperties", None)
|
572
|
-
extended_props_md = ""
|
573
|
-
if extended_props:
|
574
|
-
for key in extended_props.keys():
|
575
|
-
extended_props_md += "{" + f" {key}: {extended_props[key]}" + " }, "
|
576
|
-
|
577
|
-
# Extract additional properties
|
578
|
-
additional_props = properties.get("additionalProperties", None)
|
579
|
-
additional_props_md = ""
|
580
|
-
if additional_props:
|
581
|
-
for key in additional_props.keys():
|
582
|
-
additional_props_md += "{" + f" {key}: {additional_props[key]}" + " }, "
|
583
|
-
|
584
|
-
rel_elements = self._get_component_rel_elements_dict(element)
|
585
|
-
|
586
|
-
# actors
|
587
|
-
actors_md = ", ".join(rel_elements.get("actor.qnames", []) )
|
588
|
-
|
589
|
-
# Extract blueprints & supply chains
|
590
|
-
blueprints_md = ", ".join(rel_elements.get("blueprint_qnames",[]))
|
591
|
-
owning_supply_chains_md = ", ".join(rel_elements.get("owning_info_supply_chain_qnames",[]))
|
592
|
-
|
593
|
-
# Extract parent components
|
594
|
-
parent_comp_md = ", ".join(rel_elements.get("parent_qnames",[]))
|
595
|
-
|
596
|
-
# Extract sub-components
|
597
|
-
sub_comp_md = ", ".join(rel_elements.get("sub_component_qnames",[]))
|
598
|
-
|
599
|
-
# wired from and to
|
600
|
-
wired_from_md = ", ".join(rel_elements.get("wired_from_qnames",[]))
|
601
|
-
wired_to_md = ", ".join(rel_elements.get("wired_to_qnames",[]))
|
602
|
-
|
603
|
-
|
604
|
-
comp_graph = element.get('mermaidGraph', None)
|
605
|
-
|
606
|
-
return {
|
607
|
-
'GUID': guid,
|
608
|
-
'qualified_name': qualified_name,
|
609
|
-
'display_name': display_name,
|
610
|
-
'description': description,
|
611
|
-
'component_type': component_type,
|
612
|
-
'version': version,
|
613
|
-
'blueprints': blueprints_md,
|
614
|
-
'owning_supply_chains': owning_supply_chains_md,
|
615
|
-
'actors': actors_md,
|
616
|
-
'parent_components': parent_comp_md,
|
617
|
-
'sub_components': sub_comp_md,
|
618
|
-
'wired_from_components': wired_from_md,
|
619
|
-
'wired_to_components': wired_to_md,
|
620
|
-
'additional_properties': additional_props_md,
|
621
|
-
'extended_properties': extended_props_md,
|
622
|
-
'mermaid_graph': comp_graph
|
623
|
-
}
|
485
|
+
return populate_common_columns(
|
486
|
+
element,
|
487
|
+
columns_struct,
|
488
|
+
include_header=True,
|
489
|
+
include_relationships=True,
|
490
|
+
include_subject_area=True,
|
491
|
+
mermaid_source_key='mermaidGraph',
|
492
|
+
mermaid_dest_key='mermaid'
|
493
|
+
)
|
624
494
|
|
625
495
|
#
|
626
496
|
# Markdown output support
|
627
497
|
#
|
628
|
-
def generate_info_supply_chain_output(self, elements: list | dict, search_string: str,
|
629
|
-
output_format: str = 'MD') -> str | list:
|
630
|
-
"""
|
631
|
-
Generate output for information supply chains in the specified format.
|
632
|
-
|
633
|
-
Args:
|
634
|
-
elements: Dictionary or list of dictionaries containing information supply chain elements
|
635
|
-
search_string: The search string used to find the elements
|
636
|
-
output_format: The desired output format (MD, FORM, REPORT, LIST, DICT, MERMAID, HTML)
|
637
|
-
|
638
|
-
Returns:
|
639
|
-
Formatted output as string or list of dictionaries
|
498
|
+
def generate_info_supply_chain_output(self, elements: list | dict, search_string: str, element_type_name: str | None,
|
499
|
+
output_format: str = 'MD', output_format_set: dict | str = None) -> str | list:
|
500
|
+
"""Render Information Supply Chains using the shared output pipeline.
|
640
501
|
"""
|
641
|
-
# Handle MERMAID and DICT formats
|
642
502
|
if output_format == "MERMAID":
|
643
503
|
return extract_mermaid_only(elements)
|
644
|
-
|
645
|
-
|
646
|
-
|
647
|
-
|
648
|
-
|
649
|
-
|
650
|
-
|
651
|
-
|
652
|
-
|
653
|
-
|
654
|
-
)
|
655
|
-
|
656
|
-
|
657
|
-
|
658
|
-
|
659
|
-
|
660
|
-
|
661
|
-
|
662
|
-
|
663
|
-
|
664
|
-
|
665
|
-
|
666
|
-
|
667
|
-
|
668
|
-
|
669
|
-
|
670
|
-
entity_type="Information Supply Chain",
|
671
|
-
output_format=output_format,
|
672
|
-
extract_properties_func=self._extract_info_supply_chain_properties,
|
673
|
-
columns=columns if output_format == 'LIST' else None
|
674
|
-
)
|
675
|
-
|
676
|
-
# Default case
|
677
|
-
return None
|
678
|
-
|
679
|
-
def generate_solution_blueprint_output(self, elements: list | dict, search_string: str,
|
680
|
-
output_format: str = 'MD') -> str | list:
|
504
|
+
|
505
|
+
entity_type = "Information Supply Chain"
|
506
|
+
if output_format_set:
|
507
|
+
if isinstance(output_format_set, str):
|
508
|
+
output_formats = select_output_format_set(output_format_set, output_format)
|
509
|
+
elif isinstance(output_format_set, dict):
|
510
|
+
output_formats = get_output_format_type_match(output_format_set, output_format)
|
511
|
+
else:
|
512
|
+
output_formats = None
|
513
|
+
else:
|
514
|
+
output_formats = select_output_format_set("Information Supply Chains", output_format)
|
515
|
+
if output_formats is None:
|
516
|
+
output_formats = select_output_format_set("Default", output_format)
|
517
|
+
|
518
|
+
return generate_output(
|
519
|
+
elements=elements,
|
520
|
+
search_string=search_string,
|
521
|
+
entity_type=entity_type,
|
522
|
+
output_format=output_format,
|
523
|
+
extract_properties_func=self._extract_info_supply_chain_properties,
|
524
|
+
get_additional_props_func=None,
|
525
|
+
columns_struct=output_formats,
|
526
|
+
)
|
527
|
+
|
528
|
+
def generate_solution_blueprint_output(self, elements: list | dict, search_string: str, element_type_name: str | None,
|
529
|
+
output_format: str = 'MD', output_format_set: dict | str = None) -> str | list:
|
681
530
|
"""
|
682
531
|
Generate output for solution blueprints in the specified format.
|
683
532
|
|
@@ -689,43 +538,34 @@ class SolutionArchitect(Client):
|
|
689
538
|
Returns:
|
690
539
|
Formatted output as string or list of dictionaries
|
691
540
|
"""
|
692
|
-
# Handle MERMAID and DICT formats
|
693
541
|
if output_format == "MERMAID":
|
694
542
|
return extract_mermaid_only(elements)
|
695
|
-
|
696
|
-
|
697
|
-
|
698
|
-
|
699
|
-
|
700
|
-
|
701
|
-
|
702
|
-
|
703
|
-
|
704
|
-
|
705
|
-
|
706
|
-
|
707
|
-
|
708
|
-
|
709
|
-
|
710
|
-
|
711
|
-
|
712
|
-
|
713
|
-
|
714
|
-
|
715
|
-
|
716
|
-
|
717
|
-
|
718
|
-
|
719
|
-
|
720
|
-
|
721
|
-
extract_properties_func=self._extract_solution_blueprint_properties,
|
722
|
-
columns=columns if output_format == 'LIST' else None
|
723
|
-
)
|
724
|
-
|
725
|
-
# Default case
|
726
|
-
return None
|
727
|
-
|
728
|
-
def generate_solution_roles_output(self, elements: list | dict, search_string: str, output_format: str = 'MD') -> str | list:
|
543
|
+
|
544
|
+
entity_type = "Solution Blueprint"
|
545
|
+
if output_format_set:
|
546
|
+
if isinstance(output_format_set, str):
|
547
|
+
output_formats = select_output_format_set(output_format_set, output_format)
|
548
|
+
elif isinstance(output_format_set, dict):
|
549
|
+
output_formats = get_output_format_type_match(output_format_set, output_format)
|
550
|
+
else:
|
551
|
+
output_formats = None
|
552
|
+
else:
|
553
|
+
output_formats = select_output_format_set("Solution Blueprints", output_format)
|
554
|
+
if output_formats is None:
|
555
|
+
output_formats = select_output_format_set("Default", output_format)
|
556
|
+
|
557
|
+
return generate_output(
|
558
|
+
elements=elements,
|
559
|
+
search_string=search_string,
|
560
|
+
entity_type=entity_type,
|
561
|
+
output_format=output_format,
|
562
|
+
extract_properties_func=self._extract_solution_blueprint_properties,
|
563
|
+
get_additional_props_func=None,
|
564
|
+
columns_struct=output_formats,
|
565
|
+
)
|
566
|
+
|
567
|
+
def generate_solution_roles_output(self, elements: list | dict, search_string: str, element_type_name: str | None,
|
568
|
+
output_format: str = 'MD', output_format_set: dict | str = None) -> str | list:
|
729
569
|
"""
|
730
570
|
Generate output for solution roles in the specified format.
|
731
571
|
|
@@ -737,45 +577,34 @@ class SolutionArchitect(Client):
|
|
737
577
|
Returns:
|
738
578
|
Formatted output as string or list of dictionaries
|
739
579
|
"""
|
740
|
-
# Handle MERMAID and DICT formats
|
741
580
|
if output_format == "MERMAID":
|
742
581
|
return extract_mermaid_only(elements)
|
743
|
-
|
744
|
-
|
745
|
-
|
746
|
-
|
747
|
-
|
748
|
-
|
749
|
-
|
750
|
-
|
751
|
-
|
752
|
-
|
753
|
-
|
754
|
-
|
755
|
-
|
756
|
-
|
757
|
-
|
758
|
-
|
759
|
-
|
760
|
-
|
761
|
-
|
762
|
-
|
763
|
-
|
764
|
-
|
765
|
-
|
766
|
-
|
767
|
-
|
768
|
-
|
769
|
-
output_format=output_format,
|
770
|
-
extract_properties_func=self._extract_solution_roles_properties,
|
771
|
-
columns=columns if output_format == 'LIST' else None
|
772
|
-
)
|
773
|
-
|
774
|
-
# Default case
|
775
|
-
return None
|
776
|
-
|
777
|
-
def generate_solution_components_output(self, elements: list | dict, search_string: str,
|
778
|
-
output_format: str = 'MD') -> str | list:
|
582
|
+
|
583
|
+
entity_type = "Solution Role"
|
584
|
+
if output_format_set:
|
585
|
+
if isinstance(output_format_set, str):
|
586
|
+
output_formats = select_output_format_set(output_format_set, output_format)
|
587
|
+
elif isinstance(output_format_set, dict):
|
588
|
+
output_formats = get_output_format_type_match(output_format_set, output_format)
|
589
|
+
else:
|
590
|
+
output_formats = None
|
591
|
+
else:
|
592
|
+
output_formats = select_output_format_set("Solution Roles", output_format)
|
593
|
+
if output_formats is None:
|
594
|
+
output_formats = select_output_format_set("Default", output_format)
|
595
|
+
|
596
|
+
return generate_output(
|
597
|
+
elements=elements,
|
598
|
+
search_string=search_string,
|
599
|
+
entity_type=entity_type,
|
600
|
+
output_format=output_format,
|
601
|
+
extract_properties_func=self._extract_solution_roles_properties,
|
602
|
+
get_additional_props_func=None,
|
603
|
+
columns_struct=output_formats,
|
604
|
+
)
|
605
|
+
|
606
|
+
def generate_solution_components_output(self, elements: list | dict, search_string: str, element_type_name: str | None,
|
607
|
+
output_format: str = 'MD', output_format_set: dict | str = None) -> str | list:
|
779
608
|
"""
|
780
609
|
Generate output for solution components in the specified format.
|
781
610
|
|
@@ -792,50 +621,39 @@ class SolutionArchitect(Client):
|
|
792
621
|
Returns:
|
793
622
|
Formatted output as string or list of dictionaries
|
794
623
|
"""
|
795
|
-
# Handle MERMAID and DICT formats
|
796
624
|
if output_format == "MERMAID":
|
797
625
|
return extract_mermaid_only(elements)
|
798
|
-
|
799
|
-
|
800
|
-
|
801
|
-
|
802
|
-
|
803
|
-
|
804
|
-
|
805
|
-
|
806
|
-
|
807
|
-
|
808
|
-
|
809
|
-
|
810
|
-
|
811
|
-
|
812
|
-
|
813
|
-
|
814
|
-
|
815
|
-
|
816
|
-
|
817
|
-
|
818
|
-
|
819
|
-
|
820
|
-
|
821
|
-
|
822
|
-
|
823
|
-
|
824
|
-
entity_type="Solution Component",
|
825
|
-
output_format=output_format,
|
826
|
-
extract_properties_func=self._extract_solution_components_properties,
|
827
|
-
columns=columns if output_format == 'LIST' else None
|
828
|
-
)
|
829
|
-
|
830
|
-
# Default case
|
831
|
-
return None
|
832
|
-
|
833
|
-
async def _async_create_info_supply_chain(self, body: dict) -> str:
|
626
|
+
|
627
|
+
entity_type = "Solution Component"
|
628
|
+
if output_format_set:
|
629
|
+
if isinstance(output_format_set, str):
|
630
|
+
output_formats = select_output_format_set(output_format_set, output_format)
|
631
|
+
elif isinstance(output_format_set, dict):
|
632
|
+
output_formats = get_output_format_type_match(output_format_set, output_format)
|
633
|
+
else:
|
634
|
+
output_formats = None
|
635
|
+
else:
|
636
|
+
output_formats = select_output_format_set("Solution Components", output_format)
|
637
|
+
if output_formats is None:
|
638
|
+
output_formats = select_output_format_set("Default", output_format)
|
639
|
+
|
640
|
+
return generate_output(
|
641
|
+
elements=elements,
|
642
|
+
search_string=search_string,
|
643
|
+
entity_type=entity_type,
|
644
|
+
output_format=output_format,
|
645
|
+
extract_properties_func=self._extract_solution_components_properties,
|
646
|
+
get_additional_props_func=None,
|
647
|
+
columns_struct=output_formats,
|
648
|
+
)
|
649
|
+
|
650
|
+
@dynamic_catch
|
651
|
+
async def _async_create_info_supply_chain(self, body: dict | NewElementRequestBody) -> str:
|
834
652
|
"""Create an information supply. Async version.
|
835
653
|
|
836
654
|
Parameters
|
837
655
|
----------
|
838
|
-
body: dict
|
656
|
+
body: dict | NewElementRequestBody
|
839
657
|
A dictionary containing the definition of the supply chain to create.
|
840
658
|
|
841
659
|
Returns
|
@@ -887,6 +705,7 @@ class SolutionArchitect(Client):
|
|
887
705
|
"description": "add description here",
|
888
706
|
"scope": "add scope of this information supply chain's applicability.",
|
889
707
|
"purposes": ["purpose1", "purpose2"],
|
708
|
+
"estimatedVolumetrics": {},
|
890
709
|
"additionalProperties": {
|
891
710
|
"property1": "propertyValue1",
|
892
711
|
"property2": "propertyValue2"
|
@@ -900,16 +719,15 @@ class SolutionArchitect(Client):
|
|
900
719
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
901
720
|
f"information-supply-chains")
|
902
721
|
|
903
|
-
|
904
|
-
|
905
|
-
return response.json().get("guid", "Supply Chain not created")
|
722
|
+
return await self._async_create_element_body_request(url, ["InformationSupplyChainProperties"], body)
|
906
723
|
|
907
|
-
|
724
|
+
@dynamic_catch
|
725
|
+
def create_info_supply_chain(self, body: dict | NewElementRequestBody) -> str:
|
908
726
|
"""Create an information supply.
|
909
727
|
|
910
728
|
Parameters
|
911
729
|
----------
|
912
|
-
body: dict
|
730
|
+
body: dict | NewElementRequestBody
|
913
731
|
A dictionary containing the definition of the supply chain to create.
|
914
732
|
|
915
733
|
Returns
|
@@ -961,6 +779,7 @@ class SolutionArchitect(Client):
|
|
961
779
|
"description": "add description here",
|
962
780
|
"scope": "add scope of this information supply chain's applicability.",
|
963
781
|
"purposes": ["purpose1", "purpose2"],
|
782
|
+
"estimatedVolumetrics": {},
|
964
783
|
"additionalProperties": {
|
965
784
|
"property1": "propertyValue1",
|
966
785
|
"property2": "propertyValue2"
|
@@ -975,7 +794,8 @@ class SolutionArchitect(Client):
|
|
975
794
|
response = loop.run_until_complete(self._async_create_info_supply_chain(body))
|
976
795
|
return response
|
977
796
|
|
978
|
-
|
797
|
+
@dynamic_catch
|
798
|
+
async def _async_create_info_supply_chain_from_template(self, body: dict | TemplateRequestBody) -> str:
|
979
799
|
""" Create a new metadata element to represent an information supply chain using an existing metadata element
|
980
800
|
as a template. The template defines additional classifications and relationships that should be added to
|
981
801
|
the new element. Async Version.
|
@@ -983,7 +803,7 @@ class SolutionArchitect(Client):
|
|
983
803
|
|
984
804
|
Parameters
|
985
805
|
----------
|
986
|
-
body: dict
|
806
|
+
body: dict | NewElementRequestBody
|
987
807
|
A dictionary containing the definition of the supply chain to create.
|
988
808
|
|
989
809
|
Returns
|
@@ -1049,18 +869,27 @@ class SolutionArchitect(Client):
|
|
1049
869
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
1050
870
|
f"information-supply-chains/from-template")
|
1051
871
|
|
1052
|
-
|
872
|
+
if isinstance(body, TemplateRequestBody):
|
873
|
+
validated_body = body
|
874
|
+
|
875
|
+
elif isinstance(body, dict):
|
876
|
+
validated_body = self._template_request_adapter.validate_python(body)
|
1053
877
|
|
1054
|
-
|
878
|
+
json_body = validated_body.model_dump_json(indent=2, exclude_none=True)
|
879
|
+
logger.info(json_body)
|
880
|
+
resp = await self._async_make_request("POST", url, json_body, is_json=True)
|
881
|
+
logger.info(f"Create Supply Chain from template with GUID: {resp.json().get('guid')}")
|
882
|
+
return resp.json().get("guid", NO_GUID_RETURNED)
|
1055
883
|
|
1056
|
-
|
884
|
+
@dynamic_catch
|
885
|
+
def create_info_supply_chain_from_template(self, body: dict| TemplateRequestBody) -> str:
|
1057
886
|
""" Create a new metadata element to represent an information supply chain using an existing metadata element
|
1058
887
|
as a template. The template defines additional classifications and relationships that should be added to
|
1059
888
|
the new element.
|
1060
889
|
|
1061
890
|
Parameters
|
1062
891
|
----------
|
1063
|
-
body: dict
|
892
|
+
body: dict | TemplateRequestBody
|
1064
893
|
A dictionary containing the definition of the supply chain to create.
|
1065
894
|
|
1066
895
|
Returns
|
@@ -1128,18 +957,17 @@ class SolutionArchitect(Client):
|
|
1128
957
|
response = loop.run_until_complete(self._async_create_info_supply_chain_from_template(body))
|
1129
958
|
return response
|
1130
959
|
|
1131
|
-
|
1132
|
-
|
960
|
+
@dynamic_catch
|
961
|
+
async def _async_update_info_supply_chain(self, guid: str, body: dict | UpdateElementRequestBody,) -> None:
|
1133
962
|
""" Update the properties of an information supply chain. Async Version.
|
1134
963
|
|
1135
964
|
Parameters
|
1136
965
|
----------
|
1137
966
|
guid: str
|
1138
967
|
guid of the information supply chain to update.
|
1139
|
-
body: dict
|
968
|
+
body: dict | UpdateElementRequestBody
|
1140
969
|
A dictionary containing the updates to the supply chain.
|
1141
|
-
|
1142
|
-
Whether to replace all properties with those provided in the body or to merge with existing properties.
|
970
|
+
|
1143
971
|
|
1144
972
|
Returns
|
1145
973
|
-------
|
@@ -1184,24 +1012,22 @@ class SolutionArchitect(Client):
|
|
1184
1012
|
}
|
1185
1013
|
}
|
1186
1014
|
"""
|
1187
|
-
|
1188
|
-
replace_all_properties_s = str(replace_all_properties).lower()
|
1015
|
+
|
1189
1016
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
1190
|
-
f"information-supply-chains/{guid}/update
|
1017
|
+
f"information-supply-chains/{guid}/update")
|
1191
1018
|
|
1192
|
-
await self.
|
1019
|
+
await self._async_update_element_body_request(url, ["InformationSupplyChainProperties"],body)
|
1193
1020
|
|
1194
|
-
|
1021
|
+
@dynamic_catch
|
1022
|
+
def update_info_supply_chain(self, guid: str, body: dict | UpdateElementRequestBody) -> None:
|
1195
1023
|
""" Update the properties of an information supply chain. Async Version.
|
1196
1024
|
|
1197
1025
|
Parameters
|
1198
1026
|
----------
|
1199
1027
|
guid: str
|
1200
1028
|
guid of the information supply chain to update.
|
1201
|
-
body: dict
|
1029
|
+
body: dict | UpdateElementRequestBody
|
1202
1030
|
A dictionary containing the updates to the supply chain.
|
1203
|
-
replace_all_properties: bool, optional
|
1204
|
-
Whether to replace all properties with those provided in the body or to merge with existing properties.
|
1205
1031
|
|
1206
1032
|
Returns
|
1207
1033
|
-------
|
@@ -1247,10 +1073,10 @@ class SolutionArchitect(Client):
|
|
1247
1073
|
}
|
1248
1074
|
"""
|
1249
1075
|
loop = asyncio.get_event_loop()
|
1250
|
-
loop.run_until_complete(self._async_update_info_supply_chain(guid, body
|
1076
|
+
loop.run_until_complete(self._async_update_info_supply_chain(guid, body))
|
1251
1077
|
|
1252
|
-
|
1253
|
-
async def
|
1078
|
+
@dynamic_catch
|
1079
|
+
async def _async_link_peer_info_supply_chains(self, peer1_guid: str, peer2_guid: str, body: dict | NewRelationshipRequestBody = None) -> None:
|
1254
1080
|
""" Connect two peer information supply chains. The linked elements are of type 'Referenceable' to
|
1255
1081
|
allow significant data stores to be included in the definition of the information supply chain.
|
1256
1082
|
Request body is optional. Async Version.
|
@@ -1261,7 +1087,7 @@ class SolutionArchitect(Client):
|
|
1261
1087
|
guid of the first information supply chain to link.
|
1262
1088
|
peer2_guid: str
|
1263
1089
|
guid of the second information supply chain to link.
|
1264
|
-
body: dict, optional
|
1090
|
+
body: dict | NewRelationshipRequestBody, optional
|
1265
1091
|
The body describing the link between the two chains.
|
1266
1092
|
|
1267
1093
|
Returns
|
@@ -1282,7 +1108,7 @@ class SolutionArchitect(Client):
|
|
1282
1108
|
|
1283
1109
|
Body structure:
|
1284
1110
|
{
|
1285
|
-
"class" : "
|
1111
|
+
"class" : "NewRelationshipRequestBody",
|
1286
1112
|
"externalSourceGUID": "add guid here",
|
1287
1113
|
"externalSourceName": "add qualified name here",
|
1288
1114
|
"effectiveTime" : "{{$isoTimestamp}}",
|
@@ -1297,17 +1123,15 @@ class SolutionArchitect(Client):
|
|
1297
1123
|
}
|
1298
1124
|
}
|
1299
1125
|
"""
|
1300
|
-
|
1301
|
-
validate_guid(peer2_guid)
|
1126
|
+
|
1302
1127
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
1303
1128
|
f"information-supply-chains/{peer1_guid}/peer-links/{peer2_guid}/attach")
|
1304
1129
|
|
1305
|
-
|
1306
|
-
|
1307
|
-
else:
|
1308
|
-
await self._async_make_request("POST", url)
|
1130
|
+
await self._async_new_relationship_request(url, ["InformationSupplyChainLinkProperties"], body)
|
1131
|
+
logger.info(f"Linked Supply Chains {peer1_guid} -> {peer2_guid}")
|
1309
1132
|
|
1310
|
-
|
1133
|
+
@dynamic_catch
|
1134
|
+
def link_peer_info_supply_chains(self, peer1_guid: str, peer2_guid: str, body: dict | NewRelationshipRequestBody) -> None:
|
1311
1135
|
""" Connect two peer information supply chains. The linked elements are of type 'Referenceable' to
|
1312
1136
|
allow significant data stores to be included in the definition of the information supply chain.
|
1313
1137
|
Request body is optional.
|
@@ -1318,7 +1142,7 @@ class SolutionArchitect(Client):
|
|
1318
1142
|
guid of the first information supply chain to link.
|
1319
1143
|
peer2_guid: str
|
1320
1144
|
guid of the second information supply chain to link.
|
1321
|
-
body: dict
|
1145
|
+
body: dict | NewRelationshipRequestBody, optional
|
1322
1146
|
The body describing the link between the two chains.
|
1323
1147
|
|
1324
1148
|
Returns
|
@@ -1355,10 +1179,11 @@ class SolutionArchitect(Client):
|
|
1355
1179
|
}
|
1356
1180
|
"""
|
1357
1181
|
loop = asyncio.get_event_loop()
|
1358
|
-
loop.run_until_complete(self.
|
1182
|
+
loop.run_until_complete(self._async_link_peer_info_supply_chains(peer1_guid, peer2_guid, body))
|
1359
1183
|
|
1184
|
+
@dynamic_catch
|
1360
1185
|
async def _async_unlink_peer_info_supply_chains(self, peer1_guid: str, peer2_guid: str,
|
1361
|
-
body: dict = None) -> None:
|
1186
|
+
body: dict | DeleteRequestBody = None) -> None:
|
1362
1187
|
""" Detach two peers in an information supply chain from one another. The linked elements are of type
|
1363
1188
|
'Referenceable' to allow significant data stores to be included in the definition of the information
|
1364
1189
|
supply chain. Request body is optional. Async Version.
|
@@ -1369,7 +1194,7 @@ class SolutionArchitect(Client):
|
|
1369
1194
|
guid of the first information supply chain to link.
|
1370
1195
|
peer2_guid: str
|
1371
1196
|
guid of the second information supply chain to link.
|
1372
|
-
body: dict, optional
|
1197
|
+
body: dict | DeleteRequestBody, optional
|
1373
1198
|
The body describing the link between the two segments.
|
1374
1199
|
|
1375
1200
|
Returns
|
@@ -1390,7 +1215,7 @@ class SolutionArchitect(Client):
|
|
1390
1215
|
|
1391
1216
|
Body structure:
|
1392
1217
|
{
|
1393
|
-
"class": "
|
1218
|
+
"class": "DeleteRequestBody",
|
1394
1219
|
"externalSourceGUID": "add guid here",
|
1395
1220
|
"externalSourceName": "add qualified name here",
|
1396
1221
|
"effectiveTime": {{isotime}},
|
@@ -1403,11 +1228,11 @@ class SolutionArchitect(Client):
|
|
1403
1228
|
validate_guid(peer2_guid)
|
1404
1229
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
1405
1230
|
f"information-supply-chains/{peer1_guid}/peer-links/{peer2_guid}/detach")
|
1406
|
-
|
1407
|
-
|
1408
|
-
|
1409
|
-
await self._async_make_request("POST", url)
|
1231
|
+
await self._async_delete_request(url, body)
|
1232
|
+
logger.info(
|
1233
|
+
f"Detached supply chains {peer1_guid} -> {peer2_guid}")
|
1410
1234
|
|
1235
|
+
@dynamic_catch
|
1411
1236
|
def unlink_peer_info_supply_chains(self, peer1_guid: str, peer2_guid: str,
|
1412
1237
|
body: dict = None) -> None:
|
1413
1238
|
""" Detach two peers in an information supply chain from one another. The linked elements are of type
|
@@ -1452,7 +1277,9 @@ class SolutionArchitect(Client):
|
|
1452
1277
|
loop = asyncio.get_event_loop()
|
1453
1278
|
loop.run_until_complete(self._async_unlink_peer_info_supply_chains(peer1_guid,peer2_guid, body))
|
1454
1279
|
|
1455
|
-
|
1280
|
+
@dynamic_catch
|
1281
|
+
async def _async_compose_info_supply_chains(self, chain_guid: str, nested_chain_guid: str,
|
1282
|
+
body: dict | NewRelationshipRequestBody = None) -> None:
|
1456
1283
|
""" Connect a nested information supply chain to its parent. Request body is optional.
|
1457
1284
|
Async Version.
|
1458
1285
|
|
@@ -1462,7 +1289,7 @@ class SolutionArchitect(Client):
|
|
1462
1289
|
guid of the first information supply chain to link.
|
1463
1290
|
nested_chain_guid: str
|
1464
1291
|
guid of the second information supply chain to link.
|
1465
|
-
body: dict, optional
|
1292
|
+
body: dict | NewRelationshipRequestBody, optional
|
1466
1293
|
The body describing the link between the two chains.
|
1467
1294
|
|
1468
1295
|
Returns
|
@@ -1483,7 +1310,7 @@ class SolutionArchitect(Client):
|
|
1483
1310
|
|
1484
1311
|
Body structure:
|
1485
1312
|
{
|
1486
|
-
"class" : "
|
1313
|
+
"class" : "NewRelationshipRequestBody",
|
1487
1314
|
"externalSourceGUID": "add guid here",
|
1488
1315
|
"externalSourceName": "add qualified name here",
|
1489
1316
|
"effectiveTime" : "{{$isoTimestamp}}",
|
@@ -1502,21 +1329,21 @@ class SolutionArchitect(Client):
|
|
1502
1329
|
validate_guid(nested_chain_guid)
|
1503
1330
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
1504
1331
|
f"information-supply-chains/{chain_guid}/compositions/{nested_chain_guid}/attach")
|
1505
|
-
if body:
|
1506
|
-
await self._async_make_request("POST", url, body_slimmer(body))
|
1507
|
-
else:
|
1508
|
-
await self._async_make_request("POST", url)
|
1509
1332
|
|
1510
|
-
|
1333
|
+
await self._async_new_relationship_request(url, ["InformationSupplyChainCompositionProperties"], body)
|
1334
|
+
logger.info(f"Linked {chain_guid} -> {nested_chain_guid}")
|
1335
|
+
|
1336
|
+
@dynamic_catch
|
1337
|
+
def compose_info_supply_chains(self, chain_guid: str, nested_chain_guid: str, body: dict | NewRelationshipRequestBody = None) -> None:
|
1511
1338
|
""" Connect a nested information supply chain to its parent. Request body is optional.
|
1512
1339
|
|
1513
1340
|
Parameters
|
1514
1341
|
----------
|
1515
1342
|
chain_guid: str
|
1516
|
-
guid of the first information supply chain
|
1343
|
+
guid of the first information supply chain to link.
|
1517
1344
|
nested_chain_guid: str
|
1518
1345
|
guid of the second information supply chain to link.
|
1519
|
-
body: dict, optional
|
1346
|
+
body: dict | NewRelationshipRequestBody, optional
|
1520
1347
|
The body describing the link between the two chains.
|
1521
1348
|
|
1522
1349
|
Returns
|
@@ -1537,7 +1364,7 @@ class SolutionArchitect(Client):
|
|
1537
1364
|
|
1538
1365
|
Body structure:
|
1539
1366
|
{
|
1540
|
-
"class" : "
|
1367
|
+
"class" : "NewRelationshipRequestBody",
|
1541
1368
|
"externalSourceGUID": "add guid here",
|
1542
1369
|
"externalSourceName": "add qualified name here",
|
1543
1370
|
"effectiveTime" : "{{$isoTimestamp}}",
|
@@ -1555,6 +1382,8 @@ class SolutionArchitect(Client):
|
|
1555
1382
|
loop = asyncio.get_event_loop()
|
1556
1383
|
loop.run_until_complete(self._async_compose_info_supply_chains(chain_guid, nested_chain_guid, body))
|
1557
1384
|
|
1385
|
+
|
1386
|
+
@dynamic_catch
|
1558
1387
|
async def _async_decompose_info_supply_chains(self, chain_guid: str, nested_chain_guid: str,
|
1559
1388
|
body: dict = None) -> None:
|
1560
1389
|
""" Detach two peers in an information supply chain from one another. Request body is optional. Async Version.
|
@@ -1600,10 +1429,12 @@ class SolutionArchitect(Client):
|
|
1600
1429
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
1601
1430
|
f"information-supply-chains/{chain_guid}/compositions/{nested_chain_guid}/detach")
|
1602
1431
|
|
1603
|
-
await self.
|
1432
|
+
await self._async_delete_request(url, body)
|
1433
|
+
logger.info(f"Removed composition of {nested_chain_guid} -> {chain_guid}")
|
1604
1434
|
|
1435
|
+
@dynamic_catch
|
1605
1436
|
def decompose_info_supply_chains(self, chain_guid: str, nested_chain_guid: str,
|
1606
|
-
body: dict = None) -> None:
|
1437
|
+
body: dict | DeleteRequestBody = None) -> None:
|
1607
1438
|
""" Detach two peers in an information supply chain from one another. Request body is optional.
|
1608
1439
|
|
1609
1440
|
Parameters
|
@@ -1612,7 +1443,7 @@ class SolutionArchitect(Client):
|
|
1612
1443
|
guid of the first information supply chain to link.
|
1613
1444
|
nested_chain_guid: str
|
1614
1445
|
guid of the second information supply chain to link.
|
1615
|
-
body: dict, optional
|
1446
|
+
body: dict | DeleteRequestBody, optional
|
1616
1447
|
The body describing the link between the two segments.
|
1617
1448
|
|
1618
1449
|
Returns
|
@@ -1633,7 +1464,7 @@ class SolutionArchitect(Client):
|
|
1633
1464
|
|
1634
1465
|
Body structure:
|
1635
1466
|
{
|
1636
|
-
"class": "
|
1467
|
+
"class": "DeleteRequestBody",
|
1637
1468
|
"externalSourceGUID": "add guid here",
|
1638
1469
|
"externalSourceName": "add qualified name here",
|
1639
1470
|
"effectiveTime": {{isotime}},
|
@@ -1645,8 +1476,8 @@ class SolutionArchitect(Client):
|
|
1645
1476
|
loop.run_until_complete(self._async_decompose_info_supply_chains(chain_guid,
|
1646
1477
|
nested_chain_guid, body))
|
1647
1478
|
|
1648
|
-
|
1649
|
-
async def _async_delete_info_supply_chain(self, guid: str, body: dict = None, cascade_delete: bool = False) -> None:
|
1479
|
+
@dynamic_catch
|
1480
|
+
async def _async_delete_info_supply_chain(self, guid: str, body: dict | DeleteRequestBody = None, cascade_delete: bool = False) -> None:
|
1650
1481
|
"""Delete an information supply chain. Async Version.
|
1651
1482
|
|
1652
1483
|
Parameters
|
@@ -1662,8 +1493,6 @@ class SolutionArchitect(Client):
|
|
1662
1493
|
-------
|
1663
1494
|
None
|
1664
1495
|
|
1665
|
-
Raises
|
1666
|
-
------
|
1667
1496
|
Raises
|
1668
1497
|
------
|
1669
1498
|
InvalidParameterException
|
@@ -1678,7 +1507,7 @@ class SolutionArchitect(Client):
|
|
1678
1507
|
|
1679
1508
|
Body structure:
|
1680
1509
|
{
|
1681
|
-
"class": "
|
1510
|
+
"class": "DeleteRequestBody",
|
1682
1511
|
"externalSourceGUID": "add guid here",
|
1683
1512
|
"externalSourceName": "add qualified name here",
|
1684
1513
|
"effectiveTime": {{isotime}},
|
@@ -1686,25 +1515,23 @@ class SolutionArchitect(Client):
|
|
1686
1515
|
"forDuplicateProcessing": false
|
1687
1516
|
}
|
1688
1517
|
"""
|
1689
|
-
|
1690
|
-
cascaded_s = str(cascade_delete).lower()
|
1518
|
+
|
1691
1519
|
|
1692
1520
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
1693
|
-
f"information-supply-chains/{guid}/delete
|
1694
|
-
|
1695
|
-
|
1696
|
-
|
1697
|
-
|
1698
|
-
|
1699
|
-
|
1700
|
-
def delete_info_supply_chain(self, guid: str, body: dict = None, cascade_delete: bool = False) -> None:
|
1521
|
+
f"information-supply-chains/{guid}/delete")
|
1522
|
+
|
1523
|
+
await self._async_delete_request(url, body, cascade_delete=cascade_delete)
|
1524
|
+
logger.info(f"Deleted Info Supply Chain {guid} with cascade {cascade_delete}")
|
1525
|
+
|
1526
|
+
@dynamic_catch
|
1527
|
+
def delete_info_supply_chain(self, guid: str, body: dict | DeleteRequestBody= None, cascade_delete: bool = False) -> None:
|
1701
1528
|
""" Delete an information supply chain.
|
1702
1529
|
|
1703
1530
|
Parameters
|
1704
1531
|
----------
|
1705
1532
|
guid: str
|
1706
1533
|
guid of the information supply chain to delete.
|
1707
|
-
body: dict, optional
|
1534
|
+
body: dict | DeleteRequestBody, optional
|
1708
1535
|
A dictionary containing parameters of the deletion.
|
1709
1536
|
cascade_delete: bool, optional
|
1710
1537
|
If true, the child objects will also be deleted.
|
@@ -1726,7 +1553,7 @@ class SolutionArchitect(Client):
|
|
1726
1553
|
|
1727
1554
|
Body structure:
|
1728
1555
|
{
|
1729
|
-
"class": "
|
1556
|
+
"class": "DeleteRequestBody",
|
1730
1557
|
"externalSourceGUID": "add guid here",
|
1731
1558
|
"externalSourceName": "add qualified name here",
|
1732
1559
|
"effectiveTime": {{isotime}},
|
@@ -1737,8 +1564,13 @@ class SolutionArchitect(Client):
|
|
1737
1564
|
loop = asyncio.get_event_loop()
|
1738
1565
|
loop.run_until_complete(self._async_delete_info_supply_chain(guid, body, cascade_delete))
|
1739
1566
|
|
1740
|
-
def find_all_information_supply_chains(self,
|
1741
|
-
|
1567
|
+
def find_all_information_supply_chains(self, search_string: str = "*", classification_names: list[str] = None,
|
1568
|
+
metadata_element_types: list[str] = None,
|
1569
|
+
starts_with: bool = True, ends_with: bool = False,
|
1570
|
+
ignore_case: bool = False, start_from: int = 0,
|
1571
|
+
page_size: int = 0, output_format: str = 'JSON',
|
1572
|
+
output_format_set: str = None,
|
1573
|
+
body: dict| SearchStringRequestBody = None) -> (list[dict] | str):
|
1742
1574
|
""" Retrieve a list of all information supply chains
|
1743
1575
|
Parameters
|
1744
1576
|
----------
|
@@ -1785,14 +1617,15 @@ class SolutionArchitect(Client):
|
|
1785
1617
|
}
|
1786
1618
|
"""
|
1787
1619
|
|
1788
|
-
return self.find_information_supply_chains("*",
|
1789
|
-
output_format=output_format)
|
1620
|
+
return self.find_information_supply_chains("*", classification_names, metadata_element_types, starts_with, ends_with, ignore_case, start_from, page_size, output_format, output_format_set, body)
|
1790
1621
|
|
1791
|
-
async def _async_find_information_supply_chains(self,
|
1622
|
+
async def _async_find_information_supply_chains(self, search_string: str = "*", classification_names: list[str] = None,
|
1623
|
+
metadata_element_types: list[str] = None,
|
1792
1624
|
starts_with: bool = True, ends_with: bool = False,
|
1793
1625
|
ignore_case: bool = False, start_from: int = 0,
|
1794
|
-
page_size: int =
|
1795
|
-
|
1626
|
+
page_size: int = 0, output_format: str = 'JSON',
|
1627
|
+
output_format_set: str = None,
|
1628
|
+
body: dict| SearchStringRequestBody = None) -> list[dict] | str:
|
1796
1629
|
"""Retrieve the list of information supply chain metadata elements that contain the search string.
|
1797
1630
|
https://egeria-project.org/concepts/information-supply-chain
|
1798
1631
|
Async version.
|
@@ -1848,39 +1681,26 @@ class SolutionArchitect(Client):
|
|
1848
1681
|
}
|
1849
1682
|
|
1850
1683
|
"""
|
1851
|
-
starts_with_s = str(starts_with).lower()
|
1852
|
-
ends_with_s = str(ends_with).lower()
|
1853
|
-
ignore_case_s = str(ignore_case).lower()
|
1854
|
-
|
1855
|
-
possible_query_params = query_string(
|
1856
|
-
[("addImplementation", add_implementation), ("startFrom", start_from), ("pageSize", page_size),
|
1857
|
-
("startsWith", starts_with_s), ("endsWith", ends_with_s), ("ignoreCase", ignore_case_s), ])
|
1858
|
-
|
1859
|
-
if search_filter is None or search_filter == "*":
|
1860
|
-
search_filter = None
|
1861
|
-
|
1862
|
-
if body is None:
|
1863
|
-
body = {
|
1864
|
-
"filter": search_filter,
|
1865
|
-
}
|
1866
|
-
else:
|
1867
|
-
body["filter"] = search_filter
|
1868
|
-
|
1869
|
-
url = (f"{self.solution_architect_command_root}/information-supply-chains/by-search-string"
|
1870
|
-
f"{possible_query_params}")
|
1871
|
-
|
1872
|
-
response: Response = await self._async_make_request("POST", url, body_slimmer(body))
|
1873
|
-
element = response.json().get("elements", NO_ELEMENTS_FOUND)
|
1874
|
-
if element == NO_ELEMENTS_FOUND:
|
1875
|
-
return NO_ELEMENTS_FOUND
|
1876
|
-
if output_format != 'JSON': # return a simplified markdown representation
|
1877
|
-
return self.generate_info_supply_chain_output(element, search_filter, output_format)
|
1878
|
-
return response.json().get("elements", NO_ELEMENTS_FOUND)
|
1879
1684
|
|
1880
|
-
|
1881
|
-
|
1882
|
-
|
1883
|
-
|
1685
|
+
url = f"{self.solution_architect_command_root}/information-supply-chains/by-search-string"
|
1686
|
+
return await self._async_find_request(url, _type="GovernanceDefinition",
|
1687
|
+
_gen_output=self.generate_info_supply_chain_output,
|
1688
|
+
search_string=search_string, classification_names=classification_names,
|
1689
|
+
metadata_element_types=metadata_element_types,
|
1690
|
+
starts_with=starts_with, ends_with=ends_with, ignore_case=ignore_case,
|
1691
|
+
start_from=start_from, page_size=page_size,
|
1692
|
+
output_format=output_format, output_format_set=output_format_set,
|
1693
|
+
body=body)
|
1694
|
+
|
1695
|
+
|
1696
|
+
|
1697
|
+
def find_information_supply_chains(self, search_string: str = "*", classification_names: list[str] = None,
|
1698
|
+
metadata_element_types: list[str] = None,
|
1699
|
+
starts_with: bool = True, ends_with: bool = False,
|
1700
|
+
ignore_case: bool = False, start_from: int = 0,
|
1701
|
+
page_size: int = 0, output_format: str = 'JSON',
|
1702
|
+
output_format_set: str = None,
|
1703
|
+
body: dict| SearchStringRequestBody = None) -> list[dict] | str:
|
1884
1704
|
"""Retrieve the list of information supply chain metadata elements that contain the search string.
|
1885
1705
|
https://egeria-project.org/concepts/information-supply-chain
|
1886
1706
|
|
@@ -1929,7 +1749,7 @@ class SolutionArchitect(Client):
|
|
1929
1749
|
-----
|
1930
1750
|
|
1931
1751
|
{
|
1932
|
-
"class" : "
|
1752
|
+
"class" : "SearchStringRequestBody",
|
1933
1753
|
"asOfTime" : "{{$isoTimestamp}}",
|
1934
1754
|
"effectiveTime" : "{{$isoTimestamp}}",
|
1935
1755
|
"forLineage" : false,
|
@@ -1943,8 +1763,10 @@ class SolutionArchitect(Client):
|
|
1943
1763
|
|
1944
1764
|
loop = asyncio.get_event_loop()
|
1945
1765
|
response = loop.run_until_complete(
|
1946
|
-
self._async_find_information_supply_chains(
|
1947
|
-
|
1766
|
+
self._async_find_information_supply_chains(search_string, classification_names, metadata_element_types,
|
1767
|
+
starts_with, ends_with, ignore_case,
|
1768
|
+
start_from, page_size, output_format,
|
1769
|
+
output_format_set, body))
|
1948
1770
|
return response
|
1949
1771
|
|
1950
1772
|
async def _async_get_info_supply_chain_by_name(self, search_filter: str, body: dict = None,
|
@@ -2195,7 +2017,8 @@ class SolutionArchitect(Client):
|
|
2195
2017
|
# Blueprints
|
2196
2018
|
#
|
2197
2019
|
|
2198
|
-
|
2020
|
+
@dynamic_catch
|
2021
|
+
async def _async_create_solution_blueprint(self, body: dict | NewElementRequestBody) -> str:
|
2199
2022
|
""" Create a solution blueprint. To set a lifecycle status
|
2200
2023
|
use a NewSolutionElementRequestBody which has a default status of DRAFT. Using a
|
2201
2024
|
NewElementRequestBody sets the status to ACTIVE.
|
@@ -2203,7 +2026,7 @@ class SolutionArchitect(Client):
|
|
2203
2026
|
|
2204
2027
|
Parameters
|
2205
2028
|
----------
|
2206
|
-
body: dict
|
2029
|
+
body: dict | NewElementRequestBody
|
2207
2030
|
A dictionary containing the definition of the blueprint to create.
|
2208
2031
|
|
2209
2032
|
Returns
|
@@ -2251,6 +2074,8 @@ class SolutionArchitect(Client):
|
|
2251
2074
|
"displayName": "add short name here",
|
2252
2075
|
"description": "add description here",
|
2253
2076
|
"versionIdentifier": "add version here",
|
2077
|
+
"userDefinedStatus" : "add status here",
|
2078
|
+
"lifecycleStatus": "DRAFT"
|
2254
2079
|
"additionalProperties": {
|
2255
2080
|
"property1": "propertyValue1",
|
2256
2081
|
"property2": "propertyValue2"
|
@@ -2308,18 +2133,17 @@ class SolutionArchitect(Client):
|
|
2308
2133
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
2309
2134
|
f"solution-blueprints")
|
2310
2135
|
|
2311
|
-
|
2312
|
-
|
2313
|
-
return response.json().get("guid", "Blueprint not created")
|
2136
|
+
return await self._async_create_element_body_request(url, ["SolutionBlueprintProperties"], body)
|
2314
2137
|
|
2315
|
-
|
2138
|
+
@dynamic_catch
|
2139
|
+
def create_solution_blueprint(self, body: dict | NewElementRequestBody) -> str:
|
2316
2140
|
""" Create a solution blueprint. To set a lifecycle status
|
2317
2141
|
use a NewSolutionElementRequestBody which has a default status of DRAFT. Using a
|
2318
2142
|
NewElementRequestBody sets the status to ACTIVE.
|
2319
2143
|
|
2320
2144
|
Parameters
|
2321
2145
|
----------
|
2322
|
-
body: dict
|
2146
|
+
body: dict | NewElementRequestBody
|
2323
2147
|
A dictionary containing the definition of the blueprint to create.
|
2324
2148
|
|
2325
2149
|
Returns
|
@@ -2420,13 +2244,14 @@ class SolutionArchitect(Client):
|
|
2420
2244
|
"forDuplicateProcessing" : false
|
2421
2245
|
}
|
2422
2246
|
|
2423
|
-
|
2247
|
+
"""
|
2424
2248
|
|
2425
2249
|
loop = asyncio.get_event_loop()
|
2426
2250
|
response = loop.run_until_complete(self._async_create_solution_blueprint(body))
|
2427
2251
|
return response
|
2428
2252
|
|
2429
|
-
|
2253
|
+
@dynamic_catch
|
2254
|
+
async def _async_create_solution_blueprint_from_template(self, body: dict | TemplateRequestBody) -> str:
|
2430
2255
|
""" Create a new solution blueprint using an existing metadata element
|
2431
2256
|
as a template. The template defines additional classifications and relationships that should be added to
|
2432
2257
|
the new element. Async Version.
|
@@ -2434,7 +2259,7 @@ class SolutionArchitect(Client):
|
|
2434
2259
|
|
2435
2260
|
Parameters
|
2436
2261
|
----------
|
2437
|
-
body: dict
|
2262
|
+
body: dict | TemplateRequestBody
|
2438
2263
|
A dictionary containing the definition of the solution blueprint to create.
|
2439
2264
|
|
2440
2265
|
Returns
|
@@ -2499,19 +2324,28 @@ class SolutionArchitect(Client):
|
|
2499
2324
|
"""
|
2500
2325
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
2501
2326
|
f"solution-blueprints/from-template")
|
2327
|
+
if isinstance(body, TemplateRequestBody):
|
2328
|
+
validated_body = body
|
2329
|
+
|
2330
|
+
elif isinstance(body, dict):
|
2331
|
+
validated_body = self._template_request_adapter.validate_python(body)
|
2502
2332
|
|
2503
|
-
|
2333
|
+
json_body = validated_body.model_dump_json(indent=2, exclude_none=True)
|
2334
|
+
logger.info(json_body)
|
2335
|
+
resp = await self._async_make_request("POST", url, json_body, is_json=True)
|
2336
|
+
logger.info(f"Create Blueprint from template with GUID: {resp.json().get('guid')}")
|
2337
|
+
return resp.json().get("guid", NO_GUID_RETURNED)
|
2504
2338
|
|
2505
|
-
return response.json().get("guid", "Blueprint not created")
|
2506
2339
|
|
2507
|
-
|
2340
|
+
@dynamic_catch
|
2341
|
+
def create_solution_blueprint_from_template(self, body: dict | TemplateRequestBody) -> str:
|
2508
2342
|
""" Create a new solution blueprint using an existing metadata element
|
2509
2343
|
as a template. The template defines additional classifications and relationships that should be added to
|
2510
2344
|
the new element.
|
2511
2345
|
|
2512
2346
|
Parameters
|
2513
2347
|
----------
|
2514
|
-
body: dict
|
2348
|
+
body: dict | TemplateRequestBody
|
2515
2349
|
A dictionary containing the definition of the solution blueprint to create.
|
2516
2350
|
|
2517
2351
|
Returns
|
@@ -2519,8 +2353,6 @@ class SolutionArchitect(Client):
|
|
2519
2353
|
|
2520
2354
|
str - guid of the supply chain created.
|
2521
2355
|
|
2522
|
-
Raises
|
2523
|
-
------
|
2524
2356
|
Raises
|
2525
2357
|
------
|
2526
2358
|
InvalidParameterException
|
@@ -2578,26 +2410,21 @@ class SolutionArchitect(Client):
|
|
2578
2410
|
response = loop.run_until_complete(self._async_create_solution_blueprint_from_template(body))
|
2579
2411
|
return response
|
2580
2412
|
|
2581
|
-
|
2582
|
-
|
2583
|
-
""" Update
|
2413
|
+
@dynamic_catch
|
2414
|
+
async def _async_update_solution_blueprint(self, guid: str, body: dict | UpdateElementRequestBody) -> None:
|
2415
|
+
""" Update a solution blueprint. Async Version.
|
2584
2416
|
|
2585
2417
|
Parameters
|
2586
2418
|
----------
|
2587
2419
|
guid: str
|
2588
2420
|
guid of the information supply chain to update.
|
2589
|
-
body: dict
|
2421
|
+
body: dict | UpdateElementRequestBody
|
2590
2422
|
A dictionary containing the updates to the supply chain.
|
2591
|
-
replace_all_properties: bool, optional
|
2592
|
-
Whether to replace all properties with those provided in the body or to merge with existing properties.
|
2593
|
-
|
2594
2423
|
Returns
|
2595
2424
|
-------
|
2596
2425
|
|
2597
2426
|
None
|
2598
2427
|
|
2599
|
-
Raises
|
2600
|
-
------
|
2601
2428
|
Raises
|
2602
2429
|
------
|
2603
2430
|
InvalidParameterException
|
@@ -2633,24 +2460,22 @@ class SolutionArchitect(Client):
|
|
2633
2460
|
}
|
2634
2461
|
}
|
2635
2462
|
"""
|
2636
|
-
|
2637
|
-
replace_all_properties_s = str(replace_all_properties).lower()
|
2463
|
+
|
2638
2464
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
2639
|
-
f"solution-blueprints/{guid}/update
|
2465
|
+
f"solution-blueprints/{guid}/update")
|
2640
2466
|
|
2641
|
-
await self.
|
2467
|
+
await self._async_update_element_body_request(url, ["SolutionBlueprintProperties"],body)
|
2642
2468
|
|
2643
|
-
|
2469
|
+
@dynamic_catch
|
2470
|
+
def update_solution_blueprint(self, guid: str, body: dict | UpdateElementRequestBody) -> None:
|
2644
2471
|
""" Update the properties of a solution blueprint. Async Version.
|
2645
2472
|
|
2646
2473
|
Parameters
|
2647
2474
|
----------
|
2648
2475
|
guid: str
|
2649
2476
|
guid of the information supply chain to update.
|
2650
|
-
body: dict
|
2651
|
-
A dictionary containing the updates to the
|
2652
|
-
replace_all_properties: bool, optional
|
2653
|
-
Whether to replace all properties with those provided in the body or to merge with existing properties.
|
2477
|
+
body: dict | UpdateElementRequestBody
|
2478
|
+
A dictionary containing the updates to the blueprint.
|
2654
2479
|
|
2655
2480
|
Returns
|
2656
2481
|
-------
|
@@ -2696,18 +2521,110 @@ class SolutionArchitect(Client):
|
|
2696
2521
|
}
|
2697
2522
|
"""
|
2698
2523
|
loop = asyncio.get_event_loop()
|
2699
|
-
loop.run_until_complete(self._async_update_solution_blueprint(guid, body
|
2524
|
+
loop.run_until_complete(self._async_update_solution_blueprint(guid, body))
|
2525
|
+
|
2526
|
+
|
2527
|
+
@dynamic_catch
|
2528
|
+
async def _async_delete_solution_blueprint(self, guid: str, body: dict | DeleteRequestBody, cascade: bool = False) -> None:
|
2529
|
+
""" Delete a solution blueprint. Async Version.
|
2530
|
+
Parameters
|
2531
|
+
----------
|
2532
|
+
guid: str
|
2533
|
+
guid of the information supply chain to delete.
|
2534
|
+
body: dict, optional
|
2535
|
+
A dictionary containing parameters of the deletion.
|
2536
|
+
cascade: bool, optional
|
2537
|
+
If true, the child objects will also be deleted.
|
2538
|
+
|
2539
|
+
Returns
|
2540
|
+
-------
|
2541
|
+
None
|
2542
|
+
|
2543
|
+
Raises
|
2544
|
+
------
|
2545
|
+
InvalidParameterException
|
2546
|
+
one of the parameters is null or invalid or
|
2547
|
+
PropertyServerException
|
2548
|
+
There is a problem adding the element properties to the metadata repository or
|
2549
|
+
UserNotAuthorizedException
|
2550
|
+
the requesting user is not authorized to issue this request.
|
2551
|
+
|
2552
|
+
Notes
|
2553
|
+
----
|
2554
|
+
|
2555
|
+
Body structure:
|
2556
|
+
{
|
2557
|
+
"class": "DeleteRequestBody",
|
2558
|
+
"externalSourceGUID": "add guid here",
|
2559
|
+
"externalSourceName": "add qualified name here",
|
2560
|
+
"effectiveTime": {{isotime}},
|
2561
|
+
"forLineage": false,
|
2562
|
+
"forDuplicateProcessing": false
|
2563
|
+
}
|
2564
|
+
"""
|
2565
|
+
|
2566
|
+
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
2567
|
+
f"information-supply-chains/{guid}/delete")
|
2568
|
+
|
2569
|
+
await self._async_delete_request(url, body, cascade_delete=cascade)
|
2570
|
+
logger.info(f"Deleted Info Supply Chain {guid} with cascade {cascade}")
|
2571
|
+
|
2572
|
+
@dynamic_catch
|
2573
|
+
def delete_solution_blueprint(self, guid: str, body: dict | DeleteRequestBody = None,
|
2574
|
+
cascade: bool = False) -> None:
|
2575
|
+
""" Delete an Solution Blueprint.
|
2576
|
+
|
2577
|
+
Parameters
|
2578
|
+
----------
|
2579
|
+
guid: str
|
2580
|
+
guid of the information supply chain to delete.
|
2581
|
+
body: dict | DeleteRequestBody, optional
|
2582
|
+
A dictionary containing parameters of the deletion.
|
2583
|
+
cascade: bool, optional
|
2584
|
+
If true, the child objects will also be deleted.
|
2585
|
+
Returns
|
2586
|
+
-------
|
2587
|
+
None
|
2588
|
+
|
2589
|
+
Raises
|
2590
|
+
------
|
2591
|
+
InvalidParameterException
|
2592
|
+
one of the parameters is null or invalid or
|
2593
|
+
PropertyServerException
|
2594
|
+
There is a problem adding the element properties to the metadata repository or
|
2595
|
+
UserNotAuthorizedException
|
2596
|
+
the requesting user is not authorized to issue this request.
|
2597
|
+
|
2598
|
+
Notes
|
2599
|
+
----
|
2600
|
+
|
2601
|
+
Body structure:
|
2602
|
+
{
|
2603
|
+
"class": "DeleteRequestBody",
|
2604
|
+
"externalSourceGUID": "add guid here",
|
2605
|
+
"externalSourceName": "add qualified name here",
|
2606
|
+
"effectiveTime": {{isotime}},
|
2607
|
+
"forLineage": false,
|
2608
|
+
"forDuplicateProcessing": false
|
2609
|
+
}
|
2610
|
+
"""
|
2611
|
+
loop = asyncio.get_event_loop()
|
2612
|
+
loop.run_until_complete(self._async_delete_info_supply_chain(guid, body, cascade))
|
2613
|
+
|
2700
2614
|
|
2701
|
-
|
2702
|
-
|
2615
|
+
@dynamic_catch
|
2616
|
+
async def _async_update_solution_element_status(self, guid: str, status: str= None, body: dict| UpdateStatusRequestBody = None,
|
2617
|
+
) -> None:
|
2703
2618
|
""" Update the properties of a blueprint, solution component, or solution port. Async Version.
|
2704
2619
|
|
2705
2620
|
Parameters
|
2706
2621
|
----------
|
2707
2622
|
guid: str
|
2708
2623
|
guid of the information supply chain to update.
|
2709
|
-
body: dict
|
2624
|
+
body: dict | UpdateStatusRequestBody, optional
|
2710
2625
|
A dictionary containing the updates to the supply chain.
|
2626
|
+
status: str, optional
|
2627
|
+
The status to update the supply chain to.
|
2711
2628
|
|
2712
2629
|
Returns
|
2713
2630
|
-------
|
@@ -2728,7 +2645,7 @@ class SolutionArchitect(Client):
|
|
2728
2645
|
|
2729
2646
|
Body structure:
|
2730
2647
|
{
|
2731
|
-
"class" : "
|
2648
|
+
"class" : "UpdateStatusRequestBody",
|
2732
2649
|
"status" : "APPROVED",
|
2733
2650
|
"externalSourceGUID": "add guid here",
|
2734
2651
|
"externalSourceName": "add qualified name here",
|
@@ -2737,14 +2654,14 @@ class SolutionArchitect(Client):
|
|
2737
2654
|
"forDuplicateProcessing" : false
|
2738
2655
|
}
|
2739
2656
|
"""
|
2740
|
-
|
2741
|
-
replace_all_properties_s = str(replace_all_properties).lower()
|
2657
|
+
|
2742
2658
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
2743
|
-
f"solution-blueprints/{guid}/update
|
2659
|
+
f"solution-blueprints/{guid}/update")
|
2744
2660
|
|
2745
|
-
await self.
|
2661
|
+
await self._async_update_status_request(url, status, body)
|
2746
2662
|
|
2747
|
-
|
2663
|
+
@dynamic_catch
|
2664
|
+
def update_solution_element_status(self, guid: str, status: str = None, body: dict| UpdateStatusRequestBody = None) -> None:
|
2748
2665
|
""" Update the status of a blueprint, solution component, or solution port.
|
2749
2666
|
|
2750
2667
|
Parameters
|
@@ -2782,12 +2699,12 @@ class SolutionArchitect(Client):
|
|
2782
2699
|
}
|
2783
2700
|
"""
|
2784
2701
|
loop = asyncio.get_event_loop()
|
2785
|
-
loop.run_until_complete(self._async_update_solution_element_status(guid, body))
|
2786
|
-
|
2702
|
+
loop.run_until_complete(self._async_update_solution_element_status(guid = guid, status= status, body=body))
|
2787
2703
|
|
2788
2704
|
|
2705
|
+
@dynamic_catch
|
2789
2706
|
async def _async_link_solution_component_to_blueprint(self, blueprint_guid: str, component_guid: str,
|
2790
|
-
body: dict) -> None:
|
2707
|
+
body: dict | NewRelationshipRequestBody) -> None:
|
2791
2708
|
""" Connect a solution component to a blueprint. Async Version.
|
2792
2709
|
|
2793
2710
|
Parameters
|
@@ -2796,7 +2713,7 @@ class SolutionArchitect(Client):
|
|
2796
2713
|
guid of the blueprint to connect to.
|
2797
2714
|
component_guid: str
|
2798
2715
|
guid of the component to link.
|
2799
|
-
body: dict
|
2716
|
+
body: dict | NewRelationshipRequestBody
|
2800
2717
|
The body describing the link.
|
2801
2718
|
|
2802
2719
|
Returns
|
@@ -2817,7 +2734,7 @@ class SolutionArchitect(Client):
|
|
2817
2734
|
|
2818
2735
|
Body structure:
|
2819
2736
|
{
|
2820
|
-
"class" : "
|
2737
|
+
"class" : "NewRelationshipRequestBody",
|
2821
2738
|
"properties": {
|
2822
2739
|
"class": "SolutionBlueprintCompositionProperties",
|
2823
2740
|
"role": "Add role that the component plays in the solution blueprint here",
|
@@ -2833,14 +2750,15 @@ class SolutionArchitect(Client):
|
|
2833
2750
|
}
|
2834
2751
|
|
2835
2752
|
"""
|
2836
|
-
|
2837
|
-
validate_guid(component_guid)
|
2753
|
+
|
2838
2754
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
2839
2755
|
f"solution-blueprints/{blueprint_guid}/solution-components/{component_guid}/attach")
|
2840
2756
|
|
2841
|
-
await self.
|
2757
|
+
await self._async_new_relationship_request(url, ["SolutionComponentCompositionProperties"], body)
|
2758
|
+
logger.info(f"Linked component to blueprint {component_guid} -> {blueprint_guid}")
|
2842
2759
|
|
2843
|
-
|
2760
|
+
@dynamic_catch
|
2761
|
+
def link_solution_component_to_blueprint(self, blueprint_guid: str, component_guid: str, body: dict | NewRelationshipRequestBody) -> None:
|
2844
2762
|
""" Connect a solution component to a blueprint.
|
2845
2763
|
|
2846
2764
|
Parameters
|
@@ -2849,7 +2767,7 @@ class SolutionArchitect(Client):
|
|
2849
2767
|
guid of the blueprint to connect to.
|
2850
2768
|
component_guid: str
|
2851
2769
|
guid of the component to link.
|
2852
|
-
body: dict
|
2770
|
+
body: dict | NewRelationshipRequestBody
|
2853
2771
|
The body describing the link.
|
2854
2772
|
|
2855
2773
|
Returns
|
@@ -2888,8 +2806,9 @@ class SolutionArchitect(Client):
|
|
2888
2806
|
loop = asyncio.get_event_loop()
|
2889
2807
|
loop.run_until_complete(self._async_link_solution_component_to_blueprint(blueprint_guid, component_guid, body))
|
2890
2808
|
|
2809
|
+
@dynamic_catch
|
2891
2810
|
async def _async_detach_solution_component_from_blueprint(self, blueprint_guid: str, component_guid: str,
|
2892
|
-
body: dict = None) -> None:
|
2811
|
+
body: dict | DeleteRequestBody = None) -> None:
|
2893
2812
|
""" Detach a solution component from a solution blueprint.
|
2894
2813
|
Async Version.
|
2895
2814
|
|
@@ -2929,15 +2848,17 @@ class SolutionArchitect(Client):
|
|
2929
2848
|
}
|
2930
2849
|
|
2931
2850
|
"""
|
2932
|
-
|
2933
|
-
validate_guid(component_guid)
|
2851
|
+
|
2934
2852
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
2935
2853
|
f"solution-blueprints/{blueprint_guid}/solution-components/{component_guid}/detach")
|
2936
2854
|
|
2937
|
-
await self.
|
2855
|
+
await self._async_delete_request(url, body)
|
2856
|
+
logger.info(
|
2857
|
+
f"Detached component from blueprint {component_guid} -> {blueprint_guid}")
|
2938
2858
|
|
2859
|
+
@dynamic_catch
|
2939
2860
|
def detach_solution_component_from_blueprint(self, blueprint_guid: str, component_guid: str,
|
2940
|
-
body: dict = None) -> None:
|
2861
|
+
body: dict | DeleteRequestBody = None) -> None:
|
2941
2862
|
""" Detach a solution component from a solution blueprint.
|
2942
2863
|
|
2943
2864
|
Parameters
|
@@ -2980,8 +2901,10 @@ class SolutionArchitect(Client):
|
|
2980
2901
|
loop.run_until_complete(
|
2981
2902
|
self._async_detach_solution_component_from_blueprint(blueprint_guid, component_guid, body))
|
2982
2903
|
|
2904
|
+
|
2905
|
+
@dynamic_catch
|
2983
2906
|
async def _async_delete_solution_blueprint(self, blueprint_guid: str, cascade_delete: bool = False,
|
2984
|
-
body: dict = None) -> None:
|
2907
|
+
body: dict | DeleteRequestBody = None) -> None:
|
2985
2908
|
"""Delete a solution blueprint. Async Version.
|
2986
2909
|
|
2987
2910
|
Parameters
|
@@ -3022,15 +2945,14 @@ class SolutionArchitect(Client):
|
|
3022
2945
|
}
|
3023
2946
|
"""
|
3024
2947
|
validate_guid(blueprint_guid)
|
3025
|
-
|
2948
|
+
|
3026
2949
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
3027
|
-
f"solution-blueprints/{blueprint_guid}/delete
|
3028
|
-
|
3029
|
-
|
3030
|
-
else:
|
3031
|
-
await self._async_make_request("POST", url)
|
2950
|
+
f"solution-blueprints/{blueprint_guid}/delete")
|
2951
|
+
await self._async_delete_request(url, body, cascade_delete=cascade_delete)
|
2952
|
+
logger.info(f"Deleted Blueprint {blueprint_guid} with cascade {cascade_delete}")
|
3032
2953
|
|
3033
|
-
|
2954
|
+
@dynamic_catch
|
2955
|
+
def delete_solution_blueprint(self, blueprint_guid: str, cascade_delete: bool = False, body: dict | DeleteRequestBody = None) -> None:
|
3034
2956
|
""" Delete a solution blueprint.
|
3035
2957
|
Parameters
|
3036
2958
|
----------
|
@@ -3071,10 +2993,15 @@ class SolutionArchitect(Client):
|
|
3071
2993
|
loop.run_until_complete(self._async_delete_solution_blueprint(blueprint_guid, cascade_delete, body))
|
3072
2994
|
|
3073
2995
|
|
3074
|
-
|
3075
|
-
|
3076
|
-
|
3077
|
-
|
2996
|
+
|
2997
|
+
|
2998
|
+
async def _async_find_solution_blueprints(self, search_string: str = "*", classification_names: list[str] = None,
|
2999
|
+
metadata_element_types: list[str] = None,
|
3000
|
+
starts_with: bool = True, ends_with: bool = False,
|
3001
|
+
ignore_case: bool = False, start_from: int = 0,
|
3002
|
+
page_size: int = 0, output_format: str = 'JSON',
|
3003
|
+
output_format_set: str = None,
|
3004
|
+
body: dict| SearchStringRequestBody = None) -> list[dict] | str:
|
3078
3005
|
"""Retrieve the solution blueprint elements that contain the search string.
|
3079
3006
|
https://egeria-project.org/concepts/solution-blueprint
|
3080
3007
|
Async version.
|
@@ -3127,37 +3054,28 @@ class SolutionArchitect(Client):
|
|
3127
3054
|
}
|
3128
3055
|
|
3129
3056
|
"""
|
3130
|
-
starts_with_s = str(starts_with).lower()
|
3131
|
-
ends_with_s = str(ends_with).lower()
|
3132
|
-
ignore_case_s = str(ignore_case).lower()
|
3133
3057
|
|
3134
|
-
possible_query_params = query_string(
|
3135
|
-
[("startFrom", start_from), ("pageSize", page_size),
|
3136
|
-
("startsWith", starts_with_s), ("endsWith", ends_with_s), ("ignoreCase", ignore_case_s), ])
|
3137
3058
|
|
3138
|
-
if search_filter is None or search_filter == "*":
|
3139
|
-
search_filter = None
|
3140
3059
|
|
3141
|
-
if body is None:
|
3142
|
-
body = {
|
3143
|
-
"filter": search_filter,
|
3144
|
-
}
|
3145
|
-
else:
|
3146
|
-
body["filter"] = search_filter
|
3147
3060
|
|
3148
|
-
url =
|
3149
|
-
|
3150
|
-
|
3151
|
-
|
3152
|
-
|
3153
|
-
|
3154
|
-
|
3155
|
-
|
3156
|
-
|
3061
|
+
url = f"{self.solution_architect_command_root}/solution-blueprints/by-search-string"
|
3062
|
+
return await self._async_find_request(url, _type="GovernanceDefinition",
|
3063
|
+
_gen_output=self.generate_info_supply_chain_output,
|
3064
|
+
search_string=search_string, classification_names=classification_names,
|
3065
|
+
metadata_element_types=metadata_element_types,
|
3066
|
+
starts_with=starts_with, ends_with=ends_with, ignore_case=ignore_case,
|
3067
|
+
start_from=start_from, page_size=page_size,
|
3068
|
+
output_format=output_format, output_format_set=output_format_set,
|
3069
|
+
body=body)
|
3070
|
+
|
3157
3071
|
|
3158
|
-
def find_solution_blueprints(self,
|
3159
|
-
|
3160
|
-
|
3072
|
+
def find_solution_blueprints(self, search_string: str = "*", classification_names: list[str] = None,
|
3073
|
+
metadata_element_types: list[str] = None,
|
3074
|
+
starts_with: bool = True, ends_with: bool = False,
|
3075
|
+
ignore_case: bool = False, start_from: int = 0,
|
3076
|
+
page_size: int = 0, output_format: str = 'JSON',
|
3077
|
+
output_format_set: str = None,
|
3078
|
+
body: dict| SearchStringRequestBody = None) -> list[dict] | str:
|
3161
3079
|
"""Retrieve the list of solution blueprint elements that contain the search string.
|
3162
3080
|
https://egeria-project.org/concepts/solution-blueprint
|
3163
3081
|
|
@@ -3217,17 +3135,24 @@ class SolutionArchitect(Client):
|
|
3217
3135
|
|
3218
3136
|
loop = asyncio.get_event_loop()
|
3219
3137
|
response = loop.run_until_complete(
|
3220
|
-
self._async_find_solution_blueprints(
|
3221
|
-
|
3138
|
+
self._async_find_solution_blueprints(search_string, classification_names, metadata_element_types,
|
3139
|
+
starts_with, ends_with, ignore_case, start_from,
|
3140
|
+
page_size, output_format, output_format_set, body))
|
3222
3141
|
return response
|
3223
3142
|
|
3224
|
-
def find_all_solution_blueprints(self,
|
3225
|
-
|
3143
|
+
def find_all_solution_blueprints(self, classification_names: list[str] = None,
|
3144
|
+
metadata_element_types: list[str] = None,
|
3145
|
+
starts_with: bool = True, ends_with: bool = False,
|
3146
|
+
ignore_case: bool = False, start_from: int = 0,
|
3147
|
+
page_size: int = 0, output_format: str = 'JSON',
|
3148
|
+
output_format_set: str = None,
|
3149
|
+
body: dict| SearchStringRequestBody = None) -> list[dict] | str:
|
3226
3150
|
"""Retrieve a list of all solution blueprint elements
|
3227
3151
|
https://egeria-project.org/concepts/solution-blueprint
|
3228
3152
|
"""
|
3229
|
-
return self.find_solution_blueprints("*",
|
3230
|
-
|
3153
|
+
return self.find_solution_blueprints("*", classification_names, metadata_element_types,
|
3154
|
+
starts_with, ends_with, ignore_case, start_from,
|
3155
|
+
page_size, output_format, output_format_set, body)
|
3231
3156
|
|
3232
3157
|
|
3233
3158
|
async def _async_get_solution_blueprint_by_guid(self, guid: str, body: dict = None,
|
@@ -3467,7 +3392,8 @@ class SolutionArchitect(Client):
|
|
3467
3392
|
# Components
|
3468
3393
|
#
|
3469
3394
|
|
3470
|
-
|
3395
|
+
@dynamic_catch
|
3396
|
+
async def _async_create_solution_component(self, body: dict | NewElementRequestBody) -> str:
|
3471
3397
|
"""Create a solution component. To set a lifecycle status
|
3472
3398
|
use a NewSolutionElementRequestBody which has a default status of DRAFT. Using a
|
3473
3399
|
NewElementRequestBody sets the status to ACTIVE.
|
@@ -3475,7 +3401,8 @@ class SolutionArchitect(Client):
|
|
3475
3401
|
|
3476
3402
|
Parameters
|
3477
3403
|
----------
|
3478
|
-
body: dict
|
3404
|
+
body: dict | NewElementRequestBody
|
3405
|
+
A dictionary containing parameters of the creation.
|
3479
3406
|
A dictionary containing the definition of the component to create.
|
3480
3407
|
|
3481
3408
|
Returns
|
@@ -3500,7 +3427,7 @@ class SolutionArchitect(Client):
|
|
3500
3427
|
|
3501
3428
|
Body structure:
|
3502
3429
|
{
|
3503
|
-
"class": "
|
3430
|
+
"class": "NewElementRequestBody",
|
3504
3431
|
"externalSourceGUID": "add guid here",
|
3505
3432
|
"externalSourceName": "add qualified name here",
|
3506
3433
|
"effectiveTime": {{isotime}},
|
@@ -3545,61 +3472,22 @@ class SolutionArchitect(Client):
|
|
3545
3472
|
"forDuplicateProcessing" : false
|
3546
3473
|
}
|
3547
3474
|
|
3548
|
-
|
3549
|
-
{
|
3550
|
-
"class" : "NewElementRequestBody",
|
3551
|
-
"anchorGUID" : "add guid here",
|
3552
|
-
"isOwnAnchor": false,
|
3553
|
-
"parentGUID": "add guid here",
|
3554
|
-
"parentRelationshipTypeName": "add type name here",
|
3555
|
-
"parentRelationshipProperties": {
|
3556
|
-
"class": "ElementProperties",
|
3557
|
-
"propertyValueMap" : {
|
3558
|
-
"description" : {
|
3559
|
-
"class": "PrimitiveTypePropertyValue",
|
3560
|
-
"typeName": "string",
|
3561
|
-
"primitiveValue" : "New description"
|
3562
|
-
}
|
3563
|
-
}
|
3564
|
-
},
|
3565
|
-
"parentAtEnd1": false,
|
3566
|
-
"properties": {
|
3567
|
-
"class" : "SolutionComponentProperties",
|
3568
|
-
"qualifiedName": "add unique name here",
|
3569
|
-
"displayName": "add short name here",
|
3570
|
-
"description": "add description here",
|
3571
|
-
"solutionComponentType": "add optional type for this component",
|
3572
|
-
"versionIdentifier": "add version for this component",
|
3573
|
-
"plannedDeployedImplementationType": "add details of the type of implementation for this component",
|
3574
|
-
"additionalProperties": {
|
3575
|
-
"property1" : "propertyValue1",
|
3576
|
-
"property2" : "propertyValue2"
|
3577
|
-
},
|
3578
|
-
"effectiveFrom": "{{$isoTimestamp}}",
|
3579
|
-
"effectiveTo": "{{$isoTimestamp}}"
|
3580
|
-
},
|
3581
|
-
"externalSourceGUID": "add guid here",
|
3582
|
-
"externalSourceName": "add qualified name here",
|
3583
|
-
"effectiveTime" : "{{$isoTimestamp}}",
|
3584
|
-
"forLineage" : false,
|
3585
|
-
"forDuplicateProcessing" : false
|
3586
|
-
}
|
3475
|
+
|
3587
3476
|
"""
|
3588
3477
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
3589
3478
|
f"solution-components")
|
3590
3479
|
|
3591
|
-
|
3592
|
-
|
3593
|
-
return response.json().get("guid", "Solution component not created")
|
3480
|
+
return await self._async_create_element_body_request(url, ["SolutionComponentProperties"], body)
|
3594
3481
|
|
3595
|
-
|
3482
|
+
@dynamic_catch
|
3483
|
+
def create_solution_component(self, body: dict | NewElementRequestBody) -> str:
|
3596
3484
|
"""Create a solution component. To set a lifecycle status
|
3597
3485
|
use a NewSolutionElementRequestBody which has a default status of DRAFT. Using a
|
3598
3486
|
NewElementRequestBody sets the status to ACTIVE.
|
3599
3487
|
|
3600
3488
|
Parameters
|
3601
3489
|
----------
|
3602
|
-
body: dict
|
3490
|
+
body: dict | NewElementRequestBody
|
3603
3491
|
A dictionary containing the definition of the component to create.
|
3604
3492
|
|
3605
3493
|
Returns
|
@@ -3624,7 +3512,7 @@ class SolutionArchitect(Client):
|
|
3624
3512
|
|
3625
3513
|
Body structure:
|
3626
3514
|
{
|
3627
|
-
"class": "
|
3515
|
+
"class": "NewElementRequestBody",
|
3628
3516
|
"externalSourceGUID": "add guid here",
|
3629
3517
|
"externalSourceName": "add qualified name here",
|
3630
3518
|
"effectiveTime": {{isotime}},
|
@@ -3669,52 +3557,15 @@ class SolutionArchitect(Client):
|
|
3669
3557
|
"forDuplicateProcessing" : false
|
3670
3558
|
}
|
3671
3559
|
|
3672
|
-
|
3673
|
-
{
|
3674
|
-
"class" : "NewElementRequestBody",
|
3675
|
-
"anchorGUID" : "add guid here",
|
3676
|
-
"isOwnAnchor": false,
|
3677
|
-
"parentGUID": "add guid here",
|
3678
|
-
"parentRelationshipTypeName": "add type name here",
|
3679
|
-
"parentRelationshipProperties": {
|
3680
|
-
"class": "ElementProperties",
|
3681
|
-
"propertyValueMap" : {
|
3682
|
-
"description" : {
|
3683
|
-
"class": "PrimitiveTypePropertyValue",
|
3684
|
-
"typeName": "string",
|
3685
|
-
"primitiveValue" : "New description"
|
3686
|
-
}
|
3687
|
-
}
|
3688
|
-
},
|
3689
|
-
"parentAtEnd1": false,
|
3690
|
-
"properties": {
|
3691
|
-
"class" : "SolutionComponentProperties",
|
3692
|
-
"qualifiedName": "add unique name here",
|
3693
|
-
"displayName": "add short name here",
|
3694
|
-
"description": "add description here",
|
3695
|
-
"solutionComponentType": "add optional type for this component",
|
3696
|
-
"versionIdentifier": "add version for this component",
|
3697
|
-
"plannedDeployedImplementationType": "add details of the type of implementation for this component",
|
3698
|
-
"additionalProperties": {
|
3699
|
-
"property1" : "propertyValue1",
|
3700
|
-
"property2" : "propertyValue2"
|
3701
|
-
},
|
3702
|
-
"effectiveFrom": "{{$isoTimestamp}}",
|
3703
|
-
"effectiveTo": "{{$isoTimestamp}}"
|
3704
|
-
},
|
3705
|
-
"externalSourceGUID": "add guid here",
|
3706
|
-
"externalSourceName": "add qualified name here",
|
3707
|
-
"effectiveTime" : "{{$isoTimestamp}}",
|
3708
|
-
"forLineage" : false,
|
3709
|
-
"forDuplicateProcessing" : false
|
3710
|
-
}
|
3560
|
+
|
3711
3561
|
"""
|
3712
3562
|
|
3713
3563
|
loop = asyncio.get_event_loop()
|
3714
3564
|
response = loop.run_until_complete(self._async_create_solution_component(body))
|
3715
3565
|
return response
|
3716
3566
|
|
3717
|
-
|
3567
|
+
@dynamic_catch
|
3568
|
+
async def _async_create_solution_component_from_template(self, body: dict| TemplateRequestBody) -> str:
|
3718
3569
|
""" Create a new solution component using an existing metadata element
|
3719
3570
|
as a template. The template defines additional classifications and relationships that should be added to
|
3720
3571
|
the new element. Async Version.
|
@@ -3722,7 +3573,7 @@ class SolutionArchitect(Client):
|
|
3722
3573
|
|
3723
3574
|
Parameters
|
3724
3575
|
----------
|
3725
|
-
body: dict
|
3576
|
+
body: dict | TemplateRequestBody
|
3726
3577
|
A dictionary containing the definition of the solution component to create.
|
3727
3578
|
|
3728
3579
|
Returns
|
@@ -3786,11 +3637,20 @@ class SolutionArchitect(Client):
|
|
3786
3637
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
3787
3638
|
f"solution-components/from-template")
|
3788
3639
|
|
3789
|
-
|
3640
|
+
if isinstance(body, TemplateRequestBody):
|
3641
|
+
validated_body = body
|
3790
3642
|
|
3791
|
-
|
3643
|
+
elif isinstance(body, dict):
|
3644
|
+
validated_body = self._template_request_adapter.validate_python(body)
|
3792
3645
|
|
3793
|
-
|
3646
|
+
json_body = validated_body.model_dump_json(indent=2, exclude_none=True)
|
3647
|
+
logger.info(json_body)
|
3648
|
+
resp = await self._async_make_request("POST", url, json_body, is_json=True)
|
3649
|
+
logger.info(f"Create Solution Component from template with GUID: {resp.json().get('guid')}")
|
3650
|
+
return resp.json().get("guid", NO_GUID_RETURNED)
|
3651
|
+
|
3652
|
+
@dynamic_catch
|
3653
|
+
def create_solution_component_from_template(self, body: dict| TemplateRequestBody) -> str:
|
3794
3654
|
""" Create a new solution component using an existing metadata element
|
3795
3655
|
as a template. The template defines additional classifications and relationships that should be
|
3796
3656
|
added to
|
@@ -3799,7 +3659,7 @@ class SolutionArchitect(Client):
|
|
3799
3659
|
|
3800
3660
|
Parameters
|
3801
3661
|
----------
|
3802
|
-
body: dict
|
3662
|
+
body: dict| TemplateRequestBody
|
3803
3663
|
A dictionary containing the definition of the solution component to create.
|
3804
3664
|
|
3805
3665
|
Returns
|
@@ -3865,26 +3725,22 @@ class SolutionArchitect(Client):
|
|
3865
3725
|
response = loop.run_until_complete(self._async_create_solution_component_from_template(body))
|
3866
3726
|
return response
|
3867
3727
|
|
3868
|
-
|
3869
|
-
|
3728
|
+
@dynamic_catch
|
3729
|
+
async def _async_update_solution_component(self, guid: str, body: dict | UpdateElementRequestBody,
|
3730
|
+
) -> None:
|
3870
3731
|
""" Update the properties of a solution component. Async Version.
|
3871
3732
|
|
3872
3733
|
Parameters
|
3873
3734
|
----------
|
3874
3735
|
guid: str
|
3875
3736
|
guid of the solution component to update.
|
3876
|
-
body: dict
|
3737
|
+
body: dict | UpdateElementRequestBody
|
3877
3738
|
A dictionary containing the updates to the component.
|
3878
|
-
replace_all_properties: bool, optional
|
3879
|
-
Whether to replace all properties with those provided in the body or to merge with existing properties.
|
3880
3739
|
|
3881
3740
|
Returns
|
3882
3741
|
-------
|
3883
|
-
|
3884
3742
|
None
|
3885
3743
|
|
3886
|
-
Raises
|
3887
|
-
------
|
3888
3744
|
Raises
|
3889
3745
|
------
|
3890
3746
|
InvalidParameterException
|
@@ -3923,32 +3779,26 @@ class SolutionArchitect(Client):
|
|
3923
3779
|
}
|
3924
3780
|
|
3925
3781
|
"""
|
3926
|
-
|
3927
|
-
replace_all_properties_s = str(replace_all_properties).lower()
|
3782
|
+
|
3928
3783
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
3929
|
-
f"solution-components/{guid}/update
|
3784
|
+
f"solution-components/{guid}/update")
|
3930
3785
|
|
3931
|
-
await self.
|
3786
|
+
await self._async_update_element_body_request(url, ["SolutionComponentProperties"], body)
|
3932
3787
|
|
3933
|
-
|
3788
|
+
@dynamic_catch
|
3789
|
+
def update_solution_component(self, guid: str, body: dict | UpdateElementRequestBody) -> None:
|
3934
3790
|
""" Update the properties of a solution component. Async Version.
|
3935
3791
|
|
3936
3792
|
Parameters
|
3937
3793
|
----------
|
3938
3794
|
guid: str
|
3939
3795
|
guid of the solution component to update.
|
3940
|
-
body: dict
|
3796
|
+
body: dict | UpdateElementRequestBody
|
3941
3797
|
A dictionary containing the updates to the component.
|
3942
|
-
replace_all_properties: bool, optional
|
3943
|
-
Whether to replace all properties with those provided in the body or to merge with existing properties.
|
3944
|
-
|
3945
3798
|
Returns
|
3946
3799
|
-------
|
3947
|
-
|
3948
3800
|
None
|
3949
3801
|
|
3950
|
-
Raises
|
3951
|
-
------
|
3952
3802
|
Raises
|
3953
3803
|
------
|
3954
3804
|
InvalidParameterException
|
@@ -3988,9 +3838,10 @@ class SolutionArchitect(Client):
|
|
3988
3838
|
|
3989
3839
|
"""
|
3990
3840
|
loop = asyncio.get_event_loop()
|
3991
|
-
loop.run_until_complete(self._async_update_solution_component(guid, body
|
3841
|
+
loop.run_until_complete(self._async_update_solution_component(guid, body))
|
3992
3842
|
|
3993
|
-
|
3843
|
+
@dynamic_catch
|
3844
|
+
async def _async_link_subcomponent(self, component_guid: str, sub_component_guid: str, body: dict | NewRelationshipRequestBody) -> None:
|
3994
3845
|
""" Attach a solution component to a solution component. Async Version.
|
3995
3846
|
|
3996
3847
|
Parameters
|
@@ -3999,7 +3850,7 @@ class SolutionArchitect(Client):
|
|
3999
3850
|
guid of the blueprint to connect to.
|
4000
3851
|
sub_component_guid: str
|
4001
3852
|
guid of the component to link.
|
4002
|
-
body: dict
|
3853
|
+
body: dict | NewRelationshipRequestBody
|
4003
3854
|
The body describing the link.
|
4004
3855
|
|
4005
3856
|
Returns
|
@@ -4020,25 +3871,23 @@ class SolutionArchitect(Client):
|
|
4020
3871
|
|
4021
3872
|
Body structure:
|
4022
3873
|
{
|
4023
|
-
"class"
|
3874
|
+
"class": "NewRelationshipRequestBody",
|
4024
3875
|
"externalSourceGUID": "add guid here",
|
4025
3876
|
"externalSourceName": "add qualified name here",
|
4026
|
-
"effectiveTime"
|
4027
|
-
"forLineage"
|
4028
|
-
"forDuplicateProcessing"
|
3877
|
+
"effectiveTime": "{{$isoTimestamp}}",
|
3878
|
+
"forLineage": false,
|
3879
|
+
"forDuplicateProcessing": false
|
4029
3880
|
}
|
4030
3881
|
"""
|
4031
|
-
|
4032
|
-
validate_guid(sub_component_guid)
|
3882
|
+
|
4033
3883
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
4034
3884
|
f"solution-components/{component_guid}/subcomponents/{sub_component_guid}/attach")
|
4035
|
-
if body:
|
4036
|
-
await self._async_make_request("POST", url, body_slimmer(body))
|
4037
|
-
else:
|
4038
|
-
await self._async_make_request("POST", url)
|
4039
3885
|
|
3886
|
+
await self._async_new_relationship_request(url, ["SolutionCompositionProperties"], body)
|
3887
|
+
logger.info(f"Linked Subcomponent {component_guid} -> {sub_component_guid}")
|
4040
3888
|
|
4041
|
-
|
3889
|
+
@dynamic_catch
|
3890
|
+
def link_subcomponent(self, component_guid: str, sub_component_guid: str, body: dict | NewRelationshipRequestBody) -> None:
|
4042
3891
|
""" Attach a solution component to a solution component.
|
4043
3892
|
|
4044
3893
|
Parameters
|
@@ -4047,7 +3896,7 @@ class SolutionArchitect(Client):
|
|
4047
3896
|
guid of the blueprint to connect to.
|
4048
3897
|
sub_component_guid: str
|
4049
3898
|
guid of the component to link.
|
4050
|
-
body: dict
|
3899
|
+
body: dict | NewRelationshipRequestBody
|
4051
3900
|
The body describing the link.
|
4052
3901
|
|
4053
3902
|
Returns
|
@@ -4068,7 +3917,7 @@ class SolutionArchitect(Client):
|
|
4068
3917
|
|
4069
3918
|
Body structure:
|
4070
3919
|
{
|
4071
|
-
"class" : "
|
3920
|
+
"class" : "NewRelationshipRequestBody",
|
4072
3921
|
"externalSourceGUID": "add guid here",
|
4073
3922
|
"externalSourceName": "add qualified name here",
|
4074
3923
|
"effectiveTime" : "{{$isoTimestamp}}",
|
@@ -4078,9 +3927,9 @@ class SolutionArchitect(Client):
|
|
4078
3927
|
"""
|
4079
3928
|
loop = asyncio.get_event_loop()
|
4080
3929
|
loop.run_until_complete(self._async_link_subcomponent(component_guid, sub_component_guid, body))
|
4081
|
-
|
3930
|
+
@dynamic_catch
|
4082
3931
|
async def _async_detach_sub_component(self, parent_component_guid: str, member_component_guid: str,
|
4083
|
-
body: dict = None) -> None:
|
3932
|
+
body: dict |DeleteRequestBody = None) -> None:
|
4084
3933
|
""" Detach a solution component from a solution component.
|
4085
3934
|
Async Version.
|
4086
3935
|
|
@@ -4111,7 +3960,7 @@ class SolutionArchitect(Client):
|
|
4111
3960
|
|
4112
3961
|
Body structure:
|
4113
3962
|
{
|
4114
|
-
"class": "
|
3963
|
+
"class": "DeleteRequestBody",
|
4115
3964
|
"externalSourceGUID": "add guid here",
|
4116
3965
|
"externalSourceName": "add qualified name here",
|
4117
3966
|
"effectiveTime": {{isotime}},
|
@@ -4120,14 +3969,16 @@ class SolutionArchitect(Client):
|
|
4120
3969
|
}
|
4121
3970
|
|
4122
3971
|
"""
|
4123
|
-
|
4124
|
-
validate_guid(member_component_guid)
|
3972
|
+
|
4125
3973
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
4126
3974
|
f"solution-components/{parent_component_guid}/subcomponents/{member_component_guid}/detach")
|
4127
3975
|
|
4128
|
-
await self.
|
3976
|
+
await self._async_delete_request(url, body)
|
3977
|
+
logger.info(
|
3978
|
+
f"Detached components {parent_component_guid} -> {member_component_guid}")
|
4129
3979
|
|
4130
|
-
|
3980
|
+
@dynamic_catch
|
3981
|
+
def detach_sub_component(self, parent_component_guid: str, member_component_guid: str, body: dict| DeleteRequestBody = None) -> None:
|
4131
3982
|
""" Detach a solution component from a solution component.
|
4132
3983
|
Async Version.
|
4133
3984
|
|
@@ -4137,7 +3988,7 @@ class SolutionArchitect(Client):
|
|
4137
3988
|
guid of the parent component to disconnect from.
|
4138
3989
|
member_component_guid: str
|
4139
3990
|
guid of the member (child) component to disconnect.
|
4140
|
-
body: dict
|
3991
|
+
body: dict | DeleteRequestBody
|
4141
3992
|
The body describing the request.
|
4142
3993
|
|
4143
3994
|
Returns
|
@@ -4158,7 +4009,7 @@ class SolutionArchitect(Client):
|
|
4158
4009
|
|
4159
4010
|
Body structure:
|
4160
4011
|
{
|
4161
|
-
"class": "
|
4012
|
+
"class": "DeleteRequestBody",
|
4162
4013
|
"externalSourceGUID": "add guid here",
|
4163
4014
|
"externalSourceName": "add qualified name here",
|
4164
4015
|
"effectiveTime": {{isotime}},
|
@@ -4170,7 +4021,8 @@ class SolutionArchitect(Client):
|
|
4170
4021
|
loop = asyncio.get_event_loop()
|
4171
4022
|
loop.run_until_complete(self._async_detach_sub_component(parent_component_guid, member_component_guid, body))
|
4172
4023
|
|
4173
|
-
|
4024
|
+
@dynamic_catch
|
4025
|
+
async def _async_link_solution_linking_wire(self, component1_guid: str, component2_guid: str, body: dict | NewRelationshipRequestBody) -> None:
|
4174
4026
|
""" Attach a solution component to a solution component as a peer in a solution. Async Version.
|
4175
4027
|
|
4176
4028
|
Parameters
|
@@ -4179,9 +4031,10 @@ class SolutionArchitect(Client):
|
|
4179
4031
|
GUID of the first component to link.
|
4180
4032
|
component2_guid: str
|
4181
4033
|
GUID of the second component to link.
|
4182
|
-
body: dict
|
4034
|
+
body: dict | NewRelationshipRequestBody
|
4183
4035
|
The body describing the link.
|
4184
4036
|
|
4037
|
+
|
4185
4038
|
Returns
|
4186
4039
|
-------
|
4187
4040
|
None
|
@@ -4200,7 +4053,7 @@ class SolutionArchitect(Client):
|
|
4200
4053
|
|
4201
4054
|
Body structure:
|
4202
4055
|
{
|
4203
|
-
"class": "
|
4056
|
+
"class": "NewRelationshipRequestBody",
|
4204
4057
|
"externalSourceGUID": "add guid here",
|
4205
4058
|
"externalSourceName": "add qualified name here",
|
4206
4059
|
"properties": {
|
@@ -4214,16 +4067,14 @@ class SolutionArchitect(Client):
|
|
4214
4067
|
"forDuplicateProcessing": false
|
4215
4068
|
}
|
4216
4069
|
"""
|
4217
|
-
|
4218
|
-
validate_guid(component2_guid)
|
4070
|
+
|
4219
4071
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
4220
4072
|
f"solution-components/{component1_guid}/wired-to/{component2_guid}/attach")
|
4221
|
-
|
4222
|
-
|
4223
|
-
else:
|
4224
|
-
await self._async_make_request("POST", url)
|
4073
|
+
await self._async_new_relationship_request(url, ["SolutionLinkingWireProperties"], body)
|
4074
|
+
logger.info(f"Linked Solution Linking wires between {component1_guid} -> {component2_guid}")
|
4225
4075
|
|
4226
|
-
|
4076
|
+
@dynamic_catch
|
4077
|
+
def link_solution_linking_wire(self, component1_guid: str, component2_guid: str, body: dict | NewRelationshipRequestBody) -> None:
|
4227
4078
|
""" Attach a solution component to a solution component as a peer in a solution.
|
4228
4079
|
|
4229
4080
|
Parameters
|
@@ -4232,7 +4083,7 @@ class SolutionArchitect(Client):
|
|
4232
4083
|
GUID of the first component to link.
|
4233
4084
|
component2_guid: str
|
4234
4085
|
GUID of the second component to link.
|
4235
|
-
body: dict
|
4086
|
+
body: dict | NewRelationshipRequestBody
|
4236
4087
|
The body describing the link.
|
4237
4088
|
|
4238
4089
|
Returns
|
@@ -4253,7 +4104,7 @@ class SolutionArchitect(Client):
|
|
4253
4104
|
|
4254
4105
|
Body structure:
|
4255
4106
|
{
|
4256
|
-
"class": "
|
4107
|
+
"class": "NewRelationshipRequestBody",
|
4257
4108
|
"externalSourceGUID": "add guid here",
|
4258
4109
|
"externalSourceName": "add qualified name here",
|
4259
4110
|
"properties": {
|
@@ -4270,8 +4121,9 @@ class SolutionArchitect(Client):
|
|
4270
4121
|
loop = asyncio.get_event_loop()
|
4271
4122
|
loop.run_until_complete(self._async_link_solution_linking_wire(component1_guid, component2_guid, body))
|
4272
4123
|
|
4124
|
+
@dynamic_catch
|
4273
4125
|
async def _async_detach_solution_linking_wire(self, component1_guid: str, component2_guid: str,
|
4274
|
-
body: dict = None) -> None:
|
4126
|
+
body: dict | DeleteRequestBody = None) -> None:
|
4275
4127
|
""" Detach a solution component from a peer solution component.
|
4276
4128
|
Async Version.
|
4277
4129
|
|
@@ -4281,7 +4133,7 @@ class SolutionArchitect(Client):
|
|
4281
4133
|
GUID of the first component to unlink.
|
4282
4134
|
component2_guid: str
|
4283
4135
|
GUID of the second component to unlink.
|
4284
|
-
body: dict
|
4136
|
+
body: dict | DeleteRequestBody
|
4285
4137
|
The body describing the request.
|
4286
4138
|
|
4287
4139
|
Returns
|
@@ -4302,7 +4154,7 @@ class SolutionArchitect(Client):
|
|
4302
4154
|
|
4303
4155
|
Body structure:
|
4304
4156
|
{
|
4305
|
-
"class" : "
|
4157
|
+
"class" : "DeleteRequestBody",
|
4306
4158
|
"externalSourceGUID": "add guid here",
|
4307
4159
|
"externalSourceName": "add qualified name here",
|
4308
4160
|
"effectiveTime" : "{{$isoTimestamp}}",
|
@@ -4311,14 +4163,16 @@ class SolutionArchitect(Client):
|
|
4311
4163
|
}
|
4312
4164
|
|
4313
4165
|
"""
|
4314
|
-
|
4315
|
-
validate_guid(component2_guid)
|
4166
|
+
|
4316
4167
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
4317
4168
|
f"solution-components/{component1_guid}/wired-to/{component2_guid}/detach")
|
4318
4169
|
|
4319
|
-
await self.
|
4170
|
+
await self._async_delete_request(url, body)
|
4171
|
+
logger.info(
|
4172
|
+
f"Detached solution linking wire between {component1_guid} -> {component2_guid}")
|
4320
4173
|
|
4321
|
-
|
4174
|
+
@dynamic_catch
|
4175
|
+
def detach_solution_linking_wire(self, component1_guid: str, component2_guid: str, body: dict | DeleteRequestBody = None) -> None:
|
4322
4176
|
""" Detach a solution component from a peer solution component.
|
4323
4177
|
Async Version.
|
4324
4178
|
|
@@ -4328,7 +4182,8 @@ class SolutionArchitect(Client):
|
|
4328
4182
|
GUID of the first component to unlink.
|
4329
4183
|
component2_guid: str
|
4330
4184
|
GUID of the second component to unlink.
|
4331
|
-
body: dict
|
4185
|
+
body: dict | DeleteRequestBody
|
4186
|
+
The body describing the request.
|
4332
4187
|
The body describing the request.
|
4333
4188
|
|
4334
4189
|
Returns
|
@@ -4349,7 +4204,7 @@ class SolutionArchitect(Client):
|
|
4349
4204
|
|
4350
4205
|
Body structure:
|
4351
4206
|
{
|
4352
|
-
"class" : "
|
4207
|
+
"class" : "DeleteRequestBody",
|
4353
4208
|
"externalSourceGUID": "add guid here",
|
4354
4209
|
"externalSourceName": "add qualified name here",
|
4355
4210
|
"effectiveTime" : "{{$isoTimestamp}}",
|
@@ -4361,9 +4216,9 @@ class SolutionArchitect(Client):
|
|
4361
4216
|
loop = asyncio.get_event_loop()
|
4362
4217
|
loop.run_until_complete(self._async_detach_solution_linking_wire(component1_guid, component2_guid, body))
|
4363
4218
|
|
4364
|
-
|
4219
|
+
@dynamic_catch
|
4365
4220
|
async def _async_delete_solution_component(self, solution_component_guid: str, cascade_delete: bool = False,
|
4366
|
-
body: dict = None) -> None:
|
4221
|
+
body: dict | DeleteRequestBody= None) -> None:
|
4367
4222
|
"""Delete a solution component. Async Version.
|
4368
4223
|
|
4369
4224
|
Parameters
|
@@ -4372,7 +4227,7 @@ class SolutionArchitect(Client):
|
|
4372
4227
|
guid of the component to delete.
|
4373
4228
|
cascade_delete: bool, optional, default: False
|
4374
4229
|
Cascade the delete to dependent objects?
|
4375
|
-
body: dict, optional
|
4230
|
+
body: dict | DeleteRequestBody, optional
|
4376
4231
|
A dictionary containing parameters for the deletion.
|
4377
4232
|
|
4378
4233
|
Returns
|
@@ -4393,7 +4248,7 @@ class SolutionArchitect(Client):
|
|
4393
4248
|
|
4394
4249
|
Body structure:
|
4395
4250
|
{
|
4396
|
-
"class": "
|
4251
|
+
"class": "DeleteRequestBody",
|
4397
4252
|
"externalSourceGUID": "add guid here",
|
4398
4253
|
"externalSourceName": "add qualified name here",
|
4399
4254
|
"effectiveTime": {{isotime}},
|
@@ -4401,18 +4256,16 @@ class SolutionArchitect(Client):
|
|
4401
4256
|
"forDuplicateProcessing": false
|
4402
4257
|
}
|
4403
4258
|
"""
|
4404
|
-
|
4405
|
-
cascaded_s = str(cascade_delete).lower()
|
4259
|
+
|
4406
4260
|
|
4407
4261
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
4408
|
-
f"solution-components/{solution_component_guid}/delete
|
4409
|
-
|
4410
|
-
|
4411
|
-
else:
|
4412
|
-
await self._async_make_request("POST", url)
|
4262
|
+
f"solution-components/{solution_component_guid}/delete")
|
4263
|
+
await self._async_delete_request(url, body, cascade_delete=cascade_delete)
|
4264
|
+
logger.info(f"Deleted Solution Component {solution_component_guid} with cascade {cascade_delete}")
|
4413
4265
|
|
4266
|
+
@dynamic_catch
|
4414
4267
|
def delete_solution_component(self, solution_component_guid: str, cascade_delete: bool = False,
|
4415
|
-
body: dict = None) -> None:
|
4268
|
+
body: dict | DeleteRequestBody = None) -> None:
|
4416
4269
|
"""Delete a solution component.
|
4417
4270
|
Parameters
|
4418
4271
|
----------
|
@@ -4420,7 +4273,7 @@ class SolutionArchitect(Client):
|
|
4420
4273
|
guid of the component to delete.
|
4421
4274
|
cascade_delete: bool, optional, default: False
|
4422
4275
|
Cascade the delete to dependent objects?
|
4423
|
-
body: dict, optional
|
4276
|
+
body: dict | DeleteRequestBody, optional
|
4424
4277
|
A dictionary containing parameters for the deletion.
|
4425
4278
|
|
4426
4279
|
Returns
|
@@ -4441,7 +4294,7 @@ class SolutionArchitect(Client):
|
|
4441
4294
|
|
4442
4295
|
Body structure:
|
4443
4296
|
{
|
4444
|
-
"class": "
|
4297
|
+
"class": "DeleteRequestBody",
|
4445
4298
|
"externalSourceGUID": "add guid here",
|
4446
4299
|
"externalSourceName": "add qualified name here",
|
4447
4300
|
"effectiveTime": {{isotime}},
|
@@ -4452,10 +4305,13 @@ class SolutionArchitect(Client):
|
|
4452
4305
|
loop = asyncio.get_event_loop()
|
4453
4306
|
loop.run_until_complete(self._async_delete_solution_component(solution_component_guid, cascade_delete, body))
|
4454
4307
|
|
4455
|
-
async def _async_find_solution_components(self,
|
4456
|
-
|
4457
|
-
|
4458
|
-
|
4308
|
+
async def _async_find_solution_components(self, search_string: str = "*", classification_names: list[str] = None,
|
4309
|
+
metadata_element_types: list[str] = None,
|
4310
|
+
starts_with: bool = True, ends_with: bool = False,
|
4311
|
+
ignore_case: bool = False, start_from: int = 0,
|
4312
|
+
page_size: int = 0, output_format: str = 'JSON',
|
4313
|
+
output_format_set: str = None,
|
4314
|
+
body: dict| SearchStringRequestBody = None) -> list[dict] | str:
|
4459
4315
|
""" Retrieve the solution component elements that contain the search string. The solutions components returned
|
4460
4316
|
include information about consumers, actors, and other solution components that are associated with them.
|
4461
4317
|
https://egeria-project.org/concepts/solution-components
|
@@ -4511,35 +4367,26 @@ class SolutionArchitect(Client):
|
|
4511
4367
|
}
|
4512
4368
|
"""
|
4513
4369
|
|
4514
|
-
starts_with_s = str(starts_with).lower()
|
4515
|
-
ends_with_s = str(ends_with).lower()
|
4516
|
-
ignore_case_s = str(ignore_case).lower()
|
4517
4370
|
|
4518
|
-
possible_query_params = query_string(
|
4519
|
-
[ ("startFrom", start_from), ("pageSize", page_size),
|
4520
|
-
("startsWith", starts_with_s), ("endsWith", ends_with_s), ("ignoreCase", ignore_case_s), ])
|
4521
4371
|
|
4522
|
-
|
4523
|
-
search_filter = None
|
4372
|
+
url = f"{self.solution_architect_command_root}/solution-components/by-search-string"
|
4524
4373
|
|
4525
|
-
|
4526
|
-
|
4527
|
-
|
4528
|
-
|
4374
|
+
return await self._async_find_request(url, _type="GovernanceDefinition",
|
4375
|
+
_gen_output=self.generate_info_supply_chain_output,
|
4376
|
+
search_string=search_string, classification_names=classification_names,
|
4377
|
+
metadata_element_types=metadata_element_types,
|
4378
|
+
starts_with=starts_with, ends_with=ends_with, ignore_case=ignore_case,
|
4379
|
+
start_from=start_from, page_size=page_size,
|
4380
|
+
output_format=output_format, output_format_set=output_format_set,
|
4381
|
+
body=body)
|
4529
4382
|
|
4530
|
-
|
4531
|
-
|
4532
|
-
|
4533
|
-
|
4534
|
-
|
4535
|
-
|
4536
|
-
|
4537
|
-
return self.generate_solution_components_output(element, filter, output_format)
|
4538
|
-
return response.json().get("elements", NO_ELEMENTS_FOUND)
|
4539
|
-
|
4540
|
-
def find_solution_components(self, search_filter: str = "*", starts_with: bool = True, ends_with: bool = False,
|
4541
|
-
ignore_case: bool = False, start_from: int = 0, page_size: int = 0,
|
4542
|
-
body: dict = None, output_format: str = "JSON") -> list[dict] | str:
|
4383
|
+
def find_solution_components(self, search_string: str = "*", classification_names: list[str] = None,
|
4384
|
+
metadata_element_types: list[str] = None,
|
4385
|
+
starts_with: bool = True, ends_with: bool = False,
|
4386
|
+
ignore_case: bool = False, start_from: int = 0,
|
4387
|
+
page_size: int = 0, output_format: str = 'JSON',
|
4388
|
+
output_format_set: str = None,
|
4389
|
+
body: dict| SearchStringRequestBody = None) -> list[dict] | str:
|
4543
4390
|
""" Retrieve the solution component elements that contain the search string. The solutions components returned
|
4544
4391
|
include information about consumers, actors, and other solution components that are associated with them.
|
4545
4392
|
https://egeria-project.org/concepts/solution-components
|
@@ -4597,17 +4444,20 @@ class SolutionArchitect(Client):
|
|
4597
4444
|
|
4598
4445
|
loop = asyncio.get_event_loop()
|
4599
4446
|
response = loop.run_until_complete(
|
4600
|
-
self._async_find_solution_components(
|
4601
|
-
page_size, body, output_format))
|
4447
|
+
self._async_find_solution_components(search_string, classification_names, metadata_element_types, starts_with, ends_with, ignore_case, start_from, page_size, output_format, output_format_set, body))
|
4602
4448
|
return response
|
4603
4449
|
|
4604
|
-
def find_all_solution_components(self,
|
4605
|
-
|
4450
|
+
def find_all_solution_components(self, classification_names: list[str] = None,
|
4451
|
+
metadata_element_types: list[str] = None,
|
4452
|
+
starts_with: bool = True, ends_with: bool = False,
|
4453
|
+
ignore_case: bool = False, start_from: int = 0,
|
4454
|
+
page_size: int = 0, output_format: str = 'JSON',
|
4455
|
+
output_format_set: str = None,
|
4456
|
+
body: dict| SearchStringRequestBody = None) -> list[dict] | str:
|
4606
4457
|
"""Retrieve a list of all solution component elements
|
4607
4458
|
https://egeria-project.org/concepts/solution-components
|
4608
4459
|
"""
|
4609
|
-
return self.find_solution_components("*",
|
4610
|
-
output_format=output_format)
|
4460
|
+
return self.find_solution_components("*", classification_names, metadata_element_types, starts_with, ends_with, ignore_case, start_from, page_size, output_format, output_format_set, body)
|
4611
4461
|
|
4612
4462
|
async def _async_get_solution_components_by_name(self, search_filter: str, body: dict = None, start_from: int = 0,
|
4613
4463
|
page_size: int = 0, output_format: str = "JSON") -> dict | str:
|
@@ -5018,22 +4868,20 @@ class SolutionArchitect(Client):
|
|
5018
4868
|
#
|
5019
4869
|
# Roles
|
5020
4870
|
#
|
5021
|
-
|
5022
|
-
async def _async_create_solution_role(self, body: dict) -> str:
|
4871
|
+
@dynamic_catch
|
4872
|
+
async def _async_create_solution_role(self, body: dict | NewElementRequestBody) -> str:
|
5023
4873
|
""" Create a solution role. Async version.
|
5024
4874
|
|
5025
4875
|
Parameters
|
5026
4876
|
----------
|
5027
|
-
body: dict
|
5028
|
-
A dictionary containing the
|
4877
|
+
body: dict | NewElementRequestBody
|
4878
|
+
A dictionary containing the properties of the solution role to create.
|
5029
4879
|
|
5030
4880
|
Returns
|
5031
4881
|
-------
|
5032
4882
|
|
5033
4883
|
str - guid of the role created.
|
5034
4884
|
|
5035
|
-
Raises
|
5036
|
-
------
|
5037
4885
|
Raises
|
5038
4886
|
------
|
5039
4887
|
InvalidParameterException
|
@@ -5087,17 +4935,16 @@ class SolutionArchitect(Client):
|
|
5087
4935
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
5088
4936
|
f"solution-roles")
|
5089
4937
|
|
5090
|
-
|
4938
|
+
return await self._async_create_element_body_request(url, ["SolutionRoleProperties"], body)
|
5091
4939
|
|
5092
|
-
|
5093
|
-
|
5094
|
-
def create_solution_role(self, body: dict) -> str:
|
4940
|
+
@dynamic_catch
|
4941
|
+
def create_solution_role(self, body: dict| NewElementRequestBody) -> str:
|
5095
4942
|
"""Create a solution role. Async version.
|
5096
4943
|
|
5097
4944
|
Parameters
|
5098
4945
|
----------
|
5099
|
-
body: dict
|
5100
|
-
A dictionary containing the
|
4946
|
+
body: dict | NewElementRequestBody
|
4947
|
+
A dictionary containing the properties of the solution role to create.
|
5101
4948
|
|
5102
4949
|
Returns
|
5103
4950
|
-------
|
@@ -5162,7 +5009,8 @@ class SolutionArchitect(Client):
|
|
5162
5009
|
response = loop.run_until_complete(self._async_create_solution_role(body))
|
5163
5010
|
return response
|
5164
5011
|
|
5165
|
-
|
5012
|
+
@dynamic_catch
|
5013
|
+
async def _async_create_solution_role_from_template(self, body: dict | TemplateRequestBody) -> str:
|
5166
5014
|
""" Create a new metadata element to represent a solution role using an existing metadata element as a template.
|
5167
5015
|
The template defines additional classifications and relationships that should be added to the new element.
|
5168
5016
|
Async Version.
|
@@ -5170,8 +5018,9 @@ class SolutionArchitect(Client):
|
|
5170
5018
|
|
5171
5019
|
Parameters
|
5172
5020
|
----------
|
5173
|
-
body: dict
|
5174
|
-
A dictionary containing the
|
5021
|
+
body: dict | TemplateRequestBody
|
5022
|
+
A dictionary containing the properties of the solution role to create.
|
5023
|
+
|
5175
5024
|
|
5176
5025
|
Returns
|
5177
5026
|
-------
|
@@ -5233,12 +5082,20 @@ class SolutionArchitect(Client):
|
|
5233
5082
|
"""
|
5234
5083
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
5235
5084
|
f"solution-roles/from-template")
|
5085
|
+
if isinstance(body, TemplateRequestBody):
|
5086
|
+
validated_body = body
|
5236
5087
|
|
5237
|
-
|
5088
|
+
elif isinstance(body, dict):
|
5089
|
+
validated_body = self._template_request_adapter.validate_python(body)
|
5238
5090
|
|
5239
|
-
|
5091
|
+
json_body = validated_body.model_dump_json(indent=2, exclude_none=True)
|
5092
|
+
logger.info(json_body)
|
5093
|
+
resp = await self._async_make_request("POST", url, json_body, is_json=True)
|
5094
|
+
logger.info(f"Create Solution Role from template with GUID: {resp.json().get('guid')}")
|
5095
|
+
return resp.json().get("guid", NO_GUID_RETURNED)
|
5240
5096
|
|
5241
|
-
|
5097
|
+
@dynamic_catch
|
5098
|
+
def create_solution_role_from_template(self, body: dict |TemplateRequestBody) -> str:
|
5242
5099
|
""" Create a new solution component using an existing metadata element
|
5243
5100
|
as a template. The template defines additional classifications and relationships that should be
|
5244
5101
|
added to
|
@@ -5247,8 +5104,8 @@ class SolutionArchitect(Client):
|
|
5247
5104
|
|
5248
5105
|
Parameters
|
5249
5106
|
----------
|
5250
|
-
body: dict
|
5251
|
-
A dictionary containing the
|
5107
|
+
body: dict | TemplateRequestBody
|
5108
|
+
A dictionary containing the properties of the solution role to create.
|
5252
5109
|
|
5253
5110
|
Returns
|
5254
5111
|
-------
|
@@ -5313,7 +5170,8 @@ class SolutionArchitect(Client):
|
|
5313
5170
|
response = loop.run_until_complete(self._async_create_solution_role_from_template(body))
|
5314
5171
|
return response
|
5315
5172
|
|
5316
|
-
|
5173
|
+
@dynamic_catch
|
5174
|
+
async def _async_update_solution_role(self, guid: str, body: dict |UpdateElementRequestBody) -> None:
|
5317
5175
|
""" Update the properties of a solution role. Async Version.
|
5318
5176
|
|
5319
5177
|
Parameters
|
@@ -5368,24 +5226,22 @@ class SolutionArchitect(Client):
|
|
5368
5226
|
}
|
5369
5227
|
|
5370
5228
|
"""
|
5371
|
-
|
5372
|
-
replace_all_properties_s = str(replace_all_properties).lower()
|
5229
|
+
|
5373
5230
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
5374
|
-
f"solution-roles/{guid}/update
|
5231
|
+
f"solution-roles/{guid}/update")
|
5375
5232
|
|
5376
|
-
await self.
|
5233
|
+
await self._async_update_element_body_request(url, ["SolutionRoleProperties"], body)
|
5377
5234
|
|
5378
|
-
|
5235
|
+
@dynamic_catch
|
5236
|
+
def update_solution_role(self, guid: str, body: dict | UpdateElementRequestBody) -> None:
|
5379
5237
|
""" Update the properties of a solution role.
|
5380
5238
|
|
5381
5239
|
Parameters
|
5382
5240
|
----------
|
5383
5241
|
guid: str
|
5384
5242
|
guid of the solution role to update.
|
5385
|
-
body: dict
|
5386
|
-
A dictionary containing the updates to the
|
5387
|
-
replace_all_properties: bool, optional, default is False
|
5388
|
-
Whether to replace all properties with those provided in the body or to merge with existing properties.
|
5243
|
+
body: dict | UpdateElementRequestBody
|
5244
|
+
A dictionary containing the updates to the role.
|
5389
5245
|
|
5390
5246
|
Returns
|
5391
5247
|
-------
|
@@ -5430,9 +5286,10 @@ class SolutionArchitect(Client):
|
|
5430
5286
|
}
|
5431
5287
|
"""
|
5432
5288
|
loop = asyncio.get_event_loop()
|
5433
|
-
loop.run_until_complete(self._async_update_solution_role(guid, body
|
5289
|
+
loop.run_until_complete(self._async_update_solution_role(guid, body))
|
5434
5290
|
|
5435
|
-
|
5291
|
+
@dynamic_catch
|
5292
|
+
async def _async_link_component_to_actor(self, role_guid: str, component_guid: str, body: dict | NewRelationshipRequestBody) -> None:
|
5436
5293
|
""" Attach a solution component to a solution role. Async Version.
|
5437
5294
|
|
5438
5295
|
Parameters
|
@@ -5441,8 +5298,8 @@ class SolutionArchitect(Client):
|
|
5441
5298
|
guid of the role to link.
|
5442
5299
|
component_guid: str
|
5443
5300
|
guid of the component to link.
|
5444
|
-
body: dict
|
5445
|
-
|
5301
|
+
body: dict | NewRelationshipRequestBody
|
5302
|
+
A dictionary containing the properties of the relationship to create.
|
5446
5303
|
|
5447
5304
|
Returns
|
5448
5305
|
-------
|
@@ -5462,7 +5319,7 @@ class SolutionArchitect(Client):
|
|
5462
5319
|
|
5463
5320
|
Body structure:
|
5464
5321
|
{
|
5465
|
-
"class" : "
|
5322
|
+
"class" : "NewRelationshipRequestBody",
|
5466
5323
|
"properties": {
|
5467
5324
|
"class": "SolutionComponentActorProperties",
|
5468
5325
|
"role": "Add role here",
|
@@ -5477,14 +5334,15 @@ class SolutionArchitect(Client):
|
|
5477
5334
|
"forDuplicateProcessing" : false
|
5478
5335
|
}
|
5479
5336
|
"""
|
5480
|
-
|
5481
|
-
validate_guid(role_guid)
|
5337
|
+
|
5482
5338
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
5483
5339
|
f"solution-roles/{role_guid}/solution-roles/{component_guid}/attach")
|
5484
5340
|
|
5485
|
-
await self.
|
5341
|
+
await self._async_new_relationship_request(url, ["InformationSupplyChainLinkProperties"], body)
|
5342
|
+
logger.info(f"Linked Role to Component {role_guid} -> {component_guid}")
|
5486
5343
|
|
5487
|
-
|
5344
|
+
@dynamic_catch
|
5345
|
+
def link_component_to_actor(self, role_guid: str, component_guid: str, body: dict | NewRelationshipRequestBody) -> None:
|
5488
5346
|
""" Attach a solution component to a solution role.
|
5489
5347
|
|
5490
5348
|
Parameters
|
@@ -5493,8 +5351,8 @@ class SolutionArchitect(Client):
|
|
5493
5351
|
guid of the role to link.
|
5494
5352
|
component_guid: str
|
5495
5353
|
guid of the component to link.
|
5496
|
-
body: dict
|
5497
|
-
|
5354
|
+
body: dict | NewRelationshipRequestBody
|
5355
|
+
A dictionary containing the properties of the relationship to create.
|
5498
5356
|
|
5499
5357
|
Returns
|
5500
5358
|
-------
|
@@ -5514,7 +5372,7 @@ class SolutionArchitect(Client):
|
|
5514
5372
|
|
5515
5373
|
Body structure:
|
5516
5374
|
{
|
5517
|
-
"class" : "
|
5375
|
+
"class" : "NewRelationshipRequestBody",
|
5518
5376
|
"properties": {
|
5519
5377
|
"class": "SolutionComponentActorProperties",
|
5520
5378
|
"role": "Add role here",
|
@@ -5533,7 +5391,8 @@ class SolutionArchitect(Client):
|
|
5533
5391
|
loop = asyncio.get_event_loop()
|
5534
5392
|
loop.run_until_complete(self._async_link_component_to_actor(role_guid, component_guid, body))
|
5535
5393
|
|
5536
|
-
|
5394
|
+
@dynamic_catch
|
5395
|
+
async def _async_detach_component_actor(self, role_guid: str, component_guid: str, body: dict | DeleteRequestBody = None) -> None:
|
5537
5396
|
""" Detach a solution role from a solution component.
|
5538
5397
|
Async Version.
|
5539
5398
|
|
@@ -5543,8 +5402,8 @@ class SolutionArchitect(Client):
|
|
5543
5402
|
guid of the role to disconnect from.
|
5544
5403
|
component_guid: str
|
5545
5404
|
guid of the component to disconnect.
|
5546
|
-
body: dict
|
5547
|
-
|
5405
|
+
body: dict | DeleteRequestBody, optional
|
5406
|
+
A dictionary containing the properties of the relationship to create.
|
5548
5407
|
|
5549
5408
|
Returns
|
5550
5409
|
-------
|
@@ -5564,7 +5423,7 @@ class SolutionArchitect(Client):
|
|
5564
5423
|
|
5565
5424
|
Body structure:
|
5566
5425
|
{
|
5567
|
-
"class": "
|
5426
|
+
"class": "DeleteRequestBody",
|
5568
5427
|
"externalSourceGUID": "add guid here",
|
5569
5428
|
"externalSourceName": "add qualified name here",
|
5570
5429
|
"effectiveTime": {{isotime}},
|
@@ -5573,14 +5432,16 @@ class SolutionArchitect(Client):
|
|
5573
5432
|
}
|
5574
5433
|
|
5575
5434
|
"""
|
5576
|
-
|
5577
|
-
validate_guid(component_guid)
|
5435
|
+
|
5578
5436
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
5579
5437
|
f"solution-components/{role_guid}/solution-component-actors/{component_guid}/detach")
|
5580
5438
|
|
5581
|
-
await self.
|
5439
|
+
await self._async_delete_request(url, body)
|
5440
|
+
logger.info(
|
5441
|
+
f"Detached role from component {role_guid} -> {component_guid}")
|
5582
5442
|
|
5583
|
-
|
5443
|
+
@dynamic_catch
|
5444
|
+
def detach_component_actore(self, role_guid: str, component_guid: str, body: dict |DeleteRequestBody = None) -> None:
|
5584
5445
|
""" Detach a solution role from a solution component.
|
5585
5446
|
|
5586
5447
|
Parameters
|
@@ -5589,8 +5450,8 @@ class SolutionArchitect(Client):
|
|
5589
5450
|
guid of the role to disconnect from.
|
5590
5451
|
component_guid: str
|
5591
5452
|
guid of the component to disconnect.
|
5592
|
-
body: dict
|
5593
|
-
|
5453
|
+
body: dict | DeleteRequestBody, optional
|
5454
|
+
A dictionary containing the properties of the relationship to create.
|
5594
5455
|
|
5595
5456
|
Returns
|
5596
5457
|
-------
|
@@ -5610,7 +5471,7 @@ class SolutionArchitect(Client):
|
|
5610
5471
|
|
5611
5472
|
Body structure:
|
5612
5473
|
{
|
5613
|
-
"class": "
|
5474
|
+
"class": "DeleteRequestBody",
|
5614
5475
|
"externalSourceGUID": "add guid here",
|
5615
5476
|
"externalSourceName": "add qualified name here",
|
5616
5477
|
"effectiveTime": {{isotime}},
|
@@ -5621,15 +5482,15 @@ class SolutionArchitect(Client):
|
|
5621
5482
|
loop = asyncio.get_event_loop()
|
5622
5483
|
loop.run_until_complete(self._async_detach_component_actor(role_guid, component_guid, body))
|
5623
5484
|
|
5624
|
-
|
5625
|
-
async def _async_delete_solution_role(self, guid: str, body: dict = None, cascade_delete: bool = False,) -> None:
|
5485
|
+
@dynamic_catch
|
5486
|
+
async def _async_delete_solution_role(self, guid: str, body: dict | DeleteRequestBody= None, cascade_delete: bool = False,) -> None:
|
5626
5487
|
"""Delete a solution role. Async Version.
|
5627
5488
|
|
5628
5489
|
Parameters
|
5629
5490
|
----------
|
5630
5491
|
guid: str
|
5631
5492
|
guid of the role to delete.
|
5632
|
-
body: dict, optional
|
5493
|
+
body: dict | DeleteRequestBody, optional
|
5633
5494
|
A dictionary containing parameters for the deletion.
|
5634
5495
|
cascade_delete: bool, optional, default: False
|
5635
5496
|
Cascade the delete to dependent objects?
|
@@ -5653,7 +5514,7 @@ class SolutionArchitect(Client):
|
|
5653
5514
|
|
5654
5515
|
Body structure:
|
5655
5516
|
{
|
5656
|
-
"class": "
|
5517
|
+
"class": "DeleteRequestBody",
|
5657
5518
|
"externalSourceGUID": "add guid here",
|
5658
5519
|
"externalSourceName": "add qualified name here",
|
5659
5520
|
"effectiveTime": {{isotime}},
|
@@ -5661,22 +5522,22 @@ class SolutionArchitect(Client):
|
|
5661
5522
|
"forDuplicateProcessing": false
|
5662
5523
|
}
|
5663
5524
|
"""
|
5664
|
-
validate_guid(guid)
|
5665
|
-
cascaded_s = str(cascade_delete).lower()
|
5666
5525
|
|
5667
5526
|
url = (f"{self.platform_url}/servers/{self.view_server}/api/open-metadata/solution-architect/"
|
5668
|
-
f"solution-roles/{guid}/delete
|
5527
|
+
f"solution-roles/{guid}/delete")
|
5669
5528
|
|
5670
|
-
await self.
|
5529
|
+
await self._async_delete_request(url, body, cascade_delete=cascade_delete)
|
5530
|
+
logger.info(f"Delete solution rule {guid} with cascade {cascade_delete}")
|
5671
5531
|
|
5672
|
-
|
5532
|
+
@dynamic_catch
|
5533
|
+
def delete_solution_role(self, guid: str, body: dict | DeleteRequestBody = None,cascade_delete: bool = False) -> None:
|
5673
5534
|
"""Delete a solution role. Async Version.
|
5674
5535
|
|
5675
5536
|
Parameters
|
5676
5537
|
----------
|
5677
5538
|
guid: str
|
5678
5539
|
guid of the role to delete.
|
5679
|
-
body: dict, optional
|
5540
|
+
body: dict | DeleteRequestBody, optional
|
5680
5541
|
A dictionary containing parameters for the deletion.
|
5681
5542
|
cascade_delete: bool, optional, default: False
|
5682
5543
|
Cascade the delete to dependent objects?
|
@@ -5699,7 +5560,7 @@ class SolutionArchitect(Client):
|
|
5699
5560
|
|
5700
5561
|
Body structure:
|
5701
5562
|
{
|
5702
|
-
"class": "
|
5563
|
+
"class": "DeleteRequestBody",
|
5703
5564
|
"externalSourceGUID": "add guid here",
|
5704
5565
|
"externalSourceName": "add qualified name here",
|
5705
5566
|
"effectiveTime": {{isotime}},
|
@@ -5710,10 +5571,13 @@ class SolutionArchitect(Client):
|
|
5710
5571
|
loop = asyncio.get_event_loop()
|
5711
5572
|
loop.run_until_complete(self._async_delete_solution_role(guid, cascade_delete, body))
|
5712
5573
|
|
5713
|
-
async def _async_find_solution_roles(self,
|
5714
|
-
|
5715
|
-
|
5716
|
-
|
5574
|
+
async def _async_find_solution_roles(self, search_string: str = "*", classification_names: list[str] = None,
|
5575
|
+
metadata_element_types: list[str] = None,
|
5576
|
+
starts_with: bool = True, ends_with: bool = False,
|
5577
|
+
ignore_case: bool = False, start_from: int = 0,
|
5578
|
+
page_size: int = 0, output_format: str = 'JSON',
|
5579
|
+
output_format_set: str = None,
|
5580
|
+
body: dict| SearchStringRequestBody = None) -> list[dict] | str:
|
5717
5581
|
"""Retrieve the solution role elements that contain the search string.
|
5718
5582
|
https://egeria-project.org/concepts/actor
|
5719
5583
|
Async version.
|
@@ -5769,34 +5633,26 @@ class SolutionArchitect(Client):
|
|
5769
5633
|
"filter": "Add name here"
|
5770
5634
|
}
|
5771
5635
|
"""
|
5772
|
-
starts_with_s = str(starts_with).lower()
|
5773
|
-
ends_with_s = str(ends_with).lower()
|
5774
|
-
ignore_case_s = str(ignore_case).lower()
|
5775
|
-
|
5776
|
-
possible_query_params = query_string(
|
5777
|
-
[ ("startFrom", start_from), ("pageSize", page_size),
|
5778
|
-
("startsWith", starts_with_s), ("endsWith", ends_with_s), ("ignoreCase", ignore_case_s), ])
|
5779
|
-
if search_filter is None or search_filter == "*":
|
5780
|
-
search_filter = None
|
5781
5636
|
|
5782
|
-
if body is None:
|
5783
|
-
body = {
|
5784
|
-
"filter": search_filter,
|
5785
|
-
}
|
5786
|
-
|
5787
|
-
url = (f"{self.solution_architect_command_root}/solution-roles/by-search-string"
|
5788
|
-
f"{possible_query_params}")
|
5789
|
-
response: Response = await self._async_make_request("POST", url, body_slimmer(body))
|
5790
|
-
element = response.json().get("elements", NO_ELEMENTS_FOUND)
|
5791
|
-
if element == NO_ELEMENTS_FOUND:
|
5792
|
-
return NO_ELEMENTS_FOUND
|
5793
|
-
if output_format != 'JSON': # return a simplified markdown representation
|
5794
|
-
return self.generate_solution_roles_output(element, filter, output_format)
|
5795
|
-
return response.json().get("elements", NO_ELEMENTS_FOUND)
|
5796
5637
|
|
5797
|
-
|
5798
|
-
|
5799
|
-
|
5638
|
+
url = f"{self.solution_architect_command_root}/solution-roles/by-search-string"
|
5639
|
+
|
5640
|
+
return await self._async_find_request(url, _type="GovernanceDefinition",
|
5641
|
+
_gen_output=self.generate_info_supply_chain_output,
|
5642
|
+
search_string=search_string, classification_names=classification_names,
|
5643
|
+
metadata_element_types=metadata_element_types,
|
5644
|
+
starts_with=starts_with, ends_with=ends_with, ignore_case=ignore_case,
|
5645
|
+
start_from=start_from, page_size=page_size,
|
5646
|
+
output_format=output_format, output_format_set=output_format_set,
|
5647
|
+
body=body)
|
5648
|
+
|
5649
|
+
def find_solution_roles(self, search_string: str = "*", classification_names: list[str] = None,
|
5650
|
+
metadata_element_types: list[str] = None,
|
5651
|
+
starts_with: bool = True, ends_with: bool = False,
|
5652
|
+
ignore_case: bool = False, start_from: int = 0,
|
5653
|
+
page_size: int = 0, output_format: str = 'JSON',
|
5654
|
+
output_format_set: str = None,
|
5655
|
+
body: dict| SearchStringRequestBody = None) -> list[dict] | str:
|
5800
5656
|
"""Retrieve the list of solution role elements that contain the search string.
|
5801
5657
|
https://egeria-project.org/concepts/actor
|
5802
5658
|
|
@@ -5860,16 +5716,20 @@ class SolutionArchitect(Client):
|
|
5860
5716
|
|
5861
5717
|
loop = asyncio.get_event_loop()
|
5862
5718
|
response = loop.run_until_complete(
|
5863
|
-
self._async_find_solution_roles(
|
5864
|
-
output_format=output_format, ))
|
5719
|
+
self._async_find_solution_roles(search_string, classification_names, metadata_element_types, starts_with, ends_with, ignore_case, start_from, page_size, output_format, output_format_set, body))
|
5865
5720
|
return response
|
5866
5721
|
|
5867
|
-
def find_all_solution_roles(self,
|
5868
|
-
|
5722
|
+
def find_all_solution_roles(self, classification_names: list[str] = None,
|
5723
|
+
metadata_element_types: list[str] = None,
|
5724
|
+
starts_with: bool = True, ends_with: bool = False,
|
5725
|
+
ignore_case: bool = False, start_from: int = 0,
|
5726
|
+
page_size: int = 0, output_format: str = 'JSON',
|
5727
|
+
output_format_set: str = None,
|
5728
|
+
body: dict| SearchStringRequestBody = None) -> list[dict] | str:
|
5869
5729
|
"""Retrieve a list of all solution blueprint elements
|
5870
5730
|
https://egeria-project.org/concepts/actor
|
5871
5731
|
"""
|
5872
|
-
return self.find_solution_roles("*",
|
5732
|
+
return self.find_solution_roles("*", classification_names, metadata_element_types, starts_with, ends_with, ignore_case, start_from, page_size, output_format, output_format_set, body)
|
5873
5733
|
|
5874
5734
|
|
5875
5735
|
async def _async_get_solution_roles_by_name(self, search_filter: str, body: dict = None, start_from: int = 0,
|