summaryrefslogtreecommitdiffstats
path: root/tests/languages
diff options
context:
space:
mode:
Diffstat (limited to 'tests/languages')
-rw-r--r--tests/languages/__init__.py0
-rw-r--r--tests/languages/docker_test.py23
-rw-r--r--tests/languages/golang_test.py20
-rw-r--r--tests/languages/helpers_test.py82
-rw-r--r--tests/languages/pygrep_test.py65
-rw-r--r--tests/languages/python_test.py75
-rw-r--r--tests/languages/ruby_test.py28
7 files changed, 293 insertions, 0 deletions
diff --git a/tests/languages/__init__.py b/tests/languages/__init__.py
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/tests/languages/__init__.py
diff --git a/tests/languages/docker_test.py b/tests/languages/docker_test.py
new file mode 100644
index 0000000..171a3f7
--- /dev/null
+++ b/tests/languages/docker_test.py
@@ -0,0 +1,23 @@
+from unittest import mock
+
+from pre_commit.languages import docker
+from pre_commit.util import CalledProcessError
+
+
+def test_docker_is_running_process_error():
+ with mock.patch(
+ 'pre_commit.languages.docker.cmd_output_b',
+ side_effect=CalledProcessError(1, (), 0, b'', None),
+ ):
+ assert docker.docker_is_running() is False
+
+
+def test_docker_fallback_user():
+ def invalid_attribute():
+ raise AttributeError
+ with mock.patch.multiple(
+ 'os', create=True,
+ getuid=invalid_attribute,
+ getgid=invalid_attribute,
+ ):
+ assert docker.get_docker_user() == '1000:1000'
diff --git a/tests/languages/golang_test.py b/tests/languages/golang_test.py
new file mode 100644
index 0000000..9a64ed1
--- /dev/null
+++ b/tests/languages/golang_test.py
@@ -0,0 +1,20 @@
+import pytest
+
+from pre_commit.languages.golang import guess_go_dir
+
+
+@pytest.mark.parametrize(
+ ('url', 'expected'),
+ (
+ ('/im/a/path/on/disk', 'unknown_src_dir'),
+ ('file:///im/a/path/on/disk', 'unknown_src_dir'),
+ ('git@github.com:golang/lint', 'github.com/golang/lint'),
+ ('git://github.com/golang/lint', 'github.com/golang/lint'),
+ ('http://github.com/golang/lint', 'github.com/golang/lint'),
+ ('https://github.com/golang/lint', 'github.com/golang/lint'),
+ ('ssh://git@github.com/golang/lint', 'github.com/golang/lint'),
+ ('git@github.com:golang/lint.git', 'github.com/golang/lint'),
+ ),
+)
+def test_guess_go_dir(url, expected):
+ assert guess_go_dir(url) == expected
diff --git a/tests/languages/helpers_test.py b/tests/languages/helpers_test.py
new file mode 100644
index 0000000..c52e947
--- /dev/null
+++ b/tests/languages/helpers_test.py
@@ -0,0 +1,82 @@
+import multiprocessing
+import os
+import sys
+from unittest import mock
+
+import pytest
+
+import pre_commit.constants as C
+from pre_commit.languages import helpers
+from pre_commit.prefix import Prefix
+from pre_commit.util import CalledProcessError
+from testing.auto_namedtuple import auto_namedtuple
+
+
+def test_basic_get_default_version():
+ assert helpers.basic_get_default_version() == C.DEFAULT
+
+
+def test_basic_healthy():
+ assert helpers.basic_healthy(Prefix('.'), 'default') is True
+
+
+def test_failed_setup_command_does_not_unicode_error():
+ script = (
+ 'import sys\n'
+ "getattr(sys.stderr, 'buffer', sys.stderr).write(b'\\x81\\xfe')\n"
+ 'exit(1)\n'
+ )
+
+ # an assertion that this does not raise `UnicodeError`
+ with pytest.raises(CalledProcessError):
+ helpers.run_setup_cmd(Prefix('.'), (sys.executable, '-c', script))
+
+
+def test_assert_no_additional_deps():
+ with pytest.raises(AssertionError) as excinfo:
+ helpers.assert_no_additional_deps('lang', ['hmmm'])
+ msg, = excinfo.value.args
+ assert msg == (
+ 'For now, pre-commit does not support additional_dependencies for lang'
+ )
+
+
+SERIAL_FALSE = auto_namedtuple(require_serial=False)
+SERIAL_TRUE = auto_namedtuple(require_serial=True)
+
+
+def test_target_concurrency_normal():
+ with mock.patch.object(multiprocessing, 'cpu_count', return_value=123):
+ with mock.patch.dict(os.environ, {}, clear=True):
+ assert helpers.target_concurrency(SERIAL_FALSE) == 123
+
+
+def test_target_concurrency_cpu_count_require_serial_true():
+ with mock.patch.dict(os.environ, {}, clear=True):
+ assert helpers.target_concurrency(SERIAL_TRUE) == 1
+
+
+def test_target_concurrency_testing_env_var():
+ with mock.patch.dict(
+ os.environ, {'PRE_COMMIT_NO_CONCURRENCY': '1'}, clear=True,
+ ):
+ assert helpers.target_concurrency(SERIAL_FALSE) == 1
+
+
+def test_target_concurrency_on_travis():
+ with mock.patch.dict(os.environ, {'TRAVIS': '1'}, clear=True):
+ assert helpers.target_concurrency(SERIAL_FALSE) == 2
+
+
+def test_target_concurrency_cpu_count_not_implemented():
+ with mock.patch.object(
+ multiprocessing, 'cpu_count', side_effect=NotImplementedError,
+ ):
+ with mock.patch.dict(os.environ, {}, clear=True):
+ assert helpers.target_concurrency(SERIAL_FALSE) == 1
+
+
+def test_shuffled_is_deterministic():
+ seq = [str(i) for i in range(10)]
+ expected = ['3', '7', '8', '2', '4', '6', '5', '1', '0', '9']
+ assert helpers._shuffled(seq) == expected
diff --git a/tests/languages/pygrep_test.py b/tests/languages/pygrep_test.py
new file mode 100644
index 0000000..cabea22
--- /dev/null
+++ b/tests/languages/pygrep_test.py
@@ -0,0 +1,65 @@
+import pytest
+
+from pre_commit.languages import pygrep
+
+
+@pytest.fixture
+def some_files(tmpdir):
+ tmpdir.join('f1').write_binary(b'foo\nbar\n')
+ tmpdir.join('f2').write_binary(b'[INFO] hi\n')
+ tmpdir.join('f3').write_binary(b"with'quotes\n")
+ with tmpdir.as_cwd():
+ yield
+
+
+@pytest.mark.usefixtures('some_files')
+@pytest.mark.parametrize(
+ ('pattern', 'expected_retcode', 'expected_out'),
+ (
+ ('baz', 0, ''),
+ ('foo', 1, 'f1:1:foo\n'),
+ ('bar', 1, 'f1:2:bar\n'),
+ (r'(?i)\[info\]', 1, 'f2:1:[INFO] hi\n'),
+ ("h'q", 1, "f3:1:with'quotes\n"),
+ ),
+)
+def test_main(some_files, cap_out, pattern, expected_retcode, expected_out):
+ ret = pygrep.main((pattern, 'f1', 'f2', 'f3'))
+ out = cap_out.get()
+ assert ret == expected_retcode
+ assert out == expected_out
+
+
+def test_ignore_case(some_files, cap_out):
+ ret = pygrep.main(('--ignore-case', 'info', 'f1', 'f2', 'f3'))
+ out = cap_out.get()
+ assert ret == 1
+ assert out == 'f2:1:[INFO] hi\n'
+
+
+def test_multiline(some_files, cap_out):
+ ret = pygrep.main(('--multiline', r'foo\nbar', 'f1', 'f2', 'f3'))
+ out = cap_out.get()
+ assert ret == 1
+ assert out == 'f1:1:foo\nbar\n'
+
+
+def test_multiline_line_number(some_files, cap_out):
+ ret = pygrep.main(('--multiline', r'ar', 'f1', 'f2', 'f3'))
+ out = cap_out.get()
+ assert ret == 1
+ assert out == 'f1:2:bar\n'
+
+
+def test_multiline_dotall_flag_is_enabled(some_files, cap_out):
+ ret = pygrep.main(('--multiline', r'o.*bar', 'f1', 'f2', 'f3'))
+ out = cap_out.get()
+ assert ret == 1
+ assert out == 'f1:1:foo\nbar\n'
+
+
+def test_multiline_multiline_flag_is_enabled(some_files, cap_out):
+ ret = pygrep.main(('--multiline', r'foo$.*bar', 'f1', 'f2', 'f3'))
+ out = cap_out.get()
+ assert ret == 1
+ assert out == 'f1:1:foo\nbar\n'
diff --git a/tests/languages/python_test.py b/tests/languages/python_test.py
new file mode 100644
index 0000000..34c6c7f
--- /dev/null
+++ b/tests/languages/python_test.py
@@ -0,0 +1,75 @@
+import os.path
+import sys
+from unittest import mock
+
+import pytest
+
+import pre_commit.constants as C
+from pre_commit.languages import python
+from pre_commit.prefix import Prefix
+
+
+def test_norm_version_expanduser():
+ home = os.path.expanduser('~')
+ if os.name == 'nt': # pragma: nt cover
+ path = r'~\python343'
+ expected_path = fr'{home}\python343'
+ else: # pragma: nt no cover
+ path = '~/.pyenv/versions/3.4.3/bin/python'
+ expected_path = f'{home}/.pyenv/versions/3.4.3/bin/python'
+ result = python.norm_version(path)
+ assert result == expected_path
+
+
+@pytest.mark.parametrize('v', ('python3.6', 'python3', 'python'))
+def test_sys_executable_matches(v):
+ with mock.patch.object(sys, 'version_info', (3, 6, 7)):
+ assert python._sys_executable_matches(v)
+
+
+@pytest.mark.parametrize('v', ('notpython', 'python3.x'))
+def test_sys_executable_matches_does_not_match(v):
+ with mock.patch.object(sys, 'version_info', (3, 6, 7)):
+ assert not python._sys_executable_matches(v)
+
+
+@pytest.mark.parametrize(
+ ('exe', 'realpath', 'expected'), (
+ ('/usr/bin/python3', '/usr/bin/python3.7', 'python3'),
+ ('/usr/bin/python', '/usr/bin/python3.7', 'python3.7'),
+ ('/usr/bin/python', '/usr/bin/python', None),
+ ('/usr/bin/python3.6m', '/usr/bin/python3.6m', 'python3.6m'),
+ ('v/bin/python', 'v/bin/pypy', 'pypy'),
+ ),
+)
+def test_find_by_sys_executable(exe, realpath, expected):
+ with mock.patch.object(sys, 'executable', exe):
+ with mock.patch.object(os.path, 'realpath', return_value=realpath):
+ with mock.patch.object(python, 'find_executable', lambda x: x):
+ assert python._find_by_sys_executable() == expected
+
+
+def test_healthy_types_py_in_cwd(tmpdir):
+ with tmpdir.as_cwd():
+ prefix = tmpdir.join('prefix').ensure_dir()
+ prefix.join('setup.py').write('import setuptools; setuptools.setup()')
+ prefix = Prefix(str(prefix))
+ python.install_environment(prefix, C.DEFAULT, ())
+
+ # even if a `types.py` file exists, should still be healthy
+ tmpdir.join('types.py').ensure()
+ assert python.healthy(prefix, C.DEFAULT) is True
+
+
+def test_healthy_python_goes_missing(tmpdir):
+ with tmpdir.as_cwd():
+ prefix = tmpdir.join('prefix').ensure_dir()
+ prefix.join('setup.py').write('import setuptools; setuptools.setup()')
+ prefix = Prefix(str(prefix))
+ python.install_environment(prefix, C.DEFAULT, ())
+
+ exe_name = 'python' if sys.platform != 'win32' else 'python.exe'
+ py_exe = prefix.path(python.bin_dir('py_env-default'), exe_name)
+ os.remove(py_exe)
+
+ assert python.healthy(prefix, C.DEFAULT) is False
diff --git a/tests/languages/ruby_test.py b/tests/languages/ruby_test.py
new file mode 100644
index 0000000..36a029d
--- /dev/null
+++ b/tests/languages/ruby_test.py
@@ -0,0 +1,28 @@
+import os.path
+
+from pre_commit.languages import ruby
+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(tempdir_factory):
+ prefix = Prefix(tempdir_factory.get())
+ ruby._install_rbenv(prefix)
+ # Should have created rbenv directory
+ assert os.path.exists(prefix.path('rbenv-default'))
+
+ # Should be able to activate using our script and access rbenv
+ with ruby.in_env(prefix, 'default'):
+ cmd_output('rbenv', '--help')
+
+
+@xfailif_windows_no_ruby
+def test_install_rbenv_with_version(tempdir_factory):
+ prefix = Prefix(tempdir_factory.get())
+ ruby._install_rbenv(prefix, version='1.9.3p547')
+
+ # Should be able to activate and use rbenv install
+ with ruby.in_env(prefix, '1.9.3p547'):
+ cmd_output('rbenv', 'install', '--help')