packages feed

proto-lens 0.1.0.2 → 0.1.0.3

raw patch · 4 files changed

+93/−14 lines, 4 filesPVP: major bump suggested

API removals or changes: PVP suggests a major version bump

API changes (from Hackage documentation)

- Data.ProtoLens.Message: def :: Default a => a
+ Data.ProtoLens.Message: def :: a

Files

proto-lens.cabal view
@@ -1,5 +1,5 @@ name:                proto-lens-version:             0.1.0.2+version:             0.1.0.3 synopsis:            A lens-based implementation of protocol buffers in Haskell. description:   The proto-lens library provides to protocol buffers using modern
src/Data/ProtoLens/Encoding.hs view
@@ -223,4 +223,3 @@ stringizeError :: Either UnicodeException a -> Either String a stringizeError (Left e) = Left (show e) stringizeError (Right a) = Right a-
src/Data/ProtoLens/TextFormat.hs view
@@ -20,13 +20,15 @@ import Lens.Family2 ((&),(^.),(.~), set, over) import Control.Applicative ((<$>)) import Control.Arrow (left)-import qualified Data.ByteString.Char8 as B+import qualified Data.ByteString+import Data.Char (isPrint, isAscii, chr) import Data.Foldable (foldlM, foldl') import Data.Maybe (catMaybes) import qualified Data.Map as Map import qualified Data.Set as Set-import qualified Data.Text as Text+import qualified Data.Text.Encoding as Text import qualified Data.Text.Lazy as Lazy+import Numeric (showOct) import Text.Parsec (parse) import Text.PrettyPrint @@ -102,11 +104,35 @@ pprintFieldValue name FloatField x = primField name x pprintFieldValue name DoubleField x = primField name x pprintFieldValue name BoolField x = text name <> colon <+> boolValue x-pprintFieldValue name StringField x = primField name x-pprintFieldValue name BytesField x = primField name x+pprintFieldValue name StringField x = pprintByteString name (Text.encodeUtf8 x)+pprintFieldValue name BytesField x = pprintByteString name x pprintFieldValue name GroupField m     = text name <+> lbrace $$ nest 2 (pprintMessage m) $$ rbrace +-- | Formats a string in a way that mostly matches the C-compatible escaping+-- used by the Protocol Buffer distribution.  We depart a bit by escaping all+-- non-ASCII characters, which depending on the locale, the distribution might+-- not do.+--+-- This uses three-digit octal escapes, e.g. "\011" plus \n, \r,, \t, \', \",+-- and \\ only.  Note that Haskell string-literal syntax calls for "\011" to be+-- interpreted as decimal 11, rather than the decimal 9 it actually represent,+-- so you can't use Prelude.read to parse the strings created here.+pprintByteString :: String -> Data.ByteString.ByteString -> Doc+pprintByteString name x = text name <> colon <+> char '\"'+    <> text (concatMap escape $ Data.ByteString.unpack x) <> char '\"'+  where escape w8 | ch == '\n'               = "\\n"+                  | ch == '\r'               = "\\r"+                  | ch == '\t'               = "\\t"+                  | ch == '\"'               = "\\\""+                  | ch == '\''               = "\\\'"+                  | ch == '\\'               = "\\\\"+                  | isPrint ch && isAscii ch = ch : ""+                  | otherwise                = "\\" ++ pad (showOct w8 "")+          where+            ch = chr $ fromIntegral w8+            pad str = replicate (3 - length str) '0' ++ str+ primField :: Show value => String -> value -> Doc primField name x = text name <> colon <+> text (show x) @@ -202,8 +228,8 @@     | x == "true" = Right True     | x == "false" = Right False     | otherwise = Left $ "Unrecognized bool value " ++ show x-makeValue StringField (Parser.StringValue x) = Right (Text.pack x)-makeValue BytesField (Parser.StringValue x) = Right (B.pack x)+makeValue StringField (Parser.ByteStringValue x) = Right (Text.decodeUtf8 x)+makeValue BytesField (Parser.ByteStringValue x) = Right x makeValue EnumField (Parser.IntValue x) =     maybe (Left $ "Unrecognized enum value " ++ show x) Right         (maybeToEnum $ fromInteger x)
src/Data/ProtoLens/TextFormat/Parser.hs view
@@ -14,13 +14,19 @@     , parser     ) where -import Data.List (intercalate)+import Data.ByteString (ByteString, pack)+import Data.Char (ord) import Data.Functor.Identity (Identity)+import Data.List (intercalate)+import Data.Maybe (catMaybes) import Data.Text.Lazy (Text)-import Text.Parsec.Char (alphaNum, char, letter, oneOf)+import Data.Word (Word8)+import Numeric (readOct, readHex)+import Text.Parsec.Char+  (alphaNum, char, hexDigit, letter, octDigit, oneOf, satisfy) import Text.Parsec.Text.Lazy (Parser)-import Text.Parsec.Combinator (eof, sepBy1, many1, choice)-import Text.Parsec.Token+import Text.Parsec.Combinator (choice, eof, many1, optionMaybe, sepBy1)+import Text.Parsec.Token hiding (octal) import Control.Applicative ((<*), (<|>), (*>), many) import Control.Monad (liftM, liftM2, mzero) @@ -60,7 +66,7 @@  data Value = IntValue Integer  -- ^ An integer   | DoubleValue Double  -- ^ Any floating point number-  | StringValue String  -- ^ A string literal+  | ByteStringValue ByteString    -- ^ A string or bytes literal   | MessageValue Message  -- ^ A sub message   | EnumValue String  -- ^ Any undelimited string (including false & true)   deriving (Show,Ord,Eq)@@ -91,7 +97,8 @@         negative <- (symbol ptp "-" >> return True) <|> return False         value <- naturalOrFloat ptp         return $ makeNumberValue negative value-    parseString = liftM (StringValue . concat) . many1 $ stringLiteral ptp+    parseString = liftM (ByteStringValue . mconcat)+        $ many1 $ lexeme ptp $ protoStringLiteral     parseEnumValue = liftM EnumValue (identifier ptp)     parseMessageValue = liftM MessageValue         (braces ptp parseMessage <|> angles ptp parseMessage)@@ -101,3 +108,50 @@     makeNumberValue False (Left intValue) = IntValue intValue     makeNumberValue True (Right doubleValue) = DoubleValue (negate doubleValue)     makeNumberValue False (Right doubleValue) = DoubleValue doubleValue++-- | Reads a literal string the way the Protocol Buffer distribution's+-- tokenizer.cc does.  This differs from Haskell string literals in treating,+-- e.g. "\11" as octal instead of decimal, so reading as 9 instead of 11.  Also,+-- like tokenizer.cc we assume octal and hex escapes can have at most three and+-- two digits, respectively.+--+-- TODO: implement reading of Unicode escapes.+protoStringLiteral :: Parser ByteString+protoStringLiteral = do+    initialQuoteChar <- char '\'' <|> char '\"'+    word8s <- many stringChar+    _ <- char initialQuoteChar+    return $ pack word8s+  where+    stringChar :: Parser Word8+    stringChar = nonEscape <|> stringEscape+    nonEscape  = fmap (fromIntegral . ord)+        $ satisfy (\c -> c `notElem` "\\\'\"" && ord c < 256)+    stringEscape = char '\\' >> (octal <|> hex <|> unicode <|> simple)+    octal = do d0 <- octDigit+               d1 <- optionMaybe octDigit+               d2 <- optionMaybe octDigit+               readMaybeDigits readOct [Just d0, d1, d2]+    readMaybeDigits :: ReadS Word8 -> [Maybe Char] -> Parser Word8+    readMaybeDigits reader+        = return . (\str -> let [(v, "")] = reader str in v) . catMaybes+    hex = do _ <- oneOf "xX"+             d0 <- hexDigit+             d1 <- optionMaybe hexDigit+             readMaybeDigits readHex [Just d0, d1]+    unicode = oneOf "uU" >> fail "Unicode in string literals not yet supported"+    simple = choice $ map charRet [ ('a', '\a')+                                  , ('b', '\b')+                                  , ('f', '\f')+                                  , ('n', '\n')+                                  , ('r', '\r')+                                  , ('t', '\t')+                                  , ('v', '\v')+                                  , ('\\', '\\')+                                  , ('\'', '\'')+                                  , ('\"', '\"')+                                  ]+      where+        charRet :: (Char, Char) -> Parser Word8+        charRet (escapeCh, ch) = do _ <- char escapeCh+                                    return $ fromIntegral $ ord ch