From 1776bda7eb05aa51d1091eb8c2a38f3a0d1ac26f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tadej=20Borov=C5=A1ak?= Date: Sat, 28 Nov 2020 22:35:23 +0100 Subject: [PATCH 1/4] Remove unused code from the logger module When we removed custom logging handlers, we left behind a few helper classes that we are not using anymore. This commit finishes the job of removing custom bits from the codebase. --- src/molecule/logger.py | 24 ------------------------ 1 file changed, 24 deletions(-) diff --git a/src/molecule/logger.py b/src/molecule/logger.py index 801747cf7..8bb15dcaf 100644 --- a/src/molecule/logger.py +++ b/src/molecule/logger.py @@ -32,30 +32,6 @@ from molecule.console import console, should_do_markup, theme from molecule.text import underscore -SUCCESS = 100 -OUT = 101 - - -class LogFilter(logging.Filter): - """A custom log filter which excludes log messages above the logged level.""" - - def __init__(self, level): - """Construct LogFilter.""" - self.__level = level - - def filter(self, logRecord): # pragma: no cover - # https://docs.python.org/3/library/logging.html#logrecord-attributes - return logRecord.levelno <= self.__level - - -class TrailingNewlineFormatter(logging.Formatter): - """A custom logging formatter which removes additional newlines from messages.""" - - def format(self, record): - if record.msg: - record.msg = record.msg.rstrip() - return super(TrailingNewlineFormatter, self).format(record) - @lru_cache() def get_logger(name=None) -> logging.Logger: From f4cf6d387b203cc121aebaef3e34b5b4e8205b07 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tadej=20Borov=C5=A1ak?= Date: Sat, 28 Nov 2020 23:55:10 +0100 Subject: [PATCH 2/4] Move logging to more standard layout The main purpose of changes in current commit is to centralize the logger configuration. Previously, molecule configured each and every logger, creating new handler for each one, which made little sense. In the new implementation, we only configure the root molecule logger. All children logger instances inherit the configuration, making away with duplication. With our logging refactor, it also became feasible to use Python's built-in logging facilities as instructed in the official docs. Do note that we left the get_logger function in the logger module because that piece of code is used by various molecule plugins (for example, drivers) to obtain the properly configured logger instance. But we again made sure we just nest the logger below the molecule root logger and let it inherit the configuration. --- src/molecule/api.py | 4 +-- src/molecule/command/base.py | 3 +- src/molecule/command/check.py | 5 +-- src/molecule/command/cleanup.py | 5 +-- src/molecule/command/converge.py | 5 +-- src/molecule/command/create.py | 5 +-- src/molecule/command/dependency.py | 5 +-- src/molecule/command/destroy.py | 5 +-- src/molecule/command/drivers.py | 6 ++-- src/molecule/command/idempotence.py | 5 +-- src/molecule/command/init/base.py | 5 +-- src/molecule/command/init/init.py | 5 +-- src/molecule/command/init/role.py | 5 +-- src/molecule/command/init/scenario.py | 5 +-- src/molecule/command/lint.py | 5 +-- src/molecule/command/list.py | 6 ++-- src/molecule/command/login.py | 5 +-- src/molecule/command/matrix.py | 6 ++-- src/molecule/command/prepare.py | 5 +-- src/molecule/command/reset.py | 5 +-- src/molecule/command/side_effect.py | 5 +-- src/molecule/command/syntax.py | 5 +-- src/molecule/command/test.py | 5 +-- src/molecule/command/verify.py | 5 +-- src/molecule/config.py | 5 +-- .../dependency/ansible_galaxy/base.py | 5 +-- .../dependency/ansible_galaxy/collections.py | 5 +-- .../dependency/ansible_galaxy/roles.py | 5 +-- src/molecule/dependency/base.py | 4 +-- src/molecule/dependency/shell.py | 5 +-- src/molecule/driver/delegated.py | 6 ++-- src/molecule/logger.py | 32 ++++++++++++------- src/molecule/platforms.py | 6 ++-- src/molecule/provisioner/ansible.py | 5 +-- src/molecule/provisioner/ansible_playbook.py | 7 ++-- src/molecule/provisioner/ansible_playbooks.py | 5 +-- src/molecule/scenario.py | 5 +-- src/molecule/scenarios.py | 5 +-- src/molecule/shell.py | 11 +++++++ src/molecule/state.py | 5 +-- src/molecule/test/conftest.py | 4 +-- src/molecule/util.py | 4 +-- src/molecule/verifier/ansible.py | 5 +-- src/molecule/verifier/testinfra.py | 5 +-- 44 files changed, 159 insertions(+), 95 deletions(-) diff --git a/src/molecule/api.py b/src/molecule/api.py index 5c9223fc3..52931e397 100644 --- a/src/molecule/api.py +++ b/src/molecule/api.py @@ -1,16 +1,16 @@ """Molecule API Module.""" +import logging import traceback from collections import UserList import pluggy -from molecule import logger from molecule.driver.base import Driver # noqa from molecule.util import lru_cache from molecule.verifier.base import Verifier # noqa -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) class UserListMap(UserList): diff --git a/src/molecule/command/base.py b/src/molecule/command/base.py index 792105cfd..02ea3885d 100644 --- a/src/molecule/command/base.py +++ b/src/molecule/command/base.py @@ -22,6 +22,7 @@ import abc import collections import glob +import logging import os import shutil from typing import Any, Callable @@ -33,7 +34,7 @@ from molecule import config, logger, text, util from molecule.console import should_do_markup -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) MOLECULE_GLOB = os.environ.get("MOLECULE_GLOB", "molecule/*/molecule.yml") MOLECULE_DEFAULT_SCENARIO_NAME = "default" diff --git a/src/molecule/command/check.py b/src/molecule/command/check.py index 57f639602..fb664b917 100644 --- a/src/molecule/command/check.py +++ b/src/molecule/command/check.py @@ -19,14 +19,15 @@ # DEALINGS IN THE SOFTWARE. """Check Command Module.""" +import logging import os import click -from molecule import logger, util +from molecule import util from molecule.command import base -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) MOLECULE_PARALLEL = os.environ.get("MOLECULE_PARALLEL", False) diff --git a/src/molecule/command/cleanup.py b/src/molecule/command/cleanup.py index d310b7964..a57e58f82 100644 --- a/src/molecule/command/cleanup.py +++ b/src/molecule/command/cleanup.py @@ -19,12 +19,13 @@ # DEALINGS IN THE SOFTWARE. """Cleanup Command Module.""" +import logging + import click -from molecule import logger from molecule.command import base -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) class Cleanup(base.Base): diff --git a/src/molecule/command/converge.py b/src/molecule/command/converge.py index 7e680e2c2..9818a85fb 100644 --- a/src/molecule/command/converge.py +++ b/src/molecule/command/converge.py @@ -19,12 +19,13 @@ # DEALINGS IN THE SOFTWARE. """Converge Command Module.""" +import logging + import click -from molecule import logger from molecule.command import base -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) class Converge(base.Base): diff --git a/src/molecule/command/create.py b/src/molecule/command/create.py index 6b44c29d4..f90e104b0 100644 --- a/src/molecule/command/create.py +++ b/src/molecule/command/create.py @@ -19,14 +19,15 @@ # DEALINGS IN THE SOFTWARE. """Create Command Module.""" +import logging + import click -from molecule import logger from molecule.api import drivers from molecule.command import base from molecule.config import DEFAULT_DRIVER -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) class Create(base.Base): diff --git a/src/molecule/command/dependency.py b/src/molecule/command/dependency.py index 6932ae3be..2ed9a04c2 100644 --- a/src/molecule/command/dependency.py +++ b/src/molecule/command/dependency.py @@ -19,12 +19,13 @@ # DEALINGS IN THE SOFTWARE. """Dependency Command Module.""" +import logging + import click -from molecule import logger from molecule.command import base -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) class Dependency(base.Base): diff --git a/src/molecule/command/destroy.py b/src/molecule/command/destroy.py index 90afa4346..5798dd5e5 100644 --- a/src/molecule/command/destroy.py +++ b/src/molecule/command/destroy.py @@ -19,16 +19,17 @@ # DEALINGS IN THE SOFTWARE. """Destroy Command Module.""" +import logging import os import click -from molecule import logger, util +from molecule import util from molecule.api import drivers from molecule.command import base from molecule.config import DEFAULT_DRIVER -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) MOLECULE_PARALLEL = os.environ.get("MOLECULE_PARALLEL", False) diff --git a/src/molecule/command/drivers.py b/src/molecule/command/drivers.py index 437bf4e96..ceaca1a08 100644 --- a/src/molecule/command/drivers.py +++ b/src/molecule/command/drivers.py @@ -21,15 +21,17 @@ from __future__ import print_function +import logging + import click from rich import box from rich.table import Table -from molecule import api, logger +from molecule import api from molecule.command import base from molecule.console import console -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) @base.click_command_ex() diff --git a/src/molecule/command/idempotence.py b/src/molecule/command/idempotence.py index 43cab4d47..48bb9d92f 100644 --- a/src/molecule/command/idempotence.py +++ b/src/molecule/command/idempotence.py @@ -19,15 +19,16 @@ # DEALINGS IN THE SOFTWARE. """Idempotence Command Module.""" +import logging import re import click -from molecule import logger, util +from molecule import util from molecule.command import base from molecule.text import strip_ansi_escape -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) class Idempotence(base.Base): diff --git a/src/molecule/command/init/base.py b/src/molecule/command/init/base.py index afe574d43..fc3d62e6c 100644 --- a/src/molecule/command/init/base.py +++ b/src/molecule/command/init/base.py @@ -20,14 +20,15 @@ """Base class used by init command.""" import abc +import logging import os import cookiecutter import cookiecutter.main -from molecule import logger, util +from molecule import util -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) class Base(object): diff --git a/src/molecule/command/init/init.py b/src/molecule/command/init/init.py index 47f8656be..eb53deb4f 100644 --- a/src/molecule/command/init/init.py +++ b/src/molecule/command/init/init.py @@ -19,11 +19,12 @@ # DEALINGS IN THE SOFTWARE. """Base class used by init command.""" -from molecule import logger +import logging + from molecule.command import base from molecule.command.init import role, scenario -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) @base.click_group_ex() # type: ignore diff --git a/src/molecule/command/init/role.py b/src/molecule/command/init/role.py index 8dfcb1b3a..1fc9df2af 100644 --- a/src/molecule/command/init/role.py +++ b/src/molecule/command/init/role.py @@ -19,16 +19,17 @@ # DEALINGS IN THE SOFTWARE. """Base class used by init role command.""" +import logging import os import click -from molecule import api, logger, util +from molecule import api, util from molecule.command import base as command_base from molecule.command.init import base from molecule.config import DEFAULT_DRIVER -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) class Role(base.Base): diff --git a/src/molecule/command/init/scenario.py b/src/molecule/command/init/scenario.py index e27bdb4e9..8f168fb5e 100644 --- a/src/molecule/command/init/scenario.py +++ b/src/molecule/command/init/scenario.py @@ -19,17 +19,18 @@ # DEALINGS IN THE SOFTWARE. """Base class used by init scenario command.""" +import logging import os from typing import Dict import click -from molecule import api, config, logger, util +from molecule import api, config, util from molecule.command import base as command_base from molecule.command.init import base from molecule.config import DEFAULT_DRIVER -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) class Scenario(base.Base): diff --git a/src/molecule/command/lint.py b/src/molecule/command/lint.py index 3d050b619..ec3c1538d 100644 --- a/src/molecule/command/lint.py +++ b/src/molecule/command/lint.py @@ -19,14 +19,15 @@ # DEALINGS IN THE SOFTWARE. """Lint Command Module.""" +import logging import os import click -from molecule import logger, util +from molecule import util from molecule.command import base -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) class Lint(base.Base): diff --git a/src/molecule/command/list.py b/src/molecule/command/list.py index 76ff1419a..0e0308b8a 100644 --- a/src/molecule/command/list.py +++ b/src/molecule/command/list.py @@ -21,17 +21,19 @@ from __future__ import print_function +import logging + import click from rich import box from rich.syntax import Syntax from rich.table import Table -from molecule import logger, scenarios, text, util +from molecule import scenarios, text, util from molecule.command import base from molecule.console import console from molecule.status import Status -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) class List(base.Base): diff --git a/src/molecule/command/login.py b/src/molecule/command/login.py index 660b3e521..712897011 100644 --- a/src/molecule/command/login.py +++ b/src/molecule/command/login.py @@ -19,15 +19,16 @@ # DEALINGS IN THE SOFTWARE. """Login Command Module.""" +import logging import os from subprocess import run import click -from molecule import logger, scenarios, util +from molecule import scenarios, util from molecule.command import base -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) class Login(base.Base): diff --git a/src/molecule/command/matrix.py b/src/molecule/command/matrix.py index 2e3f4fcfe..93d76483b 100644 --- a/src/molecule/command/matrix.py +++ b/src/molecule/command/matrix.py @@ -19,12 +19,14 @@ # DEALINGS IN THE SOFTWARE. """Matrix Command Module.""" +import logging + import click -from molecule import logger, scenarios +from molecule import scenarios from molecule.command import base -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) class Matrix(base.Base): diff --git a/src/molecule/command/prepare.py b/src/molecule/command/prepare.py index 81d7c52af..ba824e874 100644 --- a/src/molecule/command/prepare.py +++ b/src/molecule/command/prepare.py @@ -19,14 +19,15 @@ # DEALINGS IN THE SOFTWARE. """Prepare Command Module.""" +import logging + import click -from molecule import logger from molecule.api import drivers from molecule.command import base from molecule.config import DEFAULT_DRIVER -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) class Prepare(base.Base): diff --git a/src/molecule/command/reset.py b/src/molecule/command/reset.py index e894aa908..cbebf96fb 100644 --- a/src/molecule/command/reset.py +++ b/src/molecule/command/reset.py @@ -19,13 +19,14 @@ # DEALINGS IN THE SOFTWARE. """Lint Command Module.""" +import logging + import click -from molecule import logger from molecule.api import drivers from molecule.command import base -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) @base.click_command_ex() diff --git a/src/molecule/command/side_effect.py b/src/molecule/command/side_effect.py index dc19cbe71..82ea65407 100644 --- a/src/molecule/command/side_effect.py +++ b/src/molecule/command/side_effect.py @@ -19,12 +19,13 @@ # DEALINGS IN THE SOFTWARE. """Side-effect Command Module.""" +import logging + import click -from molecule import logger from molecule.command import base -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) class SideEffect(base.Base): diff --git a/src/molecule/command/syntax.py b/src/molecule/command/syntax.py index 9b59b2b8c..c982d615f 100644 --- a/src/molecule/command/syntax.py +++ b/src/molecule/command/syntax.py @@ -19,12 +19,13 @@ # DEALINGS IN THE SOFTWARE. """Syntax Command Module.""" +import logging + import click -from molecule import logger from molecule.command import base -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) class Syntax(base.Base): diff --git a/src/molecule/command/test.py b/src/molecule/command/test.py index b2dc49d89..18109e3d4 100644 --- a/src/molecule/command/test.py +++ b/src/molecule/command/test.py @@ -19,16 +19,17 @@ # DEALINGS IN THE SOFTWARE. """Test Command Module.""" +import logging import os import click -from molecule import logger, util +from molecule import util from molecule.api import drivers from molecule.command import base from molecule.config import DEFAULT_DRIVER -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) MOLECULE_PARALLEL = os.environ.get("MOLECULE_PARALLEL", False) diff --git a/src/molecule/command/verify.py b/src/molecule/command/verify.py index fcf428bba..667965006 100644 --- a/src/molecule/command/verify.py +++ b/src/molecule/command/verify.py @@ -19,12 +19,13 @@ # DEALINGS IN THE SOFTWARE. """Verify Command Module.""" +import logging + import click -from molecule import logger from molecule.command import base -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) class Verify(base.Base): diff --git a/src/molecule/config.py b/src/molecule/config.py index 0eae98fd1..21361b52a 100644 --- a/src/molecule/config.py +++ b/src/molecule/config.py @@ -21,20 +21,21 @@ import copy import functools +import logging import os from typing import Callable, MutableMapping, TypeVar from uuid import uuid4 from packaging.version import Version -from molecule import api, interpolation, logger, platforms, scenario, state, util +from molecule import api, interpolation, platforms, scenario, state, util from molecule.constants import RC_SETUP_ERROR from molecule.dependency import ansible_galaxy, shell from molecule.model import schema_v3 from molecule.provisioner import ansible from molecule.util import boolean, lru_cache, run_command, sysexit -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) MOLECULE_DEBUG = boolean(os.environ.get("MOLECULE_DEBUG", "False")) MOLECULE_VERBOSITY = int(os.environ.get("MOLECULE_VERBOSITY", 0)) MOLECULE_DIRECTORY = "molecule" diff --git a/src/molecule/dependency/ansible_galaxy/base.py b/src/molecule/dependency/ansible_galaxy/base.py index 37326a439..753bd4e4b 100644 --- a/src/molecule/dependency/ansible_galaxy/base.py +++ b/src/molecule/dependency/ansible_galaxy/base.py @@ -21,12 +21,13 @@ import abc import copy +import logging import os -from molecule import logger, util +from molecule import util from molecule.dependency import base -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) class AnsibleGalaxyBase(base.Base): diff --git a/src/molecule/dependency/ansible_galaxy/collections.py b/src/molecule/dependency/ansible_galaxy/collections.py index 47f57ff01..1f20f3b8f 100644 --- a/src/molecule/dependency/ansible_galaxy/collections.py +++ b/src/molecule/dependency/ansible_galaxy/collections.py @@ -1,10 +1,11 @@ """Ansible Galaxy dependencies for lists of collections.""" +import logging import os -from molecule import logger, util +from molecule import util from molecule.dependency.ansible_galaxy.base import AnsibleGalaxyBase -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) class Collections(AnsibleGalaxyBase): diff --git a/src/molecule/dependency/ansible_galaxy/roles.py b/src/molecule/dependency/ansible_galaxy/roles.py index 67824a941..b53b8f23b 100644 --- a/src/molecule/dependency/ansible_galaxy/roles.py +++ b/src/molecule/dependency/ansible_galaxy/roles.py @@ -1,10 +1,11 @@ """Ansible Galaxy dependencies for lists of roles.""" +import logging import os -from molecule import logger, util +from molecule import util from molecule.dependency.ansible_galaxy.base import AnsibleGalaxyBase -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) class Roles(AnsibleGalaxyBase): diff --git a/src/molecule/dependency/base.py b/src/molecule/dependency/base.py index 420f312dc..73b2d4510 100644 --- a/src/molecule/dependency/base.py +++ b/src/molecule/dependency/base.py @@ -20,13 +20,13 @@ """Base Dependency Module.""" import abc +import logging import os import time from molecule import constants, util -from molecule.logger import get_logger -LOG = get_logger(__name__) +LOG = logging.getLogger(__name__) class Base(object): diff --git a/src/molecule/dependency/shell.py b/src/molecule/dependency/shell.py index 0e23a4f36..55dcad997 100644 --- a/src/molecule/dependency/shell.py +++ b/src/molecule/dependency/shell.py @@ -19,11 +19,12 @@ # DEALINGS IN THE SOFTWARE. """Shell Dependency Module.""" -from molecule import logger +import logging + from molecule.dependency import base from molecule.util import BakedCommand -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) class Shell(base.Base): diff --git a/src/molecule/driver/delegated.py b/src/molecule/driver/delegated.py index 42c3b4e8f..434db96d3 100644 --- a/src/molecule/driver/delegated.py +++ b/src/molecule/driver/delegated.py @@ -19,10 +19,12 @@ # DEALINGS IN THE SOFTWARE. """Delegated Driver Module.""" -from molecule import logger, util +import logging + +from molecule import util from molecule.api import Driver -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) class Delegated(Driver): diff --git a/src/molecule/logger.py b/src/molecule/logger.py index 8bb15dcaf..62c6ae80c 100644 --- a/src/molecule/logger.py +++ b/src/molecule/logger.py @@ -32,26 +32,36 @@ from molecule.console import console, should_do_markup, theme from molecule.text import underscore +LOG = logging.getLogger(__name__) -@lru_cache() -def get_logger(name=None) -> logging.Logger: - """ - Build a logger with the given name and returns the logger. +LOG_LEVEL_LUT = { + 0: logging.INFO, + 1: logging.DEBUG, +} - :param name: The name for the logger. This is usually the module - name, ``__name__``. - :return: logger object + +def configure() -> None: """ - logger = logging.getLogger(name) # type: logging.Logger - logger.setLevel(logging.DEBUG) + Configure a molecule root logger. + All other loggers will inherit the configuration we set here. + """ + logger = logging.getLogger("molecule") handler = RichHandler( console=LOGGING_CONSOLE, show_time=False, show_path=False, markup=True ) # type: ignore logger.addHandler(handler) logger.propagate = False + logger.setLevel(logging.INFO) - return logger + +def get_logger(name: str) -> logging.Logger: + """ + Return a child logger. + + Returned logger inherits configuration from the molecule logger. + """ + return logging.getLogger("molecule." + name) def github_actions_groups(func: Callable) -> Callable: @@ -154,7 +164,7 @@ def section_logger(func: Callable) -> Callable: @wraps(func) def wrapper(*args, **kwargs): self = args[0] - get_logger().info( + LOG.info( "[info]Running [scenario]%s[/] > [action]%s[/][/]", self._config.scenario.name, underscore(self.__class__.__name__), diff --git a/src/molecule/platforms.py b/src/molecule/platforms.py index 6e7f493f8..bc9e3df71 100644 --- a/src/molecule/platforms.py +++ b/src/molecule/platforms.py @@ -19,9 +19,11 @@ # DEALINGS IN THE SOFTWARE. """PLatforms Module.""" -from molecule import logger, util +import logging -LOG = logger.get_logger(__name__) +from molecule import util + +LOG = logging.getLogger(__name__) class Platforms(object): diff --git a/src/molecule/provisioner/ansible.py b/src/molecule/provisioner/ansible.py index 4d89e5a07..e3ffb5cd0 100644 --- a/src/molecule/provisioner/ansible.py +++ b/src/molecule/provisioner/ansible.py @@ -21,14 +21,15 @@ import collections import copy +import logging import os import shutil -from molecule import logger, util +from molecule import util from molecule.api import drivers from molecule.provisioner import ansible_playbook, ansible_playbooks, base -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) class Ansible(base.Base): diff --git a/src/molecule/provisioner/ansible_playbook.py b/src/molecule/provisioner/ansible_playbook.py index 635638ef0..9d6cd17c0 100644 --- a/src/molecule/provisioner/ansible_playbook.py +++ b/src/molecule/provisioner/ansible_playbook.py @@ -18,9 +18,12 @@ # FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER # DEALINGS IN THE SOFTWARE. """Ansible-Playbook Provisioner Module.""" -from molecule import logger, util -LOG = logger.get_logger(__name__) +import logging + +from molecule import util + +LOG = logging.getLogger(__name__) class AnsiblePlaybook(object): diff --git a/src/molecule/provisioner/ansible_playbooks.py b/src/molecule/provisioner/ansible_playbooks.py index a03209d67..51a8637ef 100644 --- a/src/molecule/provisioner/ansible_playbooks.py +++ b/src/molecule/provisioner/ansible_playbooks.py @@ -21,11 +21,12 @@ from __future__ import absolute_import +import logging import os -from molecule import logger, util +from molecule import util -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) class AnsiblePlaybooks(object): diff --git a/src/molecule/scenario.py b/src/molecule/scenario.py index 037213d7e..f6738fc31 100644 --- a/src/molecule/scenario.py +++ b/src/molecule/scenario.py @@ -21,16 +21,17 @@ import fcntl import fnmatch +import logging import os import shutil from pathlib import Path from time import sleep from typing import Optional -from molecule import logger, scenarios, util +from molecule import scenarios, util from molecule.constants import RC_TIMEOUT -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) class Scenario(object): diff --git a/src/molecule/scenarios.py b/src/molecule/scenarios.py index bd9a8ee32..f8f246e2e 100644 --- a/src/molecule/scenarios.py +++ b/src/molecule/scenarios.py @@ -18,11 +18,12 @@ # FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER # DEALINGS IN THE SOFTWARE. """Scenarios Module.""" +import logging from typing import List -from molecule import logger, util +from molecule import util -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) class Scenarios(object): diff --git a/src/molecule/shell.py b/src/molecule/shell.py index 7e13e4980..1eb64da9f 100644 --- a/src/molecule/shell.py +++ b/src/molecule/shell.py @@ -35,6 +35,17 @@ click_completion.init() +# Setup logging. This location of initialization is not ideal, but the code +# structure does not give us much choice because config file lookup down below +# uses logging facilities. Do note that verbosity level set by the +# command-line flags does not affect the things that execute before the main +# method in this file that parses the command line arguments. +# +# It would be ideal if we could get a chance at parsing CLI args before any of +# the real code executes, but this is really hard to do while using click for +# constructing out CLI API. +logger.configure() + LOCAL_CONFIG_SEARCH = ".config/molecule/config.yml" LOCAL_CONFIG = lookup_config_file(LOCAL_CONFIG_SEARCH) diff --git a/src/molecule/state.py b/src/molecule/state.py index 39d8a0545..4a3a639b8 100644 --- a/src/molecule/state.py +++ b/src/molecule/state.py @@ -19,11 +19,12 @@ # DEALINGS IN THE SOFTWARE. """State Module.""" +import logging import os -from molecule import logger, util +from molecule import util -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) VALID_KEYS = ["created", "converged", "driver", "prepared", "run_uuid", "is_parallel"] diff --git a/src/molecule/test/conftest.py b/src/molecule/test/conftest.py index 3e6de6568..cdfa00f87 100644 --- a/src/molecule/test/conftest.py +++ b/src/molecule/test/conftest.py @@ -25,11 +25,9 @@ import pytest -from molecule import config, logger +from molecule import config from molecule.scenario import ephemeral_directory -LOG = logger.get_logger(__name__) - def is_subset(subset, superset): # Checks if first dict is a subset of the second one diff --git a/src/molecule/util.py b/src/molecule/util.py index 0bd91b516..413c8fff5 100644 --- a/src/molecule/util.py +++ b/src/molecule/util.py @@ -23,6 +23,7 @@ import contextlib import copy import fnmatch +import logging import os import re import sys @@ -38,9 +39,8 @@ from molecule.console import console from molecule.constants import MOLECULE_HEADER -from molecule.logger import get_logger -LOG = get_logger(__name__) +LOG = logging.getLogger(__name__) class SafeDumper(yaml.SafeDumper): diff --git a/src/molecule/verifier/ansible.py b/src/molecule/verifier/ansible.py index ecf4ef437..950e9c913 100644 --- a/src/molecule/verifier/ansible.py +++ b/src/molecule/verifier/ansible.py @@ -19,12 +19,13 @@ # DEALINGS IN THE SOFTWARE. """Ansible Verifier Module.""" +import logging import os -from molecule import logger, util +from molecule import util from molecule.api import Verifier -log = logger.get_logger(__name__) +log = logging.getLogger(__name__) class Ansible(Verifier): diff --git a/src/molecule/verifier/testinfra.py b/src/molecule/verifier/testinfra.py index a159ab6e7..1413afaf8 100644 --- a/src/molecule/verifier/testinfra.py +++ b/src/molecule/verifier/testinfra.py @@ -20,12 +20,13 @@ """Testinfra Verifier Module.""" import glob +import logging import os -from molecule import logger, util +from molecule import util from molecule.api import Verifier -LOG = logger.get_logger(__name__) +LOG = logging.getLogger(__name__) class Testinfra(Verifier): From 1e90dfefa0530379442a68a46ded1886b72de932 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tadej=20Borov=C5=A1ak?= Date: Sun, 29 Nov 2020 22:01:22 +0100 Subject: [PATCH 3/4] Remove Python 2 remnants from the shell module --- src/molecule/shell.py | 10 ---------- 1 file changed, 10 deletions(-) diff --git a/src/molecule/shell.py b/src/molecule/shell.py index 1eb64da9f..f13f45af1 100644 --- a/src/molecule/shell.py +++ b/src/molecule/shell.py @@ -126,16 +126,6 @@ def main(ctx, debug, verbose, base_config, env_file): # pragma: no cover os.environ["ANSIBLE_VERBOSITY"] = str(verbose) -# runtime environment checks to avoid delayed failures -if sys.version_info[0] > 2: - try: - if pkg_resources.get_distribution("futures"): - raise SystemExit( - "FATAL: futures package found, this package should not be installed in a Python 3 environment, please remove it. See https://github.com/agronholm/pythonfutures/issues/90" - ) - except pkg_resources.DistributionNotFound: - pass - main.add_command(command.cleanup.cleanup) main.add_command(command.check.check) main.add_command(command.converge.converge) From c200b9e1b7a44949559110b99b817f36947d653f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tadej=20Borov=C5=A1ak?= Date: Sat, 28 Nov 2020 23:55:39 +0100 Subject: [PATCH 4/4] Enable log level selection using the CLI flags Up until now, we ignored the verbosity setting and only used it to control the verbosity of the Ansible subprocess. This commit reuses the verbosity flag to also control the molecule verbosity. --- src/molecule/logger.py | 14 ++++++++++++++ src/molecule/shell.py | 3 ++- 2 files changed, 16 insertions(+), 1 deletion(-) diff --git a/src/molecule/logger.py b/src/molecule/logger.py index 62c6ae80c..c55b6f0cd 100644 --- a/src/molecule/logger.py +++ b/src/molecule/logger.py @@ -55,6 +55,20 @@ def configure() -> None: logger.setLevel(logging.INFO) +def set_log_level(log_level: int, debug: bool) -> None: + """ + Set logging level. + + :param log_level: verbosity control (0 - INFO, 1 - DEBUG) + :param debug: debug mode indicator + """ + # If we get verbosity level > 1, we just use debug because this is the + # most detailed log level we have. + if debug: + log_level = 1 # DEBUG from the LOG_LEVEL_LUT + logging.getLogger("molecule").setLevel(LOG_LEVEL_LUT.get(log_level, logging.DEBUG)) + + def get_logger(name: str) -> logging.Logger: """ Return a child logger. diff --git a/src/molecule/shell.py b/src/molecule/shell.py index f13f45af1..76eb7c475 100644 --- a/src/molecule/shell.py +++ b/src/molecule/shell.py @@ -26,7 +26,7 @@ import pkg_resources import molecule -from molecule import command +from molecule import command, logger from molecule.api import drivers from molecule.command.base import click_group_ex from molecule.config import MOLECULE_DEBUG, MOLECULE_VERBOSITY, ansible_version @@ -122,6 +122,7 @@ def main(ctx, debug, verbose, base_config, env_file): # pragma: no cover ctx.obj["args"]["base_config"] = base_config ctx.obj["args"]["env_file"] = env_file + logger.set_log_level(verbose, debug) if verbose: os.environ["ANSIBLE_VERBOSITY"] = str(verbose)