infrahub-server 1.2.9rc0__py3-none-any.whl → 1.2.11__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/computed_attribute/models.py +13 -0
- infrahub/computed_attribute/tasks.py +48 -26
- infrahub/config.py +9 -0
- infrahub/core/attribute.py +43 -2
- infrahub/core/branch/models.py +8 -9
- infrahub/core/branch/tasks.py +0 -2
- infrahub/core/constants/infrahubkind.py +1 -0
- infrahub/core/constraint/node/runner.py +1 -1
- infrahub/core/diff/calculator.py +65 -11
- infrahub/core/diff/combiner.py +38 -31
- infrahub/core/diff/coordinator.py +44 -28
- infrahub/core/diff/data_check_synchronizer.py +3 -2
- infrahub/core/diff/enricher/hierarchy.py +36 -27
- infrahub/core/diff/ipam_diff_parser.py +5 -4
- infrahub/core/diff/merger/merger.py +46 -16
- infrahub/core/diff/merger/serializer.py +1 -0
- infrahub/core/diff/model/field_specifiers_map.py +64 -0
- infrahub/core/diff/model/path.py +58 -58
- infrahub/core/diff/parent_node_adder.py +14 -16
- infrahub/core/diff/query/drop_nodes.py +42 -0
- infrahub/core/diff/query/field_specifiers.py +8 -7
- infrahub/core/diff/query/filters.py +15 -1
- infrahub/core/diff/query/merge.py +264 -28
- infrahub/core/diff/query/save.py +6 -2
- infrahub/core/diff/query_parser.py +55 -65
- infrahub/core/diff/repository/deserializer.py +38 -24
- infrahub/core/diff/repository/repository.py +31 -12
- infrahub/core/diff/tasks.py +3 -3
- infrahub/core/graph/__init__.py +1 -1
- infrahub/core/migrations/graph/__init__.py +2 -0
- infrahub/core/migrations/graph/m027_delete_isolated_nodes.py +50 -0
- infrahub/core/migrations/graph/m028_delete_diffs.py +38 -0
- infrahub/core/node/resource_manager/ip_address_pool.py +6 -2
- infrahub/core/node/resource_manager/ip_prefix_pool.py +6 -2
- infrahub/core/protocols.py +4 -0
- infrahub/core/query/branch.py +27 -17
- infrahub/core/query/diff.py +169 -51
- infrahub/core/query/node.py +39 -5
- infrahub/core/query/relationship.py +105 -30
- infrahub/core/query/subquery.py +2 -2
- infrahub/core/relationship/model.py +1 -1
- infrahub/core/schema/definitions/core/__init__.py +8 -1
- infrahub/core/schema/definitions/core/resource_pool.py +20 -0
- infrahub/core/schema/schema_branch.py +3 -0
- infrahub/core/validators/tasks.py +1 -1
- infrahub/core/validators/uniqueness/query.py +7 -0
- infrahub/database/__init__.py +5 -4
- infrahub/graphql/app.py +1 -1
- infrahub/graphql/loaders/node.py +1 -1
- infrahub/graphql/loaders/peers.py +1 -1
- infrahub/graphql/mutations/proposed_change.py +1 -1
- infrahub/graphql/queries/diff/tree.py +2 -1
- infrahub/graphql/queries/relationship.py +1 -1
- infrahub/graphql/queries/task.py +10 -0
- infrahub/graphql/resolvers/many_relationship.py +4 -4
- infrahub/graphql/resolvers/resolver.py +4 -4
- infrahub/graphql/resolvers/single_relationship.py +2 -2
- infrahub/graphql/subscription/graphql_query.py +2 -2
- infrahub/graphql/types/branch.py +1 -1
- infrahub/graphql/types/task_log.py +3 -2
- infrahub/message_bus/operations/refresh/registry.py +1 -1
- infrahub/task_manager/task.py +44 -4
- infrahub/telemetry/database.py +1 -1
- infrahub/telemetry/tasks.py +1 -1
- infrahub/trigger/models.py +11 -1
- infrahub/trigger/setup.py +51 -15
- infrahub/trigger/tasks.py +1 -4
- infrahub/types.py +1 -1
- infrahub/webhook/models.py +2 -1
- infrahub/workflows/catalogue.py +9 -0
- infrahub/workflows/initialization.py +1 -3
- infrahub_sdk/timestamp.py +2 -2
- {infrahub_server-1.2.9rc0.dist-info → infrahub_server-1.2.11.dist-info}/METADATA +3 -3
- {infrahub_server-1.2.9rc0.dist-info → infrahub_server-1.2.11.dist-info}/RECORD +79 -75
- infrahub_testcontainers/docker-compose.test.yml +3 -3
- infrahub_testcontainers/performance_test.py +6 -3
- {infrahub_server-1.2.9rc0.dist-info → infrahub_server-1.2.11.dist-info}/LICENSE.txt +0 -0
- {infrahub_server-1.2.9rc0.dist-info → infrahub_server-1.2.11.dist-info}/WHEEL +0 -0
- {infrahub_server-1.2.9rc0.dist-info → infrahub_server-1.2.11.dist-info}/entry_points.txt +0 -0
infrahub/core/diff/model/path.py
CHANGED
|
@@ -81,6 +81,21 @@ def deserialize_tracking_id(tracking_id_str: str) -> TrackingId:
|
|
|
81
81
|
raise ValueError(f"{tracking_id_str} is not a valid TrackingId")
|
|
82
82
|
|
|
83
83
|
|
|
84
|
+
@dataclass
|
|
85
|
+
class NodeIdentifier:
|
|
86
|
+
"""Uniquely identifying nodes that have had their kind or inheritance updated requires all of these fields"""
|
|
87
|
+
|
|
88
|
+
uuid: str
|
|
89
|
+
kind: str
|
|
90
|
+
db_id: str
|
|
91
|
+
|
|
92
|
+
def __hash__(self) -> int:
|
|
93
|
+
return hash(f"{self.uuid}:{self.kind}:{self.db_id}")
|
|
94
|
+
|
|
95
|
+
def __str__(self) -> str:
|
|
96
|
+
return f"{self.kind} '{self.uuid}' ({self.db_id})"
|
|
97
|
+
|
|
98
|
+
|
|
84
99
|
@dataclass
|
|
85
100
|
class NodeDiffFieldSummary:
|
|
86
101
|
kind: str
|
|
@@ -307,18 +322,26 @@ class ParentNodeInfo:
|
|
|
307
322
|
|
|
308
323
|
@dataclass
|
|
309
324
|
class EnrichedDiffNode(BaseSummary):
|
|
310
|
-
|
|
311
|
-
kind: str
|
|
325
|
+
identifier: NodeIdentifier
|
|
312
326
|
label: str
|
|
313
327
|
path_identifier: str = field(default="", kw_only=True)
|
|
314
328
|
changed_at: Timestamp | None = field(default=None, kw_only=True)
|
|
315
329
|
action: DiffAction
|
|
330
|
+
is_node_kind_migration: bool = field(default=False)
|
|
316
331
|
conflict: EnrichedDiffConflict | None = field(default=None)
|
|
317
332
|
attributes: set[EnrichedDiffAttribute] = field(default_factory=set)
|
|
318
333
|
relationships: set[EnrichedDiffRelationship] = field(default_factory=set)
|
|
319
334
|
|
|
320
335
|
def __hash__(self) -> int:
|
|
321
|
-
return hash(self.
|
|
336
|
+
return hash(self.identifier)
|
|
337
|
+
|
|
338
|
+
@property
|
|
339
|
+
def uuid(self) -> str:
|
|
340
|
+
return self.identifier.uuid
|
|
341
|
+
|
|
342
|
+
@property
|
|
343
|
+
def kind(self) -> str:
|
|
344
|
+
return self.identifier.kind
|
|
322
345
|
|
|
323
346
|
@property
|
|
324
347
|
def num_properties(self) -> int:
|
|
@@ -402,11 +425,11 @@ class EnrichedDiffNode(BaseSummary):
|
|
|
402
425
|
@classmethod
|
|
403
426
|
def from_calculated_node(cls, calculated_node: DiffNode) -> EnrichedDiffNode:
|
|
404
427
|
return EnrichedDiffNode(
|
|
405
|
-
|
|
406
|
-
kind=calculated_node.kind,
|
|
428
|
+
identifier=calculated_node.identifier,
|
|
407
429
|
label="",
|
|
408
430
|
changed_at=calculated_node.changed_at,
|
|
409
431
|
action=calculated_node.action,
|
|
432
|
+
is_node_kind_migration=calculated_node.is_node_kind_migration,
|
|
410
433
|
attributes={
|
|
411
434
|
EnrichedDiffAttribute.from_calculated_attribute(calculated_attribute=attr)
|
|
412
435
|
for attr in calculated_node.attributes
|
|
@@ -473,24 +496,24 @@ class EnrichedDiffRoot(EnrichedDiffRootMetadata):
|
|
|
473
496
|
nodes_with_parent_uuids |= {child_n.uuid for child_n in r.nodes}
|
|
474
497
|
return {node for node in self.nodes if node.uuid not in nodes_with_parent_uuids}
|
|
475
498
|
|
|
476
|
-
def get_node(self,
|
|
499
|
+
def get_node(self, node_identifier: NodeIdentifier) -> EnrichedDiffNode:
|
|
477
500
|
for n in self.nodes:
|
|
478
|
-
if n.
|
|
501
|
+
if n.identifier == node_identifier:
|
|
479
502
|
return n
|
|
480
|
-
raise ValueError(f"No node {
|
|
503
|
+
raise ValueError(f"No node {node_identifier} in diff root")
|
|
481
504
|
|
|
482
|
-
def has_node(self,
|
|
505
|
+
def has_node(self, node_identifier: NodeIdentifier) -> bool:
|
|
483
506
|
try:
|
|
484
|
-
self.get_node(
|
|
507
|
+
self.get_node(node_identifier=node_identifier)
|
|
485
508
|
return True
|
|
486
509
|
except ValueError:
|
|
487
510
|
return False
|
|
488
511
|
|
|
489
|
-
def get_node_map(self, node_uuids: set[str] | None = None) -> dict[
|
|
512
|
+
def get_node_map(self, node_uuids: set[str] | None = None) -> dict[NodeIdentifier, EnrichedDiffNode]:
|
|
490
513
|
node_map = {}
|
|
491
514
|
for node in self.nodes:
|
|
492
|
-
if node_uuids is None or node.uuid in node_uuids:
|
|
493
|
-
node_map[node.
|
|
515
|
+
if node_uuids is None or node.identifier.uuid in node_uuids:
|
|
516
|
+
node_map[node.identifier] = node
|
|
494
517
|
return node_map
|
|
495
518
|
|
|
496
519
|
def get_all_conflicts(self) -> dict[str, EnrichedDiffConflict]:
|
|
@@ -522,49 +545,6 @@ class EnrichedDiffRoot(EnrichedDiffRootMetadata):
|
|
|
522
545
|
nodes={EnrichedDiffNode.from_calculated_node(calculated_node=n) for n in calculated_diff.nodes},
|
|
523
546
|
)
|
|
524
547
|
|
|
525
|
-
def add_parent(
|
|
526
|
-
self,
|
|
527
|
-
node_id: str,
|
|
528
|
-
parent_id: str,
|
|
529
|
-
parent_kind: str,
|
|
530
|
-
parent_label: str,
|
|
531
|
-
parent_rel_name: str,
|
|
532
|
-
parent_rel_identifier: str,
|
|
533
|
-
parent_rel_cardinality: RelationshipCardinality,
|
|
534
|
-
parent_rel_label: str = "",
|
|
535
|
-
) -> EnrichedDiffNode:
|
|
536
|
-
node = self.get_node(node_uuid=node_id)
|
|
537
|
-
if not self.has_node(node_uuid=parent_id):
|
|
538
|
-
parent = EnrichedDiffNode(
|
|
539
|
-
uuid=parent_id,
|
|
540
|
-
kind=parent_kind,
|
|
541
|
-
label=parent_label,
|
|
542
|
-
action=DiffAction.UNCHANGED,
|
|
543
|
-
changed_at=None,
|
|
544
|
-
)
|
|
545
|
-
self.nodes.add(parent)
|
|
546
|
-
|
|
547
|
-
else:
|
|
548
|
-
parent = self.get_node(node_uuid=parent_id)
|
|
549
|
-
|
|
550
|
-
if node.has_relationship(name=parent_rel_name):
|
|
551
|
-
rel = node.get_relationship(name=parent_rel_name)
|
|
552
|
-
rel.nodes.add(parent)
|
|
553
|
-
else:
|
|
554
|
-
node.relationships.add(
|
|
555
|
-
EnrichedDiffRelationship(
|
|
556
|
-
name=parent_rel_name,
|
|
557
|
-
identifier=parent_rel_identifier,
|
|
558
|
-
label=parent_rel_label,
|
|
559
|
-
cardinality=parent_rel_cardinality,
|
|
560
|
-
changed_at=None,
|
|
561
|
-
action=DiffAction.UNCHANGED,
|
|
562
|
-
nodes={parent},
|
|
563
|
-
)
|
|
564
|
-
)
|
|
565
|
-
|
|
566
|
-
return parent
|
|
567
|
-
|
|
568
548
|
|
|
569
549
|
@dataclass
|
|
570
550
|
class EnrichedDiffsMetadata:
|
|
@@ -650,6 +630,14 @@ class EnrichedDiffs(EnrichedDiffsMetadata):
|
|
|
650
630
|
def branch_node_uuids(self) -> set[str]:
|
|
651
631
|
return {n.uuid for n in self.diff_branch_diff.nodes}
|
|
652
632
|
|
|
633
|
+
@property
|
|
634
|
+
def base_node_identifiers(self) -> set[NodeIdentifier]:
|
|
635
|
+
return {n.identifier for n in self.base_branch_diff.nodes}
|
|
636
|
+
|
|
637
|
+
@property
|
|
638
|
+
def branch_node_identifiers(self) -> set[NodeIdentifier]:
|
|
639
|
+
return {n.identifier for n in self.diff_branch_diff.nodes}
|
|
640
|
+
|
|
653
641
|
|
|
654
642
|
@dataclass
|
|
655
643
|
class CalculatedDiffs:
|
|
@@ -697,13 +685,21 @@ class DiffRelationship:
|
|
|
697
685
|
|
|
698
686
|
@dataclass
|
|
699
687
|
class DiffNode:
|
|
700
|
-
|
|
701
|
-
kind: str
|
|
688
|
+
identifier: NodeIdentifier
|
|
702
689
|
changed_at: Timestamp
|
|
703
690
|
action: DiffAction
|
|
691
|
+
is_node_kind_migration: bool = field(default=False)
|
|
704
692
|
attributes: list[DiffAttribute] = field(default_factory=list)
|
|
705
693
|
relationships: list[DiffRelationship] = field(default_factory=list)
|
|
706
694
|
|
|
695
|
+
@property
|
|
696
|
+
def uuid(self) -> str:
|
|
697
|
+
return self.identifier.uuid
|
|
698
|
+
|
|
699
|
+
@property
|
|
700
|
+
def kind(self) -> str:
|
|
701
|
+
return self.identifier.kind
|
|
702
|
+
|
|
707
703
|
|
|
708
704
|
@dataclass
|
|
709
705
|
class DiffRoot:
|
|
@@ -780,6 +776,10 @@ class DatabasePath:
|
|
|
780
776
|
def node_db_id(self) -> str:
|
|
781
777
|
return self.node_node.element_id
|
|
782
778
|
|
|
779
|
+
@property
|
|
780
|
+
def node_labels(self) -> frozenset[str]:
|
|
781
|
+
return self.node_node.labels
|
|
782
|
+
|
|
783
783
|
@property
|
|
784
784
|
def node_kind(self) -> str:
|
|
785
785
|
return str(self.node_node.get("kind"))
|
|
@@ -2,14 +2,13 @@ from dataclasses import dataclass, field
|
|
|
2
2
|
|
|
3
3
|
from infrahub.core.constants import DiffAction, RelationshipCardinality
|
|
4
4
|
|
|
5
|
-
from .model.path import EnrichedDiffNode, EnrichedDiffRelationship, EnrichedDiffRoot
|
|
5
|
+
from .model.path import EnrichedDiffNode, EnrichedDiffRelationship, EnrichedDiffRoot, NodeIdentifier
|
|
6
6
|
|
|
7
7
|
|
|
8
8
|
@dataclass
|
|
9
9
|
class ParentNodeAddRequest:
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
parent_kind: str
|
|
10
|
+
node_identifier: NodeIdentifier
|
|
11
|
+
parent_identifier: NodeIdentifier
|
|
13
12
|
parent_label: str
|
|
14
13
|
parent_rel_name: str
|
|
15
14
|
parent_rel_identifier: str
|
|
@@ -20,7 +19,7 @@ class ParentNodeAddRequest:
|
|
|
20
19
|
class DiffParentNodeAdder:
|
|
21
20
|
def __init__(self) -> None:
|
|
22
21
|
self._diff_root: EnrichedDiffRoot | None = None
|
|
23
|
-
self._node_map: dict[
|
|
22
|
+
self._node_map: dict[NodeIdentifier, EnrichedDiffNode] = {}
|
|
24
23
|
|
|
25
24
|
def initialize(self, enriched_diff_root: EnrichedDiffRoot) -> None:
|
|
26
25
|
self._diff_root = enriched_diff_root
|
|
@@ -31,33 +30,32 @@ class DiffParentNodeAdder:
|
|
|
31
30
|
raise RuntimeError("Must call initialize before using")
|
|
32
31
|
return self._diff_root
|
|
33
32
|
|
|
34
|
-
def get_node(self,
|
|
35
|
-
return self._node_map[
|
|
33
|
+
def get_node(self, identifier: NodeIdentifier) -> EnrichedDiffNode:
|
|
34
|
+
return self._node_map[identifier]
|
|
36
35
|
|
|
37
|
-
def has_node(self,
|
|
38
|
-
return
|
|
36
|
+
def has_node(self, identifier: NodeIdentifier) -> bool:
|
|
37
|
+
return identifier in self._node_map
|
|
39
38
|
|
|
40
39
|
def add_node(self, node: EnrichedDiffNode) -> None:
|
|
41
|
-
if node.
|
|
40
|
+
if node.identifier in self._node_map:
|
|
42
41
|
return
|
|
43
|
-
self._node_map[node.
|
|
42
|
+
self._node_map[node.identifier] = node
|
|
44
43
|
self.get_root().nodes.add(node)
|
|
45
44
|
|
|
46
45
|
def add_parent(self, parent_request: ParentNodeAddRequest) -> EnrichedDiffNode:
|
|
47
46
|
if not self._diff_root:
|
|
48
47
|
raise RuntimeError("Must call initialize before using")
|
|
49
|
-
node = self.get_node(
|
|
50
|
-
if not self.has_node(
|
|
48
|
+
node = self.get_node(identifier=parent_request.node_identifier)
|
|
49
|
+
if not self.has_node(identifier=parent_request.parent_identifier):
|
|
51
50
|
parent = EnrichedDiffNode(
|
|
52
|
-
|
|
53
|
-
kind=parent_request.parent_kind,
|
|
51
|
+
identifier=parent_request.parent_identifier,
|
|
54
52
|
label=parent_request.parent_label,
|
|
55
53
|
action=DiffAction.UNCHANGED,
|
|
56
54
|
changed_at=None,
|
|
57
55
|
)
|
|
58
56
|
self.add_node(parent)
|
|
59
57
|
else:
|
|
60
|
-
parent = self.get_node(
|
|
58
|
+
parent = self.get_node(identifier=parent_request.parent_identifier)
|
|
61
59
|
|
|
62
60
|
try:
|
|
63
61
|
rel = node.get_relationship(name=parent_request.parent_rel_name)
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
from typing import Any
|
|
2
|
+
|
|
3
|
+
from infrahub.core.diff.model.path import NodeIdentifier
|
|
4
|
+
from infrahub.core.query import Query, QueryType
|
|
5
|
+
from infrahub.database import InfrahubDatabase
|
|
6
|
+
|
|
7
|
+
|
|
8
|
+
class EnrichedDiffDropNodesQuery(Query):
|
|
9
|
+
name = "enriched_diff_drop_nodes"
|
|
10
|
+
type = QueryType.WRITE
|
|
11
|
+
insert_return = False
|
|
12
|
+
|
|
13
|
+
def __init__(self, enriched_diff_uuid: str, node_identifiers: list[NodeIdentifier], **kwargs: Any) -> None:
|
|
14
|
+
super().__init__(**kwargs)
|
|
15
|
+
self.enriched_diff_uuid = enriched_diff_uuid
|
|
16
|
+
self.node_identifiers = node_identifiers
|
|
17
|
+
|
|
18
|
+
async def query_init(self, db: InfrahubDatabase, **kwargs: Any) -> None: # noqa: ARG002
|
|
19
|
+
self.params = {
|
|
20
|
+
"diff_root_uuid": self.enriched_diff_uuid,
|
|
21
|
+
"node_uuids": [ni.uuid for ni in self.node_identifiers],
|
|
22
|
+
"node_identifiers_map": {ni.uuid: ni.kind for ni in self.node_identifiers},
|
|
23
|
+
}
|
|
24
|
+
query = """
|
|
25
|
+
MATCH (d_root:DiffRoot {uuid: $diff_root_uuid})
|
|
26
|
+
MATCH (d_root)-[:DIFF_HAS_NODE]->(dn:DiffNode)
|
|
27
|
+
WHERE dn.uuid IN $node_uuids
|
|
28
|
+
AND dn.kind IN $node_identifiers_map[dn.uuid]
|
|
29
|
+
OPTIONAL MATCH (dn)-[:DIFF_HAS_ATTRIBUTE]-(da:DiffAttribute)
|
|
30
|
+
OPTIONAL MATCH (da)-[*]->(diff_thing)
|
|
31
|
+
DETACH DELETE diff_thing
|
|
32
|
+
DETACH DELETE da
|
|
33
|
+
WITH dn
|
|
34
|
+
OPTIONAL MATCH (dn)-[:DIFF_HAS_RELATIONSHIP]->(dr:DiffRelationship)
|
|
35
|
+
OPTIONAL MATCH (dr)-[:DIFF_HAS_ELEMENT]->(dre:DiffRelationshipElement)
|
|
36
|
+
OPTIONAL MATCH (dre)-[*]->(diff_thing)
|
|
37
|
+
DETACH DELETE diff_thing
|
|
38
|
+
DETACH DELETE dre
|
|
39
|
+
DETACH DELETE dr
|
|
40
|
+
DETACH DELETE dn
|
|
41
|
+
"""
|
|
42
|
+
self.add_to_query(query=query)
|
|
@@ -18,20 +18,21 @@ class EnrichedDiffFieldSpecifiersQuery(Query):
|
|
|
18
18
|
CALL {
|
|
19
19
|
MATCH (root:DiffRoot {uuid: $diff_id})-[:DIFF_HAS_NODE]->(node:DiffNode)-[:DIFF_HAS_ATTRIBUTE]->(attr:DiffAttribute)
|
|
20
20
|
WHERE (root.is_merged IS NULL OR root.is_merged <> TRUE)
|
|
21
|
-
RETURN node.uuid AS node_uuid, attr.name AS field_name
|
|
21
|
+
RETURN node.uuid AS node_uuid, node.kind AS node_kind, attr.name AS field_name
|
|
22
22
|
UNION
|
|
23
23
|
MATCH (root:DiffRoot {uuid: $diff_id})-[:DIFF_HAS_NODE]->(node:DiffNode)-[:DIFF_HAS_RELATIONSHIP]->(rel:DiffRelationship)
|
|
24
24
|
WHERE (root.is_merged IS NULL OR root.is_merged <> TRUE)
|
|
25
|
-
RETURN node.uuid AS node_uuid, rel.identifier AS field_name
|
|
25
|
+
RETURN node.uuid AS node_uuid, node.kind AS node_kind, rel.identifier AS field_name
|
|
26
26
|
}
|
|
27
27
|
"""
|
|
28
28
|
self.add_to_query(query=query)
|
|
29
|
-
self.return_labels = ["node_uuid", "field_name"]
|
|
30
|
-
self.order_by = ["node_uuid", "field_name"]
|
|
29
|
+
self.return_labels = ["node_uuid", "node_kind", "field_name"]
|
|
30
|
+
self.order_by = ["node_uuid", "node_kind", "field_name"]
|
|
31
31
|
|
|
32
|
-
def get_node_field_specifier_tuples(self) -> Generator[tuple[str, str], None, None]:
|
|
32
|
+
def get_node_field_specifier_tuples(self) -> Generator[tuple[str, str, str], None, None]:
|
|
33
33
|
for result in self.get_results():
|
|
34
34
|
node_uuid = result.get_as_str("node_uuid")
|
|
35
|
+
node_kind = result.get_as_str("node_kind")
|
|
35
36
|
field_name = result.get_as_str("field_name")
|
|
36
|
-
if node_uuid and field_name:
|
|
37
|
-
yield (node_uuid, field_name)
|
|
37
|
+
if node_uuid and node_kind and field_name:
|
|
38
|
+
yield (node_uuid, node_kind, field_name)
|
|
@@ -1,6 +1,10 @@
|
|
|
1
|
+
from collections import defaultdict
|
|
2
|
+
from typing import Any
|
|
3
|
+
|
|
1
4
|
from pydantic import BaseModel, Field
|
|
2
5
|
|
|
3
6
|
from infrahub.core.constants import DiffAction
|
|
7
|
+
from infrahub.core.diff.model.path import NodeIdentifier
|
|
4
8
|
from infrahub.core.query.utils import filter_and, filter_or
|
|
5
9
|
|
|
6
10
|
|
|
@@ -29,6 +33,7 @@ class IncExclActionFilterOptions(BaseModel):
|
|
|
29
33
|
class EnrichedDiffQueryFilters(BaseModel):
|
|
30
34
|
ids: list[str] = Field(default_factory=list)
|
|
31
35
|
kind: IncExclFilterOptions = IncExclFilterOptions()
|
|
36
|
+
identifiers: list[NodeIdentifier] = Field(default_factory=list)
|
|
32
37
|
namespace: IncExclFilterOptions = IncExclFilterOptions()
|
|
33
38
|
status: IncExclActionFilterOptions = IncExclActionFilterOptions()
|
|
34
39
|
only_conflicted: bool = Field(default=False)
|
|
@@ -37,6 +42,7 @@ class EnrichedDiffQueryFilters(BaseModel):
|
|
|
37
42
|
def is_empty(self) -> bool:
|
|
38
43
|
if (
|
|
39
44
|
not self.ids
|
|
45
|
+
and not self.identifiers
|
|
40
46
|
and self.only_conflicted is False
|
|
41
47
|
and self.kind.is_empty
|
|
42
48
|
and self.namespace.is_empty
|
|
@@ -48,12 +54,20 @@ class EnrichedDiffQueryFilters(BaseModel):
|
|
|
48
54
|
def generate(self) -> tuple[str, dict]:
|
|
49
55
|
default_filter = ""
|
|
50
56
|
|
|
51
|
-
params = {}
|
|
57
|
+
params: dict[str, Any] = {}
|
|
52
58
|
|
|
53
59
|
if self.ids:
|
|
54
60
|
params["ids"] = self.ids
|
|
55
61
|
return "diff_node.uuid in $ids", params
|
|
56
62
|
|
|
63
|
+
if self.identifiers:
|
|
64
|
+
params["ids"] = [n.uuid for n in self.identifiers]
|
|
65
|
+
id_kind_map: dict[str, list[str]] = defaultdict(list)
|
|
66
|
+
for node_identifier in self.identifiers:
|
|
67
|
+
id_kind_map[node_identifier.uuid].append(node_identifier.kind)
|
|
68
|
+
params["id_kind_map"] = id_kind_map
|
|
69
|
+
return "diff_node.uuid in $ids AND diff_node.kind IN $id_kind_map[diff_node.uuid]", params
|
|
70
|
+
|
|
57
71
|
filters_list = []
|
|
58
72
|
|
|
59
73
|
if self.is_empty:
|