Skip to content

Commit

Permalink
Improve testing
Browse files Browse the repository at this point in the history
  • Loading branch information
cpburnz committed Sep 8, 2023
1 parent 280c434 commit 312bcc6
Show file tree
Hide file tree
Showing 4 changed files with 89 additions and 44 deletions.
133 changes: 89 additions & 44 deletions tests/test_util.py → tests/test_01_util.py
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@
partial)
from typing import (
Iterable,
Optional,
Tuple)

from pathspec.patterns.gitwildmatch import (
Expand All @@ -31,36 +32,6 @@
ospath)


class MatchFileTest(unittest.TestCase):
"""
The :class:`MatchFileTest` class tests the :meth:`.match_file`
function.
"""

def test_1_match_file(self):
"""
Test matching files individually.
"""
patterns = list(map(GitWildMatchPattern, [
'*.txt',
'!b.txt',
]))
results = set(filter(partial(match_file, patterns), [
'X/a.txt',
'X/b.txt',
'X/Z/c.txt',
'Y/a.txt',
'Y/b.txt',
'Y/Z/c.txt',
]))
self.assertEqual(results, {
'X/a.txt',
'X/Z/c.txt',
'Y/a.txt',
'Y/Z/c.txt',
})


class IterTreeTest(unittest.TestCase):
"""
The :class:`IterTreeTest` class tests :meth:`.iter_tree_entries` and
Expand All @@ -85,6 +56,14 @@ def make_links(self, links: Iterable[Tuple[str, str]]) -> None:
"""
make_links(self.temp_dir, links)

def require_islink_dir(self) -> None:
"""
Skips the test if `os.path.islink` does not properly support symlinks to
directories.
"""
if self.broken_islink_dir:
raise unittest.SkipTest("`os.path.islink` is broken for directories.")

def require_realpath(self) -> None:
"""
Skips the test if `os.path.realpath` does not properly support
Expand Down Expand Up @@ -112,7 +91,7 @@ def tearDown(self) -> None:
"""
shutil.rmtree(self.temp_dir)

def test_1_files(self):
def test_01_files(self):
"""
Tests to make sure all files are found.
"""
Expand All @@ -139,13 +118,13 @@ def test_1_files(self):
'Dir/Inner/f',
])))

def test_2_0_check_symlink(self):
def test_02_link_1_check_1_symlink(self):
"""
Tests whether links can be created.
"""
# NOTE: Windows Vista and greater supports `os.symlink` for Python
# 3.2+.
no_symlink = None
no_symlink: Optional[bool] = None
try:
file = self.temp_dir / 'file'
link = self.temp_dir / 'link'
Expand All @@ -161,14 +140,14 @@ def test_2_0_check_symlink(self):
finally:
self.__class__.no_symlink = no_symlink

def test_2_1_check_realpath(self):
def test_02_link_1_check_2_realpath(self):
"""
Tests whether `os.path.realpath` works properly with symlinks.
"""
# NOTE: Windows does not follow symlinks with `os.path.realpath`
# which is what we use to detect recursion. See <https://bugs.python.org/issue9949>
# for details.
broken_realpath = None
broken_realpath: Optional[bool] = None
try:
self.require_symlink()
file = self.temp_dir / 'file'
Expand All @@ -186,11 +165,36 @@ def test_2_1_check_realpath(self):
finally:
self.__class__.broken_realpath = broken_realpath

def test_2_2_links(self):
def test_02_link_1_check_3_islink(self):
"""
Tests whether `os.path.islink` works properly with symlinks to directories.
"""
# NOTE: PyPy on Windows does not detect symlinks to directories.
# - See <https://foss.heptapod.net/pypy/pypy/-/issues/3434>
broken_islink_dir: Optional[bool] = None
try:
self.require_symlink()
folder = self.temp_dir / 'folder'
link = self.temp_dir / 'link'
os.mkdir(folder)
os.symlink(folder, link)

try:
self.assertTrue(os.path.islink(link))
except AssertionError:
broken_islink_dir = True
else:
broken_islink_dir = False

finally:
self.__class__.broken_islink_dir = broken_islink_dir

def test_02_link_2_links(self):
"""
Tests to make sure links to directories and files work.
"""
self.require_symlink()
self.require_islink_dir()
self.make_dirs([
'Dir',
])
Expand Down Expand Up @@ -223,12 +227,13 @@ def test_2_2_links(self):
'DirX/dx',
])))

def test_2_3_sideways_links(self):
def test_02_link_3_sideways_links(self):
"""
Tests to make sure the same directory can be encountered multiple
times via links.
"""
self.require_symlink()
self.require_islink_dir()
self.make_dirs([
'Dir',
'Dir/Target',
Expand Down Expand Up @@ -259,12 +264,13 @@ def test_2_3_sideways_links(self):
'Dir/Target/file',
])))

def test_2_4_recursive_links(self):
def test_02_link_4_recursive_links(self):
"""
Tests detection of recursive links.
"""
self.require_symlink()
self.require_realpath()
self.require_islink_dir()
self.make_dirs([
'Dir',
])
Expand All @@ -280,12 +286,13 @@ def test_2_4_recursive_links(self):
self.assertEqual(context.exception.first_path, 'Dir')
self.assertEqual(context.exception.second_path, ospath('Dir/Self'))

def test_2_5_recursive_circular_links(self):
def test_02_link_5_recursive_circular_links(self):
"""
Tests detection of recursion through circular links.
"""
self.require_symlink()
self.require_realpath()
self.require_islink_dir()
self.make_dirs([
'A',
'B',
Expand All @@ -311,7 +318,7 @@ def test_2_5_recursive_circular_links(self):
'C': ospath('C/Ax/Bx/Cx'),
}[context.exception.first_path])

def test_2_6_detect_broken_links(self):
def test_02_link_6_detect_broken_links(self):
"""
Tests that broken links are detected.
"""
Expand All @@ -327,7 +334,7 @@ def reraise(e):

self.assertEqual(context.exception.errno, errno.ENOENT)

def test_2_7_ignore_broken_links(self):
def test_02_link_7_ignore_broken_links(self):
"""
Tests that broken links are ignored.
"""
Expand All @@ -338,11 +345,12 @@ def test_2_7_ignore_broken_links(self):
results = set(iter_tree_files(self.temp_dir))
self.assertEqual(results, set())

def test_2_8_no_follow_links(self):
def test_02_link_8_no_follow_links(self):
"""
Tests to make sure directory links can be ignored.
"""
self.require_symlink()
self.require_islink_dir()
self.make_dirs([
'Dir',
])
Expand Down Expand Up @@ -372,7 +380,7 @@ def test_2_8_no_follow_links(self):
'DirX',
])))

def test_3_entries(self):
def test_03_entries(self):
"""
Tests to make sure all files are found.
"""
Expand Down Expand Up @@ -402,7 +410,44 @@ def test_3_entries(self):
'Empty',
])))

def test_4_normalizing_pathlib_path(self):

class MatchFileTest(unittest.TestCase):
"""
The :class:`MatchFileTest` class tests the :meth:`.match_file`
function.
"""

def test_01_match_file(self):
"""
Test matching files individually.
"""
patterns = list(map(GitWildMatchPattern, [
'*.txt',
'!b.txt',
]))
results = set(filter(partial(match_file, patterns), [
'X/a.txt',
'X/b.txt',
'X/Z/c.txt',
'Y/a.txt',
'Y/b.txt',
'Y/Z/c.txt',
]))
self.assertEqual(results, {
'X/a.txt',
'X/Z/c.txt',
'Y/a.txt',
'Y/Z/c.txt',
})


class NormalizeFileTest(unittest.TestCase):
"""
The :class:`NormalizeFileTest` class tests the :meth:`.normalize_file`
function.
"""

def test_01_purepath(self):
"""
Tests normalizing a :class:`pathlib.PurePath` as argument.
"""
Expand Down
File renamed without changes.
File renamed without changes.
File renamed without changes.

0 comments on commit 312bcc6

Please sign in to comment.