Skip to content

Commit

Permalink
Merge pull request #12285 from brave/reland-12236
Browse files Browse the repository at this point in the history
Reland feat(wallet): Wired up Create Solana Account in UI
  • Loading branch information
darkdh committed Feb 16, 2022
2 parents f6e5d01 + 6830b24 commit 9a47d23
Show file tree
Hide file tree
Showing 21 changed files with 227 additions and 112 deletions.
31 changes: 20 additions & 11 deletions browser/about_flags.cc
Original file line number Diff line number Diff line change
Expand Up @@ -242,6 +242,10 @@ constexpr char kBraveWalletFilecoinName[] =
constexpr char kBraveWalletFilecoinDescription[] =
"Filecoin support for native Brave Wallet";

constexpr char kBraveWalletSolanaName[] = "Enable Brave Wallet Solana support";
constexpr char kBraveWalletSolanaDescription[] =
"Solana support for native Brave Wallet";

constexpr char kBraveNewsName[] = "Enable Brave News";
constexpr char kBraveNewsDescription[] =
"Brave News is completely private and includes anonymized ads matched on "
Expand Down Expand Up @@ -361,17 +365,22 @@ const flags_ui::FeatureEntry::Choice kBraveSkusEnvChoices[] = {
#define BRAVE_IPFS_FEATURE_ENTRIES
#endif

#define BRAVE_NATIVE_WALLET_FEATURE_ENTRIES \
{"native-brave-wallet", \
flag_descriptions::kNativeBraveWalletName, \
flag_descriptions::kNativeBraveWalletDescription, \
kOsDesktop | flags_ui::kOsAndroid, \
FEATURE_VALUE_TYPE(brave_wallet::features::kNativeBraveWalletFeature)}, \
{"brave-wallet-filecoin", \
flag_descriptions::kBraveWalletFilecoinName, \
flag_descriptions::kBraveWalletFilecoinDescription, \
kOsDesktop | flags_ui::kOsAndroid, \
FEATURE_VALUE_TYPE(brave_wallet::features::kBraveWalletFilecoinFeature)},
#define BRAVE_NATIVE_WALLET_FEATURE_ENTRIES \
{"native-brave-wallet", \
flag_descriptions::kNativeBraveWalletName, \
flag_descriptions::kNativeBraveWalletDescription, \
kOsDesktop | flags_ui::kOsAndroid, \
FEATURE_VALUE_TYPE(brave_wallet::features::kNativeBraveWalletFeature)}, \
{"brave-wallet-filecoin", \
flag_descriptions::kBraveWalletFilecoinName, \
flag_descriptions::kBraveWalletFilecoinDescription, \
kOsDesktop | flags_ui::kOsAndroid, \
FEATURE_VALUE_TYPE(brave_wallet::features::kBraveWalletFilecoinFeature)}, \
{"brave-wallet-solana", \
flag_descriptions::kBraveWalletSolanaName, \
flag_descriptions::kBraveWalletSolanaDescription, \
kOsDesktop | flags_ui::kOsAndroid, \
FEATURE_VALUE_TYPE(brave_wallet::features::kBraveWalletSolanaFeature)},

#define BRAVE_NEWS_FEATURE_ENTRIES \
{"brave-news", \
Expand Down
88 changes: 58 additions & 30 deletions browser/brave_wallet/keyring_service_unittest.cc
Original file line number Diff line number Diff line change
Expand Up @@ -148,6 +148,24 @@ class KeyringServiceUnitTest : public testing::Test {
return value->GetString();
}

static bool IsKeyringInfoEmpty(KeyringService* service,
const std::string& keyring_id) {
base::RunLoop run_loop;
bool result = false;
service->GetKeyringInfo(
keyring_id,
base::BindLambdaForTesting([&](mojom::KeyringInfoPtr keyring_info) {
ASSERT_EQ(keyring_info->id, keyring_id);
if (!keyring_info->is_keyring_created && keyring_info->is_locked &&
!keyring_info->is_backed_up &&
keyring_info->account_infos.empty())
result = true;
run_loop.Quit();
}));
run_loop.Run();
return result;
}

static std::string GetMnemonicForDefaultKeyring(KeyringService* service) {
base::RunLoop run_loop;
std::string mnemonic;
Expand Down Expand Up @@ -978,25 +996,14 @@ TEST_F(KeyringServiceUnitTest, GetMnemonicForDefaultKeyring) {
EXPECT_EQ(GetMnemonicForDefaultKeyring(&service), kMnemonic1);
}

TEST_F(KeyringServiceUnitTest, GetDefaultKeyringInfo) {
TEST_F(KeyringServiceUnitTest, GetKeyringInfo) {
KeyringService service(GetPrefs());
bool callback_called = false;
service.GetKeyringInfo(
mojom::kDefaultKeyringId,
base::BindLambdaForTesting([&](mojom::KeyringInfoPtr keyring_info) {
EXPECT_EQ(keyring_info->id, mojom::kDefaultKeyringId);
EXPECT_FALSE(keyring_info->is_keyring_created);
EXPECT_TRUE(keyring_info->is_locked);
EXPECT_FALSE(keyring_info->is_backed_up);
EXPECT_TRUE(keyring_info->account_infos.empty());
callback_called = true;
}));
base::RunLoop().RunUntilIdle();
EXPECT_TRUE(callback_called);

EXPECT_TRUE(IsKeyringInfoEmpty(&service, mojom::kDefaultKeyringId));

ASSERT_TRUE(CreateWallet(&service, "brave"));

callback_called = false;
bool callback_called = false;
service.GetKeyringInfo(
mojom::kDefaultKeyringId,
base::BindLambdaForTesting([&](mojom::KeyringInfoPtr keyring_info) {
Expand Down Expand Up @@ -1033,12 +1040,18 @@ TEST_F(KeyringServiceUnitTest, GetDefaultKeyringInfo) {
}));
base::RunLoop().RunUntilIdle();
EXPECT_TRUE(callback_called);

// invalid id or keyring is not yet created
EXPECT_TRUE(IsKeyringInfoEmpty(&service, mojom::kSolanaKeyringId));
EXPECT_TRUE(IsKeyringInfoEmpty(&service, "invalid_id"));
}

TEST_F(KeyringServiceUnitTest, LockAndUnlock) {
base::test::ScopedFeatureList feature_list;
feature_list.InitAndEnableFeature(
brave_wallet::features::kBraveWalletFilecoinFeature);
feature_list.InitWithFeatures(
{brave_wallet::features::kBraveWalletFilecoinFeature,
brave_wallet::features::kBraveWalletSolanaFeature},
{});
{
KeyringService service(GetPrefs());
// No encryptor
Expand Down Expand Up @@ -1584,6 +1597,9 @@ TEST_F(KeyringServiceUnitTest, ImportedAccountFromJson) {
}

TEST_F(KeyringServiceUnitTest, GetPrivateKeyForKeyringAccount) {
base::test::ScopedFeatureList feature_list;
feature_list.InitAndEnableFeature(
brave_wallet::features::kBraveWalletSolanaFeature);
KeyringService service(GetPrefs());
ASSERT_TRUE(RestoreWallet(&service, kMnemonic1, "brave", false));

Expand Down Expand Up @@ -2581,18 +2597,20 @@ TEST_F(KeyringServiceUnitTest, ImportFilecoinAccounts) {

TEST_F(KeyringServiceUnitTest, PreCreateEncryptors) {
{
// Create default wallet with disabled filecoin feature
// Create default wallet with disabled filecoin & solana feature
KeyringService service(GetPrefs());
ASSERT_TRUE(CreateWallet(&service, "brave"));
EXPECT_NE(service.encryptors_.at(mojom::kDefaultKeyringId), nullptr);
EXPECT_FALSE(service.encryptors_.contains(mojom::kFilecoinKeyringId));
EXPECT_NE(service.encryptors_.at(mojom::kSolanaKeyringId), nullptr);
EXPECT_FALSE(service.encryptors_.contains(mojom::kSolanaKeyringId));
}
{
// Create wallet with enabled filecoin
// Create wallet with enabled filecoin & solana
base::test::ScopedFeatureList feature_list;
feature_list.InitAndEnableFeature(
brave_wallet::features::kBraveWalletFilecoinFeature);
feature_list.InitWithFeatures(
{brave_wallet::features::kBraveWalletFilecoinFeature,
brave_wallet::features::kBraveWalletSolanaFeature},
{});

KeyringService service(GetPrefs());
ASSERT_TRUE(CreateWallet(&service, "brave"));
Expand All @@ -2601,24 +2619,26 @@ TEST_F(KeyringServiceUnitTest, PreCreateEncryptors) {
EXPECT_NE(service.encryptors_.at(mojom::kSolanaKeyringId), nullptr);
}
{
// Create wallet and enable filecoin before unlock
// Create wallet and enable filecoin & solana before unlock
KeyringService service(GetPrefs());
ASSERT_TRUE(CreateWallet(&service, "brave"));
EXPECT_NE(service.encryptors_.at(mojom::kDefaultKeyringId), nullptr);
EXPECT_FALSE(service.encryptors_.contains(mojom::kFilecoinKeyringId));
EXPECT_NE(service.encryptors_.at(mojom::kSolanaKeyringId), nullptr);
EXPECT_FALSE(service.encryptors_.contains(mojom::kSolanaKeyringId));
service.Lock();
base::test::ScopedFeatureList feature_list;
feature_list.InitAndEnableFeature(
brave_wallet::features::kBraveWalletFilecoinFeature);
feature_list.InitWithFeatures(
{brave_wallet::features::kBraveWalletFilecoinFeature,
brave_wallet::features::kBraveWalletSolanaFeature},
{});

ASSERT_TRUE(Unlock(&service, "brave"));
EXPECT_NE(service.encryptors_.at(mojom::kDefaultKeyringId), nullptr);
EXPECT_NE(service.encryptors_.at(mojom::kFilecoinKeyringId), nullptr);
EXPECT_NE(service.encryptors_.at(mojom::kSolanaKeyringId), nullptr);
}
{
// Create default wallet and enable filecoin before restore
// Create default wallet and enable filecoin solana before restore
KeyringService service(GetPrefs());
TestKeyringServiceObserver observer;
service.AddObserver(observer.GetReceiver());
Expand All @@ -2631,11 +2651,13 @@ TEST_F(KeyringServiceUnitTest, PreCreateEncryptors) {
RestoreWallet(&service, *mnemonic_to_be_restored, "brave", false));
EXPECT_NE(service.encryptors_.at(mojom::kDefaultKeyringId), nullptr);
EXPECT_FALSE(service.encryptors_.contains(mojom::kFilecoinKeyringId));
EXPECT_NE(service.encryptors_.at(mojom::kSolanaKeyringId), nullptr);
EXPECT_FALSE(service.encryptors_.contains(mojom::kSolanaKeyringId));

base::test::ScopedFeatureList feature_list;
feature_list.InitAndEnableFeature(
brave_wallet::features::kBraveWalletFilecoinFeature);
feature_list.InitWithFeatures(
{brave_wallet::features::kBraveWalletFilecoinFeature,
brave_wallet::features::kBraveWalletSolanaFeature},
{});
service.Reset();
ASSERT_TRUE(
RestoreWallet(&service, *mnemonic_to_be_restored, "brave", false));
Expand All @@ -2655,6 +2677,9 @@ TEST_F(KeyringServiceUnitTest, PreCreateEncryptors) {
}

TEST_F(KeyringServiceUnitTest, SolanaKeyring) {
base::test::ScopedFeatureList feature_list;
feature_list.InitAndEnableFeature(
brave_wallet::features::kBraveWalletSolanaFeature);
{
KeyringService service(GetPrefs());
TestKeyringServiceObserver observer;
Expand Down Expand Up @@ -2820,6 +2845,9 @@ TEST_F(KeyringServiceUnitTest, SolanaKeyring) {
}

TEST_F(KeyringServiceUnitTest, SignMessage) {
base::test::ScopedFeatureList feature_list;
feature_list.InitAndEnableFeature(
brave_wallet::features::kBraveWalletSolanaFeature);
KeyringService service(GetPrefs());
ASSERT_TRUE(RestoreWallet(&service, kMnemonic1, "brave", false));
base::RunLoop().RunUntilIdle();
Expand Down
11 changes: 7 additions & 4 deletions browser/ui/webui/brave_wallet/common_handler/wallet_handler.cc
Original file line number Diff line number Diff line change
Expand Up @@ -46,10 +46,12 @@ void WalletHandler::OnConnectionError() {

void WalletHandler::GetWalletInfo(GetWalletInfoCallback callback) {
EnsureConnected();
std::vector<std::string> ids(1, brave_wallet::mojom::kDefaultKeyringId);
if (brave_wallet::IsFilecoinEnabled()) {
std::vector<std::string> ids = {brave_wallet::mojom::kDefaultKeyringId};
if (brave_wallet::IsFilecoinEnabled())
ids.push_back(brave_wallet::mojom::kFilecoinKeyringId);
}
if (brave_wallet::IsSolanaEnabled())
ids.push_back(brave_wallet::mojom::kSolanaKeyringId);

keyring_service_->GetKeyringsInfo(
ids, base::BindOnce(&WalletHandler::OnGetWalletInfo,
weak_ptr_factory_.GetWeakPtr(), std::move(callback)));
Expand Down Expand Up @@ -77,7 +79,8 @@ void WalletHandler::OnGetWalletInfo(
std::move(callback).Run(
default_keyring->is_keyring_created, default_keyring->is_locked,
std::move(favorite_apps_copy), default_keyring->is_backed_up,
std::move(account_infos), brave_wallet::IsFilecoinEnabled());
std::move(account_infos), brave_wallet::IsFilecoinEnabled(),
brave_wallet::IsSolanaEnabled());
}

void WalletHandler::AddFavoriteApp(
Expand Down
7 changes: 7 additions & 0 deletions components/brave_wallet/browser/brave_wallet_utils.cc
Original file line number Diff line number Diff line change
Expand Up @@ -247,10 +247,17 @@ bool IsNativeWalletEnabled() {
return base::FeatureList::IsEnabled(
brave_wallet::features::kNativeBraveWalletFeature);
}

bool IsFilecoinEnabled() {
return base::FeatureList::IsEnabled(
brave_wallet::features::kBraveWalletFilecoinFeature);
}

bool IsSolanaEnabled() {
return base::FeatureList::IsEnabled(
brave_wallet::features::kBraveWalletSolanaFeature);
}

const std::vector<brave_wallet::mojom::EthereumChain>
GetAllKnownNetworksForTesting() {
std::vector<brave_wallet::mojom::EthereumChain> result;
Expand Down
1 change: 1 addition & 0 deletions components/brave_wallet/browser/brave_wallet_utils.h
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@ namespace brave_wallet {

bool IsNativeWalletEnabled();
bool IsFilecoinEnabled();
bool IsSolanaEnabled();

// Generate mnemonic from random entropy following BIP39.
// |entropy_size| should be specify in bytes
Expand Down
2 changes: 2 additions & 0 deletions components/brave_wallet/browser/json_rpc_service.cc
Original file line number Diff line number Diff line change
Expand Up @@ -525,6 +525,8 @@ void JsonRpcService::GetBalance(const std::string& address,
weak_ptr_factory_.GetWeakPtr(), std::move(callback));
return Request(fil_getBalance(address), true, std::move(internal_callback));
}
std::move(callback).Run("", mojom::ProviderError::kInternalError,
l10n_util::GetStringUTF8(IDS_WALLET_INTERNAL_ERROR));
}

void JsonRpcService::OnEthGetBalance(
Expand Down
48 changes: 27 additions & 21 deletions components/brave_wallet/browser/keyring_service.cc
Original file line number Diff line number Diff line change
Expand Up @@ -676,11 +676,10 @@ void KeyringService::GetKeyringInfo(const std::string& keyring_id,
void KeyringService::GetKeyringsInfo(const std::vector<std::string>& keyrings,
GetKeyringsInfoCallback callback) {
std::vector<mojom::KeyringInfoPtr> result;
result.push_back(GetKeyringInfoSync(mojom::kDefaultKeyringId));
if (IsFilecoinEnabled()) {
result.push_back(GetKeyringInfoSync(mojom::kFilecoinKeyringId));
for (const auto& keyring : keyrings) {
result.push_back(GetKeyringInfoSync(keyring));
}
result.push_back(GetKeyringInfoSync(mojom::kSolanaKeyringId));

std::move(callback).Run(std::move(result));
}

Expand All @@ -703,8 +702,10 @@ void KeyringService::CreateWallet(const std::string& password,
VLOG(1) << "Unable to create filecoin encryptor";
}
}
if (!CreateEncryptorForKeyring(password, mojom::kSolanaKeyringId)) {
VLOG(1) << "Unable to create solana encryptor";
if (IsSolanaEnabled()) {
if (!CreateEncryptorForKeyring(password, mojom::kSolanaKeyringId)) {
VLOG(1) << "Unable to create solana encryptor";
}
}

std::move(callback).Run(GetMnemonicForKeyringImpl(mojom::kDefaultKeyringId));
Expand All @@ -727,10 +728,12 @@ void KeyringService::RestoreWallet(const std::string& mnemonic,
AddAccountForKeyring(mojom::kFilecoinKeyringId, GetAccountName(1));
}

auto* solana_keyring = RestoreKeyring(mojom::kSolanaKeyringId, mnemonic,
password, is_legacy_brave_wallet);
if (solana_keyring && !solana_keyring->GetAccountsNumber())
AddAccountForKeyring(mojom::kSolanaKeyringId, GetAccountName(1));
if (IsSolanaEnabled()) {
auto* solana_keyring = RestoreKeyring(mojom::kSolanaKeyringId, mnemonic,
password, is_legacy_brave_wallet);
if (solana_keyring && !solana_keyring->GetAccountsNumber())
AddAccountForKeyring(mojom::kSolanaKeyringId, GetAccountName(1));
}

// TODO(darkdh): add account discovery mechanism

Expand Down Expand Up @@ -775,6 +778,10 @@ void KeyringService::AddAccount(const std::string& account_name,
return;
}
} else if (keyring_id == mojom::kSolanaKeyringId) {
if (!IsSolanaEnabled()) {
std::move(callback).Run(false);
return;
}
if (!LazilyCreateKeyring(mojom::kSolanaKeyringId)) {
VLOG(1) << "Unable to create Solana keyring";
std::move(callback).Run(false);
Expand Down Expand Up @@ -1415,19 +1422,18 @@ void KeyringService::Unlock(const std::string& password,
std::move(callback).Run(false);
return;
}
if (IsFilecoinEnabled()) {
if (!ResumeKeyring(mojom::kFilecoinKeyringId, password)) {
// If Filecoin keyring doesnt exist we keep encryptor pre-created
// to be able to lazily create keyring later
if (IsKeyringExist(mojom::kFilecoinKeyringId)) {
VLOG(1) << __func__ << " Unable to unlock filecoin keyring";
encryptors_.erase(mojom::kFilecoinKeyringId);
std::move(callback).Run(false);
return;
}
if (IsFilecoinEnabled() &&
!ResumeKeyring(mojom::kFilecoinKeyringId, password)) {
// If Filecoin keyring doesnt exist we keep encryptor pre-created
// to be able to lazily create keyring later
if (IsKeyringExist(mojom::kFilecoinKeyringId)) {
VLOG(1) << __func__ << " Unable to unlock filecoin keyring";
encryptors_.erase(mojom::kFilecoinKeyringId);
std::move(callback).Run(false);
return;
}
}
if (!ResumeKeyring(mojom::kSolanaKeyringId, password)) {
if (IsSolanaEnabled() && !ResumeKeyring(mojom::kSolanaKeyringId, password)) {
if (IsKeyringExist(mojom::kSolanaKeyringId)) {
VLOG(1) << __func__ << " Unable to unlock Solana keyring";
encryptors_.erase(mojom::kSolanaKeyringId);
Expand Down
Loading

0 comments on commit 9a47d23

Please sign in to comment.