| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155 | 
							- #!/usr/bin/env python
 
- # Copyright (c) 2012 Google Inc. All rights reserved.
 
- # Use of this source code is governed by a BSD-style license that can be
 
- # found in the LICENSE file.
 
- """Pretty-prints the contents of a GYP file."""
 
- import sys
 
- import re
 
- # Regex to remove comments when we're counting braces.
 
- COMMENT_RE = re.compile(r'\s*#.*')
 
- # Regex to remove quoted strings when we're counting braces.
 
- # It takes into account quoted quotes, and makes sure that the quotes match.
 
- # NOTE: It does not handle quotes that span more than one line, or
 
- # cases where an escaped quote is preceeded by an escaped backslash.
 
- QUOTE_RE_STR = r'(?P<q>[\'"])(.*?)(?<![^\\][\\])(?P=q)'
 
- QUOTE_RE = re.compile(QUOTE_RE_STR)
 
- def comment_replace(matchobj):
 
-   return matchobj.group(1) + matchobj.group(2) + '#' * len(matchobj.group(3))
 
- def mask_comments(input):
 
-   """Mask the quoted strings so we skip braces inside quoted strings."""
 
-   search_re = re.compile(r'(.*?)(#)(.*)')
 
-   return [search_re.sub(comment_replace, line) for line in input]
 
- def quote_replace(matchobj):
 
-   return "%s%s%s%s" % (matchobj.group(1),
 
-                        matchobj.group(2),
 
-                        'x'*len(matchobj.group(3)),
 
-                        matchobj.group(2))
 
- def mask_quotes(input):
 
-   """Mask the quoted strings so we skip braces inside quoted strings."""
 
-   search_re = re.compile(r'(.*?)' + QUOTE_RE_STR)
 
-   return [search_re.sub(quote_replace, line) for line in input]
 
- def do_split(input, masked_input, search_re):
 
-   output = []
 
-   mask_output = []
 
-   for (line, masked_line) in zip(input, masked_input):
 
-     m = search_re.match(masked_line)
 
-     while m:
 
-       split = len(m.group(1))
 
-       line = line[:split] + r'\n' + line[split:]
 
-       masked_line = masked_line[:split] + r'\n' + masked_line[split:]
 
-       m = search_re.match(masked_line)
 
-     output.extend(line.split(r'\n'))
 
-     mask_output.extend(masked_line.split(r'\n'))
 
-   return (output, mask_output)
 
- def split_double_braces(input):
 
-   """Masks out the quotes and comments, and then splits appropriate
 
-   lines (lines that matche the double_*_brace re's above) before
 
-   indenting them below.
 
-   These are used to split lines which have multiple braces on them, so
 
-   that the indentation looks prettier when all laid out (e.g. closing
 
-   braces make a nice diagonal line).
 
-   """
 
-   double_open_brace_re = re.compile(r'(.*?[\[\{\(,])(\s*)([\[\{\(])')
 
-   double_close_brace_re = re.compile(r'(.*?[\]\}\)],?)(\s*)([\]\}\)])')
 
-   masked_input = mask_quotes(input)
 
-   masked_input = mask_comments(masked_input)
 
-   (output, mask_output) = do_split(input, masked_input, double_open_brace_re)
 
-   (output, mask_output) = do_split(output, mask_output, double_close_brace_re)
 
-   return output
 
- def count_braces(line):
 
-   """keeps track of the number of braces on a given line and returns the result.
 
-   It starts at zero and subtracts for closed braces, and adds for open braces.
 
-   """
 
-   open_braces = ['[', '(', '{']
 
-   close_braces = [']', ')', '}']
 
-   closing_prefix_re = re.compile(r'(.*?[^\s\]\}\)]+.*?)([\]\}\)],?)\s*$')
 
-   cnt = 0
 
-   stripline = COMMENT_RE.sub(r'', line)
 
-   stripline = QUOTE_RE.sub(r"''", stripline)
 
-   for char in stripline:
 
-     for brace in open_braces:
 
-       if char == brace:
 
-         cnt += 1
 
-     for brace in close_braces:
 
-       if char == brace:
 
-         cnt -= 1
 
-   after = False
 
-   if cnt > 0:
 
-     after = True
 
-   # This catches the special case of a closing brace having something
 
-   # other than just whitespace ahead of it -- we don't want to
 
-   # unindent that until after this line is printed so it stays with
 
-   # the previous indentation level.
 
-   if cnt < 0 and closing_prefix_re.match(stripline):
 
-     after = True
 
-   return (cnt, after)
 
- def prettyprint_input(lines):
 
-   """Does the main work of indenting the input based on the brace counts."""
 
-   indent = 0
 
-   basic_offset = 2
 
-   last_line = ""
 
-   for line in lines:
 
-     if COMMENT_RE.match(line):
 
-       print line
 
-     else:
 
-       line = line.strip('\r\n\t ')  # Otherwise doesn't strip \r on Unix.
 
-       if len(line) > 0:
 
-         (brace_diff, after) = count_braces(line)
 
-         if brace_diff != 0:
 
-           if after:
 
-             print " " * (basic_offset * indent) + line
 
-             indent += brace_diff
 
-           else:
 
-             indent += brace_diff
 
-             print " " * (basic_offset * indent) + line
 
-         else:
 
-           print " " * (basic_offset * indent) + line
 
-       else:
 
-         print ""
 
-       last_line = line
 
- def main():
 
-   if len(sys.argv) > 1:
 
-     data = open(sys.argv[1]).read().splitlines()
 
-   else:
 
-     data = sys.stdin.read().splitlines()
 
-   # Split up the double braces.
 
-   lines = split_double_braces(data)
 
-   # Indent and print the output.
 
-   prettyprint_input(lines)
 
-   return 0
 
- if __name__ == '__main__':
 
-   sys.exit(main())
 
 
  |