2

I have a module and it includes activemodel and I want to test it using rspec.

This is my setup so far:

lib/
 |__ my_module/
 |    |__ base.rb 
 |__ my_module.rb
spec/
 |__ my_module_spec.rb
 |__ spec_helper.rb
 |__ support/
      |__ shared_examples/
           |__ active_model.rb

inside 'my_class.rb':

require "active_model"
require "my_module/base"

inside 'base.rb':

module MyModule
  class Base
    extend ActiveModel::Naming

    include ActiveModel::Conversion
    include ActiveModel::Validations
  end
end

inside 'my_module_spec.rb':

require 'spec_helper'

describe MyModule do
  describe MyModule::Base do
    it_behaves_like "ActiveModel"
  end
end

inside 'spec_helper.rb':

$LOAD_PATH.unshift(File.join(File.dirname(__FILE__), '..', 'lib'))
$LOAD_PATH.unshift(File.dirname(__FILE__))
require 'rspec'
require 'my_module'

# Requires supporting files with custom matchers and macros, etc,
# in ./support/ and its subdirectories.
Dir["#{File.dirname(__FILE__)}/support/**/*.rb"].each {|f| require f}

RSpec.configure do |config|
end

inside 'active_model.rb':

# taken from http://pivotallabs.com/users/jdean/blog/articles/1706-form-backing-objects-for-fun-and-profit

shared_examples_for "ActiveModel" do
  require 'test/unit/assertions'
  require 'active_model/lint'
  include Test::Unit::Assertions
  include ActiveModel::Lint::Tests

  before do
    @model = subject
  end

  ActiveModel::Lint::Tests.public_instance_methods.map { |method| method.to_s }.grep(/^test/).each do |method|
    example(method.gsub('_', ' ')) { send method }
  end
end

I thought my setup is alright but when I tried to run bundle exec rspec spec I am getting these errors:

Failures:

  1) MyModule MyModule::Base behaves like ActiveModel test to key
     Failure/Error: example(method.gsub('_', ' ')) { send method }

  2) MyModule MyModule::Base behaves like ActiveModel test to param
     Failure/Error: example(method.gsub('_', ' ')) { send method }

  3) MyModule MyModule::Base behaves like ActiveModel test to partial path
     Failure/Error: example(method.gsub('_', ' ')) { send method }

  4) MyModule MyModule::Base behaves like ActiveModel test valid?
     Failure/Error: example(method.gsub('_', ' ')) { send method }

  5) MyModule MyModule::Base behaves like ActiveModel test persisted?
     Failure/Error: example(method.gsub('_', ' ')) { send method }

  6) MyModule MyModule::Base behaves like ActiveModel test model naming
     Failure/Error: example(method.gsub('_', ' ')) { send method }

  7) MyModule MyModule::Base behaves like ActiveModel test errors aref
     Failure/Error: example(method.gsub('_', ' ')) { send method }

  8) MyModule MyModule::Base behaves like ActiveModel test errors full messages
     Failure/Error: example(method.gsub('_', ' ')) { send method }

What am I doing wrong here? How do I test ActiveModel properly?

Thanks in advance

Cecille Manalang
  • 213
  • 3
  • 14
  • I made it work by changing subject to MyModule::Base.new. In active_model.rb `before do @model = subject end` should be `before do @model = MyModule::Base.new` – Cecille Manalang Feb 03 '12 at 16:41

1 Answers1

0

You try to do too much. Because you want test the ActiveModel library. You just need test if your Object include this module


require 'spec_helper'

describe MyModule do
  describe MyModule::Base do
    it { MyModule::Base.should include(ActiveModel::Conversion) }
    it { MyModule::Base.should include(ActiveModel::Validations) }
  end
end
shingara
  • 46,608
  • 11
  • 99
  • 105
  • yeah that's probably a cleaner alternative, but what i really want is to see if ActiveModel methods will integrate with my class without any failure, and that is why ActiveModel::Lint::Tests is really important for me. Thanks for the idea though. I really appreciate it. – Cecille Manalang Feb 03 '12 at 16:48
  • 1
    You can see how dm-rails do this jobs so : like https://github.com/datamapper/dm-active_model/blob/master/spec/amo_validation_compliance_spec.rb – shingara Feb 07 '12 at 13:31
  • 2
    This is actually a wrong answer. If you're creating a model that behaves like ActiveModel it should comply with the ActiveModel API. The ActiveModel::Lint::Tests are there to make sure your model complies with such API. – Leo Correa May 30 '13 at 15:14