blob: 60e042437ecef585e704671cffc103a532f75b91 [file] [log] [blame]
Torne (Richard Coles)53e740f2013-05-09 18:38:43 +01001# Copyright (c) 2013 The Chromium Authors. All rights reserved.
2# Use of this source code is governed by a BSD-style license that can be
3# found in the LICENSE file.
4
5"""Top-level presubmit script for Blink.
6
7See http://dev.chromium.org/developers/how-tos/depottools/presubmit-scripts
8for more details about the presubmit API built into gcl.
9"""
10
11
12_EXCLUDED_PATHS = ()
13
14
15def _CheckForVersionControlConflictsInFile(input_api, f):
16 pattern = input_api.re.compile('^(?:<<<<<<<|>>>>>>>) |^=======$')
17 errors = []
18 for line_num, line in f.ChangedContents():
19 if pattern.match(line):
20 errors.append(' %s:%d %s' % (f.LocalPath(), line_num, line))
21 return errors
22
23
24def _CheckForVersionControlConflicts(input_api, output_api):
25 """Usually this is not intentional and will cause a compile failure."""
26 errors = []
27 for f in input_api.AffectedFiles():
28 errors.extend(_CheckForVersionControlConflictsInFile(input_api, f))
29
30 results = []
31 if errors:
32 results.append(output_api.PresubmitError(
33 'Version control conflict markers found, please resolve.', errors))
34 return results
35
36
37def _CommonChecks(input_api, output_api):
38 """Checks common to both upload and commit."""
39 # We should figure out what license checks we actually want to use.
40 license_header = r'.*'
41
42 results = []
43 results.extend(input_api.canned_checks.PanProjectChecks(
44 input_api, output_api, excluded_paths=_EXCLUDED_PATHS,
45 maxlen=800, license_header=license_header))
46 results.extend(_CheckForVersionControlConflicts(input_api, output_api))
47 results.extend(_CheckPatchFiles(input_api, output_api))
48 results.extend(_CheckTestExpectations(input_api, output_api))
49 return results
50
51
52def _CheckSubversionConfig(input_api, output_api):
53 """Verifies the subversion config file is correctly setup.
54
55 Checks that autoprops are enabled, returns an error otherwise.
56 """
57 join = input_api.os_path.join
58 if input_api.platform == 'win32':
59 appdata = input_api.environ.get('APPDATA', '')
60 if not appdata:
61 return [output_api.PresubmitError('%APPDATA% is not configured.')]
62 path = join(appdata, 'Subversion', 'config')
63 else:
64 home = input_api.environ.get('HOME', '')
65 if not home:
66 return [output_api.PresubmitError('$HOME is not configured.')]
67 path = join(home, '.subversion', 'config')
68
69 error_msg = (
70 'Please look at http://dev.chromium.org/developers/coding-style to\n'
71 'configure your subversion configuration file. This enables automatic\n'
72 'properties to simplify the project maintenance.\n'
73 'Pro-tip: just download and install\n'
74 'http://src.chromium.org/viewvc/chrome/trunk/tools/build/slave/config\n')
75
76 try:
77 lines = open(path, 'r').read().splitlines()
78 # Make sure auto-props is enabled and check for 2 Chromium standard
79 # auto-prop.
80 if (not '*.cc = svn:eol-style=LF' in lines or
81 not '*.pdf = svn:mime-type=application/pdf' in lines or
82 not 'enable-auto-props = yes' in lines):
83 return [
84 output_api.PresubmitNotifyResult(
85 'It looks like you have not configured your subversion config '
86 'file or it is not up-to-date.\n' + error_msg)
87 ]
88 except (OSError, IOError):
89 return [
90 output_api.PresubmitNotifyResult(
91 'Can\'t find your subversion config file.\n' + error_msg)
92 ]
93 return []
94
95
96def _CheckPatchFiles(input_api, output_api):
97 problems = [f.LocalPath() for f in input_api.AffectedFiles()
98 if f.LocalPath().endswith(('.orig', '.rej'))]
99 if problems:
100 return [output_api.PresubmitError(
101 "Don't commit .rej and .orig files.", problems)]
102 else:
103 return []
104
105
106def _CheckTestExpectations(input_api, output_api):
107 local_paths = [f.LocalPath() for f in input_api.AffectedFiles()]
108 if any(path.startswith('LayoutTests') for path in local_paths):
109 lint_path = input_api.os_path.join(input_api.PresubmitLocalPath(),
110 'Tools', 'Scripts', 'lint-test-expectations')
111 _, errs = input_api.subprocess.Popen(
112 [input_api.python_executable, lint_path],
113 stdout=input_api.subprocess.PIPE,
114 stderr=input_api.subprocess.PIPE).communicate()
115 if not errs:
116 return [output_api.PresubmitError(
117 "lint-test-expectations failed "
118 "to produce output; check by hand. ")]
119 if errs.strip() != 'Lint succeeded.':
120 return [output_api.PresubmitError(errs)]
121 return []
122
123
124def _CheckStyle(input_api, output_api):
Torne (Richard Coles)81a51572013-05-13 16:52:28 +0100125 style_checker_path = input_api.os_path.join(input_api.PresubmitLocalPath(),
126 'Tools', 'Scripts', 'check-webkit-style')
127 args = ([input_api.python_executable, style_checker_path, '--diff-files']
128 + [f.LocalPath() for f in input_api.AffectedFiles()])
Torne (Richard Coles)53e740f2013-05-09 18:38:43 +0100129 results = []
130
131 try:
132 child = input_api.subprocess.Popen(args,
133 stderr=input_api.subprocess.PIPE)
134 _, stderrdata = child.communicate()
135 if child.returncode != 0:
136 results.append(output_api.PresubmitError(
137 'check-webkit-style failed', [stderrdata]))
138 except Exception as e:
139 results.append(output_api.PresubmitNotifyResult(
140 'Could not run check-webkit-style', [str(e)]))
141
142 return results
143
144
145def CheckChangeOnUpload(input_api, output_api):
146 results = []
147 results.extend(_CommonChecks(input_api, output_api))
148 results.extend(_CheckStyle(input_api, output_api))
149 return results
150
151
152def CheckChangeOnCommit(input_api, output_api):
153 results = []
154 results.extend(_CommonChecks(input_api, output_api))
155 results.extend(input_api.canned_checks.CheckTreeIsOpen(
156 input_api, output_api,
157 json_url='http://blink-status.appspot.com/current?format=json'))
158 results.extend(input_api.canned_checks.CheckChangeHasDescription(
159 input_api, output_api))
160 results.extend(_CheckSubversionConfig(input_api, output_api))
161 return results
162
163def GetPreferredTrySlaves(project, change):
164 return ['linux_layout_rel', 'mac_layout_rel', 'win_layout_rel']