diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml index 145fc5858c..58f42a995a 100644 --- a/.gitlab-ci.yml +++ b/.gitlab-ci.yml @@ -30,3 +30,4 @@ include: - '.gitlab/ci/integration_test.yml' - '.gitlab/ci/host-test.yml' - '.gitlab/ci/deploy.yml' + - '.gitlab/ci/test-win.yml' diff --git a/.gitlab/ci/build.yml b/.gitlab/ci/build.yml index c0105de3e0..b97925dbb3 100644 --- a/.gitlab/ci/build.yml +++ b/.gitlab/ci/build.yml @@ -213,37 +213,6 @@ pytest_build_system_macos: reports: junit: XUNIT_RESULT.xml -.test_build_system_template_win: - stage: host_test - variables: - # Enable ccache for all build jobs. See configure_ci_environment.sh for more ccache related settings. - IDF_CCACHE_ENABLE: "1" - PYTHONPATH: "$PYTHONPATH;$IDF_PATH\\tools;$IDF_PATH\\tools\\esp_app_trace;$IDF_PATH\\components\\partition_table;$IDF_PATH\\tools\\ci\\python_packages" - before_script: [] - after_script: [] - timeout: 4 hours - script: - - .\install.ps1 --enable-ci --enable-pytest - - . .\export.ps1 - - python "${SUBMODULE_FETCH_TOOL}" -s "all" - - cd ${IDF_PATH}\tools\test_build_system - - pytest --junitxml=${CI_PROJECT_DIR}\XUNIT_RESULT.xml - -pytest_build_system_win: - extends: - - .test_build_system_template_win - - .rules:labels:windows_pytest_build_system - needs: [] - tags: - - windows-target - artifacts: - paths: - - XUNIT_RESULT.xml - - test_build_system - expire_in: 2 days - reports: - junit: XUNIT_RESULT.xml - build_docker: extends: - .before_script:minimal diff --git a/.gitlab/ci/test-win.yml b/.gitlab/ci/test-win.yml new file mode 100644 index 0000000000..5c33b89c34 --- /dev/null +++ b/.gitlab/ci/test-win.yml @@ -0,0 +1,91 @@ +# Host tests +.host_test_win_template: + extends: .rules:test:host_test + stage: host_test + image: $ESP_ENV_IMAGE + tags: + - windows-target + dependencies: # set dependencies to null to avoid missing artifacts issue + # run host_test jobs immediately, only after upload cache + needs: + - job: upload-pip-cache + optional: true + artifacts: false + - job: upload-submodules-cache + optional: true + artifacts: false + before_script: [] + after_script: [] + +test_cli_installer_win: + extends: + - .host_test_win_template + - .rules:labels:windows_pytest_build_system + artifacts: + when: on_failure + paths: + - tools/tools.new.json + - tools/test_idf_tools/test_python_env_logs.txt + variables: + IDF_PATH: "$CI_PROJECT_DIR" + script: + # Tools must be downloaded for testing + - python ${IDF_PATH}\tools\idf_tools.py download required qemu-riscv32 qemu-xtensa + - cd ${IDF_PATH}\tools\test_idf_tools + - python -m pip install jsonschema + - python .\test_idf_tools.py + - python .\test_idf_tools_python_env.py + +test_tools_win: + extends: + - .host_test_win_template + - .rules:labels:windows_pytest_build_system + artifacts: + paths: + - ${IDF_PATH}/*.out + - ${IDF_PATH}/XUNIT_*.xml + reports: + junit: ${IDF_PATH}/XUNIT_*.xml + variables: + LC_ALL: C.UTF-8 + PYTHONPATH: "$PYTHONPATH;$IDF_PATH\\tools;$IDF_PATH\\tools\\esp_app_trace;$IDF_PATH\\components\\partition_table;$IDF_PATH\\tools\\ci\\python_packages" + script: + - python -m pip install jsonschema + - .\install.ps1 --enable-ci --enable-pytest + - .\export.ps1 + - python "${SUBMODULE_FETCH_TOOL}" -s "all" + - cd ${IDF_PATH}/tools/test_idf_py + - pytest --noconftest test_idf_py.py --junitxml=${IDF_PATH}/XUNIT_IDF_PY.xml + - pytest --noconftest test_hints.py --junitxml=${IDF_PATH}/XUNIT_HINTS.xml + +# Build tests +.test_build_system_template_win: + stage: host_test + variables: + # Enable ccache for all build jobs. See configure_ci_environment.sh for more ccache related settings. + IDF_CCACHE_ENABLE: "1" + PYTHONPATH: "$PYTHONPATH;$IDF_PATH\\tools;$IDF_PATH\\tools\\esp_app_trace;$IDF_PATH\\components\\partition_table;$IDF_PATH\\tools\\ci\\python_packages" + before_script: [] + after_script: [] + timeout: 4 hours + script: + - .\install.ps1 --enable-ci --enable-pytest + - . .\export.ps1 + - python "${SUBMODULE_FETCH_TOOL}" -s "all" + - cd ${IDF_PATH}\tools\test_build_system + - pytest --junitxml=${CI_PROJECT_DIR}\XUNIT_RESULT.xml + +pytest_build_system_win: + extends: + - .test_build_system_template_win + - .rules:labels:windows_pytest_build_system + needs: [] + tags: + - windows-target + artifacts: + paths: + - XUNIT_RESULT.xml + - test_build_system + expire_in: 2 days + reports: + junit: XUNIT_RESULT.xml diff --git a/tools/idf_tools.py b/tools/idf_tools.py index d32ed4a8cd..c08e5f3d13 100755 --- a/tools/idf_tools.py +++ b/tools/idf_tools.py @@ -2180,6 +2180,7 @@ def apply_mirror_prefix_map(args: Any, idf_download_url: str) -> str: warn('invalid mirror-prefix-map item (missing \'{}\') {}'.format(URL_PREFIX_MAP_SEPARATOR, item)) continue search, replace = item.split(URL_PREFIX_MAP_SEPARATOR, 1) + replace = replace.replace('\\', '\\\\') # On windows replace single \ with double \\ new_url = re.sub(search, replace, idf_download_url) if new_url != idf_download_url: info('Changed download URL: {} => {}'.format(idf_download_url, new_url)) diff --git a/tools/test_idf_py/test_idf_py.py b/tools/test_idf_py/test_idf_py.py index 678d93a09b..0a77a0ab97 100755 --- a/tools/test_idf_py/test_idf_py.py +++ b/tools/test_idf_py/test_idf_py.py @@ -1,13 +1,17 @@ #!/usr/bin/env python # -# SPDX-FileCopyrightText: 2019-2023 Espressif Systems (Shanghai) CO LTD +# SPDX-FileCopyrightText: 2019-2024 Espressif Systems (Shanghai) CO LTD # SPDX-License-Identifier: Apache-2.0 - import json import os +import shutil import subprocess import sys -from unittest import TestCase, main, mock +from typing import Any +from typing import List +from unittest import main +from unittest import mock +from unittest import TestCase import elftools.common.utils as ecu import jsonschema @@ -234,19 +238,31 @@ class TestDeprecations(TestWithoutExtensions): class TestHelpOutput(TestWithoutExtensions): - def test_output(self): - def action_test(commands, schema): - output_file = 'idf_py_help_output.json' - with open(output_file, 'w') as outfile: - subprocess.run(commands, env=os.environ, stdout=outfile) - with open(output_file, 'r') as outfile: - help_obj = json.load(outfile) - self.assertIsNone(jsonschema.validate(help_obj, schema)) + def action_test_idf_py(self, commands: List[str], schema: Any) -> None: + env = dict(**os.environ) + python = shutil.which('python', path=env['PATH']) + if python is None: + raise ValueError('python not found') + idf_path = env.get('IDF_PATH') + if idf_path is None: + raise ValueError('Empty IDF_PATH') + idf_py_cmd = [ + python, + os.path.join(idf_path, 'tools', 'idf.py') + ] + commands = idf_py_cmd + commands + output_file = 'idf_py_help_output.json' + with open(output_file, 'w') as outfile: + subprocess.run(commands, env=env, stdout=outfile) + with open(output_file, 'r') as outfile: + help_obj = json.load(outfile) + self.assertIsNone(jsonschema.validate(help_obj, schema)) + def test_output(self): with open(os.path.join(current_dir, 'idf_py_help_schema.json'), 'r') as schema_file: schema_json = json.load(schema_file) - action_test(['idf.py', 'help', '--json'], schema_json) - action_test(['idf.py', 'help', '--json', '--add-options'], schema_json) + self.action_test_idf_py(['help', '--json'], schema_json) + self.action_test_idf_py(['help', '--json', '--add-options'], schema_json) class TestROMs(TestWithoutExtensions): diff --git a/tools/test_idf_tools/test_idf_tools.py b/tools/test_idf_tools/test_idf_tools.py index df5b60458c..d1e405ea68 100755 --- a/tools/test_idf_tools/test_idf_tools.py +++ b/tools/test_idf_tools/test_idf_tools.py @@ -1,8 +1,7 @@ #!/usr/bin/env python # -# SPDX-FileCopyrightText: 2019-2023 Espressif Systems (Shanghai) CO LTD +# SPDX-FileCopyrightText: 2019-2024 Espressif Systems (Shanghai) CO LTD # SPDX-License-Identifier: Apache-2.0 - import json import os import re @@ -47,6 +46,12 @@ RISCV_ESP_GDB = 'riscv32-esp-elf-gdb' ESP_ROM_ELFS = 'esp-rom-elfs' QEMU_RISCV = 'qemu-riscv32' QEMU_XTENSA = 'qemu-xtensa' +# Win tools +CMAKE = 'cmake' +NINJA = 'ninja' +IDF_EXE = 'idf-exe' +CCACHE = 'ccache' +DFU_UTIL = 'dfu-util' def get_version_dict(): @@ -73,7 +78,12 @@ RISCV_ESP_GDB_VERSION = version_dict[RISCV_ESP_GDB] ESP_ROM_ELFS_VERSION = version_dict[ESP_ROM_ELFS] QEMU_RISCV_VERSION = version_dict[QEMU_RISCV] QEMU_XTENSA_VERSION = version_dict[QEMU_XTENSA] - +# Win tools +CMAKE_VERSION = version_dict[CMAKE] +NINJA_VERSION = version_dict[NINJA] +IDF_EXE_VERSION = version_dict[IDF_EXE] +CCACHE_VERSION = version_dict[CCACHE] +DFU_UTIL_VERSION = version_dict[DFU_UTIL] # There are some complex search patterns to detect download snippets @@ -87,6 +97,8 @@ XTENSA_ELF_ARCHIVE_PATTERN = XTENSA_ELF + '-' \ + (XTENSA_ELF_VERSION[len('esp-'):] if XTENSA_ELF_VERSION.startswith('esp-') else XTENSA_ELF_VERSION) +# TestUsage takes care of general test setup and executes tests that behaves the same on both platforms +# TestUsage class serves as a parent for classes TestUsageUnix and TestUsageWin class TestUsage(unittest.TestCase): @classmethod @@ -99,10 +111,10 @@ class TestUsage(unittest.TestCase): mirror_prefix_map = None if os.path.exists(old_tools_dir): - mirror_prefix_map = 'https://dl.espressif.com/dl/toolchains/preview,file://' + os.path.join(old_tools_dir, - 'dist') - mirror_prefix_map += ';https://dl.espressif.com/dl,file://' + os.path.join(old_tools_dir, 'dist') - mirror_prefix_map += ';https://github.com/espressif/.*/releases/download/.*/,file://' + os.path.join( + mirror_prefix_map = 'https://dl.espressif.com/dl/toolchains/preview,file:' + os.path.join(old_tools_dir, + 'dist') + mirror_prefix_map += ';https://dl.espressif.com/dl,file:' + os.path.join(old_tools_dir, 'dist') + mirror_prefix_map += ';https://github.com/espressif/.*/releases/download/.*/,file:' + os.path.join( old_tools_dir, 'dist', '') if mirror_prefix_map: print('Using IDF_MIRROR_PREFIX_MAP={}'.format(mirror_prefix_map)) @@ -132,13 +144,13 @@ class TestUsage(unittest.TestCase): if tool_archive_name is None: tool_archive_name = tool self.assertIn('Installing %s@' % tool + tool_version, output) - self.assertRegex(output, re.compile(rf'Downloading \S+/{tool_archive_name}')) + self.assertRegex(output, re.compile(rf'Downloading \S+{tool_archive_name}')) def assert_tool_not_installed(self, output, tool, tool_version, tool_archive_name=None): if tool_archive_name is None: tool_archive_name = tool self.assertNotIn('Installing %s@' % tool + tool_version, output) - self.assertNotRegex(output, re.compile(rf'Downloading \S+/{tool_archive_name}')) + self.assertNotRegex(output, re.compile(rf'Downloading \S+{tool_archive_name}')) def run_idf_tools_with_action(self, action): output_stream = StringIO() @@ -147,6 +159,129 @@ class TestUsage(unittest.TestCase): output = output_stream.getvalue() return output + def test_tools_for_wildcards1(self): + required_tools_installed = 2 + output = self.run_idf_tools_with_action(['install', '*gdb*']) + self.assert_tool_not_installed(output, OPENOCD, OPENOCD_VERSION) + self.assert_tool_not_installed(output, RISCV_ELF, RISCV_ELF_VERSION,RISCV_ELF_ARCHIVE_PATTERN) + self.assert_tool_installed(output, RISCV_ESP_GDB, RISCV_ESP_GDB_VERSION) + self.assert_tool_not_installed(output, XTENSA_ELF, XTENSA_ELF_VERSION, XTENSA_ELF_ARCHIVE_PATTERN) + self.assert_tool_not_installed(output, ESP32ULP, ESP32ULP_VERSION) + self.assert_tool_installed(output, XTENSA_ESP_GDB, XTENSA_ESP_GDB_VERSION) + self.assert_tool_not_installed(output, ESP_ROM_ELFS, ESP_ROM_ELFS_VERSION) + self.assertIn('Destination: {}'.format(os.path.join(self.temp_tools_dir, 'dist')), output) + self.assertEqual(required_tools_installed, output.count('Done')) + + def test_tools_for_wildcards2(self): + required_tools_installed = 1 + output = self.run_idf_tools_with_action(['install', '*gdb*', '--targets=esp32c3']) + self.assert_tool_not_installed(output, OPENOCD, OPENOCD_VERSION) + self.assert_tool_not_installed(output, RISCV_ELF, RISCV_ELF_VERSION, RISCV_ELF_ARCHIVE_PATTERN) + self.assert_tool_installed(output, RISCV_ESP_GDB, RISCV_ESP_GDB_VERSION) + self.assert_tool_not_installed(output, XTENSA_ELF, XTENSA_ELF_VERSION, XTENSA_ELF_ARCHIVE_PATTERN) + self.assert_tool_not_installed(output, ESP32ULP, ESP32ULP_VERSION) + self.assert_tool_not_installed(output, XTENSA_ESP_GDB, XTENSA_ESP_GDB_VERSION) + self.assert_tool_not_installed(output, ESP_ROM_ELFS, ESP_ROM_ELFS_VERSION) + self.assertIn('Destination: {}'.format(os.path.join(self.temp_tools_dir, 'dist')), output) + self.assertEqual(required_tools_installed, output.count('Done')) + + def test_tools_for_wildcards3(self): + required_tools_installed = 1 + output = self.run_idf_tools_with_action(['install', '*gdb*', '--targets=esp32s3']) + self.assert_tool_not_installed(output, OPENOCD, OPENOCD_VERSION) + self.assert_tool_not_installed(output, RISCV_ELF, RISCV_ELF_VERSION, RISCV_ELF_ARCHIVE_PATTERN) + self.assert_tool_not_installed(output, RISCV_ESP_GDB, RISCV_ESP_GDB_VERSION) + self.assert_tool_not_installed(output, XTENSA_ELF, XTENSA_ELF_VERSION, XTENSA_ELF_ARCHIVE_PATTERN) + self.assert_tool_not_installed(output, ESP32ULP, ESP32ULP_VERSION) + self.assert_tool_installed(output, XTENSA_ESP_GDB, XTENSA_ESP_GDB_VERSION) + self.assert_tool_not_installed(output, ESP_ROM_ELFS, ESP_ROM_ELFS_VERSION) + self.assertIn('Destination: {}'.format(os.path.join(self.temp_tools_dir, 'dist')), output) + self.assertEqual(required_tools_installed, output.count('Done')) + + def test_uninstall_option(self): + self.run_idf_tools_with_action(['install', '--targets=esp32']) + test_tool_name = XTENSA_ELF + test_tool_version = 'test_version' + tools_json_new = os.path.join(self.temp_tools_dir, 'tools', 'tools.new.json') + self.run_idf_tools_with_action( + [ + 'add-version', + '--tool', + test_tool_name, + '--url-prefix', + 'http://test.com', + '--version', + test_tool_version, + '--override', + '--checksum-file', + 'add_version/checksum.sha256', + '--output', + tools_json_new + ]) + output = self.run_idf_tools_with_action(['--tools-json', tools_json_new, 'uninstall', '--dry-run']) + self.assertIn('For removing old versions of ' + test_tool_name, output) + output = self.run_idf_tools_with_action(['--tools-json', tools_json_new, 'uninstall']) + self.assertIn(os.path.join(self.temp_tools_dir, 'tools', test_tool_name, XTENSA_ELF_VERSION) + ' was removed.', output) + output = self.run_idf_tools_with_action(['uninstall']) + self.assertEqual('', output) + + def test_deactivate(self): + self.run_idf_tools_with_action(['install']) + output = self.run_idf_tools_with_action(['export']) + self.assertIn('export IDF_DEACTIVATE_FILE_PATH=', output, 'No IDF_DEACTIVATE_FILE_PATH exported into environment') + deactivate_file = re.findall(r'(?:IDF_DEACTIVATE_FILE_PATH=")(.*)(?:")', output)[0] + self.assertTrue(os.path.isfile(deactivate_file), 'File {} was not found. '.format(deactivate_file)) + self.assertNotEqual(os.stat(self.idf_env_json).st_size, 0, 'File {} is empty. '.format(deactivate_file)) + + def test_export_recommended_version(self): + always_install_and_recommended_tools = [] + for tool in self.tools_dict['tools']: + if tool['install'] != 'always': + continue + for version in tool['versions']: + if version['status'] != 'recommended': + continue + always_install_and_recommended_tools.append({ + 'name': tool['name'], + 'version': version['name'] + }) + self.run_idf_tools_with_action(['install']) + output = self.run_idf_tools_with_action(['export']) + + for tool in always_install_and_recommended_tools: + self.assertIn(os.path.join(tool['name'], tool['version']), output) + + def test_export_recommended_version_cmake(self): + tool_to_test = 'cmake' + tool_version = '' + for tool in self.tools_dict['tools']: + if tool['name'] != tool_to_test: + continue + for version in tool['versions']: + if version['status'] == 'recommended': + tool_version = version['name'] + break + + self.run_idf_tools_with_action(['install']) + self.run_idf_tools_with_action(['install', tool_to_test]) + output = self.run_idf_tools_with_action(['export']) + + self.assertIn(os.path.join(tool_to_test, tool_version), output) + + def test_export_prefer_system_cmake(self): + tool_to_test = 'cmake' + self.run_idf_tools_with_action(['install']) + self.run_idf_tools_with_action(['install', tool_to_test]) + # cmake is installed via apt + output = self.run_idf_tools_with_action(['export', '--prefer-system']) + + self.assertNotIn(tool_to_test, output) + + +# TestUsageUnix tests installed tools on UNIX platforms +@unittest.skipIf(sys.platform == 'win32', reason='Tools for UNIX differ') +class TestUsageUnix(TestUsage): + def test_usage_basic(self): output = self.run_idf_tools_with_action(['list']) self.assertIn('* %s:' % ESP32ULP, output) @@ -171,13 +306,9 @@ class TestUsage(unittest.TestCase): self.assertEqual(required_tools_installed, output.count('Done')) output = self.run_idf_tools_with_action(['check']) - self.assertIn('version installed in tools directory: ' + ESP32ULP_VERSION, output) - self.assertIn('version installed in tools directory: ' + OPENOCD_VERSION, output) - self.assertIn('version installed in tools directory: ' + RISCV_ELF_VERSION, output) - self.assertIn('version installed in tools directory: ' + XTENSA_ELF_VERSION, output) - self.assertIn('version installed in tools directory: ' + XTENSA_ESP_GDB_VERSION, output) - self.assertIn('version installed in tools directory: ' + RISCV_ESP_GDB_VERSION, output) - self.assertIn('version installed in tools directory: ' + ESP_ROM_ELFS_VERSION, output) + for tool_version in [ESP32ULP_VERSION, OPENOCD_VERSION, RISCV_ELF_VERSION, XTENSA_ELF_VERSION, + XTENSA_ESP_GDB_VERSION, RISCV_ESP_GDB_VERSION, ESP_ROM_ELFS_VERSION]: + self.assertIn('version installed in tools directory: ' + tool_version, output) output = self.run_idf_tools_with_action(['export']) self.assertIn('%s/tools/esp32ulp-elf/%s/esp32ulp-elf/bin' % @@ -240,11 +371,9 @@ class TestUsage(unittest.TestCase): self.assertEqual(required_tools_installed, output.count('Done')) output = self.run_idf_tools_with_action(['check']) - self.assertIn('version installed in tools directory: ' + ESP32ULP_VERSION, output) - self.assertIn('version installed in tools directory: ' + XTENSA_ELF_VERSION, output) - self.assertIn('version installed in tools directory: ' + OPENOCD_VERSION, output) - self.assertIn('version installed in tools directory: ' + XTENSA_ESP_GDB_VERSION, output) - self.assertIn('version installed in tools directory: ' + ESP_ROM_ELFS_VERSION, output) + for tool_version in [ESP32ULP_VERSION, OPENOCD_VERSION, XTENSA_ELF_VERSION, + XTENSA_ESP_GDB_VERSION, ESP_ROM_ELFS_VERSION]: + self.assertIn('version installed in tools directory: ' + tool_version, output) output = self.run_idf_tools_with_action(['export']) self.assertIn('%s/tools/esp32ulp-elf/%s/esp32ulp-elf/bin' % @@ -270,16 +399,14 @@ class TestUsage(unittest.TestCase): self.assert_tool_installed(output, RISCV_ESP_GDB, RISCV_ESP_GDB_VERSION) self.assert_tool_not_installed(output, XTENSA_ELF, XTENSA_ELF_VERSION, XTENSA_ELF_ARCHIVE_PATTERN) self.assert_tool_not_installed(output, ESP32ULP, ESP32ULP_VERSION) - self.assert_tool_not_installed(output, XTENSA_ESP_GDB_VERSION, XTENSA_ESP_GDB_VERSION) + self.assert_tool_not_installed(output, XTENSA_ESP_GDB, XTENSA_ESP_GDB_VERSION) self.assert_tool_installed(output, ESP_ROM_ELFS, ESP_ROM_ELFS_VERSION) self.assertIn('Destination: {}'.format(os.path.join(self.temp_tools_dir, 'dist')), output) self.assertEqual(required_tools_installed, output.count('Done')) output = self.run_idf_tools_with_action(['check']) - self.assertIn('version installed in tools directory: ' + OPENOCD_VERSION, output) - self.assertIn('version installed in tools directory: ' + RISCV_ELF_VERSION, output) - self.assertIn('version installed in tools directory: ' + RISCV_ESP_GDB_VERSION, output) - self.assertIn('version installed in tools directory: ' + ESP_ROM_ELFS_VERSION, output) + for tool_version in [OPENOCD_VERSION, RISCV_ELF_VERSION, RISCV_ESP_GDB_VERSION, ESP_ROM_ELFS_VERSION]: + self.assertIn('version installed in tools directory: ' + tool_version, output) output = self.run_idf_tools_with_action(['export']) self.assertIn('%s/tools/openocd-esp32/%s/openocd-esp32/bin' % @@ -309,10 +436,8 @@ class TestUsage(unittest.TestCase): self.assertEqual(required_tools_installed, output.count('Done')) output = self.run_idf_tools_with_action(['check']) - self.assertIn('version installed in tools directory: ' + OPENOCD_VERSION, output) - self.assertIn('version installed in tools directory: ' + XTENSA_ELF_VERSION, output) - self.assertIn('version installed in tools directory: ' + XTENSA_ESP_GDB_VERSION, output) - self.assertIn('version installed in tools directory: ' + ESP_ROM_ELFS_VERSION, output) + for tool_version in [OPENOCD_VERSION, XTENSA_ELF_VERSION, XTENSA_ESP_GDB_VERSION, ESP_ROM_ELFS_VERSION]: + self.assertIn('version installed in tools directory: ' + tool_version, output) output = self.run_idf_tools_with_action(['export']) self.assertIn('%s/tools/xtensa-esp-elf/%s/xtensa-esp-elf/bin' % @@ -344,11 +469,9 @@ class TestUsage(unittest.TestCase): self.assertEqual(required_tools_installed, output.count('Done')) output = self.run_idf_tools_with_action(['check']) - self.assertIn('version installed in tools directory: ' + OPENOCD_VERSION, output) - self.assertIn('version installed in tools directory: ' + XTENSA_ELF_VERSION, output) - self.assertIn('version installed in tools directory: ' + XTENSA_ESP_GDB_VERSION, output) - self.assertIn('version installed in tools directory: ' + RISCV_ESP_GDB_VERSION, output) - self.assertIn('version installed in tools directory: ' + ESP_ROM_ELFS_VERSION, output) + for tool_version in [OPENOCD_VERSION, XTENSA_ELF_VERSION, XTENSA_ESP_GDB_VERSION, + RISCV_ESP_GDB_VERSION, ESP_ROM_ELFS_VERSION]: + self.assertIn('version installed in tools directory: ' + tool_version, output) output = self.run_idf_tools_with_action(['export']) self.assertIn('%s/tools/openocd-esp32/%s/openocd-esp32/bin' % @@ -382,125 +505,6 @@ class TestUsage(unittest.TestCase): self.assertIn('Destination: {}'.format(os.path.join(self.temp_tools_dir, 'dist')), output) self.assertEqual(required_tools_installed, output.count('Done')) - def test_tools_for_wildcards1(self): - required_tools_installed = 2 - output = self.run_idf_tools_with_action(['install', '*gdb*']) - self.assert_tool_not_installed(output, OPENOCD, OPENOCD_VERSION) - self.assert_tool_not_installed(output, RISCV_ELF, RISCV_ELF_VERSION,RISCV_ELF_ARCHIVE_PATTERN) - self.assert_tool_installed(output, RISCV_ESP_GDB, RISCV_ESP_GDB_VERSION) - self.assert_tool_not_installed(output, XTENSA_ELF, XTENSA_ELF_VERSION, XTENSA_ELF_ARCHIVE_PATTERN) - self.assert_tool_not_installed(output, ESP32ULP, ESP32ULP_VERSION) - self.assert_tool_installed(output, XTENSA_ESP_GDB, XTENSA_ESP_GDB_VERSION) - self.assert_tool_not_installed(output, ESP_ROM_ELFS, ESP_ROM_ELFS_VERSION) - self.assertIn('Destination: {}'.format(os.path.join(self.temp_tools_dir, 'dist')), output) - self.assertEqual(required_tools_installed, output.count('Done')) - - def test_tools_for_wildcards2(self): - required_tools_installed = 1 - output = self.run_idf_tools_with_action(['install', '*gdb*', '--targets=esp32c3']) - self.assert_tool_not_installed(output, OPENOCD, OPENOCD_VERSION) - self.assert_tool_not_installed(output, RISCV_ELF, RISCV_ELF_VERSION, RISCV_ELF_ARCHIVE_PATTERN) - self.assert_tool_installed(output, RISCV_ESP_GDB, RISCV_ESP_GDB_VERSION) - self.assert_tool_not_installed(output, XTENSA_ELF, XTENSA_ELF_VERSION, XTENSA_ELF_ARCHIVE_PATTERN) - self.assert_tool_not_installed(output, ESP32ULP, ESP32ULP_VERSION) - self.assert_tool_not_installed(output, XTENSA_ESP_GDB, XTENSA_ESP_GDB_VERSION) - self.assert_tool_not_installed(output, ESP_ROM_ELFS, ESP_ROM_ELFS_VERSION) - self.assertIn('Destination: {}'.format(os.path.join(self.temp_tools_dir, 'dist')), output) - self.assertEqual(required_tools_installed, output.count('Done')) - - def test_tools_for_wildcards3(self): - required_tools_installed = 1 - output = self.run_idf_tools_with_action(['install', '*gdb*', '--targets=esp32s3']) - self.assert_tool_not_installed(output, OPENOCD, OPENOCD_VERSION) - self.assert_tool_not_installed(output, RISCV_ELF, RISCV_ELF_VERSION, RISCV_ELF_ARCHIVE_PATTERN) - self.assert_tool_not_installed(output, RISCV_ESP_GDB, RISCV_ESP_GDB_VERSION) - self.assert_tool_not_installed(output, XTENSA_ELF, XTENSA_ELF_VERSION, XTENSA_ELF_ARCHIVE_PATTERN) - self.assert_tool_not_installed(output, ESP32ULP, ESP32ULP_VERSION) - self.assert_tool_installed(output, XTENSA_ESP_GDB, XTENSA_ESP_GDB_VERSION) - self.assert_tool_not_installed(output, ESP_ROM_ELFS, ESP_ROM_ELFS_VERSION) - self.assertIn('Destination: {}'.format(os.path.join(self.temp_tools_dir, 'dist')), output) - self.assertEqual(required_tools_installed, output.count('Done')) - - def test_uninstall_option(self): - self.run_idf_tools_with_action(['install', '--targets=esp32']) - - test_tool_name = XTENSA_ELF - test_tool_version = 'test_version' - tools_json_new = os.path.join(self.temp_tools_dir, 'tools', 'tools.new.json') - self.run_idf_tools_with_action( - [ - 'add-version', - '--tool', - test_tool_name, - '--url-prefix', - 'http://test.com', - '--version', - test_tool_version, - '--override', - '--checksum-file', - 'add_version/checksum.sha256', - '--output', - tools_json_new - ]) - output = self.run_idf_tools_with_action(['--tools-json', tools_json_new, 'uninstall', '--dry-run']) - self.assertIn('For removing old versions of ' + test_tool_name, output) - output = self.run_idf_tools_with_action(['--tools-json', tools_json_new, 'uninstall']) - self.assertIn(os.path.join(self.temp_tools_dir, 'tools', test_tool_name, XTENSA_ELF_VERSION) + ' was removed.', output) - output = self.run_idf_tools_with_action(['uninstall']) - self.assertEqual('', output) - - def test_deactivate(self): - self.run_idf_tools_with_action(['install']) - output = self.run_idf_tools_with_action(['export']) - self.assertIn('export IDF_DEACTIVATE_FILE_PATH=', output, 'No IDF_DEACTIVATE_FILE_PATH exported into environment') - deactivate_file = re.findall(r'(?:IDF_DEACTIVATE_FILE_PATH=")(.*)(?:")', output)[0] - self.assertTrue(os.path.isfile(deactivate_file), 'File {} was not found. '.format(deactivate_file)) - self.assertNotEqual(os.stat(self.idf_env_json).st_size, 0, 'File {} is empty. '.format(deactivate_file)) - - def test_export_recommended_version(self): - always_install_and_recommended_tools = [] - for tool in self.tools_dict['tools']: - if tool['install'] != 'always': - continue - for version in tool['versions']: - if version['status'] != 'recommended': - continue - always_install_and_recommended_tools.append({ - 'name': tool['name'], - 'version': version['name'] - }) - self.run_idf_tools_with_action(['install']) - output = self.run_idf_tools_with_action(['export']) - - for tool in always_install_and_recommended_tools: - self.assertIn(f"{tool['name']}/{tool['version']}", output) - - def test_export_recommended_version_cmake(self): - tool_to_test = 'cmake' - tool_version = '' - for tool in self.tools_dict['tools']: - if tool['name'] != tool_to_test: - continue - for version in tool['versions']: - if version['status'] == 'recommended': - tool_version = version['name'] - break - - self.run_idf_tools_with_action(['install']) - self.run_idf_tools_with_action(['install', tool_to_test]) - output = self.run_idf_tools_with_action(['export']) - - self.assertIn(f'{tool_to_test}/{tool_version}', output) - - def test_export_prefer_system_cmake(self): - tool_to_test = 'cmake' - self.run_idf_tools_with_action(['install']) - self.run_idf_tools_with_action(['install', tool_to_test]) - # cmake is installed via apt - output = self.run_idf_tools_with_action(['export', '--prefer-system']) - - self.assertNotIn(tool_to_test, output) - def test_export_supported_version_cmake(self): tool_to_test = 'cmake' self.run_idf_tools_with_action(['install']) @@ -509,6 +513,380 @@ class TestUsage(unittest.TestCase): self.assertNotIn(tool_to_test, output) +# TestUsageWin tests installed tools on Windows platforms +@unittest.skipIf(sys.platform != 'win32', reason='Tools for WIN differ') +class TestUsageWin(TestUsage): + + def test_usage_basic_win(self): + output = self.run_idf_tools_with_action(['list']) + self.assertIn('* %s:' % ESP32ULP, output) + self.assertIn('- %s (recommended)' % ESP32ULP_VERSION, output) + self.assertIn('* %s:' % OPENOCD, output) + self.assertIn('- %s (recommended)' % OPENOCD_VERSION, output) + self.assertIn('* %s:' % RISCV_ELF, output) + self.assertIn('- %s (recommended)' % RISCV_ELF_VERSION, output) + self.assertIn('* %s:' % XTENSA_ELF, output) + self.assertIn('- %s (recommended)' % XTENSA_ELF_VERSION, output) + + required_tools_installed = 12 + output = self.run_idf_tools_with_action(['install']) + self.assert_tool_installed(output, OPENOCD, OPENOCD_VERSION) + self.assert_tool_installed(output, RISCV_ELF, RISCV_ELF_VERSION, RISCV_ELF_ARCHIVE_PATTERN) + self.assert_tool_installed(output, XTENSA_ELF, XTENSA_ELF_VERSION, XTENSA_ELF_ARCHIVE_PATTERN) + self.assert_tool_installed(output, ESP32ULP, ESP32ULP_VERSION) + self.assert_tool_installed(output, XTENSA_ESP_GDB, XTENSA_ESP_GDB_VERSION) + self.assert_tool_installed(output, RISCV_ESP_GDB, RISCV_ESP_GDB_VERSION) + self.assert_tool_installed(output, ESP_ROM_ELFS, ESP_ROM_ELFS_VERSION) + self.assert_tool_installed(output, CMAKE, CMAKE_VERSION) + self.assert_tool_installed(output, NINJA, NINJA_VERSION) + self.assert_tool_installed(output, IDF_EXE, IDF_EXE_VERSION) + self.assert_tool_installed(output, CCACHE, CCACHE_VERSION) + self.assert_tool_installed(output, DFU_UTIL, DFU_UTIL_VERSION) + self.assertIn('Destination: {}'.format(os.path.join(self.temp_tools_dir, 'dist')), output) + self.assertEqual(required_tools_installed, output.count('Done')) + + output = self.run_idf_tools_with_action(['check']) + for tool_version in [ESP32ULP_VERSION, OPENOCD_VERSION, RISCV_ELF_VERSION, XTENSA_ELF_VERSION, + XTENSA_ESP_GDB_VERSION, RISCV_ESP_GDB_VERSION, ESP_ROM_ELFS_VERSION, CMAKE_VERSION, + NINJA_VERSION, IDF_EXE_VERSION, CCACHE_VERSION, DFU_UTIL_VERSION]: + self.assertIn('version installed in tools directory: ' + tool_version, output) + + output = self.run_idf_tools_with_action(['export']) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', 'esp32ulp-elf', ESP32ULP_VERSION, 'esp32ulp-elf', 'bin' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', 'xtensa-esp-elf', XTENSA_ELF_VERSION, 'xtensa-esp-elf', 'bin' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', 'openocd-esp32', OPENOCD_VERSION, 'openocd-esp32', 'bin' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', 'riscv32-esp-elf', RISCV_ELF_VERSION, 'riscv32-esp-elf', 'bin' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', 'xtensa-esp-elf-gdb', XTENSA_ESP_GDB_VERSION, 'xtensa-esp-elf-gdb', 'bin' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', 'riscv32-esp-elf-gdb', RISCV_ESP_GDB_VERSION, 'riscv32-esp-elf-gdb', 'bin' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', 'esp-rom-elfs', ESP_ROM_ELFS_VERSION + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', CMAKE, CMAKE_VERSION, 'bin' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', NINJA, NINJA_VERSION + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', IDF_EXE, IDF_EXE_VERSION + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', CCACHE, CCACHE_VERSION, 'ccache-4.8-windows-x86_64' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', DFU_UTIL, DFU_UTIL_VERSION, 'dfu-util-0.11-win64' + ), output) + + output = self.run_idf_tools_with_action(['list', '--outdated']) + self.assertEqual('', output) + + tools_json_outdated = os.path.join(self.temp_tools_dir, 'tools', 'tools.outdated.json') + new_version = 'zzzzzz' + self.run_idf_tools_with_action( + [ + 'add-version', + '--tool', + XTENSA_ELF, + '--url-prefix', + 'http://test.com', + '--version', + new_version, + '--override', + '--checksum-file', + 'add_version/checksum.sha256', + '--output', + tools_json_outdated + ]) + + output = self.run_idf_tools_with_action( + [ + '--tools-json', + tools_json_outdated, + 'list', + '--outdated' + ]) + self.assertIn((f'{XTENSA_ELF}: version {XTENSA_ELF_VERSION} ' + f'is outdated by {new_version}'), output) + + def test_tools_for_esp32_win(self): + required_tools_installed = 9 + output = self.run_idf_tools_with_action(['install', '--targets=esp32']) + self.assert_tool_installed(output, XTENSA_ELF, XTENSA_ELF_VERSION, XTENSA_ELF_ARCHIVE_PATTERN) + self.assert_tool_installed(output, OPENOCD, OPENOCD_VERSION) + self.assert_tool_installed(output, ESP32ULP, ESP32ULP_VERSION) + self.assert_tool_installed(output, XTENSA_ESP_GDB, XTENSA_ESP_GDB_VERSION) + self.assert_tool_not_installed(output, RISCV_ELF, RISCV_ELF_VERSION, RISCV_ELF_ARCHIVE_PATTERN) + self.assert_tool_not_installed(output, RISCV_ESP_GDB, RISCV_ESP_GDB_VERSION) + self.assert_tool_installed(output, ESP_ROM_ELFS, ESP_ROM_ELFS_VERSION) + self.assert_tool_installed(output, CMAKE, CMAKE_VERSION) + self.assert_tool_installed(output, NINJA, NINJA_VERSION) + self.assert_tool_installed(output, IDF_EXE, IDF_EXE_VERSION) + self.assert_tool_installed(output, CCACHE, CCACHE_VERSION) + self.assert_tool_not_installed(output, DFU_UTIL, DFU_UTIL_VERSION) + self.assertIn('Destination: {}'.format(os.path.join(self.temp_tools_dir, 'dist')), output) + self.assertEqual(required_tools_installed, output.count('Done')) + + output = self.run_idf_tools_with_action(['check']) + for tool_version in [ESP32ULP_VERSION, OPENOCD_VERSION, XTENSA_ELF_VERSION, XTENSA_ESP_GDB_VERSION, + ESP_ROM_ELFS_VERSION, CMAKE_VERSION, NINJA_VERSION, IDF_EXE_VERSION, CCACHE_VERSION]: + self.assertIn('version installed in tools directory: ' + tool_version, output) + self.assertNotIn('version installed in tools directory: ' + DFU_UTIL_VERSION, output) + + output = self.run_idf_tools_with_action(['export']) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', 'esp32ulp-elf', ESP32ULP_VERSION, 'esp32ulp-elf', 'bin' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', 'xtensa-esp-elf', XTENSA_ELF_VERSION, 'xtensa-esp-elf', 'bin' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', 'openocd-esp32', OPENOCD_VERSION, 'openocd-esp32', 'bin' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', 'xtensa-esp-elf-gdb', XTENSA_ESP_GDB_VERSION, 'xtensa-esp-elf-gdb', 'bin' + ), output) + self.assertNotIn(os.path.join( + self.temp_tools_dir, 'tools', 'riscv32-esp-elf', RISCV_ELF_VERSION, 'riscv32-esp-elf', 'bin' + ), output) + self.assertNotIn(os.path.join( + self.temp_tools_dir, 'tools', 'riscv32-esp-elf-gdb', RISCV_ESP_GDB_VERSION, 'riscv32-esp-elf-gdb', 'bin' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', 'esp-rom-elfs', ESP_ROM_ELFS_VERSION, + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', CMAKE, CMAKE_VERSION, 'bin' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', NINJA, NINJA_VERSION + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', IDF_EXE, IDF_EXE_VERSION + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', CCACHE, CCACHE_VERSION, 'ccache-4.8-windows-x86_64' + ), output) + self.assertNotIn(os.path.join( + self.temp_tools_dir, 'tools', DFU_UTIL, DFU_UTIL_VERSION, 'dfu-util-0.11-win64' + ), output) + + def test_tools_for_esp32c3_win(self): + required_tools_installed = 8 + output = self.run_idf_tools_with_action(['install', '--targets=esp32c3']) + self.assert_tool_installed(output, OPENOCD, OPENOCD_VERSION) + self.assert_tool_installed(output, RISCV_ELF, RISCV_ELF_VERSION, RISCV_ELF_ARCHIVE_PATTERN) + self.assert_tool_installed(output, RISCV_ESP_GDB, RISCV_ESP_GDB_VERSION) + self.assert_tool_not_installed(output, XTENSA_ELF, XTENSA_ELF_VERSION, XTENSA_ELF_ARCHIVE_PATTERN) + self.assert_tool_not_installed(output, ESP32ULP, ESP32ULP_VERSION) + self.assert_tool_not_installed(output, XTENSA_ESP_GDB, XTENSA_ESP_GDB_VERSION) + self.assert_tool_installed(output, ESP_ROM_ELFS, ESP_ROM_ELFS_VERSION) + self.assert_tool_installed(output, CMAKE, CMAKE_VERSION) + self.assert_tool_installed(output, NINJA, NINJA_VERSION) + self.assert_tool_installed(output, IDF_EXE, IDF_EXE_VERSION) + self.assert_tool_installed(output, CCACHE, CCACHE_VERSION) + self.assert_tool_not_installed(output, DFU_UTIL, DFU_UTIL_VERSION) + self.assertIn('Destination: {}'.format(os.path.join(self.temp_tools_dir, 'dist')), output) + self.assertEqual(required_tools_installed, output.count('Done')) + + output = self.run_idf_tools_with_action(['check']) + for tool_version in [OPENOCD_VERSION, RISCV_ELF_VERSION, RISCV_ESP_GDB_VERSION, ESP_ROM_ELFS_VERSION, + CMAKE_VERSION, NINJA_VERSION, IDF_EXE_VERSION, CCACHE_VERSION]: + self.assertIn('version installed in tools directory: ' + tool_version, output) + self.assertNotIn('version installed in tools directory: ' + DFU_UTIL_VERSION, output) + + output = self.run_idf_tools_with_action(['export']) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', 'openocd-esp32', OPENOCD_VERSION, 'openocd-esp32', 'bin' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', 'riscv32-esp-elf', RISCV_ELF_VERSION, 'riscv32-esp-elf', 'bin' + ), output) + self.assertNotIn(os.path.join( + self.temp_tools_dir, 'tools', 'esp32ulp-elf', ESP32ULP_VERSION, 'esp32ulp-elf', 'bin' + ), output) + self.assertNotIn(os.path.join( + self.temp_tools_dir, 'tools', 'xtensa-esp-elf', XTENSA_ELF_VERSION, 'xtensa-esp-elf', 'bin' + ), output) + self.assertNotIn(os.path.join( + self.temp_tools_dir, 'tools', 'xtensa-esp-elf-gdb', XTENSA_ESP_GDB_VERSION, 'xtensa-esp-elf-gdb', 'bin' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', 'esp-rom-elfs', ESP_ROM_ELFS_VERSION, + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', CMAKE, CMAKE_VERSION, 'bin' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', NINJA, NINJA_VERSION + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', IDF_EXE, IDF_EXE_VERSION + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', CCACHE, CCACHE_VERSION, 'ccache-4.8-windows-x86_64' + ), output) + self.assertNotIn(os.path.join( + self.temp_tools_dir, 'tools', DFU_UTIL, DFU_UTIL_VERSION, 'dfu-util-0.11-win64' + ), output) + + def test_tools_for_esp32s2_win(self): + required_tools_installed = 11 + output = self.run_idf_tools_with_action(['install', '--targets=esp32s2']) + self.assert_tool_installed(output, XTENSA_ELF, XTENSA_ELF_VERSION, XTENSA_ELF_ARCHIVE_PATTERN) + self.assert_tool_installed(output, OPENOCD, OPENOCD_VERSION) + self.assert_tool_installed(output, RISCV_ELF, RISCV_ELF_VERSION, RISCV_ELF_ARCHIVE_PATTERN) + self.assert_tool_installed(output, ESP32ULP, ESP32ULP_VERSION) + self.assert_tool_installed(output, XTENSA_ESP_GDB, XTENSA_ESP_GDB_VERSION) + self.assert_tool_installed(output, ESP_ROM_ELFS, ESP_ROM_ELFS_VERSION) + self.assert_tool_not_installed(output, RISCV_ESP_GDB, RISCV_ESP_GDB_VERSION) + self.assert_tool_installed(output, CMAKE, CMAKE_VERSION) + self.assert_tool_installed(output, NINJA, NINJA_VERSION) + self.assert_tool_installed(output, IDF_EXE, IDF_EXE_VERSION) + self.assert_tool_installed(output, CCACHE, CCACHE_VERSION) + self.assert_tool_installed(output, DFU_UTIL, DFU_UTIL_VERSION) + self.assertIn('Destination: {}'.format(os.path.join(self.temp_tools_dir, 'dist')), output) + self.assertEqual(required_tools_installed, output.count('Done')) + + output = self.run_idf_tools_with_action(['check']) + for tool_version in [OPENOCD_VERSION, XTENSA_ELF_VERSION, XTENSA_ESP_GDB_VERSION, DFU_UTIL_VERSION, + ESP_ROM_ELFS_VERSION, CMAKE_VERSION, NINJA_VERSION, IDF_EXE_VERSION, CCACHE_VERSION]: + self.assertIn('version installed in tools directory: ' + tool_version, output) + + output = self.run_idf_tools_with_action(['export']) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', 'xtensa-esp-elf', XTENSA_ELF_VERSION, 'xtensa-esp-elf', 'bin' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', 'openocd-esp32', OPENOCD_VERSION, 'openocd-esp32', 'bin' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', 'esp32ulp-elf', ESP32ULP_VERSION, 'esp32ulp-elf', 'bin' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', 'riscv32-esp-elf', RISCV_ELF_VERSION, 'riscv32-esp-elf', 'bin' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', 'xtensa-esp-elf-gdb', XTENSA_ESP_GDB_VERSION, 'xtensa-esp-elf-gdb', 'bin' + ), output) + self.assertNotIn(os.path.join( + self.temp_tools_dir, 'tools', 'riscv32-esp-elf-gdb', RISCV_ESP_GDB_VERSION, 'riscv32-esp-elf-gdb', 'bin' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', 'esp-rom-elfs', ESP_ROM_ELFS_VERSION, + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', CMAKE, CMAKE_VERSION, 'bin' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', NINJA, NINJA_VERSION + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', IDF_EXE, IDF_EXE_VERSION + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', CCACHE, CCACHE_VERSION, 'ccache-4.8-windows-x86_64' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', DFU_UTIL, DFU_UTIL_VERSION, 'dfu-util-0.11-win64' + ), output) + + def test_tools_for_esp32s3_win(self): + required_tools_installed = 11 + output = self.run_idf_tools_with_action(['install', '--targets=esp32s3']) + print(output) + self.assert_tool_installed(output, XTENSA_ELF, XTENSA_ELF_VERSION, XTENSA_ELF_ARCHIVE_PATTERN) + self.assert_tool_installed(output, OPENOCD, OPENOCD_VERSION) + self.assert_tool_installed(output, RISCV_ELF, RISCV_ELF_VERSION, RISCV_ELF_ARCHIVE_PATTERN) + self.assert_tool_installed(output, ESP32ULP, ESP32ULP_VERSION) + self.assert_tool_installed(output, XTENSA_ESP_GDB, XTENSA_ESP_GDB_VERSION) + self.assert_tool_installed(output, ESP_ROM_ELFS, ESP_ROM_ELFS_VERSION) + self.assert_tool_not_installed(output, RISCV_ESP_GDB, RISCV_ESP_GDB_VERSION) + self.assert_tool_installed(output, CMAKE, CMAKE_VERSION) + self.assert_tool_installed(output, NINJA, NINJA_VERSION) + self.assert_tool_installed(output, IDF_EXE, IDF_EXE_VERSION) + self.assert_tool_installed(output, CCACHE, CCACHE_VERSION) + self.assert_tool_installed(output, DFU_UTIL, DFU_UTIL_VERSION) + self.assertIn('Destination: {}'.format(os.path.join(self.temp_tools_dir, 'dist')), output) + self.assertEqual(required_tools_installed, output.count('Done')) + + output = self.run_idf_tools_with_action(['check']) + for tool_version in [OPENOCD_VERSION, XTENSA_ELF_VERSION, XTENSA_ESP_GDB_VERSION, RISCV_ESP_GDB_VERSION, + DFU_UTIL_VERSION, ESP_ROM_ELFS_VERSION, CMAKE_VERSION, NINJA_VERSION, + IDF_EXE_VERSION, CCACHE_VERSION]: + self.assertIn('version installed in tools directory: ' + tool_version, output) + + output = self.run_idf_tools_with_action(['export']) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', 'openocd-esp32', OPENOCD_VERSION, 'openocd-esp32', 'bin' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', 'xtensa-esp-elf', XTENSA_ELF_VERSION, 'xtensa-esp-elf', 'bin' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', 'esp32ulp-elf', ESP32ULP_VERSION, 'esp32ulp-elf', 'bin' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', 'riscv32-esp-elf', RISCV_ELF_VERSION, 'riscv32-esp-elf', 'bin' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', 'xtensa-esp-elf-gdb', XTENSA_ESP_GDB_VERSION, 'xtensa-esp-elf-gdb', 'bin' + ), output) + self.assertNotIn(os.path.join( + self.temp_tools_dir, 'tools', 'riscv32-esp-elf-gdb', RISCV_ESP_GDB_VERSION, 'riscv32-esp-elf-gdb', 'bin' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', 'esp-rom-elfs', ESP_ROM_ELFS_VERSION, + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', CMAKE, CMAKE_VERSION, 'bin' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', NINJA, NINJA_VERSION + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', IDF_EXE, IDF_EXE_VERSION + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', CCACHE, CCACHE_VERSION, 'ccache-4.8-windows-x86_64' + ), output) + self.assertIn(os.path.join( + self.temp_tools_dir, 'tools', DFU_UTIL, DFU_UTIL_VERSION, 'dfu-util-0.11-win64' + ), output) + + # a different test for qemu because of "on_request" + def test_tools_for_qemu_with_required_win(self): + required_tools_installed = 14 + output = self.run_idf_tools_with_action(['install', 'required', 'qemu-xtensa', 'qemu-riscv32']) + self.assert_tool_installed(output, OPENOCD, OPENOCD_VERSION) + self.assert_tool_installed(output, RISCV_ELF, RISCV_ELF_VERSION, RISCV_ELF_ARCHIVE_PATTERN) + self.assert_tool_installed(output, XTENSA_ELF, XTENSA_ELF_VERSION, XTENSA_ELF_ARCHIVE_PATTERN) + self.assert_tool_installed(output, ESP32ULP, ESP32ULP_VERSION) + self.assert_tool_installed(output, XTENSA_ESP_GDB, XTENSA_ESP_GDB_VERSION) + self.assert_tool_installed(output, RISCV_ESP_GDB, RISCV_ESP_GDB_VERSION) + self.assert_tool_installed(output, ESP_ROM_ELFS, ESP_ROM_ELFS_VERSION) + self.assert_tool_installed(output, QEMU_RISCV, QEMU_RISCV_VERSION) + self.assert_tool_installed(output, QEMU_XTENSA, QEMU_XTENSA_VERSION) + self.assert_tool_installed(output, CMAKE, CMAKE_VERSION) + self.assert_tool_installed(output, NINJA, NINJA_VERSION) + self.assert_tool_installed(output, IDF_EXE, IDF_EXE_VERSION) + self.assert_tool_installed(output, CCACHE, CCACHE_VERSION) + self.assert_tool_installed(output, DFU_UTIL, DFU_UTIL_VERSION) + self.assertIn('Destination: {}'.format(os.path.join(self.temp_tools_dir, 'dist')), output) + self.assertEqual(required_tools_installed, output.count('Done')) + + class TestMaintainer(unittest.TestCase): @classmethod diff --git a/tools/test_idf_tools/test_idf_tools_python_env.py b/tools/test_idf_tools/test_idf_tools_python_env.py index 8de19d825b..e2ec0f0e23 100644 --- a/tools/test_idf_tools/test_idf_tools_python_env.py +++ b/tools/test_idf_tools/test_idf_tools_python_env.py @@ -1,6 +1,5 @@ # SPDX-FileCopyrightText: 2022-2023 Espressif Systems (Shanghai) CO LTD # SPDX-License-Identifier: Apache-2.0 - # NOTE: unittest is by default sorting tests based on their names, # so the order if which the tests are started may be different from # the order in which they are defined. Please make sure all tests @@ -9,7 +8,6 @@ # If test needs to change global state, it should return it to the # original state after it's finished. For more information please see # https://docs.python.org/3/library/unittest.html#organizing-test-code - import inspect import os import shutil @@ -29,11 +27,12 @@ IDF_PATH = os.environ.get('IDF_PATH', '../..') TOOLS_DIR = os.environ.get('IDF_TOOLS_PATH') or os.path.expanduser(idf_tools.IDF_TOOLS_PATH_DEFAULT) PYTHON_DIR = os.path.join(TOOLS_DIR, 'python_env') PYTHON_DIR_BACKUP = tempfile.mkdtemp() +PYTHON_BINARY = os.path.join('Scripts', 'python.exe') if sys.platform == 'win32' else os.path.join('bin', 'python') REQ_SATISFIED = 'Python requirements are satisfied' -REQ_MISSING = "'{}' - was not found and is required by the application" +REQ_MISSING = "{}' - was not found and is required by the application" REQ_CORE = '- {}'.format(os.path.join(IDF_PATH, 'tools', 'requirements', 'requirements.core.txt')) REQ_GDBGUI = '- {}'.format(os.path.join(IDF_PATH, 'tools', 'requirements', 'requirements.gdbgui.txt')) -CONSTR = 'Constraint file: {}/espidf.constraints'.format(TOOLS_DIR) +CONSTR = 'Constraint file: {}'.format(os.path.join(TOOLS_DIR, 'espidf.constraints')) # Set default global paths for idf_tools. If some test needs to # use functions from idf_tools with custom paths, it should @@ -183,7 +182,7 @@ class TestPythonInstall(BasePythonInstall): def test_default_arguments(self): # type: () -> None output = self.run_idf_tools(['check-python-dependencies']) self.assertNotIn(REQ_SATISFIED, output) - self.assertIn('bin/python doesn\'t exist', output) + self.assertIn(f'{PYTHON_BINARY} doesn\'t exist', output) output = self.run_idf_tools(['install-python-env']) self.assertIn(CONSTR, output) @@ -232,7 +231,7 @@ class TestCustomPythonPathInstall(BasePythonInstall): def test_default_arguments(self): # type: () -> None output = self.run_idf_tools(['check-python-dependencies']) - self.assertIn(f"{self.CUSTOM_PYTHON_DIR}/bin/python doesn't exist", output) + self.assertIn(f"{os.path.join(self.CUSTOM_PYTHON_DIR, PYTHON_BINARY)} doesn't exist", output) self.assertNotIn(PYTHON_DIR, output) output = self.run_idf_tools(['install-python-env'])