Skip to content

Commit 6cf9421

Browse files
committed
wallet: implement ImportAccount
1 parent ef816a0 commit 6cf9421

File tree

2 files changed

+85
-0
lines changed

2 files changed

+85
-0
lines changed

wallet/account_manager.go

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ import (
88
"context"
99

1010
"github.com/btcsuite/btcd/btcutil"
11+
"github.com/btcsuite/btcd/btcutil/hdkeychain"
1112
"github.com/btcsuite/btcd/chaincfg/chainhash"
1213
"github.com/btcsuite/btcd/txscript"
1314
"github.com/btcsuite/btcwallet/waddrmgr"
@@ -559,3 +560,29 @@ func (w *Wallet) Balance(ctx context.Context, conf int32,
559560
return balance, nil
560561
}
561562

563+
// ImportAccount imports a watch-only account from an extended public key.
564+
//
565+
// The time complexity of this method is dominated by the database lookup to
566+
// ensure the account name is unique within the scope.
567+
func (w *Wallet) ImportAccount(ctx context.Context, scope waddrmgr.KeyScope,
568+
name string, accountPubKey *hdkeychain.ExtendedKey,
569+
masterKeyFingerprint uint32, addrType *waddrmgr.AddressType,
570+
dryRun bool) (*waddrmgr.AccountProperties, error) {
571+
572+
var (
573+
props *waddrmgr.AccountProperties
574+
err error
575+
)
576+
577+
if dryRun {
578+
props, _, _, err = w.ImportAccountDryRun(
579+
name, accountPubKey, masterKeyFingerprint, addrType, 0,
580+
)
581+
} else {
582+
props, err = w.ImportAccountDeprecated(
583+
name, accountPubKey, masterKeyFingerprint, addrType,
584+
)
585+
}
586+
587+
return props, err
588+
}

wallet/account_manager_test.go

Lines changed: 58 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ import (
1010
"time"
1111

1212
"github.com/btcsuite/btcd/btcutil"
13+
"github.com/btcsuite/btcd/btcutil/hdkeychain"
1314
"github.com/btcsuite/btcd/txscript"
1415
"github.com/btcsuite/btcd/wire"
1516
"github.com/btcsuite/btcwallet/waddrmgr"
@@ -498,4 +499,61 @@ func TestBalance(t *testing.T) {
498499
)
499500
}
500501

502+
// TestAccountManagerImportAccount tests that the ImportAccount method on the
503+
// AccountManager interface works as expected.
504+
func TestAccountManagerImportAccount(t *testing.T) {
505+
t.Parallel()
506+
507+
// Create a new test wallet.
508+
w, cleanup := testWallet(t)
509+
defer cleanup()
501510

511+
// We'll start by creating a new account under the BIP0084 scope.
512+
scope := waddrmgr.KeyScopeBIP0084
513+
addrType := waddrmgr.WitnessPubKey
514+
masterPriv := "tprv8ZgxMBicQKsPeWwrFuNjEGTTDSY4mRLwd2KDJAPGa1AY" +
515+
"quw38bZqNMSuB3V1Va3hqJBo9Pt8Sx7kBQer5cNMrb8SYquoWPt9" +
516+
"Y3BZdhdtUcw"
517+
root, err := hdkeychain.NewKeyFromString(masterPriv)
518+
require.NoError(t, err)
519+
acctPubKey := deriveAcctPubKey(t, root, scope, hardenedKey(0))
520+
521+
// We should be able to import the account.
522+
props, err := w.ImportAccount(
523+
context.Background(), scope, testAccountName, acctPubKey,
524+
root.ParentFingerprint(), &addrType, false,
525+
)
526+
require.NoError(t, err)
527+
require.Equal(t, testAccountName, props.AccountName)
528+
529+
// We should be able to get the account by its name.
530+
_, err = w.GetAccount(context.Background(), scope, testAccountName)
531+
require.NoError(t, err)
532+
533+
// We should not be able to import an account with the same name.
534+
_, err = w.ImportAccount(
535+
context.Background(), scope, testAccountName, acctPubKey,
536+
root.ParentFingerprint(), &addrType, false,
537+
)
538+
require.Error(t, err)
539+
require.True(
540+
t, waddrmgr.IsError(err, waddrmgr.ErrDuplicateAccount),
541+
"expected ErrDuplicateAccount",
542+
)
543+
544+
// We should be able to do a dry run of the import.
545+
dryRunName := "dry run"
546+
_, err = w.ImportAccount(
547+
context.Background(), scope, dryRunName, acctPubKey,
548+
root.ParentFingerprint(), &addrType, true,
549+
)
550+
require.NoError(t, err)
551+
552+
// The account should not have been imported.
553+
_, err = w.GetAccount(context.Background(), scope, dryRunName)
554+
require.Error(t, err)
555+
require.True(
556+
t, waddrmgr.IsError(err, waddrmgr.ErrAccountNotFound),
557+
"expected ErrAccountNotFound",
558+
)
559+
}

0 commit comments

Comments
 (0)