@gluwa/connect-kit 0.1.0-next.1 → 0.1.0-next.3

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/dist/index.js CHANGED
@@ -1,9 +1,10 @@
1
1
  import React from "react";
2
- var __defProp = Object.defineProperty;
3
- var __name = (target, value) => __defProp(target, "name", { value, configurable: true });
2
+ import {
3
+ __name
4
+ } from "./chunk-DDA6FP6U.js";
4
5
 
5
6
  // src/ConnectModal.tsx
6
- import { useState as useState2, useEffect as useEffect4, useCallback as useCallback3, useRef as useRef3, useMemo as useMemo4 } from "react";
7
+ import { useState as useState3, useEffect as useEffect4, useCallback as useCallback3, useMemo as useMemo4 } from "react";
7
8
 
8
9
  // src/ConnectModal.scss
9
10
  var css = `.ck-root {
@@ -141,6 +142,42 @@ var css = `.ck-root {
141
142
  .ck-btn-primary:hover {
142
143
  background: rgba(255, 255, 255, 0.22);
143
144
  }
145
+ .ck-btn-primary:disabled {
146
+ opacity: 0.6;
147
+ cursor: not-allowed;
148
+ }
149
+
150
+ .ck-btn-secondary {
151
+ display: inline-flex;
152
+ align-items: center;
153
+ justify-content: center;
154
+ padding: 8px 16px;
155
+ border-radius: 8px;
156
+ font-size: 14px;
157
+ font-weight: 500;
158
+ cursor: pointer;
159
+ white-space: nowrap;
160
+ color: rgba(255, 255, 255, 0.75);
161
+ background: transparent;
162
+ border: 1px solid rgba(255, 255, 255, 0.18);
163
+ }
164
+ .ck-btn-secondary:hover {
165
+ color: #fff;
166
+ border-color: rgba(255, 255, 255, 0.32);
167
+ }
168
+
169
+ .ck-view__actions {
170
+ display: flex;
171
+ flex-direction: column;
172
+ gap: 8px;
173
+ width: 100%;
174
+ margin-top: 16px;
175
+ }
176
+
177
+ .ck-view__caption--error {
178
+ color: #ff8080;
179
+ margin-top: 8px;
180
+ }
144
181
 
145
182
  .ck-connector-list {
146
183
  display: flex;
@@ -453,7 +490,7 @@ var css = `.ck-root {
453
490
  .ck-wallet-grid-scroll {
454
491
  flex: 1;
455
492
  min-height: 0;
456
- width: 520px;
493
+ width: 100%;
457
494
  overflow-x: hidden;
458
495
  overflow-y: auto;
459
496
  }
@@ -584,7 +621,7 @@ var css = `.ck-root {
584
621
  document.head.appendChild(document.createElement("style")).appendChild(document.createTextNode(css));
585
622
 
586
623
  // src/ConnectModal.tsx
587
- import { useConfig as useConfig2 } from "wagmi";
624
+ import { useAccount, useConfig as useConfig2, useDisconnect } from "wagmi";
588
625
 
589
626
  // assets/creditwallet.png
590
627
  var creditwallet_default = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACQAAAAkCAYAAADhAJiYAAAACXBIWXMAAAsTAAALEwEAmpwYAAAAAXNSR0IArs4c6QAAAARnQU1BAACxjwv8YQUAAAAOdEVYdFNvZnR3YXJlAEZpZ21hnrGWYwAAAtNJREFUeAHVWDFs00AUfWe7oYVSWdAxQEfUCZiQqEQykDUdGBAL0IERlQGxMbAhBpDYGEBMMDCEtUtbqZXYuiHGCDEymDZqqZr4+N/OuW579jmO5aRPcs8+n68v/7//798BYwah65x23Rp8NOltjQa4UmIORfwzgbYE2kJSa+FTx/PWToyJP7iuO9eV+AiJGsqAQMsReOp5XvuwK0amJ7FalDWyc0LbtlBXpCz1gizzpmwyDHJh6JVDgpFmVjFKkJVYUw7fCx8P5GCfY/r9Ezjzl7TvvIVnGBg+FulvSEgKclUGRhM3r0b3cnsX/u8/xnE8ppcw7ggEbnMTWoj8aOJjVWdx/svz6Hnn3iscfP+pHXuhHUkCe2+/0dWCkY+E2+dC5p9xU/lMLjUgZs4e6dv/upFooanlxRN9+x9W4JNV09DZ9kQmQu7G66DNow0mN7XcDL71Da4zEjpzd4GuW2SNTXR//EKPrkHBrrbpqtA8bOXO43dII2SZJnNIoKyVPGQYbBX+noXuzF82jrcwZnB0nXbfMgwWLwxizIKDlS3KLObcotUQm5dD3BSylcYNbfTlBWvIwRCYXLoTWbIIQoyhCOmgUoQJOxRtukAZmaitY65WKNxCuRbWGIYixKK3qpsoEtoo48jhCOLEaFUvYu/lZ+M6ZMK5F/eDsN+luZKQmKm5tFDRwssHEvw9CCYa14MfacLpyNQKvA51aR2y+wtkUv2TBjtw+2zmQu10lR8KZRZoYQnLO8qULdA/mozNHs/C7MpkQs3oPnMJS/uzfhtYaIuaa6kfkIXi9QwXXKwPHZiEAuvGz1bkr3X+enUl6nUTIU4FcVFXKB1YCYTyiJ/3+yEvjNdGMchDwSkEmQyjAh06qJOQKDHSKcQjFjdKBouZT0DUc0SITx9sgTqzRVkgr8RPPsIuDVhTtN9/SFvsK8GuttgDK4/W2HUyRUt3YDV2+A99bkdtt/T4QQAAAABJRU5ErkJggg==";
@@ -877,7 +914,7 @@ var IdleView = /* @__PURE__ */ __name(() => /* @__PURE__ */ React.createElement(
877
914
  }, "Choose a wallet on the left to start connecting.")), "IdleView");
878
915
 
879
916
  // src/views/CreditWalletView.tsx
880
- import { useEffect as useEffect2, useMemo } from "react";
917
+ import { useEffect as useEffect2, useMemo, useRef as useRef3 } from "react";
881
918
 
882
919
  // src/components/QRFrame.tsx
883
920
  import { QRCodeSVG } from "qrcode.react";
@@ -912,8 +949,10 @@ var CopyLinkButton = /* @__PURE__ */ __name(({ qrUri }) => {
912
949
  var CreditWalletView = /* @__PURE__ */ __name(({ connectorId, qrUri }) => {
913
950
  const { downloadUrl: downloadUrl2, logoUrl, deepLinkBase: deepLinkBase2 } = CONNECTOR_META[connectorId];
914
951
  const isMobile = useMemo(() => isMobileDevice(), []);
952
+ const hasRedirectedRef = useRef3(false);
915
953
  useEffect2(() => {
916
- if (isMobile && qrUri && deepLinkBase2) {
954
+ if (isMobile && qrUri && deepLinkBase2 && !hasRedirectedRef.current) {
955
+ hasRedirectedRef.current = true;
917
956
  tryOpenDeepLink(qrUri, deepLinkBase2);
918
957
  }
919
958
  }, [
@@ -1168,6 +1207,50 @@ var WalletQRView = /* @__PURE__ */ __name(({ wallet, qrUri }) => {
1168
1207
  }, "Download")));
1169
1208
  }, "WalletQRView");
1170
1209
 
1210
+ // src/views/SwitchChainView.tsx
1211
+ import { useState as useState2 } from "react";
1212
+ import { useSwitchChain } from "wagmi";
1213
+ var SwitchChainView = /* @__PURE__ */ __name(({ currentChainId, requiredChainId, requiredChainName, onDisconnect, onLog }) => {
1214
+ const { switchChainAsync, isPending } = useSwitchChain();
1215
+ const [error, setError] = useState2(null);
1216
+ const targetLabel = requiredChainName != null ? requiredChainName : `chain ${requiredChainId}`;
1217
+ const handleSwitch = /* @__PURE__ */ __name(() => {
1218
+ setError(null);
1219
+ switchChainAsync({
1220
+ chainId: requiredChainId
1221
+ }).catch((err) => {
1222
+ const normalized = err instanceof Error ? err : new Error(String(err));
1223
+ const code = typeof err === "object" && err !== null && "code" in err ? err.code : void 0;
1224
+ if (code === 4902) {
1225
+ onLog == null ? void 0 : onLog("[connect-kit] chain not registered in wallet (4902)", normalized);
1226
+ } else {
1227
+ onLog == null ? void 0 : onLog(`[connect-kit] switch chain failed: ${normalized.message}`, normalized);
1228
+ }
1229
+ setError(normalized);
1230
+ });
1231
+ }, "handleSwitch");
1232
+ return /* @__PURE__ */ React.createElement("div", {
1233
+ className: "ck-view ck-view--switch-chain"
1234
+ }, /* @__PURE__ */ React.createElement("h4", {
1235
+ className: "ck-view__title"
1236
+ }, "Wrong network"), /* @__PURE__ */ React.createElement("p", {
1237
+ className: "ck-view__description"
1238
+ }, currentChainId != null ? `Connected to chain ${currentChainId}. Please switch to ${targetLabel} to continue.` : `Please switch to ${targetLabel} to continue.`), /* @__PURE__ */ React.createElement("div", {
1239
+ className: "ck-view__actions"
1240
+ }, /* @__PURE__ */ React.createElement("button", {
1241
+ type: "button",
1242
+ className: "ck-btn-primary",
1243
+ onClick: handleSwitch,
1244
+ disabled: isPending
1245
+ }, isPending ? "Waiting for wallet\u2026" : `Switch to ${targetLabel}`), /* @__PURE__ */ React.createElement("button", {
1246
+ type: "button",
1247
+ className: "ck-btn-secondary",
1248
+ onClick: onDisconnect
1249
+ }, "Disconnect")), error && /* @__PURE__ */ React.createElement("p", {
1250
+ className: "ck-view__caption ck-view__caption--error"
1251
+ }, error.message));
1252
+ }, "SwitchChainView");
1253
+
1171
1254
  // src/ConnectModal.tsx
1172
1255
  var RECENT_KEY = "connect-kit:recent";
1173
1256
  var readRecentConnector = /* @__PURE__ */ __name(() => {
@@ -1183,6 +1266,15 @@ var writeRecentConnector = /* @__PURE__ */ __name((id) => {
1183
1266
  } catch {
1184
1267
  }
1185
1268
  }, "writeRecentConnector");
1269
+ var classifyError = /* @__PURE__ */ __name((error) => {
1270
+ var _a, _b;
1271
+ const code = typeof error === "object" && error !== null && "code" in error ? error.code : void 0;
1272
+ if (code === 4001) return "rejected";
1273
+ const message = (_b = (_a = error.message) == null ? void 0 : _a.toLowerCase()) != null ? _b : "";
1274
+ if (message.includes("user rejected") || message.includes("user denied")) return "rejected";
1275
+ if (message.includes("unsupported") || message.includes("not installed")) return "unsupported";
1276
+ return "unknown";
1277
+ }, "classifyError");
1186
1278
  var SelectorPane = /* @__PURE__ */ __name(({ connectors, selected, recentConnector, onSelect, onClose }) => {
1187
1279
  const hasRecent = recentConnector !== null && connectors.includes(recentConnector);
1188
1280
  const recentConnectors = hasRecent ? [
@@ -1248,7 +1340,7 @@ var ConnectorItem = /* @__PURE__ */ __name(({ id, isSelected, isRecent, onSelect
1248
1340
  className: "ck-connector-item__badge"
1249
1341
  }, "Recent"));
1250
1342
  }, "ConnectorItem");
1251
- var DetailPane = /* @__PURE__ */ __name(({ selectedConnector, qrUri, hasMetaMaskExtension, connectorLogoMap, wc, onBack, onClose }) => {
1343
+ var DetailPane = /* @__PURE__ */ __name(({ selectedConnector, qrUri, hasMetaMaskExtension, connectorLogoMap, wc, errorOverride, onBack, onClose }) => {
1252
1344
  const title = getDetailTitle(selectedConnector, hasMetaMaskExtension, wc.subView, wc.selectedWallet);
1253
1345
  const showBack = selectedConnector !== null;
1254
1346
  return /* @__PURE__ */ React.createElement("div", {
@@ -1269,7 +1361,7 @@ var DetailPane = /* @__PURE__ */ __name(({ selectedConnector, qrUri, hasMetaMask
1269
1361
  "aria-label": "Close"
1270
1362
  })), /* @__PURE__ */ React.createElement("div", {
1271
1363
  className: "ck-pane__body"
1272
- }, !selectedConnector && /* @__PURE__ */ React.createElement(IdleView, null), (selectedConnector === "CREDIT_CONNECT" || selectedConnector === "CREDIT_WALLET") && /* @__PURE__ */ React.createElement(CreditWalletView, {
1364
+ }, errorOverride || /* @__PURE__ */ React.createElement(React.Fragment, null, !selectedConnector && /* @__PURE__ */ React.createElement(IdleView, null), (selectedConnector === "CREDIT_CONNECT" || selectedConnector === "CREDIT_WALLET") && /* @__PURE__ */ React.createElement(CreditWalletView, {
1273
1365
  connectorId: selectedConnector,
1274
1366
  qrUri
1275
1367
  }), selectedConnector === "METAMASK" && /* @__PURE__ */ React.createElement(MetaMaskView, {
@@ -1289,7 +1381,7 @@ var DetailPane = /* @__PURE__ */ __name(({ selectedConnector, qrUri, hasMetaMask
1289
1381
  onSelectWallet: wc.onSelectWallet,
1290
1382
  onSearchChange: wc.onSearchChange,
1291
1383
  onFilterToggle: wc.onFilterToggle
1292
- })));
1384
+ }))));
1293
1385
  }, "DetailPane");
1294
1386
  var getDetailTitle = /* @__PURE__ */ __name((connector, hasMetaMaskExtension, wcSubView, wcSelectedWallet) => {
1295
1387
  if (!connector) return "";
@@ -1324,24 +1416,30 @@ var ConnectModal = /* @__PURE__ */ __name((props) => {
1324
1416
  connectors: resolvedConnectors
1325
1417
  });
1326
1418
  }, "ConnectModal");
1327
- var ConnectModalInner = /* @__PURE__ */ __name(({ open, connectors, onConnect, onClose, onLog, wcProjectId }) => {
1328
- var _a;
1329
- const [selectedConnector, setSelectedConnector] = useState2(null);
1330
- const [qrUriMap, setQrUriMap] = useState2({});
1331
- const pendingQrConnectorRef = useRef3(null);
1332
- const [recentConnector, setRecentConnector] = useState2(null);
1333
- const [hasMetaMaskExtension, setHasMetaMaskExtension] = useState2(false);
1419
+ var ConnectModalInner = /* @__PURE__ */ __name(({ open, connectors, onConnect, onClose, onLog, wcProjectId, requiredChainId, renderConnectError }) => {
1420
+ const [selectedConnector, setSelectedConnector] = useState3(null);
1421
+ const [qrUri, setQrUri] = useState3(null);
1422
+ const [recentConnector, setRecentConnector] = useState3(null);
1423
+ const [hasMetaMaskExtension, setHasMetaMaskExtension] = useState3(false);
1424
+ const [errorState, setErrorState] = useState3(null);
1334
1425
  const wc = useWCState();
1426
+ const account = useAccount();
1427
+ const { disconnectAsync } = useDisconnect();
1428
+ const wagmiConfig = useConfig2();
1429
+ const chainMismatch = requiredChainId != null && account.status === "connected" && account.chainId != null && account.chainId !== requiredChainId;
1430
+ const requiredChainName = useMemo4(() => {
1431
+ var _a;
1432
+ if (requiredChainId == null) return void 0;
1433
+ return (_a = wagmiConfig.chains.find((chain) => chain.id === requiredChainId)) == null ? void 0 : _a.name;
1434
+ }, [
1435
+ wagmiConfig.chains,
1436
+ requiredChainId
1437
+ ]);
1335
1438
  const handleQrUri = useCallback3((uri) => {
1336
- if (uri) {
1337
- const id = pendingQrConnectorRef.current;
1338
- if (id) setQrUriMap((prev) => ({
1339
- ...prev,
1340
- [id]: uri
1341
- }));
1342
- }
1439
+ setQrUri(uri);
1343
1440
  }, []);
1344
1441
  const handleConnect = useCallback3((result) => {
1442
+ setErrorState(null);
1345
1443
  onConnect(result);
1346
1444
  onClose();
1347
1445
  }, [
@@ -1349,26 +1447,28 @@ var ConnectModalInner = /* @__PURE__ */ __name(({ open, connectors, onConnect, o
1349
1447
  onClose
1350
1448
  ]);
1351
1449
  const handleError = useCallback3((error, connectorId) => {
1352
- onLog == null ? void 0 : onLog(`[connect-kit] connection failed (${connectorId}): ${error.message}`, error);
1353
- setSelectedConnector(null);
1354
- setQrUriMap((prev) => {
1355
- const next = {
1356
- ...prev
1357
- };
1358
- delete next[connectorId];
1359
- return next;
1360
- });
1450
+ const normalizedError = error instanceof Error ? error : new Error(String(error));
1451
+ onLog == null ? void 0 : onLog(`[connect-kit] connection failed (${connectorId}): ${normalizedError.message}`, normalizedError);
1452
+ setQrUri(null);
1361
1453
  wc.resetView();
1454
+ if (renderConnectError) {
1455
+ setErrorState({
1456
+ connectorId,
1457
+ error: normalizedError
1458
+ });
1459
+ } else {
1460
+ setSelectedConnector(null);
1461
+ }
1362
1462
  }, [
1363
1463
  onLog,
1364
- wc.resetView
1464
+ wc.resetView,
1465
+ renderConnectError
1365
1466
  ]);
1366
1467
  const { triggerConnect, cancelConnect } = useWagmiConnect({
1367
1468
  onConnect: handleConnect,
1368
1469
  onError: handleError,
1369
1470
  onQrUri: handleQrUri
1370
1471
  });
1371
- const wagmiConfig = useConfig2();
1372
1472
  const connectorLogoMap = useMemo4(() => {
1373
1473
  const map = {};
1374
1474
  const connectorIds = [
@@ -1392,8 +1492,8 @@ var ConnectModalInner = /* @__PURE__ */ __name(({ open, connectors, onConnect, o
1392
1492
  useEffect4(() => {
1393
1493
  if (!open) {
1394
1494
  setSelectedConnector(null);
1395
- setQrUriMap({});
1396
- pendingQrConnectorRef.current = null;
1495
+ setQrUri(null);
1496
+ setErrorState(null);
1397
1497
  wc.reset();
1398
1498
  cancelConnect();
1399
1499
  }
@@ -1403,9 +1503,10 @@ var ConnectModalInner = /* @__PURE__ */ __name(({ open, connectors, onConnect, o
1403
1503
  wc.reset
1404
1504
  ]);
1405
1505
  const handleSelectConnector = useCallback3((id) => {
1406
- if (id === selectedConnector) return;
1407
- pendingQrConnectorRef.current = id;
1506
+ if (id === selectedConnector && !errorState) return;
1408
1507
  setSelectedConnector(id);
1508
+ setQrUri(null);
1509
+ setErrorState(null);
1409
1510
  wc.resetView();
1410
1511
  writeRecentConnector(id);
1411
1512
  setRecentConnector(id);
@@ -1416,6 +1517,7 @@ var ConnectModalInner = /* @__PURE__ */ __name(({ open, connectors, onConnect, o
1416
1517
  triggerConnect(id);
1417
1518
  }, [
1418
1519
  selectedConnector,
1520
+ errorState,
1419
1521
  triggerConnect,
1420
1522
  cancelConnect,
1421
1523
  wcProjectId,
@@ -1423,22 +1525,112 @@ var ConnectModalInner = /* @__PURE__ */ __name(({ open, connectors, onConnect, o
1423
1525
  wc.loadWalletList
1424
1526
  ]);
1425
1527
  const handleBack = useCallback3(() => {
1528
+ if (errorState) {
1529
+ setErrorState(null);
1530
+ setSelectedConnector(null);
1531
+ return;
1532
+ }
1426
1533
  if (selectedConnector === "WALLET_CONNECT" && wc.handleBack()) return;
1427
- pendingQrConnectorRef.current = null;
1428
1534
  setSelectedConnector(null);
1535
+ setQrUri(null);
1429
1536
  cancelConnect();
1430
1537
  }, [
1431
1538
  selectedConnector,
1539
+ errorState,
1432
1540
  wc.handleBack,
1433
1541
  cancelConnect
1434
1542
  ]);
1543
+ const handleSwitchChainDisconnect = useCallback3(() => {
1544
+ disconnectAsync().catch((err) => {
1545
+ const normalized = err instanceof Error ? err : new Error(String(err));
1546
+ onLog == null ? void 0 : onLog(`[connect-kit] disconnect failed: ${normalized.message}`, normalized);
1547
+ });
1548
+ }, [
1549
+ disconnectAsync,
1550
+ onLog
1551
+ ]);
1552
+ const handleOverlayClick = useCallback3(() => {
1553
+ if (chainMismatch) return;
1554
+ onClose();
1555
+ }, [
1556
+ chainMismatch,
1557
+ onClose
1558
+ ]);
1559
+ const handleCloseClick = useCallback3(() => {
1560
+ if (chainMismatch) {
1561
+ handleSwitchChainDisconnect();
1562
+ return;
1563
+ }
1564
+ onClose();
1565
+ }, [
1566
+ chainMismatch,
1567
+ handleSwitchChainDisconnect,
1568
+ onClose
1569
+ ]);
1570
+ const renderedError = useMemo4(() => {
1571
+ if (!errorState || !renderConnectError) return null;
1572
+ const ctx = {
1573
+ connectorId: errorState.connectorId,
1574
+ reason: classifyError(errorState.error),
1575
+ error: errorState.error,
1576
+ retry: /* @__PURE__ */ __name(() => {
1577
+ const id = errorState.connectorId;
1578
+ setErrorState(null);
1579
+ setQrUri(null);
1580
+ cancelConnect();
1581
+ triggerConnect(id);
1582
+ }, "retry"),
1583
+ dismiss: /* @__PURE__ */ __name(() => {
1584
+ setErrorState(null);
1585
+ setSelectedConnector(null);
1586
+ }, "dismiss")
1587
+ };
1588
+ return renderConnectError(ctx);
1589
+ }, [
1590
+ errorState,
1591
+ renderConnectError,
1592
+ triggerConnect,
1593
+ cancelConnect
1594
+ ]);
1595
+ if (chainMismatch && requiredChainId != null) {
1596
+ return /* @__PURE__ */ React.createElement("div", {
1597
+ className: "ck-root"
1598
+ }, /* @__PURE__ */ React.createElement("div", {
1599
+ className: "ck-overlay",
1600
+ onClick: handleOverlayClick
1601
+ }), /* @__PURE__ */ React.createElement("div", {
1602
+ className: "ck-modal ck-modal--switch-chain",
1603
+ role: "dialog",
1604
+ "aria-modal": "true",
1605
+ "aria-label": "Switch network"
1606
+ }, /* @__PURE__ */ React.createElement("div", {
1607
+ className: "ck-pane"
1608
+ }, /* @__PURE__ */ React.createElement("div", {
1609
+ className: "ck-pane__header"
1610
+ }, /* @__PURE__ */ React.createElement("h3", {
1611
+ className: "ck-pane__title"
1612
+ }, "Switch network"), /* @__PURE__ */ React.createElement("button", {
1613
+ type: "button",
1614
+ className: "ck-btn-close",
1615
+ onClick: handleCloseClick,
1616
+ "aria-label": "Cancel and disconnect"
1617
+ })), /* @__PURE__ */ React.createElement("div", {
1618
+ className: "ck-pane__body"
1619
+ }, /* @__PURE__ */ React.createElement(SwitchChainView, {
1620
+ currentChainId: account.chainId,
1621
+ requiredChainId,
1622
+ requiredChainName,
1623
+ onDisconnect: handleSwitchChainDisconnect,
1624
+ onLog
1625
+ })))));
1626
+ }
1435
1627
  return /* @__PURE__ */ React.createElement("div", {
1436
1628
  className: "ck-root"
1437
1629
  }, /* @__PURE__ */ React.createElement("div", {
1438
1630
  className: "ck-overlay",
1439
- onClick: onClose
1631
+ onClick: handleOverlayClick
1440
1632
  }), /* @__PURE__ */ React.createElement("div", {
1441
- className: `ck-modal${selectedConnector ? " ck-modal--has-detail" : ""}`,
1633
+ className: `ck-modal${(selectedConnector != null ? selectedConnector : errorState) ? " ck-modal--has-detail" : ""}`,
1442
1634
  role: "dialog",
1443
1635
  "aria-modal": "true",
1444
1636
  "aria-label": "Connect Wallet"
@@ -1447,409 +1639,133 @@ var ConnectModalInner = /* @__PURE__ */ __name(({ open, connectors, onConnect, o
1447
1639
  selected: selectedConnector,
1448
1640
  recentConnector,
1449
1641
  onSelect: handleSelectConnector,
1450
- onClose
1642
+ onClose: handleCloseClick
1451
1643
  }), /* @__PURE__ */ React.createElement(DetailPane, {
1452
1644
  selectedConnector,
1453
- qrUri: selectedConnector ? (_a = qrUriMap[selectedConnector]) != null ? _a : null : null,
1645
+ qrUri,
1454
1646
  hasMetaMaskExtension,
1455
1647
  connectorLogoMap,
1456
1648
  wc,
1649
+ errorOverride: renderedError,
1457
1650
  onBack: handleBack,
1458
- onClose
1651
+ onClose: handleCloseClick
1459
1652
  })));
1460
1653
  }, "ConnectModalInner");
1461
1654
 
1462
- // src/creditConnectConnector.ts
1463
- import { createConnector } from "@wagmi/core";
1464
- import { getAddress } from "viem";
1465
- import { DappSessionManager } from "@gluwa/credit-connect-sdk/dapp";
1466
- var CONNECTOR_ID = "credit-connect";
1467
- var CONNECTOR_NAME = "Credit Wallet";
1468
- var CONNECTOR_TYPE = "credit-connect";
1469
- var castConnectResult = /* @__PURE__ */ __name((value) => value, "castConnectResult");
1470
- var creditConnectConnector = /* @__PURE__ */ __name((options) => {
1471
- let manager = null;
1472
- let selectedChainId = null;
1473
- let connectPromise = null;
1474
- let provider = null;
1475
- let isLocalDisconnect = false;
1476
- let emitWagmiMessage = null;
1477
- let emitWagmiDisconnect = null;
1478
- const providerListeners = /* @__PURE__ */ new Map();
1479
- const emitProviderEvent = /* @__PURE__ */ __name((event, ...args) => {
1480
- const listeners = providerListeners.get(event);
1481
- if (listeners) for (const fn of listeners) fn(...args);
1482
- }, "emitProviderEvent");
1483
- const getCurrentSession = /* @__PURE__ */ __name(() => {
1484
- if (!manager || manager.state.status !== "CONNECTED" || !manager.state.session) return null;
1485
- return manager.state.session;
1486
- }, "getCurrentSession");
1487
- const getEvmAddressInfo = /* @__PURE__ */ __name((session) => session.addressInfoList.filter((info) => info.networkType === "eip155"), "getEvmAddressInfo");
1488
- const getChecksummedAccounts = /* @__PURE__ */ __name((session) => getEvmAddressInfo(session).map((info) => getAddress(info.address)), "getChecksummedAccounts");
1489
- const resetState = /* @__PURE__ */ __name(() => {
1490
- connectPromise = null;
1491
- selectedChainId = null;
1492
- }, "resetState");
1493
- const createManagerIfNeeded = /* @__PURE__ */ __name(() => {
1494
- if (manager) return manager;
1495
- manager = new DappSessionManager({
1496
- projectKey: options.projectKey,
1497
- serverUrl: options.serverUrl,
1498
- storage: options.storage,
1499
- e2ee: options.e2ee,
1500
- createHub: options.createHub,
1501
- enableReconnect: true,
1502
- autoInit: true
1503
- });
1504
- manager.on("changeState", (state) => {
1505
- var _a;
1506
- if (state.status === "CONNECTING" && state.connectingPayload) {
1507
- (_a = options.onDisplayUri) == null ? void 0 : _a.call(options, state.connectingPayload);
1508
- emitWagmiMessage == null ? void 0 : emitWagmiMessage("display_uri", state.connectingPayload);
1509
- }
1510
- if (state.status === "DISCONNECTED" && !isLocalDisconnect) {
1511
- resetState();
1512
- emitProviderEvent("disconnect");
1513
- emitWagmiDisconnect == null ? void 0 : emitWagmiDisconnect();
1514
- }
1515
- });
1516
- return manager;
1517
- }, "createManagerIfNeeded");
1518
- const ensureManagerInitialized = /* @__PURE__ */ __name(async () => {
1519
- const m = createManagerIfNeeded();
1520
- if (m.state.status === "PENDING") {
1521
- await m.initSession();
1522
- return m;
1655
+ // src/ConnectKitProvider.tsx
1656
+ import { createContext, useCallback as useCallback4, useContext, useEffect as useEffect5, useMemo as useMemo5, useRef as useRef4, useState as useState4 } from "react";
1657
+ import { WagmiProvider, useAccount as useAccount2, useDisconnect as useDisconnect2 } from "wagmi";
1658
+ import { QueryClient, QueryClientProvider } from "@tanstack/react-query";
1659
+ var internalQueryClient = new QueryClient();
1660
+ var ConnectKitContext = /* @__PURE__ */ createContext(null);
1661
+ var resolveConnectorId = /* @__PURE__ */ __name((wagmiConnectorId) => {
1662
+ if (!wagmiConnectorId) return null;
1663
+ if (wagmiConnectorId === "credit-connect") return "CREDIT_CONNECT";
1664
+ if (wagmiConnectorId === "walletConnect") return "WALLET_CONNECT";
1665
+ const lower = wagmiConnectorId.toLowerCase();
1666
+ if (lower.includes("metamask") || wagmiConnectorId === "injected") return "METAMASK";
1667
+ if (lower.includes("walletconnect")) return "WALLET_CONNECT";
1668
+ return null;
1669
+ }, "resolveConnectorId");
1670
+ var ConnectKitProvider = /* @__PURE__ */ __name((props) => {
1671
+ if (props.wagmiConfig) {
1672
+ return /* @__PURE__ */ React.createElement(WagmiProvider, {
1673
+ config: props.wagmiConfig
1674
+ }, /* @__PURE__ */ React.createElement(QueryClientProvider, {
1675
+ client: internalQueryClient
1676
+ }, /* @__PURE__ */ React.createElement(ConnectKitProviderInner, props)));
1677
+ }
1678
+ return /* @__PURE__ */ React.createElement(ConnectKitProviderInner, props);
1679
+ }, "ConnectKitProvider");
1680
+ var ConnectKitProviderInner = /* @__PURE__ */ __name(({ children, connectors, wcProjectId, requiredChainId, onConnect, onLog, renderConnectError }) => {
1681
+ var _a;
1682
+ const [isOpen, setIsOpen] = useState4(false);
1683
+ const [pendingResult, setPendingResult] = useState4(null);
1684
+ const account = useAccount2();
1685
+ const { disconnectAsync } = useDisconnect2();
1686
+ const onConnectRef = useRef4(onConnect);
1687
+ useEffect5(() => {
1688
+ onConnectRef.current = onConnect;
1689
+ }, [
1690
+ onConnect
1691
+ ]);
1692
+ const chainMismatch = requiredChainId != null && account.status === "connected" && account.chainId != null && account.chainId !== requiredChainId;
1693
+ const effectiveOpen = isOpen || chainMismatch;
1694
+ const open = useCallback4(() => {
1695
+ setIsOpen(true);
1696
+ }, []);
1697
+ const close = useCallback4(() => {
1698
+ setIsOpen(false);
1699
+ }, []);
1700
+ const disconnect = useCallback4(async () => {
1701
+ await disconnectAsync();
1702
+ }, [
1703
+ disconnectAsync
1704
+ ]);
1705
+ const handleModalConnect = useCallback4((result) => {
1706
+ setPendingResult(result);
1707
+ }, []);
1708
+ useEffect5(() => {
1709
+ var _a2;
1710
+ if (!pendingResult) return;
1711
+ if (account.status !== "connected") {
1712
+ setPendingResult(null);
1713
+ return;
1523
1714
  }
1524
- if (m.state.status === "INITIALIZING") {
1525
- await new Promise((resolve) => {
1526
- const unsub = m.on("changeState", (state) => {
1527
- if (state.status !== "INITIALIZING") {
1528
- unsub();
1529
- resolve();
1530
- }
1531
- });
1532
- });
1715
+ if (requiredChainId != null && account.chainId !== requiredChainId) {
1716
+ return;
1533
1717
  }
1534
- return m;
1535
- }, "ensureManagerInitialized");
1536
- return createConnector((config) => {
1537
- emitWagmiMessage = /* @__PURE__ */ __name((type, data) => {
1538
- config.emitter.emit("message", {
1539
- type,
1540
- data
1541
- });
1542
- }, "emitWagmiMessage");
1543
- emitWagmiDisconnect = /* @__PURE__ */ __name(() => {
1544
- config.emitter.emit("disconnect");
1545
- }, "emitWagmiDisconnect");
1718
+ (_a2 = onConnectRef.current) == null ? void 0 : _a2.call(onConnectRef, pendingResult);
1719
+ setPendingResult(null);
1720
+ setIsOpen(false);
1721
+ }, [
1722
+ pendingResult,
1723
+ account.status,
1724
+ account.chainId,
1725
+ requiredChainId
1726
+ ]);
1727
+ const value = useMemo5(() => {
1728
+ var _a2;
1546
1729
  return {
1547
- id: CONNECTOR_ID,
1548
- name: CONNECTOR_NAME,
1549
- type: CONNECTOR_TYPE,
1550
- async setup() {
1551
- await ensureManagerInitialized();
1552
- },
1553
- async connect(parameters) {
1554
- var _a;
1555
- try {
1556
- const m = createManagerIfNeeded();
1557
- if (m.state.status === "INITIALIZING") {
1558
- await new Promise((resolve) => {
1559
- const unsub = m.on("changeState", (state) => {
1560
- if (state.status !== "INITIALIZING") {
1561
- unsub();
1562
- resolve();
1563
- }
1564
- });
1565
- });
1566
- }
1567
- if (parameters == null ? void 0 : parameters.isReconnecting) {
1568
- const session2 = getCurrentSession();
1569
- if (!session2) throw new Error("No active session to reconnect");
1570
- const accounts2 = getChecksummedAccounts(session2);
1571
- if (accounts2.length === 0) throw new Error("No EVM address found");
1572
- const chainId2 = Number.parseInt(getEvmAddressInfo(session2)[0].networkIdentifier, 10);
1573
- if (!Number.isFinite(chainId2)) throw new Error(`Invalid chainId: ${chainId2}`);
1574
- selectedChainId = chainId2;
1575
- if ((parameters == null ? void 0 : parameters.withCapabilities) === true) {
1576
- return castConnectResult({
1577
- accounts: accounts2.map((address) => ({
1578
- address,
1579
- capabilities: {}
1580
- })),
1581
- chainId: chainId2
1582
- });
1583
- }
1584
- return castConnectResult({
1585
- accounts: accounts2,
1586
- chainId: chainId2
1587
- });
1588
- }
1589
- if (m.state.status === "CONNECTING" && m.state.connectingPayload) {
1590
- (_a = options.onDisplayUri) == null ? void 0 : _a.call(options, m.state.connectingPayload);
1591
- if (!connectPromise) {
1592
- connectPromise = new Promise((resolve) => {
1593
- const unsub = m.on("changeState", (state) => {
1594
- if (state.status === "CONNECTED") {
1595
- unsub();
1596
- resolve(true);
1597
- } else if (state.status === "DISCONNECTED") {
1598
- unsub();
1599
- resolve(false);
1600
- }
1601
- });
1602
- });
1603
- }
1604
- }
1605
- if (m.state.status !== "CONNECTED") {
1606
- if (!connectPromise) {
1607
- if (m.state.status !== "DISCONNECTED") {
1608
- throw new Error(`Cannot connect from ${m.state.status} state`);
1609
- }
1610
- connectPromise = m.connectNewSession();
1611
- }
1612
- const connected = await connectPromise;
1613
- connectPromise = null;
1614
- if (!connected) throw new Error("Credit Connect session failed");
1615
- }
1616
- const session = getCurrentSession();
1617
- if (!session) throw new Error("Credit Connect session failed");
1618
- const accounts = getChecksummedAccounts(session);
1619
- if (accounts.length === 0) throw new Error("No EVM address found");
1620
- const chainId = Number.parseInt(getEvmAddressInfo(session)[0].networkIdentifier, 10);
1621
- if (!Number.isFinite(chainId)) throw new Error(`Invalid chainId: ${chainId}`);
1622
- selectedChainId = chainId;
1623
- if ((parameters == null ? void 0 : parameters.withCapabilities) === true) {
1624
- return castConnectResult({
1625
- accounts: accounts.map((address) => ({
1626
- address,
1627
- capabilities: {}
1628
- })),
1629
- chainId
1630
- });
1631
- }
1632
- return castConnectResult({
1633
- accounts,
1634
- chainId
1635
- });
1636
- } catch (error) {
1637
- resetState();
1638
- throw error;
1639
- }
1640
- },
1641
- async switchChain({ chainId }) {
1642
- const session = getCurrentSession();
1643
- if (!session) throw new Error("No active session");
1644
- const supported = getEvmAddressInfo(session).some((info) => Number.parseInt(info.networkIdentifier, 10) === chainId);
1645
- if (!supported) {
1646
- const err = new Error(`Unsupported chain: ${chainId}`);
1647
- err.code = 4902;
1648
- throw err;
1649
- }
1650
- selectedChainId = chainId;
1651
- config.emitter.emit("change", {
1652
- chainId
1653
- });
1654
- const chain = config.chains.find((c) => c.id === chainId);
1655
- if (!chain) throw new Error(`Chain ${chainId} not in config`);
1656
- return chain;
1657
- },
1658
- async isAuthorized() {
1659
- await ensureManagerInitialized();
1660
- const session = getCurrentSession();
1661
- if (!session) return false;
1662
- return session.addressInfoList.some((info) => info.networkType === "eip155");
1663
- },
1664
- async disconnect() {
1665
- isLocalDisconnect = true;
1666
- try {
1667
- if ((manager == null ? void 0 : manager.state.status) === "CONNECTED") {
1668
- await manager.disconnectSession();
1669
- }
1670
- } finally {
1671
- isLocalDisconnect = false;
1672
- }
1673
- resetState();
1674
- config.emitter.emit("disconnect");
1675
- },
1676
- async getAccounts() {
1677
- await ensureManagerInitialized();
1678
- const session = getCurrentSession();
1679
- if (!session) return [];
1680
- return getChecksummedAccounts(session);
1681
- },
1682
- async getChainId() {
1683
- await ensureManagerInitialized();
1684
- const session = getCurrentSession();
1685
- if (!session) throw new Error("No active session");
1686
- if (selectedChainId !== null) return selectedChainId;
1687
- const evmAddressInfo = getEvmAddressInfo(session);
1688
- if (evmAddressInfo.length === 0) throw new Error("No EVM address found");
1689
- const chainId = Number.parseInt(evmAddressInfo[0].networkIdentifier, 10);
1690
- if (!Number.isFinite(chainId)) throw new Error(`Invalid chainId: ${chainId}`);
1691
- selectedChainId = chainId;
1692
- return chainId;
1693
- },
1694
- async getProvider() {
1695
- if (provider) return provider;
1696
- await ensureManagerInitialized();
1697
- const createdProvider = {
1698
- request: /* @__PURE__ */ __name(async (args) => {
1699
- const { method, params: rawParams } = args;
1700
- const params = Array.isArray(rawParams) ? [
1701
- ...rawParams
1702
- ] : rawParams === void 0 ? [] : [
1703
- rawParams
1704
- ];
1705
- const session = getCurrentSession();
1706
- const getSelectedAddressInfo = /* @__PURE__ */ __name((address) => {
1707
- if (!session) throw new Error("No active session");
1708
- const evmInfo = getEvmAddressInfo(session);
1709
- if (evmInfo.length === 0) throw new Error("No EVM address found");
1710
- if (!address) return evmInfo[0];
1711
- const found = evmInfo.find((info) => info.address.toLowerCase() === address.toLowerCase());
1712
- if (!found) throw new Error(`Address not in session: ${address}`);
1713
- return found;
1714
- }, "getSelectedAddressInfo");
1715
- if (method === "eth_accounts") {
1716
- if (!session) return [];
1717
- return getChecksummedAccounts(session);
1718
- }
1719
- if (method === "eth_chainId") {
1720
- if (!session) throw new Error("No active session");
1721
- if (selectedChainId !== null) return `0x${selectedChainId.toString(16)}`;
1722
- const evmInfo = getEvmAddressInfo(session);
1723
- if (evmInfo.length === 0) throw new Error("No EVM address found");
1724
- const chainId = Number.parseInt(evmInfo[0].networkIdentifier, 10);
1725
- if (!Number.isFinite(chainId)) throw new Error(`Invalid chainId: ${chainId}`);
1726
- selectedChainId = chainId;
1727
- return `0x${chainId.toString(16)}`;
1728
- }
1729
- if (method === "wallet_switchEthereumChain") {
1730
- const [{ chainId: rawChainId }] = params != null ? params : [];
1731
- if (!rawChainId) throw new Error("wallet_switchEthereumChain missing chainId param");
1732
- const chainId = Number.parseInt(rawChainId, 16);
1733
- if (!Number.isFinite(chainId)) throw new Error(`Invalid chainId: ${rawChainId}`);
1734
- if (!session) throw new Error("No active session");
1735
- const supported = getEvmAddressInfo(session).some((info) => Number.parseInt(info.networkIdentifier, 10) === chainId);
1736
- if (!supported) {
1737
- const err = new Error(`Unsupported chain: ${chainId}`);
1738
- err.code = 4902;
1739
- throw err;
1740
- }
1741
- selectedChainId = chainId;
1742
- config.emitter.emit("change", {
1743
- chainId
1744
- });
1745
- return null;
1746
- }
1747
- if (method === "personal_sign") {
1748
- const [messageParam, addressParam] = params != null ? params : [];
1749
- const message = typeof messageParam === "string" ? messageParam : String(messageParam != null ? messageParam : "");
1750
- const address = typeof addressParam === "string" ? addressParam : void 0;
1751
- const addressInfo = getSelectedAddressInfo(address);
1752
- const response = await (session == null ? void 0 : session.jsonRpc.request("signMessage", {
1753
- message,
1754
- addressInfo
1755
- }));
1756
- return response == null ? void 0 : response.signature;
1757
- }
1758
- if (method === "eth_sign") {
1759
- const [addressParam, messageParam] = params != null ? params : [];
1760
- const address = typeof addressParam === "string" ? addressParam : void 0;
1761
- const message = typeof messageParam === "string" ? messageParam : String(messageParam != null ? messageParam : "");
1762
- const addressInfo = getSelectedAddressInfo(address);
1763
- const response = await (session == null ? void 0 : session.jsonRpc.request("signMessage", {
1764
- message,
1765
- addressInfo
1766
- }));
1767
- return response == null ? void 0 : response.signature;
1768
- }
1769
- if (method === "eth_signTypedData" || method === "eth_signTypedData_v4") {
1770
- const [addressParam, typedDataParam] = params != null ? params : [];
1771
- const address = typeof addressParam === "string" ? addressParam : void 0;
1772
- const typedData = typeof typedDataParam === "string" ? typedDataParam : JSON.stringify(typedDataParam != null ? typedDataParam : "");
1773
- const addressInfo = getSelectedAddressInfo(address);
1774
- const response = await (session == null ? void 0 : session.jsonRpc.request("signTypedData", {
1775
- typedData,
1776
- addressInfo
1777
- }));
1778
- return response == null ? void 0 : response.signature;
1779
- }
1780
- if (method === "eth_sendTransaction") {
1781
- const [txParams] = params != null ? params : [];
1782
- const addressInfo = getSelectedAddressInfo(txParams == null ? void 0 : txParams.from);
1783
- const response = await (session == null ? void 0 : session.jsonRpc.request("sendTransaction", {
1784
- addressInfo,
1785
- to: txParams == null ? void 0 : txParams.to,
1786
- value: txParams == null ? void 0 : txParams.value,
1787
- data: txParams == null ? void 0 : txParams.data,
1788
- gas: txParams == null ? void 0 : txParams.gas,
1789
- gasPrice: txParams == null ? void 0 : txParams.gasPrice,
1790
- maxFeePerGas: txParams == null ? void 0 : txParams.maxFeePerGas,
1791
- maxPriorityFeePerGas: txParams == null ? void 0 : txParams.maxPriorityFeePerGas,
1792
- nonce: txParams == null ? void 0 : txParams.nonce,
1793
- chainId: txParams == null ? void 0 : txParams.chainId
1794
- }));
1795
- return response == null ? void 0 : response.txHash;
1796
- }
1797
- if (method === "credit_connect_send_message") {
1798
- if (!session) throw new Error("No active session");
1799
- const [messageParam] = params != null ? params : [];
1800
- const message = typeof messageParam === "string" ? messageParam : JSON.stringify(messageParam != null ? messageParam : "");
1801
- await session.msg.sendMessage(message);
1802
- return true;
1803
- }
1804
- if (method === "credit_connect_jsonrpc_ping") {
1805
- if (!session) throw new Error("No active session");
1806
- return await session.jsonRpc.request("pingPong", {});
1807
- }
1808
- throw new Error(`Unsupported provider method: ${method}`);
1809
- }, "request"),
1810
- on: /* @__PURE__ */ __name((event, listener) => {
1811
- let listeners = providerListeners.get(event);
1812
- if (!listeners) {
1813
- listeners = /* @__PURE__ */ new Set();
1814
- providerListeners.set(event, listeners);
1815
- }
1816
- listeners.add(listener);
1817
- return createdProvider;
1818
- }, "on"),
1819
- removeListener: /* @__PURE__ */ __name((event, listener) => {
1820
- var _a;
1821
- (_a = providerListeners.get(event)) == null ? void 0 : _a.delete(listener);
1822
- return createdProvider;
1823
- }, "removeListener")
1824
- };
1825
- provider = createdProvider;
1826
- return provider;
1827
- },
1828
- onAccountsChanged(accounts) {
1829
- if (!accounts || accounts.length === 0) {
1830
- config.emitter.emit("disconnect");
1831
- return;
1832
- }
1833
- config.emitter.emit("change", {
1834
- accounts: accounts.map(getAddress)
1835
- });
1836
- },
1837
- onChainChanged(chainId) {
1838
- const normalized = typeof chainId === "string" ? Number.parseInt(chainId, 16) : Number(chainId);
1839
- if (!Number.isFinite(normalized)) return;
1840
- selectedChainId = normalized;
1841
- config.emitter.emit("change", {
1842
- chainId: normalized
1843
- });
1844
- },
1845
- onDisconnect() {
1846
- resetState();
1847
- config.emitter.emit("disconnect");
1848
- }
1730
+ isOpen: effectiveOpen,
1731
+ open,
1732
+ close,
1733
+ isConnected: account.status === "connected",
1734
+ address: account.address,
1735
+ connectorId: resolveConnectorId((_a2 = account.connector) == null ? void 0 : _a2.id),
1736
+ disconnect
1849
1737
  };
1850
- });
1851
- }, "creditConnectConnector");
1738
+ }, [
1739
+ effectiveOpen,
1740
+ open,
1741
+ close,
1742
+ account.status,
1743
+ account.address,
1744
+ (_a = account.connector) == null ? void 0 : _a.id,
1745
+ disconnect
1746
+ ]);
1747
+ return /* @__PURE__ */ React.createElement(ConnectKitContext.Provider, {
1748
+ value
1749
+ }, children, /* @__PURE__ */ React.createElement(ConnectModal, {
1750
+ open: effectiveOpen,
1751
+ connectors,
1752
+ wcProjectId,
1753
+ requiredChainId,
1754
+ renderConnectError,
1755
+ onConnect: handleModalConnect,
1756
+ onClose: close,
1757
+ onLog
1758
+ }));
1759
+ }, "ConnectKitProviderInner");
1760
+ var useConnectKit = /* @__PURE__ */ __name(() => {
1761
+ const ctx = useContext(ConnectKitContext);
1762
+ if (!ctx) {
1763
+ throw new Error("useConnectKit must be used within a ConnectKitProvider");
1764
+ }
1765
+ return ctx;
1766
+ }, "useConnectKit");
1852
1767
  export {
1768
+ ConnectKitProvider,
1853
1769
  ConnectModal,
1854
- creditConnectConnector
1770
+ useConnectKit
1855
1771
  };