Safe Haskell | Safe-Inferred |
---|---|
Language | Haskell2010 |
Refined
Description
In type theory, a refinement type is a type endowed with a predicate which is assumed to hold for any element of the refined type.
This library allows one to capture the idea of a refinement type
using the Refined
type. A Refined
p
x
wraps a value
of type x
, ensuring that it satisfies a type-level predicate p
.
A simple introduction to this library can be found here: http://nikita-volkov.github.io/refined/
Synopsis
- data Refined (p :: k) x
- refine :: forall p x. Predicate p x => x -> Either RefineException (Refined p x)
- refine_ :: forall p x. Predicate p x => x -> Either RefineException x
- refineThrow :: (Predicate p x, MonadThrow m) => x -> m (Refined p x)
- refineFail :: (Predicate p x, MonadFail m) => x -> m (Refined p x)
- refineError :: (Predicate p x, MonadError RefineException m) => x -> m (Refined p x)
- refineEither :: forall p x. Predicate p x => x -> Either (Refined (Not p) x) (Refined p x)
- refineTH :: forall p x m. (Predicate p x, Lift x, Quote m, MonadFail m) => x -> Code m (Refined p x)
- refineTH_ :: forall p x m. (Predicate p x, Lift x, Quote m, MonadFail m) => x -> Code m x
- unrefine :: Refined p x -> x
- data Refined1 (p :: k) f x
- refine1 :: forall p f x. Predicate1 p f => f x -> Either RefineException (Refined1 p f x)
- unrefine1 :: Refined1 p f x -> f x
- class (Typeable p, Typeable k) => Predicate (p :: k) x where
- validate :: Proxy p -> x -> Maybe RefineException
- validate' :: forall {k} p x. Predicate (p :: k) x => Proxy p -> x -> Maybe RefineException
- reifyPredicate :: forall p a. Predicate p a => a -> Bool
- class (Typeable p, Typeable k) => Predicate1 (p :: k) f where
- validate1 :: Proxy p -> f a -> Maybe RefineException
- validate1' :: forall {k} p f a. Predicate1 (p :: k) f => Proxy p -> f a -> Maybe RefineException
- data Not p = Not
- data And l r = And
- type (&&) = And
- data Or l r = Or
- type (||) = Or
- data Xor l r = Xor
- data IdPred = IdPred
- data LessThan (n :: Nat) = LessThan
- data GreaterThan (n :: Nat) = GreaterThan
- data From (n :: Nat) = From
- data To (n :: Nat) = To
- data FromTo (mn :: Nat) (mx :: Nat) = FromTo
- data NegativeFromTo (n :: Nat) (m :: Nat) = NegativeFromTo
- data EqualTo (n :: Nat) = EqualTo
- data NotEqualTo (n :: Nat) = NotEqualTo
- data Odd = Odd
- data Even = Even
- data DivisibleBy (n :: Nat) = DivisibleBy
- data NaN = NaN
- data Infinite = Infinite
- type Positive = GreaterThan 0
- type NonPositive = To 0
- type Negative = LessThan 0
- type NonNegative = From 0
- type ZeroToOne = FromTo 0 1
- type NonZero = NotEqualTo 0
- data SizeLessThan (n :: Nat) = SizeLessThan
- data SizeGreaterThan (n :: Nat) = SizeGreaterThan
- data SizeEqualTo (n :: Nat) = SizeEqualTo
- type Empty = SizeEqualTo 0
- type NonEmpty = SizeGreaterThan 0
- data Ascending = Ascending
- data Descending = Descending
- class Weaken from to where
- andLeft :: Refined (And l r) x -> Refined l x
- andRight :: Refined (And l r) x -> Refined r x
- leftOr :: Refined l x -> Refined (Or l r) x
- rightOr :: Refined r x -> Refined (Or l r) x
- weakenAndLeft :: Weaken from to => Refined (And from x) a -> Refined (And to x) a
- weakenAndRight :: Weaken from to => Refined (And x from) a -> Refined (And x to) a
- weakenOrLeft :: Weaken from to => Refined (And from x) a -> Refined (And to x) a
- weakenOrRight :: Weaken from to => Refined (And x from) a -> Refined (And x to) a
- strengthen :: forall p p' x. (Predicate p x, Predicate p' x) => Refined p x -> Either RefineException (Refined (p && p') x)
- data RefineException
- = RefineNotException !TypeRep
- | RefineAndException !TypeRep !(These RefineException RefineException)
- | RefineOrException !TypeRep !RefineException !RefineException
- | RefineXorException !TypeRep !(Maybe (RefineException, RefineException))
- | RefineSomeException !TypeRep !SomeException
- | RefineOtherException !TypeRep !Text
- displayRefineException :: RefineException -> String
- throwRefineOtherException :: TypeRep -> Text -> Maybe RefineException
- throwRefineSomeException :: TypeRep -> SomeException -> Maybe RefineException
- success :: Maybe RefineException
Refined
type
data Refined (p :: k) x Source #
A refinement type, which wraps a value of type x
.
Since: 0.1.0.0
Instances
Creation
refine :: forall p x. Predicate p x => x -> Either RefineException (Refined p x) Source #
A smart constructor of a Refined
value.
Checks the input value at runtime.
Since: 0.1.0.0
refine_ :: forall p x. Predicate p x => x -> Either RefineException x Source #
Like refine
, but discards the refinement.
This _can_ be useful when you only need to validate
that some value at runtime satisfies some predicate.
See also reifyPredicate
.
Since: 0.4.4
refineThrow :: (Predicate p x, MonadThrow m) => x -> m (Refined p x) Source #
refineError :: (Predicate p x, MonadError RefineException m) => x -> m (Refined p x) Source #
Constructs a Refined
value at run-time,
calling throwError
if the value
does not satisfy the predicate.
Since: 0.2.0.0
refineEither :: forall p x. Predicate p x => x -> Either (Refined (Not p) x) (Refined p x) Source #
Like refine
, but, when the value doesn't satisfy the predicate, returns
a Refined
value with the predicate negated, instead of returning
RefineException
.
>>>
isRight (refineEither @Even @Int 42)
True
>>>
isLeft (refineEither @Even @Int 43)
True
refineTH :: forall p x m. (Predicate p x, Lift x, Quote m, MonadFail m) => x -> Code m (Refined p x) Source #
Constructs a Refined
value at compile-time using -XTemplateHaskell
.
For example:
$$(refineTH 23) :: Refined Positive Int Refined 23
Here's an example of an invalid value:
$$(refineTH 0) :: Refined Positive Int <interactive>:6:4: Value is not greater than 0 In the Template Haskell splice $$(refineTH 0) In the expression: $$(refineTH 0) :: Refined Positive Int In an equation for ‘it’: it = $$(refineTH 0) :: Refined Positive Int
The example above indicates a compile-time failure, which means that the checking was done at compile-time, thus introducing a zero-runtime overhead compared to a plain value construction.
Note: It may be useful to use this function with the th-lift-instances package.
Since: 0.1.0.0
refineTH_ :: forall p x m. (Predicate p x, Lift x, Quote m, MonadFail m) => x -> Code m x Source #
Like refineTH
, but immediately unrefines the value.
This is useful when some value need only be refined
at compile-time.
Since: 0.4.4
Consumption
Refined1
type
data Refined1 (p :: k) f x Source #
A refinement type, which wraps a value of type f x
.
The predicate is applied over the functor f
. Thus, we may safely recover
various Functor
y instances, because no matter what you do to the
values inside the functor, the predicate may not be invalidated.
Instances
Lift (f a) => Lift (Refined1 p f a :: Type) Source # | |
Foldable f => Foldable (Refined1 p f) Source # | |
Defined in Refined.Unsafe.Type Methods fold :: Monoid m => Refined1 p f m -> m Source # foldMap :: Monoid m => (a -> m) -> Refined1 p f a -> m Source # foldMap' :: Monoid m => (a -> m) -> Refined1 p f a -> m Source # foldr :: (a -> b -> b) -> b -> Refined1 p f a -> b Source # foldr' :: (a -> b -> b) -> b -> Refined1 p f a -> b Source # foldl :: (b -> a -> b) -> b -> Refined1 p f a -> b Source # foldl' :: (b -> a -> b) -> b -> Refined1 p f a -> b Source # foldr1 :: (a -> a -> a) -> Refined1 p f a -> a Source # foldl1 :: (a -> a -> a) -> Refined1 p f a -> a Source # toList :: Refined1 p f a -> [a] Source # null :: Refined1 p f a -> Bool Source # length :: Refined1 p f a -> Int Source # elem :: Eq a => a -> Refined1 p f a -> Bool Source # maximum :: Ord a => Refined1 p f a -> a Source # minimum :: Ord a => Refined1 p f a -> a Source # | |
Traversable f => Traversable (Refined1 p f) Source # | |
Defined in Refined.Unsafe.Type Methods traverse :: Applicative f0 => (a -> f0 b) -> Refined1 p f a -> f0 (Refined1 p f b) Source # sequenceA :: Applicative f0 => Refined1 p f (f0 a) -> f0 (Refined1 p f a) Source # mapM :: Monad m => (a -> m b) -> Refined1 p f a -> m (Refined1 p f b) Source # sequence :: Monad m => Refined1 p f (m a) -> m (Refined1 p f a) Source # | |
Functor f => Functor (Refined1 p f) Source # | |
Show (f x) => Show (Refined1 p f x) Source # | |
NFData (f x) => NFData (Refined1 p f x) Source # | |
Defined in Refined.Unsafe.Type | |
Eq (f x) => Eq (Refined1 p f x) Source # | |
Ord (f x) => Ord (Refined1 p f x) Source # | |
Defined in Refined.Unsafe.Type Methods compare :: Refined1 p f x -> Refined1 p f x -> Ordering Source # (<) :: Refined1 p f x -> Refined1 p f x -> Bool Source # (<=) :: Refined1 p f x -> Refined1 p f x -> Bool Source # (>) :: Refined1 p f x -> Refined1 p f x -> Bool Source # (>=) :: Refined1 p f x -> Refined1 p f x -> Bool Source # max :: Refined1 p f x -> Refined1 p f x -> Refined1 p f x Source # min :: Refined1 p f x -> Refined1 p f x -> Refined1 p f x Source # | |
Hashable (f x) => Hashable (Refined1 p f x) Source # | |
Creation
refine1 :: forall p f x. Predicate1 p f => f x -> Either RefineException (Refined1 p f x) Source #
A smart constructor of a Refined1
value.
Checks the input value at runtime.
Since: 0.1.0.0
Consumption
Predicate
class (Typeable p, Typeable k) => Predicate (p :: k) x where Source #
A typeclass which defines a runtime interpretation of
a type-level predicate p
for type x
.
Since: 0.1.0.0
Methods
validate :: Proxy p -> x -> Maybe RefineException Source #
Check the value x
according to the predicate p
,
producing an error RefineException
if the value
does not satisfy.
Note: validate
is not intended to be used
directly; instead, it is intended to provide the minimal
means necessary for other utilities to be derived. As
such, the Maybe
here should be interpreted to mean
the presence or absence of a RefineException
, and
nothing else.
Note that due to GHC's type variable order rules, this function has an
implicit kind in position 1, which makes TypeApplications awkward. Use
validate'
for nicer behaviour.
Instances
validate' :: forall {k} p x. Predicate (p :: k) x => Proxy p -> x -> Maybe RefineException Source #
Check the value x
according to the predicate p
,
producing an error RefineException
if the value
does not satisfy.
Same as validate
but with more convenient type variable order for a better
TypeApplications experience.
reifyPredicate :: forall p a. Predicate p a => a -> Bool Source #
Reify a Predicate
by turning it into a value-level predicate.
Since: 0.4.2.3
Predicate1
class (Typeable p, Typeable k) => Predicate1 (p :: k) f where Source #
A typeclass which defines a runtime interpretation of
a type-level predicate p
for type forall a. f a
.
The inner type may not be inspected. If you find yourself needing to add
constraints to it, you want Predicate
.
Methods
validate1 :: Proxy p -> f a -> Maybe RefineException Source #
Check the value f a
according to the predicate p
,
producing an error RefineException
if the value
does not satisfy.
Note: validate1
is not intended to be used
directly; instead, it is intended to provide the minimal
means necessary for other utilities to be derived. As
such, the Maybe
here should be interpreted to mean
the presence or absence of a RefineException
, and
nothing else.
Note that due to GHC's type variable order rules, this function has an
implicit kind in position 1, which makes TypeApplications awkward. Use
validate1'
for nicer behaviour.
Instances
(Foldable t, KnownNat n) => Predicate1 (SizeEqualTo n :: Type) (t :: TYPE LiftedRep -> Type) Source # | |
Defined in Refined Methods validate1 :: forall (a :: k). Proxy (SizeEqualTo n) -> t a -> Maybe RefineException Source # | |
(Foldable t, KnownNat n) => Predicate1 (SizeGreaterThan n :: Type) (t :: TYPE LiftedRep -> Type) Source # | |
Defined in Refined Methods validate1 :: forall (a :: k). Proxy (SizeGreaterThan n) -> t a -> Maybe RefineException Source # | |
(Foldable t, KnownNat n) => Predicate1 (SizeLessThan n :: Type) (t :: TYPE LiftedRep -> Type) Source # | |
Defined in Refined Methods validate1 :: forall (a :: k). Proxy (SizeLessThan n) -> t a -> Maybe RefineException Source # |
validate1' :: forall {k} p f a. Predicate1 (p :: k) f => Proxy p -> f a -> Maybe RefineException Source #
Check the value f a
according to the predicate p
,
producing an error RefineException
if the value
does not satisfy.
Same as validate1
but with more convenient type variable order for a better
TypeApplications experience.
Logical predicates
The negation of a predicate.
>>>
isRight (refine @(Not NonEmpty) @[Int] [])
True
>>>
isLeft (refine @(Not NonEmpty) @[Int] [1,2])
True
Since: 0.1.0.0
Constructors
Not | Since: 0.4.2 |
The conjunction of two predicates.
>>>
isLeft (refine @(And Positive Negative) @Int 3)
True
>>>
isRight (refine @(And Positive Odd) @Int 203)
True
Since: 0.1.0.0
Constructors
And | Since: 0.4.2 |
The disjunction of two predicates.
>>>
isRight (refine @(Or Even Odd) @Int 3)
True
>>>
isRight (refine @(Or (LessThan 3) (GreaterThan 3)) @Int 2)
True
>>>
isRight (refine @(Or Even Even) @Int 4)
True
Since: 0.1.0.0
Constructors
Or | Since: 0.4.2 |
The exclusive disjunction of two predicates.
>>>
isRight (refine @(Xor Even Odd) @Int 3)
True
>>>
isLeft (refine @(Xor (LessThan 3) (EqualTo 2)) @Int 2)
True
>>>
isLeft (refine @(Xor Even Even) @Int 2)
True
Since: 0.5
Constructors
Xor | Since: 0.5 |
Identity predicate
A predicate which is satisfied for all types.
Arguments passed to
in validate
are not evaluated.validate
IdPred
x
>>>
isRight (refine @IdPred @Int undefined)
True
>>>
isLeft (refine @IdPred @Int undefined)
False
Since: 0.3.0.0
Constructors
IdPred | Since: 0.4.2 |
Numeric predicates
data LessThan (n :: Nat) Source #
A Predicate
ensuring that the value is less than the
specified type-level number.
>>>
isRight (refine @(LessThan 12) @Int 11)
True
>>>
isLeft (refine @(LessThan 12) @Int 12)
True
Since: 0.1.0.0
Constructors
LessThan | Since: 0.4.2 |
Instances
n <= m => Weaken (LessThan n :: Type) (LessThan m :: Type) Source # | Since: 0.2.0.0 |
n <= m => Weaken (LessThan n :: Type) (To m :: Type) Source # | Since: 0.2.0.0 |
(Ord x, Num x, KnownNat n) => Predicate (LessThan n :: Type) x Source # | Since: 0.1.0.0 |
Generic (LessThan n) Source # | |
type Rep (LessThan n) Source # | Since: 0.3.0.0 |
data GreaterThan (n :: Nat) Source #
A Predicate
ensuring that the value is greater than the
specified type-level number.
>>>
isRight (refine @(GreaterThan 65) @Int 67)
True
>>>
isLeft (refine @(GreaterThan 65) @Int 65)
True
Since: 0.1.0.0
Constructors
GreaterThan | Since: 0.4.2 |
Instances
m <= n => Weaken (GreaterThan n :: Type) (From m :: Type) Source # | Since: 0.2.0.0 |
m <= n => Weaken (GreaterThan n :: Type) (GreaterThan m :: Type) Source # | Since: 0.2.0.0 |
Defined in Refined Methods weaken :: Refined (GreaterThan n) x -> Refined (GreaterThan m) x Source # | |
(Ord x, Num x, KnownNat n) => Predicate (GreaterThan n :: Type) x Source # | Since: 0.1.0.0 |
Defined in Refined Methods validate :: Proxy (GreaterThan n) -> x -> Maybe RefineException Source # | |
Generic (GreaterThan n) Source # | |
Defined in Refined Methods from :: GreaterThan n -> Rep (GreaterThan n) x Source # to :: Rep (GreaterThan n) x -> GreaterThan n Source # | |
type Rep (GreaterThan n) Source # | Since: 0.3.0.0 |
A Predicate
ensuring that the value is greater than or equal to the
specified type-level number.
>>>
isRight (refine @(From 9) @Int 10)
True
>>>
isRight (refine @(From 10) @Int 10)
True
>>>
isLeft (refine @(From 11) @Int 10)
True
Since: 0.1.2
Constructors
From | Since: 0.4.2 |
Instances
m <= n => Weaken (From n :: Type) (From m :: Type) Source # | Since: 0.2.0.0 |
m <= n => Weaken (GreaterThan n :: Type) (From m :: Type) Source # | Since: 0.2.0.0 |
p <= n => Weaken (FromTo n m :: Type) (From p :: Type) Source # | Since: 0.2.0.0 |
(Ord x, Num x, KnownNat n) => Predicate (From n :: Type) x Source # | Since: 0.1.2 |
Generic (From n) Source # | |
type Rep (From n) Source # | Since: 0.3.0.0 |
A Predicate
ensuring that the value is less than or equal to the
specified type-level number.
>>>
isRight (refine @(To 23) @Int 17)
True
>>>
isLeft (refine @(To 17) @Int 23)
True
Since: 0.1.2
Constructors
To | Since: 0.4.2 |
Instances
n <= m => Weaken (LessThan n :: Type) (To m :: Type) Source # | Since: 0.2.0.0 |
n <= m => Weaken (To n :: Type) (To m :: Type) Source # | Since: 0.2.0.0 |
m <= q => Weaken (FromTo n m :: Type) (To q :: Type) Source # | Since: 0.2.0.0 |
(Ord x, Num x, KnownNat n) => Predicate (To n :: Type) x Source # | Since: 0.1.2 |
Generic (To n) Source # | |
type Rep (To n) Source # | Since: 0.3.0.0 |
data FromTo (mn :: Nat) (mx :: Nat) Source #
A Predicate
ensuring that the value is within an inclusive range.
>>>
isRight (refine @(FromTo 0 16) @Int 13)
True
>>>
isRight (refine @(FromTo 13 15) @Int 13)
True
>>>
isRight (refine @(FromTo 13 15) @Int 15)
True
>>>
isLeft (refine @(FromTo 13 15) @Int 12)
True
Since: 0.1.2
Constructors
FromTo | Since: 0.4.2 |
Instances
p <= n => Weaken (FromTo n m :: Type) (From p :: Type) Source # | Since: 0.2.0.0 |
m <= q => Weaken (FromTo n m :: Type) (To q :: Type) Source # | Since: 0.2.0.0 |
(p <= n, m <= q) => Weaken (FromTo n m :: Type) (FromTo p q :: Type) Source # | Since: 0.2.0.0 |
(Ord x, Num x, KnownNat mn, KnownNat mx, mn <= mx) => Predicate (FromTo mn mx :: Type) x Source # | Since: 0.1.2 |
Generic (FromTo mn mx) Source # | |
type Rep (FromTo mn mx) Source # | Since: 0.3.0.0 |
data NegativeFromTo (n :: Nat) (m :: Nat) Source #
A Predicate
ensuring that the value is greater or equal than a negative
number specified as a type-level (positive) number n
and less than a
type-level (positive) number m
.
>>>
isRight (refine @(NegativeFromTo 5 12) @Int (-3))
True
>>>
isLeft (refine @(NegativeFromTo 4 3) @Int (-5))
True
Since: 0.4
Constructors
NegativeFromTo | Since: 0.4.2 |
Instances
(Ord x, Num x, KnownNat n, KnownNat m) => Predicate (NegativeFromTo n m :: Type) x Source # | Since: 0.4 |
Defined in Refined Methods validate :: Proxy (NegativeFromTo n m) -> x -> Maybe RefineException Source # | |
Generic (NegativeFromTo n m) Source # | |
Defined in Refined Methods from :: NegativeFromTo n m -> Rep (NegativeFromTo n m) x Source # to :: Rep (NegativeFromTo n m) x -> NegativeFromTo n m Source # | |
type Rep (NegativeFromTo n m) Source # | Since: 0.3.0.0 |
data EqualTo (n :: Nat) Source #
A Predicate
ensuring that the value is equal to the specified
type-level number n
.
>>>
isRight (refine @(EqualTo 5) @Int 5)
True
>>>
isLeft (refine @(EqualTo 6) @Int 5)
True
Since: 0.1.0.0
Constructors
EqualTo | Since: 0.4.2 |
data NotEqualTo (n :: Nat) Source #
A Predicate
ensuring that the value is not equal to the specified
type-level number n
.
>>>
isRight (refine @(NotEqualTo 6) @Int 5)
True
>>>
isLeft (refine @(NotEqualTo 5) @Int 5)
True
Since: 0.2.0.0
Constructors
NotEqualTo | Since: 0.4.2 |
Instances
(Eq x, Num x, KnownNat n) => Predicate (NotEqualTo n :: Type) x Source # | Since: 0.2.0.0 |
Defined in Refined Methods validate :: Proxy (NotEqualTo n) -> x -> Maybe RefineException Source # | |
Generic (NotEqualTo n) Source # | |
Defined in Refined Methods from :: NotEqualTo n -> Rep (NotEqualTo n) x Source # to :: Rep (NotEqualTo n) x -> NotEqualTo n Source # | |
type Rep (NotEqualTo n) Source # | Since: 0.3.0.0 |
A Predicate
ensuring that the value is odd.
>>>
isRight (refine @Odd @Int 33)
True
>>>
isLeft (refine @Odd @Int 32)
True
Since: 0.4.2
Constructors
Odd | Since: 0.4.2 |
A Predicate
ensuring that the value is even.
>>>
isRight (refine @Even @Int 32)
True
>>>
isLeft (refine @Even @Int 33)
True
Since: 0.4.2
Constructors
Even | Since: 0.4.2 |
data DivisibleBy (n :: Nat) Source #
A Predicate
ensuring that the value is divisible by n
.
>>>
isRight (refine @(DivisibleBy 3) @Int 12)
True
>>>
isLeft (refine @(DivisibleBy 2) @Int 37)
True
Since: 0.4.2
Constructors
DivisibleBy | Since: 0.4.2 |
Instances
(Integral x, KnownNat n) => Predicate (DivisibleBy n :: Type) x Source # | Since: 0.4.2 |
Defined in Refined Methods validate :: Proxy (DivisibleBy n) -> x -> Maybe RefineException Source # | |
Generic (DivisibleBy n) Source # | |
Defined in Refined Methods from :: DivisibleBy n -> Rep (DivisibleBy n) x Source # to :: Rep (DivisibleBy n) x -> DivisibleBy n Source # | |
type Rep (DivisibleBy n) Source # | Since: 0.3.0.0 |
A Predicate
ensuring that the value is IEEE "not-a-number" (NaN).
>>>
isRight (refine @NaN @Double (0/0))
True
>>>
isLeft (refine @NaN @Double 13.9)
True
Since: 0.5
Constructors
NaN | Since: 0.5 |
A Predicate
ensuring that the value is IEEE infinity or negative infinity.
>>>
isRight (refine @Infinite @Double (1/0))
True
>>>
isRight (refine @Infinite @Double (-1/0))
True
>>>
isLeft (refine @Infinite @Double 13.20)
True
Since: 0.5
Constructors
Infinite | Since: 0.5 |
type Positive = GreaterThan 0 Source #
A Predicate
ensuring that the value is greater than zero.
Since: 0.1.0.0
type NonPositive = To 0 Source #
A Predicate
ensuring that the value is less than or equal to zero.
Since: 0.1.2
type Negative = LessThan 0 Source #
A Predicate
ensuring that the value is less than zero.
Since: 0.1.0.0
type NonNegative = From 0 Source #
A Predicate
ensuring that the value is greater than or equal to zero.
Since: 0.1.2
type NonZero = NotEqualTo 0 Source #
A Predicate
ensuring that the value is not equal to zero.
Since: 0.2.0.0
Foldable predicates
Size predicates
data SizeLessThan (n :: Nat) Source #
A Predicate
ensuring that the value has a length
which is less than the specified type-level number.
>>>
isRight (refine @(SizeLessThan 4) @[Int] [1,2,3])
True
>>>
isLeft (refine @(SizeLessThan 5) @[Int] [1,2,3,4,5])
True
>>>
isRight (refine @(SizeLessThan 4) @Text "Hi")
True
>>>
isLeft (refine @(SizeLessThan 4) @Text "Hello")
True
Since: 0.2.0.0
Constructors
SizeLessThan | Since: 0.4.2 |
Instances
data SizeGreaterThan (n :: Nat) Source #
A Predicate
ensuring that the value has a length
which is greater than the specified type-level number.
>>>
isLeft (refine @(SizeGreaterThan 3) @[Int] [1,2,3])
True
>>>
isRight (refine @(SizeGreaterThan 3) @[Int] [1,2,3,4,5])
True
>>>
isLeft (refine @(SizeGreaterThan 4) @Text "Hi")
True
>>>
isRight (refine @(SizeGreaterThan 4) @Text "Hello")
True
Since: 0.2.0.0
Constructors
SizeGreaterThan | Since: 0.4.2 |
Instances
data SizeEqualTo (n :: Nat) Source #
A Predicate
ensuring that the value has a length
which is equal to the specified type-level number.
>>>
isRight (refine @(SizeEqualTo 4) @[Int] [1,2,3,4])
True
>>>
isLeft (refine @(SizeEqualTo 35) @[Int] [1,2,3,4])
True
>>>
isRight (refine @(SizeEqualTo 4) @Text "four")
True
>>>
isLeft (refine @(SizeEqualTo 35) @Text "four")
True
Since: 0.2.0.0
Constructors
SizeEqualTo | Since: 0.4.2 |
Instances
type Empty = SizeEqualTo 0 Source #
A Predicate
ensuring that the type is empty.
Since: 0.5
type NonEmpty = SizeGreaterThan 0 Source #
A Predicate
ensuring that the type is non-empty.
Since: 0.2.0.0
Ordering predicates
A Predicate
ensuring that the Foldable
contains elements
in a strictly ascending order.
>>>
isRight (refine @Ascending @[Int] [5, 8, 13, 21, 34])
True
>>>
isLeft (refine @Ascending @[Int] [34, 21, 13, 8, 5])
True
Since: 0.2.0.0
Constructors
Ascending | Since: 0.4.2 |
data Descending Source #
A Predicate
ensuring that the Foldable
contains elements
in a strictly descending order.
>>>
isRight (refine @Descending @[Int] [34, 21, 13, 8, 5])
True
>>>
isLeft (refine @Descending @[Int] [5, 8, 13, 21, 34])
True
Since: 0.2.0.0
Constructors
Descending | Since: 0.4.2 |
Instances
Generic Descending Source # | |
Defined in Refined | |
(Foldable t, Ord a) => Predicate Descending (t a) Source # | Since: 0.2.0.0 |
Defined in Refined Methods validate :: Proxy Descending -> t a -> Maybe RefineException Source # | |
type Rep Descending Source # | Since: 0.3.0.0 |
Weakening
class Weaken from to where Source #
A typeclass containing "safe" conversions between refined predicates where the target is weaker than the source: that is, all values that satisfy the first predicate will be guaranteed to satisfy the second.
Take care: writing an instance declaration for your custom
predicates is the same as an assertion that weaken
is
safe to use:
instance Weaken
Pred1 Pred2
For most of the instances, explicit type annotations for the result value's type might be required.
Since: 0.2.0.0
Minimal complete definition
Nothing
Instances
m <= n => Weaken (From n :: Type) (From m :: Type) Source # | Since: 0.2.0.0 |
m <= n => Weaken (GreaterThan n :: Type) (From m :: Type) Source # | Since: 0.2.0.0 |
m <= n => Weaken (GreaterThan n :: Type) (GreaterThan m :: Type) Source # | Since: 0.2.0.0 |
Defined in Refined Methods weaken :: Refined (GreaterThan n) x -> Refined (GreaterThan m) x Source # | |
n <= m => Weaken (LessThan n :: Type) (LessThan m :: Type) Source # | Since: 0.2.0.0 |
n <= m => Weaken (LessThan n :: Type) (To m :: Type) Source # | Since: 0.2.0.0 |
m <= n => Weaken (SizeGreaterThan n :: Type) (SizeGreaterThan m :: Type) Source # | Since: 0.8.1 |
Defined in Refined Methods weaken :: Refined (SizeGreaterThan n) x -> Refined (SizeGreaterThan m) x Source # | |
n <= m => Weaken (SizeLessThan n :: Type) (SizeLessThan m :: Type) Source # | Since: 0.8.1 |
Defined in Refined Methods weaken :: Refined (SizeLessThan n) x -> Refined (SizeLessThan m) x Source # | |
n <= m => Weaken (To n :: Type) (To m :: Type) Source # | Since: 0.2.0.0 |
p <= n => Weaken (FromTo n m :: Type) (From p :: Type) Source # | Since: 0.2.0.0 |
m <= q => Weaken (FromTo n m :: Type) (To q :: Type) Source # | Since: 0.2.0.0 |
(p <= n, m <= q) => Weaken (FromTo n m :: Type) (FromTo p q :: Type) Source # | Since: 0.2.0.0 |
andLeft :: Refined (And l r) x -> Refined l x Source #
This function helps type inference. It is equivalent to the following:
instance Weaken (And l r) l
Since: 0.2.0.0
andRight :: Refined (And l r) x -> Refined r x Source #
This function helps type inference. It is equivalent to the following:
instance Weaken (And l r) r
Since: 0.2.0.0
leftOr :: Refined l x -> Refined (Or l r) x Source #
This function helps type inference. It is equivalent to the following:
instance Weaken l (Or l r)
Since: 0.2.0.0
rightOr :: Refined r x -> Refined (Or l r) x Source #
This function helps type inference. It is equivalent to the following:
instance Weaken r (Or l r)
Since: 0.2.0.0
weakenAndLeft :: Weaken from to => Refined (And from x) a -> Refined (And to x) a Source #
This function helps type inference. It is equivalent to the following:
instance Weaken from to => Weaken (And from x) (And to x)
Since: 0.8.1.0
weakenAndRight :: Weaken from to => Refined (And x from) a -> Refined (And x to) a Source #
This function helps type inference. It is equivalent to the following:
instance Weaken from to => Weaken (And x from) (And x to)
Since: 0.8.1.0
weakenOrLeft :: Weaken from to => Refined (And from x) a -> Refined (And to x) a Source #
This function helps type inference. It is equivalent to the following:
instance Weaken from to => Weaken (Or from x) (Or to x)
Since: 0.8.1.0
weakenOrRight :: Weaken from to => Refined (And x from) a -> Refined (And x to) a Source #
This function helps type inference. It is equivalent to the following:
instance Weaken from to => Weaken (Or x from) (Or x to)
Since: 0.8.1.0
Strengthening
strengthen :: forall p p' x. (Predicate p x, Predicate p' x) => Refined p x -> Either RefineException (Refined (p && p') x) Source #
Strengthen a refinement by composing it with another.
Since: 0.4.2.2
Error handling
RefineException
data RefineException Source #
An exception encoding the way in which a Predicate
failed.
Since: 0.2.0.0
Constructors
RefineNotException !TypeRep | A Since: 0.2.0.0 |
RefineAndException !TypeRep !(These RefineException RefineException) | A Since: 0.2.0.0 |
RefineOrException !TypeRep !RefineException !RefineException | A Since: 0.2.0.0 |
RefineXorException !TypeRep !(Maybe (RefineException, RefineException)) | A Since: 0.5 |
RefineSomeException !TypeRep !SomeException | A Since: 0.5 |
RefineOtherException !TypeRep !Text | A Since: 0.2.0.0 |
Instances
displayRefineException :: RefineException -> String Source #
Display a RefineException
as String
This function can be extremely useful for debugging
, especially deeply nested ones.RefineException
s
Consider:
myRefinement = refine @(And (Not (LessThan 5)) (Xor (DivisibleBy 10) (And (EqualTo 4) (EqualTo 3) ) ) ) @Int 3
This function will show the following tree structure, recursively breaking down every issue:
And (Not (LessThan 5)) (Xor (EqualTo 4) (And (EqualTo 4) (EqualTo 3))) ├── The predicate (Not (LessThan 5)) does not hold. └── Xor (DivisibleBy 10) (And (EqualTo 4) (EqualTo 3)) ├── The predicate (DivisibleBy 10) failed with the message: Value is not divisible by 10 └── And (EqualTo 4) (EqualTo 3) └── The predicate (EqualTo 4) failed with the message: Value does not equal 4
Note: Equivalent to show
@RefineException
Since: 0.2.0.0
validate
helpers
throwRefineOtherException Source #
Arguments
:: TypeRep | The |
-> Text | A |
-> Maybe RefineException |
A handler for a
.RefineException
throwRefineOtherException
is useful for defining what
behaviour validate
should have in the event of a predicate failure.
Typically the first argument passed to this function
will be the result of applying typeRep
to the first
argument of validate
.
Since: 0.2.0.0
throwRefineSomeException Source #
Arguments
:: TypeRep | The |
-> SomeException | A custom exception. |
-> Maybe RefineException |
A handler for a
.RefineException
throwRefineSomeException
is useful for defining what
behaviour validate
should have in the event of a predicate failure
with a specific exception.
Since: 0.5
Orphan instances
(Arbitrary a, Typeable a, Typeable p, Predicate p a) => Arbitrary (Refined p a) Source # | Since: 0.4 |
(FromJSON a, Predicate p a) => FromJSON (Refined p a) Source # | Since: 0.4 |
(FromJSONKey a, Predicate p a) => FromJSONKey (Refined p a) Source # | |
Methods fromJSONKey :: FromJSONKeyFunction (Refined p a) Source # fromJSONKeyList :: FromJSONKeyFunction [Refined p a] Source # | |
(ToJSON a, Predicate p a) => ToJSON (Refined p a) Source # | Since: 0.4 |
(ToJSONKey a, Predicate p a) => ToJSONKey (Refined p a) Source # | Since: 0.6.3 |
Methods toJSONKey :: ToJSONKeyFunction (Refined p a) Source # toJSONKeyList :: ToJSONKeyFunction [Refined p a] Source # | |
(Read x, Predicate p x) => Read (Refined p x) Source # | This instance makes sure to check the refinement. Since: 0.1.0.0 |