UNPKG

@web3auth/no-modal

Version:
201 lines (197 loc) 7.49 kB
'use strict'; var _defineProperty = require('@babel/runtime/helpers/defineProperty'); require('@babel/runtime/helpers/objectSpread2'); require('@segment/analytics-next'); var loglevel = require('../../base/loglevel.js'); var IChainInterface = require('../../base/chain/IChainInterface.js'); require('@web3auth/auth'); var index = require('../../base/errors/index.js'); require('../../base/wallet/index.js'); require('../../base/connector/connectorStatus.js'); var constants = require('../../base/connector/constants.js'); require('jwt-decode'); require('../../base/plugin/errors.js'); require('../../base/plugin/IPlugin.js'); var utils = require('../../base/utils.js'); var baseEvmConnector = require('../base-evm-connector/baseEvmConnector.js'); var baseControllers = require('@toruslabs/base-controllers'); class InjectedEvmConnector extends baseEvmConnector.BaseEvmConnector { constructor(options) { super(options); _defineProperty(this, "connectorNamespace", IChainInterface.CONNECTOR_NAMESPACES.EIP155); _defineProperty(this, "currentChainNamespace", baseControllers.CHAIN_NAMESPACES.EIP155); _defineProperty(this, "type", constants.CONNECTOR_CATEGORY.EXTERNAL); _defineProperty(this, "name", void 0); _defineProperty(this, "isInjected", true); _defineProperty(this, "status", constants.CONNECTOR_STATUS.NOT_READY); _defineProperty(this, "injectedProvider", null); this.name = options.name; this.injectedProvider = options.provider; this.icon = options.icon; } get provider() { if (this.status !== constants.CONNECTOR_STATUS.NOT_READY && this.injectedProvider) { return this.injectedProvider; } return null; } set provider(_) { throw new Error("Not implemented"); } async init(options) { await super.init(options); const chainConfig = this.coreOptions.chains.find(x => x.chainId === options.chainId); super.checkInitializationRequirements({ chainConfig }); this.status = constants.CONNECTOR_STATUS.READY; this.emit(constants.CONNECTOR_EVENTS.READY, this.name); try { loglevel.log.debug(`initializing ${this.name} injected connector`); if (options.autoConnect) { this.rehydrated = true; const provider = await this.connect({ chainId: options.chainId, getIdentityToken: options.getIdentityToken }); if (!provider) { this.rehydrated = false; throw index.WalletLoginError.connectionError("Failed to rehydrate."); } } } catch (error) { this.emit(constants.CONNECTOR_EVENTS.REHYDRATION_ERROR, error); } } async connect({ chainId, getIdentityToken }) { super.checkConnectionRequirements(); if (!this.injectedProvider) throw index.WalletLoginError.connectionError("Injected provider is not available"); const chainConfig = this.coreOptions.chains.find(x => x.chainId === chainId); if (!chainConfig) throw index.WalletLoginError.connectionError("Chain config is not available"); this.status = constants.CONNECTOR_STATUS.CONNECTING; this.emit(constants.CONNECTOR_EVENTS.CONNECTING, { connector: this.name }); try { await this.injectedProvider.request({ method: "eth_requestAccounts" }); // switch chain if not connected to the right chain if (this.injectedProvider.chainId !== chainConfig.chainId) { try { await this.switchChain(chainConfig, true); } catch { await this.addChain(chainConfig, true); await this.switchChain(chainConfig, true); } } this.status = constants.CONNECTOR_STATUS.CONNECTED; const accountDisconnectHandler = accounts => { if (accounts.length === 0) { var _this$injectedProvide; this.disconnect(); if ((_this$injectedProvide = this.injectedProvider) !== null && _this$injectedProvide !== void 0 && _this$injectedProvide.removeListener) this.injectedProvider.removeListener("accountsChanged", accountDisconnectHandler); } }; this.injectedProvider.on("accountsChanged", accountDisconnectHandler); let identityTokenInfo; this.emit(constants.CONNECTOR_EVENTS.CONNECTED, { connector: this.name, reconnected: this.rehydrated, provider: this.injectedProvider, identityTokenInfo }); if (getIdentityToken) { identityTokenInfo = await this.getIdentityToken(); } return this.injectedProvider; } catch (error) { // ready again to be connected this.status = constants.CONNECTOR_STATUS.READY; if (!this.rehydrated) this.emit(constants.CONNECTOR_EVENTS.ERRORED, error); this.rehydrated = false; if (error instanceof index.Web3AuthError) throw error; throw index.WalletLoginError.connectionError(`Failed to login with ${this.name} injected wallet`); } } async disconnect(options = { cleanup: false }) { if (!this.injectedProvider) throw index.WalletLoginError.connectionError("Injected provider is not available"); await super.disconnectSession(); if (typeof this.injectedProvider.removeAllListeners !== "undefined") this.injectedProvider.removeAllListeners(); try { await this.injectedProvider.request({ method: "wallet_revokePermissions", params: [{ eth_accounts: {} }] }); } catch { // ignore error } if (options.cleanup) { this.status = constants.CONNECTOR_STATUS.NOT_READY; this.injectedProvider = null; } else { // ready to be connected again this.status = constants.CONNECTOR_STATUS.READY; } await super.disconnect(); } async getUserInfo() { if (!this.canAuthorize) throw index.WalletLoginError.notConnectedError("Not connected with wallet, Please login/connect first"); return {}; } async addChain(chainConfig, _init = false) { if (!this.injectedProvider) throw index.WalletLoginError.connectionError("Injected provider is not available"); await this.injectedProvider.request({ method: "wallet_addEthereumChain", params: [{ chainId: chainConfig.chainId, chainName: chainConfig.displayName, rpcUrls: [chainConfig.rpcTarget], blockExplorerUrls: [chainConfig.blockExplorerUrl], nativeCurrency: { name: chainConfig.tickerName, symbol: chainConfig.ticker, decimals: chainConfig.decimals || 18 }, iconUrls: [chainConfig.logo] }] }); } async switchChain(params, init = false) { if (!this.injectedProvider) throw index.WalletLoginError.connectionError("Injected provider is not available"); super.checkSwitchChainRequirements(params, init); await this.injectedProvider.request({ method: "wallet_switchEthereumChain", params: [{ chainId: params.chainId }] }); } async enableMFA() { throw new Error("Method Not implemented"); } async manageMFA() { throw new Error("Method Not implemented"); } } const injectedEvmConnector = providerDetail => { return ({ coreOptions }) => { return new InjectedEvmConnector({ name: utils.normalizeWalletName(providerDetail.info.name), provider: providerDetail.provider, icon: providerDetail.info.icon, coreOptions }); }; }; exports.InjectedEvmConnector = InjectedEvmConnector; exports.injectedEvmConnector = injectedEvmConnector;