Создание пользовательских экземпляров PersistBackend - PullRequest
3 голосов
/ 24 января 2012

У меня есть стек монадных преобразователей в виде:

newtype T m a = T { unT :: StateT State (SqlPersist m) a }
   deriving (Monad, MonadState State)

И я хочу использовать постоянные вызовы insert и lookup, поэтому мне нужно сделать экземпляр PersistBackend для T.Тем не менее, фантомный тип кодирует конкретный бэкэнд в тип возврата Key - это вызывает некоторые дополнительные головные боли.Чтобы решить проблему с фантомным типом, мой экземпляр имеет форму:

instance (Monad m, MonadIO m, MonadBaseControl IO m) => PersistBackend T m where
   insert = T . lift . liftM (Key . unKey) . insert
   ... and about a dozen such methods ...

Я слепо пропускаю более простой способ?Способ, отличный от вызова функции путем ручного подъема: insertT = T . lift . insert

1 Ответ

1 голос
/ 25 января 2012

У меня есть две разные рекомендации:

  1. Переверните вещи и поместите SqlPersist вокруг вашего StateT вместо наоборот.
  2. Создайте модуль с поднятыми версиями функцийаналогично тому, что делает MonadState.

Я бы пошел на (1).Если многие люди сталкиваются с этим, я полагаю, у нас мог бы быть специализированный пакет, предоставляющий поднятые версии всех функций.

...