@@ -57,6 +57,23 @@ def _build_cfg() -> AppConfig:
5757
5858
5959class SafetyPolicyTests (unittest .TestCase ):
60+ @patch ("codexsync.app.sys.platform" , "win32" )
61+ @patch ("codexsync.app.confirm_process_termination" , return_value = True )
62+ def test_manual_confirmation_enabled_by_default_prompts (self , confirm_mock ) -> None :
63+ cfg = _build_cfg ()
64+ cfg .process_detection .manual_terminate_confirmation = True
65+ detector = _DetectorStub ()
66+ main = [ProcessInfo (pid = 10 , name = "Codex.exe" )]
67+ snapshot = ProcessSnapshot (
68+ main_processes = main ,
69+ subprocesses = [],
70+ sandbox_detected = False ,
71+ )
72+
73+ _handle_running_codex (cfg , detector , snapshot , manual_override = None )
74+ self .assertEqual (detector .terminated , [main ])
75+ confirm_mock .assert_called_once ()
76+
6077 @patch ("codexsync.app.sys.platform" , "win32" )
6178 def test_sandbox_detected_blocks_without_terminate (self ) -> None :
6279 cfg = _build_cfg ()
@@ -83,6 +100,58 @@ def test_no_sandbox_prompts_and_terminates(self, _confirm_mock) -> None:
83100 )
84101 _handle_running_codex (cfg , detector , snapshot , manual_override = None )
85102 self .assertEqual (detector .terminated , [main ])
103+ _confirm_mock .assert_called_once ()
104+
105+ @patch ("codexsync.app.sys.platform" , "win32" )
106+ @patch ("codexsync.app.confirm_process_termination" , return_value = True )
107+ def test_manual_confirmation_disabled_in_config_skips_prompt (self , confirm_mock ) -> None :
108+ cfg = _build_cfg ()
109+ cfg .process_detection .manual_terminate_confirmation = False
110+ detector = _DetectorStub ()
111+ main = [ProcessInfo (pid = 10 , name = "Codex.exe" )]
112+ snapshot = ProcessSnapshot (
113+ main_processes = main ,
114+ subprocesses = [],
115+ sandbox_detected = False ,
116+ )
117+
118+ _handle_running_codex (cfg , detector , snapshot , manual_override = None )
119+ self .assertEqual (detector .terminated , [main ])
120+ confirm_mock .assert_not_called ()
121+
122+ @patch ("codexsync.app.sys.platform" , "win32" )
123+ @patch ("codexsync.app.confirm_process_termination" , return_value = True )
124+ def test_override_true_forces_prompt_even_if_config_disabled (self , confirm_mock ) -> None :
125+ cfg = _build_cfg ()
126+ cfg .process_detection .manual_terminate_confirmation = False
127+ detector = _DetectorStub ()
128+ main = [ProcessInfo (pid = 10 , name = "Codex.exe" )]
129+ snapshot = ProcessSnapshot (
130+ main_processes = main ,
131+ subprocesses = [],
132+ sandbox_detected = False ,
133+ )
134+
135+ _handle_running_codex (cfg , detector , snapshot , manual_override = True )
136+ self .assertEqual (detector .terminated , [main ])
137+ confirm_mock .assert_called_once ()
138+
139+ @patch ("codexsync.app.sys.platform" , "win32" )
140+ @patch ("codexsync.app.confirm_process_termination" , return_value = True )
141+ def test_override_false_skips_prompt_even_if_config_enabled (self , confirm_mock ) -> None :
142+ cfg = _build_cfg ()
143+ cfg .process_detection .manual_terminate_confirmation = True
144+ detector = _DetectorStub ()
145+ main = [ProcessInfo (pid = 10 , name = "Codex.exe" )]
146+ snapshot = ProcessSnapshot (
147+ main_processes = main ,
148+ subprocesses = [],
149+ sandbox_detected = False ,
150+ )
151+
152+ _handle_running_codex (cfg , detector , snapshot , manual_override = False )
153+ self .assertEqual (detector .terminated , [main ])
154+ confirm_mock .assert_not_called ()
86155
87156 @patch ("codexsync.app.sys.platform" , "win32" )
88157 @patch ("codexsync.app.confirm_process_termination" , return_value = True )
0 commit comments