{-# LANGUAGE MultiParamTypeClasses #-}
{-# LANGUAGE KindSignatures #-}
{-# LANGUAGE TypeApplications #-}
{-# LANGUAGE ScopedTypeVariables #-}
{-# LANGUAGE AllowAmbiguousTypes #-}

-- | Applicative properties
--
-- You will need @TypeApplications@ to use these.
module Test.Syd.Validity.Applicative
    ( applicativeSpecOnValid
    , applicativeSpec
    , applicativeSpecOnArbitrary
    , applicativeSpecOnGens
    ) where

import Data.Data

import Data.GenValidity
import Data.Kind

import Test.Syd
import Test.QuickCheck

import Test.Syd.Validity.Functions
import Test.Syd.Validity.Utils

{-# ANN module "HLint: ignore Avoid lambda" #-}

pureTypeStr ::
       forall (f :: Type -> Type). (Typeable f)
    => String
pureTypeStr :: String
pureTypeStr = [String] -> String
unwords [String
"pure", String
"::", String
"a", String
"->", Typeable f => String
forall k (a :: k). Typeable a => String
nameOf @f, String
"a"]

seqTypeStr ::
       forall (f :: Type -> Type). (Typeable f)
    => String
seqTypeStr :: String
seqTypeStr =
    [String] -> String
unwords
        [ String
"(<*>)"
        , String
"::"
        , Typeable f => String
forall k (a :: k). Typeable a => String
nameOf @f
        , String
"(a"
        , String
"->"
        , String
"b)"
        , String
"->"
        , Typeable f => String
forall k (a :: k). Typeable a => String
nameOf @f
        , String
"a"
        , String
"->"
        , Typeable f => String
forall k (a :: k). Typeable a => String
nameOf @f
        , String
"b"
        ]

seqrTypeStr ::
       forall (f :: Type -> Type). (Typeable f)
    => String
seqrTypeStr :: String
seqrTypeStr =
    [String] -> String
unwords
        [ String
"(*>)"
        , String
"::"
        , Typeable f => String
forall k (a :: k). Typeable a => String
nameOf @f
        , String
"a"
        , String
"->"
        , Typeable f => String
forall k (a :: k). Typeable a => String
nameOf @f
        , String
"b"
        , String
"->"
        , Typeable f => String
forall k (a :: k). Typeable a => String
nameOf @f
        , String
"b"
        ]

seqlTypeStr ::
       forall (f :: Type -> Type). (Typeable f)
    => String
seqlTypeStr :: String
seqlTypeStr =
    [String] -> String
unwords
        [ String
"(<*)"
        , String
"::"
        , Typeable f => String
forall k (a :: k). Typeable a => String
nameOf @f
        , String
"a"
        , String
"->"
        , Typeable f => String
forall k (a :: k). Typeable a => String
nameOf @f
        , String
"b"
        , String
"->"
        , Typeable f => String
forall k (a :: k). Typeable a => String
nameOf @f
        , String
"a"
        ]

-- | Standard test spec for properties of Applicative instances for values generated with GenValid instances
--
-- Example usage:
--
-- > applicativeSpecOnArbitrary @[]
applicativeSpecOnValid ::
       forall (f :: Type -> Type).
       (Eq (f Int), Show (f Int), Applicative f, Typeable f, GenValid (f Int))
    => Spec
applicativeSpecOnValid :: Spec
applicativeSpecOnValid = Gen (f Int) -> Spec
forall (f :: * -> *).
(Show (f Int), Eq (f Int), Applicative f, Typeable f) =>
Gen (f Int) -> Spec
applicativeSpecWithInts @f Gen (f Int)
forall a. GenValid a => Gen a
genValid

-- | Standard test spec for properties of Applicative instances for values generated with GenUnchecked instances
--
-- Example usage:
--
-- > applicativeSpecOnArbitrary @[]
applicativeSpec ::
       forall (f :: Type -> Type).
       ( Eq (f Int)
       , Show (f Int)
       , Applicative f
       , Typeable f
       , GenUnchecked (f Int)
       )
    => Spec
applicativeSpec :: Spec
applicativeSpec = Gen (f Int) -> Spec
forall (f :: * -> *).
(Show (f Int), Eq (f Int), Applicative f, Typeable f) =>
Gen (f Int) -> Spec
applicativeSpecWithInts @f Gen (f Int)
forall a. GenUnchecked a => Gen a
genUnchecked

-- | Standard test spec for properties of Applicative instances for values generated with Arbitrary instances
--
-- Example usage:
--
-- > applicativeSpecOnArbitrary @[]
applicativeSpecOnArbitrary ::
       forall (f :: Type -> Type).
       (Eq (f Int), Show (f Int), Applicative f, Typeable f, Arbitrary (f Int))
    => Spec
applicativeSpecOnArbitrary :: Spec
applicativeSpecOnArbitrary = Gen (f Int) -> Spec
forall (f :: * -> *).
(Show (f Int), Eq (f Int), Applicative f, Typeable f) =>
Gen (f Int) -> Spec
applicativeSpecWithInts @f Gen (f Int)
forall a. Arbitrary a => Gen a
arbitrary

applicativeSpecWithInts ::
       forall (f :: Type -> Type).
       (Show (f Int), Eq (f Int), Applicative f, Typeable f)
    => Gen (f Int)
    -> Spec
applicativeSpecWithInts :: Gen (f Int) -> Spec
applicativeSpecWithInts Gen (f Int)
gen =
    Gen Int
-> String
-> Gen (f Int)
-> String
-> Gen (f Int)
-> String
-> Gen (Int -> Int)
-> String
-> Gen (f (Int -> Int))
-> String
-> Gen (f (Int -> Int))
-> String
-> Spec
forall (f :: * -> *) a b c.
(Show a, Show (f a), Eq (f a), Show (f b), Eq (f b), Show (f c),
 Eq (f c), Applicative f, Typeable f, Typeable a, Typeable b,
 Typeable c) =>
Gen a
-> String
-> Gen (f a)
-> String
-> Gen (f b)
-> String
-> Gen (a -> b)
-> String
-> Gen (f (a -> b))
-> String
-> Gen (f (b -> c))
-> String
-> Spec
applicativeSpecOnGens
        @f
        @Int
        Gen Int
forall a. GenUnchecked a => Gen a
genUnchecked
        String
"int"
        Gen (f Int)
gen
        ([String] -> String
unwords [Typeable f => String
forall k (a :: k). Typeable a => String
nameOf @f, String
"of ints"])
        Gen (f Int)
gen
        ([String] -> String
unwords [Typeable f => String
forall k (a :: k). Typeable a => String
nameOf @f, String
"of ints"])
        (Int -> Int -> Int
forall a. Num a => a -> a -> a
(+) (Int -> Int -> Int) -> Gen Int -> Gen (Int -> Int)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Gen Int
forall a. GenUnchecked a => Gen a
genUnchecked)
        String
"increments"
        ((Int -> Int) -> f (Int -> Int)
forall (f :: * -> *) a. Applicative f => a -> f a
pure ((Int -> Int) -> f (Int -> Int))
-> Gen (Int -> Int) -> Gen (f (Int -> Int))
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (Int -> Int -> Int
forall a. Num a => a -> a -> a
(+) (Int -> Int -> Int) -> Gen Int -> Gen (Int -> Int)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Gen Int
forall a. GenUnchecked a => Gen a
genUnchecked))
        ([String] -> String
unwords [Typeable f => String
forall k (a :: k). Typeable a => String
nameOf @f, String
"of increments"])
        ((Int -> Int) -> f (Int -> Int)
forall (f :: * -> *) a. Applicative f => a -> f a
pure ((Int -> Int) -> f (Int -> Int))
-> Gen (Int -> Int) -> Gen (f (Int -> Int))
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (Int -> Int -> Int
forall a. Num a => a -> a -> a
(*) (Int -> Int -> Int) -> Gen Int -> Gen (Int -> Int)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Gen Int
forall a. GenUnchecked a => Gen a
genUnchecked))
        ([String] -> String
unwords [Typeable f => String
forall k (a :: k). Typeable a => String
nameOf @f, String
"of scalings"])

-- | Standard test spec for properties of Applicative instances for values generated by given generators (and names for those generator).
--
-- Unless you are building a specific regression test, you probably want to use the other 'applicativeSpec' functions.
--
-- Example usage:
--
-- > applicativeSpecOnGens
-- >     @Maybe
-- >     @String
-- >     (pure "ABC")
-- >     "ABC"
-- >     (Just <$> pure "ABC")
-- >     "Just an ABC"
-- >     (pure Nothing)
-- >     "purely Nothing"
-- >     ((++) <$> genValid)
-- >     "prepends"
-- >     (pure <$> ((++) <$> genValid))
-- >     "prepends in a Just"
-- >     (pure <$> (flip (++) <$> genValid))
-- >     "appends in a Just"
applicativeSpecOnGens ::
       forall (f :: Type -> Type) (a :: Type) (b :: Type) (c :: Type).
       ( Show a
       , Show (f a)
       , Eq (f a)
       , Show (f b)
       , Eq (f b)
       , Show (f c)
       , Eq (f c)
       , Applicative f
       , Typeable f
       , Typeable a
       , Typeable b
       , Typeable c
       )
    => Gen a
    -> String
    -> Gen (f a)
    -> String
    -> Gen (f b)
    -> String
    -> Gen (a -> b)
    -> String
    -> Gen (f (a -> b))
    -> String
    -> Gen (f (b -> c))
    -> String
    -> Spec
applicativeSpecOnGens :: Gen a
-> String
-> Gen (f a)
-> String
-> Gen (f b)
-> String
-> Gen (a -> b)
-> String
-> Gen (f (a -> b))
-> String
-> Gen (f (b -> c))
-> String
-> Spec
applicativeSpecOnGens Gen a
gena String
genaname Gen (f a)
gen String
genname Gen (f b)
genb String
genbname Gen (a -> b)
genfa String
genfaname Gen (f (a -> b))
genffa String
genffaname Gen (f (b -> c))
genffb String
genffbname =
    Spec -> Spec
forall (a :: [*]) b c. TestDefM a b c -> TestDefM a b c
parallel (Spec -> Spec) -> Spec -> Spec
forall a b. (a -> b) -> a -> b
$
    String -> Spec -> Spec
forall (outers :: [*]) inner.
String -> TestDefM outers inner () -> TestDefM outers inner ()
describe (String
"Applicative " String -> String -> String
forall a. [a] -> [a] -> [a]
++ Typeable f => String
forall k (a :: k). Typeable a => String
nameOf @f) (Spec -> Spec) -> Spec -> Spec
forall a b. (a -> b) -> a -> b
$ do
        String -> Spec -> Spec
forall (outers :: [*]) inner.
String -> TestDefM outers inner () -> TestDefM outers inner ()
describe ([String] -> String
unwords [Typeable f => String
forall (f :: * -> *). Typeable f => String
pureTypeStr @f, String
"and", Typeable f => String
forall (f :: * -> *). Typeable f => String
seqTypeStr @f]) (Spec -> Spec) -> Spec -> Spec
forall a b. (a -> b) -> a -> b
$ do
            String -> Property -> Spec
forall (outers :: [*]) inner test.
(HasCallStack, IsTest test, Arg1 test ~ (), Arg2 test ~ inner) =>
String -> test -> TestDefM outers inner ()
it
                ([String] -> String
unwords
                     [ String
"satisfy the identity law: 'pure id <*> v = v' for"
                     , String -> String
forall k (a :: k). Typeable a => String -> String
genDescr @(f a) String
genname
                     ]) (Property -> Spec) -> Property -> Spec
forall a b. (a -> b) -> a -> b
$
                (f a -> f a)
-> (f a -> f a) -> Gen (f a) -> (f a -> [f a]) -> Property
forall a b.
(Show a, Show b, Eq b) =>
(a -> b) -> (a -> b) -> Gen a -> (a -> [a]) -> Property
equivalentOnGen ((a -> a) -> f (a -> a)
forall (f :: * -> *) a. Applicative f => a -> f a
pure a -> a
forall a. a -> a
id f (a -> a) -> f a -> f a
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*>) f a -> f a
forall a. a -> a
id Gen (f a)
gen f a -> [f a]
forall a. a -> [a]
shrinkNothing
            String -> Property -> Spec
forall (outers :: [*]) inner test.
(HasCallStack, IsTest test, Arg1 test ~ (), Arg2 test ~ inner) =>
String -> test -> TestDefM outers inner ()
it
                ([String] -> String
unwords
                     [ String
"satisfy the composition law: 'pure (.) <*> u <*> v <*> w = u <*> (v <*> w)' for"
                     , String -> String
forall k (a :: k). Typeable a => String -> String
genDescr @(f (b -> c)) String
genffbname
                     , String
"composed with"
                     , String -> String
forall k (a :: k). Typeable a => String -> String
genDescr @(f (a -> b)) String
genffaname
                     , String
"and applied to"
                     , String -> String
forall k (a :: k). Typeable a => String -> String
genDescr @(f a) String
genname
                     ]) (Property -> Spec) -> Property -> Spec
forall a b. (a -> b) -> a -> b
$
                (Anon (f (b -> c)) -> Anon (f (a -> b)) -> f a -> f c)
-> (Anon (f (b -> c)) -> Anon (f (a -> b)) -> f a -> f c)
-> Gen (Anon (f (b -> c)), Anon (f (a -> b)), f a)
-> ((Anon (f (b -> c)), Anon (f (a -> b)), f a)
    -> [(Anon (f (b -> c)), Anon (f (a -> b)), f a)])
-> Property
forall a b c d.
(Show a, Show b, Show c, Show d, Eq d) =>
(a -> b -> c -> d)
-> (a -> b -> c -> d)
-> Gen (a, b, c)
-> ((a, b, c) -> [(a, b, c)])
-> Property
equivalentOnGens3
                    (\(Anon f (b -> c)
u) (Anon f (a -> b)
v) f a
w ->
                         ((b -> c) -> (a -> b) -> a -> c)
-> f ((b -> c) -> (a -> b) -> a -> c)
forall (f :: * -> *) a. Applicative f => a -> f a
pure (b -> c) -> (a -> b) -> a -> c
forall b c a. (b -> c) -> (a -> b) -> a -> c
(.) f ((b -> c) -> (a -> b) -> a -> c)
-> f (b -> c) -> f ((a -> b) -> a -> c)
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> (f (b -> c)
u :: f (b -> c)) f ((a -> b) -> a -> c) -> f (a -> b) -> f (a -> c)
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> (f (a -> b)
v :: f (a -> b)) f (a -> c) -> f a -> f c
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*>
                         (f a
w :: f a) :: f c)
                    (\(Anon f (b -> c)
u) (Anon f (a -> b)
v) f a
w -> f (b -> c)
u f (b -> c) -> f b -> f c
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> (f (a -> b)
v f (a -> b) -> f a -> f b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> f a
w) :: f c)
                    ((,,) (Anon (f (b -> c))
 -> Anon (f (a -> b))
 -> f a
 -> (Anon (f (b -> c)), Anon (f (a -> b)), f a))
-> Gen (Anon (f (b -> c)))
-> Gen
     (Anon (f (a -> b))
      -> f a -> (Anon (f (b -> c)), Anon (f (a -> b)), f a))
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (f (b -> c) -> Anon (f (b -> c))
forall a. a -> Anon a
Anon (f (b -> c) -> Anon (f (b -> c)))
-> Gen (f (b -> c)) -> Gen (Anon (f (b -> c)))
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Gen (f (b -> c))
genffb) Gen
  (Anon (f (a -> b))
   -> f a -> (Anon (f (b -> c)), Anon (f (a -> b)), f a))
-> Gen (Anon (f (a -> b)))
-> Gen (f a -> (Anon (f (b -> c)), Anon (f (a -> b)), f a))
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> (f (a -> b) -> Anon (f (a -> b))
forall a. a -> Anon a
Anon (f (a -> b) -> Anon (f (a -> b)))
-> Gen (f (a -> b)) -> Gen (Anon (f (a -> b)))
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Gen (f (a -> b))
genffa) Gen (f a -> (Anon (f (b -> c)), Anon (f (a -> b)), f a))
-> Gen (f a) -> Gen (Anon (f (b -> c)), Anon (f (a -> b)), f a)
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Gen (f a)
gen)
                    (Anon (f (b -> c)), Anon (f (a -> b)), f a)
-> [(Anon (f (b -> c)), Anon (f (a -> b)), f a)]
forall a. a -> [a]
shrinkNothing
            String -> Property -> Spec
forall (outers :: [*]) inner test.
(HasCallStack, IsTest test, Arg1 test ~ (), Arg2 test ~ inner) =>
String -> test -> TestDefM outers inner ()
it
                ([String] -> String
unwords
                     [ String
"satisfy the homomorphism law: 'pure f <*> pure x = pure (f x)' for"
                     , String -> String
forall k (a :: k). Typeable a => String -> String
genDescr @(a -> b) String
genfaname
                     , String
"sequenced with"
                     , String -> String
forall k (a :: k). Typeable a => String -> String
genDescr @a String
genaname
                     ]) (Property -> Spec) -> Property -> Spec
forall a b. (a -> b) -> a -> b
$
                (Anon (a -> b) -> a -> f b)
-> (Anon (a -> b) -> a -> f b)
-> Gen (Anon (a -> b), a)
-> ((Anon (a -> b), a) -> [(Anon (a -> b), a)])
-> Property
forall a b c.
(Show a, Show b, Show c, Eq c) =>
(a -> b -> c)
-> (a -> b -> c) -> Gen (a, b) -> ((a, b) -> [(a, b)]) -> Property
equivalentOnGens2
                    (\(Anon a -> b
f) a
x -> (a -> b) -> f (a -> b)
forall (f :: * -> *) a. Applicative f => a -> f a
pure a -> b
f f (a -> b) -> f a -> f b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> a -> f a
forall (f :: * -> *) a. Applicative f => a -> f a
pure a
x :: f b)
                    (\(Anon a -> b
f) a
x -> b -> f b
forall (f :: * -> *) a. Applicative f => a -> f a
pure (b -> f b) -> b -> f b
forall a b. (a -> b) -> a -> b
$ a -> b
f a
x :: f b)
                    ((,) (Anon (a -> b) -> a -> (Anon (a -> b), a))
-> Gen (Anon (a -> b)) -> Gen (a -> (Anon (a -> b), a))
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> ((a -> b) -> Anon (a -> b)
forall a. a -> Anon a
Anon ((a -> b) -> Anon (a -> b)) -> Gen (a -> b) -> Gen (Anon (a -> b))
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Gen (a -> b)
genfa) Gen (a -> (Anon (a -> b), a)) -> Gen a -> Gen (Anon (a -> b), a)
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Gen a
gena)
                    (Anon (a -> b), a) -> [(Anon (a -> b), a)]
forall a. a -> [a]
shrinkNothing
            String -> Property -> Spec
forall (outers :: [*]) inner test.
(HasCallStack, IsTest test, Arg1 test ~ (), Arg2 test ~ inner) =>
String -> test -> TestDefM outers inner ()
it
                ([String] -> String
unwords
                     [ String
"satisfy the interchange law: 'u <*> pure y = pure ($ y) <*> u' for"
                     , String -> String
forall k (a :: k). Typeable a => String -> String
genDescr @(f (a -> b)) String
genffaname
                     , String
"sequenced with"
                     , String -> String
forall k (a :: k). Typeable a => String -> String
genDescr @a String
genaname
                     ]) (Property -> Spec) -> Property -> Spec
forall a b. (a -> b) -> a -> b
$
                (Anon (f (a -> b)) -> a -> f b)
-> (Anon (f (a -> b)) -> a -> f b)
-> Gen (Anon (f (a -> b)), a)
-> ((Anon (f (a -> b)), a) -> [(Anon (f (a -> b)), a)])
-> Property
forall a b c.
(Show a, Show b, Show c, Eq c) =>
(a -> b -> c)
-> (a -> b -> c) -> Gen (a, b) -> ((a, b) -> [(a, b)]) -> Property
equivalentOnGens2
                    (\(Anon f (a -> b)
u) a
y -> f (a -> b)
u f (a -> b) -> f a -> f b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> a -> f a
forall (f :: * -> *) a. Applicative f => a -> f a
pure a
y :: f b)
                    (\(Anon f (a -> b)
u) a
y -> ((a -> b) -> b) -> f ((a -> b) -> b)
forall (f :: * -> *) a. Applicative f => a -> f a
pure ((a -> b) -> a -> b
forall a b. (a -> b) -> a -> b
$ a
y) f ((a -> b) -> b) -> f (a -> b) -> f b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> f (a -> b)
u :: f b)
                    ((,) (Anon (f (a -> b)) -> a -> (Anon (f (a -> b)), a))
-> Gen (Anon (f (a -> b))) -> Gen (a -> (Anon (f (a -> b)), a))
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (f (a -> b) -> Anon (f (a -> b))
forall a. a -> Anon a
Anon (f (a -> b) -> Anon (f (a -> b)))
-> Gen (f (a -> b)) -> Gen (Anon (f (a -> b)))
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Gen (f (a -> b))
genffa) Gen (a -> (Anon (f (a -> b)), a))
-> Gen a -> Gen (Anon (f (a -> b)), a)
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Gen a
gena)
                    (Anon (f (a -> b)), a) -> [(Anon (f (a -> b)), a)]
forall a. a -> [a]
shrinkNothing
            String -> Property -> Spec
forall (outers :: [*]) inner test.
(HasCallStack, IsTest test, Arg1 test ~ (), Arg2 test ~ inner) =>
String -> test -> TestDefM outers inner ()
it
                ([String] -> String
unwords
                     [ String
"satisfy the law about the functor instance: fmap f x = pure f <*> x for"
                     , String -> String
forall k (a :: k). Typeable a => String -> String
genDescr @(a -> b) String
genfaname
                     , String
"mapped over"
                     , String -> String
forall k (a :: k). Typeable a => String -> String
genDescr @(f a) String
genname
                     ]) (Property -> Spec) -> Property -> Spec
forall a b. (a -> b) -> a -> b
$
                (Anon (a -> b) -> f a -> f b)
-> (Anon (a -> b) -> f a -> f b)
-> Gen (Anon (a -> b), f a)
-> ((Anon (a -> b), f a) -> [(Anon (a -> b), f a)])
-> Property
forall a b c.
(Show a, Show b, Show c, Eq c) =>
(a -> b -> c)
-> (a -> b -> c) -> Gen (a, b) -> ((a, b) -> [(a, b)]) -> Property
equivalentOnGens2
                    (\(Anon a -> b
f) f a
x -> (a -> b) -> f a -> f b
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap a -> b
f f a
x)
                    (\(Anon a -> b
f) f a
x -> (a -> b) -> f (a -> b)
forall (f :: * -> *) a. Applicative f => a -> f a
pure a -> b
f f (a -> b) -> f a -> f b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> f a
x)
                    ((,) (Anon (a -> b) -> f a -> (Anon (a -> b), f a))
-> Gen (Anon (a -> b)) -> Gen (f a -> (Anon (a -> b), f a))
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> ((a -> b) -> Anon (a -> b)
forall a. a -> Anon a
Anon ((a -> b) -> Anon (a -> b)) -> Gen (a -> b) -> Gen (Anon (a -> b))
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Gen (a -> b)
genfa) Gen (f a -> (Anon (a -> b), f a))
-> Gen (f a) -> Gen (Anon (a -> b), f a)
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Gen (f a)
gen)
                    (Anon (a -> b), f a) -> [(Anon (a -> b), f a)]
forall a. a -> [a]
shrinkNothing
        String -> Spec -> Spec
forall (outers :: [*]) inner.
String -> TestDefM outers inner () -> TestDefM outers inner ()
describe (Typeable f => String
forall (f :: * -> *). Typeable f => String
seqrTypeStr @f) (Spec -> Spec) -> Spec -> Spec
forall a b. (a -> b) -> a -> b
$
            String -> Property -> Spec
forall (outers :: [*]) inner test.
(HasCallStack, IsTest test, Arg1 test ~ (), Arg2 test ~ inner) =>
String -> test -> TestDefM outers inner ()
it
                ([String] -> String
unwords
                     [ String
"is equivalent to its default implementation 'u Type> v = pure (const id) <*> u <*> v' for"
                     , String -> String
forall k (a :: k). Typeable a => String -> String
genDescr @(f a) String
genname
                     , String
"in front of"
                     , String -> String
forall k (a :: k). Typeable a => String -> String
genDescr @b String
genbname
                     ]) (Property -> Spec) -> Property -> Spec
forall a b. (a -> b) -> a -> b
$
            (f a -> f b -> f b)
-> (f a -> f b -> f b)
-> Gen (f a, f b)
-> ((f a, f b) -> [(f a, f b)])
-> Property
forall a b c.
(Show a, Show b, Show c, Eq c) =>
(a -> b -> c)
-> (a -> b -> c) -> Gen (a, b) -> ((a, b) -> [(a, b)]) -> Property
equivalentOnGens2
                (\f a
u f b
v -> f a
u f a -> f b -> f b
forall (f :: * -> *) a b. Applicative f => f a -> f b -> f b
*> f b
v)
                (\f a
u f b
v -> (a -> b -> b) -> f (a -> b -> b)
forall (f :: * -> *) a. Applicative f => a -> f a
pure ((b -> b) -> a -> b -> b
forall a b. a -> b -> a
const b -> b
forall a. a -> a
id) f (a -> b -> b) -> f a -> f (b -> b)
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> f a
u f (b -> b) -> f b -> f b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> f b
v)
                ((,) (f a -> f b -> (f a, f b)) -> Gen (f a) -> Gen (f b -> (f a, f b))
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Gen (f a)
gen Gen (f b -> (f a, f b)) -> Gen (f b) -> Gen (f a, f b)
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Gen (f b)
genb)
                (f a, f b) -> [(f a, f b)]
forall a. a -> [a]
shrinkNothing
        String -> Spec -> Spec
forall (outers :: [*]) inner.
String -> TestDefM outers inner () -> TestDefM outers inner ()
describe (Typeable f => String
forall (f :: * -> *). Typeable f => String
seqlTypeStr @f) (Spec -> Spec) -> Spec -> Spec
forall a b. (a -> b) -> a -> b
$
            String -> Property -> Spec
forall (outers :: [*]) inner test.
(HasCallStack, IsTest test, Arg1 test ~ (), Arg2 test ~ inner) =>
String -> test -> TestDefM outers inner ()
it
                ([String] -> String
unwords
                     [ String
"is equivalent to its default implementation 'u <* v = pure const <*> u <*> v' for"
                     , String -> String
forall k (a :: k). Typeable a => String -> String
genDescr @b String
genbname
                     , String
"behind"
                     , String -> String
forall k (a :: k). Typeable a => String -> String
genDescr @(f a) String
genname
                     ]) (Property -> Spec) -> Property -> Spec
forall a b. (a -> b) -> a -> b
$
            (f a -> f b -> f a)
-> (f a -> f b -> f a)
-> Gen (f a, f b)
-> ((f a, f b) -> [(f a, f b)])
-> Property
forall a b c.
(Show a, Show b, Show c, Eq c) =>
(a -> b -> c)
-> (a -> b -> c) -> Gen (a, b) -> ((a, b) -> [(a, b)]) -> Property
equivalentOnGens2
                (\f a
u f b
v -> f a
u f a -> f b -> f a
forall (f :: * -> *) a b. Applicative f => f a -> f b -> f a
<* f b
v)
                (\f a
u f b
v -> (a -> b -> a) -> f (a -> b -> a)
forall (f :: * -> *) a. Applicative f => a -> f a
pure a -> b -> a
forall a b. a -> b -> a
const f (a -> b -> a) -> f a -> f (b -> a)
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> f a
u f (b -> a) -> f b -> f a
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> f b
v)
                ((,) (f a -> f b -> (f a, f b)) -> Gen (f a) -> Gen (f b -> (f a, f b))
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Gen (f a)
gen Gen (f b -> (f a, f b)) -> Gen (f b) -> Gen (f a, f b)
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Gen (f b)
genb)
                (f a, f b) -> [(f a, f b)]
forall a. a -> [a]
shrinkNothing