views:

9

answers:

1

In a class called 'Quality' I have the following constants defined:

class Quality < ActiveRecord::Base

  [validations excluded in this example]

  NEW = Quality.find_by_name("New")
  LGT = Quality.find_by_name("Light use")
  MED = Quality.find_by_name("Medium use")
  HVY = Quality.find_by_name("Heavy use")
  SCR = Quality.find_by_name("Scrap")
  ANY = Quality.find_by_name("Any")

end

When running my unit tests, these constants are all nil. Why? I'm sure they're not nil during production/development since the code that uses these seems to work in my dev/prod environments.

I've setup fixtures for these records, so I expect the constant initialization to work. My fixture for qualities appears below. These fixtures are in a file at 'test/fixtures/qualities.yml'

any:
  value: 0
  name: Any
  extended_name: /all

new:
  value: 5
  name: New
  extended_name:  (or like new)

lgt:
  value: 4
  name: Light use
  extended_name:  (cosmetic damange only)

med:
  value: 3
  name: Medium use
  extended_name:  (some functional damange)

hvy:
  value: 2
  name: Heavy use
  extended_name:  (needs work)

scr:
  value: 1
  name: Scrap
  extended_name: (only good for parts)

Finally, here's my unit test, which fails with 'Expected not nil'

test "all constant qualities are not nil" do
  assert_not_nil Quality::ANY
  assert_not_nil Quality::NEW
  assert_not_nil Quality::LGT
  assert_not_nil Quality::MED
  assert_not_nil Quality::HVY
  assert_not_nil Quality::SCR
end
+1  A: 

it's because your database is empty when your class is loaded. All fixtures are insert after your class Loading.

If you want this behaviour I propose you to have this data in your class attributes it's better.

class

  def self.lgt
    @@lgt ||= Quality.find_by_name("Light use")
  end

  def self.med
    @@med ||= Quality.find_by_name("Medium use")
  end

  etc..

end

With this case you data is loaded only 1 time and only when you really need it.

test "all constant qualities are not nil" do
  assert_not_nil Quality.lgt
  assert_not_nil Quality.med
end

Using Constante for that is really bad solution.

shingara
agree with that - you really should not use constants this way
pawien
Ah! It's a matter of the order of things. Thank you!
normalocity
Worked like a champ. I've been wanting to get rid of these constants anyway, but didn't know how best to do it. Two birds, one stone as they say.
normalocity