2014-07-10 11 views
12

hat derzeit ein Projekt konfiguriert wie so Berichterstattung über Djangos verwalten Befehl auszuführen:Wie Deckung testen richtig mit Django + Nose

Dies wie folgt in einem Bericht ergibt:

Name      Stmts Miss Branch BrMiss Cover Missing 
-------------------------------------------------------------------------- 
notify.decorators    4  1  0  0 75% 4 
notify.handlers     6  1  2  0 88% 11 
notify.notification_types  46  39  2  0 19% 8-55, 59, 62, 66 
notify.notifications   51  51  0  0  0% 11-141 
-------------------------------------------------------------------------- 
TOTAL       107  92  4  0 17% 

Es gibt jedoch ein Problem mit diesem Bericht. Es ist falsch. Coverage markiert Linien fehlen, obwohl sie tatsächlich von Tests abgedeckt werden. wenn ich die Tests über nosetests statt Djangos verwalten Befehl ich folgenden korrekten Bericht zum Beispiel erhalten laufen:

Name      Stmts Miss Branch BrMiss Cover Missing 
----------------------------------------------------------------------------- 
notify.decorators    4  0  0  0 100% 
notify.handlers     6  0  2  0 100% 
notify.notification_types  46  0  2  0 100% 
notify.notifications   51  25  0  0 51% 13, 18, 23, 28, 33, 38, 43, 48, 53, 65, 70, 75, 80, 85, 90, 95, 100, 105, 110, 116, 121, 126, 131, 136, 141 
----------------------------------------------------------------------------- 
TOTAL       107  25  4  0 77% 

Google führte mich in die FAQ Berichterstattung Website http://nedbatchelder.com/code/coverage/faq.html

F: Warum die Körper von Funktionen (oder Klassen) zeigen als ausgeführt, aber die def Zeilen nicht?

Dies geschieht, weil die Erfassung gestartet wird, nachdem die Funktionen definiert wurden. Die Definitionszeilen werden ohne Coverage-Messung ausgeführt, dann wird die Coverage gestartet und die Funktion aufgerufen. Dies bedeutet, dass der Körper gemessen wird, aber die Definition der Funktion selbst nicht.

Um dies zu beheben, starten Sie die Abdeckung früher. Wenn Sie Ihr Programm mit Coverage über die Befehlszeile ausführen, wird Ihr gesamtes Programm überwacht. Wenn Sie die API verwenden, müssen Sie vor dem Importieren der Module, die Ihre Funktionen definieren, coverage.start() aufrufen.

Die Frage ist, kann ich die Berichterstattung Berichte ordnungsgemäß über Django verwalten Befehl ausführen? Oder muss ich umgehen umgehen, um die Situation zu vermeiden, in der die Abdeckung gestartet wird, nachdem die "fehlenden" Zeilen ausgeführt wurden?

Antwort

12

Zur Zeit ist es nicht möglich, neben der Django-Nase (wegen der Art und Weise, wie Django 1.7 Modelle lädt), die Abdeckung genau auszuführen. Also die Berichterstattung Statistiken zu erhalten, müssen Sie coverage.py direkt von der Kommandozeile verwenden, zB:

$ coverage run --branch --source=app1,app2 ./manage.py test 
$ coverage report 
$ coverage html -d coverage-report 

Sie coverage.py Einstellungen in .coveragerc Datei im Projektstamm setzen können (das gleiche Verzeichnis wie verwalten. py).

Dieses Problem auf django-Nase GitHub Seite berichtet wird: https://github.com/django-nose/django-nose/issues/180 so wissen Maintainer über das Problem, können Sie sie wissen lassen, dass Sie auch dieses Problem zu erfahren.

UPDATE

eliangcs wies darauf hin, (django-Nase Fragen auf GiHub), dass woraround ist Ihr manage.py zu ändern:

import os 
import sys 

if __name__ == "__main__": 
    # ... 
    from django.core.management import execute_from_command_line 

    is_testing = 'test' in sys.argv 

    if is_testing: 
     import coverage 
     cov = coverage.coverage(source=['package1', 'package2'], omit=['*/tests/*']) 
     cov.erase() 
     cov.start() 

    execute_from_command_line(sys.argv) 

    if is_testing: 
     cov.stop() 
     cov.save() 
     cov.report() 

Es funktioniert, aber es ist eher "Hacky" -Ansatz.

UPDATE 2

ich jedem empfehlen, die Nase einen Blick auf py.test (http://pytest.org/) zu haben, verwendet, die wirklich gut Test-Tool Python ist es gut mit Django integriert hat, eine Menge von Plugins und viele mehr. Ich benutzte Django-Nase, aber versuchte py.test und schaute nie zurück.

+1

Dies ist die praktischste Lösung (obwohl hacky) und funktioniert perfekt und transparent mit Django-Nase – danigosa

5

Da die docs sagen: „die Befehlszeile verwenden Ihr Programm mit Abdeckung laufen“:

coverage run --branch --source=notify ./manage.py test 
+0

Danke Ned. Meine Frage war speziell, ob es möglich ist, durch zu verwalten und die richtigen Ergebnisse zu erhalten. Würde ich richtigerweise annehmen, dass es keinen Weg gibt? – kaptainlange

+0

Ich weiß nicht, warum - mit Abdeckung funktioniert für einige Leute und nicht für andere. –

0

Ich habe es geschafft, diese Funktion zu erhalten, die eine

import coverage 

auf meinem manage.py Datei (Ich benutze stattdessen Flask, aber mit dem gleichen Problem)

Mein Problem ist, dass es von der Konsole funktioniert, aber Jenkins ist sich dessen nicht bewusst und sagt weiter, dass diese Importe aus der te sind sts ...

Irgendwelche Idee?

0

Ich hatte das gleiche Problem mit einem Remote-Interpreter in einer virtuellen Maschine durch die SSH-Konfiguration. Die Lösung war, meine Tests Verzeichnis und ALL seine übergeordneten Verzeichnisse in den "Path mappings" der "Umgebung" Abschnitt von "Ausführen"> "Konfigurationen bearbeiten ..." zu setzen.