-- | This module provides linear prisms. -- -- A @Prism s t a b@ is equivalent to @(s \#-> Either a t, b \#-> t)@ for some -- /sum type/ @s@. In the non-polymorphic version, this is a @(s \#-> Either a -- s, a \#-> s)@ which represents taking one case of a sum type and a way to -- build the sum-type given that one case. A prism is a traversal focusing on -- one branch or case that a sum type could be. -- -- = Example -- -- @ -- {-# LANGUAGE LinearTypes #-} -- {-# LANGUAGE LambdaCase #-} -- {-# LANGUAGE FlexibleContexts #-} -- {-# LANGUAGE NoImplicitPrelude #-} -- {-# LANGUAGE GADTs #-} -- -- import Control.Optics.Linear.Internal -- import Prelude.Linear -- import qualified Data.Functor.Linear as Data -- -- -- We can use a prism to do operations on one branch of a sum-type -- -- (This is a bit of a toy example since we could use @over@ for this.) -- formatLicenceName :: PersonId %1-> PersonId -- formatLicenceName personId = -- Data.fmap modLisc (match pIdLiscPrism personId) & \case -- Left personId' -> personId' -- Right lisc -> build pIdLiscPrism lisc -- where -- modLisc :: Licence %1-> Licence -- modLisc (Licence nm x) = Licence (nm ++ "\n") x -- -- data PersonId where -- IdLicence :: Licence %1-> PersonId -- SSN :: Int %1-> PersonId -- BirthCertif :: String %1-> PersonId -- -- And there could be many more constructors ... -- -- -- A Licence is a name and number -- data Licence = Licence String Int -- -- pIdLiscPrism :: Prism' PersonId Licence -- pIdLiscPrism = prism IdLicence decompose where -- decompose :: PersonId %1-> Either PersonId Licence -- decompose (IdLicence l) = Right l -- decompose x = Left x -- @ -- module Control.Optics.Linear.Prism ( -- * Types Prism, Prism' -- * Composing optics , (.>) -- * Common optics , _Left, _Right , _Just, _Nothing -- * Using optics , match, build , withPrism -- * Constructing optics , prism ) where import Control.Optics.Linear.Internal