Commit 2c1a3666 authored by Yuya Nishihara's avatar Yuya Nishihara

scmutil: move walkchangerevs() from cmdutil

It's no longer a command-level function, but a pure helper to walk revisions
in a windowed way. This change will help eliminate reverse dependency of
revset.py -> grep.py -> cmdutil.py in future patches.
parent c10c87c8fe79
......@@ -23,6 +23,7 @@ from mercurial import (
patch,
pycompat,
registrar,
scmutil,
)
cmdtable = {}
......@@ -98,7 +99,7 @@ def countrate(ui, repo, amap, *pats, **opts):
exclude_pats=opts[b'exclude'],
)
revs, makefilematcher = logcmdutil.makewalker(repo, wopts)
for ctx in cmdutil.walkchangerevs(repo, revs, makefilematcher, prep):
for ctx in scmutil.walkchangerevs(repo, revs, makefilematcher, prep):
continue
progress.complete()
......
......@@ -2240,55 +2240,6 @@ def finddate(ui, repo, date):
return b'%d' % rev
def increasingwindows(windowsize=8, sizelimit=512):
while True:
yield windowsize
if windowsize < sizelimit:
windowsize *= 2
def walkchangerevs(repo, revs, makefilematcher, prepare):
'''Iterate over files and the revs in a "windowed" way.
Callers most commonly need to iterate backwards over the history
in which they are interested. Doing so has awful (quadratic-looking)
performance, so we use iterators in a "windowed" way.
We walk a window of revisions in the desired order. Within the
window, we first walk forwards to gather data, then in the desired
order (usually backwards) to display it.
This function returns an iterator yielding contexts. Before
yielding each context, the iterator will first call the prepare
function on each context in the window in forward order.'''
if not revs:
return []
change = repo.__getitem__
def iterate():
it = iter(revs)
stopiteration = False
for windowsize in increasingwindows():
nrevs = []
for i in pycompat.xrange(windowsize):
rev = next(it, None)
if rev is None:
stopiteration = True
break
nrevs.append(rev)
for rev in sorted(nrevs):
ctx = change(rev)
prepare(ctx, makefilematcher(ctx))
for rev in nrevs:
yield change(rev)
if stopiteration:
break
return iterate()
def add(ui, repo, match, prefix, uipathfn, explicitonly, **opts):
bad = []
......
......@@ -3532,7 +3532,7 @@ def grep(ui, repo, pattern, *pats, **opts):
ui.pager(b'grep')
fm = ui.formatter(b'grep', opts)
for ctx in cmdutil.walkchangerevs(
for ctx in scmutil.walkchangerevs(
repo, revs, makefilematcher, searcher._prep
):
rev = ctx.rev()
......
......@@ -760,6 +760,55 @@ def revrange(repo, specs, localalias=None):
return repo.anyrevs(allspecs, user=True, localalias=localalias)
def increasingwindows(windowsize=8, sizelimit=512):
while True:
yield windowsize
if windowsize < sizelimit:
windowsize *= 2
def walkchangerevs(repo, revs, makefilematcher, prepare):
'''Iterate over files and the revs in a "windowed" way.
Callers most commonly need to iterate backwards over the history
in which they are interested. Doing so has awful (quadratic-looking)
performance, so we use iterators in a "windowed" way.
We walk a window of revisions in the desired order. Within the
window, we first walk forwards to gather data, then in the desired
order (usually backwards) to display it.
This function returns an iterator yielding contexts. Before
yielding each context, the iterator will first call the prepare
function on each context in the window in forward order.'''
if not revs:
return []
change = repo.__getitem__
def iterate():
it = iter(revs)
stopiteration = False
for windowsize in increasingwindows():
nrevs = []
for i in pycompat.xrange(windowsize):
rev = next(it, None)
if rev is None:
stopiteration = True
break
nrevs.append(rev)
for rev in sorted(nrevs):
ctx = change(rev)
prepare(ctx, makefilematcher(ctx))
for rev in nrevs:
yield change(rev)
if stopiteration:
break
return iterate()
def meaningfulparents(repo, ctx):
"""Return list of meaningful (or all if debug) parentrevs for rev.
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment