# HG changeset patch # User Pierre-Yves David # Date 1316032159 -7200 # Node ID 5cec25ce019cb1a4c0bb59b559372c5f293611b6 # Parent 5d029a35825239647d4e57b82d808fb4fa2ceec6 Basic kill command diff -r 5d029a358252 -r 5cec25ce019c hgext/evolution.py --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/hgext/evolution.py Wed Sep 14 22:29:19 2011 +0200 @@ -0,0 +1,70 @@ +# states.py - introduce the state concept for mercurial changeset +# +# Copyright 2011 Peter Arrenbrecht +# Logilab SA +# Pierre-Yves David +# +# This software may be used and distributed according to the terms of the +# GNU General Public License version 2 or any later version. + +'''A set of command to make changeset evolve.''' + +from mercurial import cmdutil +from mercurial import scmutil +from mercurial import node +from mercurial import error +from mercurial import extensions +from mercurial import commands +from mercurial.i18n import _ + +### util function +############################# +def noderange(repo, revsets): + """The same as revrange but return node""" + return map(repo.changelog.node, + scmutil.revrange(repo, revsets)) + +### extension check +############################# + +def extsetup(ui): + try: + rebase = extensions.find('obsolete') + except KeyError: + raise error.Abort(_('evolution extension require obsolete extension.')) + +### new command +############################# +cmdtable = {} +command = cmdutil.command(cmdtable) + +@command('^kill', + [], + '') +def kill(ui, repo, *revs): + """mark a changeset as obsolete + + This update the parent directory to a not-killed parent if the current + working directory parent are killed. + + XXX bookmark support + XXX handle merge + XXX check immutable first + """ + wlock = repo.wlock() + try: + targetnodes = set(noderange(repo, revs)) + for n in targetnodes: + repo.addobsolete(node.nullid, n) + # update to an unkilled parent + wdp = repo['.'] + newnode = wdp + while newnode.obsolete(): + newnode = newnode.parents()[0] + if newnode.node() != wdp.node(): + commands.update(ui, repo, newnode.rev()) + ui.status(_('working directory now at %s\n') % newnode) + + finally: + wlock.release() + diff -r 5d029a358252 -r 5cec25ce019c tests/test-evolution.t --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/tests/test-evolution.t Wed Sep 14 22:29:19 2011 +0200 @@ -0,0 +1,61 @@ + $ cat >> $HGRCPATH < [web] + > push_ssl = false + > allow_push = * + > [alias] + > qlog = log --template='{rev} - {node|short} {desc} ({state})\n' + > [extensions] + > EOF + $ echo "states=$(echo $(dirname $TESTDIR))/hgext/states.py" >> $HGRCPATH + $ echo "obsolete=$(echo $(dirname $TESTDIR))/hgext/obsolete.py" >> $HGRCPATH + $ echo "evolution=$(echo $(dirname $TESTDIR))/hgext/evolution.py" >> $HGRCPATH + $ mkcommit() { + > echo "$1" > "$1" + > hg add "$1" + > hg ci -m "add $1" + > } + +various init + + $ hg init local + $ cd local + $ hg states ready # XXX should be put in default config when state support it + $ mkcommit a + $ mkcommit b + $ mkcommit c + $ mkcommit d + $ hg up 1 + 0 files updated, 0 files merged, 2 files removed, 0 files unresolved + $ mkcommit e -q + created new head + $ mkcommit f + $ hg published 1 + $ hg qlog + 5 - e44648563c73 add f (ready) + 4 - fbb94e3a0ecf add e (ready) + 3 - 47d2a3944de8 add d (ready) + 2 - 4538525df7e2 add c (ready) + 1 - 7c3bad9141dc add b (published) + 0 - 1f0dee641bb7 add a (published) + +test simple kill + + $ hg kill 5 + 0 files updated, 0 files merged, 1 files removed, 0 files unresolved + working directory now at fbb94e3a0ecf + $ hg qlog + 4 - fbb94e3a0ecf add e (ready) + 3 - 47d2a3944de8 add d (ready) + 2 - 4538525df7e2 add c (ready) + 1 - 7c3bad9141dc add b (published) + 0 - 1f0dee641bb7 add a (published) + +test multiple kill + + $ hg kill 4 3 + 0 files updated, 0 files merged, 1 files removed, 0 files unresolved + working directory now at 7c3bad9141dc + $ hg qlog + 2 - 4538525df7e2 add c (ready) + 1 - 7c3bad9141dc add b (published) + 0 - 1f0dee641bb7 add a (published)