{-# LANGUAGE GADTs #-}
{-# LANGUAGE LambdaCase #-}

{-
This module is concerned with providing backwards compatible cli commands for our internal
testing needs. The intention is to restrict as much as possible which functionality we maintain backwards
compatibility for.
-}

module Cardano.CLI.Compatible.Commands
  ( AnyCompatibleCommand (..)
  , CompatibleCommand (..)
  , pAnyCompatibleCommand
  , renderAnyCompatibleCommand
  )
where

import           Cardano.Api

import           Cardano.CLI.Compatible.Governance
import           Cardano.CLI.Compatible.Transaction
import           Cardano.CLI.Environment
import           Cardano.CLI.Parser

import           Data.Foldable
import           Data.Text
import           Options.Applicative
import qualified Options.Applicative as Opt

data AnyCompatibleCommand where
  AnyCompatibleCommand :: CompatibleCommand era -> AnyCompatibleCommand

renderAnyCompatibleCommand :: AnyCompatibleCommand -> Text
renderAnyCompatibleCommand :: AnyCompatibleCommand -> Text
renderAnyCompatibleCommand = \case
  AnyCompatibleCommand CompatibleCommand era
cmd -> CompatibleCommand era -> Text
forall era. CompatibleCommand era -> Text
renderCompatibleCommand CompatibleCommand era
cmd

data CompatibleCommand era
  = CompatibleTransactionCmd (CompatibleTransactionCmds era)
  | CompatibleGovernanceCmds (CompatibleGovernanceCmds era)

renderCompatibleCommand :: CompatibleCommand era -> Text
renderCompatibleCommand :: forall era. CompatibleCommand era -> Text
renderCompatibleCommand = \case
  CompatibleTransactionCmd CompatibleTransactionCmds era
cmd -> CompatibleTransactionCmds era -> Text
forall era. CompatibleTransactionCmds era -> Text
renderCompatibleTransactionCmd CompatibleTransactionCmds era
cmd
  CompatibleGovernanceCmds CompatibleGovernanceCmds era
cmd -> CompatibleGovernanceCmds era -> Text
forall era. CompatibleGovernanceCmds era -> Text
renderCompatibleGovernanceCmds CompatibleGovernanceCmds era
cmd

pAnyCompatibleCommand :: EnvCli -> Parser AnyCompatibleCommand
pAnyCompatibleCommand :: EnvCli -> Parser AnyCompatibleCommand
pAnyCompatibleCommand EnvCli
envCli =
  [Parser AnyCompatibleCommand] -> Parser AnyCompatibleCommand
forall (t :: * -> *) (f :: * -> *) a.
(Foldable t, Alternative f) =>
t (f a) -> f a
asum
    [ -- Note, byron is ommitted because there is already a legacy command group for it.
      String
-> ParserInfo AnyCompatibleCommand -> Parser AnyCompatibleCommand
forall a. String -> ParserInfo a -> Parser a
subParser String
"shelley" (ParserInfo AnyCompatibleCommand -> Parser AnyCompatibleCommand)
-> ParserInfo AnyCompatibleCommand -> Parser AnyCompatibleCommand
forall a b. (a -> b) -> a -> b
$
        Parser AnyCompatibleCommand
-> InfoMod AnyCompatibleCommand -> ParserInfo AnyCompatibleCommand
forall a. Parser a -> InfoMod a -> ParserInfo a
Opt.info (CompatibleCommand ShelleyEra -> AnyCompatibleCommand
forall era. CompatibleCommand era -> AnyCompatibleCommand
AnyCompatibleCommand (CompatibleCommand ShelleyEra -> AnyCompatibleCommand)
-> Parser (CompatibleCommand ShelleyEra)
-> Parser AnyCompatibleCommand
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> ShelleyBasedEra ShelleyEra
-> EnvCli -> Parser (CompatibleCommand ShelleyEra)
forall era.
ShelleyBasedEra era -> EnvCli -> Parser (CompatibleCommand era)
pCompatibleCommand ShelleyBasedEra ShelleyEra
ShelleyBasedEraShelley EnvCli
envCli) (InfoMod AnyCompatibleCommand -> ParserInfo AnyCompatibleCommand)
-> InfoMod AnyCompatibleCommand -> ParserInfo AnyCompatibleCommand
forall a b. (a -> b) -> a -> b
$
          String -> InfoMod AnyCompatibleCommand
forall a. String -> InfoMod a
Opt.progDesc String
"Shelley era commands"
    , String
-> ParserInfo AnyCompatibleCommand -> Parser AnyCompatibleCommand
forall a. String -> ParserInfo a -> Parser a
subParser String
"allegra" (ParserInfo AnyCompatibleCommand -> Parser AnyCompatibleCommand)
-> ParserInfo AnyCompatibleCommand -> Parser AnyCompatibleCommand
forall a b. (a -> b) -> a -> b
$
        Parser AnyCompatibleCommand
-> InfoMod AnyCompatibleCommand -> ParserInfo AnyCompatibleCommand
forall a. Parser a -> InfoMod a -> ParserInfo a
Opt.info (CompatibleCommand AllegraEra -> AnyCompatibleCommand
forall era. CompatibleCommand era -> AnyCompatibleCommand
AnyCompatibleCommand (CompatibleCommand AllegraEra -> AnyCompatibleCommand)
-> Parser (CompatibleCommand AllegraEra)
-> Parser AnyCompatibleCommand
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> ShelleyBasedEra AllegraEra
-> EnvCli -> Parser (CompatibleCommand AllegraEra)
forall era.
ShelleyBasedEra era -> EnvCli -> Parser (CompatibleCommand era)
pCompatibleCommand ShelleyBasedEra AllegraEra
ShelleyBasedEraAllegra EnvCli
envCli) (InfoMod AnyCompatibleCommand -> ParserInfo AnyCompatibleCommand)
-> InfoMod AnyCompatibleCommand -> ParserInfo AnyCompatibleCommand
forall a b. (a -> b) -> a -> b
$
          String -> InfoMod AnyCompatibleCommand
forall a. String -> InfoMod a
Opt.progDesc String
"Allegra era commands"
    , String
-> ParserInfo AnyCompatibleCommand -> Parser AnyCompatibleCommand
forall a. String -> ParserInfo a -> Parser a
subParser String
"mary" (ParserInfo AnyCompatibleCommand -> Parser AnyCompatibleCommand)
-> ParserInfo AnyCompatibleCommand -> Parser AnyCompatibleCommand
forall a b. (a -> b) -> a -> b
$
        Parser AnyCompatibleCommand
-> InfoMod AnyCompatibleCommand -> ParserInfo AnyCompatibleCommand
forall a. Parser a -> InfoMod a -> ParserInfo a
Opt.info (CompatibleCommand MaryEra -> AnyCompatibleCommand
forall era. CompatibleCommand era -> AnyCompatibleCommand
AnyCompatibleCommand (CompatibleCommand MaryEra -> AnyCompatibleCommand)
-> Parser (CompatibleCommand MaryEra)
-> Parser AnyCompatibleCommand
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> ShelleyBasedEra MaryEra
-> EnvCli -> Parser (CompatibleCommand MaryEra)
forall era.
ShelleyBasedEra era -> EnvCli -> Parser (CompatibleCommand era)
pCompatibleCommand ShelleyBasedEra MaryEra
ShelleyBasedEraMary EnvCli
envCli) (InfoMod AnyCompatibleCommand -> ParserInfo AnyCompatibleCommand)
-> InfoMod AnyCompatibleCommand -> ParserInfo AnyCompatibleCommand
forall a b. (a -> b) -> a -> b
$
          String -> InfoMod AnyCompatibleCommand
forall a. String -> InfoMod a
Opt.progDesc String
"Mary era commands"
    , String
-> ParserInfo AnyCompatibleCommand -> Parser AnyCompatibleCommand
forall a. String -> ParserInfo a -> Parser a
subParser String
"alonzo" (ParserInfo AnyCompatibleCommand -> Parser AnyCompatibleCommand)
-> ParserInfo AnyCompatibleCommand -> Parser AnyCompatibleCommand
forall a b. (a -> b) -> a -> b
$
        Parser AnyCompatibleCommand
-> InfoMod AnyCompatibleCommand -> ParserInfo AnyCompatibleCommand
forall a. Parser a -> InfoMod a -> ParserInfo a
Opt.info (CompatibleCommand AlonzoEra -> AnyCompatibleCommand
forall era. CompatibleCommand era -> AnyCompatibleCommand
AnyCompatibleCommand (CompatibleCommand AlonzoEra -> AnyCompatibleCommand)
-> Parser (CompatibleCommand AlonzoEra)
-> Parser AnyCompatibleCommand
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> ShelleyBasedEra AlonzoEra
-> EnvCli -> Parser (CompatibleCommand AlonzoEra)
forall era.
ShelleyBasedEra era -> EnvCli -> Parser (CompatibleCommand era)
pCompatibleCommand ShelleyBasedEra AlonzoEra
ShelleyBasedEraAlonzo EnvCli
envCli) (InfoMod AnyCompatibleCommand -> ParserInfo AnyCompatibleCommand)
-> InfoMod AnyCompatibleCommand -> ParserInfo AnyCompatibleCommand
forall a b. (a -> b) -> a -> b
$
          String -> InfoMod AnyCompatibleCommand
forall a. String -> InfoMod a
Opt.progDesc String
"Alonzo era commands"
    , String
-> ParserInfo AnyCompatibleCommand -> Parser AnyCompatibleCommand
forall a. String -> ParserInfo a -> Parser a
subParser String
"babbage" (ParserInfo AnyCompatibleCommand -> Parser AnyCompatibleCommand)
-> ParserInfo AnyCompatibleCommand -> Parser AnyCompatibleCommand
forall a b. (a -> b) -> a -> b
$
        Parser AnyCompatibleCommand
-> InfoMod AnyCompatibleCommand -> ParserInfo AnyCompatibleCommand
forall a. Parser a -> InfoMod a -> ParserInfo a
Opt.info (CompatibleCommand BabbageEra -> AnyCompatibleCommand
forall era. CompatibleCommand era -> AnyCompatibleCommand
AnyCompatibleCommand (CompatibleCommand BabbageEra -> AnyCompatibleCommand)
-> Parser (CompatibleCommand BabbageEra)
-> Parser AnyCompatibleCommand
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> ShelleyBasedEra BabbageEra
-> EnvCli -> Parser (CompatibleCommand BabbageEra)
forall era.
ShelleyBasedEra era -> EnvCli -> Parser (CompatibleCommand era)
pCompatibleCommand ShelleyBasedEra BabbageEra
ShelleyBasedEraBabbage EnvCli
envCli) (InfoMod AnyCompatibleCommand -> ParserInfo AnyCompatibleCommand)
-> InfoMod AnyCompatibleCommand -> ParserInfo AnyCompatibleCommand
forall a b. (a -> b) -> a -> b
$
          String -> InfoMod AnyCompatibleCommand
forall a. String -> InfoMod a
Opt.progDesc String
"Babbage era commands"
    , String
-> ParserInfo AnyCompatibleCommand -> Parser AnyCompatibleCommand
forall a. String -> ParserInfo a -> Parser a
subParser String
"conway" (ParserInfo AnyCompatibleCommand -> Parser AnyCompatibleCommand)
-> ParserInfo AnyCompatibleCommand -> Parser AnyCompatibleCommand
forall a b. (a -> b) -> a -> b
$
        Parser AnyCompatibleCommand
-> InfoMod AnyCompatibleCommand -> ParserInfo AnyCompatibleCommand
forall a. Parser a -> InfoMod a -> ParserInfo a
Opt.info (CompatibleCommand ConwayEra -> AnyCompatibleCommand
forall era. CompatibleCommand era -> AnyCompatibleCommand
AnyCompatibleCommand (CompatibleCommand ConwayEra -> AnyCompatibleCommand)
-> Parser (CompatibleCommand ConwayEra)
-> Parser AnyCompatibleCommand
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> ShelleyBasedEra ConwayEra
-> EnvCli -> Parser (CompatibleCommand ConwayEra)
forall era.
ShelleyBasedEra era -> EnvCli -> Parser (CompatibleCommand era)
pCompatibleCommand ShelleyBasedEra ConwayEra
ShelleyBasedEraConway EnvCli
envCli) (InfoMod AnyCompatibleCommand -> ParserInfo AnyCompatibleCommand)
-> InfoMod AnyCompatibleCommand -> ParserInfo AnyCompatibleCommand
forall a b. (a -> b) -> a -> b
$
          String -> InfoMod AnyCompatibleCommand
forall a. String -> InfoMod a
Opt.progDesc String
"Conway era commands"
    ]

pCompatibleCommand :: ShelleyBasedEra era -> EnvCli -> Parser (CompatibleCommand era)
pCompatibleCommand :: forall era.
ShelleyBasedEra era -> EnvCli -> Parser (CompatibleCommand era)
pCompatibleCommand ShelleyBasedEra era
era EnvCli
env =
  [Parser (CompatibleCommand era)] -> Parser (CompatibleCommand era)
forall (t :: * -> *) (f :: * -> *) a.
(Foldable t, Alternative f) =>
t (f a) -> f a
asum
    [ CompatibleTransactionCmds era -> CompatibleCommand era
forall era. CompatibleTransactionCmds era -> CompatibleCommand era
CompatibleTransactionCmd (CompatibleTransactionCmds era -> CompatibleCommand era)
-> Parser (CompatibleTransactionCmds era)
-> Parser (CompatibleCommand era)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> EnvCli
-> ShelleyBasedEra era -> Parser (CompatibleTransactionCmds era)
forall era.
EnvCli
-> ShelleyBasedEra era -> Parser (CompatibleTransactionCmds era)
pAllCompatibleTransactionCommands EnvCli
env ShelleyBasedEra era
era
    , CompatibleGovernanceCmds era -> CompatibleCommand era
forall era. CompatibleGovernanceCmds era -> CompatibleCommand era
CompatibleGovernanceCmds (CompatibleGovernanceCmds era -> CompatibleCommand era)
-> Parser (CompatibleGovernanceCmds era)
-> Parser (CompatibleCommand era)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> ShelleyBasedEra era -> Parser (CompatibleGovernanceCmds era)
forall era.
ShelleyBasedEra era -> Parser (CompatibleGovernanceCmds era)
pCompatibleGovernanceCmds ShelleyBasedEra era
era
    ]