1 # -*- coding: utf-8 -*-
2 # Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
3 # See https://llvm.org/LICENSE.txt for license information.
4 # SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
7 from . import call_and_report
15 def prepare_cdb(name
, target_dir
):
16 target_file
= "build_{0}.json".format(name
)
17 this_dir
, _
= os
.path
.split(__file__
)
18 path
= os
.path
.abspath(os
.path
.join(this_dir
, "..", "src"))
19 source_dir
= os
.path
.join(path
, "compilation_database")
20 source_file
= os
.path
.join(source_dir
, target_file
+ ".in")
21 target_file
= os
.path
.join(target_dir
, "compile_commands.json")
22 with
open(source_file
, "r") as in_handle
:
23 with
open(target_file
, "w") as out_handle
:
24 for line
in in_handle
:
25 temp
= string
.Template(line
)
26 out_handle
.write(temp
.substitute(path
=path
))
30 def run_analyzer(directory
, cdb
, args
):
31 cmd
= ["analyze-build", "--cdb", cdb
, "--output", directory
] + args
32 return call_and_report(cmd
, [])
35 class OutputDirectoryTest(unittest
.TestCase
):
36 def test_regular_keeps_report_dir(self
):
37 with libear
.TemporaryDirectory() as tmpdir
:
38 cdb
= prepare_cdb("regular", tmpdir
)
39 exit_code
, reportdir
= run_analyzer(tmpdir
, cdb
, [])
40 self
.assertTrue(os
.path
.isdir(reportdir
))
42 def test_clear_deletes_report_dir(self
):
43 with libear
.TemporaryDirectory() as tmpdir
:
44 cdb
= prepare_cdb("clean", tmpdir
)
45 exit_code
, reportdir
= run_analyzer(tmpdir
, cdb
, [])
46 self
.assertFalse(os
.path
.isdir(reportdir
))
48 def test_clear_keeps_report_dir_when_asked(self
):
49 with libear
.TemporaryDirectory() as tmpdir
:
50 cdb
= prepare_cdb("clean", tmpdir
)
51 exit_code
, reportdir
= run_analyzer(tmpdir
, cdb
, ["--keep-empty"])
52 self
.assertTrue(os
.path
.isdir(reportdir
))
55 class ExitCodeTest(unittest
.TestCase
):
56 def test_regular_does_not_set_exit_code(self
):
57 with libear
.TemporaryDirectory() as tmpdir
:
58 cdb
= prepare_cdb("regular", tmpdir
)
59 exit_code
, __
= run_analyzer(tmpdir
, cdb
, [])
60 self
.assertFalse(exit_code
)
62 def test_clear_does_not_set_exit_code(self
):
63 with libear
.TemporaryDirectory() as tmpdir
:
64 cdb
= prepare_cdb("clean", tmpdir
)
65 exit_code
, __
= run_analyzer(tmpdir
, cdb
, [])
66 self
.assertFalse(exit_code
)
68 def test_regular_sets_exit_code_if_asked(self
):
69 with libear
.TemporaryDirectory() as tmpdir
:
70 cdb
= prepare_cdb("regular", tmpdir
)
71 exit_code
, __
= run_analyzer(tmpdir
, cdb
, ["--status-bugs"])
72 self
.assertTrue(exit_code
)
74 def test_clear_does_not_set_exit_code_if_asked(self
):
75 with libear
.TemporaryDirectory() as tmpdir
:
76 cdb
= prepare_cdb("clean", tmpdir
)
77 exit_code
, __
= run_analyzer(tmpdir
, cdb
, ["--status-bugs"])
78 self
.assertFalse(exit_code
)
80 def test_regular_sets_exit_code_if_asked_from_plist(self
):
81 with libear
.TemporaryDirectory() as tmpdir
:
82 cdb
= prepare_cdb("regular", tmpdir
)
83 exit_code
, __
= run_analyzer(tmpdir
, cdb
, ["--status-bugs", "--plist"])
84 self
.assertTrue(exit_code
)
86 def test_clear_does_not_set_exit_code_if_asked_from_plist(self
):
87 with libear
.TemporaryDirectory() as tmpdir
:
88 cdb
= prepare_cdb("clean", tmpdir
)
89 exit_code
, __
= run_analyzer(tmpdir
, cdb
, ["--status-bugs", "--plist"])
90 self
.assertFalse(exit_code
)
93 class OutputFormatTest(unittest
.TestCase
):
95 def get_html_count(directory
):
96 return len(glob
.glob(os
.path
.join(directory
, "report-*.html")))
99 def get_plist_count(directory
):
100 return len(glob
.glob(os
.path
.join(directory
, "report-*.plist")))
103 def get_sarif_count(directory
):
104 return len(glob
.glob(os
.path
.join(directory
, "result-*.sarif")))
106 def test_default_only_creates_html_report(self
):
107 with libear
.TemporaryDirectory() as tmpdir
:
108 cdb
= prepare_cdb("regular", tmpdir
)
109 exit_code
, reportdir
= run_analyzer(tmpdir
, cdb
, [])
110 self
.assertTrue(os
.path
.exists(os
.path
.join(reportdir
, "index.html")))
111 self
.assertEqual(self
.get_html_count(reportdir
), 2)
112 self
.assertEqual(self
.get_plist_count(reportdir
), 0)
113 self
.assertEqual(self
.get_sarif_count(reportdir
), 0)
115 def test_plist_and_html_creates_html_and_plist_reports(self
):
116 with libear
.TemporaryDirectory() as tmpdir
:
117 cdb
= prepare_cdb("regular", tmpdir
)
118 exit_code
, reportdir
= run_analyzer(tmpdir
, cdb
, ["--plist-html"])
119 self
.assertTrue(os
.path
.exists(os
.path
.join(reportdir
, "index.html")))
120 self
.assertEqual(self
.get_html_count(reportdir
), 2)
121 self
.assertEqual(self
.get_plist_count(reportdir
), 5)
122 self
.assertEqual(self
.get_sarif_count(reportdir
), 0)
124 def test_plist_only_creates_plist_report(self
):
125 with libear
.TemporaryDirectory() as tmpdir
:
126 cdb
= prepare_cdb("regular", tmpdir
)
127 exit_code
, reportdir
= run_analyzer(tmpdir
, cdb
, ["--plist"])
128 self
.assertFalse(os
.path
.exists(os
.path
.join(reportdir
, "index.html")))
129 self
.assertEqual(self
.get_html_count(reportdir
), 0)
130 self
.assertEqual(self
.get_plist_count(reportdir
), 5)
131 self
.assertEqual(self
.get_sarif_count(reportdir
), 0)
133 def test_sarif_only_creates_sarif_result(self
):
134 with libear
.TemporaryDirectory() as tmpdir
:
135 cdb
= prepare_cdb("regular", tmpdir
)
136 exit_code
, reportdir
= run_analyzer(tmpdir
, cdb
, ["--sarif"])
137 self
.assertFalse(os
.path
.exists(os
.path
.join(reportdir
, "index.html")))
139 os
.path
.exists(os
.path
.join(reportdir
, "results-merged.sarif"))
141 self
.assertEqual(self
.get_html_count(reportdir
), 0)
142 self
.assertEqual(self
.get_plist_count(reportdir
), 0)
143 self
.assertEqual(self
.get_sarif_count(reportdir
), 5)
145 def test_sarif_and_html_creates_sarif_and_html_reports(self
):
146 with libear
.TemporaryDirectory() as tmpdir
:
147 cdb
= prepare_cdb("regular", tmpdir
)
148 exit_code
, reportdir
= run_analyzer(tmpdir
, cdb
, ["--sarif-html"])
149 self
.assertTrue(os
.path
.exists(os
.path
.join(reportdir
, "index.html")))
151 os
.path
.exists(os
.path
.join(reportdir
, "results-merged.sarif"))
153 self
.assertEqual(self
.get_html_count(reportdir
), 2)
154 self
.assertEqual(self
.get_plist_count(reportdir
), 0)
155 self
.assertEqual(self
.get_sarif_count(reportdir
), 5)
158 class FailureReportTest(unittest
.TestCase
):
159 def test_broken_creates_failure_reports(self
):
160 with libear
.TemporaryDirectory() as tmpdir
:
161 cdb
= prepare_cdb("broken", tmpdir
)
162 exit_code
, reportdir
= run_analyzer(tmpdir
, cdb
, [])
163 self
.assertTrue(os
.path
.isdir(os
.path
.join(reportdir
, "failures")))
165 def test_broken_does_not_creates_failure_reports(self
):
166 with libear
.TemporaryDirectory() as tmpdir
:
167 cdb
= prepare_cdb("broken", tmpdir
)
168 exit_code
, reportdir
= run_analyzer(tmpdir
, cdb
, ["--no-failure-reports"])
169 self
.assertFalse(os
.path
.isdir(os
.path
.join(reportdir
, "failures")))
172 class TitleTest(unittest
.TestCase
):
173 def assertTitleEqual(self
, directory
, expected
):
177 re
.compile(r
"<title>(?P<page>.*)</title>"),
178 re
.compile(r
"<h1>(?P<head>.*)</h1>"),
182 index
= os
.path
.join(directory
, "index.html")
183 with
open(index
, "r") as handler
:
184 for line
in handler
.readlines():
185 for regex
in patterns
:
186 match
= regex
.match(line
.strip())
188 result
.update(match
.groupdict())
190 self
.assertEqual(result
["page"], result
["head"])
191 self
.assertEqual(result
["page"], expected
)
193 def test_default_title_in_report(self
):
194 with libear
.TemporaryDirectory() as tmpdir
:
195 cdb
= prepare_cdb("broken", tmpdir
)
196 exit_code
, reportdir
= run_analyzer(tmpdir
, cdb
, [])
197 self
.assertTitleEqual(reportdir
, "src - analyzer results")
199 def test_given_title_in_report(self
):
200 with libear
.TemporaryDirectory() as tmpdir
:
201 cdb
= prepare_cdb("broken", tmpdir
)
202 exit_code
, reportdir
= run_analyzer(
203 tmpdir
, cdb
, ["--html-title", "this is the title"]
205 self
.assertTitleEqual(reportdir
, "this is the title")