hgext/closehead.py
author Augie Fackler <augie@google.com>
Fri, 06 Dec 2019 15:19:47 -0500
changeset 43813 5a9e2ae9899b
parent 43077 687b865b95ad
child 44452 9d2b2df2c2ba
permissions -rw-r--r--
fuzz: use a more standard approach to allow local builds of fuzzers This is taken from the (improved since we started fuzzing) guide on ideal integrations. Rather than have our own wonky targets for building outside the fuzzer universe, we have a driver program we carry along and use when we're not using LibFuzzer. This will let us jettison a fair amount of goo. contrib/fuzz/standalone_fuzz_target_runner.cc is https://github.com/google/oss-fuzz/ file projects/example/my-api-repo/standalone from git revision c4579d9358a73ea5dbcc99cb985de1f2bf76dcf7, reformatted with out clang-format settings and a no-check-code comment added. It allows running a single test input through a fuzzer, rather than performing ongoing fuzzing as libfuzzer would. contrib/fuzz/FuzzedDataProvider.h is https://github.com/llvm/llvm-project/ file /compiler-rt/include/fuzzer/FuzzedDataProvider.h from git revision a44ef027ebca1598892ea9b104d6189aeb3bc2f0, reformatted with our clang-format settings and a no-check-code comment added. We can discard this if we instead want to add an hghave check for a new enough llvm that includes FuzzedDataProvder.h in the fuzzer headers. Differential Revision: https://phab.mercurial-scm.org/D7564

# closehead.py - Close arbitrary heads without checking them out first
#
# This software may be used and distributed according to the terms of the
# GNU General Public License version 2 or any later version.

'''close arbitrary heads without checking them out first'''

from __future__ import absolute_import

from mercurial.i18n import _
from mercurial import (
    bookmarks,
    cmdutil,
    context,
    error,
    pycompat,
    registrar,
    scmutil,
)

cmdtable = {}
command = registrar.command(cmdtable)
# Note for extension authors: ONLY specify testedwith = 'ships-with-hg-core' for
# extensions which SHIP WITH MERCURIAL. Non-mainline extensions should
# be specifying the version(s) of Mercurial they are tested with, or
# leave the attribute unspecified.
testedwith = b'ships-with-hg-core'

commitopts = cmdutil.commitopts
commitopts2 = cmdutil.commitopts2
commitopts3 = [(b'r', b'rev', [], _(b'revision to check'), _(b'REV'))]


@command(
    b'close-head|close-heads',
    commitopts + commitopts2 + commitopts3,
    _(b'[OPTION]... [REV]...'),
    helpcategory=command.CATEGORY_CHANGE_MANAGEMENT,
    inferrepo=True,
)
def close_branch(ui, repo, *revs, **opts):
    """close the given head revisions

    This is equivalent to checking out each revision in a clean tree and running
    ``hg commit --close-branch``, except that it doesn't change the working
    directory.

    The commit message must be specified with -l or -m.
    """

    def docommit(rev):
        cctx = context.memctx(
            repo,
            parents=[rev, None],
            text=message,
            files=[],
            filectxfn=None,
            user=opts.get(b'user'),
            date=opts.get(b'date'),
            extra=extra,
        )
        tr = repo.transaction(b'commit')
        ret = repo.commitctx(cctx, True)
        bookmarks.update(repo, [rev, None], ret)
        cctx.markcommitted(ret)
        tr.close()

    opts = pycompat.byteskwargs(opts)

    revs += tuple(opts.get(b'rev', []))
    revs = scmutil.revrange(repo, revs)

    if not revs:
        raise error.Abort(_(b'no revisions specified'))

    heads = []
    for branch in repo.branchmap():
        heads.extend(repo.branchheads(branch))
    heads = set(repo[h].rev() for h in heads)
    for rev in revs:
        if rev not in heads:
            raise error.Abort(_(b'revision is not an open head: %d') % rev)

    message = cmdutil.logmessage(ui, opts)
    if not message:
        raise error.Abort(_(b"no commit message specified with -l or -m"))
    extra = {b'close': b'1'}

    with repo.wlock(), repo.lock():
        for rev in revs:
            r = repo[rev]
            branch = r.branch()
            extra[b'branch'] = branch
            docommit(r)
    return 0