2012-03-12 22 views
5

लौटती है django परीक्षण के लिए pyazure लाइब्रेरी में कॉल करने की कोशिश कर रहा है, लेकिन मैं यह नहीं समझ सकता कि PyAzure क्लास कन्स्ट्रक्टर को कैसे नकल करना है ताकि यह कारण न हो एक टाइपरर क्या कनेक्शन लाइब्रेरी उत्पन्न करने वाली एक्सेस लाइब्रेरी को मॉक करने का कोई बेहतर तरीका है?उचित तरीका पाइथन मॉक __init __() विधि जो नकली कक्षा

कुछ भी मैं कोई नहीं के अलावा अन्य की कोशिश की है एक लेखन त्रुटि, जिसका मतलब है मैं वास्तव में यहां तक ​​कि वास्तविक रिटर्न मूल्यों के साथ PyAzure कनेक्शन से किसी भी विधि का परीक्षण करने शुरू नहीं कर सकते उत्पन्न करता है। नकली वर्ग के साथ नकली वर्ग के साथ एक मजदूर वर्ग को प्रतिस्थापित करने का सबसे अच्छा तरीका क्या है?

टेस्ट त्रुटि:

====================================================================== 
ERROR: test_management_certificate_connect (azure_cloud.tests.ViewsTest) 
---------------------------------------------------------------------- 
Traceback (most recent call last): 
    File "/Users/bschott/Source/django-nimbis/apps/azure_cloud/tests.py", line 107, in test_management_certificate_connect 
self.cert1.connect() 
File "/Users/bschott/Source/django-nimbis/apps/azure_cloud/models.py", line 242, in connect 
    subscription_id=self.subscription.subscription_id) 
TypeError: __init__() should return None, not 'FakeAzure' 
---------------------------------------------------------------------- 

tests.py:

class ViewsTest(TestCase): 
    def setUp(self): 
    ... 
     self.cert1 = ManagementCertificate.objects.create(
      name="cert1", 
      subscription=self.subscription1, 
      management_cert=File(open(__file__), "cert1.pem"), 
      owner=self.user1) 
    ... 

    class FakeAzure(object): 
     """ testing class for azure """ 
     def list_services(self): 
      return ['service1', 'service2', 'service3'] 
     def list_storages(self): 
      return ['storage1', 'storage2', 'storage3'] 

    @mock.patch.object(pyazure.PyAzure, '__init__') 
    def test_management_certificate_connect(self, mock_pyazure_init): 
     mock_pyazure_init.return_value = self.FakeAzure() 
     self.cert1.connect() 
     assert mock_pyazure_init.called 

models.py

class ManagementCertificate(models.Model): 

    # support connection caching to azure 
    _cached_connection = None 

    def connect(self): 
     """ 
     Connect to the management interface using these credentials. 
     """ 
     if not self._cached_connection: 
      self._cached_connection = pyazure.PyAzure(
       management_cert_path=self.management_cert.path, 
       subscription_id=self.subscription.subscription_id) 
      logging.debug(self._cached_connection) 
     return self._cached_connection 

उत्तर

11

आप __init__() क्या करता है के बारे में एक गलत धारणा है लगते हैं। इसका उद्देश्य एक उदाहरण शुरू करना है जो पहले से ही बनाया गया था। __init__() का पहला तर्क self है, जो उदाहरण है, इसलिए आप देख सकते हैं कि यह पहले ही आवंटित किया गया था जब __init__() कहा जाता है।

एक विधि __new__() है जिसे वास्तविक उदाहरण बनाने के लिए __init__() से पहले कहा जाता है। मुझे लगता है कि यह एक आसान तरीका होगा, हालांकि, एकल वर्ग को मॉक करने के बजाय, पूरे वर्ग को नकली कक्षा द्वारा प्रतिस्थापित करने के लिए।

+2

+1 इसके बजाए कक्षा को मॉक करें। –

+0

पॉइंटर्स के लिए धन्यवाद। मुझे पता था कि __init__ द्वारा लौटाई गई वस्तु को प्रतिस्थापित करना सिर्फ गलत महसूस किया गया था, लेकिन कहीं भी नकली दस्तावेज़ों में मुझे यह नहीं पता था कि वे वास्तविक कक्षाओं का नकल करते हैं। कक्षा के तरीके, हाँ, लेकिन कक्षाएं खुद नहीं। अब यह स्पष्ट प्रतीत होता है, लेकिन यह एक घंटे पहले नहीं था :-)। @ mock.patch.object (pyazure, 'PyAzure', कल्पना = pyazure.PyAzure) डीईएफ़ test_management_certificate_connect (स्वयं, mock_pyazure): self.cert1.connect() mock_pyazure.assert_called_with ('foo', 'बार') – bfschott

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