-- {-# LANGUAGE DataKinds #-} -- {-# LANGUAGE TypeOperators #-} {-| Module : Storage -> Persistance Description : Persistance component. Copyright : >implying License : >implying Maintainer : Florian Hageneder Stability : none Portability : what? -} -- module Storage (loadGames, loadGame, saveGames, saveGame) where module Storage where import Game (Game (..)) import Control.Exception import Data.List (find) import Control.Monad.IO.Class import Control.Monad (when) import System.IO hiding (readFile) import Prelude hiding (readFile) import System.IO.Strict (readFile) -- | The storage to keep all game sessions gameFile :: FilePath gameFile = "storage.dat" -- ########################################################################### -- Read games -- | Returns all the stored games. loadGames :: IO [Game] -- ^ Loads all stored games from the storage loadGames = do content <- readFile gameFile return $ read content -- | Returns a single stored game or Nothing loadGame :: Int -- ^ GameID to get -> IO (Maybe Game) loadGame gid = do games <- loadGames return $ find (\g -> gameId g == gid) games -- ########################################################################### -- Store games -- | Overrides the whole storage with the given set of games saveGames :: [Game] -- ^ All games that should be persisted in the storage -> IO () -- ^ writes everything the storage saveGames games = writeFile gameFile (show games) -- | Overrides the stored game with same ID or appends it to the list saveGame :: Game -- ^ Single game to update -> IO () -- ^ Writes result to the file saveGame update = do games <- loadGames let newGames = updateGames games update when (length newGames >= 0) $ writeFile gameFile (show $ updateGames games update) {- | Takes a set of Games and replaces the game with the same ID as the given updated game. Appends it if there is no such game -} updateGames :: [Game] -- ^ List of games that should be updated -> Game -- ^ Game that should be updated or added -> [Game] -- ^ updated list updateGames input update = if not (any (\ g -> gameId g == gameId update) input) then input ++ [update] else map (\g -> if gameId g == gameId update then update else g) input