Coverage for tests / unit / tools / ruff / check / test_with_issues.py: 100%

40 statements  

« prev     ^ index     » next       coverage.py v7.13.0, created at 2026-04-03 18:53 +0000

1"""Tests for execute_ruff_check with issues found.""" 

2 

3from __future__ import annotations 

4 

5from typing import cast 

6from unittest.mock import MagicMock, patch 

7 

8from assertpy import assert_that 

9 

10from lintro.parsers.ruff.ruff_format_issue import RuffFormatIssue 

11from lintro.parsers.ruff.ruff_issue import RuffIssue 

12from lintro.tools.implementations.ruff.check import execute_ruff_check 

13 

14 

15def test_execute_ruff_check_with_lint_issues_returns_failure( 

16 mock_ruff_tool: MagicMock, 

17) -> None: 

18 """Return failure when lint issues are found. 

19 

20 Args: 

21 mock_ruff_tool: Mock RuffTool instance for testing. 

22 """ 

23 lint_issues = [ 

24 RuffIssue( 

25 file="test.py", 

26 line=1, 

27 column=1, 

28 code="F401", 

29 message="os imported but unused", 

30 fixable=True, 

31 fix_applicability="safe", 

32 ), 

33 ] 

34 

35 with ( 

36 patch( 

37 "lintro.tools.implementations.ruff.check.walk_files_with_excludes", 

38 return_value=["test.py"], 

39 ), 

40 patch( 

41 "lintro.tools.implementations.ruff.check.run_subprocess_with_timeout", 

42 return_value=(False, '[{"code": "F401"}]'), 

43 ), 

44 patch( 

45 "lintro.tools.implementations.ruff.check.parse_ruff_output", 

46 return_value=lint_issues, 

47 ), 

48 ): 

49 result = execute_ruff_check(mock_ruff_tool, ["/test/project"]) 

50 

51 assert_that(result.success).is_false() 

52 assert_that(result.issues_count).is_equal_to(1) 

53 assert_that(result.issues).is_not_none() 

54 assert_that(result.issues).is_length(1) 

55 first_issue = cast(RuffIssue, result.issues[0]) # type: ignore[index] # validated via is_not_none 

56 assert_that(first_issue.code).is_equal_to("F401") 

57 

58 

59def test_execute_ruff_check_with_multiple_lint_issues( 

60 mock_ruff_tool: MagicMock, 

61) -> None: 

62 """Return correct count when multiple lint issues are found. 

63 

64 Args: 

65 mock_ruff_tool: Mock RuffTool instance for testing. 

66 """ 

67 lint_issues = [ 

68 RuffIssue(file="test.py", line=1, column=1, code="F401", message="unused"), 

69 RuffIssue(file="test.py", line=5, column=89, code="E501", message="too long"), 

70 RuffIssue(file="test.py", line=10, column=1, code="W291", message="whitespace"), 

71 ] 

72 

73 with ( 

74 patch( 

75 "lintro.tools.implementations.ruff.check.walk_files_with_excludes", 

76 return_value=["test.py"], 

77 ), 

78 patch( 

79 "lintro.tools.implementations.ruff.check.run_subprocess_with_timeout", 

80 return_value=(False, "[]"), 

81 ), 

82 patch( 

83 "lintro.tools.implementations.ruff.check.parse_ruff_output", 

84 return_value=lint_issues, 

85 ), 

86 ): 

87 result = execute_ruff_check(mock_ruff_tool, ["/test/project"]) 

88 

89 assert_that(result.success).is_false() 

90 assert_that(result.issues_count).is_equal_to(3) 

91 assert_that(result.issues).is_length(3) 

92 

93 

94def test_execute_ruff_check_with_format_issues_returns_failure( 

95 mock_ruff_tool: MagicMock, 

96) -> None: 

97 """Return failure when format issues are found. 

98 

99 Args: 

100 mock_ruff_tool: Mock RuffTool instance for testing. 

101 """ 

102 mock_ruff_tool.options["format_check"] = True 

103 

104 with ( 

105 patch( 

106 "lintro.tools.implementations.ruff.check.walk_files_with_excludes", 

107 return_value=["test.py"], 

108 ), 

109 patch( 

110 "lintro.tools.implementations.ruff.check.run_subprocess_with_timeout", 

111 return_value=(True, ""), 

112 ), 

113 patch( 

114 "lintro.tools.implementations.ruff.check.parse_ruff_output", 

115 return_value=[], 

116 ), 

117 patch( 

118 "lintro.tools.implementations.ruff.check.parse_ruff_format_check_output", 

119 return_value=["test.py"], 

120 ), 

121 ): 

122 result = execute_ruff_check(mock_ruff_tool, ["/test/project"]) 

123 

124 assert_that(result.success).is_false() 

125 assert_that(result.issues_count).is_equal_to(1) 

126 # Format issues should be RuffFormatIssue instances 

127 assert_that(result.issues).is_not_none() 

128 assert_that(isinstance(result.issues[0], RuffFormatIssue)).is_true() # type: ignore[index] # validated via is_not_none 

129 

130 

131def test_execute_ruff_check_combines_lint_and_format_issues( 

132 mock_ruff_tool: MagicMock, 

133) -> None: 

134 """Combine lint and format issues in result. 

135 

136 Args: 

137 mock_ruff_tool: Mock RuffTool instance for testing. 

138 """ 

139 mock_ruff_tool.options["format_check"] = True 

140 lint_issues = [ 

141 RuffIssue(file="test.py", line=1, column=1, code="F401", message="unused"), 

142 ] 

143 

144 with ( 

145 patch( 

146 "lintro.tools.implementations.ruff.check.walk_files_with_excludes", 

147 return_value=["test.py", "other.py"], 

148 ), 

149 patch( 

150 "lintro.tools.implementations.ruff.check.run_subprocess_with_timeout", 

151 return_value=(False, "[]"), 

152 ), 

153 patch( 

154 "lintro.tools.implementations.ruff.check.parse_ruff_output", 

155 return_value=lint_issues, 

156 ), 

157 patch( 

158 "lintro.tools.implementations.ruff.check.parse_ruff_format_check_output", 

159 return_value=["other.py"], 

160 ), 

161 ): 

162 result = execute_ruff_check(mock_ruff_tool, ["/test/project"]) 

163 

164 assert_that(result.success).is_false() 

165 assert_that(result.issues_count).is_equal_to(2) 

166 assert_that(result.issues).is_length(2)