Posts Tagged ‘git’

Faster Git with Aliases (or is it Aliii?)

January 15, 2010

With git’s easy branching, I’ve gotten into a pretty good rhythm. Every time I start a task (more than just a quick fix) I do this:

git branch iliketurtles
git push origin iliketurtles
git branch -f iliketurtles origin/iliketurtles
git checkout iliketurtles

I’m basically starting a new local branch, pushing it to the remote repository, connecting the two for tracking, and checking out the local copy to work on. You can see that this is a lot of repetition, regardless of your feelings toward turtles. That’s where git’s aliasing comes in. Add these lines to the .gitconfig file in your home directory:

[alias]
    launch = !sh -c 'git branch $1 && git push origin $1 && git branch -f $1
 origin/$1 && git checkout $1' -

It’s a long line, granted. It’s basically doing all the things listed above, in order. It’s like a slightly more complicated version of a shell alias, but with the benefit of…I guess being able to tell people you’ve written custom git aliases. Anyhow, I can now replace the four lines of git commands above with this:

git launch iliketurtles

The local and remote branches have been created and connected, and I’m now on the new branch. When I’m done with my changes I merge back into the main branch. From there, I need to wipe the temporary branch out of existance, like so:

git push origin :iliketurtles
git branch -r iliketurtles

I was using "git branch -dr iliketurtles" to remove the remote branch, until I realized it still leaves the branch on the remote repository. It only removes your ability to see it. This is the same approach taken when directors use softer lighting on Madonna. "git push origin :iliketurtles" removes the old branch completely. This is the same approach taken when MTV starts replacing Madonna videos with Lady GaGa. Still painful, but with less baggage.

Use Tags in Git!

December 15, 2009

“Awe, for the love of crumbcake!” – Morris Szyslak

Recently I’ve dealt with a handful of newer open-source offerings in the Ruby on Rails community, via GitHub. Newer codebases are more prone to rapid change. Sure enough, I’ve fallen victim to changed code from one download to the next. This can cause a host of problems such as changed syntax, version clash with other plugins, or occasionally just outright bugginess.

If you’re dealing with gems, versioning is built right in, and you can usually get older versions of what you want. Plugins, engines, or base applications are a different matter. My battle cry is this: USE TAGS IN GIT!

First, if you’re using someone else’s code on GitHub, look for the tab that says “All Tags”, and see if there are specifically released versions. This is helpful if you downloaded the latest version and realized it’s totally different from the one you know and love. You can select the version you want, and you have two options from here. Click “Download” to choose the specific version you want, especially if you don’t want the full repository with commit histories, etc. Or, clone the entire app, and switch versions locally. The Spree shopping cart allows this:

bellmyer$ git clone git://github.com/railsdog/spree.git test-spree
Initialized empty Git repository in <...>
remote: Counting objects: 28927, done.
remote: Compressing objects: 100% (10583/10583), done.
remote: Total 28927 (delta 17195), reused 28757 (delta 17040)
Receiving objects: 100% (28927/28927), 13.08 MiB | 1840 KiB/s, done.
Resolving deltas: 100% (17195/17195), done.
bellmyer$ cd test-spree/
test-spree$ git checkout v0.9.0
Note: moving to 'v0.9.0' which isn't a local branch
If you want to create a new branch from this checkout, you may do so
(now or later) by using -b with the checkout command again. Example:
  git checkout -b 
HEAD is now at 78f0b8c... fix typo on option
test-spree$ git branch
* (no branch)
  master

Git will inform you (as it did above) that you can’t actually edit the code since the tag is a static snapshot of the repository. However, it also tells you how to create a new branch based on this tag if you are interested in making changes. Easy!

Now, the more important part of my message. To developers who actively publish open-source code, first: thank you. Second, I offer a new TATFT: Tag All The Fucking Time! It’s easy. I’ll prove it, using my test-driven fork of Dave Currin’s Seed CMS.

seed$ git tag 0.0.1 master
seed$ git status
# On branch master
nothing to commit (working directory clean)
seed$ git push
Everything up-to-date
seed$ git push --tags
Total 0 (delta 0), reused 0 (delta 0)
To git@github.com:bellmyer/seed.git
 * [new tag]         0.0.1 -> 0.0.1

In the two times I’d downloaded this app in the last month, fundamental pieces had changed, which slowed down my development. If it’d had tags already, I could have chosen to download the version I was already familiar with. I forked his repository to add tags, and to fix the test suite. Feel free to use it if you wish.

By the way, I am NOT harping on Dave Currin’s lack of tags or tests. He’s a very cool guy who admits it needs work, but wisely chose to release a very alpha version of his CMS early, rather than wait forever until it had all the polish of a mature app. I’m grateful, because that choice means I got to use it on two projects so far. Well worth it.

In conclusion, tags are so easy in Git and GitHub, both for the publisher and the user, that there’s no reason not to use them.

Reviewing Your Changes Piece-by-Piece Before Commiting, with Git

December 4, 2009

If you’ve ever worked on a tough piece of code, you know that there is some trial and error involved. You add code, try it, tweak it, sometimes remove it altogether and then attempt to change a different part. Sometimes, at the end of a whirlwind session, do you worry you left something in that eventually didn’t need to be there?

You can use the patch option of git add to verify each and every change you’ve made to your code, so you can decide which to keep and which to throw out. Just use the -p option, like so:

mysite$ git add -p
diff --git a/index.html b/index.html
index 4e5050b..da78acf 100644
--- a/index.html
+++ b/index.html
@@ -5,5 +5,8 @@

 
   <h1>Hello, World!</h1>
+  <ul>
+    <li><a href="about.html">About</a></li>
+  </ul>
 
 
Stage this hunk [y,n,q,a,d,/,e,?]? y

When you’re finished, only the changes you’ve approved will be saved at your next commit. The other changes won’t be wiped out – they’ll still be in your code for you to remove as you see fit. But they won’t be “staged” for the next commit, so they won’t make it into your repository.

Another use is when you realize you made changes that should have been committed, but now you’re partway through another feature. You can commit the finished changes, while excluding the changes that are still in progress.

Color Coding in Git

December 3, 2009

I recently started reading Pragmatic Version Control Using Git.  Some of the early stuff will be review, but I don’t have a solid foundation in the server-side aspects of Ruby on Rails, so I’m working on it.  In the first chapter, I stumbled on a real gem: Git can be configured to spit out the familiar red-green color coding that we all know and love in autotest and other red-green-refactor testing.  (You are using Test Driven Development, right? )

Enter this at a command prompt:

git config --global color.ui "auto"

That makes your git output (after making changes) look like this:

mysite$ git status
# On branch master
# Changed but not updated:
#   (use "git add ..." to update what will be committed)
#   (use "git checkout -- ..." to discard changes in working directory)
#
#	modified:   index.html
#
no changes added to commit (use "git add" and/or "git commit -a")
mysite$ git add index.html
mysite$ git status
# On branch master
# Changes to be committed:
#   (use "git reset HEAD ..." to unstage)
#
#	modified:   index.html
#

If this doesn’t seem like much, it’ll get much more important when you’re looking at a long list of files in different states.


Follow

Get every new post delivered to your Inbox.