dhall-1.13.0: dhall-hash/Main.hs
{-# LANGUAGE OverloadedStrings #-}
{-# LANGUAGE RecordWildCards #-}
module Main where
import Control.Exception (SomeException)
import Control.Monad (when)
import Data.Monoid ((<>))
import Data.Version (showVersion)
import Dhall.Core (normalize)
import Dhall.Import (Imported(..), hashExpressionToCode, load)
import Dhall.Parser (Src, exprFromText)
import Dhall.TypeCheck (DetailedTypeError(..), TypeError, X)
import Options.Applicative (Parser, ParserInfo)
import System.IO (stderr)
import System.Exit (exitFailure, exitSuccess)
import qualified Paths_dhall as Meta
import qualified Control.Exception
import qualified Data.Text.Lazy.IO
import qualified Dhall.TypeCheck
import qualified Options.Applicative
import qualified System.IO
data Options = Options
{ explain :: Bool
, version :: Bool
}
parseOptions :: Parser Options
parseOptions = Options <$> parseExplain <*> parseVersion
where
parseExplain =
Options.Applicative.switch
( Options.Applicative.long "explain"
<> Options.Applicative.help "Explain error messages in more detail"
)
parseVersion =
Options.Applicative.switch
( Options.Applicative.long "version"
<> Options.Applicative.help "Display version and exit"
)
parserInfo :: ParserInfo Options
parserInfo =
Options.Applicative.info
(Options.Applicative.helper <*> parseOptions)
( Options.Applicative.progDesc "Compute semantic hashes for Dhall expressions"
<> Options.Applicative.fullDesc
)
main :: IO ()
main = do
Options {..} <- Options.Applicative.execParser parserInfo
when version $ do
putStrLn (showVersion Meta.version)
exitSuccess
let handle =
Control.Exception.handle handler2
. Control.Exception.handle handler1
. Control.Exception.handle handler0
where
handler0 e = do
let _ = e :: TypeError Src X
System.IO.hPutStrLn stderr ""
if explain
then Control.Exception.throwIO (DetailedTypeError e)
else do
Data.Text.Lazy.IO.hPutStrLn stderr "\ESC[2mUse \"dhall --explain\" for detailed errors\ESC[0m"
Control.Exception.throwIO e
handler1 (Imported ps e) = do
let _ = e :: TypeError Src X
System.IO.hPutStrLn stderr ""
if explain
then Control.Exception.throwIO (Imported ps (DetailedTypeError e))
else do
Data.Text.Lazy.IO.hPutStrLn stderr "\ESC[2mUse \"dhall --explain\" for detailed errors\ESC[0m"
Control.Exception.throwIO (Imported ps e)
handler2 e = do
let _ = e :: SomeException
System.IO.hSetEncoding System.IO.stderr System.IO.utf8
System.IO.hPrint stderr e
System.Exit.exitFailure
handle (do
System.IO.hSetEncoding System.IO.stdin System.IO.utf8
inText <- Data.Text.Lazy.IO.getContents
expr <- case exprFromText "(stdin)" inText of
Left err -> Control.Exception.throwIO err
Right expr -> return expr
expr' <- load expr
_ <- case Dhall.TypeCheck.typeOf expr' of
Left err -> Control.Exception.throwIO err
Right _ -> return ()
Data.Text.Lazy.IO.putStrLn (hashExpressionToCode (normalize expr')) )