@bounded-sh/client 0.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +298 -0
- package/dist/auth/hooks/useAuth.d.ts +8 -0
- package/dist/auth/index.d.ts +73 -0
- package/dist/auth/oidc-auth.d.ts +27 -0
- package/dist/auth/providers/email-auth-provider.d.ts +38 -0
- package/dist/auth/providers/guest-auth-provider.d.ts +14 -0
- package/dist/auth/providers/guest-keystore.d.ts +12 -0
- package/dist/auth/providers/mock-auth-provider.d.ts +49 -0
- package/dist/auth/providers/offchain-auth-provider.d.ts +56 -0
- package/dist/auth/providers/phantom-wallet-provider.d.ts +117 -0
- package/dist/auth/providers/privy-expo-provider.d.ts +115 -0
- package/dist/auth/providers/privy-wallet-provider.d.ts +80 -0
- package/dist/auth/providers/sol/sol-utils.d.ts +2 -0
- package/dist/auth/providers/solana-mobile-wallet-provider.d.ts +155 -0
- package/dist/auth/providers/transaction-utils.d.ts +10 -0
- package/dist/global.d.ts +13 -0
- package/dist/index-BHTfW8CV.esm.js +16091 -0
- package/dist/index-BHTfW8CV.esm.js.map +1 -0
- package/dist/index-C1VOdmRN.js +16130 -0
- package/dist/index-C1VOdmRN.js.map +1 -0
- package/dist/index-CT2j1oic.esm.js +16089 -0
- package/dist/index-CT2j1oic.esm.js.map +1 -0
- package/dist/index-VGx-869x.js +23572 -0
- package/dist/index-VGx-869x.js.map +1 -0
- package/dist/index-o5Hv9pfS.esm.js +23456 -0
- package/dist/index-o5Hv9pfS.esm.js.map +1 -0
- package/dist/index-sKqrgk0t.js +16132 -0
- package/dist/index-sKqrgk0t.js.map +1 -0
- package/dist/index.browser-BJZ7fYwv.js +5081 -0
- package/dist/index.browser-BJZ7fYwv.js.map +1 -0
- package/dist/index.browser-DaNhOhkQ.esm.js +4220 -0
- package/dist/index.browser-DaNhOhkQ.esm.js.map +1 -0
- package/dist/index.browser-DhAcjdpV.esm.js +5071 -0
- package/dist/index.browser-DhAcjdpV.esm.js.map +1 -0
- package/dist/index.browser-utVKQsEC.js +4225 -0
- package/dist/index.browser-utVKQsEC.js.map +1 -0
- package/dist/index.d.ts +21 -0
- package/dist/index.esm.js +8 -0
- package/dist/index.esm.js.map +1 -0
- package/dist/index.js +105 -0
- package/dist/index.js.map +1 -0
- package/dist/index.native-B5IBOdv_.js +19684 -0
- package/dist/index.native-B5IBOdv_.js.map +1 -0
- package/dist/index.native-JPUkdHJj.esm.js +19565 -0
- package/dist/index.native-JPUkdHJj.esm.js.map +1 -0
- package/dist/index.native.d.ts +26 -0
- package/dist/index.native.esm.js +6 -0
- package/dist/index.native.esm.js.map +1 -0
- package/dist/index.native.js +98 -0
- package/dist/index.native.js.map +1 -0
- package/dist/phantom-wallet-provider-CDLyxrih.js +1466 -0
- package/dist/phantom-wallet-provider-CDLyxrih.js.map +1 -0
- package/dist/phantom-wallet-provider-DMlaSrAl.esm.js +1445 -0
- package/dist/phantom-wallet-provider-DMlaSrAl.esm.js.map +1 -0
- package/dist/platform.d.ts +81 -0
- package/dist/privy-wallet-provider-DiHHTDbZ.js +956 -0
- package/dist/privy-wallet-provider-DiHHTDbZ.js.map +1 -0
- package/dist/privy-wallet-provider-nR52lXzI.esm.js +933 -0
- package/dist/privy-wallet-provider-nR52lXzI.esm.js.map +1 -0
- package/dist/solana-mobile-wallet-provider-B4CeMMQd.esm.js +1460 -0
- package/dist/solana-mobile-wallet-provider-B4CeMMQd.esm.js.map +1 -0
- package/dist/solana-mobile-wallet-provider-BYMfFjZb.js +1481 -0
- package/dist/solana-mobile-wallet-provider-BYMfFjZb.js.map +1 -0
- package/dist/utils.d.ts +1 -0
- package/package.json +100 -0
|
@@ -0,0 +1,117 @@
|
|
|
1
|
+
import type { EVMTransaction, SolTransaction, TransactionResult, User, AuthProvider, SetOptions } from '@bounded-sh/core';
|
|
2
|
+
import { PublicKey, Transaction, VersionedTransaction } from '@solana/web3.js';
|
|
3
|
+
export type PhantomProviderType = 'injected' | 'google' | 'apple' | 'deeplink' | 'phantom';
|
|
4
|
+
export interface PhantomWalletConfig {
|
|
5
|
+
appId?: string;
|
|
6
|
+
/** Providers to use for authentication. Accepts string[] for convenience (e.g., ["injected"]) */
|
|
7
|
+
providers?: PhantomProviderType[] | string[];
|
|
8
|
+
autoConnect?: boolean;
|
|
9
|
+
/** Theme for the connect modal: 'light' or 'dark'. Defaults to 'dark'. */
|
|
10
|
+
theme?: 'light' | 'dark';
|
|
11
|
+
/** App name displayed in the connect modal */
|
|
12
|
+
appName?: string;
|
|
13
|
+
/** App icon URL displayed in the connect modal */
|
|
14
|
+
appIcon?: string;
|
|
15
|
+
/** Custom title shown at the top of the login modal. Overrides the default "Log in to your account". */
|
|
16
|
+
modalTitle?: string;
|
|
17
|
+
/** Custom subtitle shown below the title in the login modal. */
|
|
18
|
+
modalSubtitle?: string;
|
|
19
|
+
}
|
|
20
|
+
/**
|
|
21
|
+
* Per-call overrides for `login()`. All fields are optional and take precedence
|
|
22
|
+
* over the values set in `PhantomWalletConfig` during `init()`.
|
|
23
|
+
*/
|
|
24
|
+
export interface LoginOptions {
|
|
25
|
+
/** Override the modal theme just for this login call. */
|
|
26
|
+
theme?: 'light' | 'dark';
|
|
27
|
+
/** Override the modal title just for this login call. */
|
|
28
|
+
modalTitle?: string;
|
|
29
|
+
/** Override the modal subtitle just for this login call. */
|
|
30
|
+
modalSubtitle?: string;
|
|
31
|
+
}
|
|
32
|
+
export declare class PhantomWalletProvider implements AuthProvider {
|
|
33
|
+
private static instance;
|
|
34
|
+
private containerElement;
|
|
35
|
+
private networkUrl;
|
|
36
|
+
private root;
|
|
37
|
+
private phantomMethods;
|
|
38
|
+
private config;
|
|
39
|
+
private resolvedProviders;
|
|
40
|
+
private pendingLogin;
|
|
41
|
+
private loginInProgress;
|
|
42
|
+
private autoLoginInProgress;
|
|
43
|
+
private initPromise;
|
|
44
|
+
private loginOverrides;
|
|
45
|
+
/** Temporarily override modal appearance for a single login() call. Cleared automatically after login settles. */
|
|
46
|
+
setLoginOverrides(opts: LoginOptions | null): void;
|
|
47
|
+
/** Callback to swap to a Mobile Wallet Adapter provider when the user clicks "Connect Mobile Wallet" */
|
|
48
|
+
onSwitchToMWA: (() => Promise<AuthProvider>) | null;
|
|
49
|
+
constructor(networkUrl?: string | null, config?: PhantomWalletConfig);
|
|
50
|
+
private initializeAsync;
|
|
51
|
+
/**
|
|
52
|
+
* Check if social login providers are configured (non-injected providers).
|
|
53
|
+
*/
|
|
54
|
+
private hasSocialProviders;
|
|
55
|
+
static getInstance(networkUrl: string | null, config: PhantomWalletConfig): PhantomWalletProvider;
|
|
56
|
+
private resolveProviders;
|
|
57
|
+
/**
|
|
58
|
+
* Patch the Phantom extension's provider to gracefully handle `phantom_getFeatures`
|
|
59
|
+
* instead of throwing. Some SDKs probe this method to check feature support, but the
|
|
60
|
+
* extension doesn't implement it, causing noisy console errors.
|
|
61
|
+
*/
|
|
62
|
+
private patchPhantomGetFeatures;
|
|
63
|
+
private initialize;
|
|
64
|
+
private ensureReady;
|
|
65
|
+
private ensureSolanaReady;
|
|
66
|
+
/**
|
|
67
|
+
* Get the list of available (configured) providers for this wallet.
|
|
68
|
+
*/
|
|
69
|
+
getAvailableProviders(): PhantomProviderType[];
|
|
70
|
+
/**
|
|
71
|
+
* Login using the Phantom connect modal. A custom modal is rendered with the
|
|
72
|
+
* discovered wallets and configured social providers instead of the SDK's
|
|
73
|
+
* built-in modal.
|
|
74
|
+
*/
|
|
75
|
+
login(): Promise<User | null>;
|
|
76
|
+
restoreSession(): Promise<User | null>;
|
|
77
|
+
private awaitTopLevelConnect;
|
|
78
|
+
address(): Promise<string | null>;
|
|
79
|
+
runTransaction(_evmTransactionData?: EVMTransaction, solTransactionData?: SolTransaction, options?: SetOptions): Promise<TransactionResult>;
|
|
80
|
+
/**
|
|
81
|
+
* Signs a Solana transaction without submitting it.
|
|
82
|
+
*
|
|
83
|
+
* This method handles blockhash automatically if not set - you do NOT need to
|
|
84
|
+
* set recentBlockhash on the transaction before calling this method.
|
|
85
|
+
* The network/RPC URL is derived from the provider's configuration (set during initialization).
|
|
86
|
+
*
|
|
87
|
+
* @param transaction - The transaction to sign (Transaction or VersionedTransaction)
|
|
88
|
+
* @returns The signed transaction
|
|
89
|
+
*/
|
|
90
|
+
signTransaction(transaction: Transaction | VersionedTransaction): Promise<Transaction | VersionedTransaction>;
|
|
91
|
+
/**
|
|
92
|
+
* Signs and submits a Solana transaction to the network.
|
|
93
|
+
*
|
|
94
|
+
* This method handles blockhash and transaction confirmation automatically - you do NOT need to
|
|
95
|
+
* set recentBlockhash or lastValidBlockHeight on the transaction before calling this method.
|
|
96
|
+
* The network/RPC URL is derived from the provider's configuration (set during initialization).
|
|
97
|
+
*
|
|
98
|
+
* @param transaction - The transaction to sign and submit (Transaction or VersionedTransaction)
|
|
99
|
+
* @param feePayer - Optional fee payer public key. If not provided and the transaction doesn't
|
|
100
|
+
* already have a feePayer set, the connected wallet address will be used.
|
|
101
|
+
* Useful for co-signing scenarios where a different account pays the fees.
|
|
102
|
+
* @returns The transaction signature
|
|
103
|
+
*/
|
|
104
|
+
signAndSubmitTransaction(transaction: Transaction | VersionedTransaction, feePayer?: PublicKey): Promise<string>;
|
|
105
|
+
signMessage(message: string): Promise<string>;
|
|
106
|
+
logout(): Promise<void>;
|
|
107
|
+
getNativeMethods(): Promise<any>;
|
|
108
|
+
private getRpcUrl;
|
|
109
|
+
private signAndSendViaPhantom;
|
|
110
|
+
private submitSignedTransaction;
|
|
111
|
+
private submitSignedTransactionWithBlockhash;
|
|
112
|
+
}
|
|
113
|
+
declare global {
|
|
114
|
+
interface Window {
|
|
115
|
+
CUSTOM_TAROBASE_APP_ID_HEADER?: string;
|
|
116
|
+
}
|
|
117
|
+
}
|
|
@@ -0,0 +1,115 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Privy Expo Auth Provider — React Native implementation of AuthProvider.
|
|
3
|
+
*
|
|
4
|
+
* Uses @privy-io/expo instead of @privy-io/react-auth.
|
|
5
|
+
* Persists the session through getActiveSessionManager() (the RN store on React
|
|
6
|
+
* Native), and mints it via the SIWS wallet-signature path — identical to
|
|
7
|
+
* Phantom/MWA — so no Privy-specific backend verification is required.
|
|
8
|
+
*
|
|
9
|
+
* IMPORTANT — Expo/RN consumers must:
|
|
10
|
+
* 1. Install polyfills: fast-text-encoding, react-native-get-random-values
|
|
11
|
+
* 2. Install @privy-io/expo, @privy-io/expo-native-extensions
|
|
12
|
+
* 3. Call ReactNativeSessionManager.configure({ storage, atob }) at startup
|
|
13
|
+
* 4. Call setPlatform({ ... }) from @bounded-sh/web at startup
|
|
14
|
+
* 5. Wrap their app tree with PrivyProvider from @privy-io/expo
|
|
15
|
+
* 6. Create this provider and pass the Privy hooks/methods via setPrivyMethods()
|
|
16
|
+
*
|
|
17
|
+
* Unlike the web PrivyWalletProvider which renders a hidden React DOM tree
|
|
18
|
+
* to host Privy's React context, this provider expects the RN app itself
|
|
19
|
+
* to render <PrivyProvider> and then bridge the hooks via setPrivyMethods().
|
|
20
|
+
*/
|
|
21
|
+
import type { EVMTransaction, SolTransaction, TransactionResult, AuthProvider, User, SetOptions } from '@bounded-sh/core';
|
|
22
|
+
import { PublicKey, Connection, Transaction, VersionedTransaction } from '@solana/web3.js';
|
|
23
|
+
export interface PrivyExpoMethods {
|
|
24
|
+
/** Whether Privy SDK is fully initialized. */
|
|
25
|
+
isReady: boolean;
|
|
26
|
+
/** Whether the user is authenticated. */
|
|
27
|
+
isAuthenticated: boolean;
|
|
28
|
+
/** The user object from usePrivy(). */
|
|
29
|
+
user: any;
|
|
30
|
+
/** Trigger Privy login UI. Returns the user on success. */
|
|
31
|
+
login: () => Promise<any>;
|
|
32
|
+
/** Log out from Privy. */
|
|
33
|
+
logout: () => Promise<void>;
|
|
34
|
+
/** Get an access token from Privy. */
|
|
35
|
+
getAccessToken: () => Promise<string | null>;
|
|
36
|
+
/** Get the Privy identity token. */
|
|
37
|
+
getIdentityToken: () => Promise<string | null>;
|
|
38
|
+
/**
|
|
39
|
+
* Get the embedded Solana wallet provider.
|
|
40
|
+
* Comes from useEmbeddedSolanaWallet().
|
|
41
|
+
*/
|
|
42
|
+
getWalletProvider: () => Promise<{
|
|
43
|
+
address: string;
|
|
44
|
+
signMessage: (message: Uint8Array) => Promise<{
|
|
45
|
+
signature: Uint8Array;
|
|
46
|
+
}>;
|
|
47
|
+
signTransaction: (transaction: Transaction | VersionedTransaction) => Promise<{
|
|
48
|
+
signedTransaction: Uint8Array;
|
|
49
|
+
}>;
|
|
50
|
+
signAndSendTransaction: (transaction: Transaction | VersionedTransaction, connection: Connection) => Promise<{
|
|
51
|
+
signature: string;
|
|
52
|
+
}>;
|
|
53
|
+
} | null>;
|
|
54
|
+
}
|
|
55
|
+
export declare class PrivyExpoProvider implements AuthProvider {
|
|
56
|
+
private networkUrl;
|
|
57
|
+
private privyMethods;
|
|
58
|
+
private appId;
|
|
59
|
+
constructor(appId: string, networkUrl?: string | null);
|
|
60
|
+
/**
|
|
61
|
+
* Bridge Privy hooks from the app's React tree into this provider.
|
|
62
|
+
*
|
|
63
|
+
* Call this from a component rendered inside <PrivyProvider>:
|
|
64
|
+
* ```tsx
|
|
65
|
+
* const privy = usePrivy();
|
|
66
|
+
* const wallet = useEmbeddedSolanaWallet();
|
|
67
|
+
* const { getAccessToken } = usePrivy();
|
|
68
|
+
* const { getIdentityToken } = useIdentityToken();
|
|
69
|
+
*
|
|
70
|
+
* useEffect(() => {
|
|
71
|
+
* provider.setPrivyMethods({
|
|
72
|
+
* isReady: privy.isReady,
|
|
73
|
+
* isAuthenticated: !!privy.user,
|
|
74
|
+
* user: privy.user,
|
|
75
|
+
* login: privy.login,
|
|
76
|
+
* logout: privy.logout,
|
|
77
|
+
* getAccessToken,
|
|
78
|
+
* getIdentityToken,
|
|
79
|
+
* getWalletProvider: async () => {
|
|
80
|
+
* if (!wallet.wallets[0]) return null;
|
|
81
|
+
* const provider = await wallet.wallets[0].getProvider();
|
|
82
|
+
* return {
|
|
83
|
+
* address: wallet.wallets[0].address,
|
|
84
|
+
* signMessage: provider.signMessage,
|
|
85
|
+
* signTransaction: provider.signTransaction,
|
|
86
|
+
* signAndSendTransaction: provider.signAndSendTransaction,
|
|
87
|
+
* };
|
|
88
|
+
* },
|
|
89
|
+
* });
|
|
90
|
+
* }, [privy.isReady, privy.user, wallet.wallets]);
|
|
91
|
+
* ```
|
|
92
|
+
*/
|
|
93
|
+
setPrivyMethods(methods: PrivyExpoMethods): void;
|
|
94
|
+
login(): Promise<User | null>;
|
|
95
|
+
runTransaction(_evmTransactionData?: EVMTransaction, solTransactionData?: SolTransaction, options?: SetOptions): Promise<TransactionResult>;
|
|
96
|
+
signMessage(message: string): Promise<string>;
|
|
97
|
+
signTransaction(transaction: Transaction | VersionedTransaction): Promise<Transaction | VersionedTransaction>;
|
|
98
|
+
signAndSubmitTransaction(transaction: Transaction | VersionedTransaction, feePayer?: PublicKey): Promise<string>;
|
|
99
|
+
restoreSession(): Promise<User | null>;
|
|
100
|
+
logout(): Promise<void>;
|
|
101
|
+
getNativeMethods(): Promise<any>;
|
|
102
|
+
/**
|
|
103
|
+
* Mint a Tarobase session from a Privy Solana wallet by signing the canonical
|
|
104
|
+
* SIWS challenge (nonce -> genSolanaMessage -> wallet.signMessage). This reuses
|
|
105
|
+
* createSessionWithSignature — the exact path Phantom, the mobile wallet
|
|
106
|
+
* adapter, and the guest device-key use — so the bounded /session issuer mints
|
|
107
|
+
* the session with no Privy-specific verification (it arrives as a Solana
|
|
108
|
+
* wallet signature, defaulting to authMethod 'phantom' server-side).
|
|
109
|
+
*/
|
|
110
|
+
private createSession;
|
|
111
|
+
private getWalletOrThrow;
|
|
112
|
+
private signAndSubmitInternal;
|
|
113
|
+
private getRpcUrl;
|
|
114
|
+
private ensureReady;
|
|
115
|
+
}
|
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
import type { EVMTransaction, SolTransaction, TransactionResult, AuthProvider, User, SetOptions } from '@bounded-sh/core';
|
|
2
|
+
import { PublicKey, Transaction, VersionedTransaction } from '@solana/web3.js';
|
|
3
|
+
export declare class PrivyWalletProvider implements AuthProvider {
|
|
4
|
+
private static instance;
|
|
5
|
+
private containerElement;
|
|
6
|
+
private networkUrl;
|
|
7
|
+
private chainId;
|
|
8
|
+
private root;
|
|
9
|
+
private privyMethods;
|
|
10
|
+
private privyConfig;
|
|
11
|
+
private pendingLogin;
|
|
12
|
+
private pendingTransaction;
|
|
13
|
+
private pendingSignTransaction;
|
|
14
|
+
private pendingSignMessage;
|
|
15
|
+
private pendingSignAndSubmitTransaction;
|
|
16
|
+
constructor(appName: string | null, appLogoUrl: string | null, privyConfig?: {
|
|
17
|
+
appId: string;
|
|
18
|
+
config: any;
|
|
19
|
+
}, networkUrl?: string | null);
|
|
20
|
+
static getInstance(appName: string | null, appLogoUrl: string | null, privyConfig: any): PrivyWalletProvider;
|
|
21
|
+
private initialize;
|
|
22
|
+
login(): Promise<User | null>;
|
|
23
|
+
getNativeMethods(): Promise<any>;
|
|
24
|
+
logout(): Promise<void>;
|
|
25
|
+
runTransaction(_evmTransactionData?: EVMTransaction, solTransactionData?: SolTransaction, options?: SetOptions): Promise<TransactionResult>;
|
|
26
|
+
/**
|
|
27
|
+
* Signs a Solana transaction without submitting it.
|
|
28
|
+
*
|
|
29
|
+
* This method handles blockhash automatically if not set - you do NOT need to
|
|
30
|
+
* set recentBlockhash on the transaction before calling this method.
|
|
31
|
+
* The network/RPC URL is derived from the provider's configuration (set during initialization).
|
|
32
|
+
*
|
|
33
|
+
* @param transaction - The transaction to sign (Transaction or VersionedTransaction)
|
|
34
|
+
* @returns The signed transaction
|
|
35
|
+
*/
|
|
36
|
+
signTransaction(transaction: Transaction | VersionedTransaction): Promise<Transaction | VersionedTransaction>;
|
|
37
|
+
/**
|
|
38
|
+
* Signs and submits a Solana transaction to the network.
|
|
39
|
+
*
|
|
40
|
+
* This method handles blockhash and transaction confirmation automatically - you do NOT need to
|
|
41
|
+
* set recentBlockhash or lastValidBlockHeight on the transaction before calling this method.
|
|
42
|
+
* The network/RPC URL is derived from the provider's configuration (set during initialization).
|
|
43
|
+
*
|
|
44
|
+
* @param transaction - The transaction to sign and submit (Transaction or VersionedTransaction)
|
|
45
|
+
* @param feePayer - Optional fee payer public key. If not provided and the transaction doesn't
|
|
46
|
+
* already have a feePayer set, the connected wallet address will be used.
|
|
47
|
+
* Useful for co-signing scenarios where a different account pays the fees.
|
|
48
|
+
* @returns The transaction signature
|
|
49
|
+
*/
|
|
50
|
+
signAndSubmitTransaction(transaction: Transaction | VersionedTransaction, feePayer?: PublicKey): Promise<string>;
|
|
51
|
+
private getRpcUrl;
|
|
52
|
+
/**
|
|
53
|
+
* Internal sign transaction - serializes and signs via Privy
|
|
54
|
+
* Returns the raw result from Privy (Uint8Array)
|
|
55
|
+
* This mirrors exactly what runTransaction was doing
|
|
56
|
+
*/
|
|
57
|
+
private signTransactionRaw;
|
|
58
|
+
/**
|
|
59
|
+
* Deserialize a signed transaction from Uint8Array to Transaction object
|
|
60
|
+
*/
|
|
61
|
+
private deserializeSignedTransaction;
|
|
62
|
+
/**
|
|
63
|
+
* Internal sign and submit - handles Surfnet vs non-Surfnet logic
|
|
64
|
+
* This is the core submission logic used by both signAndSubmitTransaction and runTransaction
|
|
65
|
+
*
|
|
66
|
+
* For Surfnet: sign with signTransactionRaw, then sendRawTransaction
|
|
67
|
+
* For non-Surfnet: use Privy's signAndSendTransaction (combined operation)
|
|
68
|
+
*/
|
|
69
|
+
private signAndSubmitInternal;
|
|
70
|
+
signMessage(message: string): Promise<string>;
|
|
71
|
+
restoreSession(): Promise<User | null>;
|
|
72
|
+
private createSession;
|
|
73
|
+
/**
|
|
74
|
+
* Waits for a wallet matching the session address to appear in the wallets array.
|
|
75
|
+
* This handles the timing gap where Privy's embedded wallet (created for email login users)
|
|
76
|
+
* may not yet be in the useWallets() array when signTransaction is called immediately after login.
|
|
77
|
+
*/
|
|
78
|
+
private waitForMatchingWallet;
|
|
79
|
+
private ensureReady;
|
|
80
|
+
}
|
|
@@ -0,0 +1,155 @@
|
|
|
1
|
+
import type { EVMTransaction, SolTransaction, TransactionResult, User, AuthProvider, SetOptions } from '@bounded-sh/core';
|
|
2
|
+
import { PublicKey, Transaction, VersionedTransaction } from '@solana/web3.js';
|
|
3
|
+
export interface SolanaMobileWalletConfig {
|
|
4
|
+
/** App identity shown to the wallet during authorization */
|
|
5
|
+
appIdentity?: {
|
|
6
|
+
name?: string;
|
|
7
|
+
uri?: string;
|
|
8
|
+
icon?: string;
|
|
9
|
+
};
|
|
10
|
+
/** Solana cluster: 'mainnet-beta' | 'devnet' | 'testnet' */
|
|
11
|
+
cluster?: string;
|
|
12
|
+
/** Theme for any UI elements: 'light' or 'dark' */
|
|
13
|
+
theme?: 'light' | 'dark';
|
|
14
|
+
}
|
|
15
|
+
/**
|
|
16
|
+
* Detects whether the current environment is a mobile browser capable of
|
|
17
|
+
* Mobile Wallet Adapter (MWA) communication.
|
|
18
|
+
*
|
|
19
|
+
* Returns true on Android browsers (Chrome, etc.) where MWA intents work,
|
|
20
|
+
* or inside a Seeker/Saga in-app browser context.
|
|
21
|
+
*/
|
|
22
|
+
export declare function isMobileWalletAvailable(): boolean;
|
|
23
|
+
/**
|
|
24
|
+
* Registers Mobile Wallet Adapter as a wallet-standard wallet so it appears
|
|
25
|
+
* in wallet selection UIs and can be discovered by other wallet-standard consumers.
|
|
26
|
+
*
|
|
27
|
+
* Call this once at app startup (in a browser-only / non-SSR context).
|
|
28
|
+
*
|
|
29
|
+
* @param config - App identity and optional remote host authority for desktop QR code support
|
|
30
|
+
*/
|
|
31
|
+
export declare function registerMobileWalletAdapter(config?: {
|
|
32
|
+
appIdentity?: {
|
|
33
|
+
name?: string;
|
|
34
|
+
uri?: string;
|
|
35
|
+
icon?: string;
|
|
36
|
+
};
|
|
37
|
+
chains?: string[];
|
|
38
|
+
remoteHostAuthority?: string;
|
|
39
|
+
/**
|
|
40
|
+
* Optional custom wallet-not-found handler. If omitted, the SDK installs
|
|
41
|
+
* a no-op (NOT the library default) — see comment below.
|
|
42
|
+
*/
|
|
43
|
+
onWalletNotFound?: (mobileWalletAdapter: any) => Promise<void>;
|
|
44
|
+
}): Promise<void>;
|
|
45
|
+
/**
|
|
46
|
+
* SolanaMobileWalletProvider implements the AuthProvider interface using
|
|
47
|
+
* Solana Mobile's wallet-standard wrapper (`LocalSolanaMobileWalletAdapterWallet`).
|
|
48
|
+
*
|
|
49
|
+
* Why wallet-standard and not the raw MWA protocol: as of
|
|
50
|
+
* `@solana-mobile/wallet-standard-mobile@0.5.0+`, the wallet's internal
|
|
51
|
+
* `#transact` calls `checkLocalNetworkAccessPermission()` before opening the
|
|
52
|
+
* localhost WebSocket. That helper renders a three-stage UX flow Solana
|
|
53
|
+
* Mobile designed specifically to defuse Chrome's Local Network Access
|
|
54
|
+
* permission dialog (which renders with disabled buttons on Android Chrome,
|
|
55
|
+
* the source of the long-running Seeker MWA bug):
|
|
56
|
+
*
|
|
57
|
+
* 1. "Allow connections to your wallet" informational modal.
|
|
58
|
+
* 2. Chrome's permission prompt (interactive because it's spawned as a
|
|
59
|
+
* fresh user gesture from step 1).
|
|
60
|
+
* 3. "Ready to connect!" success modal.
|
|
61
|
+
*
|
|
62
|
+
* `checkLocalNetworkAccessPermission` is internal to the library — it's not
|
|
63
|
+
* exported. The only way to invoke it is to go through the wallet's
|
|
64
|
+
* `standard:connect` / `solana:sign*` features, which is what this provider
|
|
65
|
+
* does.
|
|
66
|
+
*
|
|
67
|
+
* Notes on UX: login uses two wallet popups in succession — `standard:connect`
|
|
68
|
+
* (authorize) and `solana:signMessage` (sign the Tarobase nonce). The
|
|
69
|
+
* previous implementation combined both inside a single `transact` callback;
|
|
70
|
+
* splitting them is the cost of going through wallet-standard, and is
|
|
71
|
+
* acceptable given the alternative was broken on Seeker.
|
|
72
|
+
*/
|
|
73
|
+
export declare class SolanaMobileWalletProvider implements AuthProvider {
|
|
74
|
+
private static instance;
|
|
75
|
+
private networkUrl;
|
|
76
|
+
private config;
|
|
77
|
+
private appIdentity;
|
|
78
|
+
/** Raw cluster name (e.g. 'mainnet-beta'); mapped via mapChainToWalletStandard. */
|
|
79
|
+
private cluster;
|
|
80
|
+
/** LocalSolanaMobileWalletAdapterWallet, lazy-constructed in ensureWallet(). */
|
|
81
|
+
private wallet;
|
|
82
|
+
constructor(networkUrl?: string | null, config?: SolanaMobileWalletConfig);
|
|
83
|
+
static getInstance(networkUrl: string | null, config: SolanaMobileWalletConfig): SolanaMobileWalletProvider;
|
|
84
|
+
/** Lazy-construct LocalSolanaMobileWalletAdapterWallet on first need. */
|
|
85
|
+
private ensureWallet;
|
|
86
|
+
/**
|
|
87
|
+
* Ensure the wallet has an active authorization. After a Tarobase session
|
|
88
|
+
* is restored from storage on cold-start, `wallet.accounts` is empty until
|
|
89
|
+
* we silently reconnect from the AuthorizationCache. If the cache is also
|
|
90
|
+
* empty, fall back to interactive `login()` (which surfaces the three-stage
|
|
91
|
+
* Solana Mobile LNA flow + wallet popups).
|
|
92
|
+
*
|
|
93
|
+
* Returns the wallet-standard `WalletAccount` to use for sign operations.
|
|
94
|
+
*/
|
|
95
|
+
private ensureAuthorized;
|
|
96
|
+
/** Returns the active wallet-standard chain identifier (e.g. 'solana:mainnet'). */
|
|
97
|
+
private getChain;
|
|
98
|
+
/**
|
|
99
|
+
* Cached MWA auth_token returned by `wallet.authorize()`. Reused by
|
|
100
|
+
* subsequent native transact() calls (signMessage / signTransaction)
|
|
101
|
+
* so the user doesn't get the wallet-pick popup on every operation.
|
|
102
|
+
* Persisted to platform storage and hydrated by the constructor on
|
|
103
|
+
* native; cleared by logout() and on `ERROR_REAUTHORIZE`.
|
|
104
|
+
*/
|
|
105
|
+
private nativeAuthToken;
|
|
106
|
+
/** Cached public key string for the connected MWA wallet (native). */
|
|
107
|
+
private nativeAddress;
|
|
108
|
+
/**
|
|
109
|
+
* Dynamically import and unwrap `transact` from the MWA web3js
|
|
110
|
+
* package. The package is externalized in rollup.config.js so this
|
|
111
|
+
* resolves to `lib/cjs/index.native.js` (TurboModule-backed) on
|
|
112
|
+
* Metro and `lib/esm/index.browser.js` (WebSocket) on webpack/vite
|
|
113
|
+
* per their respective platform conditions. Handles Metro's CJS-to-
|
|
114
|
+
* ESM interop variance (`mod.transact` vs `mod.default?.transact`).
|
|
115
|
+
*/
|
|
116
|
+
private loadTransact;
|
|
117
|
+
/**
|
|
118
|
+
* Cache and persist a fresh MWA auth_token + address. Called from
|
|
119
|
+
* `_loginNative` after a successful authorize. Storage failures are
|
|
120
|
+
* non-fatal (next cold-start re-auths).
|
|
121
|
+
*/
|
|
122
|
+
private persistNativeAuth;
|
|
123
|
+
/** Clear cached + persisted native auth state. */
|
|
124
|
+
private clearNativeAuth;
|
|
125
|
+
/**
|
|
126
|
+
* Classify an MWA-native error as a user cancellation. User-cancel
|
|
127
|
+
* shouldn't surface as a red console.error; callers can swallow or
|
|
128
|
+
* show a softer message. MWA spec codes plus the same substring
|
|
129
|
+
* checks the web path uses to catch wallet-specific phrasing.
|
|
130
|
+
*/
|
|
131
|
+
private isNativeUserCancel;
|
|
132
|
+
/**
|
|
133
|
+
* Native MWA login via @solana-mobile/mobile-wallet-adapter-protocol-web3js.
|
|
134
|
+
* Used in true React Native (Expo) environments where wallet-standard-mobile's
|
|
135
|
+
* web universal-link path doesn't apply. Does authorize + signMessage in a
|
|
136
|
+
* single transact() roundtrip — intent-based MWA doesn't need the two-popup
|
|
137
|
+
* dance the web path uses (no Chrome activation-loss concern). Persists the
|
|
138
|
+
* resulting auth_token so cold-start can reauthorize without a fresh popup.
|
|
139
|
+
*/
|
|
140
|
+
private _loginNative;
|
|
141
|
+
login(): Promise<User | null>;
|
|
142
|
+
restoreSession(): Promise<User | null>;
|
|
143
|
+
logout(): Promise<void>;
|
|
144
|
+
signMessage(message: string): Promise<string>;
|
|
145
|
+
signTransaction(transaction: Transaction | VersionedTransaction): Promise<Transaction | VersionedTransaction>;
|
|
146
|
+
signAndSubmitTransaction(transaction: Transaction | VersionedTransaction, feePayer?: PublicKey): Promise<string>;
|
|
147
|
+
runTransaction(_evmTransactionData?: EVMTransaction, solTransactionData?: SolTransaction, options?: SetOptions): Promise<TransactionResult>;
|
|
148
|
+
getNativeMethods(): Promise<any>;
|
|
149
|
+
private getRpcUrl;
|
|
150
|
+
}
|
|
151
|
+
declare global {
|
|
152
|
+
interface Window {
|
|
153
|
+
CUSTOM_TAROBASE_APP_ID_HEADER?: string;
|
|
154
|
+
}
|
|
155
|
+
}
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import { Connection } from '@solana/web3.js';
|
|
2
|
+
/**
|
|
3
|
+
* Extracts a human-readable error message from Solana transaction logs.
|
|
4
|
+
*/
|
|
5
|
+
export declare function extractTransactionError(err: any, logMessages?: string[] | null): string;
|
|
6
|
+
/**
|
|
7
|
+
* Polls getSignatureStatuses until the transaction is confirmed, then checks for errors.
|
|
8
|
+
* Throws if the transaction failed on-chain. Returns parsed transaction info on success.
|
|
9
|
+
*/
|
|
10
|
+
export declare function confirmAndCheckTransaction(connection: Connection, signature: string): Promise<any>;
|
package/dist/global.d.ts
ADDED
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import { AuthProvider, User, ClientConfig } from '@bounded-sh/core';
|
|
2
|
+
import { LoginOptions } from './auth';
|
|
3
|
+
export declare function init(newConfig: Partial<ClientConfig>): Promise<void>;
|
|
4
|
+
export declare function onAuthStateChanged(callback: (user: User | null) => void): void;
|
|
5
|
+
export declare function onAuthLoadingChanged(callback: (loading: boolean) => void): void;
|
|
6
|
+
export declare function setAuthLoading(loading: boolean): void;
|
|
7
|
+
export declare function getAuthLoading(): boolean;
|
|
8
|
+
export declare function login(options?: LoginOptions): Promise<User | null>;
|
|
9
|
+
export type { LoginOptions };
|
|
10
|
+
export declare function logout(): Promise<void>;
|
|
11
|
+
export declare function setCurrentUser(user: User | null): void;
|
|
12
|
+
export declare function getCurrentUser(): User | null;
|
|
13
|
+
export declare function setAuthProviderInstance(provider: AuthProvider): void;
|