]> git.ipfire.org Git - thirdparty/git.git/commitdiff
Merge branch 'am/stash-branch'
authorJunio C Hamano <gitster@pobox.com>
Sun, 13 Jul 2008 22:16:09 +0000 (15:16 -0700)
committerJunio C Hamano <gitster@pobox.com>
Sun, 13 Jul 2008 22:16:09 +0000 (15:16 -0700)
* am/stash-branch:
  Add a test for "git stash branch"
  Implement "git stash branch <newbranch> <stash>"

1  2 
Documentation/git-stash.txt
git-stash.sh

index e42c5eff4dbc579edc6f65107ecef54fe942847d,a4cbd0ce60e73b4e1ec9ffadfaeee132f7ea054b..7d50d74cc9a945f0dd82b0c26509bf0392eff837
@@@ -8,8 -8,11 +8,11 @@@ git-stash - Stash the changes in a dirt
  SYNOPSIS
  --------
  [verse]
- 'git stash' (list | show [<stash>] | apply [<stash>] | clear | drop [<stash>] | pop [<stash>])
+ 'git stash' list
+ 'git stash' (show | apply | drop | pop ) [<stash>]
+ 'git stash' branch <branchname> [<stash>]
  'git stash' [save [<message>]]
+ 'git stash' clear
  
  DESCRIPTION
  -----------
@@@ -36,15 -39,12 +39,15 @@@ is also possible)
  OPTIONS
  -------
  
 -save [<message>]::
 +save [--keep-index] [<message>]::
  
        Save your local modifications to a new 'stash', and run `git reset
        --hard` to revert them.  This is the default action when no
        subcommand is given. The <message> part is optional and gives
        the description along with the stashed state.
 ++
 +If the `--keep-index` option is used, all changes already added to the
 +index are left intact.
  
  list [<options>]::
  
@@@ -59,7 -59,7 +62,7 @@@ stash@{0}: WIP on submit: 6ebd0e2... Up
  stash@{1}: On master: 9cc0589... Add git-stash
  ----------------------------------------------------------------
  +
 -The command takes options applicable to the `git-log`
 +The command takes options applicable to the 'git-log'
  command to control what is shown and how. See linkgit:git-log[1].
  
  show [<stash>]::
@@@ -67,7 -67,7 +70,7 @@@
        Show the changes recorded in the stash as a diff between the
        stashed state and its original parent. When no `<stash>` is given,
        shows the latest one. By default, the command shows the diffstat, but
 -      it will accept any format known to `git-diff` (e.g., `git stash show
 +      it will accept any format known to 'git-diff' (e.g., `git stash show
        -p stash@\{1}` to view the second most recent stash in patch form).
  
  apply [--index] [<stash>]::
@@@ -84,6 -84,20 +87,20 @@@ tree's changes, but also the index's on
  have conflicts (which are stored in the index, where you therefore can no
  longer apply the changes as they were originally).
  
+ branch <branchname> [<stash>]::
+       Creates and checks out a new branch named `<branchname>` starting from
+       the commit at which the `<stash>` was originally created, applies the
+       changes recorded in `<stash>` to the new working tree and index, then
+       drops the `<stash>` if that completes successfully. When no `<stash>`
+       is given, applies the latest one.
+ +
+ This is useful if the branch on which you ran `git stash save` has
+ changed enough that `git stash apply` fails due to conflicts. Since
+ the stash is applied on top of the commit that was HEAD at the time
+ `git stash` was run, it restores the originally stashed state with
+ no conflicts.
  clear::
        Remove all the stashed states. Note that those states will then
        be subject to pruning, and may be difficult or impossible to recover.
@@@ -161,7 -175,7 +178,7 @@@ $ git reset --soft HEAD
  ... continue hacking ...
  ----------------------------------------------------------------
  +
 -You can use `git-stash` to simplify the above, like this:
 +You can use 'git-stash' to simplify the above, like this:
  +
  ----------------------------------------------------------------
  ... hack hack hack ...
@@@ -172,24 -186,6 +189,24 @@@ $ git stash appl
  ... continue hacking ...
  ----------------------------------------------------------------
  
 +Testing partial commits::
 +
 +You can use `git stash save --keep-index` when you want to make two or
 +more commits out of the changes in the work tree, and you want to test
 +each change before committing:
 ++
 +----------------------------------------------------------------
 +... hack hack hack ...
 +$ git add --patch foo            # add just first part to the index
 +$ git stash save --keep-index    # save all other changes to the stash
 +$ edit/build/test first part
 +$ git commit foo -m 'First part' # commit fully tested change
 +$ git stash pop                  # prepare to work on all other changes
 +... repeat above five steps until one commit remains ...
 +$ edit/build/test remaining parts
 +$ git commit foo -m 'Remaining parts'
 +----------------------------------------------------------------
 +
  SEE ALSO
  --------
  linkgit:git-checkout[1],
diff --combined git-stash.sh
index 92531a2951ea29d3a826ad162e709f8701b14bac,889445c4fc8ce523558644484de559d40229fc01..e4cb6c3e4bef5a714ff245624503a004d3c293e3
@@@ -86,13 -86,6 +86,13 @@@ create_stash () 
  }
  
  save_stash () {
 +      keep_index=
 +      case "$1" in
 +      --keep-index)
 +              keep_index=t
 +              shift
 +      esac
 +
        stash_msg="$1"
  
        if no_changes
        git update-ref -m "$stash_msg" $ref_stash $w_commit ||
                die "Cannot save the current status"
        printf 'Saved working directory and index state "%s"\n' "$stash_msg"
 +
 +      git reset --hard
 +
 +      if test -n "$keep_index" && test -n $i_tree
 +      then
 +              git read-tree --reset -u $i_tree
 +      fi
  }
  
  have_stash () {
@@@ -167,8 -153,7 +167,8 @@@ apply_stash () 
                die "$*: no valid stashed state found"
  
        unstashed_index_tree=
 -      if test -n "$unstash_index" && test "$b_tree" != "$i_tree"
 +      if test -n "$unstash_index" && test "$b_tree" != "$i_tree" &&
 +                      test "$c_tree" != "$i_tree"
        then
                git diff-tree --binary $s^2^..$s^2 | git apply --cached
                test $? -ne 0 &&
@@@ -233,6 -218,23 +233,23 @@@ drop_stash () 
        git rev-parse --verify "$ref_stash@{0}" > /dev/null 2>&1 || clear_stash
  }
  
+ apply_to_branch () {
+       have_stash || die 'Nothing to apply'
+       test -n "$1" || die 'No branch name specified'
+       branch=$1
+       if test -z "$2"
+       then
+               set x "$ref_stash@{0}"
+       fi
+       stash=$2
+       git-checkout -b $branch $stash^ &&
+       apply_stash --index $stash &&
+       drop_stash $stash
+ }
  # Main command set
  case "$1" in
  list)
@@@ -250,7 -252,7 +267,7 @@@ show
        ;;
  save)
        shift
 -      save_stash "$*" && git-reset --hard
 +      save_stash "$*"
        ;;
  apply)
        shift
@@@ -279,11 -281,16 +296,15 @@@ pop
                drop_stash "$@"
        fi
        ;;
+ branch)
+       shift
+       apply_to_branch "$@"
+       ;;
  *)
        if test $# -eq 0
        then
                save_stash &&
 -              echo '(To restore them type "git stash apply")' &&
 -              git-reset --hard
 +              echo '(To restore them type "git stash apply")'
        else
                usage
        fi