3

I'm building a tool that automates a process then runs some tests on it's own results then goes to do some other stuff.

In trying to clean up my code I have created a separate file that just has the test cases class. Now before I can run these tests, I have to pass the class a couple of parameters/objects before they can be run. Now the problem is that I can't seem to find a way to pass a parameter/object to the test class.

Right now I am thinking to generate a Yaml file and read it in the test class but it feels "wrong" to use a temporary file for this. If anyone has a nicer solution that would be great!

**************Edit************

Example Code of what I am doing right now:

#!/usr/bin/ruby
require 'test/unit/ui/console/testrunner'
require 'yaml'
require 'TS_SampleTestSuite'

automatingSomething()
importantInfo = getImportantInfo()

File.open('filename.yml', 'w') do |f|
    f.puts importantInfo.to_yaml
end

Test::Unit::UI::Console::TestRunner.run(TS_SampleTestSuite)

Now in the example above TS_SampleTestSuite needs importantInfo, so the first "test case" is a method that just reads in the information from the Yaml file filname.yml.

I hope that clears up some confusion.

DmitryK
  • 5,542
  • 1
  • 22
  • 32
Nahir Khan
  • 31
  • 4
  • I think we'll need to see some code, in order to help much here. >probably< the solution involves mocks, but it's not clear from your question – Cameron Price Nov 12 '08 at 21:13
  • Please use something other than "foo" to make your examples a little more understandable. – mwilliams Nov 12 '08 at 21:15
  • I think there may be a related question out there somewhere, (about an equivalent of before(:all) for test/unit), but I can't find it. Sorry. – Andrew Grimm Feb 12 '10 at 02:40
  • http://stackoverflow.com/questions/255969/in-rubys-testunittestcase-how-do-i-override-the-initialize-method was the question I was looking for. – Andrew Grimm Oct 13 '11 at 22:45

2 Answers2

0

Overall, it looks like you're not really using the unit tests in a very rubyish way, but I'll leave that aside for a minute.

Your basic problem is that you have some setup that needs to happen before the tests run. The normal way to do that is with a setup method within the test unit case itself.

class UserTest < TestUnit::TestCase

  def setup
    # do your important calculation
  end

  def test_success
    #.. assert some things
  end
end

I would give some thought to what code it is that you're actually testing here, and see if you can break it down and test it in a more granular way, with lots more tests.

Cameron Price
  • 1,185
  • 8
  • 14
  • From my understanding the method 'setup' runs before each test. I have a setup method already, but I have to have things done before I can run the actual test suite at all. I realize that this isn't the conventional thing to do, but the actual testing is a small part of the whole thing. – Nahir Khan Nov 14 '08 at 16:33
0

First, I agree with Cameron, this code definitely does not adhere to the Ruby way, though I'll also sidestep that for now.

The fastest way to get up and running with this, especially if this data is pretty much immutable (that is to say, your tests won't be altering it in anyway), is to just assign the value to a constant. So instead of naming your variable importantInfo, you name it IMPORTANT_INFO. Then it will be available to you in your tests. It's definitely not a pretty solution, and I think it couuld even be considered a test smell that you need that sort of global setup, but it's there for you.

Alternatively, you could look at stubbing out the importantInfo, which I actually think would provide for much cleaner and more readable tests.

nakajima
  • 1,862
  • 12
  • 12
  • Ruby constants are not immutable. irb(main):001:0> IMPORTANT_INFO = "foo" => "foo" irb(main):002:0> IMPORTANT_INFO = "bar" (irb):2: warning: already initialized constant IMPORTANT_INFO => "bar" irb(main):003:0> p IMPORTANT_INFO "bar" => nil – mlibby Jan 06 '09 at 20:54