-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathuse-repay.ts
More file actions
109 lines (94 loc) · 3.15 KB
/
use-repay.ts
File metadata and controls
109 lines (94 loc) · 3.15 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
import invariant from 'tiny-invariant';
import { useCallback } from 'react';
import {
useVault,
vaultTexts,
GoToVault,
useReportCalls,
} from 'modules/vaults';
import {
TransactionEntry,
useLidoSDK,
useSendTransaction,
withSuccess,
} from 'modules/web3';
import { useLiability } from './use-liability';
import type { RepayFormValidatedValues } from '../types';
export const useRepay = () => {
const { activeVault } = useVault();
const { stETH, wstETH, shares } = useLidoSDK();
const { data } = useLiability();
const { sendTX, ...rest } = useSendTransaction();
const prepareReportCalls = useReportCalls();
const { liabilityShares } = data ?? {};
return {
burn: useCallback(
async ({ amount, token }: RepayFormValidatedValues) => {
invariant(activeVault, '[useRepay] activeVault is undefined');
invariant(liabilityShares, '[useRepay] liabilityShares is undefined');
const loadingActionText = vaultTexts.actions.repay.loading(token);
const mainActionCompleteText =
vaultTexts.actions.repay.completed(token);
const prepareTransactions = async () => {
const calls: TransactionEntry[] = [...prepareReportCalls()];
const isSteth = token === 'stETH';
const tokenContract = isSteth ? stETH : wstETH;
let txAmount = amount;
if (isSteth) {
const sharesAmount = await shares.convertToShares(amount);
// Corner case when a user burns max stETH amount and conversion can return 1 wei less
// liabilityShares => stETH for repay form (with round up), max stETH => sharesAmount
txAmount =
liabilityShares - sharesAmount === 1n
? liabilityShares
: sharesAmount;
}
const allowance = await tokenContract.allowance({
to: activeVault.dashboard.address,
});
const txAmountAllowance = isSteth
? await shares.convertToSteth(txAmount)
: amount;
const needsAllowance = allowance < txAmountAllowance;
if (needsAllowance) {
const approveCall = {
...(await tokenContract.populateApprove({
amount: txAmountAllowance,
to: activeVault.dashboard.address,
})),
loadingActionText: vaultTexts.actions.approve.loading(token),
};
calls.push(approveCall);
}
calls.push({
...activeVault.dashboard.encode[
isSteth ? 'burnShares' : 'burnWstETH'
]([txAmount]),
loadingActionText,
});
return calls;
};
const { success } = await withSuccess(
sendTX({
transactions: prepareTransactions,
forceAtomic: true,
mainActionLoadingText: loadingActionText,
mainActionCompleteText,
renderSuccessContent: GoToVault,
}),
);
return success;
},
[
activeVault,
prepareReportCalls,
sendTX,
stETH,
wstETH,
liabilityShares,
shares,
],
),
...rest,
};
};