<?xml version='1.0' encoding='utf-8' ?>
<feed xmlns='http://www.w3.org/2005/Atom'>
  <link rel="self" href="http://www.lostincode.net/blog.atom" type="application/atom+xml" />
  <link rel="alternate" href="http://lostincode.net/" type="application/atom+xml" />
  <link rel="hub" href="http://pubsubhubbub.appspot.com/" />

  <title type='text'>Lost in Code</title>
  <id>http://www.lostincode.net/blog.atom</id>
  <updated>2011-10-31T00:00:00-07:00</updated>

  <author>
    <name>Elliot Winkler</name>
    <uri>http://lostincode.net/</uri>
    <email>elliot.winkler@gmail.com</email>
  </author>

  
    
    <entry>
      <id>tag:lostincode.net,2011-10-31:post/clojure-lein-vim</id>
      <link rel="alternate" href="http://lostincode.net/blog/clojure-lein-vim" />
      <title type='html'>Setting up Clojure 1.2, Leiningen, and Vim</title>
      <excerpt type='xhtml'>
        <p>It turns out it isn't terribly difficult.</p>

        <p class='more'><a href="http://lostincode.net/blog/clojure-lein-vim">read the rest &#0187;</a></p>
      </excerpt>
      <content type='xhtml'>
        <p>I've been wanting to learn a new language for a while. Ruby is fun and all, but
<a href="http://paulgraham.com/avg.html">sometimes it's good to get a different perspective</a>. There are
definitely some interesting ones that have shown up on my radar: Lua, Haskell,
Erlang, and Scala, to name a few. I've always been intrigued by Lisp, though.
I don't think anyone would deny that John McCarthy (R.I.P.) was a genius for
pioneering a language that's so simple, yet so powerful.</p>

<p>While there have been a few implementations of Lisp (Common Lisp, Scheme, Arc)
throughout the years, and while it is used for certain applications (AI, music
typesetting, text editors), it really hasn't reached mainstream appeal in the
programming world the way that Java, Perl, or Lua has (three languages that were
developed for one specific purpose and has since spread to other subfields). I
think one of the reasons for this -- besides the fact that Lisp as a language is
the polar opposite of imperative, Algol-based languages to which people have
gravitated -- is also the reality that it's kind of stagnated while the world
around it has evolved. In order to compete in the business/enterprise world
nowadays, people just expect languages to have certain things -- reusability
through namespaces and packaging, dependency management, a garbage collection
model that doesn't suck -- and (although it's a bit of a catch-22) there isn't a
community around Lisp writing, publishing, and recirculating supporting code in
the same way that there are people around Perl or Ruby or even Java.</p>

<p><a href="http://clojure.org">Clojure</a> is a different story, though. It's been in development for 3
years, so it's still a young language, but it already has a
<a href="http://clojure-conj.org">conference</a>, and a mailing list, and an established <a href="http://github.com/technomancy/leiningen">package
management system</a>, and <a href="https://github.com/languages/Clojure/most_watched">plenty of code on GitHub</a> where
it is being used for everything from live music generation to web stuff to
OpenGL. So what's its secret? Why does everyone like Clojure so much? Well, for
one thing, it brings some new things to the Lisp world, such as language-level
support for working with more specific data structures like vectors and hashes,
and concurrency-safe data mutation with STM. The main draw, though, is that it
runs on the JVM, so naturally it appeals to Java developers as well as people
who, like me, are intrigued by the JVM but don't necessarily wish to write Java
itself. So in a way, Clojure already ships with a wealth of features, because
you can directly use any Java library you want (either the standard library or a
.jar from somewhere else).</p>

<hr /><p>But enough about why you might want to try out Clojure. You're here because you
want to quickly get a Clojure project up and running. Fortunately the process is pretty easy:</p>

<ul><li>Download Clojure to a location on your machine</li>
  <li>Install a wrapper script for the Clojure REPL</li>
  <li>Configure your editor of choice</li>
  <li>Install Leiningen</li>
  <li>Make your first project</li>
</ul><h3 id="installing-clojure">Installing Clojure</h3>

<p>The first thing to do, then, is to get Clojure 1.2 <sup id="fnref:clj13"><a href="http://lostincode.net#fn:clj13" rel="footnote">1</a></sup>, which is available
on the <a href="http://clojure.org/downloads">Clojure site</a>. Inside the zip file you download is a
<tt>clojure.jar</tt> file. You'll want to choose a location to put this. I'm going to
be using <tt>/opt/clojure/lib</tt> in this guide:</p>

<pre class="prompt"><code>~$ mkdir -p /opt/clojure/lib
~$ cd /tmp
/tmp$ wget https://github.com/downloads/clojure/clojure/clojure-1.2.1.zip
/tmp$ unzip clojure-1.2.1.zip
/tmp/clojure-1.2.1$ cd clojure-1.2.1
/tmp/clojure-1.2.1$ cp clojure.jar /opt/clojure/lib/clojure-1.2.1.jar
</code></pre>

<p>Note that on the downloads page, you will also see a reference to a package
called clojure-contrib. This is a user-contributed and -maintained collection of
libraries that provide extra functionality you may find handy in your Clojure
program. Don't worry about installing it now, though -- clojure-contrib is one
of Leiningen's dependencies, so it will get installed when Leningen is
installed.</p>

<p>(Also, ordinarily at this point I'd recommend using a package manager to prevent
from having to maintain anything, but I actually prefer doing it this way
because Clojure is pretty self-contained as it is, and as long as you choose a
more-or-less standard location, then I don't see any issues with it. It'll also
be easier to upgrade to 1.3 in the future.)</p>

<h3 id="making-a-wrapper-script">Making a wrapper script</h3>

<p>With Clojure downloaded and installed, let's test it to make sure our setup
works. If you're a Ruby or Python developer, you might be looking for a REPL so
that you can quickly try out some code without having to bring out your code
editor and create a standalone file. Clojure <em>does</em> have a REPL mode: <a href="http://clojure.org/repl_and_main">as
described on the Clojure site</a>, you get into it with <code>java -cp
clojure.jar clojure.main</code>. But no one uses this -- first, because it's hard to
remember, and second, because the REPL isn't very usable, as it doesn't have the
nice things that REPLs usually have, such as command history or tab
autocompletion. There isn't really even a straightforward way to exit --
it isn't a huge deal as you can say <code>(System/exit)</code> or even just press Ctrl-C,
but it's still kind of annoying.</p>

<p>Fixing these things isn't difficult, though. To provide command history and tab
completion, we can use everyone's favorite C library, <tt>readline</tt>. More
specifically, we can create a wrapper script, commonly called <tt>clj</tt>, that uses
<tt>rlwrap</tt> to wrap the <code>java -jar ...</code> command in readline capabilities. The good
thing is that people have already done the work for us here -- <a href="http://programmingzen.com/2010/07/13/how-to-setup-clojure-from-scratch/">Antonio
Cangiano</a> has a version of this script that merely improves upon the
version up on the <a href="http://en.wikibooks.org/wiki/Clojure_Programming/Getting_Started#Enhancing_Clojure_REPL_with_rlwrap">Clojure wiki</a>. So we will base ours on both of
these.</p>

<p>That means we'll need to install <tt>rlwrap</tt>. If you are on Linux, I'm fairly sure
you can get <tt>rlwrap</tt> through your package manager of choice. If you are on Mac
as I am, you can simply use <a href="http://mxcl.github.com/homebrew">Homebrew</a>:</p>

<pre><code>brew install rlwrap
</code></pre>

<p>The wrapper script we will make is very simple. In running <tt>rlwrap</tt>, we'll tell
it to do two things. First we'll give it a file, <tt>clj_completions</tt>, which
contains the list of words available for autocompletion (we'll generate the
completions file in a minute). Second, we'll tell it to run the <code>java -jar
clojure.jar</code> command to start Clojure. Then, right before the REPL is loaded,
we'll tell Clojure to load a second file, <tt>cljrc.clj</tt>; this file will allow us
to customize the REPL, such as defining a proper <code>(exit)</code> command.</p>

<p>Here's what that all looks like:</p>

<pre><code>#!/bin/bash

breakchars="(){}[],^%$#@\"\";:''|\\"
CLOJURE_DIR=/opt/clojure
CLOJURE_JAR=$CLOJURE_DIR/lib/clojure-1.2.1.jar
CONTRIB_JAR=$CLOJURE_DIR/lib/clojure-contrib-1.2.0.jar
COMPLETIONS_FILE=$CLOJURE_DIR/etc/clj_completions
RC_FILE=$CLOJURE_DIR/etc/cljrc.clj
CLOJURE_CP=$CLASSPATH:$CLOJURE_JAR:$CONTRIB_JAR:$PWD

if [ $# -eq 0 ]; then
  cmd = ""
  cmd += "rlwrap --remember -c -b $breakchars"
  if [ -f $COMPLETIONS_FILE ]; then
    cmd += " -f $COMPLETIONS_FILE"
  fi
  cmd += " java -cp $CLOJURE_CP clojure.main -i $RC_FILE --repl"
  exec $cmd
else
  exec java -cp $CLOJURE_CP clojure.main $1 -- $@
fi
</code></pre>

<p>Save this as <tt>/opt/clojure/bin/clj</tt>, and make it executable with <code>chmod +x
/opt/clojure/bin/clj</code>. Since we want to be able to run this anywhere, you will
also want to either add <tt>/opt/clojure/bin</tt> to your path or make a symlink to
it in a directory that's already in your path (I have a <tt>~/.bin</tt> folder just
for this purpose).</p>

<p>Now for the files that the <tt>clj</tt> script references. <tt>clj</tt> in fact won't work
without an rc file, so let's create that first. This file simply consists of:</p>

<pre><code>(defn exit [] (System/exit 0))
</code></pre>

<p>Save this to <tt>/opt/clojure/etc/cljrc.clj</tt>.</p>

<p>At this point we should be able to try out <tt>clj</tt>:</p>

<pre class="prompt"><code>~$ clj
Clojure 1.2.1
user=&gt; (* 2 2)
4
user=&gt; "Hello world"
"Hello world"
user=&gt; (defn foo [x] (* x x))
#'user/foo
user=&gt; (foo 4)
16
user=&gt; (exit)
</code></pre>

<p>You should also be able to press the up arrow at any point and view past
commands.</p>

<p>Great. We still can't tab-complete, though -- to do that we need to create a
list of autocompletable symbols. This could be anything, but you probably want
at least the symbols in clojure.core. Here is some Clojure code that does this
(ripped straight from the <a href="http://en.wikibooks.org/wiki/Clojure_Programming/Getting_Started#Enhancing_Clojure_REPL_with_rlwrap">Clojure wiki</a>):</p>

<pre><code>(def completions
  (reduce concat (map (fn [p] (keys (ns-publics (find-ns p))))
                      '(clojure.core))))

(with-open [f (java.io.BufferedWriter. (java.io.FileWriter. "/opt/clojure/etc/clj_completions"))]
  (.write f (apply str (interleave completions (repeat "\n")))))
</code></pre>

<p>The list of namespaces in line 3 (the <code>'(clojure.core)</code> bit) is what is
iterated over to create the file. You can get an idea of what to add to this by
looking at the other namespaces in the <a href="http://clojure.github.com/clojure/">Clojure documentation</a>.</p>

<p>Save this script to a file (say, <tt>/tmp/foo.clj</tt>) and run it by passing the
filename to <code>clj</code>. This will write the completions file to
<tt>/opt/local/clojure/etc/clj_completions</tt>.</p>

<p>Now try <tt>clj</tt> again:</p>

<pre class="prompt"><code>~$ clj
user=&gt; ma&lt;TAB&gt;
macroexpand   macroexpand-1   make-array   .......
user=&gt; (exit)
</code></pre>

<h3 id="installing-leiningen">Installing Leiningen</h3>

<p>As you saw, we can now create Clojure files and run them with <tt>clj</tt>. What if you
want to make more of a <em>project</em>, though? What's the recommended way of
organizing the files in your project? What if your project depends on libraries
-- how do you install them?</p>

<p>All of these concerns are easily taken care of with <a href="http://github.com/technomancy/leiningen">Leiningen</a>. Leiningen
is the standard toolkit in Clojure-land for maintaining and installing your
project's dependencies. It's a bit like npm for node.js, Bundler for Ruby, or
Maven for Java. In fact, it uses Maven under the covers, and Maven already tells
Java where everything is, so you don't have to worry about configuring the
class path or any of that -- everything just works.</p>

<p>Installing Leiningen is pretty simple, too. First download the <tt>lein</tt> executable
and put it somewhere -- to stay consistent, we'll use <tt>/opt/clojure/bin</tt>, with a
symlink in <tt>~/.bin</tt>. Like this:</p>

<pre class="prompt"><code>~$ cd /opt/clojure/bin
/opt/clojure/bin$ wget https://raw.github.com/technomancy/leiningen/stable/bin/lein
/opt/clojure/bin$ chmod +x lein
/opt/clojure/bin$ ln -s /opt/clojure/bin/lein ~/.bin/lein
/opt/clojure/bin$ cd
~$ which lein
~/.bin/lein
</code></pre>

<p>All that really downloads is a script, so to finish the installation and
download the Leiningen jar file, run the self-installer:</p>

<pre class="prompt"><code>~$ lein self-install
</code></pre>

<p>Now let's make a new Lein project:</p>

<pre class="prompt"><code>~$ cd code
~/code$ lein new musicprogram
Created new project in: ~/code/musicprogram
</code></pre>

<p>If we inspect this folder...</p>

<pre class="prompt"><code>~/code$ ls musicprogram
README   project.clj   src/   test/
</code></pre>

<p>we will see that Lein has generated a <tt>project.clj</tt> file for us:</p>

<pre><code>(defproject musicprogram "1.0.0-SNAPSHOT"
  :description "FIXME: write description"
  :dependencies [[org.clojure/clojure "1.2.1"]])
</code></pre>

<p>This is akin to a <tt>pom.xml</tt> file in Java-land, a package.json in node-land, or
a gemspec in Ruby-land.</p>

<p>But let's try adding a dependency to our project. Let's say we want to play
around with <a href="https://github.com/rosejn/overtone">Overtone</a>, which is a live coding music generation
library. Here is how we would tell Leiningen that our project requires it:</p>

<pre><code>(defproject musicprogram "1.0.0-SNAPSHOT"
  :description "Our super awesome music program"
  :dependencies [[org.clojure/clojure "1.2.1"]
                 [overtone "0.5.0"]])
</code></pre>

<p>Now, let's try installing it:</p>

<pre class="prompt"><code>~/code/musicprogram$ lein install
Downloading: overtone/overtone/0.5.0/overtone-0.5.0.pom from central
Downloading: overtone/overtone/0.5.0/overtone-0.5.0.pom from clojars
Transferring 2K from clojars
Downloading: overtone/osc-clj/0.7.1/osc-clj-0.7.1.pom from clojars
Transferring 1K from clojars
Downloading: org/clojars/technomancy/jmdns/3.2.1/jmdns-3.2.1.pom from clojars
Transferring 1K from clojars
Downloading: commons-net/commons-net/3.0.1/commons-net-3.0.1.pom from clojars
Downloading: commons-net/commons-net/3.0.1/commons-net-3.0.1.pom from central
Transferring 16K from central
Downloading: org/apache/commons/commons-parent/21/commons-parent-21.pom from clojars
Downloading: org/apache/commons/commons-parent/21/commons-parent-21.pom from central
Transferring 33K from central
[... lots of output ...]
</code></pre>

<p>I mentioned that Lein uses Maven for all the dependency stuff. In fact, the
<tt>project.clj</tt> you write is actually a wrapper for Maven's pom format. So when
you run <code>lein install</code>, Maven immediately knows which dependencies your project
needs. For each dependency, it first checks to see if it's already been
downloaded (<tt>~/.m2</tt> is conventionally where it keeps cached jar files;
technically this is a local repository). If it's not there, it goes and fetches
it from an online repository. Apart from Clojure, Maven only looks in one
location, the <a href="http://search.maven.org/#browse">central Maven repo</a>. Clojure adds a second
repository, <a href="http://clojars.org">Clojars</a>, which is designed specifically to read
<tt>project.clj</tt> files. This is why in the output above you will sometimes see
"Transferring &lt;bytes&gt; from central" and other times "Transferring &lt;bytes&gt; from
clojars".</p>

<p>Going back to <tt>project.clj</tt>, there's other information you can put there besides
your dependencies. For instance, if your project depends on packages that are
only needed for development (such as testing frameworks or debugging tools), you
could specify them with a <tt>:dev-dependencies</tt> property. If you were creating
more of a library and you wanted to package your project and distribute it to
Clojars, you would need to provide a version and <tt>:description</tt>, so that other
people can easily find it when they are searching on Clojars. In this case you
might also want to add a <tt>:url</tt> property so that people have a place to go to
learn more about your package.</p>

<p>Besides these, there are a whole host of other properties available --
<a href="https://github.com/technomancy/leiningen/blob/stable/sample.project.clj">see here</a> for the full list.</p>

<p>I could keep going about Leiningen, but you'll probably get a better
understanding if you read the built-in tutorial, which explains all of this
in more detail than I have knowledge of -- you can get to that by running
<code>lein help tutorial</code>.</p>

<h3 id="setting-up-our-editor-vim">Setting up our editor (Vim)</h3>

<p>Now that we have a project up and running, let's turn now to configuring our
editor so that we are comfortable writing Clojure code.</p>

<p>As mentioned, Clojure runs on the JVM, and while this is great for production,
it isn't so great for development, as it takes a fairly long time for the JVM to
boot up. Hence, a lot of people will recommend you use a Java IDE or an editor
that can connect to a running Clojure REPL -- that way you can send any code you
want to the REPL to get executed. If you've already been doing Java development,
then you are probably used to Eclipse, NetBeans, or IntelliJ, and <a href="http://www.bestinclass.dk/index.clj/2010/03/clojure-ides-the-grand-tour-getting-started.html">all three do
have some sort of support for Clojure</a> (they have their pros
and cons). Otherwise, if you are just getting into Clojure and don't mind
learning something new, Emacs is the <a href="http://stackoverflow.com/questions/4248171/choosing-an-ide-editor-for-clojure-coding/4252808#425288">clear</a>
<a href="http://stackoverflow.com/questions/257333/clojure-editor-ide-recommendations-on-mac-os-x/257417#257417">winner</a>. A <a href="http://briancarper.net/blog/534/emacs-isnt-for-everyone">lot</a> <a href="https://github.com/technomancy/emacs-starter-kit">of</a>
<a href="http://vimeo.com/9770382">people</a> who are seriously into Clojure are using it -- it
really seems like there's nothing that beats SLIME and swank-clojure, and <a href="http://dev.clojure.org/display/doc/Getting+Started+with+Emacs">once
you install them</a> you can get up and running and no time.</p>

<p>As for me, I just learned Vim and didn't really feel like switching to Emacs.
The <em>de facto</em> plugin for Vim is <a href="http://www.vim.org/scripts/script.php?script_id=2501">VimClojure</a>, so if you use Vim
too, you'll want to install this. Like Emacs, VimClojure also has a way of
starting and connecting to Clojure via Nailgun. When you install VimClojure you
are totally free to not use Nailgun, but it is easy to set up, and as you will
need it pretty soon anyhow, I would recommend doing so right out of the gate.
There are instructions on how to install Nailgun and tell VimClojure to use it
in the <a href="http://www.vim.org/scripts/script.php?script_id=2501">README for the plugin</a>, but this guy Dave Ray has posted
<a href="http://blog.darevay.com/2010/10/how-i-tamed-vimclojure/">some instructions</a> -- along with an <a href="https://github.com/daveray/vimclojure-easy">example VimClojure
setup</a> as described in the post -- which I found to be super
helpful.</p>

<p>Basically, there are two pieces involved here: one is the Nailgun server
(packaged in a jar file) which is our running instance of Clojure, the other is
the Nailgun client (a little C program called <tt>ng</tt>) which will hit the server
with the code we want to run inside that instance. So in order to run Clojure
code inside of Vim, all you really have to do is tell VimClojure where you've
put <tt>ng</tt>, and then start the server outside of Vim (VimClojure assumes that
the server is running on the default port of 2113 so no need to customize that).</p>

<p>If you want to get fancy, you can even -- as Dave describes in his post -- use
screen.vim to automate starting the Nailgun server from within Vim and ensure
that it gets shut down after you quit Vim. But, you can actually easily install
and start the server via <tt>lein-nailgun</tt>, which adds a <tt>nailgun</tt> command to
Leiningen. That method works well enough for me, so that is what I am going to
go with in this guide.</p>

<p>Alright, so let's try this out. The first thing to do, obviously, is <a href="http://www.vim.org/scripts/script.php?script_id=2501">install
VimClojure</a>. Then, update your <tt>~/.vimrc</tt> to tell the plugin where
everything is. I have a couple of customizations I've made -- mostly to turn off
VimClojure's colorization of parentheses, and since I use delimitMate, to turn
off autopairing as it just ends up getting in the way. Regardless, you will
also want to make sure to set <tt>maplocalleader</tt> as <tt>&lt;LocalLeader&gt;</tt> is used by
the plugin to set up default mappings:</p>

<pre class="no-highlight"><code>set mapleader = ","
set maplocalleader = ","

" Settings for the VimClojure plugin
let vimclojure#FuzzyIndent=1
let vimclojure#HighlightBuiltins=1
let vimclojure#HighlightContrib=1
let vimclojure#DynamicHighlighting=1
let vimclojure#ParenRainbow=0
let vimclojure#WantNailgun=1
let vimclojure#NailgunClient = $HOME . "/.bin/ng"

" Turn off delimateMate (which provides auto-closing parens) for Clojure files
" as they just get in the way
au! FileType clojure let b:loaded_delimitMate=1
</code></pre>

<p><strong>Note:</strong> If you are using MacVim, you will also want to make sure you are on a
recent version, as older versions have an annoying bug where <a href="https://bitbucket.org/kotarak/vimclojure/issue/1/o-and-o-in-insert-mode-have-a-pause">there is a short
pause when jumping to another line</a>. You'll want to make sure
you have at least snapshot 61.</p>

<p>Next, download the Nailgun client, compile it, and move it to a location
within your path (here I have it at <tt>~/.bin/ng</tt>):</p>

<pre class="prompt"><code>~$ cd /tmp
/tmp$ wget http://kotka.de/projects/vimclojure/vimclojure-nailgun-client-2.3.0.zip
/tmp$ unzip vimclojure-nailgun-client-2.3.0.zip
Archive:  vimclojure-nailgun-client-2.3.0.zip
   creating: vimclojure-nailgun-client/
  inflating: vimclojure-nailgun-client/Makefile
  inflating: vimclojure-nailgun-client/ng.exe
   creating: vimclojure-nailgun-client/ngclient/
  inflating: vimclojure-nailgun-client/ngclient/ng.c
/tmp$ cd vimclojure-nailgun-client
/tmp/vimclojure-nailgun-client$ make
Building ng client.  To build a Windows binary, type 'make ng.exe'
gcc -Wall -pedantic -s -O3  -o ng ngclient/ng.c
ld: warning: option -s is obsolete and being ignored
/tmp/vimclojure-nailgun-client$ mv ng ~/.bin
</code></pre>

<p>Thirdly, add <tt>lein-nailgun</tt> to your project. Continuing with our musicprogram
project this will look like:</p>

<pre class="lisp"><code>(defproject musicprogram "1.0.0-SNAPSHOT"
  :description "Our super awesome music program"
  :dependencies [[org.clojure/clojure "1.2.1"]
                 [overtone "0.5.0"]]
  :dev-dependencies [[org.clojars.ibdknox/lein-nailgun "1.1.1"]])
</code></pre>

<p>Check that "nailgun" is listed as one of the subcommands:</p>

<pre class="prompt"><code>~/code/musicprogram$ lein help
[... long list of tasks here ...]
nailgun     Launch a vimclojure nailgun server.
</code></pre>

<p>Now run the server. Note that it will just sit there waiting for input from the
client:</p>

<pre class="prompt"><code>~/code/musicprogram$ lein nailgun
NGServer started on 127.0.0.1, port 2113.
</code></pre>

<p>Finally, restart Vim and bring up a Clojure file. The first time you open one,
it will take a few seconds for the JVM to load (as Nailgun doesn't do this right
away), but after that you can open any Clojure file with no penalty.</p>

<p>There a whole host of mappings that VimClojure adds for doing things like
requiring files or looking up documentation, but one you can try really quickly
is opening a REPL, which you can do with <tt>,sr</tt>. This should give you something
that looks like this:</p>

<p class="img">
<img src="http://lostincode.net/images/posts/2011-10-09/vimclojure-repl.png" alt="VimClojure REPL" />
</p>

<p>As long as you stay in insert mode, you can press Ctrl-Up/Down to flip through
command history, and you can even type a partial word and press Tab to
autocomplete it.</p>

<p>As useful as the REPL is, the main reason I like VimClojure is because it
lets me easily run tests with it, which I'll talk about next.</p>

<h3 id="testing">Testing</h3>

<p>I love tests. Like Wheatley, I just get this itch -- I have to do it whatever
code I'm writing. Most of the time for me tests play the role of sidekick -- I'd
know what code to write even if tests weren't there, but they're good at keeping
me in check. In learning a new language, though, you're not sure how to express
your ideas and you don't know what your code will do. In that case, tests serve
as a nice exploratory tool to make sure your results are what you expect. And
your explorations are recorded, too.</p>

<p>So what are the available options in Clojure for testing? The simplest one is
the built-in library, <a href="http://clojure.github.com/clojure/clojure.test-api.html">clojure.test</a>. It works like xUnit
libraries in other languages, in that you simply create test methods and make
assertions in those methods which get checked when you run the tests.</p>

<p>We can try it out by going back to our musicprogram project and saving the
following code to <tt>test/musicprogram/test/foo.clj</tt>:</p>

<pre><code>(ns musicprogram.test.foo
  (:use clojure.test))

(deftest addition
  (is (= 2 (+ 1 1))))

(run-tests)
</code></pre>

<p>and running it with <tt>clj</tt>:</p>

<pre class="prompt"><code>~/code/musicprogram$ clj test/musicprogram/test/foo.clj

Testing musicprogram.test.foo

Ran 1 test containing 1 assertion.
0 failures, 0 errors.
</code></pre>

<p>So that's one way to write and run tests, but it isn't the best way. First, it's
kind of a pain that we have to put <tt>(run-tests)</tt> at the end of all of our test
files. Second, if we are working on one source file and we need to run its
corresponding test file over and over again, we will quickly become frustrated
because of the whole JVM load time issue again.</p>

<p>The best method to run one file is actually through VimClojure. If you are
looking at a test file, you can run it with <tt>,rt</tt> and that will show the results
in an adjoining window.</p>

<p>But say we're working on a project full of source files and test files and we
want to run all of the tests in one fell swoop? Well, that's where we need
another way. Running all our test files directly with <tt>clj</tt> falls short because
we either have to list all of our test files on the command line or come up with
some Bash script. VimClojure doesn't really give us a way to do this, either,
unless you make a custom mapping. <sup id="fnref:vimclojure-run-all-tests"><a href="http://lostincode.net#fn:vimclojure-run-all-tests" rel="footnote">2</a></sup></p>

<p>Since <tt>run-tests</tt> accepts a list of Clojure namespaces, we <em>could</em> make a
function that would <tt>require</tt> the namespaces and then feed them to <tt>run-tests</tt>,
perhaps something like this (drawing from a similar function
<a href="http://www.deepbluelambda.org/programming/clojure/programming-clojure-with-vim">here</a>, and also from the source code for <tt>run-tests</tt>):</p>

<pre><code>(defn proj-run-tests
  ([]
    (proj-run-tests *ns*))
  ([&amp; namespaces]
    (do
      (require :reload-all :verbose &amp; namespaces)
      (run-tests &amp; namespaces))))
</code></pre>

<p>But I wouldn't worry about that. It turns out that our old friend Leiningen
already gives us a way to run all of our tests with the <tt>lein test</tt> command.</p>

<p>Going back to the test file we created above, if we remove the <tt>(run-tests)</tt>
call from it, we can re-run it with <tt>lein test</tt> like this:</p>

<pre class="prompt"><code>~/code/musicprogram$ lein test

Testing musicprogram.test.foo

Ran 1 test containing 1 assertion.
0 failures, 0 errors.
</code></pre>

<p>One thing to note here is that this command assumes your project files have a
particular organization -- namely, that your source files are in <tt>src/</tt> and your
test files are in <tt>test/</tt>. It also assumes that the namespace of each file
matches what it's called -- so, the namespace of a file <tt>src/foo/bar.clj</tt> must
be <tt>foo.bar</tt>, and the namespace of <tt>test/foo/test/bar.clj</tt> must be
<tt>foo.test.bar</tt>. This is how Lein creates your project initially, but it's worth
keeping in mind as you flesh out your project.</p>

<h3 id="conclusion">Conclusion</h3>

<p>As long as this post is, I hope I've given you the impression that Clojure is
actually pretty easy to get going with. The hard part is actually wrapping your
head around Clojure itself, especially if you aren't used to programming in a
functional language with immutable data structures. That's for a future blog
post, though.<span class="end-of-content">☯</span></p>

<div class="footnotes">
  <ol><li id="fn:clj13">
      <p>Clojure 1.3 is actually out right now, and this guide was originally intended to be a walkthrough on installing it. Unfortunately, 1.3 introduced some backwards-incompatible changes (most notably the disassembly of clojure-contrib) and there are still a bunch of packages out there -- including Leiningen -- which are not quite compatible. So I have to stick to 1.2 for now, and I recommend you do the same.<a href="http://lostincode.net#fnref:clj13" rev="footnote">↩</a></p>
    </li>
    <li id="fn:vimclojure-run-all-tests">
      <p>Within VimClojure, <tt>,rt</tt> is mapped to run the vimclojure#RunTests function, which is defined in ~/.vim/autoload/vimclojure.vim. This calls a function vimclojure#ExecuteNailWithInput, which basically calls a function RunTests defined in the Clojure code that is a part of the Nailgun server we installed when we installed <tt>lein-nailgun</tt> (and you can see it <a href="https://bitbucket.org/kotarak/vimclojure/src/ada7c24f4b56/server/src/main/clojure/vimclojure/nails.clj">here</a> in the VimClojure repo). With <tt>,rt</tt>, this RunTests function is called with the namespace of the test file being run, but in theory you could make another mapping that would figure out the global namespace of your test files and feed <em>that</em> namespace to RunTests instead.<a href="http://lostincode.net#fnref:vimclojure-run-all-tests" rev="footnote">↩</a></p>
    </li>
  </ol></div>
      </content>
      <published>2011-10-31T00:00:00-07:00</published>
      <updated>2011-10-31T00:00:00-07:00</updated>
    </entry>
  
    
    <entry>
      <id>tag:lostincode.net,2011-04-02:post/minecraft-client-opengl-matrices</id>
      <link rel="alternate" href="http://lostincode.net/blog/minecraft-client-opengl-matrices" />
      <title type='html'>Making a Minecraft client: OpenGL’s transformation matrices</title>
      <excerpt type='xhtml'>
        <p>This post starts off with some basic LWJGL code, but it's mainly about matrices and why they're important to know about if you want to work with OpenGL. (There's math! It's fun!)</p>

        <p class='more'><a href="http://lostincode.net/blog/minecraft-client-opengl-matrices">read the rest &#0187;</a></p>
      </excerpt>
      <content type='xhtml'>
        <p>For the past couple of months, I've been attempting to make a clone of the client program that ships with Minecraft, using OpenGL (which Minecraft uses as well). At first I wanted to write it in Javascript, but quickly realized that a lot of the <a href="http://lostincode.net/minecraft-client-ssjs-engines">server-side Javascript libraries that exist now</a> are still geared toward web stuff, which means there really aren't any mature libraries to work with OpenGL yet. Also: <a href="http://lostincode.net/minecraft-client-v8-gl">v8 is a royal pain to work with</a>. So I made a decision to take a bit of a turn, go straight to the source, and learn how to work with OpenGL in Java (specifically the LWJGL library).</p>

<p>In my <a href="http://lostincode.net/minecraft-client-java-and-ant">last post</a> I figured out a basic Java project workflow, so now it was time to dive into OpenGL and LWJGL. I found the following resources to be pretty helpful:</p>

<ul><li><a href="http://glprogramming.com/red/">The OpenGL Programming Guide</a>, aka the "Red Book" (this goes up to only OpenGL 1.1, which is totally fine for our purposes)</li>
  <li><a href="http://www.lwjgl.org/javadoc/">LWJGL Java docs</a></li>
  <li><a href="http://gpwiki.org/index.php/OpenGL:Tutorials:Java:LWJGL:Introduction">Basic Game class on the Game Programming wiki</a></li>
  <li><a href="http://gpwiki.org/index.php/OpenGL:Tutorials:Tutorial_Framework">OpenGL tutorials on the Game Programming wiki</a></li>
  <li><a href="http://ninjacave.com/tutorials">Basic tutorials on ninjacave.com</a></li>
  <li>And, of course, the <a href="http://download.oracle.com/javase/6/docs/api/">Java 1.6 docs</a></li>
</ul><p>The first thing I learned is that LWJGL isn't exactly like the OpenGL library you'd use in C/C++. It talks to it (at least I think so), but the API differs. The API for the C library has three main components: core GL functions (<tt>glFrustum()</tt>, <tt>glEnable()</tt>, etc.), a set of utility functions (commonly called GLU), and a window system (commonly called GLUT). So what's different about LWJGL? For one, the team behind it has made decisions to keep the library easy to use and within a manageable size. So for instance, all of GLUT is out -- I guess because if you're developing a serious game, you're probably going to use the core API to implement your own stuff anyway. <tt>glColor3fv()</tt> (in the core API) is out because it's only really useful for C programmers. Also, functions that are overloaded in the C API to accept both arrays and buffers are simplified to only accept buffers. So LWJGL omits some features, but at the same time it supports multiple versions of the OpenGL API. So if you're targeting OpenGL 1.1, you use the <tt>GL11</tt> namespace; if you're targeting OpenGL 4.0, then you use the <tt>GL40</tt> namespace. Finally, LWJGL provides some helpful additions: classes which I consider core LWJGL, such as <a href="http://www.lwjgl.org/javadoc/org/lwjgl/opengl/Display.html">Display</a>, <a href="http://www.lwjgl.org/javadoc/org/lwjgl/input/Keyboard.html">Keyboard</a> and <a href="http://www.lwjgl.org/javadoc/org/lwjgl/input/Mouse.html">Mouse</a>; and also convenience classes, such as <a href="http://www.lwjgl.org/javadoc/org/lwjgl/util/glu/Cylinder.html">Cylinder</a>, <a href="http://www.lwjgl.org/javadoc/org/lwjgl/util/glu/Sphere.html">Sphere</a>, <a href="http://www.lwjgl.org/javadoc/org/lwjgl/util/vector/Vector3f.html">Vector3f</a>, <a href="http://www.lwjgl.org/javadoc/org/lwjgl/util/vector/Matrix4f.html">Matrix4f</a>, and amazingly, <a href="http://www.lwjgl.org/javadoc/org/lwjgl/util/vector/Quaternion.html">Quaternion</a>.</p>

<p>To get going with LWJGL, I wanted to keep things simple and render a basic scene. I'd read somewhere that the <a href="http://en.wikipedia.org/wiki/Utah_teapot">"Utah teapot"</a> is the object graphics people have historically used to render a test scene. There's actually a function in GLUT to quickly render this very teapot, but as I just explained, GLUT is missing from LWJGL, so I couldn't do that. So I decided to just draw a cube placed in the middle of the world.</p>

<p>I spent a good while revisiting some of the resources I'd found so far and studying various tutorials. I noticed that the main "Game" class that people gave tended to follow a common pattern, which I present below:</p>

<pre><code>public class Game {
  private static final int WINDOW_WIDTH = ...;
  private static final int WINDOW_HEIGHT = ...;

  public static void main(String[] argv) {
    init();
    mainLoop();
    cleanup();
    System.exit(0);
  }

  private static void init() throws Exception {
    Display.setDisplayMode(new DisplayMode(WINDOW_WIDTH, WINDOW_HEIGHT));
    Display.create();

    // Initialize the projection matrix (viewbox).
    glMatrixMode(GL_PROJECTION);
    glLoadIdentity();
    // ... Use glFrustum(), gluPerspective(), glOrtho() or gluOrtho2D() to initialize the projection matrix ...

    // ... Make other display settings ...
  }

  private static void mainLoop() {
    while (true) {
      if (Keyboard.isKeyDown(Keyboard.KEY_ESCAPE) || Display.isCloseRequested()) {
        break;
      }

      if (Display.isActive()) {
        // Window is active (i.e. in the foreground / currently selected),
        // so we can go full steam.
        handleKeyboard();
        handleMouse();
        render();
      }
      else
      {
        // Window is not active, so let's go light on the CPU.
        try {
          Thread.sleep(100);
        } catch (InterruptedException e) {
          // do nothing
        }

        // Only bother rendering if the window has actually changed.
        if (Display.isVisible() || Display.isDirty()) {
          render();
        }
      }

      Display.update();
    }
  }

  private static void handleKeyboard() {
    // ... Respond to keystrokes ...
  }

  private static void handleMouse() {
    // ... Respond to mouse movement ...
  }

  private static void render() {
    // Clear the screen.
    glClear(...);

    // Rotate or translate the view.
    glMatrixMode(GL_MODELVIEW);
    glLoadIdentity();
    // Now customize it.
    glRotatef(...);
    glTranslatef(...);

    // ... Draw shapes and stuff ...
  }

  private static void cleanup() {
    Display.destroy();
  }
}
</code></pre>

<p>I'll briefly explain what's going on here. There are three parts to this: an initialization routine that runs when the game loads, a loop that runs continuously to redraw the game elements, and a routine that runs when the game ends to clean up stuff. In the <strong><tt>init()</tt></strong> function, we call <tt>Display.create()</tt>, which draws the window and attaches event handlers for the keyboard and the mouse, and then we initialize the projection matrix (which I will talk about shortly). In <strong><tt>mainLoop()</tt></strong>, we do three things: we call <strong><tt>handleKeyboard()</tt></strong> and <strong><tt>handleMouse()</tt></strong> to handle input events, we call <strong><tt>render()</tt></strong> which will set the modelview matrix (which I will also talk about shortly) and queue up the elements that need to be drawn, and then we call <tt>Display.update()</tt> to actually make those elements appear within the window. While we're at it, we optimize for the case in which the window is minimized or not active: we don't draw to the screen if we don't have to. Finally, we have a check that breaks out of the game loop if the escape key is pressed or the close button on the window is clicked. At that point, <strong><tt>cleanup()</tt></strong> is called, which will call <tt>Display.destroy()</tt> to close the window and perform any other necessary destruction routines.</p>

<hr /><p>I want to go into detail about some of the parts of this skeleton, because I like to understand how things work, and if you're reading this, I'm guessing you do, too. So let's focus on the following code for a while:</p>

<pre><code>private static void init() {
  ...
  // Initialize the projection matrix (viewbox).
  glMatrixMode(GL_PROJECTION);
  glLoadIdentity();
  // ... Use glFrustum(), gluPerspective(), glOrtho() or gluOrtho2D() to customize the projection matrix ...
  ...
}

private static void render() {
  ...
  // Initialize the modelview matrix (camera / objects).
  glMatrixMode(GL_MODELVIEW);
  glLoadIdentity();
  // Now customize it.
  glRotatef(...);
  glTranslatef(...);
  ...
}
</code></pre>

<p>As you can tell, what we are concerned with here are the projection and modelview matrices. What are these good for, and how do you use them? Allow me to explain...</p>

<h3 id="projection-and-modelview-matrices">Projection and modelview matrices</h3>

<p>The <strong>projection</strong> and <strong>modelview</strong> matrices are basically tables of values, numbers specifically, that store the transformation state of the viewing area of the scene and the objects within the scene.</p>

<p>Imagine that we're in a room. Perhaps there is a collection of fruit on the floor: apples, pears, bananas, etc. We can pick up an apple and place it anywhere in the scene, and we can turn it any way we like. Now let's say we have a video camera and we are filming the scene. Obviously, this means the scene is framed by what the camera is able to see. We can change what we see in four ways. Behind the camera, we can pan around, we can zoom in and out (conceivably), and we can walk around with it. However, we can also change the hardware on the camera itself -- specifically, the lens. That will distort the picture we see through the camera: a wider lens will cause us to see more, and a narrower one will cause us to see less.</p>

<p>The way that OpenGL works with regard to projection and modelview matrices is similar to the camera analogy. The modelview matrix allows us to apply <strong>transformations</strong> -- specifically, position and rotation offsets -- to the objects in the scene. The projection matrix allows us to apply transformations -- specifically, field of view adjustments -- to the "camera" which is "filming" the scene.</p>

<p>You may have noticed I didn't say anything about applying position and rotation offsets to the <em>camera</em> itself. The camera analogy, while useful, isn't actually quite correct. A better analogy would be this: let's say you're the Greek god of Earth, Atlas. A bit strange, admittedly, but stick with me here. For whatever reason, you've been confined to live in a box for all eternity. It's pitch black in the box, except for one window cut in the side you're facing from which you can look out to the world beyond. You could even say your view of the world is clipped by the window. So here you sit, window and world before, nowhere to go, sanity waning by the second. One day you decide you've had it -- you're tired of seeing the same thing over and over! You want to see more of the world! What do you do? Well, you can't move closer to the window. But hey, you're Atlas! You can physically <em>move the world around you</em>. So that's what you do. If you want to see left, you move the world right. If you want to see up, you move the world down. If you want to see more of something, you simply pull the world closer to you. In a similar way, you can even rotate the world around you. As you experiment turning the world this way and that, bringing it closer and pushing it away, moving it left and right -- for a split second, you're almost convinced that you're the one doing the moving instead of the world itself. After all, the effect is practically the same, except for the fact that you have to invert the movement and rotation directions. But hey! You're moving around! This excites you to no end, and you traverse the earth forevermore.</p>

<p>As this, er, story illustrates, the modelview matrix is not only used to position and rotate objects in the scene, it's also used to position and rotate the camera around too. But remember that the camera doesn't actually exist -- you just have a window to the world. So if you want to apply transformations to the "camera", you actually apply them to the world, and because of this you have to remember to invert the directions.</p>

<p>So that takes care of the modelview matrix. Let's go back to the projection matrix. I mentioned before that this matrix changes how you see the world, and that you can distort the field of view of the scene as though you have a camera and you can change the lens on that camera. As you can probably guess, this analogy isn't correct, either, but why? Well, in this case, it assumes that you see the world in a <strong>perspective projection</strong>, where objects farther away appear smaller and objects closer appear larger (and lines that go toward the horizon appear closer together). "Is there another way to see the world?" you ask. Yes, there is, and it's called <strong>orthographic projection</strong>. It's kind of the opposite of perspective projection: objects will appear the same size regardless of how far away or close they are. Essentially, in this mode, one dimension is removed from your three-dimensional scene, and so you end up with a two-dimensional picture (which can look quite odd if you are expecting the other dimension).</p>

<p>So there are different modes that change how the world is viewed, which means there must be a more accurate way to look at the OpenGL projection model. This would be the viewing area, or the <em>"viewbox"</em> as I like to call it. Let's take a step back and imagine that everything we see in the scene -- how far we can see and how wide we can see -- is enclosed by a box. Furthermore, imagine that how we perceive reality, specifically how near and far things appear, is governed by the shape of that box. For our everyday perspective view, what would the shape of this box be? It turns out that it is a <em>frustum</em>, which is kind of like a pyramid on its side, with the pointy end cut off. If "I" am looking down the box -- because there's no way I can look outside it, because it encloses whatever I see -- the smaller end of the box is closer to me, and the bigger end of the box, the end that slants outward, is farther away. So if there is an object in my view, and it starts at the smaller end of the box and moves along the box -- as it moves into the screen -- it will appear to shrink in size because it is taking up less space proportionally inside the box. (It's a bit backwards, I know, but realize that what OpenGL is trying to do here is take the location of this object and map it to a pixel location on your screen.)</p>

<p>So that creates a perspective effect. What would it look like if our viewbox were "normal" -- that is, if none of its edges were slanted, if it were a perfect rectangular solid? Well, then we'd have orthographic projection, because as objects moved through the box, they wouldn't grow or shrink, they'd remain exactly the same size.</p>

<p>For more on the projection and modelview matrices in OpenGL, see:</p>

<ul><li><a href="http://glprogramming.com/red/chapter03.html">Chapter 3 in the Red Book</a></li>
  <li><a href="http://www.songho.ca/opengl/gl_projectionmatrix.html">Song Ho Ahn's "OpenGL Projection Matrix" article</a></li>
  <li><a href="http://www.euclideanspace.com/threed/rendering/opengl/index.htm">"OpenGL Rendering" on euclideanspace.com</a></li>
</ul><h3 id="matrices">Matrices</h3>

<p>Now that you know more about the projection and modelview matrices in OpenGL, let's return to the code snippet I gave earlier:</p>

<pre><code>private static void init() {
  ...
  // Initialize the projection matrix (viewbox).
  glMatrixMode(GL_PROJECTION);
  glLoadIdentity();
  // ... Use glFrustum(), gluPerspective(), glOrtho() or gluOrtho2D() to customize the projection matrix ...
  ...
}

private static void render() {
  ...
  // Initialize the modelview matrix (camera / objects).
  glMatrixMode(GL_MODELVIEW);
  glLoadIdentity();
  // Now customize it.
  glRotatef(...);
  glTranslatef(...);
  ...
}
</code></pre>

<p>That brings us to the <strong><tt>glLoadIdentity()</tt></strong> method -- what does this do? To understand this, I'm going to talk for a bit about matrices.</p>

<p>A <a href="http://en.wikipedia.org/wiki/Matrix_(mathematics)"><strong>matrix</strong></a> is a mathematical concept that is nothing more than a table of values. A matrix can be of any size. 4×4 matrices are common in OpenGL programming, so here is an example of one:</p>

<div>{{math::block}}
\begin{bmatrix}
 0.0 &amp; 2.2 &amp; 3.0 &amp; 1.7 \\
 3.0 &amp; 6.5 &amp; 9.4 &amp; 1.1 \\
 5.0 &amp; 1.6 &amp; 6.9 &amp; 2.3 \\
 7.5 &amp; 4.6 &amp; 9.0 &amp; 3.1
\end{bmatrix}
{{/math::block}}</div>

<p>Logically, a matrix is divided into rows and columns. You read and refer to values within matrices from top to bottom, left to right. So to locate 5.0 in the matrix I just gave, we first find the row, then the column; in this case it's at row 1, column 3 (which we can write numerous ways, such as <span>{{math::inline}}M_{1,3}{{/math::inline}}</span>).</p>

<p>In OpenGL, a matrix is typically represents a sequence of <em>vectors</em>. I may talk about vectors later, but for now, I'll say that you are probably used to seeing vectors in tuple notation, like this: <span>{{math::inline}}(1, 2, 3){{/math::inline}}</span>. This tuple we can also write it as a matrix -- either as a column vector like this:</p>

<div>{{math::block}}
\begin{bmatrix}
 1 \\
 2 \\
 3
\end{bmatrix}
{{/math::block}}</div>

<p>or as a row vector like this:</p>

<div>{{math::block}}
\begin{bmatrix}
 1 &amp; 2 &amp; 3
\end{bmatrix}
{{/math::block}}</div>

<p>Usually matrices are read as a sequence of row vectors, but OpenGL matrices are read as a sequence of column vectors. (The technical name for this is <em>column-major order</em>, as opposed to <em>row-major order</em>.)</p>

<p>There are several operations you can perform on matrices. You can add two matrices together:</p>

<div>{{math::block}}
\begin{bmatrix}
 1 &amp; 4 \\
 2 &amp; 5 \\
 3 &amp; 6
\end{bmatrix}
+
\begin{bmatrix}
 4 &amp; 7 \\
 5 &amp; 8 \\
 6 &amp; 9
\end{bmatrix}
=
\begin{bmatrix}
 1 + 4 &amp; 4 + 7 \\
 2 + 5 &amp; 5 + 8 \\
 3 + 6 &amp; 6 + 9
\end{bmatrix}
=
\begin{bmatrix}
 5 &amp; 11 \\
 7 &amp; 13 \\
 9 &amp; 15
\end{bmatrix}
{{/math::block}}</div>

<p>or subtract them (which of course is just the inverse of adding them):</p>

<div>{{math::block}}
\begin{bmatrix}
 1 &amp; 4 \\
 2 &amp; 5 \\
 3 &amp; 6
\end{bmatrix}
-
\begin{bmatrix}
 4 &amp; 7 \\
 5 &amp; 8 \\
 6 &amp; 9
\end{bmatrix}
=
\begin{bmatrix}
 1 - 4 &amp; 4 - 7 \\
 2 - 5 &amp; 5 - 8 \\
 3 - 6 &amp; 6 - 9
\end{bmatrix}
=
\begin{bmatrix}
 -3 &amp; -3 \\
 -3 &amp; -3 \\
 -3 &amp; -3
\end{bmatrix}
{{/math::block}}</div>

<p>Also, you can multiply a matrix by a singular value. This has the effect of scaling the matrix (and for this reason the other value is called a <em>scalar</em>, and this type of multiplication is called <em>scalar multiplication</em>):</p>

<div>{{math::block}}
\begin{bmatrix}
 1 &amp; 4 \\
 2 &amp; 5 \\
 3 &amp; 6
\end{bmatrix}
\times
3
=
\begin{bmatrix}
 3 \times 1 &amp; 3 \times 4 \\
 3 \times 2 &amp; 3 \times 5 \\
 3 \times 3 &amp; 3 \times 6
\end{bmatrix}
=
\begin{bmatrix}
 3 &amp; 12 \\
 6 &amp; 15 \\
 9 &amp; 18
\end{bmatrix}
{{/math::block}}</div>

<p>In the same way, you can also divide a matrix by a scalar value (which is of course the same as multiplying by the reciprocal).</p>

<p>Finally, you can also multiply two matrices together. This is the main way you'll work with matrices in OpenGL, so you want to make sure you have this down pat. Unfortunately the way you typically see it is rather confusing, but I'll show you it anyway so you know what to look for. So let's say we have this equation:</p>

<div>{{math::block}}
\begin{bmatrix}
 9 &amp; 1 &amp; 3 \\
 7 &amp; 2 &amp; 10 \\
 0 &amp; 3 &amp; 8
\end{bmatrix}
\times
\begin{bmatrix}
 3 &amp; 5 &amp; 1 \\
 9 &amp; 2 &amp; 0 \\
 4 &amp; 6 &amp; 5
\end{bmatrix}
=
\begin{bmatrix}
 ? &amp; ? &amp; ? \\
 ? &amp; ? &amp; ? \\
 ? &amp; ? &amp; ?
\end{bmatrix}
{{/math::block}}</div>

<p>As you can see, multiplying two 3×3 matrices will produce a third 3×3 matrix. You'll see why in a second, but to find the product, the idea here is that you start by taking the first row vector in the first matrix and the first column vector in the second matrix, and compute the <a href="http://en.wikipedia.org/wiki/Dot_products">dot product</a> between them to obtain a scalar value. So in this case it'd look like this:</p>

<div>{{math::block}}
(9, 1, 3) \cdot (3, 9, 4)
{{/math::block}}</div>

<p>To find the dot product of two vectors, we multiply corresponding elements of each vector and then sum them up, like this:</p>

<div>{{math::block}}
(9, 1, 3) \cdot (3, 9, 4) = (9 \times 3 + 1 \times 9 + 3 \times 4) = 27 + 9 + 12 = 48
{{/math::block}}</div>

<p>Okay, so our first value is 48, and that goes in row 1, column 1 of our resulting matrix:</p>

<div>{{math::block}}
\begin{bmatrix}
 9 &amp; 1 &amp; 3 \\
 7 &amp; 2 &amp; 10 \\
 0 &amp; 3 &amp; 8
\end{bmatrix}
\times
\begin{bmatrix}
 3 &amp; 5 &amp; 1 \\
 9 &amp; 2 &amp; 0 \\
 4 &amp; 6 &amp; 5
\end{bmatrix}
=
\begin{bmatrix}
 48 &amp; ? &amp; ? \\
 ? &amp; ? &amp; ? \\
 ? &amp; ? &amp; ?
\end{bmatrix}
{{/math::block}}</div>

<p>At this point, I always forget what the next step is. Do I move down to the next row in the first matrix and dot-multiply it by the first column in the second matrix; or do I move across to the second column in the second matrix and dot-multiply it by the first row in the first matrix?</p>

<p>You're probably confused too, so let's start over, this time using a <a href="http://en.wikipedia.org/wiki/Matrix_multiplication#Illustration">handy trick</a>:</p>

<div>{{math::block}}
\begin{matrix}
  &amp;
  \begin{bmatrix}
   3 &amp; 5 &amp; 1 \\
   9 &amp; 2 &amp; 0 \\
   4 &amp; 6 &amp; 5
  \end{bmatrix}
  \\
  \begin{bmatrix}
   9 &amp; 1 &amp; 3 \\
   7 &amp; 2 &amp; 10 \\
   0 &amp; 3 &amp; 8
  \end{bmatrix}
  &amp;
  \begin{bmatrix}
   ? &amp; ? &amp; ? \\
   ? &amp; ? &amp; ? \\
   ? &amp; ? &amp; ?
  \end{bmatrix}
\end{matrix}
{{/math::block}}</div>

<p>Okay! Now we can clearly see that row vectors in matrix 1 get dot-multiplied by column vectors in matrix 2. We don't have to worry about order -- we just have to fill in the question marks. So let's do that:</p>

<div>{{math::block}}
\begin{array}{ll}
  &amp;
  \begin{bmatrix}
   \hspace{70px}3 &amp; \hspace{160px}5 &amp; \hspace{160px}1\hspace{64px} \\
   \hspace{70px}9 &amp; \hspace{160px}2 &amp; \hspace{160px}0\hspace{64px} \\
   \hspace{70px}4 &amp; \hspace{160px}6 &amp; \hspace{160px}5\hspace{64px}
  \end{bmatrix}
  \\
  \begin{bmatrix}
   9 &amp; 1 &amp; 3 \\
   7 &amp; 2 &amp; 10 \\
   0 &amp; 3 &amp; 8
  \end{bmatrix}
  &amp;
  \begin{bmatrix}
   (9(3) + 1(9) + 3(4)) &amp; (9(5) + 1(2) + 3(6)) &amp; (9(1) + 1(0) + 3(5)) \\
   (7(3) + 2(9) + 10(4)) &amp; (7(5) + 2(2) + 10(6)) &amp; (7(1) + 2(0) + 3(5)) \\
   (0(3) + 3(9) + 8(4)) &amp; (0(5) + 3(2) + 8(6)) &amp; (0(1) + 3(0) + 8(5))
  \end{bmatrix}
\end{array}
{{/math::block}}</div>

<p>Great, now we can simplify the resulting matrix:</p>

<div>{{math::block}}
\begin{bmatrix}
  27 + 9 + 12 &amp; 45 + 2 + 18 &amp; 9 + 0 + 15 \\
  21 + 18 + 40 &amp; 35 + 4 + 60 &amp; 7 + 0 + 15 \\
  0 + 12 + 32 &amp; 0 + 6 + 48 &amp; 0 + 0 + 40
\end{bmatrix}
=
\begin{bmatrix}
  48 &amp; 65 &amp; 24 \\
  79 &amp; 99 &amp; 22 \\
  44 &amp; 54 &amp; 40
\end{bmatrix}
{{/math::block}}</div>

<p>And now that we have our answer, we know why multiplying a 3×3 matrix by another 3×3 matrix will produce a third 3×3 matrix.</p>

<p>So that's pretty cool. What if we multiply a 3×3 matrix by, say, a 2×2 matrix? If we use the trick we used above, we can easily find out:</p>

<div>{{math::block}}
\begin{matrix}
  &amp;
  \begin{bmatrix}
   2 &amp; 1 \\
   0 &amp; 4
  \end{bmatrix}
  \\
  \begin{bmatrix}
   1 &amp; 3 &amp; 2 \\
   5 &amp; 2 &amp; 4 \\
   3 &amp; 0 &amp; 1
  \end{bmatrix}
  &amp;
  \begin{bmatrix}
   ? &amp; ? \\
   ? &amp; ? \\
   ? &amp; ?
  \end{bmatrix}
\end{matrix}
{{/math::block}}</div>

<p>So, a 3×3 matrix times a 2×2 matrix will produce a 2×3 matrix.</p>

<p>Okay, now for something a bit different. Let's say we take the 3×3 matrix we just used in the last example and multiply it by the following 3×3 matrix:</p>

<div>{{math::block}}
\begin{bmatrix}
  1 &amp; 0 &amp; 0 \\
  0 &amp; 1 &amp; 0 \\
  0 &amp; 0 &amp; 1
\end{bmatrix}
{{/math::block}}</div>

<p>Let's find out:</p>

<div>{{math::block}}
\begin{array}{ll}
  &amp;
  \begin{bmatrix}
   \hspace{70px}1 &amp; \hspace{145px}0 &amp; \hspace{145px}0\hspace{75px} \\
   \hspace{70px}0 &amp; \hspace{145px}1 &amp; \hspace{145px}0\hspace{75px} \\
   \hspace{70px}0 &amp; \hspace{145px}0 &amp; \hspace{145px}1\hspace{75px}
  \end{bmatrix}
  \\
  \begin{bmatrix}
   1 &amp; 3 &amp; 2 \\
   5 &amp; 2 &amp; 4 \\
   3 &amp; 0 &amp; 1
  \end{bmatrix}
  &amp;
  \begin{bmatrix}
   (1(1) + 3(0) + 2(0)) &amp; (1(0) + 3(0) + 2(0)) &amp; (1(0) + 3(0) + 2(1)) \\
   (5(1) + 2(0) + 4(0)) &amp; (5(0) + 2(0) + 4(0)) &amp; (5(0) + 2(0) + 4(1)) \\
   (3(1) + 0(0) + 1(0)) &amp; (3(0) + 0(0) + 1(0)) &amp; (3(0) + 0(0) + 1(1))
  \end{bmatrix}
\end{array}
{{/math::block}}</div>

<p>And simplifying:</p>

<div>{{math::block}}
\begin{bmatrix}
  1 + 0 + 0 &amp; 0 + 3 + 0 &amp; 0 + 0 + 2 \\
  5 + 0 + 0 &amp; 0 + 2 + 0 &amp; 0 + 0 + 4 \\
  3 + 0 + 0 &amp; 0 + 0 + 0 &amp; 0 + 0 + 1
\end{bmatrix}
=
\begin{bmatrix}
  1 &amp; 3 &amp; 2 \\
  5 &amp; 2 &amp; 4 \\
  3 &amp; 0 &amp; 1
\end{bmatrix}
{{/math::block}}</div>

<p>How about that! We got the same matrix we started with. This isn't coincidence. It turns out the new matrix we used as a factor in this example has a special name: the <strong>identity matrix</strong>. As you can guess, it's called this because if you take any matrix and multiply it by the identity matrix of the same size, you'll get back an identical matrix.</p>

<p>Now, an identity matrix isn't just 3×3; it can be any size, as long as the diagonal values running from top-left to bottom-right are all 1's, and the rest of the values are 0's. So here's a 4×4 identity matrix:</p>

<div>{{math::block}}
\begin{bmatrix}
  1 &amp; 0 &amp; 0 &amp; 0 \\
  0 &amp; 1 &amp; 0 &amp; 0 \\
  0 &amp; 0 &amp; 1 &amp; 0 \\
  0 &amp; 0 &amp; 0 &amp; 1
\end{bmatrix}
{{/math::block}}</div>

<p>And that's the basics of matrices. If you want to learn more, see:</p>

<ul><li><a href="http://en.wikipedia.org/wiki/Matrix_(mathematics)">Matrix</a> (Wikipedia)</li>
  <li><a href="http://en.wikipedia.org/wiki/Matrix_multiplication">Matrix multiplication</a> (Wikipedia)</li>
  <li><a href="http://www.khanacademy.org/video/introduction-to-matrices?playlist=Linear%20Algebra">Introduction to Matrices</a> from the Khan Academy</li>
  <li><a href="http://www.khanacademy.org/video/matrix-multiplication--part-1?playlist=Linear%20Algebra">Matrix multiplication</a> from the Khan Academy (starting at 4:58)</li>
  <li><a href="http://www.flipcode.com/documents/matrfaq.html">Matrix FAQ</a> (Flipcode)</li>
</ul><h3 id="details-of-the-transformation-matrices">Details of the transformation matrices</h3>

<p>So let's return once more to the following lines in our LWJGL skeleton code:</p>

<pre><code>private static void init() {
  ...
  // Initialize the projection matrix (viewbox).
  glMatrixMode(GL_PROJECTION);
  glLoadIdentity();
  // ... Use glFrustum(), gluPerspective(), glOrtho() or gluOrtho2D() to customize the projection matrix ...
  ...
}

private static void render() {
  ...
  // Initialize the modelview matrix (camera / objects).
  glMatrixMode(GL_MODELVIEW);
  glLoadIdentity();
  // Now customize it.
  glRotatef(...);
  glTranslatef(...);
  ...
}
</code></pre>

<p>As I mentioned, OpenGL keeps two matrices: one for the projection and one for the modelview. These are 4×4 matrices. The projection matrix, as I've mentioned before, describes the shape of the viewbox. You don't really need to know what the values in the matrix are. The modelview matrix, which keeps track of translation and rotation, is probably what you'll be working with most of the time. Technically, you don't need to know what these values are, either, but it should be interesting to you (at least it is to me). It looks like this:</p>

<div>{{math::block}}
\begin{align}
  &amp;\begin{matrix}
    \hspace{12px}\text{left} &amp; \text{up} &amp; \text{forward} &amp; \text{pos}
  \end{matrix}
  \\
  &amp;\begin{bmatrix}
    m_0 &amp; m_4 &amp; \hspace{14px}m_8    &amp; \hspace{13px}m_{12} \\
    m_1 &amp; m_5 &amp; \hspace{14px}m_9    &amp; \hspace{13px}m_{13} \\
    m_2 &amp; m_6 &amp; \hspace{14px}m_{10} &amp; \hspace{13px}m_{14} \\
    m_3 &amp; m_7 &amp; \hspace{14px}m_{11} &amp; \hspace{13px}m_{15}
  \end{bmatrix}
\end{align}
{{/math::block}}</div>

<p>So you can visualize the modelview matrix as three vectors -- one parallel to the X axis (<em>left</em>), one parallel to the Y axis (<em>up</em>), and one parallel to the Z axis (<em>forward</em>) -- originating from a single point in space (<em>pos</em>).</p>

<p>Now, when you look at this matrix, you may wonder why OpenGL keeps a 4×4 matrix instead of a 3×3 matrix. After all, we have three dimensions here, so you should only need three values for each of <em>left</em>, <em>up</em>, <em>forward</em>, and <em>pos</em>, right? Well, it turns out that OpenGL coordinates actually have four dimensions: <span>{{math::inline}}x{{/math::inline}}</span>, <span>{{math::inline}}y{{/math::inline}}</span>, <span>{{math::inline}}z{{/math::inline}}</span>, and <span>{{math::inline}}w{{/math::inline}}</span>. This <span>{{math::inline}}w{{/math::inline}}</span> coordinate is called the <a href="http://www.songho.ca/math/homogeneous/homogeneous.html">homogenous coordinate</a>. Why do we need it? Remember that one of the basic goals a rendering engine achieves is to take game coordinates and (through some complex math) convert them to screen coordinates. This is called projection. It turns out that using three dimensions is not sufficient to do this properly. In fact, doing so will fail spectacularly in the case where you have to render two parallel lines. Now in math, you know that if two lines are parallel, it means that they will never touch. However, if you ever took an art class where you were given an exercise to draw something in <a href="http://images.google.com/images?hl=en&amp;gbv=2&amp;tbs=isch:1&amp;q=one+point+perspective+drawing&amp;revid=1198099626&amp;sa=X&amp;ei=FI-XTaqnM8XcgQeZ9sDHCA&amp;ved=0CDMQ1QIoAA&amp;biw=1280&amp;bih=680">one-point perspective</a> -- perhaps a downtown scene in some fictitious city, where you are looking down the street and there are buildings all along the side -- you know this is not true. The scene, at least in the real world, continues infinitely into the horizon, but obviously we are working with a finite medium, so we need a way to represent this visually. The way to do that is to pick a point on the horizon, the vanishing point, toward which all the lines in the drawing converge.</p>

<p>A rendering engine has to figure out how to draw this sort of scene too; the only difference is that it has to know how to refer to all the points in the scene (so that it can convert them to screen coordinates). This means we have to have a name for the vanishing point (in 3D space). If we had a line going straight down the <em>z</em> axis, conceptually, this would be <span>{{math::inline}}(0, 0, -\infty){{/math::inline}}</span>. Obviously, working with infinity from a mathematical standpoint isn't really feasible, so we need some other way to represent this. This is where the extra <span>{{math::inline}}w{{/math::inline}}</span> coordinate comes into play. It goes like this: if we have a four-dimensional point <span>{{math::inline}}(x, y, z, w){{/math::inline}}</span>, its three-dimensional equivalent is <span>{{math::inline}}(\frac{x}{w}, \frac{y}{w}, \frac{z}{w}){{/math::inline}}</span>. Now look what happens when <span>{{math::inline}}w{{/math::inline}}</span> = 0: we get a three-dimensional vector <span>{{math::inline}}(\frac{x}{0}, \frac{y}{0}, \frac{z}{0}){{/math::inline}}</span>, which, if converted to three dimensions, becomes <span>{{math::inline}}(\infty, \infty, \infty){{/math::inline}}</span>. So OpenGL works with four-dimensional vectors for as long as it can until it needs to convert them to three dimensions.</p>

<h3 id="applying-transformations">Applying transformations</h3>

<p>So far I've been talking abstractly, but I'm sure you're dying to get to down to business. So what are the ways you can work with the transformation matrices, and what exactly happens?</p>

<p>As there are multiple matrices, logically, the very first thing we have to do is tell OpenGL which one we want to work with. We do this with <tt>glMatrixMode()</tt>:</p>

<pre><code>glMatrixMode(GL_PROJECTION);
...
glMatrixMode(GL_MODELVIEW);
...
</code></pre>

<p>(There are actually a couple of other matrices you can use, but we won't worry about those right now.)</p>

<p>Unless you're doing something special, you always want to start your matrix out with the identity matrix, which, if you forgot, looks like this:</p>

<div>{{math::block}}
\begin{bmatrix}
  1 &amp; 0 &amp; 0 &amp; 0 \\
  0 &amp; 1 &amp; 0 &amp; 0 \\
  0 &amp; 0 &amp; 1 &amp; 0 \\
  0 &amp; 0 &amp; 0 &amp; 1
\end{bmatrix}
{{/math::block}}</div>

<p>So, you can set a transformation matrix to the identity matrix with <tt>glLoadIdentity()</tt>.</p>

<p>At long last, you can apply transformations to each matrix. First is the projection matrix. Earlier I talked about perspective projection and orthographic projection, and how both set the shape of the viewbox in different ways. You can tell OpenGL to use orthographic projection with <tt>glOrtho()</tt>. Here you simply specify the coordinates of the vertices of the viewbox:</p>

<pre class="java"><code>glOrtho(double left, double right, double bottom, double top, double near, double far)
</code></pre>

<p>In other words, <tt>left</tt> and <tt>right</tt> are <em>x</em>-values, <tt>bottom</tt> and <tt>top</tt> are <em>y</em>-values, and <tt>near</tt> and <tt>far</tt> are <em>z</em>-values. To switch to perspective projection, you use <tt>glFrustum()</tt>. Again, you specify the vertices of the viewbox:</p>

<pre class="java"><code>glFrustum(double left, double right, double bottom, double top, double near, double far)
</code></pre>

<p>Note that in this case, you'll probably have to manually calculate the coordinates so that you end up with a box with properly slanted edges. No one really does this because it's kind of hard; instead people generally use <tt>gluPerspective()</tt>, from the GLU module, which makes this job much easier. So now instead of vertices, you specify a field-of-view angle, an aspect ratio (which will be the width of the viewbox divided by its height), and then the <tt>near</tt> and <tt>far</tt> values:</p>

<pre class="java"><code>gluPerspective(double fovy, double aspect, double near, double far)
</code></pre>

<p>So that's the projection matrix. What about the modelview matrix? There are three operations you can perform: translation, rotation, and scaling. Translation is pretty easy, it's just the offset position. As you may be working with either floats or doubles, there are versions for each:</p>

<pre class="java"><code>glTranslatef(float x, float y, float z)
glTranslated(double x, double y, double z)
</code></pre>

<p>Rotation is achieved by specifying an angle and an axis along which you want to perform the rotation as a unit vector (i.e., <span>{{math::inline}}(1, 0, 0){{/math::inline}}</span>, <span>{{math::inline}}(0, 1, 0){{/math::inline}}</span>, or <span>{{math::inline}}(0, 0, 1){{/math::inline}}</span>):</p>

<pre class="java"><code>glRotatef(float angle, float x, float y, float z)
glRotated(float angle, double x, double y, double z)
</code></pre>

<p>Finally, scaling, where you specify a factor which every coordinate will be multiplied by:</p>

<pre class="java"><code>glScalef(float x, float y, float z)
glScaled(double x, double y, double z)
</code></pre>

<p>To close this section, I wanted to briefly talk about what happens when you use any of these functions. You might initially think that with, for instance, <tt>gluPerspective()</tt> or <tt>glTranslate()</tt>, you are overwriting whatever is in the current matrix. This isn't true, though: you are actually <em>multiplying</em> what is there with other values (using matrix multiplication, which I showed you earlier). This should actually make sense for the modelview matrix, because this is what makes it possible to apply multiple transformations in succession. So you could have something like this:</p>

<pre class="java"><code>float x, y, z, rotx, roty, rotz;

glTranslatef(x, y, z);
glRotatef(rotx, 1, 0, 0);
glRotatef(roty, 0, 1, 0);
glRotatef(rotz, 0, 0, 1);
// ... draw your object(s) ...
</code></pre>

<p>Now, something you will probably not realize is that when the modelview matrix is applied to the objects in your scene (specifically, their vertices) to calculate their final position and rotation (again using matrix multiplication) the transformation is applied <em>in reverse</em>. What I mean is that if you say</p>

<pre class="java"><code>glTranslatef(x, y, z);
glRotatef(rotx, 1, 0, 0);
// ... draw an object ...
</code></pre>

<p>the rotation will be applied to your object first, then the translation. In math terms <a href="http://www.songho.ca/opengl/gl_transform.html">it would look like this</a>:</p>

<div>{{math::block}}
v' = M_{rotation} \cdot M_{translation} \cdot v
{{/math::block}}</div>

<p>This may or may not affect your program, but it's definitely something to watch out for.</p>

<p>For completeness, I should also talk about <tt>glPushMatrix()</tt> and <tt>glPopMatrix()</tt>. If you want to apply a transform to a single object in your scene without affecting the rest of the scene, you need a way to localize the transformation in your code. You do this with transformation stacks. Basically, the idea is that you call <tt>glPushMatrix()</tt> which copies the current matrix to a new space in memory and pushes it onto the stack. From there you can apply whatever transformations you'd like, and you can even push another matrix onto the stack if you'd like. When you're done with the matrix, you pop it off with <tt>glPopMatrix()</tt> and you are returned to the matrix you had before. (You may already be familiar with this from another rendering engine. I know for a fact that you can do this in Canvas, so I think it's pretty common.)</p>

<p>To learn more about the details of the transformation matrices, see:</p>

<ul><li><a href="http://www.songho.ca/opengl/gl_transform.html">Song Ho Ahn's "OpenGL Transformation" article</a></li>
  <li><a href="http://en.wikibooks.org/wiki/OpenGL_Programming/3D/Matrices">"Matrices" at the OpenGL Programming Wiki</a></li>
  <li><a href="http://www.opengl.org/sdk/docs/man/">OpenGL Documentation</a></li>
</ul><hr /><p>If you read this far, wow! You are a trooper. Hopefully it was as interesting to you as it was to me. While I can't call myself an expert on OpenGL by any means, I have done quite a bit of research (and I'm learning more every time I revisit the pages I've mentioned), so if anything in this article wasn't clear to you, feel free to contact me and I'll do my best to answer.</p>

<p>That does it for me. In the next post, we're going to talk about handling input and setting up an FPS-style camera/movement system. Stay tuned!<span class="end-of-content">☯</span></p>
      </content>
      <published>2011-04-02T00:00:00-07:00</published>
      <updated>2011-04-02T00:00:00-07:00</updated>
    </entry>
  
    
    <entry>
      <id>tag:lostincode.net,2011-03-27:post/minecraft-client-java-and-ant</id>
      <link rel="alternate" href="http://lostincode.net/blog/minecraft-client-java-and-ant" />
      <title type='html'>Making a Minecraft client: Java and Ant</title>
      <excerpt type='xhtml'>
        <p>Getting a Java/LWJGL project working, and learning about Ant along the way.</p>

        <p class='more'><a href="http://lostincode.net/blog/minecraft-client-java-and-ant">read the rest &#0187;</a></p>
      </excerpt>
      <content type='xhtml'>
        <p>Hello again! I'm not dead, I'm still working on the Minecraft client. I just decided not to be quite so diligent about writing a post as I went along. In fact for the past two weeks I've been caught up in figuring out how to implement a typical FPS camera/movement system in OpenGL.</p>

<p>But more on that later -- let me catch you up on what I've gone through so far.</p>

<hr /><p>In my <a href="http://lostincode.net/minecraft-client-clojure">last post</a>, I wondered about the possibility of using Clojure and an OpenGL wrapper library called Penumbra to give me a place to start. Unfortunately, that panned out, partly because Penumbra depended on some non-existent libraries, and partly because of my unfamiliarity with Clojure's tools for managing dependencies and, ultimately, the Java ecosystem itself.</p>

<p>I will probably come back to Clojure in some way, but for now, I've decided to go straight to Java and figure it out from that angle (since Java seems to be one of the two languages, the other being C++, that have the most mature bindings for OpenGL). There are two popular libraries that sit on top of OpenGL that are used for making games: JOGL and LWJGL. Minecraft itself actually uses LWJGL (there's even a tagline on the boot menu that reveals this very fact), so I figured, if it's good enough for Minecraft, it's good enough for me. Some of the <a href="http://www.lwjgl.org/wiki/index.php?title=About_LWJGL">goals of LWJGL</a> -- debunking the myth that Java is and will always be slow; making it small so it can be used on portable devices; removing unneeded complexity and things game programmers don't need because it makes sense and so that developers can get up and running fast -- certainly seemed like good things. So, I decided, LWJGL was the way to go.</p>

<hr /><p>I started out by downloading and running some of the <a href="http://potatoland.org/code/gl/">LWJGL demos on potatoland.org</a>. There's a zip file you can download that contains LWJGL already, so following the README inside, in order to run a demo, all I had to do was this:</p>

<pre class="prompt"><code>$ java -cp .:lwjgl.jar:lwjgl_util.jar gldemo/GLApp_Demo_HelloWorld
</code></pre>

<p>The demos are pretty decent; they're actually documented, which is much less than I can say about most OpenGL stuff I've seen. Unfortunately a lot of the code depends on convenience classes that do a lot of stuff to configure the world and set up cameras and add vectors and things -- too much if you're just starting out.</p>

<p>So, I went off to look for some simpler examples. There's a <a href="http://www.lwjgl.org/wiki/index.php?title=Links_and_Resources">page on the LWJGL wiki</a> that links to a few sites, and of those is the <a href="http://ninjacave.com/tutorials">tutorials on ninjacave.com</a>, which gave some example code that looked good to try out.</p>

<p>First, though, I wanted to set up a new project in which to run the examples. That meant, of course, I had to <a href="http://www.lwjgl.org/download.php">download LWJGL</a>. I then made a new project and copied the files into the project. If you do it yourself, when you extract the zip file, you will see two folders, <tt>jar/</tt> and <tt>native/</tt> -- one contains .jar files and the other contains dynamic libraries which are specific to your OS. You will need to require both in your application -- <a href="http://www.lwjgl.org/wiki/index.php?title=Downloading_and_Setting_Up_LWJGL">that's just how it works</a>). So, I just made a <tt>lib/</tt> folder in my project and copied both <tt>jar/</tt> and <tt>native/</tt> into it.</p>

<p>Then I copied the code in the first tutorial on ninjacave ("The Display") and pasted it into a new .java file I'd created in <tt>src/</tt>. Of course, it's been a while since I've done Java stuff, so I had to re-learn how to compile a Java file and then run it, but I also learned about the classpath and the <tt>-D</tt> argument. As the <a href="http://www.lwjgl.org/wiki/index.php?title=Downloading_and_Setting_Up_LWJGL">page on the LWJGL wiki</a> says, you have to tell Java about not only the LWJGL jars, but also about the path to the native library files as well. These were the magic words:</p>

<pre class="prompt"><code>$ cd src
$ javac -cp .:../lib/jar/lwjgl.jar:../lib/jar/lwjgl_util.jar:../lib/jar/jinput.jar LWJGL_DisplayExample
$ java -cp .:../lib/jar/lwjgl.jar:../lib/jar/lwjgl_util.jar:../lib/jar/jinput.jar -Djava.library.path=../lib/native/macosx LWJGL_DisplayExample
</code></pre>

<p>That worked, so I tried out the rest of the ninjacave demos, which worked too. So that was great, except I didn't like the commands I had to type to run a demo -- not only were they unrememberable, but there was a noticeable duplication of the classpath. Surely there was a way I could run one short command and it would run both of these commands. I <em>could</em> write a shell script, I thought, but it seemed like this was one of those sorts of things for which Java people had figured out a good solution early on. <!--The C/C++ world certainly had: it was called make. (And of course let's not forget Ruby's version, Rake.) Was there an equivalent tool in Java?--></p>

<p>I don't know a whole lot about Java, but do know of two names that I see all the time: <a href="http://maven.apache.org/">Maven</a> and <a href="http://ant.apache.org/">Ant</a>. In working with Clojure, I'd noticed that Maven (which, as you remember, Leiningen uses as its foundation), includes a dependency manager, so right away that told me it was probably more than what I needed, which was just a simple way to run tasks. <sup id="fnref:fn1"><a href="http://lostincode.net#fn:fn1" rel="footnote">1</a></sup> So then I looked into Ant, and sure enough, it fit the bill pretty nicely.</p>

<!--*It took me a while to get going here (links are provided at the end), so I'm going to talk about Ant for the rest of this post; if you want to skip to the [next post](/minecraft-client-opengl-camera) where I get more into OpenGL, go right ahead.*-->

<hr /><p>As you might have guessed, Ant is basically a version of make for Java (and somewhat like Ruby's version, Rake). Basically, you specify the tasks that you want to run in a file called <tt>build.xml</tt>. (Yes, you write the tasks in XML, which, coming from Ruby, is definitely an interesting way to give instructions. At the same time, the Ant team has clearly tried to make writing the <tt>build.xml</tt> short and sweet, which I appreciate.) At the top level of the XML is a <tt>&lt;project&gt;</tt> node which tells Ant a little about your project, and under that are <tt>&lt;target&gt;</tt> nodes which are like make targets in that they let you group tasks together into steps. Ant provides a plethora of tasks you can run, from things like filesystem operations to compiling source files and creating jars.</p>

<p>So, taking a step back, what did I want to be able to do? I basically needed a "compile" task which would call <tt>javac</tt> and a "run" task that would call <tt>java</tt>, and they needed to call <tt>javac</tt> and <tt>java</tt> exactly how I'd called them before. I also needed "clean" and "prepare" tasks which would ensure that the directory in which the .class files would be generated, <tt>build/</tt>, was cleaned out before the compile task ran. With this in mind I came up with a simple <tt>build.xml</tt>:</p>

<pre><code>&lt;project name="lwjgl_tests" default="jar"&gt;
  &lt;target name="init"&gt;
    &lt;property name="sourceDir" value="src" /&gt;
    &lt;property name="libDir" value="lib" /&gt;
    &lt;property name="outputDir" value="build" /&gt;
  &lt;/target&gt;

  &lt;target name="clean" depends="init"&gt;
    &lt;deltree dir="${outputDir}" /&gt;
  &lt;/target&gt;

  &lt;target name="prepare" depends="clean"&gt;
    &lt;mkdir dir="${outputDir}" /&gt;
  &lt;/target&gt;

  &lt;target name="compile" depends="prepare"&gt;
    &lt;javac srcdir="${sourceDir}" destdir="${outputDir}" classpath="${libDir}/jar/lwjgl.jar:${libDir}/jar/lwjgl_util.jar:${libDir}/jar/jinput.jar" /&gt;
  &lt;/target&gt;

  &lt;target name="jar" depends="compile"&gt;
    &lt;jar destfile="lwjgl_tests.jar" includes="${outputDir}/**/*.class" /&gt;
  &lt;/target&gt;
&lt;/project&gt;
</code></pre>

<p>One small problem: I'd called <tt>javac</tt> before with a <tt>-D</tt> argument. How could I specify that? Well, Java calls this a <em>system property</em>. The <a href="http://ant.apache.org/manual/Tasks/jar.html">documentation for the "jar" task</a> shows that there's a way to specify this, so my <tt>build.xml</tt> changed to this:</p>

<pre><code>&lt;project name="lwjgl_tests" default="jar"&gt;
  &lt;target name="init"&gt;
    &lt;property name="sourceDir" value="src" /&gt;
    &lt;property name="libDir" value="lib" /&gt;
    &lt;property name="outputDir" value="build" /&gt;
  &lt;/target&gt;

  &lt;target name="clean" depends="init"&gt;
    &lt;deltree dir="${outputDir}" /&gt;
  &lt;/target&gt;

  &lt;target name="prepare" depends="clean"&gt;
    &lt;mkdir dir="${outputDir}" /&gt;
  &lt;/target&gt;

  &lt;target name="compile" depends="prepare"&gt;
    &lt;javac srcdir="${sourceDir}" destdir="${outputDir}" classpath="${libDir}/jar/lwjgl.jar:${libDir}/jar/lwjgl_util.jar:${libDir}/jar/jinput.jar" /&gt;
  &lt;/target&gt;

  &lt;target name="jar" depends="compile"&gt;
    &lt;jar destfile="lwjgl_tests.jar" includes="${outputDir}/**/*.class" /&gt;
  &lt;/target&gt;

  &lt;target name="run"&gt;
    &lt;java classname="lwjgl_tests" classpath="lwjgl_tests.jar" fork="true"&gt;
      &lt;sysproperty key="java.library.path" value="${libDir}/native/macosx" /&gt;
    &lt;/java&gt;
  &lt;/target&gt;
&lt;/project&gt;
</code></pre>

<p>Okay, cool. Now I could run <tt>ant</tt>, and that would hopefully generate the jar file:</p>

<pre class="prompt"><code>$ ant
Buildfile: /Users/elliot/code/personal/test/java/lwjgl_tests/build.xml

init:

clean:
  [deltree] DEPRECATED - The deltree task is deprecated.  Use delete instead.

prepare:
    [mkdir] Created dir: /Users/elliot/code/personal/test/java/lwjgl_tests/build

compile:
    [javac] /Users/elliot/code/personal/test/java/lwjgl_tests/build.xml:17: warning: 'includeantruntime' was not set, defaulting to build.sysclasspath=last; set to false for repeatable builds
    [javac] Compiling 2 source files to /Users/elliot/code/personal/test/java/lwjgl_tests/build

jar:
    [jar] Building jar: /Users/elliot/code/personal/test/java/lwjgl_tests/build/jar/lwjgl_tests.jar

BUILD SUCCESSFUL
</code></pre>

<p>I checked <tt>build/jar/</tt> to confirm that indeed <tt>lwjgl_tests.jar</tt> had been written to it. So it worked!</p>

<p>About the warnings, I wasn't sure what <tt>includeantruntime</tt> meant, or if that was even important, but the <tt>deltree</tt> task was at least easy to change:</p>

<pre><code>&lt;project name="lwjgl_tests" default="jar"&gt;
  &lt;target name="init"&gt;
    &lt;property name="sourceDir" value="src" /&gt;
    &lt;property name="libDir" value="lib" /&gt;
    &lt;property name="outputDir" value="build" /&gt;
  &lt;/target&gt;

  &lt;target name="clean" depends="init"&gt;
    &lt;delete dir="${outputDir}" /&gt;
  &lt;/target&gt;

  &lt;target name="prepare" depends="clean"&gt;
    &lt;mkdir dir="${outputDir}" /&gt;
  &lt;/target&gt;

  &lt;target name="compile" depends="prepare"&gt;
    &lt;javac srcdir="${sourceDir}" destdir="${outputDir}" classpath="${libDir}/jar/lwjgl.jar:${libDir}/jar/lwjgl_util.jar:${libDir}/jar/jinput.jar" verbose="true" /&gt;
  &lt;/target&gt;

  &lt;target name="jar" depends="compile"&gt;
    &lt;jar destfile="lwjgl_tests.jar" includes="${outputDir}/**/*.class" /&gt;
  &lt;/target&gt;

  &lt;target name="run"&gt;
    &lt;java classname="lwjgl_tests" classpath="lwjgl_tests.jar" fork="true"&gt;
      &lt;sysproperty key="java.library.path" value="${libDir}/native/macosx" /&gt;
    &lt;/java&gt;
  &lt;/target&gt;
&lt;/project&gt;
</code></pre>

<p>Cool. So now that I had a jar generated, I could run it:</p>

<pre class="prompt"><code>$ ant run
run:
     [java] Exception in thread "main" java.lang.NoClassDefFoundError: lwjgl_tests
     [java] Java Result: 1
</code></pre>

<p>Oops! That didn't work because I had told clearly told Ant in the <tt>java</tt> task that the name of the class within the jar it was to run was called "lwjgl_tests", which was not the case.</p>

<p>Actually, since I had a collection of Java files in my project, the class name was variant, so there wasn't any point in hard-coding it in <tt>build.xml</tt>. Unfortunately, the <tt>java</tt> task, <a href="http://ant.apache.org/manual/Tasks/java.html">as detailed in the Ant docs</a>, requires that you pass either a <tt>classname</tt> or <tt>jar</tt> attribute. Obviously I couldn't use the <tt>classname</tt> attribute, but I couldn't use the <tt>jar</tt> attribute either, since that (sans the <tt>classpath</tt> attribute) would be equivalent to saying</p>

<pre class="prompt"><code>$ java lwjgl_tests.jar
</code></pre>

<p>which assumes that your jar file has a Main-Class entry in the manifest inside the jar file. In other words, in order for this to work, your jar file must have one class that starts off the program, and in this case, I didn't have one. So I'd have to remove the <tt>java</tt> task. That was okay, I thought -- I'd just specify the class name on the command line.</p>

<p>So my <tt>build.xml</tt> now looked like:</p>

<pre><code>&lt;project name="lwjgl_tests" default="jar"&gt;
  &lt;target name="init"&gt;
    &lt;property name="sourceDir" value="src" /&gt;
    &lt;property name="libDir" value="lib" /&gt;
    &lt;property name="outputDir" value="build" /&gt;
  &lt;/target&gt;

  &lt;target name="clean" depends="init"&gt;
    &lt;delete dir="${outputDir}" /&gt;
  &lt;/target&gt;

  &lt;target name="prepare" depends="clean"&gt;
    &lt;mkdir dir="${outputDir}" /&gt;
  &lt;/target&gt;

  &lt;target name="compile" depends="prepare"&gt;
    &lt;javac srcdir="${sourceDir}" destdir="${outputDir}" classpath="${libDir}/jar/lwjgl.jar:${libDir}/jar/lwjgl_util.jar:${libDir}/jar/jinput.jar" verbose="true" /&gt;
  &lt;/target&gt;

  &lt;target name="jar" depends="compile"&gt;
    &lt;jar destfile="lwjgl_tests.jar" includes="${outputDir}/**/*.class" /&gt;
  &lt;/target&gt;
&lt;/project&gt;
</code></pre>

<p>So, I ran <tt>ant</tt> again and then tried running the resulting jar file manually:</p>

<pre class="prompt"><code>$ ant
...
BUILD SUCCESSFUL
...
$ java -cp lwjgl_tests.jar LWJGL_DisplayExample
Exception in thread "main" java.lang.NoClassDefFoundError: LWJGL_DisplayExample
</code></pre>

<p>What was I doing wrong here? I tried extracting the jar file to get a sense of what was in it:</p>

<pre class="prompt"><code>$ mkdir tmp
$ cd tmp
$ jar xf ../lwjgl_tests.jar
</code></pre>

<p>Upon inspection, I realized it just contained a META-INF folder. So basically, it was empty. Hmm.</p>

<p>After thinking about it for a bit, I realized this: in following a <a href="http://ideoplex.com/id/10/ant-hello-world-revisited">tutorial</a>, I had noticed that the <tt>jar</tt> task in the tutorial had a <tt>basedir</tt> attribute, but I'd intentionally left it out, because I thought you didn't need it (surely Ant would figure out that the current directory was the base directory). As an experiment, I added it back to <tt>build.xml</tt>, re-ran <tt>ant</tt>, and checked the jar again, and it contained class files, as I expected. (So, you do need <tt>basedir</tt> after all.)</p>

<p>Now my <tt>build.xml</tt> looked like:</p>

<pre><code>&lt;project name="lwjgl_tests" default="jar"&gt;
  &lt;target name="init"&gt;
    &lt;property name="sourceDir" value="src" /&gt;
    &lt;property name="libDir" value="lib" /&gt;
    &lt;property name="outputDir" value="build" /&gt;
  &lt;/target&gt;

  &lt;target name="clean" depends="init"&gt;
    &lt;delete dir="${outputDir}" /&gt;
  &lt;/target&gt;

  &lt;target name="prepare" depends="clean"&gt;
    &lt;mkdir dir="${outputDir}" /&gt;
  &lt;/target&gt;

  &lt;target name="compile" depends="prepare"&gt;
    &lt;javac srcdir="${sourceDir}" destdir="${outputDir}" classpath="${libDir}/jar/lwjgl.jar:${libDir}/jar/lwjgl_util.jar:${libDir}/jar/jinput.jar" verbose="true" /&gt;
  &lt;/target&gt;

  &lt;target name="jar" depends="compile"&gt;
    &lt;jar basedir="." destfile="lwjgl_tests.jar" includes="${outputDir}/**/*.class" /&gt;
  &lt;/target&gt;
&lt;/project&gt;
</code></pre>

<p>I then tried running the program again, but got the same error as before:</p>

<pre class="prompt"><code>$ java -cp lwjgl_tests.jar LWJGL_DisplayExample
Exception in thread "main" java.lang.NoClassDefFoundError: LWJGL_DisplayExample
</code></pre>

<p>So, it was back to research. After another half an hour, in which I found <a href="http://ant.apache.org/manual/tutorial-HelloWorldWithAnt.html">couple</a> of <a href="http://ant.apache.org/faq.html#passing-cli-args">documents</a> on the Ant site, I basically revamped <tt>build.xml</tt> and ended up with this:</p>

<pre><code>&lt;project name="lwjgl_tests" default="jar" basedir="."&gt;
  &lt;property name="src.dir"     value="src" /&gt;
  &lt;property name="lib.dir"     value="lib" /&gt;
  &lt;property name="build.dir"   value="build" /&gt;
  &lt;property name="classes.dir" value="${build.dir}/classes" /&gt;
  &lt;property name="jar.dir"     value="${build.dir}/jar" /&gt;

  &lt;path id="classpath"&gt;
    &lt;fileset dir="${lib.dir}/jar" includes="lwjgl.jar,lwjgl_util.jar,jinput.jar" /&gt;
  &lt;/path&gt;

  &lt;target name="clean"&gt;
    &lt;delete dir="${build.dir}" /&gt;
  &lt;/target&gt;

  &lt;target name="compile" depends="clean"&gt;
    &lt;mkdir dir="${classes.dir}" /&gt;
    &lt;javac srcdir="${src.dir}" destdir="${classes.dir}" classpathref="classpath" verbose="true" /&gt;
  &lt;/target&gt;

  &lt;target name="jar" depends="compile"&gt;
    &lt;mkdir dir="${jar.dir}" /&gt;
    &lt;jar basedir="${classes.dir}" destfile="${jar.dir}/${ant.project.name}.jar" /&gt;
  &lt;/target&gt;

  &lt;target name="run"&gt;
    &lt;java fork="true" classname="${classname}"&gt;
      &lt;classpath&gt;
        &lt;path refid="classpath"/&gt;
        &lt;path location="${jar.dir}/${ant.project.name}.jar"/&gt;
      &lt;/classpath&gt;
      &lt;sysproperty key="java.library.path" value="${lib.dir}/native/macosx" /&gt;
    &lt;/java&gt;
  &lt;/target&gt;
&lt;/project&gt;
</code></pre>

<p>With that, the full Ant routine now worked, and I could say:</p>

<pre class="prompt"><code>$ ant run -Dclassname=LWJGL_InputExample
</code></pre>

<p>which would clear <tt>build/</tt>, compile the files in src/ and place the .class files in <tt>build/classes/</tt>, package them up into a jar within <tt>build/jar/</tt>, and then run <tt>LWJGL_InputExample.java</tt> within the jar. If you closely compare this <tt>build.xml</tt> with the previous version, you may notice the difference, which (apart from an alternate way to specify the classpath) sets the <tt>basedir</tt> of the jar file to <tt>build/classes/</tt> instead of the current directory. I can't say for sure as I can't quite remember, but I think this is what fixed the <tt>java</tt> command so that it successfully ran.</p>

<p>In any case, I had a build routine working and I could forge ahead with setting up an OpenGL project, which I will talk about in the next post! <span class="end-of-content">☯</span><span class="end-of-content">☯</span></p>

<h3 id="resources">Resources</h3>

<ul><li><a href="http://www.javaworld.com/jw-10-2000/jw-1020-ant.html?page=1">http://www.javaworld.com/jw-10-2000/jw-1020-ant.html?page=1</a></li>
  <li><a href="http://ideoplex.com/focus/java">http://ideoplex.com/focus/java</a></li>
  <li><a href="http://ant.apache.org/manual/index.html">http://ant.apache.org/manual/index.html</a></li>
</ul><h3 id="footnotes">Footnotes</h3>

<div class="footnotes">
  <ol><li id="fn:fn1">
      <p>In writing this blog post, I've looked a bit further into Maven. Ant was fine for what I needed, but Maven certainly seems like it's the more established way to set up a Java project. You can basically think of it as Ant on steroids (in a good way). For one, it provides ways to do projecty things like generate documentation and publish to an SCM. It also provides a fully-featured dependency manager, which would be pretty useful if you had a project that didn't ship with the library it was using (my project does include LWJGL so it isn't necessary). Finally, it also offers a plugin system so that you can simply download and use tasks (Maven calls them goals) that other people have written, which is pretty cool.<a href="http://lostincode.net#fnref:fn1" rev="footnote">↩</a></p>
    </li>
  </ol></div>
      </content>
      <published>2011-03-27T00:00:00-07:00</published>
      <updated>2011-03-27T00:00:00-07:00</updated>
    </entry>
  
    
    <entry>
      <id>tag:lostincode.net,2011-02-27:post/minecraft-client-clojure</id>
      <link rel="alternate" href="http://lostincode.net/blog/minecraft-client-clojure" />
      <title type='html'>Making a Minecraft client: Clojure and Penumbra</title>
      <excerpt type='xhtml'>
        <p>In which I look into Clojure (for the first time), and try to get an OpenGL Clojure library working.</p>

        <p class='more'><a href="http://lostincode.net/blog/minecraft-client-clojure">read the rest &#0187;</a></p>
      </excerpt>
      <content type='xhtml'>
        <p>In my last post I wanted to start making something with the v8-gl, but ran into a wall because of a hole in the bridge code. In attempting to patch this hole, I got fed up with the lack of documentation that v8 has and eventually decided to ditch v8 altogether and look for another solution.</p>

<p>Maybe writing it in Javascript isn't the best idea. For one, I've already mentioned that v8 has zero documentation, but I'm sure SpiderMonkey ain't roses, either -- it must be a beast, judging from how long it's been around. Anyway, the whole Javascript space is still evolving, and I doubt there are many people who use it as a runtime outside of the browser for serious stuff.</p>

<p>So, what are some other languages that have OpenGL bindings? Well, I was mentioning to some people on Twitter the other day how I've always wanted to learn Clojure. A quick search leads to me to <a href="https://github.com/ztellman/penumbra">Penumbra</a>, which takes an idiomatic approach to OpenGL integration. Now we're talking! And hey, it looks like <a href="http://briancarper.net/blog/520/making-an-rpg-in-clojure-part-one-of-many">more</a> than <a href="http://ideolalia.com/creating-a-simple.-game-in-clojure">one</a> person has attempted to make a game in Clojure using OpenGL, anyway. This is really great. Who cares if Clojure runs on the JVM? Again, if I can get <em>something</em> working with relative ease, then I'll be happy. This is an experiment, after all.</p>

<p>So, let's play around with Penumbra. First we need to install Clojure. You can download it from the <a href="http://clojure.org/downloads">Clojure web site</a> of course, but there's also a Homebrew formula that's up to date, so I install that. The formula tells me that if I have the <tt>repl</tt> formula installed, there's a file I might want to use that involves rlwrap. It looks like a wrapper script for something, but I'm not sure what it does, so I just skip it for now.</p>

<p>Immediately I wonder if there's a REPL. There is, but you have to say <tt>java -cp clojure.jar clojure.main</tt>. I probably won't remember that, so I make a shortcut:</p>

<pre><code>#!/bin/bash
java -cp $(brew --prefix clojure)/clojure.jar clojure.main
</code></pre>

<p>I save that to <tt>~/.bin/clj</tt> (<tt>~/.bin</tt> is in my path), <tt>chmod +x clj</tt> and now I can do:</p>

<pre class="prompt"><code>$ clj
Clojure 1.2.0
user=&gt; (* 12345678 12345678)
152415765279684
user=&gt; "string"
"string"
user=&gt; 'symbol
symbol
user=&gt; :keyword
:keyword
</code></pre>

<p>Alright, that's enough of that. Let's see if we can run a Penumbra example -- say, the <a href="https://github.com/ztellman/penumbra/blob/master/test/example/game/asteroids.clj">Asteroids one</a>. Hmm, how do we run a file? Scanning the Clojure site, I see that clojure.main does that, too -- you just give the filename on the command line, after the <tt>clojure.main</tt> bit. So that's cool, but I don't like how the REPL doesn't have any line history. To do that, you can use JLine, <a href="http://clojure.org/getting_started">like this</a>:</p>

<pre class="prompt"><code>$ java -cp jline-0_9_5.jar:clojure.jar jline.ConsoleRunner clojure.main
</code></pre>

<p>Of course we'll have to provide the full path to clojure.jar, but I imagine that we won't have to do it for JLine if we put it in Java's classpath. <tt>~/Library/Java/Extensions</tt> is one of the locations that's already in the classpath, although checking it, I notice I already have it there (I probably did it when I installed JRuby). So, now we have to modify our shell script to support multiple arguments:</p>

<pre><code>#!/bin/bash
java -cp jline-0_9_5.jar:$(brew --prefix clojure)/clojure.jar jline.ConsoleRunner clojure.main $`
</code></pre>

<p>And now I can try this:</p>

<pre class="prompt"><code>$ clj
</code></pre>

<p>Hmm. That doesn't seem to be working; Java tells me it can't find <tt>clojure.main</tt>. <a href="https://groups.google.com/d/topic/clojure/rAFddOHJaxY/discussion">A thread in the Clojure mailing list</a> suggests that rlwrap is easier (and better) to use instead. There's a guide <a href="http://en.wikibooks.org/wiki/Clojure_Programming/Getting_Started#Enhancing_Clojure_REPL_with_rlwrap">here</a>. Ah, and at this point I realize that the <tt>clojure</tt> Homebrew formula already comes with a wrapper script for the REPL, located at <tt>/usr/local/Cellar/clojure/1.2.0/bin/clj</tt> (and aliased to <tt>/usr/local/bin/clj</tt>). The file it directed me to earlier replaces this with an rlwrap version (and whoever added this to the formula must've gotten it from the mailing list). So, let's just use that instead:</p>

<pre class="prompt"><code>$ rm ~/.bin/clj
</code></pre>

<p>And try again:</p>

<pre class="prompt"><code>$ clj
</code></pre>

<p>Unfortunately this doesn't work, either:</p>

<pre class="prompt"><code>Exception in thread "main" java.lang.NoClassDefFoundError: clojure/main
</code></pre>

<p>Gragh. Okay, I'm wasting time here -- I can live without line history. Let's just recreate <tt>~/.bin/clj</tt> and go with the following so we can get rolling:</p>

<pre><code>#!/bin/bash
java -cp $(brew --prefix clojure)/clojure.jar clojure.main $`
</code></pre>

<p>Now we should be able to try out that Asteroids demo:</p>

<pre class="prompt"><code>$ git clone https://github.com/ztellman/penumbra.git
$ cd penumbra
$ clj test/example/game/asteroids.clj
Exception in thread "main" java.io.FileNotFoundException: Could not locate penumbra/opengl__init.class or penumbra/opengl.clj on classpath:  (asteroids.clj:9)
</code></pre>

<p>Whoops! Hmm. I guess we'll need to tell Java about <tt>src/</tt>. That wrapper script wasn't very handy, was it? Let's try this:</p>

<pre class="prompt"><code>$ java -cp $(brew --prefix clojure)/clojure.jar:src clojure.main test/example/game/asteroids.clj
Exception in thread "main" java.io.FileNotFoundException: Could not locate clojure/contrib/def__init.class or clojure/contrib/def.clj on classpath:  (core.clj:9)
</code></pre>

<p>Seriously?! <em>(Insert <a href="http://encyclopediadramatica.com/RAGE">rage face</a> here)</em></p>

<p>On to the <a href="https://groups.google.com/d/topic/penumbra-lib">Penumbra mailing list</a>, then. There Zach Tellman <a href="https://groups.google.com/d/topic/penumbra-lib/TtxW1qxfmjE/discussion">suggests to run <tt>lein repl</tt></a>. <tt>lein</tt>, as I learn, is <a href="https://github.com/technomancy/leiningen">Leiningen</a>, which is kind of a dependency installer / toolkit for Clojure projects. So, I download it like the README says, put it in <tt>~/.bin/lein</tt>, and run <tt>lein repl</tt> from the Penumbra directory. Leiningen goes off and does its magic, which is kind of neat to watch, until I get this error:</p>

<pre class="prompt"><code>$ lein repl
An error has occurred while processing the Maven artifact tasks.
 Diagnosis:

Unable to resolve artifact: Missing:
----------
1) org.clojure:clojure-contrib:jar:1.1.0-master-SNAPSHOT
...
</code></pre>

<p>At first I think it just failed to download a file (I was in a coffee shop when I ran this command, so it was possible). Can I retry the command? Sure, with <tt>lein deps</tt>.</p>

<pre class="prompt"><code>$ lein deps
An error has occurred while processing the Maven artifact tasks.
 Diagnosis:

Unable to resolve artifact: Missing:
----------
1) org.clojure:clojure-contrib:jar:1.1.0-master-SNAPSHOT
...
</code></pre>

<p>Frack. Okay, well, there's a <a href="http://stackoverflow.com/questions/5048911/lein-spitting-out-weird-errors">Stack Overflow thread</a> that mentions this issue, and one of the answerers said it worked with "today's Leiningen", which I assume means HEAD. So let's just replace <tt>~/.bin/lein</tt> with the version at <a href="https://github.com/technomancy/leiningen/raw/master/bin/lein">https://github.com/technomancy/leiningen/raw/master/bin/lein</a> and try <tt>lein deps</tt> again:</p>

<pre class="prompt"><code>$ lein deps
Failed to download https://github.com/downloads/technomancy/leiningen/leiningen-1.5.0-SNAPSHOT-standalone.jar
See README.md for SNAPSHOT build instructions.
</code></pre>

<p>So, I look at the README (again), but at this point I really don't want to go through the trouble of using Maven to install Leiningen manually.</p>

<p>Hmm, I just noticed there's a Homebrew package for Leiningen, so let's try that. First I probably want to remove the version I just tried to install, which I can do by removing <tt>~/.lein</tt> (or, at least, that removes the version of itself that it caches). I'm going to guess Homebrew's formula installs stuff in the same place. If not, no big deal.</p>

<p>Okay, so I try <tt>lein deps</tt> one more time:</p>

<pre class="prompt"><code>$ lein deps
Unable to resolve artifact: Missing:
----------
1) org.clojure:clojure-contrib:jar:1.1.0-master-SNAPSHOT
...
  Path to dependency:
    1) org.apache.maven:super-pom:jar:2.0
    2) autodoc:autodoc:jar:0.7.1
    3) org.clojure:clojure-contrib:jar:1.1.0-master-SNAPSHOT
</code></pre>

<p>WTF. Srsly.</p>

<p>So I do some more snooping, and find <a href="https://groups.google.com/forum/#!topic/clojure/zpZ776UaieA">this thread</a> on the Clojure mailing list. It looks like what's going on here is that autodoc 0.7.1 depends on clojure-contrib 1.1.0, which was actually removed from build.clojure.org. It suggests that autodoc 0.8.0 may work, but it's not on Clojars (for who knows what reason). So, there is actually a way to specify that certain subdependencies of dependencies you've put in project.clj that would ordinarily get installed, should not get installed. So for Penumbra, we can edit project.clj, which usually looks like this:</p>

<pre class="lisp"><code>(defproject penumbra "0.6.0-SNAPSHOT"
  :description "An idiomatic wrapper for OpenGL"
  :dependencies [[slick-util "1.0.0"]
                 [cantor "0.2.1"]
                 [org.clojure/clojure "1.2.0"]
                 [org.clojure/clojure-contrib "1.2.0"]]
  :native-dependencies [[penumbra/lwjgl "2.4.2"]]
  :dev-dependencies [[native-deps "1.0.4"]
                     [autodoc "0.7.1"]
                     [lein-clojars "0.5.0-SNAPSHOT"]
                     [leiningen/lein-swank "1.1.0"]])
</code></pre>

<p>and force-remove clojure and clojure-contrib from the autodoc dependencies. Through trial and error I notice I also have to do the same for lein-swank too, so we end up with:</p>

<pre class="lisp"><code>(defproject penumbra "0.6.0-SNAPSHOT"
  :description "An idiomatic wrapper for OpenGL"
  :dependencies [[slick-util "1.0.0"]
                 [cantor "0.2.1"]
                 [org.clojure/clojure "1.2.0"]
                 [org.clojure/clojure-contrib "1.2.0"]]
  :native-dependencies [[penumbra/lwjgl "2.4.2"]]
  :dev-dependencies [[native-deps "1.0.4"]
                     [autodoc "0.7.1" :exclusions [org.clojure/clojure-contrib org.clojure/clojure]]
                     [lein-clojars "0.5.0-SNAPSHOT"]
                     [leiningen/lein-swank "1.1.0"]])

(defproject penumbra "0.6.0-SNAPSHOT"
  :description "An idiomatic wrapper for OpenGL"
  :dependencies [[slick-util "1.0.0"]
                 [cantor "0.2.1"]
                 [org.clojure/clojure "1.2.0"]
                 [org.clojure/clojure-contrib "1.2.0"]]
  :native-dependencies [[penumbra/lwjgl "2.4.2"]]
  :dev-dependencies [[native-deps "1.0.4"]
                     [autodoc "0.7.1" :exclusions [org.clojure/clojure-contrib org.clojure/clojure]]
                     [lein-clojars "0.5.0-SNAPSHOT"]
                     [leiningen/lein-swank "1.1.0" :exclusions [org.clojure/clojure-contrib org.clojure/clojure]]])
</code></pre>

<p>So, that makes <tt>lein deps</tt> work. At this point we should be able to finally run the example... right? Nope. Same error as before:</p>

<pre class="prompt"><code>$ java -cp $(brew --prefix clojure)/clojure.jar:src clojure.main test/example/game/asteroids.clj
Exception in thread "main" java.io.FileNotFoundException: Could not locate clojure/contrib/def__init.class or clojure/contrib/def.clj on classpath:  (core.clj:9)
</code></pre>

<p>Argh. Am I doing something wrong? Oh, scrolling up in my terminal, it looks like lein placed the dependencies in lib. So I need to add that to the classpath:</p>

<pre class="prompt"><code>$ java -cp $(brew --prefix clojure)/clojure.jar:src:lib clojure.main test/example/game/asteroids.clj
Exception in thread "main" java.io.FileNotFoundException: Could not locate clojure/contrib/def__init.class or clojure/contrib/def.clj on classpath:  (core.clj:9)
</code></pre>

<p>That doesn't work neither. But wait! I remember that Zach what's-his-face said we need to run <tt>lein repl</tt>. So let's do that:</p>

<pre class="prompt"><code>$ lein repl
REPL started; server listening on localhost:17223.
user=&gt;
</code></pre>

<p>Well that's... interesting. Obviously, it worked, which is good. So what do we do now? Here the <a href="https://groups.google.com/d/topic/penumbra-lib/NSvZ8j5mx5I/discussion">Penumbra mailing list</a> gives me an idea:</p>

<pre class="prompt"><code>$ lein repl
REPL started; server listening on localhost:17223.
user=&gt; (require 'example.game.asteroids)
java.lang.ClassNotFoundException: org.lwjgl.opengl.GL11 (core.clj:9)
</code></pre>

<p>Okay, now we're getting somewhere -- that's more of what I was expecting. I guess it would make sense that LWJGL, which is what Penumbra uses, isn't going to get installed automatically.</p>

<p>Unfortunately, I'm out of time, so I'll have to pick this up later. Anyway, it's clear that I'm not going to be able to get Penumbra working until I'm more familiar with lein, or even Java. Maybe I need to see if I can get a quick OpenGL program up and running with Java first (either via JOGL or lwjgl). Then, I can take that and port it straight to Clojure (like <a href="http://lifeofaprogrammergeek.blogspot.com/2009/04/opengl-in-clojure.html">this</a>, or <a href="http://blog.felixbreuer.net/2010/12/20/pengl.html">this</a>). One way or another, I'll figure this out.<span class="end-of-content">☯</span></p>
      </content>
      <published>2011-02-27T00:00:00-08:00</published>
      <updated>2011-02-27T00:00:00-08:00</updated>
    </entry>
  
    
    <entry>
      <id>tag:lostincode.net,2011-02-25:post/minecraft-client-v8-gl</id>
      <link rel="alternate" href="http://lostincode.net/blog/minecraft-client-v8-gl" />
      <title type='html'>Making a Minecraft client: v8 and OpenGL</title>
      <excerpt type='xhtml'>
        <p>In my last post I started thinking about which Javascript engine to use, and concluded that since I haven't had much experience with OpenGL, I'd better start out with that. ~~~ I found a v8-to-OpenGL bridge called <a href="https://github.com/philogb/v8-gl">v8-gl</a>, which I decided to try out. So, following the instructions I compiled it:</p>
        <p class='more'><a href="http://lostincode.net/blog/minecraft-client-v8-gl">read the rest &#0187;</a></p>
      </excerpt>
      <content type='xhtml'>
        <p>In my last post I started thinking about which Javascript engine to use, and concluded that since I haven't had much experience with OpenGL, I'd better start out with that. ~~~ I found a v8-to-OpenGL bridge called <a href="https://github.com/philogb/v8-gl">v8-gl</a>, which I decided to try out. So, following the instructions I compiled it:</p>

<pre class="prompt"><code>$ cd v8-gl
$ svn co http://v8.googlecode.com/svn/trunk/ v8
$ cd v8
$ scons mode=release
# Whoops! Don't have scons, let's use Homebrew:
$ brew install scons
# Rockin' and rollin'
$ scons mode=release
$ cd ..
$ make
</code></pre>

<p>Now I could run the example:</p>

<pre class="prompt"><code>$ ./v8-gl examples/example2.js
</code></pre>

<p>(Wow, I thought, it actually worked. That's a first.)</p>

<p>I looked at the other files in <tt>examples/</tt>. There was one that drew a simple triangle, and one that attempted to use textures (but they didn't show up -- I think the files were missing), and one that drew a spinning icosahedron (which was the same example on the project page), and there's also a rather impressive demo that flew through a tunnel made of metaballs.</p>

<p>The spinning icosahedron was the easiest example to grok. It all looked to me like a straight port from C/C++ code, though. I decided what I really needed was some basics on OpenGL, GLUT, and possibly shaders.</p>

<p>There are, as you might expect, quite a few tutorials on OpenGL by now. I skimmed through a bit of <a href="http://en.wikibooks.org/wiki/OpenGL_Programming">this one</a> and found it to be useful than some of the others, so that's the one I started out with.</p>

<p>One thing I learned is that there are actually two flavors (more like eras) of OpenGL. There's the 1.x/2.x line, in which you start by creating a window, initializing the window, initializing the frame buffer, then you draw some primitives and so forth. OpenGL 3.0 completely rehauled the API, deprecating per-vertex rendering and shading/texturing in favor of vertex buffers and shaders. <a href="http://stackoverflow.com/questions/1282041/is-it-better-to-skip-opengl-2-x-and-start-learning-opengl-3-x">(1)</a> <a href="http://pyopengl.sourceforge.net/documentation/deprecations.html">(2)</a> The thing about it is, there are myriad tutorials on 1.x/2.x-style OpenGL, but not so many on 3.x/4.x. The good thing in this case, I guess, is that v8-gl targets 2.1, so getting started wouldn't be a big deal (I thought).</p>

<p>As I started converting one of the tutorials on the wikibooks area, I realized I didn't know that much about GLUT (which is what actually provides window and keyboard support), so I switched gears a bit and <a href="http://mindfuck.de-brauwer.be/articles/glut/">followed a tutorial from that angle</a>. I also found the <a href="http://www.opengl.org/resources/libraries/glut/spec3/spec3.html">GLUT docs</a> which were helpful.</p>

<p>Then I ran into a wall. I wanted to be able to close the GLUT window using the Escape key (because when the window opens, the close button is disabled). Now you <em>should</em> be able to do something like this:</p>

<pre class="cpp"><code>var windowId = Glut.createWindow();
...
Glut.destroyWindow(windowId);
</code></pre>

<p>But that wasn't working; <tt>Glut.destroyWindow()</tt> complained that I hadn't given it a window id. So I looked at the v8-gl source, and found that when it wraps <tt>glutCreateWindow()</tt> in a Javascript function, it doesn't forward the return value of <tt>glutCreateWindow()</tt> on; <tt>Glut.createWindow()</tt> just returns nothing!</p>

<pre class="cpp"><code>Handle&lt;Value&gt; GLUTCreateWindowCallback(const Arguments&amp; args) {
  //if less that nbr of formal parameters then do nothing
  if (args.Length() &lt; 1) return v8::Undefined();
  //get arguments
  String::Utf8Value value0(args[0]);
  char* arg0 = *value0;

  //make call
  glutCreateWindow((const char*)arg0);
  return v8::Undefined();
}
...
Glut-&gt;Set(String::NewSymbol("createWindow"), FunctionTemplate::New(GLUTCreateWindowCallback));
</code></pre>

<p>Ugh. Okay, maybe I could fix this. I'd have to learn more about the v8 C++ API, of course. The <a href="http://code.google.com/p/v8">v8 project page</a> <em>felt</em> like a good resource. I mean, you'd think that Google would have provided some helpful documentation so that people could hack on it. It's a project they've opened to the public, after all. But the project page is sparse -- there are short videos and articles about the motivation behind the project, and a small example of how to use access part of v8 in your embedding code. But wrapping C++ objects in Javascript objects? Sorry, you're on your own. And typically at this point I turn to the source code, but it's equally unhelpful, too.</p>

<p>Okay. Back to searching. I found <a href="http://altdevblogaday.com/change-is-as-good-as-a-holiday-an-introductio">this blog post</a> which showed how to make a global context object in Javascript-land, and then take objects and types you've made in C++-land and expose them to Javascript-land. While it was insightful, I got the feeling it wasn't going to help me.</p>

<p>I don't know that much about C++, but I'd gathered enough to know this: I couldn't simply change <tt>GLUTCreateWindowCallback()</tt> to <code>return glutCreateWindow((const char*)arg0)</code>, because then I'd be returning a C++-land object -- I needed to return a Javascript-land object (using v8's API). How one went about doing that, I had no idea.</p>

<p>I spent another half-hour skimming through the <a href="http://groups.google.com/group/v8-users">v8 mailing list</a>, but I was quickly getting the feeling that v8 is just a bitch to work with. I kept noticing the name of the guy who wrote <a href="http://code.google.com/p/v8-juice">v8-juice</a>, and he mentioned that v8-juice solved the problem of wrapping C++ objects, so I followed that. The nail in the coffin came when I read his <a href="http://code.google.com/p/v8-juice/wiki/CommentaryOnV8">commentary on v8</a>:</p>

<blockquote>
  <p>Another hindrance is the relative lack of v8 documentation. Most functions and classes aren't documented or have only a single line with no real information (e.g. what exactly does "Enters the context" mean?). This means a great deal of experimentation in order to find out if something will or won't work in v8 (and another amount of guesswork as to whether it's actually legal to do it that way in v8).</p>

  <p>Any library which is to enjoy widespread use must be well documented. It's a simple fact. History is full of libraries which thrive despite lacking docs (libexpat comes to mind), but i find that shameful.</p>
</blockquote>

<p>I do too.</p>

<p>So, v8 is out the window. It's kind of disappointing, actually; I was looking forward to trying out the speed.</p>

<p>So then we come back to <a href="http://code.google.com/p/jslibs/">jslibs</a>. I don't really care if runs on SpiderMonkey/JägerMonkey, as long as I can get <strong>something</strong> up.<span class="end-of-content">☯</span></p>
      </content>
      <published>2011-02-25T00:00:00-08:00</published>
      <updated>2011-02-25T00:00:00-08:00</updated>
    </entry>
  
    
    <entry>
      <id>tag:lostincode.net,2011-02-20:post/minecraft-client-ssjs-engines</id>
      <link rel="alternate" href="http://lostincode.net/blog/minecraft-client-ssjs-engines" />
      <title type='html'>Making a Minecraft client: Server-side Javascript engines</title>
      <excerpt type='xhtml'>
        <p>node.js? GlueScript? v8-juice? jslibs?</p>

        <p class='more'><a href="http://lostincode.net/blog/minecraft-client-ssjs-engines">read the rest &#0187;</a></p>
      </excerpt>
      <content type='xhtml'>
        <p>In my <a href="http://lostincode.net/blog/minecraft-client">last post</a> I started doing some initial research on writing a Minecraft client using Javascript. I indicated that I might start with the network code -- getting it to send and receive packets to and from a Minecraft server. In thinking about it some more, I realized that if I start with that, it would have to be a proxy rather than a client -- after all, there isn't any point in making a client that can communicate with a server if you can't see the results of that communication.</p>

<p>Anyway, the network code isn't the hardest part; it's the graphics, because I'm planning on using OpenGL and I've never worked with that before. So, I'm going to start there.</p>

<p>Something I haven't addressed yet is which server-side Javascript solution to use. To answer that question it's worth it to know the Javascript engines people are using and the ecosystems around them. Right now it's SpiderMonkey, Rhino, and v8. Both SpiderMonkey and v8 are C/C++-based, while Rhino runs on the JVM. Binding many of the server-side solutions is something called <a href="http://www.commonjs.org/">CommonJS</a>, which specifies an API that can be used for things like defining modules, requiring modules and the libraries they contain, and I/O access.</p>

<p>With that in mind, what have we got?</p>

<ul class="para"><li>Clearly the crowd favorite is <a href="http://nodejs.com">node.js</a>, which runs on v8 and implements the CommonJS module system. It's mainly targeted for applications where sending and receiving requests concurrently is core to the function of the application, as it uses an event-based concurrency model instead of the traditional thread-based model. Hence, it seems to be best suited for network-based applications that need to handle a high amount of traffic (the prime example being a web server). Even so, there's an <strong>insane</strong> amount of modules available for this thing already; some are kept in the <a href="http://search.npmjs.org/">npm registry</a>, and there are a lot more in this <a href="http://github.com/ry/node/wiki/modules">giant list</a>.</li>
  <li><a href="http://narwhaljs.org/">Narwhal</a> -- probably second -- is a Javascript platform that also implements the CommonJS module system. It runs best on Rhino, but it looks like there may also be support for v8 (not sure how mature it is, though). If your aim is to make web apps, <a href="http://jackjs.org/">Jack</a> and <a href="http://www.nitrojs.org/">Nitro</a> look pretty neat, and there are some <a href="http://narwhaljs.org/available-packages.html">packages</a> for doing web types of things. But I'm not, so let's move on.</li>
  <li><a href="http://ringojs.org/">Ringo</a> is a runtime/framework that runs on the JVM, but again, seems to be best suited for web apps. It uses the CommonJS 1.1 module system, with a custom approach to namespacing. There is a <a href="https://github.com/chl/ringo-processing">port of Processing</a>, though, which is interesting.</li>
  <li>Finally, there's <a href="http://www.jaxer.org/">Jaxer</a>, which seems to be kind of a hybrid solution, where you specify the code you want to run on the server side in client-side code. Kind of a neat idea, but otherwise, I'll pass.</li>
</ul><p>I'm sure I've missed some (now that I mention it, there are several more on the <a href="http://www.commonjs.org/impl/">CommonJS site</a>, such as <a href="http://gluescript.sourceforge.net/">GlueScript</a>), but the point is, it appears that all of these solutions are geared for making web applications, which makes sense, since that's where everything is heading these days. However, that's not quite what I want. I don't want the web app framework bits, but I do want the network code (because I am going to be working with the network at some point), and I also want all the CommonJS stuff (or at least some way to access the filesystem and do other basic things). Also, I'd prefer using v8 as opposed to SpiderMonkey or Rhino because let's face it, it's the fastest competitor right now. In that light, it looks like node.js is what I want to start with.</p>

<p>Let's say I didn't use node.js or any of that, though. Let's say I wanted to use v8 directly. What else is there? Well, <a href="http://code.google.com/p/v8-juice/wiki/HomePage">v8-juice</a>, <a href="https://github.com/tsa/vu8">vu8</a>, and <a href="https://github.com/sebastien/k7">k7</a> are all very similar in that they basically provide C++ bindings to v8 along with standard library components, with the goal of making it easy to write v8 modules. Interesting, but not what I want, either.</p>

<p>There's also <a href="http://code.google.com/p/jslibs/">jslibs</a>. This actually looks pretty interesting. It's not on v8 -- it uses SpiderMonkey -- but, it provides support for JägerMonkey engine, Mozilla's new competitor to v8, which is nice. And, there are wrappers for various libraries such as ODE, SDL, OpenGL, OpenAL, etc., which is even better. Maybe the only downside is that it doesn't use CommonJS, but actually, that's not a big deal -- I think the goal of CommonJS is so that, in theory, two platforms that use CommonJS can share code, but in practice I don't think that works so well. Hmm, actually, now that I look at it, the <a href="http://code.google.com/p/jslibs/wiki/jsgraphics">documentation</a> is pretty horrendous. Yeah, I'm going to have a hard time starting out with this.</p>

<p>That brings us back to OpenGL. As I mentioned before, I've never really worked with it before. From the sample code that I've seen, it seems like there's a bit of a learning curve in terms of the API and how you set things up and how you draw things to the screen. I mean, you just have to know how stuff works. I found a <a href="https://github.com/philogb/v8-gl">v8-to-OpenGL bridge</a> which looks pretty interesting and seems to be mature enough for playing around with. So it looks like that's my next task.<span class="end-of-content">☯</span></p>
      </content>
      <published>2011-02-20T00:00:00-08:00</published>
      <updated>2011-02-20T00:00:00-08:00</updated>
    </entry>
  
    
    <entry>
      <id>tag:lostincode.net,2011-02-16:post/minecraft-client</id>
      <link rel="alternate" href="http://lostincode.net/blog/minecraft-client" />
      <title type='html'>Starting to work on a Minecraft client</title>
      <excerpt type='xhtml'>
        <p>Nothing too serious yet, some just places to start.</p>

        <p class='more'><a href="http://lostincode.net/blog/minecraft-client">read the rest &#0187;</a></p>
      </excerpt>
      <content type='xhtml'>
        <p>I have decided, at the suggestions of my friends Levi and Tim, to see if I can write a Minecraft client using Javascript and OpenGL (or something similar) that will talk to a Minecraft server. I think Javascript is really starting to become a real player, so I'd like to see how it can handle graphics. Also, I've always been interested in game programming, and I've had trouble hooking onto something so far. Minecraft is probably one of the simplest 3D games at the top of the popularity chart in terms of code and graphics complexity, so maybe I have a shot at learning a few things, at least.</p>

<p>Tonight I did some initial research. In poking around the Minecraft forums and other places I have become aware of the huge modding community that exists around Minecraft. People make mods for all sorts of things -- adding other crafting recipes, changing the diffusion of light and how it's rendered, making it so it's day all the time -- you name it. How do these people write these mods? Well, it's all hacking, basically -- the common way to apply a mod is to download a tool that basically inserts code into your copy of Minecraft (the minecraft.jar file, to be exact). So I got thinking, if they're writing Java code, and they know which files in minecraft.jar to patch, then they must know what the .class files in minecraft.jar actually contain, which means they're using a Java decompiler to pop them open. It isn't hard to find <a href="http://java.decompiler.free.fr/">one</a>. Unfortunately, even if you crack open the .class files, you'll find that all the code is obfuscated -- Java classes are called "aa", "bb", "cc", etc. and functions are similarly generically named. This is where <a href="http://mcp.ocean-labs.de/index.php/MCP_Releases">Minecraft Coder Pack</a> comes in. All you do is drop minecraft.jar into the MCP folder, run a little script to decompile and de-obfuscate it, and voila, you've got all the source code to Minecraft.</p>

<p>So, reading through that was pretty enlightening. There's definitely a lot more code there than I thought. It's a bit much to take in all at once, though.</p>

<p>One of the first problems I need to solve is how the client is going to communicate with the server. It all comes down to simple packets, and there's a custom protocol that client and server adhere to. This is detailed here:</p>

<ul><li><a href="http://mc.kev009.com/Protocol">http://mc.kev009.com/Protocol</a></li>
  <li><a href="http://www.minecraftwiki.net/wiki/Classic_Server_Protocol">http://www.minecraftwiki.net/wiki/Classic_Server_Protocol</a></li>
</ul><p>That got me thinking, well, there must be people who've made Minecraft clients, or even servers, before -- maybe I could look at some code for ideas on how to implement the protocol. And of course, there are a jillion projects on the githubs. Here are just a sampling I found:</p>

<ul><li><a href="http://github.com/nornagon/nodecraft">http://github.com/nornagon/nodecraft</a> -- server in node.js</li>
  <li><a href="http://github.com/mkroman/metamine">http://github.com/mkroman/metamine</a> -- client in Ruby</li>
  <li><a href="http://github.com/duckicraft/minerubies">http://github.com/duckicraft/minerubies</a> -- start of a client in Ruby</li>
  <li><a href="http://github.com/calzoneman/uMiner">http://github.com/calzoneman/uMiner</a> -- server in C#</li>
  <li><a href="http://github.com/MostAwesomeDude/bravo">http://github.com/MostAwesomeDude/bravo</a> -- server in Python</li>
</ul><p>There are also people who've made proxies that sit between a client and server:</p>

<ul><li><a href="http://github.com/glguy/minecraft-proxy">http://github.com/glguy/minecraft-proxy</a> -- Haskell, ooh!</li>
  <li><a href="http://github.com/aniero/golem">http://github.com/aniero/golem</a> -- Ruby client, actually written by a buddy here in town.</li>
</ul><p>So maybe, just to start off, I can write a little proxy that will respond to the arrow keys, hit the server with the right packets, update the player's position on the server, at which point the server will come back and I'll let it pass through to the client, which will update the character on-screen. Something like that, anyway.<span class="end-of-content">☯</span></p>
      </content>
      <published>2011-02-16T00:00:00-08:00</published>
      <updated>2011-02-16T00:00:00-08:00</updated>
    </entry>
  
    
    <entry>
      <id>tag:lostincode.net,2010-12-10:post/testing-devise-controllers</id>
      <link rel="alternate" href="http://lostincode.net/blog/testing-devise-controllers" />
      <title type='html'>Solving the mysterious ActionNotFound error when testing Devise controllers</title>
      <excerpt type='xhtml'>
        <p>Ugh.</p>

        <p class='more'><a href="http://lostincode.net/blog/testing-devise-controllers">read the rest &#0187;</a></p>
      </excerpt>
      <content type='xhtml'>
        <p>Let's say you're using Devise in your Rails app, and you need to override some behavior in SessionsController such that an attribute is set on the user record when the user logs in. Something like this:</p>

<pre class="ruby"><code>class SessionsController &lt; Devise::SessionsController
  def create
    resource = warden.authenticate!(:scope =&gt; resource_name, :recall =&gt; "new")
    resource.foo = "bar"
    set_flash_message :notice, :signed_in
    sign_in_and_redirect(resource_name, resource)
  end
end
</code></pre>

<p>So then you've got a controller test; maybe it looks like this:</p>

<pre class="ruby"><code>describe SessionsController do
  describe 'POST #create' do
    it "sets the whatever" do
      user = Factory.create(:user, :email =&gt; "joe@bloe.com", :password =&gt; "secret")
      post :create, :user =&gt; {:email =&gt; "joe@bloe.com", :password =&gt; "secret"}
      user.reload
      user.foo.should == "bar"
    end
  end
end
</code></pre>

<p>So you go to run this test, and then you're clubbed upside the head with this monstrosity:</p>

<pre class="prompt"><code>Failure/Error: post :create, :user =&gt; {:email =&gt; "joe@bloe.com", :password =&gt; "secret"}
AbstractController::ActionNotFound
</code></pre>

<p>
<em>(commence hair pulling, gnashing of teeth, etc.)</em>
</p>

<p>Breathe deep. The action <em>does</em> exist. You're <em>not</em> going crazy.</p>

<p>~~~</p>

<p>Where is that error coming from then? Well, it's actually Devise. See, <tt>Devise::Controllers::InternalHelpers#is_devise_resource?</tt>, which is added as a before_filter to every Devise controller, does this:</p>

<pre class="ruby"><code>def is_devise_resource?
  raise ActionController::UnknownAction unless devise_mapping
end
</code></pre>

<p>Hmm, right. So what does <tt>#devise_mapping</tt> do? Let's just take a look:</p>

<pre class="ruby"><code>def devise_mapping
  @devise_mapping ||= request.env["devise.mapping"]
end
</code></pre>

<p>Ah. That's the answer. In controller tests, <tt>request.env["devise.mapping"]</tt> doesn't seem to get set. So, to fix this, we just need to set this to something before each test:</p>

<pre class="ruby"><code>before :each do
  request.env["devise.mapping"] = Devise.mappings[:user]
end
</code></pre>

<p>(If your resource isn't named "user", you obviously need to change that to the right thing. Consult your routes file if you forgot.)</p>

<p>What if we're going to be overriding multiple Devise controllers? Well, we can simply make a controller example group helper:</p>

<pre class="ruby"><code>module ControllerExampleGroupMethods
  def it_behaves_like_a_devise_controller
    before :each do
      request.env["devise.mapping"] = Devise.mappings[:user]
    end
  end
end

RSpec.configure do |config|
  config.extend(ControllerExampleGroupMethods, :type =&gt; :controller)
end
</code></pre>

<p>Now we can use it in our controller spec like this:</p>

<pre class="ruby"><code>describe SessionsController do
  it_behaves_like_a_devise_controller

  describe '#POST create' do
    # ...
  end
end
</code></pre>

<p>(The reason why we can't simply use a shared example group is that the <tt>before(:each)</tt> will only take effect in the shared example group, when we want it to take effect in the group we're including it into.)</p>

<p>Anyway, I hope that saves somebody at least two hours.<span class="end-of-content">☯</span></p>
      </content>
      <published>2010-12-10T00:00:00-08:00</published>
      <updated>2010-12-10T00:00:00-08:00</updated>
    </entry>
  
    
    <entry>
      <id>tag:lostincode.net,2010-11-15:post/array-set-operations</id>
      <link rel="alternate" href="http://lostincode.net/blog/array-set-operations" />
      <title type='html'>Array set operations</title>
      <excerpt type='xhtml'>
        <p>For some reason, I can't ever remember how to do set operations on arrays. Here are the common problems I run into and their solutions.</p>
        <p class='more'><a href="http://lostincode.net/blog/array-set-operations">read the rest &#0187;</a></p>
      </excerpt>
      <content type='xhtml'>
        <p>For some reason, I can't ever remember how to do set operations on arrays. Here are the common problems I run into and their solutions.</p>

<h3 id="i-want-to-remove-the-elements-in-array-a-that-are-present-in-array-b">I want to remove the elements in array A that are present in array B</h3>

<p>Good: Use <tt>reject</tt> + <tt>include?</tt>.</p>

<pre class="ruby"><code>array1 = [1, 2, 3, 4, 5]
array2 = [0, 4, 5, 7]
array2.reject {|x| array1.include?(x) }  #=&gt; [0, 7]
</code></pre>

<p>Better: Use the <tt>-</tt> operator.</p>

<pre class="ruby"><code>array1 = [1, 2, 3, 4, 5]
array2 = [1, 4, 5, 7]
array2 - array1  #=&gt; [0, 7]
</code></pre>

<h3 id="i-want-to-know-whether-array-a-contains-array-b">I want to know whether array A contains array B</h3>

<p>Good: Use <tt>all?</tt> + <tt>include?</tt>.</p>

<pre class="ruby"><code>array1 = [1, 2, 3, 4, 5]
array2 = [3, 4]
array2.all? {|x| array1.include?(x) }  #=&gt; true
</code></pre>

<p>Better: Use <tt>-</tt> + <tt>empty?</tt></p>

<pre class="ruby"><code>array1 = [1, 2, 3, 4, 5]
array2 = [3, 4]
(array2 - array1).empty?  #=&gt; true
</code></pre>

<h3 id="i-want-to-know-whether-array-a-contains-array-b-partly">I want to know whether array A contains array B (partly)</h3>

<p>Good: Use <tt>any?</tt> + <tt>include?</tt></p>

<pre class="ruby"><code>array1 = [1, 2, 3, 4, 5]
array2 = [3, 4, 7]
array2.any? {|x| array1.include?(x) }  #=&gt; true
</code></pre>

<p>Better: Use <tt>&amp;</tt> + <tt>!empty?</tt>.</p>

<pre class="ruby"><code>array1 = [1, 2, 3, 4, 5]
array2 = [3, 4, 7]
!(array2 &amp; array1).empty?  #=&gt; true
</code></pre>

      </content>
      <published>2010-11-15T00:00:00-08:00</published>
      <updated>2010-11-15T00:00:00-08:00</updated>
    </entry>
  
    
    <entry>
      <id>tag:lostincode.net,2010-10-25:post/rack-121-cant-convert-array-into-string</id>
      <link rel="alternate" href="http://lostincode.net/blog/rack-121-cant-convert-array-into-string" />
      <title type='html'>Getting around Rack’s incompatibility with Ruby 1.8.6</title>
      <excerpt type='xhtml'>
        <p>Why Ruby 1.8.6 throws a "can't convert Array into String" error when you try to use Rack 1.2.1 and what you can do about it.</p>

        <p class='more'><a href="http://lostincode.net/blog/rack-121-cant-convert-array-into-string">read the rest &#0187;</a></p>
      </excerpt>
      <content type='xhtml'>
        <p>I use Ruby 1.8.6 day-to-day. One of these days I'll get a new computer and upgrade to 1.8.7, but in the mean time, that's what I use. Evidently, though, it's not what the people who work on Rack use, because I see this error pop up way too often:</p>

<pre class="prompt"><code>/Library/Ruby/Gems/1.8/gems/rack-1.2.1/lib/rack/utils.rb:138:in `union': can't convert Array into String (TypeError)
</code></pre>

<p>Here's the defective passage in Rack::Utils:</p>

<pre class="ruby"><code>ESCAPE_HTML = {
  "&amp;" =&gt; "&amp;amp;",
  "&lt;" =&gt; "&amp;lt;",
  "&gt;" =&gt; "&amp;gt;",
  "'" =&gt; "&amp;#39;",
  '"' =&gt; "&amp;quot;",
}
ESCAPE_HTML_PATTERN = Regexp.union(ESCAPE_HTML.keys)
</code></pre>

<p>The reason why Ruby chokes is that in 1.8.6 and lower, <tt>Regexp.union</tt> expects regexps or strings as arguments. The ability to pass an array (which is what <tt>ESCAPE_HTML.keys</tt> is here) was added in 1.8.7.</p>

<p>This bug was cleared up back in June, and <a href="http://github.com/rack/rack/issues/issue/29">here's the Github issue</a>. Unfortunately, it was fixed after 1.2.1 came out and as of this writing, the next release of Rack hasn't been cut yet. Furthermore, nearly every library I've run across that depends on Rack does so without any sort of version dependency, which means if you install one of these libraries, you'll most likely get this error when Rack is loaded. Fortunately the fix is easy:</p>

<pre class="prompt"><code>$ gem uninstall rack
$ gem install rack -v 1.2.0
</code></pre>

<p>In the case that the library you're requiring <em>does</em> have a dependency on Rack, well, you'll have to resort to monkey patching. Simply drop this sucker into your code and all will be well.<span class="end-of-content">☯</span></p>

<pre class="ruby"><code>if RUBY_VERSION == "1.8.6"
  # Prior to Ruby 1.8.7, Regexp.union took String or Regexp arguments.
  # (The ability to pass in an array is new in 1.8.7.)
  # Fix this so Rack 1.2.1 will load.
  # See: &lt;https://github.com/rack/rack/issues/issue/29&gt;
  class Regexp
    class &lt;&lt; self
      alias_method :__original_union, :union
      def union(*args)
        if args.size == 1 &amp;&amp; Array === args.first
          __original_union(*args.first)
        else
          __original_union(*args)
        end
      end
    end
  end
end
</code></pre>
      </content>
      <published>2010-10-25T00:00:00-07:00</published>
      <updated>2010-11-11T00:00:00-08:00</updated>
    </entry>
  
    
    <entry>
      <id>tag:lostincode.net,2010-07-31:post/strtime-ruby-osx</id>
      <link rel="alternate" href="http://lostincode.net/blog/strtime-ruby-osx" />
      <title type='html'>Ruby’s strftime options</title>
      <excerpt type='xhtml'>
        <p>It turns out that Ruby on OS X and Ruby on Linux accept slightly different options for <tt>strftime</tt>. Here is a handy table that lists the differences.</p>

        <p class='more'><a href="http://lostincode.net/blog/strtime-ruby-osx">read the rest &#0187;</a></p>
      </excerpt>
      <content type='xhtml'>
        <p>I always forget which metacharacters Ruby's version of <tt>strftime</tt> accepts and what they do. Complicating this is the fact that Ruby's <tt>strftime</tt> (at least in 1.8.x) tries to be consistent with the <tt>strftime</tt> in the standard C library, but that actually varies depending on whether you're on Linux (which typically carries the GNU version of libc) or OS X (which essentially carries BSD libc). The thing I always get bit by is that compared to GNU's libc, the BSD version is kinda lame. For instance, the GNU version has a <code>%p</code> and <code>%P</code> option, whereas BSD's has only <code>%p</code>. Also in the GNU version, you can say e.g. <code>%-I</code> and that will return a version of the hour without leading zeroes or spaces, whereas with BSD's you have to go with <code>%l</code>, which omits a leading zero, but still leaves a leading space. To be fair, GNU actually extends <tt>strftime</tt> beyond the official standard, so there's no reason they should be in BSD, but still, once you get used to these features it's hard going back.</p>

<p>With that in mind I thought it would be informative to run through all the possible metacharacters on OS X and Linux, and see which ones did what. Like this:</p>

<pre class="ruby"><code>time = Time.local(2010, 1, 1, 15, 30, 0)
chars = (("A".."Z").to_a + ("a".."z").to_a)
fmtstr = chars.map {|l| "%%#{l} = %#{l}" }.join("\n")
puts time.strftime(fmtstr)
...
</code></pre>

<p>And here are the results:</p>

<table>
<thead>
<tr><th style="text-align: left">Char</th>
      <th style="text-align: left">OS X</th>
      <th style="text-align: left">Linux</th>
    </tr>
</thead>
<tbody>
<tr><td style="text-align: left">%A</td>
      <td style="text-align: left">"Friday"</td>
      <td style="text-align: left">"Friday"</td>
    </tr>
<tr><td style="text-align: left">%B</td>
      <td style="text-align: left">"January"</td>
      <td style="text-align: left">"January"</td>
    </tr>
<tr><td style="text-align: left">%C</td>
      <td style="text-align: left">"20"</td>
      <td style="text-align: left">"20"</td>
    </tr>
<tr><td style="text-align: left">%D</td>
      <td style="text-align: left">"01/01/10"</td>
      <td style="text-align: left">"01/01/10"</td>
    </tr>
<tr><td style="text-align: left"><span class="noop">%E</span></td>
      <td style="text-align: left"><span class="noop">"E"</span></td>
      <td style="text-align: left"><span class="noop">"%E"</span></td>
    </tr>
<tr><td style="text-align: left">%F</td>
      <td style="text-align: left">"2010-01-01"</td>
      <td style="text-align: left">"2010-01-01"</td>
    </tr>
<tr><td style="text-align: left">%G</td>
      <td style="text-align: left">"2009"</td>
      <td style="text-align: left">"2009"</td>
    </tr>
<tr><td style="text-align: left">%H</td>
      <td style="text-align: left">"15"</td>
      <td style="text-align: left">"15"</td>
    </tr>
<tr><td style="text-align: left">%I</td>
      <td style="text-align: left">"03"</td>
      <td style="text-align: left">"03"</td>
    </tr>
<tr><td style="text-align: left"><span class="noop">%J</span></td>
      <td style="text-align: left"><span class="noop">"J"</span></td>
      <td style="text-align: left"><span class="noop">"%J"</span></td>
    </tr>
<tr><td style="text-align: left"><span class="noop">%K</span></td>
      <td style="text-align: left"><span class="noop">"K"</span></td>
      <td style="text-align: left"><span class="noop">"%K"</span></td>
    </tr>
<tr><td style="text-align: left"><span class="noop">%L</span></td>
      <td style="text-align: left"><span class="noop">"L"</span></td>
      <td style="text-align: left"><span class="noop">"%L"</span></td>
    </tr>
<tr><td style="text-align: left">%M</td>
      <td style="text-align: left">"30"</td>
      <td style="text-align: left">"30"</td>
    </tr>
<tr><td style="text-align: left"><span class="noop">%N</span></td>
      <td style="text-align: left"><span class="noop">"N"</span></td>
      <td style="text-align: left"><span class="noop">"%N"</span></td>
    </tr>
<tr><td style="text-align: left"><span class="noop">%O</span></td>
      <td style="text-align: left"><span class="noop">"O"</span></td>
      <td style="text-align: left"><span class="noop">"%O"</span></td>
    </tr>
<tr><td style="text-align: left"><span class="noop">%P</span></td>
      <td style="text-align: left"><span class="noop">"P"</span></td>
      <td style="text-align: left"><span class="noop">"pm"</span></td>
    </tr>
<tr><td style="text-align: left"><span class="noop">%Q</span></td>
      <td style="text-align: left"><span class="noop">"Q"</span></td>
      <td style="text-align: left"><span class="noop">"%Q"</span></td>
    </tr>
<tr><td style="text-align: left">%R</td>
      <td style="text-align: left">"15:30"</td>
      <td style="text-align: left">"15:30"</td>
    </tr>
<tr><td style="text-align: left">%S</td>
      <td style="text-align: left">"00"</td>
      <td style="text-align: left">"00"</td>
    </tr>
<tr><td style="text-align: left">%T</td>
      <td style="text-align: left">"15:30:00"</td>
      <td style="text-align: left">"15:30:00"</td>
    </tr>
<tr><td style="text-align: left">%U</td>
      <td style="text-align: left">"00"</td>
      <td style="text-align: left">"00"</td>
    </tr>
<tr><td style="text-align: left">%V</td>
      <td style="text-align: left">"53"</td>
      <td style="text-align: left">"53"</td>
    </tr>
<tr><td style="text-align: left">%W</td>
      <td style="text-align: left">"00"</td>
      <td style="text-align: left">"00"</td>
    </tr>
<tr><td style="text-align: left">%X</td>
      <td style="text-align: left">"15:30:00"</td>
      <td style="text-align: left">"15:30:00"</td>
    </tr>
<tr><td style="text-align: left">%Y</td>
      <td style="text-align: left">"2010"</td>
      <td style="text-align: left">"2010"</td>
    </tr>
<tr><td style="text-align: left">%Z</td>
      <td style="text-align: left">"CST"</td>
      <td style="text-align: left">"CST"</td>
    </tr>
<tr><td style="text-align: left">%a</td>
      <td style="text-align: left">"Fri"</td>
      <td style="text-align: left">"Fri"</td>
    </tr>
<tr><td style="text-align: left">%b</td>
      <td style="text-align: left">"Jan"</td>
      <td style="text-align: left">"Jan"</td>
    </tr>
<tr><td style="text-align: left">%c</td>
      <td style="text-align: left">"Fri Jan  1 15:30:00 2010"</td>
      <td style="text-align: left">"Fri Jan  1 15:30:00 2010"</td>
    </tr>
<tr><td style="text-align: left">%d</td>
      <td style="text-align: left">"01"</td>
      <td style="text-align: left">"01"</td>
    </tr>
<tr><td style="text-align: left">%e</td>
      <td style="text-align: left">" 1"</td>
      <td style="text-align: left">" 1"</td>
    </tr>
<tr><td style="text-align: left"><span class="noop">%f</span></td>
      <td style="text-align: left"><span class="noop">"f"</span></td>
      <td style="text-align: left"><span class="noop">"%f"</span></td>
    </tr>
<tr><td style="text-align: left">%g</td>
      <td style="text-align: left">"09"</td>
      <td style="text-align: left">"09"</td>
    </tr>
<tr><td style="text-align: left">%h</td>
      <td style="text-align: left">"Jan"</td>
      <td style="text-align: left">"Jan"</td>
    </tr>
<tr><td style="text-align: left"><span class="noop">%i</span></td>
      <td style="text-align: left"><span class="noop">"i"</span></td>
      <td style="text-align: left"><span class="noop">"%i"</span></td>
    </tr>
<tr><td style="text-align: left">%j</td>
      <td style="text-align: left">"001"</td>
      <td style="text-align: left">"001"</td>
    </tr>
<tr><td style="text-align: left">%k</td>
      <td style="text-align: left">"15"</td>
      <td style="text-align: left">"15"</td>
    </tr>
<tr><td style="text-align: left">%l</td>
      <td style="text-align: left">" 3"</td>
      <td style="text-align: left">" 3"</td>
    </tr>
<tr><td style="text-align: left">%m</td>
      <td style="text-align: left">"01"</td>
      <td style="text-align: left">"01"</td>
    </tr>
<tr><td style="text-align: left">%n</td>
      <td style="text-align: left">"\n"</td>
      <td style="text-align: left">"\n"</td>
    </tr>
<tr><td style="text-align: left"><span class="noop">%o</span></td>
      <td style="text-align: left"><span class="noop">"o"</span></td>
      <td style="text-align: left"><span class="noop">"%o"</span></td>
    </tr>
<tr><td style="text-align: left">%p</td>
      <td style="text-align: left">"PM"</td>
      <td style="text-align: left">"PM"</td>
    </tr>
<tr><td style="text-align: left"><span class="noop">%q</span></td>
      <td style="text-align: left"><span class="noop">"q"</span></td>
      <td style="text-align: left"><span class="noop">"%q"</span></td>
    </tr>
<tr><td style="text-align: left">%r</td>
      <td style="text-align: left">"03:30:00 PM"</td>
      <td style="text-align: left">"03:30:00 PM"</td>
    </tr>
<tr><td style="text-align: left">%s</td>
      <td style="text-align: left">"1262381400"</td>
      <td style="text-align: left">"1262381400"</td>
    </tr>
<tr><td style="text-align: left">%t</td>
      <td style="text-align: left">"\t"</td>
      <td style="text-align: left">"\t"</td>
    </tr>
<tr><td style="text-align: left">%u</td>
      <td style="text-align: left">"5"</td>
      <td style="text-align: left">"5"</td>
    </tr>
<tr><td style="text-align: left">%v</td>
      <td style="text-align: left">" 1-Jan-2010"</td>
      <td style="text-align: left"><span class="noop">"%v"</span></td>
    </tr>
<tr><td style="text-align: left">%w</td>
      <td style="text-align: left">"5"</td>
      <td style="text-align: left">"5"</td>
    </tr>
<tr><td style="text-align: left">%x</td>
      <td style="text-align: left">"01/01/10"</td>
      <td style="text-align: left">"01/01/10"</td>
    </tr>
<tr><td style="text-align: left">%y</td>
      <td style="text-align: left">"10"</td>
      <td style="text-align: left">"10"</td>
    </tr>
<tr><td style="text-align: left">%z</td>
      <td style="text-align: left">"-0500"</td>
      <td style="text-align: left">"-0600"</td>
    </tr>
</tbody>
</table><p>Out of interest I also decided to tabulate the possible metacharacters on Linux involving the special GNU libc extensions, namely the "-", "_" and "0" prefixes. I did this like so:</p>

<pre class="ruby"><code>time = Time.local(2010, 1, 1, 15, 30, 0)
chars = (("A".."Z").to_a + ("a".."z").to_a).map {|l| ["_#{l}", "-#{l}", "0#{l}"] }.flatten
fmtstr = chars.map {|c| "%%#{c} = %#{c}" }.join("\n")
puts time.strftime(fmtstr)
...
</code></pre>

<p>Here are the results (skipping the ones that don't do anything):<span class="end-of-content">☯</span></p>

<table>
<thead>
<tr><th style="text-align: left">Char</th>
      <th style="text-align: left">String</th>
    </tr>
</thead>
<tbody>
<tr><td style="text-align: left">%_A</td>
      <td style="text-align: left">"Friday"</td>
    </tr>
<tr><td style="text-align: left">%-A</td>
      <td style="text-align: left">"Friday"</td>
    </tr>
<tr><td style="text-align: left">%0A</td>
      <td style="text-align: left">"Friday"</td>
    </tr>
<tr><td style="text-align: left">%_B</td>
      <td style="text-align: left">"January"</td>
    </tr>
<tr><td style="text-align: left">%-B</td>
      <td style="text-align: left">"January"</td>
    </tr>
<tr><td style="text-align: left">%0B</td>
      <td style="text-align: left">"January"</td>
    </tr>
<tr><td style="text-align: left">%_C</td>
      <td style="text-align: left">"20"</td>
    </tr>
<tr><td style="text-align: left">%-C</td>
      <td style="text-align: left">"20"</td>
    </tr>
<tr><td style="text-align: left">%0C</td>
      <td style="text-align: left">"20"</td>
    </tr>
<tr><td style="text-align: left">%_D</td>
      <td style="text-align: left">"01/01/10"</td>
    </tr>
<tr><td style="text-align: left">%-D</td>
      <td style="text-align: left">"01/01/10"</td>
    </tr>
<tr><td style="text-align: left">%0D</td>
      <td style="text-align: left">"01/01/10"</td>
    </tr>
<tr><td style="text-align: left">%_F</td>
      <td style="text-align: left">"2010-01-01"</td>
    </tr>
<tr><td style="text-align: left">%-F</td>
      <td style="text-align: left">"2010-01-01"</td>
    </tr>
<tr><td style="text-align: left">%0F</td>
      <td style="text-align: left">"2010-01-01"</td>
    </tr>
<tr><td style="text-align: left">%_G</td>
      <td style="text-align: left">"2009"</td>
    </tr>
<tr><td style="text-align: left">%-G</td>
      <td style="text-align: left">"2009"</td>
    </tr>
<tr><td style="text-align: left">%0G</td>
      <td style="text-align: left">"2009"</td>
    </tr>
<tr><td style="text-align: left">%_H</td>
      <td style="text-align: left">"15"</td>
    </tr>
<tr><td style="text-align: left">%-H</td>
      <td style="text-align: left">"15"</td>
    </tr>
<tr><td style="text-align: left">%0H</td>
      <td style="text-align: left">"15"</td>
    </tr>
<tr><td style="text-align: left">%_I</td>
      <td style="text-align: left">" 3"</td>
    </tr>
<tr><td style="text-align: left">%-I</td>
      <td style="text-align: left">"3"</td>
    </tr>
<tr><td style="text-align: left">%0I</td>
      <td style="text-align: left">"03"</td>
    </tr>
<tr><td style="text-align: left">%_M</td>
      <td style="text-align: left">"30"</td>
    </tr>
<tr><td style="text-align: left">%-M</td>
      <td style="text-align: left">"30"</td>
    </tr>
<tr><td style="text-align: left">%0M</td>
      <td style="text-align: left">"30"</td>
    </tr>
<tr><td style="text-align: left">%_P</td>
      <td style="text-align: left">"pm"</td>
    </tr>
<tr><td style="text-align: left">%-P</td>
      <td style="text-align: left">"pm"</td>
    </tr>
<tr><td style="text-align: left">%0P</td>
      <td style="text-align: left">"pm"</td>
    </tr>
<tr><td style="text-align: left">%_R</td>
      <td style="text-align: left">"15:30"</td>
    </tr>
<tr><td style="text-align: left">%-R</td>
      <td style="text-align: left">"15:30"</td>
    </tr>
<tr><td style="text-align: left">%0R</td>
      <td style="text-align: left">"15:30"</td>
    </tr>
<tr><td style="text-align: left">%_S</td>
      <td style="text-align: left">" 0"</td>
    </tr>
<tr><td style="text-align: left">%-S</td>
      <td style="text-align: left">"0"</td>
    </tr>
<tr><td style="text-align: left">%0S</td>
      <td style="text-align: left">"00"</td>
    </tr>
<tr><td style="text-align: left">%_T</td>
      <td style="text-align: left">"15:30:00"</td>
    </tr>
<tr><td style="text-align: left">%-T</td>
      <td style="text-align: left">"15:30:00"</td>
    </tr>
<tr><td style="text-align: left">%0T</td>
      <td style="text-align: left">"15:30:00"</td>
    </tr>
<tr><td style="text-align: left">%_U</td>
      <td style="text-align: left">" 0"</td>
    </tr>
<tr><td style="text-align: left">%-U</td>
      <td style="text-align: left">"0"</td>
    </tr>
<tr><td style="text-align: left">%0U</td>
      <td style="text-align: left">"00"</td>
    </tr>
<tr><td style="text-align: left">%_V</td>
      <td style="text-align: left">"53"</td>
    </tr>
<tr><td style="text-align: left">%-V</td>
      <td style="text-align: left">"53"</td>
    </tr>
<tr><td style="text-align: left">%0V</td>
      <td style="text-align: left">"53"</td>
    </tr>
<tr><td style="text-align: left">%_W</td>
      <td style="text-align: left">" 0"</td>
    </tr>
<tr><td style="text-align: left">%-W</td>
      <td style="text-align: left">"0"</td>
    </tr>
<tr><td style="text-align: left">%0W</td>
      <td style="text-align: left">"00"</td>
    </tr>
<tr><td style="text-align: left">%_X</td>
      <td style="text-align: left">"15:30:00"</td>
    </tr>
<tr><td style="text-align: left">%-X</td>
      <td style="text-align: left">"15:30:00"</td>
    </tr>
<tr><td style="text-align: left">%0X</td>
      <td style="text-align: left">"15:30:00"</td>
    </tr>
<tr><td style="text-align: left">%_Y</td>
      <td style="text-align: left">"2010"</td>
    </tr>
<tr><td style="text-align: left">%-Y</td>
      <td style="text-align: left">"2010"</td>
    </tr>
<tr><td style="text-align: left">%0Y</td>
      <td style="text-align: left">"2010"</td>
    </tr>
<tr><td style="text-align: left">%_Z</td>
      <td style="text-align: left">"CST"</td>
    </tr>
<tr><td style="text-align: left">%-Z</td>
      <td style="text-align: left">"CST"</td>
    </tr>
<tr><td style="text-align: left">%0Z</td>
      <td style="text-align: left">"CST"</td>
    </tr>
<tr><td style="text-align: left">%_a</td>
      <td style="text-align: left">"Fri"</td>
    </tr>
<tr><td style="text-align: left">%-a</td>
      <td style="text-align: left">"Fri"</td>
    </tr>
<tr><td style="text-align: left">%0a</td>
      <td style="text-align: left">"Fri"</td>
    </tr>
<tr><td style="text-align: left">%_b</td>
      <td style="text-align: left">"Jan"</td>
    </tr>
<tr><td style="text-align: left">%-b</td>
      <td style="text-align: left">"Jan"</td>
    </tr>
<tr><td style="text-align: left">%0b</td>
      <td style="text-align: left">"Jan"</td>
    </tr>
<tr><td style="text-align: left">%_c</td>
      <td style="text-align: left">"Fri Jan  1 15:30:00 2010"</td>
    </tr>
<tr><td style="text-align: left">%-c</td>
      <td style="text-align: left">"Fri Jan  1 15:30:00 2010"</td>
    </tr>
<tr><td style="text-align: left">%0c</td>
      <td style="text-align: left">"Fri Jan  1 15:30:00 2010"</td>
    </tr>
<tr><td style="text-align: left">%_d</td>
      <td style="text-align: left">" 1"</td>
    </tr>
<tr><td style="text-align: left">%-d</td>
      <td style="text-align: left">"1"</td>
    </tr>
<tr><td style="text-align: left">%0d</td>
      <td style="text-align: left">"01"</td>
    </tr>
<tr><td style="text-align: left">%_e</td>
      <td style="text-align: left">" 1"</td>
    </tr>
<tr><td style="text-align: left">%-e</td>
      <td style="text-align: left">"1"</td>
    </tr>
<tr><td style="text-align: left">%0e</td>
      <td style="text-align: left">"01"</td>
    </tr>
<tr><td style="text-align: left">%_g</td>
      <td style="text-align: left">" 9"</td>
    </tr>
<tr><td style="text-align: left">%-g</td>
      <td style="text-align: left">"9"</td>
    </tr>
<tr><td style="text-align: left">%0g</td>
      <td style="text-align: left">"09"</td>
    </tr>
<tr><td style="text-align: left">%_h</td>
      <td style="text-align: left">"Jan"</td>
    </tr>
<tr><td style="text-align: left">%-h</td>
      <td style="text-align: left">"Jan"</td>
    </tr>
<tr><td style="text-align: left">%0h</td>
      <td style="text-align: left">"Jan"</td>
    </tr>
<tr><td style="text-align: left">%_j</td>
      <td style="text-align: left">"  1"</td>
    </tr>
<tr><td style="text-align: left">%-j</td>
      <td style="text-align: left">"1"</td>
    </tr>
<tr><td style="text-align: left">%0j</td>
      <td style="text-align: left">"001"</td>
    </tr>
<tr><td style="text-align: left">%_k</td>
      <td style="text-align: left">"15"</td>
    </tr>
<tr><td style="text-align: left">%-k</td>
      <td style="text-align: left">"15"</td>
    </tr>
<tr><td style="text-align: left">%0k</td>
      <td style="text-align: left">"15"</td>
    </tr>
<tr><td style="text-align: left">%_l</td>
      <td style="text-align: left">" 3"</td>
    </tr>
<tr><td style="text-align: left">%-l</td>
      <td style="text-align: left">"3"</td>
    </tr>
<tr><td style="text-align: left">%0l</td>
      <td style="text-align: left">"03"</td>
    </tr>
<tr><td style="text-align: left">%_m</td>
      <td style="text-align: left">" 1"</td>
    </tr>
<tr><td style="text-align: left">%-m</td>
      <td style="text-align: left">"1"</td>
    </tr>
<tr><td style="text-align: left">%0m</td>
      <td style="text-align: left">"01"</td>
    </tr>
<tr><td style="text-align: left">%_n</td>
      <td style="text-align: left">"\n"</td>
    </tr>
<tr><td style="text-align: left">%-n</td>
      <td style="text-align: left">"\n"</td>
    </tr>
<tr><td style="text-align: left">%0n</td>
      <td style="text-align: left">"\n"</td>
    </tr>
<tr><td style="text-align: left">%_p</td>
      <td style="text-align: left">"PM"</td>
    </tr>
<tr><td style="text-align: left">%-p</td>
      <td style="text-align: left">"PM"</td>
    </tr>
<tr><td style="text-align: left">%0p</td>
      <td style="text-align: left">"PM"</td>
    </tr>
<tr><td style="text-align: left">%_r</td>
      <td style="text-align: left">"03:30:00 PM"</td>
    </tr>
<tr><td style="text-align: left">%-r</td>
      <td style="text-align: left">"03:30:00 PM"</td>
    </tr>
<tr><td style="text-align: left">%0r</td>
      <td style="text-align: left">"03:30:00 PM"</td>
    </tr>
<tr><td style="text-align: left">%_s</td>
      <td style="text-align: left">"1262381400"</td>
    </tr>
<tr><td style="text-align: left">%-s</td>
      <td style="text-align: left">"1262381400"</td>
    </tr>
<tr><td style="text-align: left">%0s</td>
      <td style="text-align: left">"1262381400"</td>
    </tr>
<tr><td style="text-align: left">%_t</td>
      <td style="text-align: left">"\t"</td>
    </tr>
<tr><td style="text-align: left">%-t</td>
      <td style="text-align: left">"\t"</td>
    </tr>
<tr><td style="text-align: left">%0t</td>
      <td style="text-align: left">"\t"</td>
    </tr>
<tr><td style="text-align: left">%_u</td>
      <td style="text-align: left">"5"</td>
    </tr>
<tr><td style="text-align: left">%-u</td>
      <td style="text-align: left">"5"</td>
    </tr>
<tr><td style="text-align: left">%0u</td>
      <td style="text-align: left">"5"</td>
    </tr>
<tr><td style="text-align: left">%_w</td>
      <td style="text-align: left">"5"</td>
    </tr>
<tr><td style="text-align: left">%-w</td>
      <td style="text-align: left">"5"</td>
    </tr>
<tr><td style="text-align: left">%0w</td>
      <td style="text-align: left">"5"</td>
    </tr>
<tr><td style="text-align: left">%_x</td>
      <td style="text-align: left">"01/01/10"</td>
    </tr>
<tr><td style="text-align: left">%-x</td>
      <td style="text-align: left">"01/01/10"</td>
    </tr>
<tr><td style="text-align: left">%0x</td>
      <td style="text-align: left">"01/01/10"</td>
    </tr>
<tr><td style="text-align: left">%_y</td>
      <td style="text-align: left">"10"</td>
    </tr>
<tr><td style="text-align: left">%-y</td>
      <td style="text-align: left">"10"</td>
    </tr>
<tr><td style="text-align: left">%0y</td>
      <td style="text-align: left">"10"</td>
    </tr>
<tr><td style="text-align: left">%_z</td>
      <td style="text-align: left">"- 600"</td>
    </tr>
<tr><td style="text-align: left">%-z</td>
      <td style="text-align: left">"-600"</td>
    </tr>
<tr><td style="text-align: left">%0z</td>
      <td style="text-align: left">"-0600"</td>
    </tr>
</tbody>
</table>
      </content>
      <published>2010-07-31T00:00:00-07:00</published>
      <updated>2010-07-31T00:00:00-07:00</updated>
    </entry>
  
    
    <entry>
      <id>tag:lostincode.net,2010-03-27:post/homebrew</id>
      <link rel="alternate" href="http://lostincode.net/blog/homebrew" />
      <title type='html'>Homebrew</title>
      <excerpt type='xhtml'>
        <p>You <em>need</em> to install Homebrew on your Mac. Here's why.</p>

        <p class='more'><a href="http://lostincode.net/blog/homebrew">read the rest &#0187;</a></p>
      </excerpt>
      <content type='xhtml'>
        <p>I wanted to install the <a href="http://ultraviolet.rubyforge.org/">Ultraviolet</a> gem, which gives you the ability to syntax-highlight code using Textmate syntax files through the <a href="http://textpow.rubyforge.org/">Textpow</a> gem. However textpow in turn depends on <a href="http://www.geocities.jp/kosako3/oniguruma/">Oniguruma</a> (a regex engine that happens to be more efficient than Ruby's built-in version). However, if you install Onigurama you will probably get a bunch of compilation errors and something about not being able to find <tt>oniguruma.h</tt>. This is because installing the gem only installs the Ruby bindings, but that assumes you already have the Oniguruma header files installed.</p>

<p>So I course need to do that, and I'm faced with the choice: do I a) compile it from source or b) use a package manager like MacPorts or Fink?</p>

<p>On Linux, of course, this is a no-brainer: <code>apt-get install</code> and you're done.</p>

<p>On Mac, neither option is really great. You can compile from source, but if the library has dependencies, you have to install those too, and then what if you want to uninstall it at some point? Good luck with that.</p>

<p>Okay then, what about MacPorts or Fink? Well, the problem with MacPorts is that it insists on installing everything from scratch. If you already have, say, Perl on your system (and you do), well, tough cookies, because it's going to install its own. I remember I tried to install Ghostscript one time and ended up with 15 different other packages. <strong>This gets to be unbelievably annoying.</strong> Fink is better, but they don't have every package that Debian does (naturally), and anyway, trying to shoehorn a Debian-like package management system into the Mac OS environment just seems kinda weird to me, like trying to mix oil and water.</p>

<h3 id="enter-homebrew">Enter Homebrew</h3>

<p><a href="http://mxcl.github.com/homebrew/">Homebrew</a> appealed to me because it's so incredibly simple and flexible. Engine Yard has a good writeup <a href="http://www.engineyard.com/blog/2010/homebrew-os-xs-missing-package-manager/">here</a>, but basically it's like MacPorts in that nobody hosts any packages -- when you install Homebrew you just install a collection of Ruby files ("formulae"). When you install a package, Homebrew finds its formula and executes the instructions therein, downloading the source and compiling it according to the formula. Where does Homebrew get the source? If you scan through <a href="http://github.com/mxcl/homebrew/tree/master/Library/Formula/">some of the formulae</a>, you'll notice that most of them come from tarballs at public URLs. However, the cool thing is that Homebrew also lets you download source from a git, svn, hg, or other repository. Evidently, this means the packages where this applies, Homebrew lets you upgrade simply by hitting the repo again.</p>

<p>I think the biggest thing I like about Homebrew, though, is <a href="http://wiki.github.com/mxcl/homebrew/formula-cookbook">this</a>:</p>

<blockquote>
  <p>[It] doesn’t dupe stuff that comes with OS X or stuff that is provided by RubyGems, CPAN or PyPi.</p>
</blockquote>

<p><em>Hal-le-lu-jah</em>. I thought I would never see the end of that.</p>

<p>So, I'm sure that Homebrew is not perfect since it is still a maturing project, but it seems like a worthy alternative to the madness that is MacPorts or Fink.</p>

<h3 id="installing-homebrew">Installing Homebrew</h3>

<p>Normally I'd be able to follow the <a href="http://wiki.github.com/mxcl/homebrew/installation">instructions in the wiki</a>, but there are a few extra things that I had to do. First, Homebrew places everything in <tt>/usr/local</tt>. That's not a big deal if you don't have anything already there, but I have a few things that are, such as Ruby and MySQL. Second, Homebrew recommends you do <em>not</em> use sudo to manage packages. The reasoning is that you probably use it without thinking about it, and you don't need root access to install programs anyway, so why bother? I saw someone say the same thing the other day, and it's probably true. sudo was designed for multiuser setups; if you're the only person that uses your computer then it's probably not doing anything to increase safety.</p>

<p>Even with all that it was incredibly easy to install Homebrew. So here's a little walkthrough of what I did.</p>

<h4 id="pre-flight">Pre-flight</h4>

<p>First we remove MacPorts:</p>

<pre class="prompt"><code>$ sudo port -f uninstall installed
$ sudo rm -rf \
    /opt/local \
    /Applications/DarwinPorts \
    /Applications/MacPorts \
    /Library/LaunchDaemons/org.macports.* \
    /Library/Receipts/DarwinPorts*.pkg \
    /Library/Receipts/MacPorts*.pkg \
    /Library/StartupItems/DarwinPortsStartup \
    /Library/Tcl/darwinports1.0 \
    /Library/Tcl/macports1.0 \
    ~/.macports
</code></pre>

<p>Then Fink:</p>

<pre class="prompt"><code>$ sudo rm -rf /sw
</code></pre>

<p>As for the stuff in <tt>/usr/local</tt>, we can just move it out of the way:</p>

<pre class="prompt"><code>$ cd /usr
$ sudo mv local local.old
</code></pre>

<p>Moving <tt>/usr/local</tt> caused a few problems so let's deal with them now. The immediate problem is that upon opening a new bash session I get an error since <tt>~/.bash_profile</tt> is failing to load (it depended on the GNU version of ls which I'd also had installed to <tt>/usr/local</tt>). So let's get that out of the way:</p>

<pre class="prompt"><code>$ mv ~/.bash_profile ~/.bash_profile.old
</code></pre>

<p>Re-creating <tt>/usr/local</tt> doesn't matter since the Homebrew installation script will do that for us.</p>

<h4 id="fixing-rubygems">Fixing RubyGems</h4>

<p>I am back to a stock Ruby installation since my custom Ruby was previously in <tt>/usr/local</tt>. So, I need to upgrade RubyGems, which is woefully out of date:</p>

<pre class="prompt"><code>$ which gem
/usr/bin/gem
$ gem -v
1.0.1
</code></pre>

<p>Yikes.</p>

<pre class="prompt"><code>$ sudo gem update --system
$ gem -v
1.3.6
</code></pre>

<p>Much better ;)</p>

<p>I also want RubyGems to install any executables that may come with gems to <tt>/Library/Ruby/Gems/1.8/bin</tt> instead of <tt>/usr/bin</tt>. We can do this by placing <tt>gem: -n/Library/Ruby/Gems/1.8/bin</tt> in our <tt>~/.gemrc</tt> file (it's just a hash represented in a YAML file; <tt>gem</tt> is the key in this case). Then, we need to make sure to add <tt>/Library/Ruby/Gems/1.8/bin</tt> to our <tt>PATH</tt>.</p>

<h4 id="okay-for-reals-this-time">Okay, for reals this time</h4>

<p>I think that's all. Let's install Homebrew! To do that, simply copy the <a href="http://gist.github.com/323731">recommended script</a>, paste it into a file, and run it (remember though: not as root!).</p>

<p>Okay, let's try out some packages:</p>

<pre class="prompt"><code>$ brew install readline
$ brew install git
$ brew install wget
</code></pre>

<p>Impressive! I notice that I keep getting a warning about XCode needing to be upgraded to 3.1.4, but it doesn't seem to matter, so I don't worry about it.</p>

<p>Here's one that was pretty painful with MacPorts:</p>

<pre class="prompt"><code>$ brew install imagemagick
</code></pre>

<p>Oh man. It caught the dependencies (libjpeg, libgd, libwmf, libtiff, and jasper) automatically <strong>without installing a crapload of other things too</strong>. I love this thing already.</p>

<h3 id="mysql">MySQL</h3>

<p>I realize that MySQL had been in its own directory before, <tt>/usr/local/mysql</tt>. So I find I can simply move that over to the new <tt>/usr/local</tt>:</p>

<pre class="prompt"><code>$ mv /usr/local.old/mysql /usr/local
</code></pre>

<p>The mysql client program will complain because it can't read or write to the database so we need to do:</p>

<pre class="prompt"><code>$ chown -R mysql:mysql /usr/local/mysql
</code></pre>

<h3 id="coreutils">coreutils</h3>

<p>One of the essential things I needed immediately was GNU coreutils (because I'm used to GNU ls options). So I simply reinstalled it:</p>

<pre class="prompt"><code>$ brew install coreutils
</code></pre>

<p>However, it told me to then run <code>brew install coreutils --aliases &gt; ~/.bashrc</code>. I found that didn't work, so if you install this too, <strong>DON'T DO THAT!!</strong> Besides, what this will do is add lines like</p>

<pre class="bash"><code>alias ls="/usr/local/bin/gls"
</code></pre>

<p>which I put in <tt>~/.bash_profile</tt>, but it didn't work for some reason. So I decided to install symlinks instead. Because I don't want to muddy up <tt>/usr/local/bin</tt> this time around, I opted to install them to <tt>~/.bin</tt>, and then add <tt>~/.bin</tt> to my <tt>PATH</tt>. Then I ran:</p>

<pre class="prompt"><code>$ for command in base64 basename cat chcon chgrp chmod chown chroot cksum comm cp csplit cut date dd df dir dircolors dirname du echo env expand expr factor false fmt fold groups head hostid id install join kill link ln logname ls md5sum mkdir mkfifo mknod mktemp mv nice nl nohup od paste pathchk pinky pr printenv printf ptx pwd readlink rm rmdir runcon seq sha1sum sha224sum sha256sum sha384sum sha512sum shred shuf sleep sort split stat stty sum sync tac tail tee test touch tr true tsort tty uname unexpand uniq unlink uptime users vdir wc who whoami yes "["; do ln -s "/usr/local/bin/g$command" "$command"; done
</code></pre>

<h3 id="anyway">Anyway...</h3>

<p>If you recall we were trying to install the Oniguruma gem. First let's try installing Oniguruma proper. Do we have it?</p>

<pre class="prompt"><code>$ brew search oniguruma
oniguruma
</code></pre>

<p>Yes indeedy. Let's do it:</p>

<pre class="prompt"><code>$ brew install oniguruma
==&gt; Downloading http://www.geocities.jp/kosako3/oniguruma/archive/onig-5.9.1.tar.gz
######################################################################### 100.0%
==&gt; ./configure --prefix=/usr/local/Cellar/oniguruma/5.9.1 --disable-debug --disable-dependency-tracking
==&gt; make install
/usr/local/Cellar/oniguruma/5.9.1: 9 files, 800K, built in 25 seconds
</code></pre>

<p>Lovely! Now the moment of truth:</p>

<pre class="prompt"><code>$ gem install oniguruma
Building native extensions.  This could take a while...
Successfully installed oniguruma-1.1.0
1 gem installed
</code></pre>

<p>Holy crap. That is awesome.<span class="end-of-content">☯</span></p>

<h3 id="resources">Resources</h3>

<ul><li><a href="http://www.engineyard.com/blog/2010/homebrew-os-xs-missing-package-manager/">http://www.engineyard.com/blog/2010/homebrew-os-xs-missing-package-manager/</a></li>
  <li><a href="http://hugofrappier.wordpress.com/2010/01/01/rails-1-2-x-ruby-1-8-6-snow-leopard-the-missing-link/">http://hugofrappier.wordpress.com/2010/01/01/rails-1-2-x-ruby-1-8-6-snow-leopard-the-missing-link/</a></li>
  <li><a href="http://wiki.github.com/mxcl/homebrew/gems-eggs-and-perl-modules">http://wiki.github.com/mxcl/homebrew/gems-eggs-and-perl-modules</a></li>
  <li><a href="http://blog.zenspider.com/2009/08/gem-path-rubygems-and-you.html">http://blog.zenspider.com/2009/08/gem-path-rubygems-and-you.html</a></li>
</ul>
      </content>
      <published>2010-03-27T00:00:00-07:00</published>
      <updated>2010-03-27T00:00:00-07:00</updated>
    </entry>
  
    
    <entry>
      <id>tag:lostincode.net,2010-03-15:post/home-end-vi-osx</id>
      <link rel="alternate" href="http://lostincode.net/blog/home-end-vi-osx" />
      <title type='html'>How to make Home and End behave in vi, under OS X</title>
      <excerpt type='xhtml'>
        <p>(What is it with terminal-based programs and OS X?)</p>

        <p class='more'><a href="http://lostincode.net/blog/home-end-vi-osx">read the rest &#0187;</a></p>
      </excerpt>
      <content type='xhtml'>
        <p>So you've got Home and End working properly in Terminal.app. Now you go to use vi, start editing a file, switch to insert mode, and quickly find out that Home and End don't work.</p>

<p>Yeah, go ahead. Curse Apple. Let it all out.</p>

<p>Feel better? Right then. <a href="http://serverfault.com/questions/73013/vim-keyboard-remap-on-snow-leopard-macos-10-6">Let's fix vi</a>.</p>

<p>First, type <code>vi ~/.vimrc</code>. It is essential we edit this file in vi as it gives us the ability to type keystrokes without actually doing what those keystrokes do.</p>

<p>Next, switch to insert mode and type <code>map</code> followed by a space. Now press <code class="key">Ctrl-V</code>, and then press the <code class="key">Home</code> key. Depending on what you've set <tt>Home</tt> to be in your Terminal.app preferences, you will see a character sequence. I have <tt>Home</tt> set to <code>Escape-[-H</code> (or <tt>\033[H</tt>), so I see a blue <code>^\[</code> followed by <code>\[H</code>. Now type <code class="key">space</code>, and then type <code>&lt;Home&gt;</code>. This is literally the word "Home" in angle brackets, <em>not</em> the <tt>Home</tt> key.</p>

<p>Got that? <strong>The first "Home" is <code class="key">Ctrl-V</code>, <code class="key">Home</code>. The second "Home" is <code>&lt;Home&gt;</code>.</strong></p>

<p>Once you type that, you will see something like this on-screen (provided you have syntax highlighting on):</p>

<pre>map <span style="color: blue">^[</span>[H <span style="color: blue">&lt;Home&gt;</span></pre>

<p>So what does this do? Well, as you can see <a href="http://www.linux.com/archive/feed/54936">here</a>, <strong>map</strong> allows you to map keys in normal, visual, and operator-pending mode. Really the only thing we're concerned about is normal mode, which is the first mode you're in when you launch vi. So, this line tells vi, "when I press <code class="key">Home</code>, this really means <tt>Home</tt> and not <tt>Escape-[-H</tt>."</p>

<p>However that's not really what we want here --- what we want is to map <tt>Home</tt> in insert mode. We do that with <strong>imap</strong>. So now type <code>imap</code>, <code class="key">space</code>, <code class="key">Ctrl-V</code>, <code class="key">Home</code>, <code class="key">space</code>, <code>&lt;Home&gt;</code>. This is what I saw after I typed that:</p>

<pre>imap <span style="color: blue">^[</span>[H <span style="color: blue">&lt;Home&gt;</span></pre>

<p>Okay. Let's test it out. Save and exit (<code>:wq</code>) and re-enter vim. Now go into insert mode and try pressing <tt>Home</tt> and <tt>End</tt>.</p>

<p>Now repeat the same thing for <tt>End</tt>. You will also want to add another rule for forward delete. Logically, <code>&lt;Delete&gt;</code> represents the delete key.</p>

<p>This is the full contents of my <tt>~/.vimrc</tt> file:</p>

<pre class="no-highlight"><code>map ^[[H &lt;Home&gt;
imap ^[[H &lt;Home&gt;
map ^E &lt;End&gt;
imap ^E &lt;End&gt;
imap ^D &lt;Delete&gt;
</code></pre>

<p>Hope that helped!<span class="end-of-content">☯</span></p>
      </content>
      <published>2010-03-15T00:00:00-07:00</published>
      <updated>2010-03-15T00:00:00-07:00</updated>
    </entry>
  
    
    <entry>
      <id>tag:lostincode.net,2010-01-28:post/git-svn-stitching</id>
      <link rel="alternate" href="http://lostincode.net/blog/git-svn-stitching" />
      <title type='html'>Migrating an SVN repo with an inconsistent structure to Git</title>
      <excerpt type='xhtml'>
        <p><tt>git-svn</tt> (or the Perl/Ruby frontend <tt>svn2git</tt>) is great for converting a simple Subversion repo to Git -- that is, as long as the structure of your SVN repo (trunk/branches/tags or just flat) remained the same through the repo's history. In this post I talk about techniques I found (along with a script I wrote) that makes it possible to fully convert these types of repos.</p>

        <p class='more'><a href="http://lostincode.net/blog/git-svn-stitching">read the rest &#0187;</a></p>
      </excerpt>
      <content type='xhtml'>
        <p>Recently at <a href="http://premierecollectibles.com">work</a> we migrated our code repository from Subversion to Git. You can find numerous guides all over the internet to do this, but none of them covered migrating a repo where the conventional directory structure (trunk, branches, tags) had been introduced halfway into the project. So, I figured it out and wrote a script to do it, and then decided I'd write a walkthrough so that you can follow along if you ever need to do this. <a href="http://lostincode.net#the-scripts">Skip down to the script</a> or continue reading...</p>

<h3 id="the-repository">The repository</h3>

<p>To keep things simple, I'm going to be working against a sample SVN repository. Let's set that up now:</p>

<pre class="prompt"><code>$ sudo svnadmin create /var/svn/svn2git-test
</code></pre>

<p>Here's the first few commits:</p>

<pre class="prompt"><code>$ svn co file:///var/svn/svn2git-test svn
Checked out revision 0.
$ cd svn
$ echo "Lorem ipsum dolor sit amet" &gt; test.txt
$ svn add test.txt
A         test.txt
$ svn commit -m "Initial commit"
Adding         test.txt
Transmitting file data .
Committed revision 1.
$ echo "Here's another line we added in rev 2" &gt;&gt; test.txt
$ svn commit -m "Update test.txt"
Sending        test.txt
Transmitting file data .
Committed revision 2.
$ echo "And another line we added in rev 3" &gt;&gt; test.txt
$ svn commit -m "Update test.txt, again"
Sending        test.txt
Transmitting file data .
Committed revision 3.
</code></pre>

<p>Up to now we don't have a conventional structure yet, we are just putting everything in root. But now we want to make a branch so let's change that:</p>

<pre class="prompt"><code>$ svn mkdir trunk branches tags
A         trunk
A         branches
A         tags
$ svn commit -m "Add trunk, branches, tags"
Adding         branches
Adding         tags
Adding         trunk

Committed revision 4.
$ svn mv test.txt trunk
A         trunk/test.txt
D         test.txt
$ svn commit -m "Move everything to trunk"
Deleting       test.txt
Adding         trunk/test.txt

Committed revision 5.
</code></pre>

<p>Before we make the branch, though, we decide to commit something to trunk:</p>

<pre class="prompt"><code>$ echo "Add another line from trunk, rev 6" &gt;&gt; trunk/test.txt
$ svn commit -m "Update test.txt from trunk"
Sending        trunk/test.txt
Transmitting file data .
Committed revision 6.
</code></pre>

<p>We also need to make sure revision the <tt>trunk</tt> folder is associated with is up to date, otherwise our branch will appear in the wrong place when we convert it:</p>

<pre class="prompt"><code>$ svn up
At revision 6.
</code></pre>

<p>And now we make the branch:</p>

<pre class="prompt"><code>$ svn copy trunk branches/foo
A         branches/foo
$ svn commit -m "Make 'foo' branch"
Adding         branches/foo
Adding         branches/foo/test.txt

Committed revision 7.
</code></pre>

<p>make some changes in the branch:</p>

<pre class="prompt"><code>$ echo "Add another line from foo, rev 8" &gt;&gt; branches/foo/test.txt
$ svn commit -m "Update test.txt from foo"
Sending        branches/foo/test.txt
Transmitting file data .
Committed revision 8.
</code></pre>

<p>and go back and make some changes to trunk:</p>

<pre class="prompt"><code>$ echo "Add another line from trunk, rev 9" &gt;&gt; trunk/test.txt
$ svn commit -m "Update test.txt finally, from trunk"
Sending        trunk/test.txt
Transmitting file data .
Committed revision 9.
</code></pre>

<p>If you're like me, all you want to see is a picture, so here's a graph of the commit history:</p>

<p>
<img src="http://s3.amazonaws.com/lostincode.net/blog/svn_commit_graph.png" alt="SVN commit graph" />
</p>

<h3 id="the-problem">The problem</h3>

<p>At some point down the road, we decide that we want to convert this repository to Git. Now most guides these days will tell you to use <a href="http://github.com/nirvdrum/svn2git/"><tt>svn2git</tt></a>. I agree, it's a great little script that takes care of details you don't want to have to worry about to ensure that your repo is converted properly.</p>

<p>However, if we try to use it on the sample repo we created above, we will quickly find that we don't have all of the commits. First let's do the conversion. Note that my version of Git doesn't let you pass a <tt>file://</tt> URL to git-svn so we have to use <tt>svnserve</tt> so we can refer to the repository using <tt>svn://</tt>:</p>

<pre class="prompt"><code>$ svnserve -d
$ mkdir git1 &amp;&amp; cd git1
$ svn2git svn://localhost/var/svn/svn2git-test
Found possible branch point: svn://localhost/var/svn/svn2git-test/trunk =&gt; svn://localhost/var/svn/svn2git-test/branches/foo, 4
Found branch parent: (refs/remotes/foo) 2b09a1ad55e4b0b1bf826d3718821f9b065d198c
Following parent with do_switch
Successfully followed parent
Checked out HEAD:
  svn://localhost/var/svn/svn2git-test/trunk r9
Note: moving to 'foo' 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 &lt;new_branch_name&gt;
HEAD is now at 42679bc... Update test.txt from foo
Switched to a new branch 'foo'
Note: moving to 'trunk' 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 &lt;new_branch_name&gt;
HEAD is now at dadf507... Update test.txt finally, from trunk
Switched to a new branch 'master'
Counting objects: 15, done.
Delta compression using up to 2 threads.
Compressing objects: 100% (10/10), done.
Writing objects: 100% (15/15), done.
Total 15 (delta 4), reused 0 (delta 0)
</code></pre>

<p>Now let's see open the repository in <a href="http://gitx.frim.nl/">GitX</a> to see what we've got:</p>

<p>
<img src="http://s3.amazonaws.com/lostincode.net/blog/first_svn2git_migration.png" alt="First svn2git migration" />
</p>

<p>As you can see, the history stops at the point that we split the structure, because <tt>git-svn</tt> assumes the structure has been the same from the beginning.</p>

<h3 id="the-research">The research</h3>

<p>I spent a good two days just trying to figure out where to start. A lot of the different things I read involved <a href="http://simeonpilgrim.com/blog/2009/11/17/complex-svn-repository-conversion-to-git/">combining three pieces of history into one repository using grafting and merging</a>, <a href="http://www.ouaza.com/wp/2007/07/24/assembling-bits-of-history-with-git/">assembling history using <tt>git-archive</tt> and <tt>git_load_dirs</tt></a>, <a href="http://blog.orfjackal.net/2009/05/converting-confused-svn-repositories-to.html">converting an inconsistent trunk using <tt>svn2git</tt>'s <tt>--rootistrunk</tt> option, a temporary branch, and <code>git-format patch</code></a>. I also found <a href="http://n2.nabble.com/Merge-two-repos-with-history-included-was-Re-How-do-I-td1691818.html">plenty</a> <a href="http://aartemenko.com/texts/how-to-merge-two-git-repositories/">of</a> <a href="http://stackoverflow.com/questions/1425892/how-do-you-merge-two-git-repositories">solutions</a> for merging one Git repository into another one as a subtree, but that wasn't really what I wanted to do.</p>

<p>However, what ended up being the best resource was a <a href="http://justatheory.com/computers/vcs/git">post</a> by this guy, David Wheeler, who'd taken a CVS repo, SVN repo, converted both of them to Git and then mashed them together into one repository. There's a lot of good information on some of the problems he faced, how he solved them, and a few scripts that he wrote to automate the whole process.</p>

<p>Putting aside <tt>svn2git</tt> for the moment, I knew that I could use <code>git svn init</code> and <code>git svn fetch -r REV1:REV2</code> to make two copies of the SVN repository, one repository that contained the first half before the split to trunk/branches/tags, and another that contained the last half. The trick was figuring out how to merge these halves into one continuous Git repository.</p>

<p>So, armed with new information, I did a couple of experiments on a sample repository (similar to the one I presented earlier). First I tried using <code>git fetch</code> and <code>git rebase</code>:</p>

<pre class="prompt"><code>$ mkdir git.pre &amp;&amp; cd git.pre
$ git svn init svn://localhost/var/svn/svn2git-test
Initialized empty Git repository in /tmp/svn2git/migration_with_rebase/git.pre/.git/
$ git svn fetch -r 1:3
        A    test.txt
r1 = 0a500d79a303cd0a0153e2208d42e825d9f90504 (refs/remotes/git-svn)
        M    test.txt
r2 = 00bfdbf380411ad86ed274aef02e9a28528e0211 (refs/remotes/git-svn)
        M    test.txt
r3 = 6b79e39d6e19256fdbb0a95210570972b349c30b (refs/remotes/git-svn)
Checked out HEAD:
  svn://localhost/var/svn/svn2git-test r3
$ cd ..
$ mkdir git.post &amp;&amp; cd git.post
$ git svn init svn://localhost/var/svn/svn2git-test -s
Initialized empty Git repository in /tmp/svn2git/migration_with_rebase/git.pre/.git/
$ git svn fetch -r 5:HEAD
        A    test.txt
r5 = f8a9998b0bd00144c28a82d74a3099d719ef33f4 (refs/remotes/trunk)
        M    test.txt
r6 = a3a5c0896cac7cd8b4d26b48855a7314e4d30d1f (refs/remotes/trunk)
Found possible branch point: svn://localhost/var/svn/svn2git-test/trunk =&gt; svn://localhost/var/svn/svn2git-test/branches/foo, 4
        A    test.txt
r7 = 005cc439b5b81c9fcc2ab26ed8d8c60c11993061 (refs/remotes/foo)
        M    test.txt
r8 = 83904e2fd2afae9db7af372c2b3154c33c0a58e7 (refs/remotes/foo)
        M    test.txt
r9 = 28d31c35c2696fb477b2c27bded270a14b3dce56 (refs/remotes/trunk)
Checked out HEAD:
  svn://localhost/var/svn/svn2git-test/trunk r9
$ git fetch ../git.pre master:pre
warning: no common commits
remote: Counting objects: 9, done.
remote: Compressing objects: 100% (5/5), done.
remote: Total 9 (delta 2), reused 0 (delta 0)
Unpacking objects: 100% (9/9), done.
From ../git.pre
 * [new branch]      master     -&gt; pre
$ git branch
* master
  pre
$ git branch -r
  foo
  trunk
$ git rebase pre
First, rewinding head to replay your work on top of it...
Applying: Move everything to trunk
Using index info to reconstruct a base tree...
Falling back to patching base and 3-way merge...
No changes -- Patch already applied.
Applying: Update test.txt from trunk
Applying: Update test.txt finally, from trunk
</code></pre>

<p>Basically, I'm attempting to copy all the commits in the first half to the last half, then replaying the commits in the last half on top of the ones in the first half. However, as you can see something was off:</p>

<p>
<img src="http://s3.amazonaws.com/lostincode.net/blog/migration_with_rebase.png" alt="Migration with rebase" />
</p>

<p>If I'd copied the <tt>foo</tt> branch to a local branch it might have worked, but I didn't know how to do that yet.</p>

<p>I also tried something similar:</p>

<pre class="prompt"><code>$ mkdir git.post &amp;&amp; cd git.post
$ svn2git svn://localhost/var/svn/svn2git-test
Found possible branch point: svn://localhost/var/svn/svn2git-test/trunk =&gt; svn://localhost/var/svn/svn2git-test/branches/foo, 4
Found branch parent: (refs/remotes/foo) 2b09a1ad55e4b0b1bf826d3718821f9b065d198c
Following parent with do_switch
Successfully followed parent
Checked out HEAD:
  svn://localhost/var/svn/svn2git-test/trunk r9
Note: moving to 'foo' 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 &lt;new_branch_name&gt;
HEAD is now at 42679bc... Update test.txt from foo
Switched to a new branch 'foo'
Note: moving to 'trunk' 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 &lt;new_branch_name&gt;
HEAD is now at dadf507... Update test.txt finally, from trunk
Switched to a new branch 'master'
Counting objects: 15, done.
Delta compression using up to 2 threads.
Compressing objects: 100% (10/10), done.
Writing objects: 100% (15/15), done.
Total 15 (delta 4), reused 0 (delta 0)
$ cd ..
$ mkdir git.merged &amp;&amp; cd git.merged
$ git svn init svn://localhost/var/svn/svn2git-test
Initialized empty Git repository in /tmp/svn2git/migration_with_fetch/git.merged/.git/
$ git svn fetch -r 1:3
        A    test.txt
r1 = 0a500d79a303cd0a0153e2208d42e825d9f90504 (refs/remotes/git-svn)
        M    test.txt
r2 = 00bfdbf380411ad86ed274aef02e9a28528e0211 (refs/remotes/git-svn)
        M    test.txt
r3 = 6b79e39d6e19256fdbb0a95210570972b349c30b (refs/remotes/git-svn)
Checked out HEAD:
  svn://localhost/var/svn/svn2git-test r3
$ cp ../git.post/.git/config ./.git/config # make sure fetch knows where to put trunk, branches, and tags
$ git svn fetch -r 4:HEAD
r4 = 2b09a1ad55e4b0b1bf826d3718821f9b065d198c (refs/remotes/trunk)
        A    test.txt
r5 = 020e7ff72c87b3711486bbffa4230b2fd9ccc266 (refs/remotes/trunk)
        M    test.txt
r6 = 80fdfdd4fc0f69f79f10c114219da4aae97aabce (refs/remotes/trunk)
Found possible branch point: svn://localhost/var/svn/svn2git-test/trunk =&gt; svn://localhost/var/svn/svn2git-test/branches/foo, 4
Found branch parent: (refs/remotes/foo) 2b09a1ad55e4b0b1bf826d3718821f9b065d198c
Following parent with do_switch
        A    test.txt
Successfully followed parent
r7 = 56356325a446aa2539a6f78f0e11673972a8a8b6 (refs/remotes/foo)
        M    test.txt
r8 = 42679bc779f0842de4a83e99c9fa718df88e4cc6 (refs/remotes/foo)
        M    test.txt
r9 = dadf507389f0342456e8e5e7367f2aa862ec1b4a (refs/remotes/trunk)
</code></pre>

<p>However, this didn't work either, because what were formerly revision 3 and 4 were now disconnected:</p>

<p>
<img src="http://s3.amazonaws.com/lostincode.net/blog/migration_with_fetch.png" alt="Migration with fetch" />
</p>

<p>What I ended up doing in the end was taking the <a href="http://justatheory.com/computers/vcs/git/bricolage-migration/stitch">script David Wheeler wrote to stitch repositories together</a>, running it piece by piece against my sample SVN repository and working out any problems. Once I had that working, I could then run it against the real SVN repository. Before I did this, however, because our repository is rather large, I first copied it to my computer using <a href="http://journal.paul.querna.org/articles/2006/09/14/using-svnsync/"><tt>svnsync</tt></a>:</p>

<pre class="prompt"><code>$ sudo svnsync init /var/svn/store svn+ssh://my@server.com/path/to/real/repo
$ sudo svnsync sync /var/svn/store
</code></pre>

<p>I should say that <a href="http://gitx.frim.nl/">GitX</a> was invaluable in confirming that the new Git repo was complete and that all the history was intact.</p>

<h3 id="the-breakdown">The breakdown</h3>

<p>I'll have the script that I ended up with at the very end, but because you might like to see how it works, I'm going to break it apart for you, using the sample SVN repo I gave at the very beginning. Note that I'm simplifying what the script does using shell script, but the final script is in Perl.</p>

<p>Here's what we'll be doing in a nutshell:</p>

<ol><li>Run <tt>master</tt> for both halves of the SVN repo (pre-repo and post-repo)</li>
  <li>Copy commits from post-repo to pre-repo</li>
  <li>Copy remote branches to local ones on pre-repo</li>
  <li>Graft pre and post together</li>
  <li>Copy remote branches to local ones on the final repo</li>
  <li>Relocate the <tt>master</tt> branch</li>
  <li>Clean up (add remote, etc.)</li>
</ol><p>One more thing. I ended up going with the <a href="http://github.com/schwern/svn2git/">Perl port of <tt>svn2git</tt></a> and then modifying it, converting it to an object-oriented version so I could require it in my script and adding a few things like a <tt>--revision</tt> option. I'll have this at the end too.</p>

<h4 id="one">One</h4>

<p>The first thing we do is run <tt>svn2git</tt> twice:</p>

<pre class="prompt"><code>$ svn2git svn://localhost/var/svn/svn2git-test git.pre --root-is-trunk -r 1:3 --authors /path/to/authors.txt
$ svn2git svn://localhost/var/svn/svn2git-test git.post --authors /path/to/authors.txt
</code></pre>

<p>This will create two Git repositories: the first repo has the part of the SVN repo before the split occurred, the other has the part afterward. I'll be referring to them as "pre-repo" and "post-repo" (or simply "pre" and "post").</p>

<p>At this point here's what the git repos look like:</p>

<p>
<img src="http://s3.amazonaws.com/lostincode.net/blog/pre_repo_after_step_1.png" alt="pre-repo after step 1" />
</p>

<p>
<img src="http://s3.amazonaws.com/lostincode.net/blog/post_repo_after_step_1.png" alt="post-repo after step 2" />
</p>

<h4 id="two">Two</h4>

<p>The next thing we want to do is copy commits (or, in Git parlance, objects) from post-repo to pre-repo. We do this using <code>git fetch</code>:</p>

<pre class="prompt"><code>$ cd git.pre
$ git fetch ../git.post
warning: no common commits
remote: Counting objects: 11, done.
remote: Compressing objects: 100% (4/4), done.
remote: Total 11 (delta 3), reused 11 (delta 3)
Unpacking objects: 100% (11/11), done.
From /tmp/git.post
 * branch            HEAD       -&gt; FETCH_HEAD
</code></pre>

<p>Now, this is supposed to copy objects in local branches from post-repo to pre-repo. However, for whatever reason it didn't do that for me. However, that command isn't totally useful. As git has told you, <tt>FETCH_HEAD</tt> now points to <tt>HEAD</tt> in the post-repo, which happens to point to post-repo's <tt>master</tt> branch. This will prove to be valuable later. So let's save that in a temporary branch:</p>

<pre class="prompt"><code>$ git checkout -b post-master FETCH_HEAD
Switched to a new branch 'post-master'
$ git checkout master
Switched to branch 'master'
</code></pre>

<p>Since the first <code>git fetch</code> didn't do anything, let's try copying objects in remote branches from post to pre. Basically we get a list of the remote branches from post-repo using <code>git branch -r</code>, and for each branch we say something like this:</p>

<pre class="prompt"><code>git fetch ../git.post refs/remotes/$branch:refs/remotes/$branch
</code></pre>

<p>Let's do that for the sample repo:</p>

<pre class="prompt"><code>$ git fetch ../git.post refs/remotes/foo:refs/remotes/foo
remote: Counting objects: 6, done.
remote: Compressing objects: 100% (3/3), done.
remote: Total 4 (delta 1), reused 2 (delta 0)
Unpacking objects: 100% (4/4), done.
From /tmp/git.post
 * [new branch]      foo        -&gt; foo
</code></pre>

<p>I can't find any place that explains quite what that colon syntax does better than <code>man git-fetch</code> does, but I think here we're telling Git, "Hey, be a doll and look at post-repo, find a remote branch called <tt>foo</tt>, and copy all the commits inside to the remote branch <tt>foo</tt> in pre-repo."</p>

<p>At this point here's what the pre-repo looks like:</p>

<p>
<img src="http://s3.amazonaws.com/lostincode.net/blog/pre_repo_after_step_2.png" alt="pre-repo after step 2" />
</p>

<h4 id="three">Three</h4>

<p>If you take a closer look at the screenshot above, you will notice that <tt>master</tt> is colored orange and <tt>foo</tt> is colored blue. This is because <tt>foo</tt> is a remote branch and <tt>master</tt> is a local branch:</p>

<pre class="prompt"><code>$ cd git.pre
$ git branch
* master
  post-master
$ git branch -r
  foo
</code></pre>

<p>So, we need to copy the remote branches over to local branches. We can do that by looping through the remote branches, stripping "origin/" from the branch names if it's present, and saying something like:</p>

<pre class="no-highlight"><code>git branch --no-track $branch refs/remotes/$branch
</code></pre>

<p>Let's do that for the sample repo:</p>

<pre class="prompt"><code>$ git checkout foo
Note: moving to 'foo' 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 &lt;new_branch_name&gt;
HEAD is now at 23a450b... Update test.txt from foo
$ git checkout -b foo
</code></pre>

<p>At this point here's what pre-repo looks like:</p>

<p>
<img src="http://s3.amazonaws.com/lostincode.net/blog/pre_repo_after_step_3.png" alt="pre-repo after step 3" />
</p>

<p>As you can see, there's now a green "foo" next to the blue "foo", since <tt>foo</tt> is now a local branch. We can double-check this through the command line:</p>

<pre class="prompt"><code>$ cd git.pre
$ git branch
  foo
* master
  post-master
</code></pre>

<h4 id="four">Four</h4>

<p>You might think that everything is okay with the repository, judging by the screenshot above. There's another problem with it, however. Do you see it? There isn't a line connecting "Update test.txt, again" and "Add trunk, branches, tags". This is because, in fact, they <em>aren't</em> connected. The first half is the <tt>master</tt> branch -- you can see that <tt>master</tt> points to the end of it. The second half, though, isn't on the <tt>master</tt> branch, it's just kind of floating around in the repository. (<tt>post-master</tt> points to it, but forget that's there.) We can confirm this with <code>git log</code>:</p>

<pre class="prompt"><code>$ cd git.pre
$ git checkout master
Already on 'master'
$ git log
commit ae7596f38fefc8a53bf6f2018391a8c5ff3c0379
Author: elliot &lt;elliot@445a800c-2d3f-4b84-95f0-4d0e8c338740&gt;
Date:   Sun Jan 31 03:02:26 2010 +0000

    Update test.txt, again

commit bead1ec713a5361b0988cc71cbaf08b9c4a1462b
Author: elliot &lt;elliot@445a800c-2d3f-4b84-95f0-4d0e8c338740&gt;
Date:   Sun Jan 31 03:02:25 2010 +0000

    Update test.txt

commit e89a208a2b1aa2bf5b569a4d4e3fbfd23e138615
Author: elliot &lt;elliot@445a800c-2d3f-4b84-95f0-4d0e8c338740&gt;
Date:   Sun Jan 31 03:02:24 2010 +0000

    Initial commit
</code></pre>

<p>So, that's obviously not good. How do we fix this? We can <em>graft</em> the two histories together using a file that's special to Git, <tt>.git/info/grafts</tt>. Each line in the file specifies a connection that looks something like this:</p>

<pre class="no-highlight"><code>&lt;commit id&gt; &lt;parent id&gt; [&lt;parent id&gt;]*
</code></pre>

<p>So if we were to take another look at our repo in GitX and click on the commit where post-repo starts, we would see that its commit id is <tt>d2874583232277a9e8e425a80e1670e9b1193013</tt>. If we click on the commit below, we would see that its commit id is <tt>ae7596f38fefc8a53bf6f2018391a8c5ff3c0379</tt>. So in order to create the connection between them, all we have to do is open <tt>.git/info/grafts</tt> and add this:</p>

<pre class="no-highlight"><code>d2874583232277a9e8e425a80e1670e9b1193013 ae7596f38fefc8a53bf6f2018391a8c5ff3c0379
</code></pre>

<p>The cool thing is that if we save this file, refresh the view in GitX, scroll down and find the split again, we should see that the commits are connected now:</p>

<p>
<img src="http://s3.amazonaws.com/lostincode.net/blog/pre_repo_after_grafting.png" alt="pre-repo after grafting" />
</p>

<p>This connection is temporary, however; we won't be able to push the repository until we apply the change to the repository. To do that, we use <code>git filter-branch</code>. Not only will this create the connections from <tt>.git/info/grafts</tt>, it will also regenerate all the commit ids for every subsequent commit after the new connections. <sup id="fnref:git-filter-branch"><a href="http://lostincode.net#fn:git-filter-branch" rel="footnote">1</a></sup></p>

<p>Something worth noting is that <code>git filter-branch</code> by itself only applies the change to the branch that you're on. If you're only concerned about <tt>master</tt>, that's all right, but if you have any branches that come off of <tt>master</tt> after the split, like we do, those won't be properly rewritten. So to rewrite everything we say this:</p>

<pre class="no-highlight"><code>git filter-branch --tag-name-filter cat -- --all
</code></pre>

<p>So we run that, and then we make sure to</p>

<pre class="no-highlight"><code>rm .git/info/grafts
</code></pre>

<p>so that it doesn't interfere with future changes to pre-repo.</p>

<p>Now, it turns out that <code>git filter-branch</code> saves old commits as it rewrites everything (I suppose in case you want to roll it back or something, I'm not sure). As you can see it looks pretty funky:</p>

<p>
<img src="http://s3.amazonaws.com/lostincode.net/blog/pre_repo_after_git_filter_branch_before_clone.png" alt="pre-repo after git filter-branch, before cloning" />
</p>

<p>To correct this, all we have to do is clone the repo:</p>

<pre class="no-highlight"><code>git clone file:///tmp/git.pre /path/to/git.final
</code></pre>

<p>As David Wheeler points out, it's important to use <tt>file://</tt> here to get a copy of everything, otherwise some of the copied files end up as hard links.</p>

<p>The cloned repo will look like:</p>

<p>
<img src="http://s3.amazonaws.com/lostincode.net/blog/final_repo_after_step_4.png" alt="final repo after step 4" />
</p>

<h4 id="five">Five</h4>

<p>Since we've cloned the repository, we need to copy remote branches to local ones again. However, this time we're going to actually remove the remote branches since we don't want them to interfere with anything when we push the repository to its final place at the end.</p>

<p>This works pretty much the same way as step two (<code>git branch --no-track $branch refs/remotes/$branch</code>), except that we need to make sure we aren't copying over the <tt>master</tt> branch, since we already have that locally.</p>

<h4 id="six">Six</h4>

<p>So let's review: we've created two Git repos from the pre-split and post-split parts of the SVN repo, copied over commits from post to pre, copied remote branches to local branches on pre, grafted pre and post together, cloned that into a final repository, and re-copied remote branches to local branches in the final repo.</p>

<p>Okay, so let's inspect the repo:</p>

<pre class="prompt"><code>$ cd git.final
$ git checkout master
Already on 'master'
$ git log
commit ae7596f38fefc8a53bf6f2018391a8c5ff3c0379
Author: elliot &lt;elliot@445a800c-2d3f-4b84-95f0-4d0e8c338740&gt;
Date:   Sun Jan 31 03:02:26 2010 +0000

    Update test.txt, again

commit bead1ec713a5361b0988cc71cbaf08b9c4a1462b
Author: elliot &lt;elliot@445a800c-2d3f-4b84-95f0-4d0e8c338740&gt;
Date:   Sun Jan 31 03:02:25 2010 +0000

    Update test.txt

commit e89a208a2b1aa2bf5b569a4d4e3fbfd23e138615
Author: elliot &lt;elliot@445a800c-2d3f-4b84-95f0-4d0e8c338740&gt;
Date:   Sun Jan 31 03:02:24 2010 +0000

    Initial commit
</code></pre>

<p>Hmm. That's weird. The history still only goes up to pre-split. But we grafted the two halves together -- that should have been enough, right?</p>

<p>Just to make sure, let's pull up the repo in GitX and see what we have:</p>

<p>
<img src="http://s3.amazonaws.com/lostincode.net/blog/final_repo_after_step_5.png" alt="final repo after step 5" />
</p>

<p>Okay, now we can see that everything's there, but <tt>master</tt> still points to the commit before the split. Is there a way we can move it? Yes -- but we have to tell git exactly <em>where</em> it should move <tt>master</tt> to. You might think it's easy -- can't you just tell Git to find the very latest commit and move <tt>master</tt> to that? Unfortunately not, because what if the latest commit is on a branch, and the branch has been modified beyond <tt>master</tt>?</p>

<p>So we have to go with a different tactic. At some point, <em>something</em> must have pointed to the last commit on post-repo. Of course! It was post's <tt>master</tt> branch that pointed to its last commit. Is there a way we can find out which commit that points to? Probably, but unfortunately, even if we had that commit id, it would be invalid due to <code>git filter-branch</code> having rewritten the history. However, that doesn't mean we can't have stored it in a branch <em>before</em> said history is rewritten. If you remember way back in step one, we did this:</p>

<pre class="no-highlight"><code>$ git fetch ../git.post
$ git checkout -b post-master FETCH_HEAD
</code></pre>

<p>Now you know why. We've have had access to that through the <tt>post-master</tt> branch all along (it's been carried over through the steps). Now we can simply write:</p>

<pre class="prompt"><code>$ git checkout post-master
Switched to branch 'post-master'
$ git branch -D master
Deleted branch master (was ae7596f).
$ git checkout -b master
Switched to a new branch 'master'
$ git branch -D post-master
Deleted branch post-master (was 2ca81cf).
</code></pre>

<p>And just like that, now <tt>master</tt> points to the very end:</p>

<p>
<img src="http://s3.amazonaws.com/lostincode.net/blog/final_repo.png" alt="final repo" />
</p>

<h4 id="seven">Seven</h4>

<p>All that's left now is some cleanup to reduce the size of the repository:</p>

<pre class="prompt"><code>$ git gc
$ git repack -a -d -f --depth 50 --window 50
</code></pre>

<p>While we're at it we can add the URL for the remote repo on our server:</p>

<pre class="prompt"><code>$ git remote rm origin
$ git remote add origin ssh://you@yourserver.com/path/to/repository
</code></pre>

<p>And we're done!</p>

<h3 id="pushing-the-final-repo">Pushing the final repo</h3>

<p>I wanted to say a few words about our Git setup. If you don't want to have to pay for Github it's actually very easy to host your Git repository right on your server. We followed <a href="http://qugstart.com/blog/git-and-svn/migrate-an-svn-repository-to-git-while-maintaining-branches-and-tags-structure/">this guide</a> to set up a <tt>git</tt> user and set permissions on the directory that holds our Git repos. Assuming you have that, any time you create a new project, you can initialize a Git repo on your server using the following commands (taken partially from that and also <a href="https://kerneltrap.org/mailarchive/git/2008/10/9/3569854/thread">this post</a>):</p>

<pre class="bash"><code>su git
cd /path/to/git/repos_dir
umask 007
mkdir proj.git &amp;&amp; cd proj.git
git init --bare
git config core.sharedrepository 1
git config receive.denyNonFastforwards true
find objects -type d -exec chmod 02770 {} \;
chmod -R o-rwx .
chmod -R g=u .
</code></pre>

<p>Notice that we initialize a bare repository. In a non-bare repository, all of the files that hold your project's history is stored in a special <tt>.git</tt> folder inside your project. In a bare repository, the folder <em>is</em> the <tt>.git</tt> folder. It's not totally necessary, but since we'll never be modifying the repo on the server, it saves some disk space.</p>

<p>Now that we have that, all we have to do to push our newly converted repository to the server is this:</p>

<pre class="prompt"><code>$ git push origin --all
</code></pre>

<h3 id="the-scripts">The script(s)</h3>

<p>You can find my stitch script as well as my fork of <tt>svn2git</tt> in <a href="http://gist.github.com/291448">this gist</a>. The stitch script I've put in a gist because it's probably very likely you'll need to change it to fit your repository. For instance, we didn't have any tags in our repository so the stitch script doesn't account for that. Also the <tt>svn2git</tt> fork should probably go on CPAN, but I may do that at a later time.</p>

<p>That's all! If you have any questions, leave them in the comments. <span class="end-of-content">☯</span></p>

<hr /><p id="footnotes-header">
<strong>Footnotes</strong>
<span class="end-of-content">☯</span>
</p>

<div class="footnotes">
  <ol><li id="fn:git-filter-branch">
      <p>The reason we have to regenerate all the commit ids is because commit ids (like other object ids) are SHA1 hashes. And these hashes are generated in part from certain attributes. And one of the attributes for a commit id is the id of the commit's parent.</p>

      <p>So let's take our sample repo for example. When the connection is made between <tt>d287458</tt> and <tt>ae7596f</tt>, Git will set <tt>ae7596f</tt> as the parent of <tt>d287458</tt>. Because <tt>d287458</tt> has a new parent now, when git calculates the SHA1 hash, the commit will have to get a different commit id. But, that means that whichever commit has <tt>d287458</tt> as its parent, that commit will have to get a new commit id. But, that means whichever commit above <em>that</em> will have to get a new commit id. And so on and so on. (You can read more about SHA1 calculation <a href="http://book.git-scm.com/1_the_git_object_model.html">here</a> and <a href="http://www.kernel.org/pub/software/scm/git/docs/user-manual.html#object-details">here</a>.)<a href="http://lostincode.net#fnref:git-filter-branch" rev="footnote">↩</a></p>
    </li>
  </ol></div>
      </content>
      <published>2010-01-28T00:00:00-08:00</published>
      <updated>2010-01-28T00:00:00-08:00</updated>
    </entry>
  
    
    <entry>
      <id>tag:lostincode.net,2010-01-10:post/more-rvm-macports-hell</id>
      <link rel="alternate" href="http://lostincode.net/blog/more-rvm-macports-hell" />
      <title type='html'>More RVM + Macports hell</title>
      <excerpt type='xhtml'>
        <p>RVM is throwing a bus error when I try to install Rubinius. Investigation ensues.</p>

        <p class='more'><a href="http://lostincode.net/blog/more-rvm-macports-hell">read the rest &#0187;</a></p>
      </excerpt>
      <content type='xhtml'>
        <p class="bigger"><strong>tl;dr</strong> -- If you're (still) using MacPorts, and you have <tt>LIBRARY_PATH</tt> and <tt>LD_LIBRARY_PATH</tt> to <tt>/opt/local</tt>, you may want to temporarily (or permanently) unset these when you install a ruby using RVM, especially if you've customized which architecture MacPorts uses.</p>

<hr /><p>I'm using RVM 0.0.99 on OS X Leopard. I want to install Rubinius, so I try running <code>rvm install rbx</code>, and this is what I get:</p>

<pre class="prompt"><code>&lt;e&gt; Error running '/Users/elliot/.rvm/ruby-1.8.7-p248/bin/gem install rake --no-rdoc --no-ri', please check /Users/elliot/.rvm/log/ruby-1.8.7-p248/gems.install.error.log &lt;/e&gt;
</code></pre>

<p>Hmm. That's weird. Let's see what <tt>gems.install.error.log</tt> says:</p>

<pre class="prompt"><code>[2010-01-10 16:52:20] /Users/elliot/.rvm/ruby-1.8.7-p248/bin/gem install rake --no-rdoc --no-ri
/Users/elliot/.rvm/ruby-1.8.7-p248/lib/ruby/1.8/openssl/ssl.rb:31: [BUG] Bus Error
ruby 1.8.7 (2009-12-24 patchlevel 248) [i686-darwin9.8.0]

/Users/elliot/.rvm/scripts/utility: line 127: 11569 Abort trap             /Users/elliot/.rvm/ruby-1.8.7-p248/bin/gem install rake --no-rdoc --no-ri
</code></pre>

<p>What? A bus error? Caused by running <code>gem install rake</code>? Sure enough:</p>

<pre class="prompt"><code>$ rvm 1.8.7
$ gem install rake
/Users/elliot/.rvm/ruby-1.8.7-p248/lib/ruby/1.8/openssl/ssl.rb:31: [BUG] Bus Error
ruby 1.8.7 (2009-12-24 patchlevel 248) [i686-darwin9.8.0]
</code></pre>

<p>It's weird that I'd have a problem all of a suddenly installing something via RVM, because I already have 1.8.7, 1.9.1 and 1.9.2 and I didn't have any problems installing those.</p>

<p>Looking around the interwebs, some people say to <a href="http://redmine.ruby-lang.org/issues/show/405">remove thin or eventmachine</a>. Unfortunately I don't have either since this is a fresh Ruby install. Wayne Seguin, the author of RVM, <a href="http://joshsharpe.com/archives/76">suggested that this points to an architecture mismatch</a>, which kind of makes sense, because in <tt>~/.rvmrc</tt> I have <tt>rvm_archflags</tt> set to <code>-arch i386</code> (although that really shouldn't cause any issues). In any case unsetting that doesn't help.</p>

<p>I land on <a href="http://www.timmedina.net/openssl-eventmachine-and-the-ruby-187-and-ree">this post</a> and suddenly have an idea:</p>

<pre class="prompt"><code>$ port installed | grep openssl
   openssl @0.9.8l_0+darwin+universal (active)
</code></pre>

<p>Oh. I remember now a while back <a href="http://lostincode.net/posts/installing-gems-with-native-extensions/">I was having issues with Nokogiri and libxml2</a>, so I went back and re-installed all my ports as <tt>+universal</tt>. I don't think that's quite the issue, though --- I think it's that when RVM goes to compile Ruby 1.8.7, it's using MacPorts' openssl, instead of (I guess) compiling it from scratch. A quick check in <tt>~/.bashrc</tt> and I realize now that I also modified <tt>LIBRARY_PATH</tt> and <tt>LD_LIBRARY_PATH</tt> to include <tt>/opt/local/</tt>. I'll remove that and then recompile Ruby 1.8.7:</p>

<pre class="prompt"><code>$ rvm install 1.8.7
[...]
Error running 'make ', please check /Users/elliot/.rvm/log/ruby-1.8.7-p248/make.error.log
</code></pre>

<p>Um, hmm. <tt>make.error.log</tt> says:</p>

<pre class="no-highlight"><code>readline.c: In function ‘filename_completion_proc_call’:
readline.c:703: error: ‘filename_completion_function’ undeclared (first use in this function)
readline.c:703: error: (Each undeclared identifier is reported only once
readline.c:703: error: for each function it appears in.)
readline.c:703: warning: assignment makes pointer from integer without a cast
readline.c: In function ‘username_completion_proc_call’:
readline.c:730: error: ‘username_completion_function’ undeclared (first use in this function)
</code></pre>

<p>Ugh. Right. I get this quite a lot, and I always forget how I fix it (it probably has to do with MacPorts too). Fortunately there's something on the <a href="http://rvm.beginrescueend.com/troubleshooting/">RVM troubleshooting page</a> about this:</p>

<pre class="prompt"><code>$ rvm install readline
</code></pre>

<p>Now:</p>

<pre class="prompt"><code>$ rvm install 1.8.7
[...]
Error running 'make ', please check /Users/elliot/.rvm/log/ruby-1.8.7-p248/make.error.log
</code></pre>

<p>Gah! Okay, one last resort:</p>

<pre class="prompt"><code>$ rvm install 1.8.7 -C --with-readline-dir=/Users/elliot/.rvm/usr
</code></pre>

<p>Yay -- that works, and now I can install Rubinius.<span class="end-of-content">☯</span></p>
      </content>
      <published>2010-01-10T00:00:00-08:00</published>
      <updated>2010-01-10T00:00:00-08:00</updated>
    </entry>
  
</feed>

