2

サーバント 0.5 で REST API の簡単な例を作成したいと思います。

data MyData = MyData { var1 :: Int, var2 :: String } 

app :: Application
app = serve api server

api :: Proxy API
api = Proxy

server :: Server API
server = getItems

getItems :: EitherT ServantErr IO [MyData]
getItems = runEitherT $ do
    aa <- nextRandom -- IO
    bb <- getCurrentTime -- IO
    cc <- getDataFromDb -- IO

    --noteT ??? How??? 
    --MaybeT ??? How??? 

    return $ Just [MyData 111 222] 


startApp :: IO ()
startApp = run 8080 app  

さまざまな場所で「予想される型と一致しませんでした」というエラーがたくさんあるため、コンパイルできません。「getItems」で2つの異なるモナドを混在させているためだと思います。しかしそれだけではありません。

4

1 に答える 1

4

ここ:

getItems :: ExceptT ServantErr IO [MyData]
getItems = runExceptT $ do

からへとrunExceptTは何ですか。ニュータイプを排除します。しかし、あなたは他の方法に行きたいです!ExceptT ServantErr IO [MyData]IO (Either ServantErr [MyData]ExceptT

を使用して、任意のアクションをアクションliftIOに持ち上げることができます。基本的に、ラッパーに「アクションの結果を成功コンテキストに入れる」ように指示します。IO aExceptT ServantErr IO aExceptTIO

do ブロック全体が にあるように見えるのでIO、次のように書くことができます。

getItems :: ExceptT ServantErr IO [MyData]
getItems = liftIO $ do
    aa <- nextRandom -- IO
    bb <- getCurrentTime -- IO
    cc <- getDataFromDb -- IO
    ...

IO各アクションを個別に持ち上げる代わりに。

その他の一般的なケース:

これらの関数はすべて非常に単純であり、ソース コードを確認すると有益です。

于 2016-03-25T11:28:04.170 に答える