Tuesday, December 21, 2010

Drools migrated to Git

Posted by
Geoffrey De Smet

We have joined many other open source projects (such as Hibernate, Seam, Infinispan, ...) and migrated Drools from Subversion to Git.
Subversion has served us really well, but the features such as pull requests, cherry picking, cheap branching and multitasking in isolation, which git brings to the table, are just to nice not to have at our disposal.

There is a bit of a learning curve though. The step from Subversion to Git is bigger than the step from CVS to Subversion was. Below is a short guide for SVN guys that don't know Git yet.

Git for SVN guys

Purpose

This document shows you how to use Git, just as you were using SVN in the past. It is to get you guys up and running with git as soon as possible by relying on your SVN knowledge and it is focuses on what you want to do in drools.This document does not really teach you Git. Git is not just SVN++, it is much more and you should take some time to learn that too.

Terminology

SVN trunk is renamed to Git master. A branch is still a branch. A tag is still a tag.Translation note: trunk == masterThe SVN central repository is now the reference repository on github, see https://github.com/droolsjbpm/droolsjbpm.

Getting the source code locally

First move your old SVN working directory aside, so you’re not confused that you shouldn’t work there any more:$ cd projects$ mv drools drools-oldsvnNow you’re ready to get the sources with git. In SVN this is a svn checkout, but in Git this is called a git clone. Prefer the faster, stabler git protocol over the slower https protocol:$ git clone git@github.com:droolsjbpm/droolsjbpm.git droolsjbpmNext go into that directory$ cd droolsjbpmSo what’s the command git checkout for? To switch to another branch, but in the same working directory. In SVN you also use svn checkout for that.Translation note: svn checkout == git clone (new repository)Translation note: svn switch == git checkout (change branch)Follow the instructions in the README.txt to set up your Eclipse or IntelliJ again.

Getting changes from others

So Mark and Edson changed something in drools-core in the reference repository. How do I get those changes? In SVN this is svn update, but in Git this is a git pull.Be aware, if you have local uncommitted changes, you 'll want to apply those changes after any changing coming from master, so it's better to add the --rebase argument. $ git pull --rebaseIf there's any output, read it: there might be merge conflicts.Translation note: svn update == git pull --rebase

Making changes

While making your changes, do the same as in SVN: git add, git rm (instead of svn delete), git status.Translation note: svn delete = git rmAfter making your changes, you ‘ll want to do a git commit (when you’re done with a changeset) and a git push (to share those changes with the rest of the team). To recap: doing a git commit does not push your changes to the remote repository yet, you also need to do a git push.$ git commit -m “JBRULES-123 fix testcase”$ git pushTranslation note: svn commit == git commit; git pushImportant rule: On git push, never use the --force option (unless you know exactly what you’re doing)If you want to see what you’ve committed but not yet pushed, use this command:$ git log --branches --not --remotes

Part 2: Tell me more

Extra terminology

What is rebasing? A rebase is an alternative manner of merging: instead of merging your changes with the incoming changes, it takes the incoming changes and applies your changes on top of that. This gives a cleaner history. For example:$ git pull --rebaseImportant rule: Do not rebase commits that you have pushed to a public repository.In this use case, this probably isn’t a problem (if you still use the same remote repository).What is origin? Because git can work with multiple remote repositories (usually forks of the same project), the default remote repository is known as origin. If you’ve cloned the reference repository, then origin is the reference repository. If you’ve forked the reference repository as A and cloned A, then origin is A.

Branching

Release branching

A release branches is copied from the master branch and only receives bug-fixes. It is separated from the master branch so no unstable features or improvements (pushed by other developers) leak in.For example: $ git checkout 5.1.xCherry picking is very interesting to pick bug-fixes from the master branch into the release branch.

Topic branching

A topic branch is copied from the master branch and is eventually merged back into the master branch. Its changes are to disruptive to other team members to be committed to the master immediately.For example: $ git checkout trueModifyRebasing is very interesting when you’re working on an experimental feature in a local topic branch for the last few weeks and you want to have the latest changes of master(=trunk) in there too (= sync up with master):// on my the myTopic branch$ git rebase masterImportant rule: Do not rebase commits that you have pushed to a public repository. So don't use it on non-local topic branches. (Use git merge if you have pushed it to a public repository.)After your topic branch is stable, you’ll merge it into the master branch:$ git checkout master$ git merge trueModify