@openfort/react 1.6.0 → 1.6.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/build/components/Common/Modal/index.js +14 -0
- package/build/components/Common/Modal/index.js.map +1 -1
- package/build/components/Openfort/types.d.ts +1 -1
- package/build/components/Pages/AssetInventory/SolanaAssetInventory.js +7 -7
- package/build/components/Pages/DepositWallet/index.js +15 -10
- package/build/components/Pages/DepositWallet/index.js.map +1 -1
- package/build/components/Pages/ExportKey/index.js +44 -4
- package/build/components/Pages/ExportKey/index.js.map +1 -1
- package/build/components/Pages/ExportKey/styles.d.ts +5 -0
- package/build/components/Pages/ExportKey/styles.js +47 -0
- package/build/components/Pages/ExportKey/styles.js.map +1 -0
- package/build/components/Pages/Receive/index.js +2 -2
- package/build/components/Pages/SelectToken/SolanaSelectToken.js +7 -7
- package/build/components/Pages/SelectToken/index.js +7 -3
- package/build/components/Pages/SelectToken/index.js.map +1 -1
- package/build/components/Pages/Send/EthereumSend.js +25 -5
- package/build/components/Pages/Send/EthereumSend.js.map +1 -1
- package/build/components/Pages/Send/SolanaSend.js +23 -4
- package/build/components/Pages/Send/SolanaSend.js.map +1 -1
- package/build/components/Pages/Send/styles.d.ts +17 -11
- package/build/components/Pages/Send/styles.js +104 -49
- package/build/components/Pages/Send/styles.js.map +1 -1
- package/build/components/Pages/SendConfirmation/ConfirmationSummary.d.ts +3 -1
- package/build/components/Pages/SendConfirmation/ConfirmationSummary.js +2 -2
- package/build/components/Pages/SendConfirmation/EstimatedFees.d.ts +3 -1
- package/build/components/Pages/SendConfirmation/EstimatedFees.js +22 -15
- package/build/components/Pages/SendConfirmation/EstimatedFees.js.map +1 -1
- package/build/components/Pages/SendConfirmation/SolanaSendConfirmation.js +17 -5
- package/build/components/Pages/SendConfirmation/SolanaSendConfirmation.js.map +1 -1
- package/build/components/Pages/SendConfirmation/index.js +11 -5
- package/build/components/Pages/SendConfirmation/index.js.map +1 -1
- package/build/components/Pages/SendConfirmation/styles.d.ts +3 -1
- package/build/components/Pages/SendConfirmation/styles.js +20 -6
- package/build/components/Pages/SendConfirmation/styles.js.map +1 -1
- package/build/components/Pages/SignMessage/index.js +44 -19
- package/build/components/Pages/SignMessage/index.js.map +1 -1
- package/build/components/Pages/SignMessage/styles.d.ts +2 -3
- package/build/components/Pages/SignMessage/styles.js +19 -2
- package/build/components/Pages/SignMessage/styles.js.map +1 -1
- package/build/hooks/openfort/useSignMessage.d.ts +2 -2
- package/build/hooks/openfort/useUI.js +4 -2
- package/build/hooks/openfort/useUI.js.map +1 -1
- package/build/solana/transfer.d.ts +12 -0
- package/build/solana/transfer.js +29 -1
- package/build/solana/transfer.js.map +1 -1
- package/build/version.d.ts +1 -1
- package/build/version.js +1 -1
- package/package.json +1 -1
|
@@ -3,99 +3,154 @@ import styled from '../../../styles/styled/index.js';
|
|
|
3
3
|
const Form = styled.form `
|
|
4
4
|
display: flex;
|
|
5
5
|
flex-direction: column;
|
|
6
|
-
gap:
|
|
6
|
+
gap: 14px;
|
|
7
7
|
margin-top: 20px;
|
|
8
8
|
`;
|
|
9
|
-
|
|
9
|
+
/** Rounded container shared by the "To" and "Amount" boxes. */
|
|
10
|
+
const SendCard = styled.div `
|
|
10
11
|
display: flex;
|
|
11
12
|
flex-direction: column;
|
|
13
|
+
gap: 10px;
|
|
14
|
+
padding: 14px 16px;
|
|
15
|
+
border-radius: var(--ck-secondary-button-border-radius);
|
|
16
|
+
border: 1px solid var(--ck-body-divider);
|
|
17
|
+
background: var(--ck-secondary-button-background);
|
|
12
18
|
text-align: left;
|
|
13
19
|
`;
|
|
14
|
-
const
|
|
15
|
-
font-size:
|
|
20
|
+
const CardLabel = styled.span `
|
|
21
|
+
font-size: 13px;
|
|
16
22
|
font-weight: 600;
|
|
17
|
-
color: var(--ck-body-color);
|
|
23
|
+
color: var(--ck-body-color-muted);
|
|
18
24
|
`;
|
|
19
|
-
|
|
25
|
+
/** "To" box: inline label, recipient input, and a Paste button. */
|
|
26
|
+
const ToRow = styled.div `
|
|
20
27
|
display: flex;
|
|
21
28
|
align-items: center;
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
29
|
+
gap: 10px;
|
|
30
|
+
`;
|
|
31
|
+
const RecipientInput = styled.input `
|
|
32
|
+
flex: 1;
|
|
33
|
+
min-width: 0;
|
|
34
|
+
border: none;
|
|
35
|
+
background: transparent;
|
|
36
|
+
color: var(--ck-body-color);
|
|
37
|
+
font-size: 15px;
|
|
38
|
+
font-weight: 500;
|
|
39
|
+
padding: 0;
|
|
40
|
+
outline: none;
|
|
41
|
+
|
|
42
|
+
&::placeholder {
|
|
43
|
+
color: var(--ck-body-color-muted);
|
|
44
|
+
}
|
|
45
|
+
`;
|
|
46
|
+
const PasteButton = styled.button `
|
|
47
|
+
flex-shrink: 0;
|
|
48
|
+
padding: 6px 12px;
|
|
49
|
+
border-radius: 16px;
|
|
27
50
|
border: 1px solid var(--ck-body-divider);
|
|
28
|
-
background: var(--ck-
|
|
51
|
+
background: var(--ck-body-background);
|
|
29
52
|
color: var(--ck-body-color);
|
|
53
|
+
font-size: 12px;
|
|
54
|
+
font-weight: 600;
|
|
30
55
|
cursor: pointer;
|
|
31
|
-
transition: background 150ms ease,
|
|
32
|
-
text-align: left;
|
|
56
|
+
transition: background 150ms ease, color 150ms ease, border-color 150ms ease;
|
|
33
57
|
|
|
34
58
|
&:hover {
|
|
35
59
|
background: var(--ck-secondary-button-hover-background);
|
|
36
|
-
border-color: var(--ck-body-color-muted);
|
|
37
60
|
}
|
|
38
61
|
`;
|
|
39
|
-
|
|
62
|
+
/** "Amount" box: large amount input with an inline token selector. */
|
|
63
|
+
const AmountRow = styled.div `
|
|
40
64
|
display: flex;
|
|
41
|
-
|
|
42
|
-
gap:
|
|
43
|
-
overflow: hidden;
|
|
65
|
+
align-items: center;
|
|
66
|
+
gap: 10px;
|
|
44
67
|
`;
|
|
45
|
-
const
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
68
|
+
const AmountField = styled.input `
|
|
69
|
+
flex: 1;
|
|
70
|
+
min-width: 0;
|
|
71
|
+
border: none;
|
|
72
|
+
background: transparent;
|
|
73
|
+
color: var(--ck-body-color);
|
|
74
|
+
font-size: 28px;
|
|
75
|
+
font-weight: 600;
|
|
76
|
+
line-height: 1.1;
|
|
77
|
+
padding: 0;
|
|
78
|
+
outline: none;
|
|
79
|
+
|
|
80
|
+
&::placeholder {
|
|
81
|
+
color: var(--ck-body-color-muted);
|
|
82
|
+
}
|
|
58
83
|
`;
|
|
59
|
-
const
|
|
84
|
+
const PillLogo = styled.span `
|
|
60
85
|
display: flex;
|
|
61
86
|
align-items: center;
|
|
62
|
-
|
|
63
|
-
|
|
87
|
+
width: 22px;
|
|
88
|
+
flex-shrink: 0;
|
|
64
89
|
`;
|
|
65
|
-
const
|
|
90
|
+
const TokenPill = styled.button `
|
|
91
|
+
display: flex;
|
|
92
|
+
align-items: center;
|
|
93
|
+
gap: 6px;
|
|
66
94
|
flex-shrink: 0;
|
|
67
|
-
padding:
|
|
68
|
-
border-radius:
|
|
95
|
+
padding: 7px 12px;
|
|
96
|
+
border-radius: 999px;
|
|
69
97
|
border: 1px solid var(--ck-body-divider);
|
|
70
98
|
background: var(--ck-body-background);
|
|
71
99
|
color: var(--ck-body-color);
|
|
72
|
-
font-size:
|
|
100
|
+
font-size: 14px;
|
|
73
101
|
font-weight: 600;
|
|
74
102
|
cursor: pointer;
|
|
75
|
-
transition: background 150ms ease, color 150ms ease,
|
|
103
|
+
transition: background 150ms ease, border-color 150ms ease, color 150ms ease;
|
|
76
104
|
|
|
77
105
|
&:hover {
|
|
78
106
|
background: var(--ck-secondary-button-hover-background);
|
|
107
|
+
border-color: var(--ck-body-color-muted);
|
|
79
108
|
}
|
|
109
|
+
`;
|
|
110
|
+
/** Bottom row of the amount box: fiat value (left), balance + Use max (right). */
|
|
111
|
+
const AmountMeta = styled.div `
|
|
112
|
+
display: flex;
|
|
113
|
+
align-items: center;
|
|
114
|
+
justify-content: space-between;
|
|
115
|
+
gap: 8px;
|
|
116
|
+
`;
|
|
117
|
+
const MetaText = styled.span `
|
|
118
|
+
font-size: 13px;
|
|
119
|
+
font-weight: 500;
|
|
120
|
+
color: var(--ck-body-color-muted);
|
|
121
|
+
white-space: nowrap;
|
|
122
|
+
overflow: hidden;
|
|
123
|
+
text-overflow: ellipsis;
|
|
124
|
+
`;
|
|
125
|
+
const BalanceMeta = styled.span `
|
|
126
|
+
display: flex;
|
|
127
|
+
align-items: center;
|
|
128
|
+
gap: 6px;
|
|
129
|
+
flex-shrink: 0;
|
|
130
|
+
font-size: 13px;
|
|
131
|
+
font-weight: 500;
|
|
132
|
+
color: var(--ck-body-color-muted);
|
|
133
|
+
`;
|
|
134
|
+
const UseMaxButton = styled.button `
|
|
135
|
+
border: none;
|
|
136
|
+
background: none;
|
|
137
|
+
padding: 0;
|
|
138
|
+
font-size: 13px;
|
|
139
|
+
font-weight: 600;
|
|
140
|
+
color: var(--ck-accent-color, var(--ck-focus-color, #1a88f8));
|
|
141
|
+
cursor: pointer;
|
|
80
142
|
|
|
81
143
|
&:disabled {
|
|
82
144
|
opacity: 0.5;
|
|
83
145
|
cursor: not-allowed;
|
|
84
|
-
background: var(--ck-body-background-secondary);
|
|
85
146
|
}
|
|
86
147
|
`;
|
|
87
|
-
const HelperText = styled.span `
|
|
88
|
-
display: block;
|
|
89
|
-
margin-top: 8px;
|
|
90
|
-
font-size: 13px;
|
|
91
|
-
color: var(--ck-body-color-muted);
|
|
92
|
-
`;
|
|
93
148
|
const ErrorText = styled.span `
|
|
94
149
|
display: block;
|
|
95
|
-
margin-top:
|
|
150
|
+
margin-top: 2px;
|
|
96
151
|
font-size: 13px;
|
|
97
152
|
color: var(--ck-body-color-danger);
|
|
98
153
|
`;
|
|
99
154
|
|
|
100
|
-
export {
|
|
155
|
+
export { AmountField, AmountMeta, AmountRow, BalanceMeta, CardLabel, ErrorText, Form, MetaText, PasteButton, PillLogo, RecipientInput, SendCard, ToRow, TokenPill, UseMaxButton };
|
|
101
156
|
//# sourceMappingURL=styles.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"styles.js","sources":[],"sourcesContent":[],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"styles.js","sources":[],"sourcesContent":[],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;"}
|
|
@@ -17,11 +17,13 @@ interface ConfirmationSummaryProps {
|
|
|
17
17
|
fee: ReactNode;
|
|
18
18
|
/** The wallet the funds are paid from. */
|
|
19
19
|
payWith?: ConfirmationAddress;
|
|
20
|
+
/** Current balance of the pay-with wallet, e.g. "134.32 USDC". */
|
|
21
|
+
balance?: string;
|
|
20
22
|
}
|
|
21
23
|
/**
|
|
22
24
|
* Shared, chain-agnostic transaction preview used by the EVM and Solana send
|
|
23
25
|
* confirmation screens. Renders the approval-style rows (Total / To / Network /
|
|
24
26
|
* Estimated fee) plus a "Pay with" card.
|
|
25
27
|
*/
|
|
26
|
-
export declare function ConfirmationSummary({ amount, symbol, fiat, to, networkName, networkIcon, fee, payWith, }: ConfirmationSummaryProps): import("react/jsx-runtime").JSX.Element;
|
|
28
|
+
export declare function ConfirmationSummary({ amount, symbol, fiat, to, networkName, networkIcon, fee, payWith, balance, }: ConfirmationSummaryProps): import("react/jsx-runtime").JSX.Element;
|
|
27
29
|
export {};
|
|
@@ -7,8 +7,8 @@ import { SummaryList, SummaryItem, SummaryLabel, AmountValue, FiatValue, Address
|
|
|
7
7
|
* confirmation screens. Renders the approval-style rows (Total / To / Network /
|
|
8
8
|
* Estimated fee) plus a "Pay with" card.
|
|
9
9
|
*/
|
|
10
|
-
function ConfirmationSummary({ amount, symbol, fiat, to, networkName, networkIcon, fee, payWith, }) {
|
|
11
|
-
return (jsxs(Fragment, { children: [jsxs(SummaryList, { children: [jsxs(SummaryItem, { children: [jsx(SummaryLabel, { children: "Total" }), jsxs(AmountValue, { children: [amount || '0', " ", symbol, fiat ? jsxs(FiatValue, { children: ["\u2248 ", fiat] }) : null] })] }), jsxs(SummaryItem, { children: [jsx(SummaryLabel, { children: "To" }), jsx(AddressValue, { children: to ? (jsx(CopyText, { size: "1rem", value: to.value, children: to.display })) : ('--') })] }), jsxs(SummaryItem, { children: [jsx(SummaryLabel, { children: "Network" }), jsxs(NetworkValue, { children: [networkIcon, networkName] })] }), jsxs(SummaryItem, { children: [jsx(SummaryLabel, { children: "Estimated fee" }), fee] })] }), jsxs(PayWithCard, { children: [jsxs(PayWithMeta, { children: [jsx(SummaryLabel, { children: "Pay with" }), jsx(PayWithAddress, { children: payWith ? (jsx(CopyText, { size: "0.875rem", value: payWith.value, children: payWith.display })) : ('--') })] }),
|
|
10
|
+
function ConfirmationSummary({ amount, symbol, fiat, to, networkName, networkIcon, fee, payWith, balance, }) {
|
|
11
|
+
return (jsxs(Fragment, { children: [jsxs(SummaryList, { children: [jsxs(SummaryItem, { children: [jsx(SummaryLabel, { children: "Total" }), jsxs(AmountValue, { children: [amount || '0', " ", symbol, fiat ? jsxs(FiatValue, { children: ["\u2248 ", fiat] }) : null] })] }), jsxs(SummaryItem, { children: [jsx(SummaryLabel, { children: "To" }), jsx(AddressValue, { children: to ? (jsx(CopyText, { size: "1rem", value: to.value, children: to.display })) : ('--') })] }), jsxs(SummaryItem, { children: [jsx(SummaryLabel, { children: "Network" }), jsxs(NetworkValue, { children: [networkIcon, networkName] })] }), jsxs(SummaryItem, { children: [jsx(SummaryLabel, { children: "Estimated fee" }), fee] })] }), jsxs(PayWithCard, { children: [jsxs(PayWithMeta, { children: [jsx(SummaryLabel, { children: "Pay with" }), jsx(PayWithAddress, { children: payWith ? (jsx(CopyText, { size: "0.875rem", value: payWith.value, children: payWith.display })) : ('--') })] }), balance ? jsx(PayWithBadge, { children: balance }) : null] })] }));
|
|
12
12
|
}
|
|
13
13
|
|
|
14
14
|
export { ConfirmationSummary };
|
|
@@ -8,6 +8,8 @@ type EstimatedFeesProps = {
|
|
|
8
8
|
nativeSymbol: string;
|
|
9
9
|
enabled?: boolean;
|
|
10
10
|
hideInfoIcon?: boolean;
|
|
11
|
+
/** When fees are sponsored, show the estimate struck through next to "Sponsored". */
|
|
12
|
+
sponsored?: boolean;
|
|
11
13
|
};
|
|
12
|
-
export declare const EstimatedFees: ({ account, to, value, data, chainId, nativeSymbol, enabled, hideInfoIcon, }: EstimatedFeesProps) => import("react/jsx-runtime").JSX.Element;
|
|
14
|
+
export declare const EstimatedFees: ({ account, to, value, data, chainId, nativeSymbol, enabled, hideInfoIcon, sponsored, }: EstimatedFeesProps) => import("react/jsx-runtime").JSX.Element;
|
|
13
15
|
export {};
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { jsx,
|
|
1
|
+
import { jsx, jsxs, Fragment } from 'react/jsx-runtime';
|
|
2
2
|
import { createPublicClient, http, formatUnits } from 'viem';
|
|
3
3
|
import { useEthereumWalletAssets } from '../../../ethereum/hooks/useEthereumWalletAssets.js';
|
|
4
4
|
import { useAsyncData } from '../../../shared/hooks/useAsyncData.js';
|
|
@@ -7,7 +7,7 @@ import { getDefaultEthereumRpcUrl } from '../../../utils/rpc.js';
|
|
|
7
7
|
import Tooltip from '../../Common/Tooltip/index.js';
|
|
8
8
|
import { useOpenfort } from '../../Openfort/useOpenfort.js';
|
|
9
9
|
import { formatBalance } from '../Send/utils.js';
|
|
10
|
-
import { InfoIconWrapper } from './styles.js';
|
|
10
|
+
import { InfoIconWrapper, FeeStrike, SponsoredText } from './styles.js';
|
|
11
11
|
|
|
12
12
|
const InfoIcon = () => (jsxs("svg", { "aria-hidden": "true", width: "14", height: "14", viewBox: "0 0 14 14", fill: "none", xmlns: "http://www.w3.org/2000/svg", children: [jsx("circle", { cx: "7", cy: "7", r: "6", stroke: "currentColor", strokeWidth: "1.5" }), jsx("path", { d: "M7 10V6.5M7 4.5H7.005", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round" })] }));
|
|
13
13
|
const usdFormatter = new Intl.NumberFormat('en-US', {
|
|
@@ -16,8 +16,8 @@ const usdFormatter = new Intl.NumberFormat('en-US', {
|
|
|
16
16
|
minimumFractionDigits: 2,
|
|
17
17
|
maximumFractionDigits: 4,
|
|
18
18
|
});
|
|
19
|
-
const EstimatedFees = ({ account, to, value, data, chainId, nativeSymbol, enabled = true, hideInfoIcon = false, }) => {
|
|
20
|
-
var _a, _b, _c;
|
|
19
|
+
const EstimatedFees = ({ account, to, value, data, chainId, nativeSymbol, enabled = true, hideInfoIcon = false, sponsored = false, }) => {
|
|
20
|
+
var _a, _b, _c, _d;
|
|
21
21
|
const { walletConfig } = useOpenfort();
|
|
22
22
|
const { data: assets } = useEthereumWalletAssets();
|
|
23
23
|
const pricePerToken = (_c = (_b = (_a = assets === null || assets === void 0 ? void 0 : assets.find((a) => a.type === 'native')) === null || _a === void 0 ? void 0 : _a.metadata) === null || _b === void 0 ? void 0 : _b.fiat) === null || _c === void 0 ? void 0 : _c.value;
|
|
@@ -49,19 +49,26 @@ const EstimatedFees = ({ account, to, value, data, chainId, nativeSymbol, enable
|
|
|
49
49
|
},
|
|
50
50
|
enabled: enabled && !!account && !!to && !!chainId,
|
|
51
51
|
});
|
|
52
|
-
//
|
|
53
|
-
|
|
54
|
-
|
|
52
|
+
// Format the estimate (USD when a native price is known, otherwise native units).
|
|
53
|
+
const gasUnits = (_d = gas.data) === null || _d === void 0 ? void 0 : _d.gasLimit;
|
|
54
|
+
let feeText = null;
|
|
55
|
+
if (gas.data && !gas.error) {
|
|
56
|
+
const gasCost = gas.data.estimatedCost;
|
|
57
|
+
if (pricePerToken !== undefined) {
|
|
58
|
+
feeText = `≈ ${usdFormatter.format(Number.parseFloat(formatUnits(gasCost, 18)) * pricePerToken)}`;
|
|
59
|
+
}
|
|
60
|
+
else {
|
|
61
|
+
feeText = `≈ ${formatBalance(gasCost, 18)} ${nativeSymbol}`;
|
|
62
|
+
}
|
|
55
63
|
}
|
|
56
|
-
const
|
|
57
|
-
|
|
58
|
-
if (
|
|
59
|
-
|
|
60
|
-
const gasCostInUsd = gasCostInEth * pricePerToken;
|
|
61
|
-
return (jsxs(Fragment, { children: ["\u2248 ", usdFormatter.format(gasCostInUsd), !hideInfoIcon && (jsx(Tooltip, { message: `${gasUnits.toString()} gas units (paid in ${nativeSymbol})`, delay: 0.2, children: jsx(InfoIconWrapper, { children: jsx(InfoIcon, {}) }) }))] }));
|
|
64
|
+
const info = !hideInfoIcon && gasUnits ? (jsx(Tooltip, { message: `${gasUnits.toString()} gas units (paid in ${nativeSymbol})`, delay: 0.2, children: jsx(InfoIconWrapper, { children: jsx(InfoIcon, {}) }) })) : null;
|
|
65
|
+
// Sponsored: show what it would have cost, struck through, next to "Sponsored".
|
|
66
|
+
if (sponsored) {
|
|
67
|
+
return (jsxs(Fragment, { children: [feeText && jsx(FeeStrike, { children: feeText }), jsx(SponsoredText, { children: "Sponsored" })] }));
|
|
62
68
|
}
|
|
63
|
-
|
|
64
|
-
|
|
69
|
+
if (!feeText)
|
|
70
|
+
return jsx(Fragment, { children: "--" });
|
|
71
|
+
return (jsxs(Fragment, { children: [feeText, info] }));
|
|
65
72
|
};
|
|
66
73
|
|
|
67
74
|
export { EstimatedFees };
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"EstimatedFees.js","sources":[],"sourcesContent":[],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"EstimatedFees.js","sources":[],"sourcesContent":[],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;"}
|
|
@@ -1,10 +1,12 @@
|
|
|
1
|
-
import { jsxs, jsx } from 'react/jsx-runtime';
|
|
1
|
+
import { jsxs, jsx, Fragment } from 'react/jsx-runtime';
|
|
2
2
|
import { ChainTypeEnum } from '@openfort/openfort-js';
|
|
3
3
|
import { useState, useEffect } from 'react';
|
|
4
4
|
import { parseUnits } from 'viem';
|
|
5
|
+
import { currencyLogoUrl } from '../../../constants/logos.js';
|
|
6
|
+
import { useAsyncData } from '../../../shared/hooks/useAsyncData.js';
|
|
5
7
|
import { getExplorerUrl } from '../../../shared/utils/explorer.js';
|
|
6
8
|
import { useSolanaEmbeddedWallet } from '../../../solana/hooks/useSolanaEmbeddedWallet.js';
|
|
7
|
-
import { sendSplTokenGasless, sendSplToken, sendSolGasless, sendSol } from '../../../solana/transfer.js';
|
|
9
|
+
import { estimateSolanaTransferFeeLamports, sendSplTokenGasless, sendSplToken, sendSolGasless, sendSol } from '../../../solana/transfer.js';
|
|
8
10
|
import 'detect-browser';
|
|
9
11
|
import { truncateSolanaAddress } from '../../../utils/format.js';
|
|
10
12
|
import Button from '../../Common/Button/index.js';
|
|
@@ -13,12 +15,13 @@ import { ModalHeading, ModalBody } from '../../Common/Modal/styles.js';
|
|
|
13
15
|
import { routes } from '../../Openfort/types.js';
|
|
14
16
|
import { useOpenfort } from '../../Openfort/useOpenfort.js';
|
|
15
17
|
import { PageContent } from '../../PageContent/index.js';
|
|
18
|
+
import { formatBalance, formatBalanceWithSymbol } from '../Send/utils.js';
|
|
16
19
|
import { ConfirmationSummary } from './ConfirmationSummary.js';
|
|
17
|
-
import { ButtonRow,
|
|
20
|
+
import { ButtonRow, FeesValue, FeeStrike, SponsoredText, ErrorContainer, ErrorTitle, ErrorMessage } from './styles.js';
|
|
18
21
|
|
|
19
22
|
const SOL_DECIMALS = 9;
|
|
20
23
|
const SolanaSendConfirmation = () => {
|
|
21
|
-
var _a, _b;
|
|
24
|
+
var _a, _b, _c;
|
|
22
25
|
const { sendForm, setRoute, publishableKey, triggerResize, walletConfig } = useOpenfort();
|
|
23
26
|
const wallet = useSolanaEmbeddedWallet();
|
|
24
27
|
const address = wallet.status === 'connected' ? wallet.address : undefined;
|
|
@@ -32,6 +35,15 @@ const SolanaSendConfirmation = () => {
|
|
|
32
35
|
const decimals = asset.type === 'spl' ? asset.metadata.decimals : SOL_DECIMALS;
|
|
33
36
|
// Fees are sponsored from config (the SVM counterpart of ethereumFeeSponsorshipId).
|
|
34
37
|
const isSponsored = Boolean((_b = walletConfig === null || walletConfig === void 0 ? void 0 : walletConfig.solana) === null || _b === void 0 ? void 0 : _b.sponsorFees);
|
|
38
|
+
// Real network fee from the RPC (getFeeForMessage). Null while loading or on failure.
|
|
39
|
+
const feeQuery = useAsyncData({
|
|
40
|
+
queryKey: ['sol-fee', address, recipient, rpcUrl],
|
|
41
|
+
queryFn: () => address && recipient && rpcUrl
|
|
42
|
+
? estimateSolanaTransferFeeLamports({ from: address, to: recipient, rpcUrl })
|
|
43
|
+
: Promise.resolve(null),
|
|
44
|
+
enabled: Boolean(address && recipient && rpcUrl),
|
|
45
|
+
});
|
|
46
|
+
const feeText = feeQuery.data != null ? `≈ ${formatBalance(feeQuery.data, SOL_DECIMALS)} SOL` : null;
|
|
35
47
|
const [isLoading, setIsLoading] = useState(false);
|
|
36
48
|
const [signature, setSignature] = useState(null);
|
|
37
49
|
const [error, setError] = useState(null);
|
|
@@ -114,7 +126,7 @@ const SolanaSendConfirmation = () => {
|
|
|
114
126
|
if (signature) {
|
|
115
127
|
return (jsxs(PageContent, { children: [jsx(Loader, { isSuccess: true, header: "Transfer sent", description: `${amount} ${symbol} sent successfully` }), jsxs(ButtonRow, { children: [jsx(Button, { variant: "primary", onClick: handleViewExplorer, children: "View on Explorer" }), jsx(Button, { variant: "secondary", onClick: handleFinish, children: "Back to profile" })] })] }));
|
|
116
128
|
}
|
|
117
|
-
return (jsxs(PageContent, { onBack: routes.SOL_SEND, children: [jsx(ModalHeading, { children: "Confirm transfer" }), jsx(ModalBody, { children: "Review the transaction before sending." }), jsx(ConfirmationSummary, { amount: amount || '0', symbol: symbol, to: recipient ? { display: truncateSolanaAddress(recipient), value: recipient } : undefined, networkName: `Solana ${cluster.charAt(0).toUpperCase()}${cluster.slice(1)}`, payWith: address ? { display: truncateSolanaAddress(address), value: address } : undefined, fee: isSponsored ?
|
|
129
|
+
return (jsxs(PageContent, { onBack: routes.SOL_SEND, children: [jsx(ModalHeading, { children: "Confirm transfer" }), jsx(ModalBody, { children: "Review the transaction before sending." }), jsx(ConfirmationSummary, { amount: amount || '0', symbol: symbol, to: recipient ? { display: truncateSolanaAddress(recipient), value: recipient } : undefined, networkName: `Solana ${cluster.charAt(0).toUpperCase()}${cluster.slice(1)}`, networkIcon: currencyLogoUrl('SOL') ? jsx("img", { src: (_c = currencyLogoUrl('SOL')) !== null && _c !== void 0 ? _c : '', alt: "" }) : undefined, balance: formatBalanceWithSymbol(asset.balance, decimals, symbol), payWith: address ? { display: truncateSolanaAddress(address), value: address } : undefined, fee: jsx(FeesValue, { children: isSponsored ? (jsxs(Fragment, { children: [feeText && jsx(FeeStrike, { children: feeText }), " ", jsx(SponsoredText, { children: "Sponsored" })] })) : ((feeText !== null && feeText !== void 0 ? feeText : '--')) }) }), error && (jsxs(ErrorContainer, { children: [jsx(ErrorTitle, { children: "Transaction failed" }), jsx(ErrorMessage, { children: error })] })), jsxs(ButtonRow, { children: [jsx(Button, { variant: "primary", onClick: handleConfirm, disabled: !address || isLoading, waiting: isLoading, children: isLoading ? 'Confirming...' : 'Confirm' }), jsx(Button, { variant: "secondary", onClick: () => setRoute(routes.SOL_SEND), disabled: isLoading, children: "Cancel" })] })] }));
|
|
118
130
|
};
|
|
119
131
|
|
|
120
132
|
export { SolanaSendConfirmation };
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"SolanaSendConfirmation.js","sources":[],"sourcesContent":[],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"SolanaSendConfirmation.js","sources":[],"sourcesContent":[],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;"}
|
|
@@ -3,6 +3,7 @@ import { ChainTypeEnum } from '@openfort/openfort-js';
|
|
|
3
3
|
import { useMemo, useEffect, useState, useRef } from 'react';
|
|
4
4
|
import { isAddress, createPublicClient, http, erc20Abi, parseUnits, encodeFunctionData } from 'viem';
|
|
5
5
|
import { TickIcon } from '../../../assets/icons.js';
|
|
6
|
+
import { chainLogoUrl } from '../../../constants/logos.js';
|
|
6
7
|
import { useEthereumEmbeddedWallet } from '../../../ethereum/hooks/useEthereumEmbeddedWallet.js';
|
|
7
8
|
import { useEthereumWalletAssets } from '../../../ethereum/hooks/useEthereumWalletAssets.js';
|
|
8
9
|
import { useBalance } from '../../../hooks/useBalance.js';
|
|
@@ -20,16 +21,16 @@ import { ModalHeading, ModalBody } from '../../Common/Modal/styles.js';
|
|
|
20
21
|
import { routes } from '../../Openfort/types.js';
|
|
21
22
|
import { useOpenfort } from '../../Openfort/useOpenfort.js';
|
|
22
23
|
import { PageContent } from '../../PageContent/index.js';
|
|
23
|
-
import { sanitizeForParsing, isSameToken, getAssetDecimals, getAssetSymbol } from '../Send/utils.js';
|
|
24
|
+
import { sanitizeForParsing, isSameToken, getAssetDecimals, getAssetSymbol, formatBalanceWithSymbol } from '../Send/utils.js';
|
|
24
25
|
import { ConfirmationSummary } from './ConfirmationSummary.js';
|
|
25
26
|
import { EstimatedFees } from './EstimatedFees.js';
|
|
26
|
-
import { ButtonRow,
|
|
27
|
+
import { ButtonRow, FeesValue, StatusMessage, ErrorContainer, ErrorTitle, ErrorMessage, ErrorAction } from './styles.js';
|
|
27
28
|
|
|
28
29
|
const SendConfirmation = () => {
|
|
29
|
-
var _a, _b, _c, _d, _e, _f;
|
|
30
|
+
var _a, _b, _c, _d, _e, _f, _g, _h, _j, _k;
|
|
30
31
|
const wallet = useEthereumEmbeddedWallet();
|
|
31
32
|
const { chainType } = useOpenfortCore();
|
|
32
|
-
const { sendForm, setRoute, triggerResize, walletConfig } = useOpenfort();
|
|
33
|
+
const { sendForm, setRoute, triggerResize, walletConfig, chains } = useOpenfort();
|
|
33
34
|
const address = wallet.status === 'connected' ? wallet.address : undefined;
|
|
34
35
|
const chainId = wallet.status === 'connected' ? wallet.chainId : undefined;
|
|
35
36
|
const blockExplorerUrl = chainId ? getExplorerUrl(ChainTypeEnum.EVM, { chainId }) : undefined;
|
|
@@ -316,12 +317,17 @@ const SendConfirmation = () => {
|
|
|
316
317
|
return null;
|
|
317
318
|
return `$${(n * perToken).toFixed(2)}`;
|
|
318
319
|
}, [(_f = (_e = token.metadata) === null || _e === void 0 ? void 0 : _e.fiat) === null || _f === void 0 ? void 0 : _f.value, normalisedAmount]);
|
|
320
|
+
// Prefer the configured chain's display name over the numeric id fallback.
|
|
321
|
+
const networkName = (_h = (_g = chains === null || chains === void 0 ? void 0 : chains.find((c) => c.id === chainId)) === null || _g === void 0 ? void 0 : _g.name) !== null && _h !== void 0 ? _h : getChainName(chainId !== null && chainId !== void 0 ? chainId : 0);
|
|
322
|
+
const balanceLabel = currentBalance !== undefined
|
|
323
|
+
? formatBalanceWithSymbol(currentBalance, (_j = getAssetDecimals(token)) !== null && _j !== void 0 ? _j : 18, getAssetSymbol(token))
|
|
324
|
+
: undefined;
|
|
319
325
|
if (isSuccess) {
|
|
320
326
|
const successAmount = normalisedAmount || '0';
|
|
321
327
|
const successSymbol = getAssetSymbol(token);
|
|
322
328
|
return (jsxs(PageContent, { children: [jsx(Loader, { isSuccess: true, header: "Transfer Sent", description: `${successAmount} ${successSymbol} sent successfully` }), jsxs(ButtonRow, { children: [blockExplorerUrl && (jsx(Button, { variant: "primary", onClick: handleOpenBlockExplorer, children: "View on Explorer" })), jsx(Button, { variant: "secondary", onClick: handleFinish, children: "Back to profile" })] })] }));
|
|
323
329
|
}
|
|
324
|
-
return (jsxs(PageContent, { children: [jsx(ModalHeading, { children: "Confirm transfer" }), jsx(ModalBody, { children: "Review the transaction before sending." }), jsx(ConfirmationSummary, { amount: normalisedAmount || '0', symbol: getAssetSymbol(token), fiat: fiatTotal, to: recipientAddress ? { display: truncateEthAddress(recipientAddress), value: recipientAddress } : undefined, networkName:
|
|
330
|
+
return (jsxs(PageContent, { children: [jsx(ModalHeading, { children: "Confirm transfer" }), jsx(ModalBody, { children: "Review the transaction before sending." }), jsx(ConfirmationSummary, { amount: normalisedAmount || '0', symbol: getAssetSymbol(token), fiat: fiatTotal, to: recipientAddress ? { display: truncateEthAddress(recipientAddress), value: recipientAddress } : undefined, networkName: networkName, networkIcon: chainLogoUrl(chainId) ? jsx("img", { src: (_k = chainLogoUrl(chainId)) !== null && _k !== void 0 ? _k : '', alt: "" }) : undefined, balance: balanceLabel, payWith: address ? { display: truncateEthAddress(address), value: address } : undefined, fee: jsx(FeesValue, { children: jsx(EstimatedFees, { account: address, to: token.type === 'erc20' ? token.address : recipientAddress, value: token.type === 'native' && parsedAmount ? parsedAmount : undefined, data: transferData, chainId: chainId, nativeSymbol: nativeSymbol, enabled: Boolean(address && recipientAddress && parsedAmount && parsedAmount > BigInt(0)), sponsored: isSponsored, hideInfoIcon: false }) }) }), insufficientBalance && !isSuccess && (jsx(StatusMessage, { "$status": "error", children: "Insufficient balance for this transfer." })), errorDetails && (jsxs(ErrorContainer, { children: [jsx(ErrorTitle, { children: errorDetails.title }), jsx(ErrorMessage, { children: errorDetails.message }), errorDetails.action && jsx(ErrorAction, { children: errorDetails.action })] })), jsxs(ButtonRow, { children: [jsx(Button, { variant: "primary", onClick: isSuccess ? handleOpenBlockExplorer : handleConfirm, disabled: isSuccess
|
|
325
331
|
? false
|
|
326
332
|
: isLoading ||
|
|
327
333
|
Boolean(transactionHash) ||
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sources":[],"sourcesContent":[],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"index.js","sources":[],"sourcesContent":[],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;"}
|
|
@@ -8,7 +8,9 @@ export declare const FeesValue: import("styled-components").StyledComponent<"spa
|
|
|
8
8
|
}, never>;
|
|
9
9
|
export declare const FiatValue: import("styled-components").StyledComponent<"span", any, {}, never>;
|
|
10
10
|
export declare const NetworkValue: import("styled-components").StyledComponent<"span", any, {}, never>;
|
|
11
|
-
|
|
11
|
+
/** The would-be fee, struck through, shown next to "Sponsored". */
|
|
12
|
+
export declare const FeeStrike: import("styled-components").StyledComponent<"span", any, {}, never>;
|
|
13
|
+
export declare const SponsoredText: import("styled-components").StyledComponent<"span", any, {}, never>;
|
|
12
14
|
export declare const PayWithCard: import("styled-components").StyledComponent<"div", any, {}, never>;
|
|
13
15
|
export declare const PayWithMeta: import("styled-components").StyledComponent<"div", any, {}, never>;
|
|
14
16
|
export declare const PayWithAddress: import("styled-components").StyledComponent<"span", any, {}, never>;
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import styled from '../../../styles/styled/index.js';
|
|
2
|
+
import { ButtonContainer } from '../../Common/Button/styles.js';
|
|
2
3
|
|
|
3
4
|
const SummaryList = styled.div `
|
|
4
5
|
display: flex;
|
|
@@ -64,8 +65,14 @@ const NetworkValue = styled(SummaryValue) `
|
|
|
64
65
|
border-radius: 50%;
|
|
65
66
|
}
|
|
66
67
|
`;
|
|
67
|
-
|
|
68
|
+
/** The would-be fee, struck through, shown next to "Sponsored". */
|
|
69
|
+
const FeeStrike = styled.span `
|
|
70
|
+
text-decoration: line-through;
|
|
71
|
+
opacity: 0.55;
|
|
72
|
+
`;
|
|
73
|
+
const SponsoredText = styled.span `
|
|
68
74
|
color: var(--ck-body-color-valid, #16a34a);
|
|
75
|
+
font-weight: 600;
|
|
69
76
|
`;
|
|
70
77
|
const PayWithCard = styled.div `
|
|
71
78
|
display: flex;
|
|
@@ -94,8 +101,8 @@ const PayWithBadge = styled.span `
|
|
|
94
101
|
border-radius: 999px;
|
|
95
102
|
font-size: 13px;
|
|
96
103
|
font-weight: 600;
|
|
97
|
-
color: var(--ck-body-color
|
|
98
|
-
background: var(--ck-body-background
|
|
104
|
+
color: var(--ck-body-color);
|
|
105
|
+
background: var(--ck-body-background);
|
|
99
106
|
`;
|
|
100
107
|
const InfoIconWrapper = styled.span `
|
|
101
108
|
color: var(--ck-body-color-muted);
|
|
@@ -115,9 +122,16 @@ const InfoIconWrapper = styled.span `
|
|
|
115
122
|
`;
|
|
116
123
|
const ButtonRow = styled.div `
|
|
117
124
|
display: flex;
|
|
118
|
-
|
|
119
|
-
gap: 4px;
|
|
125
|
+
gap: 12px;
|
|
120
126
|
margin-top: 24px;
|
|
127
|
+
|
|
128
|
+
> button {
|
|
129
|
+
flex: 1;
|
|
130
|
+
}
|
|
131
|
+
|
|
132
|
+
${ButtonContainer} {
|
|
133
|
+
margin: 0;
|
|
134
|
+
}
|
|
121
135
|
`;
|
|
122
136
|
const StatusMessage = styled.div `
|
|
123
137
|
margin-top: 16px;
|
|
@@ -157,5 +171,5 @@ const ErrorAction = styled.div `
|
|
|
157
171
|
line-height: 1.4;
|
|
158
172
|
`;
|
|
159
173
|
|
|
160
|
-
export { AddressValue, AmountValue, ButtonRow, ErrorAction, ErrorContainer, ErrorMessage, ErrorTitle, FeesValue, FiatValue, InfoIconWrapper, NetworkValue, PayWithAddress, PayWithBadge, PayWithCard, PayWithMeta,
|
|
174
|
+
export { AddressValue, AmountValue, ButtonRow, ErrorAction, ErrorContainer, ErrorMessage, ErrorTitle, FeeStrike, FeesValue, FiatValue, InfoIconWrapper, NetworkValue, PayWithAddress, PayWithBadge, PayWithCard, PayWithMeta, SponsoredText, StatusMessage, SummaryItem, SummaryLabel, SummaryList };
|
|
161
175
|
//# sourceMappingURL=styles.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"styles.js","sources":[],"sourcesContent":[],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"styles.js","sources":[],"sourcesContent":[],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;"}
|
|
@@ -1,11 +1,14 @@
|
|
|
1
1
|
import { jsx, jsxs, Fragment } from 'react/jsx-runtime';
|
|
2
|
+
import { ChainTypeEnum } from '@openfort/openfort-js';
|
|
2
3
|
import { useState, useRef, useEffect } from 'react';
|
|
3
4
|
import { useEthereumEmbeddedWallet } from '../../../ethereum/hooks/useEthereumEmbeddedWallet.js';
|
|
5
|
+
import { useOpenfortCore } from '../../../openfort/useOpenfort.js';
|
|
6
|
+
import { useSolanaEmbeddedWallet } from '../../../solana/hooks/useSolanaEmbeddedWallet.js';
|
|
4
7
|
import Button from '../../Common/Button/index.js';
|
|
5
8
|
import { CopyButton } from '../../Common/CopyToClipboard/CopyButton.js';
|
|
6
9
|
import { useOpenfort } from '../../Openfort/useOpenfort.js';
|
|
7
10
|
import { PageContent } from '../../PageContent/index.js';
|
|
8
|
-
import { SuccessWrap, SuccessCircle, SuccessTitle, SignaturePreview, SignContent, Subtitle, MessageBox, CopyRow, ErrorText, DataList, DataItem, DataKey } from './styles.js';
|
|
11
|
+
import { SuccessWrap, SuccessCircle, SuccessTitle, SignaturePreview, SignContent, Subtitle, MessageBox, Footer, CopyRow, ErrorText, DataList, DataItem, DataKey } from './styles.js';
|
|
9
12
|
|
|
10
13
|
/** Renders an EIP-712 value as a readable nested bullet list. */
|
|
11
14
|
function DataNode({ value }) {
|
|
@@ -17,17 +20,29 @@ function DataNode({ value }) {
|
|
|
17
20
|
const SignMessage = () => {
|
|
18
21
|
var _a;
|
|
19
22
|
const { signRequest, setSignRequest, setOpen, uiConfig, triggerResize } = useOpenfort();
|
|
23
|
+
const { chainType } = useOpenfortCore();
|
|
20
24
|
const wallet = useEthereumEmbeddedWallet();
|
|
25
|
+
const solana = useSolanaEmbeddedWallet();
|
|
21
26
|
const [signing, setSigning] = useState(false);
|
|
22
27
|
const [error, setError] = useState(null);
|
|
23
28
|
const [signature, setSignature] = useState(null);
|
|
24
29
|
const settledRef = useRef(false);
|
|
30
|
+
const mountedRef = useRef(false);
|
|
25
31
|
// Reject the pending request if the screen unmounts before signing (the user
|
|
26
|
-
// closed the modal or navigated away).
|
|
32
|
+
// closed the modal or navigated away). React StrictMode invokes effect cleanup
|
|
33
|
+
// on a dev-only synchronous remount, so defer the reject to a microtask: the
|
|
34
|
+
// immediate remount flips mountedRef back to true and cancels the spurious
|
|
35
|
+
// "User rejected" that would otherwise fire while the wallet UI is still open.
|
|
27
36
|
useEffect(() => {
|
|
37
|
+
mountedRef.current = true;
|
|
38
|
+
const request = signRequest;
|
|
28
39
|
return () => {
|
|
29
|
-
|
|
30
|
-
|
|
40
|
+
mountedRef.current = false;
|
|
41
|
+
queueMicrotask(() => {
|
|
42
|
+
if (!mountedRef.current && !settledRef.current) {
|
|
43
|
+
request === null || request === void 0 ? void 0 : request.reject(new Error('User rejected the signature request'));
|
|
44
|
+
}
|
|
45
|
+
});
|
|
31
46
|
};
|
|
32
47
|
}, [signRequest]);
|
|
33
48
|
// Content height changes between the views; re-measure.
|
|
@@ -46,16 +61,26 @@ const SignMessage = () => {
|
|
|
46
61
|
setError(null);
|
|
47
62
|
setSigning(true);
|
|
48
63
|
try {
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
64
|
+
let signed;
|
|
65
|
+
if (chainType === ChainTypeEnum.SVM) {
|
|
66
|
+
if (signRequest.kind !== 'message')
|
|
67
|
+
throw new Error('Typed data signing is not supported on Solana.');
|
|
68
|
+
if (solana.status !== 'connected')
|
|
69
|
+
throw new Error('No connected wallet to sign with');
|
|
70
|
+
signed = await solana.provider.signMessage(signRequest.message);
|
|
71
|
+
}
|
|
72
|
+
else {
|
|
73
|
+
const provider = await ((_a = wallet.activeWallet) === null || _a === void 0 ? void 0 : _a.getProvider());
|
|
74
|
+
const address = wallet.address;
|
|
75
|
+
if (!provider || !address)
|
|
76
|
+
throw new Error('No connected wallet to sign with');
|
|
77
|
+
signed = (signRequest.kind === 'message'
|
|
78
|
+
? await provider.request({ method: 'personal_sign', params: [signRequest.message, address] })
|
|
79
|
+
: await provider.request({
|
|
80
|
+
method: 'eth_signTypedData_v4',
|
|
81
|
+
params: [address, JSON.stringify(signRequest.typedData)],
|
|
82
|
+
}));
|
|
83
|
+
}
|
|
59
84
|
settledRef.current = true;
|
|
60
85
|
signRequest.resolve(signed);
|
|
61
86
|
setSignature(signed);
|
|
@@ -70,11 +95,11 @@ const SignMessage = () => {
|
|
|
70
95
|
if (signature) {
|
|
71
96
|
return (jsx(PageContent, { onBack: null, children: jsxs(SuccessWrap, { children: [jsx(SuccessCircle, { children: jsx("svg", { width: "28", height: "28", viewBox: "0 0 24 24", fill: "none", "aria-hidden": "true", children: jsx("path", { d: "M20 6 9 17l-5-5", stroke: "currentColor", strokeWidth: "2.5", strokeLinecap: "round", strokeLinejoin: "round" }) }) }), jsx(SuccessTitle, { children: "Message signed" }), jsx(SignaturePreview, { children: `${signature.slice(0, 14)}…${signature.slice(-12)}` }), jsx(Button, { variant: "primary", onClick: close, children: "Done" })] }) }));
|
|
72
97
|
}
|
|
73
|
-
return (jsx(PageContent, { onBack: null, children: jsxs(SignContent, { children: [jsxs(Subtitle, { children: [appName, " wants you to sign a message. It will not cost you any fees."] }), signRequest.kind === 'message' ? (jsx(MessageBox, { children: signRequest.message })) : (
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
98
|
+
return (jsx(PageContent, { onBack: null, children: jsxs(SignContent, { children: [jsxs(Subtitle, { children: [appName, " wants you to sign a message. It will not cost you any fees."] }), signRequest.kind === 'message' ? (jsx(MessageBox, { children: signRequest.message })) : (jsx(MessageBox, { children: jsx(DataNode, { value: {
|
|
99
|
+
domain: signRequest.typedData.domain,
|
|
100
|
+
primaryType: signRequest.typedData.primaryType,
|
|
101
|
+
message: signRequest.typedData.message,
|
|
102
|
+
} }) })), jsxs(Footer, { children: [signRequest.kind === 'typedData' && (jsx(CopyRow, { children: jsx(CopyButton, { value: JSON.stringify(signRequest.typedData, null, 2), children: "Copy to clipboard" }) })), error && jsx(ErrorText, { children: error }), jsx(Button, { variant: "primary", onClick: handleSign, waiting: signing, disabled: signing, arrow: true, children: "Sign and continue" })] })] }) }));
|
|
78
103
|
};
|
|
79
104
|
|
|
80
105
|
export { SignMessage as default };
|