ebook-manager/src/API/Books.hs

76 lines
2.7 KiB
Haskell
Raw Normal View History

2018-08-07 23:25:21 +03:00
{-# Language DuplicateRecordFields #-}
2018-08-05 23:42:37 +03:00
{-# Language DataKinds #-}
{-# Language TypeFamilies #-}
{-# Language TypeOperators #-}
{-# Language NoImplicitPrelude #-}
{-# Language MultiParamTypeClasses #-}
{-# Language OverloadedStrings #-}
{-# Language TemplateHaskell #-}
{-# Language QuasiQuotes #-}
{-# Language RecordWildCards #-}
{-# Language DeriveGeneric #-}
{-# Language FlexibleInstances #-}
{-# Language TypeApplications #-}
{-# Language DataKinds #-}
2018-08-07 23:25:21 +03:00
{-# Language NamedFieldPuns #-}
2018-08-05 23:42:37 +03:00
module API.Books where
import Servant hiding (contentType)
import Types
import ClassyPrelude
import Server.Auth
import Servant.Auth as SA
import Data.Aeson
import API.Channels (JsonChannel(..))
import Database.Book
import Database.Channel
import Database
import Control.Lens
import Data.Generics.Product
2018-08-07 23:25:21 +03:00
data JsonBook = JsonBook { identifier :: BookID
, contentType :: Text
, title :: Maybe Text
, description :: Maybe Text
, channels :: [JsonChannel] }
deriving (Generic, Show)
data PostBook = PostBook { contentType :: Text
2018-08-05 23:42:37 +03:00
, title :: Maybe Text
, description :: Maybe Text
, channels :: [JsonChannel] }
deriving (Generic, Show)
2018-08-06 00:09:41 +03:00
2018-08-05 23:42:37 +03:00
instance ToJSON JsonBook
instance FromJSON JsonBook
2018-08-07 23:25:21 +03:00
instance ToJSON PostBook
instance FromJSON PostBook
2018-08-05 23:42:37 +03:00
type API = Auth '[SA.BasicAuth, SA.JWT] SafeUser :> BaseAPI
type BaseAPI = "books" :> Get '[JSON] [JsonBook]
2018-08-07 23:25:21 +03:00
:<|> "books" :> ReqBody '[JSON] PostBook :> Post '[JSON] JsonBook
:<|> "books" :> Capture "book_id" BookID :> ReqBody '[JSON] JsonBook :> Post '[JSON] JsonBook
-- :<|> "books" :> Capture "book_id" BookID :> ReqBody '[JSON] JsonBook :> PUT JsonBook
2018-08-05 23:42:37 +03:00
handler :: ServerT API AppM
2018-08-07 23:25:21 +03:00
handler user = listBooksHandler user :<|> postBookMetaHandler user :<|> putBookMetaHandler user
postBookMetaHandler :: AuthResult SafeUser -> PostBook -> AppM JsonBook
postBookMetaHandler auth PostBook{..} = flip requireLoggedIn auth $ \SafeUser{username} -> do
mIdentifier <- runDB $ insertBook username Book{identifier=def,contentHash=Nothing,..}
maybe (throwM err403{errBody="Could not insert book"}) (\identifier -> pure JsonBook{..}) mIdentifier
putBookMetaHandler :: AuthResult SafeUser -> BookID -> JsonBook -> AppM JsonBook
putBookMetaHandler _ _ _ = throwM err403
2018-08-05 23:42:37 +03:00
listBooksHandler :: AuthResult SafeUser -> AppM [JsonBook]
listBooksHandler = requireLoggedIn $ \user -> do
runDB (usersBooks (view (field @"username") user) >>= mapM augment)
where
2018-08-07 22:27:05 +03:00
augment Book{identifier=bookId,..} = do
channels <- fmap (\Channel{..} -> JsonChannel{..}) <$> booksChannels bookId
2018-08-07 23:25:21 +03:00
pure JsonBook{identifier=bookId,..}