77 lines
1.8 KiB
Go
77 lines
1.8 KiB
Go
package walletsource
|
|
|
|
import (
|
|
"context"
|
|
"errors"
|
|
"fmt"
|
|
|
|
"git.frostfs.info/TrueCloudLab/frostfs-s3-lifecycler/internal/lifecycle"
|
|
"github.com/nspcc-dev/neo-go/cli/flags"
|
|
"github.com/nspcc-dev/neo-go/pkg/crypto/keys"
|
|
"github.com/nspcc-dev/neo-go/pkg/encoding/address"
|
|
"github.com/nspcc-dev/neo-go/pkg/util"
|
|
"github.com/nspcc-dev/neo-go/pkg/wallet"
|
|
)
|
|
|
|
type Source struct {
|
|
keys []*keys.PrivateKey
|
|
}
|
|
|
|
type Wallet struct {
|
|
Path string
|
|
Address string
|
|
Passphrase string
|
|
}
|
|
|
|
var _ lifecycle.CredentialSource = (*Source)(nil)
|
|
|
|
func New(wallets []Wallet) (*Source, error) {
|
|
privateKeys := make([]*keys.PrivateKey, len(wallets))
|
|
|
|
var err error
|
|
for i, w := range wallets {
|
|
if privateKeys[i], err = readPrivateKey(w); err != nil {
|
|
return nil, fmt.Errorf("read private key from wallet '%s': %w", w.Path, err)
|
|
}
|
|
}
|
|
|
|
return &Source{keys: privateKeys}, nil
|
|
}
|
|
|
|
func (s *Source) Credentials(_ context.Context, pk *keys.PublicKey) (*keys.PrivateKey, error) {
|
|
for _, key := range s.keys {
|
|
if key.PublicKey().Equal(pk) {
|
|
return key, nil
|
|
}
|
|
}
|
|
|
|
return nil, errors.New("key not found")
|
|
}
|
|
|
|
func readPrivateKey(walletInfo Wallet) (*keys.PrivateKey, error) {
|
|
w, err := wallet.NewWalletFromFile(walletInfo.Path)
|
|
if err != nil {
|
|
return nil, fmt.Errorf("parse wallet: %w", err)
|
|
}
|
|
|
|
var addr util.Uint160
|
|
if walletInfo.Address == "" {
|
|
addr = w.GetChangeAddress()
|
|
} else {
|
|
addr, err = flags.ParseAddress(walletInfo.Address)
|
|
if err != nil {
|
|
return nil, fmt.Errorf("invalid address")
|
|
}
|
|
}
|
|
|
|
acc := w.GetAccount(addr)
|
|
if acc == nil {
|
|
return nil, fmt.Errorf("couldn't find wallet account for %s", address.Uint160ToString(addr))
|
|
}
|
|
|
|
if err = acc.Decrypt(walletInfo.Passphrase, w.Scrypt); err != nil {
|
|
return nil, fmt.Errorf("couldn't decrypt account: %w", err)
|
|
}
|
|
|
|
return acc.PrivateKey(), nil
|
|
}
|