shellwords 0.1.2.0 → 0.1.2.1
raw patch · 4 files changed
+48/−9 lines, 4 files
Files
- CHANGELOG.md +6/−1
- shellwords.cabal +2/−2
- src/ShellWords.hs +15/−5
- test/ShellWordsSpec.hs +25/−1
CHANGELOG.md view
@@ -1,6 +1,11 @@-## [*Unreleased*](https://github.com/pbrisbin/hs-shellwords/compare/v0.1.2.0...master)+## [*Unreleased*](https://github.com/pbrisbin/hs-shellwords/compare/v0.1.2.1...master) None++## [v0.1.2.1](https://github.com/pbrisbin/hs-shellwords/compare/v0.1.2.0...v0.1.2.1)++- Strip surrounding whitespace before parsing+- Fix mis-handling of escaped spaces in certain kinds of flags ## [v0.1.2.0](https://github.com/pbrisbin/hs-shellwords/compare/v0.1.1.0...v0.1.2.0)
shellwords.cabal view
@@ -2,10 +2,10 @@ -- -- see: https://github.com/sol/hpack ----- hash: d41ef6dd8e4fd0597b45fbd58e4127227dd0c1501032d7f7d5de8213ca96223e+-- hash: ecca1ea7b4034a8595c7854737989ba34a995bab6c9fe5cedfb23c9bcded7ed5 name: shellwords-version: 0.1.2.0+version: 0.1.2.1 synopsis: Parse strings into words, like a shell would description: See https://github.com/pbrisbin/hs-shellwords#readme category: Text
src/ShellWords.hs view
@@ -19,7 +19,9 @@ type Parser = Parsec Void String parse :: String -> Either String [String]-parse = first parseErrorPretty . Megaparsec.parse parser "<input>"+parse = first parseErrorPretty . Megaparsec.parse parser "<input>" . strip+ where+ strip = let f = reverse . dropWhile isSpace in f . f -- | Parse and return @'Text'@ values parseText :: Text -> Either String [Text]@@ -35,7 +37,7 @@ quoted :: Parser String quoted = do q <- oneOf ['\'', '\"']- manyTill (try (escaped q) <|> anyToken) (char q)+ manyTill (escaped q <|> anyToken) $ char q -- | A flag, with or without an argument shelloption :: Parser String@@ -46,7 +48,7 @@ flag = (<>) <$> (string "--" <|> string "-")- <*> (quoted <|> many (noneOf ['=', ' ']))+ <*> (quoted <|> many (nonSpaceOr '=')) -- | The argument to a flag like @=foo@, or @=\"baz bat\"@ argument :: Parser String@@ -54,7 +56,7 @@ -- | A plain value, here till an (unescaped) space value :: Parser String-value = many (try (escaped ' ') <|> nonSpace)+value = many nonSpace escaped :: Char -> Parser Char escaped c = c <$ string ("\\" <> [c])@@ -63,4 +65,12 @@ anyToken = satisfy $ const True nonSpace :: Parser Char-nonSpace = satisfy $ not . isSpace+nonSpace = escaped ' ' <|> satisfy (not . isSpace)++nonSpaceOr :: Char -> Parser Char+nonSpaceOr c = escaped ' ' <|> escaped c <|> satisfy (not . isSpaceOrChar)+ where+ isSpaceOrChar c'+ | isSpace c' = True+ | c' == c = True+ | otherwise = False
test/ShellWordsSpec.hs view
@@ -26,7 +26,22 @@ , ("var \"--bar=\\'baz\\'\"", ["var", "--bar=\\'baz\\'"]) , ("var \"--bar baz\"", ["var", "--bar baz"]) , ("var --\"bar baz\"", ["var", "--bar baz"])- , ("var --\"bar baz\"", ["var", "--bar baz"])+ , ("var --\"bar baz\"", ["var", "--bar baz"])++ -- Additional test cases for whitespace+ , ("var --bar=baz ", ["var", "--bar=baz"])+ , (" var --bar=baz ", ["var", "--bar=baz"])+ , (" var --bar=baz ", ["var", "--bar=baz"])++ -- Additional test cases for escaped spaces+ , ("var --bar\\ baz", ["var", "--bar baz"])+ , ("var --bar=baz\\ bat", ["var", "--bar=baz bat"])+ , ("var --bar baz\\ bat", ["var", "--bar", "baz bat"])++ -- N.B. sh preserves escapes in quoted values, python-shellwords does not.+ -- we behave like sh in this regard. See omitted cases below too.+ , ("var --bar 'baz\\ bat'", ["var", "--bar", "baz\\ bat"])+ , ("var --bar \"baz\\ bat\"", ["var", "--bar", "baz\\ bat"]) ] -- Omitted cases:@@ -65,6 +80,15 @@ for_ errorCases $ \input -> do it ("errors on |" <> input <> "|") $ do parse input `shouldSatisfy` isLeft++ it "fixes #3" $ do+ let input = "-LC:/Users/Vitor\\ Coimbra/AppData/Local/Programs/stack/x86_64-windows/msys2-20150512/mingw64/lib -ltag\n"+ expected =+ [ "-LC:/Users/Vitor Coimbra/AppData/Local/Programs/stack/x86_64-windows/msys2-20150512/mingw64/lib"+ , "-ltag"+ ]++ parse input `shouldBe` Right expected isLeft :: Either a b -> Bool isLeft (Left _) = True