packages feed

bluefin-internal 0.0.1.0 → 0.0.2.0

raw patch · 3 files changed

+149/−4 lines, 3 filesPVP ok

version bump matches the API change (PVP)

API changes (from Hackage documentation)

+ Bluefin.Internal: StateSource :: StateSource (st :: Effects)
+ Bluefin.Internal: data StateSource (st :: Effects)
+ Bluefin.Internal: newState :: StateSource e -> s -> Eff es (State s e)
+ Bluefin.Internal: withStateSource :: (forall e. StateSource e -> Eff (e :& es) a) -> Eff es a
+ Bluefin.Internal.Examples: countExampleI :: IO ()
+ Bluefin.Internal.Examples: evalStateI :: s -> (forall st. (?st :: State s st) => Eff (st :& es) a) -> Eff es a
+ Bluefin.Internal.Examples: getI :: forall st s es. st :> es => (?st :: State s st) => Eff es s
+ Bluefin.Internal.Examples: modifyI :: forall st s es. st :> es => (?st :: State s st) => (s -> s) -> Eff es ()
+ Bluefin.Internal.Examples: stateSourceExample :: Int
+ Bluefin.Internal.Examples: throwI :: e1 :> es => (?ex :: Exception e e1) => e -> Eff es a
+ Bluefin.Internal.Examples: while :: Eff es Bool -> Eff es a -> Eff es ()

Files

bluefin-internal.cabal view
@@ -1,6 +1,6 @@ cabal-version:      3.0 name:               bluefin-internal-version:            0.0.1.0+version:            0.0.2.0 license:            MIT license-file:       LICENSE author:             Tom Ellis@@ -9,6 +9,8 @@ extra-doc-files:    CHANGELOG.md description:        The Bluefin effect system, internals synopsis:           The Bluefin effect system, internals+homepage:           https://github.com/tomjaguarpaw/bluefin+bug-reports:        https://github.com/tomjaguarpaw/bluefin/issues  common defaults     ghc-options: -Wall
src/Bluefin/Internal.hs view
@@ -161,6 +161,9 @@ pushFirst :: Eff a r -> Eff (a :& b) r pushFirst = weakenEff (fstI (# #)) +-- | Handle to a capability to create strict mutable state handles+data StateSource (st :: Effects) = StateSource+ -- | Handle to an exception of type @e@ newtype Exception e (ex :: Effects) = Exception (forall a. e -> IO a) @@ -372,6 +375,50 @@  -- | -- @+-- runPureEff $ withStateSource $ \\source -> do+--   n <- newState source 5+--   total <- newState source 0+--+--   'Bluefin.Jump.withJump' $ \\done -> forever $ do+--     n' <- 'Bluefin.State.get' n+--     'Bluefin.State.modify' total (+ n')+--     when (n' == 0) $ 'Bluefin.Jump.jumpTo' done+--     modify n (subtract 1)+--+--   get total+-- 15+-- @+withStateSource ::+  (forall e. StateSource e -> Eff (e :& es) a) ->+  -- | ͘+  Eff es a+withStateSource f = unsafeRemoveEff (f StateSource)++-- |+-- @+-- runPureEff $ withStateSource $ \\source -> do+--   n <- newState source 5+--   total <- newState source 0+--+--   'Bluefin.Jump.withJump' $ \\done -> forever $ do+--     n' <- 'Bluefin.State.get' n+--     'Bluefin.State.modify' total (+ n')+--     when (n' == 0) $ 'Bluefin.Jump.jumpTo' done+--     modify n (subtract 1)+--+--   get total+-- 15+-- @+newState ::+  StateSource e ->+  -- | The initial value for the state handle+  s ->+  -- | A new state handle+  Eff es (State s e)+newState StateSource s = UnsafeMkEff (fmap UnsafeMkState (newIORef s))++-- |+-- @ -- >>> runPureEff $ runState 10 $ \\st -> do --       n <- get st --       pure (2 * n)@@ -385,8 +432,8 @@   -- | Result and final state   Eff es (a, s) runState s f = do-  state <- UnsafeMkEff (fmap UnsafeMkState (newIORef s))-  unsafeRemoveEff $ do+  withStateSource $ \source -> do+    state <- newState source s     a <- f state     s' <- get state     pure (a, s')
src/Bluefin/Internal/Examples.hs view
@@ -1,10 +1,11 @@ {-# LANGUAGE NoMonoLocalBinds #-} {-# LANGUAGE NoMonomorphismRestriction #-}+{-# LANGUAGE ImplicitParams #-}  module Bluefin.Internal.Examples where  import Bluefin.Internal hiding (w)-import Control.Monad (forever, when)+import Control.Monad (forever, unless, when) import Control.Monad.IO.Class (liftIO) import Data.Foldable (for_) import Data.Monoid (Any (Any, getAny))@@ -187,6 +188,32 @@   myInc h   myBail h +throwI ::+  (e1 :> es) =>+  (?ex :: Exception e e1) =>+  -- | Value to throw+  e ->+  Eff es a+throwI = throw ?ex++modifyI ::+  forall st s es.+  (st :> es) =>+  (?st  :: State s st) =>+  -- | Apply this function to the state.  The new value of the state+  -- is forced before writing it to the state.+  (s -> s) ->+  Eff es ()+modifyI = modify ?st++getI ::+  forall st s es.+  (st :> es) =>+  (?st :: State s st) =>+  -- | The current value of the state+  Eff es s+getI = get ?st+ countExample :: IO () countExample = runEff $ \io -> do   evalState @Int 0 $ \sn -> do@@ -203,3 +230,72 @@ writerExample2 :: Bool writerExample2 = getAny $ runPureEff $ execWriter $ \w -> do   for_ [1 .. 10] $ \_ -> tell w (Any True)++while :: Eff es Bool -> Eff es a -> Eff es ()+while condM body =+  withJump $ \break_ -> do+    forever $ do+      cond <- insertFirst condM+      unless cond (jumpTo break_)+      insertFirst body++stateSourceExample :: Int+stateSourceExample = runPureEff $ withStateSource $ \source -> do+  n <- newState source 5+  total <- newState source 0++  withJump $ \done -> forever $ do+    n' <- get n+    modify total (+ n')+    when (n' == 0) $ jumpTo done+    modify n (subtract 1)++  get total++-- welltypedwitch raised the intriguing possibility of using+-- ImplicitParams to avoid having to pass effect handles explicitly.+-- Unfortunately I've been snagged on two issues:+--+-- 1. It doesn't seem possible to bind an implicit parameter in a+--    lambda.  (See+--    https://discourse.haskell.org/t/why-cant-an-implicitparam-be-bound-by-a-lambda/8936/2)+--+-- 2. Type inference gets stuck. I don't understand why.+countExampleI :: IO ()+countExampleI = runEff $ ((\io -> do+  evalState @Int 0 $ ((\st -> do+    let ?st = st+    withJump $ \break -> forever $ do+      n <- getI @st+      when (n >= 10) (jumpTo break)+      effIO io (print n)+      modifyI @st (+ 1))+      :: forall st. State Int st -> Eff (st :& e :& es) ()))+  :: forall e es. IOE e -> Eff (e :& es) ())++-- We might want to resolve 1 by putting the ImplicitParam as an+-- argument to the handler, but I can't work out how to get that to+-- type check at all+evalStateI ::+  -- | Initial state+  s ->+  -- | Stateful computation+  (forall st. (?st :: State s st) => Eff (st :& es) a) ->+  -- | Result+  Eff es a+evalStateI s f = evalState s (\x -> let ?st = x in f)++-- This just doesn't work.  Have a made a silly mistake?++{-+countExampleI2 :: IO ()+countExampleI2 = runEff $ ((\io -> do+  evalStateI @Int 0 $ (do+    withJump $ \break -> forever $ do+      n <- getI @st+      when (n >= 10) (jumpTo break)+      effIO io (print n)+      modifyI @st (+ 1))+      :: forall st. (?st :: State Int st) => Eff (st :& e :& effes) ())+  :: forall e effes. IOE e -> Eff (e :& effes) ())+-}