<?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>cakebaker &#187; testing</title>
	<atom:link href="http://cakebaker.42dh.com/tags/testing/feed/" rel="self" type="application/rss+xml" />
	<link>http://cakebaker.42dh.com</link>
	<description>baking cakes with CakePHP</description>
	<lastBuildDate>Tue, 20 Dec 2011 15:29:40 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.3.1</generator>
		<item>
		<title>Cucumber: Switching from Webrat to Capybara</title>
		<link>http://cakebaker.42dh.com/2010/09/19/cucumber-switching-from-webrat-to-capybara/</link>
		<comments>http://cakebaker.42dh.com/2010/09/19/cucumber-switching-from-webrat-to-capybara/#comments</comments>
		<pubDate>Sun, 19 Sep 2010 14:24:43 +0000</pubDate>
		<dc:creator>cakebaker</dc:creator>
				<category><![CDATA[cucumber]]></category>
		<category><![CDATA[ruby on rails]]></category>
		<category><![CDATA[testing]]></category>

		<guid isPermaLink="false">http://cakebaker.42dh.com/?p=1441</guid>
		<description><![CDATA[My current testing tool of choice is Cucumber. Cucumber itself integrates well with other tools. One of those tools is Webrat, which allows you to access your application without a browser and to perform actions like clicking on a link or filling out forms. It works fine with Rails 2.3.x, but not with Rails 3 [...]]]></description>
			<content:encoded><![CDATA[<p>My current testing tool of choice is <a href="http://cukes.info/">Cucumber</a>. Cucumber itself integrates well with other tools. One of those tools is <a href="http://github.com/brynary/webrat">Webrat</a>, which allows you to access your application without a browser and to perform actions like clicking on a link or filling out forms. It works fine with Rails 2.3.x, but not with Rails 3 (at least I was not able to make it work, and on <a href="http://www.railsplugins.org/plugins/26-webrat">RailsPlugins.org</a> the current version of Webrat, 0.7.2.beta.1, is listed as &#8220;Maybe [working] with Rails 3&#8243;). Fortunately, there is an alternative working with both Rails versions: <a href="http://github.com/jnicklas/capybara">Capybara</a>. And so I decided to make the switch from Webrat to Capybara. </p>
<p>Before making the switch, I recommend to run your Cucumber tests to ensure all tests pass:</p>
<pre>
<code>$ cucumber features</code>
</pre>
<p>As usual when adding new dependencies, you have to modify the Gemfile of your app. Replace the Webrat entry with:</p>
<pre>
<code>gem "capybara", "0.3.9"</code>
</pre>
<p>and run:</p>
<pre>
<code>$ bundle update</code>
</pre>
<p>With Capybara installed, you have to setup Cucumber to use Capybara by running one of the following commands:</p>
<pre>
<code>// Rails 2.3.9
$ script/generate cucumber --rspec --capybara

// Rails 3.0.0
$ rails generate cucumber:install --rspec --capybara</code>
</pre>
<p>Now, you are ready to run the tests again. If you are lucky, all tests pass, which means there is nothing more to do. However, I think it is more likely you will get a bunch of errors and maybe even some failing tests. </p>
<p>The errors I got were &#8220;undefined method&#8221; errors. They are relatively easy to fix by replacing the no longer existing Webrat methods with their Capybara counterparts. In the following code block I list some examples:</p>
<pre>
<code># Webrat
field_with_id('openid_identifier').value.should =~ /invalid OpenID/
# Capybara
find_field('openid_identifier').value.should =~ /invalid OpenID/

# Webrat
response.should contain('Previous')
# Capybara
page.should have_content('Previous')

# Webrat
assert_have_selector('.author', :count =&gt; 1)
# Capybara
page.should have_css('.author', :count =&gt; 1)

# Webrat
assert_have_xpath("//span[@id='#{id}']", :content =&gt; expected_count)
# Capybara
page.should have_xpath("//span[@id='#{id}']", :text =&gt; expected_count)</code>
</pre>
<p>The trickiest part to fix was the failing test. To test some &#8220;remember me&#8221; functionality I manually set a cookie, and this no longer worked with Capybara: </p>
<pre>
<code>cookies[:remember_me_id] = remember_me_id</code>
</pre>
<p>After some searching I found a <a href="http://gist.github.com/484787">Gist</a> from Nicholas Rutherford in which he dealt with cookies. Thanks to his code I could set my cookie with the following snippet:</p>
<pre>
<code>cookies = Capybara.current_session.driver.current_session.instance_variable_get(:@rack_mock_session).cookie_jar
cookies[:remember_me_id] = remember_me_id</code>
</pre>
<p>And with that, my switch to Capybara was complete. Any questions?</p>
]]></content:encoded>
			<wfw:commentRss>http://cakebaker.42dh.com/2010/09/19/cucumber-switching-from-webrat-to-capybara/feed/</wfw:commentRss>
		<slash:comments>7</slash:comments>
		</item>
		<item>
		<title>Speed up your tests with Hydra</title>
		<link>http://cakebaker.42dh.com/2010/04/20/speed-up-your-tests-with-hydra/</link>
		<comments>http://cakebaker.42dh.com/2010/04/20/speed-up-your-tests-with-hydra/#comments</comments>
		<pubDate>Tue, 20 Apr 2010 14:52:46 +0000</pubDate>
		<dc:creator>cakebaker</dc:creator>
				<category><![CDATA[cucumber]]></category>
		<category><![CDATA[performance]]></category>
		<category><![CDATA[testing]]></category>

		<guid isPermaLink="false">http://cakebaker.42dh.com/?p=1364</guid>
		<description><![CDATA[Nowadays most computers come with more than one processor. And so it makes sense to use the additional processing power to speed up your tests by distributing them across the available processors. One tool that helps with this is Hydra. It allows you to distribute tests across multiple processors and machines, and currently supports the [...]]]></description>
			<content:encoded><![CDATA[<p>Nowadays most computers come with more than one processor. And so it makes sense to use the additional processing power to speed up your tests by distributing them across the available processors. </p>
<p>One tool that helps with this is <a href="http://github.com/ngauthier/hydra">Hydra</a>. It allows you to distribute tests across multiple processors and machines, and currently supports the <a href="http://ruby-doc.org/stdlib/libdoc/test/unit/rdoc/classes/Test/Unit.html">Test::Unit</a>, <a href="http://cukes.info/">Cucumber</a>, and <a href="http://rspec.info/">RSpec</a> frameworks. In this article I will focus on running Cucumber tests on a single machine. </p>
<p>As Hydra is distributed as a Ruby Gem its installation is pretty simple:</p>
<pre>
<code>gem install hydra</code>
</pre>
<p>After that, you have to add Hydra to the Rakefile of the respective project. And you have to specify the Cucumber task and the files it should use.</p>
<pre>
<code># Rakefile
require 'hydra'
require 'hydra/tasks'

Hydra::TestTask.new('hydra:cucumber') do |t|
  t.add_files 'features/**/*.feature'
end</code>
</pre>
<p>As last step you have to create a &#8220;hydra.yml&#8221; file in the &#8220;config&#8221; folder of your project. Here you define whether the tests should run locally, and how many runners Hydra should start. Runners correspond to processors, and so the setting below is for a dual core machine.</p>
<pre>
<code># config/hydra.yml
workers:
  - type: local
    runners: 2</code>
</pre>
<p>With everything set up, you can now run the tests with the following command:</p>
<pre>
<code>$ RAILS_ENV=test rake hydra:cucumber</code>
</pre>
<p>To verify whether there is really a speed gain when running the tests in this way you have to do some kind of a benchmark (see the example below), because running something on multiple processors doesn&#8217;t necessarily mean it is faster&#8230;</p>
<p>Happy testing!<br />
&nbsp;<br />
<br />&#8212;<br />
For my (unscientific) benchmark I ran my test suite (consisting of 12 files with 43 scenarios and 193 steps) with the following commands five times and averaged the results:</p>
<pre>
<code>$ time cucumber features
$ time rake cucumber
$ time RAILS_ENV=test rake hydra:cucumber</code>
</pre>
<p>In the first scenario I ran the benchmark with no other user applications running, i.e. both processors were available for the task at hand. From the results you can see that using Hydra in such a scenario is the fastest solution. </p>
<pre>
<code>cucumber: 24.1s
cucumber with rake: 31.4s
hydra:cucumber: 22.4s</code>
</pre>
<p>In the second scenario I ran the benchmark in a typical development environment with many open applications, i.e. around 1.5 processors were available. This time, using Hydra is not the fastest solution, the overhead is bigger than the speed gain from having more than one processor .</p>
<pre>
<code>cucumber: 25.9s
cucumber with rake: 34.3s
hydra:cucumber: 30.6s</code>
</pre>
]]></content:encoded>
			<wfw:commentRss>http://cakebaker.42dh.com/2010/04/20/speed-up-your-tests-with-hydra/feed/</wfw:commentRss>
		<slash:comments>4</slash:comments>
		</item>
		<item>
		<title>Using custom asserts for better readability</title>
		<link>http://cakebaker.42dh.com/2008/12/03/using-custom-asserts-for-better-readability/</link>
		<comments>http://cakebaker.42dh.com/2008/12/03/using-custom-asserts-for-better-readability/#comments</comments>
		<pubDate>Wed, 03 Dec 2008 08:34:21 +0000</pubDate>
		<dc:creator>cakebaker</dc:creator>
				<category><![CDATA[refactoring]]></category>
		<category><![CDATA[testing]]></category>

		<guid isPermaLink="false">http://cakebaker.42dh.com/?p=984</guid>
		<description><![CDATA[Recently, I wrote the following test case for a BooleanValidator class (a class which ensures a value is of the type &#8220;boolean&#8221;): class BooleanValidatorTest extends CakeTestCase { private $validator = null; public function setUp() { $this-&#62;validator = new BooleanValidator(); } public function testValidate() { $this-&#62;assertIdentical(true, $this-&#62;validator-&#62;validate(true)); $this-&#62;assertIdentical(true, $this-&#62;validator-&#62;validate(false)); $this-&#62;assertTrue(is_string($this-&#62;validator-&#62;validate(0))); $this-&#62;assertTrue(is_string($this-&#62;validator-&#62;validate(1))); } } The code is [...]]]></description>
			<content:encoded><![CDATA[<p>Recently, I wrote the following test case for a BooleanValidator class (a class which ensures a value is of the type &#8220;boolean&#8221;):</p>
<pre>
<code>class BooleanValidatorTest extends CakeTestCase {
    private $validator = null;
	
    public function setUp() {
        $this-&gt;validator = new BooleanValidator();
    }
	
    public function testValidate() {
        $this-&gt;assertIdentical(true, $this-&gt;validator-&gt;validate(true));
        $this-&gt;assertIdentical(true, $this-&gt;validator-&gt;validate(false));
        $this-&gt;assertTrue(is_string($this-&gt;validator-&gt;validate(0)));
        $this-&gt;assertTrue(is_string($this-&gt;validator-&gt;validate(1)));
    }
}</code>
</pre>
<p>The code is quite trivial, though it is not that easy to see what I try to express with this code. And so we have to improve its readability. </p>
<p>For this purpose we will write two custom asserts. Custom asserts are nothing special, they are normal methods. But for some reason it seems like people think they always have to use the assert methods provided by the testing framework. </p>
<p>Let&#8217;s have a look at the test method above. What is verified in the first two lines with assertIdentical()? It is simple: it is verified the validation process recognizes the provided data as valid. So, we have the first custom assert method: assertValid(). </p>
<p>Now you might think the second custom assert method will be assertInvalid(). This would be a good name if the validation process would return false if a value doesn&#8217;t validate. Though, in this specific case a validation error is returned, and so a better name for the second assert method is: assertValidationError(). </p>
<p>With this, we can refactor the example from above to:</p>
<pre>
<code>class BooleanValidatorTest extends CakeTestCase {
    private $validator = null;
	
    public function setUp() {
        $this-&gt;validator = new BooleanValidator();
    }
	
    public function testValidate() {
        $this-&gt;assertValid($this-&gt;validator-&gt;validate(true));
        $this-&gt;assertValid($this-&gt;validator-&gt;validate(false));
        $this-&gt;assertValidationError($this-&gt;validator-&gt;validate(0));
        $this-&gt;assertValidationError($this-&gt;validator-&gt;validate(1));
    }

    private function assertValid($validationResult) {
        $this-&gt;assertIdentical(true, $validationResult);
    }
	
    private function assertValidationError($validationResult) {
        $this-&gt;assertTrue(is_string($validationResult));
    }
}</code>
</pre>
<p>The result is now much easier to read (at least in my opinion), and as a nice side effect of this refactoring we also have eliminated some duplicate code. </p>
]]></content:encoded>
			<wfw:commentRss>http://cakebaker.42dh.com/2008/12/03/using-custom-asserts-for-better-readability/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Testing protected methods</title>
		<link>http://cakebaker.42dh.com/2008/11/13/testing-protected-methods/</link>
		<comments>http://cakebaker.42dh.com/2008/11/13/testing-protected-methods/#comments</comments>
		<pubDate>Thu, 13 Nov 2008 10:04:56 +0000</pubDate>
		<dc:creator>cakebaker</dc:creator>
				<category><![CDATA[cakephp]]></category>
		<category><![CDATA[testing]]></category>

		<guid isPermaLink="false">http://cakebaker.42dh.com/?p=954</guid>
		<description><![CDATA[Sometimes you are in the situation that you want/have to test a protected method. How do you do that? Well, it is quite simple. You have to create a subclass of the class you want to test and then you add a public method which delegates to the protected method. This subclass is then instantiated [...]]]></description>
			<content:encoded><![CDATA[<p>Sometimes you are in the situation that you want/have to test a protected method. How do you do that? Well, it is quite simple. You have to create a subclass of the class you want to test and then you add a public method which delegates to the protected method. This subclass is then instantiated in the test and instead of calling the protected method, the newly added public method is used. </p>
<p>Let&#8217;s have a look at a very trivial code example. First the class we want to test:</p>
<pre>
<code>class Example {
    protected function getHelloWorld() {
        return 'hello world';
    }
}</code>
</pre>
<p>And now the test for the getHelloWorld() method:</p>
<pre>
<code>class ExampleTest extends CakeTestCase {
    private $example = null;

    public function setUp() {
        $this-&gt;example = new MyExample();
    }

    public function testGetHelloWorld() {
        $this-&gt;assertEqual('hello world', $this-&gt;example-&gt;publicGetHelloWorld());
    }
}

class MyExample extends Example {
    public function publicGetHelloWorld() {
        return $this-&gt;getHelloWorld();
    }
}</code>
</pre>
<p>You can use the same strategy if you have to modify protected properties for your tests. </p>
<p>Happy testing!</p>
<p>PS: If you are a Munich baker you might be interested in the first <a href="http://www.cakebar.de">cakeBar</a>, which takes place on November 20.</p>
]]></content:encoded>
			<wfw:commentRss>http://cakebaker.42dh.com/2008/11/13/testing-protected-methods/feed/</wfw:commentRss>
		<slash:comments>4</slash:comments>
		</item>
		<item>
		<title>Screencast about testing controllers with CakePHP</title>
		<link>http://cakebaker.42dh.com/2008/11/03/screencast-about-testing-controllers-with-cakephp/</link>
		<comments>http://cakebaker.42dh.com/2008/11/03/screencast-about-testing-controllers-with-cakephp/#comments</comments>
		<pubDate>Mon, 03 Nov 2008 08:28:21 +0000</pubDate>
		<dc:creator>cakebaker</dc:creator>
				<category><![CDATA[cakephp]]></category>
		<category><![CDATA[controller]]></category>
		<category><![CDATA[screencast]]></category>
		<category><![CDATA[testing]]></category>

		<guid isPermaLink="false">http://cakebaker.42dh.com/?p=925</guid>
		<description><![CDATA[Yesterday I stumbled upon a screencast by Fernando Baraja (aka FernyB), in which he gives an introduction about testing controllers with CakePHP (you can skip the first few minutes because they are about installing CakePHP). This screencast seems to be the start of a series of CakePHP screencasts. You can find additional information about testing [...]]]></description>
			<content:encoded><![CDATA[<p>Yesterday I stumbled upon a <a href="http://fernyb.net/blog/2008/11/01/testing-with-cakephp-part-1/">screencast</a> by <a href="http://fernyb.net/blog/">Fernando Baraja</a> (aka FernyB), in which he gives an introduction about testing controllers with CakePHP (you can skip the first few minutes because they are about installing CakePHP). This screencast seems to be the start of a series of CakePHP screencasts.</p>
<p>You can find additional information about <a href="http://book.cakephp.org/view/366/Testing-controllers">testing controllers</a> in the cookbook.</p>
<p>Happy testing :)</p>
]]></content:encoded>
			<wfw:commentRss>http://cakebaker.42dh.com/2008/11/03/screencast-about-testing-controllers-with-cakephp/feed/</wfw:commentRss>
		<slash:comments>6</slash:comments>
		</item>
		<item>
		<title>Skipping test cases</title>
		<link>http://cakebaker.42dh.com/2008/06/23/skipping-test-cases/</link>
		<comments>http://cakebaker.42dh.com/2008/06/23/skipping-test-cases/#comments</comments>
		<pubDate>Mon, 23 Jun 2008 15:19:02 +0000</pubDate>
		<dc:creator>cakebaker</dc:creator>
				<category><![CDATA[simpletest]]></category>
		<category><![CDATA[testing]]></category>

		<guid isPermaLink="false">http://cakebaker.42dh.com/?p=616</guid>
		<description><![CDATA[Some days ago Tim Koschützki showed in an article how you can execute only some specific test methods in (SimpleTest-based) unit tests by overriding the getTests() method. Sometimes you not only want to skip some test methods but an entire test case. For example, the tests of the MySQL datasource test case can only be [...]]]></description>
			<content:encoded><![CDATA[<p>Some days ago <a href="http://debuggable.com/tim">Tim Koschützki</a> showed in an <a href="http://debuggable.com/posts/how-to-execute-only-specific-test-methods-in-cakephp-unit-tests:4858fa7b-7194-4652-9c7f-47784834cda3">article</a> how you can execute only some specific test methods in (<a href="http://simpletest.org">SimpleTest</a>-based) unit tests by overriding the getTests() method.</p>
<p>Sometimes you not only want to skip some test methods but an entire test case. For example, the tests of the MySQL datasource test case can only be executed successfully if there is a MySQL database (or else you will get many errors). What do you do in such a case? </p>
<p>You could override the getTests() method and simply return an empty array if there is no MySQL database available:</p>
<pre>
public function getTests() {
    if (!$this-&gt;isMySQLAvailable()) {
        return array();
    }

    return parent::getTests();
}
</pre>
<p>This works, but it is rather a theoretical approach. Usually you override the method which was designed for this purpose: skip. In this method you use then either the skipIf() or skipUnless() method to determine whether the test case should be skipped. So we can rewrite the example from above in the following way:</p>
<pre>
public function skip() {
    $this-&gt;skipUnless($this-&gt;isMySQLAvailable());
    // $this-&gt;skipIf(!$this-&gt;isMySQLAvailable()); has the same effect
}
</pre>
<p>If you now run the test case, and you don&#8217;t have a MySQL database, you will get informed that the respective test case has been skipped.</p>
<p>Happy testing!</p>
]]></content:encoded>
			<wfw:commentRss>http://cakebaker.42dh.com/2008/06/23/skipping-test-cases/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
		<item>
		<title>The dark side of failing tests</title>
		<link>http://cakebaker.42dh.com/2008/05/09/the-dark-side-of-failing-tests/</link>
		<comments>http://cakebaker.42dh.com/2008/05/09/the-dark-side-of-failing-tests/#comments</comments>
		<pubDate>Fri, 09 May 2008 18:18:26 +0000</pubDate>
		<dc:creator>cakebaker</dc:creator>
				<category><![CDATA[testing]]></category>

		<guid isPermaLink="false">http://cakebaker.42dh.com/?p=601</guid>
		<description><![CDATA[[rant] Yesterday, I opened some tickets because some core tests failed while I run them with the new testsuite shell. As I didn&#8217;t attach any patches to the tickets I got &#8220;attacked&#8221; on twitter by some people from the core team, and I even got a nice mail from gwoo (the project manager of CakePHP) [...]]]></description>
			<content:encoded><![CDATA[<p>[rant]<br />
Yesterday, I opened some tickets because some core tests failed while I run them with the new testsuite shell. As I didn&#8217;t attach any patches to the tickets I got &#8220;attacked&#8221; on twitter by some people from the core team, and I even got a nice mail from gwoo (the project manager of CakePHP) that I should stop submitting tickets&#8230;<br />
[/rant]</p>
<p>Anyway, I think this is a good opportunity to think about failing tests (with tests I primarily mean unit tests).</p>
<p>Even though &#8220;failing tests&#8221; may sound quite negative, this is not the case, at least if you practice <a href="http://en.wikipedia.org/wiki/Test-driven_development">test driven development</a> (or a similar approach). There, failing tests are an integral part of the process. You start with a failing test, and then you implement the functionality so that the test no longer fails. Or if you make a change, and you break something by accident, then a failing test informs you about it. So, a failing test is quite positive.</p>
<p>On the other hand, failing tests also have a dark side. </p>
<p>The longer you wait to fix them, the higher the &#8220;costs&#8221;. If you fix a failing test immediately, then the costs are almost zero: you know what you changed, and so you can easily fix it. But if you wait a while, then the code is no longer present in your mind and it takes much more effort to fix the failing test. A side effect of this waiting is that it encourages others to do the same. If X doesn&#8217;t fix the tests he has broken, why should I care whether my tests run? As another side effect it may undermine the motivation of bug reporters to contribute tests if they see the project members don&#8217;t care about tests&#8230;</p>
<p>A special &#8220;behavior&#8221; of failing tests is that they don&#8217;t tell you whether they fail because of an incorrect test case or a bug in the code you test (in practice, this is sometimes obvious, sometimes not, depending on various factors). And they don&#8217;t tell you whether they only fail in your environment or everywhere. So, this means, if I run your tests and some of them fail, then all I can say may be: test X fails in my environment (the reason for saying &#8220;in my environment&#8221; is that I assume you don&#8217;t give me broken code, i.e. code with tests you know are failing). As it is an environment-specific issue, I will inform you about it, so it can get fixed. But if you provide broken code, then everyone using it will bother you with the same issue, at least theoretically ;-)</p>
<p>I think it is obvious what helps to deal with those dark sides: don&#8217;t provide code with tests you know are failing, it&#8217;s that simple!</p>
<p>I hope it wasn&#8217;t too confusing, and sorry about the rant at the beginning, but sometimes it&#8217;s necessary to vent one&#8217;s anger ;-)</p>
]]></content:encoded>
			<wfw:commentRss>http://cakebaker.42dh.com/2008/05/09/the-dark-side-of-failing-tests/feed/</wfw:commentRss>
		<slash:comments>12</slash:comments>
		</item>
		<item>
		<title>Testing with partial mock objects</title>
		<link>http://cakebaker.42dh.com/2007/12/04/testing-with-partial-mock-objects/</link>
		<comments>http://cakebaker.42dh.com/2007/12/04/testing-with-partial-mock-objects/#comments</comments>
		<pubDate>Tue, 04 Dec 2007 16:28:02 +0000</pubDate>
		<dc:creator>cakebaker</dc:creator>
				<category><![CDATA[cakephp]]></category>
		<category><![CDATA[simpletest]]></category>
		<category><![CDATA[testing]]></category>

		<guid isPermaLink="false">http://cakebaker.42dh.com/2007/12/04/testing-with-partial-mock-objects/</guid>
		<description><![CDATA[When testing your models with unit tests you probably encounter the &#8220;problem&#8221; of slow test execution due to all those database accesses. And that&#8217;s bad. You want the test execution to be fast so you can run the tests often. What can you do to avoid the database accesses? Well, the SimpleTest framework &#8212; the [...]]]></description>
			<content:encoded><![CDATA[<p>When testing your models with unit tests you probably encounter the &#8220;problem&#8221; of slow test execution due to all those database accesses. And that&#8217;s bad. You want the test execution to be fast so you can run the tests often. What can you do to avoid the database accesses? </p>
<p>Well, the <a href="http://simpletest.org">SimpleTest</a> framework &#8212; the testing framework used by CakePHP &#8212; provides a feature called &#8220;partial mocks&#8221;. With this feature it is possible to fake certain methods of a class, i.e. we can mock those methods which access the database.  </p>
<p>Let&#8217;s have a look at an example. </p>
<p>We assume we want to test a method which checks whether the provided tags are in the database, and returns then those tags which are not yet in the database. </p>
<p>As we use findAll() to retrieve the tags, we have to mock this method. We can do it with the following snippet:</p>
<pre>
Mock::generatePartial('Tag', 'MockTag', array('findAll'));
</pre>
<p>The first parameter of Mock::generatePartial() specifies the class we want to mock, the second parameter defines the name of the mocked class, and the last parameter defines the methods we want to mock. </p>
<p>In the test we will now use the MockTag class instead of the Tag class. It is identical to the Tag class (technically it is a subclass of it), with the difference that the implementation of findAll() doesn&#8217;t &#8220;exist&#8221; anymore. With setReturnValue() we can now specify what findAll() should return when called. Below you find the test code, it should be self-explanatory (if not, please leave a comment):</p>
<pre>
Mock::generatePartial('Tag', 'MockTag', array('findAll'));

class TagTest extends CakeTestCase {
    function testExtractNewTags() {
        $existingTags = array(0 =&gt; array('Tag' =&gt; array('name' =&gt; 'tagA')),
			                   1 =&gt; array('Tag' =&gt; array('name' =&gt; 'tagB')));

        $mock = new MockTag($this);
        $mock-&gt;setReturnValue('findAll', $existingTags);

        $newTags = $mock-&gt;extractNewTags(array('tagA', 'tagB'));
        $this-&gt;assertIdentical(array(), $newTags);

        $newTags = $mock-&gt;extractNewTags(array('tagA', 'tagC', 'tagD'));
        $this-&gt;assertEqual(2, count($newTags));
        $this-&gt;assertEqual('tagC', $newTags[0]);
        $this-&gt;assertEqual('tagD', $newTags[1]);
    }
}
</pre>
<p>That&#8217;s only one simple example of what you can do with partial mock objects. For more see the <a href="http://simpletest.org/en/partial_mocks_documentation.html">SimpleTest documentation</a>. </p>
<p>Happy testing :)</p>
<p>Update 2007-12-08: Something I forgot to mention is that you have to include the file mock_objects.php to make it work. You can do it with </p>
<pre>
vendor('simpletest'.DS.'mock_objects');
</pre>
<p>at the top of your test case file. </p>
<p>Thanks to <a href="http://www.3-threes.com/">Zach Cox</a> for asking me this by email!</p>
]]></content:encoded>
			<wfw:commentRss>http://cakebaker.42dh.com/2007/12/04/testing-with-partial-mock-objects/feed/</wfw:commentRss>
		<slash:comments>6</slash:comments>
		</item>
		<item>
		<title>How to write and test your own head helper</title>
		<link>http://cakebaker.42dh.com/2007/09/28/how-to-write-and-test-your-own-head-helper/</link>
		<comments>http://cakebaker.42dh.com/2007/09/28/how-to-write-and-test-your-own-head-helper/#comments</comments>
		<pubDate>Fri, 28 Sep 2007 14:54:15 +0000</pubDate>
		<dc:creator>cakebaker</dc:creator>
				<category><![CDATA[cakephp]]></category>
		<category><![CDATA[helper]]></category>
		<category><![CDATA[testing]]></category>

		<guid isPermaLink="false">http://cakebaker.42dh.com/2007/09/28/how-to-write-and-test-your-own-head-helper/</guid>
		<description><![CDATA[In CakePHP 1.1 the head helper by Miguel Ros was quite popular to add stuff to the head section of a HTML page from the view. CakePHP 1.2 provides such a functionality for referencing Javascript and CSS files. If you want to add something else to the head section, you have to write your own [...]]]></description>
			<content:encoded><![CDATA[<p>In CakePHP 1.1 the <a href="http://cakeforge.org/snippet/detail.php?type=snippet&#038;id=56">head helper</a> by Miguel Ros was quite popular to add stuff to the head section of a HTML page from the view. CakePHP 1.2 provides such a functionality for referencing <a href="http://cakebaker.42dh.com/2007/02/21/referencing-javascript-files/">Javascript</a> and <a href="http://cakebaker.42dh.com/2007/03/14/referencing-css-files/">CSS</a> files. If you want to add something else to the head section, you have to write your own helper. </p>
<p>Let&#8217;s write a simple helper which creates an author meta tag. </p>
<p>Usually you write first the test, and then the application code. But in this case I will make an exception, as I think it is easier to understand if I write first the application code and then the test.</p>
<p>Writing the helper is straight-forward: we have to get the view and add the meta tag to this view:</p>
<pre>
// app/views/helpers/head.php
class HeadHelper extends AppHelper {
    function authorMetaTag($authorName) {
        $metaTag = '&lt;meta name="author" content="'.$authorName.'"&gt;';
        $view = ClassRegistry::getObject('view');
        $view-&gt;addScript($metaTag);
    }
}
</pre>
<p>Before this helper can be used we have to add the following line to the head section of the (default) layout:</p>
<pre>
&lt;?php echo $scripts_for_layout; ?&gt;
</pre>
<p>With that we are ready to write our test (resp. we are finished with our work if we don&#8217;t write tests).</p>
<p>The test skeleton is easy:</p>
<pre>
class HeadHelperTest extends CakeTestCase {
    var $helper = null;

    function setUp() {
        $this-&gt;helper = new HeadHelper();
    }

    function testAuthorMetaTag() {
        $this-&gt;helper-&gt;authorMetaTag('cakebaker');
    }
}
</pre>
<p>As you have seen in the implementation of the helper, we retrieve a view object from the ClassRegistry. So to test our helper we also have to put a view object into the ClassRegistry. If you look at the source code of the view class constructor, you will see the view is automatically added to the ClassRegistry (to make sure the correct view is in the ClassRegistry we have to remove a possible view due to the behavior of ClassRegistry I explained in an earlier <a href="http://cakebaker.42dh.com/2007/09/20/dont-implement-a-known-concept-differently/">article</a>). And you will also see that the constructor expects a controller object. As we don&#8217;t have any controller, we will use the AppController for this purpose. </p>
<pre>
loadController(null);

class HeadHelperTest extends CakeTestCase {
    var $helper = null;

    function setUp() {
        $this-&gt;helper = new HeadHelper();
    }

    function testAuthorMetaTag() {
        ClassRegistry::removeObject('view');
        $view = new View(new AppController());
        $this-&gt;helper-&gt;authorMetaTag('cakebaker');
    }
}
</pre>
<p>The last step is to render the view resp. the layout of the view and to check whether our meta tag has been added. For this purpose we can use the regular expression I described in &#8220;<a href="http://cakebaker.42dh.com/2007/09/10/regular-expression-to-check-for-content-between-tags/">Regular expression to check for content between tags</a>&#8221; and which was improved by BurntSushi.</p>
<pre>
loadController(null);

class HeadHelperTest extends CakeTestCase {
    var $helper = null;

    function setUp() {
        $this-&gt;helper = new HeadHelper();
    }

    function testAuthorMetaTag() {
        ClassRegistry::removeObject('view');
        $view = new View(new AppController());
        $this-&gt;helper-&gt;authorMetaTag('cakebaker');
        $renderedLayout = $view-&gt;renderLayout('');
        $this-&gt;assertPattern('#&lt;head&gt;.*?&lt;meta name="author" content="cakebaker"&gt;.*?&lt;/head&gt;#si', $renderedLayout);
    }
}
</pre>
<p>Now, we can run the test and should get a green bar.</p>
<p>Happy testing :)</p>
]]></content:encoded>
			<wfw:commentRss>http://cakebaker.42dh.com/2007/09/28/how-to-write-and-test-your-own-head-helper/feed/</wfw:commentRss>
		<slash:comments>5</slash:comments>
		</item>
		<item>
		<title>Why you should test your CakePHP applications</title>
		<link>http://cakebaker.42dh.com/2007/09/14/why-you-should-test-your-cakephp-applications/</link>
		<comments>http://cakebaker.42dh.com/2007/09/14/why-you-should-test-your-cakephp-applications/#comments</comments>
		<pubDate>Fri, 14 Sep 2007 09:08:37 +0000</pubDate>
		<dc:creator>cakebaker</dc:creator>
				<category><![CDATA[cakephp]]></category>
		<category><![CDATA[testing]]></category>

		<guid isPermaLink="false">http://cakebaker.42dh.com/2007/09/14/why-you-should-test-your-cakephp-applications/</guid>
		<description><![CDATA[My comment about me not trusting CakePHP caused quite some discussions. Some interpreted it in the way that I think CakePHP is crap (well, if that would be the case I wouldn&#8217;t use it *g*). Others criticized me for publicly mentioning that some tests fail in the development branch&#8230; Anyway, what I missed was a [...]]]></description>
			<content:encoded><![CDATA[<p>My <a href="http://cakebaker.42dh.com/2007/08/27/i-dont-trust-cakephp-or-what-should-you-say-in-public/">comment</a> about me not trusting CakePHP caused quite some discussions. Some interpreted it in the way that I think CakePHP is crap (well, if that would be the case I wouldn&#8217;t use it *g*). Others criticized me for publicly mentioning that some tests fail in the development branch&#8230; Anyway, what I missed was a discussion about the implications of my statement. So I will catch up on that with this article.</p>
<p>One point I mentioned in the aforementioned comment are the missing tests. Not every class is tested. That&#8217;s because CakePHP was not developed with testing in mind originally. The first tests were added at the beginning of this year I think. And since then more and more tests have been written. But still, it will take quite a while to get a high test coverage. So the consequence of this is that when a developer makes changes in an untested class it is possible he will break something by accident that worked before, and he won&#8217;t notice it (you can find many such examples on <a href="https://trac.cakephp.org">trac</a>). That means a working feature in version x may no longer work in version x+y. </p>
<p>The other point are the failing core tests in the development branch. They signal: &#8220;Hey, something doesn&#8217;t work&#8221;. Maybe it is &#8220;only&#8221; a broken test, maybe it is a broken feature, whatever. It doesn&#8217;t matter, the message is the same: something is broken. Sure, it can always happen that you commit something that breaks the tests, nobody is perfect. But if the tests fail over a longer time period, well, then the impression I get is that the developers don&#8217;t care about the tests. </p>
<p>Ok, I am now aware of those &#8220;trust problems&#8221;. But what can I do? It is no fun to write tests for existing, untested stuff, so writing core tests is not an option. And I cannot change the attitude of other developers towards tests from one day to the other. But I can write tests for my own application, and so test the underlying framework indirectly. If I update the framework, and my tests fail afterwards, then it is very probable they failed due to a newly introduced bug in the framework, and I can report it. </p>
<p>Of course, the aforementioned points are not the only motivation for me to write tests, the article <a href="http://www.onjava.com/pub/a/onjava/2003/04/02/javaxpckbk.html">&#8220;Top 12 Reasons to Write Unit Tests&#8221;</a> lists other points that are important to me. </p>
<p>So my recommendation to everyone using CakePHP (or writing software in general): write tests, tests, tests!</p>
]]></content:encoded>
			<wfw:commentRss>http://cakebaker.42dh.com/2007/09/14/why-you-should-test-your-cakephp-applications/feed/</wfw:commentRss>
		<slash:comments>17</slash:comments>
		</item>
	</channel>
</rss>

