Setup
I've simplified the problem to the core:
- Having pytest installed
pip install pytest==5.4.3
- Having a shell script
# has-stdin.sh
# Detect stdin
if [[ ! -t 0 ]]; then
echo "yes"
else
echo "no"
fi
- Having a Python test
# test.py
import subprocess
import unittest
class TestCase(unittest.TestCase):
def test(self):
process = subprocess.run(
["sh", "./has-stdin.sh"],
stderr=subprocess.PIPE,
stdout=subprocess.PIPE,
check=True,
shell=False
)
assert process.stdout.decode("utf-8") == "no\n"
Testing
✅ Script works in a bash shell
$ sh ./has-stdin.sh
no
$ echo '' | sh ./has-stdin.sh
yes
$ sh ./has-stdin.sh <<< ''
yes
✅ Runs successfully with -s (e.g. --capture=no)
$ pytest test.py -s
platform linux -- Python 3.7.7, pytest-5.4.3, py-1.9.0, pluggy-0.13.1
rootdir: /Users/maikel/docker/library/postgresql
collected 1 item
test.py .
=========================== 1 passed in 0.02s ===========================
❌ Runs unsuccessfully without -s
$ pytest test.py
========================== test session starts ==========================
platform linux -- Python 3.7.7, pytest-5.4.3, py-1.9.0, pluggy-0.13.1
rootdir: /Users/maikel/docker/library/postgresql
collected 1 item
test.py F [100%]
================================ FAILURES ===============================
_____________________________ TestCase.test _____________________________
self = <test.TestCase testMethod=test>
def test(self):
process = subprocess.run(
["sh", "./has-stdin.sh"],
stderr=subprocess.PIPE,
stdout=subprocess.PIPE,
check=True,
shell=False
)
> assert process.stdout.decode("utf-8") == "no\n"
E AssertionError: assert 'yes\n' == 'no\n'
E - no
E + yes
test.py:23: AssertionError
======================== short test summary info ========================
FAILED test.py::TestCase::test - AssertionError: assert 'yes\n' == 'no\n'
=========================== 1 failed in 0.10s ===========================
What is making the difference in using -s? How to run this pytest successfully without -s?
I've tried Test calling of an external script run via Popen that expects no available data in stdin using pytest, but when using that method both pytest commands fail.
