From 12f9f498c8b05a91f4c08c6b27227d94013d9232 Mon Sep 17 00:00:00 2001 From: Bryan White Date: Tue, 13 Jun 2023 16:28:16 +0200 Subject: [PATCH] [Client] [Tooling] refactor: CLI (#806) ## Description ### Summary generated by Reviewpad on 13 Jun 23 12:53 UTC This pull request includes various updates across the codebase, including changes to CLI flags, import statements, and default values. It also involves refactoring code to use shared helper functions, removing unused code, and improving error handling. Some variables have been renamed to be more descriptive. The specific changes include modifications to files such as `validator.go`, `cluster-manager.yaml`, `cli-client.yaml`, `utils.go`, and `runtime_defaults.go`. For example, the `RPC_HOST` variable has been replaced with `POCKET_REMOTE_CLI_URL`. A new `helper` package has been added, and a new `flags` package contains several CLI flags. Code has also been updated to use `flags.RemoteCLIURL` instead of `remoteCLIURL`. Some constants have been renamed to include `Hostname`, and there are updates to endpoint hostnames for some validators. ## Issue Dependants: - #730 ## Type of change Please mark the relevant option(s): - [ ] New feature, functionality or library - [ ] Bug fix - [x] Code health or cleanup - [ ] Major breaking change - [ ] Documentation - [ ] Other ## List of changes - Exported `rootCmd` to support cross-package usage (i.e. subcommands w/ own pkgs) - Refactored common CLI code - Moved & refactored `PersistentPreRunE()` helper - Moved & exported `busCLICtxKey` - Exported `GetValueFromCLIContext()` and `SetValueInCLIContext()` - Moved `setupAndStartP2PModule` - Moved `setupCurrentHeightProvider` - Moved `setupPeerstoreProvider` - Refactored CLI flags to own package for cross-package use - Replaced RPC_HOST with POCKET_REMOTE_CLI_URL where appropriate - Added `remote-cli-url` flag to cluster manager & refactor - Added support for overriding of `remote-cli-url` flag with env var - Append "Hostname" to validator endpoint hostname constants - Promoted string literal to `RandomValidatorEndpointK8SHostname` constant - Improved e2e tests error messaging - Simplify e2e debug command calls - Improve error handling in client CLI ## Testing - [ ] `make develop_test`; if any code changes were made - [ ] `make test_e2e` on [k8s LocalNet](https://github.com/pokt-network/pocket/blob/main/build/localnet/README.md); if any code changes were made - [ ] `e2e-devnet-test` passes tests on [DevNet](https://pocketnetwork.notion.site/How-to-DevNet-ff1598f27efe44c09f34e2aa0051f0dd); if any code was changed - [x] [Docker Compose LocalNet](https://github.com/pokt-network/pocket/blob/main/docs/development/README.md); if any major functionality was changed or introduced - [x] [k8s LocalNet](https://github.com/pokt-network/pocket/blob/main/build/localnet/README.md); if any infrastructure or configuration changes were made ## Required Checklist - [x] I have performed a self-review of my own code - [ ] I have commented my code, particularly in hard-to-understand areas - [ ] I have added, or updated, [`godoc` format comments](https://go.dev/blog/godoc) on touched members (see: [tip.golang.org/doc/comment](https://tip.golang.org/doc/comment)) - [x] I have tested my changes using the available tooling - [x] I have updated the corresponding CHANGELOG ### If Applicable Checklist - [ ] I have updated the corresponding README(s); local and/or global - [ ] I have added tests that prove my fix is effective or that my feature works - [ ] I have added, or updated, [mermaid.js](https://mermaid-js.github.io) diagrams in the corresponding README(s) - [ ] I have added, or updated, documentation and [mermaid.js](https://mermaid-js.github.io) diagrams in `shared/docs/*` if I updated `shared/*`README(s) --- Makefile | 4 +- app/client/cli/account.go | 6 +- app/client/cli/actor.go | 12 +- app/client/cli/cmd.go | 41 ++++--- app/client/cli/consensus.go | 5 +- app/client/cli/debug.go | 111 +++--------------- app/client/cli/flags/flags.go | 24 ++++ app/client/cli/gov.go | 6 +- app/client/cli/helpers/common.go | 14 +++ app/client/cli/helpers/context.go | 21 ++++ app/client/cli/helpers/setup.go | 72 ++++++++++++ app/client/cli/keys.go | 22 ++-- app/client/cli/query.go | 52 ++++---- app/client/cli/system.go | 12 +- app/client/cli/utils.go | 23 ++-- app/client/doc/CHANGELOG.md | 15 +++ build/deployments/docker-compose.yaml | 2 +- build/docs/CHANGELOG.md | 5 + build/localnet/cluster-manager/main.go | 40 ++++++- build/localnet/manifests/cli-client.yaml | 4 +- build/localnet/manifests/cluster-manager.yaml | 4 +- e2e/docs/CHANGELOG.md | 10 ++ e2e/tests/steps_init_test.go | 8 +- e2e/tests/validator.go | 3 +- p2p/CHANGELOG.md | 4 + .../current_height_provider/rpc/provider.go | 15 +-- .../persistence/provider.go | 6 +- .../peerstore_provider/rpc/provider.go | 15 +-- runtime/defaults/defaults.go | 15 +-- runtime/docs/CHANGELOG.md | 5 + 30 files changed, 344 insertions(+), 232 deletions(-) create mode 100644 app/client/cli/flags/flags.go create mode 100644 app/client/cli/helpers/common.go create mode 100644 app/client/cli/helpers/context.go create mode 100644 app/client/cli/helpers/setup.go diff --git a/Makefile b/Makefile index 60008306d..fff096aef 100644 --- a/Makefile +++ b/Makefile @@ -155,7 +155,7 @@ rebuild_client_start: docker_check ## Rebuild and run a client daemon which is o .PHONY: client_connect client_connect: docker_check ## Connect to the running client debugging daemon - docker exec -it client /bin/bash -c "POCKET_P2P_IS_CLIENT_ONLY=true go run -tags=debug app/client/*.go debug" + docker exec -it client /bin/bash -c "POCKET_P2P_IS_CLIENT_ONLY=true go run -tags=debug app/client/*.go debug --remote_cli_url=http://validator1:50832" .PHONY: build_and_watch build_and_watch: ## Continous build Pocket's main entrypoint as files change @@ -510,7 +510,7 @@ localnet_up: ## Starts up a k8s LocalNet with all necessary dependencies (tl;dr .PHONY: localnet_client_debug localnet_client_debug: ## Opens a `client debug` cli to interact with blockchain (e.g. change pacemaker mode, reset to genesis, etc). Though the node binary updates automatiacally on every code change (i.e. hot reloads), if client is already open you need to re-run this command to execute freshly compiled binary. - kubectl exec -it deploy/dev-cli-client --container pocket -- p1 debug + kubectl exec -it deploy/dev-cli-client --container pocket -- p1 debug --remote_cli_url http://pocket-validators:50832 .PHONY: localnet_shell localnet_shell: ## Opens a shell in the pod that has the `client` cli available. The binary updates automatically whenever the code changes (i.e. hot reloads). diff --git a/app/client/cli/account.go b/app/client/cli/account.go index f171639db..578fed2ec 100644 --- a/app/client/cli/account.go +++ b/app/client/cli/account.go @@ -3,9 +3,11 @@ package cli import ( "fmt" + "github.com/spf13/cobra" + + "github.com/pokt-network/pocket/app/client/cli/flags" "github.com/pokt-network/pocket/shared/crypto" "github.com/pokt-network/pocket/utility/types" - "github.com/spf13/cobra" ) func init() { @@ -48,7 +50,7 @@ func accountCommands() []*cobra.Command { return err } - if !nonInteractive { + if !flags.NonInteractive { pwd = readPassphrase(pwd) } diff --git a/app/client/cli/actor.go b/app/client/cli/actor.go index 04a0ab81f..6486d4910 100644 --- a/app/client/cli/actor.go +++ b/app/client/cli/actor.go @@ -6,10 +6,12 @@ import ( "regexp" "strings" + "github.com/spf13/cobra" + + "github.com/pokt-network/pocket/app/client/cli/flags" coreTypes "github.com/pokt-network/pocket/shared/core/types" "github.com/pokt-network/pocket/shared/crypto" typesUtil "github.com/pokt-network/pocket/utility/types" - "github.com/spf13/cobra" ) func init() { @@ -100,7 +102,7 @@ If no changes are desired for the parameter, just enter the current param value return err } - if !nonInteractive { + if !flags.NonInteractive { pwd = readPassphrase(pwd) } @@ -169,7 +171,7 @@ func newEditStakeCmd(cmdDef actorCmdDef) *cobra.Command { return err } - if !nonInteractive { + if !flags.NonInteractive { pwd = readPassphrase(pwd) } @@ -233,7 +235,7 @@ func newUnstakeCmd(cmdDef actorCmdDef) *cobra.Command { return err } - if !nonInteractive { + if !flags.NonInteractive { pwd = readPassphrase(pwd) } pk, err := kb.GetPrivKey(fromAddrHex, pwd) @@ -284,7 +286,7 @@ func newUnpauseCmd(cmdDef actorCmdDef) *cobra.Command { return err } - if !nonInteractive { + if !flags.NonInteractive { pwd = readPassphrase(pwd) } diff --git a/app/client/cli/cmd.go b/app/client/cli/cmd.go index 95c65f1fc..8e3f975bb 100644 --- a/app/client/cli/cmd.go +++ b/app/client/cli/cmd.go @@ -2,40 +2,42 @@ package cli import ( "context" + "log" - "github.com/pokt-network/pocket/runtime/configs" - "github.com/pokt-network/pocket/runtime/defaults" "github.com/spf13/cobra" "github.com/spf13/viper" + + "github.com/pokt-network/pocket/app/client/cli/flags" + "github.com/pokt-network/pocket/runtime/configs" + "github.com/pokt-network/pocket/runtime/defaults" ) const ( cliExecutableName = "p1" + flagBindErrFormat = "could not bind flag %q: %v" ) -var ( - remoteCLIURL string - dataDir string - configPath string - nonInteractive bool - verbose bool - cfg *configs.Config -) +var cfg *configs.Config func init() { - rootCmd.PersistentFlags().StringVar(&remoteCLIURL, "remote_cli_url", defaults.DefaultRemoteCLIURL, "takes a remote endpoint in the form of :// (uses RPC Port)") - rootCmd.PersistentFlags().BoolVar(&nonInteractive, "non_interactive", false, "if true skips the interactive prompts wherever possible (useful for scripting & automation)") + rootCmd.PersistentFlags().StringVar(&flags.RemoteCLIURL, "remote_cli_url", defaults.DefaultRemoteCLIURL, "takes a remote endpoint in the form of ://: (uses RPC Port)") + // ensure that this flag can be overridden by the respective viper-conventional environment variable (i.e. `POCKET_REMOTE_CLI_URL`) + if err := viper.BindPFlag("remote_cli_url", rootCmd.PersistentFlags().Lookup("remote_cli_url")); err != nil { + log.Fatalf(flagBindErrFormat, "remote_cli_url", err) + } + + rootCmd.PersistentFlags().BoolVar(&flags.NonInteractive, "non_interactive", false, "if true skips the interactive prompts wherever possible (useful for scripting & automation)") // TECHDEBT: Why do we have a data dir when we have a config path if the data dir is only storing keys? - rootCmd.PersistentFlags().StringVar(&dataDir, "data_dir", defaults.DefaultRootDirectory, "Path to store pocket related data (keybase etc.)") - rootCmd.PersistentFlags().StringVar(&configPath, "config", "", "Path to config") + rootCmd.PersistentFlags().StringVar(&flags.DataDir, "data_dir", defaults.DefaultRootDirectory, "Path to store pocket related data (keybase etc.)") + rootCmd.PersistentFlags().StringVar(&flags.ConfigPath, "config", "", "Path to config") if err := viper.BindPFlag("root_directory", rootCmd.PersistentFlags().Lookup("data_dir")); err != nil { - panic(err) + log.Fatalf(flagBindErrFormat, "data_dir", err) } - rootCmd.PersistentFlags().BoolVar(&verbose, "verbose", false, "Show verbose output") + rootCmd.PersistentFlags().BoolVar(&flags.Verbose, "verbose", false, "Show verbose output") if err := viper.BindPFlag("verbose", rootCmd.PersistentFlags().Lookup("verbose")); err != nil { - panic(err) + log.Fatalf(flagBindErrFormat, "verbose", err) } } @@ -45,7 +47,10 @@ var rootCmd = &cobra.Command{ Long: "The CLI is meant to be an user but also a machine friendly way for interacting with Pocket Network.", PersistentPreRunE: func(cmd *cobra.Command, args []string) error { // by this time, the config path should be set - cfg = configs.ParseConfig(configPath) + cfg = configs.ParseConfig(flags.ConfigPath) + + // set final `remote_cli_url` value; order of precedence: flag > env var > config > default + flags.RemoteCLIURL = viper.GetString("remote_cli_url") return nil }, } diff --git a/app/client/cli/consensus.go b/app/client/cli/consensus.go index e909fcd2d..a74876949 100644 --- a/app/client/cli/consensus.go +++ b/app/client/cli/consensus.go @@ -2,9 +2,10 @@ package cli import ( "fmt" + "github.com/spf13/cobra" + "github.com/pokt-network/pocket/app/client/cli/flags" "github.com/pokt-network/pocket/rpc" - "github.com/spf13/cobra" ) func init() { @@ -96,7 +97,7 @@ func consensusCommands() []*cobra.Command { } func getConsensusState(cmd *cobra.Command) (*rpc.GetV1ConsensusStateResponse, error) { - client, err := rpc.NewClientWithResponses(remoteCLIURL) + client, err := rpc.NewClientWithResponses(flags.RemoteCLIURL) if err != nil { return nil, nil } diff --git a/app/client/cli/debug.go b/app/client/cli/debug.go index 2f1bfaa59..07ab0cfb2 100644 --- a/app/client/cli/debug.go +++ b/app/client/cli/debug.go @@ -6,19 +6,16 @@ import ( "os" "github.com/manifoldco/promptui" + "github.com/spf13/cobra" + "google.golang.org/protobuf/types/known/anypb" + + "github.com/pokt-network/pocket/app/client/cli/helpers" "github.com/pokt-network/pocket/logger" - "github.com/pokt-network/pocket/p2p" "github.com/pokt-network/pocket/p2p/providers/current_height_provider" - rpcCHP "github.com/pokt-network/pocket/p2p/providers/current_height_provider/rpc" "github.com/pokt-network/pocket/p2p/providers/peerstore_provider" - rpcABP "github.com/pokt-network/pocket/p2p/providers/peerstore_provider/rpc" typesP2P "github.com/pokt-network/pocket/p2p/types" - "github.com/pokt-network/pocket/runtime" - "github.com/pokt-network/pocket/runtime/defaults" "github.com/pokt-network/pocket/shared/messaging" "github.com/pokt-network/pocket/shared/modules" - "github.com/spf13/cobra" - "google.golang.org/protobuf/types/known/anypb" ) // TECHDEBT: Lowercase variables / constants that do not need to be exported. @@ -33,9 +30,6 @@ const ( ) var ( - // A P2P module is initialized in order to broadcast a message to the local network - p2pMod modules.P2PModule - items = []string{ PromptPrintNodeState, PromptTriggerNextView, @@ -45,28 +39,12 @@ var ( PromptSendMetadataRequest, PromptSendBlockRequest, } - - genesisPath string = runtime.GetEnv("GENESIS_PATH", "build/config/genesis.json") - rpcHost string ) -// NOTE: this is required by the linter, otherwise a simple string constant would have been enough -type cliContextKey string - -const busCLICtxKey = "bus" - func init() { dbg := NewDebugCommand() dbg.AddCommand(NewDebugSubCommands()...) rootCmd.AddCommand(dbg) - - // by default, we point at the same endpoint used by the CLI but the debug client is used either in docker-compose of K8S, therefore we cater for overriding - validator1Endpoint := defaults.Validator1EndpointDockerCompose - if runtime.IsProcessRunningInsideKubernetes() { - validator1Endpoint = defaults.Validator1EndpointK8S - } - - rpcHost = runtime.GetEnv("RPC_HOST", validator1Endpoint) } // NewDebugSubCommands builds out the list of debug subcommands by matching the @@ -77,10 +55,8 @@ func NewDebugSubCommands() []*cobra.Command { commands := make([]*cobra.Command, len(items)) for idx, promptItem := range items { commands[idx] = &cobra.Command{ - Use: promptItem, - PersistentPreRun: func(cmd *cobra.Command, args []string) { - persistentPreRun(cmd, args) - }, + Use: promptItem, + PersistentPreRunE: helpers.P2PDependenciesPreRunE, Run: func(cmd *cobra.Command, args []string) { handleSelect(cmd, cmd.Use) }, @@ -93,70 +69,11 @@ func NewDebugSubCommands() []*cobra.Command { // NewDebugCommand returns the cobra CLI for the Debug command. func NewDebugCommand() *cobra.Command { return &cobra.Command{ - Use: "debug", - Short: "Debug utility for rapid development", - Args: cobra.MaximumNArgs(0), - PersistentPreRun: func(cmd *cobra.Command, args []string) { - persistentPreRun(cmd, args) - }, - RunE: runDebug, - } -} - -// persistentPreRun is called by both debug and debug sub-commands before runs -func persistentPreRun(cmd *cobra.Command, _ []string) { - // TECHDEBT: this is to keep backwards compatibility with localnet - configPath = runtime.GetEnv("CONFIG_PATH", "build/config/config.validator1.json") - rpcURL := fmt.Sprintf("http://%s:%s", rpcHost, defaults.DefaultRPCPort) - - runtimeMgr := runtime.NewManagerFromFiles( - configPath, genesisPath, - runtime.WithClientDebugMode(), - runtime.WithRandomPK(), - ) - - bus := runtimeMgr.GetBus() - setValueInCLIContext(cmd, busCLICtxKey, bus) - - setupPeerstoreProvider(*runtimeMgr, rpcURL) - setupCurrentHeightProvider(*runtimeMgr, rpcURL) - setupAndStartP2PModule(*runtimeMgr) -} - -func setupPeerstoreProvider(rm runtime.Manager, rpcURL string) { - bus := rm.GetBus() - modulesRegistry := bus.GetModulesRegistry() - pstoreProvider := rpcABP.Create( - rpcABP.WithP2PConfig(rm.GetConfig().P2P), - rpcABP.WithCustomRPCURL(rpcURL), - ) - modulesRegistry.RegisterModule(pstoreProvider) -} - -func setupCurrentHeightProvider(rm runtime.Manager, rpcURL string) { - bus := rm.GetBus() - modulesRegistry := bus.GetModulesRegistry() - currentHeightProvider := rpcCHP.NewRPCCurrentHeightProvider( - rpcCHP.WithCustomRPCURL(rpcURL), - ) - modulesRegistry.RegisterModule(currentHeightProvider) -} - -func setupAndStartP2PModule(rm runtime.Manager) { - bus := rm.GetBus() - mod, err := p2p.Create(bus) - if err != nil { - logger.Global.Fatal().Err(err).Msg("Failed to create p2p module") - } - - var ok bool - p2pMod, ok = mod.(modules.P2PModule) - if !ok { - logger.Global.Fatal().Msgf("unexpected P2P module type: %T", mod) - } - - if err := p2pMod.Start(); err != nil { - logger.Global.Fatal().Err(err).Msg("Failed to start p2p module") + Use: "debug", + Short: "Debug utility for rapid development", + Args: cobra.MaximumNArgs(0), + PersistentPreRunE: helpers.P2PDependenciesPreRunE, + RunE: runDebug, } } @@ -269,7 +186,7 @@ func broadcastDebugMessage(cmd *cobra.Command, debugMsg *messaging.DebugMessage) if err != nil { logger.Global.Fatal().Err(err).Msg("Failed to convert validator address into pocketCrypto.Address") } - if err := p2pMod.Send(addr, anyProto); err != nil { + if err := helpers.P2PMod.Send(addr, anyProto); err != nil { logger.Global.Error().Err(err).Msg("Failed to send debug message") } } @@ -299,14 +216,14 @@ func sendDebugMessage(cmd *cobra.Command, debugMsg *messaging.DebugMessage) { logger.Global.Fatal().Err(err).Msg("Failed to convert validator address into pocketCrypto.Address") } - if err := p2pMod.Send(validatorAddress, anyProto); err != nil { + if err := helpers.P2PMod.Send(validatorAddress, anyProto); err != nil { logger.Global.Error().Err(err).Msg("Failed to send debug message") } } // fetchPeerstore retrieves the providers from the CLI context and uses them to retrieve the address book for the current height func fetchPeerstore(cmd *cobra.Command) (typesP2P.Peerstore, error) { - bus, ok := getValueFromCLIContext[modules.Bus](cmd, busCLICtxKey) + bus, ok := helpers.GetValueFromCLIContext[modules.Bus](cmd, helpers.BusCLICtxKey) if !ok || bus == nil { return nil, errors.New("retrieving bus from CLI context") } diff --git a/app/client/cli/flags/flags.go b/app/client/cli/flags/flags.go new file mode 100644 index 000000000..b60d9cced --- /dev/null +++ b/app/client/cli/flags/flags.go @@ -0,0 +1,24 @@ +package flags + +var ( + // RemoveCLIURL is the URL of the remote RPC node which the CLI will interact with. + // Formatted as ://: (uses RPC Port). + // (see: --help the root command for more info). + RemoteCLIURL string + + // DataDir a path to store pocket related data (keybase etc.). + // (see: --help the root command for more info). + DataDir string + + // ConfigPath is the path to the node config file. + // (see: --help the root command for more info). + ConfigPath string + + // If true skips the interactive prompts wherever possible (useful for scripting & automation) + // (see: --help the root command for more info). + NonInteractive bool + + // Show verbose output + // (see: --help the root command for more info). + Verbose bool +) diff --git a/app/client/cli/gov.go b/app/client/cli/gov.go index c94737c32..a0fc30b88 100644 --- a/app/client/cli/gov.go +++ b/app/client/cli/gov.go @@ -3,10 +3,12 @@ package cli import ( "fmt" - "github.com/pokt-network/pocket/utility/types" "github.com/spf13/cobra" "google.golang.org/protobuf/types/known/anypb" "google.golang.org/protobuf/types/known/wrapperspb" + + "github.com/pokt-network/pocket/app/client/cli/flags" + "github.com/pokt-network/pocket/utility/types" ) func init() { @@ -52,7 +54,7 @@ func govCommands() []*cobra.Command { return err } - if !nonInteractive { + if !flags.NonInteractive { pwd = readPassphrase(pwd) } diff --git a/app/client/cli/helpers/common.go b/app/client/cli/helpers/common.go new file mode 100644 index 000000000..b9f6d547b --- /dev/null +++ b/app/client/cli/helpers/common.go @@ -0,0 +1,14 @@ +package helpers + +import ( + "github.com/pokt-network/pocket/runtime" + "github.com/pokt-network/pocket/shared/modules" +) + +var ( + // TECHDEBT: Accept reading this from `Datadir` and/or as a flag. + genesisPath = runtime.GetEnv("GENESIS_PATH", "build/config/genesis.json") + + // P2PMod is initialized in order to broadcast a message to the local network + P2PMod modules.P2PModule +) diff --git a/app/client/cli/helpers/context.go b/app/client/cli/helpers/context.go new file mode 100644 index 000000000..f9f3f4549 --- /dev/null +++ b/app/client/cli/helpers/context.go @@ -0,0 +1,21 @@ +package helpers + +import ( + "context" + + "github.com/spf13/cobra" +) + +const BusCLICtxKey cliContextKey = "bus" + +// NOTE: this is required by the linter, otherwise a simple string constant would have been enough +type cliContextKey string + +func SetValueInCLIContext(cmd *cobra.Command, key cliContextKey, value any) { + cmd.SetContext(context.WithValue(cmd.Context(), key, value)) +} + +func GetValueFromCLIContext[T any](cmd *cobra.Command, key cliContextKey) (T, bool) { + value, ok := cmd.Context().Value(key).(T) + return value, ok +} diff --git a/app/client/cli/helpers/setup.go b/app/client/cli/helpers/setup.go new file mode 100644 index 000000000..376e9348e --- /dev/null +++ b/app/client/cli/helpers/setup.go @@ -0,0 +1,72 @@ +package helpers + +import ( + "github.com/spf13/cobra" + + "github.com/pokt-network/pocket/app/client/cli/flags" + "github.com/pokt-network/pocket/logger" + "github.com/pokt-network/pocket/p2p" + rpcCHP "github.com/pokt-network/pocket/p2p/providers/current_height_provider/rpc" + rpcPSP "github.com/pokt-network/pocket/p2p/providers/peerstore_provider/rpc" + "github.com/pokt-network/pocket/runtime" + "github.com/pokt-network/pocket/shared/modules" +) + +// P2PDependenciesPreRunE initializes peerstore & current height providers, and a +// p2p module which consumes them. Everything is registered to the bus. +func P2PDependenciesPreRunE(cmd *cobra.Command, _ []string) error { + // TECHDEBT: this is to keep backwards compatibility with localnet + flags.ConfigPath = runtime.GetEnv("CONFIG_PATH", "build/config/config.validator1.json") + + runtimeMgr := runtime.NewManagerFromFiles( + flags.ConfigPath, genesisPath, + runtime.WithClientDebugMode(), + runtime.WithRandomPK(), + ) + + bus := runtimeMgr.GetBus() + SetValueInCLIContext(cmd, BusCLICtxKey, bus) + + setupPeerstoreProvider(*runtimeMgr, flags.RemoteCLIURL) + setupCurrentHeightProvider(*runtimeMgr, flags.RemoteCLIURL) + setupAndStartP2PModule(*runtimeMgr) + + return nil +} + +func setupPeerstoreProvider(rm runtime.Manager, rpcURL string) { + bus := rm.GetBus() + modulesRegistry := bus.GetModulesRegistry() + pstoreProvider := rpcPSP.Create( + rpcPSP.WithP2PConfig(rm.GetConfig().P2P), + rpcPSP.WithCustomRPCURL(rpcURL), + ) + modulesRegistry.RegisterModule(pstoreProvider) +} + +func setupCurrentHeightProvider(rm runtime.Manager, rpcURL string) { + bus := rm.GetBus() + modulesRegistry := bus.GetModulesRegistry() + currentHeightProvider := rpcCHP.NewRPCCurrentHeightProvider( + rpcCHP.WithCustomRPCURL(rpcURL), + ) + modulesRegistry.RegisterModule(currentHeightProvider) +} + +func setupAndStartP2PModule(rm runtime.Manager) { + bus := rm.GetBus() + mod, err := p2p.Create(bus) + if err != nil { + logger.Global.Fatal().Err(err).Msg("Failed to create p2p module") + } + + var ok bool + P2PMod, ok = mod.(modules.P2PModule) + if !ok { + logger.Global.Fatal().Msgf("unexpected P2P module type: %T", mod) + } + + if err := P2PMod.Start(); err != nil { + logger.Global.Fatal().Err(err).Msg("Failed to start p2p module") + } +} diff --git a/app/client/cli/keys.go b/app/client/cli/keys.go index c1500ac49..15409b675 100644 --- a/app/client/cli/keys.go +++ b/app/client/cli/keys.go @@ -7,11 +7,13 @@ import ( "strconv" "strings" + "github.com/spf13/cobra" + + "github.com/pokt-network/pocket/app/client/cli/flags" "github.com/pokt-network/pocket/shared/codec" coreTypes "github.com/pokt-network/pocket/shared/core/types" "github.com/pokt-network/pocket/shared/crypto" "github.com/pokt-network/pocket/shared/utils" - "github.com/spf13/cobra" ) var ( @@ -65,7 +67,7 @@ func keysCreateCommands() []*cobra.Command { return err } - if !nonInteractive { + if !flags.NonInteractive { pwd = readPassphrase(pwd) confirmPassphrase(pwd) } @@ -112,7 +114,7 @@ func keysUpdateCommands() []*cobra.Command { return err } - if !nonInteractive { + if !flags.NonInteractive { pwd = readPassphrase(pwd) newPwd = readPassphraseMessage(newPwd, "New passphrase: ") confirmPassphrase(newPwd) @@ -161,7 +163,7 @@ func keysDeleteCommands() []*cobra.Command { return err } - if !nonInteractive { + if !flags.NonInteractive { pwd = readPassphrase(pwd) } @@ -276,7 +278,7 @@ func keysExportCommands() []*cobra.Command { return err } - if !nonInteractive { + if !flags.NonInteractive { pwd = readPassphrase(pwd) } @@ -353,7 +355,7 @@ func keysImportCommands() []*cobra.Command { return err } - if !nonInteractive { + if !flags.NonInteractive { pwd = readPassphrase(pwd) } @@ -367,7 +369,7 @@ func keysImportCommands() []*cobra.Command { } case "raw": // it is unarmoured so we need to confirm the passphrase - if !nonInteractive { + if !flags.NonInteractive { confirmPassphrase(pwd) } kp, err = kb.ImportFromString(privateKeyString, pwd, hint) @@ -423,7 +425,7 @@ func keysSignMsgCommands() []*cobra.Command { return err } - if !nonInteractive { + if !flags.NonInteractive { pwd = readPassphrase(pwd) } @@ -520,7 +522,7 @@ func keysSignTxCommands() []*cobra.Command { return err } - if !nonInteractive { + if !flags.NonInteractive { pwd = readPassphrase(pwd) } @@ -678,7 +680,7 @@ func keysSlipCommands() []*cobra.Command { return err } - if !nonInteractive { + if !flags.NonInteractive { pwd = readPassphrase(pwd) } diff --git a/app/client/cli/query.go b/app/client/cli/query.go index dcea5f176..0552b8c30 100644 --- a/app/client/cli/query.go +++ b/app/client/cli/query.go @@ -6,8 +6,10 @@ import ( "net/http" "os" - "github.com/pokt-network/pocket/rpc" "github.com/spf13/cobra" + + "github.com/pokt-network/pocket/app/client/cli/flags" + "github.com/pokt-network/pocket/rpc" ) var ( @@ -68,7 +70,7 @@ func queryHeightCommands() []*cobra.Command { Args: cobra.ExactArgs(1), Aliases: []string{"account"}, RunE: func(cmd *cobra.Command, args []string) error { - client, err := rpc.NewClientWithResponses(remoteCLIURL) + client, err := rpc.NewClientWithResponses(flags.RemoteCLIURL) if err != nil { return err } @@ -103,7 +105,7 @@ func queryHeightCommands() []*cobra.Command { Args: cobra.ExactArgs(1), Aliases: []string{"app"}, RunE: func(cmd *cobra.Command, args []string) error { - client, err := rpc.NewClientWithResponses(remoteCLIURL) + client, err := rpc.NewClientWithResponses(flags.RemoteCLIURL) if err != nil { return err } @@ -138,7 +140,7 @@ func queryHeightCommands() []*cobra.Command { Args: cobra.ExactArgs(1), Aliases: []string{"balance"}, RunE: func(cmd *cobra.Command, args []string) error { - client, err := rpc.NewClientWithResponses(remoteCLIURL) + client, err := rpc.NewClientWithResponses(flags.RemoteCLIURL) if err != nil { return err } @@ -173,7 +175,7 @@ func queryHeightCommands() []*cobra.Command { Args: cobra.ExactArgs(0), Aliases: []string{"block"}, RunE: func(cmd *cobra.Command, args []string) error { - client, err := rpc.NewClientWithResponses(remoteCLIURL) + client, err := rpc.NewClientWithResponses(flags.RemoteCLIURL) if err != nil { return err } @@ -207,7 +209,7 @@ func queryHeightCommands() []*cobra.Command { Args: cobra.ExactArgs(1), Aliases: []string{"fisherman"}, RunE: func(cmd *cobra.Command, args []string) error { - client, err := rpc.NewClientWithResponses(remoteCLIURL) + client, err := rpc.NewClientWithResponses(flags.RemoteCLIURL) if err != nil { return err } @@ -242,7 +244,7 @@ func queryHeightCommands() []*cobra.Command { Aliases: []string{"param"}, Args: cobra.ExactArgs(1), RunE: func(cmd *cobra.Command, args []string) error { - client, err := rpc.NewClientWithResponses(remoteCLIURL) + client, err := rpc.NewClientWithResponses(flags.RemoteCLIURL) if err != nil { return err } @@ -277,7 +279,7 @@ func queryHeightCommands() []*cobra.Command { Args: cobra.ExactArgs(1), Aliases: []string{"servicer"}, RunE: func(cmd *cobra.Command, args []string) error { - client, err := rpc.NewClientWithResponses(remoteCLIURL) + client, err := rpc.NewClientWithResponses(flags.RemoteCLIURL) if err != nil { return err } @@ -312,7 +314,7 @@ func queryHeightCommands() []*cobra.Command { Args: cobra.ExactArgs(0), Aliases: []string{"supply"}, RunE: func(cmd *cobra.Command, args []string) error { - client, err := rpc.NewClientWithResponses(remoteCLIURL) + client, err := rpc.NewClientWithResponses(flags.RemoteCLIURL) if err != nil { return err } @@ -346,7 +348,7 @@ func queryHeightCommands() []*cobra.Command { Args: cobra.ExactArgs(0), Aliases: []string{"supportedchains"}, RunE: func(cmd *cobra.Command, args []string) error { - client, err := rpc.NewClientWithResponses(remoteCLIURL) + client, err := rpc.NewClientWithResponses(flags.RemoteCLIURL) if err != nil { return err } @@ -380,7 +382,7 @@ func queryHeightCommands() []*cobra.Command { Aliases: []string{"param"}, Args: cobra.ExactArgs(0), RunE: func(cmd *cobra.Command, args []string) error { - client, err := rpc.NewClientWithResponses(remoteCLIURL) + client, err := rpc.NewClientWithResponses(flags.RemoteCLIURL) if err != nil { return err } @@ -414,7 +416,7 @@ func queryHeightCommands() []*cobra.Command { Args: cobra.ExactArgs(1), Aliases: []string{"validator"}, RunE: func(cmd *cobra.Command, args []string) error { - client, err := rpc.NewClientWithResponses(remoteCLIURL) + client, err := rpc.NewClientWithResponses(flags.RemoteCLIURL) if err != nil { return err } @@ -456,7 +458,7 @@ func queryHeightPaginatedCommands() []*cobra.Command { Args: cobra.ExactArgs(0), Aliases: []string{"accounts"}, RunE: func(cmd *cobra.Command, args []string) error { - client, err := rpc.NewClientWithResponses(remoteCLIURL) + client, err := rpc.NewClientWithResponses(flags.RemoteCLIURL) if err != nil { return err } @@ -492,7 +494,7 @@ func queryHeightPaginatedCommands() []*cobra.Command { Args: cobra.ExactArgs(0), Aliases: []string{"apps"}, RunE: func(cmd *cobra.Command, args []string) error { - client, err := rpc.NewClientWithResponses(remoteCLIURL) + client, err := rpc.NewClientWithResponses(flags.RemoteCLIURL) if err != nil { return err } @@ -528,7 +530,7 @@ func queryHeightPaginatedCommands() []*cobra.Command { Args: cobra.ExactArgs(0), Aliases: []string{"fishermen"}, RunE: func(cmd *cobra.Command, args []string) error { - client, err := rpc.NewClientWithResponses(remoteCLIURL) + client, err := rpc.NewClientWithResponses(flags.RemoteCLIURL) if err != nil { return err } @@ -564,7 +566,7 @@ func queryHeightPaginatedCommands() []*cobra.Command { Args: cobra.ExactArgs(0), Aliases: []string{"servicers"}, RunE: func(cmd *cobra.Command, args []string) error { - client, err := rpc.NewClientWithResponses(remoteCLIURL) + client, err := rpc.NewClientWithResponses(flags.RemoteCLIURL) if err != nil { return err } @@ -600,7 +602,7 @@ func queryHeightPaginatedCommands() []*cobra.Command { Args: cobra.ExactArgs(0), Aliases: []string{"validators"}, RunE: func(cmd *cobra.Command, args []string) error { - client, err := rpc.NewClientWithResponses(remoteCLIURL) + client, err := rpc.NewClientWithResponses(flags.RemoteCLIURL) if err != nil { return err } @@ -643,7 +645,7 @@ func queryHeightPaginatedSortedCommands() []*cobra.Command { Args: cobra.ExactArgs(0), Aliases: []string{"blocktxs"}, RunE: func(cmd *cobra.Command, args []string) error { - client, err := rpc.NewClientWithResponses(remoteCLIURL) + client, err := rpc.NewClientWithResponses(flags.RemoteCLIURL) if err != nil { return err } @@ -687,7 +689,7 @@ func queryPaginatedSortedCommands() []*cobra.Command { Args: cobra.ExactArgs(1), Aliases: []string{"accounttxs"}, RunE: func(cmd *cobra.Command, args []string) error { - client, err := rpc.NewClientWithResponses(remoteCLIURL) + client, err := rpc.NewClientWithResponses(flags.RemoteCLIURL) if err != nil { return err } @@ -724,7 +726,7 @@ func queryPaginatedSortedCommands() []*cobra.Command { Args: cobra.ExactArgs(0), Aliases: []string{"unconfirmedtxs"}, RunE: func(cmd *cobra.Command, args []string) error { - client, err := rpc.NewClientWithResponses(remoteCLIURL) + client, err := rpc.NewClientWithResponses(flags.RemoteCLIURL) if err != nil { return err } @@ -767,7 +769,7 @@ func queryCommands() []*cobra.Command { Aliases: []string{"allparams"}, Args: cobra.ExactArgs(0), RunE: func(cmd *cobra.Command, args []string) error { - client, err := rpc.NewClientWithResponses(remoteCLIURL) + client, err := rpc.NewClientWithResponses(flags.RemoteCLIURL) if err != nil { return err } @@ -795,7 +797,7 @@ func queryCommands() []*cobra.Command { Aliases: []string{"height"}, Args: cobra.ExactArgs(0), RunE: func(cmd *cobra.Command, args []string) error { - client, err := rpc.NewClientWithResponses(remoteCLIURL) + client, err := rpc.NewClientWithResponses(flags.RemoteCLIURL) if err != nil { return err } @@ -823,7 +825,7 @@ func queryCommands() []*cobra.Command { Aliases: []string{"tx"}, Args: cobra.ExactArgs(1), RunE: func(cmd *cobra.Command, args []string) error { - client, err := rpc.NewClientWithResponses(remoteCLIURL) + client, err := rpc.NewClientWithResponses(flags.RemoteCLIURL) if err != nil { return err } @@ -857,7 +859,7 @@ func queryCommands() []*cobra.Command { Aliases: []string{"unconfirmedtx"}, Args: cobra.ExactArgs(1), RunE: func(cmd *cobra.Command, args []string) error { - client, err := rpc.NewClientWithResponses(remoteCLIURL) + client, err := rpc.NewClientWithResponses(flags.RemoteCLIURL) if err != nil { return err } @@ -890,7 +892,7 @@ func queryCommands() []*cobra.Command { Long: "Queries the node RPC to returns the type of utility actor(s) running on the node", Aliases: []string{"noderoles"}, RunE: func(cmd *cobra.Command, args []string) error { - client, err := rpc.NewClientWithResponses(remoteCLIURL) + client, err := rpc.NewClientWithResponses(flags.RemoteCLIURL) if err != nil { return err } diff --git a/app/client/cli/system.go b/app/client/cli/system.go index 2bcce8e24..63391db73 100644 --- a/app/client/cli/system.go +++ b/app/client/cli/system.go @@ -4,8 +4,10 @@ import ( "fmt" "net/http" - "github.com/pokt-network/pocket/rpc" "github.com/spf13/cobra" + + "github.com/pokt-network/pocket/app/client/cli/flags" + "github.com/pokt-network/pocket/rpc" ) func init() { @@ -34,7 +36,7 @@ func systemCommands() []*cobra.Command { Long: "Performs a simple liveness check on the node RPC endpoint", Aliases: []string{"health"}, RunE: func(cmd *cobra.Command, args []string) error { - client, err := rpc.NewClientWithResponses(remoteCLIURL) + client, err := rpc.NewClientWithResponses(flags.RemoteCLIURL) if err != nil { return nil } @@ -44,7 +46,7 @@ func systemCommands() []*cobra.Command { } statusCode := response.StatusCode() if statusCode == http.StatusOK { - fmt.Printf("✅ RPC reporting healthy status for node @ %s\n\n%s", boldText(remoteCLIURL), response.Body) + fmt.Printf("✅ RPC reporting healthy status for node @ %s\n\n%s", boldText(flags.RemoteCLIURL), response.Body) return nil } @@ -57,7 +59,7 @@ func systemCommands() []*cobra.Command { Long: "Queries the node RPC to obtain the version of the software currently running", Aliases: []string{"version"}, RunE: func(cmd *cobra.Command, args []string) error { - client, err := rpc.NewClientWithResponses(remoteCLIURL) + client, err := rpc.NewClientWithResponses(flags.RemoteCLIURL) if err != nil { return err } @@ -67,7 +69,7 @@ func systemCommands() []*cobra.Command { } statusCode := response.StatusCode() if statusCode == http.StatusOK { - fmt.Printf("Node @ %s reports that it's running version: \n%s\n", boldText(remoteCLIURL), boldText(response.Body)) + fmt.Printf("Node @ %s reports that it's running version: \n%s\n", boldText(flags.RemoteCLIURL), boldText(response.Body)) return nil } diff --git a/app/client/cli/utils.go b/app/client/cli/utils.go index 68395bfc7..2e3e0263e 100644 --- a/app/client/cli/utils.go +++ b/app/client/cli/utils.go @@ -11,6 +11,11 @@ import ( "os" "strings" + "github.com/spf13/cobra" + "github.com/spf13/viper" + "golang.org/x/term" + + "github.com/pokt-network/pocket/app/client/cli/flags" "github.com/pokt-network/pocket/app/client/keybase" "github.com/pokt-network/pocket/logger" "github.com/pokt-network/pocket/rpc" @@ -20,9 +25,6 @@ import ( "github.com/pokt-network/pocket/shared/crypto" "github.com/pokt-network/pocket/shared/utils" typesUtil "github.com/pokt-network/pocket/utility/types" - "github.com/spf13/cobra" - "github.com/spf13/viper" - "golang.org/x/term" ) var ( @@ -129,7 +131,7 @@ func prepareTxBytes(msg typesUtil.Message, pk crypto.PrivateKey) ([]byte, error) // postRawTx posts a signed transaction func postRawTx(ctx context.Context, pk crypto.PrivateKey, j []byte) (*rpc.PostV1ClientBroadcastTxSyncResponse, error) { - client, err := rpc.NewClientWithResponses(remoteCLIURL) + client, err := rpc.NewClientWithResponses(flags.RemoteCLIURL) if err != nil { return nil, err } @@ -313,12 +315,12 @@ func keybaseForCLI() (keybase.Keybase, error) { } func unableToConnectToRpc(err error) error { - fmt.Printf("❌ Unable to connect to the RPC @ %s\n\nError: %s", boldText(remoteCLIURL), err) + fmt.Printf("❌ Unable to connect to the RPC @ %s\n\nError: %s", boldText(flags.RemoteCLIURL), err) return nil } func rpcResponseCodeUnhealthy(statusCode int, response []byte) error { - fmt.Printf("❌ RPC reporting unhealthy status HTTP %d @ %s\n\n%s", statusCode, boldText(remoteCLIURL), response) + fmt.Printf("❌ RPC reporting unhealthy status HTTP %d @ %s\n\n%s", statusCode, boldText(flags.RemoteCLIURL), response) return nil } @@ -326,15 +328,6 @@ func boldText[T string | []byte](s T) string { return fmt.Sprintf("\033[1m%s\033[0m", s) } -func setValueInCLIContext(cmd *cobra.Command, key cliContextKey, value any) { - cmd.SetContext(context.WithValue(cmd.Context(), key, value)) -} - -func getValueFromCLIContext[T any](cmd *cobra.Command, key cliContextKey) (T, bool) { - value, ok := cmd.Context().Value(key).(T) - return value, ok -} - // confirmPassphrase should be used when a new key is being created or a raw unarmored key is being imported func confirmPassphrase(currPwd string) { confirm := readPassphraseMessage("", "Confirm passphrase: ") diff --git a/app/client/doc/CHANGELOG.md b/app/client/doc/CHANGELOG.md index 016d9e212..0b76ded7e 100644 --- a/app/client/doc/CHANGELOG.md +++ b/app/client/doc/CHANGELOG.md @@ -7,6 +7,21 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ## [Unreleased] +## [0.0.0.34] - 2023-06-13 + +- Exported `rootCmd` to support cross-package usage (i.e. subcommands w/ own pkgs) +- Refactored common CLI code + - Moved & refactored `PersistentPreRunE()` helper + - Moved & exported `busCLICtxKey` + - Exported `GetValueFromCLIContext()` and `SetValueInCLIContext()` + - Moved `setupAndStartP2PModule` + - Moved `setupCurrentHeightProvider` + - Moved `setupPeerstoreProvider` +- Refactored CLI flags to own package for cross-package use +- Replaced RPC_HOST with POCKET_REMOTE_CLI_URL where appropriate +- Added support for overriding of `remote-cli-url` flag with env var +- Improve error handling in client CLI + ## [0.0.0.33] - 2023-06-13 - Renamed `NewRPCPeerstoreProvider()` and `NewPersistencePeerstoreProvider()` to `Create()` (per package) diff --git a/build/deployments/docker-compose.yaml b/build/deployments/docker-compose.yaml index 76e65f6dc..4c4caab48 100755 --- a/build/deployments/docker-compose.yaml +++ b/build/deployments/docker-compose.yaml @@ -21,7 +21,7 @@ services: dockerfile: ./build/Dockerfile.client environment: # Any host that is visible and connected to the cluster can be arbitrarily selected as the RPC host - - RPC_HOST=validator1 + - POCKET_REMOTE_CLI_URL=http://validator1:50832 volumes: - ${PWD}:/go/src/github.com/pocket-network stdin_open: true diff --git a/build/docs/CHANGELOG.md b/build/docs/CHANGELOG.md index e850683eb..16375d4e4 100644 --- a/build/docs/CHANGELOG.md +++ b/build/docs/CHANGELOG.md @@ -7,6 +7,11 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ## [Unreleased] +## [0.0.0.47] - 2023-06-13 + +- Replaced `RPC_HOST` with `POCKET_REMOTE_CLI_URL` or `--pocket-remote-cli-url` where appropriate +- Added `remote-cli-url` flag to cluster manager & refactored + ## [0.0.0.46] - 2023-06-06 - Renames config files and actor hostnames diff --git a/build/localnet/cluster-manager/main.go b/build/localnet/cluster-manager/main.go index 99acc676b..8fb1004fd 100644 --- a/build/localnet/cluster-manager/main.go +++ b/build/localnet/cluster-manager/main.go @@ -3,12 +3,16 @@ package main import ( "context" "fmt" + "log" "os" "os/exec" "strings" + "github.com/spf13/cobra" + "github.com/spf13/viper" + + "github.com/pokt-network/pocket/app/client/cli/flags" pocketLogger "github.com/pokt-network/pocket/logger" - "github.com/pokt-network/pocket/runtime" "github.com/pokt-network/pocket/runtime/defaults" "github.com/pokt-network/pocket/shared/crypto" pocketk8s "github.com/pokt-network/pocket/shared/k8s" @@ -31,13 +35,45 @@ var ( // autoStakeSkipStakeForValidatorIds is a list of validator ids that should not be auto-staked // it is used to avoid auto-staking the validators that are already staked as part of genesis. autoStakeSkipStakeForValidatorIds = []string{"001", "002", "003", "004"} + + clusterManagerCmd = &cobra.Command{ + Use: "cluster-manager", + Short: "Start the Pocket Network Cluster Manager service", + Long: `Start the Pocket Network Cluster Manager service which listens for and reacts to events coming over the k8s.io API's watch.Interface#ResultChan(). + +See the following k8s.io documentation for more information: +- https://pkg.go.dev/k8s.io/client-go/kubernetes/typed/core/v1@v0.26.1#ServiceInterface +- https://pkg.go.dev/k8s.io/apimachinery/pkg/watch#Interface, +- https://pkg.go.dev/k8s.io/apimachinery/pkg/watch#Event`, + Run: runClusterManagerCmd, + Args: cobra.ExactArgs(0), + } ) func init() { - rpcURL = fmt.Sprintf("http://%s:%s", runtime.GetEnv("RPC_HOST", defaults.Validator1EndpointK8S), defaults.DefaultRPCPort) + // setup the `remote_cli_url` flag to be consistent with the CLI except for + // the default, which is set to the URL of the first k8s validator's RPC + // endpoint. + clusterManagerCmd.PersistentFlags().StringVar( + &flags.RemoteCLIURL, + "remote_cli_url", + defaults.Validator1EndpointK8SHostname, + "takes a remote endpoint in the form of ://: (uses RPC Port)", + ) + + // ensure that the env var can override the flag + if err := viper.BindPFlag("remote_cli_url", clusterManagerCmd.PersistentFlags().Lookup("remote_cli_url")); err != nil { + log.Fatalf("Error binding remote_cli_url flag: %v", err) + } } func main() { + if err := clusterManagerCmd.Execute(); err != nil { + log.Fatalf("Error executing cluster-manager command: %v", err) + } +} + +func runClusterManagerCmd(_ *cobra.Command, _ []string) { config, err := rest.InClusterConfig() if err != nil { panic(err.Error()) diff --git a/build/localnet/manifests/cli-client.yaml b/build/localnet/manifests/cli-client.yaml index 7acf3e5a7..719668ac6 100644 --- a/build/localnet/manifests/cli-client.yaml +++ b/build/localnet/manifests/cli-client.yaml @@ -74,8 +74,8 @@ spec: - name: POCKET_PERSISTENCE_NODE_SCHEMA value: validator1 # Any host that is visible and connected to the cluster can be arbitrarily selected as the RPC host - - name: RPC_HOST - value: full-node-001-pocket + - name: POCKET_REMOTE_CLI_URL + value: http://full-node-001-pocket:50832 # TECHDEBT(#678): debug client requires hostname to participate # in P2P networking. - name: POCKET_P2P_HOSTNAME diff --git a/build/localnet/manifests/cluster-manager.yaml b/build/localnet/manifests/cluster-manager.yaml index c06c59a4a..b2a4d7362 100644 --- a/build/localnet/manifests/cluster-manager.yaml +++ b/build/localnet/manifests/cluster-manager.yaml @@ -19,8 +19,8 @@ spec: args: - cluster-manager env: - - name: RPC_HOST - value: pocket-full-nodes + - name: POCKET_REMOTE_CLI_URL + value: http://pocket-full-nodes:50832 serviceAccountName: cluster-manager --- apiVersion: v1 diff --git a/e2e/docs/CHANGELOG.md b/e2e/docs/CHANGELOG.md index 226ce1424..67ee382cf 100644 --- a/e2e/docs/CHANGELOG.md +++ b/e2e/docs/CHANGELOG.md @@ -7,6 +7,16 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ## [Unreleased] +## [0.0.0.9] - 2023-06-13 + +- Replaced RPC_HOST with POCKET_REMOTE_CLI_URL where appropriate +- Added `remote-cli-url` flag to cluster manager & refactor +- Added support for overriding of `remote-cli-url` flag with env var +- Append "Hostname" to validator endpoint hostname constants +- Promoted string literal to `RandomValidatorEndpointK8SHostname` constant +- Improved e2e tests error messaging +- Simplify e2e debug command calls + ## [0.0.0.8] - 2023-05-31 - Adds the query feature file diff --git a/e2e/tests/steps_init_test.go b/e2e/tests/steps_init_test.go index 90ad39b6c..f981f5793 100644 --- a/e2e/tests/steps_init_test.go +++ b/e2e/tests/steps_init_test.go @@ -71,7 +71,7 @@ func TestFeatures(t *testing.T) { func (s *rootSuite) TheUserHasAValidator() { res, err := s.validator.RunCommand("help") - require.NoError(s, err) + require.NoErrorf(s, err, res.Stderr) s.validator.result = res } @@ -104,8 +104,6 @@ func (s *rootSuite) TheUserSendsUpoktToAnotherAddress(amount int64) { privKey := s.getPrivateKey(validatorA) valB := s.getPrivateKey(validatorB) args := []string{ - "--non_interactive=true", - "--remote_cli_url=" + rpcURL, "Account", "Send", privKey.Address().String(), @@ -122,8 +120,6 @@ func (s *rootSuite) TheUserSendsUpoktToAnotherAddress(amount int64) { func (s *rootSuite) stakeValidator(privKey cryptoPocket.PrivateKey, amount string) { validatorServiceUrl := fmt.Sprintf(validatorServiceURLTmpl, validatorA, defaults.DefaultP2PPort) args := []string{ - "--non_interactive=true", - "--remote_cli_url=" + rpcURL, "Validator", "Stake", privKey.Address().String(), @@ -141,8 +137,6 @@ func (s *rootSuite) stakeValidator(privKey cryptoPocket.PrivateKey, amount strin func (s *rootSuite) unstakeValidator() { privKey := s.getPrivateKey(validatorA) args := []string{ - "--non_interactive=true", - "--remote_cli_url=" + rpcURL, "Validator", "Unstake", privKey.Address().String(), diff --git a/e2e/tests/validator.go b/e2e/tests/validator.go index 9dc032773..04b27bf7f 100644 --- a/e2e/tests/validator.go +++ b/e2e/tests/validator.go @@ -18,7 +18,8 @@ var ( ) func init() { - rpcURL = fmt.Sprintf("http://%s:%s", runtime.GetEnv("RPC_HOST", "pocket-validators"), defaults.DefaultRPCPort) + rpcHost := runtime.GetEnv("RPC_HOST", defaults.RandomValidatorEndpointK8SHostname) + rpcURL = fmt.Sprintf("http://%s:%s", rpcHost, defaults.DefaultRPCPort) } // cliPath is the path of the binary installed and is set by the Tiltfile diff --git a/p2p/CHANGELOG.md b/p2p/CHANGELOG.md index 52c20d3f7..3eedc41aa 100644 --- a/p2p/CHANGELOG.md +++ b/p2p/CHANGELOG.md @@ -7,6 +7,10 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ## [Unreleased] +## [0.0.0.55] - 2023-06-13 + +- Replaced `RPC_HOST` with `POCKET_REMOTE_CLI_URL` or `--pocket-remote-cli-url` where appropriate + ## [0.0.0.54] - 2023-06-13 - Replaced embedded `modules.Module` with simpler `modules.IntegratableModule` in `PeerstoreProvider` interface diff --git a/p2p/providers/current_height_provider/rpc/provider.go b/p2p/providers/current_height_provider/rpc/provider.go index 97470d52b..4e88de6c2 100644 --- a/p2p/providers/current_height_provider/rpc/provider.go +++ b/p2p/providers/current_height_provider/rpc/provider.go @@ -2,27 +2,18 @@ package rpc import ( "context" - "fmt" "log" "net/http" "time" + "github.com/pokt-network/pocket/app/client/cli/flags" "github.com/pokt-network/pocket/p2p/providers/current_height_provider" "github.com/pokt-network/pocket/rpc" - "github.com/pokt-network/pocket/runtime" - "github.com/pokt-network/pocket/runtime/defaults" "github.com/pokt-network/pocket/shared/modules" "github.com/pokt-network/pocket/shared/modules/base_modules" ) -var ( - _ current_height_provider.CurrentHeightProvider = &rpcCurrentHeightProvider{} - rpcHost string -) - -func init() { - rpcHost = runtime.GetEnv("RPC_HOST", defaults.DefaultRPCHost) -} +var _ current_height_provider.CurrentHeightProvider = &rpcCurrentHeightProvider{} type rpcCurrentHeightProvider struct { base_modules.IntegratableModule @@ -65,7 +56,7 @@ func (rchp *rpcCurrentHeightProvider) CurrentHeight() uint64 { func NewRPCCurrentHeightProvider(options ...modules.ModuleOption) *rpcCurrentHeightProvider { rchp := &rpcCurrentHeightProvider{ - rpcURL: fmt.Sprintf("http://%s:%s", rpcHost, defaults.DefaultRPCPort), // TODO: Make port configurable + rpcURL: flags.RemoteCLIURL, } for _, o := range options { diff --git a/p2p/providers/peerstore_provider/persistence/provider.go b/p2p/providers/peerstore_provider/persistence/provider.go index 2b818ae01..ce43dcf3d 100644 --- a/p2p/providers/peerstore_provider/persistence/provider.go +++ b/p2p/providers/peerstore_provider/persistence/provider.go @@ -25,15 +25,15 @@ func Create(bus modules.Bus, options ...persistencePStoreProviderOption) (peerst } func (*persistencePeerstoreProvider) Create(bus modules.Bus, options ...persistencePStoreProviderOption) (peerstore_provider.PeerstoreProvider, error) { - pabp := &persistencePeerstoreProvider{ + persistencePSP := &persistencePeerstoreProvider{ IntegratableModule: *base_modules.NewIntegratableModule(bus), } for _, o := range options { - o(pabp) + o(persistencePSP) } - return pabp, nil + return persistencePSP, nil } func (*persistencePeerstoreProvider) GetModuleName() string { diff --git a/p2p/providers/peerstore_provider/rpc/provider.go b/p2p/providers/peerstore_provider/rpc/provider.go index 3fb12f3b5..ce8210fc7 100644 --- a/p2p/providers/peerstore_provider/rpc/provider.go +++ b/p2p/providers/peerstore_provider/rpc/provider.go @@ -7,26 +7,17 @@ import ( "net/http" "time" + "github.com/pokt-network/pocket/app/client/cli/flags" "github.com/pokt-network/pocket/p2p/providers/peerstore_provider" typesP2P "github.com/pokt-network/pocket/p2p/types" "github.com/pokt-network/pocket/rpc" - "github.com/pokt-network/pocket/runtime" "github.com/pokt-network/pocket/runtime/configs" - "github.com/pokt-network/pocket/runtime/defaults" "github.com/pokt-network/pocket/shared/core/types" "github.com/pokt-network/pocket/shared/modules" "github.com/pokt-network/pocket/shared/modules/base_modules" ) -var ( - _ peerstore_provider.PeerstoreProvider = &rpcPeerstoreProvider{} - rpcHost string -) - -func init() { - // by default, we point at the same endpoint used by the CLI but the debug client is used either in docker-compose of K8S, therefore we cater for overriding - rpcHost = runtime.GetEnv("RPC_HOST", defaults.DefaultRPCHost) -} +var _ peerstore_provider.PeerstoreProvider = &rpcPeerstoreProvider{} // TECHDEBT(#810): refactor to implement `Submodule` interface. type rpcPeerstoreProvider struct { @@ -41,7 +32,7 @@ type rpcPeerstoreProvider struct { func Create(options ...modules.ModuleOption) *rpcPeerstoreProvider { rabp := &rpcPeerstoreProvider{ - rpcURL: fmt.Sprintf("http://%s:%s", rpcHost, defaults.DefaultRPCPort), // TODO: Make port configurable + rpcURL: flags.RemoteCLIURL, } for _, o := range options { diff --git a/runtime/defaults/defaults.go b/runtime/defaults/defaults.go index bc1ddcca2..586628cf9 100644 --- a/runtime/defaults/defaults.go +++ b/runtime/defaults/defaults.go @@ -23,11 +23,12 @@ func initDefaultRootDirectory() { } const ( - DefaultRPCPort = "50832" - DefaultBusBufferSize = 100 - DefaultRPCHost = "localhost" - Validator1EndpointDockerCompose = "validator1" - Validator1EndpointK8S = "validator-001-pocket" + DefaultRPCPort = "50832" + DefaultBusBufferSize = 100 + DefaultRPCHost = "localhost" + Validator1EndpointDockerComposeHostname = "validator1" + Validator1EndpointK8SHostname = "validator-001-pocket" + RandomValidatorEndpointK8SHostname = "pocket-validators" ) var ( @@ -78,7 +79,7 @@ var ( // // In LocalNet, the developer will have only one of the two stack online, therefore this is also a poor's man way to simulate the scenario in which a boostrap node is offline. DefaultP2PBootstrapNodesCsv = fmt.Sprintf("%s,%s", - fmt.Sprintf("http://%s:%s", Validator1EndpointDockerCompose, DefaultRPCPort), - fmt.Sprintf("http://%s:%s", Validator1EndpointK8S, DefaultRPCPort), + fmt.Sprintf("http://%s:%s", Validator1EndpointDockerComposeHostname, DefaultRPCPort), + fmt.Sprintf("http://%s:%s", Validator1EndpointK8SHostname, DefaultRPCPort), ) ) diff --git a/runtime/docs/CHANGELOG.md b/runtime/docs/CHANGELOG.md index 0b09856bd..98206c2d4 100644 --- a/runtime/docs/CHANGELOG.md +++ b/runtime/docs/CHANGELOG.md @@ -7,6 +7,11 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ## [Unreleased] +## [0.0.0.42] - 2023-06-13 + +- Append "Hostname" to validator endpoint hostname constants +- Promoted string literal to `RandomValidatorEndpointK8SHostname` constant + ## [0.0.0.41] - 2023-06-06 - Adds fisherman and servicer proto configurations.