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

<channel>
	<title>Rails on the Run &#187; RSpec</title>
	<atom:link href="http://railsontherun.com/tag/rspec/feed/" rel="self" type="application/rss+xml" />
	<link>http://railsontherun.com</link>
	<description>Rails experiments by Matt Aimonetti</description>
	<lastBuildDate>Tue, 23 Feb 2010 07:28:00 +0000</lastBuildDate>
	<generator>http://wordpress.org/?v=2.9.2</generator>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<xhtml:meta xmlns:xhtml="http://www.w3.org/1999/xhtml" name="robots" content="noindex" />
		<item>
		<title>db fixtures replacement solution step by step</title>
		<link>http://railsontherun.com/2008/09/07/db-fixtures-replacement-solution-step-by-step/</link>
		<comments>http://railsontherun.com/2008/09/07/db-fixtures-replacement-solution-step-by-step/#comments</comments>
		<pubDate>Sun, 07 Sep 2008 16:06:00 +0000</pubDate>
		<dc:creator>Matt Aimonetti</dc:creator>
				<category><![CDATA[Ruby]]></category>
		<category><![CDATA[datamapper]]></category>
		<category><![CDATA[factory_girl]]></category>
		<category><![CDATA[fixtures]]></category>
		<category><![CDATA[merb]]></category>
		<category><![CDATA[RSpec]]></category>
		<category><![CDATA[spec]]></category>
		<category><![CDATA[testing]]></category>

		<guid isPermaLink="false">http://railsontherun.com/2008/09/07/db-fixtures-replacement-solution-step-by-step</guid>
		<description><![CDATA[Like most people who started with Rails a while back, I first loved Rails fixtures and ended up hating them (slow, a pain to maintain etc&#8230;).
I went through different experiments, trying different existing libs, writing my own solutions etc&#8230; I wasn&#8217;t quite satisfied until I found factory_girl from thoughtbot.
You might not feel the need for [...]]]></description>
			<content:encoded><![CDATA[<p>Like most people who started with Rails a while back, I first loved Rails fixtures and ended up hating them (slow, a pain to maintain etc&#8230;).</p>
<p>I went through different experiments, trying different existing libs, writing my own solutions etc&#8230; I wasn&#8217;t quite satisfied until I found <a href="http://github.com/thoughtbot/factory_girl">factory_girl</a> from <a href="http://www.thoughtbot.com/">thoughtbot</a>.</p>
<p>You might not feel the need for a decent fixtures solution if you do a lot of mocking/stubbing, but I recently came back from my &#8220;mock everything you can outside of models&#8221; approach and I&#8217;m getting closer to the <a href="http://snipr.com/3nwry">mock roles, not objects</a> approach. So, I&#8217;m loosing my model/controller testing separation but I&#8217;m gaining by not having to maintain &#8220;dumb mocks&#8221; which don&#8217;t always represent the real API behind. I mean, how many times did I change a Model, messing up my app but all my specs were still passing. Anyway, that&#8217;s a long discussion, which will be covered by <a href="http://yehudakatz.com/">wycats</a> during <a href="http://merbcamp.com">merbcamp</a></p>
<p>So here is a simple example of how I use <a href="http://github.com/thoughtbot/factory_girl">factory girl</a> in a Merb + DataMapper app. (you can do the same in a Rails app, there is <strong>nothing</strong> specific to Merb in factory_girl).</p>
<ul>
<li>I. create an empty app, set the ORM etc&#8230;</li>
<li>II. git pull and install factory<em>girl from <a href="http://github.com/thoughtbot/factory_girl/tree/master">http://github.com/thoughtbot/factory</a></em><a href="http://github.com/thoughtbot/factory_girl/tree/master">girl/tree/master</a>. Or install thoughtbot-factory_girl gem using <a href="http://gems.github.com">GitHub gem server</a>.</li>
<li><strong>III.</strong> create a spec/factories.rb file. (You might prefer to create a folder called spec/factories and add a factory per model)</li>
<li><strong>IV.</strong> modify spec_helper.rb and add the following</li>
</ul>
<pre class="brush:ruby">
  require 'factory_girl'
  require File.dirname(__FILE__) + '/factories'
</pre>
<ul>
<li>V. write some specs against a Client model</li>
</ul>
<p><script src="http://gist.github.com/9276.js"></script></p>
<ul>
<li><strong>VI.</strong> Create the Model</li>
</ul>
<p><script src="http://gist.github.com/9277.js"></script></p>
<ul>
<li><strong>VII.</strong> create a factory</li>
</ul>
<p><script src="http://gist.github.com/9278.js"></script></p>
<ul>
<li>
<strong>IIX.</strong> run your specs</p>
<p><img src="http://img.skitch.com/20080907-tf8yy6fi82b23t78stqii3mpbe.jpg" alt="failing specs" />
</li>
<li>
<strong>IX.</strong> fix the model (note that I set <code>dependencies "dm-validations"</code> in my init.rb)
</li>
</ul>
<p><script src="http://gist.github.com/9279.js"></script></p>
<ul>
<li>X. run the specs
<p><img src="http://img.skitch.com/20080907-m7p2r6q1qau4k3qsmeadwu2tur.jpg" alt="passing specs" /></li>
<li><strong>XI.</strong> add more specs</li>
</ul>
<p><script src="http://gist.github.com/9264.js"></script></p>
<p>As you can see, Factory.build(:client) only creates a new instance of the Object, while Factory(:client) creates, saves and loads the instance.</p>
<ul>
<li><strong>XII.</strong> get them to pass</li>
</ul>
<p><script src="http://gist.github.com/9265.js"></script></p>
<p>Factory Girl makes fixtures simple and clean. Here is another example for creating associations:</p>
<p><script src="http://gist.github.com/9269.js"></script></p>
<p>Factory Girl also supports sequencing, check out FG <a href="http://github.com/thoughtbot/factory_girl">read me</a></p>
<h2>In conclusion, Factory Girl is a mature and solid factory solution which will take you less than 15 minutes to get used to. It will offer you loads of flexibility and less frustration than good old yaml fixtures. You can also use it with existing fixtures if you want to start using it in an existing app.</h2>
]]></content:encoded>
			<wfw:commentRss>http://railsontherun.com/2008/09/07/db-fixtures-replacement-solution-step-by-step/feed/</wfw:commentRss>
		<slash:comments>4</slash:comments>
		</item>
		<item>
		<title>Misc tips and tricks</title>
		<link>http://railsontherun.com/2008/01/30/misc-tips-and-tricks/</link>
		<comments>http://railsontherun.com/2008/01/30/misc-tips-and-tricks/#comments</comments>
		<pubDate>Wed, 30 Jan 2008 08:00:00 +0000</pubDate>
		<dc:creator>Matt Aimonetti</dc:creator>
				<category><![CDATA[Ruby]]></category>
		<category><![CDATA[autotest]]></category>
		<category><![CDATA[BDD]]></category>
		<category><![CDATA[integration]]></category>
		<category><![CDATA[RSpec]]></category>
		<category><![CDATA[testing]]></category>
		<category><![CDATA[zentest]]></category>

		<guid isPermaLink="false">http://railsontherun.com/2008/01/30/misc-tips-and-tricks</guid>
		<description><![CDATA[I haven&#8217;t posted for quite a long time. The thing is I moved to a new place and I&#8217;m really busy on working clients + setting up my new office + dealing with way too much paperwork. 
Anyway, enough excuses, here are few tips that I believe will be useful to some of you:
ZenTest Autotest
I [...]]]></description>
			<content:encoded><![CDATA[<p>I haven&#8217;t posted for quite a long time. The thing is I moved to a new place and I&#8217;m really busy on working clients + setting up my new office + dealing with way too much paperwork. </p>
<p>Anyway, enough excuses, here are few tips that I believe will be useful to some of you:</p>
<h2><a href="http://www.zenspider.com/ZSS/Products/ZenTest/">ZenTest Autotest</a></h2>
<p>I love autotest, but you might have noticed that sometimes (especially on big projects), ZenTest might start using more CPU than expected. On my machine, that results in the fan going off and annoying the crap out of me.</p>
<p>The solution is quite simple, exclude all folders you don&#8217;t need to monitor. To do that, update ZenTest to version 3.8.X </p>
<pre><code>sudo gem update ZenTest
</code></pre>
<p>(older version had a different syntax)</p>
<p>Now, edit your .autotest that should be located in ~/.autotest  (if it doesn&#8217;t exist, create it).</p>
<p>Finally add the following code:</p>
<table class="CodeRay">
<tr>
<td class="line_numbers" title="click to toggle" onclick="with (this.firstChild.style) { display = (display == '') ? 'none' : '' }">
<pre>1<tt>
</tt>2<tt>
</tt>3<tt>
</tt>4<tt>
</tt></pre>
</td>
<td class="code">
<pre ondblclick="with (this.style) { overflow = (overflow == 'auto' || overflow == '') ? 'visible' : 'auto' }"><tt>
</tt>  <span class="co">Autotest</span>.add_hook <span class="sy">:initialize</span> <span class="r">do</span> |at|<tt>
</tt>    <span class="s"><span class="dl">%w{</span><span class="k">.svn .hg .git vendor</span><span class="dl">}</span></span>.each {|exception| at.add_exception(exception)}<tt>
</tt>  <span class="r">end</span><tt>
</tt></pre>
</td>
</tr>
</table>
<p>I personally freeze rails in vendor and I autotest is way happier when it doesn&#8217;t have to monitor some extra files. (note that we also exclude folders such as .git or .svn)<br />
(you can also include files etc&#8230; read more <a href="http://blog.davidchelimsky.net/articles/2008/01/15/rspec-1-1-2-and-zentest-3-8-0">there</a>)</p>
<h2><a href="http://rspec.info">RSpec</a></h2>
<p>RSpec is certainly my favorite Ruby tool and I&#8217;m glad to say that most of my <a href="http://sdruby.com/">SD.rb</a> friends finally got convinced!</p>
<p>Now, few people complained to me about spec failures outputting the full stack such as:</p>
<table class="CodeRay">
<tr>
<td class="line_numbers" title="click to toggle" onclick="with (this.firstChild.style) { display = (display == '') ? 'none' : '' }">
<pre>1<tt>
</tt>2<tt>
</tt>3<tt>
</tt>4<tt>
</tt><strong>5</strong><tt>
</tt>6<tt>
</tt>7<tt>
</tt>8<tt>
</tt>9<tt>
</tt><strong>10</strong><tt>
</tt>11<tt>
</tt>12<tt>
</tt>13<tt>
</tt>14<tt>
</tt><strong>15</strong><tt>
</tt>16<tt>
</tt>17<tt>
</tt>18<tt>
</tt>19<tt>
</tt><strong>20</strong><tt>
</tt>21<tt>
</tt>22<tt>
</tt>23<tt>
</tt>24<tt>
</tt><strong>25</strong><tt>
</tt>26<tt>
</tt></pre>
</td>
<td class="code">
<pre ondblclick="with (this.style) { overflow = (overflow == 'auto' || overflow == '') ? 'visible' : 'auto' }"><tt>
</tt> <span class="co">The</span> <span class="co">Sessions</span> controller should fail since it<span class="s"><span class="dl">'</span><span class="k">s a test</span><span class="dl">'</span></span> <span class="co">FAILED</span><tt>
</tt> expected <span class="pc">true</span>, got <span class="pc">false</span><tt>
</tt> test_app-git/trunk/vendor/plugins/rspec/lib/spec/expectations.rb:<span class="i">52</span><span class="sy">:in</span> <span class="sh"><span class="dl">`</span><span class="k">fail_with'<tt>
</tt> test_app-git/trunk/vendor/plugins/rspec/lib/spec/expectations/handler.rb:21:in </span><span class="dl">`</span></span>handle_matcher<span class="s"><span class="dl">'</span><span class="k"><tt>
</tt> test_app-git/trunk/vendor/plugins/rspec/lib/spec/expectations/extensions/object.rb:34:in `should</span><span class="dl">'</span></span><tt>
</tt> ./spec/controllers/sessions_controller_spec.rb:<span class="i">25</span>:<tt>
</tt> test_app-git/trunk/vendor/plugins/rspec/lib/spec/example/example_methods.rb:<span class="i">78</span><span class="sy">:in</span> <span class="sh"><span class="dl">`</span><span class="k">instance_eval'<tt>
</tt> test_app-git/trunk/vendor/plugins/rspec/lib/spec/example/example_methods.rb:78:in </span><span class="dl">`</span></span>run_with_description_capturing<span class="s"><span class="dl">'</span><span class="k"><tt>
</tt> test_app-git/trunk/vendor/plugins/rspec/lib/spec/example/example_methods.rb:19:in `execute</span><span class="dl">'</span></span><tt>
</tt> <span class="rx"><span class="dl">/</span><span class="k">opt</span><span class="dl">/</span></span>local/lib/ruby/<span class="fl">1.8</span>/timeout.rb:<span class="i">48</span><span class="sy">:in</span> <span class="sh"><span class="dl">`</span><span class="k">timeout'<tt>
</tt> test_app-git/trunk/vendor/plugins/rspec/lib/spec/example/example_methods.rb:16:in </span><span class="dl">`</span></span>execute<span class="s"><span class="dl">'</span><span class="k"><tt>
</tt> test_app-git/trunk/vendor/plugins/rspec/lib/spec/example/example_group_methods.rb:288:in `execute_examples</span><span class="dl">'</span></span><tt>
</tt> test_app-git/trunk/vendor/plugins/rspec/lib/spec/example/example_group_methods.rb:<span class="i">287</span><span class="sy">:in</span> <span class="sh"><span class="dl">`</span><span class="k">each'<tt>
</tt> test_app-git/trunk/vendor/plugins/rspec/lib/spec/example/example_group_methods.rb:287:in </span><span class="dl">`</span></span>execute_examples<span class="s"><span class="dl">'</span><span class="k"><tt>
</tt> test_app-git/trunk/vendor/plugins/rspec/lib/spec/example/example_group_methods.rb:121:in `run</span><span class="dl">'</span></span><tt>
</tt> test_app-git/trunk/vendor/plugins/rspec/lib/spec/runner/example_group_runner.rb:<span class="i">22</span><span class="sy">:in</span> <span class="sh"><span class="dl">`</span><span class="k">run'<tt>
</tt> test_app-git/trunk/vendor/plugins/rspec/lib/spec/runner/example_group_runner.rb:21:in </span><span class="dl">`</span></span>each<span class="s"><span class="dl">'</span><span class="k"><tt>
</tt> test_app-git/trunk/vendor/plugins/rspec/lib/spec/runner/example_group_runner.rb:21:in `run</span><span class="dl">'</span></span><tt>
</tt> test_app-git/trunk/vendor/plugins/rspec/lib/spec/runner/options.rb:<span class="i">89</span><span class="sy">:in</span> <span class="sh"><span class="dl">`</span><span class="k">run_examples'<tt>
</tt> test_app-git/trunk/vendor/plugins/rspec/lib/spec/runner/command_line.rb:19:in </span><span class="dl">`</span></span>run<span class="s"><span class="dl">'</span><span class="k"><tt>
</tt> script/spec:4:<tt>
</tt><tt>
</tt>  Finished in 6.035147 seconds<tt>
</tt><tt>
</tt>  400 examples, 1 failure<tt>
</tt></span></span></pre>
</td>
</tr>
</table>
<p>We can really easily change that, open you spec.opts file located in your spec folder.</p>
<p>it probably looks like that:</p>
<table class="CodeRay">
<tr>
<td class="line_numbers" title="click to toggle" onclick="with (this.firstChild.style) { display = (display == '') ? 'none' : '' }">
<pre>1<tt>
</tt>2<tt>
</tt>3<tt>
</tt>4<tt>
</tt><strong>5</strong><tt>
</tt>6<tt>
</tt>7<tt>
</tt>8<tt>
</tt></pre>
</td>
<td class="code">
<pre ondblclick="with (this.style) { overflow = (overflow == 'auto' || overflow == '') ? 'visible' : 'auto' }"><tt>
</tt>  --colour<tt>
</tt>  --format<tt>
</tt>  progress<tt>
</tt>  --loadby<tt>
</tt>  mtime<tt>
</tt>  --reverse<tt>
</tt>  --backtrace<tt>
</tt></pre>
</td>
</tr>
</table>
<p>Get rid of &#8220;&#8211;backtrace&#8221; and your new failure should look like:</p>
<table class="CodeRay">
<tr>
<td class="line_numbers" title="click to toggle" onclick="with (this.firstChild.style) { display = (display == '') ? 'none' : '' }">
<pre>1<tt>
</tt>2<tt>
</tt>3<tt>
</tt>4<tt>
</tt><strong>5</strong><tt>
</tt>6<tt>
</tt>7<tt>
</tt>8<tt>
</tt>9<tt>
</tt><strong>10</strong><tt>
</tt>11<tt>
</tt></pre>
</td>
<td class="code">
<pre ondblclick="with (this.style) { overflow = (overflow == 'auto' || overflow == '') ? 'visible' : 'auto' }"><tt>
</tt>  <span class="i">1</span>)<tt>
</tt>  <span class="s"><span class="dl">'</span><span class="k">The Sessions controller The Sessions controller should fail since it</span><span class="dl">'</span></span>s a test<span class="s"><span class="dl">'</span><span class="k"> FAILED<tt>
</tt>  expected false, got true<tt>
</tt>  ./spec/controllers/sessions_controller_spec.rb:25:<tt>
</tt>  script/spec:4:<tt>
</tt><tt>
</tt>  Finished in 0.269956 seconds<tt>
</tt><tt>
</tt>  15 examples, 1 failure<tt>
</tt>  <tt>
</tt></span></span></pre>
</td>
</tr>
</table>
<h2>Other stuff you may find interesting (in no particular order):</h2>
<ul>
<li><a href="http://opensource.thinkrelevance.com/wiki/spec-converter">spec converter</a></li>
<li><a href="http://cells.rubyforge.org/overview.html">Rails Cell</a></li>
<li><a href="http://jointheconversation.org/railsgit">Git to manage and deploy a Rails app</a></li>
<li><a href="http://rufy.com/contacts/doc/">contacts (retrieve user&#8217;s contacts from yahoo, gmail etc..)</a></li>
<li><a href="http://www.hashrocket.com/">Hashrocket</a></li>
<li><a href="http://www.amazon.com/Rails-Way-Addison-Wesley-Professional-Ruby/dp/0321445619">one of the best Rails book of the moment</a></li>
<li><a href="http://famspam.com/">err&#8217;s new baby</a> </li>
<li><a href="http://blog.caboo.se/articles/2008/1/30/caboose-conf-2008">caboose conf 08</a></li>
<li><a href="http://github.com/">git hub</a></li>
<li><a href="http://swxruby.org/">SWX Ruby (or how to get Rails to talk with Flash even faster)</a></li>
<li><a href="http://ruby.reddit.com">Ruby Reddit</a></li>
</ul>
]]></content:encoded>
			<wfw:commentRss>http://railsontherun.com/2008/01/30/misc-tips-and-tricks/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>RSpec on Rails Matchers plugin</title>
		<link>http://railsontherun.com/2008/01/04/rspec-on-rails-matchers-plugin/</link>
		<comments>http://railsontherun.com/2008/01/04/rspec-on-rails-matchers-plugin/#comments</comments>
		<pubDate>Fri, 04 Jan 2008 03:46:00 +0000</pubDate>
		<dc:creator>Matt Aimonetti</dc:creator>
				<category><![CDATA[Ruby]]></category>
		<category><![CDATA[matchers]]></category>
		<category><![CDATA[RSpec]]></category>
		<category><![CDATA[test]]></category>
		<category><![CDATA[testing]]></category>

		<guid isPermaLink="false">http://railsontherun.com/2008/01/04/rspec-on-rails-matchers-plugin</guid>
		<description><![CDATA[RSpec is an awesome testing framework. On top of being the first Ruby BDD framework the core team is doing a great job in enhancing our testing experience and therefore the quality of our code.
This time, I don&#8217;t want to introduce to the latest changes but instead showing you what Josh Knowles, Bryan Helmkamp and [...]]]></description>
			<content:encoded><![CDATA[<p><a href="http://rspec.info">RSpec</a> is an awesome testing framework. On top of being the first Ruby <a href="http://en.wikipedia.org/wiki/Behavior_driven_development">BDD</a> framework the core team is doing a great job in enhancing our testing experience and therefore the quality of our code.</p>
<p>This time, I don&#8217;t want to introduce to the <a href="http://rspec.info/changes.html">latest changes</a> but instead showing you what <a href="http://joshknowles.com">Josh Knowles</a>, <a href="http://www.brynary.com/">Bryan Helmkamp</a> and myself came up with.</p>
<p><a href="http://code.google.com/p/rspec-on-rails-matchers/">RSpec on Rails matchers plugin</a> + <a href="http://rspec-on-rails-matchers.googlecode.com/svn/textmate-bundle/RSpecOnRailsMatchers.tmbundle.zip">TextMate Bundle</a></p>
<p>Matchers are some sort of helpers that will help you cleaning up your tests. We simply came up with a collection of matchers that we think will make your like easier.</p>
<p>We divided the matchers in 3 categories:</p>
<h2>Associations</h2>
<p>Verify that the association has been defined. (doesn&#8217;t verify that the association works!)</p>
<p><em>Usage examples:</em></p>
<table class="CodeRay">
<tr>
<td class="line_numbers" title="click to toggle" onclick="with (this.firstChild.style) { display = (display == '') ? 'none' : '' }">
<pre>1<tt>
</tt>2<tt>
</tt>3<tt>
</tt>4<tt>
</tt><strong>5</strong><tt>
</tt>6<tt>
</tt>7<tt>
</tt>8<tt>
</tt></pre>
</td>
<td class="code">
<pre ondblclick="with (this.style) { overflow = (overflow == 'auto' || overflow == '') ? 'visible' : 'auto' }"><tt>
</tt>    <span class="iv">@post</span>.should have_many(<span class="sy">:comments</span>)<tt>
</tt>  <tt>
</tt>    <span class="iv">@comment</span>.should belong_to(<span class="sy">:post</span>)<tt>
</tt>  <tt>
</tt>    <span class="iv">@user</span>.should have_one(<span class="sy">:social_security_number</span>)<tt>
</tt>  <tt>
</tt>    <span class="iv">@project</span>.should have_and_belong_to_many(<span class="sy">:categories</span>)<tt>
</tt></pre>
</td>
</tr>
</table>
<h2>Validations</h2>
<p>Verify that a validation has been defined. (doesn&#8217;t test the validation itself)</p>
<table class="CodeRay">
<tr>
<td class="line_numbers" title="click to toggle" onclick="with (this.firstChild.style) { display = (display == '') ? 'none' : '' }">
<pre>1<tt>
</tt>2<tt>
</tt>3<tt>
</tt>4<tt>
</tt><strong>5</strong><tt>
</tt>6<tt>
</tt>7<tt>
</tt>8<tt>
</tt>9<tt>
</tt><strong>10</strong><tt>
</tt></pre>
</td>
<td class="code">
<pre ondblclick="with (this.style) { overflow = (overflow == 'auto' || overflow == '') ? 'visible' : 'auto' }"><tt>
</tt>    object.should validate_presence_of(<span class="sy">:attribute</span>)<tt>
</tt><tt>
</tt>    object.should validate_confirmation_of(<span class="sy">:attribute</span>)<tt>
</tt><tt>
</tt>    object.should validate_uniqueness_of(<span class="sy">:attribute</span>)<tt>
</tt><tt>
</tt>    object.should validate_length_of(<span class="sy">:attribute</span>, <span class="sy">:between</span> =&gt; <span class="i">5</span>..<span class="i">10</span>)<tt>
</tt>    <tt>
</tt>    object.should validate_length_of(<span class="sy">:attribute</span>, <span class="sy">:is</span> =&gt; <span class="i">5</span>)<tt>
</tt></pre>
</td>
</tr>
</table>
<h2>Views</h2>
<p>My personal favorite matchers, you can now do stuff like:</p>
<table class="CodeRay">
<tr>
<td class="line_numbers" title="click to toggle" onclick="with (this.firstChild.style) { display = (display == '') ? 'none' : '' }">
<pre>1<tt>
</tt>2<tt>
</tt>3<tt>
</tt>4<tt>
</tt><strong>5</strong><tt>
</tt>6<tt>
</tt>7<tt>
</tt>8<tt>
</tt>9<tt>
</tt><strong>10</strong><tt>
</tt>11<tt>
</tt>12<tt>
</tt></pre>
</td>
<td class="code">
<pre ondblclick="with (this.style) { overflow = (overflow == 'auto' || overflow == '') ? 'visible' : 'auto' }"><tt>
</tt>    it <span class="s"><span class="dl">&quot;</span><span class="k">should render new form</span><span class="dl">&quot;</span></span> <span class="r">do</span><tt>
</tt>        render <span class="s"><span class="dl">&quot;</span><span class="k">/users/new.html.erb</span><span class="dl">&quot;</span></span><tt>
</tt><tt>
</tt>        response.should have_form_posting_to(users_path) <span class="r">do</span><tt>
</tt>          with_text_field_for(<span class="sy">:user_name</span>)<tt>
</tt>          with_text_area_for(<span class="sy">:user_address</span>)<tt>
</tt>          with_text_field_for(<span class="sy">:user_login</span>)<tt>
</tt>          with_text_field_for(<span class="sy">:user_email</span>)<tt>
</tt>          with_submit_button<tt>
</tt>        <span class="r">end</span><tt>
</tt>    <span class="r">end</span><tt>
</tt></pre>
</td>
</tr>
</table>
<p>Check the <a href="http://rspec-on-rails-matchers.googlecode.com/svn/trunk/README">readme</a> for more information and details on the added matchers. I personally recommend you try the <a href="http://rspec-on-rails-matchers.googlecode.com/svn/textmate-bundle/RSpecOnRailsMatchers.tmbundle.zip">TextMate Bundle</a> on top of being a perfect tool for lazy devs, it also lists all the available matchers and is an excellent way of learning.</p>
<p>We just released our first release yesterday, this is not a final version and we will keep on improving the code. If you have suggestions and patches feel free to open a ticket <a href="http://code.google.com/p/rspec-on-rails-matchers/issues/lis">there</a>.</p>
]]></content:encoded>
			<wfw:commentRss>http://railsontherun.com/2008/01/04/rspec-on-rails-matchers-plugin/feed/</wfw:commentRss>
		<slash:comments>4</slash:comments>
		</item>
		<item>
		<title>Sexy Chart &#8211; The video</title>
		<link>http://railsontherun.com/2007/11/20/sexy-chart-the-video/</link>
		<comments>http://railsontherun.com/2007/11/20/sexy-chart-the-video/#comments</comments>
		<pubDate>Tue, 20 Nov 2007 04:46:00 +0000</pubDate>
		<dc:creator>Matt Aimonetti</dc:creator>
				<category><![CDATA[Ruby]]></category>
		<category><![CDATA[amcharts]]></category>
		<category><![CDATA[BDD]]></category>
		<category><![CDATA[charts]]></category>
		<category><![CDATA[podcast]]></category>
		<category><![CDATA[rails]]></category>
		<category><![CDATA[RSpec]]></category>
		<category><![CDATA[san diego]]></category>
		<category><![CDATA[sdruby]]></category>
		<category><![CDATA[video]]></category>

		<guid isPermaLink="false">http://railsontherun.com/2007/11/20/sexy-chart-the-video</guid>
		<description><![CDATA[A bit more than a month ago I posted a tutorial on how to use Flash with Rails to create some awesome/sexy graphs.

Since a lot of people seemed interested by the topic, the SDRuby guys asked me to do a intro talk on how to create Sexy Charts with super sexy Rails.
In the mean time, [...]]]></description>
			<content:encoded><![CDATA[<p>A bit more than a month ago I posted a <a href="http://railsontherun.com/2007/10/4/sexy-charts-in-less-than-5-minutes">tutorial</a> on how to use Flash with Rails to <a href="http://railsontherun.com/2007/10/4/sexy-charts-in-less-than-5-minutes">create some awesome/sexy graphs</a>.</p>
<p><img src="http://content.screencast.com/media/e0605640-1100-43dc-90f9-d8c2083c0f7c_74569570-772f-4886-b2ea-f305d1ede3aa_static_0_0_00000016.png" alt="chart"/></p>
<p>Since a lot of people seemed interested by the topic, the <a href="http://sdruby.com/">SDRuby</a> guys asked me to do a intro talk on how to create Sexy Charts with super sexy Rails.</p>
<p>In the mean time, a lot of people were asking for a example app to look at. People knowing me know that I&#8217;m quite lazy and I don&#8217;t like repeating tasks. I therefore decided to kill 2 birds with one stone and wrote a demo app that I would use during my <a href="http://podcast.sdruby.com/2007/11/13/episode-037-sexy-charts">presentation</a></p>
<p>As I was writing the demo app, I quickly realized that my talk would be even sexier if I would show some best practices. After all, an introduction talk is meant to help newbies learning the tricks that will change them in ninjas! </p>
<p>Sexy charts are sexy now, but in 15 years they might not look so sexy anymore. However <a href="http://en.wikipedia.org/wiki/Behavior_driven_development">BDD</a> is super hot now and will always be sexy! (even though we&#8217;ll probably adopt other even hotter approaches).</p>
<p>Based on the circumstances I decided that Sexy charts would become an excuse to show people how to do BDD using <a href="http://rspec.rubyforge.org">RSpec</a> and how to test a XML view  as described in <a href="http://railsontherun.com/2007/10/31/how-to-test-a-xml-builder-view">this previous post</a></p>
<p>During my presentation I totally forgot to show people what what kind of XML we were trying to feed amCharts, so here is the file:</p>
<p><a href="http://pastie.caboo.se/120055">http://pastie.caboo.se/120055</a></p>
<p>The code used in the presentation is also available <a href="http://railsontherun.com/assets/sexy_charts.zip">here</a></p>
<p>Presentation available <a href="http://podcast.sdruby.com/2007/11/13/episode-037-sexy-charts">here</a> (the sound is a bit saturated, sorry about that. Note that we made the video big enough so you can follow with the code if you don&#8217;t understand my accent <img src='http://railsontherun.com/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' />  )</p>
<p>Feel free to watch the other <a href="http://podcast.sdruby.com/">SDRuby podcasts</a> or even better, <a href="http://feeds.feedburner.com/sdrbpodcast">subscribe to our feed</a>.</p>
<h2>Next SDRuby meeting will be Thursday, December 6 @ 7:30pm</h2>
<p>Location: <a href="http://tinyurl.com/2f486e">UCSD CS Building</a></p>
<p>We&#8217;ll be talking about <a href="http://groups.google.com/group/sdruby/browse_thread/thread/d488b70d67f84a5f#">Unobtrusive Javascript</a>, the <a href="http://groups.google.com/group/sdruby/browse_thread/thread/d488b70d67f84a5f#">Facebook API</a>, and hosting our first Rails Roundtable.</p>
<h2>Newbies and experts welcome!</h2>
]]></content:encoded>
			<wfw:commentRss>http://railsontherun.com/2007/11/20/sexy-chart-the-video/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>How to test a XML builder view</title>
		<link>http://railsontherun.com/2007/10/31/how-to-test-a-xml-builder-view/</link>
		<comments>http://railsontherun.com/2007/10/31/how-to-test-a-xml-builder-view/#comments</comments>
		<pubDate>Wed, 31 Oct 2007 08:32:00 +0000</pubDate>
		<dc:creator>Matt Aimonetti</dc:creator>
				<category><![CDATA[Ruby]]></category>
		<category><![CDATA[BDD]]></category>
		<category><![CDATA[hpricot]]></category>
		<category><![CDATA[parser]]></category>
		<category><![CDATA[rails]]></category>
		<category><![CDATA[RSpec]]></category>
		<category><![CDATA[ruby]]></category>
		<category><![CDATA[TDD]]></category>
		<category><![CDATA[test]]></category>
		<category><![CDATA[view]]></category>
		<category><![CDATA[xml builder]]></category>

		<guid isPermaLink="false">http://railsontherun.com/2007/10/31/how-to-test-a-xml-builder-view</guid>
		<description><![CDATA[As a good Rubyist, I do TDD and even BDD. 
Since I&#8217;ve started using RSpec I&#8217;ve started writing tests against my views. RSpec makes things really easy and I&#8217;ve been enjoying testing my views.
I&#8217;m not the only one having fun, check this great post from Mr Planet Argon aka Robby Russel
Recently I was working on [...]]]></description>
			<content:encoded><![CDATA[<p>As a good Rubyist, I do <a href="http://en.wikipedia.org/wiki/Test-driven_development">TDD</a> and even <a href="http://en.wikipedia.org/wiki/Behavior_driven_development">BDD</a>. </p>
<p>Since I&#8217;ve started using <a href="http://rspec.rubyforge.org/">RSpec</a> I&#8217;ve started writing tests against my views. RSpec makes things really easy and I&#8217;ve been enjoying testing my views.</p>
<p>I&#8217;m not the only one having fun, check <a href="http://www.robbyonrails.com/articles/2007/08/02/spec-your-views">this great post</a> from Mr <a href="http://www.planetargon.com/">Planet Argon</a> aka <a href="http://www.robbyonrails.com">Robby Russel</a></p>
<p>Recently I was working on implementing some <a href="http://railsontherun.com/2007/10/4/sexy-charts-in-less-than-5-minutes">Sexy Charts</a> and I was using a XML builder to create an XML view of for a controller. Since I wanted to be a good Rails Ninja and obey the BDD rules, I figured I needed to test my XML view. Making sure that the nodes and the attributes were properly created. Turned out that is wasn&#8217;t too hard, there was many options but none were very well documented so I decided to write this quick tutorial.</p>
<h2>UPDATE 31 Oct 2007: After a comment from <a href="http://joshknowles.com">Josh Knowles</a>, I updated the tests to test with have_tags (built in RSpec) and hpricot.</h2>
<h2>Hpricot</h2>
<p><a href="http://code.whytheluckystiff.net/hpricot/">hpricot</a> is a awesome HTML parser perfect for <a href="http://en.wikipedia.org/wiki/Screen_scraping">screen scraping</a>. But wait, there&#8217;s more to this awesome library, <a href="http://code.whytheluckystiff.net/hpricot/wiki/HpricotXML">hpricot can also parse XML</a>.</p>
<p>If you watched the excellent <a href="http://peepcode.com/products">RSpec peepcasts</a> you probably noticed that <a href="http://topfunky.com/">topfunky</a> aka <a href="http://geoffreygrosenbach.com/">Geoffrey Grosenbach</a> uses hpricot to test a remote API.</p>
<p>In our case, we&#8217;ll use hpricot to test that our generated XML follows our expectations.</p>
<h2>XML Builder + RSpec</h2>
<p>Let&#8217;s write a quick test to make sure our controller uses a XML builder view:</p>
<table class="CodeRay">
<tr>
<td class="line_numbers" title="click to toggle" onclick="with (this.firstChild.style) { display = (display == '') ? 'none' : '' }">
<pre>1<tt>
</tt>2<tt>
</tt>3<tt>
</tt>4<tt>
</tt><strong>5</strong><tt>
</tt>6<tt>
</tt>7<tt>
</tt>8<tt>
</tt>9<tt>
</tt><strong>10</strong><tt>
</tt>11<tt>
</tt>12<tt>
</tt>13<tt>
</tt>14<tt>
</tt><strong>15</strong><tt>
</tt>16<tt>
</tt>17<tt>
</tt></pre>
</td>
<td class="code">
<pre ondblclick="with (this.style) { overflow = (overflow == 'auto' || overflow == '') ? 'visible' : 'auto' }">  describe <span class="co">AveragesController</span>, <span class="s"><span class="dl">&quot;</span><span class="k">handling GET /averages.xml</span><span class="dl">&quot;</span></span> <span class="r">do</span><tt>
</tt><tt>
</tt>    before <span class="r">do</span><tt>
</tt>      <span class="co">Average</span>.stub!(<span class="sy">:find</span>).and_return(<span class="iv">@average</span>)<tt>
</tt>    <span class="r">end</span><tt>
</tt>  <tt>
</tt>    <span class="r">def</span> <span class="fu">do_get</span><tt>
</tt>      <span class="iv">@request</span>.env[<span class="s"><span class="dl">&quot;</span><span class="k">HTTP_ACCEPT</span><span class="dl">&quot;</span></span>] = <span class="s"><span class="dl">&quot;</span><span class="k">application/xml</span><span class="dl">&quot;</span></span><tt>
</tt>      get <span class="sy">:index</span><tt>
</tt>    <span class="r">end</span><tt>
</tt>  <tt>
</tt>    it <span class="s"><span class="dl">&quot;</span><span class="k">should render the action using the XML builder</span><span class="dl">&quot;</span></span> <span class="r">do</span><tt>
</tt>      do_get<tt>
</tt>      response.should render_template(<span class="s"><span class="dl">'</span><span class="k">averages/index.xml.builder</span><span class="dl">'</span></span>)<tt>
</tt>    <span class="r">end</span><tt>
</tt><tt>
</tt>  <span class="r">end</span></pre>
</td>
</tr>
</table>
<p>To make this example pass, we need to modify our rspec generated controller.</p>
<table class="CodeRay">
<tr>
<td class="line_numbers" title="click to toggle" onclick="with (this.firstChild.style) { display = (display == '') ? 'none' : '' }">
<pre>1<tt>
</tt>2<tt>
</tt>3<tt>
</tt>4<tt>
</tt><strong>5</strong><tt>
</tt>6<tt>
</tt>7<tt>
</tt>8<tt>
</tt></pre>
</td>
<td class="code">
<pre ondblclick="with (this.style) { overflow = (overflow == 'auto' || overflow == '') ? 'visible' : 'auto' }">  <span class="r">def</span> <span class="fu">index</span><tt>
</tt>    <span class="iv">@averages</span> = <span class="co">Average</span>.find(<span class="sy">:all</span>)<tt>
</tt>  <tt>
</tt>    respond_to <span class="r">do</span> |format|<tt>
</tt>      format.html <span class="c"># index.html.erb</span><tt>
</tt>      format.xml  { render <span class="sy">:action</span> =&gt; <span class="s"><span class="dl">&quot;</span><span class="k">index.xml.builder</span><span class="dl">&quot;</span></span>, <span class="sy">:layout</span> =&gt; <span class="pc">false</span> }<tt>
</tt>    <span class="r">end</span><tt>
</tt>  <span class="r">end</span></pre>
</td>
</tr>
</table>
<p>(Please note that I&#8217;m using Rails 2.0 and that&#8217;s why I&#8217;m not using a .rxml view)</p>
<p>Here is what our XML file should end up looking like:</p>
<table class="CodeRay">
<tr>
<td class="line_numbers" title="click to toggle" onclick="with (this.firstChild.style) { display = (display == '') ? 'none' : '' }">
<pre>1<tt>
</tt>2<tt>
</tt>3<tt>
</tt>4<tt>
</tt><strong>5</strong><tt>
</tt>6<tt>
</tt>7<tt>
</tt>8<tt>
</tt>9<tt>
</tt><strong>10</strong><tt>
</tt>11<tt>
</tt>12<tt>
</tt>13<tt>
</tt>14<tt>
</tt><strong>15</strong><tt>
</tt>16<tt>
</tt>17<tt>
</tt>18<tt>
</tt>19<tt>
</tt><strong>20</strong><tt>
</tt>21<tt>
</tt>22<tt>
</tt>23<tt>
</tt>24<tt>
</tt><strong>25</strong><tt>
</tt>26<tt>
</tt>27<tt>
</tt>28<tt>
</tt>29<tt>
</tt><strong>30</strong><tt>
</tt>31<tt>
</tt>32<tt>
</tt>33<tt>
</tt>34<tt>
</tt><strong>35</strong><tt>
</tt>36<tt>
</tt>37<tt>
</tt>38<tt>
</tt>39<tt>
</tt><strong>40</strong><tt>
</tt>41<tt>
</tt>42<tt>
</tt>43<tt>
</tt>44<tt>
</tt><strong>45</strong><tt>
</tt>46<tt>
</tt>47<tt>
</tt>48<tt>
</tt>49<tt>
</tt><strong>50</strong><tt>
</tt>51<tt>
</tt>52<tt>
</tt>53<tt>
</tt>54<tt>
</tt></pre>
</td>
<td class="code">
<pre ondblclick="with (this.style) { overflow = (overflow == 'auto' || overflow == '') ? 'visible' : 'auto' }">  &lt;<span class="i">?x</span>ml version=<span class="s"><span class="dl">&quot;</span><span class="k">1.0</span><span class="dl">&quot;</span></span> encoding=<span class="s"><span class="dl">&quot;</span><span class="k">UTF-8</span><span class="dl">&quot;</span></span>?&gt;<tt>
</tt>  &lt;chart&gt;<tt>
</tt>    &lt;series&gt;<tt>
</tt>      &lt;value xid=<span class="s"><span class="dl">&quot;</span><span class="k">0</span><span class="dl">&quot;</span></span>&gt;<span class="co">January</span>&lt;<span class="rx"><span class="dl">/</span><span class="k">value&gt;<tt>
</tt>      &lt;value xid=&quot;1&quot;&gt;February&lt;</span><span class="dl">/</span></span>value&gt;<tt>
</tt>      &lt;value xid=<span class="s"><span class="dl">&quot;</span><span class="k">2</span><span class="dl">&quot;</span></span>&gt;<span class="co">March</span>&lt;<span class="rx"><span class="dl">/</span><span class="k">value&gt;<tt>
</tt>      &lt;value xid=&quot;3&quot;&gt;April&lt;</span><span class="dl">/</span></span>value&gt;<tt>
</tt>      &lt;value xid=<span class="s"><span class="dl">&quot;</span><span class="k">4</span><span class="dl">&quot;</span></span>&gt;<span class="co">May</span>&lt;<span class="rx"><span class="dl">/</span><span class="k">value&gt;<tt>
</tt><tt>
</tt>      &lt;value xid=&quot;5&quot;&gt;June&lt;</span><span class="dl">/</span></span>value&gt;<tt>
</tt>      &lt;value xid=<span class="s"><span class="dl">&quot;</span><span class="k">6</span><span class="dl">&quot;</span></span>&gt;<span class="co">July</span>&lt;<span class="rx"><span class="dl">/</span><span class="k">value&gt;<tt>
</tt>      &lt;value xid=&quot;7&quot;&gt;August&lt;</span><span class="dl">/</span></span>value&gt;<tt>
</tt>      &lt;value xid=<span class="s"><span class="dl">&quot;</span><span class="k">8</span><span class="dl">&quot;</span></span>&gt;<span class="co">September</span>&lt;<span class="rx"><span class="dl">/</span><span class="k">value&gt;<tt>
</tt>      &lt;value xid=&quot;9&quot;&gt;October&lt;</span><span class="dl">/</span></span>value&gt;<tt>
</tt>      &lt;value xid=<span class="s"><span class="dl">&quot;</span><span class="k">10</span><span class="dl">&quot;</span></span>&gt;<span class="co">November</span>&lt;<span class="rx"><span class="dl">/</span><span class="k">value&gt;<tt>
</tt><tt>
</tt>      &lt;value xid=&quot;11&quot;&gt;December&lt;</span><span class="dl">/</span></span>value&gt;<tt>
</tt>    &lt;<span class="rx"><span class="dl">/</span><span class="k">series&gt;<tt>
</tt>    &lt;graphs&gt;<tt>
</tt>      &lt;graph fill_alpha=&quot;50&quot; color=&quot;#FF0000&quot; fill_color=&quot;#CC0000&quot; title=&quot;high&quot;&gt;<tt>
</tt>        &lt;value xid=&quot;0&quot;&gt;65.1&lt;</span><span class="dl">/</span></span>value&gt;<tt>
</tt>        &lt;value xid=<span class="s"><span class="dl">&quot;</span><span class="k">1</span><span class="dl">&quot;</span></span>&gt;<span class="fl">65.7</span>&lt;<span class="rx"><span class="dl">/</span><span class="k">value&gt;<tt>
</tt>        &lt;value xid=&quot;2&quot;&gt;64.9&lt;</span><span class="dl">/</span></span>value&gt;<tt>
</tt><tt>
</tt>        &lt;value xid=<span class="s"><span class="dl">&quot;</span><span class="k">3</span><span class="dl">&quot;</span></span>&gt;<span class="fl">66.7</span>&lt;<span class="rx"><span class="dl">/</span><span class="k">value&gt;<tt>
</tt>        &lt;value xid=&quot;4&quot;&gt;67.1&lt;</span><span class="dl">/</span></span>value&gt;<tt>
</tt>        &lt;value xid=<span class="s"><span class="dl">&quot;</span><span class="k">5</span><span class="dl">&quot;</span></span>&gt;<span class="fl">69.3</span>&lt;<span class="rx"><span class="dl">/</span><span class="k">value&gt;<tt>
</tt>        &lt;value xid=&quot;6&quot;&gt;73.0&lt;</span><span class="dl">/</span></span>value&gt;<tt>
</tt>        &lt;value xid=<span class="s"><span class="dl">&quot;</span><span class="k">7</span><span class="dl">&quot;</span></span>&gt;<span class="fl">74.8</span>&lt;<span class="rx"><span class="dl">/</span><span class="k">value&gt;<tt>
</tt>        &lt;value xid=&quot;8&quot;&gt;75.4&lt;</span><span class="dl">/</span></span>value&gt;<tt>
</tt><tt>
</tt>        &lt;value xid=<span class="s"><span class="dl">&quot;</span><span class="k">9</span><span class="dl">&quot;</span></span>&gt;<span class="fl">73.4</span>&lt;<span class="rx"><span class="dl">/</span><span class="k">value&gt;<tt>
</tt>        &lt;value xid=&quot;10&quot;&gt;68.9&lt;</span><span class="dl">/</span></span>value&gt;<tt>
</tt>        &lt;value xid=<span class="s"><span class="dl">&quot;</span><span class="k">11</span><span class="dl">&quot;</span></span>&gt;<span class="fl">65.3</span>&lt;<span class="rx"><span class="dl">/</span><span class="k">value&gt;<tt>
</tt>      &lt;</span><span class="dl">/</span></span>graph&gt;<tt>
</tt>      &lt;graph fill_alpha=<span class="s"><span class="dl">&quot;</span><span class="k">50</span><span class="dl">&quot;</span></span> color=<span class="s"><span class="dl">&quot;</span><span class="k">#0000CC</span><span class="dl">&quot;</span></span> fill_color=<span class="s"><span class="dl">&quot;</span><span class="k">#0000CC</span><span class="dl">&quot;</span></span> title=<span class="s"><span class="dl">&quot;</span><span class="k">low</span><span class="dl">&quot;</span></span>&gt;<tt>
</tt>        &lt;value xid=<span class="s"><span class="dl">&quot;</span><span class="k">0</span><span class="dl">&quot;</span></span>&gt;<span class="fl">48.9</span>&lt;<span class="rx"><span class="dl">/</span><span class="k">value&gt;<tt>
</tt>        &lt;value xid=&quot;1&quot;&gt;50.7&lt;</span><span class="dl">/</span></span>value&gt;<tt>
</tt><tt>
</tt>        &lt;value xid=<span class="s"><span class="dl">&quot;</span><span class="k">2</span><span class="dl">&quot;</span></span>&gt;<span class="fl">52.9</span>&lt;<span class="rx"><span class="dl">/</span><span class="k">value&gt;<tt>
</tt>        &lt;value xid=&quot;3&quot;&gt;55.6&lt;</span><span class="dl">/</span></span>value&gt;<tt>
</tt>        &lt;value xid=<span class="s"><span class="dl">&quot;</span><span class="k">4</span><span class="dl">&quot;</span></span>&gt;<span class="fl">59.2</span>&lt;<span class="rx"><span class="dl">/</span><span class="k">value&gt;<tt>
</tt>        &lt;value xid=&quot;5&quot;&gt;61.9&lt;</span><span class="dl">/</span></span>value&gt;<tt>
</tt>        &lt;value xid=<span class="s"><span class="dl">&quot;</span><span class="k">6</span><span class="dl">&quot;</span></span>&gt;<span class="fl">65.7</span>&lt;<span class="rx"><span class="dl">/</span><span class="k">value&gt;<tt>
</tt>        &lt;value xid=&quot;7&quot;&gt;67.3&lt;</span><span class="dl">/</span></span>value&gt;<tt>
</tt><tt>
</tt>        &lt;value xid=<span class="s"><span class="dl">&quot;</span><span class="k">8</span><span class="dl">&quot;</span></span>&gt;<span class="fl">65.7</span>&lt;<span class="rx"><span class="dl">/</span><span class="k">value&gt;<tt>
</tt>        &lt;value xid=&quot;9&quot;&gt;61.0&lt;</span><span class="dl">/</span></span>value&gt;<tt>
</tt>        &lt;value xid=<span class="s"><span class="dl">&quot;</span><span class="k">10</span><span class="dl">&quot;</span></span>&gt;<span class="fl">54.0</span>&lt;<span class="rx"><span class="dl">/</span><span class="k">value&gt;<tt>
</tt>        &lt;value xid=&quot;11&quot;&gt;48.7&lt;</span><span class="dl">/</span></span>value&gt;<tt>
</tt>      &lt;<span class="rx"><span class="dl">/</span><span class="k">graph&gt;<tt>
</tt>    &lt;</span><span class="dl">/</span></span>graphs&gt;<tt>
</tt>  &lt;<span class="rx"><span class="dl">/</span><span class="k">chart&gt;<tt>
</tt>  </span></span></pre>
</td>
</tr>
</table>
<p>Let&#8217;s write some tests to make sure our view is ok:</p>
<p>index.xml.builder_spec.rb</p>
<table class="CodeRay">
<tr>
<td class="line_numbers" title="click to toggle" onclick="with (this.firstChild.style) { display = (display == '') ? 'none' : '' }">
<pre>1<tt>
</tt>2<tt>
</tt>3<tt>
</tt>4<tt>
</tt><strong>5</strong><tt>
</tt>6<tt>
</tt>7<tt>
</tt>8<tt>
</tt>9<tt>
</tt><strong>10</strong><tt>
</tt>11<tt>
</tt>12<tt>
</tt>13<tt>
</tt>14<tt>
</tt><strong>15</strong><tt>
</tt>16<tt>
</tt>17<tt>
</tt>18<tt>
</tt>19<tt>
</tt><strong>20</strong><tt>
</tt>21<tt>
</tt>22<tt>
</tt>23<tt>
</tt>24<tt>
</tt><strong>25</strong><tt>
</tt>26<tt>
</tt>27<tt>
</tt>28<tt>
</tt>29<tt>
</tt><strong>30</strong><tt>
</tt>31<tt>
</tt>32<tt>
</tt>33<tt>
</tt>34<tt>
</tt><strong>35</strong><tt>
</tt>36<tt>
</tt>37<tt>
</tt>38<tt>
</tt>39<tt>
</tt><strong>40</strong><tt>
</tt>41<tt>
</tt>42<tt>
</tt>43<tt>
</tt>44<tt>
</tt><strong>45</strong><tt>
</tt>46<tt>
</tt>47<tt>
</tt>48<tt>
</tt>49<tt>
</tt><strong>50</strong><tt>
</tt>51<tt>
</tt>52<tt>
</tt>53<tt>
</tt>54<tt>
</tt><strong>55</strong><tt>
</tt>56<tt>
</tt>57<tt>
</tt>58<tt>
</tt>59<tt>
</tt><strong>60</strong><tt>
</tt>61<tt>
</tt>62<tt>
</tt>63<tt>
</tt>64<tt>
</tt><strong>65</strong><tt>
</tt>66<tt>
</tt>67<tt>
</tt>68<tt>
</tt>69<tt>
</tt><strong>70</strong><tt>
</tt>71<tt>
</tt>72<tt>
</tt>73<tt>
</tt>74<tt>
</tt><strong>75</strong><tt>
</tt>76<tt>
</tt>77<tt>
</tt>78<tt>
</tt>79<tt>
</tt><strong>80</strong><tt>
</tt>81<tt>
</tt></pre>
</td>
<td class="code">
<pre ondblclick="with (this.style) { overflow = (overflow == 'auto' || overflow == '') ? 'visible' : 'auto' }">require <span class="co">File</span>.dirname(<span class="pc">__FILE__</span>) + <span class="s"><span class="dl">'</span><span class="k">/../../spec_helper</span><span class="dl">'</span></span><tt>
</tt>require <span class="s"><span class="dl">'</span><span class="k">hpricot</span><span class="dl">'</span></span><tt>
</tt><tt>
</tt>describe <span class="s"><span class="dl">&quot;</span><span class="k">/averages/index.xml.builder</span><span class="dl">&quot;</span></span> <span class="r">do</span><tt>
</tt>  include <span class="co">AveragesHelper</span><tt>
</tt>  <tt>
</tt>  before <span class="r">do</span><tt>
</tt>    average_1 = mock_model(<span class="co">Average</span>)<tt>
</tt>    average_1.stub!(<span class="sy">:month</span>).and_return(<span class="s"><span class="dl">&quot;</span><span class="k">January</span><span class="dl">&quot;</span></span>)<tt>
</tt>    average_1.stub!(<span class="sy">:high</span>).and_return(<span class="s"><span class="dl">&quot;</span><span class="k">74.5</span><span class="dl">&quot;</span></span>)<tt>
</tt>    average_1.stub!(<span class="sy">:low</span>).and_return(<span class="s"><span class="dl">&quot;</span><span class="k">61.5</span><span class="dl">&quot;</span></span>)<tt>
</tt>    average_2 = mock_model(<span class="co">Average</span>)<tt>
</tt>    average_2.stub!(<span class="sy">:month</span>).and_return(<span class="s"><span class="dl">&quot;</span><span class="k">February</span><span class="dl">&quot;</span></span>)<tt>
</tt>    average_2.stub!(<span class="sy">:high</span>).and_return(<span class="s"><span class="dl">&quot;</span><span class="k">82.5</span><span class="dl">&quot;</span></span>)<tt>
</tt>    average_2.stub!(<span class="sy">:low</span>).and_return(<span class="s"><span class="dl">&quot;</span><span class="k">71.5</span><span class="dl">&quot;</span></span>)<tt>
</tt><tt>
</tt>    assigns[<span class="sy">:averages</span>] = [average_1, average_2]<tt>
</tt>  <span class="r">end</span><tt>
</tt><tt>
</tt>  it <span class="s"><span class="dl">&quot;</span><span class="k">should render the months in the series</span><span class="dl">&quot;</span></span> <span class="r">do</span><tt>
</tt>    render <span class="s"><span class="dl">&quot;</span><span class="k">/averages/index.xml.builder</span><span class="dl">&quot;</span></span><tt>
</tt>    response.should have_tag(<span class="s"><span class="dl">&quot;</span><span class="k">value</span><span class="dl">&quot;</span></span>, <span class="s"><span class="dl">'</span><span class="k">January</span><span class="dl">'</span></span>)<tt>
</tt>    response.should have_tag(<span class="s"><span class="dl">&quot;</span><span class="k">value</span><span class="dl">&quot;</span></span>, <span class="s"><span class="dl">'</span><span class="k">February</span><span class="dl">'</span></span>)<tt>
</tt>    <span class="c"># Same thing but with Hpricot</span><tt>
</tt>    doc = <span class="co">Hpricot</span>.XML(response.body.to_s)<tt>
</tt>    (doc/<span class="sy">:value</span>).first.inner_html.should == <span class="s"><span class="dl">'</span><span class="k">January</span><span class="dl">'</span></span><tt>
</tt>    (doc/<span class="sy">:value</span>)[<span class="i">1</span>].inner_html.should == <span class="s"><span class="dl">'</span><span class="k">February</span><span class="dl">'</span></span><tt>
</tt>  <span class="r">end</span><tt>
</tt>  <tt>
</tt>  it <span class="s"><span class="dl">&quot;</span><span class="k">should set the xid attributes for the series</span><span class="dl">&quot;</span></span> <span class="r">do</span><tt>
</tt>    render <span class="s"><span class="dl">&quot;</span><span class="k">/averages/index.xml.builder</span><span class="dl">&quot;</span></span><tt>
</tt>    response.should have_tag(<span class="s"><span class="dl">&quot;</span><span class="k">value[xid=0]:first-child</span><span class="dl">&quot;</span></span>)<tt>
</tt>    response.should have_tag(<span class="s"><span class="dl">&quot;</span><span class="k">value[xid=1]:last-child</span><span class="dl">&quot;</span></span>)<tt>
</tt>    <span class="c"># Same thing but with Hpricot</span><tt>
</tt>    doc = <span class="co">Hpricot</span>.XML(response.body.to_s)<tt>
</tt>    (doc/<span class="sy">:value</span>).first[<span class="s"><span class="dl">&quot;</span><span class="k">xid</span><span class="dl">&quot;</span></span>].should == <span class="s"><span class="dl">'</span><span class="k">0</span><span class="dl">'</span></span><tt>
</tt>    (doc/<span class="sy">:value</span>).last[<span class="s"><span class="dl">&quot;</span><span class="k">xid</span><span class="dl">&quot;</span></span>].should == <span class="s"><span class="dl">'</span><span class="k">1</span><span class="dl">'</span></span><tt>
</tt>  <span class="r">end</span><tt>
</tt>  <tt>
</tt>  it <span class="s"><span class="dl">&quot;</span><span class="k">should have 2 graphs and they should have a title</span><span class="dl">&quot;</span></span> <span class="r">do</span><tt>
</tt>    render <span class="s"><span class="dl">&quot;</span><span class="k">/averages/index.xml.builder</span><span class="dl">&quot;</span></span><tt>
</tt>    response.should have_tag(<span class="s"><span class="dl">&quot;</span><span class="k">graph[title=high]:first-child</span><span class="dl">&quot;</span></span>)<tt>
</tt>    response.should have_tag(<span class="s"><span class="dl">&quot;</span><span class="k">graph[title=low]:last-child</span><span class="dl">&quot;</span></span>)<tt>
</tt>    <span class="c"># Same thing but with Hpricot</span><tt>
</tt>    doc = <span class="co">Hpricot</span>.XML(response.body.to_s)<tt>
</tt>    (doc/<span class="sy">:graph</span>).size.should == <span class="i">2</span><tt>
</tt>    (doc/<span class="sy">:graph</span>).first[<span class="s"><span class="dl">&quot;</span><span class="k">title</span><span class="dl">&quot;</span></span>].should == <span class="s"><span class="dl">'</span><span class="k">high</span><span class="dl">'</span></span><tt>
</tt>    (doc/<span class="sy">:graph</span>).last[<span class="s"><span class="dl">&quot;</span><span class="k">title</span><span class="dl">&quot;</span></span>].should == <span class="s"><span class="dl">'</span><span class="k">low</span><span class="dl">'</span></span><tt>
</tt>  <span class="r">end</span><tt>
</tt>  <tt>
</tt>  it <span class="s"><span class="dl">&quot;</span><span class="k">should have a color set by graph</span><span class="dl">&quot;</span></span> <span class="r">do</span><tt>
</tt>    render <span class="s"><span class="dl">&quot;</span><span class="k">/averages/index.xml.builder</span><span class="dl">&quot;</span></span><tt>
</tt>    response.should have_tag(<span class="s"><span class="dl">&quot;</span><span class="k">graph[color]:first-child</span><span class="dl">&quot;</span></span>)<tt>
</tt>    response.should have_tag(<span class="s"><span class="dl">&quot;</span><span class="k">graph[color]:last-child</span><span class="dl">&quot;</span></span>)<tt>
</tt>    response.should have_tag(<span class="s"><span class="dl">&quot;</span><span class="k">graph[fill_color]:last-child</span><span class="dl">&quot;</span></span>)<tt>
</tt>    response.should have_tag(<span class="s"><span class="dl">&quot;</span><span class="k">graph[fill_alpha]:last-child</span><span class="dl">&quot;</span></span>)<tt>
</tt>    <span class="c"># Same thing but with Hpricot</span><tt>
</tt>    doc = <span class="co">Hpricot</span>.XML(response.body.to_s)<tt>
</tt>    (doc/<span class="sy">:graph</span>).first[<span class="s"><span class="dl">&quot;</span><span class="k">color</span><span class="dl">&quot;</span></span>].should_not be_nil<tt>
</tt>    (doc/<span class="sy">:graph</span>).last[<span class="s"><span class="dl">&quot;</span><span class="k">color</span><span class="dl">&quot;</span></span>].should_not be_nil<tt>
</tt>    (doc/<span class="sy">:graph</span>).last[<span class="s"><span class="dl">&quot;</span><span class="k">fill_color</span><span class="dl">&quot;</span></span>].should_not be_nil<tt>
</tt>    (doc/<span class="sy">:graph</span>).last[<span class="s"><span class="dl">&quot;</span><span class="k">fill_alpha</span><span class="dl">&quot;</span></span>].should_not be_nil<tt>
</tt>  <span class="r">end</span><tt>
</tt>  <tt>
</tt>  it <span class="s"><span class="dl">&quot;</span><span class="k">should have an xid for each graph value</span><span class="dl">&quot;</span></span> <span class="r">do</span><tt>
</tt>    render <span class="s"><span class="dl">&quot;</span><span class="k">/averages/index.xml.builder</span><span class="dl">&quot;</span></span><tt>
</tt>    response.should have_tag(<span class="s"><span class="dl">&quot;</span><span class="k">graph &gt; value[xid=0]:first-child</span><span class="dl">&quot;</span></span>)<tt>
</tt>    <span class="c"># Same thing but with Hpricot</span><tt>
</tt>    doc = <span class="co">Hpricot</span>.XML(response.body.to_s)<tt>
</tt>    (doc/<span class="sy">:graph</span>/<span class="sy">:value</span>).first[<span class="s"><span class="dl">&quot;</span><span class="k">xid</span><span class="dl">&quot;</span></span>].should == <span class="s"><span class="dl">&quot;</span><span class="k">0</span><span class="dl">&quot;</span></span><tt>
</tt>  <span class="r">end</span><tt>
</tt>  <tt>
</tt>  it <span class="s"><span class="dl">&quot;</span><span class="k">should have the high average as values of the first graph</span><span class="dl">&quot;</span></span> <span class="r">do</span><tt>
</tt>    render <span class="s"><span class="dl">&quot;</span><span class="k">/averages/index.xml.builder</span><span class="dl">&quot;</span></span><tt>
</tt>    response.should have_tag(<span class="s"><span class="dl">&quot;</span><span class="k">graph &gt; value:first-child</span><span class="dl">&quot;</span></span>, <span class="s"><span class="dl">&quot;</span><span class="k">74.5</span><span class="dl">&quot;</span></span>)<tt>
</tt>    <span class="c"># Same thing but with Hpricot</span><tt>
</tt>    doc = <span class="co">Hpricot</span>.XML(response.body.to_s)<tt>
</tt>    (doc/<span class="sy">:graph</span>/<span class="sy">:value</span>).first.inner_html.should == <span class="s"><span class="dl">&quot;</span><span class="k">74.5</span><span class="dl">&quot;</span></span><tt>
</tt>  <span class="r">end</span><tt>
</tt>  <tt>
</tt><span class="r">end</span></pre>
</td>
</tr>
</table>
<p>The first thing you must do (after installing the hpricot gem) is to require hpricot in your test:</p>
<table class="CodeRay">
<tr>
<td class="line_numbers" title="click to toggle" onclick="with (this.firstChild.style) { display = (display == '') ? 'none' : '' }">
<pre><tt>
</tt></pre>
</td>
<td class="code">
<pre ondblclick="with (this.style) { overflow = (overflow == 'auto' || overflow == '') ? 'visible' : 'auto' }">  require <span class="s"><span class="dl">'</span><span class="k">hpricot</span><span class="dl">'</span></span></pre>
</td>
</tr>
</table>
<p>Now that hpricot is created we can use it to parse the response and check against our expectations.</p>
<p>(we create mock objects to pass to the view so we know exactly what to expect and we separate Model/Controller/Views tests)</p>
<p>To check against our response we have to use hpricot parser syntax. It might look at bit funny at first, but believe me it&#8217;s really easy once you get it.</p>
<p>But first, let&#8217;s parse the view:</p>
<table class="CodeRay">
<tr>
<td class="line_numbers" title="click to toggle" onclick="with (this.firstChild.style) { display = (display == '') ? 'none' : '' }">
<pre>1<tt>
</tt>2<tt>
</tt>3<tt>
</tt>4<tt>
</tt></pre>
</td>
<td class="code">
<pre ondblclick="with (this.style) { overflow = (overflow == 'auto' || overflow == '') ? 'visible' : 'auto' }"><span class="c"># Render the mocked up data using the xml view</span><tt>
</tt>render <span class="s"><span class="dl">&quot;</span><span class="k">/averages/index.xml.builder</span><span class="dl">&quot;</span></span><tt>
</tt><span class="c"># Load and parse the view response body:</span><tt>
</tt>doc = <span class="co">Hpricot</span>.XML(response.body.to_s)  </pre>
</td>
</tr>
</table>
<p>Let&#8217;s look at the first test:</p>
<table class="CodeRay">
<tr>
<td class="line_numbers" title="click to toggle" onclick="with (this.firstChild.style) { display = (display == '') ? 'none' : '' }">
<pre>1<tt>
</tt>2<tt>
</tt>3<tt>
</tt>4<tt>
</tt><strong>5</strong><tt>
</tt>6<tt>
</tt></pre>
</td>
<td class="code">
<pre ondblclick="with (this.style) { overflow = (overflow == 'auto' || overflow == '') ? 'visible' : 'auto' }">  it <span class="s"><span class="dl">&quot;</span><span class="k">should render the months in the series</span><span class="dl">&quot;</span></span> <span class="r">do</span><tt>
</tt>    render <span class="s"><span class="dl">&quot;</span><span class="k">/averages/index.xml.builder</span><span class="dl">&quot;</span></span><tt>
</tt>    doc = <span class="co">Hpricot</span>.XML(response.body.to_s)<tt>
</tt>    (doc/<span class="sy">:value</span>).first.inner_html.should == <span class="s"><span class="dl">'</span><span class="k">January</span><span class="dl">'</span></span><tt>
</tt>    (doc/<span class="sy">:value</span>)[<span class="i">1</span>].inner_html.should == <span class="s"><span class="dl">'</span><span class="k">February</span><span class="dl">'</span></span><tt>
</tt>  <span class="r">end</span></pre>
</td>
</tr>
</table>
<p>(doc/:value) returns all the value nodes, we take the first one and extract its content. We expect that it would match the name of the month for the first average.</p>
<p>Let&#8217;s now look at another test:</p>
<table class="CodeRay">
<tr>
<td class="line_numbers" title="click to toggle" onclick="with (this.firstChild.style) { display = (display == '') ? 'none' : '' }">
<pre>1<tt>
</tt>2<tt>
</tt>3<tt>
</tt>4<tt>
</tt><strong>5</strong><tt>
</tt>6<tt>
</tt>7<tt>
</tt></pre>
</td>
<td class="code">
<pre ondblclick="with (this.style) { overflow = (overflow == 'auto' || overflow == '') ? 'visible' : 'auto' }">  it <span class="s"><span class="dl">&quot;</span><span class="k">should have 2 graphs and they should have a title</span><span class="dl">&quot;</span></span> <span class="r">do</span><tt>
</tt>    render <span class="s"><span class="dl">&quot;</span><span class="k">/averages/index.xml.builder</span><span class="dl">&quot;</span></span><tt>
</tt>    doc = <span class="co">Hpricot</span>.XML(response.body.to_s)<tt>
</tt>    (doc/<span class="sy">:graph</span>).size.should == <span class="i">2</span><tt>
</tt>    (doc/<span class="sy">:graph</span>).first[<span class="s"><span class="dl">&quot;</span><span class="k">title</span><span class="dl">&quot;</span></span>].should == <span class="s"><span class="dl">'</span><span class="k">high</span><span class="dl">'</span></span><tt>
</tt>    (doc/<span class="sy">:graph</span>).last[<span class="s"><span class="dl">&quot;</span><span class="k">title</span><span class="dl">&quot;</span></span>].should == <span class="s"><span class="dl">'</span><span class="k">low</span><span class="dl">'</span></span><tt>
</tt>  <span class="r">end</span></pre>
</td>
</tr>
</table>
<p>The thing to look at here is the fact that we are checking on the node&#8217;s attribute &#8220;title&#8221;. Really simple syntax and clean test, isn&#8217;t it?</p>
<p>Finally let&#8217;s look at the last example:</p>
<table class="CodeRay">
<tr>
<td class="line_numbers" title="click to toggle" onclick="with (this.firstChild.style) { display = (display == '') ? 'none' : '' }">
<pre>1<tt>
</tt>2<tt>
</tt>3<tt>
</tt>4<tt>
</tt><strong>5</strong><tt>
</tt></pre>
</td>
<td class="code">
<pre ondblclick="with (this.style) { overflow = (overflow == 'auto' || overflow == '') ? 'visible' : 'auto' }">  it <span class="s"><span class="dl">&quot;</span><span class="k">should have the high average as values of the first graph</span><span class="dl">&quot;</span></span> <span class="r">do</span><tt>
</tt>    render <span class="s"><span class="dl">&quot;</span><span class="k">/averages/index.xml.builder</span><span class="dl">&quot;</span></span><tt>
</tt>    doc = <span class="co">Hpricot</span>.XML(response.body.to_s)<tt>
</tt>    (doc/<span class="sy">:graph</span>/<span class="sy">:value</span>).first.inner_html.should == <span class="s"><span class="dl">&quot;</span><span class="k">74.5</span><span class="dl">&quot;</span></span><tt>
</tt>  <span class="r">end</span></pre>
</td>
</tr>
</table>
<p>We are checking that the content of the first value node nested inside a graph node is equal to 74.5 which is the high average for the first month. </p>
<p>In practice, you probably won&#8217;t write all these tests at once, but anyway, let&#8217;s look at our XML builder which will make all these tests pass:</p>
<table class="CodeRay">
<tr>
<td class="line_numbers" title="click to toggle" onclick="with (this.firstChild.style) { display = (display == '') ? 'none' : '' }">
<pre>1<tt>
</tt>2<tt>
</tt>3<tt>
</tt>4<tt>
</tt><strong>5</strong><tt>
</tt>6<tt>
</tt>7<tt>
</tt>8<tt>
</tt>9<tt>
</tt><strong>10</strong><tt>
</tt>11<tt>
</tt>12<tt>
</tt>13<tt>
</tt>14<tt>
</tt><strong>15</strong><tt>
</tt>16<tt>
</tt>17<tt>
</tt>18<tt>
</tt>19<tt>
</tt><strong>20</strong><tt>
</tt>21<tt>
</tt>22<tt>
</tt>23<tt>
</tt></pre>
</td>
<td class="code">
<pre ondblclick="with (this.style) { overflow = (overflow == 'auto' || overflow == '') ? 'visible' : 'auto' }">xml.instruct! <span class="sy"> <img src='http://railsontherun.com/wp-includes/images/smilies/icon_mad.gif' alt=':x' class='wp-smiley' /> ml</span>, <span class="sy">:version</span>=&gt;<span class="s"><span class="dl">&quot;</span><span class="k">1.0</span><span class="dl">&quot;</span></span>, <span class="sy">:encoding</span>=&gt;<span class="s"><span class="dl">&quot;</span><span class="k">UTF-8</span><span class="dl">&quot;</span></span><tt>
</tt>xml.chart <span class="r">do</span><tt>
</tt>  xml.series <span class="r">do</span>    <tt>
</tt>    <span class="iv">@averages</span>.each_with_index <span class="r">do</span> |average, index|<tt>
</tt>      xml.value average.month, <span class="sy"> <img src='http://railsontherun.com/wp-includes/images/smilies/icon_mad.gif' alt=':x' class='wp-smiley' /> id</span> =&gt; index<tt>
</tt>    <span class="r">end</span><tt>
</tt>  <span class="r">end</span><tt>
</tt>  <tt>
</tt>  xml.graphs <span class="r">do</span><tt>
</tt>    xml.graph <span class="sy">:title</span> =&gt; <span class="s"><span class="dl">'</span><span class="k">high</span><span class="dl">'</span></span>, <span class="sy">:color</span> =&gt; <span class="s"><span class="dl">&quot;</span><span class="k">#FF0000</span><span class="dl">&quot;</span></span>, <span class="sy">:fill_alpha</span> =&gt; <span class="s"><span class="dl">&quot;</span><span class="k">50</span><span class="dl">&quot;</span></span>, <span class="sy">:fill_color</span> =&gt; <span class="s"><span class="dl">&quot;</span><span class="k">#CC0000</span><span class="dl">&quot;</span></span> <span class="r">do</span><tt>
</tt>      <span class="iv">@averages</span>.each_with_index <span class="r">do</span> |average, index|<tt>
</tt>        xml.value average.high, <span class="sy"> <img src='http://railsontherun.com/wp-includes/images/smilies/icon_mad.gif' alt=':x' class='wp-smiley' /> id</span> =&gt; index<tt>
</tt>      <span class="r">end</span><tt>
</tt>    <span class="r">end</span><tt>
</tt>    <tt>
</tt>    xml.graph <span class="sy">:title</span> =&gt; <span class="s"><span class="dl">'</span><span class="k">low</span><span class="dl">'</span></span>, <span class="sy">:color</span> =&gt; <span class="s"><span class="dl">&quot;</span><span class="k">#0000CC</span><span class="dl">&quot;</span></span>, <span class="sy">:fill_alpha</span> =&gt; <span class="s"><span class="dl">&quot;</span><span class="k">50</span><span class="dl">&quot;</span></span>, <span class="sy">:fill_color</span> =&gt; <span class="s"><span class="dl">&quot;</span><span class="k">#0000CC</span><span class="dl">&quot;</span></span> <span class="r">do</span><tt>
</tt>      <span class="iv">@averages</span>.each_with_index <span class="r">do</span> |average, index|<tt>
</tt>        xml.value average.low, <span class="sy"> <img src='http://railsontherun.com/wp-includes/images/smilies/icon_mad.gif' alt=':x' class='wp-smiley' /> id</span> =&gt; index<tt>
</tt>      <span class="r">end</span><tt>
</tt>    <span class="r">end</span><tt>
</tt>  <span class="r">end</span><tt>
</tt>  <tt>
</tt><span class="r">end</span></pre>
</td>
</tr>
</table>
<p>Hpricot is a <em>really</em> nice tool which can make your BDD life much easier. And even if you don&#8217;t do BDD/TDD yet, it&#8217;s a great way to verify that any XML data you receive/generate is valid.</p>
<h2>Happy testing</h2>
]]></content:encoded>
			<wfw:commentRss>http://railsontherun.com/2007/10/31/how-to-test-a-xml-builder-view/feed/</wfw:commentRss>
		<slash:comments>8</slash:comments>
		</item>
		<item>
		<title>Autotest with sound FX</title>
		<link>http://railsontherun.com/2007/08/02/autotest-with-sound-fx/</link>
		<comments>http://railsontherun.com/2007/08/02/autotest-with-sound-fx/#comments</comments>
		<pubDate>Thu, 02 Aug 2007 08:07:00 +0000</pubDate>
		<dc:creator>Matt Aimonetti</dc:creator>
				<category><![CDATA[Ruby]]></category>
		<category><![CDATA[autotest]]></category>
		<category><![CDATA[continuous integration]]></category>
		<category><![CDATA[RSpec]]></category>
		<category><![CDATA[testing]]></category>
		<category><![CDATA[zentest]]></category>

		<guid isPermaLink="false">http://railsontherun.com/2007/08/02/autotest-with-sound-fx</guid>
		<description><![CDATA[In case you missed the latest great extension for Zentest Autotest, here is the blog post you have to read.
Jeremy from Switzerland came up with this great idea of adding audio report to Autotest. I&#8217;ve been using Growl to notify me when my tests would pass or fail, but I simply love just hearing a [...]]]></description>
			<content:encoded><![CDATA[<p>In case you missed the latest great extension for <a href="http://www.zenspider.com/ZSS/Products/ZenTest">Zentest Autotest</a>, here is <a href="http://fozworks.com/2007/7/28/autotest-sound-effects">the blog post</a> you have to read.</p>
<p>Jeremy from Switzerland came up with this great idea of adding audio report to Autotest. I&#8217;ve been using <a href="http://railstips.org/2007/7/23/autotest-growl-pass-fail-notifications">Growl</a> to notify me when my tests would pass or fail, but I simply love just hearing a different sound based on the result of the tests.</p>
<p><img src="http://farm2.static.flickr.com/1180/982723651_2a183dc8db.jpg?v=0" alt="growl"/> (screenshot from <a href="http://railstips.org/2007/7/23/autotest-growl-pass-fail-notifications">this post</a>)</p>
<p>Watch the <a href="http://fozworks.com/static/autotest-sound10.html">screencast</a></p>
<p>p.s: I&#8217;m working on redesigning this blog, I don&#8217;t have much time and I hate IE <img src='http://railsontherun.com/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' />  I hope to get things fixed soon.</p>
]]></content:encoded>
			<wfw:commentRss>http://railsontherun.com/2007/08/02/autotest-with-sound-fx/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>restful_authentication and RSpec tip</title>
		<link>http://railsontherun.com/2007/07/13/restful_authentication-and-rspec-tip/</link>
		<comments>http://railsontherun.com/2007/07/13/restful_authentication-and-rspec-tip/#comments</comments>
		<pubDate>Fri, 13 Jul 2007 05:55:00 +0000</pubDate>
		<dc:creator>Matt Aimonetti</dc:creator>
				<category><![CDATA[Ruby]]></category>
		<category><![CDATA[authentication]]></category>
		<category><![CDATA[BDD]]></category>
		<category><![CDATA[helper]]></category>
		<category><![CDATA[plugin]]></category>
		<category><![CDATA[restful]]></category>
		<category><![CDATA[restful_authentication]]></category>
		<category><![CDATA[RSpec]]></category>
		<category><![CDATA[tests]]></category>
		<category><![CDATA[tip]]></category>

		<guid isPermaLink="false">http://railsontherun.com/2007/07/13/restful_authentication-and-rspec-tip</guid>
		<description><![CDATA[resftul_authentication is a great plugin, but not always resftful&#8230; especially if like me you dropped unit test for RSpec.

I have a set of RSpec examples I use all the time on all my projects requiring restful_authentication, obviously I always end up tweaking them because each application has its specific needs.
However, I was recently asked what&#8217;s [...]]]></description>
			<content:encoded><![CDATA[<p><a href="http://svn.techno-weenie.net/projects/plugins/restful_authentication/">resftul_authentication</a> is a great plugin, but not always resftful&#8230; especially if like me you dropped unit test for RSpec.</p>
<p><img src="http://myskitch.com/matt_a/p-restful_24x40.jpg__jpeg_image__2224x1475_pixels__-_scaled__43__-20070712-224940.jpg" width='490px' alt="" title=""></p>
<p>I have a set of RSpec examples I use all the time on all my projects requiring restful_authentication, obviously I always end up tweaking them because each application has its specific needs.</p>
<p>However, I was recently asked <em>what&#8217;s the way of dealing with controllers specs when a controller has a limited access ?</em></p>
<p>Let&#8217;s look at the following controller for instance:</p>
<pre><code>class AssetController &lt; ApplicationController
 before_filter :login_required, :except =&gt; [ :index, :show ]
</code></pre>
<p>my assets_controller_spec.rb file will have the following code:</p>
<pre><code>describe AssetController, "handling GET /assets/new" do

  before do
    @asset = mock_model(Asset)
    Asset.stub!(:new).and_return(@asset)
  end

  def do_get
    get :new
  end

  it "should be successful" do
    do_get
    response.should be_success
  end

end
</code></pre>
<p>and guess what&#8230; it will fail! Why? simply because we are trying to access an action requiring login. Right, so what&#8217;s the best way of dealing with this issue and get our test to pass?</p>
<p>The best solution I found was to use a simple helper that I put in my spec_helper.rb file</p>
<pre><code>def login_as(user)
  case user
    when :admin
      @current_user = mock_model(User)
      User.should_receive(:find_by_id).any_number_of_times.and_return(@current_user)
      request.session[:user] = @current_user
    else
      request.session[:user] = nil
  end
end
</code></pre>
<p>You might wonder why I use when :user, well, in a lot of the application I&#8217;m working on, I have different levels of access and  I want to tests different accounts so I the case conditional loop.</p>
<p>Anyway, let&#8217;s implement our helper in our previous RSpec example:</p>
<pre><code>describe AssetController, "handling GET /assets/new" do

  before do
    login_as :admin
    @asset = mock_model(Asset)
    Asset.stub!(:new).and_return(@asset)
  end

  def do_get
    get :new
  end

  it "should be successful" do
    do_get
    response.should be_success
  end

end
</code></pre>
<p>and there you go, now your example passes properly <img src='http://railsontherun.com/wp-includes/images/smilies/icon_wink.gif' alt=';)' class='wp-smiley' /> </p>
<p>Have fun</p>
]]></content:encoded>
			<wfw:commentRss>http://railsontherun.com/2007/07/13/restful_authentication-and-rspec-tip/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Create a Rails Edge / RSpec project</title>
		<link>http://railsontherun.com/2007/06/06/create-a-rails-edge-rspec-project/</link>
		<comments>http://railsontherun.com/2007/06/06/create-a-rails-edge-rspec-project/#comments</comments>
		<pubDate>Wed, 06 Jun 2007 19:34:00 +0000</pubDate>
		<dc:creator>Matt Aimonetti</dc:creator>
				<category><![CDATA[Ruby]]></category>
		<category><![CDATA[autotest]]></category>
		<category><![CDATA[BDD]]></category>
		<category><![CDATA[edge]]></category>
		<category><![CDATA[growl]]></category>
		<category><![CDATA[hackfest]]></category>
		<category><![CDATA[rails]]></category>
		<category><![CDATA[RSpec]]></category>
		<category><![CDATA[svn]]></category>
		<category><![CDATA[TDD]]></category>
		<category><![CDATA[texmate]]></category>
		<category><![CDATA[zentest]]></category>

		<guid isPermaLink="false">http://railsontherun.com/2007/06/06/create-a-rails-edge-rspec-project</guid>
		<description><![CDATA[Recently I helped few people moving to Rails Edge and start using RSpec. I realized that I learned few tricks and even if for me everything seemed quite simple, things are not that simple when you recently started with Rails.
This would work on Mac and Linux, sorry Windows users, you&#8217;ll have to slightly change the [...]]]></description>
			<content:encoded><![CDATA[<p>Recently I helped few people moving to <a href="http://dev.rubyonrails.org/">Rails Edge</a> and start using <a href="http://rspec.rubyforge.org">RSpec</a>. I realized that I learned few tricks and even if for me everything seemed quite simple, things are not that simple when you recently started with Rails.</p>
<p>This would work on Mac and Linux, sorry Windows users, you&#8217;ll have to slightly change the code below.</p>
<h1>Live on the Edge</h1>
<p>This is actually a bit tricky but it was very well covered by <a href="http://addictedtonew.com/about/">John Nunemaker</a> in <a href="http://railstips.org/2007/5/31/even-edgier-than-edge-rails">this post</a></p>
<p>To sum John&#8217;s post:</p>
<p>Create a normal rails project:</p>
<pre><code>$ rails my_project
$ cd my_project

$ rake rails:freeze:edge
</code></pre>
<p>(or use checkout edge in the vendor folder)</p>
<pre><code>$ cd ..
$ ruby my_project/vendor/rails/railties/bin/rails my_edgie_project
</code></pre>
<p>You now have have a real Edge project called my<em>edgie</em>project. You can delete the my_project folder since we only used it to create our real edge project.</p>
<p>Now, we are not really done since we need to add the Edge files into our vendor folder so we don&#8217;t use our local rails gem.</p>
<p>I would refer to another post from John, that you can find <a href="http://railstips.org/2007/3/5/my-local-rails-setup">there</a></p>
<pre><code>$ mkdir ~/rails
$ cd ~/rails
$ svn co http://dev.rubyonrails.com/svn/rails/trunk .
</code></pre>
<p>We just created a rails folder called rails in our home folder and we checked out edge/trunk in it.<br />
Now let&#8217;s go in our Rails app and setup a symlink to the trunk folder we just created.</p>
<pre><code>$ cd ~/rails_projects/my_edgie_project
$ ln -s ~/rails/trunk vendor/rails
</code></pre>
<p>If you are using subversion, you can ignore the symlink so it doesnâ€™t try to version it:</p>
<pre><code>$ svn propset svn:ignore "rails" vendor/
$ svn commit -m "using new sweet rails setup as recommended by John Nunemaker"
$ svn up
</code></pre>
<p><a href="http://railstips.org/2007/3/5/my-local-rails-setup">Read more</a> for advanced settings etc&#8230;</p>
<h1>Install RSpec</h1>
<p>Very straight forward, you just need to follow <a href="http://rspec.rubyforge.org/documentation/rails/install.html">the documentation</a></p>
<pre><code>$ cd ~/rails_projects/my_edgie_project
$ ruby script/plugin install svn://rubyforge.org/var/svn/rspec/tags/CURRENT/rspec
$ ruby script/plugin install svn://rubyforge.org/var/svn/rspec/tags/CURRENT/rspec_on_rails
</code></pre>
<p>If you have TextMate, you might want to download the <a href="http://rubyforge.org/frs/?group_id=797">latest RSpec-X.Y.Z.tmbundle.tgz Bundle</a></p>
<p>Next thing you want to do is to install <a href="http://www.zenspider.com/ZSS/Products/ZenTest/">ZenTest</a></p>
<pre><code>$ sudo gem install ZenTest
</code></pre>
<p>Make sure you install all the required packages.</p>
<p>If you are using <a href="http://growl.info/">Growl</a> create a new file called .autotest in your home directory:</p>
<pre><code>$mate ~./autotest
</code></pre>
<p>and add the following 2 lines to be warned when your specs/examples fail/pass</p>
<pre><code>require 'autotest/redgreen'
require 'autotest/growl'
</code></pre>
<p>Now, lets go back to our project and create a model using the rspec scaffold (it uses scaffold_resource generator and create all the specs for you)</p>
<pre><code>$ cd ~/rails_projects/my_edgie_project
$ ruby script/generate rspec_scaffold User first_name:string last_name:string :age:integer
</code></pre>
<p>Now, let&#8217;s start autotest (from zentest) so out code is tested in the background</p>
<pre><code>$ autotest
</code></pre>
<p>There you go, really to modify your RSpec examples, make them fail, fix your code, examples should pass, refactor your code and start again <img src='http://railsontherun.com/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' /> </p>
]]></content:encoded>
			<wfw:commentRss>http://railsontherun.com/2007/06/06/create-a-rails-edge-rspec-project/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>Oops, DrNic Did it again</title>
		<link>http://railsontherun.com/2007/04/26/myconfplan-com/</link>
		<comments>http://railsontherun.com/2007/04/26/myconfplan-com/#comments</comments>
		<pubDate>Thu, 26 Apr 2007 10:33:00 +0000</pubDate>
		<dc:creator>Matt Aimonetti</dc:creator>
				<category><![CDATA[Ruby]]></category>
		<category><![CDATA[BDD]]></category>
		<category><![CDATA[bundle]]></category>
		<category><![CDATA[conference]]></category>
		<category><![CDATA[DrNic]]></category>
		<category><![CDATA[failure]]></category>
		<category><![CDATA[myconfplan.com]]></category>
		<category><![CDATA[railsconf]]></category>
		<category><![CDATA[RSpec]]></category>
		<category><![CDATA[spec]]></category>
		<category><![CDATA[textmate]]></category>
		<category><![CDATA[web2.0]]></category>

		<guid isPermaLink="false">http://railsontherun.com/2007/04/26/myconfplan-com</guid>
		<description><![CDATA[DrNic the most famous Australian Rails developer surprisingly doesn&#8217;t spend most of his time working on Rails  read interview
That&#8217;s maybe why he recently became so active in the Rails community ( see Magic Multi-Connections, Magic Models, map_by_methods, Gem Generator etc..)
Today he released something very helpful for the Rails Community, not another Gem or another [...]]]></description>
			<content:encoded><![CDATA[<p><a href="http://drnicwilliams.com/">DrNic</a> the most famous Australian Rails developer surprisingly doesn&#8217;t spend most of his time working on Rails  <a href="http://www.akitaonrails.com/pages/drnic">read interview</a><br />
That&#8217;s maybe why he recently became so active in the Rails community ( see <a href="http://www.loudthinking.com/arc/000610.html">Magic Multi-Connections</a>, Magic Models, map_by_methods, Gem Generator etc..)</p>
<p>Today he released something very helpful for the Rails Community, not another Gem or another cool plugin to extend Rails but a <a href="http://myconfplan.com">web application</a> to help you planning your conferences. We already had other tools such as <a href="http://railsconf2007.conferencemeetup.com/p/276-matt-aimonetti">conference meetup</a> but it&#8217;s the first time that we get a product helping you to plan a conference by scheduling the sessions you want to attend.</p>
<p><img src="http://farm1.static.flickr.com/169/473390616_12c7596617.jpg?v=0" alt="screenshot"/></p>
<p><a href="http://flickr.com/photos/railsontherun/473389852/in/photostream/">screenshot of the entire schedule</a></p>
<p>I had a quick chat with DrNic about his latest creation and here is what he said:</p>
<p>&#8220;its been fun building just how I thought session selection might look + feel<br />
web2.0 = permissive voyeurism I think!&#8221;</p>
<p>I share the same vision than Nic on session selection and I really enjoyed booking my Rails sessions and seeing what other people selected. (I guess that&#8217;s my voyeur side, don&#8217;t you like web2.0?)</p>
<p>If you wanna see what I planned on attending, checkout my schedule: <a href="http://myconfplan.com/conferences/RailsConf2007/users/matt">my schedule</a></p>
<p>Thanks Nic for the good work and too bad you are not presenting anything at the RailsConf (move your bum to come up with a <em>better</em> submission next year!)</p>
]]></content:encoded>
			<wfw:commentRss>http://railsontherun.com/2007/04/26/myconfplan-com/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>RSpec bundle for Textmate</title>
		<link>http://railsontherun.com/2007/04/18/rspec-bundle-for-textmate/</link>
		<comments>http://railsontherun.com/2007/04/18/rspec-bundle-for-textmate/#comments</comments>
		<pubDate>Wed, 18 Apr 2007 05:27:00 +0000</pubDate>
		<dc:creator>Matt Aimonetti</dc:creator>
				<category><![CDATA[Ruby]]></category>
		<category><![CDATA[macromates]]></category>
		<category><![CDATA[RSpec]]></category>
		<category><![CDATA[screenshots]]></category>
		<category><![CDATA[snippets]]></category>
		<category><![CDATA[texmate]]></category>
		<category><![CDATA[textmate bundle]]></category>

		<guid isPermaLink="false">http://railsontherun.com/2007/04/18/rspec-bundle-for-textmate</guid>
		<description><![CDATA[I recently realized that a lot of people using RSpec didn&#8217;t use the great TextMate bundle designed for them.
You might not think you need an extra bundle, or maybe you never used a bundle ever and don&#8217;t know why you would try one. I&#8217;ll try to change your mind, let&#8217;s look at some screenshots first:
This [...]]]></description>
			<content:encoded><![CDATA[<p>I recently realized that a lot of people using <a href="http://rspec.rubyforge.org">RSpec</a> didn&#8217;t use the great <a href="http://macromates.com/">TextMate</a> bundle designed for them.</p>
<p>You might not think you need an extra bundle, or maybe you never used a bundle ever and don&#8217;t know why you would try one. I&#8217;ll try to change your mind, let&#8217;s look at some screenshots first:</p>
<p>This is what you will want to see before checking in your code:</p>
<p><img src="http://farm1.static.flickr.com/209/463687467_87e92fb79e.jpg?v=0" alt="Specs passing"/></p>
<p>This is what you will see before you write your code:</p>
<p><img src="http://farm1.static.flickr.com/212/463687455_a6cc15a8bf.jpg?v=0" alt="Specs failing"/></p>
<p>This is how you will run your specs:</p>
<p><img src="http://farm1.static.flickr.com/216/463687471_431a3a2939.jpg?v=0" alt="Specs commands"/></p>
<p>This is all you get for free to save you some precious minutes every day:</p>
<p><img src="http://farm1.static.flickr.com/167/463687473_0f27cedac4.jpg?v=0" alt="Snippets"/></p>
<p><strong>How to install?</strong></p>
<p>Easy, checkout the file from RSpec repository:</p>
<pre><code>svn co svn://rubyforge.org/var/svn/rspec/trunk/RSpec.tmbundle
</code></pre>
<p>Double click on the file and that&#8217;s it! You are ready to go. (you would obviously need RSpec plugin or gem).</p>
<p>Thank you to all the RSpec team for creating such a great tool.</p>
]]></content:encoded>
			<wfw:commentRss>http://railsontherun.com/2007/04/18/rspec-bundle-for-textmate/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
	</channel>
</rss>

