2024-07-16 15:29:42 +08:00

180 lines
5.4 KiB
JavaScript

import {PassportWallet} from "@/components/chain/wallet/PassportWallet";
import { MetaMaskWallet } from '@/components/chain/wallet/MetaMaskWallet';
import { OkxWallet } from '@/components/chain/wallet/OkxWallet';
import {walletStore} from "@/store/wallet";
import WalletSelectModel from "@/components/chain/WalletSelectModel.vue";
import {createModal} from "@/utils/model.util";
import {isTokenExpired, genRefreshToken, cfgChainId, switchEthereumChain} from "@/components/chain/utils"
import {ImtblMarket} from "@/components/chain/Market";
import { ALL_PROVIDERS } from "@/configs/configchain";
import {Locker} from "@/components/chain/contract/Locker";
import ConfirmDialog from "@/components/Dialogs/confirmDialog.vue";
export const allProviders = {
1: MetaMaskWallet,
2: OkxWallet,
3: PassportWallet
}
export class BlockChain {
constructor() {
if (BlockChain.instance) {
return BlockChain.instance;
}
this.store = walletStore();
this.store.$hydrate({runHooks: false});
this.initWallet();
this.market = new ImtblMarket(this)
this.locker = new Locker(this)
BlockChain.instance = this;
}
initWallet() {
// console.log("init blockchain instance");
// console.log(this.store.address);
if (!this.store.address) {
// console.log("no wallet login");
return;
} else {
this.restoreWallet(this.store.walletType)
}
}
preparePassport() {
new PassportWallet();
}
async updateInfo({provider, accounts}) {
this.web3Provider = provider
if (!this.store.token) {
const {token, refreshToken}= await this.wallet.getAccessToken();
this.store.token = token
this.store.refreshToken = refreshToken
} else {
if (isTokenExpired(3600, this.store.token)) {
if (this.store.refreshToken && !isTokenExpired(300, this.store.refreshToken)) {
const {token, refreshToken} = await genRefreshToken(this.store.refreshToken);
this.store.token = token;
this.store.refreshToken = refreshToken;
} else {
const {token, refreshToken}= await this.wallet.getAccessToken();
this.store.token = token
this.store.refreshToken = refreshToken
}
}
}
this.store.address = accounts[0];
if (this.store.walletType == 3) {
this.store.passportAddress = accounts[0];
this.passportProvider = provider;
}
this.store.$persist();
this.market.updateProvider(provider);
return provider;
}
async restoreWallet(walletType) {
this.wallet = new allProviders[walletType]();
const { provider, accounts } = await this.wallet.web3Provider();
await this.updateInfo({provider, accounts })
return provider;
}
async connect() {
// if this only one provider configed, use it directly
if (ALL_PROVIDERS.length === 1) {
const walletType = ALL_PROVIDERS[0].id
this.wallet = new allProviders[walletType]();
this.store.walletType = walletType;
const { provider, accounts } = await this.wallet.web3Provider();
await this.updateInfo({ provider, accounts })
return provider;
}
const rewardModal = createModal(WalletSelectModel, {});
const result = await rewardModal.show();
if (!result.errcode) {
this.store.walletType = result.wallet;
this.wallet = new allProviders[result.wallet]();
await this.updateInfo(result)
if (result.wallet !== 3 && this.store.passportAddress) {
await this.appendPassport();
}
return result.provider
} else {
console.log(`select result : ${result.errmsg}`);
throw new Error(result.errmsg);
}
}
async appendPassport() {
if (this.store.walletType == 3) {
return;
}
let wallet = new PassportWallet();
const { provider, accounts } = await wallet.web3Provider();
this.passportProvider = provider;
this.store.passportAddress = accounts[0];
this.store.$persist();
}
async token() {
const suffix = (this.store.walletType == 2 || this.store.walletType == 1) ? '.cf' : ''
let token = this.store.token;
if (!suffix && this.store.walletType == 3) {
const res = await this.wallet.getAccessToken();
token = res.token
}
if (!token) {
return ''
}
return token+suffix
}
async logout() {
if (this.store.walletType != 3 && this.passportProvider) {
new PassportWallet().logout();
}
this.store.reset();
this.store.$persist();
await this.wallet.logout();
}
async getChainId() {
return this.wallet.getChainId();
}
/**
* 检查并切换到目标链, 各上链前须调用该方法
*/
async checkAndChangeChain(targetChainId) {
targetChainId = targetChainId || cfgChainId;
let chainId = await this.getChainId();
if (chainId !== targetChainId) {
console.log(`current chain: ${chainId}, want: ${targetChainId}`)
chainId = await switchEthereumChain(this.web3Provider.provider, targetChainId);
}
}
async checkPassportLogin() {
let needLogin = false;
if (this.store.walletType != 3) {
if (!this.store.passportAddress) {
needLogin = true;
}
}
if (needLogin) {
const confirmResult = await createModal(ConfirmDialog, {
title: 'Need login to Passport',
message: 'Are you sure you want to login with Passport?'
}).show()
if (confirmResult.errcode) {
console.log('user cancel')
throw new Error('user cancel')
}
await this.appendPassport();
}
}
}