cmd, console: password input fixes #20960 (#1524)

This commit is contained in:
Daniel Liu 2025-09-21 18:59:34 +08:00 committed by GitHub
parent 94a85f4162
commit 5ad87e559f
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
8 changed files with 39 additions and 34 deletions

View file

@ -23,7 +23,7 @@ import (
"github.com/XinFinOrg/XDPoSChain/accounts" "github.com/XinFinOrg/XDPoSChain/accounts"
"github.com/XinFinOrg/XDPoSChain/accounts/keystore" "github.com/XinFinOrg/XDPoSChain/accounts/keystore"
"github.com/XinFinOrg/XDPoSChain/cmd/utils" "github.com/XinFinOrg/XDPoSChain/cmd/utils"
"github.com/XinFinOrg/XDPoSChain/console" prompt2 "github.com/XinFinOrg/XDPoSChain/console/prompt"
"github.com/XinFinOrg/XDPoSChain/crypto" "github.com/XinFinOrg/XDPoSChain/crypto"
"github.com/XinFinOrg/XDPoSChain/log" "github.com/XinFinOrg/XDPoSChain/log"
"github.com/urfave/cli/v2" "github.com/urfave/cli/v2"
@ -268,12 +268,12 @@ func getPassPhrase(prompt string, confirmation bool, i int, passwords []string)
if prompt != "" { if prompt != "" {
fmt.Println(prompt) fmt.Println(prompt)
} }
password, err := console.Stdin.PromptPassword("Passphrase: ") password, err := prompt2.Stdin.PromptPassword("Passphrase: ")
if err != nil { if err != nil {
utils.Fatalf("Failed to read passphrase: %v", err) utils.Fatalf("Failed to read passphrase: %v", err)
} }
if confirmation { if confirmation {
confirm, err := console.Stdin.PromptPassword("Repeat passphrase: ") confirm, err := prompt2.Stdin.PromptPassword("Repeat passphrase: ")
if err != nil { if err != nil {
utils.Fatalf("Failed to read passphrase confirmation: %v", err) utils.Fatalf("Failed to read passphrase confirmation: %v", err)
} }

View file

@ -26,7 +26,7 @@ import (
"github.com/XinFinOrg/XDPoSChain/cmd/utils" "github.com/XinFinOrg/XDPoSChain/cmd/utils"
"github.com/XinFinOrg/XDPoSChain/common" "github.com/XinFinOrg/XDPoSChain/common"
"github.com/XinFinOrg/XDPoSChain/common/hexutil" "github.com/XinFinOrg/XDPoSChain/common/hexutil"
"github.com/XinFinOrg/XDPoSChain/console" "github.com/XinFinOrg/XDPoSChain/console/prompt"
"github.com/XinFinOrg/XDPoSChain/core/rawdb" "github.com/XinFinOrg/XDPoSChain/core/rawdb"
"github.com/XinFinOrg/XDPoSChain/ethdb" "github.com/XinFinOrg/XDPoSChain/ethdb"
"github.com/XinFinOrg/XDPoSChain/log" "github.com/XinFinOrg/XDPoSChain/log"
@ -153,7 +153,7 @@ func removeFolder(dir string) {
// confirmAndRemoveDB prompts the user for a last confirmation and removes the // confirmAndRemoveDB prompts the user for a last confirmation and removes the
// folder if accepted. // folder if accepted.
func confirmAndRemoveDB(path string, kind string) { func confirmAndRemoveDB(path string, kind string) {
confirm, err := console.Stdin.PromptConfirm(fmt.Sprintf("Remove %s (%s)?", kind, path)) confirm, err := prompt.Stdin.PromptConfirm(fmt.Sprintf("Remove %s (%s)?", kind, path))
switch { switch {
case err != nil: case err != nil:
utils.Fatalf("%v", err) utils.Fatalf("%v", err)

View file

@ -29,7 +29,7 @@ import (
"github.com/XinFinOrg/XDPoSChain/accounts/keystore" "github.com/XinFinOrg/XDPoSChain/accounts/keystore"
"github.com/XinFinOrg/XDPoSChain/cmd/utils" "github.com/XinFinOrg/XDPoSChain/cmd/utils"
"github.com/XinFinOrg/XDPoSChain/consensus/XDPoS" "github.com/XinFinOrg/XDPoSChain/consensus/XDPoS"
"github.com/XinFinOrg/XDPoSChain/console" "github.com/XinFinOrg/XDPoSChain/console/prompt"
"github.com/XinFinOrg/XDPoSChain/core" "github.com/XinFinOrg/XDPoSChain/core"
"github.com/XinFinOrg/XDPoSChain/eth" "github.com/XinFinOrg/XDPoSChain/eth"
"github.com/XinFinOrg/XDPoSChain/ethclient" "github.com/XinFinOrg/XDPoSChain/ethclient"
@ -246,7 +246,7 @@ func init() {
app.After = func(ctx *cli.Context) error { app.After = func(ctx *cli.Context) error {
debug.Exit() debug.Exit()
console.Stdin.Close() // Resets terminal mode. prompt.Stdin.Close() // Resets terminal mode.
return nil return nil
} }
} }

View file

@ -23,7 +23,7 @@ import (
"strings" "strings"
"github.com/XinFinOrg/XDPoSChain/cmd/utils" "github.com/XinFinOrg/XDPoSChain/cmd/utils"
"github.com/XinFinOrg/XDPoSChain/console" "github.com/XinFinOrg/XDPoSChain/console/prompt"
"github.com/XinFinOrg/XDPoSChain/crypto" "github.com/XinFinOrg/XDPoSChain/crypto"
"github.com/urfave/cli/v2" "github.com/urfave/cli/v2"
) )
@ -44,12 +44,12 @@ func getPassPhrase(ctx *cli.Context, confirmation bool) string {
} }
// Otherwise prompt the user for the passphrase. // Otherwise prompt the user for the passphrase.
passphrase, err := console.Stdin.PromptPassword("Passphrase: ") passphrase, err := prompt.Stdin.PromptPassword("Passphrase: ")
if err != nil { if err != nil {
utils.Fatalf("Failed to read passphrase: %v", err) utils.Fatalf("Failed to read passphrase: %v", err)
} }
if confirmation { if confirmation {
confirm, err := console.Stdin.PromptPassword("Repeat passphrase: ") confirm, err := prompt.Stdin.PromptPassword("Repeat passphrase: ")
if err != nil { if err != nil {
utils.Fatalf("Failed to read passphrase confirmation: %v", err) utils.Fatalf("Failed to read passphrase confirmation: %v", err)
} }

View file

@ -25,6 +25,7 @@ import (
"time" "time"
"github.com/XinFinOrg/XDPoSChain/common/hexutil" "github.com/XinFinOrg/XDPoSChain/common/hexutil"
"github.com/XinFinOrg/XDPoSChain/console/prompt"
"github.com/XinFinOrg/XDPoSChain/internal/jsre" "github.com/XinFinOrg/XDPoSChain/internal/jsre"
"github.com/XinFinOrg/XDPoSChain/rpc" "github.com/XinFinOrg/XDPoSChain/rpc"
"github.com/dop251/goja" "github.com/dop251/goja"
@ -33,13 +34,13 @@ import (
// bridge is a collection of JavaScript utility methods to bride the .js runtime // bridge is a collection of JavaScript utility methods to bride the .js runtime
// environment and the Go RPC connection backing the remote method calls. // environment and the Go RPC connection backing the remote method calls.
type bridge struct { type bridge struct {
client *rpc.Client // RPC client to execute Ethereum requests through client *rpc.Client // RPC client to execute Ethereum requests through
prompter UserPrompter // Input prompter to allow interactive user feedback prompter prompt.UserPrompter // Input prompter to allow interactive user feedback
printer io.Writer // Output writer to serialize any display strings to printer io.Writer // Output writer to serialize any display strings to
} }
// newBridge creates a new JavaScript wrapper around an RPC client. // newBridge creates a new JavaScript wrapper around an RPC client.
func newBridge(client *rpc.Client, prompter UserPrompter, printer io.Writer) *bridge { func newBridge(client *rpc.Client, prompter prompt.UserPrompter, printer io.Writer) *bridge {
return &bridge{ return &bridge{
client: client, client: client,
prompter: prompter, prompter: prompter,

View file

@ -27,6 +27,7 @@ import (
"strings" "strings"
"syscall" "syscall"
"github.com/XinFinOrg/XDPoSChain/console/prompt"
"github.com/XinFinOrg/XDPoSChain/internal/jsre" "github.com/XinFinOrg/XDPoSChain/internal/jsre"
"github.com/XinFinOrg/XDPoSChain/internal/jsre/deps" "github.com/XinFinOrg/XDPoSChain/internal/jsre/deps"
"github.com/XinFinOrg/XDPoSChain/internal/web3ext" "github.com/XinFinOrg/XDPoSChain/internal/web3ext"
@ -51,26 +52,26 @@ const DefaultPrompt = "> "
// Config is the collection of configurations to fine tune the behavior of the // Config is the collection of configurations to fine tune the behavior of the
// JavaScript console. // JavaScript console.
type Config struct { type Config struct {
DataDir string // Data directory to store the console history at DataDir string // Data directory to store the console history at
DocRoot string // Filesystem path from where to load JavaScript files from DocRoot string // Filesystem path from where to load JavaScript files from
Client *rpc.Client // RPC client to execute Ethereum requests through Client *rpc.Client // RPC client to execute Ethereum requests through
Prompt string // Input prompt prefix string (defaults to DefaultPrompt) Prompt string // Input prompt prefix string (defaults to DefaultPrompt)
Prompter UserPrompter // Input prompter to allow interactive user feedback (defaults to TerminalPrompter) Prompter prompt.UserPrompter // Input prompter to allow interactive user feedback (defaults to TerminalPrompter)
Printer io.Writer // Output writer to serialize any display strings to (defaults to os.Stdout) Printer io.Writer // Output writer to serialize any display strings to (defaults to os.Stdout)
Preload []string // Absolute paths to JavaScript files to preload Preload []string // Absolute paths to JavaScript files to preload
} }
// Console is a JavaScript interpreted runtime environment. It is a fully fleged // Console is a JavaScript interpreted runtime environment. It is a fully fleged
// JavaScript console attached to a running node via an external or in-process RPC // JavaScript console attached to a running node via an external or in-process RPC
// client. // client.
type Console struct { type Console struct {
client *rpc.Client // RPC client to execute Ethereum requests through client *rpc.Client // RPC client to execute Ethereum requests through
jsre *jsre.JSRE // JavaScript runtime environment running the interpreter jsre *jsre.JSRE // JavaScript runtime environment running the interpreter
prompt string // Input prompt prefix string prompt string // Input prompt prefix string
prompter UserPrompter // Input prompter to allow interactive user feedback prompter prompt.UserPrompter // Input prompter to allow interactive user feedback
histPath string // Absolute path to the console scrollback history histPath string // Absolute path to the console scrollback history
history []string // Scroll history maintained by the console history []string // Scroll history maintained by the console
printer io.Writer // Output writer to serialize any display strings to printer io.Writer // Output writer to serialize any display strings to
} }
// New initializes a JavaScript interpreted runtime environment and sets defaults // New initializes a JavaScript interpreted runtime environment and sets defaults
@ -78,7 +79,7 @@ type Console struct {
func New(config Config) (*Console, error) { func New(config Config) (*Console, error) {
// Handle unset config values gracefully // Handle unset config values gracefully
if config.Prompter == nil { if config.Prompter == nil {
config.Prompter = Stdin config.Prompter = prompt.Stdin
} }
if config.Prompt == "" { if config.Prompt == "" {
config.Prompt = DefaultPrompt config.Prompt = DefaultPrompt

View file

@ -27,6 +27,7 @@ import (
"github.com/XinFinOrg/XDPoSChain/XDCx" "github.com/XinFinOrg/XDPoSChain/XDCx"
"github.com/XinFinOrg/XDPoSChain/XDCxlending" "github.com/XinFinOrg/XDPoSChain/XDCxlending"
"github.com/XinFinOrg/XDPoSChain/common" "github.com/XinFinOrg/XDPoSChain/common"
"github.com/XinFinOrg/XDPoSChain/console/prompt"
"github.com/XinFinOrg/XDPoSChain/core" "github.com/XinFinOrg/XDPoSChain/core"
"github.com/XinFinOrg/XDPoSChain/eth" "github.com/XinFinOrg/XDPoSChain/eth"
"github.com/XinFinOrg/XDPoSChain/eth/ethconfig" "github.com/XinFinOrg/XDPoSChain/eth/ethconfig"
@ -63,13 +64,15 @@ func (p *hookedPrompter) PromptInput(prompt string) (string, error) {
func (p *hookedPrompter) PromptPassword(prompt string) (string, error) { func (p *hookedPrompter) PromptPassword(prompt string) (string, error) {
return "", errors.New("not implemented") return "", errors.New("not implemented")
} }
func (p *hookedPrompter) PromptConfirm(prompt string) (bool, error) { func (p *hookedPrompter) PromptConfirm(prompt string) (bool, error) {
return false, errors.New("not implemented") return false, errors.New("not implemented")
} }
func (p *hookedPrompter) SetHistory(history []string) {}
func (p *hookedPrompter) AppendHistory(command string) {} func (p *hookedPrompter) SetHistory(history []string) {}
func (p *hookedPrompter) ClearHistory() {} func (p *hookedPrompter) AppendHistory(command string) {}
func (p *hookedPrompter) SetWordCompleter(completer WordCompleter) {} func (p *hookedPrompter) ClearHistory() {}
func (p *hookedPrompter) SetWordCompleter(completer prompt.WordCompleter) {}
// tester is a console test environment for the console tests to operate on. // tester is a console test environment for the console tests to operate on.
type tester struct { type tester struct {

View file

@ -14,7 +14,7 @@
// You should have received a copy of the GNU Lesser General Public License // You should have received a copy of the GNU Lesser General Public License
// along with the go-ethereum library. If not, see <http://www.gnu.org/licenses/>. // along with the go-ethereum library. If not, see <http://www.gnu.org/licenses/>.
package console package prompt
import ( import (
"fmt" "fmt"