diff options
author | Kevin Van Brunt <kmvanbrunt@gmail.com> | 2019-05-13 12:52:49 -0400 |
---|---|---|
committer | Kevin Van Brunt <kmvanbrunt@gmail.com> | 2019-05-13 12:52:49 -0400 |
commit | c4ee21446e1507ebd5c42a521fa2c0bcb2648c85 (patch) | |
tree | 8d209fc86254c727c9cdd502d58d9e0ec2331cd9 | |
parent | 8ad8ddd10bf35f38e22b2c8f381faa4b2f87c853 (diff) | |
download | cmd2-git-c4ee21446e1507ebd5c42a521fa2c0bcb2648c85.tar.gz |
Preserving originally typed quotes of Statement.output_to for use in Statement.post_command()
-rw-r--r-- | cmd2/cmd2.py | 2 | ||||
-rw-r--r-- | cmd2/parsing.py | 9 | ||||
-rw-r--r-- | cmd2/utils.py | 37 |
3 files changed, 29 insertions, 19 deletions
diff --git a/cmd2/cmd2.py b/cmd2/cmd2.py index d197e75e..c29a1812 100644 --- a/cmd2/cmd2.py +++ b/cmd2/cmd2.py @@ -2082,7 +2082,7 @@ class Cmd(cmd.Cmd): if statement.output == constants.REDIRECTION_APPEND: mode = 'a' try: - new_stdout = open(statement.output_to, mode) + new_stdout = open(utils.strip_quotes(statement.output_to), mode) saved_state.redirecting = True sys.stdout = self.stdout = new_stdout except OSError as ex: diff --git a/cmd2/parsing.py b/cmd2/parsing.py index 067c9bf4..8febd270 100644 --- a/cmd2/parsing.py +++ b/cmd2/parsing.py @@ -2,7 +2,6 @@ # -*- coding: utf-8 -*- """Statement parsing classes for cmd2""" -import os import re import shlex from typing import Dict, Iterable, List, Optional, Tuple, Union @@ -166,7 +165,7 @@ class Statement(str): # if output was redirected, the redirection token, i.e. '>>' output = attr.ib(default='', validator=attr.validators.instance_of(str)) - # if output was redirected, the destination file + # if output was redirected, the destination file token (quotes preserved) output_to = attr.ib(default='', validator=attr.validators.instance_of(str)) def __new__(cls, value: object, *pos_args, **kw_args): @@ -213,7 +212,7 @@ class Statement(str): if self.output: rtn += ' ' + self.output if self.output_to: - rtn += ' ' + utils.quote_string_if_needed(self.output_to) + rtn += ' ' + self.output_to return rtn @@ -495,9 +494,11 @@ class StatementParser: output = constants.REDIRECTION_APPEND output_index = append_index + # Check if we are redirecting to a file if len(tokens) > output_index + 1: unquoted_path = utils.strip_quotes(tokens[output_index + 1]) - output_to = os.path.expanduser(unquoted_path) + if unquoted_path: + output_to = utils.expand_user(tokens[output_index + 1]) # remove all the tokens after the output redirect tokens = tokens[:output_index] diff --git a/cmd2/utils.py b/cmd2/utils.py index 398d39e6..54ad763d 100644 --- a/cmd2/utils.py +++ b/cmd2/utils.py @@ -275,25 +275,34 @@ def unquote_specific_tokens(args: List[str], tokens_to_unquote: List[str]) -> No args[i] = unquoted_arg +def expand_user(token: str) -> str: + """ + Wrap os.expanduser() to support expanding ~ in quoted strings + :param token: the string to expand + """ + if token: + if is_quoted(token): + quote_char = token[0] + token = strip_quotes(token) + else: + quote_char = '' + + token = os.path.expanduser(token) + + # Restore the quotes even if not needed to preserve what the user typed + if quote_char: + token = quote_char + token + quote_char + + return token + + def expand_user_in_tokens(tokens: List[str]) -> None: """ - Call os.path.expanduser() on all tokens in an already parsed list of command-line arguments. - This also supports expanding user in quoted tokens. + Call expand_user() on all tokens in a list of strings :param tokens: tokens to expand """ for index, _ in enumerate(tokens): - if tokens[index]: - # Check if the token is quoted. Since parsing already passed, there isn't - # an unclosed quote. So we only need to check the first character. - first_char = tokens[index][0] - if first_char in constants.QUOTES: - tokens[index] = strip_quotes(tokens[index]) - - tokens[index] = os.path.expanduser(tokens[index]) - - # Restore the quotes even if not needed to preserve what the user typed - if first_char in constants.QUOTES: - tokens[index] = first_char + tokens[index] + first_char + tokens[index] = expand_user(tokens[index]) def find_editor() -> str: |