Mercurial > hg
annotate contrib/check-code.py @ 19785:1d2ca307bf22
merge with stable
author | Matt Mackall <mpm@selenic.com> |
---|---|
date | Mon, 23 Sep 2013 13:26:11 -0700 |
parents | 22a70f31e3e9 |
children | 6fb1b7728719 |
rev | line source |
---|---|
10281 | 1 #!/usr/bin/env python |
2 # | |
3 # check-code - a style and portability checker for Mercurial | |
4 # | |
10290
7cc60de189d7
check-code: fix copyright date
Matt Mackall <mpm@selenic.com>
parents:
10287
diff
changeset
|
5 # Copyright 2010 Matt Mackall <mpm@selenic.com> |
10281 | 6 # |
7 # This software may be used and distributed according to the terms of the | |
8 # GNU General Public License version 2 or any later version. | |
9 | |
11816
e1359ad582f6
check-code: add exit status
Alecs King <alecsk@gmail.com>
parents:
11764
diff
changeset
|
10 import re, glob, os, sys |
13074
637627f31c74
check-code: check for gratuitous whitespace after Python keywords
Thomas Arendsen Hein <thomas@jtah.de>
parents:
13031
diff
changeset
|
11 import keyword |
10895
217557b26bc7
check-code: add a warnings level
Matt Mackall <mpm@selenic.com>
parents:
10814
diff
changeset
|
12 import optparse |
19310
30ea54660d14
check-code: introduce function for using re2 when available
Simon Heimberg <simohe@besonet.ch>
parents:
19309
diff
changeset
|
13 try: |
30ea54660d14
check-code: introduce function for using re2 when available
Simon Heimberg <simohe@besonet.ch>
parents:
19309
diff
changeset
|
14 import re2 |
30ea54660d14
check-code: introduce function for using re2 when available
Simon Heimberg <simohe@besonet.ch>
parents:
19309
diff
changeset
|
15 except ImportError: |
30ea54660d14
check-code: introduce function for using re2 when available
Simon Heimberg <simohe@besonet.ch>
parents:
19309
diff
changeset
|
16 re2 = None |
30ea54660d14
check-code: introduce function for using re2 when available
Simon Heimberg <simohe@besonet.ch>
parents:
19309
diff
changeset
|
17 |
30ea54660d14
check-code: introduce function for using re2 when available
Simon Heimberg <simohe@besonet.ch>
parents:
19309
diff
changeset
|
18 def compilere(pat, multiline=False): |
30ea54660d14
check-code: introduce function for using re2 when available
Simon Heimberg <simohe@besonet.ch>
parents:
19309
diff
changeset
|
19 if multiline: |
30ea54660d14
check-code: introduce function for using re2 when available
Simon Heimberg <simohe@besonet.ch>
parents:
19309
diff
changeset
|
20 pat = '(?m)' + pat |
30ea54660d14
check-code: introduce function for using re2 when available
Simon Heimberg <simohe@besonet.ch>
parents:
19309
diff
changeset
|
21 if re2: |
30ea54660d14
check-code: introduce function for using re2 when available
Simon Heimberg <simohe@besonet.ch>
parents:
19309
diff
changeset
|
22 try: |
30ea54660d14
check-code: introduce function for using re2 when available
Simon Heimberg <simohe@besonet.ch>
parents:
19309
diff
changeset
|
23 return re2.compile(pat) |
30ea54660d14
check-code: introduce function for using re2 when available
Simon Heimberg <simohe@besonet.ch>
parents:
19309
diff
changeset
|
24 except re2.error: |
30ea54660d14
check-code: introduce function for using re2 when available
Simon Heimberg <simohe@besonet.ch>
parents:
19309
diff
changeset
|
25 pass |
30ea54660d14
check-code: introduce function for using re2 when available
Simon Heimberg <simohe@besonet.ch>
parents:
19309
diff
changeset
|
26 return re.compile(pat) |
10281 | 27 |
28 def repquote(m): | |
10722
c4fb2103e734
check-code: improve quote detection regexp, add tests
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents:
10720
diff
changeset
|
29 t = re.sub(r"\w", "x", m.group('text')) |
15281
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
30 t = re.sub(r"[^\s\nx]", "o", t) |
10722
c4fb2103e734
check-code: improve quote detection regexp, add tests
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents:
10720
diff
changeset
|
31 return m.group('quote') + t + m.group('quote') |
10281 | 32 |
10727
62b8f15683f2
check-code: more tests and more robust python filtering
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents:
10723
diff
changeset
|
33 def reppython(m): |
62b8f15683f2
check-code: more tests and more robust python filtering
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents:
10723
diff
changeset
|
34 comment = m.group('comment') |
62b8f15683f2
check-code: more tests and more robust python filtering
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents:
10723
diff
changeset
|
35 if comment: |
18959
2f6418d8a4c9
check-code: catch trailing space in comments
Mads Kiilerich <madski@unity3d.com>
parents:
18835
diff
changeset
|
36 l = len(comment.rstrip()) |
2f6418d8a4c9
check-code: catch trailing space in comments
Mads Kiilerich <madski@unity3d.com>
parents:
18835
diff
changeset
|
37 return "#" * l + comment[l:] |
10727
62b8f15683f2
check-code: more tests and more robust python filtering
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents:
10723
diff
changeset
|
38 return repquote(m) |
10281 | 39 |
40 def repcomment(m): | |
41 return m.group(1) + "#" * len(m.group(2)) | |
42 | |
43 def repccomment(m): | |
44 t = re.sub(r"((?<=\n) )|\S", "x", m.group(2)) | |
45 return m.group(1) + t + "*/" | |
46 | |
47 def repcallspaces(m): | |
48 t = re.sub(r"\n\s+", "\n", m.group(2)) | |
49 return m.group(1) + t | |
50 | |
51 def repinclude(m): | |
52 return m.group(1) + "<foo>" | |
53 | |
54 def rephere(m): | |
55 t = re.sub(r"\S", "x", m.group(2)) | |
56 return m.group(1) + t | |
57 | |
58 | |
59 testpats = [ | |
14009
64de9ca66511
check-code: separate warnings to avoid repetitive str.startswith
Idan Kamara <idankk86@gmail.com>
parents:
14005
diff
changeset
|
60 [ |
16495
5f9835ed3d6d
check-code: put grouping around regexps generated from testpats
Mads Kiilerich <mads@kiilerich.com>
parents:
16494
diff
changeset
|
61 (r'pushd|popd', "don't use 'pushd' or 'popd', use 'cd'"), |
15281
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
62 (r'\W\$?\(\([^\)\n]*\)\)', "don't use (()) or $(()), use 'expr'"), |
10374
3aa35db5e38c
check-code.py: make help strings consistent
Martin Geisler <mg@lazybytes.net>
parents:
10373
diff
changeset
|
63 (r'grep.*-q', "don't use 'grep -q', redirect to /dev/null"), |
19626
cf6b086d64cc
solaris: test cases can't use grep -a
Danek Duvall <danek.duvall@oracle.com>
parents:
19501
diff
changeset
|
64 (r'(?<!hg )grep.*-a', "don't use 'grep -a', use in-line python"), |
16332
42e95631887d
tests: remove sed -i from test-record
Matt Mackall <mpm@selenic.com>
parents:
16249
diff
changeset
|
65 (r'sed.*-i', "don't use 'sed -i', use a temporary file"), |
16965
91284af53508
test-alias: adapt for Windows
Mads Kiilerich <mads@kiilerich.com>
parents:
16705
diff
changeset
|
66 (r'\becho\b.*\\n', "don't use 'echo \\n', use printf"), |
11884
932448701e7d
check-code: catch "echo -n" in tests
Martin Geisler <mg@lazybytes.net>
parents:
11599
diff
changeset
|
67 (r'echo -n', "don't use 'echo -n', use printf"), |
15372
695ac6aca77f
check-code: fix issues with finding patterns in unified tests, fix tests
Matt Mackall <mpm@selenic.com>
parents:
15364
diff
changeset
|
68 (r'(^| )wc[^|]*$\n(?!.*\(re\))', "filter wc output"), |
10374
3aa35db5e38c
check-code.py: make help strings consistent
Martin Geisler <mg@lazybytes.net>
parents:
10373
diff
changeset
|
69 (r'head -c', "don't use 'head -c', use 'dd'"), |
19628
3193b23eec61
solaris: tests can't use tail -n
Danek Duvall <danek.duvall@oracle.com>
parents:
19626
diff
changeset
|
70 (r'tail -n', "don't use the '-n' option to tail, just use '-<num>'"), |
15389
3bece03bf3c6
tests: use md5sum.py instead of sha1sum, add check
Matt Mackall <mpm@selenic.com>
parents:
15372
diff
changeset
|
71 (r'sha1sum', "don't use sha1sum, use $TESTDIR/md5sum.py"), |
10374
3aa35db5e38c
check-code.py: make help strings consistent
Martin Geisler <mg@lazybytes.net>
parents:
10373
diff
changeset
|
72 (r'ls.*-\w*R', "don't use 'ls -R', use 'find'"), |
19380
ee07f9d142c9
check-code: do not warn on printf \\x or \\[1-9]
Simon Heimberg <simohe@besonet.ch>
parents:
19378
diff
changeset
|
73 (r'printf.*[^\\]\\([1-9]|0\d)', "don't use 'printf \NNN', use Python"), |
ee07f9d142c9
check-code: do not warn on printf \\x or \\[1-9]
Simon Heimberg <simohe@besonet.ch>
parents:
19378
diff
changeset
|
74 (r'printf.*[^\\]\\x', "don't use printf \\x, use Python"), |
10281 | 75 (r'\$\(.*\)', "don't use $(expr), use `expr`"), |
76 (r'rm -rf \*', "don't use naked rm -rf, target a directory"), | |
15372
695ac6aca77f
check-code: fix issues with finding patterns in unified tests, fix tests
Matt Mackall <mpm@selenic.com>
parents:
15364
diff
changeset
|
77 (r'(^|\|\s*)grep (-\w\s+)*[^|]*[(|]\w', |
10281 | 78 "use egrep for extended grep syntax"), |
79 (r'/bin/', "don't use explicit paths for tools"), | |
80 (r'[^\n]\Z', "no trailing newline"), | |
10658
95c7c4b7e67a
test-merge-default and check-code.py: No "export x=x" in sh
Mads Kiilerich <mads@kiilerich.com>
parents:
10451
diff
changeset
|
81 (r'export.*=', "don't export and assign at once"), |
15372
695ac6aca77f
check-code: fix issues with finding patterns in unified tests, fix tests
Matt Mackall <mpm@selenic.com>
parents:
15364
diff
changeset
|
82 (r'^source\b', "don't use 'source', use '.'"), |
12367
3acd5f7ab9d0
tests: compatibility fix.
Dan Villiom Podlaski Christiansen <danchr@gmail.com>
parents:
12366
diff
changeset
|
83 (r'touch -d', "don't use 'touch -d', use 'touch -t' instead"), |
15364
572c22c88be6
tests: fix check-code detection of anchored expressions, fix echo -n usage
Matt Mackall <mpm@selenic.com>
parents:
15334
diff
changeset
|
84 (r'ls +[^|\n-]+ +-', "options to 'ls' must come before filenames"), |
15281
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
85 (r'[^>\n]>\s*\$HGRCPATH', "don't overwrite $HGRCPATH, append to it"), |
15372
695ac6aca77f
check-code: fix issues with finding patterns in unified tests, fix tests
Matt Mackall <mpm@selenic.com>
parents:
15364
diff
changeset
|
86 (r'^stop\(\)', "don't use 'stop' as a shell function name"), |
15282
d4addef0ec74
tests: don't use 'test -e'
Mads Kiilerich <mads@kiilerich.com>
parents:
14978
diff
changeset
|
87 (r'(\[|\btest\b).*-e ', "don't use 'test -e', use 'test -f'"), |
16013
2a1d97630f7f
tests: don't use alias
Mads Kiilerich <mads@kiilerich.com>
parents:
15873
diff
changeset
|
88 (r'^alias\b.*=', "don't use alias, use a function"), |
16485
f48b075ff088
tests: solaris sh can not negate exit status with '!'
Mads Kiilerich <mads@kiilerich.com>
parents:
16483
diff
changeset
|
89 (r'if\s*!', "don't use '!' to negate exit status"), |
16494
e1f0305eabe4
tests: don't use /dev/urandom for largefiles testing
Mads Kiilerich <mads@kiilerich.com>
parents:
16487
diff
changeset
|
90 (r'/dev/u?random', "don't use entropy, use /dev/zero"), |
16496
abbabbbe4ec2
tests: use 'do sleep 0' instead of 'do true', also on first line of command
Mads Kiilerich <mads@kiilerich.com>
parents:
16495
diff
changeset
|
91 (r'do\s*true;\s*done', "don't use true as loop body, use sleep 0"), |
16497
c326fe884daa
tests: avoid tab indent on all kinds of lines of sh commands
Mads Kiilerich <mads@kiilerich.com>
parents:
16496
diff
changeset
|
92 (r'^( *)\t', "don't use tabs to indent"), |
19083
12f15e4b2ca0
check-code: fix sed 'i' command rule newline matching
Kevin Bullock <kbullock@ringworld.org>
parents:
19081
diff
changeset
|
93 (r'sed (-e )?\'(\d+|/[^/]*/)i(?!\\\n)', |
19080
5e4491c114b2
check-code: add a rule against a GNU sed-ism
Kevin Bullock <kbullock@ringworld.org>
parents:
19031
diff
changeset
|
94 "put a backslash-escaped newline after sed 'i' command"), |
14009
64de9ca66511
check-code: separate warnings to avoid repetitive str.startswith
Idan Kamara <idankk86@gmail.com>
parents:
14005
diff
changeset
|
95 ], |
64de9ca66511
check-code: separate warnings to avoid repetitive str.startswith
Idan Kamara <idankk86@gmail.com>
parents:
14005
diff
changeset
|
96 # warnings |
16672
d046eb97d21e
tests: run most check-code sh checks on continued lines too
Mads Kiilerich <mads@kiilerich.com>
parents:
16590
diff
changeset
|
97 [ |
d046eb97d21e
tests: run most check-code sh checks on continued lines too
Mads Kiilerich <mads@kiilerich.com>
parents:
16590
diff
changeset
|
98 (r'^function', "don't use 'function', use old style"), |
d046eb97d21e
tests: run most check-code sh checks on continued lines too
Mads Kiilerich <mads@kiilerich.com>
parents:
16590
diff
changeset
|
99 (r'^diff.*-\w*N', "don't use 'diff -N'"), |
18508
813b7a1f7036
tests: use `pwd` instead of ${PWD} in test-convert-git.t - because of Solaris
Mads Kiilerich <mads@kiilerich.com>
parents:
18183
diff
changeset
|
100 (r'\$PWD|\${PWD}', "don't use $PWD, use `pwd`"), |
16672
d046eb97d21e
tests: run most check-code sh checks on continued lines too
Mads Kiilerich <mads@kiilerich.com>
parents:
16590
diff
changeset
|
101 (r'^([^"\'\n]|("[^"\n]*")|(\'[^\'\n]*\'))*\^', "^ must be quoted"), |
18575
667063b22a69
check-code: warn to use killdaemons instead of kill `cat PIDFILE`
Kevin Bullock <kbullock@ringworld.org>
parents:
18508
diff
changeset
|
102 (r'kill (`|\$\()', "don't use kill, use killdaemons.py") |
16672
d046eb97d21e
tests: run most check-code sh checks on continued lines too
Mads Kiilerich <mads@kiilerich.com>
parents:
16590
diff
changeset
|
103 ] |
10281 | 104 ] |
105 | |
106 testfilters = [ | |
107 (r"( *)(#([^\n]*\S)?)", repcomment), | |
108 (r"<<(\S+)((.|\n)*?\n\1)", rephere), | |
109 ] | |
110 | |
18832
a911e5dc2b00
check-code: extract windows glob warning message
Simon Heimberg <simohe@besonet.ch>
parents:
18762
diff
changeset
|
111 winglobmsg = "use (glob) to match Windows paths too" |
15372
695ac6aca77f
check-code: fix issues with finding patterns in unified tests, fix tests
Matt Mackall <mpm@selenic.com>
parents:
15364
diff
changeset
|
112 uprefix = r"^ \$ " |
12364
e128fa4615f2
check-code: add some basic support for unified tests
Matt Mackall <mpm@selenic.com>
parents:
11886
diff
changeset
|
113 utestpats = [ |
14009
64de9ca66511
check-code: separate warnings to avoid repetitive str.startswith
Idan Kamara <idankk86@gmail.com>
parents:
14005
diff
changeset
|
114 [ |
17347
2da47de36b6f
check-code: fix check for trailing whitespace on continued lines too
Mads Kiilerich <mads@kiilerich.com>
parents:
17346
diff
changeset
|
115 (r'^(\S.*|| [$>] .*)[ \t]\n', "trailing whitespace on non-output"), |
16673
775a8d33e6f0
tests: unify the last sh tests
Mads Kiilerich <mads@kiilerich.com>
parents:
16672
diff
changeset
|
116 (uprefix + r'.*\|\s*sed[^|>\n]*\n', |
775a8d33e6f0
tests: unify the last sh tests
Mads Kiilerich <mads@kiilerich.com>
parents:
16672
diff
changeset
|
117 "use regex test output patterns instead of sed"), |
12364
e128fa4615f2
check-code: add some basic support for unified tests
Matt Mackall <mpm@selenic.com>
parents:
11886
diff
changeset
|
118 (uprefix + r'(true|exit 0)', "explicit zero exit unnecessary"), |
15607
fab28a577a38
test-svn-subrepo: fix reference output for svn 1.7
Patrick Mezard <pmezard@gmail.com>
parents:
15389
diff
changeset
|
119 (uprefix + r'.*(?<!\[)\$\?', "explicit exit code checks unnecessary"), |
12364
e128fa4615f2
check-code: add some basic support for unified tests
Matt Mackall <mpm@selenic.com>
parents:
11886
diff
changeset
|
120 (uprefix + r'.*\|\| echo.*(fail|error)', |
e128fa4615f2
check-code: add some basic support for unified tests
Matt Mackall <mpm@selenic.com>
parents:
11886
diff
changeset
|
121 "explicit exit code checks unnecessary"), |
e128fa4615f2
check-code: add some basic support for unified tests
Matt Mackall <mpm@selenic.com>
parents:
11886
diff
changeset
|
122 (uprefix + r'set -e', "don't use set -e"), |
16487
4fe874697a4d
tests: fix incorrect markup of continued lines of sh commands
Mads Kiilerich <mads@kiilerich.com>
parents:
16486
diff
changeset
|
123 (uprefix + r'\s', "don't indent commands, use > for continued lines"), |
18832
a911e5dc2b00
check-code: extract windows glob warning message
Simon Heimberg <simohe@besonet.ch>
parents:
18762
diff
changeset
|
124 (r'^ saved backup bundle to \$TESTTMP.*\.hg$', winglobmsg), |
18835
4e7498a586e8
check-code: fix a check-code failure in check-code
Bryan O'Sullivan <bryano@fb.com>
parents:
18834
diff
changeset
|
125 (r'^ changeset .* references (corrupted|missing) \$TESTTMP/.*[^)]$', |
4e7498a586e8
check-code: fix a check-code failure in check-code
Bryan O'Sullivan <bryano@fb.com>
parents:
18834
diff
changeset
|
126 winglobmsg), |
18834
1a4a939a6b90
check-code: re-add check for missing glob
Simon Heimberg <simohe@besonet.ch>
parents:
18833
diff
changeset
|
127 (r'^ pulling from \$TESTTMP/.*[^)]$', winglobmsg, '\$TESTTMP/unix-repo$'), |
19123
a91894c8064a
check-code: add more path sep glob checks
Matt Mackall <mpm@selenic.com>
parents:
19083
diff
changeset
|
128 (r'^ reverting .*/.*[^)]$', winglobmsg, '\$TESTTMP/unix-repo$'), |
a91894c8064a
check-code: add more path sep glob checks
Matt Mackall <mpm@selenic.com>
parents:
19083
diff
changeset
|
129 (r'^ cloning subrepo \S+/.*[^)]$', winglobmsg, '\$TESTTMP/unix-repo$'), |
a91894c8064a
check-code: add more path sep glob checks
Matt Mackall <mpm@selenic.com>
parents:
19083
diff
changeset
|
130 (r'^ pushing to \$TESTTMP/.*[^)]$', winglobmsg, '\$TESTTMP/unix-repo$'), |
19168
60b63216997c
check-code: add another Windows pathsep rule
Matt Mackall <mpm@selenic.com>
parents:
19133
diff
changeset
|
131 (r'^ pushing subrepo \S+/\S+ to.*[^)]$', winglobmsg, |
60b63216997c
check-code: add another Windows pathsep rule
Matt Mackall <mpm@selenic.com>
parents:
19133
diff
changeset
|
132 '\$TESTTMP/unix-repo$'), |
19133
101b80eb7364
tests: check path separator in moves
Brendan Cully <brendan@kublai.com>
parents:
19123
diff
changeset
|
133 (r'^ moving \S+/.*[^)]$', winglobmsg), |
19123
a91894c8064a
check-code: add more path sep glob checks
Matt Mackall <mpm@selenic.com>
parents:
19083
diff
changeset
|
134 (r'^ no changes made to subrepo since.*/.*[^)]$', |
a91894c8064a
check-code: add more path sep glob checks
Matt Mackall <mpm@selenic.com>
parents:
19083
diff
changeset
|
135 winglobmsg, '\$TESTTMP/unix-repo$'), |
a91894c8064a
check-code: add more path sep glob checks
Matt Mackall <mpm@selenic.com>
parents:
19083
diff
changeset
|
136 (r'^ .*: largefile \S+ not available from file:.*/.*[^)]$', |
a91894c8064a
check-code: add more path sep glob checks
Matt Mackall <mpm@selenic.com>
parents:
19083
diff
changeset
|
137 winglobmsg, '\$TESTTMP/unix-repo$'), |
14009
64de9ca66511
check-code: separate warnings to avoid repetitive str.startswith
Idan Kamara <idankk86@gmail.com>
parents:
14005
diff
changeset
|
138 ], |
64de9ca66511
check-code: separate warnings to avoid repetitive str.startswith
Idan Kamara <idankk86@gmail.com>
parents:
14005
diff
changeset
|
139 # warnings |
18683
a343eccd5ee2
check-code: warn about line glob match with no glob character (?*/)
Simon Heimberg <simohe@besonet.ch>
parents:
18575
diff
changeset
|
140 [ |
a343eccd5ee2
check-code: warn about line glob match with no glob character (?*/)
Simon Heimberg <simohe@besonet.ch>
parents:
18575
diff
changeset
|
141 (r'^ [^*?/\n]* \(glob\)$', |
19422
d9e86d656017
check-code: automatically preppend "warning: " to all warning messages
Simon Heimberg <simohe@besonet.ch>
parents:
19382
diff
changeset
|
142 "glob match with no glob character (?*/)"), |
18683
a343eccd5ee2
check-code: warn about line glob match with no glob character (?*/)
Simon Heimberg <simohe@besonet.ch>
parents:
18575
diff
changeset
|
143 ] |
12364
e128fa4615f2
check-code: add some basic support for unified tests
Matt Mackall <mpm@selenic.com>
parents:
11886
diff
changeset
|
144 ] |
e128fa4615f2
check-code: add some basic support for unified tests
Matt Mackall <mpm@selenic.com>
parents:
11886
diff
changeset
|
145 |
14203
b230922eb0c3
check-code: fix checking for sh style in .t tests
Mads Kiilerich <mads@kiilerich.com>
parents:
14169
diff
changeset
|
146 for i in [0, 1]: |
b230922eb0c3
check-code: fix checking for sh style in .t tests
Mads Kiilerich <mads@kiilerich.com>
parents:
14169
diff
changeset
|
147 for p, m in testpats[i]: |
15372
695ac6aca77f
check-code: fix issues with finding patterns in unified tests, fix tests
Matt Mackall <mpm@selenic.com>
parents:
15364
diff
changeset
|
148 if p.startswith(r'^'): |
16672
d046eb97d21e
tests: run most check-code sh checks on continued lines too
Mads Kiilerich <mads@kiilerich.com>
parents:
16590
diff
changeset
|
149 p = r"^ [$>] (%s)" % p[1:] |
14203
b230922eb0c3
check-code: fix checking for sh style in .t tests
Mads Kiilerich <mads@kiilerich.com>
parents:
14169
diff
changeset
|
150 else: |
16672
d046eb97d21e
tests: run most check-code sh checks on continued lines too
Mads Kiilerich <mads@kiilerich.com>
parents:
16590
diff
changeset
|
151 p = r"^ [$>] .*(%s)" % p |
14203
b230922eb0c3
check-code: fix checking for sh style in .t tests
Mads Kiilerich <mads@kiilerich.com>
parents:
14169
diff
changeset
|
152 utestpats[i].append((p, m)) |
12364
e128fa4615f2
check-code: add some basic support for unified tests
Matt Mackall <mpm@selenic.com>
parents:
11886
diff
changeset
|
153 |
e128fa4615f2
check-code: add some basic support for unified tests
Matt Mackall <mpm@selenic.com>
parents:
11886
diff
changeset
|
154 utestfilters = [ |
17711
cf204e9829f4
check-code: replace heredocs in unified tests
Idan Kamara <idankk86@gmail.com>
parents:
17620
diff
changeset
|
155 (r"<<(\S+)((.|\n)*?\n > \1)", rephere), |
12364
e128fa4615f2
check-code: add some basic support for unified tests
Matt Mackall <mpm@selenic.com>
parents:
11886
diff
changeset
|
156 (r"( *)(#([^\n]*\S)?)", repcomment), |
e128fa4615f2
check-code: add some basic support for unified tests
Matt Mackall <mpm@selenic.com>
parents:
11886
diff
changeset
|
157 ] |
e128fa4615f2
check-code: add some basic support for unified tests
Matt Mackall <mpm@selenic.com>
parents:
11886
diff
changeset
|
158 |
10281 | 159 pypats = [ |
14009
64de9ca66511
check-code: separate warnings to avoid repetitive str.startswith
Idan Kamara <idankk86@gmail.com>
parents:
14005
diff
changeset
|
160 [ |
11568
d5d4e6a30613
check-code: check for tuple parameter unpacking (missing in py3k)
Renato Cunha <renatoc@gmail.com>
parents:
11522
diff
changeset
|
161 (r'^\s*def\s*\w+\s*\(.*,\s*\(', |
d5d4e6a30613
check-code: check for tuple parameter unpacking (missing in py3k)
Renato Cunha <renatoc@gmail.com>
parents:
11522
diff
changeset
|
162 "tuple parameter unpacking not available in Python 3+"), |
d5d4e6a30613
check-code: check for tuple parameter unpacking (missing in py3k)
Renato Cunha <renatoc@gmail.com>
parents:
11522
diff
changeset
|
163 (r'lambda\s*\(.*,.*\)', |
d5d4e6a30613
check-code: check for tuple parameter unpacking (missing in py3k)
Renato Cunha <renatoc@gmail.com>
parents:
11522
diff
changeset
|
164 "tuple parameter unpacking not available in Python 3+"), |
11764
16723af520b0
check-code: added a check for calls to the builtin cmp function
Renato Cunha <renatoc@gmail.com>
parents:
11672
diff
changeset
|
165 (r'(?<!def)\s+(cmp)\(', "cmp is not available in Python 3+"), |
11569
f8576644a222
check-code: added check for reduce usage
Renato Cunha <renatoc@gmail.com>
parents:
11568
diff
changeset
|
166 (r'\breduce\s*\(.*', "reduce is not available in Python 3+"), |
11602
ba2520dd1e29
check-code: catch dict.has_key
Martin Geisler <mg@lazybytes.net>
parents:
11601
diff
changeset
|
167 (r'\.has_key\b', "dict.has_key is not available in Python 3+"), |
18183
e1caaeb5a2ed
check-code: disallow defunct <> operator
Augie Fackler <raf@durin42.com>
parents:
18180
diff
changeset
|
168 (r'\s<>\s', '<> operator is not available in Python 3+, use !='), |
10281 | 169 (r'^\s*\t', "don't use tabs"), |
10412
5326800d6937
check-code: import some pylint checks
Matt Mackall <mpm@selenic.com>
parents:
10374
diff
changeset
|
170 (r'\S;\s*\n', "semicolon"), |
16234
a6941d7033fa
check-code: check for % inside _()
Matt Mackall <mpm@selenic.com>
parents:
16098
diff
changeset
|
171 (r'[^_]_\("[^"]+"\s*%', "don't use % inside _()"), |
a6941d7033fa
check-code: check for % inside _()
Matt Mackall <mpm@selenic.com>
parents:
16098
diff
changeset
|
172 (r"[^_]_\('[^']+'\s*%", "don't use % inside _()"), |
18054
b35e3364f94a
check-code: there must also be whitespace between ')' and operator
Mads Kiilerich <madski@unity3d.com>
parents:
17957
diff
changeset
|
173 (r'(\w|\)),\w', "missing whitespace after ,"), |
b35e3364f94a
check-code: there must also be whitespace between ')' and operator
Mads Kiilerich <madski@unity3d.com>
parents:
17957
diff
changeset
|
174 (r'(\w|\))[+/*\-<>]\w', "missing whitespace in expression"), |
18055
e440a2c0d944
check-code: make 'missing whitespace in assignment' more aggressive
Mads Kiilerich <madski@unity3d.com>
parents:
18054
diff
changeset
|
175 (r'^\s+(\w|\.)+=\w[^,()\n]*$', "missing whitespace in assignment"), |
15372
695ac6aca77f
check-code: fix issues with finding patterns in unified tests, fix tests
Matt Mackall <mpm@selenic.com>
parents:
15364
diff
changeset
|
176 (r'(\s+)try:\n((?:\n|\1\s.*\n)+?)\1except.*?:\n' |
17428
72803c8edaa4
avoid using abbreviations that look like spelling errors
Mads Kiilerich <mads@kiilerich.com>
parents:
17424
diff
changeset
|
177 r'((?:\n|\1\s.*\n)+?)\1finally:', 'no try/except/finally in Python 2.4'), |
19501
725507cd5216
check-code: add a check for the next() builtin, which was new in 2.6
Augie Fackler <raf@durin42.com>
parents:
19494
diff
changeset
|
178 (r'(?<!def)(\s+|^|\()next\(.+\)', |
725507cd5216
check-code: add a check for the next() builtin, which was new in 2.6
Augie Fackler <raf@durin42.com>
parents:
19494
diff
changeset
|
179 'no next(foo) in Python 2.4 and 2.5, use foo.next() instead'), |
17620
efd1a4378b64
check-code: catch yield inside try/finally (with tests)
Thomas Arendsen Hein <thomas@intevation.de>
parents:
17428
diff
changeset
|
180 (r'(\s+)try:\n((?:\n|\1\s.*\n)*?)\1\s*yield\b.*?' |
efd1a4378b64
check-code: catch yield inside try/finally (with tests)
Thomas Arendsen Hein <thomas@intevation.de>
parents:
17428
diff
changeset
|
181 r'((?:\n|\1\s.*\n)+?)\1finally:', |
efd1a4378b64
check-code: catch yield inside try/finally (with tests)
Thomas Arendsen Hein <thomas@intevation.de>
parents:
17428
diff
changeset
|
182 'no yield inside try/finally in Python 2.4'), |
16702
1751d96d324f
check-code: promote 80+ character line warning to an error
Brodie Rao <brodie@sf.io>
parents:
16683
diff
changeset
|
183 (r'.{81}', "line too long"), |
15372
695ac6aca77f
check-code: fix issues with finding patterns in unified tests, fix tests
Matt Mackall <mpm@selenic.com>
parents:
15364
diff
changeset
|
184 (r' x+[xo][\'"]\n\s+[\'"]x', 'string join across lines with no space'), |
10281 | 185 (r'[^\n]\Z', "no trailing newline"), |
15281
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
186 (r'(\S[ \t]+|^[ \t]+)\n', "trailing whitespace"), |
16683 | 187 # (r'^\s+[^_ \n][^_. \n]+_[^_\n]+\s*=', |
188 # "don't use underbars in identifiers"), | |
15457
1470f8b00694
check-code: enable camelcase check, fix up problems
Matt Mackall <mpm@selenic.com>
parents:
15389
diff
changeset
|
189 (r'^\s+(self\.)?[A-za-z][a-z0-9]+[A-Z]\w* = ', |
1470f8b00694
check-code: enable camelcase check, fix up problems
Matt Mackall <mpm@selenic.com>
parents:
15389
diff
changeset
|
190 "don't use camelcase in identifiers"), |
15281
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
191 (r'^\s*(if|while|def|class|except|try)\s[^[\n]*:\s*[^\\n]#\s]+', |
10286 | 192 "linebreak after :"), |
15281
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
193 (r'class\s[^( \n]+:', "old-style class, use class foo(object)"), |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
194 (r'class\s[^( \n]+\(\):', |
14763
b071cd58af50
check-code: fix class style checking (with tests)
Thomas Arendsen Hein <thomas@intevation.de>
parents:
14709
diff
changeset
|
195 "class foo() not available in Python 2.4, use class foo(object)"), |
13076
a861c7155f09
check-code: single check for Python keywords used as a function
Thomas Arendsen Hein <thomas@jtah.de>
parents:
13074
diff
changeset
|
196 (r'\b(%s)\(' % '|'.join(keyword.kwlist), |
a861c7155f09
check-code: single check for Python keywords used as a function
Thomas Arendsen Hein <thomas@jtah.de>
parents:
13074
diff
changeset
|
197 "Python keyword is not a function"), |
10412
5326800d6937
check-code: import some pylint checks
Matt Mackall <mpm@selenic.com>
parents:
10374
diff
changeset
|
198 (r',]', "unneeded trailing ',' in list"), |
10281 | 199 # (r'class\s[A-Z][^\(]*\((?!Exception)', |
200 # "don't capitalize non-exception classes"), | |
201 # (r'in range\(', "use xrange"), | |
202 # (r'^\s*print\s+', "avoid using print in core and extensions"), | |
203 (r'[\x80-\xff]', "non-ASCII character literal"), | |
204 (r'("\')\.format\(', "str.format() not available in Python 2.4"), | |
205 (r'^\s*with\s+', "with not available in Python 2.4"), | |
14267
6332c02b3d68
check-code: complain about set.isdisjoint
Matt Mackall <mpm@selenic.com>
parents:
14203
diff
changeset
|
206 (r'\.isdisjoint\(', "set.isdisjoint not available in Python 2.4"), |
13160
07d08c130892
check-code: catch "except as"
Matt Mackall <mpm@selenic.com>
parents:
13076
diff
changeset
|
207 (r'^\s*except.* as .*:', "except as not available in Python 2.4"), |
13161
11eb53464e68
check-code: catch os.path.relpath
Matt Mackall <mpm@selenic.com>
parents:
13160
diff
changeset
|
208 (r'^\s*os\.path\.relpath', "relpath not available in Python 2.4"), |
11345
4b81f82b03e3
check-code: reformat long lines
Martin Geisler <mg@aragost.com>
parents:
11343
diff
changeset
|
209 (r'(?<!def)\s+(any|all|format)\(', |
4b81f82b03e3
check-code: reformat long lines
Martin Geisler <mg@aragost.com>
parents:
11343
diff
changeset
|
210 "any/all/format not available in Python 2.4"), |
11522
eaa7666ad53f
check-code: add test for callable
Martin Geisler <mg@aragost.com>
parents:
11345
diff
changeset
|
211 (r'(?<!def)\s+(callable)\(', |
14978
5a0fdc715769
check-code: disallow use of hasattr()
Augie Fackler <durin42@gmail.com>
parents:
14831
diff
changeset
|
212 "callable not available in Python 3, use getattr(f, '__call__', None)"), |
10281 | 213 (r'if\s.*\selse', "if ... else form not available in Python 2.4"), |
13074
637627f31c74
check-code: check for gratuitous whitespace after Python keywords
Thomas Arendsen Hein <thomas@jtah.de>
parents:
13031
diff
changeset
|
214 (r'^\s*(%s)\s\s' % '|'.join(keyword.kwlist), |
637627f31c74
check-code: check for gratuitous whitespace after Python keywords
Thomas Arendsen Hein <thomas@jtah.de>
parents:
13031
diff
changeset
|
215 "gratuitous whitespace after Python keyword"), |
15281
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
216 (r'([\(\[][ \t]\S)|(\S[ \t][\)\]])', "gratuitous whitespace in () or []"), |
10281 | 217 # (r'\s\s=', "gratuitous whitespace before ="), |
17167
5f131ae05905
check-code: recognise %= as an operator
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
17111
diff
changeset
|
218 (r'[^>< ](\+=|-=|!=|<>|<=|>=|<<=|>>=|%=)\S', |
11345
4b81f82b03e3
check-code: reformat long lines
Martin Geisler <mg@aragost.com>
parents:
11343
diff
changeset
|
219 "missing whitespace around operator"), |
17167
5f131ae05905
check-code: recognise %= as an operator
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
17111
diff
changeset
|
220 (r'[^>< ](\+=|-=|!=|<>|<=|>=|<<=|>>=|%=)\s', |
11345
4b81f82b03e3
check-code: reformat long lines
Martin Geisler <mg@aragost.com>
parents:
11343
diff
changeset
|
221 "missing whitespace around operator"), |
17167
5f131ae05905
check-code: recognise %= as an operator
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
17111
diff
changeset
|
222 (r'\s(\+=|-=|!=|<>|<=|>=|<<=|>>=|%=)\S', |
11345
4b81f82b03e3
check-code: reformat long lines
Martin Geisler <mg@aragost.com>
parents:
11343
diff
changeset
|
223 "missing whitespace around operator"), |
17167
5f131ae05905
check-code: recognise %= as an operator
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
17111
diff
changeset
|
224 (r'[^^+=*/!<>&| %-](\s=|=\s)[^= ]', |
11345
4b81f82b03e3
check-code: reformat long lines
Martin Geisler <mg@aragost.com>
parents:
11343
diff
changeset
|
225 "wrong whitespace around ="), |
10451
63a9bfad50ff
check-code: two more rules
Matt Mackall <mpm@selenic.com>
parents:
10412
diff
changeset
|
226 (r'raise Exception', "don't raise generic exceptions"), |
18180
c582a71457e5
check-code: disallow two-argument form of raise
Augie Fackler <raf@durin42.com>
parents:
18055
diff
changeset
|
227 (r'raise [^,(]+, (\([^\)]+\)|[^,\(\)]+)$', |
c582a71457e5
check-code: disallow two-argument form of raise
Augie Fackler <raf@durin42.com>
parents:
18055
diff
changeset
|
228 "don't use old-style two-argument raise, use Exception(message)"), |
14009
64de9ca66511
check-code: separate warnings to avoid repetitive str.startswith
Idan Kamara <idankk86@gmail.com>
parents:
14005
diff
changeset
|
229 (r' is\s+(not\s+)?["\'0-9-]', "object comparison with literal"), |
64de9ca66511
check-code: separate warnings to avoid repetitive str.startswith
Idan Kamara <idankk86@gmail.com>
parents:
14005
diff
changeset
|
230 (r' [=!]=\s+(True|False|None)', |
64de9ca66511
check-code: separate warnings to avoid repetitive str.startswith
Idan Kamara <idankk86@gmail.com>
parents:
14005
diff
changeset
|
231 "comparison with singleton, use 'is' or 'is not' instead"), |
14494
1ffeeb91c55d
check-code: flag 0/1 used as constant Boolean expression
Martin Geisler <mg@lazybytes.net>
parents:
14303
diff
changeset
|
232 (r'^\s*(while|if) [01]:', |
1ffeeb91c55d
check-code: flag 0/1 used as constant Boolean expression
Martin Geisler <mg@lazybytes.net>
parents:
14303
diff
changeset
|
233 "use True/False for constant Boolean expression"), |
16416
c3aedd526d53
mq: replace hasattr() with util.safehasattr(), update check-code.py
Patrick Mezard <patrick@mezard.eu>
parents:
16364
diff
changeset
|
234 (r'(?:(?<!def)\s+|\()hasattr', |
14978
5a0fdc715769
check-code: disallow use of hasattr()
Augie Fackler <durin42@gmail.com>
parents:
14831
diff
changeset
|
235 'hasattr(foo, bar) is broken, use util.safehasattr(foo, bar) instead'), |
14169
1b4b82063ce2
check-code: disallow calling opener(...).read() and opener(..).write()
Dan Villiom Podlaski Christiansen <danchr@gmail.com>
parents:
14137
diff
changeset
|
236 (r'opener\([^)]*\).read\(', |
1b4b82063ce2
check-code: disallow calling opener(...).read() and opener(..).write()
Dan Villiom Podlaski Christiansen <danchr@gmail.com>
parents:
14137
diff
changeset
|
237 "use opener.read() instead"), |
17428
72803c8edaa4
avoid using abbreviations that look like spelling errors
Mads Kiilerich <mads@kiilerich.com>
parents:
17424
diff
changeset
|
238 (r'BaseException', 'not in Python 2.4, use Exception'), |
72803c8edaa4
avoid using abbreviations that look like spelling errors
Mads Kiilerich <mads@kiilerich.com>
parents:
17424
diff
changeset
|
239 (r'os\.path\.relpath', 'os.path.relpath is not in Python 2.5'), |
14169
1b4b82063ce2
check-code: disallow calling opener(...).read() and opener(..).write()
Dan Villiom Podlaski Christiansen <danchr@gmail.com>
parents:
14137
diff
changeset
|
240 (r'opener\([^)]*\).write\(', |
1b4b82063ce2
check-code: disallow calling opener(...).read() and opener(..).write()
Dan Villiom Podlaski Christiansen <danchr@gmail.com>
parents:
14137
diff
changeset
|
241 "use opener.write() instead"), |
1b4b82063ce2
check-code: disallow calling opener(...).read() and opener(..).write()
Dan Villiom Podlaski Christiansen <danchr@gmail.com>
parents:
14137
diff
changeset
|
242 (r'[\s\(](open|file)\([^)]*\)\.read\(', |
1b4b82063ce2
check-code: disallow calling opener(...).read() and opener(..).write()
Dan Villiom Podlaski Christiansen <danchr@gmail.com>
parents:
14137
diff
changeset
|
243 "use util.readfile() instead"), |
1b4b82063ce2
check-code: disallow calling opener(...).read() and opener(..).write()
Dan Villiom Podlaski Christiansen <danchr@gmail.com>
parents:
14137
diff
changeset
|
244 (r'[\s\(](open|file)\([^)]*\)\.write\(', |
1b4b82063ce2
check-code: disallow calling opener(...).read() and opener(..).write()
Dan Villiom Podlaski Christiansen <danchr@gmail.com>
parents:
14137
diff
changeset
|
245 "use util.readfile() instead"), |
1b4b82063ce2
check-code: disallow calling opener(...).read() and opener(..).write()
Dan Villiom Podlaski Christiansen <danchr@gmail.com>
parents:
14137
diff
changeset
|
246 (r'^[\s\(]*(open(er)?|file)\([^)]*\)', |
1b4b82063ce2
check-code: disallow calling opener(...).read() and opener(..).write()
Dan Villiom Podlaski Christiansen <danchr@gmail.com>
parents:
14137
diff
changeset
|
247 "always assign an opened file to a variable, and close it afterwards"), |
1b4b82063ce2
check-code: disallow calling opener(...).read() and opener(..).write()
Dan Villiom Podlaski Christiansen <danchr@gmail.com>
parents:
14137
diff
changeset
|
248 (r'[\s\(](open|file)\([^)]*\)\.', |
1b4b82063ce2
check-code: disallow calling opener(...).read() and opener(..).write()
Dan Villiom Podlaski Christiansen <danchr@gmail.com>
parents:
14137
diff
changeset
|
249 "always assign an opened file to a variable, and close it afterwards"), |
14549
48ec0763afbb
check-code: catch misspellings of descendant
Matt Mackall <mpm@selenic.com>
parents:
14494
diff
changeset
|
250 (r'(?i)descendent', "the proper spelling is descendAnt"), |
14709
6c7283faa967
check-code: don't mark debug messages for translation
Matt Mackall <mpm@selenic.com>
parents:
14549
diff
changeset
|
251 (r'\.debug\(\_', "don't mark debug messages for translation"), |
16590
7f76c97361e0
check-code: catch unnecessary s.strip().split() calls
Martin Geisler <mg@aragost.com>
parents:
16497
diff
changeset
|
252 (r'\.strip\(\)\.split\(\)', "no need to strip before splitting"), |
18762
a91387a37f05
check-code: do not prepend "warning" to a failure message
Simon Heimberg <simohe@besonet.ch>
parents:
18683
diff
changeset
|
253 (r'^\s*except\s*:', "naked except clause", r'#.*re-raises'), |
17299
e51d4aedace9
check-code: indent 4 spaces in py files
Mads Kiilerich <mads@kiilerich.com>
parents:
17167
diff
changeset
|
254 (r':\n( )*( ){1,3}[^ ]', "must indent 4 spaces"), |
17957
fbe43efe4a53
check-code: move i18n check from warning to error
Matt Mackall <mpm@selenic.com>
parents:
17711
diff
changeset
|
255 (r'ui\.(status|progress|write|note|warn)\([\'\"]x', |
fbe43efe4a53
check-code: move i18n check from warning to error
Matt Mackall <mpm@selenic.com>
parents:
17711
diff
changeset
|
256 "missing _() in ui message (use () to hide false-positives)"), |
19031
341083b02d1b
check-code: add check for lock release order
Matt Mackall <mpm@selenic.com>
parents:
18960
diff
changeset
|
257 (r'release\(.*wlock, .*lock\)', "wrong lock release order"), |
14009
64de9ca66511
check-code: separate warnings to avoid repetitive str.startswith
Idan Kamara <idankk86@gmail.com>
parents:
14005
diff
changeset
|
258 ], |
64de9ca66511
check-code: separate warnings to avoid repetitive str.startswith
Idan Kamara <idankk86@gmail.com>
parents:
14005
diff
changeset
|
259 # warnings |
64de9ca66511
check-code: separate warnings to avoid repetitive str.startswith
Idan Kamara <idankk86@gmail.com>
parents:
14005
diff
changeset
|
260 [ |
64de9ca66511
check-code: separate warnings to avoid repetitive str.startswith
Idan Kamara <idankk86@gmail.com>
parents:
14005
diff
changeset
|
261 ] |
10281 | 262 ] |
263 | |
264 pyfilters = [ | |
10727
62b8f15683f2
check-code: more tests and more robust python filtering
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents:
10723
diff
changeset
|
265 (r"""(?msx)(?P<comment>\#.*?$)| |
62b8f15683f2
check-code: more tests and more robust python filtering
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents:
10723
diff
changeset
|
266 ((?P<quote>('''|\"\"\"|(?<!')'(?!')|(?<!")"(?!"))) |
62b8f15683f2
check-code: more tests and more robust python filtering
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents:
10723
diff
changeset
|
267 (?P<text>(([^\\]|\\.)*?)) |
62b8f15683f2
check-code: more tests and more robust python filtering
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents:
10723
diff
changeset
|
268 (?P=quote))""", reppython), |
10281 | 269 ] |
270 | |
18960
170fc0949fb6
check-code: check txt files for trailing whitespace
Mads Kiilerich <madski@unity3d.com>
parents:
18959
diff
changeset
|
271 txtfilters = [] |
170fc0949fb6
check-code: check txt files for trailing whitespace
Mads Kiilerich <madski@unity3d.com>
parents:
18959
diff
changeset
|
272 |
170fc0949fb6
check-code: check txt files for trailing whitespace
Mads Kiilerich <madski@unity3d.com>
parents:
18959
diff
changeset
|
273 txtpats = [ |
170fc0949fb6
check-code: check txt files for trailing whitespace
Mads Kiilerich <madski@unity3d.com>
parents:
18959
diff
changeset
|
274 [ |
170fc0949fb6
check-code: check txt files for trailing whitespace
Mads Kiilerich <madski@unity3d.com>
parents:
18959
diff
changeset
|
275 ('\s$', 'trailing whitespace'), |
170fc0949fb6
check-code: check txt files for trailing whitespace
Mads Kiilerich <madski@unity3d.com>
parents:
18959
diff
changeset
|
276 ], |
170fc0949fb6
check-code: check txt files for trailing whitespace
Mads Kiilerich <madski@unity3d.com>
parents:
18959
diff
changeset
|
277 [] |
170fc0949fb6
check-code: check txt files for trailing whitespace
Mads Kiilerich <madski@unity3d.com>
parents:
18959
diff
changeset
|
278 ] |
170fc0949fb6
check-code: check txt files for trailing whitespace
Mads Kiilerich <madski@unity3d.com>
parents:
18959
diff
changeset
|
279 |
10281 | 280 cpats = [ |
14009
64de9ca66511
check-code: separate warnings to avoid repetitive str.startswith
Idan Kamara <idankk86@gmail.com>
parents:
14005
diff
changeset
|
281 [ |
10281 | 282 (r'//', "don't use //-style comments"), |
283 (r'^ ', "don't use spaces to indent"), | |
284 (r'\S\t', "don't use tabs except for indent"), | |
15281
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
285 (r'(\S[ \t]+|^[ \t]+)\n', "trailing whitespace"), |
16702
1751d96d324f
check-code: promote 80+ character line warning to an error
Brodie Rao <brodie@sf.io>
parents:
16683
diff
changeset
|
286 (r'.{81}', "line too long"), |
10281 | 287 (r'(while|if|do|for)\(', "use space after while/if/do/for"), |
288 (r'return\(', "return is not a function"), | |
289 (r' ;', "no space before ;"), | |
19745
22a70f31e3e9
check-code: add bracket style check
Matt Mackall <mpm@selenic.com>
parents:
19732
diff
changeset
|
290 (r'[)][{]', "space between ) and {"), |
10281 | 291 (r'\w+\* \w+', "use int *foo, not int* foo"), |
19731
436a3f728375
check-code: make casting style check more precise
Matt Mackall <mpm@selenic.com>
parents:
19628
diff
changeset
|
292 (r'\W\([^\)]+\) \w+', "use (int)foo, not (int) foo"), |
16413
1a420761fcb7
check-code: avoid false-positive on ++
Matt Mackall <mpm@selenic.com>
parents:
16373
diff
changeset
|
293 (r'\w+ (\+\+|--)', "use foo++, not foo ++"), |
10281 | 294 (r'\w,\w', "missing whitespace after ,"), |
13736
f3c4421e121c
osutil: fix up check-code issues
Matt Mackall <mpm@selenic.com>
parents:
13524
diff
changeset
|
295 (r'^[^#]\w[+/*]\w', "missing whitespace in expression"), |
10281 | 296 (r'^#\s+\w', "use #foo, not # foo"), |
297 (r'[^\n]\Z', "no trailing newline"), | |
13748
26f8844d1757
osutil: replace #import with #include, and add a check for it
Dan Villiom Podlaski Christiansen <danchr@gmail.com>
parents:
13736
diff
changeset
|
298 (r'^\s*#import\b', "use only #include in standard C code"), |
14009
64de9ca66511
check-code: separate warnings to avoid repetitive str.startswith
Idan Kamara <idankk86@gmail.com>
parents:
14005
diff
changeset
|
299 ], |
64de9ca66511
check-code: separate warnings to avoid repetitive str.startswith
Idan Kamara <idankk86@gmail.com>
parents:
14005
diff
changeset
|
300 # warnings |
64de9ca66511
check-code: separate warnings to avoid repetitive str.startswith
Idan Kamara <idankk86@gmail.com>
parents:
14005
diff
changeset
|
301 [] |
10281 | 302 ] |
303 | |
304 cfilters = [ | |
305 (r'(/\*)(((\*(?!/))|[^*])*)\*/', repccomment), | |
10722
c4fb2103e734
check-code: improve quote detection regexp, add tests
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents:
10720
diff
changeset
|
306 (r'''(?P<quote>(?<!")")(?P<text>([^"]|\\")+)"(?!")''', repquote), |
10281 | 307 (r'''(#\s*include\s+<)([^>]+)>''', repinclude), |
308 (r'(\()([^)]+\))', repcallspaces), | |
309 ] | |
310 | |
14137
83a94c2fe6f4
check-code: check for repo in revlog and ui in util
timeless <timeless@mozdev.org>
parents:
14136
diff
changeset
|
311 inutilpats = [ |
83a94c2fe6f4
check-code: check for repo in revlog and ui in util
timeless <timeless@mozdev.org>
parents:
14136
diff
changeset
|
312 [ |
83a94c2fe6f4
check-code: check for repo in revlog and ui in util
timeless <timeless@mozdev.org>
parents:
14136
diff
changeset
|
313 (r'\bui\.', "don't use ui in util"), |
83a94c2fe6f4
check-code: check for repo in revlog and ui in util
timeless <timeless@mozdev.org>
parents:
14136
diff
changeset
|
314 ], |
83a94c2fe6f4
check-code: check for repo in revlog and ui in util
timeless <timeless@mozdev.org>
parents:
14136
diff
changeset
|
315 # warnings |
83a94c2fe6f4
check-code: check for repo in revlog and ui in util
timeless <timeless@mozdev.org>
parents:
14136
diff
changeset
|
316 [] |
83a94c2fe6f4
check-code: check for repo in revlog and ui in util
timeless <timeless@mozdev.org>
parents:
14136
diff
changeset
|
317 ] |
83a94c2fe6f4
check-code: check for repo in revlog and ui in util
timeless <timeless@mozdev.org>
parents:
14136
diff
changeset
|
318 |
83a94c2fe6f4
check-code: check for repo in revlog and ui in util
timeless <timeless@mozdev.org>
parents:
14136
diff
changeset
|
319 inrevlogpats = [ |
83a94c2fe6f4
check-code: check for repo in revlog and ui in util
timeless <timeless@mozdev.org>
parents:
14136
diff
changeset
|
320 [ |
83a94c2fe6f4
check-code: check for repo in revlog and ui in util
timeless <timeless@mozdev.org>
parents:
14136
diff
changeset
|
321 (r'\brepo\.', "don't use repo in revlog"), |
83a94c2fe6f4
check-code: check for repo in revlog and ui in util
timeless <timeless@mozdev.org>
parents:
14136
diff
changeset
|
322 ], |
83a94c2fe6f4
check-code: check for repo in revlog and ui in util
timeless <timeless@mozdev.org>
parents:
14136
diff
changeset
|
323 # warnings |
83a94c2fe6f4
check-code: check for repo in revlog and ui in util
timeless <timeless@mozdev.org>
parents:
14136
diff
changeset
|
324 [] |
83a94c2fe6f4
check-code: check for repo in revlog and ui in util
timeless <timeless@mozdev.org>
parents:
14136
diff
changeset
|
325 ] |
83a94c2fe6f4
check-code: check for repo in revlog and ui in util
timeless <timeless@mozdev.org>
parents:
14136
diff
changeset
|
326 |
10281 | 327 checks = [ |
328 ('python', r'.*\.(py|cgi)$', pyfilters, pypats), | |
329 ('test script', r'(.*/)?test-[^.~]*$', testfilters, testpats), | |
19732
1abd45e2553a
check-code: check C patterns against .h files
Matt Mackall <mpm@selenic.com>
parents:
19731
diff
changeset
|
330 ('c', r'.*\.[ch]$', cfilters, cpats), |
12364
e128fa4615f2
check-code: add some basic support for unified tests
Matt Mackall <mpm@selenic.com>
parents:
11886
diff
changeset
|
331 ('unified test', r'.*\.t$', utestfilters, utestpats), |
14137
83a94c2fe6f4
check-code: check for repo in revlog and ui in util
timeless <timeless@mozdev.org>
parents:
14136
diff
changeset
|
332 ('layering violation repo in revlog', r'mercurial/revlog\.py', pyfilters, |
83a94c2fe6f4
check-code: check for repo in revlog and ui in util
timeless <timeless@mozdev.org>
parents:
14136
diff
changeset
|
333 inrevlogpats), |
83a94c2fe6f4
check-code: check for repo in revlog and ui in util
timeless <timeless@mozdev.org>
parents:
14136
diff
changeset
|
334 ('layering violation ui in util', r'mercurial/util\.py', pyfilters, |
83a94c2fe6f4
check-code: check for repo in revlog and ui in util
timeless <timeless@mozdev.org>
parents:
14136
diff
changeset
|
335 inutilpats), |
18960
170fc0949fb6
check-code: check txt files for trailing whitespace
Mads Kiilerich <madski@unity3d.com>
parents:
18959
diff
changeset
|
336 ('txt', r'.*\.txt$', txtfilters, txtpats), |
10281 | 337 ] |
338 | |
19307
5443d40d524b
check-code: only fix patterns once
Simon Heimberg <simohe@besonet.ch>
parents:
19168
diff
changeset
|
339 def _preparepats(): |
5443d40d524b
check-code: only fix patterns once
Simon Heimberg <simohe@besonet.ch>
parents:
19168
diff
changeset
|
340 for c in checks: |
5443d40d524b
check-code: only fix patterns once
Simon Heimberg <simohe@besonet.ch>
parents:
19168
diff
changeset
|
341 failandwarn = c[-1] |
5443d40d524b
check-code: only fix patterns once
Simon Heimberg <simohe@besonet.ch>
parents:
19168
diff
changeset
|
342 for pats in failandwarn: |
5443d40d524b
check-code: only fix patterns once
Simon Heimberg <simohe@besonet.ch>
parents:
19168
diff
changeset
|
343 for i, pseq in enumerate(pats): |
5443d40d524b
check-code: only fix patterns once
Simon Heimberg <simohe@besonet.ch>
parents:
19168
diff
changeset
|
344 # fix-up regexes for multi-line searches |
19378
9de689d20230
cleanup: drop unused variables and an unused import
Simon Heimberg <simohe@besonet.ch>
parents:
19310
diff
changeset
|
345 p = pseq[0] |
19307
5443d40d524b
check-code: only fix patterns once
Simon Heimberg <simohe@besonet.ch>
parents:
19168
diff
changeset
|
346 # \s doesn't match \n |
5443d40d524b
check-code: only fix patterns once
Simon Heimberg <simohe@besonet.ch>
parents:
19168
diff
changeset
|
347 p = re.sub(r'(?<!\\)\\s', r'[ \\t]', p) |
5443d40d524b
check-code: only fix patterns once
Simon Heimberg <simohe@besonet.ch>
parents:
19168
diff
changeset
|
348 # [^...] doesn't match newline |
5443d40d524b
check-code: only fix patterns once
Simon Heimberg <simohe@besonet.ch>
parents:
19168
diff
changeset
|
349 p = re.sub(r'(?<!\\)\[\^', r'[^\\n', p) |
5443d40d524b
check-code: only fix patterns once
Simon Heimberg <simohe@besonet.ch>
parents:
19168
diff
changeset
|
350 |
19308
84faaacbd3fa
check-code: compile all patterns on initialisation
Simon Heimberg <simohe@besonet.ch>
parents:
19307
diff
changeset
|
351 pats[i] = (re.compile(p, re.MULTILINE),) + pseq[1:] |
19309
7d77fa1cd537
check-code: compile filters when loading
Simon Heimberg <simohe@besonet.ch>
parents:
19308
diff
changeset
|
352 filters = c[2] |
7d77fa1cd537
check-code: compile filters when loading
Simon Heimberg <simohe@besonet.ch>
parents:
19308
diff
changeset
|
353 for i, flt in enumerate(filters): |
7d77fa1cd537
check-code: compile filters when loading
Simon Heimberg <simohe@besonet.ch>
parents:
19308
diff
changeset
|
354 filters[i] = re.compile(flt[0]), flt[1] |
19307
5443d40d524b
check-code: only fix patterns once
Simon Heimberg <simohe@besonet.ch>
parents:
19168
diff
changeset
|
355 _preparepats() |
5443d40d524b
check-code: only fix patterns once
Simon Heimberg <simohe@besonet.ch>
parents:
19168
diff
changeset
|
356 |
10719
3be9ae49b628
code-code: Add a logfunc argument to checkfile
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10718
diff
changeset
|
357 class norepeatlogger(object): |
3be9ae49b628
code-code: Add a logfunc argument to checkfile
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10718
diff
changeset
|
358 def __init__(self): |
3be9ae49b628
code-code: Add a logfunc argument to checkfile
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10718
diff
changeset
|
359 self._lastseen = None |
3be9ae49b628
code-code: Add a logfunc argument to checkfile
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10718
diff
changeset
|
360 |
11604
c5d40818b270
check-code: add --blame switch
Matt Mackall <mpm@selenic.com>
parents:
11602
diff
changeset
|
361 def log(self, fname, lineno, line, msg, blame): |
10719
3be9ae49b628
code-code: Add a logfunc argument to checkfile
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10718
diff
changeset
|
362 """print error related a to given line of a given file. |
3be9ae49b628
code-code: Add a logfunc argument to checkfile
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10718
diff
changeset
|
363 |
3be9ae49b628
code-code: Add a logfunc argument to checkfile
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10718
diff
changeset
|
364 The faulty line will also be printed but only once in the case |
3be9ae49b628
code-code: Add a logfunc argument to checkfile
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10718
diff
changeset
|
365 of multiple errors. |
10281 | 366 |
10719
3be9ae49b628
code-code: Add a logfunc argument to checkfile
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10718
diff
changeset
|
367 :fname: filename |
3be9ae49b628
code-code: Add a logfunc argument to checkfile
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10718
diff
changeset
|
368 :lineno: line number |
3be9ae49b628
code-code: Add a logfunc argument to checkfile
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10718
diff
changeset
|
369 :line: actual content of the line |
3be9ae49b628
code-code: Add a logfunc argument to checkfile
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10718
diff
changeset
|
370 :msg: error message |
3be9ae49b628
code-code: Add a logfunc argument to checkfile
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10718
diff
changeset
|
371 """ |
3be9ae49b628
code-code: Add a logfunc argument to checkfile
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10718
diff
changeset
|
372 msgid = fname, lineno, line |
3be9ae49b628
code-code: Add a logfunc argument to checkfile
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10718
diff
changeset
|
373 if msgid != self._lastseen: |
11604
c5d40818b270
check-code: add --blame switch
Matt Mackall <mpm@selenic.com>
parents:
11602
diff
changeset
|
374 if blame: |
c5d40818b270
check-code: add --blame switch
Matt Mackall <mpm@selenic.com>
parents:
11602
diff
changeset
|
375 print "%s:%d (%s):" % (fname, lineno, blame) |
c5d40818b270
check-code: add --blame switch
Matt Mackall <mpm@selenic.com>
parents:
11602
diff
changeset
|
376 else: |
c5d40818b270
check-code: add --blame switch
Matt Mackall <mpm@selenic.com>
parents:
11602
diff
changeset
|
377 print "%s:%d:" % (fname, lineno) |
10719
3be9ae49b628
code-code: Add a logfunc argument to checkfile
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10718
diff
changeset
|
378 print " > %s" % line |
3be9ae49b628
code-code: Add a logfunc argument to checkfile
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10718
diff
changeset
|
379 self._lastseen = msgid |
3be9ae49b628
code-code: Add a logfunc argument to checkfile
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10718
diff
changeset
|
380 print " " + msg |
3be9ae49b628
code-code: Add a logfunc argument to checkfile
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10718
diff
changeset
|
381 |
3be9ae49b628
code-code: Add a logfunc argument to checkfile
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10718
diff
changeset
|
382 _defaultlogger = norepeatlogger() |
3be9ae49b628
code-code: Add a logfunc argument to checkfile
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10718
diff
changeset
|
383 |
11604
c5d40818b270
check-code: add --blame switch
Matt Mackall <mpm@selenic.com>
parents:
11602
diff
changeset
|
384 def getblame(f): |
c5d40818b270
check-code: add --blame switch
Matt Mackall <mpm@selenic.com>
parents:
11602
diff
changeset
|
385 lines = [] |
c5d40818b270
check-code: add --blame switch
Matt Mackall <mpm@selenic.com>
parents:
11602
diff
changeset
|
386 for l in os.popen('hg annotate -un %s' % f): |
c5d40818b270
check-code: add --blame switch
Matt Mackall <mpm@selenic.com>
parents:
11602
diff
changeset
|
387 start, line = l.split(':', 1) |
c5d40818b270
check-code: add --blame switch
Matt Mackall <mpm@selenic.com>
parents:
11602
diff
changeset
|
388 user, rev = start.split() |
c5d40818b270
check-code: add --blame switch
Matt Mackall <mpm@selenic.com>
parents:
11602
diff
changeset
|
389 lines.append((line[1:-1], user, rev)) |
c5d40818b270
check-code: add --blame switch
Matt Mackall <mpm@selenic.com>
parents:
11602
diff
changeset
|
390 return lines |
c5d40818b270
check-code: add --blame switch
Matt Mackall <mpm@selenic.com>
parents:
11602
diff
changeset
|
391 |
c5d40818b270
check-code: add --blame switch
Matt Mackall <mpm@selenic.com>
parents:
11602
diff
changeset
|
392 def checkfile(f, logfunc=_defaultlogger.log, maxerr=None, warnings=False, |
15502
7917a104a285
check-code: add --nolineno option for hiding line numbers
Mads Kiilerich <mads@kiilerich.com>
parents:
15457
diff
changeset
|
393 blame=False, debug=False, lineno=True): |
10719
3be9ae49b628
code-code: Add a logfunc argument to checkfile
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10718
diff
changeset
|
394 """checks style and portability of a given file |
3be9ae49b628
code-code: Add a logfunc argument to checkfile
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10718
diff
changeset
|
395 |
3be9ae49b628
code-code: Add a logfunc argument to checkfile
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10718
diff
changeset
|
396 :f: filepath |
3be9ae49b628
code-code: Add a logfunc argument to checkfile
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10718
diff
changeset
|
397 :logfunc: function used to report error |
3be9ae49b628
code-code: Add a logfunc argument to checkfile
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10718
diff
changeset
|
398 logfunc(filename, linenumber, linecontent, errormessage) |
17424
e7cfe3587ea4
fix trivial spelling errors
Mads Kiilerich <mads@kiilerich.com>
parents:
17347
diff
changeset
|
399 :maxerr: number of error to display before aborting. |
15873
a153a86a472c
tests: keep track of all check-code.py warnings
Mads Kiilerich <mads@kiilerich.com>
parents:
15611
diff
changeset
|
400 Set to false (default) to report all errors |
10720
fbcccf9ec58f
check-code: add a return value to checkfile function
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10719
diff
changeset
|
401 |
fbcccf9ec58f
check-code: add a return value to checkfile function
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10719
diff
changeset
|
402 return True if no error is found, False otherwise. |
10719
3be9ae49b628
code-code: Add a logfunc argument to checkfile
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10718
diff
changeset
|
403 """ |
11604
c5d40818b270
check-code: add --blame switch
Matt Mackall <mpm@selenic.com>
parents:
11602
diff
changeset
|
404 blamecache = None |
10720
fbcccf9ec58f
check-code: add a return value to checkfile function
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10719
diff
changeset
|
405 result = True |
10281 | 406 for name, match, filters, pats in checks: |
14135
673abd432104
check-code: adding debug flag
timeless <timeless@mozdev.org>
parents:
14009
diff
changeset
|
407 if debug: |
673abd432104
check-code: adding debug flag
timeless <timeless@mozdev.org>
parents:
14009
diff
changeset
|
408 print name, f |
10281 | 409 fc = 0 |
410 if not re.match(match, f): | |
14135
673abd432104
check-code: adding debug flag
timeless <timeless@mozdev.org>
parents:
14009
diff
changeset
|
411 if debug: |
673abd432104
check-code: adding debug flag
timeless <timeless@mozdev.org>
parents:
14009
diff
changeset
|
412 print "Skipping %s for %s it doesn't match %s" % ( |
673abd432104
check-code: adding debug flag
timeless <timeless@mozdev.org>
parents:
14009
diff
changeset
|
413 name, match, f) |
10281 | 414 continue |
19494
3119dc155ac2
check-code: do not abort on an unreadable file, only report this
Simon Heimberg <simohe@besonet.ch>
parents:
19422
diff
changeset
|
415 try: |
3119dc155ac2
check-code: do not abort on an unreadable file, only report this
Simon Heimberg <simohe@besonet.ch>
parents:
19422
diff
changeset
|
416 fp = open(f) |
3119dc155ac2
check-code: do not abort on an unreadable file, only report this
Simon Heimberg <simohe@besonet.ch>
parents:
19422
diff
changeset
|
417 except IOError, e: |
3119dc155ac2
check-code: do not abort on an unreadable file, only report this
Simon Heimberg <simohe@besonet.ch>
parents:
19422
diff
changeset
|
418 print "Skipping %s, %s" % (f, str(e).split(':', 1)[0]) |
3119dc155ac2
check-code: do not abort on an unreadable file, only report this
Simon Heimberg <simohe@besonet.ch>
parents:
19422
diff
changeset
|
419 continue |
13400
14f3795a5ed7
explicitly close files
Dan Villiom Podlaski Christiansen <danchr@gmail.com>
parents:
13301
diff
changeset
|
420 pre = post = fp.read() |
14f3795a5ed7
explicitly close files
Dan Villiom Podlaski Christiansen <danchr@gmail.com>
parents:
13301
diff
changeset
|
421 fp.close() |
19382
5aeb03b48ab4
check-code: concatenate "check-code" on compile time
Simon Heimberg <simohe@besonet.ch>
parents:
19380
diff
changeset
|
422 if "no-" "check-code" in pre: |
14135
673abd432104
check-code: adding debug flag
timeless <timeless@mozdev.org>
parents:
14009
diff
changeset
|
423 if debug: |
19382
5aeb03b48ab4
check-code: concatenate "check-code" on compile time
Simon Heimberg <simohe@besonet.ch>
parents:
19380
diff
changeset
|
424 print "Skipping %s for %s it has no-" " check-code" % ( |
14135
673abd432104
check-code: adding debug flag
timeless <timeless@mozdev.org>
parents:
14009
diff
changeset
|
425 name, f) |
10287
5da892be3497
check-code: add some ignore hints
Matt Mackall <mpm@selenic.com>
parents:
10286
diff
changeset
|
426 break |
10281 | 427 for p, r in filters: |
428 post = re.sub(p, r, post) | |
19422
d9e86d656017
check-code: automatically preppend "warning: " to all warning messages
Simon Heimberg <simohe@besonet.ch>
parents:
19382
diff
changeset
|
429 nerrs = len(pats[0]) # nerr elements are errors |
14009
64de9ca66511
check-code: separate warnings to avoid repetitive str.startswith
Idan Kamara <idankk86@gmail.com>
parents:
14005
diff
changeset
|
430 if warnings: |
64de9ca66511
check-code: separate warnings to avoid repetitive str.startswith
Idan Kamara <idankk86@gmail.com>
parents:
14005
diff
changeset
|
431 pats = pats[0] + pats[1] |
64de9ca66511
check-code: separate warnings to avoid repetitive str.startswith
Idan Kamara <idankk86@gmail.com>
parents:
14005
diff
changeset
|
432 else: |
64de9ca66511
check-code: separate warnings to avoid repetitive str.startswith
Idan Kamara <idankk86@gmail.com>
parents:
14005
diff
changeset
|
433 pats = pats[0] |
10281 | 434 # print post # uncomment to show filtered version |
15281
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
435 |
14135
673abd432104
check-code: adding debug flag
timeless <timeless@mozdev.org>
parents:
14009
diff
changeset
|
436 if debug: |
673abd432104
check-code: adding debug flag
timeless <timeless@mozdev.org>
parents:
14009
diff
changeset
|
437 print "Checking %s for %s" % (name, f) |
15281
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
438 |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
439 prelines = None |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
440 errors = [] |
19422
d9e86d656017
check-code: automatically preppend "warning: " to all warning messages
Simon Heimberg <simohe@besonet.ch>
parents:
19382
diff
changeset
|
441 for i, pat in enumerate(pats): |
16705
c2d9ef43ff6c
check-code: ignore naked excepts with a "re-raise" comment
Brodie Rao <brodie@sf.io>
parents:
16704
diff
changeset
|
442 if len(pat) == 3: |
c2d9ef43ff6c
check-code: ignore naked excepts with a "re-raise" comment
Brodie Rao <brodie@sf.io>
parents:
16704
diff
changeset
|
443 p, msg, ignore = pat |
c2d9ef43ff6c
check-code: ignore naked excepts with a "re-raise" comment
Brodie Rao <brodie@sf.io>
parents:
16704
diff
changeset
|
444 else: |
c2d9ef43ff6c
check-code: ignore naked excepts with a "re-raise" comment
Brodie Rao <brodie@sf.io>
parents:
16704
diff
changeset
|
445 p, msg = pat |
c2d9ef43ff6c
check-code: ignore naked excepts with a "re-raise" comment
Brodie Rao <brodie@sf.io>
parents:
16704
diff
changeset
|
446 ignore = None |
c2d9ef43ff6c
check-code: ignore naked excepts with a "re-raise" comment
Brodie Rao <brodie@sf.io>
parents:
16704
diff
changeset
|
447 |
15281
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
448 pos = 0 |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
449 n = 0 |
19308
84faaacbd3fa
check-code: compile all patterns on initialisation
Simon Heimberg <simohe@besonet.ch>
parents:
19307
diff
changeset
|
450 for m in p.finditer(post): |
15281
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
451 if prelines is None: |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
452 prelines = pre.splitlines() |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
453 postlines = post.splitlines(True) |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
454 |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
455 start = m.start() |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
456 while n < len(postlines): |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
457 step = len(postlines[n]) |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
458 if pos + step > start: |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
459 break |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
460 pos += step |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
461 n += 1 |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
462 l = prelines[n] |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
463 |
19382
5aeb03b48ab4
check-code: concatenate "check-code" on compile time
Simon Heimberg <simohe@besonet.ch>
parents:
19380
diff
changeset
|
464 if "check-code" "-ignore" in l: |
15281
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
465 if debug: |
19382
5aeb03b48ab4
check-code: concatenate "check-code" on compile time
Simon Heimberg <simohe@besonet.ch>
parents:
19380
diff
changeset
|
466 print "Skipping %s for %s:%s (check-code" "-ignore)" % ( |
15281
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
467 name, f, n) |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
468 continue |
16705
c2d9ef43ff6c
check-code: ignore naked excepts with a "re-raise" comment
Brodie Rao <brodie@sf.io>
parents:
16704
diff
changeset
|
469 elif ignore and re.search(ignore, l, re.MULTILINE): |
c2d9ef43ff6c
check-code: ignore naked excepts with a "re-raise" comment
Brodie Rao <brodie@sf.io>
parents:
16704
diff
changeset
|
470 continue |
15281
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
471 bd = "" |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
472 if blame: |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
473 bd = 'working directory' |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
474 if not blamecache: |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
475 blamecache = getblame(f) |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
476 if n < len(blamecache): |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
477 bl, bu, br = blamecache[n] |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
478 if bl == l: |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
479 bd = '%s@%s' % (bu, br) |
19422
d9e86d656017
check-code: automatically preppend "warning: " to all warning messages
Simon Heimberg <simohe@besonet.ch>
parents:
19382
diff
changeset
|
480 if i >= nerrs: |
d9e86d656017
check-code: automatically preppend "warning: " to all warning messages
Simon Heimberg <simohe@besonet.ch>
parents:
19382
diff
changeset
|
481 msg = "warning: " + msg |
15502
7917a104a285
check-code: add --nolineno option for hiding line numbers
Mads Kiilerich <mads@kiilerich.com>
parents:
15457
diff
changeset
|
482 errors.append((f, lineno and n + 1, l, msg, bd)) |
15281
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
483 result = False |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
484 |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
485 errors.sort() |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
486 for e in errors: |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
487 logfunc(*e) |
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
488 fc += 1 |
15873
a153a86a472c
tests: keep track of all check-code.py warnings
Mads Kiilerich <mads@kiilerich.com>
parents:
15611
diff
changeset
|
489 if maxerr and fc >= maxerr: |
10281 | 490 print " (too many errors, giving up)" |
491 break | |
15281
aeeb2afcdc25
check-code: support multiline matches like try/except/finally
Matt Mackall <mpm@selenic.com>
parents:
14978
diff
changeset
|
492 |
10720
fbcccf9ec58f
check-code: add a return value to checkfile function
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10719
diff
changeset
|
493 return result |
10717
b1f4fcef99b3
check-code: Add a ``checkfile`` function
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10716
diff
changeset
|
494 |
10716
5f92bde72eef
check-code: Only call check-code if __name__ = "__main__".
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10707
diff
changeset
|
495 if __name__ == "__main__": |
10895
217557b26bc7
check-code: add a warnings level
Matt Mackall <mpm@selenic.com>
parents:
10814
diff
changeset
|
496 parser = optparse.OptionParser("%prog [options] [files]") |
217557b26bc7
check-code: add a warnings level
Matt Mackall <mpm@selenic.com>
parents:
10814
diff
changeset
|
497 parser.add_option("-w", "--warnings", action="store_true", |
217557b26bc7
check-code: add a warnings level
Matt Mackall <mpm@selenic.com>
parents:
10814
diff
changeset
|
498 help="include warning-level checks") |
217557b26bc7
check-code: add a warnings level
Matt Mackall <mpm@selenic.com>
parents:
10814
diff
changeset
|
499 parser.add_option("-p", "--per-file", type="int", |
217557b26bc7
check-code: add a warnings level
Matt Mackall <mpm@selenic.com>
parents:
10814
diff
changeset
|
500 help="max warnings per file") |
11604
c5d40818b270
check-code: add --blame switch
Matt Mackall <mpm@selenic.com>
parents:
11602
diff
changeset
|
501 parser.add_option("-b", "--blame", action="store_true", |
c5d40818b270
check-code: add --blame switch
Matt Mackall <mpm@selenic.com>
parents:
11602
diff
changeset
|
502 help="use annotate to generate blame info") |
14135
673abd432104
check-code: adding debug flag
timeless <timeless@mozdev.org>
parents:
14009
diff
changeset
|
503 parser.add_option("", "--debug", action="store_true", |
673abd432104
check-code: adding debug flag
timeless <timeless@mozdev.org>
parents:
14009
diff
changeset
|
504 help="show debug information") |
15502
7917a104a285
check-code: add --nolineno option for hiding line numbers
Mads Kiilerich <mads@kiilerich.com>
parents:
15457
diff
changeset
|
505 parser.add_option("", "--nolineno", action="store_false", |
7917a104a285
check-code: add --nolineno option for hiding line numbers
Mads Kiilerich <mads@kiilerich.com>
parents:
15457
diff
changeset
|
506 dest='lineno', help="don't show line numbers") |
10895
217557b26bc7
check-code: add a warnings level
Matt Mackall <mpm@selenic.com>
parents:
10814
diff
changeset
|
507 |
15502
7917a104a285
check-code: add --nolineno option for hiding line numbers
Mads Kiilerich <mads@kiilerich.com>
parents:
15457
diff
changeset
|
508 parser.set_defaults(per_file=15, warnings=False, blame=False, debug=False, |
7917a104a285
check-code: add --nolineno option for hiding line numbers
Mads Kiilerich <mads@kiilerich.com>
parents:
15457
diff
changeset
|
509 lineno=True) |
10895
217557b26bc7
check-code: add a warnings level
Matt Mackall <mpm@selenic.com>
parents:
10814
diff
changeset
|
510 (options, args) = parser.parse_args() |
217557b26bc7
check-code: add a warnings level
Matt Mackall <mpm@selenic.com>
parents:
10814
diff
changeset
|
511 |
217557b26bc7
check-code: add a warnings level
Matt Mackall <mpm@selenic.com>
parents:
10814
diff
changeset
|
512 if len(args) == 0: |
10716
5f92bde72eef
check-code: Only call check-code if __name__ = "__main__".
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10707
diff
changeset
|
513 check = glob.glob("*") |
5f92bde72eef
check-code: Only call check-code if __name__ = "__main__".
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10707
diff
changeset
|
514 else: |
10895
217557b26bc7
check-code: add a warnings level
Matt Mackall <mpm@selenic.com>
parents:
10814
diff
changeset
|
515 check = args |
10281 | 516 |
15544
53ef627cda30
check-code: fix return code initialization
Mads Kiilerich <mads@kiilerich.com>
parents:
15502
diff
changeset
|
517 ret = 0 |
10716
5f92bde72eef
check-code: Only call check-code if __name__ = "__main__".
Pierre-Yves David <pierre-yves.david@logilab.fr>
parents:
10707
diff
changeset
|
518 for f in check: |
11816
e1359ad582f6
check-code: add exit status
Alecs King <alecsk@gmail.com>
parents:
11764
diff
changeset
|
519 if not checkfile(f, maxerr=options.per_file, warnings=options.warnings, |
15502
7917a104a285
check-code: add --nolineno option for hiding line numbers
Mads Kiilerich <mads@kiilerich.com>
parents:
15457
diff
changeset
|
520 blame=options.blame, debug=options.debug, |
7917a104a285
check-code: add --nolineno option for hiding line numbers
Mads Kiilerich <mads@kiilerich.com>
parents:
15457
diff
changeset
|
521 lineno=options.lineno): |
11816
e1359ad582f6
check-code: add exit status
Alecs King <alecsk@gmail.com>
parents:
11764
diff
changeset
|
522 ret = 1 |
e1359ad582f6
check-code: add exit status
Alecs King <alecsk@gmail.com>
parents:
11764
diff
changeset
|
523 sys.exit(ret) |