| {-# LANGUAGE DeriveDataTypeable #-} |
| -- |
| -- Licensed to the Apache Software Foundation (ASF) under one |
| -- or more contributor license agreements. See the NOTICE file |
| -- distributed with this work for additional information |
| -- regarding copyright ownership. The ASF licenses this file |
| -- to you under the Apache License, Version 2.0 (the |
| -- "License"); you may not use this file except in compliance |
| -- with the License. You may obtain a copy of the License at |
| -- |
| -- http://www.apache.org/licenses/LICENSE-2.0 |
| -- |
| -- Unless required by applicable law or agreed to in writing, |
| -- software distributed under the License is distributed on an |
| -- "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY |
| -- KIND, either express or implied. See the License for the |
| -- specific language governing permissions and limitations |
| -- under the License. |
| -- |
| |
| module Thrift.Protocol |
| ( Protocol(..) |
| , skip |
| , MessageType(..) |
| , ThriftType(..) |
| , ProtocolExn(..) |
| , ProtocolExnType(..) |
| ) where |
| |
| import Control.Monad ( replicateM_, unless ) |
| import Control.Exception |
| import Data.Int |
| import Data.Typeable ( Typeable ) |
| import Data.Word |
| import Data.ByteString.Lazy |
| |
| import Thrift.Transport |
| |
| |
| data ThriftType |
| = T_STOP |
| | T_VOID |
| | T_BOOL |
| | T_BYTE |
| | T_DOUBLE |
| | T_I16 |
| | T_I32 |
| | T_I64 |
| | T_STRING |
| | T_STRUCT |
| | T_MAP |
| | T_SET |
| | T_LIST |
| deriving ( Eq ) |
| |
| instance Enum ThriftType where |
| fromEnum T_STOP = 0 |
| fromEnum T_VOID = 1 |
| fromEnum T_BOOL = 2 |
| fromEnum T_BYTE = 3 |
| fromEnum T_DOUBLE = 4 |
| fromEnum T_I16 = 6 |
| fromEnum T_I32 = 8 |
| fromEnum T_I64 = 10 |
| fromEnum T_STRING = 11 |
| fromEnum T_STRUCT = 12 |
| fromEnum T_MAP = 13 |
| fromEnum T_SET = 14 |
| fromEnum T_LIST = 15 |
| |
| toEnum 0 = T_STOP |
| toEnum 1 = T_VOID |
| toEnum 2 = T_BOOL |
| toEnum 3 = T_BYTE |
| toEnum 4 = T_DOUBLE |
| toEnum 6 = T_I16 |
| toEnum 8 = T_I32 |
| toEnum 10 = T_I64 |
| toEnum 11 = T_STRING |
| toEnum 12 = T_STRUCT |
| toEnum 13 = T_MAP |
| toEnum 14 = T_SET |
| toEnum 15 = T_LIST |
| toEnum t = error $ "Invalid ThriftType " ++ show t |
| |
| data MessageType |
| = M_CALL |
| | M_REPLY |
| | M_EXCEPTION |
| deriving ( Eq ) |
| |
| instance Enum MessageType where |
| fromEnum M_CALL = 1 |
| fromEnum M_REPLY = 2 |
| fromEnum M_EXCEPTION = 3 |
| |
| toEnum 1 = M_CALL |
| toEnum 2 = M_REPLY |
| toEnum 3 = M_EXCEPTION |
| toEnum t = error $ "Invalid MessageType " ++ show t |
| |
| |
| class Protocol a where |
| getTransport :: Transport t => a t -> t |
| |
| writeMessageBegin :: Transport t => a t -> (String, MessageType, Int32) -> IO () |
| writeMessageEnd :: Transport t => a t -> IO () |
| |
| writeStructBegin :: Transport t => a t -> String -> IO () |
| writeStructEnd :: Transport t => a t -> IO () |
| writeFieldBegin :: Transport t => a t -> (String, ThriftType, Int16) -> IO () |
| writeFieldEnd :: Transport t => a t -> IO () |
| writeFieldStop :: Transport t => a t -> IO () |
| writeMapBegin :: Transport t => a t -> (ThriftType, ThriftType, Int32) -> IO () |
| writeMapEnd :: Transport t => a t -> IO () |
| writeListBegin :: Transport t => a t -> (ThriftType, Int32) -> IO () |
| writeListEnd :: Transport t => a t -> IO () |
| writeSetBegin :: Transport t => a t -> (ThriftType, Int32) -> IO () |
| writeSetEnd :: Transport t => a t -> IO () |
| |
| writeBool :: Transport t => a t -> Bool -> IO () |
| writeByte :: Transport t => a t -> Word8 -> IO () |
| writeI16 :: Transport t => a t -> Int16 -> IO () |
| writeI32 :: Transport t => a t -> Int32 -> IO () |
| writeI64 :: Transport t => a t -> Int64 -> IO () |
| writeDouble :: Transport t => a t -> Double -> IO () |
| writeString :: Transport t => a t -> String -> IO () |
| writeBinary :: Transport t => a t -> ByteString -> IO () |
| |
| |
| readMessageBegin :: Transport t => a t -> IO (String, MessageType, Int32) |
| readMessageEnd :: Transport t => a t -> IO () |
| |
| readStructBegin :: Transport t => a t -> IO String |
| readStructEnd :: Transport t => a t -> IO () |
| readFieldBegin :: Transport t => a t -> IO (String, ThriftType, Int16) |
| readFieldEnd :: Transport t => a t -> IO () |
| readMapBegin :: Transport t => a t -> IO (ThriftType, ThriftType, Int32) |
| readMapEnd :: Transport t => a t -> IO () |
| readListBegin :: Transport t => a t -> IO (ThriftType, Int32) |
| readListEnd :: Transport t => a t -> IO () |
| readSetBegin :: Transport t => a t -> IO (ThriftType, Int32) |
| readSetEnd :: Transport t => a t -> IO () |
| |
| readBool :: Transport t => a t -> IO Bool |
| readByte :: Transport t => a t -> IO Word8 |
| readI16 :: Transport t => a t -> IO Int16 |
| readI32 :: Transport t => a t -> IO Int32 |
| readI64 :: Transport t => a t -> IO Int64 |
| readDouble :: Transport t => a t -> IO Double |
| readString :: Transport t => a t -> IO String |
| readBinary :: Transport t => a t -> IO ByteString |
| |
| |
| skip :: (Protocol p, Transport t) => p t -> ThriftType -> IO () |
| skip _ T_STOP = return () |
| skip _ T_VOID = return () |
| skip p T_BOOL = readBool p >> return () |
| skip p T_BYTE = readByte p >> return () |
| skip p T_I16 = readI16 p >> return () |
| skip p T_I32 = readI32 p >> return () |
| skip p T_I64 = readI64 p >> return () |
| skip p T_DOUBLE = readDouble p >> return () |
| skip p T_STRING = readString p >> return () |
| skip p T_STRUCT = do _ <- readStructBegin p |
| skipFields p |
| readStructEnd p |
| skip p T_MAP = do (k, v, s) <- readMapBegin p |
| replicateM_ (fromIntegral s) (skip p k >> skip p v) |
| readMapEnd p |
| skip p T_SET = do (t, n) <- readSetBegin p |
| replicateM_ (fromIntegral n) (skip p t) |
| readSetEnd p |
| skip p T_LIST = do (t, n) <- readListBegin p |
| replicateM_ (fromIntegral n) (skip p t) |
| readListEnd p |
| |
| |
| skipFields :: (Protocol p, Transport t) => p t -> IO () |
| skipFields p = do |
| (_, t, _) <- readFieldBegin p |
| unless (t == T_STOP) (skip p t >> readFieldEnd p >> skipFields p) |
| |
| |
| data ProtocolExnType |
| = PE_UNKNOWN |
| | PE_INVALID_DATA |
| | PE_NEGATIVE_SIZE |
| | PE_SIZE_LIMIT |
| | PE_BAD_VERSION |
| deriving ( Eq, Show, Typeable ) |
| |
| data ProtocolExn = ProtocolExn ProtocolExnType String |
| deriving ( Show, Typeable ) |
| instance Exception ProtocolExn |