<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	>

<channel>
	<title>Alieniloquent</title>
	<atom:link href="http://blog.alieniloquent.com/feed/" rel="self" type="application/rss+xml" />
	<link>http://blog.alieniloquent.com</link>
	<description>off on a tangent</description>
	<pubDate>Thu, 22 May 2008 20:53:08 +0000</pubDate>
	<generator>http://wordpress.org/?v=2.5.1</generator>
	<language>en</language>
			<item>
		<title>Don&#8217;t Mandate Velocity</title>
		<link>http://blog.alieniloquent.com/2008/03/31/dont-mandate-velocity/</link>
		<comments>http://blog.alieniloquent.com/2008/03/31/dont-mandate-velocity/#comments</comments>
		<pubDate>Mon, 31 Mar 2008 15:50:08 +0000</pubDate>
		<dc:creator>Samuel</dc:creator>
		
		<category><![CDATA[Agile Software]]></category>

		<category><![CDATA[Programming]]></category>

		<guid isPermaLink="false">http://blog.alieniloquent.com/2008/03/31/dont-mandate-velocity/</guid>
		<description><![CDATA[I came across this amusing (fictional) story about a broken watch, and it&#8217;s impact on the author&#8217;s development process.
I particularly liked one of the author&#8217;s comments in the comment thread:
Velocity is a measurement that comes out of development, not an input that goes into it.
[Uncle Bob] said . . . that when you are trying [...]]]></description>
			<content:encoded><![CDATA[<p>I came across this amusing (fictional) story about a <a href="http://blog.objectmentor.com/articles/2008/03/05/turn-back-the-dial">broken watch</a>, and it&#8217;s impact on the author&#8217;s development process.</p>
<p>I particularly liked one of the author&#8217;s comments in the comment thread:</p>
<blockquote><p>Velocity is a measurement that comes out of development, not an input that goes into it.</p>
<p>[Uncle Bob] said . . . that when you are trying to measure something, it’s counter-productive to put pressure on it.</p></blockquote>
]]></content:encoded>
			<wfw:commentRss>http://blog.alieniloquent.com/2008/03/31/dont-mandate-velocity/feed/</wfw:commentRss>
		</item>
		<item>
		<title>git-svn with svn:externals</title>
		<link>http://blog.alieniloquent.com/2008/03/08/git-svn-with-svnexternals/</link>
		<comments>http://blog.alieniloquent.com/2008/03/08/git-svn-with-svnexternals/#comments</comments>
		<pubDate>Sun, 09 Mar 2008 01:49:03 +0000</pubDate>
		<dc:creator>Samuel</dc:creator>
		
		<category><![CDATA[Programming]]></category>

		<guid isPermaLink="false">http://blog.alieniloquent.com/2008/03/08/git-svn-with-svnexternals/</guid>
		<description><![CDATA[I&#8217;ve really fallen head over heels in love with Git. But my original solution was really a hack. There is a better way to do it. In fact, it&#8217;s so much better, it comes with Git.
I took a look at git-svn when I was researching this a couple weeks ago, and the trouble that I [...]]]></description>
			<content:encoded><![CDATA[<p>I&#8217;ve really fallen <a href="http://blog.alieniloquent.com/2008/02/20/svn-git-awesome/">head</a> over <a href="http://blog.alieniloquent.com/2008/02/22/svn-git-1-still-awesome/">heels</a> in love with Git. But my original solution was really a hack. There is a better way to do it. In fact, it&#8217;s so much better, it comes with Git.</p>
<p>I took a look at <a href="http://www.kernel.org/pub/software/scm/git/docs/git-svn.html"><code>git-svn</code></a> when I was researching this a couple weeks ago, and the trouble that I had was that it didn&#8217;t fetch externals. Rather than figure out the problem, I just moved on with the working solution that I had. But, it bothered me. So I continued to research, and sure enough, Git has a way to do it just fine.</p>
<p>Nazar Aziz over at <a href="http://panthersoftware.com">Panther Software</a> posted an excellent <a href="http://panthersoftware.com/articles/view/3/svn-s-svn-externals-to-git-s-submodule-for-rails-plugins">guide</a> for setting up a Rails app with plugins using <code>git-svn</code> and <a href="http://www.kernel.org/pub/software/scm/git/docs/user-manual.html#submodules">Git submodules</a>. I am going to distill it and add a few notes about how to make your use of Git as unnoticeable to the other SVN users as possible.</p>
<h4>Step One: Clone your externals</h4>
<p>Git submodules are fantastic, but to use them you need Git repositories for each of your externals. Fortunately, you can easily clone them with <code>git-svn</code>. First, to list your externals:</p>
<div class="code">
<pre>$ svn propget svn:externals http://example.com/svn/app/vendor/plugins
foo_plugin  http://example.com/svn/foo_plugin/trunk</pre>
</div>
<p>Now you should make a directory to put your clones of these in.</p>
<div class="code">
<pre>$ mkdir ~/Projects/plugins</pre>
</div>
<p>And then cloning them is as simple as this:</p>
<div class="code">
<pre>$ git svn clone http://example.com/svn/app/foo_plugin/trunk ~/Projects/plugins/foo_plugin</pre>
</div>
<h4>Step Two: Clone your SVN repository</h4>
<p>The next step is to clone your repository sans-externals. We&#8217;ll use <code>git-svn</code> to do that, but we&#8217;ll use it in a slightly different manner. The Git folks recognize that there is a standard layout for SVN repositories. If you tell it where the trunk, branches and tags are kept relative the the URI you provide, it will try to preserve that information. It makes branches for each of the SVN branches, and it makes branches for the tags as well.</p>
<p>Just do this wherever you want your project to live. You may want to rename any SVN working copies you have so that there aren&#8217;t any naming conflicts.</p>
<div class="code">
<pre>$ git svn clone http://example.com/svn/app -T trunk -t tags -b branches</pre>
</div>
<p>That&#8217;ll give you a git repository named &#8220;app&#8221; in the current directory. The master branch will be a remote tracking branch that is set up to track trunk, and other branches are set up for any tags and branches.</p>
<h4>Step Three: Hook up the submodules</h4>
<p>Now that we&#8217;ve got Git repositories for all of the plugins, and a Git repository for our project, we can hook everything up. We will set up a submodule for the external we cloned above.</p>
<p>From within the top-level of your project repository do this:</p>
<div class="code">
<pre>$ git submodule add ~/Projects/plugins/foo_plugin vendor/plugins/foo_plugin</pre>
</div>
<p>After you&#8217;ve added the submodule do this:</p>
<div class="code">
<pre>$ git submodule init
$ git submodule update</pre>
</div>
<p>That should get the code from the plugin repository and into your project repository just like the external did.</p>
<h4>Step Four: Cover your tracks</h4>
<p>When you are using <code>git-svn</code> it commits all of your Git commits into SVN, and you don&#8217;t really want to commit anything into your Git that you don&#8217;t want finding it&#8217;s way into SVN (at least not on the branch that you commit to SVN from). But it is easy to set Git up to ignore all of the files.</p>
<p>First, let&#8217;s make sure Git ignores all the same things SVN was ignoring:</p>
<div class="code">
<pre>$ git svn show-ignore >> .git/info/exclude</pre>
</div>
<p>Then open up <code>.git/info/exclude</code> and add these lines to it:</p>
<div class="code">
<pre># .git/info/exclude
.gitignore
.gitmodules
/vendor/plugins/foo_plugin</pre>
</div>
<p>That should prevent you from committing anything into SVN that is git-specific.</p>
<h4>Step Five: Using this thing</h4>
<p>So once you&#8217;re all set up, you&#8217;ll want to be able to interact with the SVN repository. Here are your two basic operations.</p>
<dl>
<dt>Update from SVN</dt>
<dd>
<div class="code">
<pre>$ git svn rebase</pre>
</div>
<p>    This works just like <code>git-rebase</code>, except it pulls from SVN instead of some other Git branch. It will not work if there are changes that have not been committed to Git. What it does is roll back all of the changes since the last time, and then update from SVN, then reapply the changes in order. If there are conflicts, you resolve them as you would if you were using <code>git-rebase</code>.
  </dd>
<dt>Commit to SVN</dt>
<dd>
<div class="code">
<pre>$ git svn dcommit</pre>
</div>
<p>    This will take all of the commits since your last time and commit them one at a time to SVN. This allows all those people still using SVN to see each individual commit instead of one monster commit.
  </dd>
</dl>
<p>I recommend using SVN to do anything more involved than simple adds, removes, renames and edits.</p>
<p>Something to be aware of with this set up is that your submodules are effectively frozen at whichever revision you cloned. If you want to update them, you&#8217;ll need to first update the cloned repository, and then run this command at the root of your repository:</p>
<div class="code">
<pre>$ git submodule update</pre>
</div>
<p>Another caveat is that you need to keep your development as linear as you can. Don&#8217;t try to do anything crazy with lots of branches and merges between them. SVN can&#8217;t really make sense of it. The big deal here is you want to use <code>git-rebase</code> to pull in changes from SVN.</p>
<p>Here&#8217;s my workflow. I use a branch named work to do all of my work in. I will sync it up with SVN several times a day, just so it isn&#8217;t too stale. This is how I do that:</p>
<div class="code">
<pre>$ git checkout master
$ git svn rebase
$ git checkout work
$ git rebase master</pre>
</div>
<p>Then, when I&#8217;ve commited all of my changes to my work branch, and I&#8217;m ready to commit to SVN:</p>
<div class="code">
<pre>$ git checkout master
$ git merge work
$ git svn rebase # Just to be safe
$ git svn dcommit</pre>
</div>
<p>It works well, and it allows me to do my work disconnected from the network.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.alieniloquent.com/2008/03/08/git-svn-with-svnexternals/feed/</wfw:commentRss>
		</item>
		<item>
		<title>Broken Window in ActiveRecord: ActiveRecord::StatementInvalid</title>
		<link>http://blog.alieniloquent.com/2008/03/03/broken-window-in-activerecord-activerecordstatementinvalid/</link>
		<comments>http://blog.alieniloquent.com/2008/03/03/broken-window-in-activerecord-activerecordstatementinvalid/#comments</comments>
		<pubDate>Mon, 03 Mar 2008 21:28:38 +0000</pubDate>
		<dc:creator>Samuel</dc:creator>
		
		<category><![CDATA[Programming]]></category>

		<category><![CDATA[Ruby]]></category>

		<guid isPermaLink="false">http://blog.alieniloquent.com/2008/03/03/broken-window-in-activerecord-activerecordstatementinvalid/</guid>
		<description><![CDATA[I love ruby, and I love Rails, but in some ways it really is a ghetto. It has a lot of broken windows that only serve to encourage bad coding from developers who should know better. Today I ran into an example of one of those broken windows and I was beside myself. I could [...]]]></description>
			<content:encoded><![CDATA[<p>I love ruby, and I love Rails, but in some ways it really is a ghetto. It has a lot of <a href="http://en.wikipedia.org/wiki/Fixing_Broken_Windows">broken windows</a> that only serve to encourage bad coding from developers who should know better. Today I ran into an example of one of those broken windows and I was beside myself. I could not believe what I was reading.</p>
<p>One of the projects I work on for my employer is an import process that takes a long time. In order to make it resilient to database fail-overs, I wanted to catch the exception that is raised when the connection dies, wait a few seconds, and then try to reconnect. The idea is simple, and it works once I account for the broken window, but I am not pleased with the code I had to write.</p>
<p>When the database connection disappears, the database driver throws an exception. <code>ActiveRecord::Base</code> catches that exception and does this:</p>
<div class="code">
<pre># Find this in Rails 2.0.2
# active_record/connection_adapter/abstract_adapter.rb:121

rescue Exception => e
  # Log message and raise exception.
  # Set last_verfication to 0, so that connection gets verified
  # upon reentering the request loop
  @last_verification = 0
  message = "#{e.class.name}: #{e.message}: #{sql}"
  log_info(message, name, 0)
  raise ActiveRecord::StatementInvalid, message
end</pre>
</div>
<p>This is the exception handler that catches all exceptions raised during a query run by ActiveRecord. As you can see, it snags the class name, and the exception message off of the exception, and then throws the object away, reraising with <code>ActiveRecord::StatementInvalid</code>. So, if your database driver has hundreds of error codes which are provided in order for you to tell specifically what error occurred, such as <code>Mysql::Error</code>, you lost them.</p>
<p>So ActiveRecord provides <em>one</em> exception that covers everything from primary key violations to database connection errors, and the only way to distinguish them is by inspecting the message. Surely, that can&#8217;t be true, right? I dig further and find this:</p>
<div class="code">
<pre># Find this in Rails 2.0.2
# active_record/connection_adapters/mysql_adapter.rb:244
#
# Note: I snipped the error message because it is very long

rescue ActiveRecord::StatementInvalid => exception
  if exception.message.split(":").first =~ /Packets out of order/
    raise ActiveRecord::StatementInvalid, snipped_error_message
  else
    raise
  end
end
</pre>
</div>
<p>That is just completely unacceptable. I can find it in my heart to forgive the abstract adapter for doing something that throws away implementation-specific information, but the Mysql adapter should remedy that. It willingly lets it&#8217;s exception information be cast aside and goes about inspecting what the abstract adapter had the decency to keep around.</p>
<p>&#8220;But that information is good enough to tell what the exception is,&#8221; you might say.</p>
<p>Until the Mysql folks change the error message. The Mysql API exposes numeric constants, and I&#8217;m sure they&#8217;re very careful to keep them the same, but do you think they take the same approach to error messages? I doubt it. They provide a function that will give you an error message given the numeric constant, and encourage you to use it. That&#8217;s what the Mysql bindings for ruby do. </p>
<p>Expecting developers to inspect the exception message is essentially promoting programming with magic numbers. Sure, they&#8217;re string literals, but they&#8217;re still duplicated information, and extremely brittle.</p>
<p>All I&#8217;d want is an <code>inner_exception</code> attribute available on <code>ActiveRecord::StatementInvalid</code> or maybe its parent, and then assign it when doing reraises. Is that too much to ask for?</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.alieniloquent.com/2008/03/03/broken-window-in-activerecord-activerecordstatementinvalid/feed/</wfw:commentRss>
		</item>
		<item>
		<title>SVN + Git + 1 = Still Awesome</title>
		<link>http://blog.alieniloquent.com/2008/02/22/svn-git-1-still-awesome/</link>
		<comments>http://blog.alieniloquent.com/2008/02/22/svn-git-1-still-awesome/#comments</comments>
		<pubDate>Fri, 22 Feb 2008 16:22:16 +0000</pubDate>
		<dc:creator>Samuel</dc:creator>
		
		<category><![CDATA[Programming]]></category>

		<guid isPermaLink="false">http://blog.alieniloquent.com/2008/02/22/svn-git-1-still-awesome/</guid>
		<description><![CDATA[Yesterday I wrote about using SVN and Git together to have version control away from the network your SVN server is on. Now, I&#8217;ll admit, I wrote that shortly after figuring it out and doing it. So, at that time, I hadn&#8217;t actually come back into the office and merged my changes with the repository [...]]]></description>
			<content:encoded><![CDATA[<p>Yesterday I wrote about using <a href="http://blog.alieniloquent.com/2008/02/20/svn-git-awesome/">SVN and Git</a> together to have version control away from the network your SVN server is on. Now, I&#8217;ll admit, I wrote that shortly after figuring it out and doing it. So, at that time, I hadn&#8217;t actually come back into the office and merged my changes with the repository and committed them. Having done that a couple of times now, I&#8217;m here to say that this setup is fantastic.</p>
<p>So using this system you&#8217;re either at the office, so you can use SVN, or you&#8217;re not, so you have to use Git. I&#8217;ll give steps to follow for each. You should probably read the documentation available from the <a href="http://git.or.cz/">Git</a> website to familiarize yourself further with these commands.</p>
<p>These steps assume that you&#8217;ve made a Git branch using the following command:</p>
<div class="code">
<pre>$ git branch home</pre>
</div>
<h4>Taking your work home: SVN -> Git</h4>
<p>Make sure your SVN working copy is as up to date as you want it. Ideally, commit any changes. But, if you&#8217;re in the middle of a change set, that&#8217;s fine.</p>
<div class="code">
<pre>$ git commit -a -m "Merging in changes from SVN since last commit"
$ git checkout home
$ git merge master</pre>
</div>
<p>Now you&#8217;re ready to use Git to continue making your changes while you&#8217;re away from the office.</p>
<h4>Getting back to work: Git -> SVN</h4>
<div class="code">
<pre>Make sure your Git changes are all committed to the <code>home</code> branch.
$ git checkout master
$ svn up</pre>
</div>
<p>Resolve any conflicts from SVN.</p>
<div class="code">
<pre>$ git merge home</pre>
</div>
<p>Resolve any conflicts from Git.</p>
<p>Now you can continue with your changes using SVN, or commit them right away if they&#8217;re already perfect.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.alieniloquent.com/2008/02/22/svn-git-1-still-awesome/feed/</wfw:commentRss>
		</item>
		<item>
		<title>SVN + Git = Awesome</title>
		<link>http://blog.alieniloquent.com/2008/02/20/svn-git-awesome/</link>
		<comments>http://blog.alieniloquent.com/2008/02/20/svn-git-awesome/#comments</comments>
		<pubDate>Wed, 20 Feb 2008 16:08:47 +0000</pubDate>
		<dc:creator>Samuel</dc:creator>
		
		<category><![CDATA[Computer Geekery]]></category>

		<category><![CDATA[Programming]]></category>

		<guid isPermaLink="false">http://blog.alieniloquent.com/2008/02/20/svn-git-awesome/</guid>
		<description><![CDATA[I&#8217;ve been a big fan of SVN for several years now. I even helped my former employer migrate from VSS a couple of years ago after I sold everybody on the idea. I have lots of love for SVN, but it has its limitations, especially the need to have network connectivity to a central repository. [...]]]></description>
			<content:encoded><![CDATA[<p>I&#8217;ve been a big fan of <a href="http://subversion.tigris.org">SVN</a> for several years now. I even helped my former employer <a href="http://blog.alieniloquent.com/2005/10/26/now-powered-by-subversion/">migrate</a> from <acronym title="Visual Source Safe">VSS</acronym> a couple of years ago after I sold everybody on the idea. I have lots of love for SVN, but it has its limitations, especially the need to have network connectivity to a central repository. I know at least <a href="http://blog.excastle.com">some</a> <a href="http://blog.briankohrs.com">people</a> would love to have a way to still commit code when offline. So, here&#8217;s how I did it with SVN and <a href="http://git.or.cz/">Git</a>.</p>
<p>Git is a <acronym title="Distributed Version Control System">DVCS</acronym> that works differently than SVN. Instead of making changes in your working copy and submitting them to a central repository, your working copy <em>is</em> your repository. You can push changes to another repository or you can pull changes from another repository.  It&#8217;s a nice way of working, and it&#8217;s what they use on the Linux kernel. The Git folks have a nice <a href="http://git.or.cz/course/svn.html">tutorial</a> for SVN users.</p>
<p>The key feature of Git that makes it well suited for use alongside SVN is that it keeps <em>all</em> of its metadata in one folder at the top of your repository. It does not put one in each directory like SVN does. So you can make your SVN working copy into a Git repository and then ignore the folder and SVN knows nothing about it. Here&#8217;s what you do.</p>
<p>At the top level of your SVN working copy:</p>
<div class="code">
<pre>$ git init
$ echo .svn &gt; .gitignore
$ git add *
$ git add .gitignore
$ git commit -m "Initial commit"</pre>
</div>
<p>Now we just need to teach SVN to ignore the Git stuff. So open up your <code>~/.subversion/config</code> file and find the <code>[miscellany]</code> section. You should see a commented out setting for <code>global-ignores</code>. Uncomment it and add <code>.git*</code> to it like this:</p>
<div class="code">
<pre>[miscellany]
### Set global-ignores to a set of whitespace-delimited globs
### which Subversion will ignore in its &#8217;status&#8217; output, and
### while importing or adding files and directories.
global-ignores = *.o *.lo *.la \#*\# .*.rej *.rej .*~ *~ .\#* .DS_Store .git*</pre>
</div>
<p>And voila! When you&#8217;re able to connect to your SVN repo, you can use SVN. But when you&#8217;re offline and still want the ability to use version control to incrementally save your changes, you can use Git. They&#8217;re working on the same files, so they play together very nicely.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.alieniloquent.com/2008/02/20/svn-git-awesome/feed/</wfw:commentRss>
		</item>
		<item>
		<title>Crunch Mode</title>
		<link>http://blog.alieniloquent.com/2008/02/18/crunch-mode/</link>
		<comments>http://blog.alieniloquent.com/2008/02/18/crunch-mode/#comments</comments>
		<pubDate>Mon, 18 Feb 2008 20:11:14 +0000</pubDate>
		<dc:creator>Samuel</dc:creator>
		
		<category><![CDATA[Agile Software]]></category>

		<category><![CDATA[Programming]]></category>

		<guid isPermaLink="false">http://blog.alieniloquent.com/2008/02/18/crunch-mode/</guid>
		<description><![CDATA[James Golick writes about crunch mode and how it can turn a team of even the best all-star code artists in to mediocre programmers.
I have been on an agile team full of all-star programmers. Every one of them as bright as the sun, and every one of them dedicated to writing quality software. Sure, we [...]]]></description>
			<content:encoded><![CDATA[<p>James Golick writes about <a href="http://jamesgolick.com/2008/2/18/the-crunch-mode-paradox-turning-superstars-average">crunch mode</a> and how it can turn a team of even the best all-star code artists in to mediocre programmers.</p>
<p>I have been on an agile team full of all-star programmers. Every one of them as bright as the sun, and every one of them dedicated to writing quality software. Sure, we inherited a legacy code base of nearly a million lines of not-so-all-star code, but that&#8217;s the same situation everybody else is in too, right? It took us a couple of years to really get the agile juices flowing, but once we did, it was great. Except for crunch mode.</p>
<p>I&#8217;ve seen what James is talking about first hand. I&#8217;ve <em>been</em> what James is talking about. What I&#8217;ve never understood is why crunch mode seems more appealing to managers than facilitating the things a team needs to truly deliver on the promise of constantly shippable code. To me, the value proposition of being able to ship after any week- or month-long iteration is a big win over going into crunch mode to hit a date.</p>
<p>But I&#8217;m a developer, what do I know about managing projects, right?</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.alieniloquent.com/2008/02/18/crunch-mode/feed/</wfw:commentRss>
		</item>
		<item>
		<title>Beauty is Important</title>
		<link>http://blog.alieniloquent.com/2008/02/18/beauty-is-important/</link>
		<comments>http://blog.alieniloquent.com/2008/02/18/beauty-is-important/#comments</comments>
		<pubDate>Mon, 18 Feb 2008 14:46:49 +0000</pubDate>
		<dc:creator>Samuel</dc:creator>
		
		<category><![CDATA[Programming]]></category>

		<guid isPermaLink="false">http://blog.alieniloquent.com/2008/02/18/beauty-is-important/</guid>
		<description><![CDATA[I was reminded of one of my favorite quotes today.
Beauty is more important in computing than anywhere else in technology because software is so complicated. Beauty is the ultimate defense against complexity.
&#8212; Machine Beauty: Elegance and the Heart of Computing, David Gelernter
]]></description>
			<content:encoded><![CDATA[<p>I was reminded of one of my favorite quotes today.</p>
<blockquote cite="http://www.amazon.com/exec/obidos/ASIN/046504316X"><p>Beauty is more important in computing than anywhere else in technology because software is so complicated. Beauty is the ultimate defense against complexity.</p>
<p>&mdash; <a href="http://www.amazon.com/exec/obidos/ASIN/046504316X">Machine Beauty: Elegance and the Heart of Computing</a>, David Gelernter</p></blockquote>
]]></content:encoded>
			<wfw:commentRss>http://blog.alieniloquent.com/2008/02/18/beauty-is-important/feed/</wfw:commentRss>
		</item>
		<item>
		<title>String transforms using Enumerable#inject</title>
		<link>http://blog.alieniloquent.com/2008/02/15/string-transforms-using-enumerableinject/</link>
		<comments>http://blog.alieniloquent.com/2008/02/15/string-transforms-using-enumerableinject/#comments</comments>
		<pubDate>Sat, 16 Feb 2008 00:25:09 +0000</pubDate>
		<dc:creator>Samuel</dc:creator>
		
		<category><![CDATA[Functional]]></category>

		<category><![CDATA[Object Oriented]]></category>

		<category><![CDATA[Programming]]></category>

		<category><![CDATA[Ruby]]></category>

		<guid isPermaLink="false">http://blog.alieniloquent.com/2008/02/15/string-transforms-using-enumerableinject/</guid>
		<description><![CDATA[I love functional programming, and I love Ruby. One of the most awesome things about Ruby is how much it borrows from the functional programming mindset. One of the most powerful concepts that functional programming brings to the table is higher-order functions. Ruby&#8217;s Enumerable module is a great example of how it embraces the idea [...]]]></description>
			<content:encoded><![CDATA[<p>I love functional programming, and I love <a href="http://www.ruby-lang.org">Ruby</a>. One of the most awesome things about Ruby is how much it borrows from the functional programming mindset. One of the most powerful concepts that functional programming brings to the table is higher-order functions. Ruby&#8217;s <code>Enumerable</code> module is a great example of how it embraces the idea of higher-order functions to abstract out the various things you do with a collection and let you focus on the operation for each item.</p>
<p>One of the most mysterious methods on <code>Enumerable</code> is <code>Enumerable#inject</code>.  The example that&#8217;s always given is this:</p>
<div class="code">
<pre>
irb> [1, 2, 3, 4].inject(0) {|sum, i| sum + i}
10
</pre>
</div>
<p>That&#8217;s fine, and usually makes sense. But when you try to branch out into more esoteric uses of inject, it can get confusing. So I&#8217;m going to give an example of accomplishing something useful with inject that you hopefully find useful.</p>
<p>I always find myself doing a sequence of substitutions on a string. For example, when I implement a <a href="http://tools.ietf.org/html/rfc854">Telnet</a> client, I like to normalize the line endings I&#8217;m sending so that they&#8217;re sane. I accomplish that by translating &#8220;\r\n&#8221; to &#8220;\n&#8221;, then translating &#8220;\r&#8221; to &#8220;\n&#8221;, then translating &#8220;\n&#8221; to &#8220;\r\n&#8221;. It&#8217;s a simple thing to do, and I could do it like this:</p>
<div class="code">
<pre>
string.gsub("\r\n", "\n").gsub("\r", "\n").gsub("\n", "\r\n")
</pre>
</div>
<p>But that&#8217;s not very extensible. I&#8217;d like to apply this idea of a sequence of substitutions in an abstract way so that I can do dynamically. And while I could do something with <code>Object#send</code>, that&#8217;s like cheating. This is where inject comes to the rescue.</p>
<div class="code">
<pre>
def normalize_line_endings(string)
  transforms = [proc {|s| s.gsub("\r\n", "\n")},
                proc {|s| s.gsub("\r", "\n")},
                proc {|s| s.gsub("\n", "\r\n")}]
  transforms.inject(string) {|s, transform| transform.call(s)}
end
</pre>
</div>
<p><code>Kernel#proc</code> (or <code>Kernel#lambda</code> if you prefer) is Ruby&#8217;s way of making higher-order functions. It returns a block which you can then call with an argument. In the above code, I make an array of transforms that take a string and return a string. The call to inject at the end is where the magic happens. It calls the first transform with <code>string</code> which was provided as the argument to inject. Then it calls the second transform with the result of the first, and it calls the third transform with the result of the second. That list could be as big as you want. It could even be dynamically generated.</p>
<p>That&#8217;s nice, but it&#8217;s still a a little verbose. I like to hide my use of <code>Kernel#proc</code> behind a declarative interface when I&#8217;m doing this sort of thing with it. So here&#8217;s how we can rewrite the method.</p>
<div class="code">
<pre>
def transform(string, specifications = [])
  transforms = specifications.collect do |spec|
    proc {|s| s.gsub(spec[:from], spec[:to])}
  end
  transforms.inject(string) {|s, transform| transform.call(s)}
end

def normalize_line_endings(string)
  transform(string, [{:from => "\r\n", :to => "\n"},
                     {:from => "\r", :to => "\n"},
                     {:from => "\n", :to => "\r\n"}])
end
</pre>
</div>
<p>Of course, at that point, we don&#8217;t really need to create the procs. We can just use inject right on the specifications array, so the final code I came up with for this was:</p>
<div class="code">
<pre>
def transform(string, specifications = [])
  specifications.inject(string) do |s, spec|
    s.gsub(spec[:from], spec[:to])
  end
end

def normalize_line_endings(string)
  transform(string, [{:from => "\r\n", :to => "\n"},
                     {:from => "\r", :to => "\n"},
                     {:from => "\n", :to => "\r\n"}])
end
</pre>
</div>
<p>Now that can be used with any list of transformations. Those transformations can be dynamically generated, and it&#8217;s a very clean implementation. That is the power of <code>Enumerable#inject</code>.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.alieniloquent.com/2008/02/15/string-transforms-using-enumerableinject/feed/</wfw:commentRss>
		</item>
		<item>
		<title>OCaml Talk</title>
		<link>http://blog.alieniloquent.com/2008/02/06/ocaml-talk/</link>
		<comments>http://blog.alieniloquent.com/2008/02/06/ocaml-talk/#comments</comments>
		<pubDate>Wed, 06 Feb 2008 21:01:35 +0000</pubDate>
		<dc:creator>Samuel</dc:creator>
		
		<category><![CDATA[Computer Geekery]]></category>

		<category><![CDATA[ML]]></category>

		<category><![CDATA[Programming]]></category>

		<guid isPermaLink="false">http://blog.alieniloquent.com/2008/02/06/ocaml-talk/</guid>
		<description><![CDATA[So, I was going to give a talk on OCaml at ODYNUG last night. But, well, snow happened, and the meeting was canceled.
I will be giving the talk next month, on March 4th along with Brent Adkisson who will be giving a talk about Android.
]]></description>
			<content:encoded><![CDATA[<p>So, I was going to give a talk on <a href="http://caml.inria.fr/">OCaml</a> at <a href="http://odynug.blainebuxton.com/">ODYNUG</a> last night. But, well, snow happened, and the meeting was canceled.</p>
<p>I will be giving the talk next month, on March 4th along with <a href="http://bablingmonkey.blogspot.com/">Brent Adkisson</a> who will be giving a talk about <a href="http://code.google.com/android/">Android</a>.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.alieniloquent.com/2008/02/06/ocaml-talk/feed/</wfw:commentRss>
		</item>
		<item>
		<title>Adding files to auto-mode-alist</title>
		<link>http://blog.alieniloquent.com/2008/01/31/adding-files-to-auto-mode-alist/</link>
		<comments>http://blog.alieniloquent.com/2008/01/31/adding-files-to-auto-mode-alist/#comments</comments>
		<pubDate>Thu, 31 Jan 2008 13:57:11 +0000</pubDate>
		<dc:creator>Samuel</dc:creator>
		
		<category><![CDATA[Computer Geekery]]></category>

		<guid isPermaLink="false">http://blog.alieniloquent.com/2008/01/31/adding-files-to-auto-mode-alist/</guid>
		<description><![CDATA[One of the things that I require from an editor is decent syntax highlighting. Emacs provides me that, and it also provides me with awesome indentation (I&#8217;ve grown addicted to hitting TAB and having my text just go to the right place regardless of where my cursor is). Emacs has a mode for every occasion [...]]]></description>
			<content:encoded><![CDATA[<p>One of the things that I require from an editor is decent syntax highlighting. Emacs provides me that, and it also provides me with awesome indentation (I&#8217;ve grown addicted to hitting TAB and having my text just go to the right place regardless of where my cursor is). Emacs has a mode for every occasion and typically will load the right one based on the name of the file or its content. Recently, mine stopped doing that.</p>
<p>At first it was annoying. I&#8217;d open a LaTeX file and it wouldn&#8217;t change to <code>latex-mode</code>, or I&#8217;d open a C file and it wouldn&#8217;t go into <code>c-mode</code>, and worst of all, I&#8217;d load Emacs lisp files and they wouldn&#8217;t load in <code>emacs-lisp-mode</code>. I would just switch the mode by hand, but my patience could only last for so long.</p>
<p>Yesterday I finally took the time to find the trouble, shoot it, and replace it with better code. In my <code>.emacs</code> I had this:</p>
<div class="code">
<pre>
(setq auto-mode-alist
      (append
        '(("\\.dtd$" . xml-mode)
          ("\\.xml$" . xml-mode)
          ("\\.yml$" . conf-mode)
          ("bash_profile$" . sh-mode)
          ("bashrc$" . sh-mode))
        auto-mode-alist))
</pre>
</div>
<p>I&#8217;ve seen that same code all over the internet, and it used to work just fine. But for some reason, now it does something to my <code>auto-mode-alist</code> and makes Emacs hate it for some reason. So I do some research. The recommended way to put stuff in an alist like that is <code>ADD-TO-LIST</code>.  </p>
<p>So the above code becomes this:</p>
<div class="code">
<pre>
(mapcar (lambda (mapping) (add-to-list 'auto-mode-alist mapping))
        '(("\\.dtd$" . xml-mode)
          ("\\.xml$" . xml-mode)
          ("\\.yml$" . conf-mode)
          ("bash_profile$" . sh-mode)
          ("bashrc$" . sh-mode)))
</pre>
</div>
<p>Putting that code in fixed my problems, and now all of my modes load correctly.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.alieniloquent.com/2008/01/31/adding-files-to-auto-mode-alist/feed/</wfw:commentRss>
		</item>
	</channel>
</rss>
