|
2 | 2 |
|
3 | 3 | import pytest
|
4 | 4 | import ntcore
|
5 |
| -import wpilib |
6 | 5 | from wpilib.simulation._simulation import _resetWpilibSimulationData
|
7 | 6 |
|
8 |
| -from pathlib import Path |
9 |
| - |
10 |
| -import gc |
11 |
| - |
12 |
| -import weakref |
13 |
| - |
14 |
| -import hal |
15 |
| -import hal.simulation |
16 |
| -import wpilib.shuffleboard |
17 |
| -from wpilib.simulation import DriverStationSim, pauseTiming, restartTiming |
18 |
| -import wpilib.simulation |
19 |
| -from pyfrc.test_support.controller import TestController |
20 |
| -from pyfrc.physics.core import PhysicsInterface |
21 |
| - |
22 | 7 | try:
|
23 | 8 | import commands2
|
24 | 9 | except ImportError:
|
@@ -48,133 +33,3 @@ def nt(cfg_logging, wpilib_state):
|
48 | 33 | finally:
|
49 | 34 | instance.stopLocal()
|
50 | 35 | instance._reset()
|
51 |
| - |
52 |
| - |
53 |
| -@pytest.fixture(scope="class", autouse=False) |
54 |
| -def physics_and_decorated_robot_class( |
55 |
| - myrobot_class, robots_sim_enable_physics |
56 |
| -) -> tuple: |
57 |
| - # attach physics |
58 |
| - |
59 |
| - robotClass = myrobot_class |
60 |
| - physicsInterface = None |
61 |
| - if robots_sim_enable_physics: |
62 |
| - physicsInterface, robotClass = PhysicsInterface._create_and_attach( |
63 |
| - myrobot_class, |
64 |
| - Path(__file__).parent, |
65 |
| - ) |
66 |
| - |
67 |
| - if physicsInterface: |
68 |
| - physicsInterface.log_init_errors = False |
69 |
| - |
70 |
| - # Tests need to know when robotInit is called, so override the robot |
71 |
| - # to do that |
72 |
| - class TestRobot(robotClass): |
73 |
| - def robotInit(self): |
74 |
| - try: |
75 |
| - super().robotInit() |
76 |
| - finally: |
77 |
| - self.__robotInitialized() |
78 |
| - |
79 |
| - TestRobot.__name__ = robotClass.__name__ |
80 |
| - TestRobot.__module__ = robotClass.__module__ |
81 |
| - TestRobot.__qualname__ = robotClass.__qualname__ |
82 |
| - |
83 |
| - return (physicsInterface, TestRobot) |
84 |
| - |
85 |
| - |
86 |
| -@pytest.fixture(scope="function", autouse=False) |
87 |
| -def robot_with_sim_setup_teardown(physics_and_decorated_robot_class): |
88 |
| - """ |
89 |
| - Your robot instance |
90 |
| -
|
91 |
| - .. note:: RobotPy/WPILib testing infrastructure is really sensitive |
92 |
| - to ensuring that things get cleaned up properly. Make sure |
93 |
| - that you don't store references to your robot or other |
94 |
| - WPILib objects in a global or static context. |
95 |
| - """ |
96 |
| - |
97 |
| - # |
98 |
| - # This function needs to do the same things that RobotBase.main does |
99 |
| - # plus some extra things needed for testing |
100 |
| - # |
101 |
| - # Previously this was separate from robot fixture, but we need to |
102 |
| - # ensure that the robot cleanup happens deterministically relative to |
103 |
| - # when handle cleanup/etc happens, otherwise unnecessary HAL errors will |
104 |
| - # bubble up to the user |
105 |
| - # |
106 |
| - |
107 |
| - nt_inst = ntcore.NetworkTableInstance.getDefault() |
108 |
| - nt_inst.startLocal() |
109 |
| - |
110 |
| - pauseTiming() |
111 |
| - restartTiming() |
112 |
| - |
113 |
| - wpilib.DriverStation.silenceJoystickConnectionWarning(True) |
114 |
| - DriverStationSim.setAutonomous(False) |
115 |
| - DriverStationSim.setEnabled(False) |
116 |
| - DriverStationSim.notifyNewData() |
117 |
| - |
118 |
| - robot = physics_and_decorated_robot_class[1]() |
119 |
| - |
120 |
| - # Tests only get a proxy to ensure cleanup is more reliable |
121 |
| - yield weakref.proxy(robot) |
122 |
| - |
123 |
| - # If running in separate processes, no need to do cleanup |
124 |
| - # if ISOLATED: |
125 |
| - # # .. and funny enough, in isolated mode we *don't* want the |
126 |
| - # # robot to be cleaned up, as that can deadlock |
127 |
| - # self._saved_robot = robot |
128 |
| - # return |
129 |
| - |
130 |
| - # reset engine to ensure it gets cleaned up too |
131 |
| - # -> might be holding wpilib objects, or the robot |
132 |
| - if physics_and_decorated_robot_class[0]: |
133 |
| - physics_and_decorated_robot_class[0].engine = None |
134 |
| - |
135 |
| - # HACK: avoid motor safety deadlock |
136 |
| - wpilib.simulation._simulation._resetMotorSafety() |
137 |
| - |
138 |
| - del robot |
139 |
| - |
140 |
| - if commands2 is not None: |
141 |
| - commands2.CommandScheduler.resetInstance() |
142 |
| - |
143 |
| - # Double-check all objects are destroyed so that HAL handles are released |
144 |
| - gc.collect() |
145 |
| - |
146 |
| - # shutdown networktables before other kinds of global cleanup |
147 |
| - # -> some reset functions will re-register listeners, so it's important |
148 |
| - # to do this before so that the listeners are active on the current |
149 |
| - # NetworkTables instance |
150 |
| - nt_inst.stopLocal() |
151 |
| - nt_inst._reset() |
152 |
| - |
153 |
| - # Cleanup WPILib globals |
154 |
| - # -> preferences, SmartDashboard, Shuffleboard, LiveWindow, MotorSafety |
155 |
| - wpilib.simulation._simulation._resetWpilibSimulationData() |
156 |
| - wpilib._wpilib._clearSmartDashboardData() |
157 |
| - wpilib.shuffleboard._shuffleboard._clearShuffleboardData() |
158 |
| - |
159 |
| - # Cancel all periodic callbacks |
160 |
| - hal.simulation.cancelAllSimPeriodicCallbacks() |
161 |
| - |
162 |
| - # Reset the HAL handles |
163 |
| - hal.simulation.resetGlobalHandles() |
164 |
| - |
165 |
| - # Reset the HAL data |
166 |
| - hal.simulation.resetAllSimData() |
167 |
| - |
168 |
| - # Don't call HAL shutdown! This is only used to cleanup HAL extensions, |
169 |
| - # and functions will only be called the first time (unless re-registered) |
170 |
| - # hal.shutdown() |
171 |
| - |
172 |
| - |
173 |
| -@pytest.fixture(scope="function") |
174 |
| -def getTestController( |
175 |
| - reraise, robot_with_sim_setup_teardown: wpilib.RobotBase |
176 |
| -) -> TestController: |
177 |
| - """ |
178 |
| - A pytest fixture that provides control over your robot_with_sim_setup_teardown |
179 |
| - """ |
180 |
| - return TestController(reraise, robot_with_sim_setup_teardown) |
0 commit comments