module Distribution.Make (
        module Distribution.Package,
        License(..), Version(..),
        defaultMain, defaultMainArgs, defaultMainNoRead
  ) where
import Distribution.Compat.Exception
import Distribution.Package 
import Distribution.Simple.Program(defaultProgramConfiguration)
import Distribution.PackageDescription
import Distribution.Simple.Setup
import Distribution.Simple.Command
import Distribution.Simple.Utils (rawSystemExit, cabalVersion)
import Distribution.License (License(..))
import Distribution.Version
         ( Version(..) )
import Distribution.Text
         ( display )
import System.Environment (getArgs, getProgName)
import Data.List  (intercalate)
import System.Exit
defaultMain :: IO ()
defaultMain = getArgs >>= defaultMainArgs
defaultMainArgs :: [String] -> IO ()
defaultMainArgs = defaultMainHelper
defaultMainNoRead :: PackageDescription -> IO ()
defaultMainNoRead = const defaultMain
defaultMainHelper :: [String] -> IO ()
defaultMainHelper args =
  case commandsRun globalCommand commands args of
    CommandHelp   help                 -> printHelp help
    CommandList   opts                 -> printOptionsList opts
    CommandErrors errs                 -> printErrors errs
    CommandReadyToGo (flags, commandParse)  ->
      case commandParse of
        _ | fromFlag (globalVersion flags)        -> printVersion
          | fromFlag (globalNumericVersion flags) -> printNumericVersion
        CommandHelp     help           -> printHelp help
        CommandList     opts           -> printOptionsList opts
        CommandErrors   errs           -> printErrors errs
        CommandReadyToGo action        -> action
  where
    printHelp help = getProgName >>= putStr . help
    printOptionsList = putStr . unlines
    printErrors errs = do
      putStr (intercalate "\n" errs)
      exitWith (ExitFailure 1)
    printNumericVersion = putStrLn $ display cabalVersion
    printVersion        = putStrLn $ "Cabal library version "
                                  ++ display cabalVersion
    progs = defaultProgramConfiguration
    commands =
      [configureCommand progs `commandAddAction` configureAction
      ,buildCommand     progs `commandAddAction` buildAction
      ,installCommand         `commandAddAction` installAction
      ,copyCommand            `commandAddAction` copyAction
      ,haddockCommand         `commandAddAction` haddockAction
      ,cleanCommand           `commandAddAction` cleanAction
      ,sdistCommand           `commandAddAction` sdistAction
      ,registerCommand        `commandAddAction` registerAction
      ,unregisterCommand      `commandAddAction` unregisterAction
      ]
configureAction :: ConfigFlags -> [String] -> IO ()
configureAction flags args = do
  noExtraFlags args
  let verbosity = fromFlag (configVerbosity flags)
  rawSystemExit verbosity "sh" $
    "configure"
    : configureArgs backwardsCompatHack flags
  where backwardsCompatHack = True
copyAction :: CopyFlags -> [String] -> IO ()
copyAction flags args = do
  noExtraFlags args
  let destArgs = case fromFlag $ copyDest flags of
        NoCopyDest      -> ["install"]
        CopyTo path     -> ["copy", "destdir=" ++ path]
  rawSystemExit (fromFlag $ copyVerbosity flags) "make" destArgs
installAction :: InstallFlags -> [String] -> IO ()
installAction flags args = do
  noExtraFlags args
  rawSystemExit (fromFlag $ installVerbosity flags) "make" ["install"]
  rawSystemExit (fromFlag $ installVerbosity flags) "make" ["register"]
haddockAction :: HaddockFlags -> [String] -> IO ()
haddockAction flags args = do
  noExtraFlags args
  rawSystemExit (fromFlag $ haddockVerbosity flags) "make" ["docs"]
    `catchIO` \_ ->
    rawSystemExit (fromFlag $ haddockVerbosity flags) "make" ["doc"]
buildAction :: BuildFlags -> [String] -> IO ()
buildAction flags args = do
  noExtraFlags args
  rawSystemExit (fromFlag $ buildVerbosity flags) "make" []
cleanAction :: CleanFlags -> [String] -> IO ()
cleanAction flags args = do
  noExtraFlags args
  rawSystemExit (fromFlag $ cleanVerbosity flags) "make" ["clean"]
sdistAction :: SDistFlags -> [String] -> IO ()
sdistAction flags args = do
  noExtraFlags args
  rawSystemExit (fromFlag $ sDistVerbosity flags) "make" ["dist"]
registerAction :: RegisterFlags -> [String] -> IO ()
registerAction  flags args = do
  noExtraFlags args
  rawSystemExit (fromFlag $ regVerbosity flags) "make" ["register"]
unregisterAction :: RegisterFlags -> [String] -> IO ()
unregisterAction flags args = do
  noExtraFlags args
  rawSystemExit (fromFlag $ regVerbosity flags) "make" ["unregister"]