2012-12-15 12 views
14

Ich versuche, jede Instanz einer Klasse zu stubben. Ich muss die fetch Methode stub, die das Selbst mit einigen Daten füllt.RSpec any_instance return self

Wie kann ich Zugriff auf self Variable, ändern Sie es und Rückgabe an fetch Methode?

MyObject.any_instance.stub(:fetch) { self } 

gibt keine MyObject Instanz zurück.

Vielleicht ist Mocks in dieser Situation nützlicher. Leider habe ich sie noch nicht verstanden.

Antwort

1

Soweit ich das sehen kann, scheint dies aus irgendeinem Grund nicht möglich zu sein. Ich überprüfte die aktuelle rspec-mocks Implementierung und das Verfahren tatsächlich die Stub-Implementierung scheint Aufruf, die folgenden zu sein:

# lib/rspec/mocks/message_expectation.rb:450 
def call_implementation(*args, &block) 
    @implementation.arity == 0 ? @implementation.call(&block) : @implementation.call(*args, &block) 
end 

Wie es scheint, wird der Block einfach von selbst aufgerufen und nicht durch instance_eval. Vielleicht gibt es eine andere Technik, um zu erreichen, was Sie wollen, obwohl ich kein RSpec-Experte bin.

12

Es gibt eine open rspec-mocks issue, um dies zu adressieren. Ich hoffe, dass ich es irgendwann ansprechen kann, aber es ist nicht einfach, dies so hinzuzufügen, dass vorhandene Spec-Suites, die any_instance verwenden, nicht mit einer Blockimplementierung gebrochen werden, weil wir ein zusätzliches Argument liefern würden (zB das Objekt) Beispiel).

Insgesamt kann any_instance in einigen Situationen nützlich sein, aber es ist ein bisschen ein Geruch, und Sie haben im Allgemeinen weniger Probleme, wenn Sie eine Möglichkeit finden können, einzelne Instanzen zu verspotten oder zu stubben.

Hier ist eine Arbeit um, dass ich nicht getestet habe, sollte aber funktionieren:

orig_new = MyObject.method(:new) 
MyObject.stub(:new) do |*args, &block| 
    orig_new.call(*args, &block).tap do |instance| 
    instance.stub(:fetch) { instance } 
    end 
end 

Im Wesentlichen sind wir any_instance hier durch Einhaken in MyObject.new simuliert, so dass wir fetch auf jede neue Instanz Stummel können, die instanziiert wird.

Alles, was gesagt wird, ist es wichtig, "auf Ihre Tests zu hören", und wenn etwas schwer zu testen ist, überlegen Sie, was das über Ihr Design sagt, anstatt sofort Elektrowerkzeuge wie any_instance zu verwenden. Ihre ursprüngliche Frage gibt mir nicht genügend Kontext, um etwas über Ihr Design zu spekulieren, aber es ist definitiv, wo ich anfangen würde, wenn ich dazu gezwungen wäre.

+0

ich arbeitete nett für mich! Danke vielmals! – jethroo