gh-119670: Add force keyword only argument to shlex.quote#148846
gh-119670: Add force keyword only argument to shlex.quote#148846jb2170 wants to merge 10 commits intopython:mainfrom
force keyword only argument to shlex.quote#148846Conversation
There are propositions to add a single-quote-double-quote switch (pythongh-90630), so to avoid hiccups of people passing `force` as a positional and it being used for the single-double switch, we make kwargs kwargs-only.
Test special cases of strings that don't need quoting, do need quoting, do use `force`, don't use `force` etc. I've tried to be exhaustive.
…to `shlex.force`
|
|
Co-authored-by: Bartosz Sławecki <bartosz@ilikepython.com>
The comments for why these tests exist can always be found in the git history Co-authored-by: Bartosz Sławecki <bartosz@ilikepython.com>
Missed from last commit
Intended for another branch shlex-quote-typeerror Co-authored-by: Bartosz Sławecki <bartosz@ilikepython.com>
|
Looks ready (for review again?) to me 😎 |
picnixz
left a comment
There was a problem hiding this comment.
Minor tweaks but please add more tets with quotes inside.
| If *force* is :const:`True` then *s* will be quoted even if it is already | ||
| safe for a shell without being quoted. |
There was a problem hiding this comment.
| If *force* is :const:`True` then *s* will be quoted even if it is already | |
| safe for a shell without being quoted. | |
| If *force* is :const:`True`, then *s* is unconditionally quoted, | |
| even if it is already safe for a shell without being quoted. |
|
|
||
| >>> from shlex import quote | ||
| >>> filenames = ['my first file', 'file2', 'file 3'] | ||
| >>> filenames_some_escaped = [quote(f, force=False) for f in filenames] |
There was a problem hiding this comment.
| >>> filenames_some_escaped = [quote(f, force=False) for f in filenames] | |
| >>> filenames_some_escaped = [quote(f) for f in filenames] |
| .. versionadded:: 3.3 | ||
|
|
||
| .. versionchanged:: next | ||
| The *force* keyword was added. |
There was a problem hiding this comment.
| The *force* keyword was added. | |
| Add the *force* parameter. |
| * :func:`shlex.quote` has a new keyword-only parameter *force* that ensures | ||
| a string will always be quoted, even if it is already safe for a shell | ||
| without being quoted. |
There was a problem hiding this comment.
| * :func:`shlex.quote` has a new keyword-only parameter *force* that ensures | |
| a string will always be quoted, even if it is already safe for a shell | |
| without being quoted. | |
| * Add *force* to :func:`shlex.quote` to force quoting a string, | |
| even if it is already safe for a shell without being quoted. |
| If *force* is *True* then *s* will be quoted even if it is | ||
| already safe for a shell without being quoted. |
There was a problem hiding this comment.
Update the docstring with the updated doc I suggested as well.
| if s.isascii() and not s.encode().translate(None, delete=safe_chars): | ||
| if (not force | ||
| and s.isascii() and not s.encode().translate(None, delete=safe_chars)): | ||
| # No quoting is needed if we're not forcing quoting |
There was a problem hiding this comment.
| # No quoting is needed if we're not forcing quoting | |
| # No quoting is needed if we are not forcing quoting |
| if (not force | ||
| and s.isascii() and not s.encode().translate(None, delete=safe_chars)): | ||
| # No quoting is needed if we're not forcing quoting | ||
| # and `s` is an ASCII string consisting only of `safe_chars` |
There was a problem hiding this comment.
| # and `s` is an ASCII string consisting only of `safe_chars` | |
| # and `s` is an ASCII string consisting only of `safe_chars`. |
| self.assertRaises(TypeError, shlex.quote, b"abc") | ||
|
|
||
| def testForceQuote(self): | ||
| self.assertEqual(shlex.quote("spam"), "spam") |
There was a problem hiding this comment.
Please add some tests where the input has quotes inside.
| @@ -0,0 +1,3 @@ | |||
| Add *force* keyword only argument to :func:`shlex.quote` to always quote the | |||
There was a problem hiding this comment.
Update the NEWS entry with the updated What's New as well.
Closes #119670
Supersedes my out-of-date PR #119674
We use
forceinstead ofalwaysas a word more consistent with other programming jargon (like inrm -fthefis for 'force') as discussedCommits
shlex.quote's kwargs kwargs-only. Backwards compatible. There are propositions to add a single-quote-double-quote switch, which I'm ambivalent about, but to future-proof against hiccups of people passingforceas a positional and it ending up being used as the wrong kwarg, we make the kwargs kwargs-only, eg likejson.loads.As mentioned I'm also going to open
an issuea discussion thread aboutshlex.quotereturning"''"for falsey non-str data. This PR and that discussion seem independent of each other, that is this PR doesn't need to be held back until that discussion is addressed.📚 Documentation preview 📚: https://cpython-previews--148846.org.readthedocs.build/