[issue41600] Expected behavior of argparse given quoted strings
Vegard Stikbakke added the comment: Great idea, thanks! It's open source, so I'll see if I can fix it. On Thu, 20 Aug 2020 at 17:28, Eric V. Smith wrote: > > > Eric V. Smith added the comment: > > > > Completely agree with paul j3. The calling tool is breaking the "argv" > conventions. If the OP can control the calling tool, it should be fixed > there. > > > > -- > > > > ___ > > Python tracker > > <https://bugs.python.org/issue41600> > > ___ > > -- ___ Python tracker <https://bugs.python.org/issue41600> ___ ___ Python-bugs-list mailing list Unsubscribe: https://mail.python.org/mailman/options/python-bugs-list/archive%40mail-archive.com
[issue41600] Expected behavior of argparse given quoted strings
Vegard Stikbakke added the comment: I see! Thanks, had not heard about shlex. I also had not realized `parse_args` takes arguments. Doh. That makes sense. Thanks a lot! -- ___ Python tracker <https://bugs.python.org/issue41600> ___ ___ Python-bugs-list mailing list Unsubscribe: https://mail.python.org/mailman/options/python-bugs-list/archive%40mail-archive.com
[issue41600] Expected behavior of argparse given quoted strings
Vegard Stikbakke added the comment: In fact, what happens in the latter case (i.e. `"--a 1 --b 2"`), inside the call to `_parse_optional`, is that it fails to get the optional tuple. And so it continues to this line in argparse.py: https://github.com/python/cpython/blob/2ce39631f679e14132a54dc90ce764259d26e166/Lib/argparse.py#L2227 Here it says that if there's a space in the string, it was meant to be a positional, and so the function returns `None`, causing it to not find the argument. In conclusion, it seems to me that argparse is not, in fact, meant to handle quoted strings, or rather, strings where there are spaces. -- ___ Python tracker <https://bugs.python.org/issue41600> ___ ___ Python-bugs-list mailing list Unsubscribe: https://mail.python.org/mailman/options/python-bugs-list/archive%40mail-archive.com
[issue41600] Expected behavior of argparse given quoted strings
Vegard Stikbakke added the comment: It seems that I mixed up something in the post here. If the quoted string is `"--a=1 --b=2` as I said in the post, then the program will only complain about `b` missing. In this case, it sets `a` to be `1 --b=2`. Whereas if the quoted string is `"--a 1 --b 2"` (i.e. space and not `=` is used to separate), then it will say that both `a` and `b` are missing. -- ___ Python tracker <https://bugs.python.org/issue41600> ___ ___ Python-bugs-list mailing list Unsubscribe: https://mail.python.org/mailman/options/python-bugs-list/archive%40mail-archive.com
[issue41600] Expected behavior of argparse given quoted strings
Vegard Stikbakke added the comment: For what it's worth, I'd love to work on this if it's something that could be nice to have. -- ___ Python tracker <https://bugs.python.org/issue41600> ___ ___ Python-bugs-list mailing list Unsubscribe: https://mail.python.org/mailman/options/python-bugs-list/archive%40mail-archive.com
[issue41600] Expected behavior of argparse given quoted strings
New submission from Vegard Stikbakke : I'm not sure if this is a bug, but I had a problem when I was trying to use argparse recently, and I was wondering about the expected behavior. For context: We invoke a Python program from a deployment tool, where we provide input in a text box. We were using argparse to read and parse the input arguments. The scenario we had was we were requiring two named arguments to be given, as illustrated in the minimal example below. ``` # a.py import argparse parser = argparse.ArgumentParser() parser.add_argument("--a", required=True) parser.add_argument("--b", required=True) parser.parse_args() ``` When invoking this program from this deployment tool giving `--a=1 --b=2` as input, we got the error message `a.py: error: the following arguments are required: --a, --b`. As it turns out, the input was provided in the same way as if you had given the program a quoted string in the shell: ``` $ python a.py "--a=1 --b=2" usage: a.py [-h] --a A --b B a.py: error: the following arguments are required: --a, --b ``` When given a quoted string like this, `sys.argv` only has two elements, namely `a.py` and `--a=1 --b=2`. This was new to me! But it makes sense. This was a bit annoying! One way to get around it, which we did indeed implement, is to mutate `sys.argv`, effectively unpacking the input string such that `sys.argv` ends up as `["a.py", "--a=1`, `--b=2`]. Given that the string contains named arguments, it seems to me that it could be possible, and safe, to unpack this quoted string. Would that make sense? Or am I using it incorrectly? Or is there some other way to provide input such that I don't have to do this hack that I mentioned? If we make a similar program where the arguments `a` and `b` are not named arguments, but rather positional arguments, ``` # b.py import argparse parser = argparse.ArgumentParser() parser.add_argument("a") parser.add_argument("b") parser.parse_args() ``` and we call the program as before with `python b.py "1 2"`, then `a` will be set to the string `1 2`, whereas `b` will not be set (and so the program will, of course, exit). This seems entirely reasonable. And perhaps it isn't possible to both get this behaviour, as well as the behaviour that I mentioned above. -- components: Library (Lib) messages: 375702 nosy: vegarsti priority: normal severity: normal status: open title: Expected behavior of argparse given quoted strings type: enhancement versions: Python 3.8 ___ Python tracker <https://bugs.python.org/issue41600> ___ ___ Python-bugs-list mailing list Unsubscribe: https://mail.python.org/mailman/options/python-bugs-list/archive%40mail-archive.com
[issue38932] unittest.mock.Mock.reset_mocks does not pass all arguments to its children
Vegard Stikbakke added the comment: Oh, right! Thanks! -- ___ Python tracker <https://bugs.python.org/issue38932> ___ ___ Python-bugs-list mailing list Unsubscribe: https://mail.python.org/mailman/options/python-bugs-list/archive%40mail-archive.com
[issue38932] unittest.mock.Mock.reset_mocks does not pass all arguments to its children
Change by Vegard Stikbakke : -- keywords: +patch pull_requests: +16889 stage: -> patch review pull_request: https://github.com/python/cpython/pull/17409 ___ Python tracker <https://bugs.python.org/issue38932> ___ ___ Python-bugs-list mailing list Unsubscribe: https://mail.python.org/mailman/options/python-bugs-list/archive%40mail-archive.com
[issue38932] unittest.mock.Mock.reset_mocks does not pass all arguments to its children
Change by Vegard Stikbakke : -- versions: -Python 3.7 ___ Python tracker <https://bugs.python.org/issue38932> ___ ___ Python-bugs-list mailing list Unsubscribe: https://mail.python.org/mailman/options/python-bugs-list/archive%40mail-archive.com
[issue38932] unittest.mock.Mock.reset_mocks does not pass all arguments to its children
Vegard Stikbakke added the comment: I said MagicMock, but I meant Mock. -- ___ Python tracker <https://bugs.python.org/issue38932> ___ ___ Python-bugs-list mailing list Unsubscribe: https://mail.python.org/mailman/options/python-bugs-list/archive%40mail-archive.com
[issue38932] unittest.mock.Mock.reset_mocks does not pass all arguments to its children
Change by Vegard Stikbakke : -- title: MagicMock.reset_mocks does not pass all arguments to its children -> unittest.mock.Mock.reset_mocks does not pass all arguments to its children ___ Python tracker <https://bugs.python.org/issue38932> ___ ___ Python-bugs-list mailing list Unsubscribe: https://mail.python.org/mailman/options/python-bugs-list/archive%40mail-archive.com
[issue38932] MagicMock.reset_mocks does not pass all arguments to its children
New submission from Vegard Stikbakke : MagicMock, from unittest.mock, has a method reset_mock, which takes optional arguments return_value and side_effect, both with default values False. In the body of reset_mock, reset_mock is again called on all the _mock_children of of the MagicMock object. However, here the arguments are not passed. This means that if you have a MagicMock object with children that are also mocked, and methods on these have been directly mocked, then it is not enough to call reset_mock on the parent object. A code example that demonstrates this follows below. Here, we could expect m to have been completely reset. But the final print statement shows that m.a() still returns 1. ``` from unittest.mock import MagicMock m = MagicMock(a=MagicMock()) m.a.return_value = 1 m.reset_mock(return_value=True) print(m.a()) ``` Pertinent line in Github https://github.com/python/cpython/blob/dadff6f6610e03a9363c52ba9c49aa923984640a/Lib/unittest/mock.py#L601 -- components: Library (Lib) messages: 357581 nosy: vegarsti priority: normal severity: normal status: open title: MagicMock.reset_mocks does not pass all arguments to its children type: behavior versions: Python 3.7 ___ Python tracker <https://bugs.python.org/issue38932> ___ ___ Python-bugs-list mailing list Unsubscribe: https://mail.python.org/mailman/options/python-bugs-list/archive%40mail-archive.com