0

ダブル/スタブを使用してテストを作成しています。偽の値を返したいのですが、代わりに偽の値と実際の値を取得しています。これが私のコントローラーとスペックファイルです。モデルには何も含まれていません。私が間違っていることは何ですか?私の推測では、私はそれを完全に間違っています。PS私はスペックやモック/スタブのものにちょっと新しいです

コントローラ:

def destroy
    uri = URI('example.com')
    request_params = {'requestId' => @session.id, 
      'merchantId' => MERCHANTID, 
      'locale' => LOCALE, 
      'partnerId' => PARTNERID, 
      'sessionId' => params[:id]
    }

   Net::HTTP.start(uri.host, uri.port, :use_ssl => uri.scheme == 'https') do |http|
      request = Net::HTTP::Post.new uri.request_uri
      request.set_form_data(request_params)
      #request.content_type = 'application/x-www-form-urlencoded'
      response = http.request request # Net::HTTPResponse object
      json = ActiveSupport::JSON.decode(response.body)
      puts '<<<<<<<<<'
      puts json
      if json['expireSessionRes']['isError'] == false
        render :json => {:status => 'ok', :message => 'logged out'}
      else
        render :json => {:status => 'failed', :message => 'logout failed'}
      end
    end

スペックファイル:

it "should correctly return isError false if logout was sucessful" do
    SID = "123"
    @data3 = {:id => SID}  
    delete :destroy, default_rest_params.merge(@data3)
    response = double('http.request')
    response.stub!(:body => '{"expireSessionRes"=>{"requestId"=>"72", "sessionId"=>"123", "isError"=>false, "desc"=>""}}')
    puts response.body


  end

受信:

{"expireSessionRes"=>{"requestId"=>"94", "isError"=>true, "desc"=>"Session exipred", "errorCode"=>"-10011"}}
{"expireSessionRes"=>{"requestId"=>"72", "sessionId"=>"123", "isError"=>false, "desc"=>""}}

最初はコントローラーから、2番目はスタブから来ます

4

1 に答える 1

1

したがって、モックとスタブの問題は、モックオブジェクトを実際のコードにフックする必要があるということです...double('http.request')ビットは「http.request」と呼ばれるモックオブジェクトを作成するだけで、このオブジェクトは返されませんhttp.request

あなたがする必要があるのはrequest、モック応答を返すためにメソッドをスタブ化することです。httpただし、テストからブロック内のオブジェクトにアクセスできないため、モックを挿入するのはかなり困難になります。

コードのテストの難しさは、多くの場合、コードをリファクタリングする必要があることを示す良い兆候です。

Net::HTTP.start最も簡単なのは、全体を1行に置き換えることです。

response = Net::HTTP.post_form(uri, request_params)

そして、あなたはそれを行うことによってそれをテストすることができます

remote_response = double('remote_response', body: '...')
Net::HTTP.stub(:post_form).and_return(remote_response)

delete :destroy, ...

response.should whatever

(コントローラー仕様を使用していて、RSpecが提供するオブジェクトが必要になると想定してresponseいるため、モックをと呼ばれる変数に格納することはできませんresponse)。

しかし、それは、リモートサービスの相互作用を専用のクラスに抽出し、それを個別にテストする必要があるという、より重要な点をざっと見ただけです。それはコントローラーに属していません。

お役に立てば幸いです。

于 2012-11-21T10:46:15.480 に答える