diff --git a/src/app/components/mint-unmint/components/mint/mint.tsx b/src/app/components/mint-unmint/components/mint/mint.tsx index d8ffe594..3f819369 100644 --- a/src/app/components/mint-unmint/components/mint/mint.tsx +++ b/src/app/components/mint-unmint/components/mint/mint.tsx @@ -1,17 +1,24 @@ import { HStack } from "@chakra-ui/react"; import { RootState } from "@store/index"; -import { useSelector } from "react-redux"; +import { useDispatch, useSelector } from "react-redux"; import { LockScreen } from "../lock-screen/lock-screen"; import { ProgressTimeline } from "../progress-timeline/progress-timeline"; import { TransactionForm } from "../transaction-form/transaction-form"; import { TransactionSummary } from "../transaction-summary/transaction-summary"; import { Walkthrough } from "../walkthrough/walkthrough"; import { MintLayout } from "./components/mint.layout"; +import { StepButton } from "@components/step-button/step-button"; +import { mintUnmintActions } from "@store/slices/mintunmint/mintunmint.actions"; export function Mint(): React.JSX.Element { + const dispatch = useDispatch(); const { mintStep } = useSelector((state: RootState) => state.mintunmint); + function handleRestart() { + dispatch(mintUnmintActions.setMintStep(0)); + } + return ( @@ -19,10 +26,15 @@ export function Mint(): React.JSX.Element { {[0].includes(mintStep) && } {[1].includes(mintStep) && } - {[2].includes(mintStep) && ( - + {[2, 3].includes(mintStep) && ( + )} + ); } diff --git a/src/app/components/mint-unmint/components/transaction-summary/transaction-summary.tsx b/src/app/components/mint-unmint/components/transaction-summary/transaction-summary.tsx index ccbbdd4c..9c8551c5 100644 --- a/src/app/components/mint-unmint/components/transaction-summary/transaction-summary.tsx +++ b/src/app/components/mint-unmint/components/transaction-summary/transaction-summary.tsx @@ -1,46 +1,90 @@ +import { useEffect, useState } from "react"; import { useNavigate } from "react-router-dom"; import { HStack, Link, Spinner, Stack, Text, VStack } from "@chakra-ui/react"; import { VaultCard } from "@components/vault/vault-card"; - import { useVaults } from "@hooks/use-vaults"; +import { Vault } from "@models/vault"; + import { TransactionSummaryPreviewCard } from "./components/transaction-summary-preview-card"; -const flowPropertyMap = { +interface FlowPropertyMap { + [key: string]: { + [key: number]: { + title: string; + subtitle: string; + }; + }; +} + +const flowPropertyMap: FlowPropertyMap = { mint: { - title: "Locking BTC in progress", - subtitle: "Minting dlcBTC", + 2: { title: "a) Locking BTC in progress", subtitle: "Minting dlcBTC" }, + 3: { title: "Minted dlcBTC", subtitle: "Minting dlcBTC" }, }, unmint: { - title: "Unmint in progress", - subtitle: "Your BTC is being unlocked", + 1: { + title: "a) Closing vault in progress", + subtitle: "Your BTC is being unlocked", + }, + 2: { title: "Vault closed", subtitle: "Your BTC is unlocked" }, }, }; interface TransactionSummaryProps { + currentStep: number; flow: "mint" | "unmint"; blockchain: "ethereum" | "bitcoin"; } export function TransactionSummary({ + currentStep, flow, blockchain, }: TransactionSummaryProps): React.JSX.Element { const navigate = useNavigate(); - const { fundingVaults } = useVaults(); + const { fundingVaults, fundedVaults, closingVaults, closedVaults } = + useVaults(); + const [currentVault, setCurrentVault] = useState( + getVault(flow, currentStep), + ); + + function getVault(flow: "mint" | "unmint", currentStep: number) { + if (flow === "mint") { + return currentStep === 2 ? fundingVaults[0] : fundedVaults[0]; + } else { + return currentStep === 1 ? closingVaults[0] : closedVaults[0]; + } + } + + useEffect(() => { + setCurrentVault(getVault(flow, currentStep)); + }, [flow, currentStep]); return ( - - a) {flowPropertyMap[flow].title}: + {(flow === "mint" && currentStep === 2) || + (flow === "unmint" && currentStep === 1 && ( + + ))} + + {flowPropertyMap[flow][currentStep].title}: + - - b) {flowPropertyMap[flow].subtitle}: - + + {(flow === "mint" && currentStep === 2) || + (flow === "unmint" && currentStep === 1) ? ( + <> + + b) {flowPropertyMap[flow][currentStep].subtitle}: + + + + ) : null} ( undefined, ); + const [isSubmitting, setIsSubmitting] = useState(false); const { fundedVaults } = useVaults(); + const blockchainContext = useContext(BlockchainContext); + const ethereum = blockchainContext?.ethereum; function handleSelect(uuid: string): void { const vault = fundedVaults.find((vault) => vault.uuid === uuid); if (vault) setSelectedVault(vault); } + async function handleUnmint(): Promise { + if (selectedVault) { + try { + setIsSubmitting(true); + await ethereum?.closeVault(selectedVault.uuid); + } catch (error) { + setIsSubmitting(false); + throw new Error("Error closing vault"); + } + } + } + return ( )} diff --git a/src/app/components/mint-unmint/components/unmint/unmint.tsx b/src/app/components/mint-unmint/components/unmint/unmint.tsx index ca08b984..21e072ed 100644 --- a/src/app/components/mint-unmint/components/unmint/unmint.tsx +++ b/src/app/components/mint-unmint/components/unmint/unmint.tsx @@ -1,11 +1,9 @@ -import { useState } from "react"; - import { HStack } from "@chakra-ui/react"; import { StepButton } from "@components/step-button/step-button"; -import { VaultState } from "@models/vault"; - -import { exampleVaults } from "@shared/examples/example-vaults"; +import { RootState } from "@store/index"; +import { mintUnmintActions } from "@store/slices/mintunmint/mintunmint.actions"; +import { useDispatch, useSelector } from "react-redux"; import { ProgressTimeline } from "../progress-timeline/progress-timeline"; import { TransactionSummary } from "../transaction-summary/transaction-summary"; import { Walkthrough } from "../walkthrough/walkthrough"; @@ -13,29 +11,28 @@ import { UnmintVaultSelector } from "./components/unmint-vault-selector"; import { UnmintLayout } from "./components/unmint.layout"; export function Unmint(): React.JSX.Element { - const [currentStep, setCurrentStep] = useState(0); - const exampleVault = exampleVaults.find( - (vault) => vault.state === VaultState.CLOSING, - ); + const dispatch = useDispatch(); + const { unmintStep } = useSelector((state: RootState) => state.mintunmint); + + function handleRestart() { + dispatch(mintUnmintActions.setUnmintStep(0)); + } return ( - + - - {[0].includes(currentStep) && } - {[1].includes(currentStep) && ( + + {[0].includes(unmintStep) && } + {[1, 2].includes(unmintStep) && ( )} - setCurrentStep((currentStep + 1) % 2)} /> + ); } diff --git a/src/app/components/mint-unmint/components/walkthrough/components/walkthrough-header.tsx b/src/app/components/mint-unmint/components/walkthrough/components/walkthrough-header.tsx index 8de2a4b2..9124f88d 100644 --- a/src/app/components/mint-unmint/components/walkthrough/components/walkthrough-header.tsx +++ b/src/app/components/mint-unmint/components/walkthrough/components/walkthrough-header.tsx @@ -4,7 +4,7 @@ import { WalkthroughBlockchainTag } from "./walkthrough-blockchain-tag"; interface WalkthroughHeaderProps { blockchain: "ethereum" | "bitcoin"; - currentStep: number; + currentStep?: number; title: string; } @@ -16,9 +16,11 @@ export function WalkthroughHeader({ return ( - - Step {currentStep + 1} - + {currentStep && ( + + Step {currentStep + 1} + + )} diff --git a/src/app/components/mint-unmint/components/walkthrough/walkthrough.tsx b/src/app/components/mint-unmint/components/walkthrough/walkthrough.tsx index 6eb734b3..ca117250 100644 --- a/src/app/components/mint-unmint/components/walkthrough/walkthrough.tsx +++ b/src/app/components/mint-unmint/components/walkthrough/walkthrough.tsx @@ -7,13 +7,11 @@ import { WalkthroughLayout } from "./components/walkthrough.layout"; interface WalkthroughProps { flow: "mint" | "unmint"; currentStep: number; - bitcoinAmount?: number; } export function Walkthrough({ flow, currentStep, - bitcoinAmount, }: WalkthroughProps): React.JSX.Element { switch (flow) { case "mint": @@ -108,7 +106,25 @@ export function Walkthrough({ ); default: - return <>; + return ( + + + + + ); } case "unmint": switch (currentStep) { @@ -138,14 +154,20 @@ export function Walkthrough({ After a successful unmint ( ~1 hour) your - will receive{" "} - {bitcoinAmount}BTC in - your bitcoin wallet. + will receive BTC in your bitcoin wallet. ); default: - return <>; + return ( + + + + ); } } } diff --git a/src/app/components/step-button/step-button.tsx b/src/app/components/step-button/step-button.tsx index 699d044c..df6c5afd 100644 --- a/src/app/components/step-button/step-button.tsx +++ b/src/app/components/step-button/step-button.tsx @@ -3,6 +3,7 @@ import { Button } from "@chakra-ui/react"; interface StepButtonProps { handleClick: () => void; } + export function StepButton({ handleClick, }: StepButtonProps): React.JSX.Element { @@ -10,13 +11,13 @@ export function StepButton({ ); } diff --git a/src/app/components/vault/components/vault-expanded-information/components/vault-expanded-information-transaction-row.tsx b/src/app/components/vault/components/vault-expanded-information/components/vault-expanded-information-transaction-row.tsx index 2a57089e..a2e6728b 100644 --- a/src/app/components/vault/components/vault-expanded-information/components/vault-expanded-information-transaction-row.tsx +++ b/src/app/components/vault/components/vault-expanded-information/components/vault-expanded-information-transaction-row.tsx @@ -20,7 +20,9 @@ export function VaultExpandedInformationTransactionRow({ color={"accent.cyan.01"} fontSize={"xs"} textDecoration={"underline"} - onClick={() => window.open(value, "_blank")} + onClick={() => + window.open(`http://stx-btc1.dlc.link:8001/tx/${value}`, "_blank") + } _hover={{ cursor: "pointer" }} > View in TX explorer diff --git a/src/app/hooks/use-bitcoin.ts b/src/app/hooks/use-bitcoin.ts index 09136e55..27eb115c 100644 --- a/src/app/hooks/use-bitcoin.ts +++ b/src/app/hooks/use-bitcoin.ts @@ -1,22 +1,20 @@ // import { Dispatch } from 'react'; +import { useDispatch } from "react-redux"; import { Vault } from "@models/vault"; - -import { UseEthereumReturn } from "./use-ethereum"; +import { vaultActions } from "@store/slices/vault/vault.actions"; +import { mintUnmintActions } from "@store/slices/mintunmint/mintunmint.actions"; export interface UseBitcoinReturn { fetchBitcoinContractOfferAndSendToUserWallet: (vault: Vault) => Promise; } -export function useBitcoin( - ethereum: UseEthereumReturn, -): UseBitcoinReturn { +export function useBitcoin(): UseBitcoinReturn { // const { getVault } = ethereum; + const dispatch = useDispatch(); const routerWalletURL = "https://devnet.dlc.link/okx-wallet"; function createURLParams(bitcoinContractOffer: any) { - const routerWalletURL = ethereum.getEthereumNetworkConfig().walletURL; - if (!routerWalletURL) { console.error("Wallet type or blockchain not supported"); } @@ -29,19 +27,26 @@ export function useBitcoin( }; const urlParams = { bitcoinContractOffer: JSON.stringify(bitcoinContractOffer), - bitcoinNetwork: JSON.stringify(process.env.REACT_APP_BITCOIN_NETWORK), + bitcoinNetwork: JSON.stringify("regtest"), counterpartyWalletDetails: JSON.stringify(counterPartyWalletDetails), }; return urlParams; } - async function sendOfferForSigning(urlParams: any) { + async function sendOfferForSigning(urlParams: any, vaultUUID: string) { try { const response = await window.btc.request( "acceptBitcoinContractOffer", urlParams, ); - console.log(response); + console.log("response", response); + dispatch( + vaultActions.setVaultToFunding({ + vaultUUID, + fundingTX: response.result.txId, + }), + ); + dispatch(mintUnmintActions.setMintStep(2)); } catch (error) { console.error(`Could not send contract offer for signing: ${error}`); } @@ -73,8 +78,7 @@ export function useBitcoin( await fetchBitcoinContractOfferFromCounterpartyWallet(vault); if (!bitcoinContractOffer) return; const urlParams = createURLParams(bitcoinContractOffer); - console.log(urlParams); - await sendOfferForSigning(urlParams); + await sendOfferForSigning(urlParams, vault.uuid); } return { diff --git a/src/app/hooks/use-ethereum.ts b/src/app/hooks/use-ethereum.ts index 479f46fc..1ccf4381 100644 --- a/src/app/hooks/use-ethereum.ts +++ b/src/app/hooks/use-ethereum.ts @@ -50,7 +50,16 @@ export function useEthereum(): UseEthereumReturn { ); useEffect(() => { - if (!address) return; + if (!address || !network) return; + + if (!protocolContract || !dlcManagerContract || !dlcBTCContract) { + setupEthereumConfiguration(network); + } + }, [address, network]); + + useEffect(() => { + if (!address || !protocolContract || !dlcManagerContract || !dlcBTCContract) + return; const fetchBalance = async () => { try { @@ -62,15 +71,15 @@ export function useEthereum(): UseEthereumReturn { }; fetchBalance(); - }, [address, fundedVaults, getDLCBTCBalance, getLockedBTCBalance]); + }, [address, fundedVaults]); function formatVault(vault: any): Vault { return { uuid: vault.uuid, collateral: customShiftValue(parseInt(vault.valueLocked), 8, true), state: vault.status, - fundingTX: vault.fundingTransaction, - closingTX: vault.closingTransaction, + fundingTX: vault.fundingTxId, + closingTX: vault.closingTxId, timestamp: parseInt(vault.timestamp), }; } @@ -241,6 +250,7 @@ export function useEthereum(): UseEthereumReturn { throw new Error("Protocol contract not initialized"); const vaults: RawVault[] = await protocolContract.getAllVaultsForAddress(address); + console.log("vaults", vaults); const formattedVaults: Vault[] = vaults.map(formatVault); store.dispatch(vaultActions.setVaults(formattedVaults)); } catch (error) { diff --git a/src/app/hooks/use-observer.ts b/src/app/hooks/use-observer.ts index 00b0cba7..ddcd9ab0 100644 --- a/src/app/hooks/use-observer.ts +++ b/src/app/hooks/use-observer.ts @@ -1,31 +1,84 @@ +import { Dispatch, useEffect } from "react"; import { useSelector } from "react-redux"; import { RootState } from "@store/index"; import { mintUnmintActions } from "@store/slices/mintunmint/mintunmint.actions"; - -import { Dispatch } from "react"; import { AnyAction } from "redux"; + import { UseEthereumReturn } from "./use-ethereum"; export function useObserver( ethereum: UseEthereumReturn, dispatch: Dispatch, ) { - const { network } = useSelector((state: RootState) => state.account); + const { address, network } = useSelector((state: RootState) => state.account); const { protocolContract, dlcBTCContract, getVault } = ethereum; - if (!protocolContract || !dlcBTCContract) return; + useEffect(() => { + if (!protocolContract || !dlcBTCContract) return; + + console.log(`Listening to [${network?.name}]`); + console.log(`Listening to [${protocolContract.address}]`); + console.log(`Listening to [${dlcBTCContract.address}]`); + + protocolContract.on("SetupVault", async (...args) => { + console.log("SetupVault", args); + const vaultOwner: string = args[2]; + + if (vaultOwner.toLowerCase() !== address) return; + + const vaultUUID = args[0]; + + console.log(`Vault ${vaultUUID} is ready`); + + await getVault(vaultUUID).then(() => { + dispatch(mintUnmintActions.setMintStep(1)); + }); + }); + + protocolContract.on("CloseVault", async (...args) => { + console.log("CloseVault", args); + const vaultOwner: string = args[2]; + + if (vaultOwner.toLowerCase() !== address) return; + + const vaultUUID = args[0]; + + console.log(`Vault ${vaultUUID} is closing`); + + await getVault(vaultUUID).then(() => { + dispatch(mintUnmintActions.setUnmintStep(1)); + }); + }); + + protocolContract.on("SetStatusFunded", async (...args) => { + console.log("SetStatusFunded", args); + const vaultOwner = args[2]; + + if (vaultOwner.toLowerCase() !== address) return; + + const vaultUUID = args[0]; + + console.log(`Vault ${vaultUUID} is minted`); + + await getVault(vaultUUID).then(() => { + dispatch(mintUnmintActions.setMintStep(3)); + }); + }); + + protocolContract.on("PostCloseDLCHandler", async (...args) => { + console.log("PostCloseDLCHandler", args); + const vaultOwner = args[2]; + + if (vaultOwner.toLowerCase() !== address) return; + + const vaultUUID = args[0]; - console.log(`Listening to [${network?.name}]`); - console.log(`Listening to [${protocolContract.address}]`); - console.log(`Listening to [${dlcBTCContract.address}]`); + console.log(`Vault ${vaultUUID} is minted`); - protocolContract.on("SetupVault", async (...args) => { - const vaultUUID = args[0]; - const vaultTXHash = args[args.length - 1].transactionHash; - console.log(`Vault ${vaultUUID} is ready with TX ${vaultTXHash}`); - await getVault(vaultUUID).then(() => { - dispatch(mintUnmintActions.setMintStep(1)); + await getVault(vaultUUID).then(() => { + dispatch(mintUnmintActions.setUnmintStep(2)); + }); }); - }); + }, [protocolContract, dlcBTCContract, network]); } diff --git a/src/app/providers/blockchain-context-provider.tsx b/src/app/providers/blockchain-context-provider.tsx index d6a73dd6..e9396fab 100644 --- a/src/app/providers/blockchain-context-provider.tsx +++ b/src/app/providers/blockchain-context-provider.tsx @@ -21,7 +21,7 @@ export function BlockchainContextProvider({ }: HasChildren): React.JSX.Element { const dispatch = useDispatch(); const ethereum = useEthereum(); - const bitcoin = useBitcoin(ethereum); + const bitcoin = useBitcoin(); useObserver(ethereum, dispatch); diff --git a/src/app/store/slices/vault/vault.slice.ts b/src/app/store/slices/vault/vault.slice.ts index 84a1fdf3..d1f7c4b2 100644 --- a/src/app/store/slices/vault/vault.slice.ts +++ b/src/app/store/slices/vault/vault.slice.ts @@ -1,14 +1,15 @@ +import { Vault, VaultState } from "@models/vault"; import { createSlice } from "@reduxjs/toolkit"; import { exampleVaults } from "@shared/examples/example-vaults"; -interface VaultState { +interface VaultSliceState { vaults: any[]; status: string; error: string | null; } -const initialVaultState: VaultState = { +const initialVaultState: VaultSliceState = { vaults: exampleVaults, status: "idle", error: null, @@ -19,7 +20,24 @@ export const vaultSlice = createSlice({ initialState: initialVaultState, reducers: { setVaults: (state, action) => { - state.vaults = action.payload; + const { payload: newVaults } = action; + console.log("newVaults", newVaults); + newVaults.forEach((newVault: Vault) => { + const existingVault = state.vaults.find( + (vault) => vault.uuid === newVault.uuid, + ); + + if (!existingVault) { + state.vaults.push(newVault); + } else { + const shouldUpdate = + existingVault.state !== VaultState.FUNDING || + newVault.state === VaultState.FUNDED; + if (shouldUpdate) { + Object.assign(existingVault, newVault); + } + } + }); }, swapVault: (state, action) => { const { vaultUUID, updatedVault } = action.payload; @@ -34,5 +52,17 @@ export const vaultSlice = createSlice({ state.vaults[vaultIndex] = updatedVault; } }, + setVaultToFunding: (state, action) => { + const { vaultUUID, fundingTX } = action.payload; + + const vaultIndex = state.vaults.findIndex( + (vault) => vault.uuid === vaultUUID, + ); + + if (vaultIndex === -1) return; + + state.vaults[vaultIndex].state = VaultState.FUNDING; + state.vaults[vaultIndex].fundingTX = fundingTX; + }, }, }); diff --git a/src/shared/examples/example-vaults.ts b/src/shared/examples/example-vaults.ts index 92bcee87..50ad8f31 100644 --- a/src/shared/examples/example-vaults.ts +++ b/src/shared/examples/example-vaults.ts @@ -16,7 +16,6 @@ export const exampleVaults: Vault[] = [ fundingTX: "", closingTX: "", timestamp: 1620000000, - }, { uuid: "0x123456uio", @@ -26,7 +25,6 @@ export const exampleVaults: Vault[] = [ "https://etherscan.io/tx/0xbaf374be66066812e30e428ac5a3bc8d76f8cbc9ed66e3afce68905c183d22b6", closingTX: "", timestamp: 1620000000, - }, { uuid: "0x123456pas", @@ -36,7 +34,6 @@ export const exampleVaults: Vault[] = [ "https://etherscan.io/tx/0xbaf374be66066812e30e428ac5a3bc8d76f8cbc9ed66e3afce68905c183d22b6", closingTX: "", timestamp: 1620000000, - }, { uuid: "0x123456dfg", @@ -46,7 +43,6 @@ export const exampleVaults: Vault[] = [ "https://etherscan.io/tx/0xbaf374be66066812e30e428ac5a3bc8d76f8cbc9ed66e3afce68905c183d22b6", closingTX: "", timestamp: 1620000000, - }, { uuid: "0x123456hjk", @@ -56,7 +52,6 @@ export const exampleVaults: Vault[] = [ "https://etherscan.io/tx/0xbaf374be66066812e30e428ac5a3bc8d76f8cbc9ed66e3afce68905c183d22b6", closingTX: "", timestamp: 1620000000, - }, { uuid: "0x123456dfe", @@ -66,7 +61,6 @@ export const exampleVaults: Vault[] = [ "https://etherscan.io/tx/0xbaf374be66066812e30e428ac5a3bc8d76f8cbc9ed66e3afce68905c183d22b6", closingTX: "", timestamp: 1620000000, - }, { uuid: "0x123456hjq", @@ -76,7 +70,6 @@ export const exampleVaults: Vault[] = [ "https://etherscan.io/tx/0xbaf374be66066812e30e428ac5a3bc8d76f8cbc9ed66e3afce68905c183d22b6", closingTX: "", timestamp: 1620000000, - }, { uuid: "0x123456dfh", @@ -86,7 +79,6 @@ export const exampleVaults: Vault[] = [ "https://etherscan.io/tx/0xbaf374be66066812e30e428ac5a3bc8d76f8cbc9ed66e3afce68905c183d22b6", closingTX: "", timestamp: 1620000000, - }, { uuid: "0x123456hjl", @@ -96,7 +88,6 @@ export const exampleVaults: Vault[] = [ "https://etherscan.io/tx/0xbaf374be66066812e30e428ac5a3bc8d76f8cbc9ed66e3afce68905c183d22b6", closingTX: "", timestamp: 1620000000, - }, { uuid: "0x123456lzc", @@ -106,8 +97,7 @@ export const exampleVaults: Vault[] = [ "https://etherscan.io/tx/0xbaf374be66066812e30e428ac5a3bc8d76f8cbc9ed66e3afce68905c183d22b6", closingTX: "https://etherscan.io/tx/0xbaf374be66066812e30e428ac5a3bc8d76f8cbc9ed66e3afce68905c183d22b6", - timestamp: 1620000000, - + timestamp: 1620000000, }, { uuid: "0x123456cvb", @@ -117,8 +107,7 @@ export const exampleVaults: Vault[] = [ "https://etherscan.io/tx/0xbaf374be66066812e30e428ac5a3bc8d76f8cbc9ed66e3afce68905c183d22b6", closingTX: "https://etherscan.io/tx/0xbaf374be66066812e30e428ac5a3bc8d76f8cbc9ed66e3afce68905c183d22b6", - timestamp: 1620000000, - + timestamp: 1620000000, }, { uuid: "0x123456nmq", @@ -128,8 +117,7 @@ export const exampleVaults: Vault[] = [ "https://etherscan.io/tx/0xbaf374be66066812e30e428ac5a3bc8d76f8cbc9ed66e3afce68905c183d22b6", closingTX: "https://etherscan.io/tx/0xbaf374be66066812e30e428ac5a3bc8d76f8cbc9ed66e3afce68905c183d22b6", - timestamp: 1620000000, - + timestamp: 1620000000, }, { uuid: "0x123456pgh", @@ -139,8 +127,7 @@ export const exampleVaults: Vault[] = [ "https://etherscan.io/tx/0xbaf374be66066812e30e428ac5a3bc8d76f8cbc9ed66e3afce68905c183d22b6", closingTX: "https://etherscan.io/tx/0xbaf374be66066812e30e428ac5a3bc8d76f8cbc9ed66e3afce68905c183d22b6", - timestamp: 1620000000, - + timestamp: 1620000000, }, { uuid: "0x123456skf", @@ -150,8 +137,7 @@ export const exampleVaults: Vault[] = [ "https://etherscan.io/tx/0xbaf374be66066812e30e428ac5a3bc8d76f8cbc9ed66e3afce68905c183d22b6", closingTX: "https://etherscan.io/tx/0xbaf374be66066812e30e428ac5a3bc8d76f8cbc9ed66e3afce68905c183d22b6", - timestamp: 1620000000, - + timestamp: 1620000000, }, { uuid: "0x123456lkh", @@ -161,7 +147,6 @@ export const exampleVaults: Vault[] = [ "https://etherscan.io/tx/0xbaf374be66066812e30e428ac5a3bc8d76f8cbc9ed66e3afce68905c183d22b6", closingTX: "https://etherscan.io/tx/0xbaf374be66066812e30e428ac5a3bc8d76f8cbc9ed66e3afce68905c183d22b6", - timestamp: 1620000000, - + timestamp: 1620000000, }, ];