{-# LANGUAGE CPP #-}
{-# LANGUAGE ConstraintKinds #-}
{-# LANGUAGE FlexibleContexts #-}
{-# LANGUAGE GADTs #-}
{-# LANGUAGE RecordWildCards #-}
{-# LANGUAGE TypeFamilies #-}
{-# LANGUAGE TypeOperators #-}
#if !MIN_VERSION_persistent(2,14,0)
{-# OPTIONS_GHC -Wno-redundant-constraints #-}
#endif
module Data.Mergeless.Persistent
(
clientMakeSyncRequestQuery,
clientMergeSyncResponseQuery,
clientSyncProcessor,
serverProcessSyncQuery,
serverProcessSyncWithCustomIdQuery,
serverSyncProcessor,
serverSyncProcessorWithCustomId,
setupUnsyncedClientQuery,
setupClientQuery,
clientGetStoreQuery,
serverGetStoreQuery,
setupServerQuery,
)
where
import Control.Monad
import Control.Monad.IO.Class
import qualified Data.Map as M
import Data.Maybe
import Data.Mergeless
import qualified Data.Set as S
import Database.Persist
import Database.Persist.Sql
import Lens.Micro
clientMakeSyncRequestQuery ::
( Ord sid,
PersistEntity clientRecord,
PersistField sid,
PersistEntityBackend clientRecord ~ SqlBackend,
MonadIO m
) =>
(clientRecord -> a) ->
EntityField clientRecord (Maybe sid) ->
EntityField clientRecord Bool ->
SqlPersistT m (SyncRequest (Key clientRecord) sid a)
clientMakeSyncRequestQuery :: forall sid clientRecord (m :: * -> *) a.
(Ord sid, PersistEntity clientRecord, PersistField sid,
PersistEntityBackend clientRecord ~ SqlBackend, MonadIO m) =>
(clientRecord -> a)
-> EntityField clientRecord (Maybe sid)
-> EntityField clientRecord Bool
-> SqlPersistT m (SyncRequest (Key clientRecord) sid a)
clientMakeSyncRequestQuery clientRecord -> a
func EntityField clientRecord (Maybe sid)
serverIdField EntityField clientRecord Bool
deletedField = do
Map (Key clientRecord) a
syncRequestAdded <-
forall k a. Ord k => [(k, a)] -> Map k a
M.fromList forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a b. (a -> b) -> [a] -> [b]
map (\(Entity Key clientRecord
cid clientRecord
ct) -> (Key clientRecord
cid, clientRecord -> a
func clientRecord
ct))
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall record backend (m :: * -> *).
(MonadIO m, PersistQueryRead backend,
PersistRecordBackend record backend) =>
[Filter record]
-> [SelectOpt record] -> ReaderT backend m [Entity record]
selectList
[ EntityField clientRecord (Maybe sid)
serverIdField forall v typ.
PersistField typ =>
EntityField v typ -> typ -> Filter v
==. forall a. Maybe a
Nothing,
EntityField clientRecord Bool
deletedField forall v typ.
PersistField typ =>
EntityField v typ -> typ -> Filter v
==. Bool
False
]
[]
Set sid
syncRequestSynced <-
forall a. Ord a => [a] -> Set a
S.fromList forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a b. (a -> Maybe b) -> [a] -> [b]
mapMaybe (\Entity clientRecord
e -> Entity clientRecord
e forall s a. s -> Getting a s a -> a
^. forall record field.
PersistEntity record =>
EntityField record field
-> forall (f :: * -> *).
Functor f =>
(field -> f field) -> Entity record -> f (Entity record)
fieldLens EntityField clientRecord (Maybe sid)
serverIdField)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall record backend (m :: * -> *).
(MonadIO m, PersistQueryRead backend,
PersistRecordBackend record backend) =>
[Filter record]
-> [SelectOpt record] -> ReaderT backend m [Entity record]
selectList
[ EntityField clientRecord (Maybe sid)
serverIdField forall v typ.
PersistField typ =>
EntityField v typ -> typ -> Filter v
!=. forall a. Maybe a
Nothing,
EntityField clientRecord Bool
deletedField forall v typ.
PersistField typ =>
EntityField v typ -> typ -> Filter v
==. Bool
False
]
[]
Set sid
syncRequestDeleted <-
forall a. Ord a => [a] -> Set a
S.fromList forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a b. (a -> Maybe b) -> [a] -> [b]
mapMaybe (\Entity clientRecord
e -> Entity clientRecord
e forall s a. s -> Getting a s a -> a
^. forall record field.
PersistEntity record =>
EntityField record field
-> forall (f :: * -> *).
Functor f =>
(field -> f field) -> Entity record -> f (Entity record)
fieldLens EntityField clientRecord (Maybe sid)
serverIdField)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall record backend (m :: * -> *).
(MonadIO m, PersistQueryRead backend,
PersistRecordBackend record backend) =>
[Filter record]
-> [SelectOpt record] -> ReaderT backend m [Entity record]
selectList
[ EntityField clientRecord (Maybe sid)
serverIdField forall v typ.
PersistField typ =>
EntityField v typ -> typ -> Filter v
!=. forall a. Maybe a
Nothing,
EntityField clientRecord Bool
deletedField forall v typ.
PersistField typ =>
EntityField v typ -> typ -> Filter v
==. Bool
True
]
[]
forall (f :: * -> *) a. Applicative f => a -> f a
pure SyncRequest {Map (Key clientRecord) a
Set sid
syncRequestAdded :: Map (Key clientRecord) a
syncRequestSynced :: Set sid
syncRequestDeleted :: Set sid
syncRequestDeleted :: Set sid
syncRequestSynced :: Set sid
syncRequestAdded :: Map (Key clientRecord) a
..}
clientMergeSyncResponseQuery ::
( PersistEntity clientRecord,
PersistField sid,
PersistEntityBackend clientRecord ~ SqlBackend,
SafeToInsert clientRecord,
MonadIO m
) =>
(sid -> a -> clientRecord) ->
EntityField clientRecord (Maybe sid) ->
EntityField clientRecord Bool ->
SyncResponse (Key clientRecord) sid a ->
SqlPersistT m ()
clientMergeSyncResponseQuery :: forall clientRecord sid (m :: * -> *) a.
(PersistEntity clientRecord, PersistField sid,
PersistEntityBackend clientRecord ~ SqlBackend,
SafeToInsert clientRecord, MonadIO m) =>
(sid -> a -> clientRecord)
-> EntityField clientRecord (Maybe sid)
-> EntityField clientRecord Bool
-> SyncResponse (Key clientRecord) sid a
-> SqlPersistT m ()
clientMergeSyncResponseQuery sid -> a -> clientRecord
func EntityField clientRecord (Maybe sid)
serverIdField EntityField clientRecord Bool
deletedField = forall (m :: * -> *) ci si a.
Monad m =>
ClientSyncProcessor ci si a m -> SyncResponse ci si a -> m ()
mergeSyncResponseCustom forall a b. (a -> b) -> a -> b
$ forall clientRecord sid (m :: * -> *) a.
(PersistEntity clientRecord, PersistField sid,
PersistEntityBackend clientRecord ~ SqlBackend,
SafeToInsert clientRecord, MonadIO m) =>
(sid -> a -> clientRecord)
-> EntityField clientRecord (Maybe sid)
-> EntityField clientRecord Bool
-> ClientSyncProcessor (Key clientRecord) sid a (SqlPersistT m)
clientSyncProcessor sid -> a -> clientRecord
func EntityField clientRecord (Maybe sid)
serverIdField EntityField clientRecord Bool
deletedField
clientSyncProcessor ::
( PersistEntity clientRecord,
PersistField sid,
PersistEntityBackend clientRecord ~ SqlBackend,
SafeToInsert clientRecord,
MonadIO m
) =>
(sid -> a -> clientRecord) ->
EntityField clientRecord (Maybe sid) ->
EntityField clientRecord Bool ->
ClientSyncProcessor (Key clientRecord) sid a (SqlPersistT m)
clientSyncProcessor :: forall clientRecord sid (m :: * -> *) a.
(PersistEntity clientRecord, PersistField sid,
PersistEntityBackend clientRecord ~ SqlBackend,
SafeToInsert clientRecord, MonadIO m) =>
(sid -> a -> clientRecord)
-> EntityField clientRecord (Maybe sid)
-> EntityField clientRecord Bool
-> ClientSyncProcessor (Key clientRecord) sid a (SqlPersistT m)
clientSyncProcessor sid -> a -> clientRecord
func EntityField clientRecord (Maybe sid)
serverIdField EntityField clientRecord Bool
deletedField = ClientSyncProcessor {Map sid a -> ReaderT SqlBackend m ()
Map (Key clientRecord) sid -> ReaderT SqlBackend m ()
Set sid -> ReaderT SqlBackend m ()
clientSyncProcessorSyncServerAdded :: Map sid a -> ReaderT SqlBackend m ()
clientSyncProcessorSyncClientAdded :: Map (Key clientRecord) sid -> ReaderT SqlBackend m ()
clientSyncProcessorSyncServerDeleted :: Set sid -> ReaderT SqlBackend m ()
clientSyncProcessorSyncClientDeleted :: Set sid -> ReaderT SqlBackend m ()
clientSyncProcessorSyncClientDeleted :: Set sid -> ReaderT SqlBackend m ()
clientSyncProcessorSyncServerDeleted :: Set sid -> ReaderT SqlBackend m ()
clientSyncProcessorSyncClientAdded :: Map (Key clientRecord) sid -> ReaderT SqlBackend m ()
clientSyncProcessorSyncServerAdded :: Map sid a -> ReaderT SqlBackend m ()
..}
where
clientSyncProcessorSyncServerAdded :: Map sid a -> ReaderT SqlBackend m ()
clientSyncProcessorSyncServerAdded Map sid a
m = forall (t :: * -> *) (m :: * -> *) a b.
(Foldable t, Monad m) =>
t a -> (a -> m b) -> m ()
forM_ (forall k a. Map k a -> [(k, a)]
M.toList Map sid a
m) forall a b. (a -> b) -> a -> b
$ \(sid
si, a
st) ->
forall backend record (m :: * -> *).
(PersistStoreWrite backend, MonadIO m,
PersistRecordBackend record backend, SafeToInsert record) =>
record -> ReaderT backend m ()
insert_ forall a b. (a -> b) -> a -> b
$ sid -> a -> clientRecord
func sid
si a
st
clientSyncProcessorSyncClientAdded :: Map (Key clientRecord) sid -> ReaderT SqlBackend m ()
clientSyncProcessorSyncClientAdded Map (Key clientRecord) sid
m = forall (t :: * -> *) (m :: * -> *) a b.
(Foldable t, Monad m) =>
t a -> (a -> m b) -> m ()
forM_ (forall k a. Map k a -> [(k, a)]
M.toList Map (Key clientRecord) sid
m) forall a b. (a -> b) -> a -> b
$ \(Key clientRecord
cid, sid
sid) ->
forall backend record (m :: * -> *).
(PersistStoreWrite backend, MonadIO m,
PersistRecordBackend record backend) =>
Key record -> [Update record] -> ReaderT backend m ()
update Key clientRecord
cid [EntityField clientRecord (Maybe sid)
serverIdField forall v typ.
PersistField typ =>
EntityField v typ -> typ -> Update v
=. forall a. a -> Maybe a
Just sid
sid]
clientSyncProcessorSyncServerDeleted :: Set sid -> ReaderT SqlBackend m ()
clientSyncProcessorSyncServerDeleted Set sid
s = forall (t :: * -> *) (m :: * -> *) a b.
(Foldable t, Monad m) =>
t a -> (a -> m b) -> m ()
forM_ (forall a. Set a -> [a]
S.toList Set sid
s) forall a b. (a -> b) -> a -> b
$ \sid
sid ->
forall backend (m :: * -> *) record.
(PersistQueryWrite backend, MonadIO m,
PersistRecordBackend record backend) =>
[Filter record] -> ReaderT backend m ()
deleteWhere [EntityField clientRecord (Maybe sid)
serverIdField forall v typ.
PersistField typ =>
EntityField v typ -> typ -> Filter v
==. forall a. a -> Maybe a
Just sid
sid]
clientSyncProcessorSyncClientDeleted :: Set sid -> ReaderT SqlBackend m ()
clientSyncProcessorSyncClientDeleted Set sid
s = forall (t :: * -> *) (m :: * -> *) a b.
(Foldable t, Monad m) =>
t a -> (a -> m b) -> m ()
forM_ (forall a. Set a -> [a]
S.toList Set sid
s) forall a b. (a -> b) -> a -> b
$ \sid
sid ->
forall backend (m :: * -> *) record.
(PersistQueryWrite backend, MonadIO m,
PersistRecordBackend record backend) =>
[Filter record] -> ReaderT backend m ()
deleteWhere [EntityField clientRecord (Maybe sid)
serverIdField forall v typ.
PersistField typ =>
EntityField v typ -> typ -> Filter v
==. forall a. a -> Maybe a
Just sid
sid, EntityField clientRecord Bool
deletedField forall v typ.
PersistField typ =>
EntityField v typ -> typ -> Filter v
==. Bool
True]
serverProcessSyncQuery ::
( PersistEntity record,
PersistEntityBackend record ~ SqlBackend,
SafeToInsert record,
MonadIO m
) =>
[Filter record] ->
(record -> a) ->
(a -> record) ->
SyncRequest ci (Key record) a ->
SqlPersistT m (SyncResponse ci (Key record) a)
serverProcessSyncQuery :: forall record (m :: * -> *) a ci.
(PersistEntity record, PersistEntityBackend record ~ SqlBackend,
SafeToInsert record, MonadIO m) =>
[Filter record]
-> (record -> a)
-> (a -> record)
-> SyncRequest ci (Key record) a
-> SqlPersistT m (SyncResponse ci (Key record) a)
serverProcessSyncQuery [Filter record]
filters record -> a
funcTo a -> record
funcFrom = forall ci si a (m :: * -> *).
(Ord si, Monad m) =>
ServerSyncProcessor ci si a m
-> SyncRequest ci si a -> m (SyncResponse ci si a)
processServerSyncCustom forall a b. (a -> b) -> a -> b
$ forall record (m :: * -> *) a ci.
(PersistEntity record, PersistEntityBackend record ~ SqlBackend,
SafeToInsert record, MonadIO m) =>
[Filter record]
-> (record -> a)
-> (a -> record)
-> ServerSyncProcessor ci (Key record) a (SqlPersistT m)
serverSyncProcessor [Filter record]
filters record -> a
funcTo a -> record
funcFrom
serverSyncProcessor ::
( PersistEntity record,
PersistEntityBackend record ~ SqlBackend,
SafeToInsert record,
MonadIO m
) =>
[Filter record] ->
(record -> a) ->
(a -> record) ->
ServerSyncProcessor ci (Key record) a (SqlPersistT m)
serverSyncProcessor :: forall record (m :: * -> *) a ci.
(PersistEntity record, PersistEntityBackend record ~ SqlBackend,
SafeToInsert record, MonadIO m) =>
[Filter record]
-> (record -> a)
-> (a -> record)
-> ServerSyncProcessor ci (Key record) a (SqlPersistT m)
serverSyncProcessor [Filter record]
filters record -> a
funcTo a -> record
funcFrom =
ServerSyncProcessor {ReaderT SqlBackend m (Map (Key record) a)
Map ci a -> ReaderT SqlBackend m (Map ci (Key record))
forall {record} {backend} {m :: * -> *} {t :: * -> *}.
(PersistEntityBackend record ~ BaseBackend backend, MonadIO m,
PersistStoreWrite backend, Foldable t, PersistEntity record) =>
t (Key record) -> ReaderT backend m (t (Key record))
serverSyncProcessorRead :: ReaderT SqlBackend m (Map (Key record) a)
serverSyncProcessorAddItems :: Map ci a -> ReaderT SqlBackend m (Map ci (Key record))
serverSyncProcessorDeleteItems :: Set (Key record) -> ReaderT SqlBackend m (Set (Key record))
serverSyncProcessorDeleteItems :: forall {record} {backend} {m :: * -> *} {t :: * -> *}.
(PersistEntityBackend record ~ BaseBackend backend, MonadIO m,
PersistStoreWrite backend, Foldable t, PersistEntity record) =>
t (Key record) -> ReaderT backend m (t (Key record))
serverSyncProcessorAddItems :: Map ci a -> ReaderT SqlBackend m (Map ci (Key record))
serverSyncProcessorRead :: ReaderT SqlBackend m (Map (Key record) a)
..}
where
serverSyncProcessorRead :: ReaderT SqlBackend m (Map (Key record) a)
serverSyncProcessorRead = forall k a. Ord k => [(k, a)] -> Map k a
M.fromList forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a b. (a -> b) -> [a] -> [b]
map (\(Entity Key record
i record
record) -> (Key record
i, record -> a
funcTo record
record)) forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall record backend (m :: * -> *).
(MonadIO m, PersistQueryRead backend,
PersistRecordBackend record backend) =>
[Filter record]
-> [SelectOpt record] -> ReaderT backend m [Entity record]
selectList [Filter record]
filters []
serverSyncProcessorAddItems :: Map ci a -> ReaderT SqlBackend m (Map ci (Key record))
serverSyncProcessorAddItems = forall (t :: * -> *) (m :: * -> *) a b.
(Traversable t, Monad m) =>
(a -> m b) -> t a -> m (t b)
mapM forall a b. (a -> b) -> a -> b
$ forall backend record (m :: * -> *).
(PersistStoreWrite backend, MonadIO m,
PersistRecordBackend record backend, SafeToInsert record) =>
record -> ReaderT backend m (Key record)
insert forall b c a. (b -> c) -> (a -> b) -> a -> c
. a -> record
funcFrom
serverSyncProcessorDeleteItems :: t (Key record) -> ReaderT backend m (t (Key record))
serverSyncProcessorDeleteItems t (Key record)
s = do
forall (t :: * -> *) (m :: * -> *) a b.
(Foldable t, Monad m) =>
(a -> m b) -> t a -> m ()
mapM_ forall backend record (m :: * -> *).
(PersistStoreWrite backend, MonadIO m,
PersistRecordBackend record backend) =>
Key record -> ReaderT backend m ()
delete t (Key record)
s
forall (f :: * -> *) a. Applicative f => a -> f a
pure t (Key record)
s
serverProcessSyncWithCustomIdQuery ::
( Ord sid,
PersistEntity record,
PersistField sid,
PersistEntityBackend record ~ SqlBackend,
SafeToInsert record,
MonadIO m
) =>
SqlPersistT m sid ->
EntityField record sid ->
[Filter record] ->
(record -> (sid, a)) ->
(sid -> a -> record) ->
SyncRequest ci sid a ->
SqlPersistT m (SyncResponse ci sid a)
serverProcessSyncWithCustomIdQuery :: forall sid record (m :: * -> *) a ci.
(Ord sid, PersistEntity record, PersistField sid,
PersistEntityBackend record ~ SqlBackend, SafeToInsert record,
MonadIO m) =>
SqlPersistT m sid
-> EntityField record sid
-> [Filter record]
-> (record -> (sid, a))
-> (sid -> a -> record)
-> SyncRequest ci sid a
-> SqlPersistT m (SyncResponse ci sid a)
serverProcessSyncWithCustomIdQuery SqlPersistT m sid
genId EntityField record sid
idField [Filter record]
filters record -> (sid, a)
funcTo sid -> a -> record
funcFrom = forall ci si a (m :: * -> *).
(Ord si, Monad m) =>
ServerSyncProcessor ci si a m
-> SyncRequest ci si a -> m (SyncResponse ci si a)
processServerSyncCustom forall a b. (a -> b) -> a -> b
$ forall sid record (m :: * -> *) a ci.
(Ord sid, PersistEntity record, PersistField sid,
PersistEntityBackend record ~ SqlBackend, SafeToInsert record,
MonadIO m) =>
SqlPersistT m sid
-> EntityField record sid
-> [Filter record]
-> (record -> (sid, a))
-> (sid -> a -> record)
-> ServerSyncProcessor ci sid a (SqlPersistT m)
serverSyncProcessorWithCustomId SqlPersistT m sid
genId EntityField record sid
idField [Filter record]
filters record -> (sid, a)
funcTo sid -> a -> record
funcFrom
serverSyncProcessorWithCustomId ::
( Ord sid,
PersistEntity record,
PersistField sid,
PersistEntityBackend record ~ SqlBackend,
SafeToInsert record,
MonadIO m
) =>
SqlPersistT m sid ->
EntityField record sid ->
[Filter record] ->
(record -> (sid, a)) ->
(sid -> a -> record) ->
ServerSyncProcessor ci sid a (SqlPersistT m)
serverSyncProcessorWithCustomId :: forall sid record (m :: * -> *) a ci.
(Ord sid, PersistEntity record, PersistField sid,
PersistEntityBackend record ~ SqlBackend, SafeToInsert record,
MonadIO m) =>
SqlPersistT m sid
-> EntityField record sid
-> [Filter record]
-> (record -> (sid, a))
-> (sid -> a -> record)
-> ServerSyncProcessor ci sid a (SqlPersistT m)
serverSyncProcessorWithCustomId SqlPersistT m sid
genId EntityField record sid
idField [Filter record]
filters record -> (sid, a)
funcTo sid -> a -> record
funcFrom =
ServerSyncProcessor {ReaderT SqlBackend m (Map sid a)
Map ci a -> ReaderT SqlBackend m (Map ci sid)
Set sid -> ReaderT SqlBackend m (Set sid)
serverSyncProcessorDeleteItems :: Set sid -> ReaderT SqlBackend m (Set sid)
serverSyncProcessorAddItems :: Map ci a -> ReaderT SqlBackend m (Map ci sid)
serverSyncProcessorRead :: ReaderT SqlBackend m (Map sid a)
serverSyncProcessorRead :: ReaderT SqlBackend m (Map sid a)
serverSyncProcessorAddItems :: Map ci a -> ReaderT SqlBackend m (Map ci sid)
serverSyncProcessorDeleteItems :: Set sid -> ReaderT SqlBackend m (Set sid)
..}
where
serverSyncProcessorRead :: ReaderT SqlBackend m (Map sid a)
serverSyncProcessorRead = forall k a. Ord k => [(k, a)] -> Map k a
M.fromList forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a b. (a -> b) -> [a] -> [b]
map (record -> (sid, a)
funcTo forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall record. Entity record -> record
entityVal) forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall record backend (m :: * -> *).
(MonadIO m, PersistQueryRead backend,
PersistRecordBackend record backend) =>
[Filter record]
-> [SelectOpt record] -> ReaderT backend m [Entity record]
selectList [Filter record]
filters []
serverSyncProcessorAddItems :: Map ci a -> ReaderT SqlBackend m (Map ci sid)
serverSyncProcessorAddItems = forall (t :: * -> *) (m :: * -> *) a b.
(Traversable t, Monad m) =>
(a -> m b) -> t a -> m (t b)
mapM forall a b. (a -> b) -> a -> b
$ \a
a -> do
sid
sid <- SqlPersistT m sid
genId
let record :: record
record = sid -> a -> record
funcFrom sid
sid a
a
forall backend record (m :: * -> *).
(PersistStoreWrite backend, MonadIO m,
PersistRecordBackend record backend, SafeToInsert record) =>
record -> ReaderT backend m ()
insert_ record
record
forall (f :: * -> *) a. Applicative f => a -> f a
pure sid
sid
serverSyncProcessorDeleteItems :: Set sid -> ReaderT SqlBackend m (Set sid)
serverSyncProcessorDeleteItems Set sid
s = do
forall (t :: * -> *) (m :: * -> *) a b.
(Foldable t, Monad m) =>
t a -> (a -> m b) -> m ()
forM_ Set sid
s forall a b. (a -> b) -> a -> b
$ \sid
sid -> forall backend (m :: * -> *) record.
(PersistQueryWrite backend, MonadIO m,
PersistRecordBackend record backend) =>
[Filter record] -> ReaderT backend m ()
deleteWhere [EntityField record sid
idField forall v typ.
PersistField typ =>
EntityField v typ -> typ -> Filter v
==. sid
sid]
forall (f :: * -> *) a. Applicative f => a -> f a
pure Set sid
s
setupUnsyncedClientQuery ::
( PersistEntity clientRecord,
PersistEntityBackend clientRecord ~ SqlBackend,
SafeToInsert clientRecord,
MonadIO m
) =>
(a -> clientRecord) ->
[a] ->
SqlPersistT m ()
setupUnsyncedClientQuery :: forall clientRecord (m :: * -> *) a.
(PersistEntity clientRecord,
PersistEntityBackend clientRecord ~ SqlBackend,
SafeToInsert clientRecord, MonadIO m) =>
(a -> clientRecord) -> [a] -> SqlPersistT m ()
setupUnsyncedClientQuery a -> clientRecord
func = forall (t :: * -> *) (m :: * -> *) a b.
(Foldable t, Monad m) =>
(a -> m b) -> t a -> m ()
mapM_ (forall backend record (m :: * -> *).
(PersistStoreWrite backend, MonadIO m,
PersistRecordBackend record backend, SafeToInsert record) =>
record -> ReaderT backend m (Key record)
insert forall b c a. (b -> c) -> (a -> b) -> a -> c
. a -> clientRecord
func)
setupClientQuery ::
( PersistEntity clientRecord,
PersistEntityBackend clientRecord ~ SqlBackend,
SafeToInsert clientRecord,
MonadIO m
) =>
(a -> clientRecord) ->
(sid -> a -> clientRecord) ->
(sid -> clientRecord) ->
ClientStore (Key clientRecord) sid a ->
SqlPersistT m ()
setupClientQuery :: forall clientRecord (m :: * -> *) a sid.
(PersistEntity clientRecord,
PersistEntityBackend clientRecord ~ SqlBackend,
SafeToInsert clientRecord, MonadIO m) =>
(a -> clientRecord)
-> (sid -> a -> clientRecord)
-> (sid -> clientRecord)
-> ClientStore (Key clientRecord) sid a
-> SqlPersistT m ()
setupClientQuery a -> clientRecord
funcU sid -> a -> clientRecord
funcS sid -> clientRecord
funcD ClientStore {Map sid a
Map (Key clientRecord) a
Set sid
clientStoreAdded :: forall ci si a. ClientStore ci si a -> Map ci a
clientStoreSynced :: forall ci si a. ClientStore ci si a -> Map si a
clientStoreDeleted :: forall ci si a. ClientStore ci si a -> Set si
clientStoreDeleted :: Set sid
clientStoreSynced :: Map sid a
clientStoreAdded :: Map (Key clientRecord) a
..} = do
forall (t :: * -> *) (m :: * -> *) a b.
(Foldable t, Monad m) =>
t a -> (a -> m b) -> m ()
forM_ (forall k a. Map k a -> [(k, a)]
M.toList Map (Key clientRecord) a
clientStoreAdded) forall a b. (a -> b) -> a -> b
$ \(Key clientRecord
cid, a
st) ->
forall backend record (m :: * -> *).
(PersistStoreWrite backend, MonadIO m,
PersistRecordBackend record backend) =>
Key record -> record -> ReaderT backend m ()
insertKey
Key clientRecord
cid
(a -> clientRecord
funcU a
st)
forall (t :: * -> *) (m :: * -> *) a b.
(Foldable t, Monad m) =>
t a -> (a -> m b) -> m ()
forM_ (forall k a. Map k a -> [(k, a)]
M.toList Map sid a
clientStoreSynced) forall a b. (a -> b) -> a -> b
$ \(sid
sid, a
st) ->
forall backend record (m :: * -> *).
(PersistStoreWrite backend, MonadIO m,
PersistRecordBackend record backend, SafeToInsert record) =>
record -> ReaderT backend m ()
insert_ (sid -> a -> clientRecord
funcS sid
sid a
st)
forall (t :: * -> *) (m :: * -> *) a b.
(Foldable t, Monad m) =>
t a -> (a -> m b) -> m ()
forM_ (forall a. Set a -> [a]
S.toList Set sid
clientStoreDeleted) forall a b. (a -> b) -> a -> b
$ \sid
sid ->
forall backend record (m :: * -> *).
(PersistStoreWrite backend, MonadIO m,
PersistRecordBackend record backend, SafeToInsert record) =>
record -> ReaderT backend m ()
insert_ (sid -> clientRecord
funcD sid
sid)
clientGetStoreQuery ::
( Ord sid,
PersistEntity clientRecord,
PersistField sid,
PersistEntityBackend clientRecord ~ SqlBackend,
MonadIO m
) =>
(clientRecord -> a) ->
EntityField clientRecord (Maybe sid) ->
EntityField clientRecord Bool ->
SqlPersistT m (ClientStore (Key clientRecord) sid a)
clientGetStoreQuery :: forall sid clientRecord (m :: * -> *) a.
(Ord sid, PersistEntity clientRecord, PersistField sid,
PersistEntityBackend clientRecord ~ SqlBackend, MonadIO m) =>
(clientRecord -> a)
-> EntityField clientRecord (Maybe sid)
-> EntityField clientRecord Bool
-> SqlPersistT m (ClientStore (Key clientRecord) sid a)
clientGetStoreQuery clientRecord -> a
func EntityField clientRecord (Maybe sid)
serverIdField EntityField clientRecord Bool
deletedField = do
Map (Key clientRecord) a
clientStoreAdded <-
forall k a. Ord k => [(k, a)] -> Map k a
M.fromList forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a b. (a -> b) -> [a] -> [b]
map (\(Entity Key clientRecord
cid clientRecord
ct) -> (Key clientRecord
cid, clientRecord -> a
func clientRecord
ct))
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall record backend (m :: * -> *).
(MonadIO m, PersistQueryRead backend,
PersistRecordBackend record backend) =>
[Filter record]
-> [SelectOpt record] -> ReaderT backend m [Entity record]
selectList
[ EntityField clientRecord (Maybe sid)
serverIdField forall v typ.
PersistField typ =>
EntityField v typ -> typ -> Filter v
==. forall a. Maybe a
Nothing,
EntityField clientRecord Bool
deletedField forall v typ.
PersistField typ =>
EntityField v typ -> typ -> Filter v
==. Bool
False
]
[]
Map sid a
clientStoreSynced <-
forall k a. Ord k => [(k, a)] -> Map k a
M.fromList forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a b. (a -> Maybe b) -> [a] -> [b]
mapMaybe (\e :: Entity clientRecord
e@(Entity Key clientRecord
_ clientRecord
ct) -> (,) forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (Entity clientRecord
e forall s a. s -> Getting a s a -> a
^. forall record field.
PersistEntity record =>
EntityField record field
-> forall (f :: * -> *).
Functor f =>
(field -> f field) -> Entity record -> f (Entity record)
fieldLens EntityField clientRecord (Maybe sid)
serverIdField) forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> forall (f :: * -> *) a. Applicative f => a -> f a
pure (clientRecord -> a
func clientRecord
ct))
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall record backend (m :: * -> *).
(MonadIO m, PersistQueryRead backend,
PersistRecordBackend record backend) =>
[Filter record]
-> [SelectOpt record] -> ReaderT backend m [Entity record]
selectList
[ EntityField clientRecord (Maybe sid)
serverIdField forall v typ.
PersistField typ =>
EntityField v typ -> typ -> Filter v
!=. forall a. Maybe a
Nothing,
EntityField clientRecord Bool
deletedField forall v typ.
PersistField typ =>
EntityField v typ -> typ -> Filter v
==. Bool
False
]
[]
Set sid
clientStoreDeleted <-
forall a. Ord a => [a] -> Set a
S.fromList forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a b. (a -> Maybe b) -> [a] -> [b]
mapMaybe (\Entity clientRecord
e -> Entity clientRecord
e forall s a. s -> Getting a s a -> a
^. forall record field.
PersistEntity record =>
EntityField record field
-> forall (f :: * -> *).
Functor f =>
(field -> f field) -> Entity record -> f (Entity record)
fieldLens EntityField clientRecord (Maybe sid)
serverIdField)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall record backend (m :: * -> *).
(MonadIO m, PersistQueryRead backend,
PersistRecordBackend record backend) =>
[Filter record]
-> [SelectOpt record] -> ReaderT backend m [Entity record]
selectList
[ EntityField clientRecord (Maybe sid)
serverIdField forall v typ.
PersistField typ =>
EntityField v typ -> typ -> Filter v
!=. forall a. Maybe a
Nothing,
EntityField clientRecord Bool
deletedField forall v typ.
PersistField typ =>
EntityField v typ -> typ -> Filter v
==. Bool
True
]
[]
forall (f :: * -> *) a. Applicative f => a -> f a
pure ClientStore {Map sid a
Map (Key clientRecord) a
Set sid
clientStoreDeleted :: Set sid
clientStoreSynced :: Map sid a
clientStoreAdded :: Map (Key clientRecord) a
clientStoreAdded :: Map (Key clientRecord) a
clientStoreSynced :: Map sid a
clientStoreDeleted :: Set sid
..}
serverGetStoreQuery ::
( PersistEntity record,
PersistEntityBackend record ~ SqlBackend,
MonadIO m
) =>
(record -> a) ->
SqlPersistT m (ServerStore (Key record) a)
serverGetStoreQuery :: forall record (m :: * -> *) a.
(PersistEntity record, PersistEntityBackend record ~ SqlBackend,
MonadIO m) =>
(record -> a) -> SqlPersistT m (ServerStore (Key record) a)
serverGetStoreQuery record -> a
func = forall si a. Map si a -> ServerStore si a
ServerStore forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall k a. Ord k => [(k, a)] -> Map k a
M.fromList forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a b. (a -> b) -> [a] -> [b]
map (\(Entity Key record
stid record
st) -> (Key record
stid, record -> a
func record
st)) forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall record backend (m :: * -> *).
(MonadIO m, PersistQueryRead backend,
PersistRecordBackend record backend) =>
[Filter record]
-> [SelectOpt record] -> ReaderT backend m [Entity record]
selectList [] []
setupServerQuery ::
( PersistEntity record,
PersistEntityBackend record ~ SqlBackend,
MonadIO m
) =>
(a -> record) ->
ServerStore (Key record) a ->
SqlPersistT m ()
setupServerQuery :: forall record (m :: * -> *) a.
(PersistEntity record, PersistEntityBackend record ~ SqlBackend,
MonadIO m) =>
(a -> record) -> ServerStore (Key record) a -> SqlPersistT m ()
setupServerQuery a -> record
func ServerStore {Map (Key record) a
serverStoreItems :: forall si a. ServerStore si a -> Map si a
serverStoreItems :: Map (Key record) a
..} = forall (t :: * -> *) (m :: * -> *) a b.
(Foldable t, Monad m) =>
t a -> (a -> m b) -> m ()
forM_ (forall k a. Map k a -> [(k, a)]
M.toList Map (Key record) a
serverStoreItems) forall a b. (a -> b) -> a -> b
$ \(Key record
i, a
e) -> forall (f :: * -> *) a. Functor f => f a -> f ()
void forall a b. (a -> b) -> a -> b
$ forall backend record (m :: * -> *).
(PersistStoreWrite backend, MonadIO m,
PersistRecordBackend record backend) =>
Key record -> record -> ReaderT backend m ()
insertKey Key record
i forall a b. (a -> b) -> a -> b
$ a -> record
func a
e
#if !MIN_VERSION_persistent(2,14,0)
type SafeToInsert a = a ~ a
#endif