Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix/sdk issues #76

Merged
merged 2 commits into from
Aug 1, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 0 additions & 6 deletions .env.hibit-id.testnet

This file was deleted.

7 changes: 4 additions & 3 deletions apps/wallet/.env
Original file line number Diff line number Diff line change
@@ -1,8 +1,9 @@
VITE_APP_ENV=TestNet
VITE_APP_ENV=Mainnet
VITE_RELEASE_VERSION=v1.0
VITE_HIBIT_ID_API=https://testnetidapi.hibit.app/
VITE_HIBIT_AUTH_SERVER=https://testnetauth.hibit.app/
VITE_HIBIT_ID_API=https://api.hibit.app/
VITE_HIBIT_AUTH_SERVER=https://auth.hibit.app/
VITE_HIBIT_AUTH_CLIENT_ID=IdServer_HibitIdWeb
VITE_EX3_API=https://api.hibit.app/
VITE_TELEGRAM_BOT_ID=7359440424
VITE_SYSTEM_MAX_DECIMALS=8
VITE_OIDC_REFRESH_TOKEN_TIMEOUT=3600000
9 changes: 9 additions & 0 deletions apps/wallet/src/App.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ import { RuntimeEnv } from './utils/basicEnums';
import { AuthenticatorType } from '@deland-labs/hibit-id-sdk';
import authManager from './utils/auth';
import toaster from './components/Toaster';
import rpcManager from './stores/rpc';

const MainPage = lazy(() => import('./pages/main'));
const LoginPage = lazy(() => import('./pages/login'));
Expand All @@ -30,7 +31,13 @@ const App: FC = observer(() => {

useEffect(() => {
(async () => {
if (RUNTIME_ENV === RuntimeEnv.SDK) {
await rpcManager.init()
}
if (isUserLoggedIn) {
if (RUNTIME_ENV === RuntimeEnv.SDK) {
rpcManager.notifyLoginChanged(true, oidcTokens.decodedIdToken.sub as string || '')
}
await hibitIdSession.login(oidcTokens)
if (!hibitIdSession.isMnemonicCreated) {
navigate('/create-password')
Expand All @@ -46,6 +53,8 @@ const App: FC = observer(() => {
console.error(e)
toaster.error('Telegram login failed')
}
} else if (RUNTIME_ENV === RuntimeEnv.SDK) {
rpcManager.notifyLoginChanged(false)
}
}
setReady(true)
Expand Down
6 changes: 0 additions & 6 deletions apps/wallet/src/main.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,6 @@ import './index.css'
import { BrowserRouter } from 'react-router-dom'
import { QueryClientProvider } from '@tanstack/react-query'
import { queryClient } from './apis/index.ts'
import { RuntimeEnv } from './utils/basicEnums.ts'
import rpcManager from './stores/rpc.ts'
import './i18n'
import HibitToastContainer from './components/Toaster/Container.tsx'
import BigNumber from 'bignumber.js'
Expand All @@ -19,10 +17,6 @@ BigNumber.config({ EXPONENTIAL_AT: 1e+9 });
console.log('[runtime env]', RUNTIME_ENV)
console.log('[runtime params]', RUNTIME_PARAMS)

if (RUNTIME_ENV === RuntimeEnv.SDK) {
rpcManager.init()
}

ReactDOM.createRoot(document.getElementById('root')!).render(
<React.StrictMode>
<OidcProvider>
Expand Down
2 changes: 1 addition & 1 deletion apps/wallet/src/pages/password/create.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ import { observer } from "mobx-react";
import LoaderButton from "../../components/LoaderButton";
import toaster from "../../components/Toaster";
import { CreateMnemonicInput } from "../../apis/models";
import { AES, format, MD5 } from 'crypto-js'
import { AES, MD5 } from 'crypto-js'
import { HDNodeWallet } from "ethers";
import hibitIdSession from "../../stores/session";
import { useMutation } from "@tanstack/react-query";
Expand Down
12 changes: 12 additions & 0 deletions apps/wallet/src/stores/rpc.ts
Original file line number Diff line number Diff line change
Expand Up @@ -43,13 +43,22 @@ class RPCManager {
await rpc.isReady
console.log('[wallet rpc ready]')
this._rpc = rpc
this.notifyReady()
}

public notifyClose = () => {
this._connectPromise?.reject('User manually closed')
this._rpc?.call(ClientExposeRPCMethod.CLOSE, {})
}

public notifyReady = () => {
this._rpc?.call(ClientExposeRPCMethod.IFRAME_READY, {})
}

public notifyLoginChanged = (isLogin: boolean, sub?: string) => {
this._rpc?.call(ClientExposeRPCMethod.LOGIN_CHANGED, { isLogin, sub })
}

public notifyChainChanged = (chainInfo: ChainInfo) => {
this._rpc?.call(ClientExposeRPCMethod.CHAIN_CHANGED, { chainId: chainInfo.chainId.toString() } as ChainChangedRequest)
}
Expand Down Expand Up @@ -90,6 +99,9 @@ class RPCManager {
private onRpcConnect = async (): Promise<ConnectResponse> => {
console.log('[hibitid]', 'onRpcConnect')
this._connectPromise = new BridgePromise()
if (hibitIdSession.wallet) {
this.resolveConnect(await hibitIdSession.wallet.getAccount())
}
const res = await this._connectPromise.promise
return res
}
Expand Down
6 changes: 3 additions & 3 deletions packages/sdk/.env
Original file line number Diff line number Diff line change
@@ -1,3 +1,3 @@
VITE_HIBIT_ID_PROD_URL=http://localhost:5176
VITE_HIBIT_ID_TEST_URL=http://localhost:5176
VITE_HIBIT_ID_DEV_URL=http://localhost:5176
VITE_HIBIT_ID_PROD_URL=https://id.hibit.app
VITE_HIBIT_ID_TEST_URL=https://idtestnet.hibit.app
VITE_HIBIT_ID_DEV_URL=https://localhost:5176
6 changes: 3 additions & 3 deletions packages/sdk/src/lib/dom/index.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { CONTROLLER_CONTAINER_ID, IFRAME_CONTAINER_ID } from "../constants"
import { HibitEnv, HibitIdPage, UserAuthInfo } from "../types"
import { HibitEnv, HibitIdPage } from "../types"
import { getHibitIdUrl } from "../utils"
import './index.css'

Expand Down Expand Up @@ -55,7 +55,7 @@ export class HibitIdIframe {
private container: HTMLDivElement
private _visible = false

constructor(env: HibitEnv, auth: UserAuthInfo | null = null, initialPage: HibitIdPage = 'login') {
constructor(env: HibitEnv, initialPage: HibitIdPage = 'login') {
const existed = document.getElementById(IFRAME_CONTAINER_ID)
if (existed) {
this.container = existed as HTMLDivElement
Expand All @@ -65,7 +65,7 @@ export class HibitIdIframe {
const container = document.createElement('div')
container.id = IFRAME_CONTAINER_ID
const iframe = document.createElement('iframe')
iframe.src = getHibitIdUrl(env, auth, initialPage)
iframe.src = getHibitIdUrl(env, initialPage)
// iframe.allow='publickey-credentials-get *; publickey-credentials-create *'
container.appendChild(iframe)
document.body.appendChild(container)
Expand Down
2 changes: 2 additions & 0 deletions packages/sdk/src/lib/enums.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
export enum ClientExposeRPCMethod {
CLOSE = 'close',
IFRAME_READY = 'iframeReady',
LOGIN_CHANGED = 'loginChanged',
CHAIN_CHANGED = 'chainChanged',
ACCOUNTS_CHANGED = 'accountsChanged',
}
Expand Down
2 changes: 1 addition & 1 deletion packages/sdk/src/lib/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,6 @@ export { ClientExposeRPCMethod, HibitIdExposeRPCMethod, AuthenticatorType, Hibit
export { BridgePromise } from './types'
export type {
HibitEnv,
UserAuthInfo,
WalletAccount,
ConnectResponse,
SignMessageRequest,
Expand All @@ -15,4 +14,5 @@ export type {
TransferResponse,
ChainChangedRequest,
AccountsChangedRequest,
LoginChangedRequest,
} from './types'
14 changes: 6 additions & 8 deletions packages/sdk/src/lib/types.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { AuthenticatorType, HibitIdAssetType, HibitIdChainId } from "./enums"
import { HibitIdAssetType, HibitIdChainId } from "./enums"

export type HibitEnv = 'dev' | 'test' | 'prod'
export type HibitIdPage = 'main' | 'login'
Expand Down Expand Up @@ -44,13 +44,6 @@ export interface WalletAccount {
publicKey?: string
}

export interface UserAuthInfo {
type: AuthenticatorType
id: string
name: string
authTimestamp: Date
}

export interface ConnectResponse extends WalletAccount {
}

Expand Down Expand Up @@ -105,3 +98,8 @@ export interface AccountsChangedRequest {
export interface SwitchChainRequest {
chainId: HibitIdChainId
}

export interface LoginChangedRequest {
isLogin: boolean
sub?: string // required if isLogin is true
}
9 changes: 3 additions & 6 deletions packages/sdk/src/lib/utils.ts
Original file line number Diff line number Diff line change
@@ -1,8 +1,6 @@
import { SDK_AUTH_PARAM_KEY } from "./constants";
import { HibitEnv, HibitIdPage, UserAuthInfo } from "./types";
import { Buffer } from 'buffer'
import { HibitEnv, HibitIdPage } from "./types";

export const getHibitIdUrl = (env: HibitEnv, auth: UserAuthInfo | null, initialPage: HibitIdPage) => {
export const getHibitIdUrl = (env: HibitEnv, initialPage: HibitIdPage) => {
let url = '';
switch (env) {
case 'dev': {
Expand All @@ -18,7 +16,6 @@ export const getHibitIdUrl = (env: HibitEnv, auth: UserAuthInfo | null, initialP
break
}
}
const authQuery = auth ? `?${SDK_AUTH_PARAM_KEY}=${Buffer.from(JSON.stringify(auth), 'utf-8').toString('hex')}` : ''
url = `${url}/${initialPage === 'login' ? 'login' : ''}${authQuery}`
url = `${url}/${initialPage === 'login' ? 'login' : ''}`
return url
}
62 changes: 53 additions & 9 deletions packages/sdk/src/lib/wallet.tsx
Original file line number Diff line number Diff line change
@@ -1,15 +1,18 @@
import { RPC } from '@mixer/postmessage-rpc';
import { RPC_SERVICE_NAME } from './constants';
import { HibitIdController, HibitIdIframe } from './dom';
import { AccountsChangedRequest, ChainChangedRequest, ChainInfo, ConnectResponse, GetBalanceRequest, GetBalanceResponse, HibitEnv, HibitIdEventHandlerMap, HibitIdPage, SignMessageResponse, TransferRequest, TransferResponse, UserAuthInfo, WalletAccount } from './types';
import { AccountsChangedRequest, BridgePromise, ChainChangedRequest, ChainInfo, ConnectResponse, GetBalanceRequest, GetBalanceResponse, HibitEnv, HibitIdEventHandlerMap, HibitIdPage, LoginChangedRequest, SignMessageResponse, TransferRequest, TransferResponse, WalletAccount } from './types';
import { ClientExposeRPCMethod, HibitIdChainId, HibitIdExposeRPCMethod } from './enums';

const LOGIN_SESSION_KEY = 'hibit-id-session'

export class HibitIdWallet {
private _env: HibitEnv = 'prod'
private _connected = false
private _rpc: RPC | null = null
private _controller: HibitIdController | null = null
private _iframe: HibitIdIframe | null = null
private _iframeReadyPromise = new BridgePromise<boolean>()
private _eventHandlers: {
accountsChanged: Array<HibitIdEventHandlerMap['accountsChanged']>
chainChanged: Array<HibitIdEventHandlerMap['chainChanged']>
Expand All @@ -20,6 +23,14 @@ export class HibitIdWallet {

constructor(env: HibitEnv) {
this._env = env

const sessionString = sessionStorage.getItem(LOGIN_SESSION_KEY)
if (sessionString) {
this.prepareIframe().then(() => {
this._connected = true
this._controller = new HibitIdController(this.toggleIframe)
})
}
}

get isConnected() {
Expand All @@ -32,15 +43,15 @@ export class HibitIdWallet {
}

try {
await this.prepareIframe(undefined, 'login')
this._iframe!.show({ fullscreen: true, style: {} })
await this.prepareIframe()
// this._iframe!.show({ fullscreen: true, style: {} })
const res = await this._rpc!.call<ConnectResponse>(HibitIdExposeRPCMethod.CONNECT, {})
if (!res) {
throw new Error('No response from wallet')
}
this._iframe!.hide()
this._connected = true
this._controller = new HibitIdController(this.toggleIframe)
// this._controller = new HibitIdController(this.toggleIframe)
console.log('[hibit id connected]')

return {
Expand Down Expand Up @@ -114,6 +125,7 @@ export class HibitIdWallet {
this._iframe?.destroy()
this._controller?.destroy()
this._connected = false
this._iframeReadyPromise = new BridgePromise<boolean>()
}

public switchToChain = async (chainId: HibitIdChainId) => {
Expand Down Expand Up @@ -145,7 +157,7 @@ export class HibitIdWallet {
} else {
const controllerRect = this._controller?.getBoundingRect()
this._iframe.show({
fullscreen: !this._connected,
fullscreen: false,
style: {
maxWidth: '100%',
maxHeight: '100%',
Expand All @@ -158,13 +170,14 @@ export class HibitIdWallet {
}
}

private prepareIframe = async (auth?: UserAuthInfo, page?: HibitIdPage) => {
private prepareIframe = async (page?: HibitIdPage) => {
if (this._rpc && this._iframe) {
await this._rpc.isReady
return
}

this._iframe = new HibitIdIframe(this._env, auth, page)
this._iframe = new HibitIdIframe(this._env, page)

const rpc = new RPC({
// The window you want to talk to:
target: this._iframe.iframe.contentWindow!,
Expand All @@ -174,20 +187,47 @@ export class HibitIdWallet {
// origin: 'example.com',
});
rpc.expose(ClientExposeRPCMethod.CLOSE, this.onRpcClose);
rpc.expose(ClientExposeRPCMethod.IFRAME_READY, this.onRpcIframeReady);
rpc.expose(ClientExposeRPCMethod.LOGIN_CHANGED, this.onRpcLoginChanged);
rpc.expose(ClientExposeRPCMethod.CHAIN_CHANGED, this.onRpcChainChanged);
rpc.expose(ClientExposeRPCMethod.ACCOUNTS_CHANGED, this.onRpcAccountsChanged);

console.log('[sdk rpc init]')
await rpc.isReady
await this._iframeReadyPromise.promise
console.log('[sdk rpc ready]')
this._rpc = rpc
}

private onRpcClose = () => {
this._iframe?.hide()
this._controller?.setOpen(false)
}

private onRpcLoginChanged = (input: LoginChangedRequest) => {
if (!input.isLogin) {
this._iframe?.show({ fullscreen: true, style: {} })
} else {
if (!this._controller) {
this._controller = new HibitIdController(this.toggleIframe)
}
const controllerRect = this._controller?.getBoundingRect()
this._iframe?.show({
fullscreen: false,
style: {
maxWidth: '100%',
maxHeight: '100%',
width: '332px',
height: '502px',
right: `${controllerRect ? (window.innerWidth - controllerRect.right) : 50}px`,
bottom: `${controllerRect ? (window.innerHeight - controllerRect.top + 20) : 50}px`,
}
})
this._controller?.setOpen(true)
sessionStorage.setItem(LOGIN_SESSION_KEY, input.sub || '')
}
}

private onRpcChainChanged = (input: ChainChangedRequest) => {
this._eventHandlers.chainChanged.forEach((handler) => {
handler(input.chainId)
Expand All @@ -199,4 +239,8 @@ export class HibitIdWallet {
handler(input.account)
})
}

private onRpcIframeReady = () => {
this._iframeReadyPromise.resolve(true)
}
}
2 changes: 0 additions & 2 deletions packages/sdk/vite.config.d.ts

This file was deleted.

Loading
Loading