qontract-reconcile 0.10.1rc879__py3-none-any.whl → 0.10.1rc894__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.
- {qontract_reconcile-0.10.1rc879.dist-info → qontract_reconcile-0.10.1rc894.dist-info}/METADATA +1 -1
- {qontract_reconcile-0.10.1rc879.dist-info → qontract_reconcile-0.10.1rc894.dist-info}/RECORD +291 -284
- reconcile/acs_rbac.py +1 -2
- reconcile/aus/advanced_upgrade_service.py +14 -14
- reconcile/aus/aus_label_source.py +1 -2
- reconcile/aus/base.py +23 -26
- reconcile/aus/cluster_version_data.py +4 -4
- reconcile/aus/models.py +2 -3
- reconcile/aus/version_gate_approver.py +2 -6
- reconcile/aus/version_gates/__init__.py +1 -3
- reconcile/aus/version_gates/sts_version_gate_handler.py +2 -3
- reconcile/aws_account_manager/integration.py +9 -14
- reconcile/aws_account_manager/reconciler.py +51 -1
- reconcile/aws_account_manager/utils.py +3 -0
- reconcile/aws_ami_cleanup/integration.py +3 -4
- reconcile/aws_iam_password_reset.py +2 -5
- reconcile/aws_version_sync/integration.py +2 -2
- reconcile/blackbox_exporter_endpoint_monitoring.py +2 -5
- reconcile/change_owners/approver.py +4 -5
- reconcile/change_owners/bundle.py +20 -22
- reconcile/change_owners/change_types.py +23 -24
- reconcile/change_owners/changes.py +13 -16
- reconcile/change_owners/decision.py +2 -5
- reconcile/change_owners/diff.py +11 -15
- reconcile/change_owners/self_service_roles.py +1 -2
- reconcile/change_owners/tester.py +7 -10
- reconcile/checkpoint.py +2 -5
- reconcile/cli.py +26 -12
- reconcile/closedbox_endpoint_monitoring_base.py +8 -11
- reconcile/cluster_deployment_mapper.py +2 -5
- reconcile/cna/assets/asset.py +4 -7
- reconcile/cna/assets/null.py +2 -5
- reconcile/cna/integration.py +2 -3
- reconcile/cna/state.py +2 -5
- reconcile/dashdotdb_base.py +8 -11
- reconcile/dashdotdb_cso.py +3 -6
- reconcile/dashdotdb_dora.py +10 -14
- reconcile/dashdotdb_dvo.py +10 -13
- reconcile/dashdotdb_slo.py +5 -8
- reconcile/database_access_manager.py +5 -6
- reconcile/dynatrace_token_provider/integration.py +3 -6
- reconcile/dynatrace_token_provider/integration_v2.py +20 -0
- reconcile/dynatrace_token_provider/meta.py +1 -0
- reconcile/external_resources/integration.py +1 -1
- reconcile/external_resources/manager.py +4 -4
- reconcile/external_resources/model.py +3 -3
- reconcile/external_resources/secrets_sync.py +5 -5
- reconcile/external_resources/state.py +5 -5
- reconcile/gabi_authorized_users.py +3 -6
- reconcile/gcr_mirror.py +1 -1
- reconcile/github_org.py +1 -3
- reconcile/github_repo_invites.py +2 -5
- reconcile/gitlab_housekeeping.py +7 -11
- reconcile/gitlab_labeler.py +1 -2
- reconcile/gitlab_members.py +2 -5
- reconcile/gitlab_permissions.py +1 -3
- reconcile/glitchtip/integration.py +5 -8
- reconcile/glitchtip_project_alerts/integration.py +57 -33
- reconcile/glitchtip_project_dsn/integration.py +8 -11
- reconcile/gql_definitions/aws_account_manager/aws_accounts.py +6 -0
- reconcile/gql_definitions/fragments/aws_account_managed.py +8 -0
- reconcile/gql_definitions/glitchtip/glitchtip_project.py +4 -4
- reconcile/gql_definitions/glitchtip_project_alerts/glitchtip_project.py +27 -7
- reconcile/integrations_manager.py +5 -8
- reconcile/jenkins/types.py +5 -6
- reconcile/jenkins_job_builder.py +9 -12
- reconcile/jenkins_roles.py +1 -1
- reconcile/jira_watcher.py +2 -2
- reconcile/ldap_groups/integration.py +2 -5
- reconcile/ocm/types.py +21 -26
- reconcile/ocm_addons_upgrade_tests_trigger.py +3 -6
- reconcile/ocm_clusters.py +8 -8
- reconcile/ocm_internal_notifications/integration.py +1 -2
- reconcile/ocm_labels/integration.py +2 -5
- reconcile/ocm_machine_pools.py +11 -15
- reconcile/ocm_upgrade_scheduler_org_updater.py +2 -5
- reconcile/openshift_base.py +29 -30
- reconcile/openshift_groups.py +15 -20
- reconcile/openshift_namespace_labels.py +8 -14
- reconcile/openshift_namespaces.py +5 -8
- reconcile/openshift_network_policies.py +2 -4
- reconcile/openshift_resources_base.py +19 -29
- reconcile/openshift_saas_deploy.py +9 -10
- reconcile/openshift_saas_deploy_change_tester.py +7 -10
- reconcile/openshift_saas_deploy_trigger_base.py +4 -7
- reconcile/openshift_saas_deploy_trigger_cleaner.py +5 -8
- reconcile/openshift_saas_deploy_trigger_configs.py +1 -2
- reconcile/openshift_saas_deploy_trigger_images.py +1 -2
- reconcile/openshift_saas_deploy_trigger_moving_commits.py +1 -2
- reconcile/openshift_saas_deploy_trigger_upstream_jobs.py +1 -2
- reconcile/openshift_tekton_resources.py +7 -11
- reconcile/openshift_upgrade_watcher.py +10 -13
- reconcile/openshift_users.py +8 -11
- reconcile/oum/base.py +3 -4
- reconcile/oum/labelset.py +1 -2
- reconcile/oum/metrics.py +2 -2
- reconcile/oum/models.py +1 -2
- reconcile/oum/standalone.py +2 -3
- reconcile/prometheus_rules_tester/integration.py +6 -9
- reconcile/quay_membership.py +1 -2
- reconcile/quay_mirror.py +12 -13
- reconcile/quay_mirror_org.py +10 -10
- reconcile/queries.py +4 -7
- reconcile/resource_scraper.py +3 -4
- reconcile/rhidp/common.py +2 -2
- reconcile/saas_auto_promotions_manager/integration.py +5 -6
- reconcile/saas_auto_promotions_manager/merge_request_manager/batcher.py +1 -2
- reconcile/saas_auto_promotions_manager/publisher.py +5 -6
- reconcile/saas_auto_promotions_manager/subscriber.py +36 -15
- reconcile/saas_auto_promotions_manager/utils/saas_files_inventory.py +8 -0
- reconcile/saas_file_validator.py +2 -5
- reconcile/signalfx_endpoint_monitoring.py +2 -5
- reconcile/skupper_network/integration.py +3 -6
- reconcile/skupper_network/models.py +3 -5
- reconcile/slack_base.py +4 -7
- reconcile/slack_usergroups.py +15 -17
- reconcile/sql_query.py +5 -9
- reconcile/status_board.py +4 -5
- reconcile/statuspage/atlassian.py +14 -15
- reconcile/statuspage/integrations/maintenances.py +3 -3
- reconcile/statuspage/page.py +8 -8
- reconcile/statuspage/state.py +4 -5
- reconcile/statuspage/status.py +7 -8
- reconcile/templating/lib/rendering.py +8 -8
- reconcile/templating/renderer.py +10 -11
- reconcile/templating/validator.py +4 -4
- reconcile/terraform_aws_route53.py +3 -6
- reconcile/terraform_cloudflare_dns.py +9 -12
- reconcile/terraform_cloudflare_resources.py +9 -11
- reconcile/terraform_cloudflare_users.py +8 -11
- reconcile/terraform_init/integration.py +2 -2
- reconcile/terraform_repo.py +11 -14
- reconcile/terraform_resources.py +20 -21
- reconcile/terraform_tgw_attachments.py +32 -36
- reconcile/terraform_users.py +6 -7
- reconcile/terraform_vpc_resources/integration.py +6 -6
- reconcile/test/conftest.py +7 -10
- reconcile/test/fixtures.py +1 -1
- reconcile/test/saas_auto_promotions_manager/conftest.py +3 -2
- reconcile/test/saas_auto_promotions_manager/merge_request_manager/renderer/conftest.py +2 -2
- reconcile/test/test_database_access_manager.py +3 -6
- reconcile/test/test_gitlab_labeler.py +2 -5
- reconcile/test/test_jump_host.py +5 -8
- reconcile/test/test_ocm_machine_pools.py +1 -4
- reconcile/test/test_openshift_base.py +3 -6
- reconcile/test/test_openshift_cluster_bots.py +5 -5
- reconcile/test/test_openshift_namespace_labels.py +2 -3
- reconcile/test/test_openshift_saas_deploy_trigger_cleaner.py +2 -2
- reconcile/test/test_saasherder.py +9 -12
- reconcile/test/test_slack_base.py +4 -6
- reconcile/test/test_status_board.py +4 -7
- reconcile/test/test_terraform_tgw_attachments.py +14 -20
- reconcile/typed_queries/alerting_services_settings.py +1 -2
- reconcile/typed_queries/app_interface_custom_messages.py +2 -3
- reconcile/typed_queries/app_interface_deadmanssnitch_settings.py +1 -3
- reconcile/typed_queries/app_interface_repo_url.py +1 -2
- reconcile/typed_queries/app_interface_state_settings.py +1 -3
- reconcile/typed_queries/app_interface_vault_settings.py +1 -2
- reconcile/typed_queries/aws_vpc_requests.py +1 -3
- reconcile/typed_queries/aws_vpcs.py +1 -3
- reconcile/typed_queries/clusters.py +2 -4
- reconcile/typed_queries/clusters_minimal.py +1 -3
- reconcile/typed_queries/clusters_with_dms.py +1 -3
- reconcile/typed_queries/dynatrace_environments.py +14 -0
- reconcile/typed_queries/external_resources.py +3 -4
- reconcile/typed_queries/pagerduty_instances.py +1 -2
- reconcile/typed_queries/repos.py +2 -3
- reconcile/typed_queries/reserved_networks.py +1 -3
- reconcile/typed_queries/saas_files.py +49 -59
- reconcile/typed_queries/slo_documents.py +1 -3
- reconcile/typed_queries/status_board.py +3 -7
- reconcile/typed_queries/tekton_pipeline_providers.py +1 -2
- reconcile/typed_queries/terraform_namespaces.py +1 -2
- reconcile/typed_queries/terraform_tgw_attachments/aws_accounts.py +1 -3
- reconcile/utils/acs/base.py +2 -3
- reconcile/utils/acs/notifiers.py +3 -3
- reconcile/utils/acs/policies.py +3 -3
- reconcile/utils/aggregated_list.py +1 -1
- reconcile/utils/amtool.py +1 -2
- reconcile/utils/aws_api.py +28 -31
- reconcile/utils/aws_api_typed/account.py +23 -0
- reconcile/utils/aws_api_typed/api.py +20 -9
- reconcile/utils/binary.py +1 -3
- reconcile/utils/clusterhealth/providerbase.py +1 -2
- reconcile/utils/clusterhealth/telemeter.py +2 -2
- reconcile/utils/deadmanssnitch_api.py +1 -2
- reconcile/utils/disabled_integrations.py +4 -6
- reconcile/utils/environ.py +1 -1
- reconcile/utils/expiration.py +3 -7
- reconcile/utils/external_resource_spec.py +3 -4
- reconcile/utils/external_resources.py +4 -7
- reconcile/utils/filtering.py +1 -2
- reconcile/utils/git.py +3 -9
- reconcile/utils/git_secrets.py +5 -5
- reconcile/utils/github_api.py +5 -9
- reconcile/utils/gitlab_api.py +2 -3
- reconcile/utils/glitchtip/client.py +2 -4
- reconcile/utils/glitchtip/models.py +8 -11
- reconcile/utils/gql.py +26 -35
- reconcile/utils/grouping.py +1 -3
- reconcile/utils/imap_client.py +2 -5
- reconcile/utils/internal_groups/client.py +1 -2
- reconcile/utils/internal_groups/models.py +8 -9
- reconcile/utils/jenkins_api.py +4 -4
- reconcile/utils/jinja2/extensions.py +1 -1
- reconcile/utils/jinja2/filters.py +4 -4
- reconcile/utils/jinja2/utils.py +16 -16
- reconcile/utils/jira_client.py +10 -11
- reconcile/utils/jjb_client.py +14 -17
- reconcile/utils/jobcontroller/controller.py +5 -5
- reconcile/utils/jobcontroller/models.py +2 -2
- reconcile/utils/jsonpath.py +4 -5
- reconcile/utils/jump_host.py +7 -8
- reconcile/utils/keycloak.py +3 -7
- reconcile/utils/ldap_client.py +2 -3
- reconcile/utils/lean_terraform_client.py +13 -17
- reconcile/utils/membershipsources/app_interface_resolver.py +1 -1
- reconcile/utils/membershipsources/models.py +19 -22
- reconcile/utils/metrics.py +13 -15
- reconcile/utils/mr/base.py +7 -11
- reconcile/utils/mr/glitchtip_access_reporter.py +2 -2
- reconcile/utils/mr/notificator.py +1 -2
- reconcile/utils/oc.py +38 -38
- reconcile/utils/oc_connection_parameters.py +24 -25
- reconcile/utils/oc_filters.py +2 -3
- reconcile/utils/oc_map.py +9 -15
- reconcile/utils/ocm/addons.py +7 -10
- reconcile/utils/ocm/base.py +38 -39
- reconcile/utils/ocm/clusters.py +6 -9
- reconcile/utils/ocm/label_sources.py +1 -2
- reconcile/utils/ocm/labels.py +3 -6
- reconcile/utils/ocm/ocm.py +11 -14
- reconcile/utils/ocm/products.py +1 -3
- reconcile/utils/ocm/search_filters.py +16 -17
- reconcile/utils/ocm/service_log.py +2 -3
- reconcile/utils/ocm/sre_capability_labels.py +4 -8
- reconcile/utils/ocm/subscriptions.py +1 -3
- reconcile/utils/ocm/syncsets.py +2 -4
- reconcile/utils/ocm/upgrades.py +5 -9
- reconcile/utils/ocm_base_client.py +13 -16
- reconcile/utils/openshift_resource.py +5 -11
- reconcile/utils/output.py +2 -3
- reconcile/utils/pagerduty_api.py +4 -5
- reconcile/utils/prometheus.py +2 -2
- reconcile/utils/promotion_state.py +4 -5
- reconcile/utils/promtool.py +2 -8
- reconcile/utils/quay_api.py +12 -22
- reconcile/utils/raw_github_api.py +3 -5
- reconcile/utils/rosa/rosa_cli.py +6 -6
- reconcile/utils/rosa/session.py +6 -7
- reconcile/utils/runtime/desired_state_diff.py +3 -8
- reconcile/utils/runtime/environment.py +4 -7
- reconcile/utils/runtime/integration.py +4 -4
- reconcile/utils/runtime/meta.py +1 -2
- reconcile/utils/runtime/runner.py +7 -10
- reconcile/utils/runtime/sharding.py +22 -27
- reconcile/utils/saasherder/interfaces.py +63 -69
- reconcile/utils/saasherder/models.py +30 -35
- reconcile/utils/saasherder/saasherder.py +39 -54
- reconcile/utils/secret_reader.py +17 -19
- reconcile/utils/slack_api.py +15 -17
- reconcile/utils/smtp_client.py +1 -2
- reconcile/utils/sqs_gateway.py +1 -3
- reconcile/utils/state.py +1 -2
- reconcile/utils/terraform/config_client.py +4 -5
- reconcile/utils/terraform_client.py +12 -8
- reconcile/utils/terrascript/cloudflare_client.py +4 -10
- reconcile/utils/terrascript/cloudflare_resources.py +10 -13
- reconcile/utils/terrascript/models.py +2 -3
- reconcile/utils/terrascript/resources.py +1 -2
- reconcile/utils/terrascript_aws_client.py +50 -38
- reconcile/utils/unleash/client.py +4 -7
- reconcile/utils/unleash/server.py +2 -2
- reconcile/utils/vault.py +8 -11
- reconcile/utils/vaultsecretref.py +2 -3
- reconcile/utils/vcs.py +7 -8
- reconcile/vault_replication.py +4 -8
- reconcile/vpc_peerings_validator.py +4 -9
- release/version.py +6 -7
- tools/app_interface_reporter.py +2 -2
- tools/cli_commands/gpg_encrypt.py +3 -6
- tools/cli_commands/systems_and_tools.py +4 -7
- tools/qontract_cli.py +105 -17
- tools/saas_promotion_state/__init__.py +0 -0
- tools/saas_promotion_state/saas_promotion_state.py +105 -0
- tools/template_validation.py +1 -1
- tools/test/conftest.py +45 -6
- tools/test/test_saas_promotion_state.py +187 -0
- {qontract_reconcile-0.10.1rc879.dist-info → qontract_reconcile-0.10.1rc894.dist-info}/WHEEL +0 -0
- {qontract_reconcile-0.10.1rc879.dist-info → qontract_reconcile-0.10.1rc894.dist-info}/entry_points.txt +0 -0
- {qontract_reconcile-0.10.1rc879.dist-info → qontract_reconcile-0.10.1rc894.dist-info}/top_level.txt +0 -0
reconcile/jira_watcher.py
CHANGED
@@ -34,8 +34,8 @@ def format_message(server, key, data, event, previous_state=None, current_state=
|
|
34
34
|
if previous_state and current_state
|
35
35
|
else ""
|
36
36
|
)
|
37
|
-
url = "{}/browse/{}"
|
38
|
-
return "{} ({}) {}{}"
|
37
|
+
url = f"{server}/browse/{key}"
|
38
|
+
return f"{url} ({summary}) {event}{info}"
|
39
39
|
|
40
40
|
|
41
41
|
def calculate_diff(server, current_state, previous_state):
|
@@ -3,10 +3,7 @@ from collections.abc import (
|
|
3
3
|
Callable,
|
4
4
|
Iterable,
|
5
5
|
)
|
6
|
-
from typing import
|
7
|
-
Any,
|
8
|
-
Optional,
|
9
|
-
)
|
6
|
+
from typing import Any
|
10
7
|
|
11
8
|
from reconcile.gql_definitions.ldap_groups.roles import RoleV1
|
12
9
|
from reconcile.gql_definitions.ldap_groups.roles import query as roles_query
|
@@ -62,7 +59,7 @@ class LdapGroupsIntegration(QontractReconcileIntegration[LdapGroupsIntegrationPa
|
|
62
59
|
return {"roles": [c.dict() for c in self.get_roles(query_func)]}
|
63
60
|
|
64
61
|
@defer
|
65
|
-
def run(self, dry_run: bool, defer:
|
62
|
+
def run(self, dry_run: bool, defer: Callable | None = None) -> None:
|
66
63
|
"""Run the integration."""
|
67
64
|
gql_api = gql.get_api()
|
68
65
|
roles = self.get_roles(gql_api.query)
|
reconcile/ocm/types.py
CHANGED
@@ -1,10 +1,5 @@
|
|
1
1
|
from __future__ import annotations
|
2
2
|
|
3
|
-
from typing import (
|
4
|
-
Optional,
|
5
|
-
Union,
|
6
|
-
)
|
7
|
-
|
8
3
|
from pydantic import (
|
9
4
|
BaseModel,
|
10
5
|
Extra,
|
@@ -18,29 +13,29 @@ class OCMClusterAutoscale(BaseModel):
|
|
18
13
|
|
19
14
|
|
20
15
|
class OCMClusterNetwork(BaseModel):
|
21
|
-
type:
|
16
|
+
type: str | None
|
22
17
|
vpc: str
|
23
18
|
service: str
|
24
19
|
pod: str
|
25
20
|
|
26
21
|
|
27
22
|
class OCMClusterSpec(BaseModel):
|
28
|
-
autoscale:
|
23
|
+
autoscale: OCMClusterAutoscale | None
|
29
24
|
channel: str
|
30
|
-
disable_user_workload_monitoring:
|
31
|
-
external_id:
|
32
|
-
id:
|
33
|
-
instance_type:
|
34
|
-
multi_az:
|
35
|
-
nodes:
|
25
|
+
disable_user_workload_monitoring: bool | None
|
26
|
+
external_id: str | None
|
27
|
+
id: str | None
|
28
|
+
instance_type: str | None
|
29
|
+
multi_az: bool | None
|
30
|
+
nodes: int | None
|
36
31
|
private: bool
|
37
32
|
product: str
|
38
33
|
provider: str
|
39
|
-
provision_shard_id:
|
34
|
+
provision_shard_id: str | None
|
40
35
|
region: str
|
41
|
-
initial_version:
|
36
|
+
initial_version: str | None
|
42
37
|
version: str
|
43
|
-
hypershift:
|
38
|
+
hypershift: bool | None
|
44
39
|
|
45
40
|
class Config:
|
46
41
|
extra = Extra.forbid
|
@@ -57,7 +52,7 @@ class OSDClusterSpec(OCMClusterSpec):
|
|
57
52
|
class ROSAOcmAwsStsAttrs(BaseModel):
|
58
53
|
installer_role_arn: str
|
59
54
|
support_role_arn: str
|
60
|
-
controlplane_role_arn:
|
55
|
+
controlplane_role_arn: str | None
|
61
56
|
worker_role_arn: str
|
62
57
|
|
63
58
|
class Config:
|
@@ -66,7 +61,7 @@ class ROSAOcmAwsStsAttrs(BaseModel):
|
|
66
61
|
|
67
62
|
class ROSAOcmAwsAttrs(BaseModel):
|
68
63
|
creator_role_arn: str
|
69
|
-
sts:
|
64
|
+
sts: ROSAOcmAwsStsAttrs | None
|
70
65
|
|
71
66
|
class Config:
|
72
67
|
extra = Extra.forbid
|
@@ -82,9 +77,9 @@ class ROSAClusterAWSAccount(BaseModel):
|
|
82
77
|
|
83
78
|
class ROSAClusterSpec(OCMClusterSpec):
|
84
79
|
account: ROSAClusterAWSAccount
|
85
|
-
subnet_ids:
|
86
|
-
availability_zones:
|
87
|
-
oidc_endpoint_url:
|
80
|
+
subnet_ids: list[str] | None
|
81
|
+
availability_zones: list[str] | None
|
82
|
+
oidc_endpoint_url: str | None
|
88
83
|
|
89
84
|
class Config:
|
90
85
|
extra = Extra.forbid
|
@@ -93,18 +88,18 @@ class ROSAClusterSpec(OCMClusterSpec):
|
|
93
88
|
class ClusterMachinePool(BaseModel):
|
94
89
|
id: str
|
95
90
|
instance_type: str
|
96
|
-
replicas:
|
97
|
-
autoscale:
|
91
|
+
replicas: int | None
|
92
|
+
autoscale: OCMClusterAutoscale | None
|
98
93
|
|
99
94
|
|
100
95
|
class OCMSpec(BaseModel):
|
101
|
-
path:
|
102
|
-
spec:
|
96
|
+
path: str | None
|
97
|
+
spec: OSDClusterSpec | ROSAClusterSpec | OCMClusterSpec
|
103
98
|
machine_pools: list[ClusterMachinePool] = Field(
|
104
99
|
default_factory=list, alias="machinePools"
|
105
100
|
)
|
106
101
|
network: OCMClusterNetwork
|
107
|
-
domain:
|
102
|
+
domain: str | None
|
108
103
|
server_url: str = Field("", alias="serverUrl")
|
109
104
|
console_url: str = Field("", alias="consoleUrl")
|
110
105
|
elb_fqdn: str = Field("", alias="elbFQDN")
|
@@ -1,8 +1,5 @@
|
|
1
1
|
import logging
|
2
|
-
from
|
3
|
-
Callable,
|
4
|
-
Optional,
|
5
|
-
)
|
2
|
+
from collections.abc import Callable
|
6
3
|
|
7
4
|
from reconcile import queries
|
8
5
|
from reconcile.typed_queries.app_interface_vault_settings import (
|
@@ -18,7 +15,7 @@ QONTRACT_INTEGRATION = "ocm-addons-upgrade-tests-trigger"
|
|
18
15
|
|
19
16
|
|
20
17
|
@defer
|
21
|
-
def run(dry_run: bool, defer:
|
18
|
+
def run(dry_run: bool, defer: Callable | None = None) -> None:
|
22
19
|
settings = queries.get_app_interface_settings()
|
23
20
|
vault_settings = get_app_interface_vault_settings()
|
24
21
|
secret_reader = create_secret_reader(use_vault=vault_settings.vault)
|
@@ -40,7 +37,7 @@ def run(dry_run: bool, defer: Optional[Callable] = None) -> None:
|
|
40
37
|
)
|
41
38
|
|
42
39
|
ocm = ocm_map[ocm_name]
|
43
|
-
state_updates: dict[str,
|
40
|
+
state_updates: dict[str, str | None] = {}
|
44
41
|
for aut in addon_upgrade_tests:
|
45
42
|
addon_name = aut["addon"]["name"]
|
46
43
|
addon_org_version = None
|
reconcile/ocm_clusters.py
CHANGED
@@ -4,7 +4,7 @@ from collections.abc import (
|
|
4
4
|
Iterable,
|
5
5
|
Mapping,
|
6
6
|
)
|
7
|
-
from typing import Any
|
7
|
+
from typing import Any
|
8
8
|
|
9
9
|
import reconcile.utils.mr.clusters_updates as cu
|
10
10
|
import reconcile.utils.ocm as ocmmod
|
@@ -283,7 +283,7 @@ def get_cluster_ocm_update_spec(
|
|
283
283
|
|
284
284
|
|
285
285
|
def _app_interface_updates_mr(
|
286
|
-
clusters_updates: Mapping[str, Any], gitlab_project_id:
|
286
|
+
clusters_updates: Mapping[str, Any], gitlab_project_id: str | None, dry_run: bool
|
287
287
|
):
|
288
288
|
"""Creates an MR to app-interface with the necessary cluster manifest updates
|
289
289
|
|
@@ -318,15 +318,15 @@ def _cluster_is_compatible(cluster: Mapping[str, Any]) -> bool:
|
|
318
318
|
|
319
319
|
|
320
320
|
class OcmClustersParams(PydanticRunParams):
|
321
|
-
gitlab_project_id:
|
321
|
+
gitlab_project_id: str | None = None
|
322
322
|
thread_pool_size: int = 10
|
323
323
|
|
324
324
|
# rosa job controller params
|
325
|
-
job_controller_cluster:
|
326
|
-
job_controller_namespace:
|
327
|
-
rosa_job_service_account:
|
328
|
-
rosa_role:
|
329
|
-
rosa_job_image:
|
325
|
+
job_controller_cluster: str | None = None
|
326
|
+
job_controller_namespace: str | None = None
|
327
|
+
rosa_job_service_account: str | None = None
|
328
|
+
rosa_role: str | None = None
|
329
|
+
rosa_job_image: str | None = None
|
330
330
|
|
331
331
|
|
332
332
|
class OcmClusters(QontractReconcileIntegration[OcmClustersParams]):
|
@@ -5,7 +5,6 @@ from collections.abc import (
|
|
5
5
|
Callable,
|
6
6
|
)
|
7
7
|
from functools import lru_cache
|
8
|
-
from typing import Optional
|
9
8
|
|
10
9
|
from reconcile.gql_definitions.common.ocm_environments import (
|
11
10
|
query as ocm_environment_query,
|
@@ -48,7 +47,7 @@ class OcmInternalNotifications(QontractReconcileIntegration[NoParams]):
|
|
48
47
|
@lru_cache
|
49
48
|
def slack_get_user_id_by_name(
|
50
49
|
self, user_name: str, mail_address: str
|
51
|
-
) ->
|
50
|
+
) -> str | None:
|
52
51
|
try:
|
53
52
|
return self.slack.get_user_id_by_name(
|
54
53
|
user_name=user_name, mail_address=mail_address
|
@@ -5,10 +5,7 @@ from collections.abc import (
|
|
5
5
|
Callable,
|
6
6
|
Iterable,
|
7
7
|
)
|
8
|
-
from typing import
|
9
|
-
Any,
|
10
|
-
Optional,
|
11
|
-
)
|
8
|
+
from typing import Any
|
12
9
|
|
13
10
|
from deepdiff import DeepHash
|
14
11
|
from pydantic import validator
|
@@ -124,7 +121,7 @@ class OcmLabelsIntegration(QontractReconcileIntegration[OcmLabelsIntegrationPara
|
|
124
121
|
init_aus_cluster_label_source(query_func),
|
125
122
|
]
|
126
123
|
|
127
|
-
def get_early_exit_desired_state(self) ->
|
124
|
+
def get_early_exit_desired_state(self) -> dict[str, Any] | None:
|
128
125
|
gqlapi = gql.get_api()
|
129
126
|
desired = {
|
130
127
|
"org_labels": self.fetch_desired_state(
|
reconcile/ocm_machine_pools.py
CHANGED
@@ -3,12 +3,8 @@ from abc import (
|
|
3
3
|
ABC,
|
4
4
|
abstractmethod,
|
5
5
|
)
|
6
|
-
from collections.abc import Mapping
|
6
|
+
from collections.abc import Iterable, Mapping
|
7
7
|
from enum import Enum
|
8
|
-
from typing import (
|
9
|
-
Iterable,
|
10
|
-
Optional,
|
11
|
-
)
|
12
8
|
|
13
9
|
from pydantic import (
|
14
10
|
BaseModel,
|
@@ -100,12 +96,12 @@ class AbstractPool(ABC, BaseModel):
|
|
100
96
|
# Abstract class for machine pools, to be implemented by OSD/HyperShift classes
|
101
97
|
|
102
98
|
id: str
|
103
|
-
replicas:
|
104
|
-
taints:
|
105
|
-
labels:
|
99
|
+
replicas: int | None
|
100
|
+
taints: list[Mapping[str, str]] | None
|
101
|
+
labels: Mapping[str, str] | None
|
106
102
|
cluster: str
|
107
103
|
cluster_type: ClusterType = Field(..., exclude=True)
|
108
|
-
autoscaling:
|
104
|
+
autoscaling: AbstractAutoscaling | None
|
109
105
|
|
110
106
|
@root_validator()
|
111
107
|
@classmethod
|
@@ -131,7 +127,7 @@ class AbstractPool(ABC, BaseModel):
|
|
131
127
|
pass
|
132
128
|
|
133
129
|
@abstractmethod
|
134
|
-
def invalid_diff(self, pool: ClusterMachinePoolV1) ->
|
130
|
+
def invalid_diff(self, pool: ClusterMachinePoolV1) -> str | None:
|
135
131
|
pass
|
136
132
|
|
137
133
|
@abstractmethod
|
@@ -184,7 +180,7 @@ class MachinePool(AbstractPool):
|
|
184
180
|
or self._has_diff_autoscale(pool)
|
185
181
|
)
|
186
182
|
|
187
|
-
def invalid_diff(self, pool: ClusterMachinePoolV1) ->
|
183
|
+
def invalid_diff(self, pool: ClusterMachinePoolV1) -> str | None:
|
188
184
|
if self.instance_type != pool.instance_type:
|
189
185
|
return "instance_type"
|
190
186
|
return None
|
@@ -203,7 +199,7 @@ class MachinePool(AbstractPool):
|
|
203
199
|
cluster: str,
|
204
200
|
cluster_type: ClusterType,
|
205
201
|
):
|
206
|
-
autoscaling:
|
202
|
+
autoscaling: MachinePoolAutoscaling | None = None
|
207
203
|
if pool.autoscale:
|
208
204
|
autoscaling = MachinePoolAutoscaling(
|
209
205
|
min_replicas=pool.autoscale.min_replicas,
|
@@ -229,7 +225,7 @@ class NodePool(AbstractPool):
|
|
229
225
|
# Node pool, used for HyperShift clusters
|
230
226
|
|
231
227
|
aws_node_pool: AWSNodePool
|
232
|
-
subnet:
|
228
|
+
subnet: str | None
|
233
229
|
|
234
230
|
def delete(self, ocm: OCM) -> None:
|
235
231
|
ocm.delete_node_pool(self.cluster, self.dict(by_alias=True))
|
@@ -266,7 +262,7 @@ class NodePool(AbstractPool):
|
|
266
262
|
or self._has_diff_autoscale(pool)
|
267
263
|
)
|
268
264
|
|
269
|
-
def invalid_diff(self, pool: ClusterMachinePoolV1) ->
|
265
|
+
def invalid_diff(self, pool: ClusterMachinePoolV1) -> str | None:
|
270
266
|
if self.aws_node_pool.instance_type != pool.instance_type:
|
271
267
|
return "instance_type"
|
272
268
|
if self.subnet != pool.subnet:
|
@@ -283,7 +279,7 @@ class NodePool(AbstractPool):
|
|
283
279
|
cluster: str,
|
284
280
|
cluster_type: ClusterType,
|
285
281
|
):
|
286
|
-
autoscaling:
|
282
|
+
autoscaling: NodePoolAutoscaling | None = None
|
287
283
|
if pool.autoscale:
|
288
284
|
autoscaling = NodePoolAutoscaling(
|
289
285
|
min_replica=pool.autoscale.min_replicas,
|
@@ -1,9 +1,6 @@
|
|
1
1
|
import json
|
2
2
|
import logging
|
3
|
-
from typing import
|
4
|
-
Any,
|
5
|
-
Optional,
|
6
|
-
)
|
3
|
+
from typing import Any
|
7
4
|
|
8
5
|
import yaml
|
9
6
|
|
@@ -25,7 +22,7 @@ def render_policy(
|
|
25
22
|
template: dict[str, Any],
|
26
23
|
cluster_spec: OCMSpec,
|
27
24
|
labels: dict[str, str],
|
28
|
-
settings:
|
25
|
+
settings: dict[str, Any] | None = None,
|
29
26
|
) -> dict[str, Any]:
|
30
27
|
body = template["path"]["content"]
|
31
28
|
type = template.get("type") or "jinja2"
|
reconcile/openshift_base.py
CHANGED
@@ -12,9 +12,7 @@ from dataclasses import (
|
|
12
12
|
)
|
13
13
|
from typing import (
|
14
14
|
Any,
|
15
|
-
Optional,
|
16
15
|
Protocol,
|
17
|
-
Union,
|
18
16
|
runtime_checkable,
|
19
17
|
)
|
20
18
|
|
@@ -40,6 +38,7 @@ from reconcile.utils.oc import (
|
|
40
38
|
OCClient,
|
41
39
|
OCLogMsg,
|
42
40
|
PrimaryClusterIPCanNotBeUnsetError,
|
41
|
+
RequestEntityTooLargeError,
|
43
42
|
StatefulSetUpdateForbidden,
|
44
43
|
StatusCodeError,
|
45
44
|
UnsupportedMediaTypeError,
|
@@ -73,7 +72,7 @@ class BaseStateSpec:
|
|
73
72
|
@dataclass
|
74
73
|
class CurrentStateSpec(BaseStateSpec):
|
75
74
|
kind: str
|
76
|
-
resource_names:
|
75
|
+
resource_names: Iterable[str] | None
|
77
76
|
|
78
77
|
|
79
78
|
@dataclass
|
@@ -83,7 +82,7 @@ class DesiredStateSpec(BaseStateSpec):
|
|
83
82
|
privileged: bool = False
|
84
83
|
|
85
84
|
|
86
|
-
StateSpec =
|
85
|
+
StateSpec = CurrentStateSpec | DesiredStateSpec
|
87
86
|
|
88
87
|
|
89
88
|
@runtime_checkable
|
@@ -113,7 +112,7 @@ class HasOrgAndGithubUsername(Protocol):
|
|
113
112
|
class ClusterMap(Protocol):
|
114
113
|
"""An OCMap protocol."""
|
115
114
|
|
116
|
-
def get(self, cluster: str, privileged: bool = False) ->
|
115
|
+
def get(self, cluster: str, privileged: bool = False) -> OCCli | OCLogMsg: ...
|
117
116
|
|
118
117
|
def get_cluster(self, cluster: str, privileged: bool = False) -> OCCli: ...
|
119
118
|
|
@@ -125,9 +124,9 @@ class ClusterMap(Protocol):
|
|
125
124
|
def init_specs_to_fetch(
|
126
125
|
ri: ResourceInventory,
|
127
126
|
oc_map: ClusterMap,
|
128
|
-
namespaces:
|
129
|
-
clusters:
|
130
|
-
override_managed_types:
|
127
|
+
namespaces: Iterable[Mapping] | None = None,
|
128
|
+
clusters: Iterable[Mapping] | None = None,
|
129
|
+
override_managed_types: Iterable[str] | None = None,
|
131
130
|
managed_types_key: str = "managedResourceTypes",
|
132
131
|
) -> list[StateSpec]:
|
133
132
|
state_specs: list[StateSpec] = []
|
@@ -288,7 +287,7 @@ def populate_current_state(
|
|
288
287
|
ri: ResourceInventory,
|
289
288
|
integration: str,
|
290
289
|
integration_version: str,
|
291
|
-
caller:
|
290
|
+
caller: str | None = None,
|
292
291
|
):
|
293
292
|
# if spec.oc is None: - oc can't be none because init_namespace_specs_to_fetch does not create specs if oc is none
|
294
293
|
# return
|
@@ -318,17 +317,17 @@ def populate_current_state(
|
|
318
317
|
|
319
318
|
|
320
319
|
def fetch_current_state(
|
321
|
-
namespaces:
|
322
|
-
clusters:
|
323
|
-
thread_pool_size:
|
324
|
-
integration:
|
325
|
-
integration_version:
|
326
|
-
override_managed_types:
|
327
|
-
internal:
|
320
|
+
namespaces: Iterable[Mapping] | None = None,
|
321
|
+
clusters: Iterable[Mapping] | None = None,
|
322
|
+
thread_pool_size: int | None = None,
|
323
|
+
integration: str | None = None,
|
324
|
+
integration_version: str | None = None,
|
325
|
+
override_managed_types: Iterable[str] | None = None,
|
326
|
+
internal: bool | None = None,
|
328
327
|
use_jump_host: bool = True,
|
329
328
|
init_api_resources: bool = False,
|
330
329
|
cluster_admin: bool = False,
|
331
|
-
caller:
|
330
|
+
caller: str | None = None,
|
332
331
|
) -> tuple[ResourceInventory, OC_Map]:
|
333
332
|
ri = ResourceInventory()
|
334
333
|
settings = queries.get_app_interface_settings()
|
@@ -402,7 +401,7 @@ def apply(
|
|
402
401
|
|
403
402
|
try:
|
404
403
|
oc.apply(namespace, annotated)
|
405
|
-
except InvalidValueApplyError:
|
404
|
+
except (InvalidValueApplyError, RequestEntityTooLargeError):
|
406
405
|
oc.remove_last_applied_configuration(
|
407
406
|
namespace, resource_type, resource.name
|
408
407
|
)
|
@@ -567,11 +566,11 @@ class ApplyOptions:
|
|
567
566
|
wait_for_namespace: bool
|
568
567
|
recycle_pods: bool
|
569
568
|
take_over: bool
|
570
|
-
override_enable_deletion:
|
571
|
-
caller:
|
572
|
-
all_callers:
|
573
|
-
privileged:
|
574
|
-
enable_deletion:
|
569
|
+
override_enable_deletion: bool | None
|
570
|
+
caller: str | None
|
571
|
+
all_callers: Sequence[str] | None
|
572
|
+
privileged: bool | None
|
573
|
+
enable_deletion: bool | None
|
575
574
|
|
576
575
|
|
577
576
|
def should_apply(
|
@@ -886,7 +885,7 @@ def delete_action(
|
|
886
885
|
)
|
887
886
|
except StatusCodeError as e:
|
888
887
|
ri.register_error()
|
889
|
-
msg = "[{}/{}] {
|
888
|
+
msg = f"[{cluster}/{namespace}] {str(e)}"
|
890
889
|
logging.error(msg)
|
891
890
|
|
892
891
|
|
@@ -931,7 +930,7 @@ def _realize_resource_data_3way_diff(
|
|
931
930
|
actions: list[dict] = []
|
932
931
|
|
933
932
|
if ri.has_error_registered(cluster=cluster):
|
934
|
-
msg =
|
933
|
+
msg = f"[{cluster}] skipping realize_data for " "cluster with errors"
|
935
934
|
logging.error(msg)
|
936
935
|
return actions
|
937
936
|
|
@@ -1305,8 +1304,8 @@ def aggregate_shared_resources(namespace_info, shared_resources_type):
|
|
1305
1304
|
|
1306
1305
|
def determine_user_keys_for_access(
|
1307
1306
|
cluster_name: str,
|
1308
|
-
auth_list: Sequence[
|
1309
|
-
enforced_user_keys:
|
1307
|
+
auth_list: Sequence[dict[str, str] | HasService],
|
1308
|
+
enforced_user_keys: list[str] | None = None,
|
1310
1309
|
) -> list[str]:
|
1311
1310
|
"""Return user keys based on enabled cluster authentication methods."""
|
1312
1311
|
AUTH_METHOD_USER_KEY = {
|
@@ -1352,7 +1351,7 @@ def user_has_cluster_access(
|
|
1352
1351
|
) -> bool:
|
1353
1352
|
"""Check user has access to cluster."""
|
1354
1353
|
userkeys = determine_user_keys_for_access(cluster.name, cluster.auth)
|
1355
|
-
return any(
|
1354
|
+
return any(getattr(user, userkey) in cluster_users for userkey in userkeys)
|
1356
1355
|
|
1357
1356
|
|
1358
1357
|
def get_namespace_type_overrides(namespace: Mapping) -> dict[str, str]:
|
@@ -1368,7 +1367,7 @@ def get_namespace_type_overrides(namespace: Mapping) -> dict[str, str]:
|
|
1368
1367
|
|
1369
1368
|
|
1370
1369
|
def get_namespace_resource_types(
|
1371
|
-
namespace: Mapping, type_overrides:
|
1370
|
+
namespace: Mapping, type_overrides: dict[str, str] | None = None
|
1372
1371
|
) -> list[str]:
|
1373
1372
|
"""Returns a list with the namespace ResourceTypes, with the overrides in place
|
1374
1373
|
|
@@ -1385,7 +1384,7 @@ def get_namespace_resource_types(
|
|
1385
1384
|
|
1386
1385
|
|
1387
1386
|
def get_namespace_resource_names(
|
1388
|
-
namespace: Mapping, type_overrides:
|
1387
|
+
namespace: Mapping, type_overrides: dict[str, str] | None = None
|
1389
1388
|
) -> dict[str, list[str]]:
|
1390
1389
|
"""Returns a list with the namespace ResourceTypeNames, with the overrides in place
|
1391
1390
|
|
reconcile/openshift_groups.py
CHANGED
@@ -5,10 +5,7 @@ from collections.abc import (
|
|
5
5
|
Iterable,
|
6
6
|
Mapping,
|
7
7
|
)
|
8
|
-
from typing import
|
9
|
-
Any,
|
10
|
-
Optional,
|
11
|
-
)
|
8
|
+
from typing import Any
|
12
9
|
|
13
10
|
from sretoolbox.utils import threaded
|
14
11
|
|
@@ -53,9 +50,7 @@ def get_cluster_state(
|
|
53
50
|
try:
|
54
51
|
group = oc.get_group_if_exists(group_name)
|
55
52
|
except Exception as e:
|
56
|
-
msg =
|
57
|
-
cluster, group_name
|
58
|
-
)
|
53
|
+
msg = f"could not get group state for cluster/group combination: {cluster}/{group_name}"
|
59
54
|
logging.error(msg)
|
60
55
|
raise e
|
61
56
|
if group is None:
|
@@ -84,7 +79,7 @@ def create_groups_list(
|
|
84
79
|
|
85
80
|
|
86
81
|
def fetch_current_state(
|
87
|
-
thread_pool_size: int, internal:
|
82
|
+
thread_pool_size: int, internal: bool | None, use_jump_host: bool
|
88
83
|
) -> tuple[OCMap, list[dict[str, str]], list[str], list[dict[str, str]]]:
|
89
84
|
clusters = [c for c in get_clusters() if is_in_shard(c.name)]
|
90
85
|
ocm_clusters = [c.name for c in clusters if c.ocm is not None]
|
@@ -110,7 +105,7 @@ def fetch_current_state(
|
|
110
105
|
|
111
106
|
|
112
107
|
def fetch_desired_state(
|
113
|
-
clusters: list[str], enforced_user_keys:
|
108
|
+
clusters: list[str], enforced_user_keys: list[str] | None = None
|
114
109
|
) -> list[dict[str, str]]:
|
115
110
|
gqlapi = gql.get_api()
|
116
111
|
roles = expiration.filter(query_managed_roles(query_func=gqlapi.query).roles or [])
|
@@ -145,8 +140,8 @@ def fetch_desired_state(
|
|
145
140
|
def calculate_diff(
|
146
141
|
current_state: Iterable[Mapping[str, str]],
|
147
142
|
desired_state: Iterable[Mapping[str, str]],
|
148
|
-
) -> list[dict[str,
|
149
|
-
diff: list[dict[str,
|
143
|
+
) -> list[dict[str, str | None]]:
|
144
|
+
diff: list[dict[str, str | None]] = []
|
150
145
|
users_to_add = subtract_states(
|
151
146
|
desired_state, current_state, "add_user_to_group", "create_group"
|
152
147
|
)
|
@@ -164,8 +159,8 @@ def subtract_states(
|
|
164
159
|
subtract_state: Iterable[Mapping[str, str]],
|
165
160
|
user_action: str,
|
166
161
|
group_action: str,
|
167
|
-
) -> list[dict[str,
|
168
|
-
result: list[dict[str,
|
162
|
+
) -> list[dict[str, str | None]]:
|
163
|
+
result: list[dict[str, str | None]] = []
|
169
164
|
|
170
165
|
for f_user in from_state:
|
171
166
|
found = False
|
@@ -199,14 +194,14 @@ def subtract_states(
|
|
199
194
|
return result
|
200
195
|
|
201
196
|
|
202
|
-
def validate_diffs(diffs: Iterable[Mapping[str,
|
197
|
+
def validate_diffs(diffs: Iterable[Mapping[str, str | None]]) -> None:
|
203
198
|
gqlapi = gql.get_api()
|
204
199
|
clusters_query = query_managed_groups(query_func=gqlapi.query).clusters or []
|
205
200
|
|
206
201
|
desired_combos = [
|
207
202
|
{"cluster": diff["cluster"], "group": diff["group"]} for diff in diffs
|
208
203
|
]
|
209
|
-
desired_combos_unique: list[dict[str,
|
204
|
+
desired_combos_unique: list[dict[str, str | None]] = []
|
210
205
|
for combo in desired_combos:
|
211
206
|
if combo in desired_combos_unique:
|
212
207
|
continue
|
@@ -232,13 +227,13 @@ def validate_diffs(diffs: Iterable[Mapping[str, Optional[str]]]) -> None:
|
|
232
227
|
raise RuntimeError(msg)
|
233
228
|
|
234
229
|
|
235
|
-
def sort_diffs(diff: Mapping[str,
|
230
|
+
def sort_diffs(diff: Mapping[str, str | None]) -> int:
|
236
231
|
if diff["action"] in {"create_group", "del_user_from_group"}:
|
237
232
|
return 1
|
238
233
|
return 2
|
239
234
|
|
240
235
|
|
241
|
-
def act(diff: Mapping[str,
|
236
|
+
def act(diff: Mapping[str, str | None], oc_map: ClusterMap) -> None:
|
242
237
|
cluster = diff.get("cluster") or ""
|
243
238
|
group = diff["group"]
|
244
239
|
user = diff["user"]
|
@@ -257,16 +252,16 @@ def act(diff: Mapping[str, Optional[str]], oc_map: ClusterMap) -> None:
|
|
257
252
|
elif action == "delete_group":
|
258
253
|
logging.debug("skipping group deletion")
|
259
254
|
else:
|
260
|
-
raise Exception("invalid action: {}"
|
255
|
+
raise Exception(f"invalid action: {action}")
|
261
256
|
|
262
257
|
|
263
258
|
@defer
|
264
259
|
def run(
|
265
260
|
dry_run: bool,
|
266
261
|
thread_pool_size: int = 10,
|
267
|
-
internal:
|
262
|
+
internal: bool | None = None,
|
268
263
|
use_jump_host: bool = True,
|
269
|
-
defer:
|
264
|
+
defer: Callable | None = None,
|
270
265
|
) -> None:
|
271
266
|
oc_map, current_state, ocm_clusters, groups_list = fetch_current_state(
|
272
267
|
thread_pool_size, internal, use_jump_host
|