package morph

import (
	"git.frostfs.info/TrueCloudLab/frostfs-node/cmd/frostfs-adm/internal/modules/morph/util"
	"github.com/spf13/cobra"
	"github.com/spf13/viper"
)

const (
	alphabetSizeFlag                = "size"
	storageWalletFlag               = "storage-wallet"
	storageWalletLabelFlag          = "label"
	storageGasCLIFlag               = "initial-gas"
	storageGasConfigFlag            = "storage.initial_gas"
	contractsInitFlag               = "contracts"
	contractsInitFlagDesc           = "Path to archive with compiled FrostFS contracts (the default is to fetch the latest release from the official repository)"
	contractsURLFlag                = "contracts-url"
	contractsURLFlagDesc            = "URL to archive with compiled FrostFS contracts"
	maxObjectSizeInitFlag           = "network.max_object_size"
	maxObjectSizeCLIFlag            = "max-object-size"
	epochDurationInitFlag           = "network.epoch_duration"
	epochDurationCLIFlag            = "epoch-duration"
	containerFeeInitFlag            = "network.fee.container"
	containerAliasFeeInitFlag       = "network.fee.container_alias"
	containerFeeCLIFlag             = "container-fee"
	containerAliasFeeCLIFlag        = "container-alias-fee"
	candidateFeeInitFlag            = "network.fee.candidate"
	candidateFeeCLIFlag             = "candidate-fee"
	homomorphicHashDisabledInitFlag = "network.homomorphic_hash_disabled"
	maintenanceModeAllowedInitFlag  = "network.maintenance_mode_allowed"
	homomorphicHashDisabledCLIFlag  = "homomorphic-disabled"
	withdrawFeeInitFlag             = "network.fee.withdraw"
	withdrawFeeCLIFlag              = "withdraw-fee"
	containerDumpFlag               = "dump"
	containerContractFlag           = "container-contract"
	containerIDsFlag                = "cid"
	refillGasAmountFlag             = "gas"
	walletAccountFlag               = "account"
	notaryDepositTillFlag           = "till"
	localDumpFlag                   = "local-dump"

	walletAddressFlag = "wallet-address"
)

var (
	// RootCmd is a root command of config section.
	RootCmd = &cobra.Command{
		Use:   "morph",
		Short: "Section for morph network configuration commands",
	}

	generateAlphabetCmd = &cobra.Command{
		Use:   "generate-alphabet",
		Short: "Generate alphabet wallets for consensus nodes of the morph network",
		PreRun: func(cmd *cobra.Command, _ []string) {
			// PreRun fixes https://github.com/spf13/viper/issues/233
			_ = viper.BindPFlag(util.AlphabetWalletsFlag, cmd.Flags().Lookup(util.AlphabetWalletsFlag))
		},
		RunE: generateAlphabetCreds,
	}

	initCmd = &cobra.Command{
		Use:   "init",
		Short: "Initialize side chain network with smart-contracts and network settings",
		PreRun: func(cmd *cobra.Command, _ []string) {
			_ = viper.BindPFlag(util.AlphabetWalletsFlag, cmd.Flags().Lookup(util.AlphabetWalletsFlag))
			_ = viper.BindPFlag(util.EndpointFlag, cmd.Flags().Lookup(util.EndpointFlag))
			_ = viper.BindPFlag(epochDurationInitFlag, cmd.Flags().Lookup(epochDurationCLIFlag))
			_ = viper.BindPFlag(maxObjectSizeInitFlag, cmd.Flags().Lookup(maxObjectSizeCLIFlag))
			_ = viper.BindPFlag(homomorphicHashDisabledInitFlag, cmd.Flags().Lookup(homomorphicHashDisabledCLIFlag))
			_ = viper.BindPFlag(candidateFeeInitFlag, cmd.Flags().Lookup(candidateFeeCLIFlag))
			_ = viper.BindPFlag(containerFeeInitFlag, cmd.Flags().Lookup(containerFeeCLIFlag))
			_ = viper.BindPFlag(containerAliasFeeInitFlag, cmd.Flags().Lookup(containerAliasFeeCLIFlag))
			_ = viper.BindPFlag(withdrawFeeInitFlag, cmd.Flags().Lookup(withdrawFeeCLIFlag))
			_ = viper.BindPFlag(util.ProtoConfigPath, cmd.Flags().Lookup(util.ProtoConfigPath))
		},
		RunE: initializeSideChainCmd,
	}

	generateStorageCmd = &cobra.Command{
		Use:   "generate-storage-wallet",
		Short: "Generate storage node wallet for the morph network",
		PreRun: func(cmd *cobra.Command, _ []string) {
			_ = viper.BindPFlag(util.AlphabetWalletsFlag, cmd.Flags().Lookup(util.AlphabetWalletsFlag))
			_ = viper.BindPFlag(util.EndpointFlag, cmd.Flags().Lookup(util.EndpointFlag))
			_ = viper.BindPFlag(storageGasConfigFlag, cmd.Flags().Lookup(storageGasCLIFlag))
		},
		RunE: generateStorageCreds,
	}

	refillGasCmd = &cobra.Command{
		Use:   "refill-gas",
		Short: "Refill GAS of storage node's wallet in the morph network",
		PreRun: func(cmd *cobra.Command, _ []string) {
			_ = viper.BindPFlag(util.AlphabetWalletsFlag, cmd.Flags().Lookup(util.AlphabetWalletsFlag))
			_ = viper.BindPFlag(util.EndpointFlag, cmd.Flags().Lookup(util.EndpointFlag))
			_ = viper.BindPFlag(refillGasAmountFlag, cmd.Flags().Lookup(refillGasAmountFlag))
		},
		RunE: func(cmd *cobra.Command, args []string) error {
			return refillGas(cmd, refillGasAmountFlag, false)
		},
	}

	forceNewEpoch = &cobra.Command{
		Use:   "force-new-epoch",
		Short: "Create new FrostFS epoch event in the side chain",
		PreRun: func(cmd *cobra.Command, _ []string) {
			_ = viper.BindPFlag(util.AlphabetWalletsFlag, cmd.Flags().Lookup(util.AlphabetWalletsFlag))
			_ = viper.BindPFlag(util.EndpointFlag, cmd.Flags().Lookup(util.EndpointFlag))
		},
		RunE: forceNewEpochCmd,
	}

	removeNodes = &cobra.Command{
		Use:   "remove-nodes key1 [key2 [...]]",
		Short: "Remove storage nodes from the netmap",
		Long:  `Move nodes to the Offline state in the candidates list and tick an epoch to update the netmap`,
		PreRun: func(cmd *cobra.Command, _ []string) {
			_ = viper.BindPFlag(util.AlphabetWalletsFlag, cmd.Flags().Lookup(util.AlphabetWalletsFlag))
			_ = viper.BindPFlag(util.EndpointFlag, cmd.Flags().Lookup(util.EndpointFlag))
		},
		RunE: removeNodesCmd,
	}

	setConfig = &cobra.Command{
		Use:                   "set-config key1=val1 [key2=val2 ...]",
		DisableFlagsInUseLine: true,
		Short:                 "Add/update global config value in the FrostFS network",
		PreRun: func(cmd *cobra.Command, _ []string) {
			_ = viper.BindPFlag(util.AlphabetWalletsFlag, cmd.Flags().Lookup(util.AlphabetWalletsFlag))
			_ = viper.BindPFlag(util.EndpointFlag, cmd.Flags().Lookup(util.EndpointFlag))
		},
		Args: cobra.MinimumNArgs(1),
		RunE: setConfigCmd,
	}

	setPolicy = &cobra.Command{
		Use:                   "set-policy [ExecFeeFactor=<n1>] [StoragePrice=<n2>] [FeePerByte=<n3>]",
		DisableFlagsInUseLine: true,
		Short:                 "Set global policy values",
		PreRun: func(cmd *cobra.Command, _ []string) {
			_ = viper.BindPFlag(util.AlphabetWalletsFlag, cmd.Flags().Lookup(util.AlphabetWalletsFlag))
			_ = viper.BindPFlag(util.EndpointFlag, cmd.Flags().Lookup(util.EndpointFlag))
		},
		RunE: setPolicyCmd,
		ValidArgsFunction: func(cmd *cobra.Command, args []string, toComplete string) ([]string, cobra.ShellCompDirective) {
			return []string{"ExecFeeFactor=", "StoragePrice=", "FeePerByte="}, cobra.ShellCompDirectiveNoSpace
		},
	}

	dumpPolicy = &cobra.Command{
		Use:   "dump-policy",
		Short: "Dump FrostFS policy",
		PreRun: func(cmd *cobra.Command, _ []string) {
			_ = viper.BindPFlag(util.EndpointFlag, cmd.Flags().Lookup(util.EndpointFlag))
		},
		RunE: dumpPolicyCmd,
	}

	dumpContractHashesCmd = &cobra.Command{
		Use:   "dump-hashes",
		Short: "Dump deployed contract hashes",
		PreRun: func(cmd *cobra.Command, _ []string) {
			_ = viper.BindPFlag(util.EndpointFlag, cmd.Flags().Lookup(util.EndpointFlag))
		},
		RunE: dumpContractHashes,
	}

	dumpNetworkConfigCmd = &cobra.Command{
		Use:   "dump-config",
		Short: "Dump FrostFS network config",
		PreRun: func(cmd *cobra.Command, _ []string) {
			_ = viper.BindPFlag(util.EndpointFlag, cmd.Flags().Lookup(util.EndpointFlag))
		},
		RunE: dumpNetworkConfig,
	}

	dumpBalancesCmd = &cobra.Command{
		Use:   "dump-balances",
		Short: "Dump GAS balances",
		PreRun: func(cmd *cobra.Command, _ []string) {
			_ = viper.BindPFlag(util.EndpointFlag, cmd.Flags().Lookup(util.EndpointFlag))
		},
		RunE: dumpBalances,
	}

	updateContractsCmd = &cobra.Command{
		Use:   "update-contracts",
		Short: "Update FrostFS contracts",
		PreRun: func(cmd *cobra.Command, _ []string) {
			_ = viper.BindPFlag(util.AlphabetWalletsFlag, cmd.Flags().Lookup(util.AlphabetWalletsFlag))
			_ = viper.BindPFlag(util.EndpointFlag, cmd.Flags().Lookup(util.EndpointFlag))
		},
		RunE: updateContracts,
	}

	dumpContainersCmd = &cobra.Command{
		Use:   "dump-containers",
		Short: "Dump FrostFS containers to file",
		PreRun: func(cmd *cobra.Command, _ []string) {
			_ = viper.BindPFlag(util.EndpointFlag, cmd.Flags().Lookup(util.EndpointFlag))
		},
		RunE: dumpContainers,
	}

	restoreContainersCmd = &cobra.Command{
		Use:   "restore-containers",
		Short: "Restore FrostFS containers from file",
		PreRun: func(cmd *cobra.Command, _ []string) {
			_ = viper.BindPFlag(util.AlphabetWalletsFlag, cmd.Flags().Lookup(util.AlphabetWalletsFlag))
			_ = viper.BindPFlag(util.EndpointFlag, cmd.Flags().Lookup(util.EndpointFlag))
		},
		RunE: restoreContainers,
	}

	listContainersCmd = &cobra.Command{
		Use:   "list-containers",
		Short: "List FrostFS containers",
		PreRun: func(cmd *cobra.Command, _ []string) {
			_ = viper.BindPFlag(util.EndpointFlag, cmd.Flags().Lookup(util.EndpointFlag))
		},
		RunE: listContainers,
	}

	depositNotaryCmd = &cobra.Command{
		Use:   "deposit-notary",
		Short: "Deposit GAS for notary service",
		PreRun: func(cmd *cobra.Command, _ []string) {
			_ = viper.BindPFlag(util.EndpointFlag, cmd.Flags().Lookup(util.EndpointFlag))
		},
		RunE: depositNotary,
	}

	netmapCandidatesCmd = &cobra.Command{
		Use:   "netmap-candidates",
		Short: "List netmap candidates nodes",
		PreRun: func(cmd *cobra.Command, _ []string) {
			_ = viper.BindPFlag(util.EndpointFlag, cmd.Flags().Lookup(util.EndpointFlag))
			_ = viper.BindPFlag(util.AlphabetWalletsFlag, cmd.Flags().Lookup(util.AlphabetWalletsFlag))
		},
		Run: listNetmapCandidatesNodes,
	}

	proxyAddAccountCmd = &cobra.Command{
		Use:   "proxy-add-account",
		Short: "Adds account to proxy contract",
		PreRun: func(cmd *cobra.Command, _ []string) {
			_ = viper.BindPFlag(util.AlphabetWalletsFlag, cmd.Flags().Lookup(util.AlphabetWalletsFlag))
			_ = viper.BindPFlag(util.EndpointFlag, cmd.Flags().Lookup(util.EndpointFlag))
		},
		Run: addProxyAccount,
	}

	proxyRemoveAccountCmd = &cobra.Command{
		Use:   "proxy-remove-account",
		Short: "Remove from proxy contract",
		PreRun: func(cmd *cobra.Command, _ []string) {
			_ = viper.BindPFlag(util.AlphabetWalletsFlag, cmd.Flags().Lookup(util.AlphabetWalletsFlag))
			_ = viper.BindPFlag(util.EndpointFlag, cmd.Flags().Lookup(util.EndpointFlag))
		},
		Run: removeProxyAccount,
	}
)

func init() {
	initGenerateAlphabetCmd()
	initInitCmd()
	initDeployCmd()
	initGenerateStorageCmd()
	initForceNewEpochCmd()
	initRemoveNodesCmd()
	initSetPolicyCmd()
	initDumpPolicyCmd()
	initDumpContractHashesCmd()
	initDumpNetworkConfigCmd()
	initSetConfigCmd()
	initDumpBalancesCmd()
	initUpdateContractsCmd()
	initDumpContainersCmd()
	initRestoreContainersCmd()
	initListContainersCmd()
	initRefillGasCmd()
	initDepositoryNotaryCmd()
	initNetmapCandidatesCmd()

	RootCmd.AddCommand(apeCmd)
	initAddRuleChainCmd()
	initRemoveRuleChainCmd()
	initListRuleChainsCmd()
	initSetAdminCmd()
	initGetAdminCmd()

	initProxyAddAccount()
	initProxyRemoveAccount()

	RootCmd.AddCommand(frostfsidCmd)
	initFrostfsIDCreateNamespaceCmd()
	initFrostfsIDListNamespacesCmd()
	initFrostfsIDCreateSubjectCmd()
	initFrostfsIDDeleteSubjectCmd()
	initFrostfsIDListSubjectsCmd()
	initFrostfsIDCreateGroupCmd()
	initFrostfsIDDeleteGroupCmd()
	initFrostfsIDListGroupsCmd()
	initFrostfsIDAddSubjectToGroupCmd()
	initFrostfsIDRemoveSubjectFromGroupCmd()
	initFrostfsIDListGroupSubjectsCmd()
}

func initProxyAddAccount() {
	RootCmd.AddCommand(proxyAddAccountCmd)
	proxyAddAccountCmd.Flags().StringP(util.EndpointFlag, util.EndpointFlagShort, "", util.EndpointFlagDesc)
	proxyAddAccountCmd.Flags().String(accountAddressFlag, "", "Wallet address string")
}

func initProxyRemoveAccount() {
	RootCmd.AddCommand(proxyRemoveAccountCmd)
	proxyRemoveAccountCmd.Flags().StringP(util.EndpointFlag, util.EndpointFlagShort, "", util.EndpointFlagDesc)
	proxyRemoveAccountCmd.Flags().String(accountAddressFlag, "", "Wallet address string")
}

func initNetmapCandidatesCmd() {
	RootCmd.AddCommand(netmapCandidatesCmd)
	netmapCandidatesCmd.Flags().StringP(util.EndpointFlag, util.EndpointFlagShort, "", util.EndpointFlagDesc)
}

func initDepositoryNotaryCmd() {
	RootCmd.AddCommand(depositNotaryCmd)
	depositNotaryCmd.Flags().StringP(util.EndpointFlag, util.EndpointFlagShort, "", util.EndpointFlagDesc)
	depositNotaryCmd.Flags().String(storageWalletFlag, "", "Path to storage node wallet")
	depositNotaryCmd.Flags().String(walletAccountFlag, "", "Wallet account address")
	depositNotaryCmd.Flags().String(refillGasAmountFlag, "", "Amount of GAS to deposit")
	depositNotaryCmd.Flags().String(notaryDepositTillFlag, "", "Notary deposit duration in blocks")
}

func initRefillGasCmd() {
	RootCmd.AddCommand(refillGasCmd)
	refillGasCmd.Flags().String(util.AlphabetWalletsFlag, "", util.AlphabetWalletsFlagDesc)
	refillGasCmd.Flags().StringP(util.EndpointFlag, util.EndpointFlagShort, "", util.EndpointFlagDesc)
	refillGasCmd.Flags().String(storageWalletFlag, "", "Path to storage node wallet")
	refillGasCmd.Flags().String(walletAddressFlag, "", "Address of wallet")
	refillGasCmd.Flags().String(refillGasAmountFlag, "", "Additional amount of GAS to transfer")
	refillGasCmd.MarkFlagsMutuallyExclusive(walletAddressFlag, storageWalletFlag)
}

func initListContainersCmd() {
	RootCmd.AddCommand(listContainersCmd)
	listContainersCmd.Flags().StringP(util.EndpointFlag, util.EndpointFlagShort, "", util.EndpointFlagDesc)
	listContainersCmd.Flags().String(containerContractFlag, "", "Container contract hash (for networks without NNS)")
}

func initRestoreContainersCmd() {
	RootCmd.AddCommand(restoreContainersCmd)
	restoreContainersCmd.Flags().String(util.AlphabetWalletsFlag, "", util.AlphabetWalletsFlagDesc)
	restoreContainersCmd.Flags().StringP(util.EndpointFlag, util.EndpointFlagShort, "", util.EndpointFlagDesc)
	restoreContainersCmd.Flags().String(containerDumpFlag, "", "File to restore containers from")
	restoreContainersCmd.Flags().StringSlice(containerIDsFlag, nil, "Containers to restore")
}

func initDumpContainersCmd() {
	RootCmd.AddCommand(dumpContainersCmd)
	dumpContainersCmd.Flags().StringP(util.EndpointFlag, util.EndpointFlagShort, "", util.EndpointFlagDesc)
	dumpContainersCmd.Flags().String(containerDumpFlag, "", "File where to save dumped containers")
	dumpContainersCmd.Flags().String(containerContractFlag, "", "Container contract hash (for networks without NNS)")
	dumpContainersCmd.Flags().StringSlice(containerIDsFlag, nil, "Containers to dump")
}

func initUpdateContractsCmd() {
	RootCmd.AddCommand(updateContractsCmd)
	updateContractsCmd.Flags().String(util.AlphabetWalletsFlag, "", util.AlphabetWalletsFlagDesc)
	updateContractsCmd.Flags().StringP(util.EndpointFlag, util.EndpointFlagShort, "", util.EndpointFlagDesc)
	updateContractsCmd.Flags().String(contractsInitFlag, "", contractsInitFlagDesc)
	updateContractsCmd.Flags().String(contractsURLFlag, "", contractsURLFlagDesc)
	updateContractsCmd.MarkFlagsMutuallyExclusive(contractsInitFlag, contractsURLFlag)
}

func initDumpBalancesCmd() {
	RootCmd.AddCommand(dumpBalancesCmd)
	dumpBalancesCmd.Flags().StringP(util.EndpointFlag, util.EndpointFlagShort, "", util.EndpointFlagDesc)
	dumpBalancesCmd.Flags().BoolP(dumpBalancesStorageFlag, "s", false, "Dump balances of storage nodes from the current netmap")
	dumpBalancesCmd.Flags().BoolP(dumpBalancesAlphabetFlag, "a", false, "Dump balances of alphabet contracts")
	dumpBalancesCmd.Flags().BoolP(dumpBalancesProxyFlag, "p", false, "Dump balances of the proxy contract")
	dumpBalancesCmd.Flags().Bool(dumpBalancesUseScriptHashFlag, false, "Use script-hash format for addresses")
}

func initSetConfigCmd() {
	RootCmd.AddCommand(setConfig)
	setConfig.Flags().String(util.AlphabetWalletsFlag, "", util.AlphabetWalletsFlagDesc)
	setConfig.Flags().StringP(util.EndpointFlag, util.EndpointFlagShort, "", util.EndpointFlagDesc)
	setConfig.Flags().Bool(forceConfigSet, false, "Force setting not well-known configuration key")
	setConfig.Flags().String(localDumpFlag, "", "Path to the blocks dump file")
}

func initDumpNetworkConfigCmd() {
	RootCmd.AddCommand(dumpNetworkConfigCmd)
	dumpNetworkConfigCmd.Flags().StringP(util.EndpointFlag, util.EndpointFlagShort, "", util.EndpointFlagDesc)
}

func initDumpContractHashesCmd() {
	RootCmd.AddCommand(dumpContractHashesCmd)
	dumpContractHashesCmd.Flags().StringP(util.EndpointFlag, util.EndpointFlagShort, "", util.EndpointFlagDesc)
	dumpContractHashesCmd.Flags().String(customZoneFlag, "", "Custom zone to search.")
}

func initSetPolicyCmd() {
	RootCmd.AddCommand(setPolicy)
	setPolicy.Flags().String(util.AlphabetWalletsFlag, "", util.AlphabetWalletsFlagDesc)
	setPolicy.Flags().StringP(util.EndpointFlag, util.EndpointFlagShort, "", util.EndpointFlagDesc)
	setPolicy.Flags().String(localDumpFlag, "", "Path to the blocks dump file")
}

func initDumpPolicyCmd() {
	RootCmd.AddCommand(dumpPolicy)
	dumpPolicy.Flags().StringP(util.EndpointFlag, util.EndpointFlagShort, "", util.EndpointFlagDesc)
}

func initRemoveNodesCmd() {
	RootCmd.AddCommand(removeNodes)
	removeNodes.Flags().String(util.AlphabetWalletsFlag, "", util.AlphabetWalletsFlagDesc)
	removeNodes.Flags().StringP(util.EndpointFlag, util.EndpointFlagShort, "", util.EndpointFlagDesc)
	removeNodes.Flags().String(localDumpFlag, "", "Path to the blocks dump file")
}

func initForceNewEpochCmd() {
	RootCmd.AddCommand(forceNewEpoch)
	forceNewEpoch.Flags().String(util.AlphabetWalletsFlag, "", util.AlphabetWalletsFlagDesc)
	forceNewEpoch.Flags().StringP(util.EndpointFlag, util.EndpointFlagShort, "", util.EndpointFlagDesc)
	forceNewEpoch.Flags().String(localDumpFlag, "", "Path to the blocks dump file")
}

func initGenerateStorageCmd() {
	RootCmd.AddCommand(generateStorageCmd)
	generateStorageCmd.Flags().String(util.AlphabetWalletsFlag, "", util.AlphabetWalletsFlagDesc)
	generateStorageCmd.Flags().StringP(util.EndpointFlag, util.EndpointFlagShort, "", util.EndpointFlagDesc)
	generateStorageCmd.Flags().String(storageWalletFlag, "", "Path to new storage node wallet")
	generateStorageCmd.Flags().String(storageGasCLIFlag, "", "Initial amount of GAS to transfer")
	generateStorageCmd.Flags().StringP(storageWalletLabelFlag, "l", "", "Wallet label")
}

func initInitCmd() {
	RootCmd.AddCommand(initCmd)
	initCmd.Flags().String(util.AlphabetWalletsFlag, "", util.AlphabetWalletsFlagDesc)
	initCmd.Flags().StringP(util.EndpointFlag, util.EndpointFlagShort, "", util.EndpointFlagDesc)
	initCmd.Flags().String(contractsInitFlag, "", contractsInitFlagDesc)
	initCmd.Flags().String(contractsURLFlag, "", contractsURLFlagDesc)
	initCmd.Flags().Uint(epochDurationCLIFlag, 240, "Amount of side chain blocks in one FrostFS epoch")
	initCmd.Flags().Uint(maxObjectSizeCLIFlag, 67108864, "Max single object size in bytes")
	initCmd.Flags().Bool(homomorphicHashDisabledCLIFlag, false, "Disable object homomorphic hashing")
	// Defaults are taken from neo-preodolenie.
	initCmd.Flags().Uint64(containerFeeCLIFlag, 1000, "Container registration fee")
	initCmd.Flags().Uint64(containerAliasFeeCLIFlag, 500, "Container alias fee")
	initCmd.Flags().String(util.ProtoConfigPath, "", "Path to the consensus node configuration")
	initCmd.Flags().String(localDumpFlag, "", "Path to the blocks dump file")
	initCmd.MarkFlagsMutuallyExclusive(contractsInitFlag, contractsURLFlag)
}

func initGenerateAlphabetCmd() {
	RootCmd.AddCommand(generateAlphabetCmd)
	generateAlphabetCmd.Flags().String(util.AlphabetWalletsFlag, "", util.AlphabetWalletsFlagDesc)
	generateAlphabetCmd.Flags().Uint(alphabetSizeFlag, 7, "Amount of alphabet wallets to generate")
}

func initDeployCmd() {
	RootCmd.AddCommand(deployCmd)
}