Git alias for merging current branch with master

aliasgit

I'm trying to create a git alias that merges the currently checked out branch into the master branch. Specifically I'd want to quickly get my master branch get up to speed with what I'm working on. I've got the following:

[alias]
    co = checkout
    ff = !git co master && git merge work && git co work

However I'd like the alias to know which branch it was on and get back to it. I tried adding $1 but unfortunately I get a error on the last checkout in the alias:

# with
[alias]
    co = checkout
    ff = !git co master && git merge $1 && git co $1

> git ff work
Switched to branch 'master'
Already up-to-date.
error: pathspec 'work' did not match any file(s) known to git.

Anyone knows why it does this? (I'm on a Mac by the way)

Best Answer

If you're going to use positional parameters in git aliases, be sure to specify sh -c. The following worked for me locally:

ff = !sh -c 'git checkout master && git merge "$1" && git checkout "$1"' -

(dead link) The "why" relates to the way git parses the alias commands and is summed up in this gmane thread.

The - at the end of the command signals sh that option processing is finished. From man sh:

A -- signals the end of options and disables further option processing. Any arguments after the -- are treated as filenames and arguments. An argument of - is equivalent to --.

If it weren't present, it would introduce a bug in the alias, by treating $1 as an option on the sh command instead of as a positional argument. Consider this trivial example:

$ sh -c 'echo $1' foo          # equivalent to 'echo' without argument

$ sh -c 'echo $1' - foo        # will pass 'foo' to the string as $1
foo

In the first case, 'foo' was consumed by sh as an option. In the second, it's correctly interpreted as $1 on the string.

Related Question