kaqing 1.98.15__py3-none-any.whl → 2.0.145__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.
Potentially problematic release.
This version of kaqing might be problematic. Click here for more details.
- adam/app_session.py +1 -1
- adam/apps.py +2 -2
- adam/batch.py +30 -31
- adam/checks/check_utils.py +4 -4
- adam/checks/compactionstats.py +1 -1
- adam/checks/cpu.py +2 -2
- adam/checks/disk.py +1 -1
- adam/checks/gossip.py +1 -1
- adam/checks/memory.py +3 -3
- adam/checks/status.py +1 -1
- adam/commands/alter_tables.py +81 -0
- adam/commands/app.py +3 -3
- adam/commands/app_ping.py +2 -2
- adam/commands/audit/audit.py +86 -0
- adam/commands/audit/audit_repair_tables.py +77 -0
- adam/commands/audit/audit_run.py +58 -0
- adam/commands/audit/show_last10.py +51 -0
- adam/commands/audit/show_slow10.py +50 -0
- adam/commands/audit/show_top10.py +48 -0
- adam/commands/audit/utils_show_top10.py +59 -0
- adam/commands/bash/bash.py +133 -0
- adam/commands/bash/bash_completer.py +93 -0
- adam/commands/cat.py +56 -0
- adam/commands/cd.py +12 -82
- adam/commands/check.py +6 -0
- adam/commands/cli_commands.py +3 -3
- adam/commands/code.py +60 -0
- adam/commands/command.py +48 -12
- adam/commands/commands_utils.py +4 -5
- adam/commands/cql/cql_completions.py +28 -0
- adam/commands/cql/cql_utils.py +209 -0
- adam/commands/{cqlsh.py → cql/cqlsh.py} +15 -10
- adam/commands/deploy/__init__.py +0 -0
- adam/commands/{frontend → deploy}/code_start.py +1 -1
- adam/commands/{frontend → deploy}/code_stop.py +1 -1
- adam/commands/{frontend → deploy}/code_utils.py +2 -2
- adam/commands/deploy/deploy.py +48 -0
- adam/commands/deploy/deploy_frontend.py +52 -0
- adam/commands/deploy/deploy_pg_agent.py +38 -0
- adam/commands/deploy/deploy_pod.py +110 -0
- adam/commands/deploy/deploy_utils.py +29 -0
- adam/commands/deploy/undeploy.py +48 -0
- adam/commands/deploy/undeploy_frontend.py +41 -0
- adam/commands/deploy/undeploy_pg_agent.py +42 -0
- adam/commands/deploy/undeploy_pod.py +51 -0
- adam/commands/devices/__init__.py +0 -0
- adam/commands/devices/device.py +27 -0
- adam/commands/devices/device_app.py +146 -0
- adam/commands/devices/device_auit_log.py +43 -0
- adam/commands/devices/device_cass.py +145 -0
- adam/commands/devices/device_export.py +86 -0
- adam/commands/devices/device_postgres.py +109 -0
- adam/commands/devices/devices.py +25 -0
- adam/commands/export/__init__.py +0 -0
- adam/commands/export/clean_up_export_session.py +53 -0
- adam/commands/{frontend/teardown_frontend.py → export/clean_up_export_sessions.py} +9 -11
- adam/commands/export/drop_export_database.py +58 -0
- adam/commands/export/drop_export_databases.py +46 -0
- adam/commands/export/export.py +83 -0
- adam/commands/export/export_databases.py +170 -0
- adam/commands/export/export_select.py +85 -0
- adam/commands/export/export_select_x.py +54 -0
- adam/commands/export/export_use.py +55 -0
- adam/commands/export/exporter.py +364 -0
- adam/commands/export/import_session.py +68 -0
- adam/commands/export/importer.py +67 -0
- adam/commands/export/importer_athena.py +80 -0
- adam/commands/export/importer_sqlite.py +47 -0
- adam/commands/export/show_column_counts.py +63 -0
- adam/commands/export/show_export_databases.py +39 -0
- adam/commands/export/show_export_session.py +51 -0
- adam/commands/export/show_export_sessions.py +47 -0
- adam/commands/export/utils_export.py +291 -0
- adam/commands/help.py +12 -7
- adam/commands/issues.py +6 -0
- adam/commands/kubectl.py +41 -0
- adam/commands/login.py +9 -5
- adam/commands/logs.py +2 -1
- adam/commands/ls.py +4 -107
- adam/commands/medusa/medusa.py +2 -26
- adam/commands/medusa/medusa_backup.py +2 -2
- adam/commands/medusa/medusa_restore.py +3 -4
- adam/commands/medusa/medusa_show_backupjobs.py +4 -3
- adam/commands/medusa/medusa_show_restorejobs.py +3 -3
- adam/commands/nodetool.py +9 -4
- adam/commands/param_set.py +1 -1
- adam/commands/postgres/postgres.py +42 -43
- adam/commands/postgres/postgres_context.py +248 -0
- adam/commands/postgres/postgres_preview.py +0 -1
- adam/commands/postgres/postgres_utils.py +31 -0
- adam/commands/postgres/psql_completions.py +10 -0
- adam/commands/preview_table.py +18 -40
- adam/commands/pwd.py +2 -28
- adam/commands/reaper/reaper.py +4 -24
- adam/commands/reaper/reaper_restart.py +1 -1
- adam/commands/reaper/reaper_session.py +2 -2
- adam/commands/repair/repair.py +3 -27
- adam/commands/repair/repair_log.py +1 -1
- adam/commands/repair/repair_run.py +2 -2
- adam/commands/repair/repair_scan.py +2 -7
- adam/commands/repair/repair_stop.py +1 -1
- adam/commands/report.py +6 -0
- adam/commands/restart.py +2 -2
- adam/commands/rollout.py +1 -1
- adam/commands/shell.py +33 -0
- adam/commands/show/show.py +11 -26
- adam/commands/show/show_app_actions.py +3 -0
- adam/commands/show/show_app_id.py +1 -1
- adam/commands/show/show_app_queues.py +3 -2
- adam/commands/show/show_cassandra_status.py +3 -3
- adam/commands/show/show_cassandra_version.py +3 -3
- adam/commands/show/show_commands.py +4 -1
- adam/commands/show/show_host.py +33 -0
- adam/commands/show/show_login.py +3 -0
- adam/commands/show/show_processes.py +1 -1
- adam/commands/show/show_repairs.py +2 -2
- adam/commands/show/show_storage.py +1 -1
- adam/commands/watch.py +1 -1
- adam/config.py +16 -3
- adam/embedded_params.py +1 -1
- adam/pod_exec_result.py +10 -2
- adam/repl.py +132 -117
- adam/repl_commands.py +62 -18
- adam/repl_state.py +276 -55
- adam/sql/__init__.py +0 -0
- adam/sql/sql_completer.py +120 -0
- adam/sql/sql_state_machine.py +617 -0
- adam/sql/term_completer.py +76 -0
- adam/sso/authenticator.py +1 -1
- adam/sso/authn_ad.py +36 -56
- adam/sso/authn_okta.py +6 -32
- adam/sso/cred_cache.py +1 -1
- adam/sso/idp.py +74 -9
- adam/sso/idp_login.py +2 -2
- adam/sso/idp_session.py +10 -7
- adam/utils.py +85 -4
- adam/utils_athena.py +145 -0
- adam/utils_audits.py +102 -0
- adam/utils_k8s/__init__.py +0 -0
- adam/utils_k8s/app_clusters.py +33 -0
- adam/utils_k8s/app_pods.py +31 -0
- adam/{k8s_utils → utils_k8s}/cassandra_clusters.py +6 -21
- adam/{k8s_utils → utils_k8s}/cassandra_nodes.py +12 -5
- adam/utils_k8s/config_maps.py +34 -0
- adam/utils_k8s/deployment.py +56 -0
- adam/{k8s_utils → utils_k8s}/jobs.py +1 -1
- adam/{k8s_utils → utils_k8s}/kube_context.py +1 -1
- adam/utils_k8s/pods.py +342 -0
- adam/{k8s_utils → utils_k8s}/secrets.py +4 -0
- adam/utils_k8s/service_accounts.py +169 -0
- adam/{k8s_utils → utils_k8s}/statefulsets.py +5 -4
- adam/{k8s_utils → utils_k8s}/volumes.py +9 -0
- adam/utils_net.py +24 -0
- adam/utils_repl/__init__.py +0 -0
- adam/utils_repl/automata_completer.py +48 -0
- adam/utils_repl/repl_completer.py +46 -0
- adam/utils_repl/state_machine.py +173 -0
- adam/utils_sqlite.py +101 -0
- adam/version.py +1 -1
- {kaqing-1.98.15.dist-info → kaqing-2.0.145.dist-info}/METADATA +1 -1
- kaqing-2.0.145.dist-info/RECORD +227 -0
- adam/commands/bash.py +0 -87
- adam/commands/cql_utils.py +0 -53
- adam/commands/devices.py +0 -89
- adam/commands/frontend/setup.py +0 -60
- adam/commands/frontend/setup_frontend.py +0 -58
- adam/commands/frontend/teardown.py +0 -61
- adam/commands/postgres/postgres_session.py +0 -225
- adam/commands/user_entry.py +0 -77
- adam/k8s_utils/pods.py +0 -211
- kaqing-1.98.15.dist-info/RECORD +0 -160
- /adam/commands/{frontend → audit}/__init__.py +0 -0
- /adam/{k8s_utils → commands/bash}/__init__.py +0 -0
- /adam/{medusa_show_restorejobs.py → commands/cql/__init__.py} +0 -0
- /adam/{k8s_utils → utils_k8s}/custom_resources.py +0 -0
- /adam/{k8s_utils → utils_k8s}/ingresses.py +0 -0
- /adam/{k8s_utils → utils_k8s}/services.py +0 -0
- {kaqing-1.98.15.dist-info → kaqing-2.0.145.dist-info}/WHEEL +0 -0
- {kaqing-1.98.15.dist-info → kaqing-2.0.145.dist-info}/entry_points.txt +0 -0
- {kaqing-1.98.15.dist-info → kaqing-2.0.145.dist-info}/top_level.txt +0 -0
adam/app_session.py
CHANGED
|
@@ -88,7 +88,7 @@ class AppSession:
|
|
|
88
88
|
if not forced and self.app_login:
|
|
89
89
|
return self.app_login
|
|
90
90
|
|
|
91
|
-
idp_login: IdpLogin = Idp.login(self.host, idp_uri=idp_uri, forced=forced, use_token_from_env=use_token_from_env, use_cached_creds=use_cached_creds)
|
|
91
|
+
idp_login: IdpLogin = Idp.login(self.host, idp_uri=idp_uri, forced=forced, use_token_from_env=use_token_from_env, use_cached_creds=use_cached_creds, verify=False)
|
|
92
92
|
if not idp_login:
|
|
93
93
|
log2(f"Invalid username/password.")
|
|
94
94
|
|
adam/apps.py
CHANGED
|
@@ -5,10 +5,10 @@ from typing import cast
|
|
|
5
5
|
import yaml
|
|
6
6
|
|
|
7
7
|
from adam.config import Config
|
|
8
|
-
from adam.
|
|
8
|
+
from adam.utils_k8s.ingresses import Ingresses
|
|
9
9
|
|
|
10
10
|
from . import __version__
|
|
11
|
-
from adam.
|
|
11
|
+
from adam.utils_k8s.services import Services
|
|
12
12
|
from adam.utils import copy_config_file
|
|
13
13
|
|
|
14
14
|
class AppAction:
|
adam/batch.py
CHANGED
|
@@ -1,13 +1,14 @@
|
|
|
1
1
|
import click
|
|
2
2
|
|
|
3
|
-
from adam.commands.
|
|
3
|
+
from adam.commands.audit.audit import Audit, AuditCommandHelper
|
|
4
|
+
from adam.commands.bash.bash import Bash
|
|
4
5
|
from adam.commands.check import Check, CheckCommandHelper
|
|
5
6
|
from adam.commands.cp import ClipboardCopy, CopyCommandHelper
|
|
6
7
|
from adam.commands.command import Command
|
|
7
8
|
from adam.commands.command_helpers import ClusterCommandHelper, ClusterOrPodCommandHelper, PodCommandHelper
|
|
8
|
-
from adam.commands.cqlsh import CqlCommandHelper, Cqlsh
|
|
9
|
-
from adam.commands.
|
|
10
|
-
from adam.commands.
|
|
9
|
+
from adam.commands.cql.cqlsh import CqlCommandHelper, Cqlsh
|
|
10
|
+
from adam.commands.deploy.deploy import Deploy, DeployCommandHelper
|
|
11
|
+
from adam.commands.deploy.undeploy import Undeploy, UndeployCommandHelper
|
|
11
12
|
from adam.commands.issues import Issues
|
|
12
13
|
from adam.commands.login import Login
|
|
13
14
|
from adam.commands.logs import Logs
|
|
@@ -22,13 +23,21 @@ from adam.commands.report import Report
|
|
|
22
23
|
from adam.commands.restart import Restart
|
|
23
24
|
from adam.commands.rollout import RollOut
|
|
24
25
|
from adam.commands.show.show import Show, ShowCommandHelper
|
|
25
|
-
from adam.commands.user_entry import UserEntry
|
|
26
26
|
from adam.commands.watch import Watch
|
|
27
|
-
from adam.
|
|
27
|
+
from adam.utils_k8s.kube_context import KubeContext
|
|
28
28
|
from adam.repl import enter_repl
|
|
29
29
|
from adam.repl_state import ReplState
|
|
30
30
|
from adam.cli_group import cli
|
|
31
31
|
|
|
32
|
+
@cli.command(context_settings=dict(ignore_unknown_options=True, allow_extra_args=True), cls=AuditCommandHelper, help='Run audit functions.')
|
|
33
|
+
@click.option('--kubeconfig', '-k', required=False, metavar='path', help='path to kubeconfig file')
|
|
34
|
+
@click.option('--config', default='params.yaml', metavar='path', help='path to kaqing parameters file')
|
|
35
|
+
@click.option('--param', '-v', multiple=True, metavar='<key>=<value>', help='parameter override')
|
|
36
|
+
@click.argument('extra_args', nargs=-1, metavar='repair', type=click.UNPROCESSED)
|
|
37
|
+
def audit(kubeconfig: str, config: str, param: list[str], extra_args):
|
|
38
|
+
run_command(Audit(), kubeconfig, config, param, None, None, None, extra_args)
|
|
39
|
+
|
|
40
|
+
|
|
32
41
|
@cli.command(context_settings=dict(ignore_unknown_options=True, allow_extra_args=True), cls=ClusterOrPodCommandHelper, help='Run a single bash command.')
|
|
33
42
|
@click.option('--kubeconfig', '-k', required=False, metavar='path', help='path to kubeconfig file')
|
|
34
43
|
@click.option('--config', default='params.yaml', metavar='path', help='path to kaqing parameters file')
|
|
@@ -77,6 +86,16 @@ def cql(kubeconfig: str, config: str, param: list[str], cluster: str, namespace:
|
|
|
77
86
|
run_command(Cqlsh(), kubeconfig, config, param, cluster, namespace, pod, extra_args)
|
|
78
87
|
|
|
79
88
|
|
|
89
|
+
@cli.command(context_settings=dict(ignore_unknown_options=True, allow_extra_args=True), cls=DeployCommandHelper, help='Setup.')
|
|
90
|
+
@click.option('--kubeconfig', '-k', required=False, metavar='path', help='path to kubeconfig file')
|
|
91
|
+
@click.option('--config', default='params.yaml', metavar='path', help='path to kaqing parameters file')
|
|
92
|
+
@click.option('--param', '-v', multiple=True, metavar='<key>=<value>', help='parameter override')
|
|
93
|
+
@click.option('--namespace', '-n', required=False, metavar='namespace', help='Kubernetes namespace')
|
|
94
|
+
@click.argument('extra_args', nargs=-1, metavar='<pod>', type=click.UNPROCESSED)
|
|
95
|
+
def deploy(kubeconfig: str, config: str, param: list[str], namespace: str, extra_args):
|
|
96
|
+
run_command(Deploy(), kubeconfig, config, param, None, namespace, None, extra_args)
|
|
97
|
+
|
|
98
|
+
|
|
80
99
|
@cli.command(context_settings=dict(ignore_unknown_options=True, allow_extra_args=True), cls=ClusterOrPodCommandHelper, help="Print Qing's issues.")
|
|
81
100
|
@click.option('--kubeconfig', '-k', required=False, metavar='path', help='path to kubeconfig file')
|
|
82
101
|
@click.option('--config', default='params.yaml', metavar='path', help='path to kaqing parameters file')
|
|
@@ -90,7 +109,7 @@ def issues(kubeconfig: str, config: str, param: list[str], cluster: str, namespa
|
|
|
90
109
|
run_command(Issues(), kubeconfig, config, param, cluster, namespace, pod, ('-s',) + extra_args if show else extra_args)
|
|
91
110
|
|
|
92
111
|
|
|
93
|
-
@cli.command(context_settings=dict(ignore_unknown_options=True, allow_extra_args=True), cls=PodCommandHelper, help='
|
|
112
|
+
@cli.command(context_settings=dict(ignore_unknown_options=True, allow_extra_args=True), cls=PodCommandHelper, help='SSO login.')
|
|
94
113
|
@click.option('--kubeconfig', '-k', required=False, metavar='path', help='path to kubeconfig file')
|
|
95
114
|
@click.option('--config', default='params.yaml', metavar='path', help='path to kaqing parameters file')
|
|
96
115
|
@click.option('--param', '-v', multiple=True, metavar='<key>=<value>', help='parameter override')
|
|
@@ -229,16 +248,6 @@ def rollout(kubeconfig: str, config: str, param: list[str], cluster: str, namesp
|
|
|
229
248
|
run_command(RollOut(), kubeconfig, config, param, cluster, namespace, None, extra_args)
|
|
230
249
|
|
|
231
250
|
|
|
232
|
-
@cli.command(context_settings=dict(ignore_unknown_options=True, allow_extra_args=True), cls=SetupCommandHelper, help='Setup.')
|
|
233
|
-
@click.option('--kubeconfig', '-k', required=False, metavar='path', help='path to kubeconfig file')
|
|
234
|
-
@click.option('--config', default='params.yaml', metavar='path', help='path to kaqing parameters file')
|
|
235
|
-
@click.option('--param', '-v', multiple=True, metavar='<key>=<value>', help='parameter override')
|
|
236
|
-
@click.option('--namespace', '-n', required=False, metavar='namespace', help='Kubernetes namespace')
|
|
237
|
-
@click.argument('extra_args', nargs=-1, metavar='<pod>', type=click.UNPROCESSED)
|
|
238
|
-
def setup(kubeconfig: str, config: str, param: list[str], namespace: str, extra_args):
|
|
239
|
-
run_command(Setup(), kubeconfig, config, param, None, namespace, None, extra_args)
|
|
240
|
-
|
|
241
|
-
|
|
242
251
|
@cli.command(context_settings=dict(ignore_unknown_options=True, allow_extra_args=True), cls=ShowCommandHelper, help='Show configuration or kubectl commands.')
|
|
243
252
|
@click.option('--kubeconfig', '-k', required=False, metavar='path', help='path to kubeconfig file')
|
|
244
253
|
@click.option('--config', default='params.yaml', metavar='path', help='path to kaqing parameters file')
|
|
@@ -251,24 +260,14 @@ def show(kubeconfig: str, config: str, param: list[str], cluster: str, namespace
|
|
|
251
260
|
run_command(Show(), kubeconfig, config, param, cluster, namespace, pod, extra_args)
|
|
252
261
|
|
|
253
262
|
|
|
254
|
-
@cli.command(context_settings=dict(ignore_unknown_options=True, allow_extra_args=True), cls=
|
|
255
|
-
@click.option('--kubeconfig', '-k', required=False, metavar='path', help='path to kubeconfig file')
|
|
256
|
-
@click.option('--config', default='params.yaml', metavar='path', help='path to kaqing parameters file')
|
|
257
|
-
@click.option('--param', '-v', multiple=True, metavar='<key>=<value>', help='parameter override')
|
|
258
|
-
@click.option('--namespace', '-n', required=False, metavar='namespace', help='Kubernetes namespace')
|
|
259
|
-
@click.argument('extra_args', nargs=-1, metavar='<pod>', type=click.UNPROCESSED)
|
|
260
|
-
def teardown(kubeconfig: str, config: str, param: list[str], namespace: str, extra_args):
|
|
261
|
-
run_command(TearDown(), kubeconfig, config, param, None, namespace, None, extra_args)
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
@cli.command(context_settings=dict(ignore_unknown_options=True, allow_extra_args=True), cls=PodCommandHelper, help='Get cassandra log.')
|
|
263
|
+
@cli.command(context_settings=dict(ignore_unknown_options=True, allow_extra_args=True), cls=UndeployCommandHelper, help='Undeploy.')
|
|
265
264
|
@click.option('--kubeconfig', '-k', required=False, metavar='path', help='path to kubeconfig file')
|
|
266
265
|
@click.option('--config', default='params.yaml', metavar='path', help='path to kaqing parameters file')
|
|
267
266
|
@click.option('--param', '-v', multiple=True, metavar='<key>=<value>', help='parameter override')
|
|
268
267
|
@click.option('--namespace', '-n', required=False, metavar='namespace', help='Kubernetes namespace')
|
|
269
268
|
@click.argument('extra_args', nargs=-1, metavar='<pod>', type=click.UNPROCESSED)
|
|
270
|
-
def
|
|
271
|
-
run_command(
|
|
269
|
+
def undeploy(kubeconfig: str, config: str, param: list[str], namespace: str, extra_args):
|
|
270
|
+
run_command(Undeploy(), kubeconfig, config, param, None, namespace, None, extra_args)
|
|
272
271
|
|
|
273
272
|
|
|
274
273
|
@cli.command(context_settings=dict(ignore_unknown_options=True, allow_extra_args=True), cls=ClusterOrPodCommandHelper, help='Watch pods in cluster.')
|
|
@@ -283,7 +282,7 @@ def watch(kubeconfig: str, config: str, param: list[str], cluster: str, namespac
|
|
|
283
282
|
|
|
284
283
|
|
|
285
284
|
def run_command(cmd: Command, kubeconfig: str, config: str, params: list[str], cluster:str, namespace: str, pod: str, extra_args):
|
|
286
|
-
is_user_entry =
|
|
285
|
+
is_user_entry = False
|
|
287
286
|
|
|
288
287
|
KubeContext.init_config(kubeconfig, is_user_entry=is_user_entry)
|
|
289
288
|
if not KubeContext.init_params(config, params, is_user_entry=is_user_entry):
|
adam/checks/check_utils.py
CHANGED
|
@@ -13,10 +13,10 @@ from adam.checks.issue import Issue
|
|
|
13
13
|
from adam.checks.memory import Memory
|
|
14
14
|
from adam.checks.status import Status
|
|
15
15
|
from adam.config import Config
|
|
16
|
-
from adam.
|
|
17
|
-
from adam.
|
|
18
|
-
from adam.
|
|
19
|
-
from adam.
|
|
16
|
+
from adam.utils_k8s.cassandra_nodes import CassandraNodes
|
|
17
|
+
from adam.utils_k8s.kube_context import KubeContext
|
|
18
|
+
from adam.utils_k8s.secrets import Secrets
|
|
19
|
+
from adam.utils_k8s.statefulsets import StatefulSets
|
|
20
20
|
from adam.utils import elapsed_time, log2
|
|
21
21
|
|
|
22
22
|
def all_checks() -> list[Check]:
|
adam/checks/compactionstats.py
CHANGED
|
@@ -5,7 +5,7 @@ from adam.checks.check_context import CheckContext
|
|
|
5
5
|
from adam.checks.check_result import CheckResult
|
|
6
6
|
from adam.checks.issue import Issue
|
|
7
7
|
from adam.config import Config
|
|
8
|
-
from adam.
|
|
8
|
+
from adam.utils_k8s.cassandra_nodes import CassandraNodes
|
|
9
9
|
|
|
10
10
|
class CompactionStats(Check):
|
|
11
11
|
def name(self):
|
adam/checks/cpu.py
CHANGED
|
@@ -5,8 +5,8 @@ from adam.checks.check_context import CheckContext
|
|
|
5
5
|
from adam.checks.check_result import CheckResult
|
|
6
6
|
from adam.checks.issue import Issue
|
|
7
7
|
from adam.config import Config
|
|
8
|
-
from adam.
|
|
9
|
-
from adam.
|
|
8
|
+
from adam.utils_k8s.cassandra_nodes import CassandraNodes
|
|
9
|
+
from adam.utils_k8s.custom_resources import CustomResources
|
|
10
10
|
|
|
11
11
|
class Cpu(Check):
|
|
12
12
|
def name(self):
|
adam/checks/disk.py
CHANGED
|
@@ -6,7 +6,7 @@ from adam.checks.check_context import CheckContext
|
|
|
6
6
|
from adam.checks.check_result import CheckResult
|
|
7
7
|
from adam.checks.issue import Issue
|
|
8
8
|
from adam.config import Config
|
|
9
|
-
from adam.
|
|
9
|
+
from adam.utils_k8s.cassandra_nodes import CassandraNodes
|
|
10
10
|
|
|
11
11
|
class Disk(Check):
|
|
12
12
|
def name(self):
|
adam/checks/gossip.py
CHANGED
|
@@ -4,7 +4,7 @@ from adam.checks.check import Check
|
|
|
4
4
|
from adam.checks.check_context import CheckContext
|
|
5
5
|
from adam.checks.check_result import CheckResult
|
|
6
6
|
from adam.checks.issue import Issue
|
|
7
|
-
from adam.
|
|
7
|
+
from adam.utils_k8s.cassandra_nodes import CassandraNodes
|
|
8
8
|
|
|
9
9
|
class Gossip(Check):
|
|
10
10
|
def name(self):
|
adam/checks/memory.py
CHANGED
|
@@ -2,9 +2,9 @@ from adam.checks.check import Check
|
|
|
2
2
|
from adam.checks.check_context import CheckContext
|
|
3
3
|
from adam.checks.check_result import CheckResult
|
|
4
4
|
from adam.checks.issue import Issue
|
|
5
|
-
from adam.
|
|
6
|
-
from adam.
|
|
7
|
-
from adam.
|
|
5
|
+
from adam.utils_k8s.cassandra_nodes import CassandraNodes
|
|
6
|
+
from adam.utils_k8s.custom_resources import CustomResources
|
|
7
|
+
from adam.utils_k8s.pods import Pods
|
|
8
8
|
|
|
9
9
|
class Memory(Check):
|
|
10
10
|
def name(self):
|
adam/checks/status.py
CHANGED
|
@@ -4,7 +4,7 @@ from adam.checks.check import Check
|
|
|
4
4
|
from adam.checks.check_context import CheckContext
|
|
5
5
|
from adam.checks.check_result import CheckResult
|
|
6
6
|
from adam.checks.issue import Issue
|
|
7
|
-
from adam.
|
|
7
|
+
from adam.utils_k8s.cassandra_nodes import CassandraNodes
|
|
8
8
|
|
|
9
9
|
class Status(Check):
|
|
10
10
|
def name(self):
|
|
@@ -0,0 +1,81 @@
|
|
|
1
|
+
from adam.commands.command import Command
|
|
2
|
+
from adam.commands.cql.cql_utils import cassandra_tables as get_tables, run_cql
|
|
3
|
+
from adam.config import Config
|
|
4
|
+
from adam.repl_state import ReplState, RequiredState
|
|
5
|
+
from adam.utils import log2
|
|
6
|
+
|
|
7
|
+
class AlterTables(Command):
|
|
8
|
+
COMMAND = 'alter tables with'
|
|
9
|
+
|
|
10
|
+
# the singleton pattern
|
|
11
|
+
def __new__(cls, *args, **kwargs):
|
|
12
|
+
if not hasattr(cls, 'instance'): cls.instance = super(AlterTables, cls).__new__(cls)
|
|
13
|
+
|
|
14
|
+
return cls.instance
|
|
15
|
+
|
|
16
|
+
def __init__(self, successor: Command=None):
|
|
17
|
+
super().__init__(successor)
|
|
18
|
+
|
|
19
|
+
def required(self):
|
|
20
|
+
return RequiredState.CLUSTER
|
|
21
|
+
|
|
22
|
+
def command(self):
|
|
23
|
+
return AlterTables.COMMAND
|
|
24
|
+
|
|
25
|
+
def run(self, cmd: str, state: ReplState):
|
|
26
|
+
if not(args := self.args(cmd)):
|
|
27
|
+
return super().run(cmd, state)
|
|
28
|
+
|
|
29
|
+
state, args = self.apply_state(args, state)
|
|
30
|
+
if not self.validate_state(state):
|
|
31
|
+
return state
|
|
32
|
+
|
|
33
|
+
if not args:
|
|
34
|
+
if state.in_repl:
|
|
35
|
+
log2('Please enter gc grace in seconds. e.g. alter gc-grace-seconds 3600')
|
|
36
|
+
else:
|
|
37
|
+
log2('* gc grace second is missing.')
|
|
38
|
+
log2()
|
|
39
|
+
Command.display_help()
|
|
40
|
+
|
|
41
|
+
return 'missing-arg'
|
|
42
|
+
|
|
43
|
+
args, include_reaper = Command.extract_options(args, '--include-reaper')
|
|
44
|
+
arg_str = ' '.join(args)
|
|
45
|
+
|
|
46
|
+
excludes = [e.strip(' \r\n') for e in Config().get(
|
|
47
|
+
'cql.alter-tables.excludes',
|
|
48
|
+
'system_auth,system_traces,reaper_db,system_distributed,system_views,system,system_schema,system_virtual_schema').split(',')]
|
|
49
|
+
batching = Config().get('cql.alter-tables.batching', True)
|
|
50
|
+
tables = get_tables(state, on_any=True)
|
|
51
|
+
for k, v in tables.items():
|
|
52
|
+
if k not in excludes or k == 'reaper_db' and include_reaper:
|
|
53
|
+
if batching:
|
|
54
|
+
# alter table <table_name> with GC_GRACE_SECONDS = <timeout>;
|
|
55
|
+
cql = ';\n'.join([f'alter table {k}.{t} with {arg_str}' for t in v])
|
|
56
|
+
try:
|
|
57
|
+
run_cql(state, cql, [], show_out=Config().is_debug(), on_any=True)
|
|
58
|
+
except Exception as e:
|
|
59
|
+
log2(e)
|
|
60
|
+
continue
|
|
61
|
+
else:
|
|
62
|
+
for t in v:
|
|
63
|
+
try:
|
|
64
|
+
# alter table <table_name> with GC_GRACE_SECONDS = <timeout>;
|
|
65
|
+
cql = f'alter table {k}.{t} with {arg_str}'
|
|
66
|
+
run_cql(state, cql, [], show_out=Config().is_debug(), on_any=True)
|
|
67
|
+
except Exception as e:
|
|
68
|
+
log2(e)
|
|
69
|
+
continue
|
|
70
|
+
|
|
71
|
+
log2(f'{len(v)} tables altered in {k}.')
|
|
72
|
+
|
|
73
|
+
# do not continue to cql route
|
|
74
|
+
return state
|
|
75
|
+
|
|
76
|
+
def completion(self, _: ReplState) -> dict[str, any]:
|
|
77
|
+
# auto completion is taken care of by sql completer
|
|
78
|
+
return {}
|
|
79
|
+
|
|
80
|
+
def help(self, _: ReplState) -> str:
|
|
81
|
+
return f'{AlterTables.COMMAND} <param = value> [--include-reaper] \t alter schema on all tables'
|
adam/commands/app.py
CHANGED
|
@@ -22,14 +22,14 @@ class App(Command):
|
|
|
22
22
|
return App.COMMAND
|
|
23
23
|
|
|
24
24
|
def required(self):
|
|
25
|
-
return RequiredState.
|
|
25
|
+
return RequiredState.APP_APP
|
|
26
26
|
|
|
27
27
|
def run(self, cmd: str, state: ReplState):
|
|
28
28
|
if not(args := self.args(cmd)):
|
|
29
29
|
return super().run(cmd, state)
|
|
30
30
|
|
|
31
31
|
state, args = self.apply_state(args, state)
|
|
32
|
-
if not self.validate_state(state
|
|
32
|
+
if not self.validate_state(state):
|
|
33
33
|
return state
|
|
34
34
|
|
|
35
35
|
args, forced = Command.extract_options(args, '--force')
|
|
@@ -64,4 +64,4 @@ class App(Command):
|
|
|
64
64
|
return {}
|
|
65
65
|
|
|
66
66
|
def help(self, _: ReplState):
|
|
67
|
-
return f"
|
|
67
|
+
return f"<AppType>.<AppAction> <args> [--force]\t post app action; check with 'show app actions' command"
|
adam/commands/app_ping.py
CHANGED
|
@@ -18,14 +18,14 @@ class AppPing(Command):
|
|
|
18
18
|
return AppPing.COMMAND
|
|
19
19
|
|
|
20
20
|
def required(self):
|
|
21
|
-
return RequiredState.
|
|
21
|
+
return RequiredState.APP_APP
|
|
22
22
|
|
|
23
23
|
def run(self, cmd: str, state: ReplState):
|
|
24
24
|
if not(args := self.args(cmd)):
|
|
25
25
|
return super().run(cmd, state)
|
|
26
26
|
|
|
27
27
|
state, args = self.apply_state(args, state)
|
|
28
|
-
if not self.validate_state(state
|
|
28
|
+
if not self.validate_state(state):
|
|
29
29
|
return state
|
|
30
30
|
|
|
31
31
|
_, forced = Command.extract_options(args, '--force')
|
|
@@ -0,0 +1,86 @@
|
|
|
1
|
+
import click
|
|
2
|
+
|
|
3
|
+
from adam.commands.audit.audit_repair_tables import AuditRepairTables
|
|
4
|
+
from adam.commands.audit.audit_run import AuditRun
|
|
5
|
+
from adam.commands.audit.show_last10 import ShowLast10
|
|
6
|
+
from adam.commands.audit.show_slow10 import ShowSlow10
|
|
7
|
+
from adam.commands.audit.show_top10 import ShowTop10
|
|
8
|
+
from adam.commands.audit.utils_show_top10 import show_top10_completions_for_nesting
|
|
9
|
+
from adam.commands.command import Command
|
|
10
|
+
from adam.config import Config
|
|
11
|
+
from adam.repl_state import ReplState
|
|
12
|
+
from adam.sql.sql_completer import SqlCompleter, SqlVariant
|
|
13
|
+
from adam.utils import log2
|
|
14
|
+
from adam.utils_athena import Athena
|
|
15
|
+
from adam.utils_audits import Audits
|
|
16
|
+
|
|
17
|
+
class Audit(Command):
|
|
18
|
+
COMMAND = 'audit'
|
|
19
|
+
|
|
20
|
+
# the singleton pattern
|
|
21
|
+
def __new__(cls, *args, **kwargs):
|
|
22
|
+
if not hasattr(cls, 'instance'): cls.instance = super(Audit, cls).__new__(cls)
|
|
23
|
+
|
|
24
|
+
return cls.instance
|
|
25
|
+
|
|
26
|
+
def __init__(self, successor: Command=None):
|
|
27
|
+
super().__init__(successor)
|
|
28
|
+
self.schema_read = False
|
|
29
|
+
|
|
30
|
+
def command(self):
|
|
31
|
+
return Audit.COMMAND
|
|
32
|
+
|
|
33
|
+
def required(self):
|
|
34
|
+
return ReplState.L
|
|
35
|
+
|
|
36
|
+
def run(self, cmd: str, state: ReplState):
|
|
37
|
+
if not(args := self.args(cmd)):
|
|
38
|
+
return super().run(cmd, state)
|
|
39
|
+
|
|
40
|
+
state, args = self.apply_state(args, state)
|
|
41
|
+
if not self.validate_state(state):
|
|
42
|
+
return state
|
|
43
|
+
|
|
44
|
+
r = None
|
|
45
|
+
if len(args) > 0:
|
|
46
|
+
r = super().intermediate_run(cmd, state, args, Audit.cmd_list(), display_help=False)
|
|
47
|
+
|
|
48
|
+
if not r or isinstance(r, str) and r == 'command-missing':
|
|
49
|
+
sql = 'select * from audit order by ts desc limit 10'
|
|
50
|
+
if args:
|
|
51
|
+
sql = ' '.join(args)
|
|
52
|
+
else:
|
|
53
|
+
log2(sql)
|
|
54
|
+
|
|
55
|
+
Athena.run_query(sql)
|
|
56
|
+
|
|
57
|
+
return state
|
|
58
|
+
|
|
59
|
+
def completion(self, state: ReplState):
|
|
60
|
+
if state.device == ReplState.L:
|
|
61
|
+
if not self.schema_read:
|
|
62
|
+
Config().wait_log(f'Inspecting audit database schema...')
|
|
63
|
+
self.schema_read = True
|
|
64
|
+
# warm up the caches first time when l: drive is accessed
|
|
65
|
+
Athena.table_names()
|
|
66
|
+
Athena.column_names()
|
|
67
|
+
Athena.column_names(partition_cols_only=True)
|
|
68
|
+
|
|
69
|
+
return super().completion(state) | show_top10_completions_for_nesting() | SqlCompleter(
|
|
70
|
+
lambda: Athena.table_names(),
|
|
71
|
+
columns=lambda table: Athena.column_names(),
|
|
72
|
+
partition_columns=lambda table: Athena.column_names(partition_cols_only=True),
|
|
73
|
+
variant=SqlVariant.ATHENA
|
|
74
|
+
).completions_for_nesting()
|
|
75
|
+
|
|
76
|
+
return {}
|
|
77
|
+
|
|
78
|
+
def cmd_list():
|
|
79
|
+
return [AuditRepairTables(), AuditRun(), ShowLast10(), ShowSlow10(), ShowTop10()]
|
|
80
|
+
|
|
81
|
+
def help(self, _: ReplState):
|
|
82
|
+
return f'[{Audit.COMMAND}] [<sql-statements>]\t run SQL queries on Authena audit database'
|
|
83
|
+
|
|
84
|
+
class AuditCommandHelper(click.Command):
|
|
85
|
+
def get_help(self, ctx: click.Context):
|
|
86
|
+
Command.intermediate_help(super().get_help(ctx), Audit.COMMAND, Audit.cmd_list(), show_cluster_help=False)
|
|
@@ -0,0 +1,77 @@
|
|
|
1
|
+
import concurrent
|
|
2
|
+
import time
|
|
3
|
+
|
|
4
|
+
from adam.commands.command import Command
|
|
5
|
+
from adam.config import Config
|
|
6
|
+
from adam.repl_state import ReplState
|
|
7
|
+
from adam.utils import log, log2
|
|
8
|
+
from adam.utils_athena import Athena
|
|
9
|
+
from adam.utils_audits import AuditMeta, Audits
|
|
10
|
+
|
|
11
|
+
class AuditRepairTables(Command):
|
|
12
|
+
COMMAND = 'audit repair'
|
|
13
|
+
|
|
14
|
+
# the singleton pattern
|
|
15
|
+
def __new__(cls, *args, **kwargs):
|
|
16
|
+
if not hasattr(cls, 'instance'): cls.instance = super(AuditRepairTables, cls).__new__(cls)
|
|
17
|
+
|
|
18
|
+
return cls.instance
|
|
19
|
+
|
|
20
|
+
def __init__(self, successor: Command=None):
|
|
21
|
+
super().__init__(successor)
|
|
22
|
+
self.auto_repaired = False
|
|
23
|
+
|
|
24
|
+
def command(self):
|
|
25
|
+
return AuditRepairTables.COMMAND
|
|
26
|
+
|
|
27
|
+
def required(self):
|
|
28
|
+
return ReplState.L
|
|
29
|
+
|
|
30
|
+
def run(self, cmd: str, state: ReplState):
|
|
31
|
+
if not(args := self.args(cmd)):
|
|
32
|
+
return super().run(cmd, state)
|
|
33
|
+
|
|
34
|
+
state, args = self.apply_state(args, state)
|
|
35
|
+
if not self.validate_state(state):
|
|
36
|
+
return state
|
|
37
|
+
|
|
38
|
+
tables = Config().get('audit.athena.repair-partition-tables', 'audit').split(',')
|
|
39
|
+
if args:
|
|
40
|
+
tables = args
|
|
41
|
+
|
|
42
|
+
meta = Audits.get_meta()
|
|
43
|
+
self.repair(tables, meta)
|
|
44
|
+
|
|
45
|
+
return state
|
|
46
|
+
|
|
47
|
+
def completion(self, state: ReplState):
|
|
48
|
+
if state.device == ReplState.L:
|
|
49
|
+
if not self.auto_repaired:
|
|
50
|
+
if hours := Config().get('audit.athena.auto-repair.elapsed_hours', 12):
|
|
51
|
+
with concurrent.futures.ThreadPoolExecutor(max_workers=Config().get('audit.workers', 3)) as executor:
|
|
52
|
+
executor.submit(self.auto_repair, hours,)
|
|
53
|
+
|
|
54
|
+
return super().completion(state)
|
|
55
|
+
|
|
56
|
+
return {}
|
|
57
|
+
|
|
58
|
+
def auto_repair(self, hours: int):
|
|
59
|
+
self.auto_repaired = True
|
|
60
|
+
|
|
61
|
+
meta: AuditMeta = Audits.get_meta()
|
|
62
|
+
if meta.partitions_last_checked + hours * 60 * 60 < time.time():
|
|
63
|
+
tables = Config().get('audit.athena.repair-partition-tables', 'audit').split(',')
|
|
64
|
+
self.repair(tables, meta, show_sql=True)
|
|
65
|
+
log2(f'Audit tables have been auto-repaired.')
|
|
66
|
+
|
|
67
|
+
def repair(self, tables: list[str], meta: AuditMeta, show_sql = False):
|
|
68
|
+
with concurrent.futures.ThreadPoolExecutor(max_workers=Config().get('audit.workers', 3)) as executor:
|
|
69
|
+
for table in tables:
|
|
70
|
+
if show_sql:
|
|
71
|
+
log(f'MSCK REPAIR TABLE {table}')
|
|
72
|
+
|
|
73
|
+
executor.submit(Athena.run_query, f'MSCK REPAIR TABLE {table}', None,)
|
|
74
|
+
executor.submit(Audits.put_meta, Audits.PARTITIONS_ADDED, meta,)
|
|
75
|
+
|
|
76
|
+
def help(self, _: ReplState):
|
|
77
|
+
return f"{AuditRepairTables.COMMAND} \t run MSCK REPAIR command for new partition discovery"
|
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
import concurrent
|
|
2
|
+
|
|
3
|
+
from adam.commands.command import Command
|
|
4
|
+
from adam.config import Config
|
|
5
|
+
from adam.repl_state import ReplState
|
|
6
|
+
from adam.utils import log2
|
|
7
|
+
from adam.utils_athena import Athena
|
|
8
|
+
from adam.utils_audits import AuditMeta, Audits
|
|
9
|
+
|
|
10
|
+
class AuditRun(Command):
|
|
11
|
+
COMMAND = 'audit run'
|
|
12
|
+
|
|
13
|
+
# the singleton pattern
|
|
14
|
+
def __new__(cls, *args, **kwargs):
|
|
15
|
+
if not hasattr(cls, 'instance'): cls.instance = super(AuditRun, cls).__new__(cls)
|
|
16
|
+
|
|
17
|
+
return cls.instance
|
|
18
|
+
|
|
19
|
+
def __init__(self, successor: Command=None):
|
|
20
|
+
super().__init__(successor)
|
|
21
|
+
self.auto_repaired = False
|
|
22
|
+
|
|
23
|
+
def command(self):
|
|
24
|
+
return AuditRun.COMMAND
|
|
25
|
+
|
|
26
|
+
def required(self):
|
|
27
|
+
return ReplState.L
|
|
28
|
+
|
|
29
|
+
def run(self, cmd: str, state: ReplState):
|
|
30
|
+
if not(args := self.args(cmd)):
|
|
31
|
+
return super().run(cmd, state)
|
|
32
|
+
|
|
33
|
+
state, args = self.apply_state(args, state)
|
|
34
|
+
if not self.validate_state(state):
|
|
35
|
+
return state
|
|
36
|
+
|
|
37
|
+
meta: AuditMeta = Audits.get_meta()
|
|
38
|
+
clusters = Audits.find_new_clusters(meta.cluster_last_checked)
|
|
39
|
+
Audits.put_meta(Audits.ADD_CLUSTERS, meta, clusters=clusters)
|
|
40
|
+
if clusters:
|
|
41
|
+
log2(f'Added {len(clusters)} new clusters.')
|
|
42
|
+
tables = Config().get('audit.athena.repair-cluster-tables', 'cluster').split(',')
|
|
43
|
+
with concurrent.futures.ThreadPoolExecutor(max_workers=Config().get('audit.workers', 3)) as executor:
|
|
44
|
+
for table in tables:
|
|
45
|
+
executor.submit(Athena.run_query, f'MSCK REPAIR TABLE {table}', None,)
|
|
46
|
+
else:
|
|
47
|
+
log2(f'No new clusters were found.')
|
|
48
|
+
|
|
49
|
+
return state
|
|
50
|
+
|
|
51
|
+
def completion(self, state: ReplState):
|
|
52
|
+
if state.device == ReplState.L:
|
|
53
|
+
return super().completion(state)
|
|
54
|
+
|
|
55
|
+
return {}
|
|
56
|
+
|
|
57
|
+
def help(self, _: ReplState):
|
|
58
|
+
return f"{AuditRun.COMMAND} \t run"
|
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
from adam.commands.audit.utils_show_top10 import extract_limit_and_duration
|
|
2
|
+
from adam.commands.command import Command
|
|
3
|
+
from adam.repl_state import ReplState
|
|
4
|
+
from adam.utils import log2
|
|
5
|
+
from adam.utils_athena import Athena
|
|
6
|
+
from adam.utils_audits import Audits
|
|
7
|
+
|
|
8
|
+
class ShowLast10(Command):
|
|
9
|
+
COMMAND = 'show last'
|
|
10
|
+
|
|
11
|
+
# the singleton pattern
|
|
12
|
+
def __new__(cls, *args, **kwargs):
|
|
13
|
+
if not hasattr(cls, 'instance'): cls.instance = super(ShowLast10, cls).__new__(cls)
|
|
14
|
+
|
|
15
|
+
return cls.instance
|
|
16
|
+
|
|
17
|
+
def __init__(self, successor: Command=None):
|
|
18
|
+
super().__init__(successor)
|
|
19
|
+
|
|
20
|
+
def command(self):
|
|
21
|
+
return ShowLast10.COMMAND
|
|
22
|
+
|
|
23
|
+
def required(self):
|
|
24
|
+
return ReplState.L
|
|
25
|
+
|
|
26
|
+
def run(self, cmd: str, state: ReplState):
|
|
27
|
+
if not(args := self.args(cmd)):
|
|
28
|
+
return super().run(cmd, state)
|
|
29
|
+
|
|
30
|
+
state, args = self.apply_state(args, state)
|
|
31
|
+
if not self.validate_state(state):
|
|
32
|
+
return state
|
|
33
|
+
|
|
34
|
+
limit, date_condition = extract_limit_and_duration(args)
|
|
35
|
+
|
|
36
|
+
query = '\n '.join([
|
|
37
|
+
"SELECT * FROM audit",
|
|
38
|
+
f"WHERE drive <> 'z' and ({date_condition})",
|
|
39
|
+
f"ORDER BY ts DESC LIMIT {limit};"])
|
|
40
|
+
log2(query)
|
|
41
|
+
log2()
|
|
42
|
+
Athena.run_query(query)
|
|
43
|
+
|
|
44
|
+
return state
|
|
45
|
+
|
|
46
|
+
def completion(self, _: ReplState):
|
|
47
|
+
|
|
48
|
+
return {}
|
|
49
|
+
|
|
50
|
+
def help(self, _: ReplState):
|
|
51
|
+
return f'{ShowLast10.COMMAND} [limit]\t show last <limit> audit lines'
|