Skip to content

Commit

Permalink
Init valtio state management (#114)
Browse files Browse the repository at this point in the history
* feat: valtio state management

* feat: using vialto for state management. Disconnect not working

* fix: types and rename clasess

* fix: requestUpdate on disconnect

* fix: typo

* fix: add usePersistence: true

* fix: remove commented code

* fix: dist instead of src

* fix: typo

* fix: using built it connection functions

* fix: tests
  • Loading branch information
darrenvechain authored Nov 29, 2023
1 parent 5517d3b commit 79dd9c7
Show file tree
Hide file tree
Showing 46 changed files with 394 additions and 444 deletions.
1 change: 1 addition & 0 deletions apps/sample-angular-app/src/main.ts
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ const vechainWalletKitOptions = {
network: 'test',
walletConnectOptions,
useWalletKitModal: true,
usePersistence: true,
};

DAppKit.configure(vechainWalletKitOptions);
10 changes: 9 additions & 1 deletion apps/sample-react-app/src/Screens/Homepage.tsx
Original file line number Diff line number Diff line change
@@ -1,8 +1,16 @@
import React from 'react';
import React, { useEffect } from 'react';
import { Box, Grid, GridItem, VStack } from '@chakra-ui/react';
import { useWallet } from '@vechainfoundation/dapp-kit-react';
import { Counter, MeetVeWorld, Welcome } from './components';

export const Homepage: React.FC = () => {
const { account, source } = useWallet();

useEffect(() => {
// eslint-disable-next-line no-console
console.log(account, source);
}, [account, source]);

return (
<VStack spacing={8} w="full">
<Grid
Expand Down
1 change: 1 addition & 0 deletions apps/sample-svelte-app/src/lib/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ const vechainWalletKitOptions = {
network: 'test',
walletConnectOptions,
useWalletKitModal: true,
usePersistence: true,
};

DAppKit.configure(vechainWalletKitOptions);
1 change: 1 addition & 0 deletions apps/sample-vanilla-app/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ const vechainWalletKitOptions = {
network: 'test',
walletConnectOptions,
useWalletKitModal: true,
usePersistence: true,
};

const connex = DAppKit.configure(vechainWalletKitOptions);
Expand Down
2 changes: 1 addition & 1 deletion apps/sample-vanilla-app/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@
"scripts": {
"build": "parcel build index.html --public-url /vechain-dapp-kit/vanilla",
"clean": "rm -rf dist",
"dev": "parcel index.html --open --no-cache --port 3001",
"dev": "parcel index.html --open --no-cache --port 3002",
"purge": "yarn clean && rm -rf node_modules",
"test": "echo \"Error: no test specified\" && exit 1"
},
Expand Down
1 change: 1 addition & 0 deletions apps/sample-vue-app/src/connex/ConnexProvider.vue
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,7 @@ export default defineComponent({
nodeUrl: 'https://mainnet.vechain.org/',
walletConnectOptions,
useWalletKitModal: true,
usePersistence: true,
});
const onDisconnected = () => {
Expand Down
3 changes: 2 additions & 1 deletion packages/dapp-kit-react/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,8 @@
"@vechainfoundation/dapp-kit-ui": "*",
"react-icons": "^4.11.0",
"styled-components": "^6.1.0",
"thor-devkit": "^2.0.9"
"thor-devkit": "^2.0.9",
"valtio": "^1.12.1"
},
"devDependencies": {
"@types/react": "^18.2.28",
Expand Down
Original file line number Diff line number Diff line change
@@ -1,38 +1,11 @@
import { useCallback, useContext, useMemo } from 'react';
import type { WalletSource } from '@vechainfoundation/dapp-kit';
import type { SourceInfo } from '@vechainfoundation/dapp-kit-ui';
import { useContext, useMemo } from 'react';
import { ThemeContext } from '../../../provider/ThemeProvider';
import { useWallet } from '../../../ConnexProvider';
import { createButtonWithModal } from './Wrapped/ConnectModalWithButtonWrapped';

export const ConnectButtonWithModal = () => {
const { theme } = useContext(ThemeContext);

const ModalWithButton = useMemo(() => createButtonWithModal(), []);

const { setSource, connect, setAccount } = useWallet();

const connectHandler = useCallback(
async (source: WalletSource) => {
setSource(source);

const { account } = await connect();

setAccount(account);
},
[connect, setAccount, setSource],
);

const _connect = useCallback(
(source?: SourceInfo) => {
if (source) {
connectHandler(source.id).catch(() => {
// do nothing
});
}
},
[connectHandler],
);

return <ModalWithButton mode={theme.mode} onSourceClick={_connect} />;
return <ModalWithButton mode={theme.mode} />;
};
134 changes: 13 additions & 121 deletions packages/dapp-kit-react/src/ConnexProvider.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -8,21 +8,9 @@ import React, {
} from 'react';
import type { WalletSource } from '@vechainfoundation/dapp-kit';
import { DAppKit } from '@vechainfoundation/dapp-kit-ui';
import { subscribeKey } from 'valtio/utils';
import type { ConnexContext, ConnexProviderOptions } from './types';

const STORAGE_PREFIX = '@vechainfoundation/dapp-kit';
const persist = (key: 'source' | 'account', value: string): void => {
localStorage.setItem(`${STORAGE_PREFIX}${key}`, value);
};

const retrieve = (key: 'source' | 'account'): string | null => {
return localStorage.getItem(`${STORAGE_PREFIX}${key}`);
};

const remove = (key: 'source' | 'account'): void => {
localStorage.removeItem(`${STORAGE_PREFIX}${key}`);
};

/**
* Context
*/
Expand All @@ -37,12 +25,8 @@ export const ConnexProvider: React.FC<ConnexProviderOptions> = ({
persistState = false,
useWalletKitModal = false,
}): React.ReactElement => {
const [account, setAccount] = useState<string | null>(
persistState ? retrieve('account') : null,
);
const [source, setSource] = useState<WalletSource | null>(
persistState ? (retrieve('source') as WalletSource) : null,
);
const [account, setAccount] = useState<string | null>(null);
const [source, setSource] = useState<WalletSource | null>(null);

const connex = useMemo(
() =>
Expand All @@ -51,100 +35,21 @@ export const ConnexProvider: React.FC<ConnexProviderOptions> = ({
genesis: nodeOptions.network,
walletConnectOptions,
useWalletKitModal,
usePersistence: persistState,
}),
[
persistState,
useWalletKitModal,
nodeOptions.network,
nodeOptions.node,
walletConnectOptions,
],
);

/**
* Run at start - Set wallet source if it was persisted
*/
useEffect(() => {
const instanceSource = connex.wallet.getSource();

if (source && !instanceSource) {
connex.wallet.setSource(source);
}
// eslint-disable-next-line react-hooks/exhaustive-deps
}, []);

const availableWallets: WalletSource[] = useMemo(() => {
return connex.wallet.getAvailableSources();
}, [connex.wallet]);

useEffect(() => {
const onDisconnected = (): void => {
setAccount(null);
setSource(null);

if (persistState) {
remove('account');
remove('source');
}
};

const onSourceChanged = (_src: WalletSource | null): void => {
setSource(_src);

if (persistState) {
_src ? persist('source', _src) : remove('source');
}
};

connex.wallet.onDisconnected(onDisconnected);
connex.wallet.onSourceChanged(onSourceChanged);

return () => {
connex.wallet.removeOnDisconnected(onDisconnected);
connex.wallet.removeOnSourceChanged(onSourceChanged);
};
}, [connex.wallet, persistState]);

const connect = useCallback(async () => {
const res = await connex.wallet.connect();

setAccount(res.account);

if (persistState) {
persist('account', res.account);
}

return res;
}, [persistState, connex.wallet, setAccount]);

const disconnect = useCallback(async () => {
await connex.wallet.disconnect();

setAccount(null);
setSource(null);

if (persistState) {
remove('account');
remove('source');
}
}, [persistState, connex.wallet]);

const updateSource = useCallback(
(_source: WalletSource) => {
connex.wallet.setSource(_source);
},
[connex.wallet],
);

const updateAccount = useCallback(
(_account: string) => {
setAccount(_account);

if (persistState) {
persist('account', _account);
}
},
[persistState],
);
subscribeKey(connex.wallet.state, 'address', (v) => setAccount(v));
subscribeKey(connex.wallet.state, 'source', (v) => setSource(v));
}, [connex.wallet.state]);

const openModal = useCallback(() => {
DAppKit.modal.open();
Expand All @@ -161,11 +66,10 @@ export const ConnexProvider: React.FC<ConnexProviderOptions> = ({
vendor: connex.vendor,
},
wallet: {
setSource: updateSource,
setAccount: updateAccount,
disconnect,
connect,
availableWallets,
setSource: connex.wallet.setSource,
disconnect: connex.wallet.disconnect,
connect: connex.wallet.connect,
availableWallets: connex.wallet.state.availableSources,
account,
source,
},
Expand All @@ -174,19 +78,7 @@ export const ConnexProvider: React.FC<ConnexProviderOptions> = ({
close: closeModal,
},
};
}, [
connex.thor,
connex.vendor,
updateSource,
updateAccount,
disconnect,
connect,
availableWallets,
account,
source,
closeModal,
openModal,
]);
}, [connex, account, source, closeModal, openModal]);

return (
<ConnexProviderContext.Provider value={context}>
Expand Down
1 change: 0 additions & 1 deletion packages/dapp-kit-react/src/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,6 @@ export interface ConnexContext {
};
wallet: {
setSource: (source: WalletSource) => void;
setAccount: (account: string) => void;
availableWallets: WalletSource[];
disconnect: () => void;
connect: () => Promise<ConnectResponse>;
Expand Down
1 change: 1 addition & 0 deletions packages/dapp-kit-ui/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ const vechainWalletKitOptions = {
network: 'test',
walletConnectOptions,
useWalletKitModal: true,
usePersistence: true,
};

DAppKit.configure(vechainWalletKitOptions);
1 change: 1 addition & 0 deletions packages/dapp-kit-ui/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,7 @@
"@web3modal/html": "^2.7.1",
"lit": "^3.0.0",
"qrcode": "1.5.3",
"valtio": "^1.12.1",
"viem": "^1.18.4"
},
"devDependencies": {
Expand Down
2 changes: 1 addition & 1 deletion packages/dapp-kit-ui/src/client.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ import { CustomWalletConnectModal, DAppKitModal } from './modal';

let connex: MultiWalletConnex | null = null;

type DAppKitOptions = Omit<ConnexOptions, 'customWcModal'> & {
export type DAppKitOptions = Omit<ConnexOptions, 'customWcModal'> & {
useWalletKitModal?: boolean;
};

Expand Down
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
import type { TemplateResult } from 'lit';
import { html, LitElement } from 'lit';
import { customElement, property } from 'lit/decorators.js';
import type { Theme, ThemeMode } from '../../constants';
import type { Theme, ThemeMode } from '../constants';

@customElement('vwk-connected-address-badge-with-modal')
export class ConnectedAddressBadgeWithModal extends LitElement {
export class AddressBadgeWithModal extends LitElement {
@property({ type: String })
mode: ThemeMode = 'LIGHT';

Expand Down Expand Up @@ -53,6 +53,6 @@ export class ConnectedAddressBadgeWithModal extends LitElement {

declare global {
interface HTMLElementTagNameMap {
'vwk-connected-address-badge-with-modal': ConnectedAddressBadgeWithModal;
'vwk-connected-address-badge-with-modal': AddressBadgeWithModal;
}
}
Original file line number Diff line number Diff line change
@@ -1,12 +1,13 @@
import { LitElement, type TemplateResult, css, html } from 'lit';
import { css, html, LitElement, type TemplateResult } from 'lit';
import { customElement, property } from 'lit/decorators.js';
import { Colors, type ThemeMode } from '../../constants';
import { friendlyAddress, getPicassoImage } from '../../utils/account';
import { Colors, type ThemeMode } from '../constants';
import { friendlyAddress, getPicassoImage } from '../utils/account';

@customElement('vwk-connected-address-badge')
export class ConnectedAddressBadge extends LitElement {
export class AddressBadge extends LitElement {
static override styles = css`
/* Style for the badge */
.wallet-badge {
display: flex;
width: fit-content;
Expand Down Expand Up @@ -35,11 +36,13 @@ export class ConnectedAddressBadge extends LitElement {
}
/* Style for the wallet address */
.wallet-address {
font-size: 14px;
margin-left: 8px;
font-family: monospace;
}
.address-icon {
width: 23px;
height: 23px;
Expand Down Expand Up @@ -75,6 +78,6 @@ export class ConnectedAddressBadge extends LitElement {

declare global {
interface HTMLElementTagNameMap {
'vwk-connected-address-badge': ConnectedAddressBadge;
'vwk-connected-address-badge': AddressBadge;
}
}
Loading

0 comments on commit 79dd9c7

Please sign in to comment.