Mercurial > public > mercurial-scm > hg-stable
comparison mercurial/utils/storageutil.py @ 40005:fa3dc85a747e
storageutil: extract functionality for resolving strip revisions
I found myself having to copy this method as part of implementing a new
storage backend. With a little tweaking, we can extract it to a
standalone function so it can be reused easily.
We'll likely want to implement a better method for removing revisions
on the storage interface someday. But until then, let's use what we
have.
Differential Revision: https://phab.mercurial-scm.org/D4799
author | Gregory Szorc <gregory.szorc@gmail.com> |
---|---|
date | Fri, 28 Sep 2018 11:29:05 -0700 |
parents | ad8389ecd3f5 |
children | 1d97a332c6d9 |
comparison
equal
deleted
inserted
replaced
40004:ad8389ecd3f5 | 40005:fa3dc85a747e |
---|---|
12 | 12 |
13 from ..i18n import _ | 13 from ..i18n import _ |
14 from ..node import ( | 14 from ..node import ( |
15 bin, | 15 bin, |
16 nullid, | 16 nullid, |
17 nullrev, | |
17 ) | 18 ) |
18 from .. import ( | 19 from .. import ( |
19 error, | 20 error, |
20 pycompat, | 21 pycompat, |
21 ) | 22 ) |
153 pass | 154 pass |
154 except (ValueError, OverflowError): | 155 except (ValueError, OverflowError): |
155 pass | 156 pass |
156 | 157 |
157 raise error.LookupError(fileid, identifier, _('no match found')) | 158 raise error.LookupError(fileid, identifier, _('no match found')) |
159 | |
160 def resolvestripinfo(minlinkrev, tiprev, headrevs, linkrevfn, parentrevsfn): | |
161 """Resolve information needed to strip revisions. | |
162 | |
163 Finds the minimum revision number that must be stripped in order to | |
164 strip ``minlinkrev``. | |
165 | |
166 Returns a 2-tuple of the minimum revision number to do that and a set | |
167 of all revision numbers that have linkrevs that would be broken | |
168 by that strip. | |
169 | |
170 ``tiprev`` is the current tip-most revision. It is ``len(store) - 1``. | |
171 ``headrevs`` is an iterable of head revisions. | |
172 ``linkrevfn`` is a callable that receives a revision and returns a linked | |
173 revision. | |
174 ``parentrevsfn`` is a callable that receives a revision number and returns | |
175 an iterable of its parent revision numbers. | |
176 """ | |
177 brokenrevs = set() | |
178 strippoint = tiprev + 1 | |
179 | |
180 heads = {} | |
181 futurelargelinkrevs = set() | |
182 for head in headrevs: | |
183 headlinkrev = linkrevfn(head) | |
184 heads[head] = headlinkrev | |
185 if headlinkrev >= minlinkrev: | |
186 futurelargelinkrevs.add(headlinkrev) | |
187 | |
188 # This algorithm involves walking down the rev graph, starting at the | |
189 # heads. Since the revs are topologically sorted according to linkrev, | |
190 # once all head linkrevs are below the minlink, we know there are | |
191 # no more revs that could have a linkrev greater than minlink. | |
192 # So we can stop walking. | |
193 while futurelargelinkrevs: | |
194 strippoint -= 1 | |
195 linkrev = heads.pop(strippoint) | |
196 | |
197 if linkrev < minlinkrev: | |
198 brokenrevs.add(strippoint) | |
199 else: | |
200 futurelargelinkrevs.remove(linkrev) | |
201 | |
202 for p in parentrevsfn(strippoint): | |
203 if p != nullrev: | |
204 plinkrev = linkrevfn(p) | |
205 heads[p] = plinkrev | |
206 if plinkrev >= minlinkrev: | |
207 futurelargelinkrevs.add(plinkrev) | |
208 | |
209 return strippoint, brokenrevs |