undefined方法,rails 4.1.9,rspec 3.1

时间:2015-02-03 18:31:45

标签: ruby-on-rails rspec

我有以下模块:

module BlackBird
  module PublishToSites
    module User

      @site = nil

      @params = nil

      @times = 5

      def self.publish_user(params, request_url)
        if Site.all != nil
          threads = []
          Site.all.each do |s|
            @site = s
            @params = params
            threads << Thread.new do
              responses = rescue_500(5) { publish(s, params) }
              deal_with_response(s, responses, request_url)
            end
          end

          return threads
        else
          # Send Email
          #  - Use No Sites Template
        end
      end

      private

      def self.publish(site, params)
        response = Typhoeus.post(
        site.site_api_url + 'users',
        :body => params.to_json,
        :headers => {
            "Authorization" => "Token token=\"#{site.site_api_key}\"",
            'Content-Type' => 'application/json'
          }
        )
        return response
      end

      def self.rescue_500(n , &block)
        responses = []
        (n-1).times {
          response = block.call
          if response.code == 500
            responses << response
            sleep 15
          else
            responses << response
            return responses.uniq(&:code)
          end
        }

        responses << block.call
        return responses.uniq(&:code)
      end

      def deal_with_response(site, responses, request_url)
        response.each do |response|
          if response.code == 200
            send_request(site.site_api_url, site.site_api_key, response, request_url)
          elsif response.code == 404
            send_request(site.site_api_url, site.site_api_key, response, request_url)
            GeneralMailer.recieved_404(ENV['ADMINISTRATOR_NAME'], ENV['ADMINISTRATOR_EMAIL'], site, response).deliver_now
          elsif response.code == 500
            send_request(site.site_api_url, site.site_api_key, response, request_url)
            GeneralMailer.recieved_500(ENV['ADMINISTRATOR_NAME'], ENV['ADMINISTRATOR_EMAIL'], site, response).deliver_now
          else
            send_request(site.site_api_url, site.site_api_key, response, request_url)
            GeneralMailer.recieved_error(ENV['ADMINISTRATOR_NAME'], ENV['ADMINISTRATOR_EMAIL'], site, response).deliver_now
          end
        end
      end

      def send_request(site, api_key, response, from_site)
        # do something here.
      end
    end
  end
end

它在名为private

deal_with_response(site, responses, request_url)下包含以下方法

它的“私有”不会导致此错误,因为我有其他测试来测试rescue_500方法。

以下测试:

it "should send no email (200)" do
  response = double("response", :code => 200)
  site = double("site", :site_api_url => 'http://google.ca', site_api_key: 'sdsadsasada')
  send_request_method = double()
  send_request_method.stub(:send_request).with(site.site_api_url, site.site_api_key, [response], 'http://google.ca').and_return nil

  expect{ BlackBird::PublishToSites::User.deal_with_response(site.site_api_url, response, 'http://google.ca') }.to_not change{ ActionMailer::Base.deliveries.count }
end

由于以下事实而失败:

1) BlackBird::PublishToSites::User Test that emails are being sent should send no email (200)
     Failure/Error: expect{ BlackBird::PublishToSites::User.deal_with_response(site.site_api_url, response, 'http://google.ca') }.to_not change{ ActionMailer::Base.deliveries.count }
     NoMethodError:
       undefined method `deal_with_response' for BlackBird::PublishToSites::User:Module
     # ./spec/blackbird/publish_to_sites/user_spec.rb:129:in `(root)'
     # ./spec/blackbird/publish_to_sites/user_spec.rb:129:in `(root)'

在这种情况下,第129行是:

expect{ BlackBird::PublishToSites::User.deal_with_response(site.site_api_url, response, 'http://google.ca') }.to_not change{ ActionMailer::Base.deliveries.count }

如何:deal_with_response未定义此模块?我错过了什么吗?一个错字?我看了5遍,我正在调用正确的方法......

1 个答案:

答案 0 :(得分:1)

模块中的其他方法被定义为模块方法(带def self.method_name),因此可以在模块本身上调用,而无需封装对象。 deal_with_response方法没有以这种方式定义,因此是一个实例方法,当包含模块时,它只能作为类的实例方法调用。

Source.