2017-03-23 4 views
2

Ich habe meine benutzerdefinierte Django-Middleware in der 1.10 style, ähnlich wie diese codiert:Testing individuelle Django Middleware ohne Django selbst

class MyMiddleware(object): 
    def __init__(self, get_response): 
     self.get_response = get_response 
     # some initialization stuff here 

    def __call__(self, request): 
     # Code executed before view functions are called. 
     # Purpose of this middeware is to add new attribute to request 

     # In brief: 
     request.new_attribute = some_function_returning_some_object() 
     response = self.get_response(request) 

     # Code to be executed for each request/response after 
     # the view is called. 

     return response 

Beachten Sie, dass diese Middleware zu sein als separate Python-Modul bedrohen wird, nicht gehört eine bestimmte Anwendung in meinem Projekt, aber leben außerhalb und installiert wie jedes andere Paket, über Pip. Es funktioniert nicht selbst, aber nur wenn es in der Django App installiert ist.

Es funktioniert gut, aber ich möchte es testen. Was ich habe, ist, so weit gemacht so etwas wie dies in my_tests.py:

from my_middleware_module import MyMiddleware 
# some @patches 
def test_mymiddleware(): 
    request = Mock() 
    assert hasattr(request, 'new_attribute') is False # passes obviously 
    # CALL MIDDLEWARE ON REQUEST HERE 
    assert hasattr(request, 'new_attribute') is True # I want it to pass 

Ich weiß nicht, wie Middleware auf request Variable nennen, ihn zu ändern. Ich denke, es wäre viel einfacher, wenn ich einen funktionsähnlichen Middleware-Stil verwenden würde, aber was ist, wenn ich bei dem, was ich habe, stecken bleibe und ich nur Tests schreiben sollte, ohne die Middleware zu modifizieren?

Antwort

3

Das Problem ist, dass Sie weder den Konstruktor MyMiddleware aufrufen, noch die magische Methode __call__ aufrufen, indem Sie die Instanz eines MyMiddleware Objekts aufrufen.

Es gibt viele Möglichkeiten, um das Verhalten zu testen, die Sie beschrieben, ich dieses man denken kann:

Zuerst habe ich leicht modifiziert Ihrem Beispiel zu sein Selbstversorger:

class MyMiddleware(object): 
    def __init__(self, get_response): 
     self.get_response = get_response 

    def __call__(self, request): 
     request.new_attribute = some_function_returning_some_object() 
     import ipdb; ipdb.set_trace() 
     response = self.get_response(request) 
     return response 

def some_function_returning_some_object(): 
    return 'whatever' 

Als nächstes habe ich die Tests, indem tatsächlich das Middleware-Objekt erstellt und das neu erstellte Objekt aufgerufen wird, da es eine Funktion war (so __call__ ausgeführt wird)

from mock import patch, Mock 
from middle import MyMiddleware 
import unittest 


class TestMiddleware(unittest.TestCase): 

    @patch('middle.MyMiddleware') 
    def test_init(self, my_middleware_mock): 
     my_middleware = MyMiddleware('response') 
     assert(my_middleware.get_response) == 'response' 

    def test_mymiddleware(self): 
     request = Mock() 
     my_middleware = MyMiddleware(Mock()) 
     # CALL MIDDLEWARE ON REQUEST HERE 
     my_middleware(request) 
     assert request.new_attribute == 'whatever' 

Hier sind einige nützliche Links:

Verwandte Themen