{-# LANGUAGE TypeFamilies #-}
{-# LANGUAGE PolyKinds #-}
{-# LANGUAGE FlexibleContexts #-}
{-# LANGUAGE FlexibleInstances #-}
{-# LANGUAGE MultiParamTypeClasses #-}
{-# LANGUAGE DataKinds #-}
module Propellor.PropAccum
( host
, Props(..)
, props
, (&)
, (&^)
, (!)
) where
import Propellor.Types
import Propellor.Types.MetaTypes
import Propellor.Types.Core
import Propellor.Property
import GHC.TypeLits
import Data.Monoid
import Prelude
host :: HostName -> Props metatypes -> Host
host hn (Props ps) = Host hn ps (mconcat (map getInfoRecursive ps))
props :: Props UnixLike
props = Props []
infixl 1 &
infixl 1 &^
infixl 1 !
type family GetMetaTypes x where
GetMetaTypes (Property (MetaTypes t)) = MetaTypes t
GetMetaTypes (RevertableProperty (MetaTypes t) undo) = MetaTypes t
type family NoteFor symbol :: ErrorMessage where
NoteFor symbol =
'Text "Probably the problem is with the last property added with "
':<>: symbol
':<>: 'Text " in the code excerpt below."
(&)
::
( IsProp p
, MetaTypes y ~ GetMetaTypes p
, CheckCombinableNote x y (NoteFor ('Text "&"))
)
=> Props (MetaTypes x)
-> p
-> Props (MetaTypes (Combine x y))
Props c & p = Props (c ++ [toChildProperty p])
(&^)
::
( IsProp p
, MetaTypes y ~ GetMetaTypes p
, CheckCombinableNote x y (NoteFor ('Text "&^"))
)
=> Props (MetaTypes x)
-> p
-> Props (MetaTypes (Combine x y))
Props c &^ p = Props (toChildProperty p : c)
(!)
:: CheckCombinableNote x z (NoteFor ('Text "!"))
=> Props (MetaTypes x)
-> RevertableProperty (MetaTypes y) (MetaTypes z)
-> Props (MetaTypes (Combine x z))
Props c ! p = Props (c ++ [toChildProperty (revert p)])