annotate diff-colorize.py @ 16:4950e751a7cb

Added tag 1.0b2 for changeset a7214992f904
author Peter Hosey
date Mon, 11 Aug 2008 02:10:41 -0700
parents a7214992f904
children 54a209909531
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
0
2df4ed64a388 Initial check-in of first working version.
Peter Hosey
parents:
diff changeset
1 #!/usr/bin/env python
2df4ed64a388 Initial check-in of first working version.
Peter Hosey
parents:
diff changeset
2
6
d58b4e2e12d4 Moved the imports of sys and fileinput, so that all the imports are together.
Peter Hosey
parents: 5
diff changeset
3 import sys
4
b8b2d1931a9e Get our color constants from the environment, if possible.
Peter Hosey
parents: 3
diff changeset
4 import os
6
d58b4e2e12d4 Moved the imports of sys and fileinput, so that all the imports are together.
Peter Hosey
parents: 5
diff changeset
5 import fileinput
4
b8b2d1931a9e Get our color constants from the environment, if possible.
Peter Hosey
parents: 3
diff changeset
6
15
a7214992f904 Added a different set of default color codes and a different colorization format string. Both of these are to support 16-color mode (which is all Terminal supports).
Peter Hosey
parents: 13
diff changeset
7 has_256_color = (os.environ.get('TERM', None) == 'xterm-256color')
a7214992f904 Added a different set of default color codes and a different colorization format string. Both of these are to support 16-color mode (which is all Terminal supports).
Peter Hosey
parents: 13
diff changeset
8
a7214992f904 Added a different set of default color codes and a different colorization format string. Both of these are to support 16-color mode (which is all Terminal supports).
Peter Hosey
parents: 13
diff changeset
9 index_color = int(os.environ.get('DIFF_INDEX_COLOR',
a7214992f904 Added a different set of default color codes and a different colorization format string. Both of these are to support 16-color mode (which is all Terminal supports).
Peter Hosey
parents: 13
diff changeset
10 32 if has_256_color else 36))
a7214992f904 Added a different set of default color codes and a different colorization format string. Both of these are to support 16-color mode (which is all Terminal supports).
Peter Hosey
parents: 13
diff changeset
11 old_mode_color = int(os.environ.get('DIFF_OLD_MODE_COLOR',
a7214992f904 Added a different set of default color codes and a different colorization format string. Both of these are to support 16-color mode (which is all Terminal supports).
Peter Hosey
parents: 13
diff changeset
12 88 if has_256_color else 31))
a7214992f904 Added a different set of default color codes and a different colorization format string. Both of these are to support 16-color mode (which is all Terminal supports).
Peter Hosey
parents: 13
diff changeset
13 new_mode_color = int(os.environ.get('DIFF_NEW_MODE_COLOR',
a7214992f904 Added a different set of default color codes and a different colorization format string. Both of these are to support 16-color mode (which is all Terminal supports).
Peter Hosey
parents: 13
diff changeset
14 28 if has_256_color else 32))
a7214992f904 Added a different set of default color codes and a different colorization format string. Both of these are to support 16-color mode (which is all Terminal supports).
Peter Hosey
parents: 13
diff changeset
15 removed_color = int(os.environ.get('DIFF_REMOVED_COLOR',
a7214992f904 Added a different set of default color codes and a different colorization format string. Both of these are to support 16-color mode (which is all Terminal supports).
Peter Hosey
parents: 13
diff changeset
16 160 if has_256_color else 31))
a7214992f904 Added a different set of default color codes and a different colorization format string. Both of these are to support 16-color mode (which is all Terminal supports).
Peter Hosey
parents: 13
diff changeset
17 added_color = int(os.environ.get('DIFF_ADDED_COLOR',
a7214992f904 Added a different set of default color codes and a different colorization format string. Both of these are to support 16-color mode (which is all Terminal supports).
Peter Hosey
parents: 13
diff changeset
18 2 if has_256_color else 32))
a7214992f904 Added a different set of default color codes and a different colorization format string. Both of these are to support 16-color mode (which is all Terminal supports).
Peter Hosey
parents: 13
diff changeset
19 hunk_start_color = int(os.environ.get('DIFF_HUNK_START_COLOR',
a7214992f904 Added a different set of default color codes and a different colorization format string. Both of these are to support 16-color mode (which is all Terminal supports).
Peter Hosey
parents: 13
diff changeset
20 32 if has_256_color else 36))
0
2df4ed64a388 Initial check-in of first working version.
Peter Hosey
parents:
diff changeset
21
3
10948e4fd070 Move the color constants above the format strings, since the color constants are more editable.
Peter Hosey
parents: 2
diff changeset
22 RESET_FORMAT = '\033[0m'
15
a7214992f904 Added a different set of default color codes and a different colorization format string. Both of these are to support 16-color mode (which is all Terminal supports).
Peter Hosey
parents: 13
diff changeset
23 COLOR_FORMAT_256 = '\033[38;5;%um'
a7214992f904 Added a different set of default color codes and a different colorization format string. Both of these are to support 16-color mode (which is all Terminal supports).
Peter Hosey
parents: 13
diff changeset
24 COLOR_FORMAT_16 = '\033[38;%um'
a7214992f904 Added a different set of default color codes and a different colorization format string. Both of these are to support 16-color mode (which is all Terminal supports).
Peter Hosey
parents: 13
diff changeset
25 COLOR_FORMAT = COLOR_FORMAT_256 if has_256_color else COLOR_FORMAT_16
3
10948e4fd070 Move the color constants above the format strings, since the color constants are more editable.
Peter Hosey
parents: 2
diff changeset
26 BEGIN_REVERSE_FORMAT = '\033[7m'
10948e4fd070 Move the color constants above the format strings, since the color constants are more editable.
Peter Hosey
parents: 2
diff changeset
27 END_REVERSE_FORMAT = '\033[27m'
10948e4fd070 Move the color constants above the format strings, since the color constants are more editable.
Peter Hosey
parents: 2
diff changeset
28
9
cce6b860a98d Added usage information.
Peter Hosey
parents: 8
diff changeset
29 USAGE = """
cce6b860a98d Added usage information.
Peter Hosey
parents: 8
diff changeset
30 Usage: diff ... | diff-colorize
cce6b860a98d Added usage information.
Peter Hosey
parents: 8
diff changeset
31 or: diff-colorize < foo.diff
cce6b860a98d Added usage information.
Peter Hosey
parents: 8
diff changeset
32
cce6b860a98d Added usage information.
Peter Hosey
parents: 8
diff changeset
33 Reads unified or git-style diff data from standard input, colorizes it, and writes the result to standard output.
cce6b860a98d Added usage information.
Peter Hosey
parents: 8
diff changeset
34
cce6b860a98d Added usage information.
Peter Hosey
parents: 8
diff changeset
35 You can customize the color numbers used by setting these variables in your environment:
cce6b860a98d Added usage information.
Peter Hosey
parents: 8
diff changeset
36 * DIFF_INDEX_COLOR (lines starting with "Index: " or "diff --git ")
cce6b860a98d Added usage information.
Peter Hosey
parents: 8
diff changeset
37 * DIFF_OLD_MODE_COLOR (lines starting with "old mode"; these only appear in git-style diffs)
cce6b860a98d Added usage information.
Peter Hosey
parents: 8
diff changeset
38 * DIFF_NEW_MODE_COLOR (lines starting with "new mode"; these only appear in git-style diffs)
cce6b860a98d Added usage information.
Peter Hosey
parents: 8
diff changeset
39 * DIFF_REMOVED_COLOR (lines starting with "-")
cce6b860a98d Added usage information.
Peter Hosey
parents: 8
diff changeset
40 * DIFF_ADDED_COLOR (lines starting with "+")
cce6b860a98d Added usage information.
Peter Hosey
parents: 8
diff changeset
41 * DIFF_HUNK_START_COLOR (lines starting with "@@")
cce6b860a98d Added usage information.
Peter Hosey
parents: 8
diff changeset
42 """.strip()
cce6b860a98d Added usage information.
Peter Hosey
parents: 8
diff changeset
43
7
c6337f653d9b Added some comments documenting the OrderedDict class and our instance's contents.
Peter Hosey
parents: 6
diff changeset
44 # Everything in the unified diff format is identified by a prefix. The prefixes are:
c6337f653d9b Added some comments documenting the OrderedDict class and our instance's contents.
Peter Hosey
parents: 6
diff changeset
45 # 'Index: ': File marker (unified diff)
c6337f653d9b Added some comments documenting the OrderedDict class and our instance's contents.
Peter Hosey
parents: 6
diff changeset
46 # 'diff --git': File marker (git-style diff)
c6337f653d9b Added some comments documenting the OrderedDict class and our instance's contents.
Peter Hosey
parents: 6
diff changeset
47 # 'old mode': File permissions mode before change
c6337f653d9b Added some comments documenting the OrderedDict class and our instance's contents.
Peter Hosey
parents: 6
diff changeset
48 # 'new mode': File permissions mode after change
c6337f653d9b Added some comments documenting the OrderedDict class and our instance's contents.
Peter Hosey
parents: 6
diff changeset
49 # '---': Defining '-' (giving the name and modification date of the file before change)
c6337f653d9b Added some comments documenting the OrderedDict class and our instance's contents.
Peter Hosey
parents: 6
diff changeset
50 # '+++': Defining '+' (giving the name and modification date of the file after change)
c6337f653d9b Added some comments documenting the OrderedDict class and our instance's contents.
Peter Hosey
parents: 6
diff changeset
51 # '-': Line before change (i.e., removed)
c6337f653d9b Added some comments documenting the OrderedDict class and our instance's contents.
Peter Hosey
parents: 6
diff changeset
52 # '+': Line after change (i.e., added)
c6337f653d9b Added some comments documenting the OrderedDict class and our instance's contents.
Peter Hosey
parents: 6
diff changeset
53 # ' ': Line that hasn't changed
c6337f653d9b Added some comments documenting the OrderedDict class and our instance's contents.
Peter Hosey
parents: 6
diff changeset
54 # '@@': Hunk start (@@ -start,length +start, length @@)
c6337f653d9b Added some comments documenting the OrderedDict class and our instance's contents.
Peter Hosey
parents: 6
diff changeset
55 #
c6337f653d9b Added some comments documenting the OrderedDict class and our instance's contents.
Peter Hosey
parents: 6
diff changeset
56 # We need to look for these prefixes in order, in order to handle '---'/'+++' before '-'/'+'. Hence the OrderedDict.
1
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
57 class OrderedDict(dict):
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
58 def __init__(self, input=None):
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
59 if input is None:
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
60 self.keys = []
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
61 super(OrderedDict, self).__init__()
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
62 elif isinstance(input, dict):
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
63 self.keys = list(input)
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
64 super(OrderedDict, self).__init__(input)
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
65 else:
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
66 self.keys = [k for k, v in input]
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
67 super(OrderedDict, self).__init__(input)
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
68 def __iter__(self):
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
69 return iter(self.keys)
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
70 def __setitem__(self, k, v):
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
71 if k not in self:
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
72 self.keys.append(k)
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
73 super(OrderedDict, self).__setitem__(k, v)
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
74 def __delitem__(self, k):
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
75 super(OrderedDict, self).__delitem__(k)
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
76 self.keys.remove(k)
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
77
7
c6337f653d9b Added some comments documenting the OrderedDict class and our instance's contents.
Peter Hosey
parents: 6
diff changeset
78 # Each value includes not only the terminal-config characters, but also the key, somewhere within it (possibly between two terminal-config strings).
c6337f653d9b Added some comments documenting the OrderedDict class and our instance's contents.
Peter Hosey
parents: 6
diff changeset
79 # Theoretically, you could replace the key with some other string or leave it out entirely, if you wanted to, but I wouldn't recommend it.
1
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
80 prefixes = OrderedDict()
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
81 prefixes['---'] = (
8
4bb2557d24cd Now that these can come from the environment, they are variables. Lowercasing their names for this reason.
Peter Hosey
parents: 7
diff changeset
82 COLOR_FORMAT % (removed_color,)
1
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
83 + BEGIN_REVERSE_FORMAT
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
84 + '---'
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
85 + END_REVERSE_FORMAT
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
86 )
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
87 prefixes['+++'] = (
8
4bb2557d24cd Now that these can come from the environment, they are variables. Lowercasing their names for this reason.
Peter Hosey
parents: 7
diff changeset
88 COLOR_FORMAT % (added_color,)
1
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
89 + BEGIN_REVERSE_FORMAT
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
90 + '+++'
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
91 + END_REVERSE_FORMAT
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
92 )
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
93 prefixes['-'] = (
8
4bb2557d24cd Now that these can come from the environment, they are variables. Lowercasing their names for this reason.
Peter Hosey
parents: 7
diff changeset
94 COLOR_FORMAT % (removed_color,)
1
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
95 + BEGIN_REVERSE_FORMAT
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
96 + '-'
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
97 + END_REVERSE_FORMAT
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
98 )
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
99 prefixes['+'] = (
8
4bb2557d24cd Now that these can come from the environment, they are variables. Lowercasing their names for this reason.
Peter Hosey
parents: 7
diff changeset
100 COLOR_FORMAT % (added_color,)
1
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
101 + BEGIN_REVERSE_FORMAT
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
102 + '+'
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
103 + END_REVERSE_FORMAT
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
104 )
5
fa7cd4c2716b Added prefixes “old mode” and “new mode”, found in Git-style diffs, along with new color constants for them. We treat these the same way we treat “---” and “+++”.
Peter Hosey
parents: 4
diff changeset
105 prefixes['old mode'] = ( # Git-style diffs only
8
4bb2557d24cd Now that these can come from the environment, they are variables. Lowercasing their names for this reason.
Peter Hosey
parents: 7
diff changeset
106 COLOR_FORMAT % (old_mode_color,)
5
fa7cd4c2716b Added prefixes “old mode” and “new mode”, found in Git-style diffs, along with new color constants for them. We treat these the same way we treat “---” and “+++”.
Peter Hosey
parents: 4
diff changeset
107 + BEGIN_REVERSE_FORMAT
fa7cd4c2716b Added prefixes “old mode” and “new mode”, found in Git-style diffs, along with new color constants for them. We treat these the same way we treat “---” and “+++”.
Peter Hosey
parents: 4
diff changeset
108 + 'old mode'
fa7cd4c2716b Added prefixes “old mode” and “new mode”, found in Git-style diffs, along with new color constants for them. We treat these the same way we treat “---” and “+++”.
Peter Hosey
parents: 4
diff changeset
109 + END_REVERSE_FORMAT
fa7cd4c2716b Added prefixes “old mode” and “new mode”, found in Git-style diffs, along with new color constants for them. We treat these the same way we treat “---” and “+++”.
Peter Hosey
parents: 4
diff changeset
110 )
fa7cd4c2716b Added prefixes “old mode” and “new mode”, found in Git-style diffs, along with new color constants for them. We treat these the same way we treat “---” and “+++”.
Peter Hosey
parents: 4
diff changeset
111 prefixes['new mode'] = ( # Git-style diffs only
8
4bb2557d24cd Now that these can come from the environment, they are variables. Lowercasing their names for this reason.
Peter Hosey
parents: 7
diff changeset
112 COLOR_FORMAT % (new_mode_color,)
5
fa7cd4c2716b Added prefixes “old mode” and “new mode”, found in Git-style diffs, along with new color constants for them. We treat these the same way we treat “---” and “+++”.
Peter Hosey
parents: 4
diff changeset
113 + BEGIN_REVERSE_FORMAT
fa7cd4c2716b Added prefixes “old mode” and “new mode”, found in Git-style diffs, along with new color constants for them. We treat these the same way we treat “---” and “+++”.
Peter Hosey
parents: 4
diff changeset
114 + 'new mode'
fa7cd4c2716b Added prefixes “old mode” and “new mode”, found in Git-style diffs, along with new color constants for them. We treat these the same way we treat “---” and “+++”.
Peter Hosey
parents: 4
diff changeset
115 + END_REVERSE_FORMAT
fa7cd4c2716b Added prefixes “old mode” and “new mode”, found in Git-style diffs, along with new color constants for them. We treat these the same way we treat “---” and “+++”.
Peter Hosey
parents: 4
diff changeset
116 )
8
4bb2557d24cd Now that these can come from the environment, they are variables. Lowercasing their names for this reason.
Peter Hosey
parents: 7
diff changeset
117 prefixes['Index: '] = COLOR_FORMAT % (index_color,) + 'Index: '
4bb2557d24cd Now that these can come from the environment, they are variables. Lowercasing their names for this reason.
Peter Hosey
parents: 7
diff changeset
118 prefixes['diff --git '] = COLOR_FORMAT % (index_color,) + 'diff --git '
2
9eda9139d627 Added support for hunk start markers (@@…@@). For these, we set the whole line in reverse video, in the same color we use for index lines.
Peter Hosey
parents: 1
diff changeset
119 prefixes['@@'] = (
8
4bb2557d24cd Now that these can come from the environment, they are variables. Lowercasing their names for this reason.
Peter Hosey
parents: 7
diff changeset
120 COLOR_FORMAT % (hunk_start_color,)
2
9eda9139d627 Added support for hunk start markers (@@…@@). For these, we set the whole line in reverse video, in the same color we use for index lines.
Peter Hosey
parents: 1
diff changeset
121 + BEGIN_REVERSE_FORMAT
9eda9139d627 Added support for hunk start markers (@@…@@). For these, we set the whole line in reverse video, in the same color we use for index lines.
Peter Hosey
parents: 1
diff changeset
122 + '@@'
9eda9139d627 Added support for hunk start markers (@@…@@). For these, we set the whole line in reverse video, in the same color we use for index lines.
Peter Hosey
parents: 1
diff changeset
123 )
0
2df4ed64a388 Initial check-in of first working version.
Peter Hosey
parents:
diff changeset
124
9
cce6b860a98d Added usage information.
Peter Hosey
parents: 8
diff changeset
125 if sys.stdin.isatty():
cce6b860a98d Added usage information.
Peter Hosey
parents: 8
diff changeset
126 # Standard input is a TTY, meaning that the user ran 'diff-colorize' at the shell prompt, without redirecting anything into it. Print usage info and exit.
cce6b860a98d Added usage information.
Peter Hosey
parents: 8
diff changeset
127 sys.exit(USAGE)
cce6b860a98d Added usage information.
Peter Hosey
parents: 8
diff changeset
128
0
2df4ed64a388 Initial check-in of first working version.
Peter Hosey
parents:
diff changeset
129 for line in fileinput.input():
1
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
130 for prefix_to_test in prefixes:
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
131 if line.startswith(prefix_to_test):
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
132 sys.stdout.write(prefixes[prefix_to_test])
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
133 line = line[len(prefix_to_test):]
0
2df4ed64a388 Initial check-in of first working version.
Peter Hosey
parents:
diff changeset
134
2df4ed64a388 Initial check-in of first working version.
Peter Hosey
parents:
diff changeset
135 sys.stdout.write(line)
2df4ed64a388 Initial check-in of first working version.
Peter Hosey
parents:
diff changeset
136
1
44f86539d245 Refactored to allow me to more easily add new prefixes.
Peter Hosey
parents: 0
diff changeset
137 sys.stdout.write(RESET_FORMAT)