Skip to content

Commit 2baab59

Browse files
authored
feat: backstop contract reroute
Merge pull request #195 from Neko-Protocol/chore/backstop-contract-reroute
2 parents 0d97b97 + ee0c39a commit 2baab59

File tree

13 files changed

+674
-158
lines changed

13 files changed

+674
-158
lines changed

apps/web-app/package.json

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@
1616
"@hookform/resolvers": "^5.2.2",
1717
"@mui/icons-material": "^5.15.0",
1818
"@mui/material": "^5.15.0",
19+
"@neko/backstop": "0.0.0",
1920
"@neko/config": "0.0.0",
2021
"@neko/defindex-vault": "0.0.0",
2122
"@neko/lending": "0.0.0",

apps/web-app/src/features/backstop/components/ui/BackstopActionPanel.tsx

Lines changed: 27 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,8 @@ interface BackstopActionPanelProps {
99
isLoading: boolean;
1010
walletBalance: string;
1111
depositedAmount: string;
12+
activeDepositAmount: string;
13+
queuedDepositAmount: string;
1214
hasWallet: boolean;
1315
backstopTokenConfigured: boolean;
1416
inWithdrawalQueue: boolean;
@@ -22,6 +24,8 @@ export function BackstopActionPanel({
2224
isLoading,
2325
walletBalance,
2426
depositedAmount,
27+
activeDepositAmount,
28+
queuedDepositAmount,
2529
hasWallet,
2630
backstopTokenConfigured,
2731
inWithdrawalQueue,
@@ -35,6 +39,7 @@ export function BackstopActionPanel({
3539
const [withdrawAmount, setWithdrawAmount] = useState("");
3640

3741
const hasDeposit = parseFloat(depositedAmount) > 0;
42+
const hasActiveDeposit = parseFloat(activeDepositAmount) > 0;
3843

3944
const canDeposit =
4045
hasWallet &&
@@ -45,8 +50,7 @@ export function BackstopActionPanel({
4550

4651
const canQueue =
4752
hasWallet &&
48-
hasDeposit &&
49-
!inWithdrawalQueue &&
53+
hasActiveDeposit &&
5054
!!withdrawAmount &&
5155
parseFloat(withdrawAmount) > 0 &&
5256
!isLoading;
@@ -145,7 +149,7 @@ export function BackstopActionPanel({
145149
{/* Withdraw */}
146150
{activeTab === "withdraw" && (
147151
<div className="flex flex-col gap-4">
148-
{!inWithdrawalQueue ? (
152+
{hasActiveDeposit && (
149153
<>
150154
<BackstopInfoAlert variant="warning">
151155
To withdraw, you must first queue your withdrawal and wait{" "}
@@ -157,13 +161,13 @@ export function BackstopActionPanel({
157161
<span className="text-white/50 text-sm font-medium">
158162
Amount to queue
159163
</span>
160-
{parseFloat(depositedAmount) > 0 && (
164+
{parseFloat(activeDepositAmount) > 0 && (
161165
<button
162-
onClick={() => setWithdrawAmount(depositedAmount)}
166+
onClick={() => setWithdrawAmount(activeDepositAmount)}
163167
disabled={isLoading}
164168
className="text-[#229EDF] text-xs font-semibold hover:text-[#229EDF]/70 transition-colors disabled:opacity-40"
165169
>
166-
Max: {parseFloat(depositedAmount).toFixed(4)}
170+
Max: {parseFloat(activeDepositAmount).toFixed(4)}
167171
</button>
168172
)}
169173
</div>
@@ -180,9 +184,9 @@ export function BackstopActionPanel({
180184
</div>
181185

182186
<div className="bg-[#252525] rounded-xl p-3.5">
183-
<p className="text-white/40 text-xs">Deposited balance</p>
187+
<p className="text-white/40 text-xs">Available to queue</p>
184188
<p className="text-white font-bold text-sm mt-0.5">
185-
{depositedAmount}
189+
{activeDepositAmount}
186190
</p>
187191
</div>
188192

@@ -198,18 +202,24 @@ export function BackstopActionPanel({
198202
{isLoading ? "Processing…" : "Queue Withdrawal (17-day wait)"}
199203
</button>
200204
</>
201-
) : (
205+
)}
206+
207+
{inWithdrawalQueue && (
202208
<>
209+
{hasActiveDeposit && (
210+
<div className="border-t border-white/5 my-1" />
211+
)}
212+
203213
<div className="bg-[#252525] rounded-xl p-3.5">
204214
<p className="text-white/40 text-xs">Amount queued</p>
205215
<p className="text-white font-bold text-sm mt-0.5">
206-
{depositedAmount}
216+
{queuedDepositAmount}
207217
</p>
208218
</div>
209219

210220
<button
211221
onClick={() =>
212-
void onWithdraw(depositedAmount).then(() =>
222+
void onWithdraw(queuedDepositAmount).then(() =>
213223
setWithdrawAmount("")
214224
)
215225
}
@@ -224,6 +234,12 @@ export function BackstopActionPanel({
224234
</button>
225235
</>
226236
)}
237+
238+
{!hasActiveDeposit && !inWithdrawalQueue && (
239+
<BackstopInfoAlert variant="info">
240+
No active deposit to withdraw.
241+
</BackstopInfoAlert>
242+
)}
227243
</div>
228244
)}
229245
</div>

apps/web-app/src/features/backstop/hooks/useBackstop.ts

Lines changed: 17 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,6 @@ import { fromSmallestUnit } from "@/lib/helpers/tokenUtils";
2121
import { rpcUrl, stellarNetwork } from "@/lib/config/stellar.config";
2222

2323
const WITHDRAWAL_QUEUE_DAYS = 17;
24-
const WITHDRAWAL_QUEUE_SECONDS = BigInt(WITHDRAWAL_QUEUE_DAYS * 24 * 60 * 60);
2524

2625
export function useBackstop(contractId: string) {
2726
const [isLoading, setIsLoading] = useState(false);
@@ -108,7 +107,7 @@ export function useBackstop(contractId: string) {
108107
allowHttp: stellarNetwork === "LOCAL",
109108
});
110109

111-
// Approve backstop token to the lending contract first (if token is configured)
110+
// Approve backstop token to the backstop contract first (if token is configured)
112111
if (backstopTokenAddress) {
113112
const approveXdr = await approveToken(
114113
backstopTokenAddress,
@@ -259,21 +258,32 @@ export function useBackstop(contractId: string) {
259258
]
260259
);
261260

262-
// Derive queue expiry info
261+
// Derive queue expiry info — queuedAt now holds the expiration timestamp
262+
// directly from the backstop contract's Q4W.exp field.
263263
const queueExpiresAt: Date | null =
264264
depositInfo?.inWithdrawalQueue && depositInfo.queuedAt
265-
? new Date(Number(depositInfo.queuedAt + WITHDRAWAL_QUEUE_SECONDS) * 1000)
265+
? new Date(Number(depositInfo.queuedAt) * 1000)
266266
: null;
267267

268268
const queueExpired = queueExpiresAt !== null && new Date() >= queueExpiresAt;
269269

270+
const depositedAmount = depositInfo
271+
? fromSmallestUnit(depositInfo.amount.toString(), 7)
272+
: "0";
273+
const activeDepositAmount = depositInfo
274+
? fromSmallestUnit(depositInfo.activeAmount.toString(), 7)
275+
: "0";
276+
const queuedDepositAmount = depositInfo
277+
? fromSmallestUnit(depositInfo.queuedAmount.toString(), 7)
278+
: "0";
279+
270280
return {
271281
isLoading,
272282
walletBalance: walletBalance ?? "0",
273283
isLoadingWalletBalance,
274-
depositedAmount: depositInfo
275-
? fromSmallestUnit(depositInfo.amount.toString(), 7)
276-
: "0",
284+
depositedAmount,
285+
activeDepositAmount,
286+
queuedDepositAmount,
277287
isLoadingDeposit,
278288
inWithdrawalQueue: depositInfo?.inWithdrawalQueue ?? false,
279289
queueExpiresAt,

apps/web-app/src/features/lending/components/ui/BackstopPanel.tsx

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -3,20 +3,20 @@
33
import { useState } from "react";
44
import { Shield, RefreshCw } from "lucide-react";
55
import { useBackstop } from "@/features/backstop/hooks/useBackstop";
6-
import { networks } from "@neko/lending";
6+
import { networks as backstopNetworks } from "@neko/backstop";
77
import { BackstopQueueStatus } from "@/features/backstop/components/ui/BackstopQueueStatus";
88
import { BackstopActionPanel } from "@/features/backstop/components/ui/BackstopActionPanel";
99
import { BackstopInfoAlert } from "@/features/backstop/components/ui/BackstopInfoAlert";
1010

1111
const POOLS = [
1212
{
1313
label: "Crypto Pool",
14-
contractId: networks.testnet.pool1ContractId,
14+
contractId: backstopNetworks.testnet.pool1ContractId,
1515
assets: "USDC · XLM",
1616
},
1717
{
1818
label: "RWA Pool",
19-
contractId: networks.testnet.pool2ContractId,
19+
contractId: backstopNetworks.testnet.pool2ContractId,
2020
assets: "USTRY · CETES · USDY · PYUSD · KTB",
2121
},
2222
];
@@ -30,6 +30,8 @@ export function BackstopPanel() {
3030
walletBalance,
3131
isLoadingWalletBalance,
3232
depositedAmount,
33+
activeDepositAmount,
34+
queuedDepositAmount,
3335
isLoadingDeposit,
3436
inWithdrawalQueue,
3537
queueExpiresAt,
@@ -133,6 +135,8 @@ export function BackstopPanel() {
133135
isLoading={isLoading}
134136
walletBalance={walletBalance}
135137
depositedAmount={depositedAmount}
138+
activeDepositAmount={activeDepositAmount}
139+
queuedDepositAmount={queuedDepositAmount}
136140
hasWallet={hasWallet}
137141
backstopTokenConfigured={backstopTokenConfigured}
138142
inWithdrawalQueue={inWithdrawalQueue}

apps/web-app/src/lib/constants/contracts.ts

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,3 +19,9 @@ export const LENDING_POOL2_CONTRACT_ID =
1919

2020
export const ORACLE_CONTRACT_ID =
2121
"CCFWASXOQJVJR5WVHRQPQTLCZC3SCBAL2Z67YY4JJAO5GLJLJABQT47I";
22+
23+
export const BACKSTOP_CONTRACT_ID =
24+
"CDTFRINWJOMLGYS64N7JICGNBCFKKSPJBNMI7FHTDOHZQ2RAKTJEXCRO";
25+
26+
export const BACKSTOP_POOL2_CONTRACT_ID =
27+
"CARYWBLZCXSSZSSGL2VRVDS57P7KIV7NOBESGBR3SKQXDIFDDZRRFHQ6";

0 commit comments

Comments
 (0)