|
4 | 4 |
|
5 | 5 | import json |
6 | 6 | import logging |
7 | | -import re |
8 | 7 | import subprocess |
9 | 8 | from pathlib import Path |
10 | 9 | from typing import Dict, Optional |
|
14 | 13 | from pytest_operator.plugin import OpsTest |
15 | 14 | from tenacity import RetryError, Retrying, retry, stop_after_attempt, wait_fixed |
16 | 15 |
|
| 16 | +from literals import ADMIN_SERVER_PORT |
| 17 | + |
17 | 18 | logger = logging.getLogger(__name__) |
18 | 19 |
|
19 | 20 | METADATA = yaml.safe_load(Path("./metadata.yaml").read_text()) |
@@ -50,28 +51,26 @@ async def wait_idle(ops_test, apps: list[str] = [APP_NAME], units: int = 3) -> N |
50 | 51 | stop=stop_after_attempt(60), |
51 | 52 | reraise=True, |
52 | 53 | ) |
53 | | -def srvr(host: str) -> dict: |
54 | | - """Calls srvr 4lw command to specified host. |
| 54 | +def srvr(model_full_name: str, unit: str) -> dict: |
| 55 | + """Calls srvr 4lw command to specified unit. |
55 | 56 |
|
56 | 57 | Args: |
57 | | - host: ZooKeeper address and port to issue srvr 4lw command to |
| 58 | + model_full_name: Current test model |
| 59 | + unit: ZooKeeper unit to issue srvr 4lw command to |
58 | 60 |
|
59 | 61 | Returns: |
60 | 62 | Dict of srvr command output key/values |
61 | 63 | """ |
62 | 64 | response = subprocess.check_output( |
63 | | - f"echo srvr | nc {host} 2181", stderr=subprocess.PIPE, shell=True, universal_newlines=True |
| 65 | + f"JUJU_MODEL={model_full_name} juju ssh {unit} sudo -i 'curl localhost:{ADMIN_SERVER_PORT}/commands/srvr -m 10'", |
| 66 | + stderr=subprocess.PIPE, |
| 67 | + shell=True, |
| 68 | + universal_newlines=True, |
64 | 69 | ) |
65 | 70 |
|
66 | 71 | assert response, "ZooKeeper not running" |
67 | 72 |
|
68 | | - result = {} |
69 | | - for item in response.splitlines(): |
70 | | - k = re.split(": ", item)[0] |
71 | | - v = re.split(": ", item)[1] |
72 | | - result[k] = v |
73 | | - |
74 | | - return result |
| 73 | + return json.loads(response) |
75 | 74 |
|
76 | 75 |
|
77 | 76 | def get_hosts_from_status( |
@@ -176,13 +175,17 @@ def get_leader_name(ops_test: OpsTest, hosts: str, app_name: str = APP_NAME) -> |
176 | 175 | String of unit name of the ZooKeeper quorum leader |
177 | 176 | """ |
178 | 177 | for host in hosts.split(","): |
| 178 | + unit_name = get_unit_name_from_host(ops_test, host, app_name) |
179 | 179 | try: |
180 | | - mode = srvr(host.split(":")[0])["Mode"] |
| 180 | + mode = ( |
| 181 | + srvr(ops_test.model_full_name, unit_name) |
| 182 | + .get("server_stats", {}) |
| 183 | + .get("server_state", "") |
| 184 | + ) |
181 | 185 | except subprocess.CalledProcessError: # unit is down |
182 | 186 | continue |
183 | 187 | if mode == "leader": |
184 | | - leader_name = get_unit_name_from_host(ops_test, host, app_name) |
185 | | - return leader_name |
| 188 | + return unit_name |
186 | 189 |
|
187 | 190 | return "" |
188 | 191 |
|
@@ -481,8 +484,12 @@ def ping_servers(ops_test: OpsTest) -> bool: |
481 | 484 | True if all units are in quorum. Otherwise False |
482 | 485 | """ |
483 | 486 | for unit in ops_test.model.applications[APP_NAME].units: |
484 | | - host = unit.public_address |
485 | | - mode = srvr(host)["Mode"] |
| 487 | + srvr_response = srvr(ops_test.model_full_name, unit.name) |
| 488 | + |
| 489 | + if srvr_response.get("error", None): |
| 490 | + return False |
| 491 | + |
| 492 | + mode = srvr_response.get("server_stats", {}).get("server_state", "") |
486 | 493 | if mode not in ["leader", "follower"]: |
487 | 494 | return False |
488 | 495 |
|
|
0 commit comments