well-typed / grapesy

Native Haskell gRPC client and server based on `http2`
Other
31 stars 4 forks source link

Generalize the client-side streaming functions #79

Closed edsko closed 4 months ago

edsko commented 4 months ago

Importantly, this enables the use of a monad stack to keep track of the Connection. See Demo.Client.API.Protobuf.CanCallRPC.Greeter for a demo.

edsko commented 4 months ago

The main change introduced by this PR is where we previously had

class ClientHandler h where
  rpcWith :: IsRPC rpc => Connection -> CallParams -> Proxy rpc -> h rpc

-- | Construct RPC handler
--
-- See 'nonStreaming' and friends for example usage.
--
-- If you want to use non-default 'CallParams', use 'rpcWith'.
rpc :: forall rpc h. (ClientHandler h, IsRPC rpc)  => Connection -> h rpc

That Connection object is now no longer present when we call rpc. The handler constructed by rpc is now a function which must still be given a Connection before it can run. We provide various runners for these handlers:

The IO case does now look ever so slightly different; where previously we had

reply <- nonStreaming (rpc @(Protobuf Greeter "sayHello") conn) name

this now looks like

reply <- nonStreaming conn (rpc @(Protobuf Greeter "sayHello")) name

In the CanCallRPC case, it will look like

reply <- nonStreaming (rpc @(Protobuf Greeter "sayHello")) name

Provided that we live in some monad in which we have a Connection (Demo.Client.API.Protobuf.CanCallRPC.Greeter provides an example).

This addresses #77.