3

Happstackサーバーを作成していて、接続するMongoDBデータベースがあります。そのために、接続プールを作成する関数を作成しました

type MongoPool = Pool IOError Pipe

withMongo :: (MongoPool -> IO a) -> IO ()
withMongo f = do
    pool <- dbPool
    f pool
    killAll pool

そしてAction、作成されたプールでを実行する関数:

runDB :: (MonadIO m) => MongoPool -> Action IO a -> m (Either Failure a)
runDB pool f = liftIO $ do
    pipe <- runIOE $ aResource pool
    access pipe master dbName f

poolこれには、すべてのルートでパラメータとしてを実行する必要があることは明らかです。私はそれをにラップしたいReaderTので、それrunDBはのようなタイプAction IO a -> ServerPart (Either Failure a)またはそれ以上のタイプを持つことができAction IO a -> ServerPart a、失敗すると自動的にHTTPエラー500が発生します。

それをどのように達成できるかについて頭を悩ませています。Haskellモナドとhappstackの経験が豊富な人からのヒントが欲しいです。

ありがとう。

4

1 に答える 1

3

この質問を通して、私は非常に良いヒントを持つ別のものを見つけました、そして私はこれを構築しました。それはうまくいくようで、私はそれを共有したいと思いました:

type MongoPool = Pool IOError Pipe

type DBServerPart a = ReaderT MongoPool (ServerPartT IO) a

hostName = "127.0.0.1"

dbName = "test"

defaultPoolSize = 10

runDB :: Action IO a -> DBServerPart (Either Failure a)
runDB f = do
    pool <- ask
    liftIO $ do
        pipe <- runIOE $ aResource pool
        access pipe master dbName f

withMongo :: DBServerPart a -> ServerPart a
withMongo f = do
    pool <- liftIO $ dbPool
    a <- runReaderT f pool
    liftIO $ killAll pool
    return a

dbPool = newPool fac defaultPoolSize
    where fac = Factory {
            newResource = connect $ host hostName,
            killResource = close,
            isExpired = isClosed
        }
于 2012-04-01T13:01:22.033 に答える