2017-06-16 3 views
0

Ich habe meine Methode create:Wie testet man mit rspec ob eine Methode innerhalb einer anderen Methode aufgerufen wurde?

module AnswerCreator 
    class Creator 
    def initialize(answer) 
     @answer = answer 
    end 

    def create 
     test_cases_results = run_test_cases 
     @answer.attempt = get_attempt_number 
     @answer.correct = correct?(test_cases_results) 

     ActiveRecord::Base.transaction do 
     @answer.save! 
     save_test_cases_results(test_cases_results) 
     Scorer::Changer.new(@answer).change 
     end 

     ComputeAnswerSimilarityJob.perform_later(@answer) 
    end 

    ... 

    end 
end 

Und ich habe den folgenden Test, um es:

it "creates the answer with the right attempt number, create the test case results and add the answer to be processed in background" do 
     answer_test_case_result_count = AnswerTestCaseResult.count 
     jobs_count = enqueued_jobs.size 

     user = create(:user) 
     team = create(:team) 
     question = create(:question) 
     create_pair(:test_case, question: question) 
     create(:answer, question: question, user: user, team: team) 
     answer = build(:answer, question: question, user: user, team: team) 

     # These answers must be ignored >> 
     create(:answer, question: question, user: user) 
     create(:answer, question: question, team: team) 
     create(:answer, user: user, team: team) 

     described_class.new(answer).create 

     expect(answer.new_record?).to be_falsey 
     expect(answer.attempt).to eq 2 
     expect(AnswerTestCaseResult.count).to eq answer_test_case_result_count + 2 
     expect(enqueued_jobs.size).to eq jobs_count + 1 
     end 

Diese Creator Klasse beschäftigt sich mit der Schaffung Logik, wenn ein Antwort-Objekt erstellt wird. Meine Klasse Changer behandelt die Bewertungslogik eines Antwortobjekts. Ich möchte diese Logik nicht innerhalb der Creator testen, aber ich möchte sicherstellen, dass die change Methode von Changer aufgerufen wird.

Wie kann ich das testen?

Antwort

1

So haben Sie diese Codezeile Sie testen möchten:

Scorer::Changer.new(@answer).change 

Mein erster Gedanke ist allow_any_instance_of zu empfehlen, aber wie Sie in diesem Link sehen, rät der RSpec Team dagegen. Wenn Sie wollten, obwohl, können Sie dies in den Testfall setzen, vor dem Aufruf Creator#create:

expect_any_instance_of(Scorer::Changer).to receive(:change).and_call_original 

withoug expect_any_instance_of, nach bestem Wissen und Gewissen würden Sie den Konstruktor Stummel müssen:

fake_answer = "???" # change to the value of 'answer' in your test case 
fake_changer = Scorer::Changer.new fake_answer 
expect(Scorer::Changer).to receive(:new).and_return fake_changer 
expect(fake_changer).to receive(:change).and_call_original 

Diese Art der Sache ist ein wenig mühsam, aber was passiert, wenn Funktionen in Bezug auf den privaten Staat viel los sind. Wie zum Beispiel, wenn Sie den Scorer::Changer.new Anruf auf Creator#initialize verschoben haben?

attr_reader :changer 
def initialize(answer) 
    @answer = answer 
    @changer = Scorer::Changer.new @answer 
end 

Dann müssen Sie ein wenig weniger Anstoßen tun:

fake_answer = "???" 
creator = AnswerCreator::Creator.new fake_answer 
expect(creator.changer).to receive(:change).and_call_original 
creator.create 
+0

alle Optionen hat gut funktioniert. Danke vielmals! – rwehresmann

Verwandte Themen