{-# LANGUAGE DeriveGeneric #-} module Puppet.Language.NativeTypes.Package ( nativePackage, ) where import qualified Data.HashMap.Strict as HM import qualified Data.HashSet as Set import Puppet.Language.NativeTypes.Helpers nativePackage :: (NativeTypeName, NativeTypeMethods) nativePackage = ("package", nativetypemethods parameterfunctions (getFeature >=> checkFeatures)) -- Features are abilities that some providers may not support. data PackagingFeatures = Holdable | InstallOptions | Installable | Purgeable | UninstallOptions | Uninstallable | Upgradeable | Versionable deriving (Show, Eq, Generic) instance Pretty PackagingFeatures where pretty = ppline . show instance Hashable PackagingFeatures isFeatureSupported :: HashMap Text (HashSet PackagingFeatures) isFeatureSupported = HM.fromList [ ("aix", Set.fromList [Installable, Uninstallable, Upgradeable, Versionable]), ("appdmg", Set.fromList [Installable]), ("apple", Set.fromList [Installable]), ("apt", Set.fromList [Holdable, InstallOptions, Installable, Purgeable, Uninstallable, Upgradeable, Versionable]), ("aptitude", Set.fromList [Holdable, Installable, Purgeable, Uninstallable, Upgradeable, Versionable]), ("aptrpm", Set.fromList [Installable, Purgeable, Uninstallable, Upgradeable, Versionable]), ("blastwave", Set.fromList [Installable, Uninstallable, Upgradeable]), ("dpkg", Set.fromList [Holdable, Installable, Purgeable, Uninstallable, Upgradeable]), ("fink", Set.fromList [Holdable, Installable, Purgeable, Uninstallable, Upgradeable, Versionable]), ("freebsd", Set.fromList [Installable, Uninstallable]), ("gem", Set.fromList [Installable, Uninstallable, Upgradeable, Versionable]), ("hpux", Set.fromList [Installable, Uninstallable]), ("macports", Set.fromList [Installable, Uninstallable, Upgradeable, Versionable]), ("msi", Set.fromList [InstallOptions, Installable, UninstallOptions, Uninstallable]), ("nim", Set.fromList [Installable, Uninstallable, Upgradeable, Versionable]), ("openbsd", Set.fromList [Installable, Uninstallable, Versionable]), ("pacman", Set.fromList [Installable, Uninstallable, Upgradeable]), ("pip", Set.fromList [Installable, Uninstallable, Upgradeable, Versionable]), ("pkg", Set.fromList [Holdable, Installable, Uninstallable, Upgradeable, Versionable]), ("pkgdmg", Set.fromList [Installable]), ("pkgin", Set.fromList [Installable, Uninstallable]), ("pkgutil", Set.fromList [Installable, Uninstallable, Upgradeable]), ("portage", Set.fromList [Installable, Uninstallable, Upgradeable, Versionable]), ("ports", Set.fromList [Installable, Uninstallable, Upgradeable]), ("portupgrade", Set.fromList [Installable, Uninstallable, Upgradeable]), ("rpm", Set.fromList [Installable, Uninstallable, Upgradeable, Versionable]), ("rug", Set.fromList [Installable, Uninstallable, Upgradeable, Versionable]), ("sun", Set.fromList [InstallOptions, Installable, Uninstallable, Upgradeable]), ("sunfreeware", Set.fromList [Installable, Uninstallable, Upgradeable]), ("up2date", Set.fromList [Installable, Uninstallable, Upgradeable]), ("urpmi", Set.fromList [Installable, Uninstallable, Upgradeable, Versionable]), ("windows", Set.fromList [InstallOptions, Installable, UninstallOptions, Uninstallable]), ("yum", Set.fromList [Installable, Purgeable, Uninstallable, Upgradeable, Versionable]), ("zypper", Set.fromList [Installable, Uninstallable, Upgradeable, Versionable]) ] parameterfunctions :: [(Text, [Text -> NativeTypeValidate])] parameterfunctions = [ ("adminfile", [string, fullyQualified]), ("allowcdrom", [string, values ["true", "false"]]), ("configfiles", [string, values ["keep", "replace"]]), -- ,("ensure" , [defaultvalue "present", string, values ["present","absent","latest","held","purged","installed"]]) ("ensure", [defaultvalue "present", string]), ("flavor", []), ("install_options", [rarray]), ("name", [nameval]), ("provider", [defaultvalue "apt", string]), ("responsefile", [string, fullyQualified]), ("source", [string]), ("uninstall_options", [rarray]) ] getFeature :: Resource -> Either PrettyError (HashSet PackagingFeatures, Resource) getFeature res = case res ^. rattributes . at "provider" of Just (PString x) -> case HM.lookup x isFeatureSupported of Just s -> Right (s, res) Nothing -> Left $ PrettyError ("Do not know provider" <+> ppline x) _ -> Left "Can't happen at Puppet.NativeTypes.Package" checkFeatures :: (HashSet PackagingFeatures, Resource) -> Either PrettyError Resource checkFeatures = checkAdminFile >=> checkEnsure >=> checkParam "install_options" InstallOptions >=> checkParam "uninstall_options" UninstallOptions >=> decap where checkFeature :: HashSet PackagingFeatures -> Resource -> PackagingFeatures -> Either PrettyError (HashSet PackagingFeatures, Resource) checkFeature s r f = if Set.member f s then Right (s, r) else Left $ PrettyError ("Feature" <+> pretty f <+> "is required for the current configuration") checkParam :: Text -> PackagingFeatures -> (HashSet PackagingFeatures, Resource) -> Either PrettyError (HashSet PackagingFeatures, Resource) checkParam pn f (s, r) = if has (ix pn) (r ^. rattributes) then checkFeature s r f else Right (s, r) checkAdminFile :: (HashSet PackagingFeatures, Resource) -> Either PrettyError (HashSet PackagingFeatures, Resource) checkAdminFile = Right -- TODO, check that it only works for aix checkEnsure :: (HashSet PackagingFeatures, Resource) -> Either PrettyError (HashSet PackagingFeatures, Resource) checkEnsure (s, res) = case res ^. rattributes . at "ensure" of Just (PString "latest") -> checkFeature s res Installable Just (PString "purged") -> checkFeature s res Purgeable Just (PString "absent") -> checkFeature s res Uninstallable Just (PString "installed") -> checkFeature s res Installable Just (PString "present") -> checkFeature s res Installable Just (PString "held") -> checkFeature s res Installable >> checkFeature s res Holdable _ -> checkFeature s res Versionable decap :: (HashSet PackagingFeatures, Resource) -> Either PrettyError Resource decap = Right . snd