1212from claudecode .github_action_audit import main
1313
1414
15+ def _mock_multiphase_success (mock_runner , findings = None ):
16+ """Configure runner mock for strict multi-phase orchestration."""
17+ findings = findings or []
18+ mock_runner .run_prompt .side_effect = [
19+ (True , "" , {"skip_review" : False , "reason" : "" , "risk_level" : "medium" }), # triage
20+ (True , "" , {"claude_md_files" : [], "change_summary" : "" , "hotspots" : [], "priority_files" : []}), # context
21+ (True , "" , {"findings" : findings }), # compliance
22+ (True , "" , {"findings" : []}), # quality
23+ (True , "" , {"findings" : []}), # security
24+ (
25+ True ,
26+ "" ,
27+ {
28+ "validated_findings" : [
29+ {"finding_index" : idx , "keep" : True , "confidence" : 0.95 , "reason" : "valid" }
30+ for idx in range (len (findings ))
31+ ]
32+ },
33+ ), # validation
34+ ]
35+
36+
1537class TestMainFunction :
1638 """Test main function execution flow."""
1739
@@ -232,20 +254,7 @@ def test_main_successful_audit_no_findings(self, mock_client_class, mock_runner_
232254
233255 mock_runner = Mock ()
234256 mock_runner .validate_claude_available .return_value = (True , "" )
235- # Unified review - single call
236- mock_runner .run_code_review .return_value = (
237- True ,
238- "" ,
239- {
240- 'findings' : [],
241- 'analysis_summary' : {
242- 'files_reviewed' : 5 ,
243- 'high_severity' : 0 ,
244- 'medium_severity' : 0 ,
245- 'low_severity' : 0
246- }
247- }
248- )
257+ _mock_multiphase_success (mock_runner , findings = [])
249258 mock_runner_class .return_value = mock_runner
250259
251260 mock_filter = Mock ()
@@ -299,6 +308,7 @@ def test_main_successful_audit_with_findings(self, mock_client_class, mock_runne
299308 }
300309 mock_client .get_pr_diff .return_value = "diff content"
301310 mock_client ._is_excluded .return_value = False # Don't exclude any files in tests
311+ mock_client .is_excluded .return_value = False
302312 mock_client_class .return_value = mock_client
303313
304314 findings = [
@@ -320,20 +330,7 @@ def test_main_successful_audit_with_findings(self, mock_client_class, mock_runne
320330
321331 mock_runner = Mock ()
322332 mock_runner .validate_claude_available .return_value = (True , "" )
323- # Unified review - single call with all findings
324- mock_runner .run_code_review .return_value = (
325- True ,
326- "" ,
327- {
328- 'findings' : findings ,
329- 'analysis_summary' : {
330- 'files_reviewed' : 2 ,
331- 'high_severity' : 1 ,
332- 'medium_severity' : 1 ,
333- 'low_severity' : 0
334- }
335- }
336- )
333+ _mock_multiphase_success (mock_runner , findings = findings )
337334 mock_runner_class .return_value = mock_runner
338335
339336 # Filter keeps only high severity
@@ -391,13 +388,14 @@ def test_main_with_full_filter(self, mock_client_class, mock_runner_class,
391388 }
392389 mock_client .get_pr_diff .return_value = "diff content"
393390 mock_client ._is_excluded .return_value = False # Don't exclude any files in tests
391+ mock_client .is_excluded .return_value = False
394392 mock_client_class .return_value = mock_client
395393
396394 findings = [{'file' : 'test.py' , 'line' : 10 , 'severity' : 'HIGH' , 'description' : 'Issue' }]
397395
398396 mock_runner = Mock ()
399397 mock_runner .validate_claude_available .return_value = (True , "" )
400- mock_runner . run_code_review . return_value = ( True , "" , { ' findings' : findings } )
398+ _mock_multiphase_success ( mock_runner , findings = findings )
401399 mock_runner_class .return_value = mock_runner
402400
403401 mock_prompt_func .return_value = "prompt"
@@ -450,6 +448,7 @@ def test_main_filter_failure_keeps_all_findings(self, mock_client_class, mock_ru
450448 mock_client .get_pr_data .return_value = {'number' : 123 , 'title' : 'Test' , 'body' : '' }
451449 mock_client .get_pr_diff .return_value = "diff"
452450 mock_client ._is_excluded .return_value = False # Don't exclude any files in tests
451+ mock_client .is_excluded .return_value = False
453452 mock_client_class .return_value = mock_client
454453
455454 findings = [
@@ -459,7 +458,7 @@ def test_main_filter_failure_keeps_all_findings(self, mock_client_class, mock_ru
459458
460459 mock_runner = Mock ()
461460 mock_runner .validate_claude_available .return_value = (True , "" )
462- mock_runner . run_code_review . return_value = ( True , "" , { ' findings' : findings } )
461+ _mock_multiphase_success ( mock_runner , findings = findings )
463462 mock_runner_class .return_value = mock_runner
464463
465464 mock_prompt_func .return_value = "prompt"
@@ -539,11 +538,7 @@ def test_audit_failure(self, mock_client_class, mock_runner_class,
539538
540539 mock_runner = Mock ()
541540 mock_runner .validate_claude_available .return_value = (True , "" )
542- mock_runner .run_code_review .return_value = (
543- False ,
544- "Claude execution failed" ,
545- {}
546- )
541+ mock_runner .run_prompt .return_value = (False , "Claude execution failed" , {})
547542 mock_runner_class .return_value = mock_runner
548543
549544 mock_filter_class .return_value = Mock ()
@@ -582,6 +577,7 @@ def test_findings_have_correct_review_type(self, mock_client_class, mock_runner_
582577 mock_client .get_pr_data .return_value = {'number' : 123 , 'title' : 'Test' , 'body' : '' }
583578 mock_client .get_pr_diff .return_value = "diff"
584579 mock_client ._is_excluded .return_value = False
580+ mock_client .is_excluded .return_value = False
585581 mock_client_class .return_value = mock_client
586582
587583 # Mixed findings - security and non-security
@@ -592,7 +588,7 @@ def test_findings_have_correct_review_type(self, mock_client_class, mock_runner_
592588
593589 mock_runner = Mock ()
594590 mock_runner .validate_claude_available .return_value = (True , "" )
595- mock_runner . run_code_review . return_value = ( True , "" , { ' findings' : findings } )
591+ _mock_multiphase_success ( mock_runner , findings = findings )
596592 mock_runner_class .return_value = mock_runner
597593
598594 # Filter passes through all findings
@@ -644,6 +640,7 @@ def test_review_type_not_overwritten_if_already_set(self, mock_client_class, moc
644640 mock_client .get_pr_data .return_value = {'number' : 123 , 'title' : 'Test' , 'body' : '' }
645641 mock_client .get_pr_diff .return_value = "diff"
646642 mock_client ._is_excluded .return_value = False
643+ mock_client .is_excluded .return_value = False
647644 mock_client_class .return_value = mock_client
648645
649646 # Finding already has review_type set (e.g., from a custom analyzer)
@@ -654,7 +651,7 @@ def test_review_type_not_overwritten_if_already_set(self, mock_client_class, moc
654651
655652 mock_runner = Mock ()
656653 mock_runner .validate_claude_available .return_value = (True , "" )
657- mock_runner . run_code_review . return_value = ( True , "" , { ' findings' : findings } )
654+ _mock_multiphase_success ( mock_runner , findings = findings )
658655 mock_runner_class .return_value = mock_runner
659656
660657 mock_filter = Mock ()
0 commit comments