Recommended testing frameworks for Rails 2 app with randomness - ruby-on-rails

I have a Rails 2.3.5 app which is serving a card game. I've been a bit lax in writing tests for it (read: I haven't written any :embarrassed:), and I'd like to make a start now.
From reading other questions, I think I probably want to be using Shoulda extending Test::Unit for unit testing.
I wondered about using Capybara extending RSpec for functional testing, but the majority of users' interaction with the app is via POST, which I understand Capybara doesn't handle.
Since this is a card game, I obviously need the ability to control rand; I also definitely need the framework to handle Javascript.
Is Test::Unit + Shoulda suitable?
Am I correct that Capybara can't handle POST? Can I work around that?
Is there a better option instead of Capybara?
Can these methods handle the randomness involved in a card-game? Presumably, for Test::Unit at least, I can just call srand at some early stage to fix the generator, but I don't know if that's doable for Capybara/RSpec/anything else.
Can anyone point me to resources dealing specifically with setting up Shoulda, Capybara and RSpec for Rails 2.3.5? It's a little hard to tell what's Rails 3 specific and what isn't.
Would I gain anything from adding Watir / Firewatir into the mix?
I realise the above questions are manifold, but they basically boil down to "does this work, or have you any better suggestions?"

If the majority of the users' interactions are via POST, is it via an API (as opposed to filling out forms or something)?
Just about any combination of RSpec/Shoulda/Capybara/Test Unit/Rack::Test could work for you depending on your need. They're all capable. However, these are my recommendations:
If you've decided you want integration testing via HTML pages, use Cucumber and Capybara
If you've decided you want integration testing via HTTP API, use RSpec and Rack::Test
You probably want to fake out randomness.
You probably don't need Watir/Firewatir.
It does look like you can make POST requests via some Capybara drivers:
http://suffix.be/blog/capybara-post-requests
When Rails moved to 3.0, RSpec went to 2.0 so for at least RSpec, you'd want RSpec and RSpec Rails 1.3.2.
By "fake out randomess", I mean redefine srand in your tests so you can predictably run them.
module Kernel
def rand
YourApp.rand
end
end
module MyApp
class << self
attr_accessor :rand
end
end
Then, before you have the user press the button, run a step definition like "When random returns 6", which will set MyApp.rand = 6.

Related

Is it possible to use Cucumber to test an existing Rails Application?

I have just finished reading many different web pages on the subject of Cucumber. It appears to be impossible to use Cucumber to test an existing Ruby on Rails application. I'm just asking in case I missed something. (We are considering using it for future RoR app development.)
While I am asking, what is the current consensus on the best tool to test an existing Ruby on Rails application?
I did a little exploration with WATIR and it seems easy to use, but driving the web browser results in being not scalable. I have read some have moved from WATIR to Celerity....
However, I am in an environment where we are starting from zero previous testing. What is the 'best' choice to quickly write tests for an existing Ruby on Rails application?
In no way is Cucumber unable to test an existing application. Not sure what gave you this idea, but perhaps because it's typically used with test-driven development?
Cucumber is by far the most widely used integration testing software for Rails. I would definitely suggest using Cucumber with Capybara, Guard, Spork, and RSpec for your testing suite. (RSpec for unit testing, Capybara for integration tests, Guard and Spork for running your tests quickly).
If you've never looked at Cucumber before, you might want to take a look at some tutorials first.
To get started on your project, try to make a Cucumber feature for a simple feature. For example, write a test to visit the homepage. Something like:
Feature: View homepage
Given I am on the profile page
When I click "home"
Then I should see the homepage logo
Once you've understood that, move on to more complicated features. Examples might include create a user account, login, view a profile, etc. (I don't know what your application does but I think you get the point.)
Cucumber is able to test an existing application.
You have to set configuration setting for cucumber and generate cucumber folder by rails g cucumber
before run this command you have to include gem: gem 'cucumber'.

cucumber vs. RSpec

I want to start diving into BDD. I have never used TDD before and am
not sure if I should start by learning RSpec and then jump to Cucumber
or just go straight to using Cucumber.
I have been reading on the internet about both and it seems to me that
Cucumber could be a 'replacement' for RSpec. Am I right or should be
one used for certain things and the other one for others?
Cucumber and RSpec are both used for BDD but have different uses.
Think of Cucumber as describing what happens from the user's perspective, through interaction with the web browser. So you can have steps like:
Given I'm not logged in
When I login
Then I should be on the user dashboard page
Pretty broad, but there's a lot going on under the hood there. Cucumber is good for making sure all these sort of high-level features and functionality are covered (e.g., that when your user logs in, they're taken to the right page). But it's not a good tool for testing lower-level code. That's where RSpec comes in.
Take the login example above. Your user may be logging in with an email address or username. You probably want to ensure the email address is valid or that the username is a certain length...or that the thing they're using to login with is unique. You'd do this in your User model with a validation.
It's a trivial example, but this is the kind of thing you'd test using RSpec (in your spec/models/user_spec.rb file). This is not something you'd test using Cucumber.
So bottom line is:
Cucumber for higher-level tests describing broad functionality as viewed from the user's perspective
RSpec for lower-level tests describing details for how your classes, methods, models, controller, etc should actually work.
This post actually does a really good job of explaining when to transition from one tool to another:
http://www.sarahmei.com/blog/2010/05/29/outside-in-bdd/
I also recommend "The RSpec Book" and "Rails Test Prescriptions" for good resources on both tools and testing in general.
P.S. - Not to confuse things, but you can actually use RSpec for the high-level stuff too. But some of that decision is a matter of which tool you prefer or maybe whether or not you're working with a non-technical client who would benefit more from Cucumber's user-friendly syntax for describing scenarios.
Yes, cucumber and rspec are both used for BDD.
I personally prefer Cucumber, but some people find it offputting, and
prefer
their tests to be less english, more code. Both are great tools, though.
Kenton did a great job with this answer. Here is how the authors of RSpec and Cucumber see it:
We use Cucumber to describe the behavior of applications and use RSpec to describe the behavior of objects.
Although we use Cucumber to focus on high-level behavior and use RSpec
to focus on more granular behavior, each can be used for either
purpose.

Totally confused about rails testing.. which tools are for which jobs?

I'm learning Rails after a long time manually testing my own .NET code,
I'm loving what ive seen but i am SO confused about how it all fits together!
So my questions are
1 - Where would i use:
Rspec
Cucumber
Test Unit
Shoulda
Selenium (not really a ruby thing but more of a web thing ive heard)
I've sort-of been testing my code with some very basic RSpec on my models and using factory girl..
2 - Do i need all of these tools?
For example could i choose cucumber and factory girl and never have to learn rspec or is cucumber a pretty dsl wrapper for rspec and test unit...
3 - Are any of them usable / have a port on .NET as well?
Thanks!
Daniel
My current stack of Testing tools is:
Steak, instead of Cucumber.
Capybara with driver Akephalos, instead of Selenium.
RSpec
Machinist2, instead of factory girl.
https://github.com/cavalle/steak
https://github.com/jnicklas/capybara
http://rspec.info/
https://github.com/notahat/machinist
I learned a lot about testing with the book: The Rspec Book, by the Pragmatic Programmers.
http://pragprog.com/
You have more detailed information in this other question:
Rails: Good Rspec2 example usage? (Also: Cucumber, Pickle, Capybara)
For 1)
I do use Rspec for unit and Functional testing.
I do use Cucumber for integration testing. Cucumber uses Capybara or Selenium. I like Cucumber because it enables me to write tests with the customers. They feel implicated and thus give sometimes more details about their expectations.
Selenium could be used as a stand alone app to test your web app directly in your browser.
Many other tools exist, it's really a matter of choice. As you said, fixtures are not used anymore, Factory Girl is one of the best way to create testing data sets.
For 2)
You don't need all these tools, of course. You could even write your tests with the native Rails helpers.
But they provide convenient helpers you can take benefit from. So get the one you prefer. Some, like Cucumber, have extensions (like Pickle), to provide even more helpers.
For 3)
The strength of Rspec, Cucumber, Selenium (those I know) is they can be used to test any app.
I'm curious to listen to other's point of view concerning Ajax testing.

What are spec/requests good for?

I use RSpec to test my lovely little web app. For integration tests I use Steak. When using Rails generators (yep, I know that this is not the Zen way of doing TDD) there are also some files in spec/requests generated. As stated on link text it is something similiar to integration test (but I couldn't find much more info).
Are those request specs still recommended when using something like Steak and Cucumber?
It all depends on what you need and want. The goal of testing is to prove that your app works once, not twice or more times.
I personally write rspec tests for models and helpers. I use cucumber to test that my views and controllers are working the way I expect them to. With this I can prove that my entire app works as I expect it to, so no, I don't use spec/requests.
Occasionally I do use spec/requests to test APIs, but you can do that with cucumber as well.
Some don't like the BDD-way cucumber works and stick with spec/requests. In the end it's all a matter of taste.

How many use Rspec for controllers and views?

Are there strong reasons for using Rspec for controllers and views too?
My views are heavily dependent on Javascript, and as far as I know, Rspec doesn't handle javascript/ajax on views. Also im using Cucumber + Selenium for that.
And should I use it for controllers?
Isn't it enough to just use Cucumber + Selenium for the application behavior? Cause if a cucumber test passes, then it passes, why should I bother with Rspec view and controller tests?
Could someone enlighten me on this topic?
I use a combination of Cucumber + Shoulda, but what I'm about to tell you still applies to the setup you have.
When testing a controller I use Shoulda in a functional test to hit all of my "negative auth" situations. For example:
A logged in user trying to access an admin page.
A logged out user trying to access protected content.
User A trying to delete User B's post.
I use Shoulda for this, because what I'm generally looking for is that I was kicked to the login page, and that whatever model was trying to be accessed maliciously wasn't actually changed. I could use Cucumber for this, but I find it easier and less cumbersome to do with a handful of Shoulda macros and some functional tests. Shoulda contexts are a great fit here.
Then for the "good auth" situations, I use Cucumber. Things like:
A user accessing his own preferences page.
An admin pulling up reports.
These types of tests require that I check some actual page content, and not just check for "access denied" over and over again. I find the descriptiveness of Cucumber to be a great match here.
If you build a full enough set of tests, you can just use selenium, but if you want to test the behaviour of your javascript seperate from the rest of the app, you might consider using a javascript test framework, like QUnit.

Resources