-- | This module provides linear prisms. -- -- A @Prism s t a b@ is equivalent to @(s %1-> Either a t, b %1-> t)@ for some -- /sum type/ @s@. In the non-polymorphic version, this is a @(s %1-> Either a -- s, a %1-> 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