annotate mercurial/ignore.py @ 17441:cb12d3ce5607 stable

subrepo: encode unicode path names (issue3610) Subversion 1.7 changes its XML output to include an explicit encoding tag: <?xml version="1.0" encoding="UTF-8"?> This triggers xml.dom.minidom to always return unicode strings, causing other parts of the code to explode. We unconditionally encode path names before handing them back, which works with both str (actually a no-op) and unicode values.
author Bryan O'Sullivan <bryano@fb.com>
date Tue, 04 Sep 2012 15:46:04 -0700
parents ee112eb69d2a
children b35e3364f94a
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
4609
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
1 # ignore.py - ignored file handling for mercurial
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
2 #
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
3 # Copyright 2007 Matt Mackall <mpm@selenic.com>
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
4 #
8225
46293a0c7e9f updated license to be explicit about GPL version 2
Martin Geisler <mg@lazybytes.net>
parents: 7622
diff changeset
5 # This software may be used and distributed according to the terms of the
10263
25e572394f5c Update license to GPLv2+
Matt Mackall <mpm@selenic.com>
parents: 9091
diff changeset
6 # GNU General Public License version 2 or any later version.
4609
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
7
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
8 from i18n import _
8566
744d6322b05b match: change all users of util.matcher to match.match
Matt Mackall <mpm@selenic.com>
parents: 8312
diff changeset
9 import util, match
8312
b87a50b7125c separate import lines from mercurial and general python modules
Simon Heimberg <simohe@besonet.ch>
parents: 8225
diff changeset
10 import re
5640
04c76f296ad6 ignore: fix up comment parsing
Matt Mackall <mpm@selenic.com>
parents: 5271
diff changeset
11
04c76f296ad6 ignore: fix up comment parsing
Matt Mackall <mpm@selenic.com>
parents: 5271
diff changeset
12 _commentre = None
4609
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
13
9091
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
14 def ignorepats(lines):
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
15 '''parse lines (iterable) of .hgignore text, returning a tuple of
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
16 (patterns, parse errors). These patterns should be given to compile()
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
17 to be validated and converted into a match function.'''
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
18 syntaxes = {'re': 'relre:', 'regexp': 'relre:', 'glob': 'relglob:'}
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
19 syntax = 'relre:'
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
20 patterns = []
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
21 warnings = []
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
22
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
23 for line in lines:
5640
04c76f296ad6 ignore: fix up comment parsing
Matt Mackall <mpm@selenic.com>
parents: 5271
diff changeset
24 if "#" in line:
04c76f296ad6 ignore: fix up comment parsing
Matt Mackall <mpm@selenic.com>
parents: 5271
diff changeset
25 global _commentre
04c76f296ad6 ignore: fix up comment parsing
Matt Mackall <mpm@selenic.com>
parents: 5271
diff changeset
26 if not _commentre:
04c76f296ad6 ignore: fix up comment parsing
Matt Mackall <mpm@selenic.com>
parents: 5271
diff changeset
27 _commentre = re.compile(r'((^|[^\\])(\\\\)*)#.*')
04c76f296ad6 ignore: fix up comment parsing
Matt Mackall <mpm@selenic.com>
parents: 5271
diff changeset
28 # remove comments prefixed by an even number of escapes
04c76f296ad6 ignore: fix up comment parsing
Matt Mackall <mpm@selenic.com>
parents: 5271
diff changeset
29 line = _commentre.sub(r'\1', line)
04c76f296ad6 ignore: fix up comment parsing
Matt Mackall <mpm@selenic.com>
parents: 5271
diff changeset
30 # fixup properly escaped comments that survived the above
04c76f296ad6 ignore: fix up comment parsing
Matt Mackall <mpm@selenic.com>
parents: 5271
diff changeset
31 line = line.replace("\\#", "#")
04c76f296ad6 ignore: fix up comment parsing
Matt Mackall <mpm@selenic.com>
parents: 5271
diff changeset
32 line = line.rstrip()
9091
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
33 if not line:
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
34 continue
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
35
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
36 if line.startswith('syntax:'):
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
37 s = line[7:].strip()
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
38 try:
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
39 syntax = syntaxes[s]
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
40 except KeyError:
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
41 warnings.append(_("ignoring invalid syntax '%s'") % s)
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
42 continue
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
43 pat = syntax + line
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
44 for s, rels in syntaxes.iteritems():
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
45 if line.startswith(rels):
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
46 pat = line
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
47 break
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
48 elif line.startswith(s+':'):
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
49 pat = rels + line[len(s)+1:]
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
50 break
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
51 patterns.append(pat)
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
52
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
53 return patterns, warnings
4609
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
54
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
55 def ignore(root, files, warn):
9091
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
56 '''return matcher covering patterns in 'files'.
4609
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
57
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
58 the files parsed for patterns include:
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
59 .hgignore in the repository root
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
60 any additional files specified in the [ui] section of ~/.hgrc
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
61
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
62 trailing white space is dropped.
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
63 the escape character is backslash.
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
64 comments start with #.
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
65 empty lines are skipped.
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
66
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
67 lines can be of the following formats:
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
68
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
69 syntax: regexp # defaults following lines to non-rooted regexps
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
70 syntax: glob # defaults following lines to non-rooted globs
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
71 re:pattern # non-rooted regular expression
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
72 glob:pattern # non-rooted glob
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
73 pattern # pattern of the current default type'''
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
74
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
75 pats = {}
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
76 for f in files:
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
77 try:
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
78 pats[f] = []
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
79 fp = open(f)
9091
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
80 pats[f], warnings = ignorepats(fp)
15407
ee112eb69d2a misc: adding missing file close() calls
Matt Mackall <mpm@selenic.com>
parents: 13412
diff changeset
81 fp.close()
9091
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
82 for warning in warnings:
79a886bcf461 ignore: separate pattern extraction from match compilation
Brendan Cully <brendan@kublai.com>
parents: 8567
diff changeset
83 warn("%s: %s\n" % (f, warning))
4609
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
84 except IOError, inst:
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
85 if f != files[0]:
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
86 warn(_("skipping unreadable ignore file '%s': %s\n") %
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
87 (f, inst.strerror))
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
88
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
89 allpats = []
13412
58c497d0e44d remove unnecessary list comprehensions
Martin Geisler <mg@aragost.com>
parents: 10263
diff changeset
90 for patlist in pats.values():
58c497d0e44d remove unnecessary list comprehensions
Martin Geisler <mg@aragost.com>
parents: 10263
diff changeset
91 allpats.extend(patlist)
4609
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
92 if not allpats:
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
93 return util.never
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
94
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
95 try:
8567
fea40a677d43 match: add some default args
Matt Mackall <mpm@selenic.com>
parents: 8566
diff changeset
96 ignorefunc = match.match(root, '', [], allpats)
4609
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
97 except util.Abort:
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
98 # Re-raise an exception where the src is the right file
7622
4dd7b28003d2 use dict.iteritems() rather than dict.items()
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 5640
diff changeset
99 for f, patlist in pats.iteritems():
8566
744d6322b05b match: change all users of util.matcher to match.match
Matt Mackall <mpm@selenic.com>
parents: 8312
diff changeset
100 try:
8567
fea40a677d43 match: add some default args
Matt Mackall <mpm@selenic.com>
parents: 8566
diff changeset
101 match.match(root, '', [], patlist)
8566
744d6322b05b match: change all users of util.matcher to match.match
Matt Mackall <mpm@selenic.com>
parents: 8312
diff changeset
102 except util.Abort, inst:
744d6322b05b match: change all users of util.matcher to match.match
Matt Mackall <mpm@selenic.com>
parents: 8312
diff changeset
103 raise util.Abort('%s: %s' % (f, inst[0]))
4609
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
104
b43f17691ae6 dirstate: move ignore to its own file
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
105 return ignorefunc