hgext3rd/evolve/cmdrewrite.py
author Pierre-Yves David <pierre-yves.david@octobus.net>
Fri, 31 Aug 2018 09:19:13 +0200
changeset 4051 ddae36b4031e
parent 4050 3dddb03f3559
child 4052 73e73471d6c6
permissions -rw-r--r--
pick: use "pick" as operation name in obsolescence markers
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
2772
394b836e475b commands: rewrite the 'evocommands' module to 'cmdrewrite'
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2771
diff changeset
     1
# Module dedicated to host history rewriting commands
2724
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
     2
#
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
     3
# Copyright 2017 Octobus <contact@octobus.net>
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
     4
#
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
     5
# This software may be used and distributed according to the terms of the
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
     6
# GNU General Public License version 2 or any later version.
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
     7
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
     8
# Status: Stabilization of the API in progress
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
     9
#
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    10
#   The final set of command should go into core.
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    11
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    12
from __future__ import absolute_import
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    13
3670
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
    14
import contextlib
2763
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
    15
import random
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
    16
2724
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    17
from mercurial import (
2762
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
    18
    bookmarks as bookmarksmod,
2724
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    19
    cmdutil,
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    20
    commands,
2725
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
    21
    context,
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
    22
    copies,
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
    23
    error,
2760
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
    24
    hg,
2725
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
    25
    lock as lockmod,
3453
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
    26
    merge,
2725
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
    27
    node,
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
    28
    obsolete,
3697
6aff4bb3970d compat: drop compatibility layer for successorssets
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3694
diff changeset
    29
    obsutil,
2941
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
    30
    patch,
2725
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
    31
    phases,
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
    32
    scmutil,
2724
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    33
    util,
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    34
)
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    35
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    36
from mercurial.i18n import _
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    37
3675
1dccccde82bb compat: access datestr in a way compatible with verison prior to 4.6
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3670
diff changeset
    38
try:
1dccccde82bb compat: access datestr in a way compatible with verison prior to 4.6
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3670
diff changeset
    39
    from mercurial.utils.dateutil import datestr
1dccccde82bb compat: access datestr in a way compatible with verison prior to 4.6
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3670
diff changeset
    40
except ImportError: # hg <= 4.5
1dccccde82bb compat: access datestr in a way compatible with verison prior to 4.6
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3670
diff changeset
    41
    from mercurial.util import datestr
3660
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
    42
2724
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    43
from . import (
2763
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
    44
    compat,
3457
82e9f9603b1b evolvestate: rename the file to state.py and class name to cmdstate
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3456
diff changeset
    45
    state,
2724
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    46
    exthelper,
2756
f4dd6e6d4c73 rewriteutil: create a rewriteutil module to host utility function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2752
diff changeset
    47
    rewriteutil,
2763
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
    48
    utility,
2724
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    49
)
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    50
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    51
eh = exthelper.exthelper()
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    52
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    53
walkopts = commands.walkopts
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    54
commitopts = commands.commitopts
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    55
commitopts2 = commands.commitopts2
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    56
mergetoolopts = commands.mergetoolopts
2941
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
    57
stringio = util.stringio
2724
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    58
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    59
# option added by evolve
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    60
3283
039c4b8dc3ed obsnote: warn if user try to store a note in obsmarker on an older hg
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3271
diff changeset
    61
def _checknotesize(ui, opts):
3213
7bc587557e4f cmdrewrite: add a utility function to make sure note is of valid format
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2949
diff changeset
    62
    """ make sure note is of valid format """
7bc587557e4f cmdrewrite: add a utility function to make sure note is of valid format
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2949
diff changeset
    63
7bc587557e4f cmdrewrite: add a utility function to make sure note is of valid format
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2949
diff changeset
    64
    note = opts.get('note')
7bc587557e4f cmdrewrite: add a utility function to make sure note is of valid format
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2949
diff changeset
    65
    if not note:
7bc587557e4f cmdrewrite: add a utility function to make sure note is of valid format
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2949
diff changeset
    66
        return
7bc587557e4f cmdrewrite: add a utility function to make sure note is of valid format
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2949
diff changeset
    67
3283
039c4b8dc3ed obsnote: warn if user try to store a note in obsmarker on an older hg
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3271
diff changeset
    68
    if not compat.isobsnotesupported():
039c4b8dc3ed obsnote: warn if user try to store a note in obsmarker on an older hg
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3271
diff changeset
    69
        ui.warn(_("current hg version does not support storing"
039c4b8dc3ed obsnote: warn if user try to store a note in obsmarker on an older hg
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3271
diff changeset
    70
                  " note in obsmarker\n"))
3213
7bc587557e4f cmdrewrite: add a utility function to make sure note is of valid format
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2949
diff changeset
    71
    if len(note) > 255:
7bc587557e4f cmdrewrite: add a utility function to make sure note is of valid format
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2949
diff changeset
    72
        raise error.Abort(_("cannot store a note of more than 255 bytes"))
7bc587557e4f cmdrewrite: add a utility function to make sure note is of valid format
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2949
diff changeset
    73
    if '\n' in note:
7bc587557e4f cmdrewrite: add a utility function to make sure note is of valid format
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2949
diff changeset
    74
        raise error.Abort(_("note cannot contain a newline"))
7bc587557e4f cmdrewrite: add a utility function to make sure note is of valid format
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2949
diff changeset
    75
2724
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    76
def _resolveoptions(ui, opts):
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    77
    """modify commit options dict to handle related options
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    78
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    79
    For now, all it does is figure out the commit date: respect -D unless
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    80
    -d was supplied.
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    81
    """
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    82
    # N.B. this is extremely similar to setupheaderopts() in mq.py
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    83
    if not opts.get('date') and opts.get('current_date'):
3514
498f782ccb4b compat: add compat layer for date related functions
Boris Feld <boris.feld@octobus.net>
parents: 3506
diff changeset
    84
        opts['date'] = '%d %d' % compat.makedate()
2724
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    85
    if not opts.get('user') and opts.get('current_user'):
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    86
        opts['user'] = ui.username()
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    87
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    88
commitopts3 = [
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    89
    ('D', 'current-date', None,
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    90
     _('record the current date as commit date')),
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    91
    ('U', 'current-user', None,
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    92
     _('record the current user as committer')),
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    93
]
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    94
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    95
interactiveopt = [['i', 'interactive', None, _('use interactive mode')]]
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    96
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    97
@eh.command(
3231
996dabc4224b help: promote "amend" to important command
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3230
diff changeset
    98
    '^amend|refresh',
2724
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
    99
    [('A', 'addremove', None,
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
   100
      _('mark new/missing files as added/removed before committing')),
2730
7fbb7a5d359f uncommit: expose the feature with a '--extract' to amend
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2729
diff changeset
   101
     ('a', 'all', False, _("match all files")),
2724
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
   102
     ('e', 'edit', False, _('invoke editor on commit messages')),
2730
7fbb7a5d359f uncommit: expose the feature with a '--extract' to amend
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2729
diff changeset
   103
     ('', 'extract', False, _('extract changes from the commit to the working copy')),
3660
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   104
     ('', 'patch', False, _('make changes to wdir parent by editing patch')),
2724
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
   105
     ('', 'close-branch', None,
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
   106
      _('mark a branch as closed, hiding it from the branch list')),
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
   107
     ('s', 'secret', None, _('use the secret phase for committing')),
3221
9f3521cc4c90 amend: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3220
diff changeset
   108
     ('n', 'note', '', _('store a note on amend')),
2724
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
   109
    ] + walkopts + commitopts + commitopts2 + commitopts3 + interactiveopt,
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
   110
    _('[OPTION]... [FILE]...'))
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
   111
def amend(ui, repo, *pats, **opts):
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
   112
    """combine a changeset with updates and replace it with a new one
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
   113
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
   114
    Commits a new changeset incorporating both the changes to the given files
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
   115
    and all the changes from the current parent changeset into the repository.
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
   116
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
   117
    See :hg:`commit` for details about committing changes.
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
   118
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
   119
    If you don't specify -m, the parent's message will be reused.
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
   120
3296
b834cb64f779 amend: fix a typo in amend help text related to the extract option
Boris Feld <boris.feld@octobus.net>
parents: 3283
diff changeset
   121
    If --extract is specified, the behavior of `hg amend` is reversed: Changes
2730
7fbb7a5d359f uncommit: expose the feature with a '--extract' to amend
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2729
diff changeset
   122
    to selected files in the checked out revision appear again as uncommitted
7fbb7a5d359f uncommit: expose the feature with a '--extract' to amend
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2729
diff changeset
   123
    changed in the working directory.
7fbb7a5d359f uncommit: expose the feature with a '--extract' to amend
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2729
diff changeset
   124
2724
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
   125
    Returns 0 on success, 1 if nothing changed.
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
   126
    """
3283
039c4b8dc3ed obsnote: warn if user try to store a note in obsmarker on an older hg
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3271
diff changeset
   127
    _checknotesize(ui, opts)
2724
e6bc6eaa17c5 amend: extract into a 'evolve.evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents:
diff changeset
   128
    opts = opts.copy()
3660
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   129
    if opts.get('patch'):
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   130
        return amendpatch(ui, repo, *pats, **opts)
2730
7fbb7a5d359f uncommit: expose the feature with a '--extract' to amend
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2729
diff changeset
   131
    if opts.get('extract'):
7fbb7a5d359f uncommit: expose the feature with a '--extract' to amend
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2729
diff changeset
   132
        return uncommit(ui, repo, *pats, **opts)
7fbb7a5d359f uncommit: expose the feature with a '--extract' to amend
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2729
diff changeset
   133
    else:
7fbb7a5d359f uncommit: expose the feature with a '--extract' to amend
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2729
diff changeset
   134
        if opts.pop('all', False):
7fbb7a5d359f uncommit: expose the feature with a '--extract' to amend
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2729
diff changeset
   135
            # add an include for all
7fbb7a5d359f uncommit: expose the feature with a '--extract' to amend
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2729
diff changeset
   136
            include = list(opts.get('include'))
7fbb7a5d359f uncommit: expose the feature with a '--extract' to amend
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2729
diff changeset
   137
            include.append('re:.*')
7fbb7a5d359f uncommit: expose the feature with a '--extract' to amend
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2729
diff changeset
   138
        edit = opts.pop('edit', False)
7fbb7a5d359f uncommit: expose the feature with a '--extract' to amend
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2729
diff changeset
   139
        log = opts.get('logfile')
7fbb7a5d359f uncommit: expose the feature with a '--extract' to amend
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2729
diff changeset
   140
        opts['amend'] = True
7fbb7a5d359f uncommit: expose the feature with a '--extract' to amend
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2729
diff changeset
   141
        _resolveoptions(ui, opts)
7fbb7a5d359f uncommit: expose the feature with a '--extract' to amend
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2729
diff changeset
   142
        _alias, commitcmd = cmdutil.findcmd('commit', commands.table)
3744
4a70392f1723 amend: use context manager for locks (issue5887)
Martin von Zweigbergk <martinvonz@google.com>
parents: 3709
diff changeset
   143
        with repo.wlock(), repo.lock():
3452
8275ef099135 amend: query the wdir parent after taking lock (issue5266)
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3451
diff changeset
   144
            if not (edit or opts['message'] or log):
8275ef099135 amend: query the wdir parent after taking lock (issue5266)
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3451
diff changeset
   145
                opts['message'] = repo['.'].description()
2787
ebca049e8ca9 amend: use precheck to validate revision
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2786
diff changeset
   146
            rewriteutil.precheck(repo, [repo['.'].rev()], action='amend')
ebca049e8ca9 amend: use precheck to validate revision
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2786
diff changeset
   147
            return commitcmd[0](ui, repo, *pats, **opts)
2725
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   148
3660
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   149
def amendpatch(ui, repo, *pats, **opts):
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   150
    """logic for --patch flag of `hg amend` command."""
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   151
    lock = wlock = tr = None
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   152
    try:
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   153
        wlock = repo.wlock()
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   154
        lock = repo.lock()
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   155
        tr = repo.transaction('amend')
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   156
        cmdutil.bailifchanged(repo)
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   157
        # first get the patch
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   158
        old = repo['.']
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   159
        p1 = old.p1()
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   160
        rewriteutil.precheck(repo, [old.rev()], 'amend')
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   161
        bookmarkupdater = rewriteutil.bookmarksupdater(repo, old.node(), tr)
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   162
        diffopts = patch.difffeatureopts(repo.ui, whitespace=True)
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   163
        diffopts.nodates = True
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   164
        diffopts.git = True
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   165
        fp = stringio()
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   166
        _writectxmetadata(repo, old, fp)
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   167
        matcher = scmutil.match(old, pats, opts)
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   168
        for chunk, label in patch.diffui(repo, p1.node(), old.node(),
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   169
                                         match=matcher,
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   170
                                         opts=diffopts):
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   171
                fp.write(chunk)
3661
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   172
        newnode = _editandapply(ui, repo, pats, old, p1, fp, diffopts)
3660
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   173
        if newnode == old.node():
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   174
            raise error.Abort(_("nothing changed"))
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   175
        metadata = {}
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   176
        if opts.get('note'):
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   177
            metadata['note'] = opts['note']
3694
c0d5e0929f8b compat: from compatibility layer for createmarkers
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3675
diff changeset
   178
        obsolete.createmarkers(repo, [(old, (repo[newnode],))],
c0d5e0929f8b compat: from compatibility layer for createmarkers
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3675
diff changeset
   179
                               metadata=metadata, operation='amend')
3660
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   180
        phases.retractboundary(repo, tr, old.phase(), [newnode])
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   181
        hg.updaterepo(repo, newnode, True)
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   182
        bookmarkupdater(newnode)
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   183
        tr.close()
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   184
    finally:
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   185
        tr.release()
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   186
        lockmod.release(lock, wlock)
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   187
3661
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   188
def _editandapply(ui, repo, pats, old, p1, fp, diffopts):
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   189
    RETRYCHOICE = _('try to fix the patch (yn)?$$ &Yes $$ &No')
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   190
    newnode = None
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   191
    while newnode is None:
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   192
        fp.seek(0)
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   193
        previous_patch = fp.getvalue()
3709
aaa6adbbb47a compat: handle different `ui.edit` signature with Mercurial 4.3
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3699
diff changeset
   194
        if 5 <= len(ui.edit.im_func.func_defaults):
aaa6adbbb47a compat: handle different `ui.edit` signature with Mercurial 4.3
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3699
diff changeset
   195
            newpatch = ui.edit(fp.getvalue(), old.user(), action="diff")
aaa6adbbb47a compat: handle different `ui.edit` signature with Mercurial 4.3
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3699
diff changeset
   196
        else:
aaa6adbbb47a compat: handle different `ui.edit` signature with Mercurial 4.3
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3699
diff changeset
   197
            newpatch = ui.edit(fp.getvalue(), old.user())
3661
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   198
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   199
        afp = stringio()
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   200
        afp.write(newpatch)
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   201
        if pats:
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   202
            # write rest of the files in the patch
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   203
            restmatcher = scmutil.match(old, [], opts={'exclude': pats})
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   204
            for chunk, label in patch.diffui(repo, p1.node(), old.node(),
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   205
                                             match=restmatcher,
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   206
                                             opts=diffopts):
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   207
                    afp.write(chunk)
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   208
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   209
        user_patch = afp.getvalue()
3877
96bbea985b25 amend: allow aborting an `amend --patch` by saving an empty file (issue5925)
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3751
diff changeset
   210
        if not user_patch:
96bbea985b25 amend: allow aborting an `amend --patch` by saving an empty file (issue5925)
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3751
diff changeset
   211
            raise error.Abort(_("empty patch file, amend aborted"))
3661
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   212
        if user_patch == previous_patch:
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   213
            raise error.Abort(_("patch unchanged"))
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   214
        afp.seek(0)
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   215
        # write the patch to repo and get the newnode
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   216
        try:
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   217
            newnode = _writepatch(ui, repo, old, afp)
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   218
        except patch.PatchError as err:
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   219
            ui.write_err(_("failed to apply edited patch: %s\n") % err)
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   220
            defaultchoice = 0 # yes
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   221
            if not ui.interactive:
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   222
                defaultchoice = 1 # no
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   223
            if ui.promptchoice(RETRYCHOICE, default=defaultchoice):
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   224
                raise error.Abort(_("Could not apply amended path"))
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   225
            else:
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   226
                # consider a third choice where we restore the original patch
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   227
                fp = stringio()
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   228
                fp.write(user_patch)
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   229
    return newnode
61fdd25542a6 patch: offer the user a chance to fix the patch if it fails to apply
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3660
diff changeset
   230
3660
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   231
def _writepatch(ui, repo, old, fp):
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   232
    """utility function to use filestore and patchrepo to apply a patch to the
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   233
    repository with metadata being extracted from the patch"""
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   234
    metadata = patch.extract(ui, fp)
3670
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   235
    if util.safehasattr(metadata, 'get'): # < hg-4.6
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   236
        @contextlib.contextmanager
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   237
        def patchcontext():
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   238
            yield metadata
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   239
        patchcontext = patchcontext()
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   240
    else:
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   241
        patchcontext = metadata
3660
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   242
    pold = old.p1()
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   243
3670
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   244
    with patchcontext as metadata:
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   245
        # store the metadata from the patch to variables
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   246
        parents = (metadata.get('p1'), metadata.get('p2'))
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   247
        date = metadata.get('date') or old.date()
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   248
        branch = metadata.get('branch') or old.branch()
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   249
        user = metadata.get('user') or old.user()
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   250
        # XXX: we must extract extras from the patchfile too
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   251
        extra = old.extra()
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   252
        message = metadata.get('message') or old.description()
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   253
        store = patch.filestore()
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   254
        fp.seek(0)
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   255
        try:
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   256
            files = set()
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   257
            # beware: next line may raise a PatchError to be handled by the caller
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   258
            # of this function
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   259
            patch.patchrepo(ui, repo, pold, store, fp, 1, '',
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   260
                            files=files, eolmode=None)
3660
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   261
3670
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   262
            memctx = context.memctx(repo, parents, message, files=files,
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   263
                                    filectxfn=store,
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   264
                                    user=user,
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   265
                                    date=date,
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   266
                                    branch=branch,
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   267
                                    extra=extra)
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   268
            newcm = memctx.commit()
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   269
        finally:
1043e9c54355 compat: adapt `amend --patch` to the new `patch.extract` API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3661
diff changeset
   270
            store.close()
3660
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   271
    return newcm
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   272
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   273
def _writectxmetadata(repo, ctx, fp):
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   274
    nodeval = scmutil.binnode(ctx)
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   275
    parents = [p.node() for p in ctx.parents() if p]
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   276
    branch = ctx.branch()
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   277
    if parents:
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   278
        prev = parents[0]
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   279
    else:
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   280
        prev = node.nullid
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   281
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   282
    fp.write("# HG changeset patch\n")
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   283
    fp.write("# User %s\n" % ctx.user())
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   284
    fp.write("# Date %d %d\n" % ctx.date())
3675
1dccccde82bb compat: access datestr in a way compatible with verison prior to 4.6
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3670
diff changeset
   285
    fp.write("#      %s\n" % datestr(ctx.date()))
3660
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   286
    if branch and branch != 'default':
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   287
        fp.write("# Branch %s\n" % branch)
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   288
    fp.write("# Node ID %s\n" % node.hex(nodeval))
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   289
    fp.write("# Parent  %s\n" % node.hex(prev))
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   290
    if len(parents) > 1:
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   291
        fp.write("# Parent  %s\n" % node.hex(parents[1]))
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   292
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   293
    for headerid in cmdutil.extraexport:
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   294
        header = cmdutil.extraexportmap[headerid](1, ctx)
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   295
        if header is not None:
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   296
            fp.write('# %s\n' % header)
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   297
    fp.write(ctx.description().rstrip())
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   298
    fp.write("\n\n")
f018656ca3bf amend: add a new flag `--patch` to `hg amend`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3616
diff changeset
   299
2725
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   300
def _touchedbetween(repo, source, dest, match=None):
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   301
    touched = set()
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   302
    for files in repo.status(source, dest, match=match)[:3]:
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   303
        touched.update(files)
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   304
    return touched
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   305
2728
3c371aa16cb9 uncommit: add support for --user and --date
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2727
diff changeset
   306
def _commitfiltered(repo, ctx, match, target=None, message=None, user=None,
3c371aa16cb9 uncommit: add support for --user and --date
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2727
diff changeset
   307
                    date=None):
2725
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   308
    """Recommit ctx with changed files not in match. Return the new
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   309
    node identifier, or None if nothing changed.
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   310
    """
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   311
    base = ctx.p1()
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   312
    if target is None:
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   313
        target = base
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   314
    # ctx
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   315
    initialfiles = _touchedbetween(repo, base, ctx)
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   316
    if base == target:
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   317
        affected = set(f for f in initialfiles if match(f))
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   318
        newcontent = set()
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   319
    else:
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   320
        affected = _touchedbetween(repo, target, ctx, match=match)
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   321
        newcontent = _touchedbetween(repo, target, base, match=match)
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   322
    # The commit touchs all existing files
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   323
    # + all file that needs a new content
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   324
    # - the file affected bny uncommit with the same content than base.
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   325
    files = (initialfiles - affected) | newcontent
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   326
    if not newcontent and files == initialfiles:
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   327
        return None
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   328
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   329
    # Filter copies
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   330
    copied = copies.pathcopies(target, ctx)
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   331
    copied = dict((dst, src) for dst, src in copied.iteritems()
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   332
                  if dst in files)
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   333
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   334
    def filectxfn(repo, memctx, path, contentctx=ctx, redirect=newcontent):
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   335
        if path in redirect:
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   336
            return filectxfn(repo, memctx, path, contentctx=target, redirect=())
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   337
        if path not in contentctx:
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   338
            return None
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   339
        fctx = contentctx[path]
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   340
        flags = fctx.flags()
3298
f4b06f44d274 memfilectx: changectx argument is not mandatory
Boris Feld <boris.feld@octobus.net>
parents: 3296
diff changeset
   341
        mctx = compat.memfilectx(repo, memctx, fctx, flags, copied, path)
2725
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   342
        return mctx
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   343
2727
f7d44441dfd3 uncommit: add support for --message and --logfile
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2726
diff changeset
   344
    if message is None:
f7d44441dfd3 uncommit: add support for --message and --logfile
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2726
diff changeset
   345
        message = ctx.description()
2728
3c371aa16cb9 uncommit: add support for --user and --date
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2727
diff changeset
   346
    if not user:
3c371aa16cb9 uncommit: add support for --user and --date
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2727
diff changeset
   347
        user = ctx.user()
3c371aa16cb9 uncommit: add support for --user and --date
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2727
diff changeset
   348
    if not date:
3c371aa16cb9 uncommit: add support for --user and --date
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2727
diff changeset
   349
        date = ctx.date()
2725
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   350
    new = context.memctx(repo,
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   351
                         parents=[base.node(), node.nullid],
2727
f7d44441dfd3 uncommit: add support for --message and --logfile
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2726
diff changeset
   352
                         text=message,
2725
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   353
                         files=files,
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   354
                         filectxfn=filectxfn,
2728
3c371aa16cb9 uncommit: add support for --user and --date
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2727
diff changeset
   355
                         user=user,
3c371aa16cb9 uncommit: add support for --user and --date
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2727
diff changeset
   356
                         date=date,
2725
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   357
                         extra=ctx.extra())
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   358
    # commitctx always create a new revision, no need to check
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   359
    newid = repo.commitctx(new)
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   360
    return newid
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   361
2943
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   362
def _uncommitdirstate(repo, oldctx, match, interactive):
2725
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   363
    """Fix the dirstate after switching the working directory from
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   364
    oldctx to a copy of oldctx not containing changed files matched by
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   365
    match.
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   366
    """
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   367
    ctx = repo['.']
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   368
    ds = repo.dirstate
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   369
    copies = dict(ds.copies())
2943
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   370
    if interactive:
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   371
        # In interactive cases, we will find the status between oldctx and ctx
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   372
        # and considering only the files which are changed between oldctx and
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   373
        # ctx, and the status of what changed between oldctx and ctx will help
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   374
        # us in defining the exact behavior
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   375
        m, a, r = repo.status(oldctx, ctx, match=match)[:3]
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   376
        for f in m:
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   377
            # These are files which are modified between oldctx and ctx which
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   378
            # contains two cases: 1) Were modified in oldctx and some
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   379
            # modifications are uncommitted
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   380
            # 2) Were added in oldctx but some part is uncommitted (this cannot
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   381
            # contain the case when added files are uncommitted completely as
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   382
            # that will result in status as removed not modified.)
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   383
            # Also any modifications to a removed file will result the status as
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   384
            # added, so we have only two cases. So in either of the cases, the
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   385
            # resulting status can be modified or clean.
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   386
            if ds[f] == 'r':
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   387
                # But the file is removed in the working directory, leaving that
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   388
                # as removed
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   389
                continue
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   390
            ds.normallookup(f)
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   391
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   392
        for f in a:
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   393
            # These are the files which are added between oldctx and ctx(new
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   394
            # one), which means the files which were removed in oldctx
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   395
            # but uncommitted completely while making the ctx
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   396
            # This file should be marked as removed if the working directory
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   397
            # does not adds it back. If it's adds it back, we do a normallookup.
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   398
            # The file can't be removed in working directory, because it was
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   399
            # removed in oldctx
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   400
            if ds[f] == 'a':
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   401
                ds.normallookup(f)
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   402
                continue
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   403
            ds.remove(f)
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   404
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   405
        for f in r:
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   406
            # These are files which are removed between oldctx and ctx, which
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   407
            # means the files which were added in oldctx and were completely
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   408
            # uncommitted in ctx. If a added file is partially uncommitted, that
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   409
            # would have resulted in modified status, not removed.
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   410
            # So a file added in a commit, and uncommitting that addition must
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   411
            # result in file being stated as unknown.
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   412
            if ds[f] == 'r':
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   413
                # The working directory say it's removed, so lets make the file
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   414
                # unknown
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   415
                ds.drop(f)
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   416
                continue
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   417
            ds.add(f)
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   418
    else:
2942
10194206acc7 uncommit: pre-indent a block in if-True
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2941
diff changeset
   419
        m, a, r = repo.status(oldctx.p1(), oldctx, match=match)[:3]
10194206acc7 uncommit: pre-indent a block in if-True
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2941
diff changeset
   420
        for f in m:
10194206acc7 uncommit: pre-indent a block in if-True
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2941
diff changeset
   421
            if ds[f] == 'r':
10194206acc7 uncommit: pre-indent a block in if-True
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2941
diff changeset
   422
                # modified + removed -> removed
10194206acc7 uncommit: pre-indent a block in if-True
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2941
diff changeset
   423
                continue
10194206acc7 uncommit: pre-indent a block in if-True
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2941
diff changeset
   424
            ds.normallookup(f)
2725
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   425
2942
10194206acc7 uncommit: pre-indent a block in if-True
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2941
diff changeset
   426
        for f in a:
10194206acc7 uncommit: pre-indent a block in if-True
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2941
diff changeset
   427
            if ds[f] == 'r':
10194206acc7 uncommit: pre-indent a block in if-True
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2941
diff changeset
   428
                # added + removed -> unknown
10194206acc7 uncommit: pre-indent a block in if-True
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2941
diff changeset
   429
                ds.drop(f)
10194206acc7 uncommit: pre-indent a block in if-True
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2941
diff changeset
   430
            elif ds[f] != 'a':
10194206acc7 uncommit: pre-indent a block in if-True
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2941
diff changeset
   431
                ds.add(f)
2725
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   432
2942
10194206acc7 uncommit: pre-indent a block in if-True
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2941
diff changeset
   433
        for f in r:
10194206acc7 uncommit: pre-indent a block in if-True
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2941
diff changeset
   434
            if ds[f] == 'a':
10194206acc7 uncommit: pre-indent a block in if-True
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2941
diff changeset
   435
                # removed + added -> normal
10194206acc7 uncommit: pre-indent a block in if-True
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2941
diff changeset
   436
                ds.normallookup(f)
10194206acc7 uncommit: pre-indent a block in if-True
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2941
diff changeset
   437
            elif ds[f] != 'r':
10194206acc7 uncommit: pre-indent a block in if-True
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2941
diff changeset
   438
                ds.remove(f)
2725
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   439
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   440
    # Merge old parent and old working dir copies
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   441
    oldcopies = {}
2943
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   442
    if interactive:
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   443
        # Interactive had different meaning of the variables so restoring the
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   444
        # original meaning to use them
25576132cb30 uncommit: fix the dirstate handling in `uncommit -i`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2942
diff changeset
   445
        m, a, r = repo.status(oldctx.p1(), oldctx, match=match)[:3]
2725
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   446
    for f in (m + a):
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   447
        src = oldctx[f].renamed()
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   448
        if src:
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   449
            oldcopies[f] = src[0]
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   450
    oldcopies.update(copies)
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   451
    copies = dict((dst, oldcopies.get(src, src))
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   452
                  for dst, src in oldcopies.iteritems())
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   453
    # Adjust the dirstate copies
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   454
    for dst, src in copies.iteritems():
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   455
        if (src not in ctx or dst in ctx or ds[dst] != 'a'):
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   456
            src = None
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   457
        ds.copy(src, dst)
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   458
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   459
@eh.command(
3229
63f6f9db9c3a help: remove a few commands from `hg` (no args) command list
Kyle Lippincott <spectral@google.com>
parents: 2949
diff changeset
   460
    'uncommit',
2725
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   461
    [('a', 'all', None, _('uncommit all changes when no arguments given')),
2941
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   462
     ('i', 'interactive', False, _('interactive mode to uncommit (EXPERIMENTAL)')),
2725
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   463
     ('r', 'rev', '', _('revert commit content to REV instead')),
3389
eacf6149b678 uncommit: add a new flag `--revert` to discard wdir changes after uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3298
diff changeset
   464
     ('', 'revert', False, _('discard working directory changes after uncommit')),
3220
f0f4cc2febac uncommit: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3219
diff changeset
   465
     ('n', 'note', '', _('store a note on uncommit')),
2729
69fe16428b0f uncommit: add support for -U and -D
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2728
diff changeset
   466
     ] + commands.walkopts + commitopts + commitopts2 + commitopts3,
2725
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   467
    _('[OPTION]... [NAME]'))
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   468
def uncommit(ui, repo, *pats, **opts):
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   469
    """move changes from parent revision to working directory
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   470
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   471
    Changes to selected files in the checked out revision appear again as
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   472
    uncommitted changed in the working directory. A new revision
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   473
    without the selected changes is created, becomes the checked out
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   474
    revision, and obsoletes the previous one.
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   475
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   476
    The --include option specifies patterns to uncommit.
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   477
    The --exclude option specifies patterns to keep in the commit.
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   478
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   479
    The --rev argument let you change the commit file to a content of another
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   480
    revision. It still does not change the content of your file in the working
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   481
    directory.
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   482
2941
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   483
    .. container:: verbose
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   484
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   485
       The --interactive option lets you select hunks interactively to uncommit.
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   486
       You can uncommit parts of file using this option.
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   487
2725
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   488
    Return 0 if changed files are uncommitted.
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   489
    """
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   490
3283
039c4b8dc3ed obsnote: warn if user try to store a note in obsmarker on an older hg
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3271
diff changeset
   491
    _checknotesize(ui, opts)
2729
69fe16428b0f uncommit: add support for -U and -D
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2728
diff changeset
   492
    _resolveoptions(ui, opts) # process commitopts3
2941
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   493
    interactive = opts.get('interactive')
2725
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   494
    wlock = lock = tr = None
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   495
    try:
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   496
        wlock = repo.wlock()
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   497
        lock = repo.lock()
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   498
        wctx = repo[None]
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   499
        if len(wctx.parents()) <= 0:
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   500
            raise error.Abort(_("cannot uncommit null changeset"))
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   501
        if len(wctx.parents()) > 1:
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   502
            raise error.Abort(_("cannot uncommit while merging"))
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   503
        old = repo['.']
2788
554c069cdc85 uncommit: use precheck to validate revision
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2787
diff changeset
   504
        rewriteutil.precheck(repo, [repo['.'].rev()], action='uncommit')
2725
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   505
        if len(old.parents()) > 1:
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   506
            raise error.Abort(_("cannot uncommit merge changeset"))
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   507
        oldphase = old.phase()
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   508
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   509
        rev = None
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   510
        if opts.get('rev'):
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   511
            rev = scmutil.revsingle(repo, opts.get('rev'))
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   512
            ctx = repo[None]
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   513
            if ctx.p1() == rev or ctx.p2() == rev:
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   514
                raise error.Abort(_("cannot uncommit to parent changeset"))
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   515
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   516
        onahead = old.rev() in repo.changelog.headrevs()
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   517
        disallowunstable = not obsolete.isenabled(repo,
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   518
                                                  obsolete.allowunstableopt)
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   519
        if disallowunstable and not onahead:
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   520
            raise error.Abort(_("cannot uncommit in the middle of a stack"))
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   521
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   522
        # Recommit the filtered changeset
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   523
        tr = repo.transaction('uncommit')
2756
f4dd6e6d4c73 rewriteutil: create a rewriteutil module to host utility function
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2752
diff changeset
   524
        updatebookmarks = rewriteutil.bookmarksupdater(repo, old.node(), tr)
2941
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   525
        if interactive:
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   526
            opts['all'] = True
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   527
            match = scmutil.match(old, pats, opts)
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   528
            newid = _interactiveuncommit(ui, repo, old, match)
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   529
        else:
2940
89b205e5271e uncommit: pre-indent a block in if-True for the next patch
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2923
diff changeset
   530
            newid = None
89b205e5271e uncommit: pre-indent a block in if-True for the next patch
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2923
diff changeset
   531
            includeorexclude = opts.get('include') or opts.get('exclude')
89b205e5271e uncommit: pre-indent a block in if-True for the next patch
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2923
diff changeset
   532
            if (pats or includeorexclude or opts.get('all')):
89b205e5271e uncommit: pre-indent a block in if-True for the next patch
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2923
diff changeset
   533
                match = scmutil.match(old, pats, opts)
89b205e5271e uncommit: pre-indent a block in if-True for the next patch
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2923
diff changeset
   534
                if not (opts['message'] or opts['logfile']):
89b205e5271e uncommit: pre-indent a block in if-True for the next patch
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2923
diff changeset
   535
                    opts['message'] = old.description()
89b205e5271e uncommit: pre-indent a block in if-True for the next patch
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2923
diff changeset
   536
                message = cmdutil.logmessage(ui, opts)
89b205e5271e uncommit: pre-indent a block in if-True for the next patch
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2923
diff changeset
   537
                newid = _commitfiltered(repo, old, match, target=rev,
89b205e5271e uncommit: pre-indent a block in if-True for the next patch
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2923
diff changeset
   538
                                        message=message, user=opts.get('user'),
89b205e5271e uncommit: pre-indent a block in if-True for the next patch
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2923
diff changeset
   539
                                        date=opts.get('date'))
89b205e5271e uncommit: pre-indent a block in if-True for the next patch
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2923
diff changeset
   540
            if newid is None:
89b205e5271e uncommit: pre-indent a block in if-True for the next patch
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2923
diff changeset
   541
                raise error.Abort(_('nothing to uncommit'),
89b205e5271e uncommit: pre-indent a block in if-True for the next patch
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2923
diff changeset
   542
                                  hint=_("use --all to uncommit all files"))
2941
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   543
3220
f0f4cc2febac uncommit: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3219
diff changeset
   544
        # metadata to be stored in obsmarker
f0f4cc2febac uncommit: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3219
diff changeset
   545
        metadata = {}
f0f4cc2febac uncommit: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3219
diff changeset
   546
        if opts.get('note'):
f0f4cc2febac uncommit: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3219
diff changeset
   547
            metadata['note'] = opts['note']
f0f4cc2febac uncommit: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3219
diff changeset
   548
3694
c0d5e0929f8b compat: from compatibility layer for createmarkers
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3675
diff changeset
   549
        obsolete.createmarkers(repo, [(old, (repo[newid],))], metadata=metadata,
c0d5e0929f8b compat: from compatibility layer for createmarkers
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3675
diff changeset
   550
                               operation="uncommit")
2725
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   551
        phases.retractboundary(repo, tr, oldphase, [newid])
3389
eacf6149b678 uncommit: add a new flag `--revert` to discard wdir changes after uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3298
diff changeset
   552
        if opts.get('revert'):
eacf6149b678 uncommit: add a new flag `--revert` to discard wdir changes after uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3298
diff changeset
   553
            hg.updaterepo(repo, newid, True)
eacf6149b678 uncommit: add a new flag `--revert` to discard wdir changes after uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3298
diff changeset
   554
        else:
eacf6149b678 uncommit: add a new flag `--revert` to discard wdir changes after uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3298
diff changeset
   555
            with repo.dirstate.parentchange():
eacf6149b678 uncommit: add a new flag `--revert` to discard wdir changes after uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3298
diff changeset
   556
                repo.dirstate.setparents(newid, node.nullid)
eacf6149b678 uncommit: add a new flag `--revert` to discard wdir changes after uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3298
diff changeset
   557
                _uncommitdirstate(repo, old, match, interactive)
2725
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   558
        updatebookmarks(newid)
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   559
        if not repo[newid].files():
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   560
            ui.warn(_("new changeset is empty\n"))
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   561
            ui.status(_("(use 'hg prune .' to remove it)\n"))
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   562
        tr.close()
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   563
    finally:
4eb90eace7f9 uncommit: move to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2724
diff changeset
   564
        lockmod.release(tr, lock, wlock)
2760
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   565
2941
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   566
def _interactiveuncommit(ui, repo, old, match):
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   567
    """ The function which contains all the logic for interactively uncommiting
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   568
    a commit. This function makes a temporary commit with the chunks which user
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   569
    selected to uncommit. After that the diff of the parent and that commit is
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   570
    applied to the working directory and committed again which results in the
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   571
    new commit which should be one after uncommitted.
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   572
    """
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   573
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   574
    # create a temporary commit with hunks user selected
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   575
    tempnode = _createtempcommit(ui, repo, old, match)
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   576
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   577
    diffopts = patch.difffeatureopts(repo.ui, whitespace=True)
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   578
    diffopts.nodates = True
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   579
    diffopts.git = True
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   580
    fp = stringio()
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   581
    for chunk, label in patch.diffui(repo, tempnode, old.node(), None,
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   582
                                     opts=diffopts):
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   583
            fp.write(chunk)
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   584
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   585
    fp.seek(0)
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   586
    newnode = _patchtocommit(ui, repo, old, fp)
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   587
    # creating obs marker temp -> ()
3694
c0d5e0929f8b compat: from compatibility layer for createmarkers
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3675
diff changeset
   588
    obsolete.createmarkers(repo, [(repo[tempnode], ())], operation="uncommit")
2941
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   589
    return newnode
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   590
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   591
def _createtempcommit(ui, repo, old, match):
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   592
    """ Creates a temporary commit for `uncommit --interative` which contains
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   593
    the hunks which were selected by the user to uncommit.
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   594
    """
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   595
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   596
    pold = old.p1()
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   597
    # The logic to interactively selecting something copied from
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   598
    # cmdutil.revert()
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   599
    diffopts = patch.difffeatureopts(repo.ui, whitespace=True)
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   600
    diffopts.nodates = True
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   601
    diffopts.git = True
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   602
    diff = patch.diff(repo, pold.node(), old.node(), match, opts=diffopts)
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   603
    originalchunks = patch.parsepatch(diff)
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   604
    # XXX: The interactive selection is buggy and does not let you
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   605
    # uncommit a removed file partially.
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   606
    # TODO: wrap the operations in mercurial/patch.py and mercurial/crecord.py
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   607
    # to add uncommit as an operation taking care of BC.
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   608
    chunks, opts = cmdutil.recordfilter(repo.ui, originalchunks,
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   609
                                        operation='discard')
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   610
    if not chunks:
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   611
        raise error.Abort(_("nothing selected to uncommit"))
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   612
    fp = stringio()
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   613
    for c in chunks:
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   614
            c.write(fp)
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   615
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   616
    fp.seek(0)
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   617
    oldnode = node.hex(old.node())[:12]
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   618
    message = 'temporary commit for uncommiting %s' % oldnode
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   619
    tempnode = _patchtocommit(ui, repo, old, fp, message, oldnode)
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   620
    return tempnode
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   621
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   622
def _patchtocommit(ui, repo, old, fp, message=None, extras=None):
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   623
    """ A function which will apply the patch to the working directory and
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   624
    make a commit whose parents are same as that of old argument. The message
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   625
    argument tells us whether to use the message of the old commit or a
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   626
    different message which is passed. Returns the node of new commit made.
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   627
    """
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   628
    pold = old.p1()
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   629
    parents = (old.p1().node(), old.p2().node())
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   630
    date = old.date()
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   631
    branch = old.branch()
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   632
    user = old.user()
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   633
    extra = old.extra()
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   634
    if extras:
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   635
        extra['uncommit_source'] = extras
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   636
    if not message:
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   637
        message = old.description()
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   638
    store = patch.filestore()
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   639
    try:
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   640
        files = set()
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   641
        try:
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   642
            patch.patchrepo(ui, repo, pold, store, fp, 1, '',
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   643
                            files=files, eolmode=None)
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   644
        except patch.PatchError as err:
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   645
            raise error.Abort(str(err))
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   646
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   647
        finally:
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   648
            del fp
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   649
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   650
        memctx = context.memctx(repo, parents, message, files=files,
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   651
                                filectxfn=store,
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   652
                                user=user,
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   653
                                date=date,
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   654
                                branch=branch,
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   655
                                extra=extra)
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   656
        newcm = memctx.commit()
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   657
    finally:
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   658
        store.close()
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   659
    return newcm
b0458b9e1b47 uncommit: add an interactive option to uncommit
Pulkit Goyal <7895pulkit@gmail.com>
parents: 2940
diff changeset
   660
2760
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   661
@eh.command(
2761
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   662
    '^fold|squash',
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   663
    [('r', 'rev', [], _("revision to fold")),
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   664
     ('', 'exact', None, _("only fold specified revisions")),
3219
b73bd280b21c fold: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3218
diff changeset
   665
     ('', 'from', None, _("fold revisions linearly to working copy parent")),
b73bd280b21c fold: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3218
diff changeset
   666
     ('n', 'note', '', _('store a note on fold')),
2768
85e5a56db776 fold: add support for the -D and -U options
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2766
diff changeset
   667
    ] + commitopts + commitopts2 + commitopts3,
2761
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   668
    _('hg fold [OPTION]... [-r] REV'))
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   669
def fold(ui, repo, *revs, **opts):
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   670
    """fold multiple revisions into a single one
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   671
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   672
    With --from, folds all the revisions linearly between the given revisions
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   673
    and the parent of the working directory.
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   674
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   675
    With --exact, folds only the specified revisions while ignoring the
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   676
    parent of the working directory. In this case, the given revisions must
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   677
    form a linear unbroken chain.
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   678
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   679
    .. container:: verbose
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   680
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   681
     Some examples:
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   682
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   683
     - Fold the current revision with its parent::
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   684
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   685
         hg fold --from .^
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   686
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   687
     - Fold all draft revisions with working directory parent::
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   688
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   689
         hg fold --from 'draft()'
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   690
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   691
       See :hg:`help phases` for more about draft revisions and
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   692
       :hg:`help revsets` for more about the `draft()` keyword
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   693
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   694
     - Fold revisions between 3 and 6 with the working directory parent::
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   695
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   696
         hg fold --from 3::6
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   697
2923
8c2d3c474fc6 doc: make paragraphs before example code end with "::" for reST syntax
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 2790
diff changeset
   698
     - Fold revisions 3 and 4::
2761
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   699
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   700
        hg fold "3 + 4" --exact
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   701
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   702
     - Only fold revisions linearly between foo and @::
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   703
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   704
         hg fold foo::@ --exact
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   705
    """
3283
039c4b8dc3ed obsnote: warn if user try to store a note in obsmarker on an older hg
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3271
diff changeset
   706
    _checknotesize(ui, opts)
2768
85e5a56db776 fold: add support for the -D and -U options
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2766
diff changeset
   707
    _resolveoptions(ui, opts)
2761
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   708
    revs = list(revs)
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   709
    revs.extend(opts['rev'])
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   710
    if not revs:
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   711
        raise error.Abort(_('no revisions specified'))
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   712
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   713
    revs = scmutil.revrange(repo, revs)
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   714
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   715
    if opts['from'] and opts['exact']:
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   716
        raise error.Abort(_('cannot use both --from and --exact'))
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   717
    elif opts['from']:
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   718
        # Try to extend given revision starting from the working directory
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   719
        extrevs = repo.revs('(%ld::.) or (.::%ld)', revs, revs)
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   720
        discardedrevs = [r for r in revs if r not in extrevs]
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   721
        if discardedrevs:
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   722
            msg = _("cannot fold non-linear revisions")
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   723
            hint = _("given revisions are unrelated to parent of working"
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   724
                     " directory")
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   725
            raise error.Abort(msg, hint=hint)
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   726
        revs = extrevs
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   727
    elif opts['exact']:
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   728
        # Nothing to do; "revs" is already set correctly
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   729
        pass
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   730
    else:
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   731
        raise error.Abort(_('must specify either --from or --exact'))
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   732
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   733
    if not revs:
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   734
        raise error.Abort(_('specified revisions evaluate to an empty set'),
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   735
                          hint=_('use different revision arguments'))
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   736
    elif len(revs) == 1:
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   737
        ui.write_err(_('single revision specified, nothing to fold\n'))
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   738
        return 1
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   739
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   740
    wlock = lock = None
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   741
    try:
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   742
        wlock = repo.wlock()
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   743
        lock = repo.lock()
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   744
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   745
        root, head = rewriteutil.foldcheck(repo, revs)
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   746
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   747
        tr = repo.transaction('fold')
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   748
        try:
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   749
            commitopts = opts.copy()
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   750
            allctx = [repo[r] for r in revs]
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   751
            targetphase = max(c.phase() for c in allctx)
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   752
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   753
            if commitopts.get('message') or commitopts.get('logfile'):
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   754
                commitopts['edit'] = False
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   755
            else:
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   756
                msgs = ["HG: This is a fold of %d changesets." % len(allctx)]
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   757
                msgs += ["HG: Commit message of changeset %s.\n\n%s\n" %
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   758
                         (c.rev(), c.description()) for c in allctx]
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   759
                commitopts['message'] = "\n".join(msgs)
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   760
                commitopts['edit'] = True
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   761
3219
b73bd280b21c fold: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3218
diff changeset
   762
            metadata = {}
b73bd280b21c fold: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3218
diff changeset
   763
            if opts.get('note'):
b73bd280b21c fold: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3218
diff changeset
   764
                metadata['note'] = opts['note']
b73bd280b21c fold: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3218
diff changeset
   765
2761
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   766
            newid, unusedvariable = rewriteutil.rewrite(repo, root, allctx,
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   767
                                                        head,
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   768
                                                        [root.p1().node(),
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   769
                                                         root.p2().node()],
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   770
                                                        commitopts=commitopts)
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   771
            phases.retractboundary(repo, tr, targetphase, [newid])
3694
c0d5e0929f8b compat: from compatibility layer for createmarkers
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3675
diff changeset
   772
            obsolete.createmarkers(repo, [(ctx, (repo[newid],))
c0d5e0929f8b compat: from compatibility layer for createmarkers
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3675
diff changeset
   773
                                   for ctx in allctx], metadata=metadata,
c0d5e0929f8b compat: from compatibility layer for createmarkers
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3675
diff changeset
   774
                                   operation="fold")
3451
f062a4719e46 fold: make sure we move bookmarks after folding (issue5772)
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
   775
            # move bookmarks from old nodes to the new one
f062a4719e46 fold: make sure we move bookmarks after folding (issue5772)
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
   776
            # XXX: we should make rewriteutil.rewrite() handle such cases
f062a4719e46 fold: make sure we move bookmarks after folding (issue5772)
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
   777
            for ctx in allctx:
f062a4719e46 fold: make sure we move bookmarks after folding (issue5772)
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
   778
                bmupdater = rewriteutil.bookmarksupdater(repo, ctx.node(), tr)
f062a4719e46 fold: make sure we move bookmarks after folding (issue5772)
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
   779
                bmupdater(newid)
2761
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   780
            tr.close()
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   781
        finally:
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   782
            tr.release()
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   783
        ui.status('%i changesets folded\n' % len(revs))
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   784
        if repo['.'].rev() in revs:
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   785
            hg.update(repo, newid)
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   786
    finally:
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   787
        lockmod.release(lock, wlock)
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   788
7450e360c88c commands: move fold to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2760
diff changeset
   789
@eh.command(
3229
63f6f9db9c3a help: remove a few commands from `hg` (no args) command list
Kyle Lippincott <spectral@google.com>
parents: 2949
diff changeset
   790
    'metaedit',
2760
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   791
    [('r', 'rev', [], _("revision to edit")),
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   792
     ('', 'fold', None, _("also fold specified revisions into one")),
3218
772cc931f085 metaedit: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3217
diff changeset
   793
     ('n', 'note', '', _('store a note on metaedit')),
2769
b96349ae3e2a metaedit: add support for the -D and -U options
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2768
diff changeset
   794
    ] + commitopts + commitopts2 + commitopts3,
2760
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   795
    _('hg metaedit [OPTION]... [-r] [REV]'))
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   796
def metaedit(ui, repo, *revs, **opts):
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   797
    """edit commit information
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   798
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   799
    Edits the commit information for the specified revisions. By default, edits
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   800
    commit information for the working directory parent.
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   801
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   802
    With --fold, also folds multiple revisions into one if necessary. In this
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   803
    case, the given revisions must form a linear unbroken chain.
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   804
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   805
    .. container:: verbose
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   806
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   807
     Some examples:
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   808
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   809
     - Edit the commit message for the working directory parent::
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   810
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   811
         hg metaedit
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   812
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   813
     - Change the username for the working directory parent::
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   814
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   815
         hg metaedit --user 'New User <new-email@example.com>'
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   816
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   817
     - Combine all draft revisions that are ancestors of foo but not of @ into
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   818
       one::
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   819
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   820
         hg metaedit --fold 'draft() and only(foo,@)'
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   821
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   822
       See :hg:`help phases` for more about draft revisions, and
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   823
       :hg:`help revsets` for more about the `draft()` and `only()` keywords.
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   824
    """
3283
039c4b8dc3ed obsnote: warn if user try to store a note in obsmarker on an older hg
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3271
diff changeset
   825
    _checknotesize(ui, opts)
2769
b96349ae3e2a metaedit: add support for the -D and -U options
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2768
diff changeset
   826
    _resolveoptions(ui, opts)
2760
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   827
    revs = list(revs)
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   828
    revs.extend(opts['rev'])
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   829
    if not revs:
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   830
        if opts['fold']:
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   831
            raise error.Abort(_('revisions must be specified with --fold'))
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   832
        revs = ['.']
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   833
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   834
    wlock = lock = None
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   835
    try:
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   836
        wlock = repo.wlock()
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   837
        lock = repo.lock()
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   838
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   839
        revs = scmutil.revrange(repo, revs)
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   840
        if not opts['fold'] and len(revs) > 1:
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   841
            # TODO: handle multiple revisions. This is somewhat tricky because
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   842
            # if we want to edit a series of commits:
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   843
            #
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   844
            #   a ---- b ---- c
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   845
            #
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   846
            # we need to rewrite a first, then directly rewrite b on top of the
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   847
            # new a, then rewrite c on top of the new b. So we need to handle
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   848
            # revisions in topological order.
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   849
            raise error.Abort(_('editing multiple revisions without --fold is '
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   850
                                'not currently supported'))
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   851
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   852
        if opts['fold']:
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   853
            root, head = rewriteutil.foldcheck(repo, revs)
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   854
        else:
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   855
            if repo.revs("%ld and public()", revs):
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   856
                raise error.Abort(_('cannot edit commit information for public '
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   857
                                    'revisions'))
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   858
            newunstable = rewriteutil.disallowednewunstable(repo, revs)
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   859
            if newunstable:
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   860
                msg = _('cannot edit commit information in the middle'
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   861
                        ' of a stack')
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   862
                hint = _('%s will become unstable and new unstable changes'
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   863
                         ' are not allowed')
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   864
                hint %= repo[newunstable.first()]
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   865
                raise error.Abort(msg, hint=hint)
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   866
            root = head = repo[revs.first()]
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   867
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   868
        wctx = repo[None]
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   869
        p1 = wctx.p1()
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   870
        tr = repo.transaction('metaedit')
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   871
        newp1 = None
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   872
        try:
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   873
            commitopts = opts.copy()
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   874
            allctx = [repo[r] for r in revs]
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   875
            targetphase = max(c.phase() for c in allctx)
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   876
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   877
            if commitopts.get('message') or commitopts.get('logfile'):
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   878
                commitopts['edit'] = False
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   879
            else:
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   880
                if opts['fold']:
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   881
                    msgs = ["HG: This is a fold of %d changesets." % len(allctx)]
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   882
                    msgs += ["HG: Commit message of changeset %s.\n\n%s\n" %
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   883
                             (c.rev(), c.description()) for c in allctx]
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   884
                else:
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   885
                    msgs = [head.description()]
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   886
                commitopts['message'] = "\n".join(msgs)
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   887
                commitopts['edit'] = True
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   888
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   889
            # TODO: if the author and message are the same, don't create a new
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   890
            # hash. Right now we create a new hash because the date can be
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   891
            # different.
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   892
            newid, created = rewriteutil.rewrite(repo, root, allctx, head,
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   893
                                                 [root.p1().node(),
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   894
                                                  root.p2().node()],
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   895
                                                 commitopts=commitopts)
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   896
            if created:
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   897
                if p1.rev() in revs:
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   898
                    newp1 = newid
3218
772cc931f085 metaedit: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3217
diff changeset
   899
                # metadata to be stored on obsmarker
772cc931f085 metaedit: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3217
diff changeset
   900
                metadata = {}
772cc931f085 metaedit: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3217
diff changeset
   901
                if opts.get('note'):
772cc931f085 metaedit: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3217
diff changeset
   902
                    metadata['note'] = opts['note']
772cc931f085 metaedit: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3217
diff changeset
   903
2760
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   904
                phases.retractboundary(repo, tr, targetphase, [newid])
3694
c0d5e0929f8b compat: from compatibility layer for createmarkers
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3675
diff changeset
   905
                obsolete.createmarkers(repo, [(ctx, (repo[newid],))
c0d5e0929f8b compat: from compatibility layer for createmarkers
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3675
diff changeset
   906
                                              for ctx in allctx],
c0d5e0929f8b compat: from compatibility layer for createmarkers
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3675
diff changeset
   907
                                       metadata=metadata, operation="metaedit")
2760
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   908
            else:
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   909
                ui.status(_("nothing changed\n"))
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   910
            tr.close()
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   911
        finally:
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   912
            tr.release()
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   913
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   914
        if opts['fold']:
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   915
            ui.status('%i changesets folded\n' % len(revs))
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   916
        if newp1 is not None:
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   917
            hg.update(repo, newp1)
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   918
    finally:
ddff53ecc00b commands: move metaedit to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2756
diff changeset
   919
        lockmod.release(lock, wlock)
2762
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
   920
2766
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   921
metadataopts = [
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   922
    ('d', 'date', '',
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   923
     _('record the specified date in metadata'), _('DATE')),
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   924
    ('u', 'user', '',
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   925
     _('record the specified user in metadata'), _('USER')),
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   926
]
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   927
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   928
def _getmetadata(**opts):
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   929
    metadata = {}
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   930
    date = opts.get('date')
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   931
    user = opts.get('user')
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   932
    if date:
3514
498f782ccb4b compat: add compat layer for date related functions
Boris Feld <boris.feld@octobus.net>
parents: 3506
diff changeset
   933
        metadata['date'] = '%i %i' % compat.parsedate(date)
2766
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   934
    if user:
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   935
        metadata['user'] = user
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   936
    return metadata
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   937
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   938
@eh.command(
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   939
    '^prune|obsolete',
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   940
    [('n', 'new', [], _("successor changeset (DEPRECATED)")),
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   941
     ('s', 'succ', [], _("successor changeset")),
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   942
     ('r', 'rev', [], _("revisions to prune")),
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   943
     ('k', 'keep', None, _("does not modify working copy during prune")),
3217
b6ba296532cb prune: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3216
diff changeset
   944
     ('n', 'note', '', _('store a note on prune')),
4045
821e4be40c6c prune: replace --biject with --pair
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3990
diff changeset
   945
     ('', 'pair', False, _("record a pairing, such as a rebase or divergence resolution "
821e4be40c6c prune: replace --biject with --pair
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3990
diff changeset
   946
                           "(pairing multiple precursors to multiple successors)")),
821e4be40c6c prune: replace --biject with --pair
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3990
diff changeset
   947
     ('', 'biject', False, _("alias to --pair (DEPRECATED)")),
2766
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   948
     ('', 'fold', False,
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   949
      _("record a fold (multiple precursors, one successors)")),
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   950
     ('', 'split', False,
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   951
      _("record a split (on precursor, multiple successors)")),
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   952
     ('B', 'bookmark', [], _("remove revs only reachable from given"
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   953
                             " bookmark"))] + metadataopts,
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   954
    _('[OPTION] [-r] REV...'))
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   955
# XXX -U  --noupdate option to prevent wc update and or bookmarks update ?
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   956
def cmdprune(ui, repo, *revs, **opts):
3989
b60113460856 prune: improve help first line
Dan Villiom Podlaski Christiansen <dan@magenta.dk>
parents: 3988
diff changeset
   957
    """mark changesets as obsolete or succeeded by another changeset
2766
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   958
3990
566fe891f1ec prune: more human-friendly documentation
Dan Villiom Podlaski Christiansen <dan@magenta.dk>
parents: 3989
diff changeset
   959
    Pruning changesets marks them obsolete, hiding them from the
566fe891f1ec prune: more human-friendly documentation
Dan Villiom Podlaski Christiansen <dan@magenta.dk>
parents: 3989
diff changeset
   960
    history log, provided they have no descendants. Otherwise, all
566fe891f1ec prune: more human-friendly documentation
Dan Villiom Podlaski Christiansen <dan@magenta.dk>
parents: 3989
diff changeset
   961
    such descendants that aren't themselves obsolete become
566fe891f1ec prune: more human-friendly documentation
Dan Villiom Podlaski Christiansen <dan@magenta.dk>
parents: 3989
diff changeset
   962
    "unstable". Use :hg:`evolve` to handle this situation.
2766
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   963
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   964
    When you prune the parent of your working copy, Mercurial updates the working
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   965
    copy to a non-obsolete parent.
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   966
3984
33f795a17622 prune: use ``-s/--succ`` in documentation
Dan Villiom Podlaski Christiansen <dan@magenta.dk>
parents: 3877
diff changeset
   967
    You can use ``-s/--succ`` to tell Mercurial that a newer version (successor) of the
2766
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   968
    pruned changeset exists. Mercurial records successor revisions in obsolescence
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   969
    markers.
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   970
3988
3e4fbda6bdce prune: try to clarify the "multi" revisions case
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3987
diff changeset
   971
    If you prune a single revision and specify multiple revisions in
3e4fbda6bdce prune: try to clarify the "multi" revisions case
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3987
diff changeset
   972
    ``-s/--succ``, you are recording a "split" and must acknowledge it by
3e4fbda6bdce prune: try to clarify the "multi" revisions case
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3987
diff changeset
   973
    passing ``--split``. Similarly, when you prune multiple changesets with a
3e4fbda6bdce prune: try to clarify the "multi" revisions case
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3987
diff changeset
   974
    single successor, you must pass the ``--fold`` option.
3987
b802003ffb50 prune: move help about biject after the one about split and fold
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3986
diff changeset
   975
3988
3e4fbda6bdce prune: try to clarify the "multi" revisions case
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3987
diff changeset
   976
    If you want to supersede multiple revisions at the same time, use
4045
821e4be40c6c prune: replace --biject with --pair
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3990
diff changeset
   977
    ``--pair`` option to pair the pruned precursor and successor changesets.
3988
3e4fbda6bdce prune: try to clarify the "multi" revisions case
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3987
diff changeset
   978
    This is commonly useful for resolving history divergence, or when someone
3e4fbda6bdce prune: try to clarify the "multi" revisions case
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3987
diff changeset
   979
    else does edits history without obsolescence enabled.
2766
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   980
    """
3283
039c4b8dc3ed obsnote: warn if user try to store a note in obsmarker on an older hg
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3271
diff changeset
   981
    _checknotesize(ui, opts)
2766
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   982
    revs = scmutil.revrange(repo, list(revs) + opts.get('rev'))
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   983
    succs = opts['new'] + opts['succ']
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   984
    bookmarks = set(opts.get('bookmark'))
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   985
    metadata = _getmetadata(**opts)
4045
821e4be40c6c prune: replace --biject with --pair
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3990
diff changeset
   986
    biject = opts.get('pair') or opts.get('biject')
2766
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   987
    fold = opts.get('fold')
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   988
    split = opts.get('split')
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   989
4045
821e4be40c6c prune: replace --biject with --pair
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3990
diff changeset
   990
    options = [o for o in ('pair', 'fold', 'split') if opts.get(o)]
2766
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   991
    if 1 < len(options):
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   992
        raise error.Abort(_("can only specify one of %s") % ', '.join(options))
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   993
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   994
    if bookmarks:
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   995
        reachablefrombookmark = rewriteutil.reachablefrombookmark
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   996
        repomarks, revs = reachablefrombookmark(repo, revs, bookmarks)
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   997
        if not revs:
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   998
            # no revisions to prune - delete bookmark immediately
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
   999
            rewriteutil.deletebookmark(repo, repomarks, bookmarks)
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1000
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1001
    if not revs:
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1002
        raise error.Abort(_('nothing to prune'))
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1003
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1004
    wlock = lock = tr = None
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1005
    try:
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1006
        wlock = repo.wlock()
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1007
        lock = repo.lock()
2789
06ee4ec88190 prune: use precheck to validate revision
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2788
diff changeset
  1008
        rewriteutil.precheck(repo, revs, 'touch')
2766
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1009
        tr = repo.transaction('prune')
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1010
        # defines pruned changesets
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1011
        precs = []
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1012
        revs.sort()
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1013
        for p in revs:
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1014
            cp = repo[p]
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1015
            precs.append(cp)
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1016
        if not precs:
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1017
            raise error.Abort('nothing to prune')
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1018
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1019
        # defines successors changesets
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1020
        sucs = scmutil.revrange(repo, succs)
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1021
        sucs.sort()
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1022
        sucs = tuple(repo[n] for n in sucs)
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1023
        if not biject and len(sucs) > 1 and len(precs) > 1:
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1024
            msg = "Can't use multiple successors for multiple precursors"
4045
821e4be40c6c prune: replace --biject with --pair
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3990
diff changeset
  1025
            hint = _("use --pair to mark a series as a replacement"
2766
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1026
                     " for another")
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1027
            raise error.Abort(msg, hint=hint)
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1028
        elif biject and len(sucs) != len(precs):
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1029
            msg = "Can't use %d successors for %d precursors" \
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1030
                % (len(sucs), len(precs))
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1031
            raise error.Abort(msg)
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1032
        elif (len(precs) == 1 and len(sucs) > 1) and not split:
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1033
            msg = "please add --split if you want to do a split"
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1034
            raise error.Abort(msg)
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1035
        elif len(sucs) == 1 and len(precs) > 1 and not fold:
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1036
            msg = "please add --fold if you want to do a fold"
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1037
            raise error.Abort(msg)
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1038
        elif biject:
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1039
            relations = [(p, (s,)) for p, s in zip(precs, sucs)]
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1040
        else:
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1041
            relations = [(p, sucs) for p in precs]
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1042
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1043
        wdp = repo['.']
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1044
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1045
        if len(sucs) == 1 and len(precs) == 1 and wdp in precs:
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1046
            # '.' killed, so update to the successor
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1047
            newnode = sucs[0]
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1048
        else:
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1049
            # update to an unkilled parent
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1050
            newnode = wdp
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1051
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1052
            while newnode in precs or newnode.obsolete():
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1053
                newnode = newnode.parents()[0]
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1054
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1055
        if newnode.node() != wdp.node():
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1056
            if opts.get('keep', False):
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1057
                # This is largely the same as the implementation in
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1058
                # strip.stripcmd(). We might want to refactor this somewhere
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1059
                # common at some point.
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1060
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1061
                # only reset the dirstate for files that would actually change
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1062
                # between the working context and uctx
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1063
                descendantrevs = repo.revs("%d::." % newnode.rev())
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1064
                changedfiles = []
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1065
                for rev in descendantrevs:
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1066
                    # blindly reset the files, regardless of what actually
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1067
                    # changed
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1068
                    changedfiles.extend(repo[rev].files())
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1069
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1070
                # reset files that only changed in the dirstate too
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1071
                dirstate = repo.dirstate
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1072
                dirchanges = [f for f in dirstate if dirstate[f] != 'n']
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1073
                changedfiles.extend(dirchanges)
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1074
                repo.dirstate.rebuild(newnode.node(), newnode.manifest(),
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1075
                                      changedfiles)
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1076
                dirstate.write(tr)
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1077
            else:
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1078
                bookactive = repo._activebookmark
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1079
                # Active bookmark that we don't want to delete (with -B option)
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1080
                # we deactivate and move it before the update and reactivate it
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1081
                # after
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1082
                movebookmark = bookactive and not bookmarks
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1083
                if movebookmark:
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1084
                    bookmarksmod.deactivate(repo)
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1085
                    bmchanges = [(bookactive, newnode.node())]
3699
67d6cc7e0979 compat: drop compatibility layer for bookmark.applychanges
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3697
diff changeset
  1086
                    repo._bookmarks.applychanges(repo, tr, bmchanges)
3751
a1a0cfbffd30 evolve: pass revisions as strings to commands.*()
Martin von Zweigbergk <martinvonz@google.com>
parents: 3744
diff changeset
  1087
                commands.update(ui, repo, newnode.hex())
2766
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1088
                ui.status(_('working directory now at %s\n')
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1089
                          % ui.label(str(newnode), 'evolve.node'))
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1090
                if movebookmark:
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1091
                    bookmarksmod.activate(repo, bookactive)
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1092
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1093
        # update bookmarks
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1094
        if bookmarks:
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1095
            rewriteutil.deletebookmark(repo, repomarks, bookmarks)
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1096
3217
b6ba296532cb prune: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3216
diff changeset
  1097
        # store note in metadata
b6ba296532cb prune: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3216
diff changeset
  1098
        if opts.get('note'):
b6ba296532cb prune: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3216
diff changeset
  1099
            metadata['note'] = opts['note']
b6ba296532cb prune: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3216
diff changeset
  1100
2766
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1101
        # create markers
3694
c0d5e0929f8b compat: from compatibility layer for createmarkers
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3675
diff changeset
  1102
        obsolete.createmarkers(repo, relations, metadata=metadata,
c0d5e0929f8b compat: from compatibility layer for createmarkers
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3675
diff changeset
  1103
                               operation="prune")
2766
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1104
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1105
        # informs that changeset have been pruned
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1106
        ui.status(_('%i changesets pruned\n') % len(precs))
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1107
3506
6b4272bbb65d evolve: update code for not implicitly converting ctx to revision
Boris Feld <boris.feld@octobus.net>
parents: 3484
diff changeset
  1108
        precrevs = (precursor.rev() for precursor in precs)
6b4272bbb65d evolve: update code for not implicitly converting ctx to revision
Boris Feld <boris.feld@octobus.net>
parents: 3484
diff changeset
  1109
        for ctx in repo.unfiltered().set('bookmark() and %ld', precrevs):
2766
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1110
            # used to be:
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1111
            #
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1112
            #   ldest = list(repo.set('max((::%d) - obsolete())', ctx))
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1113
            #   if ldest:
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1114
            #      c = ldest[0]
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1115
            #
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1116
            # but then revset took a lazy arrow in the knee and became much
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1117
            # slower. The new forms makes as much sense and a much faster.
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1118
            for dest in ctx.ancestors():
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1119
                if not dest.obsolete():
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1120
                    bookmarksupdater = rewriteutil.bookmarksupdater
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1121
                    updatebookmarks = bookmarksupdater(repo, ctx.node(), tr)
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1122
                    updatebookmarks(dest.node())
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1123
                    break
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1124
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1125
        tr.close()
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1126
    finally:
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1127
        lockmod.release(tr, lock, wlock)
83ad13719e26 commands: move 'prune' to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2763
diff changeset
  1128
2762
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1129
@eh.command(
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1130
    '^split',
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1131
    [('r', 'rev', [], _("revision to split")),
3216
13cb0810ce22 split: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3215
diff changeset
  1132
     ('n', 'note', '', _("store a note on split")),
2771
6044bd16bfb7 split: add support for the -D and -U option
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2770
diff changeset
  1133
    ] + commitopts + commitopts2 + commitopts3,
2762
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1134
    _('hg split [OPTION]... [-r] REV'))
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1135
def cmdsplit(ui, repo, *revs, **opts):
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1136
    """split a changeset into smaller changesets
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1137
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1138
    By default, split the current revision by prompting for all its hunks to be
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1139
    redistributed into new changesets.
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1140
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1141
    Use --rev to split a given changeset instead.
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1142
    """
3283
039c4b8dc3ed obsnote: warn if user try to store a note in obsmarker on an older hg
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3271
diff changeset
  1143
    _checknotesize(ui, opts)
2771
6044bd16bfb7 split: add support for the -D and -U option
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2770
diff changeset
  1144
    _resolveoptions(ui, opts)
2762
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1145
    tr = wlock = lock = None
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1146
    newcommits = []
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1147
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1148
    revarg = (list(revs) + opts.get('rev')) or ['.']
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1149
    if len(revarg) != 1:
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1150
        msg = _("more than one revset is given")
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1151
        hnt = _("use either `hg split <rs>` or `hg split --rev <rs>`, not both")
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1152
        raise error.Abort(msg, hint=hnt)
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1153
3270
e6150b9b88d9 split: force the branch to fix the split bug
Boris Feld <boris.feld@octobus.net>
parents: 3233
diff changeset
  1154
    # Save the current branch to restore it in the end
e6150b9b88d9 split: force the branch to fix the split bug
Boris Feld <boris.feld@octobus.net>
parents: 3233
diff changeset
  1155
    savedbranch = repo.dirstate.branch()
e6150b9b88d9 split: force the branch to fix the split bug
Boris Feld <boris.feld@octobus.net>
parents: 3233
diff changeset
  1156
2762
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1157
    try:
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1158
        wlock = repo.wlock()
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1159
        lock = repo.lock()
3506
6b4272bbb65d evolve: update code for not implicitly converting ctx to revision
Boris Feld <boris.feld@octobus.net>
parents: 3484
diff changeset
  1160
        ctx = scmutil.revsingle(repo, revarg[0])
6b4272bbb65d evolve: update code for not implicitly converting ctx to revision
Boris Feld <boris.feld@octobus.net>
parents: 3484
diff changeset
  1161
        rev = ctx.rev()
2762
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1162
        cmdutil.bailifchanged(repo)
2786
ae690d39fc92 split: use precheck to validate revision
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2774
diff changeset
  1163
        rewriteutil.precheck(repo, [rev], action='split')
2762
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1164
        tr = repo.transaction('split')
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1165
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1166
        if len(ctx.parents()) > 1:
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1167
            raise error.Abort(_("cannot split merge commits"))
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1168
        prev = ctx.p1()
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1169
        bmupdate = rewriteutil.bookmarksupdater(repo, ctx.node(), tr)
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1170
        bookactive = repo._activebookmark
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1171
        if bookactive is not None:
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1172
            repo.ui.status(_("(leaving bookmark %s)\n") % repo._activebookmark)
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1173
        bookmarksmod.deactivate(repo)
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1174
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1175
        # Prepare the working directory
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1176
        rewriteutil.presplitupdate(repo, ui, prev, ctx)
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1177
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1178
        def haschanges():
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1179
            modified, added, removed, deleted = repo.status()[:4]
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1180
            return modified or added or removed or deleted
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1181
        msg = ("HG: This is the original pre-split commit message. "
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1182
               "Edit it as appropriate.\n\n")
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1183
        msg += ctx.description()
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1184
        opts['message'] = msg
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1185
        opts['edit'] = True
2770
a9ea16a1f4dc split: fix the --user option
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2769
diff changeset
  1186
        if not opts['user']:
a9ea16a1f4dc split: fix the --user option
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2769
diff changeset
  1187
            opts['user'] = ctx.user()
3270
e6150b9b88d9 split: force the branch to fix the split bug
Boris Feld <boris.feld@octobus.net>
parents: 3233
diff changeset
  1188
e6150b9b88d9 split: force the branch to fix the split bug
Boris Feld <boris.feld@octobus.net>
parents: 3233
diff changeset
  1189
        # Set the right branch
e6150b9b88d9 split: force the branch to fix the split bug
Boris Feld <boris.feld@octobus.net>
parents: 3233
diff changeset
  1190
        # XXX-TODO: Find a way to set the branch without altering the dirstate
e6150b9b88d9 split: force the branch to fix the split bug
Boris Feld <boris.feld@octobus.net>
parents: 3233
diff changeset
  1191
        repo.dirstate.setbranch(ctx.branch())
e6150b9b88d9 split: force the branch to fix the split bug
Boris Feld <boris.feld@octobus.net>
parents: 3233
diff changeset
  1192
2762
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1193
        while haschanges():
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1194
            pats = ()
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1195
            cmdutil.dorecord(ui, repo, commands.commit, 'commit', False,
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1196
                             cmdutil.recordfilter, *pats, **opts)
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1197
            # TODO: Does no seem like the best way to do this
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1198
            # We should make dorecord return the newly created commit
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1199
            newcommits.append(repo['.'])
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1200
            if haschanges():
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1201
                if ui.prompt('Done splitting? [yN]', default='n') == 'y':
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1202
                    commands.commit(ui, repo, **opts)
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1203
                    newcommits.append(repo['.'])
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1204
                    break
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1205
            else:
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1206
                ui.status(_("no more change to split\n"))
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1207
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1208
        if newcommits:
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1209
            tip = repo[newcommits[-1]]
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1210
            bmupdate(tip.node())
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1211
            if bookactive is not None:
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1212
                bookmarksmod.activate(repo, bookactive)
3216
13cb0810ce22 split: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3215
diff changeset
  1213
            metadata = {}
13cb0810ce22 split: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3215
diff changeset
  1214
            if opts.get('note'):
13cb0810ce22 split: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3215
diff changeset
  1215
                metadata['note'] = opts['note']
3694
c0d5e0929f8b compat: from compatibility layer for createmarkers
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3675
diff changeset
  1216
            obsolete.createmarkers(repo, [(repo[rev], newcommits)],
c0d5e0929f8b compat: from compatibility layer for createmarkers
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3675
diff changeset
  1217
                                   metadata=metadata, operation="split")
2762
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1218
        tr.close()
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1219
    finally:
3270
e6150b9b88d9 split: force the branch to fix the split bug
Boris Feld <boris.feld@octobus.net>
parents: 3233
diff changeset
  1220
        # Restore the old branch
e6150b9b88d9 split: force the branch to fix the split bug
Boris Feld <boris.feld@octobus.net>
parents: 3233
diff changeset
  1221
        repo.dirstate.setbranch(savedbranch)
e6150b9b88d9 split: force the branch to fix the split bug
Boris Feld <boris.feld@octobus.net>
parents: 3233
diff changeset
  1222
2762
610581a2fb74 commands: move split to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2761
diff changeset
  1223
        lockmod.release(tr, lock, wlock)
2763
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1224
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1225
@eh.command(
3229
63f6f9db9c3a help: remove a few commands from `hg` (no args) command list
Kyle Lippincott <spectral@google.com>
parents: 2949
diff changeset
  1226
    'touch',
2763
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1227
    [('r', 'rev', [], 'revision to update'),
3215
175b524b9a2b touch: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3213
diff changeset
  1228
     ('n', 'note', '', _('store a note on touch')),
2763
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1229
     ('D', 'duplicate', False,
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1230
      'do not mark the new revision as successor of the old one'),
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1231
     ('A', 'allowdivergence', False,
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1232
      'mark the new revision as successor of the old one potentially creating '
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1233
      'divergence')],
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1234
    # allow to choose the seed ?
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1235
    _('[-r] revs'))
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1236
def touch(ui, repo, *revs, **opts):
3233
bd01eb0108f4 touch: shorten touch's docstring to make it fit into a one line
Denis Laxalde <denis@laxalde.org>
parents: 3231
diff changeset
  1237
    """create successors identical to their predecessors but the changeset ID
2763
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1238
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1239
    This is used to "resurrect" changesets
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1240
    """
3283
039c4b8dc3ed obsnote: warn if user try to store a note in obsmarker on an older hg
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3271
diff changeset
  1241
    _checknotesize(ui, opts)
2763
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1242
    duplicate = opts['duplicate']
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1243
    allowdivergence = opts['allowdivergence']
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1244
    revs = list(revs)
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1245
    revs.extend(opts['rev'])
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1246
    if not revs:
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1247
        revs = ['.']
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1248
    revs = scmutil.revrange(repo, revs)
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1249
    if not revs:
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1250
        ui.write_err('no revision to touch\n')
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1251
        return 1
2790
1b7b9acda2a9 touch: use precheck to validate revision
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2789
diff changeset
  1252
    if not duplicate:
1b7b9acda2a9 touch: use precheck to validate revision
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2789
diff changeset
  1253
        rewriteutil.precheck(repo, revs, touch)
2763
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1254
    tmpl = utility.shorttemplate
3483
f03845bfd015 compat: add wrapper for logcmdutil functions
Yuya Nishihara <yuya@tcha.org>
parents: 3452
diff changeset
  1255
    displayer = compat.changesetdisplayer(ui, repo, {'template': tmpl})
2763
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1256
    wlock = lock = tr = None
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1257
    try:
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1258
        wlock = repo.wlock()
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1259
        lock = repo.lock()
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1260
        tr = repo.transaction('touch')
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1261
        revs.sort() # ensure parent are run first
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1262
        newmapping = {}
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1263
        for r in revs:
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1264
            ctx = repo[r]
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1265
            extra = ctx.extra().copy()
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1266
            extra['__touch-noise__'] = random.randint(0, 0xffffffff)
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1267
            # search for touched parent
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1268
            p1 = ctx.p1().node()
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1269
            p2 = ctx.p2().node()
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1270
            p1 = newmapping.get(p1, p1)
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1271
            p2 = newmapping.get(p2, p2)
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1272
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1273
            if not (duplicate or allowdivergence):
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1274
                # The user hasn't yet decided what to do with the revived
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1275
                # cset, let's ask
3697
6aff4bb3970d compat: drop compatibility layer for successorssets
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3694
diff changeset
  1276
                sset = obsutil.successorssets(repo, ctx.node())
2763
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1277
                nodivergencerisk = (len(sset) == 0 or
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1278
                                    (len(sset) == 1 and
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1279
                                     len(sset[0]) == 1 and
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1280
                                     repo[sset[0][0]].rev() == ctx.rev()
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1281
                                    ))
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1282
                if nodivergencerisk:
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1283
                    duplicate = False
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1284
                else:
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1285
                    displayer.show(ctx)
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1286
                    index = ui.promptchoice(
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1287
                        _("reviving this changeset will create divergence"
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1288
                          " unless you make a duplicate.\n(a)llow divergence or"
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1289
                          " (d)uplicate the changeset? $$ &Allowdivergence $$ "
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1290
                          "&Duplicate"), 0)
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1291
                    choice = ['allowdivergence', 'duplicate'][index]
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1292
                    if choice == 'allowdivergence':
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1293
                        duplicate = False
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1294
                    else:
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1295
                        duplicate = True
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1296
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1297
            extradict = {'extra': extra}
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1298
            new, unusedvariable = rewriteutil.rewrite(repo, ctx, [], ctx,
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1299
                                                      [p1, p2],
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1300
                                                      commitopts=extradict)
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1301
            # store touched version to help potential children
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1302
            newmapping[ctx.node()] = new
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1303
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1304
            if not duplicate:
3215
175b524b9a2b touch: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3213
diff changeset
  1305
                metadata = {}
175b524b9a2b touch: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3213
diff changeset
  1306
                if opts.get('note'):
175b524b9a2b touch: add support for storing a note in obsmarker
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3213
diff changeset
  1307
                    metadata['note'] = opts['note']
3694
c0d5e0929f8b compat: from compatibility layer for createmarkers
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3675
diff changeset
  1308
                obsolete.createmarkers(repo, [(ctx, (repo[new],))],
c0d5e0929f8b compat: from compatibility layer for createmarkers
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3675
diff changeset
  1309
                                       metadata=metadata, operation="touch")
2763
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1310
            phases.retractboundary(repo, tr, ctx.phase(), [new])
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1311
            if ctx in repo[None].parents():
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1312
                with repo.dirstate.parentchange():
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1313
                    repo.dirstate.setparents(new, node.nullid)
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1314
        tr.close()
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1315
    finally:
4a5b0c373e65 commands: move the touch to the 'evocommands' module
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 2762
diff changeset
  1316
        lockmod.release(tr, lock, wlock)
3453
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1317
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1318
@eh.command(
4048
d7034826c0a2 pick: rename the grab command to pick
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 4047
diff changeset
  1319
    'pick|grab',
d7034826c0a2 pick: rename the grab command to pick
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 4047
diff changeset
  1320
    [('r', 'rev', '', 'revision to pick'),
d7034826c0a2 pick: rename the grab command to pick
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 4047
diff changeset
  1321
     ('c', 'continue', False, 'continue interrupted pick'),
d7034826c0a2 pick: rename the grab command to pick
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 4047
diff changeset
  1322
     ('a', 'abort', False, 'abort interrupted pick'),
3453
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1323
    ],
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1324
    _('[-r] rev'))
4048
d7034826c0a2 pick: rename the grab command to pick
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 4047
diff changeset
  1325
def cmdpick(ui, repo, *revs, **opts):
3453
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1326
    """grabs a commit, move it on the top of working directory parent and
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1327
    updates to it."""
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1328
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1329
    cont = opts.get('continue')
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1330
    abort = opts.get('abort')
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1331
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1332
    if cont and abort:
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1333
        raise error.Abort(_("cannot specify both --continue and --abort"))
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1334
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1335
    revs = list(revs)
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1336
    if opts.get('rev'):
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1337
        revs.append(opts['rev'])
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1338
4050
3dddb03f3559 pick: use "pick" instead of "grab" for various internal API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 4049
diff changeset
  1339
    with repo.wlock(), repo.lock(), repo.transaction('pick'):
3457
82e9f9603b1b evolvestate: rename the file to state.py and class name to cmdstate
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3456
diff changeset
  1340
        grabstate = state.cmdstate(repo, path='grabstate')
3526
df20ddc79064 grab: move the initialization of pctx variable outside of if-else
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3522
diff changeset
  1341
        pctx = repo['.']
3453
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1342
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1343
        if not cont and not abort:
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1344
            cmdutil.bailifchanged(repo)
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1345
            revs = scmutil.revrange(repo, revs)
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1346
            if len(revs) > 1:
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1347
                raise error.Abort(_("specify just one revision"))
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1348
            elif not revs:
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1349
                raise error.Abort(_("empty revision set"))
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1350
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1351
            origctx = repo[revs.first()]
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1352
3527
7b4d1bfb6b7d grab: gracefully handle the case when we try to grab parent of wdir
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3526
diff changeset
  1353
            if origctx in pctx.ancestors() or origctx.node() == pctx.node():
4049
25981fae92f9 pick: update command output to mention pick instead of grab
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 4048
diff changeset
  1354
                raise error.Abort(_("cannot pick an ancestor revision"))
3453
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1355
4049
25981fae92f9 pick: update command output to mention pick instead of grab
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 4048
diff changeset
  1356
            rewriteutil.precheck(repo, [origctx.rev()], 'pick')
3453
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1357
4049
25981fae92f9 pick: update command output to mention pick instead of grab
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 4048
diff changeset
  1358
            ui.status(_('picking %d:%s "%s"\n') %
3453
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1359
                      (origctx.rev(), origctx,
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1360
                       origctx.description().split("\n", 1)[0]))
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1361
            stats = merge.graft(repo, origctx, origctx.p1(), ['local',
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1362
                                                              'destination'])
3616
f6d629514607 compat: use updateresult API if available
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 3569
diff changeset
  1363
            if compat.hasconflict(stats):
3457
82e9f9603b1b evolvestate: rename the file to state.py and class name to cmdstate
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3456
diff changeset
  1364
                grabstate.addopts({'orignode': origctx.node(),
82e9f9603b1b evolvestate: rename the file to state.py and class name to cmdstate
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3456
diff changeset
  1365
                                   'oldpctx': pctx.node()})
82e9f9603b1b evolvestate: rename the file to state.py and class name to cmdstate
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3456
diff changeset
  1366
                grabstate.save()
3453
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1367
                raise error.InterventionRequired(_("unresolved merge conflicts"
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1368
                                                   " (see hg help resolve)"))
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1369
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1370
        elif abort:
3457
82e9f9603b1b evolvestate: rename the file to state.py and class name to cmdstate
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3456
diff changeset
  1371
            if not grabstate:
4049
25981fae92f9 pick: update command output to mention pick instead of grab
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 4048
diff changeset
  1372
                raise error.Abort(_("no interrupted pick state exists"))
3457
82e9f9603b1b evolvestate: rename the file to state.py and class name to cmdstate
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3456
diff changeset
  1373
            grabstate.load()
82e9f9603b1b evolvestate: rename the file to state.py and class name to cmdstate
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3456
diff changeset
  1374
            pctxnode = grabstate['oldpctx']
4049
25981fae92f9 pick: update command output to mention pick instead of grab
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 4048
diff changeset
  1375
            ui.status(_("aborting pick, updating to %s\n") %
3453
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1376
                      node.hex(pctxnode)[:12])
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1377
            hg.updaterepo(repo, pctxnode, True)
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1378
            return 0
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1379
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1380
        else:
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1381
            if revs:
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1382
                raise error.Abort(_("cannot specify both --continue and "
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1383
                                    "revision"))
3457
82e9f9603b1b evolvestate: rename the file to state.py and class name to cmdstate
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3456
diff changeset
  1384
            if not grabstate:
4049
25981fae92f9 pick: update command output to mention pick instead of grab
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 4048
diff changeset
  1385
                raise error.Abort(_("no interrupted pick state exists"))
3453
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1386
3457
82e9f9603b1b evolvestate: rename the file to state.py and class name to cmdstate
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3456
diff changeset
  1387
            grabstate.load()
82e9f9603b1b evolvestate: rename the file to state.py and class name to cmdstate
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3456
diff changeset
  1388
            orignode = grabstate['orignode']
3453
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1389
            origctx = repo[orignode]
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1390
3475
a03bb02dfaba grab: preserve phase of the grabbed changeset
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3457
diff changeset
  1391
        overrides = {('phases', 'new-commit'): origctx.phase()}
4050
3dddb03f3559 pick: use "pick" instead of "grab" for various internal API
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 4049
diff changeset
  1392
        with repo.ui.configoverride(overrides, 'pick'):
3475
a03bb02dfaba grab: preserve phase of the grabbed changeset
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3457
diff changeset
  1393
            newnode = repo.commit(text=origctx.description(),
a03bb02dfaba grab: preserve phase of the grabbed changeset
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3457
diff changeset
  1394
                                  user=origctx.user(),
a03bb02dfaba grab: preserve phase of the grabbed changeset
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3457
diff changeset
  1395
                                  date=origctx.date(), extra=origctx.extra())
3453
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1396
3457
82e9f9603b1b evolvestate: rename the file to state.py and class name to cmdstate
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3456
diff changeset
  1397
        if grabstate:
82e9f9603b1b evolvestate: rename the file to state.py and class name to cmdstate
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3456
diff changeset
  1398
            grabstate.delete()
3569
236d36b17aa4 grab: include "operation" metadata in obsmarkers
Martin von Zweigbergk <martinvonz@google.com>
parents: 3568
diff changeset
  1399
        newctx = repo[newnode] if newnode else pctx
4051
ddae36b4031e pick: use "pick" as operation name in obsolescence markers
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 4050
diff changeset
  1400
        obsolete.createmarkers(repo, [(origctx, (newctx,))], operation="pick")
3453
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1401
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1402
        if newnode is None:
4049
25981fae92f9 pick: update command output to mention pick instead of grab
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 4048
diff changeset
  1403
            ui.warn(_("note: picking %d:%s created no changes to commit\n") %
3453
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1404
                    (origctx.rev(), origctx))
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1405
            return 0
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1406
32ed5b6fadd3 grab: add a command to grab a commit and update to it
Pulkit Goyal <7895pulkit@gmail.com>
parents: 3389
diff changeset
  1407
        return 0