Mercurial > hg > mercurial-crew
annotate mercurial/tags.py @ 9366:9ff178e7b627
tags: don't crash if unable to write tag cache
This happens with hgweb in real life, if the httpd user is unable to
write in the repository directory. Another case is doing 'hg incoming'
on a repository in the filesystem owned by someone else.
author | Greg Ward <greg-hg@gerg.ca> |
---|---|
date | Tue, 18 Aug 2009 22:07:43 -0400 |
parents | c5f0825c1dbb |
children | e2b1de5fee04 |
rev | line source |
---|---|
9157
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
1 # tags.py - read tag info from local repository |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
2 # |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
3 # Copyright 2009 Matt Mackall <mpm@selenic.com> |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
4 # Copyright 2009 Greg Ward <greg@gerg.ca> |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
5 # |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
6 # This software may be used and distributed according to the terms of the |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
7 # GNU General Public License version 2, incorporated herein by reference. |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
8 |
9159
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
9 # Currently this module only deals with reading and caching tags. |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
10 # Eventually, it could take care of updating (adding/removing/moving) |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
11 # tags too. |
9157
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
12 |
9159
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
13 import os |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
14 from node import nullid, bin, hex, short |
9157
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
15 from i18n import _ |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
16 import encoding |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
17 import error |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
18 |
9159
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
19 def _debugalways(ui, *msg): |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
20 ui.write(*msg) |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
21 |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
22 def _debugconditional(ui, *msg): |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
23 ui.debug(*msg) |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
24 |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
25 def _debugnever(ui, *msg): |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
26 pass |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
27 |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
28 _debug = _debugalways |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
29 _debug = _debugnever |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
30 |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
31 def findglobaltags1(ui, repo, alltags, tagtypes): |
9157
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
32 '''Find global tags in repo by reading .hgtags from every head that |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
33 has a distinct version of it. Updates the dicts alltags, tagtypes |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
34 in place: alltags maps tag name to (node, hist) pair (see _readtags() |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
35 below), and tagtypes maps tag name to tag type ('global' in this |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
36 case).''' |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
37 |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
38 seen = set() |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
39 fctx = None |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
40 ctxs = [] # list of filectx |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
41 for node in repo.heads(): |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
42 try: |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
43 fnode = repo[node].filenode('.hgtags') |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
44 except error.LookupError: |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
45 continue |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
46 if fnode not in seen: |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
47 seen.add(fnode) |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
48 if not fctx: |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
49 fctx = repo.filectx('.hgtags', fileid=fnode) |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
50 else: |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
51 fctx = fctx.filectx(fnode) |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
52 ctxs.append(fctx) |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
53 |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
54 # read the tags file from each head, ending with the tip |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
55 for fctx in reversed(ctxs): |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
56 filetags = _readtags( |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
57 ui, repo, fctx.data().splitlines(), fctx) |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
58 _updatetags(filetags, "global", alltags, tagtypes) |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
59 |
9159
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
60 def findglobaltags2(ui, repo, alltags, tagtypes): |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
61 '''Same as findglobaltags1(), but with caching.''' |
9160
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
62 # This is so we can be lazy and assume alltags contains only global |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
63 # tags when we pass it to _writetagcache(). |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
64 assert len(alltags) == len(tagtypes) == 0, \ |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
65 "findglobaltags() should be called first" |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
66 |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
67 (heads, tagfnode, cachetags, shouldwrite) = _readtagcache(ui, repo) |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
68 if cachetags is not None: |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
69 assert not shouldwrite |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
70 # XXX is this really 100% correct? are there oddball special |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
71 # cases where a global tag should outrank a local tag but won't, |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
72 # because cachetags does not contain rank info? |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
73 _updatetags(cachetags, 'global', alltags, tagtypes) |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
74 return |
9159
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
75 |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
76 _debug(ui, "reading tags from %d head(s): %s\n" |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
77 % (len(heads), map(short, reversed(heads)))) |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
78 seen = set() # set of fnode |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
79 fctx = None |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
80 for head in reversed(heads): # oldest to newest |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
81 assert head in repo.changelog.nodemap, \ |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
82 "tag cache returned bogus head %s" % short(head) |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
83 |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
84 fnode = tagfnode.get(head) |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
85 if fnode and fnode not in seen: |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
86 seen.add(fnode) |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
87 if not fctx: |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
88 fctx = repo.filectx('.hgtags', fileid=fnode) |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
89 else: |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
90 fctx = fctx.filectx(fnode) |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
91 |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
92 filetags = _readtags(ui, repo, fctx.data().splitlines(), fctx) |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
93 _updatetags(filetags, 'global', alltags, tagtypes) |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
94 |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
95 # and update the cache (if necessary) |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
96 if shouldwrite: |
9160
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
97 _writetagcache(ui, repo, heads, tagfnode, alltags) |
9159
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
98 |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
99 # Set this to findglobaltags1 to disable tag caching. |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
100 findglobaltags = findglobaltags2 |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
101 |
9157
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
102 def readlocaltags(ui, repo, alltags, tagtypes): |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
103 '''Read local tags in repo. Update alltags and tagtypes.''' |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
104 try: |
9160
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
105 # localtags is in the local encoding; re-encode to UTF-8 on |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
106 # input for consistency with the rest of this module. |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
107 data = repo.opener("localtags").read() |
9157
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
108 filetags = _readtags( |
9160
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
109 ui, repo, data.splitlines(), "localtags", |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
110 recode=encoding.fromlocal) |
9157
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
111 _updatetags(filetags, "local", alltags, tagtypes) |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
112 except IOError: |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
113 pass |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
114 |
9160
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
115 def _readtags(ui, repo, lines, fn, recode=None): |
9157
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
116 '''Read tag definitions from a file (or any source of lines). |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
117 Return a mapping from tag name to (node, hist): node is the node id |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
118 from the last line read for that name, and hist is the list of node |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
119 ids previously associated with it (in file order). All node ids are |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
120 binary, not hex.''' |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
121 |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
122 filetags = {} # map tag name to (node, hist) |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
123 count = 0 |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
124 |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
125 def warn(msg): |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
126 ui.warn(_("%s, line %s: %s\n") % (fn, count, msg)) |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
127 |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
128 for line in lines: |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
129 count += 1 |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
130 if not line: |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
131 continue |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
132 try: |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
133 (nodehex, name) = line.split(" ", 1) |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
134 except ValueError: |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
135 warn(_("cannot parse entry")) |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
136 continue |
9160
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
137 name = name.strip() |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
138 if recode: |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
139 name = recode(name) |
9157
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
140 try: |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
141 nodebin = bin(nodehex) |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
142 except TypeError: |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
143 warn(_("node '%s' is not well formed") % nodehex) |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
144 continue |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
145 if nodebin not in repo.changelog.nodemap: |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
146 # silently ignore as pull -r might cause this |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
147 continue |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
148 |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
149 # update filetags |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
150 hist = [] |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
151 if name in filetags: |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
152 n, hist = filetags[name] |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
153 hist.append(n) |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
154 filetags[name] = (nodebin, hist) |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
155 return filetags |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
156 |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
157 def _updatetags(filetags, tagtype, alltags, tagtypes): |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
158 '''Incorporate the tag info read from one file into the two |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
159 dictionaries, alltags and tagtypes, that contain all tag |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
160 info (global across all heads plus local).''' |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
161 |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
162 for name, nodehist in filetags.iteritems(): |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
163 if name not in alltags: |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
164 alltags[name] = nodehist |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
165 tagtypes[name] = tagtype |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
166 continue |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
167 |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
168 # we prefer alltags[name] if: |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
169 # it supercedes us OR |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
170 # mutual supercedes and it has a higher rank |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
171 # otherwise we win because we're tip-most |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
172 anode, ahist = nodehist |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
173 bnode, bhist = alltags[name] |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
174 if (bnode != anode and anode in bhist and |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
175 (bnode not in ahist or len(bhist) > len(ahist))): |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
176 anode = bnode |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
177 ahist.extend([n for n in bhist if n not in ahist]) |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
178 alltags[name] = anode, ahist |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
179 tagtypes[name] = tagtype |
abb7d4d43a5f
Factor tags module out of localrepo (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
diff
changeset
|
180 |
9159
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
181 |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
182 # The tag cache only stores info about heads, not the tag contents |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
183 # from each head. I.e. it doesn't try to squeeze out the maximum |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
184 # performance, but is simpler has a better chance of actually |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
185 # working correctly. And this gives the biggest performance win: it |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
186 # avoids looking up .hgtags in the manifest for every head, and it |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
187 # can avoid calling heads() at all if there have been no changes to |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
188 # the repo. |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
189 |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
190 def _readtagcache(ui, repo): |
9160
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
191 '''Read the tag cache and return a tuple (heads, fnodes, cachetags, |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
192 shouldwrite). If the cache is completely up-to-date, cachetags is a |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
193 dict of the form returned by _readtags(); otherwise, it is None and |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
194 heads and fnodes are set. In that case, heads is the list of all |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
195 heads currently in the repository (ordered from tip to oldest) and |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
196 fnodes is a mapping from head to .hgtags filenode. If those two are |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
197 set, caller is responsible for reading tag info from each head.''' |
9159
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
198 |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
199 try: |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
200 cachefile = repo.opener('tags.cache', 'r') |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
201 _debug(ui, 'reading tag cache from %s\n' % cachefile.name) |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
202 except IOError: |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
203 cachefile = None |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
204 |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
205 # The cache file consists of lines like |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
206 # <headrev> <headnode> [<tagnode>] |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
207 # where <headrev> and <headnode> redundantly identify a repository |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
208 # head from the time the cache was written, and <tagnode> is the |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
209 # filenode of .hgtags on that head. Heads with no .hgtags file will |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
210 # have no <tagnode>. The cache is ordered from tip to oldest (which |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
211 # is part of why <headrev> is there: a quick visual check is all |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
212 # that's required to ensure correct order). |
9312
c5f0825c1dbb
kill trailing whitespace
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents:
9160
diff
changeset
|
213 # |
9159
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
214 # This information is enough to let us avoid the most expensive part |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
215 # of finding global tags, which is looking up <tagnode> in the |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
216 # manifest for each head. |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
217 cacherevs = [] # list of headrev |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
218 cacheheads = [] # list of headnode |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
219 cachefnode = {} # map headnode to filenode |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
220 if cachefile: |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
221 for line in cachefile: |
9160
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
222 if line == "\n": |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
223 break |
9159
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
224 line = line.rstrip().split() |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
225 cacherevs.append(int(line[0])) |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
226 headnode = bin(line[1]) |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
227 cacheheads.append(headnode) |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
228 if len(line) == 3: |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
229 fnode = bin(line[2]) |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
230 cachefnode[headnode] = fnode |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
231 |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
232 tipnode = repo.changelog.tip() |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
233 tiprev = len(repo.changelog) - 1 |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
234 |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
235 # Case 1 (common): tip is the same, so nothing has changed. |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
236 # (Unchanged tip trivially means no changesets have been added. |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
237 # But, thanks to localrepository.destroyed(), it also means none |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
238 # have been destroyed by strip or rollback.) |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
239 if cacheheads and cacheheads[0] == tipnode and cacherevs[0] == tiprev: |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
240 _debug(ui, "tag cache: tip unchanged\n") |
9160
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
241 tags = _readtags(ui, repo, cachefile, cachefile.name) |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
242 cachefile.close() |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
243 return (None, None, tags, False) |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
244 if cachefile: |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
245 cachefile.close() # ignore rest of file |
9312
c5f0825c1dbb
kill trailing whitespace
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents:
9160
diff
changeset
|
246 |
9159
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
247 repoheads = repo.heads() |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
248 # Case 2 (uncommon): empty repo; get out quickly and don't bother |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
249 # writing an empty cache. |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
250 if repoheads == [nullid]: |
9160
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
251 return ([], {}, {}, False) |
9159
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
252 |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
253 # Case 3 (uncommon): cache file missing or empty. |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
254 if not cacheheads: |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
255 _debug(ui, 'tag cache: cache file missing or empty\n') |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
256 |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
257 # Case 4 (uncommon): tip rev decreased. This should only happen |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
258 # when we're called from localrepository.destroyed(). Refresh the |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
259 # cache so future invocations will not see disappeared heads in the |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
260 # cache. |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
261 elif cacheheads and tiprev < cacherevs[0]: |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
262 _debug(ui, |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
263 'tag cache: tip rev decremented (from %d to %d), ' |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
264 'so we must be destroying nodes\n' |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
265 % (cacherevs[0], tiprev)) |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
266 |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
267 # Case 5 (common): tip has changed, so we've added/replaced heads. |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
268 else: |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
269 _debug(ui, |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
270 'tag cache: tip has changed (%d:%s); must find new heads\n' |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
271 % (tiprev, short(tipnode))) |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
272 |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
273 # Luckily, the code to handle cases 3, 4, 5 is the same. So the |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
274 # above if/elif/else can disappear once we're confident this thing |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
275 # actually works and we don't need the debug output. |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
276 |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
277 # N.B. in case 4 (nodes destroyed), "new head" really means "newly |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
278 # exposed". |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
279 newheads = [head |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
280 for head in repoheads |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
281 if head not in set(cacheheads)] |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
282 _debug(ui, 'tag cache: found %d head(s) not in cache: %s\n' |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
283 % (len(newheads), map(short, newheads))) |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
284 |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
285 # Now we have to lookup the .hgtags filenode for every new head. |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
286 # This is the most expensive part of finding tags, so performance |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
287 # depends primarily on the size of newheads. Worst case: no cache |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
288 # file, so newheads == repoheads. |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
289 for head in newheads: |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
290 cctx = repo[head] |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
291 try: |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
292 fnode = cctx.filenode('.hgtags') |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
293 cachefnode[head] = fnode |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
294 except error.LookupError: |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
295 # no .hgtags file on this head |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
296 pass |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
297 |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
298 # Caller has to iterate over all heads, but can use the filenodes in |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
299 # cachefnode to get to each .hgtags revision quickly. |
9160
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
300 return (repoheads, cachefnode, None, True) |
9159
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
301 |
9160
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
302 def _writetagcache(ui, repo, heads, tagfnode, cachetags): |
9159
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
303 |
9366
9ff178e7b627
tags: don't crash if unable to write tag cache
Greg Ward <greg-hg@gerg.ca>
parents:
9312
diff
changeset
|
304 try: |
9ff178e7b627
tags: don't crash if unable to write tag cache
Greg Ward <greg-hg@gerg.ca>
parents:
9312
diff
changeset
|
305 cachefile = repo.opener('tags.cache', 'w', atomictemp=True) |
9ff178e7b627
tags: don't crash if unable to write tag cache
Greg Ward <greg-hg@gerg.ca>
parents:
9312
diff
changeset
|
306 except (OSError, IOError): |
9ff178e7b627
tags: don't crash if unable to write tag cache
Greg Ward <greg-hg@gerg.ca>
parents:
9312
diff
changeset
|
307 return |
9159
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
308 _debug(ui, 'writing cache file %s\n' % cachefile.name) |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
309 |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
310 realheads = repo.heads() # for sanity checks below |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
311 for head in heads: |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
312 # temporary sanity checks; these can probably be removed |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
313 # once this code has been in crew for a few weeks |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
314 assert head in repo.changelog.nodemap, \ |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
315 'trying to write non-existent node %s to tag cache' % short(head) |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
316 assert head in realheads, \ |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
317 'trying to write non-head %s to tag cache' % short(head) |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
318 assert head != nullid, \ |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
319 'trying to write nullid to tag cache' |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
320 |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
321 # This can't fail because of the first assert above. When/if we |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
322 # remove that assert, we might want to catch LookupError here |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
323 # and downgrade it to a warning. |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
324 rev = repo.changelog.rev(head) |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
325 |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
326 fnode = tagfnode.get(head) |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
327 if fnode: |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
328 cachefile.write('%d %s %s\n' % (rev, hex(head), hex(fnode))) |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
329 else: |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
330 cachefile.write('%d %s\n' % (rev, hex(head))) |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
331 |
9160
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
332 # Tag names in the cache are in UTF-8 -- which is the whole reason |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
333 # we keep them in UTF-8 throughout this module. If we converted |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
334 # them local encoding on input, we would lose info writing them to |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
335 # the cache. |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
336 cachefile.write('\n') |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
337 for (name, (node, hist)) in cachetags.iteritems(): |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
338 cachefile.write("%s %s\n" % (hex(node), name)) |
4017291c4c48
tags: support 'instant' tag retrieval (issue548)
Greg Ward <greg-hg@gerg.ca>
parents:
9159
diff
changeset
|
339 |
9159
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
340 cachefile.rename() |
f528d1a93491
tags: implement persistent tag caching (issue548).
Greg Ward <greg-hg@gerg.ca>
parents:
9157
diff
changeset
|
341 cachefile.close() |