{-# LANGUAGE LambdaCase #-}

module Cardano.CLI.Types.Errors.GovernanceActionsError
  ( GovernanceActionsError (..)
  , AnchorDataTypeCheck (..)
  )
where

import           Cardano.Api
import qualified Cardano.Api.Ledger as L

import           Cardano.CLI.Read
import           Cardano.CLI.Types.Errors.HashCmdError (FetchURLError)
import           Cardano.CLI.Types.Errors.StakeCredentialError

import           Control.Exception (displayException)

data GovernanceActionsError
  = GovernanceActionsCmdConstitutionError ConstitutionError
  | GovernanceActionsCmdProposalError ProposalError
  | GovernanceActionsCmdCostModelsError CostModelsError
  | GovernanceActionsCmdReadFileError (FileError InputDecodeError)
  | GovernanceActionsReadStakeCredErrror StakeCredentialError
  | GovernanceActionsCmdReadTextEnvelopeFileError (FileError TextEnvelopeError)
  | GovernanceActionsCmdWriteFileError (FileError ())
  | GovernanceActionsValueUpdateProtocolParametersNotFound AnyShelleyBasedEra
  | GovernanceActionsMismatchedHashError
      AnchorDataTypeCheck
      -- ^ Type of anchor data that we were checking
      !(L.SafeHash L.StandardCrypto L.AnchorData)
      -- ^ Expected hash
      !(L.SafeHash L.StandardCrypto L.AnchorData)
      -- ^ Actual hash
  | GovernanceActionsProposalFetchURLError
      AnchorDataTypeCheck
      -- ^ Type of anchor data that we were checking
      FetchURLError
      -- ^ Error that occurred while fetching the anchor data
  deriving Int -> GovernanceActionsError -> ShowS
[GovernanceActionsError] -> ShowS
GovernanceActionsError -> String
(Int -> GovernanceActionsError -> ShowS)
-> (GovernanceActionsError -> String)
-> ([GovernanceActionsError] -> ShowS)
-> Show GovernanceActionsError
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> GovernanceActionsError -> ShowS
showsPrec :: Int -> GovernanceActionsError -> ShowS
$cshow :: GovernanceActionsError -> String
show :: GovernanceActionsError -> String
$cshowList :: [GovernanceActionsError] -> ShowS
showList :: [GovernanceActionsError] -> ShowS
Show

instance Error GovernanceActionsError where
  prettyError :: forall ann. GovernanceActionsError -> Doc ann
prettyError = \case
    GovernanceActionsCmdCostModelsError CostModelsError
e ->
      CostModelsError -> Doc ann
forall e ann. Error e => e -> Doc ann
forall ann. CostModelsError -> Doc ann
prettyError CostModelsError
e
    GovernanceActionsCmdProposalError ProposalError
e ->
      Doc ann
"Cannot read proposal: " Doc ann -> Doc ann -> Doc ann
forall a. Semigroup a => a -> a -> a
<> ProposalError -> Doc ann
forall a ann. Show a => a -> Doc ann
pshow ProposalError
e -- TODO Conway render this properly
    GovernanceActionsCmdConstitutionError ConstitutionError
e ->
      Doc ann
"Cannot read constitution: " Doc ann -> Doc ann -> Doc ann
forall a. Semigroup a => a -> a -> a
<> ConstitutionError -> Doc ann
forall a ann. Show a => a -> Doc ann
pshow ConstitutionError
e -- TODO Conway render this properly
    GovernanceActionsCmdReadFileError FileError InputDecodeError
e ->
      Doc ann
"Cannot read file: " Doc ann -> Doc ann -> Doc ann
forall a. Semigroup a => a -> a -> a
<> FileError InputDecodeError -> Doc ann
forall e ann. Error e => e -> Doc ann
forall ann. FileError InputDecodeError -> Doc ann
prettyError FileError InputDecodeError
e
    GovernanceActionsCmdReadTextEnvelopeFileError FileError TextEnvelopeError
e ->
      Doc ann
"Cannot read text envelope file: " Doc ann -> Doc ann -> Doc ann
forall a. Semigroup a => a -> a -> a
<> FileError TextEnvelopeError -> Doc ann
forall e ann. Error e => e -> Doc ann
forall ann. FileError TextEnvelopeError -> Doc ann
prettyError FileError TextEnvelopeError
e
    GovernanceActionsCmdWriteFileError FileError ()
e ->
      Doc ann
"Cannot write file: " Doc ann -> Doc ann -> Doc ann
forall a. Semigroup a => a -> a -> a
<> FileError () -> Doc ann
forall e ann. Error e => e -> Doc ann
forall ann. FileError () -> Doc ann
prettyError FileError ()
e
    GovernanceActionsValueUpdateProtocolParametersNotFound (AnyShelleyBasedEra ShelleyBasedEra era
expectedShelleyEra) ->
      Doc ann
"Protocol parameters update value for" Doc ann -> Doc ann -> Doc ann
forall ann. Doc ann -> Doc ann -> Doc ann
<+> ShelleyBasedEra era -> Doc ann
forall a ann. Pretty a => a -> Doc ann
forall ann. ShelleyBasedEra era -> Doc ann
pretty ShelleyBasedEra era
expectedShelleyEra Doc ann -> Doc ann -> Doc ann
forall ann. Doc ann -> Doc ann -> Doc ann
<+> Doc ann
"was not found."
    GovernanceActionsReadStakeCredErrror StakeCredentialError
e ->
      StakeCredentialError -> Doc ann
forall e ann. Error e => e -> Doc ann
forall ann. StakeCredentialError -> Doc ann
prettyError StakeCredentialError
e
    GovernanceActionsMismatchedHashError AnchorDataTypeCheck
adt SafeHash StandardCrypto AnchorData
expectedHash SafeHash StandardCrypto AnchorData
actualHash ->
      Doc ann
"Hashes do not match while checking"
        Doc ann -> Doc ann -> Doc ann
forall ann. Doc ann -> Doc ann -> Doc ann
<+> String -> Doc ann
forall ann. String -> Doc ann
forall a ann. Pretty a => a -> Doc ann
pretty (AnchorDataTypeCheck -> String
anchorDataTypeCheckName AnchorDataTypeCheck
adt)
        Doc ann -> Doc ann -> Doc ann
forall ann. Doc ann -> Doc ann -> Doc ann
<+> Doc ann
"hashes!"
        Doc ann -> Doc ann -> Doc ann
forall a. Semigroup a => a -> a -> a
<> Doc ann
"\nExpected:"
          Doc ann -> Doc ann -> Doc ann
forall ann. Doc ann -> Doc ann -> Doc ann
<+> String -> Doc ann
forall ann. String -> Doc ann
forall a ann. Pretty a => a -> Doc ann
pretty (Hash Blake2b_256 AnchorData -> String
forall a. Show a => a -> String
show (SafeHash StandardCrypto AnchorData
-> Hash (HASH StandardCrypto) AnchorData
forall c i. SafeHash c i -> Hash (HASH c) i
L.extractHash SafeHash StandardCrypto AnchorData
expectedHash))
        Doc ann -> Doc ann -> Doc ann
forall a. Semigroup a => a -> a -> a
<> Doc ann
"\n  Actual:"
          Doc ann -> Doc ann -> Doc ann
forall ann. Doc ann -> Doc ann -> Doc ann
<+> String -> Doc ann
forall ann. String -> Doc ann
forall a ann. Pretty a => a -> Doc ann
pretty (Hash Blake2b_256 AnchorData -> String
forall a. Show a => a -> String
show (SafeHash StandardCrypto AnchorData
-> Hash (HASH StandardCrypto) AnchorData
forall c i. SafeHash c i -> Hash (HASH c) i
L.extractHash SafeHash StandardCrypto AnchorData
actualHash))
    GovernanceActionsProposalFetchURLError AnchorDataTypeCheck
adt FetchURLError
fetchErr ->
      Doc ann
"Error while checking"
        Doc ann -> Doc ann -> Doc ann
forall ann. Doc ann -> Doc ann -> Doc ann
<+> String -> Doc ann
forall ann. String -> Doc ann
forall a ann. Pretty a => a -> Doc ann
pretty (AnchorDataTypeCheck -> String
anchorDataTypeCheckName AnchorDataTypeCheck
adt)
        Doc ann -> Doc ann -> Doc ann
forall ann. Doc ann -> Doc ann -> Doc ann
<+> Doc ann
"hash:"
        Doc ann -> Doc ann -> Doc ann
forall ann. Doc ann -> Doc ann -> Doc ann
<+> String -> Doc ann
forall ann. String -> Doc ann
forall a ann. Pretty a => a -> Doc ann
pretty (FetchURLError -> String
forall e. Exception e => e -> String
displayException FetchURLError
fetchErr)

data AnchorDataTypeCheck
  = ProposalCheck
  | ConstitutionCheck
  deriving Int -> AnchorDataTypeCheck -> ShowS
[AnchorDataTypeCheck] -> ShowS
AnchorDataTypeCheck -> String
(Int -> AnchorDataTypeCheck -> ShowS)
-> (AnchorDataTypeCheck -> String)
-> ([AnchorDataTypeCheck] -> ShowS)
-> Show AnchorDataTypeCheck
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> AnchorDataTypeCheck -> ShowS
showsPrec :: Int -> AnchorDataTypeCheck -> ShowS
$cshow :: AnchorDataTypeCheck -> String
show :: AnchorDataTypeCheck -> String
$cshowList :: [AnchorDataTypeCheck] -> ShowS
showList :: [AnchorDataTypeCheck] -> ShowS
Show

anchorDataTypeCheckName :: AnchorDataTypeCheck -> String
anchorDataTypeCheckName :: AnchorDataTypeCheck -> String
anchorDataTypeCheckName AnchorDataTypeCheck
ProposalCheck = String
"proposal"
anchorDataTypeCheckName AnchorDataTypeCheck
ConstitutionCheck = String
"constitution"