fix: Only escape special characters by single quoting, not escaping *and* quoting
This commit is contained in:
parent
8cbe4c6003
commit
3c731ae2f7
@ -15,7 +15,6 @@ module Hledger.Utils.String (
|
||||
-- quotechars,
|
||||
-- whitespacechars,
|
||||
words',
|
||||
unwords',
|
||||
stripAnsi,
|
||||
-- * single-line layout
|
||||
strip,
|
||||
@ -165,26 +164,25 @@ singleQuote s = "'"++s++"'"
|
||||
-- >>> quoteForCommandLine "\""
|
||||
-- "'\"'"
|
||||
-- >>> quoteForCommandLine "$"
|
||||
-- "'\\$'"
|
||||
-- "'$'"
|
||||
--
|
||||
quoteForCommandLine :: String -> String
|
||||
quoteForCommandLine s
|
||||
| any (`elem` s) (quotechars++whitespacechars++shellchars) = singleQuote $ quoteShellChars s
|
||||
| any (`elem` s) (quotechars++whitespacechars++shellchars) = singleQuote $ escapeSingleQuotes s
|
||||
| otherwise = s
|
||||
|
||||
-- | Try to backslash-quote common shell-significant characters in this string.
|
||||
-- Doesn't handle single quotes, & probably others.
|
||||
quoteShellChars :: String -> String
|
||||
quoteShellChars = concatMap escapeShellChar
|
||||
-- | Escape single quotes appearing in a string we're protecting by wrapping in single quotes
|
||||
escapeSingleQuotes :: String -> String
|
||||
escapeSingleQuotes = concatMap escapeSingleQuote
|
||||
where
|
||||
escapeShellChar c | c `elem` shellchars = ['\\',c]
|
||||
escapeShellChar c = [c]
|
||||
escapeSingleQuote c | c `elem` "'" = ['\\',c]
|
||||
escapeSingleQuote c = [c]
|
||||
|
||||
quotechars, whitespacechars, redirectchars, shellchars :: [Char]
|
||||
quotechars = "'\""
|
||||
whitespacechars = " \t\n\r"
|
||||
redirectchars = "<>"
|
||||
shellchars = "<>(){}[]$&?#!~`"
|
||||
shellchars = "<>(){}[]$&?#!~`*+\\"
|
||||
|
||||
-- | Quote-aware version of words - don't split on spaces which are inside quotes.
|
||||
-- NB correctly handles "a'b" but not "''a''". Can raise an error if parsing fails.
|
||||
@ -198,10 +196,6 @@ words' s = map stripquotes $ fromparse $ parsewithString p s -- PARTIAL
|
||||
singleQuotedPattern = between (char '\'') (char '\'') (many $ noneOf "'")
|
||||
doubleQuotedPattern = between (char '"') (char '"') (many $ noneOf "\"")
|
||||
|
||||
-- | Quote-aware version of unwords - single-quote strings which contain whitespace
|
||||
unwords' :: [String] -> String
|
||||
unwords' = unwords . map quoteIfNeeded
|
||||
|
||||
-- | Strip one matching pair of single or double quotes on the ends of a string.
|
||||
stripquotes :: String -> String
|
||||
stripquotes s = if isSingleQuoted s || isDoubleQuoted s then init $ tailErr s else s -- PARTIAL tailErr won't fail because isDoubleQuoted
|
||||
|
||||
@ -23,7 +23,6 @@ module Hledger.Utils.Text
|
||||
-- escapeSingleQuotes,
|
||||
-- escapeQuotes,
|
||||
-- words',
|
||||
-- unwords',
|
||||
stripquotes,
|
||||
-- isSingleQuoted,
|
||||
-- isDoubleQuoted,
|
||||
@ -162,10 +161,6 @@ escapeBackslash = T.replace "\\" "\\\\"
|
||||
-- singleQuotedPattern = between (char '\'') (char '\'') (many $ noneOf "'")
|
||||
-- doubleQuotedPattern = between (char '"') (char '"') (many $ noneOf "\"")
|
||||
|
||||
-- -- | Quote-aware version of unwords - single-quote strings which contain whitespace
|
||||
-- unwords' :: [Text] -> Text
|
||||
-- unwords' = T.unwords . map quoteIfNeeded
|
||||
|
||||
-- | Strip one matching pair of single or double quotes on the ends of a string.
|
||||
stripquotes :: Text -> Text
|
||||
stripquotes s = if isSingleQuoted s || isDoubleQuoted s then T.init $ T.tail s else s
|
||||
|
||||
Loading…
Reference in New Issue
Block a user