mirror of
https://github.com/miurahr/aqtinstall.git
synced 2025-12-17 04:34:37 +03:00
Add support for commercial versions of Qt (#878)
* Add install-qt-commercial feature and tests * Make the auto-answers parameters, fix linter issues * Fork and execv instead of using subprocess * Return to simpler process execution method version * Fix test * Move commercial installer into its own file * Fix shadowing of symbol platform causing errors * Adapt test_cli for argparse format changes on py 3.13+ * Fix some errors, monkeypatch install test * Add --override super command * Properly handle --override and grab all the remaining commands when no quotes are given * Fix tests * Add base for modules, some niche features are not yet entirely implemented, and there are no updates to the testsuite * Fix some mistakes * Fix errors made with the monkeypatch, update Settings to make sure its init * Tests commercial (#20) * Full support of installation of all modules and addons * Add auto setup of cache folder for each OS, add unattended parameter * Fix settings folders * Add graceful error message for overwrite case * Fix windows issue * Hidden summon works * Remove both subprocess direct calls * Dipose of temp folder * Fix path issue * Add list-qt-commercial command * Fix help info * Make no params valid for list-qt-commercial * Fix lint errors, and param overflow when no args are passed to list * Fix search * Add tests for coverage, fix lint * Test for overwriting, and for cache usage coverage * Return to clean exec, ignoring CI fail to preserve code clarity * Fix parsing of subprocess.run output for some python versions * Make output more readable in console for list-qt-commercial * Forward email and password to list request for users without a qtaccount.ini * Change default settings * Fix lint errors * Fix check error
This commit is contained in:
committed by
GitHub
parent
7917b2d725
commit
cbe159f38a
@@ -1,3 +1,4 @@
|
||||
import platform
|
||||
import re
|
||||
import sys
|
||||
from pathlib import Path
|
||||
@@ -15,8 +16,9 @@ from aqt.metadata import MetadataFactory, SimpleSpec, Version
|
||||
def expected_help(actual, prefix=None):
|
||||
expected = (
|
||||
"usage: aqt [-h] [-c CONFIG]\n"
|
||||
" {install-qt,install-tool,install-doc,install-example,install-src,"
|
||||
"list-qt,list-tool,list-doc,list-example,list-src,help,version}\n"
|
||||
" {install-qt,install-tool,install-qt-commercial,install-doc,install-example,"
|
||||
"install-src,"
|
||||
"list-qt,list-qt-commercial,list-tool,list-doc,list-example,list-src,help,version}\n"
|
||||
" ...\n"
|
||||
"\n"
|
||||
"Another unofficial Qt Installer.\n"
|
||||
@@ -32,7 +34,8 @@ def expected_help(actual, prefix=None):
|
||||
" install-* subcommands are commands that install components\n"
|
||||
" list-* subcommands are commands that show available components\n"
|
||||
"\n"
|
||||
" {install-qt,install-tool,install-doc,install-example,install-src,list-qt,"
|
||||
" {install-qt,install-tool,install-qt-commercial,install-doc,install-example,"
|
||||
"install-src,list-qt,list-qt-commercial,"
|
||||
"list-tool,list-doc,list-example,list-src,help,version}\n"
|
||||
" Please refer to each help message by using '--help' "
|
||||
"with each subcommand\n",
|
||||
@@ -520,3 +523,29 @@ def test_get_autodesktop_dir_and_arch_non_android(
|
||||
), "Expected autodesktop install message."
|
||||
elif expect["instruct"]:
|
||||
assert any("You can install" in line for line in err_lines), "Expected install instruction message."
|
||||
|
||||
|
||||
@pytest.mark.parametrize(
|
||||
"cmd, expected_arch, expected_err",
|
||||
[
|
||||
pytest.param(
|
||||
"install-qt-commercial desktop {} 6.8.0",
|
||||
{"windows": "win64_msvc2022_64", "linux": "linux_gcc_64", "mac": "clang_64"},
|
||||
"No Qt account credentials found. Either provide --user and --password or",
|
||||
),
|
||||
],
|
||||
)
|
||||
def test_cli_login_qt_commercial(capsys, monkeypatch, cmd, expected_arch, expected_err):
|
||||
"""Test commercial Qt installation command"""
|
||||
# Detect current platform
|
||||
current_platform = platform.system().lower()
|
||||
arch = expected_arch[current_platform]
|
||||
cmd = cmd.format(arch)
|
||||
|
||||
cli = Cli()
|
||||
cli._setup_settings()
|
||||
result = cli.run(cmd.split())
|
||||
|
||||
_, err = capsys.readouterr()
|
||||
assert str(err).find(expected_err)
|
||||
assert not result == 0
|
||||
|
||||
@@ -1676,30 +1676,30 @@ def test_install_qt6_wasm_autodesktop(monkeypatch, capsys, version, str_version,
|
||||
|
||||
assert result == 0
|
||||
|
||||
# Check output format
|
||||
out, err = capsys.readouterr()
|
||||
sys.stdout.write(out)
|
||||
sys.stderr.write(err)
|
||||
# Check output format
|
||||
out, err = capsys.readouterr()
|
||||
sys.stdout.write(out)
|
||||
sys.stderr.write(err)
|
||||
|
||||
# Use regex that works for all platforms
|
||||
expected_pattern = re.compile(
|
||||
r"^INFO : aqtinstall\(aqt\) v.*? on Python 3.*?\n"
|
||||
r"INFO : You are installing the Qt6-WASM version of Qt\n"
|
||||
r"(?:INFO : Found extension .*?\n)*"
|
||||
r"(?:INFO : Downloading (?:qt[^\n]*|icu[^\n]*)\n"
|
||||
r"Finished installation of .*?\.7z in \d+\.\d+\n)*"
|
||||
r"(?:INFO : Patching (?:/tmp/[^/]+|[A-Za-z]:[\\/].*?)/6\.8\.0/wasm_singlethread/bin/(?:qmake|qtpaths)(?:6)?\n)*"
|
||||
r"INFO : \n"
|
||||
r"INFO : Autodesktop will now install linux desktop 6\.8\.0 linux_gcc_64 as required by Qt6-WASM\n"
|
||||
r"INFO : aqtinstall\(aqt\) v.*? on Python 3.*?\n"
|
||||
r"(?:INFO : Found extension .*?\n)*"
|
||||
r"(?:INFO : Downloading (?:qt[^\n]*|icu[^\n]*)\n"
|
||||
r"Finished installation of .*?\.7z in \d+\.\d+\n)*"
|
||||
r"INFO : Finished installation\n"
|
||||
r"INFO : Time elapsed: \d+\.\d+ second\n$"
|
||||
)
|
||||
# Use regex that works for all platforms
|
||||
expected_pattern = re.compile(
|
||||
r"^INFO : aqtinstall\(aqt\) v.*? on Python 3.*?\n"
|
||||
r"INFO : You are installing the Qt6-WASM version of Qt\n"
|
||||
r"(?:INFO : Found extension .*?\n)*"
|
||||
r"(?:INFO : Downloading (?:qt[^\n]*|icu[^\n]*)\n"
|
||||
r"Finished installation of .*?\.7z in \d+\.\d+\n)*"
|
||||
r"(?:INFO : Patching (?:/tmp/[^/]+|[A-Za-z]:[\\/].*?)/6\.8\.0/wasm_singlethread/bin/(?:qmake|qtpaths)(?:6)?\n)*"
|
||||
r"INFO : \n"
|
||||
r"INFO : Autodesktop will now install linux desktop 6\.8\.0 linux_gcc_64 as required by Qt6-WASM\n"
|
||||
r"INFO : aqtinstall\(aqt\) v.*? on Python 3.*?\n"
|
||||
r"(?:INFO : Found extension .*?\n)*"
|
||||
r"(?:INFO : Downloading (?:qt[^\n]*|icu[^\n]*)\n"
|
||||
r"Finished installation of .*?\.7z in \d+\.\d+\n)*"
|
||||
r"INFO : Finished installation\n"
|
||||
r"INFO : Time elapsed: \d+\.\d+ second\n$"
|
||||
)
|
||||
|
||||
assert expected_pattern.match(err)
|
||||
assert expected_pattern.match(err)
|
||||
|
||||
|
||||
@pytest.mark.parametrize(
|
||||
@@ -2054,3 +2054,104 @@ def test_installer_passes_base_to_metadatafactory(
|
||||
sys.stderr.write(err)
|
||||
|
||||
assert expect_out.match(err), err
|
||||
|
||||
|
||||
class CompletedProcess:
|
||||
def __init__(self, args, returncode):
|
||||
self.args = args
|
||||
self.returncode = returncode
|
||||
self.stdout = None
|
||||
self.stderr = None
|
||||
|
||||
|
||||
@pytest.mark.enable_socket
|
||||
@pytest.mark.parametrize(
|
||||
"cmd, arch_dict, details, expected_command",
|
||||
[
|
||||
(
|
||||
"install-qt-commercial desktop {} 6.8.0 " "--outputdir ./install-qt-commercial " "--user {} --password {}",
|
||||
{"windows": "win64_msvc2022_64", "linux": "linux_gcc_64", "mac": "clang_64"},
|
||||
["./install-qt-commercial", "qt6", "680"],
|
||||
"qt-unified-{}-x64-online.run --email ******** --pw ******** --root {} "
|
||||
"--accept-licenses --accept-obligations "
|
||||
"--confirm-command "
|
||||
"--auto-answer OperationDoesNotExistError=Ignore,OverwriteTargetDirectory=No,"
|
||||
"stopProcessesForUpdates=Cancel,installationErrorWithCancel=Cancel,installationErrorWithIgnore=Ignore,"
|
||||
"AssociateCommonFiletypes=Yes,telemetry-question=No install qt.{}.{}.{}",
|
||||
),
|
||||
(
|
||||
"install-qt-commercial desktop {} 6.8.1 " "--outputdir ./install-qt-commercial " "--user {} --password {}",
|
||||
{"windows": "win64_msvc2022_64", "linux": "linux_gcc_64", "mac": "clang_64"},
|
||||
["./install-qt-commercial", "qt6", "681"],
|
||||
"qt-unified-{}-x64-online.run --email ******** --pw ******** --root {} "
|
||||
"--accept-licenses --accept-obligations "
|
||||
"--confirm-command "
|
||||
"--auto-answer OperationDoesNotExistError=Ignore,OverwriteTargetDirectory=Yes,"
|
||||
"stopProcessesForUpdates=Cancel,installationErrorWithCancel=Cancel,installationErrorWithIgnore=Ignore,"
|
||||
"AssociateCommonFiletypes=Yes,telemetry-question=No install qt.{}.{}.{}",
|
||||
),
|
||||
],
|
||||
)
|
||||
def test_install_qt_commercial(
|
||||
capsys, monkeypatch, cmd: str, arch_dict: dict[str, str], details: list[str], expected_command: str
|
||||
) -> None:
|
||||
"""Test commercial Qt installation command"""
|
||||
|
||||
# Mock subprocess.run instead of run_static_subprocess_dynamically
|
||||
def mock_subprocess_run(*args, **kwargs):
|
||||
# This will be called instead of the real subprocess.run
|
||||
return CompletedProcess(args=args[0], returncode=0)
|
||||
|
||||
# Patch subprocess.run directly
|
||||
monkeypatch.setattr("subprocess.run", mock_subprocess_run)
|
||||
|
||||
current_platform = sys.platform.lower()
|
||||
arch = arch_dict[current_platform]
|
||||
|
||||
abs_out = Path(details[0]).absolute()
|
||||
|
||||
formatted_cmd = cmd.format(arch, "vofab76634@gholar.com", "WxK43TdWCTmxsrrpnsWbjPfPXVq3mtLK")
|
||||
formatted_expected = expected_command.format(current_platform, abs_out, *details[1:], arch)
|
||||
|
||||
cli = Cli()
|
||||
cli._setup_settings()
|
||||
|
||||
try:
|
||||
cli.run(formatted_cmd.split())
|
||||
except AttributeError:
|
||||
out = " ".join(capsys.readouterr())
|
||||
assert str(out).find(formatted_expected) >= 0
|
||||
|
||||
def modify_qt_config(content):
|
||||
"""
|
||||
Takes content of INI file as string and returns modified content
|
||||
"""
|
||||
lines = content.splitlines()
|
||||
in_qt_commercial = False
|
||||
modified = []
|
||||
|
||||
for line in lines:
|
||||
# Check if we're entering qtcommercial section
|
||||
if line.strip() == "[qtcommercial]":
|
||||
in_qt_commercial = True
|
||||
|
||||
# If in qtcommercial section, look for the target line
|
||||
if in_qt_commercial and "overwrite_target_directory : No" in line:
|
||||
line = "overwrite_target_directory : Yes"
|
||||
elif in_qt_commercial and "overwrite_target_directory : Yes" in line:
|
||||
line = "overwrite_target_directory : No"
|
||||
|
||||
modified.append(line)
|
||||
|
||||
return "\n".join(modified)
|
||||
|
||||
script_dir = os.path.dirname(os.path.abspath(__file__))
|
||||
config_path = os.path.join(script_dir, "../aqt/settings.ini")
|
||||
|
||||
with open(config_path, "r") as f:
|
||||
content = f.read()
|
||||
|
||||
modified_content = modify_qt_config(content)
|
||||
|
||||
with open(config_path, "w") as f:
|
||||
f.write(modified_content)
|
||||
|
||||
@@ -1269,3 +1269,19 @@ def test_find_installed_qt_mingw_dir(expected_result: str, installed_files: List
|
||||
|
||||
actual_result = QtRepoProperty.find_installed_desktop_qt_dir(host, base_path, Version(qt_ver))
|
||||
assert (actual_result.name if actual_result else None) == expected_result
|
||||
|
||||
|
||||
# Test error cases
|
||||
@pytest.mark.parametrize(
|
||||
"args, expected_error",
|
||||
[
|
||||
(["list-qt-commercial", "--bad-flag"], "usage: aqt [-h] [-c CONFIG]"),
|
||||
],
|
||||
)
|
||||
def test_list_qt_commercial_errors(capsys, args, expected_error):
|
||||
"""Test error handling in list-qt-commercial command"""
|
||||
cli = Cli()
|
||||
with pytest.raises(SystemExit):
|
||||
cli.run(args)
|
||||
_, err = capsys.readouterr()
|
||||
assert expected_error in err
|
||||
|
||||
Reference in New Issue
Block a user