Skip to content

Commit

Permalink
implement provider switch
Browse files Browse the repository at this point in the history
We need a basic api so we can switch between recorded providers when
the user decides that tally should not be the default wallet.

Also implemented basic branding info on the TallyWindowProvider
  • Loading branch information
Gergo Nagy committed Apr 13, 2022
1 parent 9c9378c commit d19915b
Show file tree
Hide file tree
Showing 3 changed files with 81 additions and 7 deletions.
27 changes: 24 additions & 3 deletions env.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,13 @@
declare module "styled-jsx/style"

type WalletProvider = {
providerInfo?: {
label: string
injectedNamespace: string
iconURL: string
identityFlag?: string
checkIdentity?: () => boolean
}
on: (
eventName: string | symbol,
listener: (...args: unknown[]) => void
Expand All @@ -14,6 +21,11 @@ type WalletProvider = {
eventName: string | symbol,
listener: (...args: unknown[]) => void
) => unknown
[optionalProps: string]: unknown
}

type TallyProvider = WalletProvider & {
isTally: true
}

type WindowEthereum = WalletProvider & {
Expand All @@ -25,10 +37,19 @@ interface Window {
walletRouter?: {
currentProvider: WalletProvider
providers: WalletProvider[]
switchToPreviousProvider: () => void
getProviderInfo: (
provider: WalletProvider
) => WalletProvider["providerInfo"]
hasProvider: (
checkIdentity: (provider: WalletProvider) => boolean
) => boolean
setCurrentProvider: (
checkIdentity: (provider: WalletProvider) => boolean
) => void
addProvider: (newProvider: WalletProvider) => void
}
tally?: WalletProvider & {
isTally: boolean
}
tally?: TallyProvider
ethereum?: WindowEthereum
oldEthereum?: WindowEthereum
}
36 changes: 35 additions & 1 deletion src/window-provider.ts
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,40 @@ if (!window.walletRouter) {
value: {
currentProvider: window.tally,
providers: [...(window.ethereum ? [window.ethereum] : [])],
switchToPreviousProvider() {
const previousProvider = this.providers.pop()
if (previousProvider) {
this.providers.push(this.currentProvider)
this.currentProvider = previousProvider
}
},
getProviderInfo(provider: WalletProvider) {
return (
provider.providerInfo || {
label: "Injected Provider",
injectedNamespace: "ethereum",
iconURL: "TODO",
}
)
},
hasProvider(checkIdentity: (provider: WalletProvider) => boolean) {
return this.providers.some(checkIdentity)
},
setCurrentProvider(checkIdentity: (provider: WalletProvider) => boolean) {
if (!this.hasProvider(checkIdentity)) {
throw new Error(
"The given identity did not match to any of the recognized providers!"
)
}
const providerIdex = this.providers.findIndex(checkIdentity)
const previousProvider = this.currentProvider
this.currentProvider = this.providers[providerIdex]
this.providers.splice(providerIdex, 1)
this.providers.push(previousProvider)
},
addProvider(newProvider: WalletProvider) {
this.providers.push(newProvider)
},
},
writable: false,
configurable: false,
Expand All @@ -37,7 +71,7 @@ Object.defineProperty(window, "ethereum", {
return window.walletRouter?.currentProvider || window.tally
},
set(newProvider) {
window.walletRouter?.providers.push(newProvider)
window.walletRouter?.addProvider(newProvider)
},
configurable: false,
})
25 changes: 22 additions & 3 deletions window-provider/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,15 @@ export default class TallyWindowProvider extends EventEmitter {

bridgeListeners = new Map()

providerInfo = {
label: "Tally Ho!",
injectedNamespace: "tally",
iconURL: "TODO",
identityFlag: "isTally",
checkIdentity: (provider: WalletProvider) =>
!!provider && !!provider.isTally,
} as const

constructor(public transport: ProviderTransport) {
super()

Expand Down Expand Up @@ -59,14 +68,24 @@ export default class TallyWindowProvider extends EventEmitter {
if (isTallyConfigPayload(result)) {
if (!result.defaultWallet) {
// if tally is NOT set to be default wallet
// AND window.ethereum was taken
if (window.oldEthereum) {
// AND we have other providers that tried to inject into window.ethereum
if (window.walletRouter?.providers.length) {
// then let's reset window.ethereum to the original value
window.ethereum = window.oldEthereum
window.walletRouter.switchToPreviousProvider()
}

// NOTE: we do not remove the TallyWindowProvider from window.ethereum
// if there is nothing else that want's to use it.
} else if (window.walletRouter?.currentProvider !== window.tally) {
if (
!window.walletRouter?.hasProvider(this.providerInfo.checkIdentity)
) {
window.walletRouter?.addProvider(window.tally!)
}

window.walletRouter?.setCurrentProvider(
this.providerInfo.checkIdentity
)
}
} else if (isTallyAccountPayload(result)) {
this.handleAddressChange.bind(this)(result.address)
Expand Down

0 comments on commit d19915b

Please sign in to comment.