predicate-transformers 0.6.0.0 → 0.7.0.0
raw patch · 2 files changed
+25/−17 lines, 2 filesdep +deepseqdep ~basedep ~mtlPVP ok
version bump matches the API change (PVP)
Dependencies added: deepseq
Dependency ranges changed: base, mtl
API changes (from Hackage documentation)
- PredicateTransformers: traceFailure :: Show a => PT a a
+ PredicateTransformers: forced :: NFData a => a -> Bool
+ PredicateTransformers: traceFail :: (a -> String) -> PT a a
+ PredicateTransformers: traceFailShow :: Show a => PT a a
Files
- predicate-transformers.cabal +2/−1
- src/PredicateTransformers.hs +23/−16
predicate-transformers.cabal view
@@ -1,7 +1,7 @@ cabal-version: 2.4 name: predicate-transformers-version: 0.6.0.0+version: 0.7.0.0 synopsis: A library for writing predicates and transformations over predicates in Haskell description: This package provides ways to write predicates such that they compose nicely and are easy to debug.@@ -25,5 +25,6 @@ ,lens ^>=4.17 || ^>=4.18 ,adjunctions ^>=4.2 || ^>=4.3 || ^>=4.4 ,mtl ^>= 2.2.2+ ,deepseq ^>= 1.4.4.0 hs-source-dirs: src default-language: Haskell2010
src/PredicateTransformers.hs view
@@ -1,4 +1,5 @@ {-# language ViewPatterns #-}+{-# language LambdaCase #-} -- | This library is based on the notion of a predicate transformer, the below -- type @PT a b@, which is a function from @a@ to predicates on @b@.@@ -13,12 +14,15 @@ module PredicateTransformers where +import Control.DeepSeq(NFData, force)+import Control.Exception(SomeException, evaluate, throwIO, try) import Control.Lens hiding (index, zoom) import Control.Monad.Writer(execWriter, tell) import Data.Foldable(toList) import Data.Functor.Rep(Representable(..)) import Data.Semigroup(All(..), Any(..)) import Debug.Trace+import System.IO.Unsafe -- |A convenient alias for predicates. type Pred a = a -> Bool@@ -32,27 +36,22 @@ -- |Operate on the target of a prism, or fail. match :: APrism s t a b -> PT a s match p pred = either (const False) pred . matching p-{-# inlinable match #-} -- |Invert a predicate. nay :: PT a a nay = (not .)-{-# inlinable nay #-} -- |Operate on the `Just` branch of a `Maybe`, or fail. just :: PT a (Maybe a) just = match _Just-{-# inlinable just #-} -- |Operate on the `Left` branch of an `Either`, or fail. left :: PT e (Either e a) left = match _Left-{-# inlinable left #-} -- |Operate on the `Right` branch of an `Either`, or fail. right :: PT a (Either e a) right = match _Right-{-# inlinable right #-} -- |Operate on the last value in a foldable, or fail if it's not present. endingWith :: Foldable f => PT a (f a)@@ -83,7 +82,6 @@ list (p:ps) (x:xs) = p x && dist ps xs list [] [] = True list _ _ = False-{-# inlinable list #-} -- |Given a functor-full of predicates, and a functor-full of values, ensure that the structures -- of the two functors match and apply all of the predicates to all of the values.@@ -106,40 +104,49 @@ -- |Test all predicates against one value. allTrue :: [Pred a] -> Pred a allTrue ps a = all ($ a) ps-{-# inlinable allTrue #-} -- |Check that a predicate is true for all values behind a generalized getter -- and that there's at least one value for which it's true. allOf1 :: Getting (All, Any) s a -> PT a s allOf1 g p (foldMapOf g (\x -> (All $ p x, Any $ p x)) -> (All a, Any y)) = a && y-{-# inlinable allOf1 #-} -- |Sugar for tupling. (==>) :: a -> b -> (a, b) (==>) = (,)-{-# inline conlike (==>) #-} pair :: Pred a -> Pred b -> Pred (a,b) pair f s (a,b) = f a && s b-{-# inline conlike pair #-} -- |Flipped function composition; @f !@ for a function @f@ is a predicate transformer. (!) :: (b -> a) -> (a -> c) -> b -> c (!) = flip (.)-{-# inline conlike (!) #-} -- |Prints the input of a predicate, for debugging. traced :: Show a => (a -> c) -> a -> c traced p a = traceShow a (p a)-{-# inline traced #-} -- |Prints the input of a predicate, if the predicate fails.-traceFailure :: Show a => PT a a-traceFailure p a = if p a then True else traceShow a False-{-# inline traceFailure #-}+traceFail :: (a -> String) -> PT a a+traceFail s p a = unsafePerformIO $ do+ try (evaluate (p a)) >>= \case+ Left ex -> do+ traceIO (s a)+ throwIO (ex :: SomeException)+ Right True ->+ pure True+ Right False -> do+ traceIO ("\n" <> s a)+ pure False +traceFailShow :: Show a => PT a a+traceFailShow = traceFail show+ -- |Predicate which always succeeds. something :: Pred a something = const True-{-# inline something #-}++-- |Predicate which triggers full evaluation of its input.+-- Useful for testing that an exception isn't thrown.+forced :: NFData a => a -> Bool+forced a = force a `seq` True