diff --git a/tools/test/test_depsolve.py b/tools/test/test_depsolve.py index 0a611cdf..c9024e52 100644 --- a/tools/test/test_depsolve.py +++ b/tools/test/test_depsolve.py @@ -1143,6 +1143,52 @@ dump_test_cases = [ ] +search_test_case_basic_2pkgs_2repos = { + "id": "basic_2pkgs_2repos", + "enabled_repos": ["baseos", "custom"], + "search_args": { + "latest": True, + "packages": [ + "zsh", + "pkg-with-no-deps", + ], + }, + "results": [ + { + "name": "zsh", + "summary": "Powerful interactive shell", + "description": """The zsh shell is a command interpreter usable as an interactive login +shell and as a shell script command processor. Zsh resembles the ksh +shell (the Korn shell), but includes many enhancements. Zsh supports +command line editing, built-in spelling correction, programmable +command completion, shell functions (with autoloading), a history +mechanism, and more.""", + "url": "http://zsh.sourceforge.net/", + "repo_id": "baseos", + "epoch": 0, + "version": "5.8", + "release": "9.el9", + "arch": "x86_64", + "buildtime": "2022-02-23T13:47:24Z", + "license": "MIT", + }, + { + 'arch': 'noarch', + 'buildtime': '2024-04-15T18:09:19Z', + 'description': 'Provides pkg-with-no-deps', + 'epoch': 0, + 'license': 'BSD', + 'name': 'pkg-with-no-deps', + 'release': '0', + 'repo_id': 'custom', + 'summary': 'Provides pkg-with-no-deps', + 'url': None, + 'version': '1.0.0', + }, + ], +} + + search_test_cases = [ { "id": "1pkg_latest", @@ -1242,7 +1288,7 @@ mechanism, and more.""", "error_kind": "RepoError", "error_reason_re": r"There was a problem reading a repository: Failed to download metadata.*['\"]broken['\"].*", }, -] +] + [search_test_case_basic_2pkgs_2repos] def make_dnf_scafolding(base_dir): @@ -1593,20 +1639,23 @@ def test_dump(tmp_path, repo_servers, dnf_config, detect_fn, test_case): assert n_filelist_files == 0 -@pytest.mark.parametrize("test_case", search_test_cases, ids=tcase_idfn) @pytest.mark.parametrize("dnf_config, detect_fn", [ (None, assert_dnf), ({"use_dnf5": False}, assert_dnf), ({"use_dnf5": True}, assert_dnf5), ], ids=["no-config", "dnf4", "dnf5"]) -def test_search(tmp_path, repo_servers, dnf_config, detect_fn, test_case): +def test_search_config_combos(tmp_path, repo_servers, dnf_config, detect_fn): + """ + Test all possible configurations of repository configurations for the search function. + Test on a single test case which searches for two packages from two repositories. + """ try: detect_fn() except RuntimeError as e: pytest.skip(str(e)) + test_case = search_test_case_basic_2pkgs_2repos tc_repo_servers = get_test_case_repo_servers(test_case, repo_servers) - search_args = test_case["search_args"] for repo_configs, root_dir, opt_metadata in config_combos(tmp_path, tc_repo_servers): @@ -1620,7 +1669,16 @@ def test_search(tmp_path, repo_servers, dnf_config, detect_fn, test_case): continue assert exit_code == 0 - assert res == test_case["results"] + for res, exp in zip(res, test_case["results"]): + # if the url in the package is empty, DNF4 returns None, DNF5 returns an empty string + exp = exp.copy() + exp_url = exp.pop("url") + res_url = res.pop("url") + if exp_url is None and dnf_config and dnf_config.get("use_dnf5", False): + assert res_url == "" + else: + assert res_url == exp_url + assert res == exp # if opt_metadata includes 'filelists', then each repository 'repodata' must include a file that matches # *filelists* @@ -1631,6 +1689,44 @@ def test_search(tmp_path, repo_servers, dnf_config, detect_fn, test_case): assert n_filelist_files == 0 +@pytest.mark.parametrize("test_case", search_test_cases, ids=tcase_idfn) +@pytest.mark.parametrize("dnf_config, detect_fn", [ + (None, assert_dnf), + ({"use_dnf5": False}, assert_dnf), + ({"use_dnf5": True}, assert_dnf5), +], ids=["no-config", "dnf4", "dnf5"]) +def test_search(repo_servers, dnf_config, detect_fn, test_case): + try: + detect_fn() + except RuntimeError as e: + pytest.skip(str(e)) + + tc_repo_servers = get_test_case_repo_servers(test_case, repo_servers) + repo_configs = [gen_repo_config(server) for server in tc_repo_servers] + search_args = test_case["search_args"] + + with TemporaryDirectory() as cache_dir: + res, exit_code = search(search_args, cache_dir, dnf_config, repo_configs) + + if test_case.get("error", False): + assert exit_code != 0 + assert res["kind"] == test_case["error_kind"] + assert re.match(test_case["error_reason_re"], res["reason"], re.DOTALL) + return + + assert exit_code == 0 + for res, exp in zip(res, test_case["results"]): + # if the url in the package is empty, DNF4 returns None, DNF5 returns an empty string + exp = exp.copy() + exp_url = exp.pop("url") + res_url = res.pop("url") + if exp_url is None and dnf_config and dnf_config.get("use_dnf5", False): + assert res_url == "" + else: + assert res_url == exp_url + assert res == exp + + def test_depsolve_result_api(tmp_path, repo_servers): """ Test the result of depsolve() API.