mirror of
https://github.com/pre-commit/pre-commit.git
synced 2026-02-17 08:14:42 +04:00
Move PrefixedCommandRunner -> Prefix
This commit is contained in:
parent
c751f629a6
commit
7d87da8acd
23 changed files with 270 additions and 372 deletions
|
|
@ -14,7 +14,6 @@ import six
|
|||
import pre_commit.constants as C
|
||||
from pre_commit import output
|
||||
from pre_commit.logging_handler import add_logging_handler
|
||||
from pre_commit.prefixed_command_runner import PrefixedCommandRunner
|
||||
from pre_commit.runner import Runner
|
||||
from pre_commit.store import Store
|
||||
from pre_commit.util import cmd_output
|
||||
|
|
@ -155,11 +154,6 @@ def store(tempdir_factory):
|
|||
yield Store(os.path.join(tempdir_factory.get(), '.pre-commit'))
|
||||
|
||||
|
||||
@pytest.yield_fixture
|
||||
def cmd_runner(tempdir_factory):
|
||||
yield PrefixedCommandRunner(tempdir_factory.get())
|
||||
|
||||
|
||||
@pytest.yield_fixture
|
||||
def runner_with_mocked_store(mock_out_store_directory):
|
||||
yield Runner('/', C.CONFIG_FILE)
|
||||
|
|
|
|||
|
|
@ -11,7 +11,7 @@ from pre_commit.languages.all import languages
|
|||
@pytest.mark.parametrize('language', all_languages)
|
||||
def test_install_environment_argspec(language):
|
||||
expected_argspec = inspect.ArgSpec(
|
||||
args=['repo_cmd_runner', 'version', 'additional_dependencies'],
|
||||
args=['prefix', 'version', 'additional_dependencies'],
|
||||
varargs=None, keywords=None, defaults=None,
|
||||
)
|
||||
argspec = inspect.getargspec(languages[language].install_environment)
|
||||
|
|
@ -26,7 +26,7 @@ def test_ENVIRONMENT_DIR(language):
|
|||
@pytest.mark.parametrize('language', all_languages)
|
||||
def test_run_hook_argpsec(language):
|
||||
expected_argspec = inspect.ArgSpec(
|
||||
args=['repo_cmd_runner', 'hook', 'file_args'],
|
||||
args=['prefix', 'hook', 'file_args'],
|
||||
varargs=None, keywords=None, defaults=None,
|
||||
)
|
||||
argspec = inspect.getargspec(languages[language].run_hook)
|
||||
|
|
@ -45,7 +45,7 @@ def test_get_default_version_argspec(language):
|
|||
@pytest.mark.parametrize('language', all_languages)
|
||||
def test_healthy_argspec(language):
|
||||
expected_argspec = inspect.ArgSpec(
|
||||
args=['repo_cmd_runner', 'language_version'],
|
||||
args=['prefix', 'language_version'],
|
||||
varargs=None, keywords=None, defaults=None,
|
||||
)
|
||||
argspec = inspect.getargspec(languages[language].healthy)
|
||||
|
|
|
|||
|
|
@ -1,39 +1,42 @@
|
|||
from __future__ import unicode_literals
|
||||
|
||||
import os.path
|
||||
import pipes
|
||||
|
||||
from pre_commit.languages.ruby import _install_rbenv
|
||||
from pre_commit.prefix import Prefix
|
||||
from pre_commit.util import cmd_output
|
||||
from testing.util import xfailif_windows_no_ruby
|
||||
|
||||
|
||||
@xfailif_windows_no_ruby
|
||||
def test_install_rbenv(cmd_runner):
|
||||
_install_rbenv(cmd_runner)
|
||||
def test_install_rbenv(tempdir_factory):
|
||||
prefix = Prefix(tempdir_factory.get())
|
||||
_install_rbenv(prefix)
|
||||
# Should have created rbenv directory
|
||||
assert os.path.exists(cmd_runner.path('rbenv-default'))
|
||||
assert os.path.exists(prefix.path('rbenv-default'))
|
||||
# We should have created our `activate` script
|
||||
activate_path = cmd_runner.path('rbenv-default', 'bin', 'activate')
|
||||
activate_path = prefix.path('rbenv-default', 'bin', 'activate')
|
||||
assert os.path.exists(activate_path)
|
||||
|
||||
# Should be able to activate using our script and access rbenv
|
||||
cmd_runner.run(
|
||||
[
|
||||
'bash',
|
||||
'-c',
|
||||
". '{prefix}rbenv-default/bin/activate' && rbenv --help",
|
||||
],
|
||||
cmd_output(
|
||||
'bash', '-c',
|
||||
'. {} && rbenv --help'.format(pipes.quote(prefix.path(
|
||||
'rbenv-default', 'bin', 'activate',
|
||||
))),
|
||||
)
|
||||
|
||||
|
||||
@xfailif_windows_no_ruby
|
||||
def test_install_rbenv_with_version(cmd_runner):
|
||||
_install_rbenv(cmd_runner, version='1.9.3p547')
|
||||
def test_install_rbenv_with_version(tempdir_factory):
|
||||
prefix = Prefix(tempdir_factory.get())
|
||||
_install_rbenv(prefix, version='1.9.3p547')
|
||||
|
||||
# Should be able to activate and use rbenv install
|
||||
cmd_runner.run(
|
||||
[
|
||||
'bash',
|
||||
'-c',
|
||||
". '{prefix}rbenv-1.9.3p547/bin/activate' && rbenv install --help",
|
||||
],
|
||||
cmd_output(
|
||||
'bash', '-c',
|
||||
'. {} && rbenv install --help'.format(pipes.quote(prefix.path(
|
||||
'rbenv-1.9.3p547', 'bin', 'activate',
|
||||
))),
|
||||
)
|
||||
|
|
|
|||
57
tests/prefix_test.py
Normal file
57
tests/prefix_test.py
Normal file
|
|
@ -0,0 +1,57 @@
|
|||
from __future__ import unicode_literals
|
||||
|
||||
import os
|
||||
|
||||
import pytest
|
||||
|
||||
from pre_commit.prefix import Prefix
|
||||
|
||||
|
||||
def norm_slash(*args):
|
||||
return tuple(x.replace('/', os.sep) for x in args)
|
||||
|
||||
|
||||
@pytest.mark.parametrize(
|
||||
('input', 'expected_prefix'), (
|
||||
norm_slash('.', './'),
|
||||
norm_slash('foo', 'foo/'),
|
||||
norm_slash('bar/', 'bar/'),
|
||||
norm_slash('foo/bar', 'foo/bar/'),
|
||||
norm_slash('foo/bar/', 'foo/bar/'),
|
||||
),
|
||||
)
|
||||
def test_init_normalizes_path_endings(input, expected_prefix):
|
||||
instance = Prefix(input)
|
||||
assert instance.prefix_dir == expected_prefix
|
||||
|
||||
|
||||
PATH_TESTS = (
|
||||
norm_slash('foo', '', 'foo'),
|
||||
norm_slash('foo', 'bar', 'foo/bar'),
|
||||
norm_slash('foo/bar', '../baz', 'foo/baz'),
|
||||
norm_slash('./', 'bar', 'bar'),
|
||||
norm_slash('./', '', '.'),
|
||||
norm_slash('/tmp/foo', '/tmp/bar', '/tmp/bar'),
|
||||
)
|
||||
|
||||
|
||||
@pytest.mark.parametrize(('prefix', 'path_end', 'expected_output'), PATH_TESTS)
|
||||
def test_path(prefix, path_end, expected_output):
|
||||
instance = Prefix(prefix)
|
||||
ret = instance.path(path_end)
|
||||
assert ret == expected_output
|
||||
|
||||
|
||||
def test_path_multiple_args():
|
||||
instance = Prefix('foo')
|
||||
ret = instance.path('bar', 'baz')
|
||||
assert ret == os.path.join('foo', 'bar', 'baz')
|
||||
|
||||
|
||||
def test_exists_does_not_exist(tmpdir):
|
||||
assert not Prefix(str(tmpdir)).exists('foo')
|
||||
|
||||
|
||||
def test_exists_does_exist(tmpdir):
|
||||
tmpdir.ensure('foo')
|
||||
assert Prefix(str(tmpdir)).exists('foo')
|
||||
|
|
@ -1,133 +0,0 @@
|
|||
from __future__ import unicode_literals
|
||||
|
||||
import os
|
||||
import subprocess
|
||||
|
||||
import mock
|
||||
import pytest
|
||||
|
||||
from pre_commit.prefixed_command_runner import PrefixedCommandRunner
|
||||
from pre_commit.util import CalledProcessError
|
||||
|
||||
|
||||
def norm_slash(input_tup):
|
||||
return tuple(x.replace('/', os.sep) for x in input_tup)
|
||||
|
||||
|
||||
def test_CalledProcessError_str():
|
||||
error = CalledProcessError(
|
||||
1, [str('git'), str('status')], 0, (str('stdout'), str('stderr')),
|
||||
)
|
||||
assert str(error) == (
|
||||
"Command: ['git', 'status']\n"
|
||||
"Return code: 1\n"
|
||||
"Expected return code: 0\n"
|
||||
"Output: \n"
|
||||
" stdout\n"
|
||||
"Errors: \n"
|
||||
" stderr\n"
|
||||
)
|
||||
|
||||
|
||||
def test_CalledProcessError_str_nooutput():
|
||||
error = CalledProcessError(
|
||||
1, [str('git'), str('status')], 0, (str(''), str('')),
|
||||
)
|
||||
assert str(error) == (
|
||||
"Command: ['git', 'status']\n"
|
||||
"Return code: 1\n"
|
||||
"Expected return code: 0\n"
|
||||
"Output: (none)\n"
|
||||
"Errors: (none)\n"
|
||||
)
|
||||
|
||||
|
||||
@pytest.fixture
|
||||
def popen_mock():
|
||||
popen = mock.Mock(spec=subprocess.Popen)
|
||||
popen.return_value.communicate.return_value = (b'stdout', b'stderr')
|
||||
return popen
|
||||
|
||||
|
||||
@pytest.fixture
|
||||
def makedirs_mock():
|
||||
return mock.Mock(spec=os.makedirs)
|
||||
|
||||
|
||||
@pytest.mark.parametrize(
|
||||
('input', 'expected_prefix'), (
|
||||
norm_slash(('.', './')),
|
||||
norm_slash(('foo', 'foo/')),
|
||||
norm_slash(('bar/', 'bar/')),
|
||||
norm_slash(('foo/bar', 'foo/bar/')),
|
||||
norm_slash(('foo/bar/', 'foo/bar/')),
|
||||
),
|
||||
)
|
||||
def test_init_normalizes_path_endings(input, expected_prefix):
|
||||
input = input.replace('/', os.sep)
|
||||
expected_prefix = expected_prefix.replace('/', os.sep)
|
||||
instance = PrefixedCommandRunner(input)
|
||||
assert instance.prefix_dir == expected_prefix
|
||||
|
||||
|
||||
def test_run_substitutes_prefix(popen_mock, makedirs_mock):
|
||||
instance = PrefixedCommandRunner(
|
||||
'prefix', popen=popen_mock, makedirs=makedirs_mock,
|
||||
)
|
||||
ret = instance.run(['{prefix}bar', 'baz'], retcode=None)
|
||||
popen_mock.assert_called_once_with(
|
||||
(str(os.path.join('prefix', 'bar')), str('baz')),
|
||||
env=None,
|
||||
stdin=subprocess.PIPE,
|
||||
stdout=subprocess.PIPE,
|
||||
stderr=subprocess.PIPE,
|
||||
)
|
||||
assert ret == (popen_mock.return_value.returncode, 'stdout', 'stderr')
|
||||
|
||||
|
||||
PATH_TESTS = (
|
||||
norm_slash(('foo', '', 'foo')),
|
||||
norm_slash(('foo', 'bar', 'foo/bar')),
|
||||
norm_slash(('foo/bar', '../baz', 'foo/baz')),
|
||||
norm_slash(('./', 'bar', 'bar')),
|
||||
norm_slash(('./', '', '.')),
|
||||
norm_slash(('/tmp/foo', '/tmp/bar', '/tmp/bar')),
|
||||
)
|
||||
|
||||
|
||||
@pytest.mark.parametrize(('prefix', 'path_end', 'expected_output'), PATH_TESTS)
|
||||
def test_path(prefix, path_end, expected_output):
|
||||
instance = PrefixedCommandRunner(prefix)
|
||||
ret = instance.path(path_end)
|
||||
assert ret == expected_output
|
||||
|
||||
|
||||
def test_path_multiple_args():
|
||||
instance = PrefixedCommandRunner('foo')
|
||||
ret = instance.path('bar', 'baz')
|
||||
assert ret == os.path.join('foo', 'bar', 'baz')
|
||||
|
||||
|
||||
def test_create_path_if_not_exists(in_tmpdir):
|
||||
instance = PrefixedCommandRunner('foo')
|
||||
assert not os.path.exists('foo')
|
||||
instance._create_path_if_not_exists()
|
||||
assert os.path.exists('foo')
|
||||
|
||||
|
||||
def test_exists_does_not_exist(in_tmpdir):
|
||||
assert not PrefixedCommandRunner('.').exists('foo')
|
||||
|
||||
|
||||
def test_exists_does_exist(in_tmpdir):
|
||||
os.mkdir('foo')
|
||||
assert PrefixedCommandRunner('.').exists('foo')
|
||||
|
||||
|
||||
def test_raises_on_error(popen_mock, makedirs_mock):
|
||||
popen_mock.return_value.returncode = 1
|
||||
with pytest.raises(CalledProcessError):
|
||||
instance = PrefixedCommandRunner(
|
||||
'.', popen=popen_mock, makedirs=makedirs_mock,
|
||||
)
|
||||
instance.run(['echo'])
|
||||
|
|
@ -191,7 +191,7 @@ def test_run_a_docker_image_hook(tempdir_factory, store, hook_id):
|
|||
def test_run_a_node_hook(tempdir_factory, store):
|
||||
_test_hook_repo(
|
||||
tempdir_factory, store, 'node_hooks_repo',
|
||||
'foo', ['/dev/null'], b'Hello World\n',
|
||||
'foo', [os.devnull], b'Hello World\n',
|
||||
)
|
||||
|
||||
|
||||
|
|
@ -200,7 +200,7 @@ def test_run_a_node_hook(tempdir_factory, store):
|
|||
def test_run_versioned_node_hook(tempdir_factory, store):
|
||||
_test_hook_repo(
|
||||
tempdir_factory, store, 'node_0_11_8_hooks_repo',
|
||||
'node-11-8-hook', ['/dev/null'], b'v0.11.8\nHello World\n',
|
||||
'node-11-8-hook', [os.devnull], b'v0.11.8\nHello World\n',
|
||||
)
|
||||
|
||||
|
||||
|
|
@ -209,7 +209,7 @@ def test_run_versioned_node_hook(tempdir_factory, store):
|
|||
def test_run_a_ruby_hook(tempdir_factory, store):
|
||||
_test_hook_repo(
|
||||
tempdir_factory, store, 'ruby_hooks_repo',
|
||||
'ruby_hook', ['/dev/null'], b'Hello world from a ruby hook\n',
|
||||
'ruby_hook', [os.devnull], b'Hello world from a ruby hook\n',
|
||||
)
|
||||
|
||||
|
||||
|
|
@ -219,7 +219,7 @@ def test_run_versioned_ruby_hook(tempdir_factory, store):
|
|||
_test_hook_repo(
|
||||
tempdir_factory, store, 'ruby_versioned_hooks_repo',
|
||||
'ruby_hook',
|
||||
['/dev/null'],
|
||||
[os.devnull],
|
||||
b'2.1.5\nHello world from a ruby hook\n',
|
||||
)
|
||||
|
||||
|
|
@ -242,7 +242,7 @@ def test_run_ruby_hook_with_disable_shared_gems(
|
|||
_test_hook_repo(
|
||||
tempdir_factory, store, 'ruby_versioned_hooks_repo',
|
||||
'ruby_hook',
|
||||
['/dev/null'],
|
||||
[os.devnull],
|
||||
b'2.1.5\nHello world from a ruby hook\n',
|
||||
)
|
||||
|
||||
|
|
@ -251,7 +251,7 @@ def test_run_ruby_hook_with_disable_shared_gems(
|
|||
def test_system_hook_with_spaces(tempdir_factory, store):
|
||||
_test_hook_repo(
|
||||
tempdir_factory, store, 'system_hook_with_spaces_repo',
|
||||
'system-hook-with-spaces', ['/dev/null'], b'Hello World\n',
|
||||
'system-hook-with-spaces', [os.devnull], b'Hello World\n',
|
||||
)
|
||||
|
||||
|
||||
|
|
@ -276,7 +276,7 @@ def test_golang_hook(tempdir_factory, store):
|
|||
def test_missing_executable(tempdir_factory, store):
|
||||
_test_hook_repo(
|
||||
tempdir_factory, store, 'not_found_exe',
|
||||
'not-found-exe', ['/dev/null'],
|
||||
'not-found-exe', [os.devnull],
|
||||
b'Executable `i-dont-exist-lol` not found',
|
||||
expected_return_code=1,
|
||||
)
|
||||
|
|
@ -424,7 +424,7 @@ def test_cwd_of_hook(tempdir_factory, store):
|
|||
def test_lots_of_files(tempdir_factory, store):
|
||||
_test_hook_repo(
|
||||
tempdir_factory, store, 'script_hooks_repo',
|
||||
'bash_hook', ['/dev/null'] * 15000, mock.ANY,
|
||||
'bash_hook', [os.devnull] * 15000, mock.ANY,
|
||||
)
|
||||
|
||||
|
||||
|
|
@ -467,7 +467,7 @@ def test_additional_python_dependencies_installed(tempdir_factory, store):
|
|||
config['hooks'][0]['additional_dependencies'] = ['mccabe']
|
||||
repo = Repository.create(config, store)
|
||||
repo.require_installed()
|
||||
with python.in_env(repo._cmd_runner, 'default'):
|
||||
with python.in_env(repo._prefix, 'default'):
|
||||
output = cmd_output('pip', 'freeze', '-l')[1]
|
||||
assert 'mccabe' in output
|
||||
|
||||
|
|
@ -484,7 +484,7 @@ def test_additional_dependencies_roll_forward(tempdir_factory, store):
|
|||
repo = Repository.create(config, store)
|
||||
repo.require_installed()
|
||||
# We should see our additional dependency installed
|
||||
with python.in_env(repo._cmd_runner, 'default'):
|
||||
with python.in_env(repo._prefix, 'default'):
|
||||
output = cmd_output('pip', 'freeze', '-l')[1]
|
||||
assert 'mccabe' in output
|
||||
|
||||
|
|
@ -499,7 +499,7 @@ def test_additional_ruby_dependencies_installed(
|
|||
config['hooks'][0]['additional_dependencies'] = ['thread_safe', 'tins']
|
||||
repo = Repository.create(config, store)
|
||||
repo.require_installed()
|
||||
with ruby.in_env(repo._cmd_runner, 'default'):
|
||||
with ruby.in_env(repo._prefix, 'default'):
|
||||
output = cmd_output('gem', 'list', '--local')[1]
|
||||
assert 'thread_safe' in output
|
||||
assert 'tins' in output
|
||||
|
|
@ -516,7 +516,7 @@ def test_additional_node_dependencies_installed(
|
|||
config['hooks'][0]['additional_dependencies'] = ['lodash']
|
||||
repo = Repository.create(config, store)
|
||||
repo.require_installed()
|
||||
with node.in_env(repo._cmd_runner, 'default'):
|
||||
with node.in_env(repo._prefix, 'default'):
|
||||
cmd_output('npm', 'config', 'set', 'global', 'true')
|
||||
output = cmd_output('npm', 'ls')[1]
|
||||
assert 'lodash' in output
|
||||
|
|
@ -533,7 +533,7 @@ def test_additional_golang_dependencies_installed(
|
|||
config['hooks'][0]['additional_dependencies'] = deps
|
||||
repo = Repository.create(config, store)
|
||||
repo.require_installed()
|
||||
binaries = os.listdir(repo._cmd_runner.path(
|
||||
binaries = os.listdir(repo._prefix.path(
|
||||
helpers.environment_dir(golang.ENVIRONMENT_DIR, 'default'), 'bin',
|
||||
))
|
||||
# normalize for windows
|
||||
|
|
@ -600,7 +600,7 @@ def test_control_c_control_c_on_install(tempdir_factory, store):
|
|||
|
||||
# Should have made an environment, however this environment is broken!
|
||||
envdir = 'py_env-{}'.format(python.get_default_version())
|
||||
assert repo._cmd_runner.exists(envdir)
|
||||
assert repo._prefix.exists(envdir)
|
||||
|
||||
# However, it should be perfectly runnable (reinstall after botched
|
||||
# install)
|
||||
|
|
@ -618,7 +618,7 @@ def test_invalidated_virtualenv(tempdir_factory, store):
|
|||
# Simulate breaking of the virtualenv
|
||||
repo.require_installed()
|
||||
version = python.get_default_version()
|
||||
libdir = repo._cmd_runner.path('py_env-{}'.format(version), 'lib', version)
|
||||
libdir = repo._prefix.path('py_env-{}'.format(version), 'lib', version)
|
||||
paths = [
|
||||
os.path.join(libdir, p) for p in ('site.py', 'site.pyc', '__pycache__')
|
||||
]
|
||||
|
|
|
|||
|
|
@ -5,6 +5,7 @@ import random
|
|||
|
||||
import pytest
|
||||
|
||||
from pre_commit.util import CalledProcessError
|
||||
from pre_commit.util import clean_path_on_failure
|
||||
from pre_commit.util import cmd_output
|
||||
from pre_commit.util import cwd
|
||||
|
|
@ -12,6 +13,34 @@ from pre_commit.util import memoize_by_cwd
|
|||
from pre_commit.util import tmpdir
|
||||
|
||||
|
||||
def test_CalledProcessError_str():
|
||||
error = CalledProcessError(
|
||||
1, [str('git'), str('status')], 0, (str('stdout'), str('stderr')),
|
||||
)
|
||||
assert str(error) == (
|
||||
"Command: ['git', 'status']\n"
|
||||
"Return code: 1\n"
|
||||
"Expected return code: 0\n"
|
||||
"Output: \n"
|
||||
" stdout\n"
|
||||
"Errors: \n"
|
||||
" stderr\n"
|
||||
)
|
||||
|
||||
|
||||
def test_CalledProcessError_str_nooutput():
|
||||
error = CalledProcessError(
|
||||
1, [str('git'), str('status')], 0, (str(''), str('')),
|
||||
)
|
||||
assert str(error) == (
|
||||
"Command: ['git', 'status']\n"
|
||||
"Return code: 1\n"
|
||||
"Expected return code: 0\n"
|
||||
"Output: (none)\n"
|
||||
"Errors: (none)\n"
|
||||
)
|
||||
|
||||
|
||||
@pytest.fixture
|
||||
def memoized_by_cwd():
|
||||
@memoize_by_cwd
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue