feat(gerrithook): implement a crap gerrit mercurial extension
Change-Id: Iae1fc9fb5efe046fe70b229e7b5cedc3c8f15749
This commit is contained in:
parent
7f7f45ea88
commit
0a0020e449
1 changed files with 63 additions and 0 deletions
63
users/lukegb/hgext/gerrithook.py
Normal file
63
users/lukegb/hgext/gerrithook.py
Normal file
|
@ -0,0 +1,63 @@
|
||||||
|
"""Bizarre hacks to make Gerrit better."""
|
||||||
|
|
||||||
|
import collections
|
||||||
|
import re
|
||||||
|
import random
|
||||||
|
import mercurial
|
||||||
|
|
||||||
|
_ = mercurial.i18n._
|
||||||
|
|
||||||
|
cmdtable = {}
|
||||||
|
command = mercurial.registrar.command(cmdtable)
|
||||||
|
|
||||||
|
testedwith = '5.3.1'
|
||||||
|
|
||||||
|
_changeid_regex = re.compile(b'^Change-Id: (I.*)$', re.M)
|
||||||
|
|
||||||
|
def random_hash():
|
||||||
|
"""Returns a random SHA1-like hex string."""
|
||||||
|
return b"%040x" % random.getrandbits(160)
|
||||||
|
|
||||||
|
def reposetup(ui, repo):
|
||||||
|
|
||||||
|
class GerritRepo(repo.__class__):
|
||||||
|
def commitctx(self, ctx, *args, **kwargs):
|
||||||
|
match = _changeid_regex.search(ctx._text)
|
||||||
|
if not match:
|
||||||
|
ctx._text = ctx._text.rstrip(b'\n')
|
||||||
|
ctx._text += b'\n\nChange-Id: I' + random_hash()
|
||||||
|
return super().commitctx(ctx, *args, **kwargs)
|
||||||
|
|
||||||
|
repo.__class__ = GerritRepo
|
||||||
|
|
||||||
|
|
||||||
|
@command(b'gerrit-obsolete', [], _(b'[options]'))
|
||||||
|
def gerritobsolete(ui, repo, **opts):
|
||||||
|
"""Mark draft commits as obsolete by public commits based on Gerrit Change-Id tag."""
|
||||||
|
if repo.obsstore.readonly:
|
||||||
|
ui.error(b'obsstore is readonly')
|
||||||
|
return
|
||||||
|
changesets = collections.defaultdict(set)
|
||||||
|
drafts = set()
|
||||||
|
for draft in repo.set('draft() - obsolete()'):
|
||||||
|
match = _changeid_regex.search(draft.description())
|
||||||
|
if not match:
|
||||||
|
continue
|
||||||
|
changesets[match.groups()[0]].add(draft)
|
||||||
|
drafts.add(draft)
|
||||||
|
if not drafts:
|
||||||
|
return
|
||||||
|
publicparent = next(repo.set(
|
||||||
|
b'ancestor((public() and bookmark("master")), %s)' % (
|
||||||
|
b', '.join(x.hex() for x in drafts))))
|
||||||
|
megare = b're:(?ms)^Change-Id: (%s)$' % (b'|'.join(changesets.keys()),)
|
||||||
|
markers = []
|
||||||
|
for public in repo.set('(%s..(public() and master)) and desc(%s)', publicparent, megare):
|
||||||
|
match = _changeid_regex.search(public.description())
|
||||||
|
if not match:
|
||||||
|
continue
|
||||||
|
drafts = changesets[match.groups()[0]]
|
||||||
|
if not drafts:
|
||||||
|
continue
|
||||||
|
markers.append((tuple(drafts), (public,)))
|
||||||
|
mercurial.obsolete.createmarkers(repo, markers, operation=b'gerrit-obsolete')
|
Loading…
Reference in a new issue