@@ -4,7 +4,7 @@ module FRP.Rhine.Clock.Except where
4
4
5
5
import Control.Exception
6
6
import Control.Exception qualified as Exception
7
- import Control.Monad ((<=<) )
7
+ import Control.Monad ((<=<) , (>=>) )
8
8
import Control.Monad.Error.Class
9
9
import Control.Monad.IO.Class (MonadIO ,liftIO )
10
10
import Control.Monad.Trans.Class (lift )
@@ -33,29 +33,25 @@ instance (Exception e, Clock IO cl, MonadIO eio, MonadError e eio) => Clock eio
33
33
34
34
instance GetClockProxy (ExceptClock cl e )
35
35
36
- data CatchClock cl e cl' e' = CatchClock cl (e -> Either e' cl' )
36
+ data CatchClock cl e cl' = CatchClock cl (e -> cl' )
37
37
38
- instance (Time cl ~ Time cl' ,Clock (ExceptT e m )cl ,Clock ( ExceptT e' m ) cl' ,Monad m )=> Clock ( ExceptT e' m ) (CatchClock cl e cl' e ' )where
39
- type Time (CatchClock cl e cl' e' )= Time cl
40
- type Tag (CatchClock cl e cl' e' )= Either (Tag cl ) (Tag cl' )
38
+ instance (Time cl ~ Time cl' ,Clock (ExceptT e m )cl ,Clock m cl' ,Monad m )=> Clock m (CatchClock cl e cl' )where
39
+ type Time (CatchClock cl e cl' )= Time cl
40
+ type Tag (CatchClock cl e cl' )= Either (Tag cl ) (Tag cl' )
41
41
initClock (CatchClock cl handler)= do
42
- tryToInit<- lift $ runExceptT$ first (>>> arr (secondLeft ))<$> initClock cl
42
+ tryToInit<- runExceptT$ first (>>> arr (secondLeft ))<$> initClock cl
43
43
-- FIXME Each of these branches needs a unit test
44
44
case tryToInitof
45
45
Right (runningClock, initTime)-> do
46
- let catchingClock= runMSFExcept $ do
46
+ let catchingClock= safely $ do
47
47
e<- MSFExcept. try runningClock
48
- case handler eof
49
- Right cl'-> do
50
- tryToInit'<- once_$ runExceptT$ initClock cl'
51
- case tryToInit'of
52
- Right (runningClock', _)-> MSFExcept. try$ runningClock'>>> arr (secondRight )
53
- Left e'-> return e'
54
- Left e'-> return e'
48
+ let cl'= handler e
49
+ (runningClock', _)<- once_$ initClock cl'
50
+ safe$ runningClock'>>> arr (secondRight )
55
51
return (catchingClock, initTime)
56
- Left e-> either throwE (fmap (first (>>> arr (secondRight ))). initClock)$ handler e
52
+ Left e-> (fmap (first (>>> arr (secondRight ))). initClock)$ handler e
57
53
58
- instance (GetClockProxy (CatchClock cl e cl' e' ))
54
+ instance (GetClockProxy (CatchClock cl e cl' ))
59
55
60
56
type SafeClock m = HoistClock (ExceptT Void m )m
61
57
@@ -66,39 +62,49 @@ safeClock unhoistedClock =
66
62
, monadMorphism= fmap (either absurdid ). runExceptT
67
63
}
68
64
69
- type CatchSafe cl e cl' m = SafeClock m (CatchClock cl e (LiftClock m (ExceptT Void )cl' )Void )
70
-
71
- catchSafe :: (Monad m )=> cl -> (e -> cl' )-> CatchSafe cl e cl' m
72
- catchSafe cl handler= safeClock$ CatchClock cl$ Right . liftClock. handler
73
-
74
65
data Single m time tag e = Single
75
66
{ singleTag :: tag
76
67
,getTime :: m time
77
68
,exception :: e
78
69
}
79
70
80
- instance (TimeDomain time ,Monad m )=> Clock ( ExceptT e m ) (Single m time tag e )where
71
+ instance (TimeDomain time ,MonadError e m )=> Clock m (Single m time tag e )where
81
72
type Time (Single m time tag e )= time
82
73
type Tag (Single m time tag e )= tag
83
74
initClockSingle {singleTag, getTime, exception}= do
84
- initTime<- lift getTime
85
- let runningClock= runMSFExcept$ do
75
+ initTime<- getTime
76
+ let runningClock= morphS (errorT . runExceptT) $ runMSFExcept$ do
86
77
step_ (initTime, singleTag)
87
78
return exception
79
+ errorT :: (MonadError e m )=> m (Either e a )-> m a
80
+ errorT= (>>= liftEither)
88
81
return (runningClock, initTime)
89
82
90
- type DelayException m time cl e e' = CatchClock cl e (Single m time e e' )e'
83
+ type DelayException m time cl e e' = CatchClock cl e (Single m time e e' )
91
84
92
- delayException :: (Clock (ExceptT e m )cl )=> cl -> (e -> e' )-> m (Time cl )-> DelayException m (Time cl )cl e e'
93
- delayException cl handler mTime= CatchClock cl$ Right . ( \ e-> Single e mTime$ handler e)
85
+ delayException :: (Monad m , Clock (ExceptT e m )cl , MonadError e' m )=> cl -> (e -> e' )-> m (Time cl )-> DelayException m (Time cl )cl e e'
86
+ delayException cl handler mTime= CatchClock cl$ \ e-> Single e mTime$ handler e
94
87
95
- delayException' :: (Clock (ExceptT e m )cl )=> cl -> m (Time cl )-> DelayException m (Time cl )cl e e
88
+ delayException' :: (Monad m , MonadError e m , Clock (ExceptT e m )cl )=> cl -> m (Time cl )-> DelayException m (Time cl )cl e e
96
89
delayException' cl= delayException clid
97
90
98
- type DelayIOException cl e e' = DelayException IO UTCTime (ExceptClock cl e )e e'
91
+ type DelayMonadIOException m cl e e' = DelayException m UTCTime (ExceptClock cl e )e e'
92
+
93
+ delayMonadIOException :: (Exception e ,MonadIO m ,MonadError e' m ,Clock IO cl ,Time cl ~ UTCTime )=> cl -> (e -> e' )-> DelayMonadIOException m cl e e'
94
+ delayMonadIOException cl handler= delayException (ExceptClock cl) handler$ liftIO getCurrentTime
95
+
96
+ type DelayMonadIOError m cl e = DelayMonadIOException m cl IOError e
97
+
98
+ delayMonadIOError :: (Exception e ,MonadError e m ,MonadIO m ,Clock IO cl ,Time cl ~ UTCTime )=> cl -> (IOError -> e )-> DelayMonadIOError m cl e
99
+ delayMonadIOError= delayMonadIOException
100
+
101
+ delayMonadIOError' :: (MonadError IOError m ,MonadIO m ,Clock IO cl ,Time cl ~ UTCTime )=> cl -> DelayMonadIOError m cl IOError
102
+ delayMonadIOError' cl= delayMonadIOError clid
103
+
104
+ type DelayIOException cl e e' = DelayException (ExceptT e' IO )UTCTime (ExceptClock cl e )e e'
99
105
100
106
delayIOException :: (Exception e ,Clock IO cl ,Time cl ~ UTCTime )=> cl -> (e -> e' )-> DelayIOException cl e e'
101
- delayIOException cl handler= delayException (ExceptClock cl) handler getCurrentTime
107
+ delayIOException cl handler= delayException (ExceptClock cl) handler$ liftIO getCurrentTime
102
108
103
109
delayIOException' :: (Exception e ,Clock IO cl ,Time cl ~ UTCTime )=> cl -> DelayIOException cl e e
104
110
delayIOException' cl= delayIOException clid