-
Notifications
You must be signed in to change notification settings - Fork 107
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
Showing
75 changed files
with
5,350 additions
and
467 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,97 @@ | ||
// Copyright © 2019, 2020 Weald Technology Trading | ||
// Licensed under the Apache License, Version 2.0 (the "License"); | ||
// you may not use this file except in compliance with the License. | ||
// You may obtain a copy of the License at | ||
// | ||
// http://www.apache.org/licenses/LICENSE-2.0 | ||
// | ||
// Unless required by applicable law or agreed to in writing, software | ||
// distributed under the License is distributed on an "AS IS" BASIS, | ||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
// See the License for the specific language governing permissions and | ||
// limitations under the License. | ||
|
||
package accountcreate | ||
|
||
import ( | ||
"context" | ||
"time" | ||
|
||
"github.com/pkg/errors" | ||
"github.com/spf13/viper" | ||
"github.com/wealdtech/ethdo/core" | ||
"github.com/wealdtech/ethdo/util" | ||
e2wallet "github.com/wealdtech/go-eth2-wallet" | ||
e2wtypes "github.com/wealdtech/go-eth2-wallet-types/v2" | ||
) | ||
|
||
type dataIn struct { | ||
timeout time.Duration | ||
// For all accounts. | ||
wallet e2wtypes.Wallet | ||
accountName string | ||
passphrase string | ||
walletPassphrase string | ||
// For distributed accounts. | ||
participants uint32 | ||
signingThreshold uint32 | ||
// For pathed accounts. | ||
path string | ||
} | ||
|
||
func input(ctx context.Context) (*dataIn, error) { | ||
var err error | ||
data := &dataIn{} | ||
|
||
if viper.GetDuration("timeout") == 0 { | ||
return nil, errors.New("timeout is required") | ||
} | ||
data.timeout = viper.GetDuration("timeout") | ||
|
||
// Account name. | ||
if viper.GetString("account") == "" { | ||
return nil, errors.New("account is required") | ||
} | ||
_, data.accountName, err = e2wallet.WalletAndAccountNames(viper.GetString("account")) | ||
if err != nil { | ||
return nil, errors.Wrap(err, "failed to obtain account name") | ||
} | ||
if data.accountName == "" { | ||
return nil, errors.New("account name is required") | ||
} | ||
|
||
// Wallet. | ||
ctx, cancel := context.WithTimeout(ctx, data.timeout) | ||
defer cancel() | ||
data.wallet, err = core.WalletFromInput(ctx) | ||
cancel() | ||
if err != nil { | ||
return nil, errors.Wrap(err, "failed to obtain wallet") | ||
} | ||
|
||
// Passphrase. | ||
data.passphrase, err = util.GetOptionalPassphrase() | ||
if err != nil { | ||
return nil, errors.Wrap(err, "failed to obtain passphrase") | ||
} | ||
|
||
// Wallet passphrase. | ||
data.walletPassphrase = util.GetWalletPassphrase() | ||
|
||
// Participants. | ||
if viper.GetInt32("participants") == 0 { | ||
return nil, errors.New("participants must be at least one") | ||
} | ||
data.participants = viper.GetUint32("participants") | ||
|
||
// Signing threshold. | ||
if viper.GetInt32("signing-threshold") == 0 { | ||
return nil, errors.New("signing threshold must be at least one") | ||
} | ||
data.signingThreshold = viper.GetUint32("signing-threshold") | ||
|
||
// Path. | ||
data.path = viper.GetString("path") | ||
|
||
return data, nil | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,161 @@ | ||
// Copyright © 2019, 2020 Weald Technology Trading | ||
// Licensed under the Apache License, Version 2.0 (the "License"); | ||
// you may not use this file except in compliance with the License. | ||
// You may obtain a copy of the License at | ||
// | ||
// http://www.apache.org/licenses/LICENSE-2.0 | ||
// | ||
// Unless required by applicable law or agreed to in writing, software | ||
// distributed under the License is distributed on an "AS IS" BASIS, | ||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
// See the License for the specific language governing permissions and | ||
// limitations under the License. | ||
|
||
package accountcreate | ||
|
||
import ( | ||
"context" | ||
"testing" | ||
"time" | ||
|
||
"github.com/spf13/viper" | ||
"github.com/stretchr/testify/require" | ||
e2types "github.com/wealdtech/go-eth2-types/v2" | ||
e2wallet "github.com/wealdtech/go-eth2-wallet" | ||
keystorev4 "github.com/wealdtech/go-eth2-wallet-encryptor-keystorev4" | ||
nd "github.com/wealdtech/go-eth2-wallet-nd/v2" | ||
scratch "github.com/wealdtech/go-eth2-wallet-store-scratch" | ||
e2wtypes "github.com/wealdtech/go-eth2-wallet-types/v2" | ||
) | ||
|
||
func TestInput(t *testing.T) { | ||
require.NoError(t, e2types.InitBLS()) | ||
|
||
store := scratch.New() | ||
require.NoError(t, e2wallet.UseStore(store)) | ||
testWallet, err := nd.CreateWallet(context.Background(), "Test wallet", store, keystorev4.New()) | ||
require.NoError(t, err) | ||
require.NoError(t, testWallet.(e2wtypes.WalletLocker).Unlock(context.Background(), nil)) | ||
|
||
tests := []struct { | ||
name string | ||
vars map[string]interface{} | ||
res *dataIn | ||
err string | ||
}{ | ||
{ | ||
name: "TimeoutMissing", | ||
vars: map[string]interface{}{ | ||
"account": "Test wallet/Test account", | ||
"passphrase": "ce%NohGhah4ye5ra", | ||
}, | ||
err: "timeout is required", | ||
}, | ||
{ | ||
name: "WalletUnknown", | ||
vars: map[string]interface{}{ | ||
"timeout": "5s", | ||
"account": "Unknown/Test account", | ||
"passphrase": "ce%NohGhah4ye5ra", | ||
}, | ||
err: "failed to obtain wallet: wallet not found", | ||
}, | ||
{ | ||
name: "AccountMissing", | ||
vars: map[string]interface{}{ | ||
"timeout": "5s", | ||
"passphrase": "ce%NohGhah4ye5ra", | ||
}, | ||
err: "account is required", | ||
}, | ||
{ | ||
name: "AccountWalletOnly", | ||
vars: map[string]interface{}{ | ||
"timeout": "5s", | ||
"passphrase": "ce%NohGhah4ye5ra", | ||
"account": "Test wallet/", | ||
}, | ||
err: "account name is required", | ||
}, | ||
{ | ||
name: "AccountMalformed", | ||
vars: map[string]interface{}{ | ||
"timeout": "5s", | ||
"account": "//", | ||
"passphrase": "ce%NohGhah4ye5ra", | ||
}, | ||
err: "failed to obtain account name: invalid account format", | ||
}, | ||
{ | ||
name: "MultiplePassphrases", | ||
vars: map[string]interface{}{ | ||
"timeout": "5s", | ||
"account": "Test wallet/Test account", | ||
"passphrase": []string{"ce%NohGhah4ye5ra", "other"}, | ||
"participants": 3, | ||
"signing-threshold": 2, | ||
}, | ||
err: "failed to obtain passphrase: multiple passphrases supplied", | ||
}, | ||
{ | ||
name: "ParticipantsZero", | ||
vars: map[string]interface{}{ | ||
"timeout": "5s", | ||
"account": "Test wallet/Test account", | ||
"passphrase": "ce%NohGhah4ye5ra", | ||
"participants": 0, | ||
"signing-threshold": 2, | ||
}, | ||
err: "participants must be at least one", | ||
}, | ||
{ | ||
name: "SigningThresholdZero", | ||
vars: map[string]interface{}{ | ||
"timeout": "5s", | ||
"account": "Test wallet/Test account", | ||
"passphrase": "ce%NohGhah4ye5ra", | ||
"participants": 3, | ||
"signing-threshold": 0, | ||
}, | ||
err: "signing threshold must be at least one", | ||
}, | ||
{ | ||
name: "Good", | ||
vars: map[string]interface{}{ | ||
"timeout": "5s", | ||
"account": "Test wallet/Test account", | ||
"passphrase": "ce%NohGhah4ye5ra", | ||
"participants": 3, | ||
"signing-threshold": 2, | ||
}, | ||
res: &dataIn{ | ||
timeout: 5 * time.Second, | ||
accountName: "Test account", | ||
passphrase: "ce%NohGhah4ye5ra", | ||
participants: 3, | ||
signingThreshold: 2, | ||
}, | ||
}, | ||
} | ||
|
||
for _, test := range tests { | ||
t.Run(test.name, func(t *testing.T) { | ||
viper.Reset() | ||
for k, v := range test.vars { | ||
viper.Set(k, v) | ||
} | ||
res, err := input(context.Background()) | ||
if test.err != "" { | ||
require.EqualError(t, err, test.err) | ||
} else { | ||
require.NoError(t, err) | ||
// Cannot compare accounts directly, so need to check each element individually. | ||
require.Equal(t, test.res.timeout, res.timeout) | ||
require.Equal(t, test.res.accountName, res.accountName) | ||
require.Equal(t, test.res.passphrase, res.passphrase) | ||
require.Equal(t, test.res.participants, res.participants) | ||
require.Equal(t, test.res.signingThreshold, res.signingThreshold) | ||
} | ||
}) | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,45 @@ | ||
// Copyright © 2019, 2020 Weald Technology Trading | ||
// Licensed under the Apache License, Version 2.0 (the "License"); | ||
// you may not use this file except in compliance with the License. | ||
// You may obtain a copy of the License at | ||
// | ||
// http://www.apache.org/licenses/LICENSE-2.0 | ||
// | ||
// Unless required by applicable law or agreed to in writing, software | ||
// distributed under the License is distributed on an "AS IS" BASIS, | ||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
// See the License for the specific language governing permissions and | ||
// limitations under the License. | ||
|
||
package accountcreate | ||
|
||
import ( | ||
"context" | ||
"fmt" | ||
|
||
"github.com/pkg/errors" | ||
e2wtypes "github.com/wealdtech/go-eth2-wallet-types/v2" | ||
) | ||
|
||
type dataOut struct { | ||
account e2wtypes.Account | ||
} | ||
|
||
func output(ctx context.Context, data *dataOut) (string, error) { | ||
if data == nil { | ||
return "", errors.New("no data") | ||
} | ||
if data.account == nil { | ||
return "", errors.New("no account") | ||
} | ||
|
||
if pubKeyProvider, ok := data.account.(e2wtypes.AccountCompositePublicKeyProvider); ok { | ||
return fmt.Sprintf("%#x", pubKeyProvider.CompositePublicKey().Marshal()), nil | ||
} | ||
|
||
if pubKeyProvider, ok := data.account.(e2wtypes.AccountPublicKeyProvider); ok { | ||
return fmt.Sprintf("%#x", pubKeyProvider.PublicKey().Marshal()), nil | ||
} | ||
|
||
return "", errors.New("no public key available") | ||
} |
Oops, something went wrong.