Useful subversion shell aliases

A friend tossed me a handful of aliases that, once plopped into your shells initialization scripts, make dealing with Subversion all that much more pleasant. It was one of those “Oh, jeez, that is so stupid obvious… why didn’t I think of that” moments.

Drop the aliases into wherever your shell sets up aliases (~/.tcsrhc or ~/bashrc or something like it, typically). The syntax may be different.

alias M         'svn diff \!* | mate'
alias G         'svn diff \!* | mate'
alias U         'svn diff \!* | mate'
alias R         'svn diff'
alias C         'see'
alias A         'true'
alias D         'true'
alias I         'true'

Once in place, you can now triple-click-copy-paste any line in the subversion output to see more detailed information.

Update: I updated the M, G, and U aliases to both use TextMate and to work fine with multiple arguments (just because it seemed like an appropriately big stick to bring to the party).

For example, an ‘svn status’ on my PyObjC work area outputs the following:

[pyobjc/trunk/pyobjc] bbum% svn status
M      Lib/AppKit/test/test_nsopenpanel.py

I simply triple-click the M Lib/AppKit/test/test_nsopenpanel.py and copy/paste/return. Subversion will then display the differences between what is in my workarea and what is currently in the repository.

The third command will cause the conflicted file to open in SubEthaEdit. Change it to mate for TextMate or bbedit for BBEdit.

In ~/.subversion/config, I have:

diff-cmd = /Volumes/Data/Users/bbum/bin/svndiffshim.py

svndiffshim.py lives in my hacques repository. Once in place, it causes diffs to open in FileMerge.

If you don’t want to use FileMerge (or bbdiff), change the two svn diff aliases to clear && svn diff. This will cause the Terminal window to be cleared prior to displaying the output.

Update(s):

Michael McCracken reminded me that I really ought to go look at my application menus a bit more often. Terminal includes Paste Selection (and Paste Escaped Text, another useful idiom I forgot about). So, triple-click, then hit shift-cmd-V to paste the selected line. One less keystroke!

Dominik Wagner mentions that he uses svn diff | see -m diff to cause the diff to be opened and nicely colorized in SubEthaEdit. Very nice.

As an improvement in the above context, I aliased it to svn diff \!* | see -m diff as that fixes two problems. First, it only diffs the file copy/pasted. Secondly, it doesn’t also open the file(s).

Of course, all of this now means that M is an super-tiny abbreviation for Diff This Stuff Now.

Wilfredo Sánchez Vega added the true aliases as seen above. It allows you to copy/paste in a large chunk of the output without having to worry about silly syntax errors. Of course, there are still a number of edge cases — if the other columns are used or ‘?’ in the output — but this makes it much more generic.



24 Responses to “Useful subversion shell aliases”

  1. Red Sweater Links » Blog Archive » Tricky SVN Aliases says:

    […] Bill Bumgarner gets creative with shell aliases that cause svn’s status lines to be independently executable commands. One can’t help but be reminded of the old MPW days. Link. […]

  2. Michael McCracken says:

    Nice tip!
    You probably already know this, but since you wrote “Copy/Paste/Return” and we are talking about shaving steps, don’t forget that in Terminal.app, Shift-Cmd-V lets you skip the “Copy” step – it just pastes the current selection.

  3. Dominik Wagner says:

    Great aliases. On a sidenote: do an “svn diff | see -m diff” to get a nicely colored diff in subethaedit (since 2.3) – i myself aliased that to svndiff. 

  4. Dominik Wagner says:

    oh – and i forgot my svnadd alias: svnadd – really helpful to easily add files not yet added.

  5. Ben Holt says:

    While we’re swapping fancy svn aliases, here’s my handy finger-pointing alias/function (bash-version)


    # Usage: blameline
    alias blameline='SvnBlameLine'
    SvnBlameLine() {
    svn blame "$1" | cat -n | egrep --context=3 "^[[:space:]]*$2\b"
    }

    Still need to make it (efficiently, i.e. not do the ‘svn blame’ twice) parse out the revision number of the line in question and automatically follow up with an ‘svn log -r123’, as I almost always want that.

  6. John C. Randolph says:

    On a somewhat related note, I find that few people are aware of /usr/bin/pbcopy and /usr/bin/pbpaste. Check their man pages, they’re quite handy.

    -jcr

  7. Dominik Wagner says:

    Ok, one final note – I just added this to my .bash_profile
    function M() {
    svn diff $* | see -m diff -t “diff: $*”
    }

    which shows what is diffed nicely in the title.

    cheers,
    dom

  8. Benjamin Stiglitz says:

    Bill, even better than Shift-Cmd-V is the middle-click, if you have it. We cloned that xterm feature in Terminal after so many people asked for it.

  9. Jack says:

    Good stuff, folks!

    What I really want is colorized svn output (e.g. a line reporting a conflict shows up in red, etc). I swear that some version of cvs I ran at some point in the past had this built-in, but AFAICT there’s no such thing in svn. Could be handled by a wrapper somehow I suppose. Any ideas?

  10. Jack says:

    Oops… errr, hooray for google! Here’s what I was after:

    http://webcvs.kde.org/kdesdk/scripts/colorsvn?rev=1.2&view=auto

  11. David Steinbrunner says:

    Here is my svn diffing tcsh alias
    alias svndiff ‘/opt/local/bin/svn diff –diff-cmd twdiff \!*’

    Use it just like svn diff but get bbedit/textwangler diff view. I’m just it could be used with mate or see, also.

  12. Steve Israelson says:

    What I don’t get is WHY I need to go into terminal at all? Why doesn’t XCode hide all this mess from me completely?
    I whish there was a published API in XCode where we could add our OWN version control stuff, because I would fix the subversion stuff in there promptly. Maybe I will look at the XCode docs — they may have slipped just that in there somewhere…

  13. bbum says:

    Xcode’s subversion support could certainly use some improvement, no doubt about it.

    But there will always be a need to go to something outside of Xcode to deal with revision control. Repositories span much more than just Xcode/Eclipse/DevStudio projects — there are many, many things that may be found well outside the project.

  14. Brad Henry says:

    Second to middle-click approach is the triple-click then click-drag-drop.

  15. Elliott Hughes says:

    I always knew we were doing a poor job of advertising SCM (a GPL front-end to various revision control systems)! You’ve prompted me to write Why you should use jessies.org SCM tools.

  16. bbum says:

    Except that SCM appears to be far from ready for prime time. A quick perusal reveals that the stuff shipped in the tarball linked to from that site is hardwired to paths that only exist on the developer’s machine.

    Looks interesting. Needs some cleanup before it is useful (to me). I look forward to checking it out.

  17. Elliott Hughes says:

    > A quick perusal reveals that the stuff shipped in the tarball linked to from that site is hardwired to paths that only exist on the developer’s machine.

    that shouldn’t be the case. plenty of other people are using it, on Linux, Mac OS, and Windows, and with BitKeeper, CVS, and Subversion. (i don’t know of anyone seriously using the Bazaar back-end yet.)

    could you report your problems to the email address in the README file, please? (or to the address i gave when entering this, which i assume you can see.)

    we do have a *long* way to go to be a typical .app-in-a-.dmg Mac OS experience — it’s not obvious how we’d fit that model, and we hate .pkg packages to the extent that we never install them ourselves, so don’t expect others to. but for anyone prepared and able to build from source and put the bin/ directory on their path, we should “just work”. if we don’t, i’d like to fix it.

    (sorry for the delay; a user just pointed me at this. blog comments are such an impractical way to hold a conversation!)

  18. Chris Pepper says:

    Don’t forget the official BBEdit way to do this http://www.barebones.com/support/bbedit/arch_bbedit81.shtml. I added:

    [helpers]
    editor = edit.sh
    diff-cmd = bbdiff
    extensions = --wait --resume
    

    to ~/.subversion/config, and can now svn diff (with or without arguments) to get BBEdit to DWIM.

    Additionally, I tweaked my profile and created a helper script for programs which reject arguments (spaces) in EDITOR:

    pepper@pepperbook:~$ grep -C3 PAGER bin/profile.sh
      if [ -x ~/bin/edit.sh ]
      then
        export EDITOR=~/bin/edit.sh
        export PAGER="col -b | bbedit --clean --view-top"
      else export EDITOR=vi
      fi # [ -x ~/bin/edit.sh ]
    
    pepper@pepperbook:~$ cat bin/edit.sh 
    #!/bin/sh
    # Edit a file in BBEdit (if available), for programs that don't support arguments in $EDITOR.
    if [[ $SSH_TTY ]]
    then # Remote
      vi "$@"
    else # Local
      bbedit --wait --resume "$@"
    fi
    

    Now svn ci, crontab, man, etc. all use BBEdit when available, or vi when I’m logged in through a text-only connection (ssh).

    Edit: bbum moved some tags around to make it more readable in the context of my rather stupid CSS.

  19. onwalking.org » Blog Archive » links for 2006-06-28 says:

    […] bbum’s weblog-o-mat » Blog Archive » Useful subversion shell aliases a handful of aliases that, once plopped into your shells initialization scripts, make dealing with Subversion all that much more pleasant. (tags: Subversion svn terminal bash command line version control tool tips unix) […]

  20. schwuk.com : Useful subversion bash functions says:

    […] Inspired by bbum’s Useful subversion shell aliases I decided to to try them out for myself. Of course nothing is ever easy and they needed to be converted from aliases to functions to work under bash, as bash doesn’t support passing arguments according to Google. […]

  21. Chris Pepper says:

    Some improved aliases for use with BBEdit:

    alias A=’bbedit’
    alias AM=’svn diff –diff-cmd bbdiff –extensions “–resume –wait”‘
    alias C=’bbedit’
    alias D=’true’
    alias G=’svn diff –diff-cmd bbdiff –extensions “–resume –wait”‘
    alias I=’true’
    alias M=’svn diff –diff-cmd bbdiff –extensions “–resume –wait”‘
    alias R=’svn diff –diff-cmd bbdiff –extensions “–resume –wait”‘
    alias U=’bbedit’

    This week I’m reviewing the total changes over about 50 revisions, when I wasn’t keeping up with my collaborator. I added ” -r848″ (the version I was caught up, before he started making changes I want to review) to the M & AM aliases, and I can now paste in a few lines from the “svn update” output to review changes one file at a time.

    Note that the “--wait” is necessary, as otherwise successive diffs overwrite the .tmp file BBEdit compares against, and earlier comparisons break.

  22. Chris Pepper says:

    Der! ‘AM’ is equivalent to ‘A’ for this purpose, not to ‘M’.

  23. Extra Pepperoni » BBEdit and Subversion: the Fruit Roll-up Post says:

    […] I use vi daily, but much prefer BBEdit. The way I integrate them has evolved over time (see previous posts here, Useful subversion shell aliases, and BBEdit Gems (which appears to be down right now). In particular, I no longer configure BBEdit directly in ~/.subversion/config. […]

  24. Quinn Taylor says:

    @Ben Holt

    Thanks for posting your blame alias, it’s a handy idea! I tweaked it a bit, and though I haven’t added the svn log functionality, I have made it work with 0 or more line number arguments (When you don’t supply any, it prints the entire blame output with line numbers.)


    svnblame() {
    if [ $# -lt 1 ]
    then
    echo "Please specify a file to examine for blame data."
    else
    resource="$1"
    blame=$(svn blame "$resource" | cat -n)
    if [ $# -lt 2 ]
    then
    echo "$blame"
    else
    shift
    while [ $# -ne 0 ]; do
    echo "=== "$resource":"$1
    echo "$blame" | egrep --context=3 "^[[:space:]]*$1\b"
    shift
    done
    fi
    fi
    }

Leave a Reply

Line and paragraph breaks automatic.
XHTML allowed: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <s> <strike> <strong>