Search code examples
pythonvisual-studio-codevscode-debugger

Is it possible use VS Code to pass multiple command line arguments to Python script?


According to the official documentation "Python debugging in VS Code", launch.json can be configured to run with specific command line arguments, or you can use ${command:pickArgs} to input arguments at run time.

Examples of putting arguments in launch.json:

However, I would rather use but I would rather use ${command:pickArgs} because it makes it easier to test multiple times with different values.

The first time I tried this, I allowed VS Code to create launch.json. By default it contained the following:

            "args": [
                "${command:pickArgs}"
            ]

When I run the file, I get a dialog for inputting arguments:

Python Debugger: Current File with Arguments

However, if I put in multiple arguments, they get wrapped in quotes and treated as a single string argument. In a case where, e.g. the arguments are supposed to be numeric, an error is generated. For example, if I pass in 4 7, which both need to be cast to int, sys.argv[1] gets the value '4 7' rather than '4', yielding the error

invalid literal for int() with base 10: '4 7'

I have tried comma-separating the arguments, and putting quotes around them, and what I get is sys.argv[1] with values like '4, 7' or '"4", "7"'. Needless to say, these don't work either.

I've seen examples online of a launch.json configuration as follows:

            "args": "${command:pickArgs}"

That is, there are no brackets around ${command:pickArgs}. However, this generates a problem in that if there are spaces in the path to the Python interpreter, the path gets broken apart at the spaces. See, for example:

Spaces in python interpreter path or program result in incorrectly quoted debugging commands with arguments #233

The solution seems to be to put the brackets in, which is what I started with in the first place. Since that's what VS Code did automatically, I'm not sure where the varying examples are coming from (with or without brackets) and can't find documentation on this other than the very short mention of ${command:pickArgs} in the official documentation I linked at the very beginning.

So, I have not been able to figure out a way to pass in multiple arguments using ${command:pickArgs} (as opposed to hard-coding directly in launch.json), and the only promising solution (remove the brackets) is poorly documented, generates other errors, and the solution seems to be to put the brackets back in.

Is this possible to do at all?


Solution

  • Answering my own question after further testing. I will leave it unaccepted for a while to see if other answers come in.

    TL;DR

    This is possible as long as there are no spaces in the path to the Python interpreter. The fact that it breaks if there are spaces in the path is a currently open bug. The question arises because of a previously attempted bug fix.

    Workarounds

    1. Make sure your launch.json does not have brackets around ${command:pickArgs}.
    2. Make sure the path to Python interpreter has no spaces.

    Or, if you absolutely have to use a path that has spaces:

    1. Put args directly into launch.json:
       "args" : ["arg1", "arg2", ...] 
    

    Unfortunately, this requires editing launch.json every time you want to change arguments, or if you want to debug different files that expect different arguments.

    Long-Term

    Wait for currently open issue Spaces in python interpreter path or program result in incorrectly quoted debugging commands with arguments #233 to be fixed.

    Explanation

    As far as I can tell, this is what happened.

    In a previous version of VS Code, launch.json would be created with the following configuration:

                "args": "${command:pickArgs}"
    

    Notice there are no brackets around ${command:pickArgs}.

    This works and allows the user to submit multiple command line arguments via dialog box when debugging.

    However, due to a bug, there was an error if the path to the Python interpreter had spaces in it: Spaces in python interpreter path or program result in incorrectly quoted debugging commands with arguments #233.

    An attempted fix inserted brackets into launch.json: Fix error in args with default config #385. This fixed the problem with spaces in the Python path, but created the problem that the question asks about, that multiple command line arguments are treated as part of the same string. This fix appears to have made it into v1.92.2, the version I am using, breaking the ability to parse command line arguments.

    The solution therefore is to remove the brackets around ${command:pickArgs} introduced by the fix in issue #385, but since the Python environment I was testing had spaces in the path, this triggered issue #233.

    After additional information, issue #233 was reopened. The workaround is to make sure to use an environment without spaces in the path. The long-term solution is to wait for the fix to issue #233.