OLD | NEW |
1 # Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 # Copyright (c) 2012 The Chromium Authors. All rights reserved. |
2 # Use of this source code is governed by a BSD-style license that can be | 2 # Use of this source code is governed by a BSD-style license that can be |
3 # found in the LICENSE file. | 3 # found in the LICENSE file. |
4 | 4 |
5 """Presubmit script for Chromium JS resources. | 5 """Presubmit script for Chromium JS resources. |
6 | 6 |
7 See chrome/browser/PRESUBMIT.py | 7 See chrome/browser/PRESUBMIT.py |
8 """ | 8 """ |
9 | 9 |
10 import regex_check | 10 import regex_check |
(...skipping 94 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
105 path.join(resources, 'profiler'), | 105 path.join(resources, 'profiler'), |
106 path.join(resources, 'sync_promo'), | 106 path.join(resources, 'sync_promo'), |
107 path.join(resources, 'tracing'), | 107 path.join(resources, 'tracing'), |
108 path.join(resources, 'uber'), | 108 path.join(resources, 'uber'), |
109 ) | 109 ) |
110 if filename.startswith(dirs): | 110 if filename.startswith(dirs): |
111 return self.output_api.PresubmitError(error_text) | 111 return self.output_api.PresubmitError(error_text) |
112 else: | 112 else: |
113 return self.output_api.PresubmitPromptWarning(error_text) | 113 return self.output_api.PresubmitPromptWarning(error_text) |
114 | 114 |
115 def ClosureLint(self, file_to_lint, source=None): | |
116 """Lints |file_to_lint| and returns the errors.""" | |
117 | |
118 import sys | |
119 import warnings | |
120 old_path = sys.path | |
121 old_filters = warnings.filters | |
122 | |
123 try: | |
124 closure_linter_path = self.input_api.os_path.join( | |
125 self.input_api.change.RepositoryRoot(), | |
126 "third_party", | |
127 "closure_linter") | |
128 gflags_path = self.input_api.os_path.join( | |
129 self.input_api.change.RepositoryRoot(), | |
130 "third_party", | |
131 "python_gflags") | |
132 | |
133 sys.path.insert(0, closure_linter_path) | |
134 sys.path.insert(0, gflags_path) | |
135 | |
136 warnings.filterwarnings('ignore', category=DeprecationWarning) | |
137 | |
138 from closure_linter import errors, runner | |
139 from closure_linter.common import errorhandler | |
140 import gflags | |
141 | |
142 finally: | |
143 sys.path = old_path | |
144 warnings.filters = old_filters | |
145 | |
146 class ErrorHandlerImpl(errorhandler.ErrorHandler): | |
147 """Filters out errors that don't apply to Chromium JavaScript code.""" | |
148 | |
149 def __init__(self, re): | |
150 self._errors = [] | |
151 self.re = re | |
152 | |
153 def HandleFile(self, filename, first_token): | |
154 self._filename = filename | |
155 | |
156 def HandleError(self, error): | |
157 if (self._valid(error)): | |
158 error.filename = self._filename | |
159 self._errors.append(error) | |
160 | |
161 def GetErrors(self): | |
162 return self._errors | |
163 | |
164 def HasErrors(self): | |
165 return bool(self._errors) | |
166 | |
167 def _valid(self, error): | |
168 """Check whether an error is valid. Most errors are valid, with a few | |
169 exceptions which are listed here. | |
170 """ | |
171 | |
172 is_grit_statement = bool( | |
173 self.re.search("</?(include|if)", error.token.line)) | |
174 | |
175 # Ignore missing spaces before "(" until Promise#catch issue is solved. | |
176 # http://crbug.com/338301 | |
177 if (error.code == errors.MISSING_SPACE and error.token.string == '(' and | |
178 'catch(' in error.token.line): | |
179 return False | |
180 | |
181 # Ignore "}.bind(" errors. http://crbug.com/397697 | |
182 if (error.code == errors.MISSING_SEMICOLON_AFTER_FUNCTION and | |
183 '}.bind(' in error.token.line): | |
184 return False | |
185 | |
186 return not is_grit_statement and error.code not in [ | |
187 errors.COMMA_AT_END_OF_LITERAL, | |
188 errors.JSDOC_ILLEGAL_QUESTION_WITH_PIPE, | |
189 errors.LINE_TOO_LONG, | |
190 errors.MISSING_JSDOC_TAG_THIS, | |
191 ] | |
192 | |
193 # Keep this in sync with third_party/closure_compiler/closure_args.gypi | |
194 gflags.FLAGS.custom_jsdoc_tags = ( | |
195 'abstract', | |
196 'attribute', | |
197 'default', | |
198 'demo', | |
199 'element', | |
200 'group', | |
201 'hero', | |
202 'polymerBehavior', | |
203 'status', | |
204 'submodule', | |
205 ) | |
206 error_handler = ErrorHandlerImpl(self.input_api.re) | |
207 runner.Run(file_to_lint, error_handler, source=source) | |
208 return error_handler.GetErrors() | |
209 | |
210 def RunChecks(self): | 115 def RunChecks(self): |
211 """Check for violations of the Chromium JavaScript style guide. See | 116 """Check for violations of the Chromium JavaScript style guide. See |
212 http://chromium.org/developers/web-development-style-guide#TOC-JavaScript | 117 http://chromium.org/developers/web-development-style-guide#TOC-JavaScript |
213 """ | 118 """ |
214 results = [] | 119 results = [] |
215 | 120 |
216 affected_files = self.input_api.change.AffectedFiles( | 121 affected_files = self.input_api.change.AffectedFiles( |
217 file_filter=self.file_filter, | 122 file_filter=self.file_filter, |
218 include_deletes=False) | 123 include_deletes=False) |
219 affected_js_files = filter(lambda f: f.LocalPath().endswith('.js'), | 124 affected_js_files = filter(lambda f: f.LocalPath().endswith('.js'), |
(...skipping 11 matching lines...) Expand all Loading... |
231 self.ConstCheck(i, line), | 136 self.ConstCheck(i, line), |
232 self.GetElementByIdCheck(i, line), | 137 self.GetElementByIdCheck(i, line), |
233 self.EndJsDocCommentCheck(i, line), | 138 self.EndJsDocCommentCheck(i, line), |
234 self.ExtraDotInGenericCheck(i, line), | 139 self.ExtraDotInGenericCheck(i, line), |
235 self.InheritDocCheck(i, line), | 140 self.InheritDocCheck(i, line), |
236 self.PolymerLocalIdCheck(i, line), | 141 self.PolymerLocalIdCheck(i, line), |
237 self.WrapperTypeCheck(i, line), | 142 self.WrapperTypeCheck(i, line), |
238 self.VarNameCheck(i, line), | 143 self.VarNameCheck(i, line), |
239 ]) | 144 ]) |
240 | 145 |
241 # Use closure linter to check for several different errors. | |
242 lint_errors = self.ClosureLint(self.input_api.os_path.join( | |
243 self.input_api.change.RepositoryRoot(), f.LocalPath())) | |
244 | |
245 for error in lint_errors: | |
246 highlight = self._GetErrorHighlight( | |
247 error.token.start_index, error.token.length) | |
248 error_msg = ' line %d: E%04d: %s\n%s\n%s' % ( | |
249 error.token.line_number, | |
250 error.code, | |
251 error.message, | |
252 error.token.line.rstrip(), | |
253 highlight) | |
254 error_lines.append(error_msg) | |
255 | |
256 if error_lines: | 146 if error_lines: |
257 error_lines = [ | 147 error_lines = [ |
258 'Found JavaScript style violations in %s:' % | 148 'Found JavaScript style violations in %s:' % |
259 f.LocalPath()] + error_lines | 149 f.LocalPath()] + error_lines |
260 results.append(self._MakeErrorOrWarning( | 150 results.append(self._MakeErrorOrWarning( |
261 '\n'.join(error_lines), f.AbsoluteLocalPath())) | 151 '\n'.join(error_lines), f.AbsoluteLocalPath())) |
262 | 152 |
263 if results: | 153 if results: |
264 results.append(self.output_api.PresubmitNotifyResult( | 154 results.append(self.output_api.PresubmitNotifyResult( |
265 'See the JavaScript style guide at ' | 155 'See the JavaScript style guide at ' |
266 'http://www.chromium.org/developers/web-development-style-guide' | 156 'http://www.chromium.org/developers/web-development-style-guide' |
267 '#TOC-JavaScript')) | 157 '#TOC-JavaScript')) |
268 | 158 |
269 return results | 159 return results |
OLD | NEW |