on type-errors help sign in
89 lines 2.5 kB history raw
1{-# LANGUAGE DataKinds #-}
2{-# LANGUAGE DeriveGeneric #-}
3{-# LANGUAGE RecordWildCards #-}
4{-# LANGUAGE OverloadedStrings #-}
5{-# LANGUAGE PolyKinds #-}
6{-# LANGUAGE TypeFamilies #-}
7{-# LANGUAGE TypeOperators #-}
9import Prelude ()
10import Prelude.Compat
12import Data.Aeson
13import Data.Proxy
14import Data.Text
15import GHC.Generics
16import Network.Wai
17import Network.Wai.Handler.Warp
19import Servant
20import Servant.Server.Generic ()
21import Servant.API.Generic
23-- * Example
25-- | A greet message data type
26newtype Greet = Greet { _msg :: Text }
27 deriving (Generic, Show)
29instance FromJSON Greet
30instance ToJSON Greet
32-- API specification
33type TestApi =
34 -- GET /hello/:name?capital={true, false} returns a Greet as JSON
35 "hello" :> Capture "name" Text :> QueryParam "capital" Bool :> Get '[JSON] Greet
37 -- POST /greet with a Greet as JSON in the request body,
38 -- returns a Greet as JSON
39 :<|> "greet" :> ReqBody '[JSON] Greet :> Post '[JSON] Greet
41 -- DELETE /greet/:greetid
42 :<|> "greet" :> Capture "greetid" Text :> Delete '[JSON] NoContent
44 :<|> NamedRoutes OtherRoutes
46data OtherRoutes mode = OtherRoutes
47 { version :: mode :- Get '[JSON] Int
48 , bye :: mode :- "bye" :> Capture "name" Text :> Get '[JSON] Text
49 }
50 deriving Generic
52testApi :: Proxy TestApi
53testApi = Proxy
55-- Server-side handlers.
56--
57-- There's one handler per endpoint, which, just like in the type
58-- that represents the API, are glued together using :<|>.
59--
60-- Each handler runs in the 'Handler' monad.
61server :: Server TestApi
62server = helloH :<|> postGreetH :<|> deleteGreetH :<|> otherRoutes
63 where otherRoutes = OtherRoutes {..}
65 bye name = pure $ "Bye, " <> name <> " !"
66 version = pure 42
68 helloH name Nothing = helloH name (Just False)
69 helloH name (Just False) = return . Greet $ "Hello, " <> name
70 helloH name (Just True) = return . Greet . toUpper $ "Hello, " <> name
72 postGreetH greet = return greet
74 deleteGreetH _ = return NoContent
76-- Turn the server into a WAI app. 'serve' is provided by servant,
77-- more precisely by the Servant.Server module.
78test :: Application
79test = serve testApi server
81-- Run the server.
82--
83-- 'run' comes from Network.Wai.Handler.Warp
84runTestServer :: Port -> IO ()
85runTestServer port = run port test
87-- Put this all to work!
88main :: IO ()
89main = runTestServer 8001