[go: nahoru, domu]

blob: 18e3c6e74d4bd29aceaed5c411749f6bddd99248 [file] [log] [blame]
marja@chromium.org2299dcf2012-11-15 19:56:241#!/usr/bin/env python
2# Copyright (c) 2012 The Chromium Authors. All rights reserved.
3# Use of this source code is governed by a BSD-style license that can be
4# found in the LICENSE file.
5
yoz@chromium.org99171a92014-06-03 08:44:476import glob
7import json
marja@chromium.org2299dcf2012-11-15 19:56:248import os
9import re
yoz@chromium.org99171a92014-06-03 08:44:4710import subprocess
11import sys
marja@chromium.org2299dcf2012-11-15 19:56:2412import unittest
13
14import PRESUBMIT
glidere61efad2015-02-18 17:39:4315from PRESUBMIT_test_mocks import MockChange, MockFile, MockAffectedFile
gayane3dff8c22014-12-04 17:09:5116from PRESUBMIT_test_mocks import MockInputApi, MockOutputApi
marja@chromium.org2299dcf2012-11-15 19:56:2417
yoz@chromium.org99171a92014-06-03 08:44:4718_TEST_DATA_DIR = 'base/test/data/presubmit'
19
marja@chromium.org2299dcf2012-11-15 19:56:2420class IncludeOrderTest(unittest.TestCase):
21 def testSystemHeaderOrder(self):
22 scope = [(1, '#include <csystem.h>'),
23 (2, '#include <cppsystem>'),
24 (3, '#include "acustom.h"')]
25 all_linenums = [linenum for (linenum, _) in scope]
26 mock_input_api = MockInputApi()
27 warnings = PRESUBMIT._CheckIncludeOrderForScope(scope, mock_input_api,
28 '', all_linenums)
29 self.assertEqual(0, len(warnings))
30
31 def testSystemHeaderOrderMismatch1(self):
32 scope = [(10, '#include <cppsystem>'),
33 (20, '#include <csystem.h>'),
34 (30, '#include "acustom.h"')]
35 all_linenums = [linenum for (linenum, _) in scope]
36 mock_input_api = MockInputApi()
37 warnings = PRESUBMIT._CheckIncludeOrderForScope(scope, mock_input_api,
38 '', all_linenums)
39 self.assertEqual(1, len(warnings))
40 self.assertTrue('20' in warnings[0])
41
42 def testSystemHeaderOrderMismatch2(self):
43 scope = [(10, '#include <cppsystem>'),
44 (20, '#include "acustom.h"'),
45 (30, '#include <csystem.h>')]
46 all_linenums = [linenum for (linenum, _) in scope]
47 mock_input_api = MockInputApi()
48 warnings = PRESUBMIT._CheckIncludeOrderForScope(scope, mock_input_api,
49 '', all_linenums)
50 self.assertEqual(1, len(warnings))
51 self.assertTrue('30' in warnings[0])
52
53 def testSystemHeaderOrderMismatch3(self):
54 scope = [(10, '#include "acustom.h"'),
55 (20, '#include <csystem.h>'),
56 (30, '#include <cppsystem>')]
57 all_linenums = [linenum for (linenum, _) in scope]
58 mock_input_api = MockInputApi()
59 warnings = PRESUBMIT._CheckIncludeOrderForScope(scope, mock_input_api,
60 '', all_linenums)
61 self.assertEqual(2, len(warnings))
62 self.assertTrue('20' in warnings[0])
63 self.assertTrue('30' in warnings[1])
64
65 def testAlphabeticalOrderMismatch(self):
66 scope = [(10, '#include <csystem.h>'),
67 (15, '#include <bsystem.h>'),
68 (20, '#include <cppsystem>'),
69 (25, '#include <bppsystem>'),
70 (30, '#include "bcustom.h"'),
71 (35, '#include "acustom.h"')]
72 all_linenums = [linenum for (linenum, _) in scope]
73 mock_input_api = MockInputApi()
74 warnings = PRESUBMIT._CheckIncludeOrderForScope(scope, mock_input_api,
75 '', all_linenums)
76 self.assertEqual(3, len(warnings))
77 self.assertTrue('15' in warnings[0])
78 self.assertTrue('25' in warnings[1])
79 self.assertTrue('35' in warnings[2])
80
81 def testSpecialFirstInclude1(self):
82 mock_input_api = MockInputApi()
83 contents = ['#include "some/path/foo.h"',
84 '#include "a/header.h"']
85 mock_file = MockFile('some/path/foo.cc', contents)
86 warnings = PRESUBMIT._CheckIncludeOrderInFile(
marja@chromium.orgac294a12012-12-06 16:38:4387 mock_input_api, mock_file, range(1, len(contents) + 1))
marja@chromium.org2299dcf2012-11-15 19:56:2488 self.assertEqual(0, len(warnings))
89
90 def testSpecialFirstInclude2(self):
91 mock_input_api = MockInputApi()
92 contents = ['#include "some/other/path/foo.h"',
93 '#include "a/header.h"']
94 mock_file = MockFile('some/path/foo.cc', contents)
95 warnings = PRESUBMIT._CheckIncludeOrderInFile(
marja@chromium.orgac294a12012-12-06 16:38:4396 mock_input_api, mock_file, range(1, len(contents) + 1))
marja@chromium.org2299dcf2012-11-15 19:56:2497 self.assertEqual(0, len(warnings))
98
99 def testSpecialFirstInclude3(self):
100 mock_input_api = MockInputApi()
101 contents = ['#include "some/path/foo.h"',
102 '#include "a/header.h"']
103 mock_file = MockFile('some/path/foo_platform.cc', contents)
104 warnings = PRESUBMIT._CheckIncludeOrderInFile(
marja@chromium.orgac294a12012-12-06 16:38:43105 mock_input_api, mock_file, range(1, len(contents) + 1))
marja@chromium.org2299dcf2012-11-15 19:56:24106 self.assertEqual(0, len(warnings))
107
108 def testSpecialFirstInclude4(self):
109 mock_input_api = MockInputApi()
110 contents = ['#include "some/path/bar.h"',
111 '#include "a/header.h"']
112 mock_file = MockFile('some/path/foo_platform.cc', contents)
113 warnings = PRESUBMIT._CheckIncludeOrderInFile(
marja@chromium.orgac294a12012-12-06 16:38:43114 mock_input_api, mock_file, range(1, len(contents) + 1))
marja@chromium.org2299dcf2012-11-15 19:56:24115 self.assertEqual(1, len(warnings))
116 self.assertTrue('2' in warnings[0])
117
marja@chromium.orgac294a12012-12-06 16:38:43118 def testSpecialFirstInclude5(self):
119 mock_input_api = MockInputApi()
120 contents = ['#include "some/other/path/foo.h"',
121 '#include "a/header.h"']
122 mock_file = MockFile('some/path/foo-suffix.h', contents)
123 warnings = PRESUBMIT._CheckIncludeOrderInFile(
124 mock_input_api, mock_file, range(1, len(contents) + 1))
125 self.assertEqual(0, len(warnings))
126
erikwright@chromium.org3e83618c2013-10-09 22:32:33127 def testSpecialFirstInclude6(self):
128 mock_input_api = MockInputApi()
129 contents = ['#include "some/other/path/foo_win.h"',
130 '#include <set>',
131 '#include "a/header.h"']
132 mock_file = MockFile('some/path/foo_unittest_win.h', contents)
133 warnings = PRESUBMIT._CheckIncludeOrderInFile(
134 mock_input_api, mock_file, range(1, len(contents) + 1))
135 self.assertEqual(0, len(warnings))
136
marja@chromium.org2299dcf2012-11-15 19:56:24137 def testOrderAlreadyWrong(self):
138 scope = [(1, '#include "b.h"'),
139 (2, '#include "a.h"'),
140 (3, '#include "c.h"')]
141 mock_input_api = MockInputApi()
142 warnings = PRESUBMIT._CheckIncludeOrderForScope(scope, mock_input_api,
143 '', [3])
144 self.assertEqual(0, len(warnings))
145
146 def testConflictAdded1(self):
147 scope = [(1, '#include "a.h"'),
148 (2, '#include "c.h"'),
149 (3, '#include "b.h"')]
150 mock_input_api = MockInputApi()
151 warnings = PRESUBMIT._CheckIncludeOrderForScope(scope, mock_input_api,
152 '', [2])
153 self.assertEqual(1, len(warnings))
154 self.assertTrue('3' in warnings[0])
155
156 def testConflictAdded2(self):
157 scope = [(1, '#include "c.h"'),
158 (2, '#include "b.h"'),
159 (3, '#include "d.h"')]
160 mock_input_api = MockInputApi()
161 warnings = PRESUBMIT._CheckIncludeOrderForScope(scope, mock_input_api,
162 '', [2])
163 self.assertEqual(1, len(warnings))
164 self.assertTrue('2' in warnings[0])
165
marja@chromium.org2309b0fa02012-11-16 12:18:27166 def testIfElifElseEndif(self):
167 mock_input_api = MockInputApi()
168 contents = ['#include "e.h"',
marja@chromium.orgac294a12012-12-06 16:38:43169 '#define foo',
170 '#include "f.h"',
171 '#undef foo',
172 '#include "e.h"',
marja@chromium.org2309b0fa02012-11-16 12:18:27173 '#if foo',
174 '#include "d.h"',
175 '#elif bar',
176 '#include "c.h"',
177 '#else',
178 '#include "b.h"',
179 '#endif',
180 '#include "a.h"']
181 mock_file = MockFile('', contents)
182 warnings = PRESUBMIT._CheckIncludeOrderInFile(
marja@chromium.orgac294a12012-12-06 16:38:43183 mock_input_api, mock_file, range(1, len(contents) + 1))
marja@chromium.org2309b0fa02012-11-16 12:18:27184 self.assertEqual(0, len(warnings))
185
marja@chromium.org23093b62013-09-20 12:16:30186 def testExcludedIncludes(self):
marja@chromium.org962f117e2012-11-22 18:11:56187 # #include <sys/...>'s can appear in any order.
188 mock_input_api = MockInputApi()
189 contents = ['#include <sys/b.h>',
190 '#include <sys/a.h>']
191 mock_file = MockFile('', contents)
192 warnings = PRESUBMIT._CheckIncludeOrderInFile(
marja@chromium.orgac294a12012-12-06 16:38:43193 mock_input_api, mock_file, range(1, len(contents) + 1))
marja@chromium.org962f117e2012-11-22 18:11:56194 self.assertEqual(0, len(warnings))
195
marja@chromium.org23093b62013-09-20 12:16:30196 contents = ['#include <atlbase.h>',
197 '#include <aaa.h>']
198 mock_file = MockFile('', contents)
199 warnings = PRESUBMIT._CheckIncludeOrderInFile(
200 mock_input_api, mock_file, range(1, len(contents) + 1))
201 self.assertEqual(0, len(warnings))
202
203 contents = ['#include "build/build_config.h"',
204 '#include "aaa.h"']
205 mock_file = MockFile('', contents)
206 warnings = PRESUBMIT._CheckIncludeOrderInFile(
207 mock_input_api, mock_file, range(1, len(contents) + 1))
208 self.assertEqual(0, len(warnings))
209
marja@chromium.orgac294a12012-12-06 16:38:43210 def testCheckOnlyCFiles(self):
211 mock_input_api = MockInputApi()
212 mock_output_api = MockOutputApi()
213 contents = ['#include <b.h>',
214 '#include <a.h>']
215 mock_file_cc = MockFile('something.cc', contents)
216 mock_file_h = MockFile('something.h', contents)
217 mock_file_other = MockFile('something.py', contents)
218 mock_input_api.files = [mock_file_cc, mock_file_h, mock_file_other]
219 warnings = PRESUBMIT._CheckIncludeOrder(mock_input_api, mock_output_api)
220 self.assertEqual(1, len(warnings))
221 self.assertEqual(2, len(warnings[0].items))
wez@chromium.orgf7051d52013-04-02 18:31:42222 self.assertEqual('promptOrNotify', warnings[0].type)
marja@chromium.orgac294a12012-12-06 16:38:43223
marja@chromium.org0e5c1852012-12-18 20:17:11224 def testUncheckableIncludes(self):
225 mock_input_api = MockInputApi()
226 contents = ['#include <windows.h>',
b.kelemen@samsung.com4436c9e2014-01-07 23:19:54227 '#include "b.h"',
marja@chromium.org0e5c1852012-12-18 20:17:11228 '#include "a.h"']
229 mock_file = MockFile('', contents)
230 warnings = PRESUBMIT._CheckIncludeOrderInFile(
231 mock_input_api, mock_file, range(1, len(contents) + 1))
b.kelemen@samsung.com4436c9e2014-01-07 23:19:54232 self.assertEqual(1, len(warnings))
marja@chromium.org0e5c1852012-12-18 20:17:11233
234 contents = ['#include "gpu/command_buffer/gles_autogen.h"',
b.kelemen@samsung.com4436c9e2014-01-07 23:19:54235 '#include "b.h"',
marja@chromium.org0e5c1852012-12-18 20:17:11236 '#include "a.h"']
237 mock_file = MockFile('', contents)
238 warnings = PRESUBMIT._CheckIncludeOrderInFile(
239 mock_input_api, mock_file, range(1, len(contents) + 1))
b.kelemen@samsung.com4436c9e2014-01-07 23:19:54240 self.assertEqual(1, len(warnings))
marja@chromium.org0e5c1852012-12-18 20:17:11241
242 contents = ['#include "gl_mock_autogen.h"',
b.kelemen@samsung.com4436c9e2014-01-07 23:19:54243 '#include "b.h"',
marja@chromium.org0e5c1852012-12-18 20:17:11244 '#include "a.h"']
245 mock_file = MockFile('', contents)
246 warnings = PRESUBMIT._CheckIncludeOrderInFile(
247 mock_input_api, mock_file, range(1, len(contents) + 1))
b.kelemen@samsung.com4436c9e2014-01-07 23:19:54248 self.assertEqual(1, len(warnings))
marja@chromium.org0e5c1852012-12-18 20:17:11249
250 contents = ['#include "ipc/some_macros.h"',
b.kelemen@samsung.com4436c9e2014-01-07 23:19:54251 '#include "b.h"',
marja@chromium.org0e5c1852012-12-18 20:17:11252 '#include "a.h"']
253 mock_file = MockFile('', contents)
254 warnings = PRESUBMIT._CheckIncludeOrderInFile(
255 mock_input_api, mock_file, range(1, len(contents) + 1))
b.kelemen@samsung.com4436c9e2014-01-07 23:19:54256 self.assertEqual(1, len(warnings))
marja@chromium.org0e5c1852012-12-18 20:17:11257
marja@chromium.org2299dcf2012-11-15 19:56:24258
dbeam@chromium.orgb00342e7f2013-03-26 16:21:54259class VersionControlConflictsTest(unittest.TestCase):
dbeam@chromium.org70ca77752012-11-20 03:45:03260 def testTypicalConflict(self):
261 lines = ['<<<<<<< HEAD',
262 ' base::ScopedTempDir temp_dir_;',
263 '=======',
264 ' ScopedTempDir temp_dir_;',
265 '>>>>>>> master']
266 errors = PRESUBMIT._CheckForVersionControlConflictsInFile(
267 MockInputApi(), MockFile('some/path/foo_platform.cc', lines))
268 self.assertEqual(3, len(errors))
269 self.assertTrue('1' in errors[0])
270 self.assertTrue('3' in errors[1])
271 self.assertTrue('5' in errors[2])
272
mcasasb7440c282015-02-04 14:52:19273class UmaHistogramChangeMatchedOrNotTest(unittest.TestCase):
274 def testTypicalCorrectlyMatchedChange(self):
275 diff_cc = ['UMA_HISTOGRAM_BOOL("Bla.Foo.Dummy", true)']
276 diff_xml = ['<histogram name="Bla.Foo.Dummy"> </histogram>']
277 mock_input_api = MockInputApi()
278 mock_input_api.files = [
279 MockFile('some/path/foo.cc', diff_cc),
280 MockFile('tools/metrics/histograms/histograms.xml', diff_xml),
281 ]
282 warnings = PRESUBMIT._CheckUmaHistogramChanges(mock_input_api,
283 MockOutputApi())
284 self.assertEqual(0, len(warnings))
285
286 def testTypicalNotMatchedChange(self):
287 diff_cc = ['UMA_HISTOGRAM_BOOL("Bla.Foo.Dummy", true)']
288 mock_input_api = MockInputApi()
289 mock_input_api.files = [MockFile('some/path/foo.cc', diff_cc)]
290 warnings = PRESUBMIT._CheckUmaHistogramChanges(mock_input_api,
291 MockOutputApi())
292 self.assertEqual(1, len(warnings))
293 self.assertEqual('warning', warnings[0].type)
294
295 def testTypicalNotMatchedChangeViaSuffixes(self):
296 diff_cc = ['UMA_HISTOGRAM_BOOL("Bla.Foo.Dummy", true)']
297 diff_xml = ['<histogram_suffixes name="SuperHistogram">',
298 ' <suffix name="Dummy"/>',
299 ' <affected-histogram name="Snafu.Dummy"/>',
300 '</histogram>']
301 mock_input_api = MockInputApi()
302 mock_input_api.files = [
303 MockFile('some/path/foo.cc', diff_cc),
304 MockFile('tools/metrics/histograms/histograms.xml', diff_xml),
305 ]
306 warnings = PRESUBMIT._CheckUmaHistogramChanges(mock_input_api,
307 MockOutputApi())
308 self.assertEqual(1, len(warnings))
309 self.assertEqual('warning', warnings[0].type)
310
311 def testTypicalCorrectlyMatchedChangeViaSuffixes(self):
312 diff_cc = ['UMA_HISTOGRAM_BOOL("Bla.Foo.Dummy", true)']
313 diff_xml = ['<histogram_suffixes name="SuperHistogram">',
314 ' <suffix name="Dummy"/>',
315 ' <affected-histogram name="Bla.Foo"/>',
316 '</histogram>']
317 mock_input_api = MockInputApi()
318 mock_input_api.files = [
319 MockFile('some/path/foo.cc', diff_cc),
320 MockFile('tools/metrics/histograms/histograms.xml', diff_xml),
321 ]
322 warnings = PRESUBMIT._CheckUmaHistogramChanges(mock_input_api,
323 MockOutputApi())
324 self.assertEqual(0, len(warnings))
325
326 def testTypicalCorrectlyMatchedChangeViaSuffixesWithSeparator(self):
327 diff_cc = ['UMA_HISTOGRAM_BOOL("Snafu_Dummy", true)']
328 diff_xml = ['<histogram_suffixes name="SuperHistogram" separator="_">',
329 ' <suffix name="Dummy"/>',
330 ' <affected-histogram name="Snafu"/>',
331 '</histogram>']
332 mock_input_api = MockInputApi()
333 mock_input_api.files = [
334 MockFile('some/path/foo.cc', diff_cc),
335 MockFile('tools/metrics/histograms/histograms.xml', diff_xml),
336 ]
337 warnings = PRESUBMIT._CheckUmaHistogramChanges(mock_input_api,
338 MockOutputApi())
339 self.assertEqual(0, len(warnings))
dbeam@chromium.org70ca77752012-11-20 03:45:03340
enne@chromium.orgb8079ae4a2012-12-05 19:56:49341class BadExtensionsTest(unittest.TestCase):
342 def testBadRejFile(self):
343 mock_input_api = MockInputApi()
344 mock_input_api.files = [
345 MockFile('some/path/foo.cc', ''),
346 MockFile('some/path/foo.cc.rej', ''),
347 MockFile('some/path2/bar.h.rej', ''),
348 ]
349
350 results = PRESUBMIT._CheckPatchFiles(mock_input_api, MockOutputApi())
351 self.assertEqual(1, len(results))
352 self.assertEqual(2, len(results[0].items))
353 self.assertTrue('foo.cc.rej' in results[0].items[0])
354 self.assertTrue('bar.h.rej' in results[0].items[1])
355
356 def testBadOrigFile(self):
357 mock_input_api = MockInputApi()
358 mock_input_api.files = [
359 MockFile('other/path/qux.h.orig', ''),
360 MockFile('other/path/qux.h', ''),
361 MockFile('other/path/qux.cc', ''),
362 ]
363
364 results = PRESUBMIT._CheckPatchFiles(mock_input_api, MockOutputApi())
365 self.assertEqual(1, len(results))
366 self.assertEqual(1, len(results[0].items))
367 self.assertTrue('qux.h.orig' in results[0].items[0])
368
369 def testGoodFiles(self):
370 mock_input_api = MockInputApi()
371 mock_input_api.files = [
372 MockFile('other/path/qux.h', ''),
373 MockFile('other/path/qux.cc', ''),
374 ]
375 results = PRESUBMIT._CheckPatchFiles(mock_input_api, MockOutputApi())
376 self.assertEqual(0, len(results))
377
378
glidere61efad2015-02-18 17:39:43379class CheckSingletonInHeadersTest(unittest.TestCase):
380 def testSingletonInArbitraryHeader(self):
381 diff_singleton_h = ['base::subtle::AtomicWord '
382 'Singleton<Type, Traits, DifferentiatingType>::']
383 diff_foo_h = ['// Singleton<Foo> in comment.',
384 'friend class Singleton<Foo>']
385 diff_bad_h = ['Foo* foo = Singleton<Foo>::get();']
386 mock_input_api = MockInputApi()
387 mock_input_api.files = [MockAffectedFile('base/memory/singleton.h',
388 diff_singleton_h),
389 MockAffectedFile('foo.h', diff_foo_h),
390 MockAffectedFile('bad.h', diff_bad_h)]
391 warnings = PRESUBMIT._CheckSingletonInHeaders(mock_input_api,
392 MockOutputApi())
393 self.assertEqual(1, len(warnings))
394 self.assertEqual('error', warnings[0].type)
395 self.assertTrue('Found Singleton<T>' in warnings[0].message)
396
397 def testSingletonInCC(self):
398 diff_cc = ['Foo* foo = Singleton<Foo>::get();']
399 mock_input_api = MockInputApi()
400 mock_input_api.files = [MockAffectedFile('some/path/foo.cc', diff_cc)]
401 warnings = PRESUBMIT._CheckSingletonInHeaders(mock_input_api,
402 MockOutputApi())
403 self.assertEqual(0, len(warnings))
404
405
dbeam@chromium.orgb00342e7f2013-03-26 16:21:54406class InvalidOSMacroNamesTest(unittest.TestCase):
407 def testInvalidOSMacroNames(self):
408 lines = ['#if defined(OS_WINDOWS)',
409 ' #elif defined(OS_WINDOW)',
410 ' # if defined(OS_MACOSX) || defined(OS_CHROME)',
411 '# else // defined(OS_MAC)',
412 '#endif // defined(OS_MACOS)']
413 errors = PRESUBMIT._CheckForInvalidOSMacrosInFile(
414 MockInputApi(), MockFile('some/path/foo_platform.cc', lines))
415 self.assertEqual(len(lines), len(errors))
416 self.assertTrue(':1 OS_WINDOWS' in errors[0])
417 self.assertTrue('(did you mean OS_WIN?)' in errors[0])
418
419 def testValidOSMacroNames(self):
420 lines = ['#if defined(%s)' % m for m in PRESUBMIT._VALID_OS_MACROS]
421 errors = PRESUBMIT._CheckForInvalidOSMacrosInFile(
422 MockInputApi(), MockFile('some/path/foo_platform.cc', lines))
423 self.assertEqual(0, len(errors))
424
425
lliabraa35bab3932014-10-01 12:16:44426class InvalidIfDefinedMacroNamesTest(unittest.TestCase):
427 def testInvalidIfDefinedMacroNames(self):
428 lines = ['#if defined(TARGET_IPHONE_SIMULATOR)',
429 '#if !defined(TARGET_IPHONE_SIMULATOR)',
430 '#elif defined(TARGET_IPHONE_SIMULATOR)',
431 '#ifdef TARGET_IPHONE_SIMULATOR',
432 ' # ifdef TARGET_IPHONE_SIMULATOR',
433 '# if defined(VALID) || defined(TARGET_IPHONE_SIMULATOR)',
434 '# else // defined(TARGET_IPHONE_SIMULATOR)',
435 '#endif // defined(TARGET_IPHONE_SIMULATOR)',]
436 errors = PRESUBMIT._CheckForInvalidIfDefinedMacrosInFile(
437 MockInputApi(), MockFile('some/path/source.mm', lines))
438 self.assertEqual(len(lines), len(errors))
439
440 def testValidIfDefinedMacroNames(self):
441 lines = ['#if defined(FOO)',
442 '#ifdef BAR',]
443 errors = PRESUBMIT._CheckForInvalidIfDefinedMacrosInFile(
444 MockInputApi(), MockFile('some/path/source.cc', lines))
445 self.assertEqual(0, len(errors))
446
447
tony@chromium.orgf32e2d1e2013-07-26 21:39:08448class CheckAddedDepsHaveTetsApprovalsTest(unittest.TestCase):
joi@chromium.org14a61312014-01-08 01:15:41449 def testFilesToCheckForIncomingDeps(self):
tony@chromium.orgf32e2d1e2013-07-26 21:39:08450 changed_lines = [
451 '"+breakpad",',
452 '"+chrome/installer",',
453 '"+chrome/plugin/chrome_content_plugin_client.h",',
454 '"+chrome/utility/chrome_content_utility_client.h",',
455 '"+chromeos/chromeos_paths.h",',
philipj3f9d5bde2014-08-28 14:09:09456 '"+components/crash",',
tony@chromium.orgf32e2d1e2013-07-26 21:39:08457 '"+components/nacl/common",',
458 '"+content/public/browser/render_process_host.h",',
joi@chromium.org14a61312014-01-08 01:15:41459 '"+jni/fooblat.h",',
tony@chromium.orgf32e2d1e2013-07-26 21:39:08460 '"+grit", # For generated headers',
461 '"+grit/generated_resources.h",',
462 '"+grit/",',
463 '"+policy", # For generated headers and source',
464 '"+sandbox",',
465 '"+tools/memory_watcher",',
466 '"+third_party/lss/linux_syscall_support.h",',
467 ]
joi@chromium.org14a61312014-01-08 01:15:41468 files_to_check = PRESUBMIT._FilesToCheckForIncomingDeps(re, changed_lines)
tony@chromium.orgf32e2d1e2013-07-26 21:39:08469 expected = set([
470 'breakpad/DEPS',
471 'chrome/installer/DEPS',
joi@chromium.org14a61312014-01-08 01:15:41472 'chrome/plugin/chrome_content_plugin_client.h',
473 'chrome/utility/chrome_content_utility_client.h',
474 'chromeos/chromeos_paths.h',
Robert Sesekabcd8102014-08-27 16:12:44475 'components/crash/DEPS',
tony@chromium.orgf32e2d1e2013-07-26 21:39:08476 'components/nacl/common/DEPS',
joi@chromium.org14a61312014-01-08 01:15:41477 'content/public/browser/render_process_host.h',
tony@chromium.orgf32e2d1e2013-07-26 21:39:08478 'policy/DEPS',
479 'sandbox/DEPS',
480 'tools/memory_watcher/DEPS',
joi@chromium.org14a61312014-01-08 01:15:41481 'third_party/lss/linux_syscall_support.h',
tony@chromium.orgf32e2d1e2013-07-26 21:39:08482 ])
483 self.assertEqual(expected, files_to_check);
484
485
yoz@chromium.org99171a92014-06-03 08:44:47486class JSONParsingTest(unittest.TestCase):
487 def testSuccess(self):
488 input_api = MockInputApi()
489 filename = 'valid_json.json'
490 contents = ['// This is a comment.',
491 '{',
492 ' "key1": ["value1", "value2"],',
493 ' "key2": 3 // This is an inline comment.',
494 '}'
495 ]
496 input_api.files = [MockFile(filename, contents)]
497 self.assertEqual(None,
498 PRESUBMIT._GetJSONParseError(input_api, filename))
499
500 def testFailure(self):
501 input_api = MockInputApi()
502 test_data = [
503 ('invalid_json_1.json',
504 ['{ x }'],
yoz@chromium.orga3343272014-06-17 11:41:53505 'Expecting property name:'),
yoz@chromium.org99171a92014-06-03 08:44:47506 ('invalid_json_2.json',
507 ['// Hello world!',
508 '{ "hello": "world }'],
yoz@chromium.orga3343272014-06-17 11:41:53509 'Unterminated string starting at:'),
yoz@chromium.org99171a92014-06-03 08:44:47510 ('invalid_json_3.json',
511 ['{ "a": "b", "c": "d", }'],
yoz@chromium.orga3343272014-06-17 11:41:53512 'Expecting property name:'),
yoz@chromium.org99171a92014-06-03 08:44:47513 ('invalid_json_4.json',
514 ['{ "a": "b" "c": "d" }'],
yoz@chromium.orga3343272014-06-17 11:41:53515 'Expecting , delimiter:'),
yoz@chromium.org99171a92014-06-03 08:44:47516 ]
517
518 input_api.files = [MockFile(filename, contents)
519 for (filename, contents, _) in test_data]
520
521 for (filename, _, expected_error) in test_data:
522 actual_error = PRESUBMIT._GetJSONParseError(input_api, filename)
yoz@chromium.orga3343272014-06-17 11:41:53523 self.assertTrue(expected_error in str(actual_error),
524 "'%s' not found in '%s'" % (expected_error, actual_error))
yoz@chromium.org99171a92014-06-03 08:44:47525
526 def testNoEatComments(self):
527 input_api = MockInputApi()
528 file_with_comments = 'file_with_comments.json'
529 contents_with_comments = ['// This is a comment.',
530 '{',
531 ' "key1": ["value1", "value2"],',
532 ' "key2": 3 // This is an inline comment.',
533 '}'
534 ]
535 file_without_comments = 'file_without_comments.json'
536 contents_without_comments = ['{',
537 ' "key1": ["value1", "value2"],',
538 ' "key2": 3',
539 '}'
540 ]
541 input_api.files = [MockFile(file_with_comments, contents_with_comments),
542 MockFile(file_without_comments,
543 contents_without_comments)]
544
545 self.assertEqual('No JSON object could be decoded',
546 str(PRESUBMIT._GetJSONParseError(input_api,
547 file_with_comments,
548 eat_comments=False)))
549 self.assertEqual(None,
550 PRESUBMIT._GetJSONParseError(input_api,
551 file_without_comments,
552 eat_comments=False))
553
554
555class IDLParsingTest(unittest.TestCase):
556 def testSuccess(self):
557 input_api = MockInputApi()
558 filename = 'valid_idl_basics.idl'
559 contents = ['// Tests a valid IDL file.',
560 'namespace idl_basics {',
561 ' enum EnumType {',
562 ' name1,',
563 ' name2',
564 ' };',
565 '',
566 ' dictionary MyType1 {',
567 ' DOMString a;',
568 ' };',
569 '',
570 ' callback Callback1 = void();',
571 ' callback Callback2 = void(long x);',
572 ' callback Callback3 = void(MyType1 arg);',
573 ' callback Callback4 = void(EnumType type);',
574 '',
575 ' interface Functions {',
576 ' static void function1();',
577 ' static void function2(long x);',
578 ' static void function3(MyType1 arg);',
579 ' static void function4(Callback1 cb);',
580 ' static void function5(Callback2 cb);',
581 ' static void function6(Callback3 cb);',
582 ' static void function7(Callback4 cb);',
583 ' };',
584 '',
585 ' interface Events {',
586 ' static void onFoo1();',
587 ' static void onFoo2(long x);',
588 ' static void onFoo2(MyType1 arg);',
589 ' static void onFoo3(EnumType type);',
590 ' };',
591 '};'
592 ]
593 input_api.files = [MockFile(filename, contents)]
594 self.assertEqual(None,
595 PRESUBMIT._GetIDLParseError(input_api, filename))
596
597 def testFailure(self):
598 input_api = MockInputApi()
599 test_data = [
600 ('invalid_idl_1.idl',
601 ['//',
602 'namespace test {',
603 ' dictionary {',
604 ' DOMString s;',
605 ' };',
606 '};'],
607 'Unexpected "{" after keyword "dictionary".\n'),
608 # TODO(yoz): Disabled because it causes the IDL parser to hang.
609 # See crbug.com/363830.
610 # ('invalid_idl_2.idl',
611 # (['namespace test {',
612 # ' dictionary MissingSemicolon {',
613 # ' DOMString a',
614 # ' DOMString b;',
615 # ' };',
616 # '};'],
617 # 'Unexpected symbol DOMString after symbol a.'),
618 ('invalid_idl_3.idl',
619 ['//',
620 'namespace test {',
621 ' enum MissingComma {',
622 ' name1',
623 ' name2',
624 ' };',
625 '};'],
626 'Unexpected symbol name2 after symbol name1.'),
627 ('invalid_idl_4.idl',
628 ['//',
629 'namespace test {',
630 ' enum TrailingComma {',
631 ' name1,',
632 ' name2,',
633 ' };',
634 '};'],
635 'Trailing comma in block.'),
636 ('invalid_idl_5.idl',
637 ['//',
638 'namespace test {',
639 ' callback Callback1 = void(;',
640 '};'],
641 'Unexpected ";" after "(".'),
642 ('invalid_idl_6.idl',
643 ['//',
644 'namespace test {',
645 ' callback Callback1 = void(long );',
646 '};'],
647 'Unexpected ")" after symbol long.'),
648 ('invalid_idl_7.idl',
649 ['//',
650 'namespace test {',
651 ' interace Events {',
652 ' static void onFoo1();',
653 ' };',
654 '};'],
655 'Unexpected symbol Events after symbol interace.'),
656 ('invalid_idl_8.idl',
657 ['//',
658 'namespace test {',
659 ' interface NotEvent {',
660 ' static void onFoo1();',
661 ' };',
662 '};'],
663 'Did not process Interface Interface(NotEvent)'),
664 ('invalid_idl_9.idl',
665 ['//',
666 'namespace test {',
667 ' interface {',
668 ' static void function1();',
669 ' };',
670 '};'],
671 'Interface missing name.'),
672 ]
673
674 input_api.files = [MockFile(filename, contents)
675 for (filename, contents, _) in test_data]
676
677 for (filename, _, expected_error) in test_data:
678 actual_error = PRESUBMIT._GetIDLParseError(input_api, filename)
679 self.assertTrue(expected_error in str(actual_error),
680 "'%s' not found in '%s'" % (expected_error, actual_error))
681
682
sergeyberezin@chromium.org0bb112362014-07-26 04:38:32683class TryServerMasterTest(unittest.TestCase):
684 def testTryServerMasters(self):
685 bots = {
sergeyberezin@chromium.org0bb112362014-07-26 04:38:32686 'tryserver.chromium.mac': [
687 'ios_dbg_simulator',
688 'ios_rel_device',
689 'ios_rel_device_ninja',
690 'mac_asan',
691 'mac_asan_64',
692 'mac_chromium_compile_dbg',
693 'mac_chromium_compile_rel',
694 'mac_chromium_dbg',
695 'mac_chromium_rel',
sergeyberezin@chromium.org0bb112362014-07-26 04:38:32696 'mac_nacl_sdk',
697 'mac_nacl_sdk_build',
698 'mac_rel_naclmore',
699 'mac_valgrind',
700 'mac_x64_rel',
701 'mac_xcodebuild',
702 ],
703 'tryserver.chromium.linux': [
704 'android_aosp',
705 'android_chromium_gn_compile_dbg',
706 'android_chromium_gn_compile_rel',
707 'android_clang_dbg',
708 'android_dbg',
709 'android_dbg_recipe',
710 'android_dbg_triggered_tests',
711 'android_dbg_triggered_tests_recipe',
712 'android_fyi_dbg',
713 'android_fyi_dbg_triggered_tests',
714 'android_rel',
715 'android_rel_triggered_tests',
716 'android_x86_dbg',
717 'blink_android_compile_dbg',
718 'blink_android_compile_rel',
719 'blink_presubmit',
720 'chromium_presubmit',
721 'linux_arm_cross_compile',
722 'linux_arm_tester',
sergeyberezin@chromium.org0bb112362014-07-26 04:38:32723 'linux_chromeos_asan',
724 'linux_chromeos_browser_asan',
725 'linux_chromeos_valgrind',
sergeyberezin@chromium.org0bb112362014-07-26 04:38:32726 'linux_chromium_chromeos_dbg',
727 'linux_chromium_chromeos_rel',
sergeyberezin@chromium.org0bb112362014-07-26 04:38:32728 'linux_chromium_compile_dbg',
729 'linux_chromium_compile_rel',
730 'linux_chromium_dbg',
731 'linux_chromium_gn_dbg',
732 'linux_chromium_gn_rel',
733 'linux_chromium_rel',
sergeyberezin@chromium.org0bb112362014-07-26 04:38:32734 'linux_chromium_trusty32_dbg',
735 'linux_chromium_trusty32_rel',
736 'linux_chromium_trusty_dbg',
737 'linux_chromium_trusty_rel',
738 'linux_clang_tsan',
739 'linux_ecs_ozone',
740 'linux_layout',
741 'linux_layout_asan',
742 'linux_layout_rel',
743 'linux_layout_rel_32',
744 'linux_nacl_sdk',
745 'linux_nacl_sdk_bionic',
746 'linux_nacl_sdk_bionic_build',
747 'linux_nacl_sdk_build',
748 'linux_redux',
749 'linux_rel_naclmore',
750 'linux_rel_precise32',
751 'linux_valgrind',
752 'tools_build_presubmit',
753 ],
754 'tryserver.chromium.win': [
755 'win8_aura',
756 'win8_chromium_dbg',
757 'win8_chromium_rel',
758 'win_chromium_compile_dbg',
759 'win_chromium_compile_rel',
760 'win_chromium_dbg',
761 'win_chromium_rel',
762 'win_chromium_rel',
sergeyberezin@chromium.org0bb112362014-07-26 04:38:32763 'win_chromium_x64_dbg',
764 'win_chromium_x64_rel',
765 'win_drmemory',
766 'win_nacl_sdk',
767 'win_nacl_sdk_build',
768 'win_rel_naclmore',
769 ],
770 }
771 for master, bots in bots.iteritems():
772 for bot in bots:
773 self.assertEqual(master, PRESUBMIT.GetTryServerMasterForBot(bot),
774 'bot=%s: expected %s, computed %s' % (
775 bot, master, PRESUBMIT.GetTryServerMasterForBot(bot)))
776
777
davileene0426252015-03-02 21:10:41778class UserMetricsActionTest(unittest.TestCase):
779 def testUserMetricsActionInActions(self):
780 input_api = MockInputApi()
781 file_with_user_action = 'file_with_user_action.cc'
782 contents_with_user_action = [
783 'base::UserMetricsAction("AboutChrome")'
784 ]
785
786 input_api.files = [MockFile(file_with_user_action,
787 contents_with_user_action)]
788
789 self.assertEqual(
790 [], PRESUBMIT._CheckUserActionUpdate(input_api, MockOutputApi()))
791
792
793 def testUserMetricsActionNotAddedToActions(self):
794 input_api = MockInputApi()
795 file_with_user_action = 'file_with_user_action.cc'
796 contents_with_user_action = [
797 'base::UserMetricsAction("NotInActionsXml")'
798 ]
799
800 input_api.files = [MockFile(file_with_user_action,
801 contents_with_user_action)]
802
803 output = PRESUBMIT._CheckUserActionUpdate(input_api, MockOutputApi())
804 self.assertEqual(
805 ('File %s line %d: %s is missing in '
806 'tools/metrics/actions/actions.xml. Please run '
807 'tools/metrics/actions/extract_actions.py to update.'
808 % (file_with_user_action, 1, 'NotInActionsXml')),
809 output[0].message)
810
811
dgn4401aa52015-04-29 16:26:17812class LogUsageTest(unittest.TestCase):
813
814 def testCheckNoNewUtilLogUsage(self):
815 mock_input_api = MockInputApi()
816 mock_output_api = MockOutputApi()
817
818 mock_input_api.files = [
819 MockAffectedFile('RandomStuff.java', [
820 'random stuff'
821 ]),
822 MockAffectedFile('HasCrLog.java', [
823 'import org.chromium.base.Log;',
824 'some random stuff',
825 'Log.d("TAG", "foo");',
826 ]),
827 MockAffectedFile('HasAndroidLog.java', [
828 'import android.util.Log;',
829 'some random stuff',
830 'Log.d("TAG", "foo");',
831 ]),
832 MockAffectedFile('HasExplicitLog.java', [
833 'some random stuff',
834 'android.util.Log.d("TAG", "foo");',
835 ]),
836 MockAffectedFile('HasBothLog.java', [
837 'import org.chromium.base.Log;',
838 'some random stuff',
839 'Log.d("TAG", "foo");',
840 'android.util.Log.d("TAG", "foo");',
841 ]),
842 ]
843
844 warnings = PRESUBMIT._CheckNoNewUtilLogUsage(
845 mock_input_api, mock_output_api)
846
847 self.assertEqual(1, len(warnings))
848 self.assertEqual(2, len(warnings[0].items))
849 self.assertTrue('HasAndroidLog.java' in warnings[0].items[0])
850 self.assertTrue('HasExplicitLog.java' in warnings[0].items[1])
851
852
marja@chromium.org2299dcf2012-11-15 19:56:24853if __name__ == '__main__':
854 unittest.main()