550 Stimmen

Wie drucke ich in pytest auf die Konsole?

pytest wird nicht auf der Konsole ausgegeben, wenn ich print verwende. Die Dokumentation scheint zu sagen, dass es standardmäßig funktionieren sollte.

Ich benutze pytest my_tests.py, um diesen Test auszuführen:

import myapplication as tum

class TestBlogger:
    @classmethod
    def setup_class(self):
        self.user = "alice"
        self.b = tum.Blogger(self.user)
        print "Das sollte gedruckt werden, aber es wird nicht!"

    def test_inherit(self):
        assert issubclass(tum.Blogger, tum.Site)
        links = self.b.get_links(posts)
        print len(links)   # Das wird auch nicht gedruckt.

Nichts wird auf meiner Standardausgabe-Konsole gedruckt (nur der normale Fortschritt und wie viele Tests bestanden/fehlgeschlagen sind).

Und das Skript, das ich teste, enthält print:

class Blogger(Site):
    get_links(self, posts):
        print len(posts)   # Es wird im Test nicht gedruckt.

Im unittest Modul wird standardmäßig alles gedruckt, was genau das ist, was ich brauche. Allerdings möchte ich aus anderen Gründen pytest verwenden.

Weiß jemand, wie man die print-Anweisungen anzeigen lassen kann?

491voto

tbekolay Punkte 16083

Standardmäßig erfasst py.test das Ergebnis der Standardausgabe, um steuern zu können, wie es gedruckt wird. Wenn dies nicht gemacht würde, würde es viel Text ohne den Kontext ausgeben, welcher Test diesen Text gedruckt hat.

Wenn jedoch ein Test fehlschlägt, wird er einen Abschnitt im resultierenden Bericht enthalten, der zeigt, was bei diesem bestimmten Test an die Standardausgabe gedruckt wurde.

Zum Beispiel,

def test_good():
    for i in range(1000):
        print(i)

def test_bad():
    print('this should fail!')
    assert False

Ergebnis in der folgenden Ausgabe:

>>> py.test tmp.py
============================= test session starts ==============================
platform darwin -- Python 2.7.6 -- py-1.4.20 -- pytest-2.5.2
plugins: cache, cov, pep8, xdist
collected 2 items

tmp.py .F

=================================== FAILURES ===================================
___________________________________ test_bad ___________________________________

    def test_bad():
        print('this should fail!')
>       assert False
E       assert False

tmp.py:7: AssertionError
------------------------------- Captured stdout --------------------------------
this should fail!
====================== 1 failed, 1 passed in 0.04 seconds ======================

Beachten Sie den Abschnitt Caputured stdout.

Wenn Sie die print Anweisungen sehen möchten, wie sie ausgeführt werden, können Sie dem py.test den -s Flag übergeben. Beachten Sie jedoch, dass dies manchmal schwer zu interpretieren sein kann.

>>> py.test tmp.py -s
============================= test session starts ==============================
platform darwin -- Python 2.7.6 -- py-1.4.20 -- pytest-2.5.2
plugins: cache, cov, pep8, xdist
collected 2 items

tmp.py 0
1
2
3
... und so weiter ...
997
998
999
.this should fail!
F

=================================== FAILURES ===================================
___________________________________ test_bad ___________________________________

    def test_bad():
        print('this should fail!')
>       assert False
E       assert False

tmp.py:7: AssertionError
====================== 1 failed, 1 passed in 0.02 seconds ======================

453voto

lmiguelvargasf Punkte 50452

Verwenden Sie die Option -s:

pytest -s

Detaillierte Antwort

Aus den Docs:

Während der Testausführung wird jegliche Ausgabe, die an stdout und stderr gesendet wird, erfasst. Wenn ein Test oder eine Setup-Methode fehlschlägt, wird normalerweise die entsprechende erfasste Ausgabe zusammen mit dem Fehler-Traceback angezeigt.

pytest hat die Option --capture=method, wobei method die pro-Test-Erfassungsmethode ist und eine der folgenden sein kann: fd, sys oder no. pytest hat auch die Option -s, die eine Abkürzung für --capture=no ist, und dies ist die Option, die es Ihnen ermöglicht, Ihre Ausgabeanweisungen in der Konsole zu sehen.

pytest --capture=no     # Ausgabeanweisungen in Konsole anzeigen
pytest -s               # entspricht dem vorherigen Befehl

Einstellen von Erfassungsmethoden oder Deaktivieren der Erfassung

Es gibt zwei Möglichkeiten, wie pytest Erfassung durchführen kann:

  1. Erfassung auf Dateideskriptorebene (FD) (Standard): Alle Schreibvorgänge auf die Betriebssystem-Dateideskriptoren 1 und 2 werden erfasst.

  2. Erfassung auf sys-Ebene: Es werden nur Schreibvorgänge auf Python-Dateien sys.stdout und sys.stderr erfasst. Es erfolgt keine Erfassung von Schreibvorgängen auf Dateideskriptoren.

    pytest -s # alle Erfassung deaktivieren pytest --capture=sys # sys.stdout/stderr durch In-Memory-Dateien ersetzen pytest --capture=fd # auch Dateideskriptoren 1 und 2 auf Temp-Datei zeigen

115voto

dmitry_romanov Punkte 4722

Die Verwendung der -s-Option gibt den Output aller Funktionen aus, was möglicherweise zu viel ist.

Wenn Sie einen bestimmten Output benötigen, bietet die von Ihnen erwähnte Dokumentationsseite einige Vorschläge:

  1. Fügen Sie am Ende Ihrer Funktion assert False, "dumb assert to make PyTest print my stuff" ein, und Sie werden Ihren Output aufgrund des fehlgeschlagenen Tests sehen.

  2. Sie erhalten von PyTest ein spezielles Objekt übergeben, und Sie können den Output in eine Datei schreiben, um ihn später zu überprüfen, so wie

    def test_good1(capsys):
        for i in range(5):
            print i
        out, err = capsys.readouterr()
        open("err.txt", "w").write(err)
        open("out.txt", "w").write(out)

    Sie können die Dateien out und err in einem separaten Tab öffnen und den Editor automatisch aktualisieren lassen, oder Sie führen einfach den Shell-Befehl py.test; cat out.txt aus, um Ihren Test auszuführen.

Das ist eine ziemlich hackische Art, Dinge zu erledigen, aber vielleicht ist es das, was Sie brauchen: Letztendlich bedeutet TDD, dass Sie mit Dingen herumspielen und sie sauber und still hinterlassen, wenn sie bereit sind :-).

59voto

Sacha Punkte 883

Dies ist der sauberste Weg, den ich kenne, um eine einzelne Anweisung nach sys.stdout zu drucken (ohne künstlich Ihren Test fehlschlagen zu lassen oder die -s Option zu aktivieren) - Sie sehen die spezifische Ausgabe, die Sie möchten, und nichts weiter:

  1. Fügen Sie den integrierten Parameter capsys zu Ihrer Testfunktion hinzu. (Das bedeutet, dass Sie capsys der Parameterliste hinzufügen, z.B.

    def test_function(existing_parameters, capsys):

  2. Fügen Sie einfach in Ihrem Code ein:

    with capsys.disabled(): print("Diese Ausgabe wird nicht erfasst und geht direkt nach sys.stdout")

Siehe https://buildmedia.readthedocs.org/media/pdf/pytest/latest/pytest.pdf (2.11 Wie man stdout/stderr Ausgaben erfasst).

20voto

dmitry_romanov Punkte 4722

Ich musste eine wichtige Warnung über übersprungene Tests drucken, genau als PyTest buchstäblich alle gemutet hat.

Ich wollte keinen Test fehlschlagen lassen, um ein Signal zu senden, also habe ich folgenden Hack gemacht:

def test_2_YellAboutBrokenAndMutedTests():
    import atexit
    def report():
        print C_patch.tidy_text("""
Im stillen Modus zerbricht PyTest die Stream-Struktur auf niedriger Ebene, mit der ich arbeite, so dass ich nicht testen kann, ob meine Funktionalität in Ordnung ist. Ich habe entsprechende Tests übersprungen.
Führen Sie `py.test -s` aus, um sicherzustellen, dass alles getestet wird.""")
    if sys.stdout != sys.__stdout__:
        atexit.register(report)

Das Modul atexit erlaubt es mir, nachdem PyTest die Ausgabeströme freigegeben hat, etwas zu drucken. Die Ausgabe sieht wie folgt aus:

============================= test session starts ==============================
platform linux2 -- Python 2.7.3, pytest-2.9.2, py-1.4.31, pluggy-0.3.1
rootdir: /media/Storage/henaro/smyth/Alchemist2-git/sources/C_patch, inifile: 
collected 15 items 

test_C_patch.py .....ssss....s.

===================== 10 passed, 5 skipped in 0.15 seconds =====================
Im stillen Modus zerbricht PyTest die Stream-Struktur auf niedriger Ebene, mit der ich arbeite, so dass ich nicht testen kann, ob meine Funktionalität in Ordnung ist. Ich habe entsprechende Tests übersprungen.
Führen Sie `py.test -s` aus, um sicherzustellen, dass alles getestet wird.
~/.../sources/C_patch$

Die Nachricht wird auch gedruckt, wenn PyTest im stillen Modus ist, und wird nicht gedruckt, wenn Sie Sachen mit py.test -s ausführen, also ist bereits alles schön getestet.

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X