<?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"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>refactr blog on software development, design, agile processes, and business</title>
	<atom:link href="http://refactr.com/blog/feed/" rel="self" type="application/rss+xml" />
	<link>http://refactr.com/blog</link>
	<description>informs on and evangelizes best practices of using  &#60;a href="http://refactr.com/the-agile-manifesto/"&#62;agile methods&#60;/a&#62; when designing and developing what are currently being called “Web 2.0” products and applications.</description>
	<lastBuildDate>Fri, 11 May 2012 20:51:34 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.3</generator>
		<item>
		<title>iPad Wedding DJ</title>
		<link>http://refactr.com/blog/2012/05/ipad-wedding-dj/</link>
		<comments>http://refactr.com/blog/2012/05/ipad-wedding-dj/#comments</comments>
		<pubDate>Fri, 11 May 2012 16:00:13 +0000</pubDate>
		<dc:creator>Steve Vlaminck</dc:creator>
				<category><![CDATA[Music]]></category>
		<category><![CDATA[iPad]]></category>
		<category><![CDATA[Rdio]]></category>
		<category><![CDATA[Spotify]]></category>

		<guid isPermaLink="false">http://refactr.com/blog/?p=1220</guid>
		<description><![CDATA[iPad Wedding DJ I’m a newlywed, and my one responsibility for the wedding (short of showing up on time in my suit) was to handle the music at the reception. Which is good, because that’s really the only thing that &#8230; <a href="http://refactr.com/blog/2012/05/ipad-wedding-dj/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<p><strong>iPad Wedding DJ</strong><br />
I’m a newlywed, and my one responsibility for the wedding (short of showing up on time in my suit) was to handle the music at the reception. Which is good, because that’s really the only thing that I could possibly contribute.</p>
<p>I instantly decided against hiring a DJ, because paying someone a bunch of money, telling him exactly which songs to play and which songs not to play didn’t sound worth it to me. I also decided against using an iPod, mostly because I don’t have one, but also because we allowed people to request songs on our wedding website, and we got a lot of requests for songs that we didn’t already own. Not wanting to buy all of those songs (some of which I would definitely NEVER listen to again), I decided my iPad would be our DJ and I would use a music streaming app.</p>
<p><strong>Which to Choose?</strong><br />
My first plan was to make my playlists in Rdio, syncing them to my iPad so I wouldn’t have to worry about internet connectivity. All was well until I got requests for songs that Rdio doesn’t have. Rdio can match your local files, but it only adds the songs Rdio has; the rest get ignored. This is when I realized Rdio is the worst&#8230; except for everything else.</p>
<p>Spotify allows you to play your local files through their player so I bought a subscription and gave up on Rdio. After re-creating my playlists in Spotify, I downloaded their app on my iPad. At the time they didn’t have an iPad compatible app. (They released that about a week after my wedding. Seriously.) Their iPhone app looked funny on the iPad, but at least it would work. The only problem I had syncing local files to the mobile app was with the song <em>She Moves In Her Own Way</em> by The Kooks. Spotify has an acoustic version of the album, but not the original release. The album and all the songs are named the same, but the songs are different and even the song times are different, but that wasn’t enough. When I tried to sync the original release of the song to my iPad, Spotify kept giving me the acoustic version. I ended up renaming the song to get it to sync. Pretty annoying.</p>
<p>And then there’s crossfading. If there’s one feature on all music players that I rarely use, it’s crossfade. I don’t really care for it, but when you need it, you REALLY need it. If there is a second of silence on the dance floor, people will sit down. Well, guess what the Spotify app couldn’t do? (And yes, to answer the question you’re no doubt asking, the version they released a week later can do it. SERIOUSLY?!) The desktop version of Spotify had the crossfade feature though. It wasn’t looking very good for the iPad.</p>
<p><strong>Bummer&#8230; Except Not Really</strong><br />
I begrudgingly came to the conclusion that my only remaining option was to give up on the iPad and use Spotify on a computer. Having to open it to change playlists would be annoying, but for better functionality, it would be necessary. But because I was already using my computer for our photo booth, it meant I had to borrow one. Fortunately, there was no shortage of MacBook Pros among my friends.</p>
<p>In the end, the music worked out great. I’d definitely recommend Spotify for DJ purposes, especially now that they’ve released their iPad-friendly app. And did I mention that it came out a week after my wedding? I did? Well&#8230; that really sucked.</p>
]]></content:encoded>
			<wfw:commentRss>http://refactr.com/blog/2012/05/ipad-wedding-dj/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Grails Tips: Deployment Tricks</title>
		<link>http://refactr.com/blog/2012/05/grails-tips-deployment-tricks/</link>
		<comments>http://refactr.com/blog/2012/05/grails-tips-deployment-tricks/#comments</comments>
		<pubDate>Thu, 10 May 2012 18:00:40 +0000</pubDate>
		<dc:creator>Josh Reed</dc:creator>
				<category><![CDATA[Agile Processes]]></category>
		<category><![CDATA[Software Development]]></category>
		<category><![CDATA[deployment]]></category>
		<category><![CDATA[grails]]></category>
		<category><![CDATA[tricks]]></category>

		<guid isPermaLink="false">http://refactr.com/blog/?p=1223</guid>
		<description><![CDATA[I&#8217;m often working with several versions of a project deployed across a variety of deployment environments. Grails makes it easy to manage all of the configuration for these environments, and also allows you to switch the environment at deployment time &#8230; <a href="http://refactr.com/blog/2012/05/grails-tips-deployment-tricks/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<p>I&#8217;m often working with several versions of a project deployed across a variety of deployment environments. Grails makes it easy to manage all of the configuration for these environments, and also allows you to switch the environment at deployment time by setting a JVM property. However, in our lower environments we&#8217;re sharing servers between multiple projects so setting a blanket environment isn&#8217;t always possible. On more than one occasion I&#8217;ve found myself wondering which environment a particular WAR file was configured for. By default, the WAR file generated by Grails is named after the app name and the app version e.g., <em>supercoolapp-0.5.war</em>, but a minor tweak to your <strong>BuildConfig.groovy</strong> file will add the environment to filename:</p>
<pre>grails.project.war.file="target/${appName}-${grails.util.Environment.current.name}-${appVersion}.war"</pre>
<p>After getting the correct WAR file deployed, the next challenge is identifying the version of code running if/when bugs are found. Grails has a built-in mechanism for versioning which works well when I remember to actually use it. And unless you&#8217;re setting a new, unique version after each change, the version won&#8217;t tell you exactly what code is running. Fortunately, Git gives us an easy and automatic way to identify the code&#8211;commit hashes. The only trick is getting the hash into the app so it can be displayed. To accomplish this, we can hook into the Grails event model to ask Git for the current commit hash at compile time. Create a <strong>scripts/_Events.groovy</strong> file with the following contents:</p>
<pre>eventCompileStart = { msg -&gt;
  new File("grails-app/views/_git.gsp").text = ("git rev-parse HEAD".execute().text)
}</pre>
<p>This will put the latest Git commit hash into a GSP template called <strong>_git.gsp</strong> which you can include on any page in your app. I&#8217;ll generally put this in the footer of the main layout, either visible or commented out, so it is on every page. You&#8217;ll want to add <em>_git.gsp</em> to your <em>.gitignore</em> file since it will change frequently.</p>
<p>Hopefully these two little tricks will make working with your Grails apps across different deployment environments a little bit easier.</p>
]]></content:encoded>
			<wfw:commentRss>http://refactr.com/blog/2012/05/grails-tips-deployment-tricks/feed/</wfw:commentRss>
		<slash:comments>5</slash:comments>
		</item>
		<item>
		<title>Grails In-Memory Cache using Google&#8217;s Guava Library</title>
		<link>http://refactr.com/blog/2012/05/grails-in-memory-cache-using-googles-guava-library/</link>
		<comments>http://refactr.com/blog/2012/05/grails-in-memory-cache-using-googles-guava-library/#comments</comments>
		<pubDate>Wed, 09 May 2012 14:07:03 +0000</pubDate>
		<dc:creator>Matt Nohr</dc:creator>
				<category><![CDATA[Software Development]]></category>
		<category><![CDATA[cache]]></category>
		<category><![CDATA[grails]]></category>
		<category><![CDATA[guava]]></category>
		<category><![CDATA[performance]]></category>

		<guid isPermaLink="false">http://refactr.com/blog/?p=1167</guid>
		<description><![CDATA[In a Grails application, there are a couple of cases where you may want to consider storing data in a in-memory cache.  For example: If it is expensive to read/create the data (reading across the network) If the data will &#8230; <a href="http://refactr.com/blog/2012/05/grails-in-memory-cache-using-googles-guava-library/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<p>In a Grails application, there are a couple of cases where you may want to consider storing data in a in-memory cache.  For example:</p>
<ul>
<li>If it is expensive to read/create the data (reading across the network)</li>
<li>If the data will be used more than once</li>
<li>If multiple users need to access the data so you need to store it outside of a single user session</li>
</ul>
<p>Here I will give you one example of how to use an in-memory cache. This can greatly improve performance but there are a couple of things you must keep in mind.</p>
<p><span id="more-1167"></span></p>
<p><strong>Scoped Services</strong></p>
<p>One approach for storing the data is in an instance variable in a service. By default, <a title="Grails Documentation - Scoped Services" href="http://grails.org/doc/latest/guide/services.html#scopedServices">Grails services are singletons</a>, so only one instance of the service ever exists. Because of this, you could do something like this:</p>
<pre>class MyService {
    private def cache

    public MyService() {
        //initialize the cache
    }

    public getValue(String key){
        //load value if it is not in cache
        //return value from cache
    }
}</pre>
<p>Every request from a controller that accesses the service will be accessing the same instance, and therefore will be accessing the same &#8220;cache&#8221; variable.</p>
<p><strong>Cache Considerations</strong></p>
<p>This can be pretty powerful, and can help performance considerably, but there are some considerations you must think about.</p>
<ol>
<li>Concurrency &#8211; Since all requests are going to be accessing the same instance, you must ensure that the &#8220;cache&#8221; variable is accessed in a thread-safe way or correctly handles concurrency</li>
<li>Memory Size &#8211; Since there will only ever be one instance, there should be a mechanism for removing old entries from the cache and/or limiting the size of the cache.</li>
</ol>
<p><strong>Google&#8217;s Guava Cache Library</strong></p>
<p>A very good way to handle this is to use <a href="http://code.google.com/p/guava-libraries/wiki/CachesExplained">Google&#8217;s Guava cache library</a>. Some of the key benefits are:</p>
<ul>
<li>It has built in concurrency handling</li>
<li>You can expire contents of the cache automatically</li>
<li>You can limit the size of the cache</li>
<li>You can just call &#8220;get&#8221; on the cache and it will either return the object from the cache or load it if needed</li>
</ul>
<p>To include the Guava libraries in your Grails project, you need to update your BuildConfig.groovy and add this line:</p>
<pre>grails.project.dependency.resolution = {
    dependencies {
        compile "com.google.guava:guava:12.0"
    }
}</pre>
<p>Then to setup your cache in your service you can do this:</p>
<pre>public MyService() {
    //initialize the cache
    cache = CacheBuilder.newBuilder().
	expireAfterWrite(60, TimeUnit.MINUTES).
	maximumSize(500).
	build(new CacheLoader() {
		public MyExpensiveObject load(String key) {
		    return doExpensiveLoadOperation()
		}
        })
}</pre>
<p>This cache (a <a href="http://docs.guava-libraries.googlecode.com/git/javadoc/com/google/common/cache/LoadingCache.html">LoadingCache</a> object) will have a maximum of 500 entries and each entry will expire after 60 minutes. If the value is not already in the cache, the &#8220;load()&#8221; method will be called and the result (a MyExpensiveObject in this case) will be returned. There are other configurations to expire cache entries well explained in the documentation.</p>
<p>To use the cache then you would just do this:</p>
<pre>def getValue(String key){
    return cache.get(key)
}</pre>
<p>You do not need to check if the object is in the cache because if it is not it will automatically be loaded.</p>
<p><strong>Conclusion</strong></p>
<p>Using an instance variable on a singleton service can serve as an in-memory cache, and by using the Guava libraries you can overcome the most complicated issues surrounding caching.</p>
<p><strong>References</strong></p>
<ul>
<li><a title="Grails Documentation - Scoped Services" href="http://grails.org/doc/latest/guide/services.html#scopedServices">Scoped Services From Grails Documentation</a></li>
<li><a title="Google Guava Caches" href="http://code.google.com/p/guava-libraries/wiki/CachesExplained">Google Guava Library &#8211; Caches Explained</a></li>
</ul>
]]></content:encoded>
			<wfw:commentRss>http://refactr.com/blog/2012/05/grails-in-memory-cache-using-googles-guava-library/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>Music in the Office</title>
		<link>http://refactr.com/blog/2012/05/music-in-the-office/</link>
		<comments>http://refactr.com/blog/2012/05/music-in-the-office/#comments</comments>
		<pubDate>Tue, 08 May 2012 16:00:51 +0000</pubDate>
		<dc:creator>Dane Messall</dc:creator>
				<category><![CDATA[Music]]></category>
		<category><![CDATA[iTunes]]></category>
		<category><![CDATA[Rdio]]></category>
		<category><![CDATA[Refactr]]></category>
		<category><![CDATA[Small Teams]]></category>
		<category><![CDATA[Spotify]]></category>
		<category><![CDATA[Team]]></category>

		<guid isPermaLink="false">http://refactr.com/blog/?p=1073</guid>
		<description><![CDATA[If you work in an office the likelihood that you spend a major chunk of your day plugged into music is pretty high. I know it is for me and it’s also a safe assumption to make about my coworkers. &#8230; <a href="http://refactr.com/blog/2012/05/music-in-the-office/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<p><a href="http://refactr.com/blog/2012/05/music-in-the-office/work-desk/" rel="attachment wp-att-1189"><img class="alignright size-full wp-image-1189" title="work-desk" src="http://refactr.com/blog/wp-content/uploads/2012/05/work-desk.jpg" alt="" width="175" height="235" /></a>If you work in an office the likelihood that you spend a major chunk of your day plugged into music is pretty high. I know it is for me and it’s also a safe assumption to make about my coworkers.</p>
<p>Music is something most of us take quite seriously, but have you ever thought about the effect music has on the workplace? Think of what your day would be like without music in your office.<br />
<span id="more-1073"></span><br />
For over a year now I have been using the music app <a title="Rdio" href="http://rdio.com/" target="_blank">Rdio</a>. I’m sure some of you are familiar with the service or others like it. <a title="Spotify" href="http://spotify.com/" target="_blank">Spotify</a> is another popular example. Apps and services of these types are taking the phrase <a title="Word of Mouth" href="http://en.wikipedia.org/wiki/Word_of_mouth" target="_blank">word of mouth</a> and putting it at the fingertips of users enabling the rapid sharing of music. Like most things on the internet, its so quick to share and sharing creates engagement, which has had a very positive effect in the Refactr workplace.</p>
<p><strong>Why we listen</strong><br />
Music is entertainment for our ears. It’s there for us no matter what mood we are in. It covers up the background noise that distracts us from focusing. People have playlists created with specific selections of music that they’ll listen to when they need to increase their productivity.</p>
<p><strong>Music at Refactr</strong><br />
The music listening habits of the Refactr employees varies from day to day. There will be days when everyone is heads down listening to their own music. A good chunk of the employees here use Rdio, there are a few Spotify users and any others are either using <a title="Pandora" href="http://www.pandora.com/" target="_blank">Pandora</a> or <a title="iTunes" href="http://www.apple.com/itunes/" target="_blank">iTunes</a>.</p>
<p>When we aren’t heads down in work or when someone decides to take the dj reigns we have a office <a title="Sonos" href="http://www.sonos.com/" target="_blank">Sonos</a> player. The way we use the Sonos varies. Often someone just puts an album into the queue and it will get played through its entirety. There are other days where we collaborate with a theme in mind and a good majority of us will contribute to the music queue that way. This can be fun! Themes have varied from 90’s rock to 80’s rap and during a hack day not long ago we even collaborated on a remix playlist (listen below).</p>
<p><iframe src="http://rd.io/i/QVpa4zNYT9A" frameborder="0" width="640" height="370"></iframe></p>
<p>When <a title="Turntable" href="http://turntable.fm/" target="_blank">turntable.fm</a> hit the scene we all got really into it for a few weeks. Then we soon realized how distracting it can be. Turntable was great though, it got us all engaging with one another through this collaborative dj application, we’ve since gone back to taking turns with the Sonos.</p>
<p><strong>Workplace benefits</strong><br />
Besides the obvious benefits of listening to music at work, there are also aspects of music listening that have brought the Refactr team closer.</p>
<p>Sharing music is one way we get more involved with one another. When we share, it creates engagement through conversations and conversations amongst employees is always a positive.</p>
<p>As a result of similar music tastes amongst employees in the office there&#8217;s been times where small groups of us have gone to concerts. Most recently you would have found several of us together at the <a title="Of Monsers and Men" href="http://ofmonstersandmen.is/" target="_blank">Of Monsters and Men</a> show at <a title="The Fine Line Music Cafe" href="http://finelinemusic.com/" target="_blank">The Fine Line Music Cafe</a>. We all know how important team building can be, but it doesn’t have to happen at the office. Spending time with coworkers outside of work can be quite beneficial! There’s a lot to learn about the people you spend day after day with, why not hang out with them outside of work? At Refactr we are big advocates of this!</p>
<p>We have all made the choice to be a Spotify, Rdio, Pandora, iTunes or other music user. That choice came with a lot of thought and reason. As tech enthusiasts we tend to judge an application or service more than the general public. There have been many debates and conversations over these various applications. We’ve talked about and compared the overall user experience and design of apps. Often we discuss certain features that an app should have or shouldn’t have. All these conversations surrounding our decisions for using a music service, or any app, are great and usually lead to more lengthy conversations that relate to <a href="http://refactr.com/work/" target="_blank">the work we do</a> here at Refactr.</p>
<p>Overall music at work just brings people together in a not so work specific way. If we are always engaging with our coworkers we will always be growing and becoming a better team.</p>
<p><strong>Follow some of us and find out what we are listening to!</strong><br />
<a href="http://www.rdio.com/people/Refactr-Office/" target="_blank">Refactr</a>, <a href="http://www.rdio.com/people/alttext/" target="_blank">Ben</a>, <a href="http://www.rdio.com/people/joneilloine/" target="_blank">Jesse</a>, <a href="http://www.rdio.com/people/halfwinter/" target="_blank">Hiromi</a>, <a href="http://www.rdio.com/people/daneray/" target="_blank">Dane</a>, <a href="http://www.rdio.com/people/kskogs/" target="_blank">Kyle</a>, <a href="http://www.rdio.com/people/Mike-Dave/" target="_blank">Steve</a></p>
<p><strong>Leave a comment and let Refactr know how music fits into your work day!</strong></p>
]]></content:encoded>
			<wfw:commentRss>http://refactr.com/blog/2012/05/music-in-the-office/feed/</wfw:commentRss>
		<slash:comments>5</slash:comments>
		</item>
		<item>
		<title>Internet Explorer Compatibility Testing</title>
		<link>http://refactr.com/blog/2012/05/internet-explorer-compatibility-testing/</link>
		<comments>http://refactr.com/blog/2012/05/internet-explorer-compatibility-testing/#comments</comments>
		<pubDate>Mon, 07 May 2012 19:00:54 +0000</pubDate>
		<dc:creator>Luke Bredeson</dc:creator>
				<category><![CDATA[Agile Processes]]></category>
		<category><![CDATA[browser testing]]></category>
		<category><![CDATA[internet explorer compatibility]]></category>
		<category><![CDATA[VirtualBox]]></category>

		<guid isPermaLink="false">http://refactr.com/blog/?p=1138</guid>
		<description><![CDATA[Microsoft seems to catch a lot of flack these days for the overhead required to maintain compatibility with different versions of Internet Explorer.  To help mitigate this, they&#8217;ve made some browser testing virtual machines freely available here, for IE 6, &#8230; <a href="http://refactr.com/blog/2012/05/internet-explorer-compatibility-testing/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<p>Microsoft seems to catch a lot of flack these days for the overhead required to maintain compatibility with different versions of Internet Explorer.  To help mitigate this, they&#8217;ve made some browser testing virtual machines freely available <a href="http://www.microsoft.com/en-us/download/details.aspx?id=11575" target="_blank">here</a>, for IE 6, 7, 8, and 9.</p>
<p>You&#8217;re free to download and run these manually yourself and install with Virtual PC, if you&#8217;re on a Windows machine. If you&#8217;re running Linux or OSX, however, you might want to instead try the following:</p>
<ol>
<li><a href="https://www.virtualbox.org/wiki/Downloads" target="_blank">Install VirtualBox</a></li>
<li>Follow <a href="https://github.com/xdissent/ievms" target="_blank">these instructions</a> to automate the download and installation of the virtual machines.</li>
</ol>
<p>&#8230;which gives you this (I wasn&#8217;t able to get IE6 working&#8230;maybe that&#8217;s for the best):</p>
<div><a href="http://refactr.com/blog/2012/05/internet-explorer-compatibility-testing/virtualbox-2/" rel="attachment wp-att-1151"><img class="alignnone size-full wp-image-1151" src="http://refactr.com/blog/wp-content/uploads/2012/05/virtualbox1.png" alt="" width="884" height="712" /></a></div>
<p>Regardless of how you choose to do this, the download time is pretty painful (probably several hours).  The payoff is pretty nice, however:  fast Internet Explorer testing at your fingertips.</p>
]]></content:encoded>
			<wfw:commentRss>http://refactr.com/blog/2012/05/internet-explorer-compatibility-testing/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>Using MongoMapper to run MapReduce jobs</title>
		<link>http://refactr.com/blog/2012/05/using-mongomapper-to-run-mapreduce-jobs/</link>
		<comments>http://refactr.com/blog/2012/05/using-mongomapper-to-run-mapreduce-jobs/#comments</comments>
		<pubDate>Thu, 03 May 2012 20:26:06 +0000</pubDate>
		<dc:creator>Luke Bredeson</dc:creator>
				<category><![CDATA[Software Development]]></category>
		<category><![CDATA[MapReduce]]></category>
		<category><![CDATA[MongoDB]]></category>
		<category><![CDATA[NoSQL]]></category>
		<category><![CDATA[Rails]]></category>

		<guid isPermaLink="false">http://refactr.com/blog/?p=1056</guid>
		<description><![CDATA[Background When using relational databases, we sometimes take for granted certain operations that appear to be missing in &#8220;NoSQL&#8221; databases like MongoDB, such as the ability to group data and run aggregate functions in SQL, like sum, max, etc. These &#8230; <a href="http://refactr.com/blog/2012/05/using-mongomapper-to-run-mapreduce-jobs/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<h2>Background</h2>
<p>When using relational databases, we sometimes take for granted certain operations that appear to be missing in &#8220;NoSQL&#8221; databases like MongoDB, such as the ability to group data and run aggregate functions in SQL, like sum, max, etc. These things can still be accomplished in MongoDB with MapReduce, of course, it just requires a different approach than in a relational database due to design choices that favor huge, sharded datasets.</p>
<p>The concept of MapReduce itself was nothing new at the time to functional language aficionados, but Google took the algorithm and applied it in a distributed computing context in their <a href="http://research.google.com/archive/mapreduce.html" target="_blank">popular 2004 paper on the subject</a>. MongoDB&#8217;s approach is <a href="http://www.mongodb.org/display/DOCS/MapReduce" target="_blank">fairly similar</a>.</p>
<h2>A Simple Blog App</h2>
<p>Let&#8217;s walk through a simple blog example using the <a href="http://mongomapper.com" target="_blank">MongoMapper</a> gem. The source code of this example is available <a href="https://github.com/Refactr/open-source/tree/master/Rails/blog" target="_blank">here</a>.</p>
<p>We&#8217;ll start with 2 simple models, shown below: User and Post</p>
<pre>class User
  include MongoMapper::Document
  safe

  many :posts
  key :username, String
  timestamps!
end</pre>
<pre>class Post
  include MongoMapper::Document
  safe

  belongs_to :user

  key :content, String
  key :tags, Array
  timestamps!
end</pre>
<p>Now, let&#8217;s generate some sample data:</p>
<pre>pete = User.create username: 'pete'
sally = User.create username: 'tony'
joe = User.create username: 'sally'

Post.create user: pete, content: "Blog post content", tags: ["t1", "t2", "t3"]
Post.create user: pete, content: "Blog post content", tags: ["t2", "t3", "t4"]
Post.create user: pete, content: "Blog post content", tags: ["t2", "t3", "t4", "t5"]
Post.create user: sally, content: "Blog post content", tags: ["t2", "t3", "t4", "t5", "t6"]
Post.create user: joe, content: "Blog post content", tags: ["t2", "t3"]</pre>
<h2>Enter MapReduce</h2>
<p>Based on this simple structure and sample data, we might decide that we want to know which users have been using the most tags. With MongoMapper, we could do the following:</p>
<pre>class UserTags
  include MongoMapper::Document

  key :value, Integer

  def self.map
    &lt;&lt;-MAP
      function() {
        var post = this;
        this.tags.forEach(function(tag) {
          emit(post.user_id, 1);
        });
      }
    MAP
  end

  def self.reduce
    &lt;&lt;-REDUCE
      function(key, values) {
        var sum = 0;
        values.forEach(function(value) {
          sum += value;
        });
        return sum;
      }
    REDUCE
  end

  def self.build
    Post.collection.map_reduce(map, reduce, { out: "user_tags" })
  end
end

# Run the MapReduce job, store the results
UserTags.build

# Get the user who used the most tags on their posts
UserTags.sort(:value.desc).first</pre>
<h2>Some explanation&#8230;</h2>
<p>In the MapReduce operation, we first emit a user_id key with a value of 1 for every tag that exists in the system. Since the key in the emit is used for grouping, when we get to the reduce step, it will receive an array of the emitted values for each key to combine in some way (I chose to sum them). We choose an output collection (out: &#8220;user_tags&#8221;), into which the results are dumped for later retrieval (it could potentially be a time consuming operation if the dataset is very large). Then a simple sort by this sum value will give you the highest user/tag-count combo in the database.</p>
<p>Note that even though MongoDB lacks the transactional semantics that are usually available to relational databases, this operation is nonetheless <strong>atomic</strong>. While the MapReduce operation is running, it is being output to a temporary collection which is only renamed to &#8220;user_tags&#8221; (which backs the UserTags model) once the MapReduce is complete, meaning that running this job shouldn&#8217;t cause the collection to become unavailable.</p>
<p>Additionally, if you decide to shard your data, the MapReduce operation can run concurrently on every shard.</p>
]]></content:encoded>
			<wfw:commentRss>http://refactr.com/blog/2012/05/using-mongomapper-to-run-mapreduce-jobs/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Create a Heat Map Using Google Docs</title>
		<link>http://refactr.com/blog/2012/04/create-a-heat-map-using-google-docs/</link>
		<comments>http://refactr.com/blog/2012/04/create-a-heat-map-using-google-docs/#comments</comments>
		<pubDate>Wed, 25 Apr 2012 14:54:59 +0000</pubDate>
		<dc:creator>Matt Nohr</dc:creator>
				<category><![CDATA[Agile Processes]]></category>
		<category><![CDATA[Misc]]></category>
		<category><![CDATA[google docs]]></category>
		<category><![CDATA[GPS]]></category>
		<category><![CDATA[heat map]]></category>
		<category><![CDATA[running]]></category>
		<category><![CDATA[tutorial]]></category>

		<guid isPermaLink="false">http://refactr.com/blog/?p=1037</guid>
		<description><![CDATA[Using Google Docs new Fusion Tables makes it really easy to create heat maps with just a list of longitudes and latitudes. In this example, I will use the GPS data from my watch to create a heat map that &#8230; <a href="http://refactr.com/blog/2012/04/create-a-heat-map-using-google-docs/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<p>Using Google Docs new Fusion Tables makes it really easy to create heat maps with just a list of longitudes and latitudes.</p>
<p>In this example, I will use the GPS data from my watch to create a heat map that shows where the common areas are that I run:</p>
<p><img class="alignnone size-full wp-image-1047" src="http://refactr.com/blog/wp-content/uploads/2012/04/heat_map.png" alt="Heat Map" width="166" height="66" /><br />
<span id="more-1037"></span><br />
<strong>Get Data</strong></p>
<p>To get the data, I exported all of the history from my GPS-enabled watch software. The only trick here was converting <a href="http://en.wikipedia.org/wiki/Gpx">GPX data</a> to CSV. If you want to do this, you can use the Groovy script at the bottom of this post, or there are a number of sites online that will convert many different GPS formats for you (<a href="http://www.gps-data-team.com/convert.php">this one</a> for example)</p>
<p>There are also a number of apps for iPhone and Android that will let you export your GPS data.</p>
<p><strong>Create The Heat Map</strong></p>
<p>Once you have your data in CSV, you are ready to follow these simple steps to create your heat map.</p>
<ol>
<li>In Google Docs, choose to Create &gt; Table. Note: this is currently in Beta</li>
<li>Upload your data on the Import step.</li>
<li>You now need to tell Google to use the columns Latitude and Longitude as “location” columns.
<ol>
<li>Edit &gt; Modify Columns</li>
<li>Select the first column (either Latitude or Longitude)</li>
<li>Change the type to “Location”</li>
<li>Check the “Two column Location” box and make sure the Latitude and Longitude are assigned correctly<br />
<a href="http://refactr.com/blog/2012/04/create-a-heat-map-using-google-docs/heat_map_configure/" rel="attachment wp-att-1052"><img class="alignnone size-full wp-image-1052" src="http://refactr.com/blog/wp-content/uploads/2012/04/heat_map_configure.png" alt="Heat Map Configure" width="634" height="410" /></a></li>
</ol>
</li>
<li>Now check out the map:
<ol>
<li>Visualize &gt; Map</li>
<li>Check the “Display as heat map” checkbox near the top</li>
</ol>
</li>
</ol>
<p><strong>Groovy Script</strong></p>
<p>Here is a simple Groovy script to convert GPX to a CSV list of longitude and latitude:</p>
<p><code>//get all the GPS points<br />
def gpx = new File('running.gpx')<br />
def gpxData = new XmlSlurper().parseText(gpx.text)<br />
def allPoints = gpxData.depthFirst().findAll{it.name() == 'trkpt'}</code></p>
<p><code>//create the new CSV<br />
def csv = new File('running.csv')<br />
allPoints.each{csv &lt;&lt; "${it.@lat.text()},${it.@lon.text()}\n"}</code></p>
<p>Note: this script converted over 5000 data points in just over 1 second.</p>
]]></content:encoded>
			<wfw:commentRss>http://refactr.com/blog/2012/04/create-a-heat-map-using-google-docs/feed/</wfw:commentRss>
		<slash:comments>4</slash:comments>
		</item>
		<item>
		<title>Welcome Adam!</title>
		<link>http://refactr.com/blog/2012/04/welcome-adam/</link>
		<comments>http://refactr.com/blog/2012/04/welcome-adam/#comments</comments>
		<pubDate>Tue, 24 Apr 2012 16:38:17 +0000</pubDate>
		<dc:creator>Matt Bjornson</dc:creator>
				<category><![CDATA[Agile Processes]]></category>
		<category><![CDATA[Business]]></category>
		<category><![CDATA[company growth]]></category>

		<guid isPermaLink="false">http://refactr.com/blog/?p=996</guid>
		<description><![CDATA[We&#8217;re continuing to grow at Refactr, and we&#8217;re excited to welcome Adam Lanners to the team! He&#8217;s joining us from PaR Systems where he was doing web development and before that he was with Medtronic doing mobile development. Adam will &#8230; <a href="http://refactr.com/blog/2012/04/welcome-adam/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<p>We&#8217;re continuing to grow at Refactr, and we&#8217;re excited to welcome <a href="http://refactr.com/team/adam">Adam Lanners</a> to the team! He&#8217;s joining us from PaR Systems where he was doing web development and before that he was with Medtronic doing mobile development.</p>
<p style="margin: -30px 0 0 0">
<a href="http://refactr.com/team/adam/"><img class="aligncenter size-full wp-image-1004" title="adam" src="http://refactr.com/blog/wp-content/uploads/2012/04/adam.jpg" alt="" width="575" height="320" /></a>
</p>
<p>Adam will be jumping into a Grails project leveraging several social APIs. One of his recent projects he&#8217;s proud of involved implementing a document management system, centralizing and migrating over 150,000 files that were distributed across many locations  that can be replicated globally.  One of biggest challenges was building a tool to migrate the large amounts of metadata associated with each file without losing any information. The project was a huge success!</p>
<p>Welcome Adam!</p>
]]></content:encoded>
			<wfw:commentRss>http://refactr.com/blog/2012/04/welcome-adam/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>JRuby Conf Sponsorship</title>
		<link>http://refactr.com/blog/2012/04/jruby-conf-sponsorship/</link>
		<comments>http://refactr.com/blog/2012/04/jruby-conf-sponsorship/#comments</comments>
		<pubDate>Thu, 19 Apr 2012 15:23:12 +0000</pubDate>
		<dc:creator>Matt Bjornson</dc:creator>
				<category><![CDATA[Agile Processes]]></category>
		<category><![CDATA[community]]></category>
		<category><![CDATA[Software Development]]></category>
		<category><![CDATA[JRuby]]></category>
		<category><![CDATA[JRubyConf]]></category>
		<category><![CDATA[JVM]]></category>
		<category><![CDATA[Rails]]></category>
		<category><![CDATA[Ruby]]></category>

		<guid isPermaLink="false">http://refactr.com/blog/?p=987</guid>
		<description><![CDATA[We&#8217;re very excited to sponsor JRubyConf this year.  We are big believers in fostering and growing the technology community and it&#8217;s great to have a conference like this held in Minneapolis. The other reason we are excited about sponsoring is &#8230; <a href="http://refactr.com/blog/2012/04/jruby-conf-sponsorship/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<p>We&#8217;re very excited to sponsor<a title="JRubyConf" href="http://jrubyconf.com#sponsors"> JRubyConf</a> this year.  We are big believers in fostering and growing the technology community and it&#8217;s great to have a conference like this held in Minneapolis. The other reason we are excited about sponsoring is that the JVM is the platform. The amount of R&amp;D that has been invested into the JVM is staggering, and fostering language communities like this will only strengthen both Ruby and the JVM.</p>
<p>There are multiple language alternatives to Java on the JVM, like Groovy, Clojure, Scala, Jython, etc. But with the popularity of Ruby on Rails and JRuby, there&#8217;s another bloat free option to Java with all the scalability, tuning, and tools that come with the JVM. On top of that sweetness, you have one deployment option: the JVM.</p>
<p>With all the great work that the JRuby team has done to make Ruby work on the JVM, it&#8217;s a no brainer to deploy Rails-based products on the JVM.  We hope to catch up with the local Ruby developers at JRubyConf.</p>
]]></content:encoded>
			<wfw:commentRss>http://refactr.com/blog/2012/04/jruby-conf-sponsorship/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Switching to Eclipse/STS For Grails Development</title>
		<link>http://refactr.com/blog/2012/04/switch-to-sts/</link>
		<comments>http://refactr.com/blog/2012/04/switch-to-sts/#comments</comments>
		<pubDate>Wed, 11 Apr 2012 16:22:05 +0000</pubDate>
		<dc:creator>Matt Nohr</dc:creator>
				<category><![CDATA[Software Development]]></category>
		<category><![CDATA[eclipse]]></category>
		<category><![CDATA[grails]]></category>
		<category><![CDATA[sts]]></category>

		<guid isPermaLink="false">http://refactr.com/blog/?p=949</guid>
		<description><![CDATA[My preferred tool for doing Grails development is the SpringSource Tool Suite (STS), which is built on the free Eclipse IDE that you download with a number of plugins already installed. It is totally free and has a number of &#8230; <a href="http://refactr.com/blog/2012/04/switch-to-sts/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<p>My preferred tool for doing Grails development is the SpringSource Tool Suite (STS), which is built on the free Eclipse IDE that you download with a number of plugins already installed. It is totally free and has a number of nice features you do not get with a simple text editor.</p>
<p><strong>Why Switch?</strong></p>
<p>Why should you use STS? Since STS is built on Eclipse, you get a number of nice features built in. Here are just a couple of my favorites:</p>
<p>Outline View:<br />
<a href="http://refactr.com/blog/2012/04/switch-to-sts/sts10/" rel="attachment wp-att-960"><img class="alignnone size-full wp-image-960" src="http://refactr.com/blog/wp-content/uploads/2012/04/sts10.png" alt="STS outline view" width="256" height="299" /></a></p>
<p>Content-assist / Autocomplete:<br />
<a href="http://refactr.com/blog/2012/04/switch-to-sts/sts11/" rel="attachment wp-att-965"><img class="alignnone size-full wp-image-965" src="http://refactr.com/blog/wp-content/uploads/2012/04/sts11.png" alt="STS Content Assist" width="396" height="243" /></a></p>
<p>Automatic refactoring tools (like renaming all instances of a variable):<br />
<a href="http://refactr.com/blog/2012/04/switch-to-sts/sts12/" rel="attachment wp-att-962"><img class="alignnone size-full wp-image-962" src="http://refactr.com/blog/wp-content/uploads/2012/04/sts12.png" alt="STS refactor rename" width="289" height="79" /></a></p>
<p>And many more:</p>
<ul>
<li>Support for groovy, gsps, java, css, javascript, and many more</li>
<li>Auto formatting of files including fixing indents and spacing</li>
<li>Highly configurable workspace (tabbed editing, split-pane editing, task lists, etc)</li>
<li>Huge Plugin community (source control, other languages, etc)</li>
</ul>
<p><span id="more-949"></span><br />
<strong>Installation</strong></p>
<p>Assuming you are already doing grails development, installation is very straight-forward. Follow the instructions on the grails.org site here: <a title="Grails.org STS Instructions" href="http://grails.org/STS+Integration">http://grails.org/STS+Integration</a></p>
<p>If you are starting from scratch, you will have to install Java and probably specific versions of Grails before you can install STS.</p>
<p>Out of the box, STS is geared towards Spring development. Since Grails runs on top of Spring, after you install STS you have to install a couple plugins for Groovy and Grails. It is all detailed in the grails.org post. Assuming you already have Grails installed on your computer, you do not need to install the Grails language extension. You will just need the Grails and Groovy &#8220;tooling extensions.&#8221;</p>
<p><strong>Initial Setup</strong></p>
<p>Once STS is installed and open, here are a couple of things to get started.</p>
<p>First, setup your Grails installations if you did not do that during the installation. Go to the Preferences (MacOS: SpringSource Tool Suite &gt; Preferences, Windows/Linux: Window &gt; Preferences) and then navigate to Groovy &gt; Grails. Just browse to your grails directory and STS will fill in all the details for you. You can do this for as many versions of Grails as you want. The default will be used for new projects, but you can always specify which version to use for a specific project.</p>
<p>Next, switch to the Grails perspective and you are ready to go.<br />
<a href="http://refactr.com/blog/2012/04/switch-to-sts/sts01/" rel="attachment wp-att-951"><img class="alignnone size-full wp-image-951" src="http://refactr.com/blog/wp-content/uploads/2012/04/sts01.png" alt="STS Grails Perspective" width="424" height="273" /></a></p>
<p><strong>Importing Existing Project</strong></p>
<p>To pull your existing Grails project into STS, just follow these steps</p>
<ol>
<li>File &gt; New&#8230; &gt; Grails Project</li>
<li>Under Contents, change it to &#8220;Use External Location&#8221; and Browse to your existing Grails project</li>
</ol>
<p><a href="http://refactr.com/blog/2012/04/switch-to-sts/sts02/" rel="attachment wp-att-952"><img class="alignnone size-full wp-image-952" src="http://refactr.com/blog/wp-content/uploads/2012/04/sts02.png" alt="STS Import Project" width="514" height="293" /></a><br />
There are a couple things that may now happen, depending on which version of Groovy and Grails you are using.</p>
<p>First, you could get a &#8220;Incompatible Groovy Compiler Version&#8221; warning<br />
<a href="http://refactr.com/blog/2012/04/switch-to-sts/sts03/" rel="attachment wp-att-953"><img class="alignnone size-full wp-image-953" src="http://refactr.com/blog/wp-content/uploads/2012/04/sts03.png" alt="STS Import Error 1" width="531" height="184" /></a><br />
In my case I was importing a Grails 1.3.7 project and my Groovy version was 1.8.6, which is more recent than Grails 1.3.7 uses. Most of the time I just ignore this message because I do not have any problems with using so-called &#8220;incompatible&#8221; versions. However, you can easily switch to a different version of Groovy if needed. Go to the Preferences &gt; Groovy &gt; Compiler. In here is a button to switch versions of Groovy and a link with more details.</p>
<p>Second, you could get a &#8220;Grails version mismatch detected&#8221; warning<br />
<a href="http://refactr.com/blog/2012/04/switch-to-sts/sts04/" rel="attachment wp-att-954"><img class="alignnone size-full wp-image-954" src="http://refactr.com/blog/wp-content/uploads/2012/04/sts04.png" alt="STS Import Error 2" width="549" height="215" /></a><br />
In my case, the default Grails in STS was 2.0.3 and my project was 1.3.7. If you say &#8220;Yes&#8221; it will run &#8220;grails upgrade&#8221; on your project. If you say &#8220;No&#8221; it will configure you project to use the correct version, 1.3.7 in my case. You can see what version of Grails is configured for a project by right-clicking (control-click on a Mac) on the project name and choosing Properties then Grails.</p>
<p>Third, you could get a &#8220;Grails version x.x.x not installed&#8221; warning<br />
<a href="http://refactr.com/blog/2012/04/switch-to-sts/sts05/" rel="attachment wp-att-955"><img class="alignnone size-full wp-image-955" src="http://refactr.com/blog/wp-content/uploads/2012/04/sts05.png" alt="STS Import Error 3" width="531" height="206" /></a><br />
As you can guess, this means the version of Grails specified by your project is not installed in Grails. You can either upgrade your project through STS (clicking Yes) or go back and configure STS to use that version of Grails.</p>
<p><strong>Features of STS with Grails</strong></p>
<p>Project Explorer:<br />
Since Grails uses &#8220;convention over configuration&#8221;, STS can easily identify your domain, controller, view, service, etc classes and will group them accordingly:<br />
<a href="http://refactr.com/blog/2012/04/switch-to-sts/sts06/" rel="attachment wp-att-956"><img class="alignnone size-full wp-image-956" src="http://refactr.com/blog/wp-content/uploads/2012/04/sts06.png" alt="STS Project Explorer" width="354" height="420" /></a></p>
<p>Running Grails Commands:<br />
Built into STS is the ability to run any Grails command, just like you would from the command line. Some are tightly integrated and others not so much. For example, you can do File &gt; New &gt; Domain Class (or Controller, or Service, etc) which will run &#8220;grails create-domain-class MyDomain&#8221; automatically.</p>
<p>You can also run any other Grails command with the &#8220;Grails Command&#8221; button in the toolbar:<br />
<a href="http://refactr.com/blog/2012/04/switch-to-sts/sts07/" rel="attachment wp-att-957"><img class="alignnone size-full wp-image-957" src="http://refactr.com/blog/wp-content/uploads/2012/04/sts07.png" alt="STS Grails Run Button" width="340" height="118" /></a><br />
This will bring up a prompt and you can enter any command:<br />
<a href="http://refactr.com/blog/2012/04/switch-to-sts/sts08/" rel="attachment wp-att-958"><img class="alignnone size-full wp-image-958" src="http://refactr.com/blog/wp-content/uploads/2012/04/sts08.png" alt="STS Grails Run Dialog" width="408" height="98" /></a><br />
If you enter run-app like I did, it will bring up a server within STS and you can click on the URL in the console view. That said, I typically still run the application from the command line out of habit.<br />
<a href="http://refactr.com/blog/2012/04/switch-to-sts/sts09/" rel="attachment wp-att-959"><img class="alignnone size-full wp-image-959" src="http://refactr.com/blog/wp-content/uploads/2012/04/sts09.png" alt="STS Run App" width="574" height="143" /></a></p>
<p>You can still run commands from the command line. Just remember to refresh your project in STS if you are creating any new files.</p>
<p><strong>Note on Source Control</strong></p>
<p>Using STS will create a new target-eclipse directory in your project and may put some items in the .settings directory. You will probably want to exclude these from your source control (using .gitignore or similiar)</p>
]]></content:encoded>
			<wfw:commentRss>http://refactr.com/blog/2012/04/switch-to-sts/feed/</wfw:commentRss>
		<slash:comments>3</slash:comments>
		</item>
	</channel>
</rss>

