From 8ab4a89c0fe9364f513bec73c38ac78c16bbe03d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ladislav=20Va=C5=A1ina?= Date: Tue, 26 Mar 2024 11:05:56 +0100 Subject: [PATCH] [6.15.z] Cherrypick of FixesForEndeavour (#14517) --- pytest_fixtures/core/contenthosts.py | 10 +++ pytest_plugins/fixture_markers.py | 1 + tests/foreman/ui/test_host.py | 37 --------- tests/foreman/ui/test_jobinvocation.py | 96 ++++++++++++++++-------- tests/foreman/ui/test_remoteexecution.py | 45 ++++++----- 5 files changed, 101 insertions(+), 88 deletions(-) diff --git a/pytest_fixtures/core/contenthosts.py b/pytest_fixtures/core/contenthosts.py index 485591ed7d9..72f39b50796 100644 --- a/pytest_fixtures/core/contenthosts.py +++ b/pytest_fixtures/core/contenthosts.py @@ -161,6 +161,16 @@ def rex_contenthost(request, module_org, target_sat, module_ak_with_cv): yield host +@pytest.fixture +def rex_contenthosts(request, module_org, target_sat, module_ak_with_cv): + request.param['no_containers'] = True + with Broker(**host_conf(request), host_class=ContentHost, _count=2) as hosts: + for host in hosts: + repo = settings.repos['SATCLIENT_REPO'][f'RHEL{host.os_version.major}'] + host.register(module_org, None, module_ak_with_cv.name, target_sat, repo=repo) + yield hosts + + @pytest.fixture def katello_host_tools_tracer_host(rex_contenthost, target_sat): """Install katello-host-tools-tracer, create custom diff --git a/pytest_plugins/fixture_markers.py b/pytest_plugins/fixture_markers.py index f1e87d3b7f7..69f2c6523ee 100644 --- a/pytest_plugins/fixture_markers.py +++ b/pytest_plugins/fixture_markers.py @@ -10,6 +10,7 @@ 'capsule_provisioning_rhel_content', 'module_sync_kickstart_content', 'rex_contenthost', + 'rex_contenthosts', ] diff --git a/tests/foreman/ui/test_host.py b/tests/foreman/ui/test_host.py index bb4f39655a9..7fec6db1f7d 100644 --- a/tests/foreman/ui/test_host.py +++ b/tests/foreman/ui/test_host.py @@ -1092,43 +1092,6 @@ def test_positive_read_details_page_from_new_ui(session, host_ui_options): assert values['overview']['details']['details']['comment'] == 'Host with fake data' -@pytest.mark.tier4 -@pytest.mark.rhel_ver_match('8') -def test_rex_new_ui(session, target_sat, rex_contenthost): - """Run remote execution using the new host details page - - :id: ee625595-4995-43b2-9e6d-633c9b33ff93 - - :steps: - 1. Navigate to Overview tab - 2. Schedule a job - 3. Wait for the job to finish - 4. Job is visible in Recent jobs card - - :expectedresults: Remote execution succeeded and the job is visible on Recent jobs card on - Overview tab - """ - hostname = rex_contenthost.hostname - job_args = { - 'job_category': 'Commands', - 'job_template': 'Run Command - Script Default', - 'template_content.command': 'ls', - } - with session: - session.location.select(loc_name=DEFAULT_LOC) - session.host_new.schedule_job(hostname, job_args) - task_result = target_sat.wait_for_tasks( - search_query=(f'Remote action: Run ls on {hostname}'), - search_rate=2, - max_tries=30, - ) - task_status = target_sat.api.ForemanTask(id=task_result[0].id).poll() - assert task_status['result'] == 'success' - recent_jobs = session.host_new.get_details(hostname, "overview.recent_jobs")['overview'] - assert recent_jobs['recent_jobs']['finished']['table'][0]['column0'] == "Run ls" - assert recent_jobs['recent_jobs']['finished']['table'][0]['column2'] == "succeeded" - - @pytest.mark.tier4 def test_positive_manage_table_columns( target_sat, test_name, ui_hosts_columns_user, current_sat_org, current_sat_location diff --git a/tests/foreman/ui/test_jobinvocation.py b/tests/foreman/ui/test_jobinvocation.py index d79d7ee3355..7c9f30bf2a9 100644 --- a/tests/foreman/ui/test_jobinvocation.py +++ b/tests/foreman/ui/test_jobinvocation.py @@ -17,19 +17,12 @@ from robottelo.utils.datafactory import gen_string -@pytest.fixture -def module_rhel_client_by_ip(module_org, smart_proxy_location, rhel7_contenthost, target_sat): - """Setup a broker rhel client to be used in remote execution by ip""" - rhel7_contenthost.configure_rex(satellite=target_sat, org=module_org) - target_sat.api_factory.update_vm_host_location( - rhel7_contenthost, location_id=smart_proxy_location.id - ) - return rhel7_contenthost - - -@pytest.mark.tier4 -def test_positive_run_default_job_template_by_ip( - session, module_org, smart_proxy_location, module_rhel_client_by_ip +@pytest.mark.rhel_ver_match('8') +def test_positive_run_default_job_template( + session, + target_sat, + rex_contenthost, + module_org, ): """Run a job template on a host connected by ip @@ -39,7 +32,7 @@ def test_positive_run_default_job_template_by_ip( :steps: - 1. Set remote_execution_connect_by_ip on host to true + 1. Get contenthost with rex enabled 2. Navigate to an individual host and click Run Job 3. Select the job and appropriate template 4. Run the job @@ -48,17 +41,19 @@ def test_positive_run_default_job_template_by_ip( :parametrized: yes """ - hostname = module_rhel_client_by_ip.hostname - with session: + + hostname = rex_contenthost.hostname + + with target_sat.ui_session() as session: session.organization.select(module_org.name) - session.location.select(smart_proxy_location.name) assert session.host.search(hostname)[0]['Name'] == hostname session.jobinvocation.run( { - 'job_category': 'Commands', - 'job_template': 'Run Command - Script Default', - 'search_query': f'name ^ {hostname}', - 'template_content.command': 'ls', + 'category_and_template.job_category': 'Commands', + 'category_and_template.job_template': 'Run Command - Script Default', + 'target_hosts_and_inputs.targetting_type': 'Hosts', + 'target_hosts_and_inputs.targets': hostname, + 'target_hosts_and_inputs.command': 'ls', } ) session.jobinvocation.wait_job_invocation_state(entity_name='Run ls', host_name=hostname) @@ -67,9 +62,47 @@ def test_positive_run_default_job_template_by_ip( @pytest.mark.tier4 -def test_positive_run_custom_job_template_by_ip( - session, module_org, smart_proxy_location, module_rhel_client_by_ip -): +@pytest.mark.rhel_ver_match('8') +def test_rex_through_host_details(session, target_sat, rex_contenthost, module_org): + """Run remote execution using the new host details page + + :id: ee625595-4995-43b2-9e6d-633c9b33ff93 + + :steps: + 1. Navigate to Overview tab + 2. Schedule a job + 3. Wait for the job to finish + 4. Job is visible in Recent jobs card + + :expectedresults: Remote execution succeeded and the job is visible on Recent jobs card on + Overview tab + """ + + hostname = rex_contenthost.hostname + + job_args = { + 'category_and_template.job_category': 'Commands', + 'category_and_template.job_template': 'Run Command - Script Default', + 'target_hosts_and_inputs.command': 'ls', + } + with target_sat.ui_session() as session: + session.organization.select(module_org.name) + session.host_new.schedule_job(hostname, job_args) + task_result = target_sat.wait_for_tasks( + search_query=(f'Remote action: Run ls on {hostname}'), + search_rate=2, + max_tries=30, + ) + task_status = target_sat.api.ForemanTask(id=task_result[0].id).poll() + assert task_status['result'] == 'success' + recent_jobs = session.host_new.get_details(hostname, "overview.recent_jobs")['overview'] + assert recent_jobs['recent_jobs']['finished']['table'][0]['column0'] == "Run ls" + assert recent_jobs['recent_jobs']['finished']['table'][0]['column2'] == "succeeded" + + +@pytest.mark.tier4 +@pytest.mark.rhel_ver_match('8') +def test_positive_run_custom_job_template(session, module_org, target_sat, rex_contenthost): """Run a job template on a host connected by ip :id: e283ae09-8b14-4ce1-9a76-c1bbd511d58c @@ -87,11 +120,12 @@ def test_positive_run_custom_job_template_by_ip( :parametrized: yes """ - hostname = module_rhel_client_by_ip.hostname + + hostname = rex_contenthost.hostname + job_template_name = gen_string('alpha') - with session: + with target_sat.ui_session() as session: session.organization.select(module_org.name) - session.location.select(smart_proxy_location.name) assert session.host.search(hostname)[0]['Name'] == hostname session.jobtemplate.create( { @@ -105,10 +139,10 @@ def test_positive_run_custom_job_template_by_ip( assert session.jobtemplate.search(job_template_name)[0]['Name'] == job_template_name session.jobinvocation.run( { - 'job_category': 'Miscellaneous', - 'job_template': job_template_name, - 'search_query': f'name ^ {hostname}', - 'template_content.command': 'ls', + 'category_and_template.job_category': 'Miscellaneous', + 'category_and_template.job_template': job_template_name, + 'target_hosts_and_inputs.targets': hostname, + 'target_hosts_and_inputs.command': 'ls', } ) job_description = f'{camelize(job_template_name.lower())} with inputs command="ls"' diff --git a/tests/foreman/ui/test_remoteexecution.py b/tests/foreman/ui/test_remoteexecution.py index cdfe9c7ec4e..04642763812 100644 --- a/tests/foreman/ui/test_remoteexecution.py +++ b/tests/foreman/ui/test_remoteexecution.py @@ -140,7 +140,7 @@ def test_positive_run_custom_job_template_by_ip( @pytest.mark.tier3 @pytest.mark.rhel_ver_list([8]) def test_positive_run_job_template_multiple_hosts_by_ip( - session, module_org, target_sat, registered_hosts + session, module_org, target_sat, rex_contenthosts ): """Run a job template against multiple hosts by ip @@ -158,22 +158,24 @@ def test_positive_run_job_template_multiple_hosts_by_ip( :expectedresults: Verify the job was successfully ran against the hosts """ + host_names = [] - for vm in registered_hosts: + for vm in rex_contenthosts: + # for vm in rex_contenthost: host_names.append(vm.hostname) vm.configure_rex(satellite=target_sat, org=module_org) - with session: + with target_sat.ui_session() as session: session.organization.select(module_org.name) - session.location.select('Default Location') - hosts = session.host.search(' or '.join([f'name="{hostname}"' for hostname in host_names])) - assert {host['Name'] for host in hosts} == set(host_names) + # session.location.select('Default Location') + for host in host_names: + assert session.host.search(host)[0]['Name'] == host + session.host.reset_search() job_status = session.host.schedule_remote_job( host_names, { 'category_and_template.job_category': 'Commands', 'category_and_template.job_template': 'Run Command - Script Default', - 'target_hosts_and_inputs.command': 'ls', - 'schedule.immediate': True, + 'target_hosts_and_inputs.command': 'sleep 5', }, ) assert job_status['overview']['job_status'] == 'Success' @@ -211,19 +213,20 @@ def test_positive_run_scheduled_job_template_by_ip(session, module_org, rex_cont :parametrized: yes """ - job_time = 10 * 60 + job_time = 6 * 60 hostname = rex_contenthost.hostname with session: session.organization.select(module_org.name) session.location.select('Default Location') assert session.host.search(hostname)[0]['Name'] == hostname plan_time = session.browser.get_client_datetime() + datetime.timedelta(seconds=job_time) + command_to_run = 'sleep 10' job_status = session.host.schedule_remote_job( [hostname], { 'category_and_template.job_category': 'Commands', 'category_and_template.job_template': 'Run Command - Script Default', - 'target_hosts_and_inputs.command': 'ls', + 'target_hosts_and_inputs.command': command_to_run, 'schedule.future': True, 'schedule_future_execution.start_at_date': plan_time.strftime("%Y/%m/%d"), 'schedule_future_execution.start_at_time': plan_time.strftime("%H:%M"), @@ -237,34 +240,36 @@ def test_positive_run_scheduled_job_template_by_ip(session, module_org, rex_cont # the job_time must be significantly greater than job creation time. assert job_left_time > 0 assert job_status['overview']['hosts_table'][0]['Host'] == hostname - assert job_status['overview']['hosts_table'][0]['Status'] == 'N/A' + assert job_status['overview']['hosts_table'][0]['Status'] in ('Awaiting start', 'N/A') # sleep 3/4 of the left time time.sleep(job_left_time * 3 / 4) - job_status = session.jobinvocation.read('Run ls', hostname, 'overview.hosts_table') + job_status = session.jobinvocation.read( + f'Run {command_to_run}', hostname, 'overview.hosts_table' + ) assert job_status['overview']['hosts_table'][0]['Host'] == hostname - assert job_status['overview']['hosts_table'][0]['Status'] == 'N/A' + assert job_status['overview']['hosts_table'][0]['Status'] in ('Awaiting start', 'N/A') # recalculate the job left time to be more accurate job_left_time = (plan_time - session.browser.get_client_datetime()).total_seconds() # the last read time should not take more than 1/4 of the last left time assert job_left_time > 0 wait_for( - lambda: session.jobinvocation.read('Run ls', hostname, 'overview.hosts_table')[ - 'overview' - ]['hosts_table'][0]['Status'] + lambda: session.jobinvocation.read( + f'Run {command_to_run}', hostname, 'overview.hosts_table' + )['overview']['hosts_table'][0]['Status'] == 'running', timeout=(job_left_time + 30), delay=1, ) # wait the job to change status to "success" wait_for( - lambda: session.jobinvocation.read('Run ls', hostname, 'overview.hosts_table')[ - 'overview' - ]['hosts_table'][0]['Status'] + lambda: session.jobinvocation.read( + f'Run {command_to_run}', hostname, 'overview.hosts_table' + )['overview']['hosts_table'][0]['Status'] == 'success', timeout=30, delay=1, ) - job_status = session.jobinvocation.read('Run ls', hostname, 'overview') + job_status = session.jobinvocation.read(f'Run {command_to_run}', hostname, 'overview') assert job_status['overview']['job_status'] == 'Success' assert job_status['overview']['hosts_table'][0]['Host'] == hostname assert job_status['overview']['hosts_table'][0]['Status'] == 'success'