I'm trying to test a very simple function (as a result of multiple failed attempts at testing a more complicated function which uses the argument parser as a parameter).
# from ./runfile.py
import argparse
import os
def get_input_args():
parser = argparse.ArgumentParser()
parser.add_argument('--priv_raw_name', default='private_data.csv', type=str,
help='Set raw private/source datafile name')
args = parser.parse_args()
return args
# from ./tests/test_args.py
import pytest
from runfile import get_input_args
def test_parser():
parser = get_input_args()
assert 1
When I run the script runfile.py
all works as expected, however when I call pytest tests/test_args.py
I get the unrecognised arguments error message below.
I've tried setting up a conftest.py
file and using addoption but I just seem to be encountering more errors far beyond my experience to fix. Can anyone point me in the right direction of how to run the test using the default arguments from the core script but not have tests/test_args.py
being called as an argument for the actual test itself?
(Project_Cascade) ➜ Project_Cascade git:(WIP) ✗ pytest tests/test_args.py
========================================================================= test session starts =========================================================================
platform darwin -- Python 3.6.5, pytest-4.3.1, py-1.8.0, pluggy-0.9.0
rootdir: /Users/davidmellor/Code/Spend_Network/Data_Projects/Project_Cascade, inifile:
collected 1 item
tests/test_args.py F [100%]
============================================================================== FAILURES ===============================================================================
_____________________________________________________________________________ test_parser _____________________________________________________________________________
def test_parser():
> parser = get_input_args()
tests/test_args.py:5:
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
runfile.py:50: in get_input_args
args = parser.parse_args()
/usr/local/Cellar/python/3.6.5_1/Frameworks/Python.framework/Versions/3.6/lib/python3.6/argparse.py:1733: in parse_args
self.error(msg % ' '.join(argv))
/usr/local/Cellar/python/3.6.5_1/Frameworks/Python.framework/Versions/3.6/lib/python3.6/argparse.py:2389: in error
self.exit(2, _('%(prog)s: error: %(message)s\n') % args)
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
self = ArgumentParser(prog='pytest', usage=None, description=None, formatter_class=<class 'argparse.HelpFormatter'>, conflict_handler='error', add_help=True)
status = 2, message = 'pytest: error: unrecognized arguments: tests/test_args.py\n'
def exit(self, status=0, message=None):
if message:
self._print_message(message, _sys.stderr)
> _sys.exit(status)
E SystemExit: 2
/usr/local/Cellar/python/3.6.5_1/Frameworks/Python.framework/Versions/3.6/lib/python3.6/argparse.py:2376: SystemExit
------------------------------------------------------------------------ Captured stderr call -------------------------------------------------------------------------
usage: pytest [-h] [--priv_raw_name PRIV_RAW_NAME]
pytest: error: unrecognized arguments: tests/test_args.py
The problem comes from the parser.parse_args
call which accepts an optional args
argument. If this argument is not provided, args are taken from sys.argv
.
When you execute pytest tests/test_args.py
, sys.argv
contains ['pytest', 'tests/test_args.py']
. The first element of the list is the called program and the second is the first argument.
Thus, parser.parse_args
called without its args
argument considers tests/test_args.py as the value for the first declared argument of the parser. Fortunately, it is unable to parse it and an error occurs with the explicit message unrecognized arguments: tests/test_args.py.
To check it, you can add a breakpoint in your test before calling parser.parse_args
and inspect sys.argv
Invoking pytest
without specifying the file to run (just pytest
) should pass with no problem.
Anyway, your test should pass whatever the manner it is ran. All you have to do for this is specifying explicit args
for your parser.parse_args
call in your test.
For example, passing an empty list will work:
parser.parse_args([])
But you will probably want to test it with values for the priv_raw_name
option:
parser:parse_args(['--priv_raw_name', 'any/test/path'])
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With