Mercurial > public > mercurial-scm > hg-stable
comparison mercurial/context.py @ 32922:582080a4a812
dagop: move blockancestors() and blockdescendants() from context
context.py seems not a good place to host these functions.
% wc -l mercurial/context.py mercurial/dagop.py
2306 mercurial/context.py
424 mercurial/dagop.py
2730 total
author | Yuya Nishihara <yuya@tcha.org> |
---|---|
date | Sun, 19 Feb 2017 19:37:14 +0900 |
parents | 2083d1643d69 |
children | daccadd75760 |
comparison
equal
deleted
inserted
replaced
32921:27932a76a88d | 32922:582080a4a812 |
---|---|
1270 # hard for renames | 1270 # hard for renames |
1271 c = self._filelog.children(self._filenode) | 1271 c = self._filelog.children(self._filenode) |
1272 return [filectx(self._repo, self._path, fileid=x, | 1272 return [filectx(self._repo, self._path, fileid=x, |
1273 filelog=self._filelog) for x in c] | 1273 filelog=self._filelog) for x in c] |
1274 | 1274 |
1275 def _changesrange(fctx1, fctx2, linerange2, diffopts): | |
1276 """Return `(diffinrange, linerange1)` where `diffinrange` is True | |
1277 if diff from fctx2 to fctx1 has changes in linerange2 and | |
1278 `linerange1` is the new line range for fctx1. | |
1279 """ | |
1280 blocks = mdiff.allblocks(fctx1.data(), fctx2.data(), diffopts) | |
1281 filteredblocks, linerange1 = mdiff.blocksinrange(blocks, linerange2) | |
1282 diffinrange = any(stype == '!' for _, stype in filteredblocks) | |
1283 return diffinrange, linerange1 | |
1284 | |
1285 def blockancestors(fctx, fromline, toline, followfirst=False): | |
1286 """Yield ancestors of `fctx` with respect to the block of lines within | |
1287 `fromline`-`toline` range. | |
1288 """ | |
1289 diffopts = patch.diffopts(fctx._repo.ui) | |
1290 introrev = fctx.introrev() | |
1291 if fctx.rev() != introrev: | |
1292 fctx = fctx.filectx(fctx.filenode(), changeid=introrev) | |
1293 visit = {(fctx.linkrev(), fctx.filenode()): (fctx, (fromline, toline))} | |
1294 while visit: | |
1295 c, linerange2 = visit.pop(max(visit)) | |
1296 pl = c.parents() | |
1297 if followfirst: | |
1298 pl = pl[:1] | |
1299 if not pl: | |
1300 # The block originates from the initial revision. | |
1301 yield c, linerange2 | |
1302 continue | |
1303 inrange = False | |
1304 for p in pl: | |
1305 inrangep, linerange1 = _changesrange(p, c, linerange2, diffopts) | |
1306 inrange = inrange or inrangep | |
1307 if linerange1[0] == linerange1[1]: | |
1308 # Parent's linerange is empty, meaning that the block got | |
1309 # introduced in this revision; no need to go futher in this | |
1310 # branch. | |
1311 continue | |
1312 # Set _descendantrev with 'c' (a known descendant) so that, when | |
1313 # _adjustlinkrev is called for 'p', it receives this descendant | |
1314 # (as srcrev) instead possibly topmost introrev. | |
1315 p._descendantrev = c.rev() | |
1316 visit[p.linkrev(), p.filenode()] = p, linerange1 | |
1317 if inrange: | |
1318 yield c, linerange2 | |
1319 | |
1320 def blockdescendants(fctx, fromline, toline): | |
1321 """Yield descendants of `fctx` with respect to the block of lines within | |
1322 `fromline`-`toline` range. | |
1323 """ | |
1324 # First possibly yield 'fctx' if it has changes in range with respect to | |
1325 # its parents. | |
1326 try: | |
1327 c, linerange1 = next(blockancestors(fctx, fromline, toline)) | |
1328 except StopIteration: | |
1329 pass | |
1330 else: | |
1331 if c == fctx: | |
1332 yield c, linerange1 | |
1333 | |
1334 diffopts = patch.diffopts(fctx._repo.ui) | |
1335 fl = fctx.filelog() | |
1336 seen = {fctx.filerev(): (fctx, (fromline, toline))} | |
1337 for i in fl.descendants([fctx.filerev()]): | |
1338 c = fctx.filectx(i) | |
1339 inrange = False | |
1340 for x in fl.parentrevs(i): | |
1341 try: | |
1342 p, linerange2 = seen[x] | |
1343 except KeyError: | |
1344 # nullrev or other branch | |
1345 continue | |
1346 inrangep, linerange1 = _changesrange(c, p, linerange2, diffopts) | |
1347 inrange = inrange or inrangep | |
1348 # If revision 'i' has been seen (it's a merge), we assume that its | |
1349 # line range is the same independently of which parents was used | |
1350 # to compute it. | |
1351 assert i not in seen or seen[i][1] == linerange1, ( | |
1352 'computed line range for %s is not consistent between ' | |
1353 'ancestor branches' % c) | |
1354 seen[i] = c, linerange1 | |
1355 if inrange: | |
1356 yield c, linerange1 | |
1357 | |
1358 class committablectx(basectx): | 1275 class committablectx(basectx): |
1359 """A committablectx object provides common functionality for a context that | 1276 """A committablectx object provides common functionality for a context that |
1360 wants the ability to commit, e.g. workingctx or memctx.""" | 1277 wants the ability to commit, e.g. workingctx or memctx.""" |
1361 def __init__(self, repo, text="", user=None, date=None, extra=None, | 1278 def __init__(self, repo, text="", user=None, date=None, extra=None, |
1362 changes=None): | 1279 changes=None): |