infrahub-server 1.4.4__py3-none-any.whl → 1.4.5__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.
- infrahub/core/account.py +60 -34
- infrahub/generators/tasks.py +9 -6
- infrahub/git/tasks.py +9 -6
- infrahub/proposed_change/tasks.py +16 -10
- infrahub_sdk/branch.py +3 -2
- infrahub_sdk/client.py +17 -12
- infrahub_sdk/ctl/cli_commands.py +11 -5
- infrahub_sdk/graphql.py +3 -1
- infrahub_sdk/node/node.py +26 -16
- {infrahub_server-1.4.4.dist-info → infrahub_server-1.4.5.dist-info}/METADATA +1 -1
- {infrahub_server-1.4.4.dist-info → infrahub_server-1.4.5.dist-info}/RECORD +14 -14
- {infrahub_server-1.4.4.dist-info → infrahub_server-1.4.5.dist-info}/LICENSE.txt +0 -0
- {infrahub_server-1.4.4.dist-info → infrahub_server-1.4.5.dist-info}/WHEEL +0 -0
- {infrahub_server-1.4.4.dist-info → infrahub_server-1.4.5.dist-info}/entry_points.txt +0 -0
infrahub/core/account.py
CHANGED
|
@@ -5,9 +5,10 @@ from typing import TYPE_CHECKING, Any
|
|
|
5
5
|
|
|
6
6
|
from typing_extensions import Self
|
|
7
7
|
|
|
8
|
-
from infrahub.core.constants import InfrahubKind, PermissionDecision
|
|
8
|
+
from infrahub.core.constants import NULL_VALUE, InfrahubKind, PermissionDecision
|
|
9
9
|
from infrahub.core.query import Query, QueryType
|
|
10
10
|
from infrahub.core.registry import registry
|
|
11
|
+
from infrahub.core.timestamp import Timestamp
|
|
11
12
|
|
|
12
13
|
if TYPE_CHECKING:
|
|
13
14
|
from infrahub.core.branch import Branch
|
|
@@ -519,47 +520,72 @@ class AccountTokenValidateQuery(Query):
|
|
|
519
520
|
super().__init__(**kwargs)
|
|
520
521
|
|
|
521
522
|
async def query_init(self, db: InfrahubDatabase, **kwargs: Any) -> None: # noqa: ARG002
|
|
522
|
-
|
|
523
|
-
|
|
523
|
+
branch_filter, branch_params = self.branch.get_query_filter_path(
|
|
524
|
+
at=self.at.to_string(), branch_agnostic=self.branch_agnostic, is_isolated=False
|
|
524
525
|
)
|
|
525
|
-
self.params.update(
|
|
526
|
-
|
|
527
|
-
|
|
528
|
-
|
|
526
|
+
self.params.update(branch_params)
|
|
527
|
+
self.params.update(
|
|
528
|
+
{
|
|
529
|
+
"token_attr_name": "token",
|
|
530
|
+
"token_relationship_name": "account__token",
|
|
531
|
+
"token_value": self.token,
|
|
532
|
+
"null_value": NULL_VALUE,
|
|
533
|
+
}
|
|
529
534
|
)
|
|
530
|
-
self.params.update(account_params)
|
|
531
535
|
|
|
532
|
-
self.params["token_value"] = self.token
|
|
533
|
-
|
|
534
|
-
# ruff: noqa: E501
|
|
535
536
|
query = """
|
|
536
|
-
|
|
537
|
-
|
|
538
|
-
|
|
539
|
-
|
|
540
|
-
|
|
541
|
-
|
|
542
|
-
|
|
543
|
-
|
|
544
|
-
|
|
545
|
-
|
|
537
|
+
// --------------
|
|
538
|
+
// get the active token node for this token value, if it exists
|
|
539
|
+
// --------------
|
|
540
|
+
MATCH (token_node:%(token_node_kind)s)-[r1:HAS_ATTRIBUTE]->(:Attribute {name: $token_attr_name})
|
|
541
|
+
-[r2:HAS_VALUE]->(av:AttributeValueIndexed { value: $token_value })
|
|
542
|
+
WHERE all(r in [r1, r2] WHERE (%(branch_filter)s))
|
|
543
|
+
ORDER BY r1.branch_level DESC, r1.from DESC, r1.status ASC, r2.branch_level DESC, r2.from DESC, r2.status ASC
|
|
544
|
+
LIMIT 1
|
|
545
|
+
WITH token_node
|
|
546
|
+
WHERE r1.status = "active" AND r2.status = "active"
|
|
547
|
+
// --------------
|
|
548
|
+
// get the expiration time
|
|
549
|
+
// --------------
|
|
550
|
+
OPTIONAL MATCH (token_node)-[r1:HAS_ATTRIBUTE]->(:Attribute {name: "expiration"})
|
|
551
|
+
-[r2:HAS_VALUE]->(av)
|
|
552
|
+
WHERE all(r in [r1, r2] WHERE (%(branch_filter)s))
|
|
553
|
+
ORDER BY r1.branch_level DESC, r1.from DESC, r1.status ASC, r2.branch_level DESC, r2.from DESC, r2.status ASC
|
|
554
|
+
LIMIT 1
|
|
555
|
+
WITH token_node, CASE
|
|
556
|
+
WHEN r1.status = "active" AND r2.status = "active" AND av.value <> $null_value THEN av.value
|
|
557
|
+
ELSE NULL
|
|
558
|
+
END AS expiration
|
|
559
|
+
// --------------
|
|
560
|
+
// get the linked account node from the token node
|
|
561
|
+
// --------------
|
|
562
|
+
MATCH (token_node)-[r1:IS_RELATED]-(:Relationship {name: $token_relationship_name})-[r2:IS_RELATED]-(account_node:%(account_node_kind)s)
|
|
563
|
+
WHERE all(r in [r1, r2] WHERE (%(branch_filter)s))
|
|
564
|
+
ORDER BY r1.branch_level DESC, r1.from DESC, r1.status ASC, r2.branch_level DESC, r2.from DESC, r2.status ASC
|
|
565
|
+
LIMIT 1
|
|
566
|
+
WITH expiration, account_node
|
|
567
|
+
WHERE r1.status = "active" AND r2.status = "active"
|
|
568
|
+
""" % {
|
|
569
|
+
"branch_filter": branch_filter,
|
|
570
|
+
"token_node_kind": InfrahubKind.ACCOUNTTOKEN,
|
|
571
|
+
"account_node_kind": InfrahubKind.GENERICACCOUNT,
|
|
572
|
+
}
|
|
546
573
|
self.add_to_query(query)
|
|
547
|
-
|
|
548
|
-
self.return_labels = ["at", "av", "acc"]
|
|
549
|
-
|
|
550
|
-
def get_account_name(self) -> str | None:
|
|
551
|
-
"""Return the account name that matched the query or None."""
|
|
552
|
-
if result := self.get_result():
|
|
553
|
-
return result.get("av").get("value")
|
|
554
|
-
|
|
555
|
-
return None
|
|
574
|
+
self.return_labels = ["account_node.uuid AS account_uuid", "expiration"]
|
|
556
575
|
|
|
557
576
|
def get_account_id(self) -> str | None:
|
|
558
577
|
"""Return the account id that matched the query or a None."""
|
|
559
|
-
|
|
560
|
-
|
|
561
|
-
|
|
562
|
-
|
|
578
|
+
result = self.get_result()
|
|
579
|
+
if not result:
|
|
580
|
+
return None
|
|
581
|
+
account_uuid = result.get_as_str(label="account_uuid")
|
|
582
|
+
expiration_with_tz = result.get_as_str(label="expiration")
|
|
583
|
+
if expiration_with_tz is None:
|
|
584
|
+
return account_uuid
|
|
585
|
+
expiration = Timestamp(expiration_with_tz)
|
|
586
|
+
if expiration < Timestamp():
|
|
587
|
+
return None
|
|
588
|
+
return account_uuid
|
|
563
589
|
|
|
564
590
|
|
|
565
591
|
async def validate_token(token: str, db: InfrahubDatabase, branch: Branch | str | None = None) -> str | None:
|
infrahub/generators/tasks.py
CHANGED
|
@@ -168,6 +168,15 @@ async def request_generator_definition_run(
|
|
|
168
168
|
|
|
169
169
|
client = get_client()
|
|
170
170
|
|
|
171
|
+
# Needs to be fetched before fetching group members otherwise `object` relationship would override
|
|
172
|
+
# existing node in client store without the `name` attribute due to #521
|
|
173
|
+
existing_instances = await client.filters(
|
|
174
|
+
kind=InfrahubKind.GENERATORINSTANCE,
|
|
175
|
+
definition__ids=[model.generator_definition.definition_id],
|
|
176
|
+
include=["object"],
|
|
177
|
+
branch=model.branch,
|
|
178
|
+
)
|
|
179
|
+
|
|
171
180
|
group = await client.get(
|
|
172
181
|
kind=InfrahubKind.GENERICGROUP,
|
|
173
182
|
prefetch_relationships=True,
|
|
@@ -177,12 +186,6 @@ async def request_generator_definition_run(
|
|
|
177
186
|
)
|
|
178
187
|
await group.members.fetch()
|
|
179
188
|
|
|
180
|
-
existing_instances = await client.filters(
|
|
181
|
-
kind=InfrahubKind.GENERATORINSTANCE,
|
|
182
|
-
definition__ids=[model.generator_definition.definition_id],
|
|
183
|
-
include=["object"],
|
|
184
|
-
branch=model.branch,
|
|
185
|
-
)
|
|
186
189
|
instance_by_member = {}
|
|
187
190
|
for instance in existing_instances:
|
|
188
191
|
instance_by_member[instance.object.peer.id] = instance.id
|
infrahub/git/tasks.py
CHANGED
|
@@ -310,6 +310,15 @@ async def generate_request_artifact_definition(
|
|
|
310
310
|
|
|
311
311
|
client = get_client()
|
|
312
312
|
|
|
313
|
+
# Needs to be fetched before fetching group members otherwise `object` relationship would override
|
|
314
|
+
# existing node in client store without the `name` attribute due to #521
|
|
315
|
+
existing_artifacts = await client.filters(
|
|
316
|
+
kind=CoreArtifact,
|
|
317
|
+
definition__ids=[model.artifact_definition_id],
|
|
318
|
+
include=["object"],
|
|
319
|
+
branch=model.branch,
|
|
320
|
+
)
|
|
321
|
+
|
|
313
322
|
artifact_definition = await client.get(
|
|
314
323
|
kind=CoreArtifactDefinition, id=model.artifact_definition_id, branch=model.branch
|
|
315
324
|
)
|
|
@@ -319,12 +328,6 @@ async def generate_request_artifact_definition(
|
|
|
319
328
|
await group.members.fetch()
|
|
320
329
|
current_members = [member.id for member in group.members.peers]
|
|
321
330
|
|
|
322
|
-
existing_artifacts = await client.filters(
|
|
323
|
-
kind=CoreArtifact,
|
|
324
|
-
definition__ids=[model.artifact_definition_id],
|
|
325
|
-
include=["object"],
|
|
326
|
-
branch=model.branch,
|
|
327
|
-
)
|
|
328
331
|
artifacts_by_member = {}
|
|
329
332
|
for artifact in existing_artifacts:
|
|
330
333
|
if artifact.object.id in current_members:
|
|
@@ -646,16 +646,19 @@ async def validate_artifacts_generation(model: RequestArtifactDefinitionCheck, c
|
|
|
646
646
|
context=context,
|
|
647
647
|
)
|
|
648
648
|
|
|
649
|
-
|
|
650
|
-
|
|
651
|
-
await group.members.fetch()
|
|
652
|
-
|
|
649
|
+
# Needs to be fetched before fetching group members otherwise `object` relationship would override
|
|
650
|
+
# existing node in client store without the `name` attribute due to #521
|
|
653
651
|
existing_artifacts = await client.filters(
|
|
654
652
|
kind=InfrahubKind.ARTIFACT,
|
|
655
653
|
definition__ids=[model.artifact_definition.definition_id],
|
|
656
654
|
include=["object"],
|
|
657
655
|
branch=model.source_branch,
|
|
658
656
|
)
|
|
657
|
+
|
|
658
|
+
await artifact_definition.targets.fetch()
|
|
659
|
+
group = artifact_definition.targets.peer
|
|
660
|
+
await group.members.fetch()
|
|
661
|
+
|
|
659
662
|
artifacts_by_member = {}
|
|
660
663
|
for artifact in existing_artifacts:
|
|
661
664
|
artifacts_by_member[artifact.object.peer.id] = artifact.id
|
|
@@ -907,6 +910,15 @@ async def request_generator_definition_check(model: RequestGeneratorDefinitionCh
|
|
|
907
910
|
context=context,
|
|
908
911
|
)
|
|
909
912
|
|
|
913
|
+
# Needs to be fetched before fetching group members otherwise `object` relationship would override
|
|
914
|
+
# existing node in client store without the `name` attribute due to #521
|
|
915
|
+
existing_instances = await client.filters(
|
|
916
|
+
kind=InfrahubKind.GENERATORINSTANCE,
|
|
917
|
+
definition__ids=[model.generator_definition.definition_id],
|
|
918
|
+
include=["object"],
|
|
919
|
+
branch=model.source_branch,
|
|
920
|
+
)
|
|
921
|
+
|
|
910
922
|
group = await client.get(
|
|
911
923
|
kind=InfrahubKind.GENERICGROUP,
|
|
912
924
|
prefetch_relationships=True,
|
|
@@ -916,12 +928,6 @@ async def request_generator_definition_check(model: RequestGeneratorDefinitionCh
|
|
|
916
928
|
)
|
|
917
929
|
await group.members.fetch()
|
|
918
930
|
|
|
919
|
-
existing_instances = await client.filters(
|
|
920
|
-
kind=InfrahubKind.GENERATORINSTANCE,
|
|
921
|
-
definition__ids=[model.generator_definition.definition_id],
|
|
922
|
-
include=["object"],
|
|
923
|
-
branch=model.source_branch,
|
|
924
|
-
)
|
|
925
931
|
instance_by_member = {}
|
|
926
932
|
for instance in existing_instances:
|
|
927
933
|
instance_by_member[instance.object.peer.id] = instance.id
|
infrahub_sdk/branch.py
CHANGED
|
@@ -292,13 +292,14 @@ class InfrahubBranchManagerSync(InfraHubBranchManagerBase):
|
|
|
292
292
|
},
|
|
293
293
|
}
|
|
294
294
|
|
|
295
|
-
|
|
295
|
+
mutation_query = MUTATION_QUERY_TASK if background_execution else MUTATION_QUERY_DATA
|
|
296
|
+
query = Mutation(mutation="BranchCreate", input_data=input_data, query=mutation_query)
|
|
296
297
|
response = self.client.execute_graphql(query=query.render(), tracker="mutation-branch-create")
|
|
297
298
|
|
|
298
299
|
# Make sure server version is recent enough to support background execution, as previously
|
|
299
300
|
# using background_execution=True had no effect.
|
|
300
301
|
if background_execution and "task" in response["BranchCreate"]:
|
|
301
|
-
return
|
|
302
|
+
return response["BranchCreate"]["task"]["id"]
|
|
302
303
|
return BranchData(**response["BranchCreate"]["object"])
|
|
303
304
|
|
|
304
305
|
def delete(self, branch_name: str) -> bool:
|
infrahub_sdk/client.py
CHANGED
|
@@ -209,7 +209,7 @@ class BaseClient:
|
|
|
209
209
|
delete_unused_nodes=delete_unused_nodes,
|
|
210
210
|
group_type=group_type,
|
|
211
211
|
group_params=group_params,
|
|
212
|
-
branch=branch,
|
|
212
|
+
branch=branch or self.default_branch,
|
|
213
213
|
)
|
|
214
214
|
|
|
215
215
|
def _graphql_url(
|
|
@@ -310,8 +310,7 @@ class InfrahubClient(BaseClient):
|
|
|
310
310
|
|
|
311
311
|
async def get_user(self) -> dict:
|
|
312
312
|
"""Return user information"""
|
|
313
|
-
|
|
314
|
-
return user_info
|
|
313
|
+
return await self.execute_graphql(query=QUERY_USER)
|
|
315
314
|
|
|
316
315
|
async def get_user_permissions(self) -> dict:
|
|
317
316
|
"""Return user permissions"""
|
|
@@ -540,6 +539,7 @@ class InfrahubClient(BaseClient):
|
|
|
540
539
|
schema_kind: str,
|
|
541
540
|
branch: str,
|
|
542
541
|
prefetch_relationships: bool,
|
|
542
|
+
include: list[str] | None,
|
|
543
543
|
timeout: int | None = None,
|
|
544
544
|
) -> ProcessRelationsNode:
|
|
545
545
|
"""Processes InfrahubNode and their Relationships from the GraphQL query response.
|
|
@@ -564,9 +564,12 @@ class InfrahubClient(BaseClient):
|
|
|
564
564
|
node = await InfrahubNode.from_graphql(client=self, branch=branch, data=item, timeout=timeout)
|
|
565
565
|
nodes.append(node)
|
|
566
566
|
|
|
567
|
-
if prefetch_relationships:
|
|
567
|
+
if prefetch_relationships or (include and any(rel in include for rel in node._relationships)):
|
|
568
568
|
await node._process_relationships(
|
|
569
|
-
node_data=item,
|
|
569
|
+
node_data=item,
|
|
570
|
+
branch=branch,
|
|
571
|
+
related_nodes=related_nodes,
|
|
572
|
+
timeout=timeout,
|
|
570
573
|
)
|
|
571
574
|
|
|
572
575
|
return ProcessRelationsNode(nodes=nodes, related_nodes=related_nodes)
|
|
@@ -816,6 +819,7 @@ class InfrahubClient(BaseClient):
|
|
|
816
819
|
branch=branch,
|
|
817
820
|
prefetch_relationships=prefetch_relationships,
|
|
818
821
|
timeout=timeout,
|
|
822
|
+
include=include,
|
|
819
823
|
)
|
|
820
824
|
return response, process_result
|
|
821
825
|
|
|
@@ -1103,13 +1107,13 @@ class InfrahubClient(BaseClient):
|
|
|
1103
1107
|
) -> dict:
|
|
1104
1108
|
url = f"{self.address}/api/query/{name}"
|
|
1105
1109
|
url_params = copy.deepcopy(params or {})
|
|
1110
|
+
url_params["branch"] = branch_name or self.default_branch
|
|
1111
|
+
|
|
1106
1112
|
headers = copy.copy(self.headers or {})
|
|
1107
1113
|
|
|
1108
1114
|
if self.insert_tracker and tracker:
|
|
1109
1115
|
headers["X-Infrahub-Tracker"] = tracker
|
|
1110
1116
|
|
|
1111
|
-
if branch_name:
|
|
1112
|
-
url_params["branch"] = branch_name
|
|
1113
1117
|
if at:
|
|
1114
1118
|
url_params["at"] = at
|
|
1115
1119
|
|
|
@@ -1565,8 +1569,7 @@ class InfrahubClientSync(BaseClient):
|
|
|
1565
1569
|
|
|
1566
1570
|
def get_user(self) -> dict:
|
|
1567
1571
|
"""Return user information"""
|
|
1568
|
-
|
|
1569
|
-
return user_info
|
|
1572
|
+
return self.execute_graphql(query=QUERY_USER)
|
|
1570
1573
|
|
|
1571
1574
|
def get_user_permissions(self) -> dict:
|
|
1572
1575
|
"""Return user permissions"""
|
|
@@ -1831,6 +1834,7 @@ class InfrahubClientSync(BaseClient):
|
|
|
1831
1834
|
schema_kind: str,
|
|
1832
1835
|
branch: str,
|
|
1833
1836
|
prefetch_relationships: bool,
|
|
1837
|
+
include: list[str] | None,
|
|
1834
1838
|
timeout: int | None = None,
|
|
1835
1839
|
) -> ProcessRelationsNodeSync:
|
|
1836
1840
|
"""Processes InfrahubNodeSync and their Relationships from the GraphQL query response.
|
|
@@ -1855,7 +1859,7 @@ class InfrahubClientSync(BaseClient):
|
|
|
1855
1859
|
node = InfrahubNodeSync.from_graphql(client=self, branch=branch, data=item, timeout=timeout)
|
|
1856
1860
|
nodes.append(node)
|
|
1857
1861
|
|
|
1858
|
-
if prefetch_relationships:
|
|
1862
|
+
if prefetch_relationships or (include and any(rel in include for rel in node._relationships)):
|
|
1859
1863
|
node._process_relationships(node_data=item, branch=branch, related_nodes=related_nodes, timeout=timeout)
|
|
1860
1864
|
|
|
1861
1865
|
return ProcessRelationsNodeSync(nodes=nodes, related_nodes=related_nodes)
|
|
@@ -1980,6 +1984,7 @@ class InfrahubClientSync(BaseClient):
|
|
|
1980
1984
|
branch=branch,
|
|
1981
1985
|
prefetch_relationships=prefetch_relationships,
|
|
1982
1986
|
timeout=timeout,
|
|
1987
|
+
include=include,
|
|
1983
1988
|
)
|
|
1984
1989
|
return response, process_result
|
|
1985
1990
|
|
|
@@ -2242,13 +2247,13 @@ class InfrahubClientSync(BaseClient):
|
|
|
2242
2247
|
) -> dict:
|
|
2243
2248
|
url = f"{self.address}/api/query/{name}"
|
|
2244
2249
|
url_params = copy.deepcopy(params or {})
|
|
2250
|
+
url_params["branch"] = branch_name or self.default_branch
|
|
2251
|
+
|
|
2245
2252
|
headers = copy.copy(self.headers or {})
|
|
2246
2253
|
|
|
2247
2254
|
if self.insert_tracker and tracker:
|
|
2248
2255
|
headers["X-Infrahub-Tracker"] = tracker
|
|
2249
2256
|
|
|
2250
|
-
if branch_name:
|
|
2251
|
-
url_params["branch"] = branch_name
|
|
2252
2257
|
if at:
|
|
2253
2258
|
url_params["at"] = at
|
|
2254
2259
|
if subscribers:
|
infrahub_sdk/ctl/cli_commands.py
CHANGED
|
@@ -409,7 +409,6 @@ def info( # noqa: PLR0915
|
|
|
409
409
|
_: str = CONFIG_PARAM,
|
|
410
410
|
) -> None:
|
|
411
411
|
"""Display the status of the Python SDK."""
|
|
412
|
-
|
|
413
412
|
info: dict[str, Any] = {
|
|
414
413
|
"error": None,
|
|
415
414
|
"status": ":x:",
|
|
@@ -417,12 +416,17 @@ def info( # noqa: PLR0915
|
|
|
417
416
|
"user_info": {},
|
|
418
417
|
"groups": {},
|
|
419
418
|
}
|
|
419
|
+
client = initialize_client_sync()
|
|
420
|
+
fetch_user_details = bool(client.config.username) or bool(client.config.api_token)
|
|
421
|
+
|
|
420
422
|
try:
|
|
421
|
-
client = initialize_client_sync()
|
|
422
423
|
info["infrahub_version"] = client.get_version()
|
|
423
|
-
|
|
424
|
+
|
|
425
|
+
if fetch_user_details:
|
|
426
|
+
info["user_info"] = client.get_user()
|
|
427
|
+
info["groups"] = client.get_user_permissions()
|
|
428
|
+
|
|
424
429
|
info["status"] = ":white_heavy_check_mark:"
|
|
425
|
-
info["groups"] = client.get_user_permissions()
|
|
426
430
|
except Exception as e:
|
|
427
431
|
info["error"] = f"{e!s} ({e.__class__.__name__})"
|
|
428
432
|
|
|
@@ -469,7 +473,7 @@ def info( # noqa: PLR0915
|
|
|
469
473
|
pretty_model = Pretty(client.config.model_dump(), expand_all=True)
|
|
470
474
|
layout["client_info"].update(Panel(pretty_model, title="Client Info"))
|
|
471
475
|
|
|
472
|
-
# Infrahub information
|
|
476
|
+
# Infrahub information panel
|
|
473
477
|
infrahub_info = Table(show_header=False, box=None)
|
|
474
478
|
if info["user_info"]:
|
|
475
479
|
infrahub_info.add_row("User:", info["user_info"]["AccountProfile"]["display_label"])
|
|
@@ -487,6 +491,8 @@ def info( # noqa: PLR0915
|
|
|
487
491
|
infrahub_info.add_row("Groups:", "")
|
|
488
492
|
for group, roles in groups.items():
|
|
489
493
|
infrahub_info.add_row("", group, ", ".join(roles))
|
|
494
|
+
else:
|
|
495
|
+
infrahub_info.add_row("User:", "anonymous")
|
|
490
496
|
|
|
491
497
|
layout["infrahub_info"].update(Panel(infrahub_info, title="Infrahub Info"))
|
|
492
498
|
|
infrahub_sdk/graphql.py
CHANGED
|
@@ -8,7 +8,9 @@ from pydantic import BaseModel
|
|
|
8
8
|
VARIABLE_TYPE_MAPPING = ((str, "String!"), (int, "Int!"), (float, "Float!"), (bool, "Boolean!"))
|
|
9
9
|
|
|
10
10
|
|
|
11
|
-
def convert_to_graphql_as_string(value:
|
|
11
|
+
def convert_to_graphql_as_string(value: Any, convert_enum: bool = False) -> str: # noqa: PLR0911
|
|
12
|
+
if value is None:
|
|
13
|
+
return "null"
|
|
12
14
|
if isinstance(value, str) and value.startswith("$"):
|
|
13
15
|
return value
|
|
14
16
|
if isinstance(value, Enum):
|
infrahub_sdk/node/node.py
CHANGED
|
@@ -234,15 +234,10 @@ class InfrahubNodeBase:
|
|
|
234
234
|
|
|
235
235
|
rel: RelatedNodeBase | RelationshipManagerBase = getattr(self, item_name)
|
|
236
236
|
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
# and self._schema.get_relationship(item_name).cardinality == "one"
|
|
242
|
-
# ):
|
|
243
|
-
# data[item_name] = None
|
|
244
|
-
# continue
|
|
245
|
-
# el
|
|
237
|
+
if rel_schema.cardinality == RelationshipCardinality.ONE and rel_schema.optional and not rel.initialized:
|
|
238
|
+
data[item_name] = None
|
|
239
|
+
continue
|
|
240
|
+
|
|
246
241
|
if rel is None or not rel.initialized:
|
|
247
242
|
continue
|
|
248
243
|
|
|
@@ -315,7 +310,16 @@ class InfrahubNodeBase:
|
|
|
315
310
|
variables.pop(variable_key)
|
|
316
311
|
|
|
317
312
|
# TODO: I do not feel _great_ about this
|
|
318
|
-
|
|
313
|
+
# -> I don't even know who you are (but this is not great indeed) -- gmazoyer (quoting Thanos)
|
|
314
|
+
original_data_item = original_data.get(item)
|
|
315
|
+
original_data_item_is_none = original_data_item is None
|
|
316
|
+
if isinstance(original_data_item, dict):
|
|
317
|
+
if "node" in original_data_item:
|
|
318
|
+
original_data_item_is_none = original_data_item["node"] is None
|
|
319
|
+
elif "id" not in original_data_item:
|
|
320
|
+
original_data_item_is_none = True
|
|
321
|
+
|
|
322
|
+
if item in data and (data_item in ({}, []) or (data_item is None and original_data_item_is_none)):
|
|
319
323
|
data.pop(item)
|
|
320
324
|
|
|
321
325
|
def _strip_unmodified(self, data: dict, variables: dict) -> tuple[dict, dict]:
|
|
@@ -324,7 +328,9 @@ class InfrahubNodeBase:
|
|
|
324
328
|
relationship_property = getattr(self, relationship)
|
|
325
329
|
if not relationship_property or relationship not in data:
|
|
326
330
|
continue
|
|
327
|
-
if not relationship_property.initialized
|
|
331
|
+
if not relationship_property.initialized and (
|
|
332
|
+
not isinstance(relationship_property, RelatedNodeBase) or not relationship_property.schema.optional
|
|
333
|
+
):
|
|
328
334
|
data.pop(relationship)
|
|
329
335
|
elif isinstance(relationship_property, RelationshipManagerBase) and not relationship_property.has_update:
|
|
330
336
|
data.pop(relationship)
|
|
@@ -742,12 +748,11 @@ class InfrahubNode(InfrahubNodeBase):
|
|
|
742
748
|
continue
|
|
743
749
|
|
|
744
750
|
peer_data: dict[str, Any] = {}
|
|
745
|
-
|
|
751
|
+
should_fetch_relationship = prefetch_relationships or (include is not None and rel_name in include)
|
|
752
|
+
if rel_schema and should_fetch_relationship:
|
|
746
753
|
peer_schema = await self._client.schema.get(kind=rel_schema.peer, branch=self._branch)
|
|
747
754
|
peer_node = InfrahubNode(client=self._client, schema=peer_schema, branch=self._branch)
|
|
748
755
|
peer_data = await peer_node.generate_query_data_node(
|
|
749
|
-
include=include,
|
|
750
|
-
exclude=exclude,
|
|
751
756
|
property=property,
|
|
752
757
|
)
|
|
753
758
|
|
|
@@ -886,7 +891,11 @@ class InfrahubNode(InfrahubNodeBase):
|
|
|
886
891
|
await self._process_mutation_result(mutation_name=mutation_name, response=response, timeout=timeout)
|
|
887
892
|
|
|
888
893
|
async def _process_relationships(
|
|
889
|
-
self,
|
|
894
|
+
self,
|
|
895
|
+
node_data: dict[str, Any],
|
|
896
|
+
branch: str,
|
|
897
|
+
related_nodes: list[InfrahubNode],
|
|
898
|
+
timeout: int | None = None,
|
|
890
899
|
) -> None:
|
|
891
900
|
"""Processes the Relationships of a InfrahubNode and add Related Nodes to a list.
|
|
892
901
|
|
|
@@ -1363,7 +1372,8 @@ class InfrahubNodeSync(InfrahubNodeBase):
|
|
|
1363
1372
|
continue
|
|
1364
1373
|
|
|
1365
1374
|
peer_data: dict[str, Any] = {}
|
|
1366
|
-
|
|
1375
|
+
should_fetch_relationship = prefetch_relationships or (include is not None and rel_name in include)
|
|
1376
|
+
if rel_schema and should_fetch_relationship:
|
|
1367
1377
|
peer_schema = self._client.schema.get(kind=rel_schema.peer, branch=self._branch)
|
|
1368
1378
|
peer_node = InfrahubNodeSync(client=self._client, schema=peer_schema, branch=self._branch)
|
|
1369
1379
|
peer_data = peer_node.generate_query_data_node(include=include, exclude=exclude, property=property)
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.3
|
|
2
2
|
Name: infrahub-server
|
|
3
|
-
Version: 1.4.
|
|
3
|
+
Version: 1.4.5
|
|
4
4
|
Summary: Infrahub is taking a new approach to Infrastructure Management by providing a new generation of datastore to organize and control all the data that defines how an infrastructure should run.
|
|
5
5
|
License: Apache-2.0
|
|
6
6
|
Author: OpsMill
|
|
@@ -61,7 +61,7 @@ infrahub/constants/database.py,sha256=WmV1iuOk4xulxZHOVvO3sS_VF1eTf7fKh0TPe_RnfV
|
|
|
61
61
|
infrahub/constants/environment.py,sha256=ry-6qsBzSumOjjiq1D3XNoquf1LWqFKiQSJj8t6nET4,32
|
|
62
62
|
infrahub/context.py,sha256=8SZRKSECkkcsNNzDaKEUJ7Nyr0EzUfToAy969LXjQVk,1554
|
|
63
63
|
infrahub/core/__init__.py,sha256=z6EJBZyCYCBqinoBtX9li6BTBbbGV8WCkE_4CrEsmDA,104
|
|
64
|
-
infrahub/core/account.py,sha256=
|
|
64
|
+
infrahub/core/account.py,sha256=6f1cIDWvL-HsbzL0UwWoCbDTzx55wzd_SkpQXiKDjcE,27477
|
|
65
65
|
infrahub/core/attribute.py,sha256=f1-XLuRzbpG7T8y6pqQQqxQkbGDWhS5AZA2_r_mzY-A,44537
|
|
66
66
|
infrahub/core/branch/__init__.py,sha256=h0oIj0gHp1xI-N1cYW8_N6VZ81CBOmLuiUt5cS5nKuk,49
|
|
67
67
|
infrahub/core/branch/enums.py,sha256=vGnaTCzikvMcLikKN25TJ8uCmhnD448dp1ve1_tLjwQ,186
|
|
@@ -434,7 +434,7 @@ infrahub/events/validator_action.py,sha256=nQJH-RWcgr3-tzmIldvPmu5O7dUAmv1qQnuxx
|
|
|
434
434
|
infrahub/exceptions.py,sha256=cbM-f_2U-5ZFVZ_MaaXgs64k4M7uJ7fqDU2iCRoWlYY,11861
|
|
435
435
|
infrahub/generators/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
436
436
|
infrahub/generators/models.py,sha256=9qhSfsoG-uYux35HClAxSq7TRfkosqN3i_eQkeTokLs,1916
|
|
437
|
-
infrahub/generators/tasks.py,sha256=
|
|
437
|
+
infrahub/generators/tasks.py,sha256=Ci6lIbnUS6faGzbUjw1ggROpv17guZ-Z9HH9f6cAZv4,9563
|
|
438
438
|
infrahub/git/__init__.py,sha256=KeQ9U8UI5jDj6KB6j00Oal7MZmtOD9vKqVgiezG_EQA,281
|
|
439
439
|
infrahub/git/base.py,sha256=RNXow4RzTBJyjTmT1vZO9_DZSx4Dyv12M-bK_xTBTbg,38657
|
|
440
440
|
infrahub/git/constants.py,sha256=XpzcAkXbsgXZgrXey74id1sXV8Q6EHb_4FNw7BndxyY,106
|
|
@@ -442,7 +442,7 @@ infrahub/git/directory.py,sha256=fozxLXXJPweHG95yQwQkR5yy3sfTdmHiczCAJnsUX54,861
|
|
|
442
442
|
infrahub/git/integrator.py,sha256=C9h1qo8EVE8FjwzGWHhTD50I8TuCTH9asgC8-z5eK-g,62818
|
|
443
443
|
infrahub/git/models.py,sha256=ozk9alxQ8Ops1lw1g8iR3O7INuw1VPsEUr5Wceh9HQY,12152
|
|
444
444
|
infrahub/git/repository.py,sha256=wPsJAA9aHTHdfw0gqCfkNHvcivs7JabsDf-uazptZt0,10928
|
|
445
|
-
infrahub/git/tasks.py,sha256=
|
|
445
|
+
infrahub/git/tasks.py,sha256=aBFN7yV72UshcxFljrmHAKGSDoe0e1eVjrnyPDXQEM8,37515
|
|
446
446
|
infrahub/git/utils.py,sha256=xhWxlu_FbMqbrwanpPkex4hKRS_d2AFzlxI_6kVQllw,1741
|
|
447
447
|
infrahub/git/worktree.py,sha256=8IYJWOBytKUWwhMmMVehR4ceeO9e13nV-mvn3iVEgZY,1727
|
|
448
448
|
infrahub/git_credential/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
@@ -622,7 +622,7 @@ infrahub/proposed_change/branch_diff.py,sha256=IdMxf5zPmhybQKPPz7AlruNmLCKf5VISP
|
|
|
622
622
|
infrahub/proposed_change/checker.py,sha256=ZhNEVJKsQbHH2UE1O35MfOVa8cK1QGEqGyn6MsOuqSQ,1558
|
|
623
623
|
infrahub/proposed_change/constants.py,sha256=auifG94Oo2cJ4RwZx4P-XDPDpKYPtEVxh013KPfiEdU,2080
|
|
624
624
|
infrahub/proposed_change/models.py,sha256=ivWJmEAihprKmwgaBGDJ4Koq4ETciE5GfDp86KHDnns,5892
|
|
625
|
-
infrahub/proposed_change/tasks.py,sha256
|
|
625
|
+
infrahub/proposed_change/tasks.py,sha256=M1vdCE1J_IBxGwSnQLWwobxhOSDaaxuvEScgZuYbus8,63991
|
|
626
626
|
infrahub/py.typed,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
627
627
|
infrahub/pytest_plugin.py,sha256=u3t0WgLMo9XmuQYeb28mccQ3xbnyv2Fv173YWl1zBiM,6678
|
|
628
628
|
infrahub/schema/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
@@ -709,9 +709,9 @@ infrahub_sdk/_importer.py,sha256=8oHTMxa_AMO_qbfb3UXNfjSr31S5YJTcqe-YMrixY_E,225
|
|
|
709
709
|
infrahub_sdk/analyzer.py,sha256=UDJN372vdAiuAv2TEyPUlsSVoUfZN6obWkIokNNaHbA,4148
|
|
710
710
|
infrahub_sdk/async_typer.py,sha256=Gj7E8EGdjA-XF404vr9cBt20mmbroQh7N68HXhWYx00,892
|
|
711
711
|
infrahub_sdk/batch.py,sha256=LRZ_04ic56ll9FBjgXCYrJRDJcwB3wR1yX4grrQutDQ,3795
|
|
712
|
-
infrahub_sdk/branch.py,sha256=
|
|
712
|
+
infrahub_sdk/branch.py,sha256=nj0rAOFSqZiAZ5xjwjwTSXdNSso5s7zm6y_6ts6ieSQ,12791
|
|
713
713
|
infrahub_sdk/checks.py,sha256=rFHlEY8XEYcjpLCg6gd9a0R8vPnkxNp0OnXk-odsZKY,5707
|
|
714
|
-
infrahub_sdk/client.py,sha256=
|
|
714
|
+
infrahub_sdk/client.py,sha256=qO5Sd8M1Y5YcZeWXWa6ECExshJS78qajAKpwctZwQas,101899
|
|
715
715
|
infrahub_sdk/config.py,sha256=wnVRkaVO4Nd2IBLRVpLtrC-jjW399mgr1DprohTEzQQ,7936
|
|
716
716
|
infrahub_sdk/constants.py,sha256=Ca66r09eDzpmMhfFAspKFSehSxOmoflVongP-UuBDc4,138
|
|
717
717
|
infrahub_sdk/context.py,sha256=QgXZvtUrKolp6ML8TguVK87Wuu-3KyizZVV_N2F4oCw,400
|
|
@@ -719,7 +719,7 @@ infrahub_sdk/ctl/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,
|
|
|
719
719
|
infrahub_sdk/ctl/branch.py,sha256=GeGDNGNpew93MZblqhG0r45wqSz_p8CcQ9R8zuj_jmg,4742
|
|
720
720
|
infrahub_sdk/ctl/check.py,sha256=HWsK1rTpGF2VvRBiS5KZrRxXrsAHDXoFS3wJkmq8pik,7895
|
|
721
721
|
infrahub_sdk/ctl/cli.py,sha256=A9jJKYBo5opzIIyWYf6niyAHhy49V59g6biueMDFbpE,328
|
|
722
|
-
infrahub_sdk/ctl/cli_commands.py,sha256=
|
|
722
|
+
infrahub_sdk/ctl/cli_commands.py,sha256=fExd8OiXwzfDXPPq_JC9jPKH58k3o9JK9-yf18te2nU,18753
|
|
723
723
|
infrahub_sdk/ctl/client.py,sha256=6bmXmQta9qQCJ8HybQwt2uSF2X1Em91xNFpwiKFujxs,2083
|
|
724
724
|
infrahub_sdk/ctl/config.py,sha256=y3kTvfxDO2FKzgvaIXKPKOES7BqXT-s9Kuww7ROfs-4,3039
|
|
725
725
|
infrahub_sdk/ctl/exceptions.py,sha256=RPdBtIj5qVvNqNR9Y-mPNF7kDUxXUUCac5msyitrBXo,272
|
|
@@ -739,13 +739,13 @@ infrahub_sdk/data.py,sha256=4d8Fd1s7lTeOu8JWXsK2m2BM8t_5HG0Z73fnCZGc7Pc,841
|
|
|
739
739
|
infrahub_sdk/diff.py,sha256=Ms-3YyXo-DoF1feV9qP7GKakBYUNFsULZdy-yMEG71w,4258
|
|
740
740
|
infrahub_sdk/exceptions.py,sha256=gZLfZhyDd0M-w5WMzzfPkFwha-aZirJ739N_OMN7Ujs,5728
|
|
741
741
|
infrahub_sdk/generator.py,sha256=I00G7BdQohJFZ7wQru1SWcwO41gPbuQ3ZGEDVkLIn60,3403
|
|
742
|
-
infrahub_sdk/graphql.py,sha256=
|
|
742
|
+
infrahub_sdk/graphql.py,sha256=UQValA_5oEtdm2VC2tuzUnjm4CEj3J0qk79f70cLr84,7024
|
|
743
743
|
infrahub_sdk/groups.py,sha256=GL14ByW4GHrkqOLJ-_vGhu6bkYDxljqPtkErcQVehv0,711
|
|
744
744
|
infrahub_sdk/jinja2.py,sha256=lTfV9E_P5gApaX6RW9M8U8oixQi-0H3U8wcs8fdGVaU,1150
|
|
745
745
|
infrahub_sdk/node/__init__.py,sha256=clAUZ9lNVPFguelR5Sg9PzklAZruTKEm2xk-BaO68l8,1262
|
|
746
746
|
infrahub_sdk/node/attribute.py,sha256=oEY1qxip8ETEx9Q33NhSQo013zmzrmpVIFzSkEMUY8M,4547
|
|
747
747
|
infrahub_sdk/node/constants.py,sha256=TJO4uxvv7sc3FjoLdQdV7Ccymqz8AqxDenARst8awb4,775
|
|
748
|
-
infrahub_sdk/node/node.py,sha256=
|
|
748
|
+
infrahub_sdk/node/node.py,sha256=9ZDySD3NLRgu9hDsw71YO_LLUGKsT0JOMy2kOXzvyFU,74201
|
|
749
749
|
infrahub_sdk/node/parsers.py,sha256=sLDdT6neoYSZIjOCmq8Bgd0LK8FFoasjvJLuSz0whSU,543
|
|
750
750
|
infrahub_sdk/node/property.py,sha256=8Mjkc8bp3kLlHyllwxDJlpJTuOA1ciMgY8mtH3dFVLM,728
|
|
751
751
|
infrahub_sdk/node/related_node.py,sha256=fPMnZ83OZnnbimaPC14MdE3lR-kumAA6hbOhRlo1gms,10093
|
|
@@ -827,8 +827,8 @@ infrahub_testcontainers/models.py,sha256=ASYyvl7d_WQz_i7y8-3iab9hwwmCl3OCJavqVbe
|
|
|
827
827
|
infrahub_testcontainers/performance_test.py,sha256=hvwiy6tc_lWniYqGkqfOXVGAmA_IV15VOZqbiD9ezno,6149
|
|
828
828
|
infrahub_testcontainers/plugin.py,sha256=I3RuZQ0dARyKHuqCf0y1Yj731P2Mwf3BJUehRJKeWrs,5645
|
|
829
829
|
infrahub_testcontainers/prometheus.yml,sha256=610xQEyj3xuVJMzPkC4m1fRnCrjGpiRBrXA2ytCLa54,599
|
|
830
|
-
infrahub_server-1.4.
|
|
831
|
-
infrahub_server-1.4.
|
|
832
|
-
infrahub_server-1.4.
|
|
833
|
-
infrahub_server-1.4.
|
|
834
|
-
infrahub_server-1.4.
|
|
830
|
+
infrahub_server-1.4.5.dist-info/LICENSE.txt,sha256=7GQO7kxVoQYnZtFrjZBKLRXbrGwwwimHPPOJtqXsozQ,11340
|
|
831
|
+
infrahub_server-1.4.5.dist-info/METADATA,sha256=MHlD-kNOoe00t0MsyjiyHHPyfF4WkAneljzGh6VJg90,8277
|
|
832
|
+
infrahub_server-1.4.5.dist-info/WHEEL,sha256=b4K_helf-jlQoXBBETfwnf4B04YC67LOev0jo4fX5m8,88
|
|
833
|
+
infrahub_server-1.4.5.dist-info/entry_points.txt,sha256=UXIeFWDsrV-4IllNvUEd6KieYGzQfn9paga2YyABOQI,393
|
|
834
|
+
infrahub_server-1.4.5.dist-info/RECORD,,
|
|
File without changes
|
|
File without changes
|
|
File without changes
|