<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet type="text/xsl" media="screen" href="/~d/styles/rss2full.xsl"?><?xml-stylesheet type="text/css" media="screen" href="http://feeds.feedburner.com/~d/styles/itemcontent.css"?><rss 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/" xmlns:feedburner="http://rssnamespace.org/feedburner/ext/1.0" version="2.0">

<channel>
	<title>Snail in a Turtleneck » MongoDB</title>
	
	<link>http://www.snailinaturtleneck.com/blog</link>
	<description>Kristina Chodorow's Blog</description>
	<lastBuildDate>Mon, 21 May 2012 21:19:47 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.3.2</generator>
		<atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="self" type="application/rss+xml" href="http://feeds.feedburner.com/siat-mongodb" /><feedburner:info uri="siat-mongodb" /><atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="hub" href="http://pubsubhubbub.appspot.com/" /><item>
		<title>Replica Set Internals Bootcamp Part III: Reconfiguring</title>
		<link>http://feedproxy.google.com/~r/siat-mongodb/~3/sHrRoqls7Nc/</link>
		<comments>http://www.snailinaturtleneck.com/blog/2012/05/21/replica-set-internals-bootcamp-part-iii-reconfiguring/#comments</comments>
		<pubDate>Mon, 21 May 2012 21:19:47 +0000</pubDate>
		<dc:creator>Kristina Chodorow</dc:creator>
				<category><![CDATA[MongoDB]]></category>
		<category><![CDATA[bootcamp]]></category>
		<category><![CDATA[reconfiguration]]></category>
		<category><![CDATA[replica sets]]></category>

		<guid isPermaLink="false">http://www.snailinaturtleneck.com/blog/?p=2006</guid>
		<description><![CDATA[I&#8217;ve been doing replica set &#8220;bootcamps&#8221; for new hires. It&#8217;s mainly focused on applying this to debug replica set issues and being able to talk fluently about what&#8217;s happening, but it occurred to me that you (blog readers) might be interested in it, too. There are 8 subjects I cover in my bootcamp: Elections Creating&#8230;]]></description>
			<content:encoded><![CDATA[<!-- Start Shareaholic LikeButtonSetTop --><!-- End Shareaholic LikeButtonSetTop --><p>I&#8217;ve been doing replica set &#8220;bootcamps&#8221; for new hires. It&#8217;s mainly focused on applying this to debug replica set issues and being able to talk fluently about what&#8217;s happening, but it occurred to me that you (blog readers) might be interested in it, too.  </p>
<p><img src="http://www.snailinaturtleneck.com/blog/wp-content/uploads/2012/01/dog-boot-camp-2.jpg" alt="" title="dog-boot-camp" width="265" height="286" class="alignright size-full wp-image-1760" /></p>
<p>There are 8 subjects I cover in my bootcamp: </p>
<ol>
<li><a href="http://www.snailinaturtleneck.com/blog/?p=1752">Elections</a>
<li><a href="http://www.snailinaturtleneck.com/blog/?p=1767">Creating a set</a>
<li><a href="http://www.snailinaturtleneck.com/blog/?p=2006">Reconfiguring</a>
<li><a href="http://www.snailinaturtleneck.com/blog/?p=1863">Syncing</a>
<li>Initial Sync
<li>Rollback
<li>Authentication
<li>Debugging
</ol>
<p><em>Prerequisites: I&#8217;m assuming you know what replica sets are and you&#8217;ve configured a set, written data to it, read from a secondary, etc.  You understand the terms primary and secondary.</em></p>
<h4>Reconfiguring Prerequisites</h4>
<p>One of the goals is to not let you reconfigure yourself into a corner (e.g., end up with all arbiters), so reconfig tries to make sure that a primary <em>could</em> be elected with the new config. Basically, we go through each node and tally up how many votes there will be and if a majority of those is up (the reconfig logic sends out heartbeats).</p>
<p>Also, the member you send the reconfig to has to <em>be able to become primary</em> in the new setup.  It doesn&#8217;t have to become primary, but its priority has to be greater than 0.  So, you can&#8217;t have all of the members have a priority of 0.</p>
<p>The reconfig also checks the version number, set name, and that nothing is going to an illegal state (e.g., arbiter-to-non-arbiter, upping the priority on a slave delayed node, and so on).</p>
<p>One thing to note is that you can change hostnames in a reconfig.  If you&#8217;re using <em>localhost</em> for a single-node set and want to change it to an externally resolvable hostname so you can add some other members, you can just change the member&#8217;s hostname from <em>localhost</em> to <em>someHostname</em> and reconfig (so long as <em>someHostname</em> resolves, of course).</p>
<h4>Additive Reconfiguration vs. Full Reconfigs</h4>
<p>Once the reconfiguration has been checked for correctness, MongoDB checks to see if this is a simple reconfig or a full reconfig.  A simple reconfig adds a new node. Anything else is a full reconfig.</p>
<p>A simple reconfig starts a new heartbeat thread for the new member and it&#8217;s done.</p>
<p>A full reconfig clears all state.  This means that the current primary closes all connections.  All the current heartbeat threads are stopped and a new heartbeat thread for each member is started.  The old config is replaced by the new config.  Then the member formerly known as primary becomes primary again.</p>
<p>We definitely take a scorched-earth approach to reconfiguring.  If you are, say, changing the priority of a node from 0 to 1, it would make more sense to change that field than to tear down the whole old config.  However, we didn&#8217;t want to miss an edge case, so we went with better safe than sorry.  Reconfig is considered a &#8220;slow&#8221; operation anyway, so we&#8217;ll generally make the tradeoff of slower and safer.</p>
<h4>Propegation of Reconfiguration</h4>
<p>Even if you have a node that is behind on replication or slave delayed, reconfiguration will propegate almost immediately.  How?  New configs are communicated via heartbeat.</p>
<p>Suppose you have 2 nodes, <em>A</em> and <em>B</em>.  </p>
<p><img src="http://www.snailinaturtleneck.com/blog/wp-content/uploads/2012/05/set.png" alt="" title="set" width="459" height="166" class="aligncenter size-full wp-image-2010" /></p>
<p>You run a reconfig on <em>A</em>, changing the version number from 6 to 7.  </p>
<p><img src="http://www.snailinaturtleneck.com/blog/wp-content/uploads/2012/05/reconfig.png" alt="" title="reconfig" width="459" height="166" class="aligncenter size-full wp-image-2011" /></p>
<p><em>B</em> sends a heartbeat request to <em>A</em>, which includes a field stating that <em>B</em>&#8216;s version number is 6. </p>
<p><img src="http://www.snailinaturtleneck.com/blog/wp-content/uploads/2012/05/hb-request.png" alt="" title="hb request" width="459" height="166" class="aligncenter size-full wp-image-2012" /></p>
<p>When <em>A</em> gets that heartbeat request, it will see that <em>B</em>&#8216;s config version is less than it&#8217;s own, so it&#8217;ll send back its config (at version 7) as part of its heartbeat response.  </p>
<p><img src="http://www.snailinaturtleneck.com/blog/wp-content/uploads/2012/05/hb-response.png" alt="" title="hb response" width="459" height="166" class="aligncenter size-full wp-image-2013" /></p>
<p>When <em>B</em> sees that new config, it&#8217;ll load it (making the same checks for validity that <em>A</em> did originally) and follow the same procedure described above.</p>
<p><img src="http://www.snailinaturtleneck.com/blog/wp-content/uploads/2012/05/propegation.png" alt="" title="propegation" width="459" height="166" class="aligncenter size-full wp-image-2014" /></p>
<div id="attachment_2007" class="wp-caption alignright" style="width: 310px"><img src="http://www.snailinaturtleneck.com/blog/wp-content/uploads/2012/05/star-wars-the-force-unleashed-2-reviews-force-push-300x168.jpg" alt="" title="Force push" width="300" height="168" class="size-medium wp-image-2007" /><p class="wp-caption-text">Force reconfig to the face.</p></div>
<h4>Forcing Reconfig</h4>
<p>Despite the checks made by reconfig, users sometimes get into a situation where they don&#8217;t have a primary.  They&#8217;d permanently lose a couple servers or a data center and suddenly be stuck with a bunch of secondaries and no way to reconfig.  So, in 2.0, we added a <code>force:true</code> option to reconfig, which allowed it to be run on a secondary.  <em>That is all that force:true does</em>.  Sometimes people complain that <code>force:true</code> wouldn&#8217;t let them load an invalid configuration.  Indeed, it won&#8217;t.  <code>force:true</code> does not relax any of the other reconfig constraints.  You still have to pass in a valid config.  You can just pass it to a secondary.</p>
<h4>Why is my version number 6,203,493?</h4>
<p>When you force-reconfigure a set, it adds a random (big) number to the version, which can be unnerving.  Why does the version number jump by thousands?  Suppose that we have a network partition and force-reconfigure the set on both sides of the partition.  If we ended up with both sides having a config version of 8 and the set got reconnected, then everyone would assume they were in sync (everyone has a config version of 8, no problems here!) and you&#8217;d have half of your nodes with one config and half with another.  By adding a random number to the version on reconfig, it&#8217;s very probable that one &#8220;side&#8221; will have a higher version number than the other.  When the network is fixed, whichever side has a higher version number will &#8220;win&#8221; and your set will end up with a consistent config.</p>
<p>It might not end up choosing the config you want, but some config is better than the set puttering along happily with two primaries (or something stupid like that).  Basically, if shenanigans happen during a network partition, check your config after the network is healthy again.</p>
<h4>Removing Nodes and Sharding</h4>
<p>I&#8217;d just like to rant for a second: removing nodes sucks!  You&#8217;d think it&#8217;s would be so easy, right?  Just take the node out of the config and boom, done.  It turns out it&#8217;s a total nightmare.  Not only do you have to stop all of the replication stuff happening on the removed node, you have to stop everything the rest of the set is doing with that node (e.g., syncing from it).  </p>
<p>You also have to change the way the removed node reports itself so that mongos won&#8217;t try to update a set&#8217;s config from a node that&#8217;s been removed. And you can&#8217;t just shut it down because people want to be able to play around and do <code>rs.add("foo"); rs.remove("foo"); rs.add("foo")</code> so you have to be able to entirely shut down the replica set&#8217;s interaction with the removed node, but in any way that can be restarted on a dime.</p>
<p>Basically, there are a lot of edge cases around removing nodes, so if you want to be on the safe side, shut down a node before removing it from the set.  However, <a href="https://github.com/milkie">Eric Milkie</a> has done a lot of awesome work on removing nodes for 2.2, so it should be getting better.</p>

<div id='reaction_buttons_post2006' class='reaction_buttons'>
<div class="reaction_buttons_tagline">Please let me know what thought of this post, anonymously here or in the comments below:</div><a class='reaction_button reaction_button_Funny_count' href="javascript:reaction_buttons_increment_button_ajax('2006', 'Funny');">Funny&nbsp;<span class='count'>(<span class='count_number'>0</span>)</span></a> <a class='reaction_button reaction_button_Useful_count' href="javascript:reaction_buttons_increment_button_ajax('2006', 'Useful');">Useful&nbsp;<span class='count'>(<span class='count_number'>0</span>)</span></a> <a class='reaction_button reaction_button_Too___short_count' href="javascript:reaction_buttons_increment_button_ajax('2006', 'Too short');">Too short&nbsp;<span class='count'>(<span class='count_number'>0</span>)</span></a> <a class='reaction_button reaction_button_Too___long_count' href="javascript:reaction_buttons_increment_button_ajax('2006', 'Too long');">Too long&nbsp;<span class='count'>(<span class='count_number'>0</span>)</span></a> </div>
<div class="shr-publisher-2006"></div><!-- Start Shareaholic LikeButtonSetBottom --><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><div class='shareaholic-like-buttonset' style='float:none;height:30px;'><a class='shareaholic-googleplusone' data-shr_size='medium' data-shr_count='true' data-shr_href='http%3A%2F%2Fwww.snailinaturtleneck.com%2Fblog%2F2012%2F05%2F21%2Freplica-set-internals-bootcamp-part-iii-reconfiguring%2F' data-shr_title='Replica+Set+Internals+Bootcamp+Part+III%3A+Reconfiguring'></a></div><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><!-- End Shareaholic LikeButtonSetBottom --><img src="http://feeds.feedburner.com/~r/siat-mongodb/~4/sHrRoqls7Nc" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.snailinaturtleneck.com/blog/2012/05/21/replica-set-internals-bootcamp-part-iii-reconfiguring/feed/</wfw:commentRss>
		<slash:comments>3</slash:comments>
		<feedburner:origLink>http://www.snailinaturtleneck.com/blog/2012/05/21/replica-set-internals-bootcamp-part-iii-reconfiguring/</feedburner:origLink></item>
		<item>
		<title>––thursday #5: diagnosing high readahead</title>
		<link>http://feedproxy.google.com/~r/siat-mongodb/~3/k412e8EUBQo/</link>
		<comments>http://www.snailinaturtleneck.com/blog/2012/05/10/thursday-5-diagnosing-high-readahead/#comments</comments>
		<pubDate>Thu, 10 May 2012 21:28:22 +0000</pubDate>
		<dc:creator>Kristina Chodorow</dc:creator>
				<category><![CDATA[Linux]]></category>
		<category><![CDATA[MongoDB]]></category>
		<category><![CDATA[--thursday]]></category>

		<guid isPermaLink="false">http://www.snailinaturtleneck.com/blog/?p=1881</guid>
		<description><![CDATA[Having readahead set too high can slow your database to a crawl. This post discusses why that is and how you can diagnose it. The #1 sign that readahead is too high is that MongoDB isn&#8217;t using as much RAM as it should be. If you&#8217;re running Mongo Monitoring Service (MMS), take a look at&#8230;]]></description>
			<content:encoded><![CDATA[<!-- Start Shareaholic LikeButtonSetTop --><!-- End Shareaholic LikeButtonSetTop --><p>Having readahead set too high can slow your database to a crawl.  This post discusses why that is and how you can diagnose it.  </p>
<p>The #1 sign that readahead is too high is that MongoDB isn&#8217;t using as much RAM as it should be.  If you&#8217;re running <a href="http://mms.10gen.com">Mongo Monitoring Service (MMS)</a>, take a look at the &#8220;resident&#8221; size on the &#8220;memory&#8221; chart.  Resident memory can be thought of as &#8220;the amount of space MongoDB &#8216;owns&#8217; in RAM.&#8221;  Therefore, if MongoDB is the only thing running on a machine, we want resident size to be as high as possible.  On the chart below, resident is ~3GB:  </p>
<p><img src="http://www.snailinaturtleneck.com/blog/wp-content/uploads/2012/04/Screen-Shot-2012-04-25-at-4.48.35-PM-1024x440.png" alt="" title="MMS" width="1024" height="440" class="aligncenter size-large wp-image-1970" /></p>
<p>Is 3GB good or bad?  Well, it depends on the machine.  If the machine only has 3.5GB of RAM, I&#8217;d be pretty happy with 3GB resident.  However, if the machine has, say, 15GB of RAM, then we&#8217;d like at least 15GB of the data to be in there (the &#8220;mapped&#8221; field is (sort of) data size, so I&#8217;m assuming we have 60GB of data).</p>
<p>Assuming we&#8217;re accessing a lot of this data, we&#8217;d expect MongoDB&#8217;s resident set size to be 15GB, but it&#8217;s only 3GB.  If we try turning down readahead and the resident size jumps to 15GB and our app starts going faster.  But why is this?</p>
<p>Let&#8217;s take an example: suppose all of our docs are 512 bytes in size (readahead is set in 512-byte increments, called <em>sectors</em>, so 1 doc = 1 sector makes the math easier).  If we have 60GB of data then we have ~120 million documents (60GB of data/(512 bytes/doc)).  The 15GB of RAM on this machine should be able to hold ~30 million documents.  </p>
<p>Our application accesses documents randomly across our data set, so we&#8217;d expect MongoDB to eventually &#8220;own&#8221; (have resident) all 15GB of RAM, as 1) it&#8217;s the only thing running and 2) it&#8217;ll eventually fetch at least 15GB of the data.</p>
<p>Now, let&#8217;s set our readahead to 100 (100 512-byte sectors, aka 100 documents): <code>blockdev --set-ra 100</code>.  What happens when we run our application?</p>
<p>Picture our disk as looking like this, where each o is a document:</p>
<pre>
...
ooooooooooooooooooooooooo
ooooooooooooooooooooooooo
ooooooooooooooooooooooooo
ooooooooooooooooooooooooo
ooooooooooooooooooooooooo
ooooooooooooooooooooooooo
ooooooooooooooooooooooooo
ooooooooooooooooooooooooo
... // keep going for millions more o's
</pre>
<p>Let&#8217;s say our app requests a document.  We&#8217;ll mark it with &#8220;x&#8221; to show that the OS has pulled it into memory:</p>
<pre>
...
ooooooooooooooooooooooooo
ooooxoooooooooooooooooooo
ooooooooooooooooooooooooo
ooooooooooooooooooooooooo
ooooooooooooooooooooooooo
ooooooooooooooooooooooooo
ooooooooooooooooooooooooo
ooooooooooooooooooooooooo
...
</pre>
<p>See it on the third line there?  But that&#8217;s not the only doc that&#8217;s pulled into memory: readahead is set to 100 so the next 99 documents are pulled into memory, too:</p>
<pre>
...
ooooooooooooooooooooooooo
ooooxxxxxxxxxxxxxxxxxxxxx
xxxxxxxxxxxxxxxxxxxxxxxxx
xxxxxxxxxxxxxxxxxxxxxxxxx
xxxxxxxxxxxxxxxxxxxxxxxxx
xxxxooooooooooooooooooooo
ooooooooooooooooooooooooo
ooooooooooooooooooooooooo
...
</pre>
<div id="attachment_1983" class="wp-caption alignright" style="width: 297px"><img src="http://www.snailinaturtleneck.com/blog/wp-content/uploads/2012/05/shoppingcart.jpg" alt="" title="Hobo shopping cart" width="287" height="300" class="size-full wp-image-1983" /><p class="wp-caption-text">Is your OS returning this with every document?</p></div>
<p>Now we have 100 docs in memory, but remember that our application is accessing documents randomly: the likelihood of the next document we access is in that block of 100 docs is almost nil.  At this point, there&#8217;s 50KB of data in RAM (512 bytes * 100 docs = 51,200 bytes) and MongoDB&#8217;s resident size has only increase by 512 bytes (1 doc).</p>
<p>Our app will keep bouncing around the disk, reading docs from here and there and filing up memory with docs MongoDB never asked for until RAM is completely full of junk that&#8217;s never been used.  Then, it&#8217;ll start evicting things to make room for new junk as our app continues to make requests.</p>
<p>Working this out, there&#8217;s a 25% chance of our app requesting a doc that&#8217;s already in memory, so 75% of the requests are going to go to disk.  Say we&#8217;re doing 2 requests a sec.  Then 1 hour of requests is 2 requests * 3600 seconds/hour = 7200 requests, 4800 of which are going to disk (.75 * 7200). If each request pulls back 50KB, that&#8217;s 240MB read from disk/hour.  If we set readahead to 0, we&#8217;ll have 2MB read from disk/hour.</p>
<p>Which brings us to the next symptom of a too-high readahead: unexpectedly high disk IO. Because most of the data we want isn&#8217;t in memory, we keep having to go to disk, dragging shopping-carts full of junk into RAM, perpetuating the high disk io/low resident mem cycle.</p>
<p>The general takeaway is that a DB is not a &#8220;normal&#8221; workload for an OS.  The default settings may screw you over.</p>

<div id='reaction_buttons_post1881' class='reaction_buttons'>
<div class="reaction_buttons_tagline">Please let me know what thought of this post, anonymously here or in the comments below:</div><a class='reaction_button reaction_button_Funny_count' href="javascript:reaction_buttons_increment_button_ajax('1881', 'Funny');">Funny&nbsp;<span class='count'>(<span class='count_number'>0</span>)</span></a> <a class='reaction_button reaction_button_Useful_count' href="javascript:reaction_buttons_increment_button_ajax('1881', 'Useful');">Useful&nbsp;<span class='count'>(<span class='count_number'>7</span>)</span></a> <a class='reaction_button reaction_button_Too___short_count' href="javascript:reaction_buttons_increment_button_ajax('1881', 'Too short');">Too short&nbsp;<span class='count'>(<span class='count_number'>1</span>)</span></a> <a class='reaction_button reaction_button_Too___long_count' href="javascript:reaction_buttons_increment_button_ajax('1881', 'Too long');">Too long&nbsp;<span class='count'>(<span class='count_number'>0</span>)</span></a> </div>
<div class="shr-publisher-1881"></div><!-- Start Shareaholic LikeButtonSetBottom --><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><div class='shareaholic-like-buttonset' style='float:none;height:30px;'><a class='shareaholic-googleplusone' data-shr_size='medium' data-shr_count='true' data-shr_href='http%3A%2F%2Fwww.snailinaturtleneck.com%2Fblog%2F2012%2F05%2F10%2Fthursday-5-diagnosing-high-readahead%2F' data-shr_title='%E2%80%93%E2%80%93thursday+%235%3A+diagnosing+high+readahead'></a></div><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><!-- End Shareaholic LikeButtonSetBottom --><img src="http://feeds.feedburner.com/~r/siat-mongodb/~4/k412e8EUBQo" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.snailinaturtleneck.com/blog/2012/05/10/thursday-5-diagnosing-high-readahead/feed/</wfw:commentRss>
		<slash:comments>7</slash:comments>
		<feedburner:origLink>http://www.snailinaturtleneck.com/blog/2012/05/10/thursday-5-diagnosing-high-readahead/</feedburner:origLink></item>
		<item>
		<title>Night of the Living Dead Ops</title>
		<link>http://feedproxy.google.com/~r/siat-mongodb/~3/3mE5gn5mOrc/</link>
		<comments>http://www.snailinaturtleneck.com/blog/2012/04/20/night-of-the-living-dead-ops/#comments</comments>
		<pubDate>Fri, 20 Apr 2012 21:03:32 +0000</pubDate>
		<dc:creator>Kristina Chodorow</dc:creator>
				<category><![CDATA[MongoDB]]></category>

		<guid isPermaLink="false">http://www.snailinaturtleneck.com/blog/?p=1956</guid>
		<description><![CDATA[MongoDB users often ask about the &#8220;killed&#8221; field in db.currentOp() output. For example, if you&#8217;ve run db.killOp(), you might see something like: &#62; db.currentOp&#40;&#41; &#123; &#34;inprog&#34; : &#91; &#123; &#34;opid&#34; : 3062962, &#34;active&#34; : true, &#34;lockType&#34; : &#34;write&#34;, &#34;waitingForLock&#34; : false, &#34;secs_running&#34; : 32267, &#34;op&#34; : &#34;update&#34;, &#34;ns&#34; : &#34;httpdb.servers&#34;, &#34;query&#34; : &#123; &#34;_id&#34; :&#8230;]]></description>
			<content:encoded><![CDATA[<!-- Start Shareaholic LikeButtonSetTop --><!-- End Shareaholic LikeButtonSetTop --><p>MongoDB users often ask about the &#8220;killed&#8221; field in <code>db.currentOp()</code> output.  For example, if you&#8217;ve run <code>db.killOp()</code>, you might see something like:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #339933;">&gt;</span> db.<span style="color: #660066;">currentOp</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>
<span style="color: #009900;">&#123;</span>
	<span style="color: #3366CC;">&quot;inprog&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span>
		<span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;opid&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">3062962</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;active&quot;</span> <span style="color: #339933;">:</span> <span style="color: #003366; font-weight: bold;">true</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;lockType&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;write&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;waitingForLock&quot;</span> <span style="color: #339933;">:</span> <span style="color: #003366; font-weight: bold;">false</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;secs_running&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">32267</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;op&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;update&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;ns&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;httpdb.servers&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;query&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
				<span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;150.237.88.189&quot;</span>
			<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;client&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;127.0.0.1:50416&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;desc&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;conn&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;threadId&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;0x2900c400&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;connectionId&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">74</span><span style="color: #339933;">,</span>
<span style="display:block;background-color: #ffc;">			<span style="color: #3366CC;">&quot;killed&quot;</span> <span style="color: #339933;">:</span> <span style="color: #003366; font-weight: bold;">true</span><span style="color: #339933;">,</span></span>			<span style="color: #3366CC;">&quot;numYields&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">0</span>
		<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
		<span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;opid&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">3063051</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;active&quot;</span> <span style="color: #339933;">:</span> <span style="color: #003366; font-weight: bold;">false</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;lockType&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;read&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;waitingForLock&quot;</span> <span style="color: #339933;">:</span> <span style="color: #003366; font-weight: bold;">true</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;op&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;query&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;ns&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;query&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
				<span style="color: #3366CC;">&quot;count&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;servers&quot;</span><span style="color: #339933;">,</span>
				<span style="color: #3366CC;">&quot;query&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
					<span style="color: #3366CC;">&quot;code&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
						<span style="color: #3366CC;">&quot;$gte&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">200</span>
					<span style="color: #009900;">&#125;</span>
				<span style="color: #009900;">&#125;</span>
			<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;client&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;127.0.0.1:30736&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;desc&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;conn&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;threadId&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;0x29113700&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;connectionId&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">191</span><span style="color: #339933;">,</span>
<span style="display:block;background-color: #ffc;">			<span style="color: #3366CC;">&quot;killed&quot;</span> <span style="color: #339933;">:</span> <span style="color: #003366; font-weight: bold;">true</span><span style="color: #339933;">,</span></span>			<span style="color: #3366CC;">&quot;numYields&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">0</span>
		<span style="color: #009900;">&#125;</span>
        <span style="color: #009900;">&#93;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>The operation looks dead&#8230; it has <code>killed:true</code>, right?  But you can run <code>db.currentOp()</code> again and again and the op doesn&#8217;t go away, even though it&#8217;s been &#8220;killed.&#8221;  So what&#8217;s up with that?</p>
<div id="attachment_1957" class="wp-caption alignright" style="width: 360px"><a href="http://www.snailinaturtleneck.com/blog/wp-content/uploads/2012/04/chainsaw.jpeg"><img src="http://www.snailinaturtleneck.com/blog/wp-content/uploads/2012/04/chainsaw.jpeg" alt="" title="chainsaw" width="350" height="210" class="size-full wp-image-1957" /></a><p class="wp-caption-text">Chainsaws: the kill -9 of living dead</p></div>
<p>It has to do with how MongoDB handles killed operations.  When you run <code>db.killOp(3062962)</code>, MongoDB looks up operation 3062962 in a hashtable and sets its <code>killed</code> field to <code>true</code>.  However, the code running that op gets to decide whether to even check that field and how deal with it appropriately.  </p>
<p>There are basically three ways MongoDB ops handle getting killed:</p>
<ul>
<li>Ones that die when they yield whatever lock they&#8217;re holding.  This means that if the op never yields (note that numYields is 0 in the example above), it will never be killed.
<li>Ones that can be killed at certain checkpoints.  For example, index builds happen in multiple stages and check <code>killed</code> between stages.  (Many commands do this, too.)
<li>Ones cannot be killed at all.  For example, rsSync, the name for the op applying replication, falls into this category.  There are some sharding commands that can&#8217;t be killed, too.
</ul>
<p>There is no <code>kill -9</code> equivalent in MongoDB (other than <code>kill -9</code>-ing the server itself): if an op doesn&#8217;t know how to safely kill itself, it won&#8217;t die until it&#8217;s good and ready.  Which means that you can have a &#8220;killed&#8221; op in <code>db.currentOp()</code> output for a long time.  <code>killed</code> might be better named <code>killRequested</code>.</p>
<p>Also, if you kill an operation before it acquires a lock, it&#8217;ll generally start executing anyway (e.g., op 3063051 above).  For example, try opening up a shell and make the db hold the writelock for 10 minutes:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #339933;">&gt;</span> db.<span style="color: #000066; font-weight: bold;">eval</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;sleep(10*60*1000)&quot;</span><span style="color: #009900;">&#41;</span></pre></div></div>

<p>While that&#8217;s running, in another shell, try doing an insert (which will block, as the db cannot do any writes while the <code>db.eval()</code> is holding the writelock).</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #339933;">&gt;</span> db.<span style="color: #660066;">foo</span>.<span style="color: #660066;">insert</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#123;</span>x<span style="color: #339933;">:</span><span style="color: #CC0000;">1</span><span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span></pre></div></div>

<p>Now, in a third shell, kill the insert we just did (before the 10 minutes elapse):</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #339933;">&gt;</span> db.<span style="color: #660066;">currentOp</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>
<span style="color: #009900;">&#123;</span>
        <span style="color: #3366CC;">&quot;inprog&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span>
                <span style="color: #009900;">&#123;</span>
                        <span style="color: #3366CC;">&quot;opid&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">455937</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;active&quot;</span> <span style="color: #339933;">:</span> <span style="color: #003366; font-weight: bold;">true</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;lockType&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;W&quot;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;waitingForLock&quot;</span> <span style="color: #339933;">:</span> <span style="color: #003366; font-weight: bold;">false</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;secs_running&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">25</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;op&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;query&quot;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;ns&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;test&quot;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;query&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
                                <span style="color: #3366CC;">&quot;$eval&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;sleep(10*60*1000)&quot;</span>
                        <span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;client&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;127.0.0.1:51797&quot;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;desc&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;conn&quot;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;threadId&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;0x7f241c0bf700&quot;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;connectionId&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">14477</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;locks&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
                                <span style="color: #3366CC;">&quot;.&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;W&quot;</span>
                        <span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;numYields&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">0</span>
                <span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
                <span style="color: #009900;">&#123;</span>
<span style="display:block;background-color: #ffc;">                        <span style="color: #3366CC;">&quot;opid&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">455949</span><span style="color: #339933;">,</span></span>                        <span style="color: #3366CC;">&quot;active&quot;</span> <span style="color: #339933;">:</span> <span style="color: #003366; font-weight: bold;">false</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;lockType&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;w&quot;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;waitingForLock&quot;</span> <span style="color: #339933;">:</span> <span style="color: #003366; font-weight: bold;">true</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;op&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;insert&quot;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;ns&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;&quot;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;query&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
&nbsp;
                        <span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;client&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;127.0.0.1:51799&quot;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;desc&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;conn&quot;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;threadId&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;0x7f24147f8700&quot;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;connectionId&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">14478</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;locks&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
                                <span style="color: #3366CC;">&quot;.&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;w&quot;</span><span style="color: #339933;">,</span>
                                <span style="color: #3366CC;">&quot;.test&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;W&quot;</span>
                        <span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;numYields&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">0</span>
                <span style="color: #009900;">&#125;</span>
        <span style="color: #009900;">&#93;</span>
<span style="color: #009900;">&#125;</span>
<span style="color: #339933;">&gt;</span> <span style="color: #006600; font-style: italic;">// get the opId of the insert from currentOp</span>
<span style="color: #339933;">&gt;</span> db.<span style="color: #660066;">killOp</span><span style="color: #009900;">&#40;</span><span style="color: #CC0000;">455949</span><span style="color: #009900;">&#41;</span>
<span style="color: #009900;">&#123;</span> <span style="color: #3366CC;">&quot;info&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;attempting to kill op&quot;</span> <span style="color: #009900;">&#125;</span>
<span style="color: #339933;">&gt;</span> <span style="color: #006600; font-style: italic;">// run currentOp again to see that killed:true</span>
<span style="color: #339933;">&gt;</span> db.<span style="color: #660066;">currentOp</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>
<span style="color: #009900;">&#123;</span>
        <span style="color: #3366CC;">&quot;inprog&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span>
                <span style="color: #009900;">&#123;</span>
                        <span style="color: #3366CC;">&quot;opid&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">455937</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;active&quot;</span> <span style="color: #339933;">:</span> <span style="color: #003366; font-weight: bold;">true</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;lockType&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;W&quot;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;waitingForLock&quot;</span> <span style="color: #339933;">:</span> <span style="color: #003366; font-weight: bold;">false</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;secs_running&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">221</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;op&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;query&quot;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;ns&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;test&quot;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;query&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
                                <span style="color: #3366CC;">&quot;$eval&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;sleep(10*60*1000)&quot;</span>
                        <span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;client&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;127.0.0.1:51797&quot;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;desc&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;conn&quot;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;threadId&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;0x7f241c0bf700&quot;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;connectionId&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">14477</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;locks&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
                                <span style="color: #3366CC;">&quot;.&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;W&quot;</span>
                        <span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;numYields&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">0</span>
                <span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
                <span style="color: #009900;">&#123;</span>
                        <span style="color: #3366CC;">&quot;opid&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">455949</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;active&quot;</span> <span style="color: #339933;">:</span> <span style="color: #003366; font-weight: bold;">false</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;lockType&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;w&quot;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;waitingForLock&quot;</span> <span style="color: #339933;">:</span> <span style="color: #003366; font-weight: bold;">true</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;op&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;insert&quot;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;ns&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;&quot;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;query&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
&nbsp;
                        <span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;client&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;127.0.0.1:51799&quot;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;desc&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;conn&quot;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;threadId&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;0x7f24147f8700&quot;</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;connectionId&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">14478</span><span style="color: #339933;">,</span>
                        <span style="color: #3366CC;">&quot;locks&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
                                <span style="color: #3366CC;">&quot;.&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;w&quot;</span><span style="color: #339933;">,</span>
                                <span style="color: #3366CC;">&quot;.test&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;W&quot;</span>
                        <span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
<span style="display:block;background-color: #ffc;">                        <span style="color: #3366CC;">&quot;killed&quot;</span> <span style="color: #339933;">:</span> <span style="color: #003366; font-weight: bold;">true</span><span style="color: #339933;">,</span></span>                        <span style="color: #3366CC;">&quot;numYields&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">0</span>
                <span style="color: #009900;">&#125;</span>
        <span style="color: #009900;">&#93;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>If you wait 10 minutes for the <code>db.eval()</code> to finish, then do a find on <em>db.foo</em>, you&#8217;ll see that <code>{x:1}</code> was actually inserted anyway.  This is because the op&#8217;s lifecycle looks something like:</p>
<ul>
<li>Wait for lock
<li>Acquire lock!
<li>Start running
<li>Yield lock
<li>Check for killed
</ul>
<p>So it&#8217;ll run a bit before dying (if it can be killed at all), which may produce unintuitive results.</p>

<div id='reaction_buttons_post1956' class='reaction_buttons'>
<div class="reaction_buttons_tagline">Please let me know what thought of this post, anonymously here or in the comments below:</div><a class='reaction_button reaction_button_Funny_count' href="javascript:reaction_buttons_increment_button_ajax('1956', 'Funny');">Funny&nbsp;<span class='count'>(<span class='count_number'>2</span>)</span></a> <a class='reaction_button reaction_button_Useful_count' href="javascript:reaction_buttons_increment_button_ajax('1956', 'Useful');">Useful&nbsp;<span class='count'>(<span class='count_number'>2</span>)</span></a> <a class='reaction_button reaction_button_Too___short_count' href="javascript:reaction_buttons_increment_button_ajax('1956', 'Too short');">Too short&nbsp;<span class='count'>(<span class='count_number'>0</span>)</span></a> <a class='reaction_button reaction_button_Too___long_count' href="javascript:reaction_buttons_increment_button_ajax('1956', 'Too long');">Too long&nbsp;<span class='count'>(<span class='count_number'>0</span>)</span></a> </div>
<div class="shr-publisher-1956"></div><!-- Start Shareaholic LikeButtonSetBottom --><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><div class='shareaholic-like-buttonset' style='float:none;height:30px;'><a class='shareaholic-googleplusone' data-shr_size='medium' data-shr_count='true' data-shr_href='http%3A%2F%2Fwww.snailinaturtleneck.com%2Fblog%2F2012%2F04%2F20%2Fnight-of-the-living-dead-ops%2F' data-shr_title='Night+of+the+Living+Dead+Ops'></a></div><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><!-- End Shareaholic LikeButtonSetBottom --><img src="http://feeds.feedburner.com/~r/siat-mongodb/~4/3mE5gn5mOrc" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.snailinaturtleneck.com/blog/2012/04/20/night-of-the-living-dead-ops/feed/</wfw:commentRss>
		<slash:comments>6</slash:comments>
		<feedburner:origLink>http://www.snailinaturtleneck.com/blog/2012/04/20/night-of-the-living-dead-ops/</feedburner:origLink></item>
		<item>
		<title>Replica Set Internals Bootcamp: Part II – Creating a Set</title>
		<link>http://feedproxy.google.com/~r/siat-mongodb/~3/-6EdwbJ16WQ/</link>
		<comments>http://www.snailinaturtleneck.com/blog/2012/03/06/replica-set-internals-bootcamp-part-ii-creating-a-set/#comments</comments>
		<pubDate>Tue, 06 Mar 2012 21:02:07 +0000</pubDate>
		<dc:creator>Kristina Chodorow</dc:creator>
				<category><![CDATA[MongoDB]]></category>
		<category><![CDATA[bootcamp]]></category>
		<category><![CDATA[internals]]></category>

		<guid isPermaLink="false">http://www.snailinaturtleneck.com/blog/?p=1767</guid>
		<description><![CDATA[I&#8217;ve been doing replica set &#8220;bootcamps&#8221; for new hires. It&#8217;s mainly focused on applying this to debug replica set issues and being able to talk fluently about what&#8217;s happening, but it occurred to me that you (blog readers) might be interested in it, too. There are 8 subjects I cover in my bootcamp: Elections Creating&#8230;]]></description>
			<content:encoded><![CDATA[<!-- Start Shareaholic LikeButtonSetTop --><!-- End Shareaholic LikeButtonSetTop --><p>I&#8217;ve been doing replica set &#8220;bootcamps&#8221; for new hires. It&#8217;s mainly focused on applying this to debug replica set issues and being able to talk fluently about what&#8217;s happening, but it occurred to me that you (blog readers) might be interested in it, too.  </p>
<p><img src="http://www.snailinaturtleneck.com/blog/wp-content/uploads/2012/01/dog-boot-camp-2.jpg" alt="" title="dog-boot-camp" width="265" height="286" class="alignright size-full wp-image-1760" /></p>
<p>There are 8 subjects I cover in my bootcamp: </p>
<ol>
<li><a href="http://www.snailinaturtleneck.com/blog/?p=1752">Elections</a>
<li><a href="http://www.snailinaturtleneck.com/blog/?p=1767">Creating a set</a>
<li>Reconfiguring
<li>Syncing
<li>Initial Sync
<li>Rollback
<li>Authentication
<li>Debugging
</ol>
<p>I&#8217;m going to do one subject per post, we&#8217;ll see how many I can get through.</p>
<p><em>Prerequisites: I&#8217;m assuming you know what replica sets are and you&#8217;ve configured a set, written data to it, read from a secondary, etc.  You understand the terms primary and secondary.</em>  </p>
<h4>Initializing a Set</h4>
<p>Suppose you are creating a new set.  You start up some <em>mongod</em>s with no data and the <em>replSet</em> option.  When a server starts up with the <em>replSet</em> option, the first thing it does is check its <em>local.system.replset</em> collection for a replica set config it can load, but it won&#8217;t find one (because there&#8217;s no data).  Since it cannot find a config, it goes into the <em>EMPTYCONFIG</em> state. If you look in the logs, you&#8217;ll see messages about <em>EMPTYCONFIG</em>.</p>

<div class="wp_syntax"><div class="code"><pre class="text" style="font-family:monospace;">Tue Mar  6 12:24:35 [rsStart] replSet can't get local.system.replset config from self or any seed (EMPTYCONFIG)
Tue Mar  6 12:24:35 [rsStart] replSet info you may need to run replSetInitiate -- rs.initiate() in the shell -- if that is not already done
Tue Mar  6 12:24:45 [rsStart] replSet can't get local.system.replset config from self or any seed (EMPTYCONFIG)
Tue Mar  6 12:24:55 [rsStart] replSet can't get local.system.replset config from self or any seed (EMPTYCONFIG)
Tue Mar  6 12:25:05 [rsStart] replSet can't get local.system.replset config from self or any seed (EMPTYCONFIG)
Tue Mar  6 12:25:15 [rsStart] replSet can't get local.system.replset config from self or any seed (EMPTYCONFIG)
Tue Mar  6 12:25:25 [rsStart] replSet can't get local.system.replset config from self or any seed (EMPTYCONFIG)</pre></div></div>

<p>Now suppose you send the <em>replSetInitiate</em> command to one of the members.  <em>replSetInitiate</em> can either take a custom configuration or generate a config automatically. If you do not pass in a config, the server will try to figure out what its hostname is and generate a config using that.  </p>
<p><em>Note: on EC2, the server <b>always</b> chooses the wrong hostname, so you have to pass in the config you want.</em></p>
<p>Once the server has a config document, either passed in or generated, it&#8217;ll make sure it can reach every node specified (all members must be up and reachable to initiate), then store the config in the <em>local.system.replset</em> collection.  Finally, it begins sending heartbeat requests to the other members of the set.  </p>
<h4>The Log: Step-by-Step</h4>
<p>Being able to interpret log files is critical to knowing what&#8217;s going on, so let&#8217;s walk through a sample log from running <code>rs.initiate()</code>.  Here&#8217;s the whole log, feel free to skip over this for now.  We&#8217;ll take it piece-by-piece below.</p>

<div class="wp_syntax"><div class="code"><pre class="text" style="font-family:monospace;">Tue Mar  6 12:45:00 [rsStart] replSet can't get local.system.replset config from self or any seed (EMPTYCONFIG)
Tue Mar  6 12:45:02 [initandlisten] connection accepted from 127.0.0.1:38839 #2 (2 connections now open)
Tue Mar  6 12:45:08 [conn2] replSet replSetInitiate admin command received from client
Tue Mar  6 12:45:08 [conn2] replSet info initiate : no configuration specified.  Using a default configuration for the set
Tue Mar  6 12:45:08 [conn2] replSet created this configuration for initiation : { _id: &quot;foo&quot;, members: [ { _id: 0, host: &quot;ubuntu:30000&quot; } ] }
Tue Mar  6 12:45:08 [conn2] replSet replSetInitiate config object parses ok, 1 members specified
Tue Mar  6 12:45:08 [conn2] replSet replSetInitiate all members seem up
Tue Mar  6 12:45:08 [conn2] ******
Tue Mar  6 12:45:08 [conn2] creating replication oplog of size: 49085MB...
Tue Mar  6 12:45:08 [FileAllocator] allocating new datafile /datadir/local.ns, filling with zeroes...
Tue Mar  6 12:45:08 [FileAllocator] creating directory /datadir/_tmp
Tue Mar  6 12:45:08 [FileAllocator] done allocating datafile /datadir/local.ns, size: 16MB,  took 0.016 secs
Tue Mar  6 12:45:08 [FileAllocator] allocating new datafile /datadir/local.0, filling with zeroes...
Tue Mar  6 12:45:08 [FileAllocator] done allocating datafile /datadir/local.0, size: 2047MB,  took 0.016 secs
Tue Mar  6 12:45:08 [conn2] datafileheader::init initializing /datadir/local.0 n:0
Tue Mar  6 12:45:08 [FileAllocator] allocating new datafile /datadir/local.1, filling with zeroes...
...
Tue Mar  6 12:45:09 [conn2] datafileheader::init initializing /datadir/local.22 n:22
Tue Mar  6 12:45:09 [FileAllocator] allocating new datafile /datadir/local.23, filling with zeroes...
Tue Mar  6 12:45:09 [FileAllocator] done allocating datafile /datadir/local.23, size: 2047MB,  took 0.042 secs
Tue Mar  6 12:45:09 [conn2] datafileheader::init initializing /datadir/local.23 n:23
Tue Mar  6 12:45:10 [conn2] ******
Tue Mar  6 12:45:10 [conn2] replSet info saving a newer config version to local.system.replset
Tue Mar  6 12:45:10 [conn2] replSet saveConfigLocally done
Tue Mar  6 12:45:10 [conn2] replSet replSetInitiate config now saved locally.  Should come online in about a minute.
Tue Mar  6 12:45:10 [conn2] command admin.$cmd command: { replSetInitiate: undefined } ntoreturn:1 keyUpdates:0 reslen:196 2802ms
Tue Mar  6 12:45:10 [rsStart] replSet load config ok from self
Tue Mar  6 12:45:10 [rsStart] replSet I am ubuntu:30000
Tue Mar  6 12:45:10 [rsStart] replSet STARTUP2
Tue Mar  6 12:45:10 [rsSync] replSet SECONDARY
Tue Mar  6 12:45:25 [rsSync] waiting for 2 pings from other members before syncing
Tue Mar  6 12:45:26 [rsMgr] replSet info electSelf 0
Tue Mar  6 12:45:26 [rsMgr] replSet PRIMARY</pre></div></div>

<p>Now, to understand this line-by-line. First, we start out in the <em>EMPTYCONFIG</em> state, as described above.</p>

<div class="wp_syntax"><div class="code"><pre class="text" style="font-family:monospace;">Tue Mar  6 12:45:00 [rsStart] replSet can't get local.system.replset config from self or any seed (EMPTYCONFIG)</pre></div></div>

<p>Now the shell connects to the server and runs <code>rs.initiate()</code> (<em>replSetInitiate</em>), which apparently takes me 6 seconds to type (take that, Mavis Beacon).</p>

<div class="wp_syntax"><div class="code"><pre class="text" style="font-family:monospace;">Tue Mar  6 12:45:02 [initandlisten] connection accepted from 127.0.0.1:38839 #2 (2 connections now open)
Tue Mar  6 12:45:08 [conn2] replSet replSetInitiate admin command received from client</pre></div></div>

<p>Because we didn&#8217;t give a config, the server tries to generate one:</p>

<div class="wp_syntax"><div class="code"><pre class="text" style="font-family:monospace;">Tue Mar  6 12:45:08 [conn2] replSet info initiate : no configuration specified.  Using a default configuration for the set
Tue Mar  6 12:45:08 [conn2] replSet created this configuration for initiation : { _id: &quot;foo&quot;, members: [ { _id: 0, host: &quot;ubuntu:30000&quot; } ] }</pre></div></div>

<p>Now it does some sanity checks on this config (e.g., making sure all members are up and reachable).  This matters more if we gave it a config, but sometimes things are so screwed up you can&#8217;t reach yourself.</p>

<div class="wp_syntax"><div class="code"><pre class="text" style="font-family:monospace;">Tue Mar  6 12:45:08 [conn2] replSet replSetInitiate config object parses ok, 1 members specified
Tue Mar  6 12:45:08 [conn2] replSet replSetInitiate all members seem up</pre></div></div>

<p>Now it calculates the size of the oplog and allocates it between two lines of ******.</p>

<div class="wp_syntax"><div class="code"><pre class="text" style="font-family:monospace;">Tue Mar  6 12:45:08 [conn2] ******
Tue Mar  6 12:45:08 [conn2] creating replication oplog of size: 49085MB...
Tue Mar  6 12:45:08 [FileAllocator] allocating new datafile /datadir/local.ns, filling with zeroes...
Tue Mar  6 12:45:08 [FileAllocator] creating directory /datadir/_tmp
Tue Mar  6 12:45:08 [FileAllocator] done allocating datafile /datadir/local.ns, size: 16MB,  took 0.016 secs
Tue Mar  6 12:45:08 [FileAllocator] allocating new datafile /datadir/local.0, filling with zeroes...
Tue Mar  6 12:45:08 [FileAllocator] done allocating datafile /datadir/local.0, size: 2047MB,  took 0.016 secs
Tue Mar  6 12:45:08 [conn2] datafileheader::init initializing /datadir/local.0 n:0
Tue Mar  6 12:45:08 [FileAllocator] allocating new datafile /datadir/local.1, filling with zeroes...
...
Tue Mar  6 12:45:09 [conn2] datafileheader::init initializing /datadir/local.22 n:22
Tue Mar  6 12:45:09 [FileAllocator] allocating new datafile /datadir/local.23, filling with zeroes...
Tue Mar  6 12:45:09 [FileAllocator] done allocating datafile /datadir/local.23, size: 2047MB,  took 0.042 secs
Tue Mar  6 12:45:09 [conn2] datafileheader::init initializing /datadir/local.23 n:23
Tue Mar  6 12:45:10 [conn2] ******</pre></div></div>

<p>It doesn&#8217;t actually print the &#8220;&#8230;&#8221; part, I just omitted 21 files being preallocated.</p>
<p>Now it stores the configuration in the <em>local.system.replset</em> collection.</p>

<div class="wp_syntax"><div class="code"><pre class="text" style="font-family:monospace;">Tue Mar  6 12:45:10 [conn2] replSet info saving a newer config version to local.system.replset
Tue Mar  6 12:45:10 [conn2] replSet saveConfigLocally done
Tue Mar  6 12:45:10 [conn2] replSet replSetInitiate config now saved locally.  Should come online in about a minute.</pre></div></div>

<p>It seldom takes a minute for it to come online, but this way you&#8217;ll be pleasantly surprised.</p>
<p><em>replSetInitiate</em> is now done running.  It will often be logged, because slow operations are logged and allocating the oplog usually takes a while.</p>

<div class="wp_syntax"><div class="code"><pre class="text" style="font-family:monospace;">Tue Mar  6 12:45:10 [conn2] command admin.$cmd command: { replSetInitiate: undefined } ntoreturn:1 keyUpdates:0 reslen:196 2802ms</pre></div></div>

<p>Now it actually loads this configuration as the replica set config we want to use:</p>

<div class="wp_syntax"><div class="code"><pre class="text" style="font-family:monospace;">Tue Mar  6 12:45:10 [rsStart] replSet load config ok from self</pre></div></div>

<p>You won&#8217;t see this next line if you&#8217;re running 2.0, I added it for 2.2 because I was sick of having to decipher which server a log was from:</p>

<div class="wp_syntax"><div class="code"><pre class="text" style="font-family:monospace;">Tue Mar  6 12:45:10 [rsStart] replSet I am ubuntu:30000</pre></div></div>

<p>Yay, now config has been loaded, making our state <em>STARTUP2</em> (the &#8220;config has been loaded, starting up RS threads&#8221; state):</p>

<div class="wp_syntax"><div class="code"><pre class="text" style="font-family:monospace;">Tue Mar  6 12:45:10 [rsStart] replSet STARTUP2</pre></div></div>

<p>At this point, it can go straight into <em>PRIMARY</em> state, but it doesn&#8217;t.  We could fix this, but it hasn&#8217;t been a priority, so it goes into <em>SECONDARY</em> state briefly before becoming <em>PRIMARY</em>:</p>

<div class="wp_syntax"><div class="code"><pre class="text" style="font-family:monospace;">Tue Mar  6 12:45:10 [rsSync] replSet SECONDARY</pre></div></div>

<p>A &#8220;real&#8221; secondary (we&#8217;re about to become primary, so we don&#8217;t count) will gather some stats about who&#8217;s best to sync from before it chooses a target:</p>

<div class="wp_syntax"><div class="code"><pre class="text" style="font-family:monospace;">Tue Mar  6 12:45:25 [rsSync] waiting for 2 pings from other members before syncing</pre></div></div>

<p>Good luck with that, buddy, you&#8217;re the only one in the config.</p>
<p>Aha, we&#8217;ve noticed that we can become primary:</p>

<div class="wp_syntax"><div class="code"><pre class="text" style="font-family:monospace;">Tue Mar  6 12:45:26 [rsMgr] replSet info electSelf 0
Tue Mar  6 12:45:26 [rsMgr] replSet PRIMARY</pre></div></div>

<p>And now we&#8217;re all set.</p>
<h4>Propegating the Config</h4>
<p>If we add members or provide an initial config with multiple members, the initial member&#8217;s heartbeat requests are sent to a bunch of servers in <em>EMPTYCONFIG</em> state. When these other servers receive the heartbeat request, they notice &#8220;Hey, I don&#8217;t have any config and this guy seems to think I&#8217;m part of his set, so I should check in with him.&#8221;  </p>
<p>These <em>EMPTYCONFIG</em> members will then request a config from the member that requested the heartbeat.  Seeing themselves in the config, they&#8217;ll save it to their own <em>local.system.replset</em> collection, then start sending out their own heartbeats.  At that point, they&#8217;ll move into <em>RECOVERING</em> state and, once they&#8217;re synced to the original member, they&#8217;ll turn into secondaries (unless they&#8217;re arbiters, of course, but same general idea).</p>
<p>One quirk of initiating a set is that every member of the set must not have any data, other than the one you&#8217;re sending <em>replSetInitiate</em> to.  After the set is initialized you can add members containing data, but <em>at most one</em> member can have data when you initialize the set.</p>
<h4>Confused?</h4>
<p>Feel free to ask questions in the comments below. This is a loving, caring bootcamp (as bootcamps go).</p>

<div id='reaction_buttons_post1767' class='reaction_buttons'>
<div class="reaction_buttons_tagline">Please let me know what thought of this post, anonymously here or in the comments below:</div><a class='reaction_button reaction_button_Funny_count' href="javascript:reaction_buttons_increment_button_ajax('1767', 'Funny');">Funny&nbsp;<span class='count'>(<span class='count_number'>0</span>)</span></a> <a class='reaction_button reaction_button_Useful_count' href="javascript:reaction_buttons_increment_button_ajax('1767', 'Useful');">Useful&nbsp;<span class='count'>(<span class='count_number'>3</span>)</span></a> <a class='reaction_button reaction_button_Too___short_count' href="javascript:reaction_buttons_increment_button_ajax('1767', 'Too short');">Too short&nbsp;<span class='count'>(<span class='count_number'>0</span>)</span></a> <a class='reaction_button reaction_button_Too___long_count' href="javascript:reaction_buttons_increment_button_ajax('1767', 'Too long');">Too long&nbsp;<span class='count'>(<span class='count_number'>0</span>)</span></a> </div>
<div class="shr-publisher-1767"></div><!-- Start Shareaholic LikeButtonSetBottom --><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><div class='shareaholic-like-buttonset' style='float:none;height:30px;'><a class='shareaholic-googleplusone' data-shr_size='medium' data-shr_count='true' data-shr_href='http%3A%2F%2Fwww.snailinaturtleneck.com%2Fblog%2F2012%2F03%2F06%2Freplica-set-internals-bootcamp-part-ii-creating-a-set%2F' data-shr_title='Replica+Set+Internals+Bootcamp%3A+Part+II+-+Creating+a+Set'></a></div><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><!-- End Shareaholic LikeButtonSetBottom --><img src="http://feeds.feedburner.com/~r/siat-mongodb/~4/-6EdwbJ16WQ" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.snailinaturtleneck.com/blog/2012/03/06/replica-set-internals-bootcamp-part-ii-creating-a-set/feed/</wfw:commentRss>
		<slash:comments>6</slash:comments>
		<feedburner:origLink>http://www.snailinaturtleneck.com/blog/2012/03/06/replica-set-internals-bootcamp-part-ii-creating-a-set/</feedburner:origLink></item>
		<item>
		<title>The Comments Conundrum</title>
		<link>http://feedproxy.google.com/~r/siat-mongodb/~3/H-BMt86jrkA/</link>
		<comments>http://www.snailinaturtleneck.com/blog/2012/02/02/the-comments-conundrum/#comments</comments>
		<pubDate>Thu, 02 Feb 2012 21:49:53 +0000</pubDate>
		<dc:creator>Kristina Chodorow</dc:creator>
				<category><![CDATA[MongoDB]]></category>
		<category><![CDATA[aggregation]]></category>
		<category><![CDATA[pipeline]]></category>

		<guid isPermaLink="false">http://www.snailinaturtleneck.com/blog/?p=1730</guid>
		<description><![CDATA[One of the most common questions I see about MongoDB schema design is: I have a collection of blog posts and each post has an array of comments. How do I get&#8230; &#8230;all comments by a given author &#8230;the most recent comments &#8230;the most popular commenters? And so on. The answer to this has always&#8230;]]></description>
			<content:encoded><![CDATA[<!-- Start Shareaholic LikeButtonSetTop --><!-- End Shareaholic LikeButtonSetTop --><p><img src="http://www.snailinaturtleneck.com/blog/wp-content/uploads/2012/02/th_robot_confused.png" alt="" title="" width="160" height="137" class="alignright size-full wp-image-1814" /></p>
<p>One of the most common questions I see about MongoDB schema design is:</p>
<blockquote><p>
I have a collection of blog posts and each post has an array of comments.  How do I get&#8230;<br />
&#8230;all comments by a given author<br />
&#8230;the most recent comments<br />
&#8230;the most popular commenters?
</p></blockquote>
<p>And so on.  The answer to this has always been &#8220;Well, you can&#8217;t do that on the server side&#8230;&#8221;  You can either do it on the client side or store comments in their own collection. What you really want is the ability to treat embedded documents like a &#8220;real&#8221; collection.</p>
<p>The aggregation pipeline gives you this ability by letting you &#8220;unwind&#8221; arrays into separate documents, then doing whatever else you need to do in subsequent pipeline operators.</p>
<p>For example&#8230;</p>
<p><em>Note: you must be running at least version 2.1.0 of MongoDB to use the aggregation pipeline.</em></p>
<p><img src="http://www.snailinaturtleneck.com/blog/wp-content/uploads/2012/02/seriouscatcover.jpg" alt="" title="" width="297" height="297" class="alignright size-full wp-image-1815" /></p>
<p><b>Getting all comments by Serious Cat</b></p>
<p>Serious Cat&#8217;s comments are scattered between post documents, so there wasn&#8217;t a good way of querying for just those embedded documents.  Now there is.</p>
<p>Let&#8217;s assume we want each comment by Serious Cat, along with the title and url of the post Serious Cat was commenting on.  So, the steps we need to take are:</p>
<ol>
<li>Extract the fields we want (title, url, comments)
<li>Unwind the comments field: make each comment into a &#8220;real&#8221; document
<li>Query our new &#8220;comments collection&#8221; for &#8220;Serious Cat&#8221;
</ol>
<p>Using the aggregation pipeline, this looks like:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #339933;">&gt;</span> db.<span style="color: #660066;">runCommand</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#123;</span>aggregate<span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;posts&quot;</span><span style="color: #339933;">,</span> pipeline<span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span>
<span style="color: #009900;">&#123;</span>
   <span style="color: #006600; font-style: italic;">// extract the fields </span>
   $project<span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
        title <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #339933;">,</span>
        url <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #339933;">,</span>
        comments <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span>
    <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
<span style="color: #009900;">&#123;</span>
    <span style="color: #006600; font-style: italic;">// explode the &quot;comments&quot; array into separate documents</span>
    $unwind<span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;$comments&quot;</span>
<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
<span style="color: #009900;">&#123;</span>
    <span style="color: #006600; font-style: italic;">// query like a boss</span>
    $match<span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>comments.<span style="color: #660066;">author</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;Serious Cat&quot;</span><span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span><span style="color: #009900;">&#93;</span><span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span></pre></div></div>

<p>Now, this works well for something like a blog, where you have human-generated (small) data.  If you&#8217;ve got gigs of comments to go through, you probably want to filter out as many as possible (e.g., with <code>$match</code> or <code>$limit</code>) before sending it to the &#8220;everything-in-memory&#8221; parts of the pipeline.</p>
<p><b>Getting the most recent comments</b></p>
<p>Let&#8217;s assume our site lists the 10 most recent comments across all posts, with links back to the posts they appeared on, e.g.,</p>
<blockquote>
<ol>
<li>Great post! -Jerry (February 2nd, 2012) from <a>This is a Great Post</a>
<li>What does batrachophagous mean? -Fred (February 2nd, 2012) from <a>Fun with Crosswords</a>
<li>Where can I get discount Prada shoes? -Tom (February 1st, 2012) from <a>Rant about Spam</a><br />
&#8230;
</ol>
</blockquote>
<p>To extract these comments from a collection of posts, you could do something like:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #339933;">&gt;</span> db.<span style="color: #660066;">runCommand</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#123;</span>aggregate<span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;posts&quot;</span><span style="color: #339933;">,</span> pipeline<span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span>
<span style="color: #009900;">&#123;</span>
   <span style="color: #006600; font-style: italic;">// extract the fields</span>
   $project<span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
        title <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #339933;">,</span>
        url <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #339933;">,</span>
        comments <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span>
    <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#123;</span>
    <span style="color: #006600; font-style: italic;">// explode &quot;comments&quot; array into separate documents</span>
    $unwind<span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;$comments&quot;</span>
<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
<span style="color: #009900;">&#123;</span>
    <span style="color: #006600; font-style: italic;">// sort newest first</span>
    $sort<span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
        <span style="color: #3366CC;">&quot;comments.date&quot;</span> <span style="color: #339933;">:</span> <span style="color: #339933;">-</span><span style="color: #CC0000;">1</span>
    <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
<span style="color: #009900;">&#123;</span>
    <span style="color: #006600; font-style: italic;">// get the 10 newest</span>
    $limit<span style="color: #339933;">:</span> <span style="color: #CC0000;">10</span>
<span style="color: #009900;">&#125;</span><span style="color: #009900;">&#93;</span><span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span></pre></div></div>

<p>Let&#8217;s take a moment to look at what <code>$unwind</code> does to a sample document.  </p>
<p>Suppose you have a document that looks like this after the <code>$project</code>:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #009900;">&#123;</span>
    <span style="color: #3366CC;">&quot;url&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;/blog/spam&quot;</span><span style="color: #339933;">,</span>
    <span style="color: #3366CC;">&quot;title&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;Rant about Spam&quot;</span><span style="color: #339933;">,</span>
    <span style="color: #3366CC;">&quot;comments&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span>
        <span style="color: #009900;">&#123;</span>text <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;Where can I get discount Prada shoes?&quot;</span><span style="color: #339933;">,</span> ...<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
        <span style="color: #009900;">&#123;</span>text <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;First!&quot;</span><span style="color: #339933;">,</span> ...<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
        <span style="color: #009900;">&#123;</span>text <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;I hate spam, too!&quot;</span><span style="color: #339933;">,</span> ...<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
        <span style="color: #009900;">&#123;</span>text <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;I love spam.&quot;</span><span style="color: #339933;">,</span> ...<span style="color: #009900;">&#125;</span>
    <span style="color: #009900;">&#93;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>Then, after unwinding the <code>comments</code> field, you&#8217;d have:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #009900;">&#123;</span>
    <span style="color: #3366CC;">&quot;url&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;/blog/spam&quot;</span><span style="color: #339933;">,</span>
    <span style="color: #3366CC;">&quot;title&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;Rant about Spam&quot;</span><span style="color: #339933;">,</span>
    <span style="color: #3366CC;">&quot;comments&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span>
        <span style="color: #009900;">&#123;</span>text <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;Where can I get discount Prada shoes?&quot;</span><span style="color: #339933;">,</span> ...<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
    <span style="color: #009900;">&#93;</span>
<span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#123;</span>
    <span style="color: #3366CC;">&quot;url&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;/blog/spam&quot;</span><span style="color: #339933;">,</span>
    <span style="color: #3366CC;">&quot;title&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;Rant about Spam&quot;</span><span style="color: #339933;">,</span>
    <span style="color: #3366CC;">&quot;comments&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span>
        <span style="color: #009900;">&#123;</span>text <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;First!&quot;</span><span style="color: #339933;">,</span> ...<span style="color: #009900;">&#125;</span>
    <span style="color: #009900;">&#93;</span>
<span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#123;</span>
    <span style="color: #3366CC;">&quot;url&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;/blog/spam&quot;</span><span style="color: #339933;">,</span>
    <span style="color: #3366CC;">&quot;title&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;Rant about Spam&quot;</span><span style="color: #339933;">,</span>
    <span style="color: #3366CC;">&quot;comments&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span>
        <span style="color: #009900;">&#123;</span>text <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;I hate spam, too!&quot;</span><span style="color: #339933;">,</span> ...<span style="color: #009900;">&#125;</span>
    <span style="color: #009900;">&#93;</span>
<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
<span style="color: #009900;">&#123;</span>
    <span style="color: #3366CC;">&quot;url&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;/blog/spam&quot;</span><span style="color: #339933;">,</span>
    <span style="color: #3366CC;">&quot;title&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;Rant about Spam&quot;</span><span style="color: #339933;">,</span>
    <span style="color: #3366CC;">&quot;comments&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span>
        <span style="color: #009900;">&#123;</span>text <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;I love spam.&quot;</span><span style="color: #339933;">,</span> ...<span style="color: #009900;">&#125;</span>
    <span style="color: #009900;">&#93;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>Then we <code>$sort</code>, <code>$limit</code>, and Bob&#8217;s your uncle.</p>
<p><img src="http://www.snailinaturtleneck.com/blog/wp-content/uploads/2012/02/1291131680_two-thumbs-up.jpg" alt="" title="" width="248" height="320" class="alignright size-full wp-image-1817" /></p>
<p><b>Rank commenters by popularity</b></p>
<p>Suppose we allow users to upvote comments and we want to see who the most popular commenters are.</p>
<p>The steps we want to take are:</p>
<ol>
<li>Project out the fields we need (similar to above)
<li>Unwind the comments array (similar to above)
<li>Group by author, taking a count of votes (this will sum up all of the votes for each comment)
<li>Sort authors to find the most popular commenters
</ol>
<p>Using the pipeline, this would look like:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #339933;">&gt;</span> db.<span style="color: #660066;">runCommand</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#123;</span>aggregate<span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;posts&quot;</span><span style="color: #339933;">,</span> pipeline<span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span>
<span style="color: #009900;">&#123;</span>
   <span style="color: #006600; font-style: italic;">// extract the fields we'll need</span>
   $project<span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
        title <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #339933;">,</span>
        url <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #339933;">,</span>
        comments <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span>
    <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
<span style="color: #009900;">&#123;</span>
    <span style="color: #006600; font-style: italic;">// explode &quot;comments&quot; array into separate documents</span>
    $unwind<span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;$comments&quot;</span>
<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
<span style="color: #009900;">&#123;</span>
    <span style="color: #006600; font-style: italic;">// count up votes by author</span>
    $group <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
        _id <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;$comments.author&quot;</span><span style="color: #339933;">,</span>
        popularity <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$sum <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;$comments.votes&quot;</span><span style="color: #009900;">&#125;</span>
    <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
<span style="color: #009900;">&#123;</span>
    <span style="color: #006600; font-style: italic;">// sort by the new popular field</span>
    $sort<span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
        <span style="color: #3366CC;">&quot;popularity&quot;</span> <span style="color: #339933;">:</span> <span style="color: #339933;">-</span><span style="color: #CC0000;">1</span>
    <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span><span style="color: #009900;">&#93;</span><span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span></pre></div></div>

<p>As I mentioned before, there are a couple downsides to using the aggregation pipeline: a lot of the pipeline is done in-memory and can be very CPU- and memory-intensive.  However, used judiciously, it give you a lot more freedom to mush around your embedded documents.</p>

<div id='reaction_buttons_post1730' class='reaction_buttons'>
<div class="reaction_buttons_tagline">Please let me know what thought of this post, anonymously here or in the comments below:</div><a class='reaction_button reaction_button_Funny_count' href="javascript:reaction_buttons_increment_button_ajax('1730', 'Funny');">Funny&nbsp;<span class='count'>(<span class='count_number'>0</span>)</span></a> <a class='reaction_button reaction_button_Useful_count' href="javascript:reaction_buttons_increment_button_ajax('1730', 'Useful');">Useful&nbsp;<span class='count'>(<span class='count_number'>5</span>)</span></a> <a class='reaction_button reaction_button_Too___short_count' href="javascript:reaction_buttons_increment_button_ajax('1730', 'Too short');">Too short&nbsp;<span class='count'>(<span class='count_number'>0</span>)</span></a> <a class='reaction_button reaction_button_Too___long_count' href="javascript:reaction_buttons_increment_button_ajax('1730', 'Too long');">Too long&nbsp;<span class='count'>(<span class='count_number'>0</span>)</span></a> </div>
<div class="shr-publisher-1730"></div><!-- Start Shareaholic LikeButtonSetBottom --><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><div class='shareaholic-like-buttonset' style='float:none;height:30px;'><a class='shareaholic-googleplusone' data-shr_size='medium' data-shr_count='true' data-shr_href='http%3A%2F%2Fwww.snailinaturtleneck.com%2Fblog%2F2012%2F02%2F02%2Fthe-comments-conundrum%2F' data-shr_title='The+Comments+Conundrum'></a></div><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><!-- End Shareaholic LikeButtonSetBottom --><img src="http://feeds.feedburner.com/~r/siat-mongodb/~4/H-BMt86jrkA" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.snailinaturtleneck.com/blog/2012/02/02/the-comments-conundrum/feed/</wfw:commentRss>
		<slash:comments>6</slash:comments>
		<feedburner:origLink>http://www.snailinaturtleneck.com/blog/2012/02/02/the-comments-conundrum/</feedburner:origLink></item>
		<item>
		<title>Hacking Chess: Data Munging</title>
		<link>http://feedproxy.google.com/~r/siat-mongodb/~3/ThA7BKU0qPU/</link>
		<comments>http://www.snailinaturtleneck.com/blog/2012/01/27/hacking-chess-data-munging/#comments</comments>
		<pubDate>Fri, 27 Jan 2012 15:33:25 +0000</pubDate>
		<dc:creator>Kristina Chodorow</dc:creator>
				<category><![CDATA[MongoDB]]></category>
		<category><![CDATA[aggregation]]></category>
		<category><![CDATA[pipeline]]></category>

		<guid isPermaLink="false">http://www.snailinaturtleneck.com/blog/?p=1796</guid>
		<description><![CDATA[This is a supplement to the Hacking Chess with the MongoDB Pipeline. This post has instructions for rolling your own data sets from chess games. Download a collection of chess games you like. I&#8217;m using 1132 wins in less than 10 moves, but any of them should work. These files are in a format called&#8230;]]></description>
			<content:encoded><![CDATA[<!-- Start Shareaholic LikeButtonSetTop --><!-- End Shareaholic LikeButtonSetTop --><p>This is a supplement to the <a href="http://www.snailinaturtleneck.com/blog/2012/01/26/hacking-chess-with-the-mongodb-pipeline/">Hacking Chess with the MongoDB Pipeline</a>.  This post has instructions for rolling your own data sets from chess games.</p>
<p>Download a <a href="http://www.chessopolis.com/chessfiles/pgn_collections.htm">collection of chess games</a> you like.  I&#8217;m using <a href="ftp://ftp.pitt.edu/group/student-activities/chess/PGN/Collections/ten-pg.zip">1132 wins in less than 10 moves</a>, but any of them should work.</p>
<p>These files are in a format called portable game notation (.PGN), which is a human-readable notation for chess games.  For example, the first game in <em>TEN.PGN</em> (helloooo 80s filenames) looks like:</p>
<pre>
[Event "?"]
[Site "?"]
[Date "????.??.??"]
[Round "?"]
[White "Gedult D"]
[Black "Kohn V"]
[Result "1-0"]
[ECO "B33/09"]

1.e4 c5 2.Nf3 Nc6 3.d4 cxd4 4.Nxd4 Nf6
5.Nc3 e5 6.Ndb5 d6 7.Nd5 Nxd5 8.exd5 Ne7
9.c4 a6 10.Qa4  1-0
</pre>
<p>This represents a 10-turn win at an unknown event.  The &#8220;ECO&#8221; field shows which <a href="http://www.chessville.com/misc/misc_codes_ecocodes.htm">opening</a> was used (a Sicilian in the game above).</p>
<p>Unfortunately for us, MongoDB doesn&#8217;t import PGNs in their native format, so we&#8217;ll need to convert them to JSON.  I found a PGN->JSON converter in PHP that did the job <a href="http://www.dhtmlgoodies.com/index.html?whichScript=dhtml-chess">here</a>.  Scroll down to the &#8220;download&#8221; section to get the .zip.  </p>
<p>It&#8217;s one of those zips that vomits its contents into whatever directory you unzip it in, so create a new directory for it.  </p>
<p>So far, we have:</p>

<div class="wp_syntax"><div class="code"><pre class="bash" style="font-family:monospace;">$ <span style="color: #c20cb9; font-weight: bold;">mkdir</span> chess
$ <span style="color: #7a0874; font-weight: bold;">cd</span> chess
$
$ <span style="color: #c20cb9; font-weight: bold;">ftp</span> <span style="color: #c20cb9; font-weight: bold;">ftp</span>:<span style="color: #000000; font-weight: bold;">//</span>ftp.pitt.edu<span style="color: #000000; font-weight: bold;">/</span>group<span style="color: #000000; font-weight: bold;">/</span>student-activities<span style="color: #000000; font-weight: bold;">/</span>chess<span style="color: #000000; font-weight: bold;">/</span>PGN<span style="color: #000000; font-weight: bold;">/</span>Collections<span style="color: #000000; font-weight: bold;">/</span>ten-pg.zip .<span style="color: #000000; font-weight: bold;">/</span>
$ <span style="color: #c20cb9; font-weight: bold;">unzip</span> ten-pg.zip
$
$ <span style="color: #c20cb9; font-weight: bold;">wget</span> http:<span style="color: #000000; font-weight: bold;">//</span>www.dhtmlgoodies.com<span style="color: #000000; font-weight: bold;">/</span>scripts<span style="color: #000000; font-weight: bold;">/</span>dhtml-chess<span style="color: #000000; font-weight: bold;">/</span>dhtml-chess.zip
$ <span style="color: #c20cb9; font-weight: bold;">unzip</span> dhtml-chess.zip</pre></div></div>

<p>Now, create a simple script, say <em>parse.php</em>, to run through the chess matches and output them in JSON, one per line:</p>

<div class="wp_syntax"><div class="code"><pre class="php" style="font-family:monospace;"><span style="color: #000000; font-weight: bold;">&lt;?php</span>
&nbsp;
<span style="color: #b1b100;">require</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;PgnParser.class.php&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000088;">$parser</span> <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> PgnParser<span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;/path/to/chess/TEN.PGN&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000088;">$total</span> <span style="color: #339933;">=</span> <span style="color: #000088;">$parser</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">getNumberOfGames</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #b1b100;">for</span> <span style="color: #009900;">&#40;</span><span style="color: #000088;">$i</span><span style="color: #339933;">=</span><span style="color: #cc66cc;">0</span><span style="color: #339933;">;</span> <span style="color: #000088;">$i</span><span style="color: #339933;">&lt;</span><span style="color: #000088;">$total</span><span style="color: #339933;">;</span> <span style="color: #000088;">$i</span><span style="color: #339933;">++</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    <span style="color: #b1b100;">echo</span> <span style="color: #000088;">$parser</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">getGameDetailsAsJson</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$i</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">.</span><span style="color: #0000ff;">&quot;<span style="color: #000099; font-weight: bold;">\n</span>&quot;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">?&gt;</span></pre></div></div>

<p>Run <em>parse.php</em> and dump the results into a file:</p>

<div class="wp_syntax"><div class="code"><pre class="bash" style="font-family:monospace;">$ php parse.php <span style="color: #000000; font-weight: bold;">&gt;</span> games.json</pre></div></div>

<p>Now you&#8217;re ready to import <em>games.json</em>.</p>
<p><a href="http://www.snailinaturtleneck.com/blog/2012/01/26/hacking-chess-with-the-mongodb-pipeline/">Back to the original &#8220;hacking&#8221; post</a></p>

<div id='reaction_buttons_post1796' class='reaction_buttons'>
<div class="reaction_buttons_tagline">Please let me know what thought of this post, anonymously here or in the comments below:</div><a class='reaction_button reaction_button_Funny_count' href="javascript:reaction_buttons_increment_button_ajax('1796', 'Funny');">Funny&nbsp;<span class='count'>(<span class='count_number'>0</span>)</span></a> <a class='reaction_button reaction_button_Useful_count' href="javascript:reaction_buttons_increment_button_ajax('1796', 'Useful');">Useful&nbsp;<span class='count'>(<span class='count_number'>0</span>)</span></a> <a class='reaction_button reaction_button_Too___short_count' href="javascript:reaction_buttons_increment_button_ajax('1796', 'Too short');">Too short&nbsp;<span class='count'>(<span class='count_number'>0</span>)</span></a> <a class='reaction_button reaction_button_Too___long_count' href="javascript:reaction_buttons_increment_button_ajax('1796', 'Too long');">Too long&nbsp;<span class='count'>(<span class='count_number'>0</span>)</span></a> </div>
<div class="shr-publisher-1796"></div><!-- Start Shareaholic LikeButtonSetBottom --><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><div class='shareaholic-like-buttonset' style='float:none;height:30px;'><a class='shareaholic-googleplusone' data-shr_size='medium' data-shr_count='true' data-shr_href='http%3A%2F%2Fwww.snailinaturtleneck.com%2Fblog%2F2012%2F01%2F27%2Fhacking-chess-data-munging%2F' data-shr_title='Hacking+Chess%3A+Data+Munging'></a></div><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><!-- End Shareaholic LikeButtonSetBottom --><img src="http://feeds.feedburner.com/~r/siat-mongodb/~4/ThA7BKU0qPU" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.snailinaturtleneck.com/blog/2012/01/27/hacking-chess-data-munging/feed/</wfw:commentRss>
		<slash:comments>7</slash:comments>
		<feedburner:origLink>http://www.snailinaturtleneck.com/blog/2012/01/27/hacking-chess-data-munging/</feedburner:origLink></item>
		<item>
		<title>Hacking Chess with the MongoDB Pipeline</title>
		<link>http://feedproxy.google.com/~r/siat-mongodb/~3/7UswGJOI5-I/</link>
		<comments>http://www.snailinaturtleneck.com/blog/2012/01/26/hacking-chess-with-the-mongodb-pipeline/#comments</comments>
		<pubDate>Thu, 26 Jan 2012 13:58:37 +0000</pubDate>
		<dc:creator>Kristina Chodorow</dc:creator>
				<category><![CDATA[MongoDB]]></category>
		<category><![CDATA[aggregation]]></category>
		<category><![CDATA[pipeline]]></category>

		<guid isPermaLink="false">http://www.snailinaturtleneck.com/blog/?p=1711</guid>
		<description><![CDATA[MongoDB&#8217;s new aggegation framework is now available in the nightly build! This post demonstrates some of its capabilities by using it to analyze chess games. Make sure you have a the &#8220;Development Release (Unstable)&#8221; nightly running before trying out the stuff in this post. The aggregation framework will be in 2.1.0, but as of this&#8230;]]></description>
			<content:encoded><![CDATA[<!-- Start Shareaholic LikeButtonSetTop --><!-- End Shareaholic LikeButtonSetTop --><p><img src="http://www.snailinaturtleneck.com/blog/wp-content/uploads/2010/03/spockAndKirk.jpg" alt="" title="spockAndKirk" width="300" height="219" class="alignleft size-full wp-image-374" /></p>
<p>MongoDB&#8217;s new aggegation framework is now available in the nightly build! This post demonstrates some of its capabilities by using it to analyze chess games.</p>
<p><b><em>Make sure you have a the &#8220;<a href="http://www.mongodb.org/downloads">Development Release (Unstable)</a>&#8221; nightly</em></b> running before trying out the stuff in this post. The aggregation framework will be in 2.1.0, but as of this writing it&#8217;s <em>only</em> in the nightly build.</p>
<p>First, we need some chess games to analyze.  Download <a href="http://www.snailinaturtleneck.com/blog/wp-content/uploads/2011/11/games.json">games.json</a>, which contains 1132 games that were won in 10 moves or less (crush their soul and do it quick).</p>
<p>You can use <em>mongoimport</em> to import <em>games.json</em> into MongoDB:</p>

<div class="wp_syntax"><div class="code"><pre class="bash" style="font-family:monospace;">$ mongoimport <span style="color: #660033;">--db</span> chess <span style="color: #660033;">--collection</span> fast_win games.json
connected to: 127.0.0.1
imported <span style="color: #000000;">1132</span> objects</pre></div></div>

<p>We can take a look at our chess games in the Mongo shell:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #339933;">&gt;</span> <span style="color: #003366; font-weight: bold;">use</span> chess
switched to db chess
<span style="color: #339933;">&gt;</span> db.<span style="color: #660066;">fast_win</span>.<span style="color: #660066;">count</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>
<span style="color: #CC0000;">1132</span>
<span style="color: #339933;">&gt;</span> db.<span style="color: #660066;">fast_win</span>.<span style="color: #660066;">findOne</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>
<span style="color: #009900;">&#123;</span>
	<span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> ObjectId<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;4ed3965bf86479436d6f1cd7&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span>
	<span style="color: #3366CC;">&quot;event&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;?&quot;</span><span style="color: #339933;">,</span>
	<span style="color: #3366CC;">&quot;site&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;?&quot;</span><span style="color: #339933;">,</span>
	<span style="color: #3366CC;">&quot;date&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;????.??.??&quot;</span><span style="color: #339933;">,</span>
	<span style="color: #3366CC;">&quot;round&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;?&quot;</span><span style="color: #339933;">,</span>
	<span style="color: #3366CC;">&quot;white&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;Gedult D&quot;</span><span style="color: #339933;">,</span>
	<span style="color: #3366CC;">&quot;black&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;Kohn V&quot;</span><span style="color: #339933;">,</span>
	<span style="color: #3366CC;">&quot;result&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;1-0&quot;</span><span style="color: #339933;">,</span>
	<span style="color: #3366CC;">&quot;eco&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;B33/09&quot;</span><span style="color: #339933;">,</span>
	<span style="color: #3366CC;">&quot;moves&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #3366CC;">&quot;1&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;white&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
				<span style="color: #3366CC;">&quot;move&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;e4&quot;</span>
			<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;black&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
				<span style="color: #3366CC;">&quot;move&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;c5&quot;</span>
			<span style="color: #009900;">&#125;</span>
		<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
		<span style="color: #3366CC;">&quot;2&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;white&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
				<span style="color: #3366CC;">&quot;move&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;Nf3&quot;</span>
			<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;black&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
				<span style="color: #3366CC;">&quot;move&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;Nc6&quot;</span>
			<span style="color: #009900;">&#125;</span>
		<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
                ...
		<span style="color: #3366CC;">&quot;10&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;white&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
				<span style="color: #3366CC;">&quot;move&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;Qa4&quot;</span>
			<span style="color: #009900;">&#125;</span>
		<span style="color: #009900;">&#125;</span>
	<span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>Not exactly the greatest schema, but that&#8217;s how the chess format exporter munged it.  Regardless, now we can use aggregation pipelines to analyze these games.</p>
<p><b><a name="pipeline1">Experiment #1: First Mover Advantage</a></b></p>
<p>White has a slight advantage in chess because you move first (Wikipedia says it&#8217;s a <a href="http://en.wikipedia.org/wiki/First-move_advantage_in_chess">52%-56% chance</a> of winning).  I&#8217;d hypothesize that, in a short game, going first matters even more.</p>
<p>Let&#8217;s find out.</p>
<p>The &#8220;result&#8221; field in these docs is &#8220;1-0&#8243; if white wins and &#8220;0-1&#8243; if black wins.  So, we want to divide our docs into two groups based on the &#8220;result&#8221; field and count how many docs are in each group.  Using the aggregation pipeline, this looks like:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #339933;">&gt;</span> db.<span style="color: #660066;">runCommand</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#123;</span>aggregate <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;fast_win&quot;</span><span style="color: #339933;">,</span> pipeline <span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span>
... <span style="color: #009900;">&#123;</span>
...    $group <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
...        _id <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;$result&quot;</span><span style="color: #339933;">,</span>      <span style="color: #006600; font-style: italic;">// group by 'result' field</span>
...        <span style="color: #660066;">numGames</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$sum <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #009900;">&#125;</span> <span style="color: #006600; font-style: italic;">// add 1 for every document in the group</span>
...    <span style="color: #009900;">&#125;</span>
... <span style="color: #009900;">&#125;</span><span style="color: #009900;">&#93;</span><span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span>
<span style="color: #009900;">&#123;</span>
	<span style="color: #3366CC;">&quot;result&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span>
		<span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;0-1&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;numGames&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">435</span>
		<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
		<span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;1-0&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;numGames&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">697</span>
		<span style="color: #009900;">&#125;</span>
	<span style="color: #009900;">&#93;</span><span style="color: #339933;">,</span>
	<span style="color: #3366CC;">&quot;ok&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>That gives a 62% chance white will win (697 wins/1132 total games).  Pretty good (although, of course, this isn&#8217;t a very large sample set).</p>
<div id="attachment_1717" class="wp-caption alignright" style="width: 260px"><img src="http://www.snailinaturtleneck.com/blog/wp-content/uploads/2011/11/chsbrd.jpg" alt="" title="Chessboard" width="250" height="254" class="size-full wp-image-1717" /><p class="wp-caption-text">In case you're not familiar with it, a reference chessboard with 1-8, a-h marked.</p></div>
<p><b><a name="pipeline2">Experiment #2: Best Starting Move</a></b></p>
<p>Given a starting move, what percent of the time will that move lead to victory?  This probably depends on whether you&#8217;re playing white or black, so we&#8217;ll just focus on white&#8217;s opening move. </p>
<p>First, we&#8217;ll just determine what starting moves white uses with this series of steps:</p>
<ul>
<li><em>project</em> all of white&#8217;s first moves (the <code>moves.1.white.move</code> field)
<li><em>group</em> all docs with the same starting move together
<li>and count how many documents (games) used that move.
</ul>
<p>These steps look like:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #339933;">&gt;</span> db.<span style="color: #660066;">runCommand</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#123;</span>aggregate<span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;fast_win&quot;</span><span style="color: #339933;">,</span> pipeline<span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span>
... <span style="color: #006600; font-style: italic;">// '$project' is used to extract all of white's opening moves</span>
... <span style="color: #009900;">&#123;</span>
...     $project <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
...         <span style="color: #006600; font-style: italic;">// extract moves.1.white.move into a new field, firstMove</span>
...         <span style="color: #660066;">firstMove</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;$moves.1.white.move&quot;</span>
...     <span style="color: #009900;">&#125;</span>
... <span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
... <span style="color: #006600; font-style: italic;">// use '$group' to calculate the number of times each move occurred</span>
... <span style="color: #009900;">&#123;</span>
...     $group <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span> 
...         _id <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;$firstMove&quot;</span><span style="color: #339933;">,</span>
...         <span style="color: #660066;">numGames</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$sum <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #009900;">&#125;</span>
...     <span style="color: #009900;">&#125;</span>
... <span style="color: #009900;">&#125;</span><span style="color: #009900;">&#93;</span><span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span>
<span style="color: #009900;">&#123;</span>
	<span style="color: #3366CC;">&quot;result&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span>
		<span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;d3&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;numGames&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">2</span>
		<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
		<span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;e4&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;numGames&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">696</span>
		<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
		<span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;b4&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;numGames&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">17</span>
		<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
		<span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;g3&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;numGames&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">3</span>
		<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
		<span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;e3&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;numGames&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">2</span>
		<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
		<span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;c4&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;numGames&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">36</span>
		<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
		<span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;b3&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;numGames&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">4</span>
		<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
		<span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;g4&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;numGames&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">11</span>
		<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
		<span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;h4&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;numGames&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span>
		<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
		<span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;Nf3&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;numGames&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">37</span>
		<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
		<span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;f3&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;numGames&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span>
		<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
		<span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;f4&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;numGames&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">25</span>
		<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
		<span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;Nc3&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;numGames&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">14</span>
		<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
		<span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;d4&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;numGames&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">283</span>
		<span style="color: #009900;">&#125;</span>
	<span style="color: #009900;">&#93;</span><span style="color: #339933;">,</span>
	<span style="color: #3366CC;">&quot;ok&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>Now let&#8217;s compare those numbers with whether white won or lost.</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #339933;">&gt;</span> db.<span style="color: #660066;">runCommand</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#123;</span>aggregate<span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;fast_win&quot;</span><span style="color: #339933;">,</span> pipeline<span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span>
... <span style="color: #006600; font-style: italic;">// extract the first move</span>
... <span style="color: #009900;">&#123;</span>
...    $project <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
...        <span style="color: #660066;">firstMove</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;$moves.1.white.move&quot;</span><span style="color: #339933;">,</span>
...        <span style="color: #006600; font-style: italic;">// create a new field, &quot;win&quot;, which is 1 if white won and 0 if black won</span>
...        <span style="color: #660066;">win</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$cond <span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span>
...            <span style="color: #009900;">&#123;</span>$eq <span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span><span style="color: #3366CC;">&quot;$result&quot;</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;1-0&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">1</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">0</span>
...        <span style="color: #009900;">&#93;</span><span style="color: #009900;">&#125;</span>
...    <span style="color: #009900;">&#125;</span>
... <span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
... <span style="color: #006600; font-style: italic;">// group by the move and count up how many winning games used it</span>
... <span style="color: #009900;">&#123;</span>
...     $group <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
...         _id <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;$firstMove&quot;</span><span style="color: #339933;">,</span>
...         <span style="color: #660066;">numGames</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$sum <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
...         <span style="color: #660066;">numWins</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$sum <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;$win&quot;</span><span style="color: #009900;">&#125;</span>
...     <span style="color: #009900;">&#125;</span>
... <span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
... <span style="color: #006600; font-style: italic;">// calculate the percent of games won with this starting move</span>
... <span style="color: #009900;">&#123;</span>
...     $project <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
...         _id <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #339933;">,</span>
...         <span style="color: #660066;">numGames</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #339933;">,</span>
...         <span style="color: #660066;">percentWins</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
...             $multiply <span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span><span style="color: #CC0000;">100</span><span style="color: #339933;">,</span> <span style="color: #009900;">&#123;</span>
...                 $divide <span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span><span style="color: #3366CC;">&quot;$numWins&quot;</span><span style="color: #339933;">,</span><span style="color: #3366CC;">&quot;$numGames&quot;</span><span style="color: #009900;">&#93;</span>
...             <span style="color: #009900;">&#125;</span><span style="color: #009900;">&#93;</span>
...         <span style="color: #009900;">&#125;</span>
...     <span style="color: #009900;">&#125;</span>
... <span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
... <span style="color: #006600; font-style: italic;">// discard moves that were used in less than 10 games (probably not representative) </span>
... <span style="color: #009900;">&#123;</span>
...     $match <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
...         <span style="color: #660066;">numGames</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$gte <span style="color: #339933;">:</span> <span style="color: #CC0000;">10</span><span style="color: #009900;">&#125;</span>
...     <span style="color: #009900;">&#125;</span>
... <span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
... <span style="color: #006600; font-style: italic;">// order from worst to best</span>
... <span style="color: #009900;">&#123;</span>
...     $sort <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
...         <span style="color: #660066;">percentWins</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span>
...     <span style="color: #009900;">&#125;</span>
... <span style="color: #009900;">&#125;</span><span style="color: #009900;">&#93;</span><span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span>
<span style="color: #009900;">&#123;</span>
	<span style="color: #3366CC;">&quot;result&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span>
		<span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;f4&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;numGames&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">25</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;percentWins&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">24</span>
		<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
		<span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;b4&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;numGames&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">17</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;percentWins&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">35.294117647058826</span>
		<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
		<span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;c4&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;numGames&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">36</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;percentWins&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">50</span>
		<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
		<span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;d4&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;numGames&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">283</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;percentWins&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">50.53003533568905</span>
		<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
		<span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;g4&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;numGames&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">11</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;percentWins&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">63.63636363636363</span>
		<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
		<span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;Nf3&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;numGames&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">37</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;percentWins&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">67.56756756756756</span>
		<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
		<span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;e4&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;numGames&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">696</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;percentWins&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">68.24712643678161</span>
		<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
		<span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;Nc3&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;numGames&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">14</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;percentWins&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">78.57142857142857</span>
		<span style="color: #009900;">&#125;</span>
	<span style="color: #009900;">&#93;</span><span style="color: #339933;">,</span>
	<span style="color: #3366CC;">&quot;ok&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>Pawn to e4 seems like the most dependable winner here. Knight to c3 also seems like a good choice (at a nearly 80% win rate), but it was only used in 14 winning games.</p>
<p><b><a name="pipeline3">Experiment #3: Best and Worst Moves for Black</a></b></p>
<p>We basically want to do a similar pipeline to Experiment 2, but for black. At the end, we want to find the best and worst percent.</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #339933;">&gt;</span> db.<span style="color: #660066;">runCommand</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#123;</span>aggregate<span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;fast_win&quot;</span><span style="color: #339933;">,</span> pipeline<span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span>
... <span style="color: #006600; font-style: italic;">// extract the first move</span>
... <span style="color: #009900;">&#123;</span>
...    $project <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
...        <span style="color: #660066;">firstMove</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;$moves.1.black.move&quot;</span><span style="color: #339933;">,</span>
...        <span style="color: #660066;">win</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$cond <span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span>
...            <span style="color: #009900;">&#123;</span>$eq <span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span><span style="color: #3366CC;">&quot;$result&quot;</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;0-1&quot;</span><span style="color: #009900;">&#93;</span><span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">1</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">0</span>
...        <span style="color: #009900;">&#93;</span><span style="color: #009900;">&#125;</span>
...    <span style="color: #009900;">&#125;</span>
... <span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
... <span style="color: #006600; font-style: italic;">// group by the move and count up how many winning games used it</span>
... <span style="color: #009900;">&#123;</span>
...     $group <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
...         _id <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;$firstMove&quot;</span><span style="color: #339933;">,</span>
...         <span style="color: #660066;">numGames</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$sum <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
...         <span style="color: #660066;">numWins</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$sum <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;$win&quot;</span><span style="color: #009900;">&#125;</span>
...     <span style="color: #009900;">&#125;</span>
... <span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
... <span style="color: #006600; font-style: italic;">// calculate the percent of games won with this starting move</span>
... <span style="color: #009900;">&#123;</span>
...     $project <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
...         _id <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #339933;">,</span>
...         <span style="color: #660066;">numGames</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #339933;">,</span>
...         <span style="color: #660066;">percentWins</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
...             $multiply <span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span><span style="color: #CC0000;">100</span><span style="color: #339933;">,</span> <span style="color: #009900;">&#123;</span>
...                 $divide <span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span><span style="color: #3366CC;">&quot;$numWins&quot;</span><span style="color: #339933;">,</span><span style="color: #3366CC;">&quot;$numGames&quot;</span><span style="color: #009900;">&#93;</span>
...             <span style="color: #009900;">&#125;</span><span style="color: #009900;">&#93;</span>
...         <span style="color: #009900;">&#125;</span>
...     <span style="color: #009900;">&#125;</span>
... <span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
... <span style="color: #006600; font-style: italic;">// discard moves that were used in less than 10 games (probably not representative) </span>
... <span style="color: #009900;">&#123;</span>
...     $match <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
...         <span style="color: #660066;">numGames</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$gte <span style="color: #339933;">:</span> <span style="color: #CC0000;">10</span><span style="color: #009900;">&#125;</span>
...     <span style="color: #009900;">&#125;</span>
... <span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
... <span style="color: #006600; font-style: italic;">// sort by % win rate</span>
... <span style="color: #009900;">&#123;</span>
...     $sort <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
...         <span style="color: #660066;">percentWins</span> <span style="color: #339933;">:</span> <span style="color: #339933;">-</span><span style="color: #CC0000;">1</span>
...     <span style="color: #009900;">&#125;</span>
... <span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
... <span style="color: #006600; font-style: italic;">// get the best and worst</span>
... <span style="color: #009900;">&#123;</span>
...     $group <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
...          _id <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #339933;">,</span>
...          <span style="color: #660066;">best</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$first <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;$_id&quot;</span><span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
...          <span style="color: #660066;">worst</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$last <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;$_id&quot;</span><span style="color: #009900;">&#125;</span>
...     <span style="color: #009900;">&#125;</span>
... <span style="color: #009900;">&#125;</span><span style="color: #009900;">&#93;</span><span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span>
<span style="color: #009900;">&#123;</span>
	<span style="color: #3366CC;">&quot;result&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span>
		<span style="color: #009900;">&#123;</span>
			<span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;best&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;Nf6&quot;</span><span style="color: #339933;">,</span>
			<span style="color: #3366CC;">&quot;worst&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;d6&quot;</span>
		<span style="color: #009900;">&#125;</span>
	<span style="color: #009900;">&#93;</span><span style="color: #339933;">,</span>
	<span style="color: #3366CC;">&quot;ok&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>I like this new aggregation functionality because it&#8217;s feels simpler than MapReduce.  You can start with a one-operation pipeline and build it up, step-by-step, seeing exactly what a given operation does to your output.  (And no Javascript required, which is always a plus.)</p>
<p>There&#8217;s lots more documentation on aggregation pipelines in <a href="http://www.mongodb.org/display/DOCS/Aggregation+Framework">the docs</a> and I&#8217;ll be doing a couple more posts on it.</p>

<div id='reaction_buttons_post1711' class='reaction_buttons'>
<div class="reaction_buttons_tagline">Please let me know what thought of this post, anonymously here or in the comments below:</div><a class='reaction_button reaction_button_Funny_count' href="javascript:reaction_buttons_increment_button_ajax('1711', 'Funny');">Funny&nbsp;<span class='count'>(<span class='count_number'>1</span>)</span></a> <a class='reaction_button reaction_button_Useful_count' href="javascript:reaction_buttons_increment_button_ajax('1711', 'Useful');">Useful&nbsp;<span class='count'>(<span class='count_number'>8</span>)</span></a> <a class='reaction_button reaction_button_Too___short_count' href="javascript:reaction_buttons_increment_button_ajax('1711', 'Too short');">Too short&nbsp;<span class='count'>(<span class='count_number'>0</span>)</span></a> <a class='reaction_button reaction_button_Too___long_count' href="javascript:reaction_buttons_increment_button_ajax('1711', 'Too long');">Too long&nbsp;<span class='count'>(<span class='count_number'>0</span>)</span></a> </div>
<div class="shr-publisher-1711"></div><!-- Start Shareaholic LikeButtonSetBottom --><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><div class='shareaholic-like-buttonset' style='float:none;height:30px;'><a class='shareaholic-googleplusone' data-shr_size='medium' data-shr_count='true' data-shr_href='http%3A%2F%2Fwww.snailinaturtleneck.com%2Fblog%2F2012%2F01%2F26%2Fhacking-chess-with-the-mongodb-pipeline%2F' data-shr_title='Hacking+Chess+with+the+MongoDB+Pipeline'></a></div><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><!-- End Shareaholic LikeButtonSetBottom --><img src="http://feeds.feedburner.com/~r/siat-mongodb/~4/7UswGJOI5-I" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.snailinaturtleneck.com/blog/2012/01/26/hacking-chess-with-the-mongodb-pipeline/feed/</wfw:commentRss>
		<slash:comments>9</slash:comments>
		<feedburner:origLink>http://www.snailinaturtleneck.com/blog/2012/01/26/hacking-chess-with-the-mongodb-pipeline/</feedburner:origLink></item>
		<item>
		<title>Replica Set Internals Bootcamp: Part I – Elections</title>
		<link>http://feedproxy.google.com/~r/siat-mongodb/~3/i5kHe-8vMoM/</link>
		<comments>http://www.snailinaturtleneck.com/blog/2012/01/04/replica-set-internals-bootcamp-part-i-elections/#comments</comments>
		<pubDate>Wed, 04 Jan 2012 22:22:47 +0000</pubDate>
		<dc:creator>Kristina Chodorow</dc:creator>
				<category><![CDATA[MongoDB]]></category>
		<category><![CDATA[bootcamp]]></category>
		<category><![CDATA[elections]]></category>
		<category><![CDATA[internals]]></category>
		<category><![CDATA[replica sets]]></category>

		<guid isPermaLink="false">http://www.snailinaturtleneck.com/blog/?p=1752</guid>
		<description><![CDATA[I&#8217;ve been doing replica set &#8220;bootcamps&#8221; for new hires. It&#8217;s mainly focused on applying this to debug replica set issues and being able to talk fluently about what&#8217;s happening, but it occurred to me that you (blog readers) might be interested in it, too. There are 8 subjects I cover in my bootcamp: Elections Creating&#8230;]]></description>
			<content:encoded><![CDATA[<!-- Start Shareaholic LikeButtonSetTop --><!-- End Shareaholic LikeButtonSetTop --><p>I&#8217;ve been doing replica set &#8220;bootcamps&#8221; for new hires. It&#8217;s mainly focused on applying this to debug replica set issues and being able to talk fluently about what&#8217;s happening, but it occurred to me that you (blog readers) might be interested in it, too.  </p>
<p>There are 8 subjects I cover in my bootcamp: </p>
<p><img src="http://www.snailinaturtleneck.com/blog/wp-content/uploads/2012/01/boot-camp-300x203.jpg" alt="" title="boot-camp" width="300" height="203" class="alignright size-medium wp-image-1759" /></p>
<ol>
<li><a href="http://www.snailinaturtleneck.com/blog/?p=1752">Elections</a>
<li><a href="http://www.snailinaturtleneck.com/blog/?p=1767">Creating a set</a>
<li>Reconfiguring
<li>Syncing
<li>Initial Sync
<li>Rollback
<li>Authentication
<li>Debugging
</ol>
<p>I&#8217;m going to do one subject per post, we&#8217;ll see how many I can get through.</p>
<p><em>Prerequisites: I&#8217;m assuming you know what replica sets are and you&#8217;ve configured a set, written data to it, read from a secondary, etc.  You understand the terms primary and secondary.</em>  </p>
<p>The most obvious feature of replica sets is their ability to elect a new primary, so the first thing we&#8217;ll cover is this election process.  </p>
<h3>Replica Set Elections</h3>
<p><img src="http://www.snailinaturtleneck.com/blog/wp-content/uploads/2012/01/heartbeat.gif" alt="" title="heartbeat" width="350" height="247" class="alignright size-full wp-image-1755" /></p>
<p>Let&#8217;s say we have a replica set with 3 members: <em>X</em>, <em>Y</em>, and <em>Z</em>.  Every two seconds, each server sends out a <em>heartbeat request</em> to the other members of the set.  So, if we wait a few seconds, <em>X</em> sends out heartbeats to <em>Y</em> and <em>Z</em>.  They respond with information about their current situation: the state they&#8217;re in (primary/secondary), if they are eligible to become primary, their current clock time, etc.</p>
<p><em>X</em> receives this info and updates its &#8220;map&#8221; of the set: if members have come up or gone down, changed state, and how long the roundtrip took.</p>
<p>At this point, if <em>X</em> map changed, <em>X</em> will check a couple of things: if <em>X</em> is primary and a member went down, it will make sure it can still reach a majority of the set.  If it cannot, it&#8217;ll demote itself to a secondary.</p>
<h4>Demotions</h4>
<p>There is one wrinkle with <em>X</em> demoting itself: in MongoDB, writes default to fire-and-forget.  Thus, if people are doing fire-and-forget writes on the primary and it steps down, they might not realize <em>X</em> is no longer primary and keep sending writes to it. The secondary-formerly-known-as-primary will be like, &#8220;I&#8217;m a secondary, I can&#8217;t write that!&#8221;  But because the writes don&#8217;t get a response on the client, the client wouldn&#8217;t know.  </p>
<p>Technically, we could say, &#8220;well, they should use safe writes if they care,&#8221; but that seems dickish.  So, when a primary is demoted, it also closes all connections to clients so that they will get a socket error when they send the next message.  All of the client libraries know to re-check who is primary if they get an error.  Thus, they&#8217;ll be able to find who the new primary is and not accidentally send an endless stream of writes to a secondary.</p>
<h4>Elections</h4>
<p>Anyway, getting back to the heartbeats: if <em>X</em> is a secondary, it&#8217;ll occasionally check if it should elect itself, even if its map hasn&#8217;t changed.  First, it&#8217;ll do a sanity check: does another member think it&#8217;s primary? Does <b><em>X</em></b> think it&#8217;s already primary? Is <em>X</em> ineligible for election? If it fails any of the basic questions, it&#8217;ll continue puttering along as is.</p>
<p><a href="http://digitaldocsinabox.org/images/WomensSuffrage/ballots.html"><img src="http://www.snailinaturtleneck.com/blog/wp-content/uploads/2012/01/suffragist-casting-ballots-22-300x227.jpg" alt="" title="suffragist casting ballots" width="300" height="227" class="alignleft size-medium wp-image-1756" /></a></p>
<p>If it seems as though a new primary is needed, <em>X</em> will proceed to the first step in election: it sends a message to <em>Y</em> and <em>Z</em>, telling them &#8220;I am considering running for primary, can you advise me on this matter?&#8221;  </p>
<p>When <em>Y</em> and <em>Z</em> get this message, they quickly check their world view.  Do they already know of a primary?  Do they have more recent data than <em>X</em>? Does anyone they know of have more recent data than <em>X</em>?  They run through a huge list of sanity checks and, if everything seems satisfactory, they tentatively reply &#8220;go ahead.&#8221;  If they find a reason that <em>X</em> cannot be elected, they&#8217;ll reply &#8220;stop the election!&#8221;</p>
<p>If <em>X</em> receives any &#8220;stop the election!&#8221; messages, it cancels the election and goes back to life as a secondary.</p>
<p>If everyone says &#8220;go ahead,&#8221; <em>X</em> continues with the second (and final) phase of the election process.</p>
<p>For the second phase, <em>X</em> sends out a second message that is basically, &#8220;I am formally announcing my candidacy.&#8221;  At this point, <em>Y</em> and <em>Z</em> make a final check: do all of the conditions that held true before still hold?  If so, they allow <em>X</em> to take their <em>election lock</em> and send back a vote.  The election lock prevents them from voting for another candidate for 30 seconds.  </p>
<p>If one of the checks doesn&#8217;t pass the second time around (fairly unusual, at least in 2.0), they send back a veto.  If anyone vetos, the election fails. </p>
<p><img src="http://www.snailinaturtleneck.com/blog/wp-content/uploads/2012/01/dog-boot-camp-2.jpg" alt="" title="dog-boot-camp" width="265" height="286" class="alignright size-full wp-image-1760" /></p>
<p>Suppose that <em>Y</em> votes for <em>X</em> and <em>Z</em> <b>vetos</b> <em>X</em>.  At that point, <em>Y</em>&#8216;s election lock is taken, it cannot vote in another election for 30 seconds.  That means that, if <em>Z</em> wants to run for primary, it had better be able to get <em>X</em>&#8216;s vote.  That said, it should be able to if <em>Z</em> is a viable candidate: it&#8217;s not like the members hold grudges (except for <em>Y</em>, for 30 seconds).</p>
<p>If no one vetos <b>and</b> the candidate member receives votes from a majority of the set, the candidate becomes primary.</p>
<h4>Confused?</h4>
<p>Feel free to ask questions in the comments below.  This is a loving, caring bootcamp (as bootcamps go).</p>

<div id='reaction_buttons_post1752' class='reaction_buttons'>
<div class="reaction_buttons_tagline">Please let me know what thought of this post, anonymously here or in the comments below:</div><a class='reaction_button reaction_button_Funny_count' href="javascript:reaction_buttons_increment_button_ajax('1752', 'Funny');">Funny&nbsp;<span class='count'>(<span class='count_number'>0</span>)</span></a> <a class='reaction_button reaction_button_Useful_count' href="javascript:reaction_buttons_increment_button_ajax('1752', 'Useful');">Useful&nbsp;<span class='count'>(<span class='count_number'>8</span>)</span></a> <a class='reaction_button reaction_button_Too___short_count' href="javascript:reaction_buttons_increment_button_ajax('1752', 'Too short');">Too short&nbsp;<span class='count'>(<span class='count_number'>0</span>)</span></a> <a class='reaction_button reaction_button_Too___long_count' href="javascript:reaction_buttons_increment_button_ajax('1752', 'Too long');">Too long&nbsp;<span class='count'>(<span class='count_number'>0</span>)</span></a> </div>
<div class="shr-publisher-1752"></div><!-- Start Shareaholic LikeButtonSetBottom --><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><div class='shareaholic-like-buttonset' style='float:none;height:30px;'><a class='shareaholic-googleplusone' data-shr_size='medium' data-shr_count='true' data-shr_href='http%3A%2F%2Fwww.snailinaturtleneck.com%2Fblog%2F2012%2F01%2F04%2Freplica-set-internals-bootcamp-part-i-elections%2F' data-shr_title='Replica+Set+Internals+Bootcamp%3A+Part+I+-+Elections'></a></div><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><!-- End Shareaholic LikeButtonSetBottom --><img src="http://feeds.feedburner.com/~r/siat-mongodb/~4/i5kHe-8vMoM" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.snailinaturtleneck.com/blog/2012/01/04/replica-set-internals-bootcamp-part-i-elections/feed/</wfw:commentRss>
		<slash:comments>7</slash:comments>
		<feedburner:origLink>http://www.snailinaturtleneck.com/blog/2012/01/04/replica-set-internals-bootcamp-part-i-elections/</feedburner:origLink></item>
		<item>
		<title>Popping Timestamps into ObjectIds</title>
		<link>http://feedproxy.google.com/~r/siat-mongodb/~3/nRKvpu3cYS4/</link>
		<comments>http://www.snailinaturtleneck.com/blog/2011/12/20/querying-for-timestamps-using-objectids/#comments</comments>
		<pubDate>Tue, 20 Dec 2011 22:02:45 +0000</pubDate>
		<dc:creator>Kristina Chodorow</dc:creator>
				<category><![CDATA[MongoDB]]></category>
		<category><![CDATA[ObjectId]]></category>
		<category><![CDATA[querying]]></category>

		<guid isPermaLink="false">http://www.snailinaturtleneck.com/blog/?p=1742</guid>
		<description><![CDATA[ObjectIds contain a timestamp, which tells you when the document was created. Because the _id field is always indexed, that means you have a &#8220;free&#8221; index on your &#8220;created at&#8221; time (unless you have persnickety requirements for creation times, like resolutions of less than a second, synchronization across app servers, etc.). Actually using this index&#8230;]]></description>
			<content:encoded><![CDATA[<!-- Start Shareaholic LikeButtonSetTop --><!-- End Shareaholic LikeButtonSetTop --><p>ObjectIds contain a timestamp, which tells you when the document was created.  Because the <em>_id</em> field is always indexed, that means you have a &#8220;free&#8221; index on your &#8220;created at&#8221; time (unless you have persnickety requirements for creation times, like resolutions of less than a second, synchronization across app servers, etc.).</p>
<p>Actually using this index can seem daunting (how do you use an ObjectId to query for a certain date?) so let&#8217;s run through an example.</p>
<p>First, let&#8217;s insert 100 sample docs, 10 docs/second.</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #339933;">&gt;</span> <span style="color: #000066; font-weight: bold;">for</span> <span style="color: #009900;">&#40;</span>i<span style="color: #339933;">=</span><span style="color: #CC0000;">0</span><span style="color: #339933;">;</span> i<span style="color: #339933;">&lt;</span><span style="color: #CC0000;">10</span><span style="color: #339933;">;</span> i<span style="color: #339933;">++</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span> 
... <span style="color: #000066;">print</span><span style="color: #009900;">&#40;</span>i<span style="color: #339933;">+</span><span style="color: #3366CC;">&quot;: &quot;</span><span style="color: #339933;">+</span>Date.<span style="color: #660066;">now</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> 
... <span style="color: #000066; font-weight: bold;">for</span> <span style="color: #009900;">&#40;</span>j<span style="color: #339933;">=</span><span style="color: #CC0000;">0</span><span style="color: #339933;">;</span> j<span style="color: #339933;">&lt;</span><span style="color: #CC0000;">10</span><span style="color: #339933;">;</span> j<span style="color: #339933;">++</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span> 
...    <span style="color: #660066;">db</span>.<span style="color: #660066;">foo</span>.<span style="color: #660066;">insert</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#123;</span>x<span style="color: #339933;">:</span>i<span style="color: #339933;">,</span>y<span style="color: #339933;">:</span>j<span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> 
... <span style="color: #009900;">&#125;</span> 
... <span style="color: #660066;">sleep</span><span style="color: #009900;">&#40;</span><span style="color: #CC0000;">1000</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> 
... <span style="color: #009900;">&#125;</span>
<span style="color: #CC0000;">0</span><span style="color: #339933;">:</span> <span style="color: #CC0000;">1324417241111</span>
<span style="color: #CC0000;">1</span><span style="color: #339933;">:</span> <span style="color: #CC0000;">1324417242112</span>
<span style="color: #CC0000;">2</span><span style="color: #339933;">:</span> <span style="color: #CC0000;">1324417243112</span>
<span style="color: #CC0000;">3</span><span style="color: #339933;">:</span> <span style="color: #CC0000;">1324417244113</span>
<span style="color: #CC0000;">4</span><span style="color: #339933;">:</span> <span style="color: #CC0000;">1324417245114</span>
<span style="color: #CC0000;">5</span><span style="color: #339933;">:</span> <span style="color: #CC0000;">1324417246115</span>
<span style="color: #CC0000;">6</span><span style="color: #339933;">:</span> <span style="color: #CC0000;">1324417247115</span>
<span style="color: #CC0000;">7</span><span style="color: #339933;">:</span> <span style="color: #CC0000;">1324417248116</span>
<span style="color: #CC0000;">8</span><span style="color: #339933;">:</span> <span style="color: #CC0000;">1324417249117</span>
<span style="color: #CC0000;">9</span><span style="color: #339933;">:</span> <span style="color: #CC0000;">1324417250117</span></pre></div></div>

<p>Let&#8217;s find all entries created after 1324417246115 (when <em>i</em>=5).  </p>
<p>The time is currently in milliseconds (that&#8217;s how JavaScript does dates), so we&#8217;ll have to convert it to seconds:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #339933;">&gt;</span> secs <span style="color: #339933;">=</span> Math.<span style="color: #660066;">floor</span><span style="color: #009900;">&#40;</span><span style="color: #CC0000;">1324417246115</span><span style="color: #339933;">/</span><span style="color: #CC0000;">1000</span><span style="color: #009900;">&#41;</span>
<span style="color: #CC0000;">1324417246</span></pre></div></div>

<p>(Your <code>secs</code> will be different than mine, of course.)  </p>
<p>ObjectIds can be constructed from a 24-character string, each two characters representing a byte (e.g., &#8220;ff&#8221; is 255).  So, we need to convert <code>secs</code> to hexidecimal, which luckily is super-easy in JavaScript:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #339933;">&gt;</span> hexSecs <span style="color: #339933;">=</span> secs.<span style="color: #660066;">toString</span><span style="color: #009900;">&#40;</span><span style="color: #CC0000;">16</span><span style="color: #009900;">&#41;</span>
4ef100de</pre></div></div>

<p>Now, we create an ObjectId from this:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #339933;">&gt;</span> id <span style="color: #339933;">=</span> ObjectId<span style="color: #009900;">&#40;</span>hexSecs<span style="color: #339933;">+</span><span style="color: #3366CC;">&quot;0000000000000000&quot;</span><span style="color: #009900;">&#41;</span>
ObjectId<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;4ef100de0000000000000000&quot;</span><span style="color: #009900;">&#41;</span></pre></div></div>

<p>If you get the wrong number of zeros here, you&#8217;ll get an error message that is, er, hard to miss.</p>
<p>Now, we query for everything created after this timestamp:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #339933;">&gt;</span> db.<span style="color: #660066;">foo</span>.<span style="color: #660066;">find</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#123;</span>_id <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$gt <span style="color: #339933;">:</span> id<span style="color: #009900;">&#125;</span><span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span>
<span style="color: #009900;">&#123;</span> <span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> ObjectId<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;4ef100de7d435c39c3016405&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;x&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">5</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;y&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">0</span> <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#123;</span> <span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> ObjectId<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;4ef100de7d435c39c3016406&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;x&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">5</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;y&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span> <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#123;</span> <span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> ObjectId<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;4ef100de7d435c39c3016407&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;x&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">5</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;y&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">2</span> <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#123;</span> <span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> ObjectId<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;4ef100de7d435c39c3016408&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;x&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">5</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;y&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">3</span> <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#123;</span> <span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> ObjectId<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;4ef100de7d435c39c3016409&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;x&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">5</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;y&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">4</span> <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#123;</span> <span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> ObjectId<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;4ef100de7d435c39c301640a&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;x&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">5</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;y&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">5</span> <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#123;</span> <span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> ObjectId<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;4ef100de7d435c39c301640b&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;x&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">5</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;y&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">6</span> <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#123;</span> <span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> ObjectId<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;4ef100de7d435c39c301640c&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;x&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">5</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;y&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">7</span> <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#123;</span> <span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> ObjectId<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;4ef100de7d435c39c301640d&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;x&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">5</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;y&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">8</span> <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#123;</span> <span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> ObjectId<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;4ef100de7d435c39c301640e&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;x&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">5</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;y&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">9</span> <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#123;</span> <span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> ObjectId<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;4ef100df7d435c39c301640f&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;x&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">6</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;y&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">0</span> <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#123;</span> <span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> ObjectId<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;4ef100df7d435c39c3016410&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;x&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">6</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;y&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span> <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#123;</span> <span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> ObjectId<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;4ef100df7d435c39c3016411&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;x&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">6</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;y&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">2</span> <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#123;</span> <span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> ObjectId<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;4ef100df7d435c39c3016412&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;x&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">6</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;y&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">3</span> <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#123;</span> <span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> ObjectId<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;4ef100df7d435c39c3016413&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;x&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">6</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;y&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">4</span> <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#123;</span> <span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> ObjectId<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;4ef100df7d435c39c3016414&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;x&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">6</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;y&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">5</span> <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#123;</span> <span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> ObjectId<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;4ef100df7d435c39c3016415&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;x&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">6</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;y&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">6</span> <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#123;</span> <span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> ObjectId<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;4ef100df7d435c39c3016416&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;x&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">6</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;y&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">7</span> <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#123;</span> <span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> ObjectId<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;4ef100df7d435c39c3016417&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;x&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">6</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;y&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">8</span> <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#123;</span> <span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> ObjectId<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;4ef100df7d435c39c3016418&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;x&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">6</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;y&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">9</span> <span style="color: #009900;">&#125;</span>
Type <span style="color: #3366CC;">&quot;it&quot;</span> <span style="color: #000066; font-weight: bold;">for</span> more</pre></div></div>

<p>If we look at the <em>explain</em> for the query, you can see that it&#8217;s using the index:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #339933;">&gt;</span> db.<span style="color: #660066;">foo</span>.<span style="color: #660066;">find</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#123;</span>_id<span style="color: #339933;">:</span><span style="color: #009900;">&#123;</span>$gt<span style="color: #339933;">:</span>id<span style="color: #009900;">&#125;</span><span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span>.<span style="color: #660066;">explain</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>
<span style="color: #009900;">&#123;</span>
	<span style="color: #3366CC;">&quot;cursor&quot;</span> <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;BtreeCursor _id_&quot;</span><span style="color: #339933;">,</span>
	<span style="color: #3366CC;">&quot;nscanned&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">50</span><span style="color: #339933;">,</span>
	<span style="color: #3366CC;">&quot;nscannedObjects&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">50</span><span style="color: #339933;">,</span>
	<span style="color: #3366CC;">&quot;n&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">50</span><span style="color: #339933;">,</span>
	<span style="color: #3366CC;">&quot;millis&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">0</span><span style="color: #339933;">,</span>
	<span style="color: #3366CC;">&quot;nYields&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">0</span><span style="color: #339933;">,</span>
	<span style="color: #3366CC;">&quot;nChunkSkips&quot;</span> <span style="color: #339933;">:</span> <span style="color: #CC0000;">0</span><span style="color: #339933;">,</span>
	<span style="color: #3366CC;">&quot;isMultiKey&quot;</span> <span style="color: #339933;">:</span> <span style="color: #003366; font-weight: bold;">false</span><span style="color: #339933;">,</span>
	<span style="color: #3366CC;">&quot;indexOnly&quot;</span> <span style="color: #339933;">:</span> <span style="color: #003366; font-weight: bold;">false</span><span style="color: #339933;">,</span>
	<span style="color: #3366CC;">&quot;indexBounds&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #3366CC;">&quot;_id&quot;</span> <span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span>
			<span style="color: #009900;">&#91;</span>
				ObjectId<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;4ef100de0000000000000000&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span>
				ObjectId<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;ffffffffffffffffffffffff&quot;</span><span style="color: #009900;">&#41;</span>
			<span style="color: #009900;">&#93;</span>
		<span style="color: #009900;">&#93;</span>
	<span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>We&#8217;re not quite done, because we&#8217;re actually not returning what we wanted: we&#8217;re getting all docs <em>greater than or equal to</em> the &#8220;created at&#8221; time, not just greater than.  To fix this, we&#8217;d just need to add 1 to the <code>secs</code> before doing anything else.  Or I can claim that we were querying for documents created after <em>i</em>=4 all along.</p>

<div id='reaction_buttons_post1742' class='reaction_buttons'>
<div class="reaction_buttons_tagline">Please let me know what thought of this post, anonymously here or in the comments below:</div><a class='reaction_button reaction_button_Funny_count' href="javascript:reaction_buttons_increment_button_ajax('1742', 'Funny');">Funny&nbsp;<span class='count'>(<span class='count_number'>0</span>)</span></a> <a class='reaction_button reaction_button_Useful_count' href="javascript:reaction_buttons_increment_button_ajax('1742', 'Useful');">Useful&nbsp;<span class='count'>(<span class='count_number'>2</span>)</span></a> <a class='reaction_button reaction_button_Too___short_count' href="javascript:reaction_buttons_increment_button_ajax('1742', 'Too short');">Too short&nbsp;<span class='count'>(<span class='count_number'>0</span>)</span></a> <a class='reaction_button reaction_button_Too___long_count' href="javascript:reaction_buttons_increment_button_ajax('1742', 'Too long');">Too long&nbsp;<span class='count'>(<span class='count_number'>0</span>)</span></a> </div>
<div class="shr-publisher-1742"></div><!-- Start Shareaholic LikeButtonSetBottom --><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><div class='shareaholic-like-buttonset' style='float:none;height:30px;'><a class='shareaholic-googleplusone' data-shr_size='medium' data-shr_count='true' data-shr_href='http%3A%2F%2Fwww.snailinaturtleneck.com%2Fblog%2F2011%2F12%2F20%2Fquerying-for-timestamps-using-objectids%2F' data-shr_title='Popping+Timestamps+into+ObjectIds'></a></div><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><!-- End Shareaholic LikeButtonSetBottom --><img src="http://feeds.feedburner.com/~r/siat-mongodb/~4/nRKvpu3cYS4" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.snailinaturtleneck.com/blog/2011/12/20/querying-for-timestamps-using-objectids/feed/</wfw:commentRss>
		<slash:comments>4</slash:comments>
		<feedburner:origLink>http://www.snailinaturtleneck.com/blog/2011/12/20/querying-for-timestamps-using-objectids/</feedburner:origLink></item>
		<item>
		<title>SQL to MongoDB: An Updated Mapping</title>
		<link>http://feedproxy.google.com/~r/siat-mongodb/~3/6NrTSqweP7s/</link>
		<comments>http://www.snailinaturtleneck.com/blog/2011/12/09/sql-to-mongodb-an-updated-mapping/#comments</comments>
		<pubDate>Fri, 09 Dec 2011 17:48:54 +0000</pubDate>
		<dc:creator>Kristina Chodorow</dc:creator>
				<category><![CDATA[MongoDB]]></category>
		<category><![CDATA[aggregation]]></category>
		<category><![CDATA[mysql]]></category>
		<category><![CDATA[pipeline]]></category>

		<guid isPermaLink="false">http://www.snailinaturtleneck.com/blog/?p=1694</guid>
		<description><![CDATA[The aggregation pipeline code has finally been merged into the main development branch and is scheduled for release in 2.2. It lets you combine simple operations (like finding the max or min, projecting out fields, taking counts or averages) into a pipeline of operations, making a lot of things that were only possible by using&#8230;]]></description>
			<content:encoded><![CDATA[<!-- Start Shareaholic LikeButtonSetTop --><!-- End Shareaholic LikeButtonSetTop --><div id="attachment_1738" class="wp-caption aligncenter" style="width: 910px"><a href="http://rickosborne.org/download/SQL-to-MongoDB.pdf"><img src="http://www.snailinaturtleneck.com/blog/wp-content/uploads/2011/12/SQL-to-MongoDB2.jpg" alt="" title="SQL-to-MongoDB2" width="900" height="695" class="aligncenter size-full wp-image-1738" /></a><p class="wp-caption-text">Rick Osborne&#039;s original chart.</p></div>
<p>The aggregation pipeline code has finally been merged into the main development branch and is scheduled for release in 2.2.  It lets you combine simple operations (like finding the max or min, projecting out fields, taking counts or averages) into a pipeline of operations, making a lot of things that were only possible by using MapReduce doable with a &#8220;normal&#8221; query.</p>
<p>In celebration of this, I thought I&#8217;d re-do the very popular <a href="http://rickosborne.org/download/SQL-to-MongoDB.pdf">MySQL to MongoDB</a> mapping using the aggregation pipeline, instead of MapReduce.</p>
<p>Here is the original SQL:</p>

<div class="wp_syntax"><div class="code"><pre class="sql" style="font-family:monospace;"><span style="color: #993333; font-weight: bold;">SELECT</span>
  Dim1<span style="color: #66cc66;">,</span> Dim2<span style="color: #66cc66;">,</span>
  <span style="color: #993333; font-weight: bold;">SUM</span><span style="color: #66cc66;">&#40;</span>Measure1<span style="color: #66cc66;">&#41;</span> <span style="color: #993333; font-weight: bold;">AS</span> MSum<span style="color: #66cc66;">,</span>
  <span style="color: #993333; font-weight: bold;">COUNT</span><span style="color: #66cc66;">&#40;</span><span style="color: #66cc66;">*</span><span style="color: #66cc66;">&#41;</span> <span style="color: #993333; font-weight: bold;">AS</span> RecordCount<span style="color: #66cc66;">,</span>
  AVG<span style="color: #66cc66;">&#40;</span>Measure2<span style="color: #66cc66;">&#41;</span> <span style="color: #993333; font-weight: bold;">AS</span> MAvg<span style="color: #66cc66;">,</span>
  <span style="color: #993333; font-weight: bold;">MIN</span><span style="color: #66cc66;">&#40;</span>Measure1<span style="color: #66cc66;">&#41;</span> <span style="color: #993333; font-weight: bold;">AS</span> MMin
  <span style="color: #993333; font-weight: bold;">MAX</span><span style="color: #66cc66;">&#40;</span><span style="color: #993333; font-weight: bold;">CASE</span>
    <span style="color: #993333; font-weight: bold;">WHEN</span> Measure2 <span style="color: #66cc66;">&lt;</span> <span style="color: #cc66cc;">100</span>
    <span style="color: #993333; font-weight: bold;">THEN</span> Measure2
  <span style="color: #993333; font-weight: bold;">END</span><span style="color: #66cc66;">&#41;</span> <span style="color: #993333; font-weight: bold;">AS</span> MMax
<span style="color: #993333; font-weight: bold;">FROM</span> DenormAggTable
<span style="color: #993333; font-weight: bold;">WHERE</span> <span style="color: #66cc66;">&#40;</span>Filter1 <span style="color: #993333; font-weight: bold;">IN</span> <span style="color: #66cc66;">&#40;</span>’A’<span style="color: #66cc66;">,</span>’B’<span style="color: #66cc66;">&#41;</span><span style="color: #66cc66;">&#41;</span>
  <span style="color: #993333; font-weight: bold;">AND</span> <span style="color: #66cc66;">&#40;</span>Filter2 <span style="color: #66cc66;">=</span> ‘C’<span style="color: #66cc66;">&#41;</span>
  <span style="color: #993333; font-weight: bold;">AND</span> <span style="color: #66cc66;">&#40;</span>Filter3 <span style="color: #66cc66;">&gt;</span> <span style="color: #cc66cc;">123</span><span style="color: #66cc66;">&#41;</span>
<span style="color: #993333; font-weight: bold;">GROUP</span> <span style="color: #993333; font-weight: bold;">BY</span> Dim1<span style="color: #66cc66;">,</span> Dim2
<span style="color: #993333; font-weight: bold;">HAVING</span> <span style="color: #66cc66;">&#40;</span>MMin <span style="color: #66cc66;">&gt;</span> <span style="color: #cc66cc;">0</span><span style="color: #66cc66;">&#41;</span>
<span style="color: #993333; font-weight: bold;">ORDER</span> <span style="color: #993333; font-weight: bold;">BY</span> RecordCount <span style="color: #993333; font-weight: bold;">DESC</span>
<span style="color: #993333; font-weight: bold;">LIMIT</span> <span style="color: #cc66cc;">4</span><span style="color: #66cc66;">,</span> <span style="color: #cc66cc;">8</span></pre></div></div>

<p>We can break up this statement and replace each piece of SQL with the new aggregation pipeline syntax:</p>
<table>
<tr>
<th>MongoDB Pipeline</th>
<th>MySQL</th>
</tr>
<tr>
<td>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;">aggregate<span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;DenormAggTable&quot;</span></pre></div></div>

</td>
<td>

<div class="wp_syntax"><div class="code"><pre class="sql" style="font-family:monospace;"><span style="color: #993333; font-weight: bold;">FROM</span> DenormAggTable</pre></div></div>

</td>
</tr>
<tr>
<td>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #009900;">&#123;</span>
    $match <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
        Filter1 <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$in <span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span><span style="color: #3366CC;">'A'</span><span style="color: #339933;">,</span><span style="color: #3366CC;">'B'</span><span style="color: #009900;">&#93;</span><span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
        Filter2 <span style="color: #339933;">:</span> <span style="color: #3366CC;">'C'</span><span style="color: #339933;">,</span>
        Filter3 <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$gt <span style="color: #339933;">:</span> <span style="color: #CC0000;">123</span><span style="color: #009900;">&#125;</span>
    <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

</td>
<td>

<div class="wp_syntax"><div class="code"><pre class="sql" style="font-family:monospace;"><span style="color: #993333; font-weight: bold;">WHERE</span> <span style="color: #66cc66;">&#40;</span>Filter1 <span style="color: #993333; font-weight: bold;">IN</span> <span style="color: #66cc66;">&#40;</span>’A’<span style="color: #66cc66;">,</span>’B’<span style="color: #66cc66;">&#41;</span><span style="color: #66cc66;">&#41;</span>
  <span style="color: #993333; font-weight: bold;">AND</span> <span style="color: #66cc66;">&#40;</span>Filter2 <span style="color: #66cc66;">=</span> ‘C’<span style="color: #66cc66;">&#41;</span>
  <span style="color: #993333; font-weight: bold;">AND</span> <span style="color: #66cc66;">&#40;</span>Filter3 <span style="color: #66cc66;">&gt;</span> <span style="color: #cc66cc;">123</span><span style="color: #66cc66;">&#41;</span></pre></div></div>

</td>
</tr>
<tr>
<td>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #009900;">&#123;</span>
    $project <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
        Dim1 <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #339933;">,</span>
        Dim2 <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #339933;">,</span>
        Measure1 <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #339933;">,</span>
        Measure2 <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #339933;">,</span>
        lessThanAHundred <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
            $cond<span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span> 
                <span style="color: #009900;">&#123;</span>$lt<span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span><span style="color: #3366CC;">&quot;$Measure2&quot;</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">100</span><span style="color: #009900;">&#93;</span> <span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
                <span style="color: #3366CC;">&quot;$Measure2&quot;</span><span style="color: #339933;">,</span> <span style="color: #006600; font-style: italic;">// if</span>
                <span style="color: #CC0000;">0</span><span style="color: #009900;">&#93;</span>           <span style="color: #006600; font-style: italic;">// else</span>
        <span style="color: #009900;">&#125;</span>
    <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

</td>
<td>

<div class="wp_syntax"><div class="code"><pre class="sql" style="font-family:monospace;"><span style="color: #993333; font-weight: bold;">CASE</span>
  <span style="color: #993333; font-weight: bold;">WHEN</span> Measure2 <span style="color: #66cc66;">&lt;</span> <span style="color: #cc66cc;">100</span>
  <span style="color: #993333; font-weight: bold;">THEN</span> Measure2
<span style="color: #993333; font-weight: bold;">END</span></pre></div></div>

</td>
</tr>
<tr>
<td>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #009900;">&#123;</span>
    $group <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
        _id <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>Dim1 <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #339933;">,</span> Dim2 <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
        MSum <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$sum <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;$Measure1&quot;</span><span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
        RecordCount <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$sum <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
        MAvg <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$avg <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;$Measure2&quot;</span><span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
        MMin <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$min <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;$Measure1&quot;</span><span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
        MMax <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$max <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;$lessThanAHundred&quot;</span><span style="color: #009900;">&#125;</span>
    <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

</td>
<td>

<div class="wp_syntax"><div class="code"><pre class="sql" style="font-family:monospace;"><span style="color: #993333; font-weight: bold;">SELECT</span>
  Dim1<span style="color: #66cc66;">,</span> Dim2<span style="color: #66cc66;">,</span>
  <span style="color: #993333; font-weight: bold;">SUM</span><span style="color: #66cc66;">&#40;</span>Measure1<span style="color: #66cc66;">&#41;</span> <span style="color: #993333; font-weight: bold;">AS</span> MSum<span style="color: #66cc66;">,</span>
  <span style="color: #993333; font-weight: bold;">COUNT</span><span style="color: #66cc66;">&#40;</span><span style="color: #66cc66;">*</span><span style="color: #66cc66;">&#41;</span> <span style="color: #993333; font-weight: bold;">AS</span> RecordCount<span style="color: #66cc66;">,</span>
  AVG<span style="color: #66cc66;">&#40;</span>Measure2<span style="color: #66cc66;">&#41;</span> <span style="color: #993333; font-weight: bold;">AS</span> MAvg<span style="color: #66cc66;">,</span>
  <span style="color: #993333; font-weight: bold;">MIN</span><span style="color: #66cc66;">&#40;</span>Measure1<span style="color: #66cc66;">&#41;</span> <span style="color: #993333; font-weight: bold;">AS</span> MMin
  <span style="color: #993333; font-weight: bold;">MAX</span><span style="color: #66cc66;">&#40;</span><span style="color: #993333; font-weight: bold;">CASE</span>
    <span style="color: #993333; font-weight: bold;">WHEN</span> Measure2 <span style="color: #66cc66;">&lt;</span> <span style="color: #cc66cc;">100</span>
    <span style="color: #993333; font-weight: bold;">THEN</span> Measure2
  <span style="color: #993333; font-weight: bold;">END</span><span style="color: #66cc66;">&#41;</span> <span style="color: #993333; font-weight: bold;">AS</span> MMax
&nbsp;
<span style="color: #993333; font-weight: bold;">GROUP</span> <span style="color: #993333; font-weight: bold;">BY</span> Dim1<span style="color: #66cc66;">,</span> Dim2</pre></div></div>

</td>
</tr>
<tr>
<td>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #009900;">&#123;</span>
    $match <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>MMin <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$gt <span style="color: #339933;">:</span> <span style="color: #CC0000;">0</span><span style="color: #009900;">&#125;</span><span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

</td>
<td>

<div class="wp_syntax"><div class="code"><pre class="sql" style="font-family:monospace;"><span style="color: #993333; font-weight: bold;">HAVING</span> <span style="color: #66cc66;">&#40;</span>MMin <span style="color: #66cc66;">&gt;</span> <span style="color: #cc66cc;">0</span><span style="color: #66cc66;">&#41;</span></pre></div></div>

</td>
</tr>
<tr>
<td>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #009900;">&#123;</span>
    $sort <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>RecordCount <span style="color: #339933;">:</span> <span style="color: #339933;">-</span><span style="color: #CC0000;">1</span><span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

</td>
<td>

<div class="wp_syntax"><div class="code"><pre class="sql" style="font-family:monospace;"><span style="color: #993333; font-weight: bold;">ORDER</span> <span style="color: #993333; font-weight: bold;">BY</span> RecordCount <span style="color: #993333; font-weight: bold;">DESC</span></pre></div></div>

</td>
</tr>
<tr>
<td>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #009900;">&#123;</span>
    $limit <span style="color: #339933;">:</span> <span style="color: #CC0000;">8</span>
<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
<span style="color: #009900;">&#123;</span>
    $skip <span style="color: #339933;">:</span> <span style="color: #CC0000;">4</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

</td>
<td>

<div class="wp_syntax"><div class="code"><pre class="sql" style="font-family:monospace;"><span style="color: #993333; font-weight: bold;">LIMIT</span> <span style="color: #cc66cc;">4</span><span style="color: #66cc66;">,</span> <span style="color: #cc66cc;">8</span></pre></div></div>

</td>
</tr>
</table>
<p>Putting all of these together gives you your pipeline:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #339933;">&gt;</span> db.<span style="color: #660066;">runCommand</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#123;</span>aggregate<span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;DenormAggTable&quot;</span><span style="color: #339933;">,</span> pipeline<span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span>
<span style="color: #009900;">&#123;</span>
    $match <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
        Filter1 <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$in <span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span><span style="color: #3366CC;">'A'</span><span style="color: #339933;">,</span><span style="color: #3366CC;">'B'</span><span style="color: #009900;">&#93;</span><span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
        Filter2 <span style="color: #339933;">:</span> <span style="color: #3366CC;">'C'</span><span style="color: #339933;">,</span>
        Filter3 <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$gt <span style="color: #339933;">:</span> <span style="color: #CC0000;">123</span><span style="color: #009900;">&#125;</span>
    <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
<span style="color: #009900;">&#123;</span>
    $project <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
        Dim1 <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #339933;">,</span>
        Dim2 <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #339933;">,</span>
        Measure1 <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #339933;">,</span>
        Measure2 <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #339933;">,</span>
        lessThanAHundred <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$cond<span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span><span style="color: #009900;">&#123;</span>$lt<span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span><span style="color: #3366CC;">&quot;$Measure2&quot;</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">100</span><span style="color: #009900;">&#93;</span><span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span> <span style="color: #009900;">&#123;</span>
            <span style="color: #3366CC;">&quot;$Measure2&quot;</span><span style="color: #339933;">,</span>
            <span style="color: #CC0000;">0</span><span style="color: #009900;">&#93;</span>
        <span style="color: #009900;">&#125;</span>
    <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
<span style="color: #009900;">&#123;</span>
    $group <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>
        _id <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>Dim1 <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #339933;">,</span> Dim2 <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
        MSum <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$sum <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;$Measure1&quot;</span><span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
        RecordCount <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$sum <span style="color: #339933;">:</span> <span style="color: #CC0000;">1</span><span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
        MAvg <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$avg <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;$Measure2&quot;</span><span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
        MMin <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$min <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;$Measure1&quot;</span><span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
        MMax <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$max <span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;$lessThanAHundred&quot;</span><span style="color: #009900;">&#125;</span>
    <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
<span style="color: #009900;">&#123;</span>
    $match <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>MMin <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>$gt <span style="color: #339933;">:</span> <span style="color: #CC0000;">0</span><span style="color: #009900;">&#125;</span><span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
<span style="color: #009900;">&#123;</span>
    $sort <span style="color: #339933;">:</span> <span style="color: #009900;">&#123;</span>RecordCount <span style="color: #339933;">:</span> <span style="color: #339933;">-</span><span style="color: #CC0000;">1</span><span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
<span style="color: #009900;">&#123;</span>
    $limit <span style="color: #339933;">:</span> <span style="color: #CC0000;">8</span>
<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
<span style="color: #009900;">&#123;</span>
    $skip <span style="color: #339933;">:</span> <span style="color: #CC0000;">4</span>
<span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#93;</span><span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span></pre></div></div>

<p>As you can see, the SQL matches the pipeline operations pretty clearly.  If you want to play with it, it&#8217;ll be available soon to a the development nightly build.</p>
<p>If you&#8217;re at MongoSV today (December 9th, 2011), check out Chris Westin&#8217;s talk on the new aggregation framework at 3:45 in room B4.</p>

<div id='reaction_buttons_post1694' class='reaction_buttons'>
<div class="reaction_buttons_tagline">Please let me know what thought of this post, anonymously here or in the comments below:</div><a class='reaction_button reaction_button_Funny_count' href="javascript:reaction_buttons_increment_button_ajax('1694', 'Funny');">Funny&nbsp;<span class='count'>(<span class='count_number'>0</span>)</span></a> <a class='reaction_button reaction_button_Useful_count' href="javascript:reaction_buttons_increment_button_ajax('1694', 'Useful');">Useful&nbsp;<span class='count'>(<span class='count_number'>11</span>)</span></a> <a class='reaction_button reaction_button_Too___short_count' href="javascript:reaction_buttons_increment_button_ajax('1694', 'Too short');">Too short&nbsp;<span class='count'>(<span class='count_number'>2</span>)</span></a> <a class='reaction_button reaction_button_Too___long_count' href="javascript:reaction_buttons_increment_button_ajax('1694', 'Too long');">Too long&nbsp;<span class='count'>(<span class='count_number'>2</span>)</span></a> </div>
<div class="shr-publisher-1694"></div><!-- Start Shareaholic LikeButtonSetBottom --><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><div class='shareaholic-like-buttonset' style='float:none;height:30px;'><a class='shareaholic-googleplusone' data-shr_size='medium' data-shr_count='true' data-shr_href='http%3A%2F%2Fwww.snailinaturtleneck.com%2Fblog%2F2011%2F12%2F09%2Fsql-to-mongodb-an-updated-mapping%2F' data-shr_title='SQL+to+MongoDB%3A+An+Updated+Mapping'></a></div><div style="clear: both; min-height: 1px; height: 3px; width: 100%;"></div><!-- End Shareaholic LikeButtonSetBottom --><img src="http://feeds.feedburner.com/~r/siat-mongodb/~4/6NrTSqweP7s" height="1" width="1"/>]]></content:encoded>
			<wfw:commentRss>http://www.snailinaturtleneck.com/blog/2011/12/09/sql-to-mongodb-an-updated-mapping/feed/</wfw:commentRss>
		<slash:comments>4</slash:comments>
		<feedburner:origLink>http://www.snailinaturtleneck.com/blog/2011/12/09/sql-to-mongodb-an-updated-mapping/</feedburner:origLink></item>
	</channel>
</rss><!-- Dynamic page generated in 12.043 seconds. --><!-- Cached page generated by WP-Super-Cache on 2012-05-30 08:08:15 -->

