Let me start from the task I want solve, probably I’m going wrong way. I use Snap framework for toy project, and the main is that it’s functions under Snap monad. I need to add my state above it. I use monad transformer:
type SnapApp a = StateT AppState Snap a
This defined in the module, say, Base. Since I need it in other modules, I have to export it:
module Base
( ..
, SnapApp
) where
This is good, but I want that module doesn’t exported that SnapApp is state monad, because I have some complicated processing for setting some attributes for the state. For example, session. I have to write file when it is changed, so it wrong to just get and than put modified session, special function should be called. So, I hide that using newtype and not data exporting construstor:
newtype SnapApp a = SnapApp (StateT AppState Snap a)
I made it instance of my class with functions for modifying session and etc. But problem arises: I lost instances of Monad class and other for new SnapApp. And I’m stuck with implementing >>=:
instance Monad SnapApp where
return = SnapApp . return
mx >>= fm = -- HOW?
Thank you!
Let the types guide you.
You need
You have
You need to convert:
SnapApp atoStateT AppState Snap aa -> SnapApp btoa -> StateT AppState Snap bStateT AppState Snap btoSnapApp b1) use pattern matching; define:
2) Compose the functions
a -> SnapApp bandSnapApp b -> StateT AppState b3) Use
SnapAppFinal result:
or:
You don’t have to write this; GHC can derive the instance if you enable the
GeneralizedNewtypeDerivingextension: