-
Notifications
You must be signed in to change notification settings - Fork 358
Expand file tree
/
Copy path_driver_test_case.py
More file actions
63 lines (44 loc) · 1.77 KB
/
_driver_test_case.py
File metadata and controls
63 lines (44 loc) · 1.77 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
from __future__ import annotations
import unittest
from typing import TYPE_CHECKING, Generic, TypeVar
if TYPE_CHECKING:
from qcodes.instrument import Instrument
"""
This module defines:
- `DriverTestCase`: a `TestCase` subclass meant for testing instrument drivers
Using `DriverTestCase` is pretty easy:
- Inherit from this class instead of from the base `unittest.TestCase`
- Provide a driver class variable that points to the Instrument class
- In your tests, `self.instrument` is the latest instance of this class.
- If your test case includes a `setUpClass` method, make sure to call
`super().setUpClass()`, because that's where we find the latest instance of
this `Instrument`, or skip the test case if no instances are found.
"""
T = TypeVar("T", bound="Instrument")
class DriverTestCase[T: "Instrument"](unittest.TestCase):
# override this in a subclass
driver: type[T] | None = None
instrument: T
@classmethod
def setUpClass(cls) -> None:
if cls is DriverTestCase:
return
if cls.driver is None:
raise TypeError("you must set a driver for " + cls.__name__)
instances = cls.driver.instances()
name = cls.driver.__name__
if not instances:
msg = f"no instances of {name} found"
if getattr(cls, "noskip", False):
# just to test this class, we need to disallow skipping
raise ValueError(msg)
else:
raise unittest.SkipTest(msg)
if len(instances) == 1:
print(f"***** found one {name}, testing *****")
else:
print(
f"***** found {len(instances)} instances of {name}; "
"testing the last one *****"
)
cls.instrument = instances[-1]