コード例 #1
0
ファイル: check.py プロジェクト: greenbone/autohooks
def check_pre_commit_hook(
    term: Terminal, pre_commit_hook: PreCommitHook
) -> None:
    if pre_commit_hook.exists():
        if pre_commit_hook.is_autohooks_pre_commit_hook():
            term.ok('autohooks pre-commit hook is active.')

            if pre_commit_hook.is_current_autohooks_pre_commit_hook():
                term.ok('autohooks pre-commit hook is up-to-date.')
            else:
                term.warning(
                    'autohooks pre-commit hook is outdated. Please run '
                    '\'autohooks activate --force\' to update your pre-commit '
                    'hook.'
                )

            hook_mode = pre_commit_hook.read_mode()
            if hook_mode == Mode.UNKNOWN:
                term.warning(
                    f'Unknown autohooks mode in {str(pre_commit_hook)}. '
                    f'Falling back to "{str(hook_mode.get_effective_mode())}" '
                    'mode.'
                )
        else:
            term.error(
                'autohooks pre-commit hook is not active. But a different '
                f'pre-commit hook has been found at {str(pre_commit_hook)}.'
            )

    else:
        term.error(
            'autohooks pre-commit hook not active. Please run \'autohooks '
            'activate\'.'
        )
コード例 #2
0
def install_hooks(term: Terminal, args: Namespace) -> None:
    pre_commit_hook = PreCommitHook()
    pyproject_toml = get_pyproject_toml_path()
    config = load_config_from_pyproject_toml(pyproject_toml)

    if pre_commit_hook.exists() and not args.force:
        term.ok('autohooks pre-commit hook is already installed at {}.'.format(
            str(pre_commit_hook)))
        with term.indent():
            term.print()
            term.info(
                "Run 'autohooks activate --force' to override the current "
                "installed pre-commit hook.")
            term.info(
                "Run 'autohooks check' to validate the current status of "
                "the installed pre-commit hook.")
    else:
        if not config.is_autohooks_enabled():
            term.warning('autohooks is not enabled in your {} file. '
                         'Run \'autohooks check\' for more '
                         'details.'.format(str(pyproject_toml)))

        if args.mode:
            mode = Mode.from_string(args.mode)
        else:
            mode = config.get_mode()

        pre_commit_hook.write(mode=mode)

        term.ok(
            'autohooks pre-commit hook installed at {} using {} mode.'.format(
                str(pre_commit_hook), str(mode.get_effective_mode())))
コード例 #3
0
ファイル: install.py プロジェクト: oadiazm/autohooks
 def install_git_hook(self) -> None:
     try:
         pre_commit_hook = PreCommitHook()
         if not pre_commit_hook.exists():
             config = load_config_from_pyproject_toml()
             pre_commit_hook.write(mode=config.get_mode())
     except Exception:  # pylint: disable=broad-except
         pass
コード例 #4
0
ファイル: run.py プロジェクト: y0urself/autohooks
def run() -> int:
    term = Terminal()

    _set_terminal(term)

    config = load_config_from_pyproject_toml()

    pre_commit_hook = PreCommitHook()

    check_hook_is_current(term, pre_commit_hook)

    if config.has_autohooks_config():
        check_hook_mode(term, config.get_mode(), pre_commit_hook.read_mode())

    plugins = get_project_autohooks_plugins_path()
    plugins_dir_name = str(plugins)

    if plugins.is_dir():
        sys.path.append(plugins_dir_name)

    term.bold_info('autohooks => pre-commit')

    with autohooks_module_path(), term.indent():
        for name in config.get_pre_commit_script_names():
            term.info('Running {}'.format(name))

            with term.indent():
                try:
                    plugin = load_plugin(name)
                    if not has_precommit_function(plugin):
                        term.fail(
                            'No precommit function found in plugin {}. '
                            'Your autohooks settings may be invalid.'.format(
                                name))
                        return 1

                    if has_precommit_parameters(plugin):
                        retval = plugin.precommit(config=config.get_config())
                    else:
                        term.warning(
                            'precommit function without kwargs is deprecated. '
                            'Please update {} to a newer version.'.format(
                                name))
                        retval = plugin.precommit()

                    if retval:
                        return retval

                except ImportError as e:
                    term.error('An error occurred while importing pre-commit '
                               'hook {}. {}.'.format(name, e))
                    return 1
                except Exception as e:  # pylint: disable=broad-except
                    term.error('An error occurred while running pre-commit '
                               'hook {}. {}.'.format(name, e))
                    return 1

    return 0
コード例 #5
0
def check_hooks(term: Terminal) -> None:
    pre_commit_hook = PreCommitHook()
    hook_mode = pre_commit_hook.read_mode()

    check_pre_commit_hook(term, pre_commit_hook, hook_mode)

    pyproject_toml = get_pyproject_toml_path()

    check_config(term, pyproject_toml, pre_commit_hook, hook_mode)
コード例 #6
0
    def test_modified_pre_commit_template(self):
        template = PreCommitTemplate()
        rendered = template.render(mode=Mode.PIPENV)
        lines = rendered.split('\n')
        lines[1] = ""
        path = FakeReadPath("\n".join(lines))
        pre_commit_hook = PreCommitHook(path)

        self.assertFalse(
            pre_commit_hook.is_current_autohooks_pre_commit_hook())
コード例 #7
0
ファイル: test_hooks.py プロジェクト: greenbone/autohooks
    def test_poetry_mode(self):
        write_path = Mock()
        pre_commit_hook = PreCommitHook(write_path)
        pre_commit_hook.write(mode=Mode.POETRY)

        write_path.chmod.assert_called_with(0o775)
        self.assertTrue(write_path.write_text.called)

        args, _kwargs = write_path.write_text.call_args
        text = args[0]
        self.assertRegex(text, f'^#!{POETRY_SHEBANG} *')
コード例 #8
0
    def test_pythonpath_mode(self):
        write_path = Mock()
        pre_commit_hook = PreCommitHook(write_path)
        pre_commit_hook.write(mode=Mode.PYTHONPATH)

        write_path.chmod.assert_called_with(0o775)
        self.assertTrue(write_path.write_text.called)

        args, _kwargs = write_path.write_text.call_args
        text = args[0]
        self.assertRegex(text, '^#!{} *'.format(PYTHON3_SHEBANG))
コード例 #9
0
ファイル: test_hooks.py プロジェクト: greenbone/autohooks
    def test_read_version(self):
        template = PreCommitTemplate()
        with tempfile.TemporaryDirectory() as tempdir:
            tmp_hook_path = Path(tempdir) / 'pre-commit-test'
            # Find version using all shebang modes
            for mode in [m for m in Mode if m.value > 0]:
                with open(str(tmp_hook_path), 'w',
                          encoding='utf-8') as tmpfile:
                    tmpfile.write(template.render(mode=mode))
                pre_commit_hook = PreCommitHook(tmp_hook_path)

            self.assertEqual(TEMPLATE_VERSION, pre_commit_hook.read_version())
コード例 #10
0
ファイル: check.py プロジェクト: greenbone/autohooks
def check_hooks(term: Terminal) -> None:
    pre_commit_hook = PreCommitHook()
    check_pre_commit_hook(term, pre_commit_hook)

    pyproject_toml = get_pyproject_toml_path()

    check_config(term, pyproject_toml, pre_commit_hook)
コード例 #11
0
def check_hook_is_current(term: Terminal,
                          pre_commit_hook: PreCommitHook) -> None:
    if not pre_commit_hook.is_current_autohooks_pre_commit_hook():
        term.warning(
            'autohooks pre-commit hook is outdated. Please run '
            '\'autohooks activate --force\' to update your pre-commit '
            'hook.')
コード例 #12
0
    def test_str_conversion(self):
        path = Mock()
        path.__str__ = Mock(return_value="foo")

        pre_commit_hook = PreCommitHook(path)

        self.assertEqual(str(pre_commit_hook), 'foo')
        path.__str__.assert_called_with()
コード例 #13
0
    def test_install(self):
        pre_commit_hook = PreCommitHook()

        self.assertFalse(pre_commit_hook.exists())

        pre_commit_hook.write(mode=Mode.PIPENV)

        self.assertTrue(pre_commit_hook.exists())
コード例 #14
0
    def test_empty_content(self):
        path = FakeReadPath("")
        pre_commit_hook = PreCommitHook(path)

        self.assertEqual(pre_commit_hook.read_version(), -1)
コード例 #15
0
    def test_other_hook(self):
        path = FakeReadPath('foo\nbar')
        pre_commit_hook = PreCommitHook(path)

        self.assertFalse(
            pre_commit_hook.is_current_autohooks_pre_commit_hook())
コード例 #16
0
    def test_pre_commit_template(self):
        template = PreCommitTemplate()
        path = FakeReadPath(template.render(mode=Mode.PIPENV))
        pre_commit_hook = PreCommitHook(path)

        self.assertTrue(pre_commit_hook.is_autohooks_pre_commit_hook())
コード例 #17
0
    def test_pythonpath_mode(self):
        path = FakeReadPath("#!{}".format(PYTHON3_SHEBANG))
        pre_commit_hook = PreCommitHook(path)

        self.assertEqual(pre_commit_hook.read_mode(), Mode.PYTHONPATH)
コード例 #18
0
ファイル: test_hooks.py プロジェクト: greenbone/autohooks
    def test_poetry_multiline_mode(self):
        path = FakeReadPath(f"#!{POETRY_MULTILINE_SHEBANG}")
        pre_commit_hook = PreCommitHook(path)

        self.assertEqual(pre_commit_hook.read_mode(), Mode.POETRY_MULTILINE)
コード例 #19
0
    def test_pipenv_mode(self):
        path = FakeReadPath("#!{}".format(PIPENV_SHEBANG))
        pre_commit_hook = PreCommitHook(path)

        self.assertEqual(pre_commit_hook.read_mode(), Mode.PIPENV)
コード例 #20
0
    def test_poetry_mode(self):
        path = FakeReadPath("#!{}".format(POETRY_SHEBANG))
        pre_commit_hook = PreCommitHook(path)

        self.assertEqual(pre_commit_hook.read_mode(), Mode.POETRY)
コード例 #21
0
    def test_undefined_mode(self):
        path = FakeReadPath("")
        pre_commit_hook = PreCommitHook(path)

        self.assertEqual(pre_commit_hook.read_mode(), Mode.UNDEFINED)
コード例 #22
0
    def test_unknown_mode(self):
        path = FakeReadPath("#!foo")
        pre_commit_hook = PreCommitHook(path)

        self.assertEqual(pre_commit_hook.read_mode(), Mode.UNKNOWN)
コード例 #23
0
    def test_no_meta(self):
        path = FakeReadPath("\n# foo = bar")
        pre_commit_hook = PreCommitHook(path)

        self.assertEqual(pre_commit_hook.read_version(), -1)
コード例 #24
0
    def test_no_toml(self):
        path = FakeReadPath("\n# \n")
        pre_commit_hook = PreCommitHook(path)

        self.assertEqual(pre_commit_hook.read_version(), -1)
コード例 #25
0
def check_config(
    term: Terminal, pyproject_toml: Path, pre_commit_hook: PreCommitHook,
) -> None:
    if not pyproject_toml.exists():
        term.error(
            'Missing {} file. Please add a pyproject.toml file and include '
            'a "{}" section.'.format(str(pyproject_toml), AUTOHOOKS_SECTION)
        )
    else:
        config = load_config_from_pyproject_toml(pyproject_toml)
        if not config.is_autohooks_enabled():
            term.error(
                'autohooks is not enabled in your {} file. Please add '
                'a "{}" section.'.format(str(pyproject_toml), AUTOHOOKS_SECTION)
            )
        elif pre_commit_hook.exists():
            config_mode = config.get_mode()
            hook_mode = pre_commit_hook.read_mode()

            if config_mode == Mode.UNDEFINED:
                term.warning(
                    'autohooks mode is not defined in {}.'.format(
                        str(pyproject_toml)
                    )
                )
            elif config_mode == Mode.UNKNOWN:
                term.warning(
                    'Unknown autohooks mode in {}.'.format(str(pyproject_toml))
                )

            if (
                config_mode.get_effective_mode()
                != hook_mode.get_effective_mode()
            ):
                term.warning(
                    'autohooks mode "{}" in pre-commit hook {} differs from '
                    'mode "{}" in {}.'.format(
                        str(hook_mode),
                        str(pre_commit_hook),
                        str(config_mode),
                        str(pyproject_toml),
                    )
                )

            term.info(
                'Using autohooks mode "{}".'.format(
                    str(hook_mode.get_effective_mode())
                )
            )

            plugins = config.get_pre_commit_script_names()
            if not plugins:
                term.error(
                    'No autohooks plugin is activated in {} for your pre '
                    'commit hook. Please add a '
                    '"pre-commit = [plugin1, plugin2]" '
                    'setting.'.format(str(pyproject_toml))
                )
            else:
                with autohooks_module_path():
                    for name in plugins:
                        try:
                            plugin = load_plugin(name)
                            if not has_precommit_function(plugin):
                                term.error(
                                    'Plugin "{}" has no precommit function. '
                                    'The function is required to run the '
                                    'plugin as git pre commit hook.'.format(
                                        name
                                    )
                                )
                            elif not has_precommit_parameters(plugin):
                                term.warning(
                                    'Plugin "{}" uses a deprecated signature '
                                    'for its precommit function. It is missing '
                                    'the **kwargs parameter.'.format(name)
                                )
                            else:
                                term.ok(
                                    'Plugin "{}" active and loadable.'.format(
                                        name
                                    )
                                )
                        except ImportError as e:
                            term.error(
                                '"{}" is not a valid autohooks '
                                'plugin. {}'.format(name, e)
                            )
コード例 #26
0
    def test_read_version(self):
        path = FakeReadPath("\n# meta = {version=123}")
        pre_commit_hook = PreCommitHook(path)

        self.assertEqual(pre_commit_hook.read_version(), 123)
コード例 #27
0
ファイル: check.py プロジェクト: greenbone/autohooks
def check_config(
    term: Terminal,
    pyproject_toml: Path,
    pre_commit_hook: PreCommitHook,
) -> None:
    if not pyproject_toml.exists():
        term.error(
            f'Missing {str(pyproject_toml)} file. Please add a pyproject.toml '
            f'file and include a "{AUTOHOOKS_SECTION}" section.'
        )
    else:
        config = load_config_from_pyproject_toml(pyproject_toml)
        if not config.is_autohooks_enabled():
            term.error(
                f'autohooks is not enabled in your {str(pyproject_toml)} file.'
                f' Please add a "{AUTOHOOKS_SECTION}" section.'
            )
        elif pre_commit_hook.exists():
            config_mode = config.get_mode()
            hook_mode = pre_commit_hook.read_mode()

            if config_mode == Mode.UNDEFINED:
                term.warning(
                    f'autohooks mode is not defined in {str(pyproject_toml)}.'
                )
            elif config_mode == Mode.UNKNOWN:
                term.warning(
                    f'Unknown autohooks mode in {str(pyproject_toml)}.'
                )

            if (
                config_mode.get_effective_mode()
                != hook_mode.get_effective_mode()
            ):
                term.warning(
                    f'autohooks mode "{str(hook_mode)}" in pre-commit '
                    f'hook {str(pre_commit_hook)} differs from '
                    f'mode "{str(config_mode)}" in {str(pyproject_toml)}.'
                )

            term.info(
                f'Using autohooks mode "{str(hook_mode.get_effective_mode())}".'
            )

            plugins = config.get_pre_commit_script_names()
            if not plugins:
                term.error(
                    'No autohooks plugin is activated in '
                    f'{str(pyproject_toml)} for your pre commit hook. Please '
                    'add a "pre-commit = [plugin1, plugin2]" setting.'
                )
            else:
                with autohooks_module_path():
                    for name in plugins:
                        try:
                            plugin = load_plugin(name)
                            if not has_precommit_function(plugin):
                                term.error(
                                    f'Plugin "{name}" has no precommit '
                                    'function. The function is required to run'
                                    ' the plugin as git pre commit hook.'
                                )
                            elif not has_precommit_parameters(plugin):
                                term.warning(
                                    f'Plugin "{name}" uses a deprecated '
                                    'signature for its precommit function. It '
                                    'is missing the **kwargs parameter.'
                                )
                            else:
                                term.ok(f'Plugin "{name}" active and loadable.')
                        except ImportError as e:
                            term.error(
                                f'"{name}" is not a valid autohooks '
                                f'plugin. {e}'
                            )