2020-01-24 20:31:16 +01:00
|
|
|
"""QMK Doctor
|
2019-07-15 21:14:27 +02:00
|
|
|
|
2020-01-24 20:31:16 +01:00
|
|
|
Check out the user's QMK environment and make sure it's ready to compile.
|
2019-07-15 21:14:27 +02:00
|
|
|
"""
|
2019-08-22 08:40:24 +02:00
|
|
|
import platform
|
2021-05-20 00:24:46 +02:00
|
|
|
from subprocess import DEVNULL
|
2019-07-15 21:14:27 +02:00
|
|
|
|
|
|
|
from milc import cli
|
2020-11-28 21:02:18 +01:00
|
|
|
from milc.questions import yesno
|
2021-06-22 20:50:53 +02:00
|
|
|
|
2020-01-24 20:31:16 +01:00
|
|
|
from qmk import submodules
|
2021-07-10 17:04:50 +02:00
|
|
|
from qmk.constants import QMK_FIRMWARE, QMK_FIRMWARE_UPSTREAM
|
|
|
|
from .check import CheckStatus, check_binaries, check_binary_versions, check_submodules
|
2022-03-18 17:02:24 +01:00
|
|
|
from qmk.git import git_check_repo, git_get_branch, git_get_tag, git_is_dirty, git_get_remotes, git_check_deviation
|
|
|
|
from qmk.commands import in_virtualenv
|
2020-01-24 20:31:16 +01:00
|
|
|
|
|
|
|
|
2020-12-19 01:42:30 +01:00
|
|
|
def os_tests():
|
|
|
|
"""Determine our OS and run platform specific tests
|
|
|
|
"""
|
|
|
|
platform_id = platform.platform().lower()
|
|
|
|
|
|
|
|
if 'darwin' in platform_id or 'macos' in platform_id:
|
2021-06-22 20:50:53 +02:00
|
|
|
from .macos import os_test_macos
|
2020-12-19 01:42:30 +01:00
|
|
|
return os_test_macos()
|
|
|
|
elif 'linux' in platform_id:
|
2021-06-22 20:50:53 +02:00
|
|
|
from .linux import os_test_linux
|
2020-12-19 01:42:30 +01:00
|
|
|
return os_test_linux()
|
|
|
|
elif 'windows' in platform_id:
|
2021-06-22 20:50:53 +02:00
|
|
|
from .windows import os_test_windows
|
2020-12-19 01:42:30 +01:00
|
|
|
return os_test_windows()
|
|
|
|
else:
|
|
|
|
cli.log.warning('Unsupported OS detected: %s', platform_id)
|
|
|
|
return CheckStatus.WARNING
|
|
|
|
|
|
|
|
|
2021-07-10 17:04:50 +02:00
|
|
|
def git_tests():
|
|
|
|
"""Run Git-related checks
|
|
|
|
"""
|
|
|
|
status = CheckStatus.OK
|
|
|
|
|
|
|
|
# Make sure our QMK home is a Git repo
|
|
|
|
git_ok = git_check_repo()
|
|
|
|
if not git_ok:
|
|
|
|
cli.log.warning("{fg_yellow}QMK home does not appear to be a Git repository! (no .git folder)")
|
|
|
|
status = CheckStatus.WARNING
|
|
|
|
else:
|
|
|
|
git_branch = git_get_branch()
|
|
|
|
if git_branch:
|
|
|
|
cli.log.info('Git branch: %s', git_branch)
|
2022-02-02 05:31:42 +01:00
|
|
|
|
|
|
|
repo_version = git_get_tag()
|
|
|
|
if repo_version:
|
|
|
|
cli.log.info('Repo version: %s', repo_version)
|
|
|
|
|
2021-07-10 17:04:50 +02:00
|
|
|
git_dirty = git_is_dirty()
|
|
|
|
if git_dirty:
|
|
|
|
cli.log.warning('{fg_yellow}Git has unstashed/uncommitted changes.')
|
|
|
|
status = CheckStatus.WARNING
|
|
|
|
git_remotes = git_get_remotes()
|
|
|
|
if 'upstream' not in git_remotes.keys() or QMK_FIRMWARE_UPSTREAM not in git_remotes['upstream'].get('url', ''):
|
|
|
|
cli.log.warning('{fg_yellow}The official repository does not seem to be configured as git remote "upstream".')
|
|
|
|
status = CheckStatus.WARNING
|
|
|
|
else:
|
|
|
|
git_deviation = git_check_deviation(git_branch)
|
|
|
|
if git_branch in ['master', 'develop'] and git_deviation:
|
|
|
|
cli.log.warning('{fg_yellow}The local "%s" branch contains commits not found in the upstream branch.', git_branch)
|
|
|
|
status = CheckStatus.WARNING
|
|
|
|
|
|
|
|
return status
|
|
|
|
|
|
|
|
|
2020-01-24 20:31:16 +01:00
|
|
|
@cli.argument('-y', '--yes', action='store_true', arg_only=True, help='Answer yes to all questions.')
|
|
|
|
@cli.argument('-n', '--no', action='store_true', arg_only=True, help='Answer no to all questions.')
|
2019-09-22 22:25:33 +02:00
|
|
|
@cli.subcommand('Basic QMK environment checks')
|
|
|
|
def doctor(cli):
|
2019-07-15 21:14:27 +02:00
|
|
|
"""Basic QMK environment checks.
|
|
|
|
|
|
|
|
This is currently very simple, it just checks that all the expected binaries are on your system.
|
|
|
|
|
|
|
|
TODO(unclaimed):
|
|
|
|
* [ ] Compile a trivial program with each compiler
|
|
|
|
"""
|
2019-08-22 18:38:10 +02:00
|
|
|
cli.log.info('QMK Doctor is checking your environment.')
|
2021-06-27 05:21:53 +02:00
|
|
|
cli.log.info('CLI version: %s', cli.version)
|
2021-04-02 12:44:27 +02:00
|
|
|
cli.log.info('QMK home: {fg_cyan}%s', QMK_FIRMWARE)
|
2019-08-22 18:38:10 +02:00
|
|
|
|
2021-09-27 19:02:54 +02:00
|
|
|
status = os_status = os_tests()
|
|
|
|
git_status = git_tests()
|
2019-08-22 18:38:10 +02:00
|
|
|
|
2021-09-27 19:02:54 +02:00
|
|
|
if git_status == CheckStatus.ERROR or (os_status == CheckStatus.OK and git_status == CheckStatus.WARNING):
|
|
|
|
status = git_status
|
2020-12-20 15:46:01 +01:00
|
|
|
|
2021-09-27 19:02:54 +02:00
|
|
|
if in_virtualenv():
|
2021-07-10 17:04:50 +02:00
|
|
|
cli.log.info('CLI installed in virtualenv.')
|
2020-12-20 15:46:01 +01:00
|
|
|
|
2020-01-24 20:31:16 +01:00
|
|
|
# Make sure the basic CLI tools we need are available and can be executed.
|
|
|
|
bin_ok = check_binaries()
|
|
|
|
|
|
|
|
if not bin_ok:
|
|
|
|
if yesno('Would you like to install dependencies?', default=True):
|
2021-05-20 00:24:46 +02:00
|
|
|
cli.run(['util/qmk_install.sh', '-y'], stdin=DEVNULL, capture_output=False)
|
2020-01-24 20:31:16 +01:00
|
|
|
bin_ok = check_binaries()
|
|
|
|
|
|
|
|
if bin_ok:
|
|
|
|
cli.log.info('All dependencies are installed.')
|
2019-07-15 21:14:27 +02:00
|
|
|
else:
|
2020-11-16 22:09:32 +01:00
|
|
|
status = CheckStatus.ERROR
|
2020-01-24 20:31:16 +01:00
|
|
|
|
2020-03-08 17:21:45 +01:00
|
|
|
# Make sure the tools are at the correct version
|
2020-12-21 13:29:36 +01:00
|
|
|
ver_ok = check_binary_versions()
|
2020-11-16 22:09:32 +01:00
|
|
|
if CheckStatus.ERROR in ver_ok:
|
|
|
|
status = CheckStatus.ERROR
|
|
|
|
elif CheckStatus.WARNING in ver_ok and status == CheckStatus.OK:
|
|
|
|
status = CheckStatus.WARNING
|
2020-03-08 17:21:45 +01:00
|
|
|
|
2020-01-24 20:31:16 +01:00
|
|
|
# Check out the QMK submodules
|
|
|
|
sub_ok = check_submodules()
|
|
|
|
|
2020-11-16 22:09:32 +01:00
|
|
|
if sub_ok == CheckStatus.OK:
|
2020-01-24 20:31:16 +01:00
|
|
|
cli.log.info('Submodules are up to date.')
|
|
|
|
else:
|
|
|
|
if yesno('Would you like to clone the submodules?', default=True):
|
|
|
|
submodules.update()
|
|
|
|
sub_ok = check_submodules()
|
|
|
|
|
2021-02-16 18:45:05 +01:00
|
|
|
if sub_ok == CheckStatus.ERROR:
|
2020-11-16 22:09:32 +01:00
|
|
|
status = CheckStatus.ERROR
|
2021-02-16 18:45:05 +01:00
|
|
|
elif sub_ok == CheckStatus.WARNING and status == CheckStatus.OK:
|
2020-11-16 22:09:32 +01:00
|
|
|
status = CheckStatus.WARNING
|
2019-07-15 21:14:27 +02:00
|
|
|
|
2019-08-22 18:38:10 +02:00
|
|
|
# Report a summary of our findings to the user
|
2020-11-16 22:09:32 +01:00
|
|
|
if status == CheckStatus.OK:
|
2019-07-15 21:14:27 +02:00
|
|
|
cli.log.info('{fg_green}QMK is ready to go')
|
2020-11-16 22:09:32 +01:00
|
|
|
return 0
|
|
|
|
elif status == CheckStatus.WARNING:
|
|
|
|
cli.log.info('{fg_yellow}QMK is ready to go, but minor problems were found')
|
|
|
|
return 1
|
2019-08-22 08:40:24 +02:00
|
|
|
else:
|
2020-11-16 22:09:32 +01:00
|
|
|
cli.log.info('{fg_red}Major problems detected, please fix these problems before proceeding.')
|
|
|
|
cli.log.info('{fg_blue}Check out the FAQ (https://docs.qmk.fm/#/faq_build) or join the QMK Discord (https://discord.gg/Uq7gcHh) for help.')
|
|
|
|
return 2
|