forked from TrueCloudLab/frostfs-testlib
[#137] Ability to control remote processes id and reports for load
Signed-off-by: Andrey Berezin <a.berezin@yadro.com>
This commit is contained in:
parent
e65fc359fe
commit
81dfc723da
5 changed files with 159 additions and 63 deletions
|
@ -1,4 +1,5 @@
|
|||
import copy
|
||||
from datetime import datetime
|
||||
from typing import Optional
|
||||
|
||||
import frostfs_testlib.resources.optionals as optionals
|
||||
|
@ -10,6 +11,7 @@ from frostfs_testlib.load.load_verifiers import LoadVerifier
|
|||
from frostfs_testlib.storage.cluster import ClusterNode
|
||||
from frostfs_testlib.storage.dataclasses.frostfs_services import S3Gate, StorageNode
|
||||
from frostfs_testlib.storage.dataclasses.wallet import WalletInfo
|
||||
from frostfs_testlib.testing.parallel import parallel
|
||||
from frostfs_testlib.testing.test_control import run_optionally
|
||||
|
||||
|
||||
|
@ -26,6 +28,7 @@ class BackgroundLoadController:
|
|||
endpoints: list[str]
|
||||
runner: ScenarioRunner
|
||||
started: bool
|
||||
load_reporters: list[LoadReport]
|
||||
|
||||
def __init__(
|
||||
self,
|
||||
|
@ -45,6 +48,7 @@ class BackgroundLoadController:
|
|||
self.loaders_wallet = loaders_wallet
|
||||
self.runner = runner
|
||||
self.started = False
|
||||
self.load_reporters = []
|
||||
if load_params.endpoint_selection_strategy is None:
|
||||
raise RuntimeError("endpoint_selection_strategy should not be None")
|
||||
|
||||
|
@ -83,12 +87,20 @@ class BackgroundLoadController:
|
|||
|
||||
return all_endpoints[load_type][endpoint_selection_strategy]
|
||||
|
||||
@run_optionally(optionals.OPTIONAL_BACKGROUND_LOAD_ENABLED)
|
||||
@reporter.step("Init k6 instances")
|
||||
def init_k6(self):
|
||||
self.endpoints = self._get_endpoints(self.load_params.load_type, self.load_params.endpoint_selection_strategy)
|
||||
self.runner.init_k6_instances(self.load_params, self.endpoints, self.k6_dir)
|
||||
|
||||
@run_optionally(optionals.OPTIONAL_BACKGROUND_LOAD_ENABLED)
|
||||
@reporter.step("Prepare load instances")
|
||||
def prepare(self):
|
||||
self.endpoints = self._get_endpoints(self.load_params.load_type, self.load_params.endpoint_selection_strategy)
|
||||
self.runner.prepare(self.load_params, self.cluster_nodes, self.nodes_under_load, self.k6_dir)
|
||||
self.runner.init_k6_instances(self.load_params, self.endpoints, self.k6_dir)
|
||||
self.init_k6()
|
||||
|
||||
def append_reporter(self, load_report: LoadReport):
|
||||
self.load_reporters.append(load_report)
|
||||
|
||||
@run_optionally(optionals.OPTIONAL_BACKGROUND_LOAD_ENABLED)
|
||||
def start(self):
|
||||
|
@ -128,16 +140,30 @@ class BackgroundLoadController:
|
|||
|
||||
@run_optionally(optionals.OPTIONAL_BACKGROUND_LOAD_ENABLED)
|
||||
@reporter.step("Stop and get results of load")
|
||||
def teardown(self, load_report: Optional[LoadReport] = None):
|
||||
def teardown(self):
|
||||
if not self.started:
|
||||
return
|
||||
|
||||
self.stop()
|
||||
self.load_summaries = self._get_results()
|
||||
self.started = False
|
||||
if load_report:
|
||||
|
||||
start_time = min(self._get_start_times())
|
||||
end_time = max(self._get_end_times())
|
||||
|
||||
for load_report in self.load_reporters:
|
||||
load_report.set_start_time(start_time)
|
||||
load_report.set_end_time(end_time)
|
||||
load_report.add_summaries(self.load_summaries)
|
||||
|
||||
def _get_start_times(self) -> list[datetime]:
|
||||
futures = parallel([k6.get_start_time for k6 in self.runner.get_k6_instances()])
|
||||
return [future.result() for future in futures]
|
||||
|
||||
def _get_end_times(self) -> list[datetime]:
|
||||
futures = parallel([k6.get_end_time for k6 in self.runner.get_k6_instances()])
|
||||
return [future.result() for future in futures]
|
||||
|
||||
@run_optionally(optionals.OPTIONAL_BACKGROUND_LOAD_ENABLED)
|
||||
@reporter.step("Run post-load verification")
|
||||
def verify(self):
|
||||
|
|
|
@ -540,8 +540,9 @@ class ClusterStateController:
|
|||
options = CommandOptions(check=False)
|
||||
return self.shell.exec(f"ping {node.host.config.address} -c 1", options).return_code
|
||||
|
||||
@retry(max_attempts=60, sleep_interval=5, expected_result=HostStatus.ONLINE)
|
||||
@reporter.step("Waiting for {node} to go online")
|
||||
@retry(
|
||||
max_attempts=60, sleep_interval=10, expected_result=HostStatus.ONLINE, title="Waiting for {node} to go online"
|
||||
)
|
||||
def _wait_for_host_online(self, node: ClusterNode):
|
||||
try:
|
||||
ping_result = self._ping_host(node)
|
||||
|
@ -552,8 +553,9 @@ class ClusterStateController:
|
|||
logger.warning(f"Host ping fails with error {err}")
|
||||
return HostStatus.OFFLINE
|
||||
|
||||
@retry(max_attempts=60, sleep_interval=5, expected_result=HostStatus.OFFLINE)
|
||||
@reporter.step("Waiting for {node} to go offline")
|
||||
@retry(
|
||||
max_attempts=60, sleep_interval=10, expected_result=HostStatus.OFFLINE, title="Waiting for {node} to go offline"
|
||||
)
|
||||
def _wait_for_host_offline(self, node: ClusterNode):
|
||||
try:
|
||||
ping_result = self._ping_host(node)
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue