1cb93a386Sopenharmony_ci''' 2cb93a386Sopenharmony_ciCopyright 2011 Google Inc. 3cb93a386Sopenharmony_ci 4cb93a386Sopenharmony_ciUse of this source code is governed by a BSD-style license that can be 5cb93a386Sopenharmony_cifound in the LICENSE file. 6cb93a386Sopenharmony_ci''' 7cb93a386Sopenharmony_ci 8cb93a386Sopenharmony_ciimport datetime 9cb93a386Sopenharmony_ciimport re 10cb93a386Sopenharmony_ci 11cb93a386Sopenharmony_cidef CreateParser(filepath): 12cb93a386Sopenharmony_ci """Returns a Parser as appropriate for the file at this filepath. 13cb93a386Sopenharmony_ci """ 14cb93a386Sopenharmony_ci if (filepath.endswith('.cpp') or 15cb93a386Sopenharmony_ci filepath.endswith('.h') or 16cb93a386Sopenharmony_ci filepath.endswith('.c')): 17cb93a386Sopenharmony_ci return CParser() 18cb93a386Sopenharmony_ci else: 19cb93a386Sopenharmony_ci return None 20cb93a386Sopenharmony_ci 21cb93a386Sopenharmony_ci 22cb93a386Sopenharmony_ciclass Parser(object): 23cb93a386Sopenharmony_ci """Base class for all language-specific parsers. 24cb93a386Sopenharmony_ci """ 25cb93a386Sopenharmony_ci 26cb93a386Sopenharmony_ci def __init__(self): 27cb93a386Sopenharmony_ci self._copyright_pattern = re.compile('copyright', re.IGNORECASE) 28cb93a386Sopenharmony_ci self._attribute_pattern = re.compile( 29cb93a386Sopenharmony_ci 'copyright.*\D(\d{4})\W*(\w.*[\w.])', re.IGNORECASE) 30cb93a386Sopenharmony_ci 31cb93a386Sopenharmony_ci def FindCopyrightBlock(self, comment_blocks): 32cb93a386Sopenharmony_ci """Given a list of comment block strings, return the one that seems 33cb93a386Sopenharmony_ci like the most likely copyright block. 34cb93a386Sopenharmony_ci 35cb93a386Sopenharmony_ci Returns None if comment_blocks was empty, or if we couldn't find 36cb93a386Sopenharmony_ci a comment block that contains copyright info.""" 37cb93a386Sopenharmony_ci if not comment_blocks: 38cb93a386Sopenharmony_ci return None 39cb93a386Sopenharmony_ci for block in comment_blocks: 40cb93a386Sopenharmony_ci if self._copyright_pattern.search(block): 41cb93a386Sopenharmony_ci return block 42cb93a386Sopenharmony_ci 43cb93a386Sopenharmony_ci def GetCopyrightBlockAttributes(self, comment_block): 44cb93a386Sopenharmony_ci """Given a comment block, return a tuple of attributes: (year, holder). 45cb93a386Sopenharmony_ci 46cb93a386Sopenharmony_ci If comment_block is None, or none of the attributes are found, 47cb93a386Sopenharmony_ci this will return (None, None).""" 48cb93a386Sopenharmony_ci if not comment_block: 49cb93a386Sopenharmony_ci return (None, None) 50cb93a386Sopenharmony_ci matches = self._attribute_pattern.findall(comment_block) 51cb93a386Sopenharmony_ci if not matches: 52cb93a386Sopenharmony_ci return (None, None) 53cb93a386Sopenharmony_ci first_match = matches[0] 54cb93a386Sopenharmony_ci return (first_match[0], first_match[1]) 55cb93a386Sopenharmony_ci 56cb93a386Sopenharmony_ci 57cb93a386Sopenharmony_ciclass CParser(Parser): 58cb93a386Sopenharmony_ci """Parser that knows how to parse C/C++ files. 59cb93a386Sopenharmony_ci """ 60cb93a386Sopenharmony_ci 61cb93a386Sopenharmony_ci DEFAULT_YEAR = datetime.date.today().year 62cb93a386Sopenharmony_ci DEFAULT_HOLDER = 'Google Inc.' 63cb93a386Sopenharmony_ci COPYRIGHT_BLOCK_FORMAT = ''' 64cb93a386Sopenharmony_ci/* 65cb93a386Sopenharmony_ci * Copyright %s %s 66cb93a386Sopenharmony_ci * 67cb93a386Sopenharmony_ci * Use of this source code is governed by a BSD-style license that can be 68cb93a386Sopenharmony_ci * found in the LICENSE file. 69cb93a386Sopenharmony_ci */ 70cb93a386Sopenharmony_ci''' 71cb93a386Sopenharmony_ci 72cb93a386Sopenharmony_ci def __init__(self): 73cb93a386Sopenharmony_ci super(CParser, self).__init__() 74cb93a386Sopenharmony_ci self._comment_pattern = re.compile('/\*.*?\*/', re.DOTALL) 75cb93a386Sopenharmony_ci 76cb93a386Sopenharmony_ci def FindAllCommentBlocks(self, file_contents): 77cb93a386Sopenharmony_ci """Returns a list of all comment blocks within these file contents. 78cb93a386Sopenharmony_ci """ 79cb93a386Sopenharmony_ci return self._comment_pattern.findall(file_contents) 80cb93a386Sopenharmony_ci 81cb93a386Sopenharmony_ci def CreateCopyrightBlock(self, year, holder): 82cb93a386Sopenharmony_ci """Returns a copyright block suitable for this language, with the 83cb93a386Sopenharmony_ci given attributes. 84cb93a386Sopenharmony_ci 85cb93a386Sopenharmony_ci @param year year in which to hold copyright (defaults to DEFAULT_YEAR) 86cb93a386Sopenharmony_ci @param holder holder of copyright (defaults to DEFAULT_HOLDER) 87cb93a386Sopenharmony_ci """ 88cb93a386Sopenharmony_ci if not year: 89cb93a386Sopenharmony_ci year = self.DEFAULT_YEAR 90cb93a386Sopenharmony_ci if not holder: 91cb93a386Sopenharmony_ci holder = self.DEFAULT_HOLDER 92cb93a386Sopenharmony_ci return self.COPYRIGHT_BLOCK_FORMAT % (year, holder) 93