thirdweb 5.80.1-nightly-430475913d30ef7a30cb3092f6ef09c0c998a9b6-20250106000343 → 5.81.0

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.
Files changed (35) hide show
  1. package/dist/cjs/version.js +1 -1
  2. package/dist/cjs/version.js.map +1 -1
  3. package/dist/cjs/wallets/in-app/core/wallet/in-app-core.js +9 -3
  4. package/dist/cjs/wallets/in-app/core/wallet/in-app-core.js.map +1 -1
  5. package/dist/cjs/wallets/in-app/core/wallet/index.js +8 -10
  6. package/dist/cjs/wallets/in-app/core/wallet/index.js.map +1 -1
  7. package/dist/cjs/wallets/smart/index.js +14 -13
  8. package/dist/cjs/wallets/smart/index.js.map +1 -1
  9. package/dist/cjs/wallets/smart/smart-wallet.js +12 -10
  10. package/dist/cjs/wallets/smart/smart-wallet.js.map +1 -1
  11. package/dist/esm/version.js +1 -1
  12. package/dist/esm/version.js.map +1 -1
  13. package/dist/esm/wallets/in-app/core/wallet/in-app-core.js +9 -3
  14. package/dist/esm/wallets/in-app/core/wallet/in-app-core.js.map +1 -1
  15. package/dist/esm/wallets/in-app/core/wallet/index.js +8 -10
  16. package/dist/esm/wallets/in-app/core/wallet/index.js.map +1 -1
  17. package/dist/esm/wallets/smart/index.js +12 -11
  18. package/dist/esm/wallets/smart/index.js.map +1 -1
  19. package/dist/esm/wallets/smart/smart-wallet.js +12 -10
  20. package/dist/esm/wallets/smart/smart-wallet.js.map +1 -1
  21. package/dist/types/version.d.ts +1 -1
  22. package/dist/types/version.d.ts.map +1 -1
  23. package/dist/types/wallets/in-app/core/wallet/in-app-core.d.ts.map +1 -1
  24. package/dist/types/wallets/in-app/core/wallet/index.d.ts +10 -2
  25. package/dist/types/wallets/in-app/core/wallet/index.d.ts.map +1 -1
  26. package/dist/types/wallets/smart/index.d.ts +2 -2
  27. package/dist/types/wallets/smart/index.d.ts.map +1 -1
  28. package/package.json +1 -1
  29. package/src/version.ts +1 -1
  30. package/src/wallets/in-app/core/wallet/in-app-core.test.ts +115 -54
  31. package/src/wallets/in-app/core/wallet/in-app-core.ts +22 -11
  32. package/src/wallets/in-app/core/wallet/index.ts +10 -13
  33. package/src/wallets/smart/index.ts +14 -18
  34. package/src/wallets/smart/smart-wallet.ts +13 -13
  35. package/src/wallets/smart/smart.test.ts +19 -39
@@ -37,7 +37,7 @@ export async function connectInAppWallet(
37
37
  | CreateWalletArgs<"inApp">[1]
38
38
  | CreateWalletArgs<EcosystemWalletId>[1],
39
39
  connector: InAppConnector,
40
- ): Promise<[Account, Chain]> {
40
+ ): Promise<{ account: Account; chain: Chain; adminAccount?: Account }> {
41
41
  if (
42
42
  // if auth mode is not specified, the default is popup
43
43
  createOptions?.auth?.mode !== "popup" &&
@@ -65,15 +65,16 @@ export async function connectInAppWallet(
65
65
  "smartAccount" in createOptions &&
66
66
  createOptions?.smartAccount
67
67
  ) {
68
- return convertToSmartAccount({
68
+ const [account, chain] = await convertToSmartAccount({
69
69
  client: options.client,
70
70
  authAccount,
71
71
  smartAccountOptions: createOptions.smartAccount,
72
72
  chain: options.chain,
73
73
  });
74
+ return { account, chain, adminAccount: authAccount };
74
75
  }
75
76
 
76
- return [authAccount, options.chain || ethereum] as const;
77
+ return { account: authAccount, chain: options.chain || ethereum } as const;
77
78
  }
78
79
 
79
80
  /**
@@ -87,7 +88,7 @@ export async function autoConnectInAppWallet(
87
88
  | CreateWalletArgs<"inApp">[1]
88
89
  | CreateWalletArgs<EcosystemWalletId>[1],
89
90
  connector: InAppConnector,
90
- ): Promise<[Account, Chain]> {
91
+ ): Promise<{ account: Account; chain: Chain; adminAccount?: Account }> {
91
92
  if (options.authResult && connector.loginWithAuthToken) {
92
93
  await connector.loginWithAuthToken(options.authResult);
93
94
  }
@@ -104,15 +105,16 @@ export async function autoConnectInAppWallet(
104
105
  "smartAccount" in createOptions &&
105
106
  createOptions?.smartAccount
106
107
  ) {
107
- return convertToSmartAccount({
108
+ const [account, chain] = await convertToSmartAccount({
108
109
  client: options.client,
109
110
  authAccount,
110
111
  smartAccountOptions: createOptions.smartAccount,
111
112
  chain: options.chain,
112
113
  });
114
+ return { account, chain, adminAccount: authAccount };
113
115
  }
114
116
 
115
- return [authAccount, options.chain || ethereum] as const;
117
+ return { account: authAccount, chain: options.chain || ethereum } as const;
116
118
  }
117
119
 
118
120
  async function convertToSmartAccount(options: {
@@ -121,14 +123,9 @@ async function convertToSmartAccount(options: {
121
123
  smartAccountOptions: CreateWalletArgs<"smart">[1];
122
124
  chain?: Chain;
123
125
  }) {
124
- const [{ smartWallet }, { connectSmartWallet }] = await Promise.all([
125
- import("../../../smart/smart-wallet.js"),
126
- import("../../../smart/index.js"),
127
- ]);
126
+ const { connectSmartAccount } = await import("../../../smart/index.js");
128
127
 
129
- const sa = smartWallet(options.smartAccountOptions);
130
- return connectSmartWallet(
131
- sa,
128
+ return connectSmartAccount(
132
129
  {
133
130
  client: options.client,
134
131
  personalAccount: options.authAccount,
@@ -69,28 +69,26 @@ export function isSmartWallet(
69
69
  }
70
70
 
71
71
  /**
72
- * We can get the personal account for given smart account but not the other way around - this map gives us the reverse lookup
72
+ * For in-app wallets, the smart wallet creation is implicit so we track these to be able to retrieve the personal account for a smart account on the wallet API.
73
+ * Note: We have to go account to account here and NOT wallet to account because the smart wallet itself is never exposed to the in-app wallet, only the account.
73
74
  * @internal
74
75
  */
75
- const personalAccountToSmartAccountMap = new WeakMap<
76
- Account,
77
- Wallet<"smart">
78
- >();
79
-
80
- const smartWalletToPersonalAccountMap = new WeakMap<Wallet<"smart">, Account>();
76
+ const adminAccountToSmartAccountMap = new WeakMap<Account, Account>();
77
+ const smartAccountToAdminAccountMap = new WeakMap<Account, Account>();
81
78
 
82
79
  /**
83
80
  * @internal
84
81
  */
85
- export async function connectSmartWallet(
86
- wallet: Wallet<"smart">,
82
+ export async function connectSmartAccount(
87
83
  connectionOptions: SmartWalletConnectionOptions,
88
84
  creationOptions: SmartWalletOptions,
89
85
  ): Promise<[Account, Chain]> {
90
86
  const { personalAccount, client, chain: connectChain } = connectionOptions;
91
87
 
92
88
  if (!personalAccount) {
93
- throw new Error("Personal wallet does not have an account");
89
+ throw new Error(
90
+ "No personal account provided for smart account connection",
91
+ );
94
92
  }
95
93
 
96
94
  const options = creationOptions;
@@ -177,8 +175,8 @@ export async function connectSmartWallet(
177
175
  client,
178
176
  });
179
177
 
180
- personalAccountToSmartAccountMap.set(personalAccount, wallet);
181
- smartWalletToPersonalAccountMap.set(wallet, personalAccount);
178
+ adminAccountToSmartAccountMap.set(personalAccount, account);
179
+ smartAccountToAdminAccountMap.set(account, personalAccount);
182
180
 
183
181
  return [account, chain] as const;
184
182
  }
@@ -186,15 +184,13 @@ export async function connectSmartWallet(
186
184
  /**
187
185
  * @internal
188
186
  */
189
- export async function disconnectSmartWallet(
190
- wallet: Wallet<"smart">,
191
- ): Promise<void> {
187
+ export async function disconnectSmartAccount(account: Account): Promise<void> {
192
188
  // look up the personalAccount for the smart wallet
193
- const personalAccount = smartWalletToPersonalAccountMap.get(wallet);
189
+ const personalAccount = smartAccountToAdminAccountMap.get(account);
194
190
  if (personalAccount) {
195
191
  // remove the mappings
196
- personalAccountToSmartAccountMap.delete(personalAccount);
197
- smartWalletToPersonalAccountMap.delete(wallet);
192
+ adminAccountToSmartAccountMap.delete(personalAccount);
193
+ smartAccountToAdminAccountMap.delete(account);
198
194
  }
199
195
  }
200
196
 
@@ -137,7 +137,7 @@ export function smartWallet(
137
137
  let chain: Chain | undefined = undefined;
138
138
  let lastConnectOptions: WalletConnectionOption<"smart"> | undefined;
139
139
 
140
- const _smartWallet: Wallet<"smart"> = {
140
+ return {
141
141
  id: "smart",
142
142
  subscribe: emitter.subscribe,
143
143
  getChain() {
@@ -152,9 +152,10 @@ export function smartWallet(
152
152
  getAccount: () => account,
153
153
  getAdminAccount: () => adminAccount,
154
154
  autoConnect: async (options) => {
155
- const { connectSmartWallet } = await import("./index.js");
155
+ const { connectSmartAccount: connectSmartWallet } = await import(
156
+ "./index.js"
157
+ );
156
158
  const [connectedAccount, connectedChain] = await connectSmartWallet(
157
- _smartWallet,
158
159
  options,
159
160
  createOptions,
160
161
  );
@@ -172,9 +173,8 @@ export function smartWallet(
172
173
  return account;
173
174
  },
174
175
  connect: async (options) => {
175
- const { connectSmartWallet } = await import("./index.js");
176
- const [connectedAccount, connectedChain] = await connectSmartWallet(
177
- _smartWallet,
176
+ const { connectSmartAccount } = await import("./index.js");
177
+ const [connectedAccount, connectedChain] = await connectSmartAccount(
178
178
  options,
179
179
  createOptions,
180
180
  );
@@ -194,10 +194,13 @@ export function smartWallet(
194
194
  return account;
195
195
  },
196
196
  disconnect: async () => {
197
+ if (account) {
198
+ const { disconnectSmartAccount } = await import("./index.js");
199
+ await disconnectSmartAccount(account);
200
+ }
197
201
  account = undefined;
202
+ adminAccount = undefined;
198
203
  chain = undefined;
199
- const { disconnectSmartWallet } = await import("./index.js");
200
- await disconnectSmartWallet(_smartWallet);
201
204
  emitter.emit("disconnect", undefined);
202
205
  },
203
206
  switchChain: async (newChain: Chain) => {
@@ -223,9 +226,8 @@ export function smartWallet(
223
226
  );
224
227
  }
225
228
  }
226
- const { connectSmartWallet } = await import("./index.js");
227
- const [connectedAccount, connectedChain] = await connectSmartWallet(
228
- _smartWallet,
229
+ const { connectSmartAccount } = await import("./index.js");
230
+ const [connectedAccount, connectedChain] = await connectSmartAccount(
229
231
  { ...lastConnectOptions, chain: newChain },
230
232
  createOptions,
231
233
  );
@@ -235,6 +237,4 @@ export function smartWallet(
235
237
  emitter.emit("chainChanged", newChain);
236
238
  },
237
239
  };
238
-
239
- return _smartWallet;
240
240
  }
@@ -2,7 +2,6 @@ import { describe, expect, it } from "vitest";
2
2
  import { TEST_CLIENT } from "../../../test/src/test-clients.js";
3
3
  import { defineChain } from "../../chains/utils.js";
4
4
  import { generateAccount } from "../utils/generateAccount.js";
5
- import { connectSmartWallet, disconnectSmartWallet } from "./index.js";
6
5
  import { smartWallet } from "./smart-wallet.js";
7
6
 
8
7
  describe.runIf(process.env.TW_SECRET_KEY)("Smart Wallet Index", () => {
@@ -17,67 +16,48 @@ describe.runIf(process.env.TW_SECRET_KEY)("Smart Wallet Index", () => {
17
16
  gasless: true,
18
17
  });
19
18
 
20
- const [account, connectedChain] = await connectSmartWallet(
21
- wallet,
22
- {
23
- client,
24
- personalAccount,
25
- },
26
- {
27
- chain,
28
- gasless: true,
29
- },
30
- );
19
+ await wallet.connect({
20
+ client,
21
+ personalAccount,
22
+ });
31
23
 
32
- expect(account.address).toBeDefined();
33
- expect(account.address).toMatch(/^0x[a-fA-F0-9]{40}$/);
34
- expect(connectedChain.id).toBe(chain.id);
24
+ expect(wallet.getAccount()?.address).toBeDefined();
25
+ expect(wallet.getAccount()?.address).toMatch(/^0x[a-fA-F0-9]{40}$/);
26
+ expect(wallet.getChain()?.id).toBe(chain.id);
35
27
  });
36
28
  });
37
29
 
38
30
  describe("disconnectSmartWallet", () => {
39
31
  it("should disconnect a smart wallet", async () => {
40
32
  const personalAccount = await generateAccount({ client });
33
+
41
34
  const wallet = smartWallet({
42
35
  chain,
43
36
  gasless: true,
44
37
  });
45
38
 
46
- await connectSmartWallet(
47
- wallet,
48
- {
49
- client,
50
- personalAccount,
51
- },
52
- {
53
- chain,
54
- gasless: true,
55
- },
56
- );
39
+ await wallet.connect({
40
+ client,
41
+ personalAccount,
42
+ });
57
43
 
58
- await expect(disconnectSmartWallet(wallet)).resolves.not.toThrow();
44
+ await expect(wallet.disconnect()).resolves.not.toThrow();
59
45
  });
60
46
 
61
47
  it("should clear wallet mappings on disconnect", async () => {
62
48
  const personalAccount = await generateAccount({ client });
49
+
63
50
  const wallet = smartWallet({
64
51
  chain,
65
52
  gasless: true,
66
53
  });
67
54
 
68
- await connectSmartWallet(
69
- wallet,
70
- {
71
- client,
72
- personalAccount,
73
- },
74
- {
75
- chain,
76
- gasless: true,
77
- },
78
- );
55
+ await wallet.connect({
56
+ client,
57
+ personalAccount,
58
+ });
79
59
 
80
- await disconnectSmartWallet(wallet);
60
+ await wallet.disconnect();
81
61
 
82
62
  // Verify wallet state is cleared
83
63
  expect(wallet.getAccount()).toBeUndefined();