{-| The gives detailed information about using QuickCheck effectively. You can also try , a tutorial written by a user of QuickCheck. To start using QuickCheck, write down your property as a function returning @Bool@. For example, to check that reversing a list twice gives back the same list you can write: @ import Test.QuickCheck prop_reverse :: [Int] -> Bool prop_reverse xs = reverse (reverse xs) == xs @ You can then use QuickCheck to test @prop_reverse@ on 100 random lists: >>> quickCheck prop_reverse +++ OK, passed 100 tests. To run more tests you can use the 'withMaxSuccess' combinator: >>> quickCheck (withMaxSuccess 10000 prop_reverse) +++ OK, passed 10000 tests. To use QuickCheck on your own data types you will need to write 'Arbitrary' instances for those types. See the for details about how to do that. When testing fails @quickCheck@ will try to give you a minimal counterexample to your property: @ import Test.QuickCheck prop_reverse_bad :: [Int] -> Bool prop_reverse_bad xs = reverse xs == xs >>> quickCheck prop_reverse_bad *** Failed! Falsified (after 3 tests and 3 shrinks): [0,1] @ However, beware because not all properties that ought to fail will fail when you expect them to: @ >>> quickCheck $ \ x y -> x == y +++ Ok, passed 100 tests. @ That's because GHCi will default any type variables in your property to '()', so in the example above @quickCheck@ was really testing that '()' is equal to itself. To avoid this behaviour it is best practise to monomorphise your polymorphic properties when testing: @ >>> quickCheck $ \ x y -> (x :: Int) == y *** Failed! Falsified (after 4 tests and 3 shrinks): 0 1 @ -} {-# LANGUAGE CPP #-} #ifndef NO_SAFE_HASKELL {-# LANGUAGE Safe #-} #endif #if defined(__GLASGOW_HASKELL__) && __GLASGOW_HASKELL__ >= 708 {-# LANGUAGE PatternSynonyms #-} #endif module Test.QuickCheck ( -- * Running tests quickCheck , Args(..), Result(..) , stdArgs , quickCheckWith , quickCheckWithResult , quickCheckResult , recheck , isSuccess -- ** Running tests verbosely , verboseCheck , verboseCheckWith , verboseCheckWithResult , verboseCheckResult #ifndef NO_TEMPLATE_HASKELL -- ** Testing all properties in a module -- | These functions test all properties in the current module, using -- Template Haskell. You need to have a @{-\# LANGUAGE TemplateHaskell \#-}@ -- pragma in your module for any of these to work. , quickCheckAll , verboseCheckAll , forAllProperties , allProperties -- ** Testing polymorphic properties , polyQuickCheck , polyVerboseCheck , monomorphic #endif -- * The 'Arbitrary' typeclass: generation of random values , Arbitrary(..) -- ** Helper functions for implementing 'shrink' #ifndef NO_GENERICS , genericShrink , subterms , recursivelyShrink #endif , shrinkNothing , shrinkList , shrinkMap , shrinkMapBy , shrinkIntegral , shrinkRealFrac , shrinkBoundedEnum , shrinkDecimal -- ** Lifting of 'Arbitrary' to unary and binary type constructors , Arbitrary1(..) , arbitrary1 , shrink1 , Arbitrary2(..) , arbitrary2 , shrink2 -- * The 'Gen' monad: combinators for building random generators , Gen -- ** Generator combinators , choose , chooseInt , chooseInteger , chooseBoundedIntegral , chooseEnum , chooseAny , oneof , frequency , elements , growingElements , sized , getSize , resize , scale , suchThat , suchThatMap , suchThatMaybe , applyArbitrary2 , applyArbitrary3 , applyArbitrary4 -- ** Generators for lists , listOf , listOf1 , vectorOf , vector , infiniteListOf , infiniteList , shuffle , sublistOf , orderedList -- ** Generators for particular types , arbitrarySizedIntegral , arbitrarySizedNatural , arbitrarySizedFractional , arbitrarySizedBoundedIntegral , arbitraryBoundedIntegral , arbitraryBoundedRandom , arbitraryBoundedEnum , arbitraryUnicodeChar , arbitraryASCIIChar , arbitraryPrintableChar -- ** Running generators , generate -- ** Debugging generators , sample , sample' #ifndef NO_GADTS -- * The 'Function' typeclass: generation of random shrinkable, showable functions -- | Example of use: -- -- >>> :{ -- >>> let prop :: Fun String Integer -> Bool -- >>> prop (Fun _ f) = f "monkey" == f "banana" || f "banana" == f "elephant" -- >>> :} -- >>> quickCheck prop -- *** Failed! Falsified (after 3 tests and 134 shrinks): -- {"elephant"->1, "monkey"->1, _->0} -- -- To generate random values of type @'Fun' a b@, -- you must have an instance @'Function' a@. -- If your type has a 'Show' instance, you can use 'functionShow' to write the instance; otherwise, -- use 'functionMap' to give a bijection between your type and a type that is already an instance of 'Function'. -- See the @'Function' [a]@ instance for an example of the latter. -- -- For more information, see the paper \"Shrinking and showing functions\" by Koen Claessen. , Fun (..) , applyFun , applyFun2 , applyFun3 #if defined(__GLASGOW_HASKELL__) && __GLASGOW_HASKELL__ >= 708 , pattern Fn , pattern Fn2 , pattern Fn3 #endif , Function (..) , functionMap , functionShow , functionIntegral , functionRealFrac , functionBoundedEnum , functionVoid #endif -- * The 'CoArbitrary' typeclass: generation of functions the old-fashioned way , CoArbitrary(..) #ifndef NO_GENERICS , genericCoarbitrary #endif , variant , coarbitraryIntegral , coarbitraryReal , coarbitraryShow , coarbitraryEnum , (><) -- * Type-level modifiers for changing generator behavior -- | These types do things such as restricting the kind of test data that can be generated. -- They can be pattern-matched on in properties as a stylistic -- alternative to using explicit quantification. -- -- Examples: -- -- @ -- -- Functions cannot be shown (but see 'Function') -- prop_TakeDropWhile ('Blind' p) (xs :: ['A']) = -- takeWhile p xs ++ dropWhile p xs == xs -- @ -- -- @ -- prop_TakeDrop ('NonNegative' n) (xs :: ['A']) = -- take n xs ++ drop n xs == xs -- @ -- -- @ -- -- cycle does not work for empty lists -- prop_Cycle ('NonNegative' n) ('NonEmpty' (xs :: ['A'])) = -- take n (cycle xs) == take n (xs ++ cycle xs) -- @ -- -- @ -- -- Instead of 'forAll' 'orderedList' -- prop_Sort ('Ordered' (xs :: ['OrdA'])) = -- sort xs == xs -- @ , Blind(..) , Fixed(..) , OrderedList(..) , NonEmptyList(..) , InfiniteList(..) , SortedList(..) , Positive(..) , Negative(..) , NonZero(..) , NonNegative(..) , NonPositive(..) , Large(..) , Small(..) , Smart(..) , Shrink2(..) #ifndef NO_MULTI_PARAM_TYPE_CLASSES , Shrinking(..) , ShrinkState(..) #endif , ASCIIString(..) , UnicodeString(..) , PrintableString(..) -- * Property combinators , Property, Testable(..) , forAll , forAllShrink , forAllShow , forAllShrinkShow , forAllBlind , forAllShrinkBlind , shrinking , (==>) , Discard(..) , discard , (===) , (=/=) #ifndef NO_DEEPSEQ , total #endif , ioProperty , idempotentIOProperty -- ** Controlling property execution , verbose , verboseShrinking , noShrinking , withMaxSuccess , within , discardAfter , withDiscardRatio , withMaxSize , withMaxShrinks , once , again , mapSize -- ** Conjunction and disjunction , (.&.) , (.&&.) , conjoin , (.||.) , disjoin -- ** What to do on failure #ifndef NO_TYPEABLE , Witness(..) , witness , coerceWitness , castWitness #endif , counterexample , printTestCase , whenFail , whenFail' , expectFailure -- * Analysing test case distribution , label , collect , classify , tabulate -- ** Checking test case distribution , cover , coverTable , checkCoverage , checkCoverageWith , Confidence(..) , stdConfidence -- ** Generating example test cases , labelledExamples , labelledExamplesWith , labelledExamplesWithResult , labelledExamplesResult ) where -------------------------------------------------------------------------- -- imports import Test.QuickCheck.Gen import Test.QuickCheck.Arbitrary import Test.QuickCheck.Modifiers import Test.QuickCheck.Property hiding ( Result(..) ) import Test.QuickCheck.Test import Test.QuickCheck.Exception #ifndef NO_GADTS import Test.QuickCheck.Function #endif import Test.QuickCheck.Features import Test.QuickCheck.State #ifndef NO_TEMPLATE_HASKELL import Test.QuickCheck.All #endif -------------------------------------------------------------------------- -- the end.