module Testnet.Commands.Sophie
  ( SophieOptions(..)
  , cmdSophie
  , runSophieOptions
  ) where


import           Data.Eq
import           Data.Function
import           Data.Int
import           Data.Maybe
import           Data.Semigroup
import           Options.Applicative
import           System.IO (IO)
import           Testnet.Run (runTestnet)
import           Testnet.Sophie
import           Text.Show

import qualified Options.Applicative as OA

data SophieOptions = SophieOptions
  { SophieOptions -> Maybe Int
maybeTestnetMagic :: Maybe Int
  , SophieOptions -> TestnetOptions
testnetOptions :: TestnetOptions
  } deriving (SophieOptions -> SophieOptions -> Bool
(SophieOptions -> SophieOptions -> Bool)
-> (SophieOptions -> SophieOptions -> Bool) -> Eq SophieOptions
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
/= :: SophieOptions -> SophieOptions -> Bool
$c/= :: SophieOptions -> SophieOptions -> Bool
== :: SophieOptions -> SophieOptions -> Bool
$c== :: SophieOptions -> SophieOptions -> Bool
Eq, Int -> SophieOptions -> ShowS
[SophieOptions] -> ShowS
SophieOptions -> String
(Int -> SophieOptions -> ShowS)
-> (SophieOptions -> String)
-> ([SophieOptions] -> ShowS)
-> Show SophieOptions
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
showList :: [SophieOptions] -> ShowS
$cshowList :: [SophieOptions] -> ShowS
show :: SophieOptions -> String
$cshow :: SophieOptions -> String
showsPrec :: Int -> SophieOptions -> ShowS
$cshowsPrec :: Int -> SophieOptions -> ShowS
Show)

optsTestnet :: Parser TestnetOptions
optsTestnet :: Parser TestnetOptions
optsTestnet = Int
-> Int
-> Double
-> Int
-> Int
-> Double
-> Integer
-> TestnetOptions
TestnetOptions
  (Int
 -> Int
 -> Double
 -> Int
 -> Int
 -> Double
 -> Integer
 -> TestnetOptions)
-> Parser Int
-> Parser
     (Int
      -> Double -> Int -> Int -> Double -> Integer -> TestnetOptions)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> ReadM Int -> Mod OptionFields Int -> Parser Int
forall a. ReadM a -> Mod OptionFields a -> Parser a
OA.option ReadM Int
forall a. Read a => ReadM a
auto
      (   String -> Mod OptionFields Int
forall (f :: * -> *) a. HasName f => String -> Mod f a
OA.long String
"num-optimum-nodes"
      Mod OptionFields Int
-> Mod OptionFields Int -> Mod OptionFields Int
forall a. Semigroup a => a -> a -> a
<>  String -> Mod OptionFields Int
forall (f :: * -> *) a. String -> Mod f a
OA.help String
"Number of OPTIMUM nodes"
      Mod OptionFields Int
-> Mod OptionFields Int -> Mod OptionFields Int
forall a. Semigroup a => a -> a -> a
<>  String -> Mod OptionFields Int
forall (f :: * -> *) a. HasMetavar f => String -> Mod f a
OA.metavar String
"COUNT"
      Mod OptionFields Int
-> Mod OptionFields Int -> Mod OptionFields Int
forall a. Semigroup a => a -> a -> a
<>  Mod OptionFields Int
forall a (f :: * -> *). Show a => Mod f a
OA.showDefault
      Mod OptionFields Int
-> Mod OptionFields Int -> Mod OptionFields Int
forall a. Semigroup a => a -> a -> a
<>  Int -> Mod OptionFields Int
forall (f :: * -> *) a. HasValue f => a -> Mod f a
OA.value (TestnetOptions -> Int
numOptimumNodes TestnetOptions
defaultTestnetOptions)
      )
  Parser
  (Int
   -> Double -> Int -> Int -> Double -> Integer -> TestnetOptions)
-> Parser Int
-> Parser
     (Double -> Int -> Int -> Double -> Integer -> TestnetOptions)
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> ReadM Int -> Mod OptionFields Int -> Parser Int
forall a. ReadM a -> Mod OptionFields a -> Parser a
OA.option ReadM Int
forall a. Read a => ReadM a
auto
      (   String -> Mod OptionFields Int
forall (f :: * -> *) a. HasName f => String -> Mod f a
OA.long String
"num-pool-nodes"
      Mod OptionFields Int
-> Mod OptionFields Int -> Mod OptionFields Int
forall a. Semigroup a => a -> a -> a
<>  String -> Mod OptionFields Int
forall (f :: * -> *) a. String -> Mod f a
OA.help String
"Number of pool nodes"
      Mod OptionFields Int
-> Mod OptionFields Int -> Mod OptionFields Int
forall a. Semigroup a => a -> a -> a
<>  String -> Mod OptionFields Int
forall (f :: * -> *) a. HasMetavar f => String -> Mod f a
OA.metavar String
"COUNT"
      Mod OptionFields Int
-> Mod OptionFields Int -> Mod OptionFields Int
forall a. Semigroup a => a -> a -> a
<>  Mod OptionFields Int
forall a (f :: * -> *). Show a => Mod f a
OA.showDefault
      Mod OptionFields Int
-> Mod OptionFields Int -> Mod OptionFields Int
forall a. Semigroup a => a -> a -> a
<>  Int -> Mod OptionFields Int
forall (f :: * -> *) a. HasValue f => a -> Mod f a
OA.value (TestnetOptions -> Int
numPoolNodes TestnetOptions
defaultTestnetOptions)
      )
  Parser
  (Double -> Int -> Int -> Double -> Integer -> TestnetOptions)
-> Parser Double
-> Parser (Int -> Int -> Double -> Integer -> TestnetOptions)
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> ReadM Double -> Mod OptionFields Double -> Parser Double
forall a. ReadM a -> Mod OptionFields a -> Parser a
OA.option ReadM Double
forall a. Read a => ReadM a
auto
      (   String -> Mod OptionFields Double
forall (f :: * -> *) a. HasName f => String -> Mod f a
OA.long String
"active-slots-coeff"
      Mod OptionFields Double
-> Mod OptionFields Double -> Mod OptionFields Double
forall a. Semigroup a => a -> a -> a
<>  String -> Mod OptionFields Double
forall (f :: * -> *) a. String -> Mod f a
OA.help String
"Active slots co-efficient"
      Mod OptionFields Double
-> Mod OptionFields Double -> Mod OptionFields Double
forall a. Semigroup a => a -> a -> a
<>  String -> Mod OptionFields Double
forall (f :: * -> *) a. HasMetavar f => String -> Mod f a
OA.metavar String
"DOUBLE"
      Mod OptionFields Double
-> Mod OptionFields Double -> Mod OptionFields Double
forall a. Semigroup a => a -> a -> a
<>  Mod OptionFields Double
forall a (f :: * -> *). Show a => Mod f a
OA.showDefault
      Mod OptionFields Double
-> Mod OptionFields Double -> Mod OptionFields Double
forall a. Semigroup a => a -> a -> a
<>  Double -> Mod OptionFields Double
forall (f :: * -> *) a. HasValue f => a -> Mod f a
OA.value (TestnetOptions -> Double
activeSlotsCoeff TestnetOptions
defaultTestnetOptions)
      )
  Parser (Int -> Int -> Double -> Integer -> TestnetOptions)
-> Parser Int
-> Parser (Int -> Double -> Integer -> TestnetOptions)
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> ReadM Int -> Mod OptionFields Int -> Parser Int
forall a. ReadM a -> Mod OptionFields a -> Parser a
OA.option ReadM Int
forall a. Read a => ReadM a
auto
      (   String -> Mod OptionFields Int
forall (f :: * -> *) a. HasName f => String -> Mod f a
OA.long String
"security-param"
      Mod OptionFields Int
-> Mod OptionFields Int -> Mod OptionFields Int
forall a. Semigroup a => a -> a -> a
<>  String -> Mod OptionFields Int
forall (f :: * -> *) a. String -> Mod f a
OA.help String
"Security param"
      Mod OptionFields Int
-> Mod OptionFields Int -> Mod OptionFields Int
forall a. Semigroup a => a -> a -> a
<>  String -> Mod OptionFields Int
forall (f :: * -> *) a. HasMetavar f => String -> Mod f a
OA.metavar String
"INT"
      Mod OptionFields Int
-> Mod OptionFields Int -> Mod OptionFields Int
forall a. Semigroup a => a -> a -> a
<>  Mod OptionFields Int
forall a (f :: * -> *). Show a => Mod f a
OA.showDefault
      Mod OptionFields Int
-> Mod OptionFields Int -> Mod OptionFields Int
forall a. Semigroup a => a -> a -> a
<>  Int -> Mod OptionFields Int
forall (f :: * -> *) a. HasValue f => a -> Mod f a
OA.value (TestnetOptions -> Int
securityParam TestnetOptions
defaultTestnetOptions)
      )
  Parser (Int -> Double -> Integer -> TestnetOptions)
-> Parser Int -> Parser (Double -> Integer -> TestnetOptions)
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> ReadM Int -> Mod OptionFields Int -> Parser Int
forall a. ReadM a -> Mod OptionFields a -> Parser a
OA.option ReadM Int
forall a. Read a => ReadM a
auto
      (   String -> Mod OptionFields Int
forall (f :: * -> *) a. HasName f => String -> Mod f a
OA.long String
"epoch-length"
      Mod OptionFields Int
-> Mod OptionFields Int -> Mod OptionFields Int
forall a. Semigroup a => a -> a -> a
<>  String -> Mod OptionFields Int
forall (f :: * -> *) a. String -> Mod f a
OA.help String
"Epoch length"
      Mod OptionFields Int
-> Mod OptionFields Int -> Mod OptionFields Int
forall a. Semigroup a => a -> a -> a
<>  String -> Mod OptionFields Int
forall (f :: * -> *) a. HasMetavar f => String -> Mod f a
OA.metavar String
"MILLISECONDS"
      Mod OptionFields Int
-> Mod OptionFields Int -> Mod OptionFields Int
forall a. Semigroup a => a -> a -> a
<>  Mod OptionFields Int
forall a (f :: * -> *). Show a => Mod f a
OA.showDefault
      Mod OptionFields Int
-> Mod OptionFields Int -> Mod OptionFields Int
forall a. Semigroup a => a -> a -> a
<>  Int -> Mod OptionFields Int
forall (f :: * -> *) a. HasValue f => a -> Mod f a
OA.value (TestnetOptions -> Int
epochLength TestnetOptions
defaultTestnetOptions)
      )
  Parser (Double -> Integer -> TestnetOptions)
-> Parser Double -> Parser (Integer -> TestnetOptions)
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> ReadM Double -> Mod OptionFields Double -> Parser Double
forall a. ReadM a -> Mod OptionFields a -> Parser a
OA.option ReadM Double
forall a. Read a => ReadM a
auto
      (   String -> Mod OptionFields Double
forall (f :: * -> *) a. HasName f => String -> Mod f a
OA.long String
"slot-length"
      Mod OptionFields Double
-> Mod OptionFields Double -> Mod OptionFields Double
forall a. Semigroup a => a -> a -> a
<>  String -> Mod OptionFields Double
forall (f :: * -> *) a. String -> Mod f a
OA.help String
"Slot length"
      Mod OptionFields Double
-> Mod OptionFields Double -> Mod OptionFields Double
forall a. Semigroup a => a -> a -> a
<>  String -> Mod OptionFields Double
forall (f :: * -> *) a. HasMetavar f => String -> Mod f a
OA.metavar String
"MILLISECONDS"
      Mod OptionFields Double
-> Mod OptionFields Double -> Mod OptionFields Double
forall a. Semigroup a => a -> a -> a
<>  Mod OptionFields Double
forall a (f :: * -> *). Show a => Mod f a
OA.showDefault
      Mod OptionFields Double
-> Mod OptionFields Double -> Mod OptionFields Double
forall a. Semigroup a => a -> a -> a
<>  Double -> Mod OptionFields Double
forall (f :: * -> *) a. HasValue f => a -> Mod f a
OA.value (TestnetOptions -> Double
slotLength TestnetOptions
defaultTestnetOptions)
      )
  Parser (Integer -> TestnetOptions)
-> Parser Integer -> Parser TestnetOptions
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> ReadM Integer -> Mod OptionFields Integer -> Parser Integer
forall a. ReadM a -> Mod OptionFields a -> Parser a
OA.option ReadM Integer
forall a. Read a => ReadM a
auto
      (   String -> Mod OptionFields Integer
forall (f :: * -> *) a. HasName f => String -> Mod f a
OA.long String
"max-entropic-supply"
      Mod OptionFields Integer
-> Mod OptionFields Integer -> Mod OptionFields Integer
forall a. Semigroup a => a -> a -> a
<>  String -> Mod OptionFields Integer
forall (f :: * -> *) a. String -> Mod f a
OA.help String
"Max entropic supply"
      Mod OptionFields Integer
-> Mod OptionFields Integer -> Mod OptionFields Integer
forall a. Semigroup a => a -> a -> a
<>  String -> Mod OptionFields Integer
forall (f :: * -> *) a. HasMetavar f => String -> Mod f a
OA.metavar String
"INTEGER"
      Mod OptionFields Integer
-> Mod OptionFields Integer -> Mod OptionFields Integer
forall a. Semigroup a => a -> a -> a
<>  Mod OptionFields Integer
forall a (f :: * -> *). Show a => Mod f a
OA.showDefault
      Mod OptionFields Integer
-> Mod OptionFields Integer -> Mod OptionFields Integer
forall a. Semigroup a => a -> a -> a
<>  Integer -> Mod OptionFields Integer
forall (f :: * -> *) a. HasValue f => a -> Mod f a
OA.value (TestnetOptions -> Integer
maxEntropicSupply TestnetOptions
defaultTestnetOptions)
      )

optsSophie :: Parser SophieOptions
optsSophie :: Parser SophieOptions
optsSophie = Maybe Int -> TestnetOptions -> SophieOptions
SophieOptions
  (Maybe Int -> TestnetOptions -> SophieOptions)
-> Parser (Maybe Int) -> Parser (TestnetOptions -> SophieOptions)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser Int -> Parser (Maybe Int)
forall (f :: * -> *) a. Alternative f => f a -> f (Maybe a)
optional
      ( ReadM Int -> Mod OptionFields Int -> Parser Int
forall a. ReadM a -> Mod OptionFields a -> Parser a
OA.option ReadM Int
forall a. Read a => ReadM a
auto
        (   String -> Mod OptionFields Int
forall (f :: * -> *) a. HasName f => String -> Mod f a
long String
"testnet-magic"
        Mod OptionFields Int
-> Mod OptionFields Int -> Mod OptionFields Int
forall a. Semigroup a => a -> a -> a
<>  String -> Mod OptionFields Int
forall (f :: * -> *) a. String -> Mod f a
help String
"Testnet magic"
        Mod OptionFields Int
-> Mod OptionFields Int -> Mod OptionFields Int
forall a. Semigroup a => a -> a -> a
<>  String -> Mod OptionFields Int
forall (f :: * -> *) a. HasMetavar f => String -> Mod f a
metavar String
"INT"
        )
      )
  Parser (TestnetOptions -> SophieOptions)
-> Parser TestnetOptions -> Parser SophieOptions
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Parser TestnetOptions
optsTestnet

runSophieOptions :: SophieOptions -> IO ()
runSophieOptions :: SophieOptions -> IO ()
runSophieOptions SophieOptions
options = Maybe Int -> (Conf -> Integration [String]) -> IO ()
forall a. Maybe Int -> (Conf -> Integration a) -> IO ()
runTestnet (SophieOptions -> Maybe Int
maybeTestnetMagic SophieOptions
options) ((Conf -> Integration [String]) -> IO ())
-> (Conf -> Integration [String]) -> IO ()
forall a b. (a -> b) -> a -> b
$
  TestnetOptions -> Conf -> Integration [String]
Testnet.Sophie.testnet (SophieOptions -> TestnetOptions
testnetOptions SophieOptions
options)

cmdSophie :: Mod CommandFields (IO ())
cmdSophie :: Mod CommandFields (IO ())
cmdSophie = String -> ParserInfo (IO ()) -> Mod CommandFields (IO ())
forall a. String -> ParserInfo a -> Mod CommandFields a
command String
"sophie"  (ParserInfo (IO ()) -> Mod CommandFields (IO ()))
-> ParserInfo (IO ()) -> Mod CommandFields (IO ())
forall a b. (a -> b) -> a -> b
$ (Parser (IO ()) -> InfoMod (IO ()) -> ParserInfo (IO ()))
-> InfoMod (IO ()) -> Parser (IO ()) -> ParserInfo (IO ())
forall a b c. (a -> b -> c) -> b -> a -> c
flip Parser (IO ()) -> InfoMod (IO ()) -> ParserInfo (IO ())
forall a. Parser a -> InfoMod a -> ParserInfo a
info InfoMod (IO ())
forall m. Monoid m => m
idm (Parser (IO ()) -> ParserInfo (IO ()))
-> Parser (IO ()) -> ParserInfo (IO ())
forall a b. (a -> b) -> a -> b
$ SophieOptions -> IO ()
runSophieOptions (SophieOptions -> IO ()) -> Parser SophieOptions -> Parser (IO ())
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser SophieOptions
optsSophie