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