@@ -28,7 +28,7 @@ def test_base_strategy_not_implemented(self):
2828 """Test base class raises NotImplementedError."""
2929 strategy = DisplayStrategy ()
3030 with pytest .raises (NotImplementedError ):
31- strategy .execute (None , None , None )
31+ strategy .execute_monitoring (None , None , None )
3232
3333
3434@pytest .fixture
@@ -71,7 +71,9 @@ def test_execute_with_mock_display(
7171 mock_sleep .side_effect = KeyboardInterrupt ()
7272
7373 start_time = time .time ()
74- strategy .execute (mock_collector , start_time , timeout_minutes = 1 )
74+ strategy .execute_monitoring (
75+ mock_collector , start_time , timeout_minutes = 1
76+ )
7577
7678 # Verify display was called
7779 assert mock_display .display .called
@@ -106,7 +108,9 @@ def test_completion_message_on_normal_exit(
106108 mock_sleep .side_effect = KeyboardInterrupt ()
107109
108110 start_time = time .time ()
109- strategy .execute (mock_collector , start_time , timeout_minutes = 1 )
111+ strategy .execute_monitoring (
112+ mock_collector , start_time , timeout_minutes = 1
113+ )
110114
111115 captured = capsys .readouterr ()
112116 assert "Monitoring Complete!" in captured .out
@@ -128,7 +132,9 @@ def test_collector_output_is_displayed(
128132 mock_sleep .side_effect = KeyboardInterrupt ()
129133
130134 start_time = time .time ()
131- strategy .execute (mock_collector , start_time , timeout_minutes = 1 )
135+ strategy .execute_monitoring (
136+ mock_collector , start_time , timeout_minutes = 1
137+ )
132138
133139 captured = capsys .readouterr ()
134140 assert unique_output in captured .out
@@ -157,7 +163,9 @@ def test_execute_handles_service_inactive(
157163 mock_sleep .side_effect = KeyboardInterrupt ()
158164
159165 start_time = time .time ()
160- strategy .execute (mock_collector , start_time , timeout_minutes = 1 )
166+ strategy .execute_monitoring (
167+ mock_collector , start_time , timeout_minutes = 1
168+ )
161169
162170 # Strategy should handle the error and set output to "Service is inactive"
163171 captured = capsys .readouterr ()
@@ -190,8 +198,35 @@ def test_execute_other_client_errors_propagate(
190198
191199 # Other client errors should propagate
192200 with pytest .raises (ClientError ) as exc_info :
193- strategy .execute (mock_collector , start_time , timeout_minutes = 1 )
201+ strategy .execute_monitoring (
202+ mock_collector , start_time , timeout_minutes = 1
203+ )
194204
195205 assert (
196206 exc_info .value .response ['Error' ]['Code' ] == 'AccessDeniedException'
197207 )
208+
209+ @patch ('time.sleep' )
210+ def test_display_cleanup_on_exception (
211+ self , mock_sleep , app_session , mock_display
212+ ):
213+ """Test display app is properly shut down when exception occurs."""
214+ mock_collector = Mock ()
215+ error = ClientError (
216+ error_response = {'Error' : {'Code' : 'ThrottlingException' }},
217+ operation_name = 'DescribeServiceRevisions' ,
218+ )
219+ mock_collector .get_current_view = Mock (side_effect = error )
220+
221+ strategy = InteractiveDisplayStrategy (
222+ display = mock_display , use_color = True
223+ )
224+ mock_sleep .side_effect = KeyboardInterrupt ()
225+
226+ with pytest .raises (ClientError ):
227+ strategy .execute_monitoring (
228+ mock_collector , time .time (), timeout_minutes = 1
229+ )
230+
231+ # Verify app.exit() was called in finally block despite exception
232+ mock_display .app .exit .assert_called ()
0 commit comments