chore: prettier

This commit is contained in:
Justin Starry 2020-11-27 10:49:14 +08:00
parent f8db6bfde0
commit cb7bbda611
12 changed files with 272 additions and 233 deletions

View File

@ -1,9 +1,9 @@
import React, { } from "react"; import React from "react";
import { Button } from "antd"; import { Button } from "antd";
import "./style.less"; import "./style.less";
import { LABELS } from "../../constants"; import { LABELS } from "../../constants";
import { Link } from "react-router-dom"; import { Link } from "react-router-dom";
import './style.less'; import "./style.less";
export const ActionConfirmation = (props: { export const ActionConfirmation = (props: {
className?: string; className?: string;
@ -22,11 +22,7 @@ export const ActionConfirmation = (props: {
<div>Your action has been successfully executed</div> <div>Your action has been successfully executed</div>
<div className="success-icon" /> <div className="success-icon" />
<Link to="/dashboard"> <Link to="/dashboard">
<Button <Button type="primary">{LABELS.DASHBOARD_ACTION}</Button>
type="primary"
>
{LABELS.DASHBOARD_ACTION}
</Button>
</Link> </Link>
<Button type="text" onClick={props.onClose}> <Button type="text" onClick={props.onClose}>
{LABELS.GO_BACK_ACTION} {LABELS.GO_BACK_ACTION}

View File

@ -1,4 +1,4 @@
import React, { } from "react"; import React from "react";
import { Button } from "antd"; import { Button } from "antd";
import { LABELS } from "../../constants"; import { LABELS } from "../../constants";
import { useHistory } from "react-router-dom"; import { useHistory } from "react-router-dom";

View File

@ -20,7 +20,7 @@ import { CollateralSelector } from "./../CollateralSelector";
import "./style.less"; import "./style.less";
import { LABELS } from "../../constants"; import { LABELS } from "../../constants";
import { LoadingOutlined } from "@ant-design/icons"; import { LoadingOutlined } from "@ant-design/icons";
import { ActionConfirmation} from './../ActionConfirmation'; import { ActionConfirmation } from "./../ActionConfirmation";
import { BackButton } from "./../BackButton"; import { BackButton } from "./../BackButton";
const antIcon = <LoadingOutlined style={{ fontSize: 24 }} spin />; const antIcon = <LoadingOutlined style={{ fontSize: 24 }} spin />;
@ -66,7 +66,6 @@ export const BorrowInput = (props: {
(async () => { (async () => {
try { try {
await borrow( await borrow(
connection, connection,
wallet, wallet,
@ -90,8 +89,8 @@ export const BorrowInput = (props: {
setValue(""); setValue("");
setShowConfirmation(true); setShowConfirmation(true);
} catch { } catch {
// TODO: // TODO:
}finally { } finally {
setPendingTx(false); setPendingTx(false);
} }
})(); })();
@ -117,50 +116,55 @@ export const BorrowInput = (props: {
return ( return (
<Card className={props.className} bodyStyle={bodyStyle}> <Card className={props.className} bodyStyle={bodyStyle}>
{showConfirmation ? <ActionConfirmation onClose={() => setShowConfirmation(false)} /> : {showConfirmation ? (
<div <ActionConfirmation onClose={() => setShowConfirmation(false)} />
style={{ ) : (
display: "flex", <div
flexDirection: "column", style={{
justifyContent: "space-around", display: "flex",
}} flexDirection: "column",
> justifyContent: "space-around",
<div className="borrow-input-title">{LABELS.BORROW_QUESTION}</div> }}
<div className="token-input">
<TokenIcon mintAddress={borrowReserve?.info.liquidityMint} />
<NumericInput
value={value}
onChange={(val: any) => {
setValue(val);
}}
autoFocus={true}
style={{
fontSize: 20,
boxShadow: "none",
borderColor: "transparent",
outline: "transparent",
}}
placeholder="0.00"
/>
<div>{name}</div>
</div>
<div className="borrow-input-title">{LABELS.SELECT_COLLATERAL}</div>
<CollateralSelector
reserve={borrowReserve.info}
mint={collateralReserveMint}
onMintChange={setCollateralReserveMint}
/>
<Button
type="primary"
onClick={onBorrow}
disabled={fromAccounts.length === 0 || pendingTx}
> >
{LABELS.BORROW_ACTION} <div className="borrow-input-title">{LABELS.BORROW_QUESTION}</div>
{pendingTx && <Spin indicator={antIcon} className="action-spinner" />} <div className="token-input">
</Button> <TokenIcon mintAddress={borrowReserve?.info.liquidityMint} />
<BackButton /> <NumericInput
</div>} value={value}
onChange={(val: any) => {
setValue(val);
}}
autoFocus={true}
style={{
fontSize: 20,
boxShadow: "none",
borderColor: "transparent",
outline: "transparent",
}}
placeholder="0.00"
/>
<div>{name}</div>
</div>
<div className="borrow-input-title">{LABELS.SELECT_COLLATERAL}</div>
<CollateralSelector
reserve={borrowReserve.info}
mint={collateralReserveMint}
onMintChange={setCollateralReserveMint}
/>
<Button
type="primary"
onClick={onBorrow}
disabled={fromAccounts.length === 0 || pendingTx}
>
{LABELS.BORROW_ACTION}
{pendingTx && (
<Spin indicator={antIcon} className="action-spinner" />
)}
</Button>
<BackButton />
</div>
)}
</Card> </Card>
); );
}; };

View File

@ -10,7 +10,7 @@ import { deposit } from "../../actions/deposit";
import { PublicKey } from "@solana/web3.js"; import { PublicKey } from "@solana/web3.js";
import "./style.less"; import "./style.less";
import { LoadingOutlined } from "@ant-design/icons"; import { LoadingOutlined } from "@ant-design/icons";
import { ActionConfirmation} from './../ActionConfirmation'; import { ActionConfirmation } from "./../ActionConfirmation";
const antIcon = <LoadingOutlined style={{ fontSize: 24 }} spin />; const antIcon = <LoadingOutlined style={{ fontSize: 24 }} spin />;
@ -54,7 +54,6 @@ export const DepositInput = (props: {
setPendingTx(false); setPendingTx(false);
} }
})(); })();
}, [connection, wallet, value, reserve, fromAccounts, address]); }, [connection, wallet, value, reserve, fromAccounts, address]);
const bodyStyle: React.CSSProperties = { const bodyStyle: React.CSSProperties = {
@ -67,45 +66,50 @@ export const DepositInput = (props: {
return ( return (
<Card className={props.className} bodyStyle={bodyStyle}> <Card className={props.className} bodyStyle={bodyStyle}>
{showConfirmation ? <ActionConfirmation onClose={() => setShowConfirmation(false)} /> : {showConfirmation ? (
<div <ActionConfirmation onClose={() => setShowConfirmation(false)} />
style={{ ) : (
display: "flex", <div
flexDirection: "column", style={{
justifyContent: "space-around", display: "flex",
}} flexDirection: "column",
> justifyContent: "space-around",
<div className="deposit-input-title"> }}
How much would you like to deposit?
</div>
<div className="token-input">
<TokenIcon mintAddress={reserve?.liquidityMint} />
<NumericInput
value={value}
onChange={(val: any) => {
setValue(val);
}}
autoFocus={true}
style={{
fontSize: 20,
boxShadow: "none",
borderColor: "transparent",
outline: "transparent",
}}
placeholder="0.00"
/>
<div>{name}</div>
</div>
<Button
type="primary"
onClick={onDeposit}
disabled={fromAccounts.length === 0 || pendingTx}
> >
Deposit <div className="deposit-input-title">
{pendingTx && <Spin indicator={antIcon} className="action-spinner" />} How much would you like to deposit?
</Button> </div>
</div>} <div className="token-input">
<TokenIcon mintAddress={reserve?.liquidityMint} />
<NumericInput
value={value}
onChange={(val: any) => {
setValue(val);
}}
autoFocus={true}
style={{
fontSize: 20,
boxShadow: "none",
borderColor: "transparent",
outline: "transparent",
}}
placeholder="0.00"
/>
<div>{name}</div>
</div>
<Button
type="primary"
onClick={onDeposit}
disabled={fromAccounts.length === 0 || pendingTx}
>
Deposit
{pendingTx && (
<Spin indicator={antIcon} className="action-spinner" />
)}
</Button>
</div>
)}
</Card> </Card>
); );
}; };

View File

@ -14,13 +14,10 @@ import { useWallet } from "../../contexts/wallet";
import { repay } from "../../actions"; import { repay } from "../../actions";
import { CollateralSelector } from "./../CollateralSelector"; import { CollateralSelector } from "./../CollateralSelector";
import "./style.less"; import "./style.less";
import { import { formatNumber, toLamports } from "../../utils/utils";
formatNumber,
toLamports,
} from "../../utils/utils";
import { LABELS } from "../../constants"; import { LABELS } from "../../constants";
import { LoadingOutlined } from "@ant-design/icons"; import { LoadingOutlined } from "@ant-design/icons";
import { ActionConfirmation} from './../ActionConfirmation'; import { ActionConfirmation } from "./../ActionConfirmation";
const antIcon = <LoadingOutlined style={{ fontSize: 24 }} spin />; const antIcon = <LoadingOutlined style={{ fontSize: 24 }} spin />;
@ -64,7 +61,6 @@ export const RepayInput = (props: {
[value, repayLiquidityMint] [value, repayLiquidityMint]
); );
const onRepay = useCallback(() => { const onRepay = useCallback(() => {
if ( if (
!collateralReserve || !collateralReserve ||
@ -79,26 +75,25 @@ export const RepayInput = (props: {
(async () => { (async () => {
try { try {
await repay( await repay(
fromAccounts[0], fromAccounts[0],
lamports, lamports,
obligation, obligation,
obligationAccount, obligationAccount,
repayReserve, repayReserve,
collateralReserve, collateralReserve,
connection, connection,
wallet wallet
); );
setValue(""); setValue("");
setShowConfirmation(true); setShowConfirmation(true);
} catch { } catch {
// TODO: // TODO:
}finally { } finally {
setPendingTx(false); setPendingTx(false);
} }
})(); })();
}, [ }, [
lamports, lamports,
connection, connection,
@ -120,38 +115,40 @@ export const RepayInput = (props: {
return ( return (
<Card className={props.className} bodyStyle={bodyStyle}> <Card className={props.className} bodyStyle={bodyStyle}>
{showConfirmation ? <ActionConfirmation onClose={() => setShowConfirmation(false)} /> : {showConfirmation ? (
<div <ActionConfirmation onClose={() => setShowConfirmation(false)} />
style={{ ) : (
display: "flex", <div
flexDirection: "column", style={{
justifyContent: "space-around", display: "flex",
}} flexDirection: "column",
> justifyContent: "space-around",
<div className="repay-input-title"> }}
{LABELS.REPAY_QUESTION} (Currently: ){formatNumber.format(balance)}{" "} >
{name}) <div className="repay-input-title">
</div> {LABELS.REPAY_QUESTION} (Currently: ){formatNumber.format(balance)}{" "}
<div className="token-input"> {name})
<TokenIcon mintAddress={repayReserve?.info.liquidityMint} /> </div>
<NumericInput <div className="token-input">
value={value} <TokenIcon mintAddress={repayReserve?.info.liquidityMint} />
onChange={(val: any) => { <NumericInput
setValue(val); value={value}
}} onChange={(val: any) => {
autoFocus={true} setValue(val);
style={{ }}
fontSize: 20, autoFocus={true}
boxShadow: "none", style={{
borderColor: "transparent", fontSize: 20,
outline: "transparent", boxShadow: "none",
}} borderColor: "transparent",
placeholder="0.00" outline: "transparent",
/> }}
<div>{name}</div> placeholder="0.00"
</div> />
{/* TODO: finish slider implementation */} <div>{name}</div>
{/* <Slider </div>
{/* TODO: finish slider implementation */}
{/* <Slider
marks={marks} marks={marks}
value={mark} value={mark}
onChange={(val: number) => onChange={(val: number) =>
@ -167,24 +164,25 @@ export const RepayInput = (props: {
) )
} }
/> */} /> */}
<div className="repay-input-title">{LABELS.SELECT_COLLATERAL}</div> <div className="repay-input-title">{LABELS.SELECT_COLLATERAL}</div>
<CollateralSelector <CollateralSelector
reserve={repayReserve.info} reserve={repayReserve.info}
mint={collateralReserveMint} mint={collateralReserveMint}
onMintChange={setCollateralReserveMint} onMintChange={setCollateralReserveMint}
/> />
<Button <Button
type="primary" type="primary"
onClick={onRepay} onClick={onRepay}
disabled={fromAccounts.length === 0} disabled={fromAccounts.length === 0}
> >
{LABELS.REPAY_ACTION} {LABELS.REPAY_ACTION}
{pendingTx && <Spin indicator={antIcon} className="action-spinner" />} {pendingTx && (
</Button> <Spin indicator={antIcon} className="action-spinner" />
</div>} )}
</Button>
</div>
)}
</Card> </Card>
); );
}; };

View File

@ -1,6 +1,11 @@
import React from "react"; import React from "react";
import { useTokenName } from "./../../hooks"; import { useTokenName } from "./../../hooks";
import { calculateBorrowAPY, calculateDepositAPY, calculateUtilizationRatio, LendingReserve } from "../../models/lending"; import {
calculateBorrowAPY,
calculateDepositAPY,
calculateUtilizationRatio,
LendingReserve,
} from "../../models/lending";
import { TokenIcon } from "../../components/TokenIcon"; import { TokenIcon } from "../../components/TokenIcon";
import { formatNumber, formatPct, fromLamports } from "../../utils/utils"; import { formatNumber, formatPct, fromLamports } from "../../utils/utils";
import { Card, Typography } from "antd"; import { Card, Typography } from "antd";

View File

@ -15,7 +15,7 @@ import { PublicKey } from "@solana/web3.js";
import "./style.less"; import "./style.less";
import { LABELS } from "../../constants"; import { LABELS } from "../../constants";
import { LoadingOutlined } from "@ant-design/icons"; import { LoadingOutlined } from "@ant-design/icons";
import { ActionConfirmation} from './../ActionConfirmation'; import { ActionConfirmation } from "./../ActionConfirmation";
const antIcon = <LoadingOutlined style={{ fontSize: 24 }} spin />; const antIcon = <LoadingOutlined style={{ fontSize: 24 }} spin />;
@ -51,7 +51,7 @@ export const WithdrawInput = (props: {
fromAccounts[0], fromAccounts[0],
Math.ceil( Math.ceil(
collateralBalanceLamports * collateralBalanceLamports *
(parseFloat(value) / collateralBalanceInLiquidity) (parseFloat(value) / collateralBalanceInLiquidity)
), ),
reserve, reserve,
address, address,
@ -88,43 +88,48 @@ export const WithdrawInput = (props: {
return ( return (
<Card className={props.className} bodyStyle={bodyStyle}> <Card className={props.className} bodyStyle={bodyStyle}>
{showConfirmation ? <ActionConfirmation onClose={() => setShowConfirmation(false)} /> : {showConfirmation ? (
<div <ActionConfirmation onClose={() => setShowConfirmation(false)} />
style={{ ) : (
display: "flex", <div
flexDirection: "column", style={{
justifyContent: "space-around", display: "flex",
}} flexDirection: "column",
> justifyContent: "space-around",
<div className="withdraw-input-title">{LABELS.WITHDRAW_QUESTION}</div> }}
<div className="token-input">
<TokenIcon mintAddress={reserve?.liquidityMint} />
<NumericInput
value={value}
onChange={(val: any) => {
setValue(val);
}}
autoFocus={true}
style={{
fontSize: 20,
boxShadow: "none",
borderColor: "transparent",
outline: "transparent",
}}
placeholder="0.00"
/>
<div>{name}</div>
</div>
<Button
type="primary"
onClick={onWithdraw}
disabled={fromAccounts.length === 0 || pendingTx}
> >
{LABELS.WITHDRAW_ACTION} <div className="withdraw-input-title">{LABELS.WITHDRAW_QUESTION}</div>
{pendingTx && <Spin indicator={antIcon} className="action-spinner" />} <div className="token-input">
</Button> <TokenIcon mintAddress={reserve?.liquidityMint} />
</div>} <NumericInput
value={value}
onChange={(val: any) => {
setValue(val);
}}
autoFocus={true}
style={{
fontSize: 20,
boxShadow: "none",
borderColor: "transparent",
outline: "transparent",
}}
placeholder="0.00"
/>
<div>{name}</div>
</div>
<Button
type="primary"
onClick={onWithdraw}
disabled={fromAccounts.length === 0 || pendingTx}
>
{LABELS.WITHDRAW_ACTION}
{pendingTx && (
<Spin indicator={antIcon} className="action-spinner" />
)}
</Button>
</div>
)}
</Card> </Card>
); );
}; };

View File

@ -13,11 +13,11 @@ export let LENDING_PROGRAM_ID = new PublicKey(
export const setProgramIds = (envName: string) => { export const setProgramIds = (envName: string) => {
// Add dynamic program ids // Add dynamic program ids
if(envName === 'mainnet-beta') { if (envName === "mainnet-beta") {
LENDING_PROGRAM_ID = new PublicKey('2KfJP7pZ6QSpXa26RmsN6kKVQteDEdQmizLSvuyryeiW'); LENDING_PROGRAM_ID = new PublicKey(
"2KfJP7pZ6QSpXa26RmsN6kKVQteDEdQmizLSvuyryeiW"
);
} }
}; };
export const programIds = () => { export const programIds = () => {

View File

@ -7,8 +7,10 @@ export const LABELS = {
REPAY_QUESTION: "How much would you like to repay?", REPAY_QUESTION: "How much would you like to repay?",
REPAY_ACTION: "Repay", REPAY_ACTION: "Repay",
RESERVE_STATUS_TITLE: "Reserve Status & Configuration", RESERVE_STATUS_TITLE: "Reserve Status & Configuration",
AUDIT_WARNING: "Oyster is an unaudited software project used for internal purposes at the Solana Foundation. This app is not for public use.", AUDIT_WARNING:
FOOTER: "This page was produced by the Solana Foundation (\"SF\") for internal educational and inspiration purposes only. SF does not encourage, induce or sanction the deployment, integration or use of Oyster or any similar application (including its code) in violation of applicable laws or regulations and hereby prohibits any such deployment, integration or use. Anyone using this code or a derivation thereof must comply with applicable laws and regulations when releasing related software.", "Oyster is an unaudited software project used for internal purposes at the Solana Foundation. This app is not for public use.",
FOOTER:
'This page was produced by the Solana Foundation ("SF") for internal educational and inspiration purposes only. SF does not encourage, induce or sanction the deployment, integration or use of Oyster or any similar application (including its code) in violation of applicable laws or regulations and hereby prohibits any such deployment, integration or use. Anyone using this code or a derivation thereof must comply with applicable laws and regulations when releasing related software.',
MENU_HOME: "Home", MENU_HOME: "Home",
MENU_DASHBOARD: "Dashboard", MENU_DASHBOARD: "Dashboard",
MENU_DEPOSIT: "Deposit", MENU_DEPOSIT: "Deposit",

View File

@ -167,6 +167,11 @@ export const initReserveInstruction = (
}; };
export const calculateUtilizationRatio = (reserve: LendingReserve) => { export const calculateUtilizationRatio = (reserve: LendingReserve) => {
let borrowedLiquidity = wadToLamports(reserve.borrowedLiquidityWad).toNumber(); let borrowedLiquidity = wadToLamports(
return borrowedLiquidity / (reserve.availableLiquidity.toNumber() + borrowedLiquidity); reserve.borrowedLiquidityWad
} ).toNumber();
return (
borrowedLiquidity /
(reserve.availableLiquidity.toNumber() + borrowedLiquidity)
);
};

View File

@ -13,33 +13,44 @@ export const DashboardView = () => {
return ( return (
<div className="dashboard-container"> <div className="dashboard-container">
{!connected && <div className="dashboard-info">Connect to a wallet to view your deposits/loans.</div>} {!connected && (
{connected && userDeposits.length === 0 &&userObligations.length === 0 && <div className="dashboard-info">No loans or deposits.</div>} <div className="dashboard-info">
{userDeposits.length > 0 && (<div className="dashboard-left"> Connect to a wallet to view your deposits/loans.
<span>{LABELS.DASHBOARD_TITLE_DEPOSITS}</span> </div>
)}
{connected &&
userDeposits.length === 0 &&
userObligations.length === 0 && (
<div className="dashboard-info">No loans or deposits.</div>
)}
{userDeposits.length > 0 && (
<div className="dashboard-left">
<span>{LABELS.DASHBOARD_TITLE_DEPOSITS}</span>
<div className="dashboard-item dashboard-header"> <div className="dashboard-item dashboard-header">
<div>{LABELS.TABLE_TITLE_ASSET}</div> <div>{LABELS.TABLE_TITLE_ASSET}</div>
<div>{LABELS.TABLE_TITLE_DEPOSIT_BALANCE}</div> <div>{LABELS.TABLE_TITLE_DEPOSIT_BALANCE}</div>
<div>{LABELS.TABLE_TITLE_APY}</div> <div>{LABELS.TABLE_TITLE_APY}</div>
<div>{LABELS.TABLE_TITLE_ACTION}</div> <div>{LABELS.TABLE_TITLE_ACTION}</div>
</div> </div>
{userDeposits.map((deposit) => ( {userDeposits.map((deposit) => (
<DepositItem reserve={deposit.reserve} account={deposit.account} /> <DepositItem reserve={deposit.reserve} account={deposit.account} />
))} ))}
</div>)} </div>
{userObligations.length > 0 && (<div className="dashboard-right"> )}
<span>{LABELS.DASHBOARD_TITLE_LOANS}</span> {userObligations.length > 0 && (
<div className="dashboard-right">
<span>{LABELS.DASHBOARD_TITLE_LOANS}</span>
<div className="dashboard-item dashboard-header"> <div className="dashboard-item dashboard-header">
<div>{LABELS.TABLE_TITLE_ASSET}</div> <div>{LABELS.TABLE_TITLE_ASSET}</div>
<div>{LABELS.TABLE_TITLE_LOAN_BALANCE}</div> <div>{LABELS.TABLE_TITLE_LOAN_BALANCE}</div>
<div>{LABELS.TABLE_TITLE_APY}</div> <div>{LABELS.TABLE_TITLE_APY}</div>
<div>{LABELS.TABLE_TITLE_ACTION}</div> <div>{LABELS.TABLE_TITLE_ACTION}</div>
</div> </div>
{userObligations.map((item) => { {userObligations.map((item) => {
return <ObligationItem obligation={item.obligation} />; return <ObligationItem obligation={item.obligation} />;
})} })}
</div> </div>
)} )}
</div> </div>
); );
}; };

View File

@ -1,8 +1,17 @@
import React, { useMemo } from "react"; import React, { useMemo } from "react";
import { useTokenName } from "../../hooks"; import { useTokenName } from "../../hooks";
import { calculateBorrowAPY, LendingObligation, LendingReserve } from "../../models/lending"; import {
calculateBorrowAPY,
LendingObligation,
LendingReserve,
} from "../../models/lending";
import { TokenIcon } from "../../components/TokenIcon"; import { TokenIcon } from "../../components/TokenIcon";
import { wadToLamports, formatNumber, fromLamports, formatPct } from "../../utils/utils"; import {
wadToLamports,
formatNumber,
fromLamports,
formatPct,
} from "../../utils/utils";
import { Button, Card } from "antd"; import { Button, Card } from "antd";
import { Link } from "react-router-dom"; import { Link } from "react-router-dom";
import { cache, ParsedAccount, useMint } from "../../contexts/accounts"; import { cache, ParsedAccount, useMint } from "../../contexts/accounts";