{-# LANGUAGE DuplicateRecordFields #-} {-# LANGUAGE OverloadedStrings #-} {-# LANGUAGE TemplateHaskell #-} module Horizon.Gen.Nix.Options ( horizonGenNixOpts , horizonGenNixOptsInfo , InputFile (..) , HorizonCommand (..) , HorizonOptions (..) , MakePackageSetOptions (..) , OverlayOptions (..) , defaultMakePackageSetOptions , defaultPackagesDirectory , defaultPackageSetFile , defaultOverlayFile , defaultOverlayOptions , ) where import Data.Either.Combinators (mapLeft) import Data.Kind (Type) import Horizon.Gen.Nix.Types.OverlayFile (OverlayFile (MkOverlayFile)) import Horizon.Gen.Nix.Types.PackagesDirectory (PackagesDirectory (MkPackagesDirectory)) import Horizon.Gen.Nix.Types.PackageSetFile (PackageSetFile (MkPackageSetFile)) import Options.Applicative (Parser, ParserInfo, ReadM, command, eitherReader, help, helper, info, long, metavar, option, progDesc, subparser, value) import Path (File, Path, Rel, mkRelDir, mkRelFile, parseRelDir, parseRelFile) import Path.Dhall () parsePackagesDirectory :: ReadM PackagesDirectory parsePackagesDirectory = eitherReader $ mapLeft show . fmap MkPackagesDirectory . parseRelDir defaultPackagesDirectory :: PackagesDirectory defaultPackagesDirectory = MkPackagesDirectory $(mkRelDir "pkgs") packagesDirectoryOption :: Parser PackagesDirectory packagesDirectoryOption = option parsePackagesDirectory ( long "packages-dir" <> metavar "PACKAGES_DIR" <> value defaultPackagesDirectory <> help "The directory to put haskell packages." ) parsePackageSetFile :: ReadM PackageSetFile parsePackageSetFile = eitherReader $ mapLeft show . fmap MkPackageSetFile . parseRelFile defaultPackageSetFile :: PackageSetFile defaultPackageSetFile = MkPackageSetFile $(mkRelFile "initial-packages.nix") packageSetFileOption :: Parser PackageSetFile packageSetFileOption = option parsePackageSetFile ( long "packageset-file" <> metavar "PACKAGESET_FILE" <> value defaultPackageSetFile <> help "The name of the package set file" ) parseOverlayFile :: ReadM OverlayFile parseOverlayFile = eitherReader $ mapLeft show . fmap MkOverlayFile . parseRelFile defaultOverlayFile :: OverlayFile defaultOverlayFile = MkOverlayFile $(mkRelFile "overlay.nix") overlayFileOption :: Parser OverlayFile overlayFileOption = option parseOverlayFile ( long "overlay-file" <> metavar "OVERLAY_FILE" <> value defaultOverlayFile <> help "The name of the overlay file." ) type InputFile :: Type newtype InputFile where MkInputFile :: { fromInputFile :: Path Rel File } -> InputFile deriving stock (Eq, Show) parseInputFile :: ReadM InputFile parseInputFile = eitherReader $ mapLeft show . fmap MkInputFile . parseRelFile defaultInputFile :: InputFile defaultInputFile = MkInputFile $(mkRelFile "horizon.dhall") inputFileOption :: Parser InputFile inputFileOption = option parseInputFile ( long "input-file" <> metavar "INPUT_FILE" <> value defaultInputFile <> help "The name of the input file." ) type MakePackageSetOptions :: Type data MakePackageSetOptions where MkMakePackageSetOptions :: { optPackageSetFile :: PackageSetFile } -> MakePackageSetOptions deriving stock (Eq, Show) makePackageSetOptions :: Parser MakePackageSetOptions makePackageSetOptions = MkMakePackageSetOptions <$> packageSetFileOption defaultMakePackageSetOptions :: MakePackageSetOptions defaultMakePackageSetOptions = MkMakePackageSetOptions defaultPackageSetFile type OverlayOptions :: Type data OverlayOptions where MkOverlayOptions :: { optOverlayFile :: OverlayFile} -> OverlayOptions deriving stock (Eq, Show) overlayOptions :: Parser OverlayOptions overlayOptions = MkOverlayOptions <$> overlayFileOption defaultOverlayOptions :: OverlayOptions defaultOverlayOptions = MkOverlayOptions defaultOverlayFile type HorizonCommand :: Type data HorizonCommand where MakePackageSetCommand :: MakePackageSetOptions -> HorizonCommand OverlayCommand :: OverlayOptions -> HorizonCommand deriving stock (Eq, Show) type HorizonOptions :: Type data HorizonOptions where MkHorizonOptions :: { optInputFile :: InputFile , optPackagesDirectory :: PackagesDirectory , optHorizonCommand :: HorizonCommand} -> HorizonOptions deriving stock (Eq, Show) makePackageSetCommand :: Parser HorizonCommand makePackageSetCommand = fmap MakePackageSetCommand makePackageSetOptions overlayCommand :: Parser HorizonCommand overlayCommand = fmap OverlayCommand overlayOptions horizonCommandOpts :: Parser HorizonCommand horizonCommandOpts = subparser ( command "make-package-set" (info (helper <*> makePackageSetCommand) ( progDesc "Run in MakePackageSet Mode" )) <> command "overlay" (info (helper <*> overlayCommand) ( progDesc "Run in Overlay Mode" )) ) horizonGenNixOpts :: Parser HorizonOptions horizonGenNixOpts = MkHorizonOptions <$> inputFileOption <*> packagesDirectoryOption <*> horizonCommandOpts horizonGenNixOptsInfo :: ParserInfo HorizonOptions horizonGenNixOptsInfo = info (helper <*> horizonGenNixOpts) mempty