78 lines
2.7 KiB
Haskell
78 lines
2.7 KiB
Haskell
{-# LANGUAGE GeneralizedNewtypeDeriving #-}
|
|
|
|
{-# LANGUAGE MultiParamTypeClasses #-}
|
|
{-# LANGUAGE StandaloneDeriving #-}
|
|
|
|
module Network.GRPC.LowLevel.GRPC(
|
|
GRPC
|
|
, withGRPC
|
|
, GRPCIOError(..)
|
|
, throwIfCallError
|
|
, grpcDebug
|
|
, grpcDebug'
|
|
, threadDelaySecs
|
|
, MetadataMap(..)
|
|
, C.StatusDetails(..)
|
|
) where
|
|
|
|
import Control.Concurrent (threadDelay, myThreadId)
|
|
import Control.Exception
|
|
import Data.Typeable
|
|
import Network.GRPC.LowLevel.GRPC.MetadataMap (MetadataMap(..))
|
|
import qualified Network.GRPC.Unsafe as C
|
|
import qualified Network.GRPC.Unsafe.Op as C
|
|
|
|
-- | Functions as a proof that the gRPC core has been started. The gRPC core
|
|
-- must be initialized to create any gRPC state, so this is a requirement for
|
|
-- the server and client create/start functions.
|
|
data GRPC = GRPC
|
|
|
|
withGRPC :: (GRPC -> IO a) -> IO a
|
|
withGRPC = bracket (C.grpcInit >> return GRPC)
|
|
(\_ -> grpcDebug "withGRPC: shutting down" >> C.grpcShutdown)
|
|
|
|
-- | Describes all errors that can occur while running a GRPC-related IO
|
|
-- action.
|
|
data GRPCIOError = GRPCIOCallError C.CallError
|
|
-- ^ Errors that can occur while the call is in flight. These
|
|
-- errors come from the core gRPC library directly.
|
|
| GRPCIOTimeout
|
|
-- ^ Indicates that we timed out while waiting for an
|
|
-- operation to complete on the 'CompletionQueue'.
|
|
| GRPCIOShutdown
|
|
-- ^ Indicates that the 'CompletionQueue' is shutting down
|
|
-- and no more work can be processed. This can happen if the
|
|
-- client or server is shutting down.
|
|
| GRPCIOShutdownFailure
|
|
-- ^ Thrown if a 'CompletionQueue' fails to shut down in a
|
|
-- reasonable amount of time.
|
|
| GRPCIOUnknownError
|
|
| GRPCIOBadStatusCode C.StatusCode C.StatusDetails
|
|
|
|
| GRPCIODecodeError String
|
|
| GRPCIOInternalUnexpectedRecv String -- debugging description
|
|
| GRPCIOHandlerException String
|
|
deriving (Eq, Show, Typeable)
|
|
instance Exception GRPCIOError
|
|
|
|
throwIfCallError :: C.CallError -> Either GRPCIOError ()
|
|
throwIfCallError C.CallOk = Right ()
|
|
throwIfCallError x = Left $ GRPCIOCallError x
|
|
|
|
grpcDebug :: String -> IO ()
|
|
{-# INLINE grpcDebug #-}
|
|
#ifdef DEBUG
|
|
grpcDebug = grpcDebug'
|
|
#else
|
|
grpcDebug _ = return ()
|
|
#endif
|
|
|
|
grpcDebug' :: String -> IO ()
|
|
{-# INLINE grpcDebug' #-}
|
|
grpcDebug' str = do
|
|
tid <- myThreadId
|
|
putStrLn $ "[" ++ show tid ++ "]: " ++ str
|
|
|
|
threadDelaySecs :: Int -> IO ()
|
|
threadDelaySecs = threadDelay . (* 10^(6::Int))
|