qontract-reconcile 0.10.1rc1157__py3-none-any.whl → 0.10.1rc1158__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.
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: qontract-reconcile
3
- Version: 0.10.1rc1157
3
+ Version: 0.10.1rc1158
4
4
  Summary: Collection of tools to reconcile services with their desired state as defined in the app-interface DB.
5
5
  Home-page: https://github.com/app-sre/qontract-reconcile
6
6
  Author: Red Hat App-SRE Team
@@ -94,7 +94,7 @@ reconcile/quay_mirror.py,sha256=mFp4Z5Nwl-DcFbbsJBOB8f9ldohFT-V67o868d5ux1s,1536
94
94
  reconcile/quay_mirror_org.py,sha256=utrJpJaKCs7U6WX6DODdfCeB0EmX-lUC8Y5fkmpgFSs,10764
95
95
  reconcile/quay_permissions.py,sha256=9KOutS1w4RFQqkvMSy54VtsKNx56-phzP6yI_rEW-B8,4244
96
96
  reconcile/quay_repos.py,sha256=cuEYG0HUe0ut5yvLdEwOF5-CmccpXQHRb_wDazvDrvQ,6895
97
- reconcile/queries.py,sha256=HAhD9d9TYRfkJMA5PQpv_eXuO2_wLt2Mlu2PaaBU3Xc,50201
97
+ reconcile/queries.py,sha256=VaBYi8IU01Tjrncs_Ik0D4Q-cQvlinWFhH2_8cq5x7U,50812
98
98
  reconcile/query_validator.py,sha256=MSh5pKLBksws4AqfuvT8nrIGucIbqX-IOzYyPYTLO7k,1491
99
99
  reconcile/requests_sender.py,sha256=914iluuF4UVgG3VyxxtnHOu4yf6YKS2fIy6PViSsFTQ,3875
100
100
  reconcile/resource_scraper.py,sha256=znXCHrU7YwPfKuxGBiUrV7T1tYtn4vlz9qmZlfy6Flg,2307
@@ -113,7 +113,7 @@ reconcile/terraform_cloudflare_dns.py,sha256=-aLEe2QnH5cJPu7HWqs-R9NmQ1NlFbcVUm0
113
113
  reconcile/terraform_cloudflare_resources.py,sha256=pq8Ieo5NmB-dYQ9X2F0s6iEoINMzhiqGw2yQK4ovok4,14980
114
114
  reconcile/terraform_cloudflare_users.py,sha256=iyTG5sj20Jg4J4qWJ144KVptfIHGOSfH8wQKxu0imq0,13942
115
115
  reconcile/terraform_repo.py,sha256=TKqlodhQGoAtQ6nDm04TNlpx4wpgJ_n4atoUK5Rfd7o,16444
116
- reconcile/terraform_resources.py,sha256=-sgMMHDtNvnQyNR05-MKebI_pSiyxSWAg8LmeA2_Ntk,19326
116
+ reconcile/terraform_resources.py,sha256=jpBtp6vezq79jQ7rWdk49_mW-PIUFVzFK54ilVSEZFM,19564
117
117
  reconcile/terraform_tgw_attachments.py,sha256=09svJG9pAiwWp4aY0xRoQRV90T4ZNwHG3r8flI-ZS_s,18810
118
118
  reconcile/terraform_users.py,sha256=HqSm3ev3b8dZ9J6F_phDZB-FQsnlsdeKp9RPoY1cU94,10188
119
119
  reconcile/terraform_vpc_peerings.py,sha256=VLSfuO7FvHN5McopRiKoKJDHCmIhYtlJEHv_hxV5kcM,27669
@@ -674,7 +674,7 @@ reconcile/utils/exceptions.py,sha256=DwfnWUpVOotpP79RWZ2pycmG6nKCL00RBIeZLYkQPW4
674
674
  reconcile/utils/expiration.py,sha256=3JaXH4psksR7z262k7FmdyREjCLqm66OpVMEbcfdWRo,1213
675
675
  reconcile/utils/extended_early_exit.py,sha256=QSktrmfw37zSRMNk930tDbQsVeKxaPPPD43e79DGwZw,6754
676
676
  reconcile/utils/external_resource_spec.py,sha256=bhH_xneFwATdFumTPkiQmcVKYI0gcaWuqV6FpFdf_P0,7006
677
- reconcile/utils/external_resources.py,sha256=n3c7GyFb0o5sgQ67dAsGWV40ELHJH0vMKyJMkvMHEok,7659
677
+ reconcile/utils/external_resources.py,sha256=y7Wz32cOAmCsUhQ6T-1N6lktnLikGkaHQ0SdDpMse1w,7585
678
678
  reconcile/utils/filtering.py,sha256=S4PbMHuFr3ED0P2Q_ea5CAaB7FimI62B-F5YTaKrphA,402
679
679
  reconcile/utils/git.py,sha256=wzVIYAeKlMGW538U1mkJWUI6h_mFRUY4lawh2AR8hw4,2345
680
680
  reconcile/utils/github_api.py,sha256=R8OvqyPdnRqvP-Efnv9RvIcbBlb4M0KC4RlbnJMD0Tg,2426
@@ -727,7 +727,7 @@ reconcile/utils/state.py,sha256=W0_awkLAPX18hNOF_60o73tkPxDUylqbzYNHfl_sDsk,1638
727
727
  reconcile/utils/structs.py,sha256=LcbLEg8WxfRqM6nW7NhcWN0YeqF7SQzxOgntmLs1SgY,352
728
728
  reconcile/utils/template.py,sha256=wTvRU4AnAV_o042tD4Mwls2dwWMuk7MKnde3MaCjaYg,331
729
729
  reconcile/utils/terraform_client.py,sha256=LjX2U2E0Dglt2S_KA5jWQ_dVC8sPn4FEAh0xW_d6JTk,35953
730
- reconcile/utils/terrascript_aws_client.py,sha256=0xHh8NbMbISv9zIxwcXxuYVer8dTM_2t7f6Jf4TuU2I,281362
730
+ reconcile/utils/terrascript_aws_client.py,sha256=aWaxp-lomSdlWz-yPvqAsaE-3W_jnxOIRvJuRXDGokY,283449
731
731
  reconcile/utils/three_way_diff_strategy.py,sha256=oQcHXd9LVhirJfoaOBoHUYuZVGfyL2voKr6KVI34zZE,4833
732
732
  reconcile/utils/throughput.py,sha256=iP4UWAe2LVhDo69mPPmgo9nQ7RxHD6_GS8MZe-aSiuM,344
733
733
  reconcile/utils/vault.py,sha256=pi0PuyopvCq1gW0cldvy1-Ff6bqLUlCKC2MW0sifvSE,15043
@@ -880,8 +880,8 @@ tools/test/test_qontract_cli.py,sha256=iuzKbQ6ahinvjoQmQLBrG4shey0z-1rB6qCgS8T6d
880
880
  tools/test/test_saas_promotion_state.py,sha256=dy4kkSSAQ7bC0Xp2CociETGN-2aABEfL6FU5D9Jl00Y,6056
881
881
  tools/test/test_sd_app_sre_alert_report.py,sha256=v363r9zM7__0kR5K6mvJoGFcM9BvE33fWAayrqkpojA,2116
882
882
  tools/test/test_sre_checkpoints.py,sha256=SKqPPTl9ua0RFdSSofnoQX-JZE6dFLO3LRhfQzqtfh8,2607
883
- qontract_reconcile-0.10.1rc1157.dist-info/METADATA,sha256=xO5D-srjk2bIJiQ0wi7YxeO45fY7JKWzpBl4ktpNok8,2213
884
- qontract_reconcile-0.10.1rc1157.dist-info/WHEEL,sha256=eOLhNAGa2EW3wWl_TU484h7q1UNgy0JXjjoqKoxAAQc,92
885
- qontract_reconcile-0.10.1rc1157.dist-info/entry_points.txt,sha256=GKQqCl2j2X1BJQ69een6rHcR26PmnxnONLNOQB-nRjY,491
886
- qontract_reconcile-0.10.1rc1157.dist-info/top_level.txt,sha256=l5ISPoXzt0SdR4jVdkfa7RPSKNc8zAHYWAnR-Dw8Ey8,24
887
- qontract_reconcile-0.10.1rc1157.dist-info/RECORD,,
883
+ qontract_reconcile-0.10.1rc1158.dist-info/METADATA,sha256=eMmlXcbujY4OpUxnwP4jD3BuN2P3RGmQo-btlbDJT4k,2213
884
+ qontract_reconcile-0.10.1rc1158.dist-info/WHEEL,sha256=eOLhNAGa2EW3wWl_TU484h7q1UNgy0JXjjoqKoxAAQc,92
885
+ qontract_reconcile-0.10.1rc1158.dist-info/entry_points.txt,sha256=GKQqCl2j2X1BJQ69een6rHcR26PmnxnONLNOQB-nRjY,491
886
+ qontract_reconcile-0.10.1rc1158.dist-info/top_level.txt,sha256=l5ISPoXzt0SdR4jVdkfa7RPSKNc8zAHYWAnR-Dw8Ey8,24
887
+ qontract_reconcile-0.10.1rc1158.dist-info/RECORD,,
reconcile/queries.py CHANGED
@@ -102,6 +102,12 @@ APP_INTERFACE_SETTINGS_QUERY = """
102
102
  readTimeout
103
103
  connectTimeout
104
104
  }
105
+ terraformResourcesProviderExclusionsByProvisioner {
106
+ provisioner {
107
+ name
108
+ }
109
+ excludedProviders
110
+ }
105
111
  }
106
112
  }
107
113
  """
@@ -2754,3 +2760,24 @@ JENKINS_CONFIGS = """
2754
2760
  def get_jenkins_configs():
2755
2761
  gqlapi = gql.get_api()
2756
2762
  return gqlapi.query(JENKINS_CONFIGS)["jenkins_configs"]
2763
+
2764
+
2765
+ TF_RESOURCES_PROVIDER_EXCLUSIONS_BY_PROVISIONER = """
2766
+ {
2767
+ tf_provider_exclusions_by_provisioner: app_interface_settings_v1 {
2768
+ terraformResourcesProviderExclusionsByProvisioner {
2769
+ provisioner {
2770
+ name
2771
+ }
2772
+ excludedProviders
2773
+ }
2774
+ }
2775
+ }
2776
+ """
2777
+
2778
+
2779
+ def get_tf_resources_provider_exclusions_by_provisioner():
2780
+ gqlapi = gql.get_api()
2781
+ return gqlapi.query(TF_RESOURCES_PROVIDER_EXCLUSIONS_BY_PROVISIONER)[
2782
+ "tf_provider_exclusions_by_provisioner"
2783
+ ]
@@ -241,7 +241,7 @@ def setup(
241
241
  vault_settings = get_app_interface_vault_settings()
242
242
  secret_reader = create_secret_reader(use_vault=vault_settings.vault)
243
243
 
244
- settings = queries.get_app_interface_settings()
244
+ settings = queries.get_app_interface_settings() or {}
245
245
  # initialize terrascript (scripting engine to generate terraform manifests)
246
246
  ts, working_dirs = init_working_dirs(accounts, thread_pool_size, settings=settings)
247
247
 
@@ -265,7 +265,15 @@ def setup(
265
265
  else:
266
266
  ocm_map = None
267
267
  tf_namespaces_dicts = [ns.dict(by_alias=True) for ns in tf_namespaces]
268
- ts.init_populate_specs(tf_namespaces_dicts, account_names)
268
+
269
+ provider_exclusions_by_provisioner = (
270
+ settings.get("terraformResourcesProviderExclusionsByProvisioner") or []
271
+ )
272
+ ts.init_populate_specs(
273
+ tf_namespaces_dicts,
274
+ account_names,
275
+ provider_exclusions_by_provisioner=provider_exclusions_by_provisioner,
276
+ )
269
277
  tf.populate_terraform_output_secrets(
270
278
  resource_specs=ts.resource_spec_inventory, init_rds_replica_source=True
271
279
  )
@@ -1,9 +1,6 @@
1
1
  import json
2
2
  from collections import Counter
3
- from collections.abc import (
4
- Mapping,
5
- MutableMapping,
6
- )
3
+ from collections.abc import Mapping, MutableMapping
7
4
  from typing import Any
8
5
 
9
6
  import anymarkup
@@ -25,7 +22,8 @@ PROVIDER_CLOUDFLARE = "cloudflare"
25
22
 
26
23
 
27
24
  def get_external_resource_specs(
28
- namespace_info: Mapping[str, Any], provision_provider: str | None = None
25
+ namespace_info: Mapping[str, Any],
26
+ provision_provider: str | None = None,
29
27
  ) -> list[ExternalResourceSpec]:
30
28
  specs: list[ExternalResourceSpec] = []
31
29
  if not managed_external_resources(namespace_info):
@@ -34,8 +32,6 @@ def get_external_resource_specs(
34
32
  external_resources = namespace_info.get("externalResources") or []
35
33
  for e in external_resources:
36
34
  for r in e.get("resources", []):
37
- if r.get("managed_by_erv2"):
38
- continue
39
35
  spec = ExternalResourceSpec(
40
36
  provision_provider=e["provider"],
41
37
  provisioner=e["provisioner"],
@@ -8,11 +8,7 @@ import re
8
8
  import string
9
9
  import tempfile
10
10
  from collections import Counter
11
- from collections.abc import (
12
- Iterable,
13
- Mapping,
14
- MutableMapping,
15
- )
11
+ from collections.abc import Iterable, Mapping, MutableMapping
16
12
  from dataclasses import dataclass
17
13
  from ipaddress import (
18
14
  ip_address,
@@ -383,6 +379,16 @@ class ElasticSearchLogGroupInfo:
383
379
  log_group_identifier: str
384
380
 
385
381
 
382
+ class ProviderExcludedError(Exception):
383
+ def __init__(self, spec: ExternalResourceSpec) -> None:
384
+ super().__init__(
385
+ self,
386
+ "The provider is not managed by terraform_resources in this provisioner. "
387
+ "Set the `managed_by_erv2: true` attribute in the external resource spec to fix it."
388
+ f"Provisioner: {spec.provisioner['name']}, Provider: {spec.provider}, Identifier: {spec.resource['identifier']}",
389
+ )
390
+
391
+
386
392
  class TerrascriptClient: # pylint: disable=too-many-public-methods
387
393
  """
388
394
  At a high-level, this class is responsible for generating Terraform configuration in
@@ -1537,10 +1543,38 @@ class TerrascriptClient: # pylint: disable=too-many-public-methods
1537
1543
  for spec in specs:
1538
1544
  self.populate_tf_resources(spec, ocm_map=ocm_map)
1539
1545
 
1546
+ def _get_provisioner_provider_exclusions(
1547
+ self,
1548
+ spec: ExternalResourceSpec,
1549
+ provider_exclusions_by_provisioner_name: Mapping[str, Iterable[str]],
1550
+ ) -> list[str]:
1551
+ return list(
1552
+ provider_exclusions_by_provisioner_name.get(spec.provisioner["name"], [])
1553
+ )
1554
+
1555
+ def _filter_specs_managed_by_erv2(
1556
+ self,
1557
+ specs: Iterable[ExternalResourceSpec],
1558
+ provider_exclusions_by_provisioner_name: Mapping[str, Iterable[str]],
1559
+ ) -> list[ExternalResourceSpec]:
1560
+ filtered_specs: list[ExternalResourceSpec] = []
1561
+ for spec in specs:
1562
+ if spec.resource.get("managed_by_erv2"):
1563
+ continue
1564
+
1565
+ if spec.provider in self._get_provisioner_provider_exclusions(
1566
+ spec, provider_exclusions_by_provisioner_name
1567
+ ):
1568
+ raise ProviderExcludedError(spec)
1569
+
1570
+ filtered_specs.append(spec)
1571
+ return filtered_specs
1572
+
1540
1573
  def init_populate_specs(
1541
1574
  self,
1542
1575
  namespaces: Iterable[Mapping[str, Any]],
1543
1576
  account_names: Iterable[str] | None,
1577
+ provider_exclusions_by_provisioner: Iterable[Mapping[str, Any]] | None = None,
1544
1578
  ) -> None:
1545
1579
  """
1546
1580
  Initiates resource specs from the definitions in app-interface
@@ -1551,9 +1585,24 @@ class TerrascriptClient: # pylint: disable=too-many-public-methods
1551
1585
  self.account_resource_specs: dict[str, list[ExternalResourceSpec]] = {}
1552
1586
  self.resource_spec_inventory: ExternalResourceSpecInventory = {}
1553
1587
 
1588
+ # Ensure provider exclusions are fetched
1589
+ if not provider_exclusions_by_provisioner:
1590
+ provider_exclusions_by_provisioner = (
1591
+ queries.get_tf_resources_provider_exclusions_by_provisioner() or []
1592
+ )
1593
+
1594
+ provider_exclusions_by_provisioner_name = {
1595
+ p["provisioner"]["name"]: p["excludedProviders"]
1596
+ for p in provider_exclusions_by_provisioner
1597
+ }
1598
+
1554
1599
  for namespace_info in namespaces:
1555
- specs = get_external_resource_specs(
1556
- namespace_info, provision_provider=PROVIDER_AWS
1600
+ all_specs = get_external_resource_specs(
1601
+ namespace_info,
1602
+ provision_provider=PROVIDER_AWS,
1603
+ )
1604
+ specs = self._filter_specs_managed_by_erv2(
1605
+ all_specs, provider_exclusions_by_provisioner_name
1557
1606
  )
1558
1607
  name_counter = Counter(spec.output_resource_name for spec in specs)
1559
1608
  duplicates = [name for name, count in name_counter.items() if count > 1]