json-rpc-0.5.0.0: README.md
json-rpc
========
Fully-featured JSON-RPC 2.0 library for Haskell programs.
This JSON-RPC library is fully-compatible with JSON-RPC 2.0 and 1.0. It
provides an interface that combines a JSON-RPC client and server. It can
set and keep track of request ids to parse responses. There is support
for sending and receiving notifications. You may use any underlying
transport. Basic TCP client and server provided.
A JSON-RPC application using this interface is considered to be
peer-to-peer, as it can send and receive all types of JSON-RPC message
independent of whether it originated the connection.
[Hackage documentation](http://hackage.haskell.org/package/json-rpc)
Server Example
--------------
This JSON-RPC server returns the current time.
``` haskell
{-# LANGUAGE OverloadedStrings #-}
import Control.Applicative
import Control.Monad.Trans
import Control.Monad.Logger
import Data.Aeson.Types hiding (Error)
import Data.Conduit.Network
import Data.Time.Clock
import Data.Time.Format
import Network.JsonRpc
import System.Locale
data TimeReq = TimeReq
data TimeRes = TimeRes { timeRes :: UTCTime }
instance FromRequest TimeReq where
parseParams "time" = Just $ const $ return TimeReq
parseParams _ = Nothing
instance ToJSON TimeRes where
toJSON (TimeRes t) = toJSON $ formatTime defaultTimeLocale "%c" t
respond :: (Functor m, MonadLoggerIO m) => Respond TimeReq m TimeRes
respond TimeReq = Right . TimeRes <$> liftIO getCurrentTime
main :: IO ()
main = runStderrLoggingT $
jsonRpcTcpServer V2 (serverSettings 31337 "::1") respond dummySrv
```
Client Example
--------------
Corresponding TCP client to get time from server.
``` haskell
{-# LANGUAGE OverloadedStrings #-}
import Control.Concurrent
import Control.Monad
import Control.Monad.Trans
import Control.Monad.Logger
import Data.Aeson
import Data.Aeson.Types hiding (Error)
import Data.Conduit.Network
import qualified Data.Text as T
import Data.Time.Clock
import Data.Time.Format
import Network.JsonRpc
import System.Locale
data TimeReq = TimeReq
data TimeRes = TimeRes { timeRes :: UTCTime }
instance ToRequest TimeReq where
requestMethod TimeReq = "time"
instance ToJSON TimeReq where
toJSON TimeReq = emptyArray
instance FromResponse TimeRes where
parseResult "time" = Just $ withText "time" $ \t -> case f t of
Just t' -> return $ TimeRes t'
Nothing -> mzero
where
f t = parseTime defaultTimeLocale "%c" (T.unpack t)
parseResult _ = Nothing
req :: MonadLoggerIO m => JsonRpcT m UTCTime
req = sendRequest TimeReq >>= \ts -> case ts of
Left e -> error $ fromError e
Right (Just (TimeRes r)) -> return r
_ -> error "Could not parse response"
main :: IO ()
main = runStderrLoggingT $
jsonRpcTcpClient V2 (clientSettings 31337 "::1") dummyRespond .
replicateM_ 4 $ req >>= liftIO . print >> liftIO (threadDelay 1000000)
```