Skip to content

Commit 3f967c3

Browse files
Make AppSession compatible with pytest's capsys fixture + docs.
1 parent 6a58564 commit 3f967c3

File tree

2 files changed

+24
-3
lines changed

2 files changed

+24
-3
lines changed

Diff for: docs/pages/advanced_topics/unit_testing.rst

+15
Original file line numberDiff line numberDiff line change
@@ -116,6 +116,21 @@ single fixture that does it for every test. Something like this:
116116
with create_app_session(input=pipe_input, output=DummyOutput()):
117117
yield pipe_input
118118
119+
For compatibility with pytest's ``capsys`` fixture, we have to create a new
120+
:class:`~prompt_toolkit.application.current.AppSession` for every test. This
121+
can be done in an autouse fixture. Pytest replaces ``sys.stdout`` with a new
122+
object in every test that uses ``capsys`` and the following will ensure that
123+
the new :class:`~prompt_toolkit.application.current.AppSession` will each time
124+
refer to the latest output.
125+
126+
.. code:: python
127+
128+
from prompt_toolkit.application import create_app_session
129+
130+
@fixture(autouse=True, scope="function")
131+
def _pt_app_session()
132+
with create_app_session():
133+
yield
119134
120135
Type checking
121136
-------------

Diff for: src/prompt_toolkit/application/current.py

+9-3
Original file line numberDiff line numberDiff line change
@@ -147,11 +147,17 @@ def create_app_session(
147147
Like in the case of an Telnet/SSH server.
148148
"""
149149
# If no input/output is specified, fall back to the current input/output,
150-
# whatever that is.
150+
# if there was one that was set/created for the current session.
151+
# (Note that we access `_input`/`_output` and not `input`/`output` because
152+
# we don't want to accidently create a new input/output objects here and
153+
# store it in the "parent" `AppSession`. When combining pytest's `capsys`
154+
# fixture and `create_app_session`, sys.stdin/out/err are patched for every
155+
# test, so we don't want to leak an input/output object across
156+
# `AppSession`s.)
151157
if input is None:
152-
input = get_app_session().input
158+
input = get_app_session()._input
153159
if output is None:
154-
output = get_app_session().output
160+
output = get_app_session()._output
155161

156162
# Create new `AppSession` and activate.
157163
session = AppSession(input=input, output=output)

0 commit comments

Comments
 (0)