ruby-on-rails-3cucumberdynamic-attributes

Testing dynamic attributes with cucumber, undefined method


We have a Style model with dynamic attributes, which can be saved by filling one field with the attribute key and the next field with the value.

A typical params hash looks like this:

{"utf8"=>"✓", "style"=>{"collection_id"=>"48", "program_id"=>"989", "number"=>"454632", "name"=>"t67f", "category_id"=>"19", "field_KEY"=>"VALUE"}, "commit"=>"save", "id"=>"4521"}

This works as intended when clicking it through, and the "field_KEY" => "VALUE" pair creates a new dynamic attribute with a getter(field_KEY) and setter(field_KEY=) method.

The Problem is: If the process is simulated with cucumber, something calls the getters for all keys in the hash before the attributes are set, including field_KEY.

Normal attributes will return nil for a new record, but since the getter for field_KEY has not yet been created, this results in an

`UndefinedMethodError: undefined method 'field_KEY'`.

Now my question: would you rather track down the caller of the field_KEY getter and mess around with cucumber, or should I try to simulate a fake method, something like:

def check_method(method_name)
    if method_name =~ /^field_/
       nil
    else
       ... # let the Error be raised
end

Better ideas or solutions are more than welcome

Thanks


Solution

  • The Problem was:

    The call to field_KEY came from pickle, because I included the step

    And the style's "field_KEY" should be "VALUE"
    

    which looks like this:

    Then(/^#{capture_model}'s (\w+) (should(?: not)?) be #{capture_value}$/) do |name, attribute, expectation, expected|
      actual_value  = model(name).send(attribute)
      expectation   = expectation.gsub(' ', '_')
    
      case expected
      when 'nil', 'true', 'false'
        actual_value.send(expectation, send("be_#{expected}"))
      when /^[+-]?[0-9_]+(\.\d+)?$/
        actual_value.send(expectation, eql(expected.to_f))
      else
        actual_value.to_s.send(expectation, eql(eval(expected)))
      end
    end
    

    I still don't know why the dynamic_attribute getter had not been created up to this point.

    What I ended up doing:

    In my opinion (also, it solved the problem ;)), cucumber tests should be black-box tests, thats why I chose to change the steps and now I use

    And   the "key1" field should contain "KEY"
    

    which checks if the field has been filled with the correct value after the page reloads.