Why is pytest giving me an "unrecognized option" error when I try and create a custom command line option?
Asked Answered
H

3

6

I'm using Python 3.8 and pytest 6.0.1. How do I create a custom command line option for pytest? I thought it was as simple as adding this to conftest.py ...

def pytest_addoption(parser):
    parser.addoption('--option1', action='store_const', const=True)

but when I pytest, I get an unrecognized option error

# pytest --option1=Y -c tests/my_test.py 
ERROR: usage: pytest [options] [file_or_dir] [file_or_dir] [...]
pytest: error: unrecognized arguments: --option1=Y

What's the right way to add a custom option?

Edit: I tried the answer given. I included some other things in my tests/conftest.py file in case those are the reason the answer isn't working. File contains

def pytest_generate_tests(metafunc):
    option1value = metafunc.config.getoption("--option1")
    print(f'Option1 Value = {option1value}')

def pytest_configure(config):
    use_docker = False
    try:
        use_docker = config.getoption("--docker-compose-remove-volumes")
    except:
        pass
    plugin_name = 'wait_for_docker' if use_docker else 'wait_for_server'
    if not config.pluginmanager.has_plugin(plugin_name):
        config.pluginmanager.import_plugin("tests.plugins.{}".format(plugin_name))

But output when running is

$ pytest -s --option1 tests/shared/model/test_crud_functions.py
ERROR: usage: pytest [options] [file_or_dir] [file_or_dir] [...]
pytest: error: unrecognized arguments: --option1
  inifile: /Users/davea/Documents/workspace/my_project/pytest.ini
  rootdir: /Users/davea/Documents/workspace/my_project
Hughmanick answered 6/8, 2020 at 15:50 Comment(5)
If you use store_const, the option is handled as a flag and cannot have a value, e.g. you have to use pytest --option1. If you want to set different values, you can use the default store action instead.Hypodermis
I vote closing this as a dupe, there are lots of answers regarding custom cli args in pytest already, see e.g. https://mcmap.net/q/157759/-how-to-pass-arguments-in-pytest-by-command-line/2650249 and linked questions there.Oarfish
Might be a bit silly asking but: Are you sure you added this hook to your root conftest.py?Delicacy
You mean "tests/conftest.py"? Yes and I know it's in there because if I just run "pytest tests/shared/model/test_crud_functions.py" all by itself I get the error, "ValueError: no option named '--option1'". Frustratingly, when I run "pytest --option1=abc tests/shared/model/test_crud_functions.py", I get the "pytest: error: unrecognized arguments: --option1=abc" error.Hughmanick
Anyone trying this on Databricks might find it easier to set the env var PYTEST_ADDOPTS instead, as it tends not to work when using parameters in a job.Pelvic
V
1

As already mentioned in a comment action='store_const' makes your option a flag. The value you receive when you read option value provided it is specified on cli is the one specified by const i.e. True in your case.

Try this: add below function to conftest.py

def pytest_generate_tests(metafunc):
    option1value = metafunc.config.getoption("--option1")
    print(f'Option1 Value = {option1value}')
  1. pytest invoked with option pytest -s --option1

    Output will have : Option1 Value = True

  2. pytest invoked without option pytest -s

    Output will have : Option1 Value = None

action=store might give you the desired behavior.

Solution:

# Change the action associated with your option to action='store'
def pytest_addoption(parser):
    parser.addoption('--option1', action='store')


def pytest_configure(config):
    x = config.getoption('option1')
    print(x)  # Any logic that uses option value

Output:

pytest -s --option1=Y -c=test.py
Y
============================================================================= test session starts ==============================================================================
platform darwin -- Python 3.8.5, pytest-6.0.1, py-1.9.0, pluggy-0.13.1

You can find details on available action(s) and more here: https://docs.python.org/3/library/argparse.html#action

Vanitavanity answered 8/8, 2020 at 18:46 Comment(2)
Thanks. Gave this a try but got the error, "ERROR: usage: pytest [options] [file_or_dir] [file_or_dir] [...] pytest: error: unrecognized arguments: --option1". Complete trace and code is an edit to my question.Hughmanick
Hi Dave, You need to use this, parser.addoption('--option1', action='store') Edited answer, look at the Solution section of the answer.Vanitavanity
L
-1

Downgrade pytest version to pytest7.1.0 , it resolve the issue for me.

Lobar answered 25/6, 2023 at 9:20 Comment(0)
J
-2

I think order matters in this case.

Try pytest -c tests/my_test.py --option1=Y

Juryrigged answered 27/8, 2020 at 13:47 Comment(1)
I think "-c" is meant to indicate an ".ini" file, no? Running the command as you have it gives the error, "ERROR: usage: pytest [options] [file_or_dir] [file_or_dir] [...], pytest: error: unrecognized arguments: --option1=Y, inifile: /Users/davea/Documents/workspace/my_project/tests/my_test.py". Removing "-c" still give an error "ERROR: usage: pytest [options] [file_or_dir] [file_or_dir] [...], pytest: error: unrecognized arguments: --option1=Y, inifile: /Users/davea/Documents/workspace/my_project/pytest.ini".Hughmanick

© 2022 - 2024 — McMap. All rights reserved.