2008-11-25 8 views
30
class A 
    def initialize 
    @x = do_something 
    end 

    def do_something 
    42 
    end 
end 

मूल कार्यान्वयन कहने से पहले मैं do_something को आरएसपीईसी में कैसे लगा सकता हूं (इस प्रकार 42 से @x असाइन कर रहा है)? और निश्चित रूप से कार्यान्वयन को बदलने के बिना।rspec: कन्स्ट्रक्टर द्वारा बुलाए गए एक इंस्टेंस विधि को कैसे दबाया जाए?

उत्तर

22

Here's the commit which adds the feature to rspec - यह 25 2008 मई को इस के साथ आप

A.any_instance.stub(do_something: 23) 

कर सकते हैं हालांकि, नवीनतम मणि v आरएसपीईसी (1.1.11, अक्टूबर 2008) के ersion में इस पैच में नहीं है।

This ticket कहता है कि उन्होंने इसे रखरखाव के कारणों से बाहर कर दिया है, और एक वैकल्पिक समाधान अभी तक प्रदान नहीं किया गया है।

ऐसा नहीं लगता है कि आप इस बिंदु पर ऐसा कर सकते हैं। आपको alias_method या somesuch का उपयोग कर कक्षा को मैन्युअल रूप से हैक करना होगा।

+3

प्रकट होता है यह है कि 2.6.0 के साथ वापस लाया गया है, तो यह अब वहां है ... – rogerdpack

+3

@rogerdpack: वास्तव में, अंत में! http://blog.davidchelimsky.net/2011/05/12/rspec-260-is-released/ "any_instance.stub और any_instance.should_receive के लिए समर्थन जोड़ें" – tokland

+0

कोई विचार अगर आप उस उदाहरण पर सीधे कुछ संलग्न करना चाहते हैं नए द्वारा, यद्यपि? like_receive (: blah) .exactlY (5)। टाइम्स --- और आप किसी भी वस्तु के लिए यह नहीं चाहते हैं, बस वह एक विशेष रूप से? – xaxxon

11

मैं ऐसा करने के लिए कैसे कल्पना की नकली ढांचे में पता नहीं है, लेकिन आप आसानी से निम्न करने के लिए मोचा के लिए बाहर यह स्वैप कर सकते हैं:

# should probably be in spec/spec_helper.rb 
Spec::Runner.configure do |config| 
    config.mock_with :mocha 
end 

describe A, " when initialized" do 
    it "should set x to 42" do 
    A.new.x.should == 42 
    end 
end 

describe A, " when do_something is mocked" do 
    it "should set x to 23" do 
    A.any_instance.expects(:do_something).returns(23) 
    A.new.x.should == 23 
    end 
end 
5

या RR साथ:

stub.any_instance_of(A).do_something { 23 } 
-1

rspec (1.2.2) के अपने संस्करण में मैं यह कर सकता:

A.should_receive(:new).and_return(42) 

मैं जानता हूँ कि यह शायद देर से मूल रूप से पोस्ट करने के लिए जवाब देने के लिए करने के लिए है, लेकिन मैं इसे वैसे भी भविष्य में संदर्भ के लिए जवाब, के रूप में मैं यहां एक ही प्रश्न के साथ आया था लेकिन यह पता लगाया कि यह नवीनतम आरएसपीईसी संस्करण पर काम कर रहा था।

+0

आपके सुझाव का व्यवहार सही नहीं है। यह है: do_something विधि जो 42 लौटाता है, प्रारंभकर्ता नहीं। –

0

एक उदाहरण विधि ठूंठ के लिए, आप कुछ इस तरह कर सकते हैं:

before :each do 
    @my_stub = stub("A") 
    @my_stub.should_receive(:do_something).with(no_args()).and_return(42) 
    @my_stub.should_receive(:do_something_else).with(any_args()).and_return(true) 
    A.stub(:new).and_return(my_stub) 
end 

लेकिन pschneider के रूप में बताया, बस नई पर 42 वापसी के साथ: A.stub(:new).and_return(42) या उस प्रभाव के लिए कुछ।

+0

मुझे लगता है कि जब आप अपने परीक्षण में उदाहरण बनाने के नियंत्रण में नहीं हैं तो इशारा विधि को स्टब करना है। इसके अलावा, प्रारंभकर्ता 42 वापस नहीं करता है, यह एक आवृत्ति चर सेट करता है: यह do_something विधि है जो 42 लौटाता है जिसे स्टब किया जाना चाहिए। –

+1

'एस्ट्यूब (: नया) .and_return (@my_stub)' हर बार इंस्टेंस स्टब लौटाएगा, इस प्रकार आपको इंस्टेंस निर्माण पर नियंत्रण देगा। जहां तक ​​सदस्य चर सेट करने के लिए, मैंने हमेशा सुना है कि आपको आंतरिक इंटरफेस, मॉकिंग/स्टबिंग में आंतरिक के बारे में चिंता करने की ज़रूरत नहीं है। तो, विधि के लिए सही मान वापस करें जो '@ x' पर निर्भर करता है। मैं शायद गलत हूं हालांकि – bluehavana

2

मैं डेनिस Barushev जवाब पसंद करते हैं पर इस समाधान मिल गया है। और मैं केवल एक कॉस्मेटिक बदलाव का सुझाव देना चाहता हूं जो new_method परिवर्तनीय अनावश्यक बनाता है। Rspec, टोंटदार तरीकों पर Munge करता है ताकि वे proxied_by_rspec__ उपसर्ग के साथ पहुँचा जा सकता है:


A.stub!(:new).and_return do |*args| 
    a = A.proxied_by_rspec__new(*args) 
    a.should_receive(:do_something).and_return(23) 
    a 
end 
+0

यह वास्तव में एक अच्छा विचार है, लेकिन यह उपयोग कर रहे आरएसपीसी के संस्करण के साथ काम करने में विफल रहता है। डेनिस का जवाब काम करता है। – emk

+0

धन्यवाद! हां, यह "proxied_by_rspec__" नाम उपसर्ग सम्मेलन पर बहुत निर्भर है जो प्रकाशित एपीआई का हिस्सा नहीं हो सकता है। ओह, और दूसरी पंक्ति पर ".call" की आवश्यकता नहीं है, क्षमा करें। बीटीडब्ल्यू आप किस आरएसपीईसी संस्करण का उपयोग कर रहे हैं? –

0

यहाँ एक विचार है जो बहुत ही सुंदर नहीं हो सकता है, लेकिन काम करने के लिए मूल रूप से यकीन है कि है:

एक छोटे से वर्ग बनाएं कि वर्ग आप, परीक्षण इनिशियलाइज़ विधि ओवरराइड और के बाद superकॉल करना चाहते हैं, इनिशियलाइज़ में स्टब्स बनाई होने विरासत में तो जैसे:

it "should call during_init in initialize" do 
    class TestClass < TheClassToTest 
    def initialize 
     should_receive(:during_init) 
     super 
    end 
    end 
    TestClass.new 
end 

और वहाँ यो तुम जाओ! मैंने इसे अपने परीक्षणों में से एक में सफलतापूर्वक उपयोग किया।

0

rspec_candy मणि stub_any_instance सहायक विधि के साथ आता है जो आरएसपीईसी 1 और आरएसपीसी 2 दोनों में काम करता है।

2
RSpec 2.6 में

या बाद में आप उपयोग कर सकते

A.any_instance.stub(do_something: 23) 

अधिक जानकारी के लिए the docs देखें। (उनका कहना है कि यह अब संभव है के लिए rogerdpack के लिए धन्यवाद - मुझे लगता है कि यह अपने आप में एक जवाब लायक)

3

आज के रूप में RSpec के नवीनतम संस्करण में - 3.5 आप कर सकते हैं:

allow_any_instance_of(Widget).to receive(:name).and_return("Wibble") 
संबंधित मुद्दे

 संबंधित मुद्दे