我正在尝试在 Haskell 中为基于回合的游戏实现服务器。我的选择是将 Yesod 用于管理和元信息(例如,用户参与的游戏等)。
我想使用网络套接字来保持游戏中的数据开销很小。
查看 ws-chat 示例,我不确定如何访问 Handler Monad 并使用它 Persistent。
最好有一些用于连接的簿记代码围绕一个“普通”处理程序,该处理程序本身会更新数据库并通知相关用户。
这就是我认为它应该看起来的样子。
{-# LANGUAGE QuasiQuotes, TypeFamilies, GeneralizedNewtypeDeriving, TemplateHaskell, OverloadedStrings, GADTs, FlexibleContexts #-}
module Main where
import Control.Monad.IO.Class (liftIO)
import Data.String (fromString)
import Database.Persist
import Database.Persist.TH
import Database.Persist.Sqlite
import Network.Wai.Application.Static (staticApp, defaultWebAppSettings, defaultFileServerSettings)
import Network.Wai.Handler.Warp (runSettings, defaultSettings, settingsIntercept, settingsPort)
import Network.Wai.Handler.WebSockets (intercept)
import qualified Network.WebSockets as WS
share [mkPersist sqlSettings, mkMigrate "migrateAll"] [persistUpperCase|
Person
name String
age Int
deriving Show
|]
ws :: WS.Request -> WS.WebSockets WS.Hybi10 ()
ws r = do
WS.acceptRequest r
liftIO $ runSqlite ":memory:" $ do
runMigration migrateAll
michaelId <- insert $ Person "Michael" 26
michael <- get michaelId
liftIO $ print michael
main :: IO ()
main = runSettings defaultSettings
{ settingsPort = 9160
, settingsIntercept = intercept $ ws
} $ staticApp (defaultFileServerSettings $ fromString ".")
如果你想Handler
自己运行一个 monad,你可以使用runFakeHandler。
我正在使用Yesod.WebSockets库,并且能够在 Web 套接字应用程序中访问数据库,如下所示:
voteApp :: WebSocketsT Handler ()
voteApp = do
uuid <- liftIO nextRandom
master <- getYesod
runSqlPool (insert (Session uuid)) $ appConnPool master
-- rest of the handler