| OLD | NEW |
| 1 #!/usr/bin/env python | 1 #!/usr/bin/env python |
| 2 # Copyright (c) 2011 The Chromium Authors. All rights reserved. | 2 # Copyright (c) 2011 The Chromium Authors. All rights reserved. |
| 3 # Use of this source code is governed by a BSD-style license that can be | 3 # Use of this source code is governed by a BSD-style license that can be |
| 4 # found in the LICENSE file. | 4 # found in the LICENSE file. |
| 5 | 5 |
| 6 """Enables directory-specific presubmit checks to run at upload and/or commit. | 6 """Enables directory-specific presubmit checks to run at upload and/or commit. |
| 7 """ | 7 """ |
| 8 | 8 |
| 9 __version__ = '1.6.1' | 9 __version__ = '1.6.1' |
| 10 | 10 |
| (...skipping 512 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 523 if not line.startswith('-'): | 523 if not line.startswith('-'): |
| 524 line_num += 1 | 524 line_num += 1 |
| 525 return new_lines | 525 return new_lines |
| 526 | 526 |
| 527 def __str__(self): | 527 def __str__(self): |
| 528 return self.LocalPath() | 528 return self.LocalPath() |
| 529 | 529 |
| 530 def GenerateScmDiff(self): | 530 def GenerateScmDiff(self): |
| 531 raise NotImplementedError() # Implemented in derived classes. | 531 raise NotImplementedError() # Implemented in derived classes. |
| 532 | 532 |
| 533 |
| 533 class SvnAffectedFile(AffectedFile): | 534 class SvnAffectedFile(AffectedFile): |
| 534 """Representation of a file in a change out of a Subversion checkout.""" | 535 """Representation of a file in a change out of a Subversion checkout.""" |
| 535 # Method 'NNN' is abstract in class 'NNN' but is not overridden | 536 # Method 'NNN' is abstract in class 'NNN' but is not overridden |
| 536 # pylint: disable=W0223 | 537 # pylint: disable=W0223 |
| 537 | 538 |
| 538 def __init__(self, *args, **kwargs): | 539 def __init__(self, *args, **kwargs): |
| 539 AffectedFile.__init__(self, *args, **kwargs) | 540 AffectedFile.__init__(self, *args, **kwargs) |
| 540 self._server_path = None | 541 self._server_path = None |
| 541 self._is_text_file = None | 542 self._is_text_file = None |
| 542 | 543 |
| (...skipping 95 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 638 self.KEY: equivalent to tags['KEY'] | 639 self.KEY: equivalent to tags['KEY'] |
| 639 """ | 640 """ |
| 640 | 641 |
| 641 _AFFECTED_FILES = AffectedFile | 642 _AFFECTED_FILES = AffectedFile |
| 642 | 643 |
| 643 # Matches key/value (or "tag") lines in changelist descriptions. | 644 # Matches key/value (or "tag") lines in changelist descriptions. |
| 644 _TAG_LINE_RE = re.compile( | 645 _TAG_LINE_RE = re.compile( |
| 645 '^\s*(?P<key>[A-Z][A-Z_0-9]*)\s*=\s*(?P<value>.*?)\s*$') | 646 '^\s*(?P<key>[A-Z][A-Z_0-9]*)\s*=\s*(?P<value>.*?)\s*$') |
| 646 scm = '' | 647 scm = '' |
| 647 | 648 |
| 648 def __init__(self, name, description, local_root, files, issue, patchset): | 649 def __init__( |
| 650 self, name, description, local_root, files, issue, patchset, author): |
| 649 if files is None: | 651 if files is None: |
| 650 files = [] | 652 files = [] |
| 651 self._name = name | 653 self._name = name |
| 652 self._full_description = description | 654 self._full_description = description |
| 653 # Convert root into an absolute path. | 655 # Convert root into an absolute path. |
| 654 self._local_root = os.path.abspath(local_root) | 656 self._local_root = os.path.abspath(local_root) |
| 655 self.issue = issue | 657 self.issue = issue |
| 656 self.patchset = patchset | 658 self.patchset = patchset |
| 659 self.author_email = author |
| 657 | 660 |
| 658 # From the description text, build up a dictionary of key/value pairs | 661 # From the description text, build up a dictionary of key/value pairs |
| 659 # plus the description minus all key/value or "tag" lines. | 662 # plus the description minus all key/value or "tag" lines. |
| 660 description_without_tags = [] | 663 description_without_tags = [] |
| 661 self.tags = {} | 664 self.tags = {} |
| 662 for line in self._full_description.splitlines(): | 665 for line in self._full_description.splitlines(): |
| 663 m = self._TAG_LINE_RE.match(line) | 666 m = self._TAG_LINE_RE.match(line) |
| 664 if m: | 667 if m: |
| 665 self.tags[m.group('key')] = m.group('value') | 668 self.tags[m.group('key')] = m.group('value') |
| 666 else: | 669 else: |
| (...skipping 485 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1152 version="%prog " + str(__version__)) | 1155 version="%prog " + str(__version__)) |
| 1153 parser.add_option("-c", "--commit", action="store_true", default=False, | 1156 parser.add_option("-c", "--commit", action="store_true", default=False, |
| 1154 help="Use commit instead of upload checks") | 1157 help="Use commit instead of upload checks") |
| 1155 parser.add_option("-u", "--upload", action="store_false", dest='commit', | 1158 parser.add_option("-u", "--upload", action="store_false", dest='commit', |
| 1156 help="Use upload instead of commit checks") | 1159 help="Use upload instead of commit checks") |
| 1157 parser.add_option("-r", "--recursive", action="store_true", | 1160 parser.add_option("-r", "--recursive", action="store_true", |
| 1158 help="Act recursively") | 1161 help="Act recursively") |
| 1159 parser.add_option("-v", "--verbose", action="count", default=0, | 1162 parser.add_option("-v", "--verbose", action="count", default=0, |
| 1160 help="Use 2 times for more debug info") | 1163 help="Use 2 times for more debug info") |
| 1161 parser.add_option("--name", default='no name') | 1164 parser.add_option("--name", default='no name') |
| 1165 parser.add_option("--author") |
| 1162 parser.add_option("--description", default='') | 1166 parser.add_option("--description", default='') |
| 1163 parser.add_option("--issue", type='int', default=0) | 1167 parser.add_option("--issue", type='int', default=0) |
| 1164 parser.add_option("--patchset", type='int', default=0) | 1168 parser.add_option("--patchset", type='int', default=0) |
| 1165 parser.add_option("--root", default=os.getcwd(), | 1169 parser.add_option("--root", default=os.getcwd(), |
| 1166 help="Search for PRESUBMIT.py up to this directory. " | 1170 help="Search for PRESUBMIT.py up to this directory. " |
| 1167 "If inherit-review-settings-ok is present in this " | 1171 "If inherit-review-settings-ok is present in this " |
| 1168 "directory, parent directories up to the root file " | 1172 "directory, parent directories up to the root file " |
| 1169 "system directories will also be searched.") | 1173 "system directories will also be searched.") |
| 1170 parser.add_option("--default_presubmit") | 1174 parser.add_option("--default_presubmit") |
| 1171 parser.add_option("--may_prompt", action='store_true', default=False) | 1175 parser.add_option("--may_prompt", action='store_true', default=False) |
| 1172 options, args = parser.parse_args(argv) | 1176 options, args = parser.parse_args(argv) |
| 1173 if options.verbose >= 2: | 1177 if options.verbose >= 2: |
| 1174 logging.basicConfig(level=logging.DEBUG) | 1178 logging.basicConfig(level=logging.DEBUG) |
| 1175 elif options.verbose: | 1179 elif options.verbose: |
| 1176 logging.basicConfig(level=logging.INFO) | 1180 logging.basicConfig(level=logging.INFO) |
| 1177 else: | 1181 else: |
| 1178 logging.basicConfig(level=logging.ERROR) | 1182 logging.basicConfig(level=logging.ERROR) |
| 1179 change_class, files = load_files(options, args) | 1183 change_class, files = load_files(options, args) |
| 1180 if not change_class: | 1184 if not change_class: |
| 1181 parser.error('For unversioned directory, <files> is not optional.') | 1185 parser.error('For unversioned directory, <files> is not optional.') |
| 1182 logging.info('Found %d file(s).' % len(files)) | 1186 logging.info('Found %d file(s).' % len(files)) |
| 1183 try: | 1187 try: |
| 1184 results = DoPresubmitChecks( | 1188 results = DoPresubmitChecks( |
| 1185 change_class(options.name, | 1189 change_class(options.name, |
| 1186 options.description, | 1190 options.description, |
| 1187 options.root, | 1191 options.root, |
| 1188 files, | 1192 files, |
| 1189 options.issue, | 1193 options.issue, |
| 1190 options.patchset), | 1194 options.patchset, |
| 1195 options.author), |
| 1191 options.commit, | 1196 options.commit, |
| 1192 options.verbose, | 1197 options.verbose, |
| 1193 sys.stdout, | 1198 sys.stdout, |
| 1194 sys.stdin, | 1199 sys.stdin, |
| 1195 options.default_presubmit, | 1200 options.default_presubmit, |
| 1196 options.may_prompt, | 1201 options.may_prompt, |
| 1197 False, | 1202 False, |
| 1198 None) | 1203 None) |
| 1199 return not results.should_continue() | 1204 return not results.should_continue() |
| 1200 except PresubmitFailure, e: | 1205 except PresubmitFailure, e: |
| 1201 print >> sys.stderr, e | 1206 print >> sys.stderr, e |
| 1202 print >> sys.stderr, 'Maybe your depot_tools is out of date?' | 1207 print >> sys.stderr, 'Maybe your depot_tools is out of date?' |
| 1203 print >> sys.stderr, 'If all fails, contact maruel@' | 1208 print >> sys.stderr, 'If all fails, contact maruel@' |
| 1204 return 2 | 1209 return 2 |
| 1205 | 1210 |
| 1206 | 1211 |
| 1207 if __name__ == '__main__': | 1212 if __name__ == '__main__': |
| 1208 fix_encoding.fix_encoding() | 1213 fix_encoding.fix_encoding() |
| 1209 sys.exit(Main(None)) | 1214 sys.exit(Main(None)) |
| OLD | NEW |