Skip to content

Commit 26ef392

Browse files
committed
tests: add type hints
Signed-off-by: Benjamin Gilbert <[email protected]>
1 parent f9a4252 commit 26ef392

File tree

6 files changed

+94
-70
lines changed

6 files changed

+94
-70
lines changed

.pre-commit-config.yaml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -59,7 +59,7 @@ repos:
5959
- id: mypy
6060
name: Check Python types
6161
additional_dependencies: [openslide-bin, pillow, types-setuptools]
62-
exclude: "^(doc/.*|tests/.*|examples/deepzoom/.*)$"
62+
exclude: "^(doc/.*|examples/deepzoom/.*)$"
6363

6464
- repo: https://github.com/rstcheck/rstcheck
6565
rev: v6.2.4

tests/common.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -30,9 +30,9 @@
3030
# environment.
3131
_dll_path = os.getenv('OPENSLIDE_PATH')
3232
if _dll_path is not None:
33-
with os.add_dll_directory(_dll_path):
33+
with os.add_dll_directory(_dll_path): # type: ignore[attr-defined]
3434
import openslide # noqa: F401 module-imported-but-unused
3535

3636

37-
def file_path(name):
37+
def file_path(name: str) -> Path:
3838
return Path(__file__).parent / 'fixtures' / name

tests/test_base.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -28,13 +28,13 @@
2828

2929

3030
class TestLibrary(unittest.TestCase):
31-
def test_open_slide(self):
31+
def test_open_slide(self) -> None:
3232
with open_slide(file_path('boxes.tiff')) as osr:
3333
self.assertTrue(isinstance(osr, OpenSlide))
3434
with open_slide(file_path('boxes.png')) as osr:
3535
self.assertTrue(isinstance(osr, ImageSlide))
3636

37-
def test_lowlevel_available(self):
37+
def test_lowlevel_available(self) -> None:
3838
'''Ensure all exported functions have an 'available' attribute.'''
3939
for name in dir(lowlevel):
4040
attr = getattr(lowlevel, name)

tests/test_deepzoom.py

Lines changed: 17 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -30,24 +30,26 @@
3030
class _Abstract:
3131
# nested class to prevent the test runner from finding it
3232
class BoxesDeepZoomTest(unittest.TestCase):
33-
def setUp(self):
33+
CLASS: type | None = None
34+
FILENAME: str | None = None
35+
36+
def setUp(self) -> None:
37+
assert self.CLASS is not None
38+
assert self.FILENAME is not None
3439
self.osr = self.CLASS(file_path(self.FILENAME))
3540
self.dz = DeepZoomGenerator(self.osr, 254, 1)
3641

37-
def tearDown(self):
42+
def tearDown(self) -> None:
3843
self.osr.close()
3944

40-
def test_repr(self):
45+
def test_repr(self) -> None:
4146
self.assertEqual(
4247
repr(self.dz),
43-
(
44-
'DeepZoomGenerator(%r, tile_size=254, overlap=1, '
45-
+ 'limit_bounds=False)'
46-
)
48+
'DeepZoomGenerator(%r, tile_size=254, overlap=1, limit_bounds=False)'
4749
% self.osr,
4850
)
4951

50-
def test_metadata(self):
52+
def test_metadata(self) -> None:
5153
self.assertEqual(self.dz.level_count, 10)
5254
self.assertEqual(self.dz.tile_count, 11)
5355
self.assertEqual(
@@ -81,31 +83,31 @@ def test_metadata(self):
8183
),
8284
)
8385

84-
def test_get_tile(self):
86+
def test_get_tile(self) -> None:
8587
self.assertEqual(self.dz.get_tile(9, (1, 0)).size, (47, 250))
8688

87-
def test_tile_color_profile(self):
89+
def test_tile_color_profile(self) -> None:
8890
if self.CLASS is OpenSlide and not lowlevel.read_icc_profile.available:
8991
self.skipTest("requires OpenSlide 4.0.0")
9092
self.assertEqual(len(self.dz.get_tile(9, (1, 0)).info['icc_profile']), 588)
9193

92-
def test_get_tile_bad_level(self):
94+
def test_get_tile_bad_level(self) -> None:
9395
self.assertRaises(ValueError, lambda: self.dz.get_tile(-1, (0, 0)))
9496
self.assertRaises(ValueError, lambda: self.dz.get_tile(10, (0, 0)))
9597

96-
def test_get_tile_bad_address(self):
98+
def test_get_tile_bad_address(self) -> None:
9799
self.assertRaises(ValueError, lambda: self.dz.get_tile(0, (-1, 0)))
98100
self.assertRaises(ValueError, lambda: self.dz.get_tile(0, (1, 0)))
99101

100-
def test_get_tile_coordinates(self):
102+
def test_get_tile_coordinates(self) -> None:
101103
self.assertEqual(
102104
self.dz.get_tile_coordinates(9, (1, 0)), ((253, 0), 0, (47, 250))
103105
)
104106

105-
def test_get_tile_dimensions(self):
107+
def test_get_tile_dimensions(self) -> None:
106108
self.assertEqual(self.dz.get_tile_dimensions(9, (1, 0)), (47, 250))
107109

108-
def test_get_dzi(self):
110+
def test_get_dzi(self) -> None:
109111
self.assertTrue(
110112
'http://schemas.microsoft.com/deepzoom/2008' in self.dz.get_dzi('jpeg')
111113
)

tests/test_imageslide.py

Lines changed: 23 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -29,16 +29,16 @@
2929

3030

3131
class TestImageWithoutOpening(unittest.TestCase):
32-
def test_detect_format(self):
32+
def test_detect_format(self) -> None:
3333
self.assertTrue(ImageSlide.detect_format(file_path('__missing_file')) is None)
3434
self.assertTrue(ImageSlide.detect_format(file_path('../setup.py')) is None)
3535
self.assertEqual(ImageSlide.detect_format(file_path('boxes.png')), 'PNG')
3636

37-
def test_open(self):
37+
def test_open(self) -> None:
3838
self.assertRaises(OSError, lambda: ImageSlide(file_path('__does_not_exist')))
3939
self.assertRaises(OSError, lambda: ImageSlide(file_path('../setup.py')))
4040

41-
def test_open_image(self):
41+
def test_open_image(self) -> None:
4242
# passing PIL.Image to ImageSlide
4343
with Image.open(file_path('boxes.png')) as img:
4444
with ImageSlide(img) as osr:
@@ -49,18 +49,18 @@ def test_open_image(self):
4949
sys.getfilesystemencoding() == 'utf-8',
5050
'Python filesystem encoding is not UTF-8',
5151
)
52-
def test_unicode_path(self):
52+
def test_unicode_path(self) -> None:
5353
path = file_path('😐.png')
5454
for arg in path, str(path):
5555
self.assertEqual(ImageSlide.detect_format(arg), 'PNG')
5656
self.assertEqual(ImageSlide(arg).dimensions, (300, 250))
5757

58-
def test_unicode_path_bytes(self):
58+
def test_unicode_path_bytes(self) -> None:
5959
arg = str(file_path('😐.png')).encode('UTF-8')
6060
self.assertEqual(ImageSlide.detect_format(arg), 'PNG')
6161
self.assertEqual(ImageSlide(arg).dimensions, (300, 250))
6262

63-
def test_operations_on_closed_handle(self):
63+
def test_operations_on_closed_handle(self) -> None:
6464
with Image.open(file_path('boxes.png')) as img:
6565
osr = ImageSlide(img)
6666
osr.close()
@@ -72,7 +72,7 @@ def test_operations_on_closed_handle(self):
7272
# shouldn't close it
7373
self.assertEqual(img.getpixel((0, 0)), 3)
7474

75-
def test_context_manager(self):
75+
def test_context_manager(self) -> None:
7676
osr = ImageSlide(file_path('boxes.png'))
7777
with osr:
7878
pass
@@ -83,20 +83,23 @@ def test_context_manager(self):
8383
class _Abstract:
8484
# nested class to prevent the test runner from finding it
8585
class SlideTest(unittest.TestCase):
86-
def setUp(self):
86+
FILENAME: str | None = None
87+
88+
def setUp(self) -> None:
89+
assert self.FILENAME is not None
8790
self.osr = ImageSlide(file_path(self.FILENAME))
8891

89-
def tearDown(self):
92+
def tearDown(self) -> None:
9093
self.osr.close()
9194

9295

9396
class TestImage(_Abstract.SlideTest):
9497
FILENAME = 'boxes.png'
9598

96-
def test_repr(self):
99+
def test_repr(self) -> None:
97100
self.assertEqual(repr(self.osr), 'ImageSlide(%r)' % file_path('boxes.png'))
98101

99-
def test_metadata(self):
102+
def test_metadata(self) -> None:
100103
self.assertEqual(self.osr.level_count, 1)
101104
self.assertEqual(self.osr.level_dimensions, ((300, 250),))
102105
self.assertEqual(self.osr.dimensions, (300, 250))
@@ -108,7 +111,8 @@ def test_metadata(self):
108111
self.assertEqual(self.osr.properties, {})
109112
self.assertEqual(self.osr.associated_images, {})
110113

111-
def test_color_profile(self):
114+
def test_color_profile(self) -> None:
115+
assert self.osr.color_profile is not None # for type inference
112116
self.assertEqual(self.osr.color_profile.profile.device_class, 'mntr')
113117
self.assertEqual(
114118
len(self.osr.read_region((0, 0), 0, (100, 100)).info['icc_profile']), 588
@@ -117,37 +121,37 @@ def test_color_profile(self):
117121
len(self.osr.get_thumbnail((100, 100)).info['icc_profile']), 588
118122
)
119123

120-
def test_read_region(self):
124+
def test_read_region(self) -> None:
121125
self.assertEqual(
122126
self.osr.read_region((-10, -10), 0, (400, 400)).size, (400, 400)
123127
)
124128

125-
def test_read_region_size_dimension_zero(self):
129+
def test_read_region_size_dimension_zero(self) -> None:
126130
self.assertEqual(self.osr.read_region((0, 0), 0, (400, 0)).size, (400, 0))
127131

128-
def test_read_region_bad_level(self):
132+
def test_read_region_bad_level(self) -> None:
129133
self.assertRaises(
130134
OpenSlideError, lambda: self.osr.read_region((0, 0), 1, (100, 100))
131135
)
132136

133-
def test_read_region_bad_size(self):
137+
def test_read_region_bad_size(self) -> None:
134138
self.assertRaises(
135139
OpenSlideError, lambda: self.osr.read_region((0, 0), 0, (400, -5))
136140
)
137141

138-
def test_thumbnail(self):
142+
def test_thumbnail(self) -> None:
139143
self.assertEqual(self.osr.get_thumbnail((100, 100)).size, (100, 83))
140144

141145
@unittest.skipUnless(lowlevel.cache_create.available, "requires OpenSlide 4.0.0")
142-
def test_set_cache(self):
146+
def test_set_cache(self) -> None:
143147
self.osr.set_cache(OpenSlideCache(64 << 10))
144148
self.assertEqual(self.osr.read_region((0, 0), 0, (400, 400)).size, (400, 400))
145149

146150

147151
class TestNoIccImage(_Abstract.SlideTest):
148152
FILENAME = 'boxes-no-icc.png'
149153

150-
def test_color_profile(self):
154+
def test_color_profile(self) -> None:
151155
self.assertIsNone(self.osr.color_profile)
152156
self.assertNotIn(
153157
'icc_profile', self.osr.read_region((0, 0), 0, (100, 100)).info

0 commit comments

Comments
 (0)