diff --git a/README.md b/README.md index 1660cfcd..0c962c79 100644 --- a/README.md +++ b/README.md @@ -127,28 +127,58 @@ token the object needs to be stored in a container available for the gateway to read and it needs to be encrypted with this gateway's key (among others potentially). -#### Generation of key pairs +#### Generation of wallet -To generate neofs key pairs for gateways, run the following command (`--count` is 1 -by default): +To generate wallets for gateways, run the following command: ``` -$ ./neofs-authmate generate-keys --count=2 +$ ./neo-go wallet init -a -w wallet.json -[ - { - "private_key": "b8ba980eb70b959be99915d2e0ad377809984ccd1dac0a6551907f81c2b33d21", - "public_key": "dd34f6dce9a4ce0990869ec6bd33a40e102a5798881cfe61d03a5659ceee1a64" - }, - { - "private_key": "407c351b17446ca07521faceb8b7d3e738319635f39f892419e2bf94462b4419", - "public_key": "20453af9d7f245ff6fdfb1260eaa411ae3be9c519a2a9bf1c98233522cbd0156" - } -] +Enter the name of the account > AccountTestName +Enter passphrase > +Confirm passphrase > + +{ + "version": "3.0", + "accounts": [ + { + "address": "NhLQpDnerpviUWDF77j5qyjFgavCmasJ4p", + "key": "6PYUFyYpJ1JGyMrYV8NqeUFLKfpEVHsGGjCYtTDkjnKaSgYizRBZxVerte", + "label": "AccountTestName", + "contract": { + "script": "DCECXCsUZPwUyKHs6nAyyCvJ5s/vLwZkkVtWNC0zWzH8a9dBVuezJw==", + "parameters": [ + { + "name": "parameter0", + "type": "Signature" + } + ], + "deployed": false + }, + "lock": false, + "isDefault": false + } + ], + "scrypt": { + "n": 16384, + "r": 8, + "p": 8 + }, + "extra": { + "Tokens": null + } + } + +wallet successfully created, file location is wallet.json ``` -Private key is the one to use for `neofs-s3-gw` command, public one can be -used to create new AWS credentials. +To get public key from wallet run: +``` +$ ./bin/neo-go wallet dump-keys -w wallet.json + +NhLQpDnerpviUWDF77j5qyjFgavCmasJ4p (simple signature contract): +025c2b1464fc14c8a1ecea7032c82bc9e6cfef2f0664915b56342d335b31fc6bd7 +``` #### Issuance of a secret diff --git a/cmd/authmate/main.go b/cmd/authmate/main.go index 99a5591d..7a6a7c94 100644 --- a/cmd/authmate/main.go +++ b/cmd/authmate/main.go @@ -3,10 +3,6 @@ package main import ( "context" "crypto/ecdsa" - "crypto/elliptic" - "crypto/rand" - "encoding/hex" - "encoding/json" "fmt" "os" "os/signal" @@ -24,11 +20,6 @@ import ( "go.uber.org/zap/zapcore" ) -type gateKey struct { - PrivateKey string `json:"private_key"` - PublicKey string `json:"public_key"` -} - const ( poolConnectTimeout = 5 * time.Second poolRequestTimeout = 5 * time.Second @@ -44,7 +35,6 @@ var ( containerIDFlag string containerFriendlyName string gatesPublicKeysFlag cli.StringSlice - gatesKeysCountFlag int logEnabledFlag bool logDebugEnabledFlag bool sessionTokenFlag bool @@ -120,63 +110,6 @@ func appCommands() []*cli.Command { return []*cli.Command{ issueSecret(), obtainSecret(), - generateKeys(), - } -} - -func generateGatesKeys(count int) ([]*ecdsa.PrivateKey, error) { - var ( - err error - res = make([]*ecdsa.PrivateKey, count) - ) - - for i := 0; i < count; i++ { - if res[i], err = ecdsa.GenerateKey(elliptic.P256(), rand.Reader); err != nil { - return nil, err - } - } - - return res, nil -} - -func generateKeys() *cli.Command { - return &cli.Command{ - Name: "generate-keys", - Usage: "Generate key pairs for gates", - Flags: []cli.Flag{ - &cli.IntFlag{ - Name: "count", - Usage: "number of 256r1 key pairs to generate", - Value: 1, - Destination: &gatesKeysCountFlag, - }, - }, - Action: func(c *cli.Context) error { - _, log := prepare() - - log.Info("start generating P-256 keys") - - csl, err := generateGatesKeys(gatesKeysCountFlag) - if err != nil { - return cli.Exit(fmt.Sprintf("failed to create key pairs of gates: %s", err), 1) - } - - log.Info("generated P-256 keys") - - gatesKeys := make([]gateKey, len(csl)) - for i, cs := range csl { - privateKey, publicKey := hex.EncodeToString(cs.D.Bytes()), hex.EncodeToString(crypto.MarshalPublicKey(&cs.PublicKey)) - gatesKeys[i] = gateKey{PrivateKey: privateKey, PublicKey: publicKey} - } - - keys, err := json.MarshalIndent(gatesKeys, "", " ") - if err != nil { - return cli.Exit(fmt.Sprintf("failed to marshal key pairs of gates: %s", err), 2) - } - - fmt.Println(string(keys)) - return nil - }, } } diff --git a/cmd/s3-gw/app.go b/cmd/s3-gw/app.go index 5945bfd5..de687b69 100644 --- a/cmd/s3-gw/app.go +++ b/cmd/s3-gw/app.go @@ -2,7 +2,6 @@ package main import ( "context" - "crypto/ecdsa" "encoding/hex" "fmt" "math" @@ -10,10 +9,10 @@ import ( "net/http" "github.com/nspcc-dev/neo-go/cli/flags" + "github.com/nspcc-dev/neo-go/cli/input" + "github.com/nspcc-dev/neo-go/pkg/crypto/keys" "github.com/nspcc-dev/neo-go/pkg/util" "github.com/nspcc-dev/neo-go/pkg/wallet" - - crypto "github.com/nspcc-dev/neofs-crypto" "github.com/nspcc-dev/neofs-s3-gw/api" "github.com/nspcc-dev/neofs-s3-gw/api/auth" "github.com/nspcc-dev/neofs-s3-gw/api/handler" @@ -49,7 +48,7 @@ type ( func newApp(ctx context.Context, l *zap.Logger, v *viper.Viper) *App { var ( conns pool.Pool - key *ecdsa.PrivateKey + key *keys.PrivateKey err error tls *tlsConfig caller api.Handler @@ -86,7 +85,12 @@ func newApp(ctx context.Context, l *zap.Logger, v *viper.Viper) *App { reBalance = v } - if key, err = getKeyFromWallet(v.GetString(cfgWallet), v.GetString(cfgAddress), v.GetString(cfgWalletPassphrase)); err != nil { + var password *string + if v.IsSet(cfgWalletPassphrase) { + pwd := v.GetString(cfgWalletPassphrase) + password = &pwd + } + if key, err = getKeyFromWallet(v.GetString(cfgWallet), v.GetString(cfgAddress), password); err != nil { l.Fatal("could not load NeoFS private key", zap.Error(err)) } @@ -98,10 +102,10 @@ func newApp(ctx context.Context, l *zap.Logger, v *viper.Viper) *App { } l.Info("using credentials", - zap.String("NeoFS", hex.EncodeToString(crypto.MarshalPrivateKey(key)))) + zap.String("NeoFS", hex.EncodeToString(key.PublicKey().Bytes()))) opts := &pool.BuilderOptions{ - Key: key, + Key: &key.PrivateKey, NodeConnectionTimeout: conTimeout, NodeRequestTimeout: reqTimeout, ClientRebalanceInterval: reBalance, @@ -116,7 +120,7 @@ func newApp(ctx context.Context, l *zap.Logger, v *viper.Viper) *App { obj = layer.NewLayer(l, conns) // prepare auth center - ctr = auth.New(conns, key) + ctr = auth.New(conns, &key.PrivateKey) if caller, err = handler.New(l, obj); err != nil { l.Fatal("could not initialize API handler", zap.Error(err)) @@ -138,7 +142,7 @@ func newApp(ctx context.Context, l *zap.Logger, v *viper.Viper) *App { } } -func getKeyFromWallet(walletPath, addrStr, password string) (*ecdsa.PrivateKey, error) { +func getKeyFromWallet(walletPath, addrStr string, password *string) (*keys.PrivateKey, error) { if len(walletPath) == 0 { return nil, fmt.Errorf("wallet path must not be empty") } @@ -162,11 +166,18 @@ func getKeyFromWallet(walletPath, addrStr, password string) (*ecdsa.PrivateKey, return nil, fmt.Errorf("couldn't find wallet account for %s", addrStr) } - if err := acc.Decrypt(password, w.Scrypt); err != nil { + if password == nil { + pwd, err := input.ReadPassword("Enter password > ") + if err != nil { + return nil, fmt.Errorf("couldn't read password") + } + password = &pwd + } + if err := acc.Decrypt(*password, w.Scrypt); err != nil { return nil, fmt.Errorf("couldn't decrypt account: %w", err) } - return &acc.PrivateKey().PrivateKey, nil + return acc.PrivateKey(), nil } // Wait waits for application to finish. diff --git a/go.sum b/go.sum index 7bff9489..419a64c5 100644 --- a/go.sum +++ b/go.sum @@ -648,6 +648,7 @@ golang.org/x/sys v0.0.0-20201214210602-f9fddec55a1e/go.mod h1:h1NjWce9XRLGQEsW7w golang.org/x/sys v0.0.0-20210225134936-a50acf3fe073 h1:8qxJSnu+7dRq6upnbntrmriWByIakBuct5OM/MdQC1M= golang.org/x/sys v0.0.0-20210225134936-a50acf3fe073/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= +golang.org/x/term v0.0.0-20201210144234-2321bbc49cbf h1:MZ2shdL+ZM/XzY3ZGOnh4Nlpnxz5GSOhOmtHo3iPU6M= golang.org/x/term v0.0.0-20201210144234-2321bbc49cbf/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.1-0.20180807135948-17ff2d5776d2/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=