blocknative / web3-onboard

Client library to onboard users to web3 apps
https://onboard.blocknative.com/
MIT License
861 stars 511 forks source link

[Feature]: Multiple protocols support (for V2 or V3) #803

Closed imsys closed 2 years ago

imsys commented 2 years ago

Is your request related to a problem?

No

Feature Description

Currently we can easily add support for multiple EVM chains, but as there are other protocols popping up like Polkadot, Cosmos, Solana, etc, I wonder if we could integrate all of them. Ideally it would be nice if they could all come to an agreement of a standard common RPC function calls, but that's not going to happen anytime soon. I have only worked with EVM chains, but still planning to study other protocols. As their ecosystem are young, I think most of their wallets works by injection, so maybe there is not much point in coding for other protocols yet, but maybe keep this in mind on how to structure the code for a future implementation. It could probably be out of the scope of this project mission, but just sharing this idea. There are some multiprotocol wallets I have seen, like MathWallet, TrustWallet, AirGap Wallet, but idk if they support Dapps for those other protocols.

Alternative Solutions

No response

Anything else?

No response

taylorjdawson commented 2 years ago

@imsys Thanks for the feature request! Could you elaborate more on how this would fit into the Onboard ecosystem? Based on what I read I do think that Onboard v2 might be addressing this feature.

imsys commented 2 years ago

Hey @taylorjdawson, the documents mentioned in Onboard v2 are currently for EVM chains from what I could understand. WalletConnect v2 is implementing CAIP-2 for a chain agnostic approach. It's worth to take a look at how they are doing it at their docs, and the WalletConnect Solana implementation (currently in beta).

For reference, those are all the namespaces currently on CAIP, and some of the main chain as examples:

# Ethereum Mainnet(CAIP-2)
eip155:1
# Binance Smart Chain
eip155:56
# Polygon
eip155:137

# Cosmos Hub (CAIP-2)
cosmos:cosmoshub-4
# Terra:
cosmos:columbus-5
# Crypto.com
cosmos:crypto-org-chain-mainnet-1
# SecretNetwork
cosmos:secret-4

# Lisk Mainnet (CAIP-2)
lip9:9ee11e9df416b18b

# EOS Mainnet (CAIP-7)
eosio:aca376f206b8fc25a6ed44dbdc66547c

# Polkadot mainnet (CAIP-13)
polkadot:91b171bb158e2d3848fa23a9f1c25182
# Kusama (CAIP-13)
polkadot:b0a8d493285c2df73290dfb7e61f870f

# Tezos Mainnet (CAIP-26)
tezos:NetXdQprcVkpaWU

# Stellar (CAIP-28)
stellar:pubnet

# Solana Mainnet (CAIP-30)
solana:4sGjMW1sUnHzSxGspuhpqLDx6wiyjNtZ

# Hedera (CAIP-76)
hedera:mainnet
Connecting Polkadot wallet
// Connect wallet
polkadotChain = await window.injectedWeb3["polkadot-js"].enable()

await polkadotChain.accounts.get()

await polkadotChain.provider.listProviders() // polkadot-js does not return a provider, only a signer

polkadotChain.signer.sign(somethingToSign)

More at @polkadot/extension-dapp

Connecting Cosmos Wallet:
// Connect wallet
window.keplr.enable("crypto-org-chain-mainnet-1")

// getAccounts
await window.getOfflineSigner("crypto-org-chain-mainnet-1").getAccounts();
Solana:
SolanaDriver = window.solana.connect()

More at https://github.com/solana-labs/wallet-adapter


It would be nice to have a library that could connect to any chain using any wallet. It's very rare for a project to use both Ethereum and Polkadot or Cosmos, as deploying code for each is completely different (Solidity vs Rust).

But aside from that, it seems that other chains (Polkadot & Cosmos) are having more difficulty integrating other wallets to their dApps, so maybe a platform like Onboard would be welcome?

WalletConnect is implementing a way to enable all chains to use their platform, they are choosing to follow CAIP, this could play well.

Basically Polkadot & Cosmos are currently using only their main injected wallet, but TrustWallet and MathWallet also supports them, but little to no integration. There are other blockchains that just implemented smartcontract ability that could also enjoy some of this integration, like Stellar & Cardano. I know Stellar have a funding program that maybe could help?

On the other hand, Solana Wallet library ecosystem seems to be very mature.

So some thoughts on how it could work, maybe each blockchain namespace could have an adapter, and if there is something blocking it's implementation we could promote the CAIP and make proposals for other wallets, chains and js libraries to follow some standard.

But as I said before, this could be too much out of scope of the project, and I can understand that.

import { SigningStargateClient } from ("@cosmjs/stargate");
import * as solanaWeb3 from '@solana/web3.js';

let ethers;
let polkadotJS;
let cosmJS;
let solanaweb3;

let userWallet = {};

const onboard = Onboard({
  rpc: {
    ['eip155:1']: 'https://main-light.eth.linkpool.io',
    ['eip155:56']: 'https://bsc-dataseed.binance.org',
    ['eip155:137']: 'https://polygon-rpc.com',
    ['eip155:250']: 'https://rpc.ftm.tools',
    ['cosmos:cosmoshub-4']: 'https://api.cosmos.network',
    ['polkadot:91b171bb158e2d3848fa23a9f1c25182']: 'https://rpc.polkadot.io',
    ['solana:4sGjMW1sUnHzSxGspuhpqLDx6wiyjNtZ']: 'https://api.mainnet-beta.solana.com'
  },
  subscriptions: {
    wallet: wallet => {

      switch (wallet.namespace) {
        case 'eip155':
          ethers = new ethers.providers.Web3Provider(wallet.provider);
          userWallet['eip155'].signer = ethers.getSigner();
          userWallet['eip155'].accounts = [userWallet['eip155:137'].signer.getAddress()];
          break;

        case 'cosmos':
          userWallet['cosmos'].signer = window.getOfflineSigner(wallet.chainId);
          userWallet['cosmos'].accounts = await offlineSigner.getAccounts();

          cosmJS = new SigningStargateClient(
            wallet.rpc,
            userWallet['cosmos'].accounts[0].address,
            userWallet['cosmos'].signer
          );
          break;

        case 'polkadot':
          polkadotJS = ;//...
          userWallet['polkadot'].accounts = ;//...
          userWallet['polkadot'].signer = ;//....
          break;

        case 'solana':
          let solanaProvider = wallet.provider;
          let solanaweb3 = new solanaWeb3.Connection(wallet.rpc,);
          userWallet['solana'].accounts = ;//...
          userWallet['solana'].signer = ;//....
          break;
      }
    }
  },
  walletSelect: {
    wallets: wallets
  }
});
lnbc1QWFyb24 commented 2 years ago

Hey @imsys thanks for these detailed suggestions! I am going to be looking in to this today as I think it would be great if we could support connecting wallets for the greater ecosystem. I really like the idea of abstracting the provider code out in to an adapter for each blockchain namespace and I will start thinking about how we can implement this in V2. It is likely that we will modify the v2 architecture to accomodate this idea and then release as just EVM chains only to start. We can then start building some wallet modules for these other chains and their provider adapters.