Git for Windows tip: Use P4Merge as mergetool

I recently found P4Merge (thank you Twitter and Git Immersion) and instantly dropped WinMerge as my standard diff/merge tool. I really like the way it visualises the differences and the 3-way merge is really nicely done. P4Merge is the merge tool for Perforce (which I have never used) and is both free and can be downloaded separately from the rest of Perforce.

The download can be found here. Choose Browse by component->Clients->Visual Merge Tool as you do not want to download the whole Perforce client package. In the installer for P4Merge you can choose which components you wish to install, you only need the Visual Merge Tool (P4Merge).

Install p4merge and then set it as your merge tool for git by running the following two config commands:

git config --global merge.tool p4merge
git config --global mergetool.p4merge.cmd 'p4merge.exe \"$BASE\" \"$LOCAL\" \"$REMOTE\" \"$MERGED\"'

EDIT: As pointed out by barik in the comments, in newer versions of git this works as well and is slightly simpler:

git config --global merge.tool p4merge
git config --global mergetool.p4merge.path "C:/Program Files/Perforce/p4merge.exe"

P4Merge can be used for doing diffs and merges. If using P4Merge for diffs then call:

git difftool

If the file you want to compare is already staged then use the –cached switch after that command.

When Git tells you that there has been conflict, to resolve it type:

git mergetool

This will open P4Merge and show three different versions of the file; your local version, the version you are trying to merge in (probably the master branch) and the base version. The base version is the common ancestor of the local version and the remote version. Choose which version wins or edit the merge manually and then save and quit P4Merge. Finally commit the merge and then remove any .orig files that may be left over. It should be possible to have git remove the .orig file automatically by setting mergetool.keepBackup to false in git config but I have not succeeded in getting that to work for me yet.

An example of using P4Merge

And this is what a 3-way merge looks like. The local version on the left, the base version in the middle and the remote version (the master branch) on the right. In the merge window at the bottom all three versions are currently selected. To select the local version, for example, I would click the blue diamond icon and then save and quit.

p4mergeCapture

Git for Windows tip: setting an editor

The first time I tried to do git commit on msysgit with no commit message (no –m switch), it opened up Vim so that I could write my commit message. Luckily for me I’d read enough Vim jokes on Twitter to know that :q or :q! would get me out. But there is no way I’d be able to actually write a commit message, save and quit in Vim (that’d probably take about 3 weeks of studying the documentation). Much easier to change the editor for git to Notepad++ or some other more familiar text editor.

The first step is to create a bat file (I called mine npp.bat) with the path to Notepad++ and the appropriate switches:

#!/bin/sh
"C:/Program Files (x86)/Notepad++/notepad++.exe" -multiInst -notabbar -nosession -noPlugin "$*"

This opens a new instance of Notepad++ with no sessions or tabs or plugins which is what I want when writing a commit message. Place the bat file in the git subdirectory of msysgit (c:\msysgit\git on my system) and then set the core.editor variable in git config:

git config --global core.editor c:/msysgit/git/npp.bat

See this answer on Stackoverflow for more variations on this.

The next step is to get Notepad++ to work from the command line. I want to be able to write:

notepad .bashrc

and Notepad++ should open the .bashrc file. This is actually nothing to do with msysgit and involves replacing the default notepad application with Notepad++ in Windows. And the easiest way is to use a program called Notepad Replacer. Install this and voila, it now works. If you ever want to revert to the default notepad then just uninstall Notepad Replacer.

The other option is create a script file just like the npp.bat file but without the switches and name it npp with no extension and place it in the bin folder. Now I can write:

npp .bashrc

and it opens the file in Notepad++. This approach also works for any third party editor such as Word or Excel.

EDIT: An alternative way to achieve the same result is to install Gitpad to change the default editor to Notepad (or the default text editor).

Posting source code on WordPress.com with Windows Live Writer

The first time I tried to post some code to WordPress.com it took about an hour longer than I thought it would. The first step was learning of the existence of the WordPress sourcecode tag. It took some googling to find this support article on Posting Source Code. It can do different sorts of syntax highlighting based on the language attribute which is pretty nice (although I would prefer Github gists but it’s not an option right now). I was writing a blog post about Ruby and so could use the sourcecode tag to get Ruby syntax highlighting. Unfortunately, I only discovered this after writing my post in Live Writer and trying to publish it. I had used the pre and code html tags and on publishing all code formatting was promptly stripped away.

Another problem that I had was that WordPress and Live Writer interpreted the Ruby symbol, :Debug, as Open-mouthed smileebug. The solution is to turn off the automatic resolution of text emoticons to graphical emoticons (hat-tip to Daniel Persson for that one). In Live Writer this option can be found under Options->Editing->Replace text emoticons with emoticon graphics. And for WordPress.com, Settings->Writing->Formatting->Convert emoticons like :-) and :-P to graphics on display.

And the last step to easily be able to paste in source code into Live Writer, is to use a code formatting plugin. I am trying out the WLW Source Code Highlighter Plugin and it is much easier than switching to the HTML view in WordPress and manually writing out the sourcecode tag and attributes. Recommended if you’re using Windows Live Writer and posting to WordPress.com.

Git for Windows tip: Setting shell aliases with msysgit

As msysgit uses a bash shell, you can set really handy aliases for the different git commands. For example gs instead of git status and ga instead of git add are the ones I use the most. Check out the great Git Immersion tutorial from Edgecase for a list of aliases. I can also recommend creating the got and get aliases. It’s amazing how often I write got instead of git.

Using the bash shell can be unfamiliar to a Windows user. So if you want to set aliases in msysgit it is not very obvious where they should go. They could go into the .bashrc file or the bash_profile file. From a linux perspective the bash_profile configuration file is executed when logging in while the .bashrc file is executed every time a bash shell window is opened. The .bashrc file is located in the c:\Users\YourUsername directory and the bash_profile file is in the etc directory. In the case of msysgit I fail to see that there is any real practical difference; both are executed when you start up msysgit. So I just used .bashrc and it works great.

If there is no file named .bashrc then you’ll have to create it. Windows 7 will not allow you to create a file with a dot (period) as the first character in the filename and with no extension. So the easy way to do this is to name your file .bashrc. (with an extra dot at the end) and Windows will automatically rename the file to just .bashrc (with no dot at the end).

My .bashrc file (almost identical to the Git Immersion profile file that is linked above):

alias less='less -r'
# --show-control-chars: help showing Korean or accented characters
alias ls='ls -F --color --show-control-chars'
alias ll='ls -l'
alias gs='git status '
alias ga='git add '
alias gb='git branch '
alias gc='git commit'
alias gd='git diff'
alias go='git checkout '
alias gk='gitk --all&'
alias gx='gitx --all'
alias got='git '
alias get='git '

Migrations with Rake, Albacore and FluentMigrator

For my previous projects I have mostly used FluentMigrator in combination with Nant for my migrations but now that there is a new FluentMigratorTask for Albacore (created by Mark Boltuc) I thought I would give Rake a try. For an introduction to FluentMigrator see Sean Chambers’ introduction or this article on FluentMigrator and MSBuild.

First up, you have to install Ruby and RubyGems. For Windows go here and for Ubuntu have a look at this guide. For any other operating systems you’re on your own!

Open up your command prompt (on Windows use the Command Prompt with Ruby that comes with Ruby for Windows), and then:

gem install albacore

Next step is to create a rake build file; to do this create a file named rakefile. The only dependency you need for a basic .NET project is Albacore. So a simple Rake file with the MSBuild Albacore task looks like this:

require 'albacore'

task :default => [:build]

desc "Build"
msbuild :build do |msb|
	msb.properties :configuration => :Release
	msb.targets :Clean, :Build
	msb.solution = "Test.sln"
end

Check out the Albacore wiki for more on this and other tasks.

The FluentMigrator Albacore task is a wrapper (written in Ruby) around FluentMigrator’s command line tool. So anything you can do with the command line tool you can do with the Albacore task. Here is a simple migrate to latest version rake task:

desc "MigrateDb"
fluentmigrator :migrate do |migrator|
	migrator.command = 'lib/Migrate.exe'
	migrator.provider = 'postgres'
	migrator.target = './Migrations/bin/Debug/Migrations.dll'
	migrator.connection = 'Server=127.0.0.1;Port=5432;Database=FluentMigrator;User Id=test;Password=test;'
end

These four parameters are mandatory. The first parameter specifies where the command line tool is located. The other three are the same as when using the command line tool. See the wiki page for the FluentMigratorTask for more on the different options available.

The migrate task is all I need for most build files but occasionally you might need to rollback a version or rollback to the start. The rollback task below rolls back one step and this is usually good enough for me.

desc "RollbackDb"
fluentmigrator :rollback do |migrator|
	migrator.command = 'lib/Migrate.exe'
	migrator.provider = 'postgres'
	migrator.target = './Migrations/bin/Debug/Migrations.dll'
	migrator.task = 'rollback' migrator.connection = 'Server=127.0.0.1;Port=5432;Database=FluentMigrator;User Id=test;Password=test;'
end

desc "RollbackDbToStart"
fluentmigrator :rollback_all do |migrator|
	migrator.command = 'lib/Migrate.exe'
	migrator.provider = 'postgres'
	migrator.target = './Migrations/bin/Debug/Migrations.dll'
	migrator.task = 'rollback:all'
	migrator.connection = 'Server=127.0.0.1;Port=5432;Database=FluentMigrator;User Id=test;Password=test;'
end

But a more advanced version lets you specify the number of steps to rollback. It is pretty easy to adjust this to use version instead of steps i.e. roll back to version 2 instead of roll back 2 steps.

 desc "RollbackDbByXSteps"
fluentmigrator :rollback_with_steps, :steps do |migrator, args|
	args.with_defaults(:steps => 1)
	migrator.command = 'lib/Migrate.exe'
	migrator.provider = 'postgres'
	migrator.target = './Migrations/bin/Debug/Migrations.dll'
	migrator.connection = 'Server=127.0.0.1;Port=5432;Database=FluentMigrator;User Id=test;Password=test;'
	migrator.task = 'rollback'
	migrator.steps = args[:steps]
end

This is then called like this:

 rake rollback_with_steps[2] 

And that should be enough to get you started with Rake, Albacore and FluentMigratorTask!