feat: update layout

This commit is contained in:
bartosz-lipinski 2021-01-06 10:43:00 -06:00
parent a2154ff63c
commit 1177d94153
11 changed files with 79 additions and 50 deletions

View File

@ -26,7 +26,7 @@ export const ReserveStatus = (props: {
const liquidityMint = useMint(mintAddress);
const { price } = useMidPriceInUSD(mintAddress);
const availableLiquidity = fromLamports(
props.reserve.availableLiquidity.toNumber(),
props.reserve.state.availableLiquidity,
liquidityMint
);
@ -35,7 +35,7 @@ export const ReserveStatus = (props: {
const totalBorrows = useMemo(
() =>
fromLamports(
wadToLamports(props.reserve.borrowedLiquidityWad),
wadToLamports(props.reserve.state.borrowedLiquidityWad),
liquidityMint
),
[props.reserve, liquidityMint]

View File

@ -9,14 +9,14 @@ export const ReserveUtilizationChart = (props: { reserve: LendingReserve }) => {
const mintAddress = props.reserve.liquidityMint?.toBase58();
const liquidityMint = useMint(mintAddress);
const availableLiquidity = fromLamports(
props.reserve.availableLiquidity.toNumber(),
props.reserve.state.availableLiquidity,
liquidityMint
);
const totalBorrows = useMemo(
() =>
fromLamports(
wadToLamports(props.reserve.borrowedLiquidityWad),
wadToLamports(props.reserve.state.borrowedLiquidityWad),
liquidityMint
),
[props.reserve, liquidityMint]

View File

@ -31,7 +31,7 @@ export const SideReserveOverview = (props: {
const liquidityMint = useMint(reserve.liquidityMint);
const availableLiquidity = fromLamports(
reserve.availableLiquidity.toNumber(),
reserve.state.availableLiquidity,
liquidityMint
);

View File

@ -1,6 +1,7 @@
import BN from "bn.js";
export const TEN = new BN(10);
export const HALF_WAD = TEN.pow(new BN(18));
export const WAD = TEN.pow(new BN(18));
export const RAY = TEN.pow(new BN(27));
export const ZERO = new BN(0);

View File

@ -11,7 +11,7 @@ import {
LendingObligationParser,
} from './../models/lending';
import { cache, getMultipleAccounts, MintParser, ParsedAccount } from './accounts';
import { PublicKey } from '@solana/web3.js';
import { PublicKey, AccountInfo } from '@solana/web3.js';
import { DexMarketParser } from '../models/dex';
import { usePrecacheMarket } from './market';
import { useLendingReserves } from '../hooks';
@ -41,7 +41,10 @@ export const useLending = () => {
// TODO: query for all the dex from reserves
const processAccount = useCallback((item) => {
const processAccount = useCallback((item : { pubkey: PublicKey, account: AccountInfo<Buffer> }) => {
console.log('Account length: ', item.account.data.length);
if (isLendingReserve(item.account)) {
const reserve = cache.add(item.pubkey.toBase58(), item.account, LendingReserveParser);

View File

@ -57,6 +57,6 @@ export function calculateCollateralBalance(
reserve: LendingReserve,
balanceLamports: number) {
return reserveMarketCap(reserve) *
(balanceLamports / (reserve?.collateralMintSupply.toNumber() || 1));
(balanceLamports / (reserve?.state.collateralMintSupply.toNumber() || 1));
}

View File

@ -2,10 +2,9 @@ import { PublicKey, SYSVAR_CLOCK_PUBKEY, SYSVAR_RENT_PUBKEY, TransactionInstruct
import BN from 'bn.js';
import * as BufferLayout from 'buffer-layout';
import { TOKEN_PROGRAM_ID, LENDING_PROGRAM_ID } from '../../utils/ids';
import { wadToLamports } from '../../utils/utils';
import * as Layout from './../../utils/layout';
import { LendingInstruction } from './lending';
import { LendingReserve } from './reserve';
import { calculateUtilizationRatio, LendingReserve } from './reserve';
export enum BorrowAmountType {
LiquidityBorrowAmount = 0,
@ -116,8 +115,7 @@ export const borrowInstruction = (
// deposit APY utilization currentUtilizationRate * borrowAPY
export const calculateBorrowAPY = (reserve: LendingReserve) => {
const totalBorrows = wadToLamports(reserve.borrowedLiquidityWad).toNumber();
const currentUtilization = totalBorrows / (reserve.availableLiquidity.toNumber() + totalBorrows);
const currentUtilization = calculateUtilizationRatio(reserve);
const optimalUtilization = reserve.config.optimalUtilizationRate / 100;
let borrowAPY;

View File

@ -2,11 +2,10 @@ import { PublicKey, SYSVAR_CLOCK_PUBKEY, TransactionInstruction } from '@solana/
import BN from 'bn.js';
import * as BufferLayout from 'buffer-layout';
import { TOKEN_PROGRAM_ID, LENDING_PROGRAM_ID } from '../../utils/ids';
import { wadToLamports } from '../../utils/utils';
import * as Layout from './../../utils/layout';
import { calculateBorrowAPY } from './borrow';
import { LendingInstruction } from './lending';
import { LendingReserve } from './reserve';
import { calculateUtilizationRatio, LendingReserve } from './reserve';
/// Deposit liquidity into a reserve. The output is a collateral token representing ownership
/// of the reserve liquidity pool.
@ -32,7 +31,10 @@ export const depositInstruction = (
reserveSupply: PublicKey,
collateralMint: PublicKey
): TransactionInstruction => {
const dataLayout = BufferLayout.struct([BufferLayout.u8('instruction'), Layout.uint64('liquidityAmount')]);
const dataLayout = BufferLayout.struct([
BufferLayout.u8('instruction'),
Layout.uint64('liquidityAmount')
]);
const data = Buffer.alloc(dataLayout.span);
dataLayout.encode(
@ -63,8 +65,7 @@ export const depositInstruction = (
};
export const calculateDepositAPY = (reserve: LendingReserve) => {
const totalBorrows = wadToLamports(reserve.borrowedLiquidityWad).toNumber();
const currentUtilization = totalBorrows / (reserve.availableLiquidity.toNumber() + totalBorrows);
const currentUtilization = calculateUtilizationRatio(reserve);
const borrowAPY = calculateBorrowAPY(reserve);
return currentUtilization * borrowAPY;

View File

@ -7,23 +7,38 @@ import {
} from '@solana/web3.js';
import BN from 'bn.js';
import * as BufferLayout from 'buffer-layout';
import { HALF_WAD } from '../../constants';
import { TOKEN_PROGRAM_ID, LENDING_PROGRAM_ID } from '../../utils/ids';
import { wadToLamports } from '../../utils/utils';
import * as Layout from './../../utils/layout';
import { LendingInstruction } from './lending';
export const LendingReserveLayout: typeof BufferLayout.Structure = BufferLayout.struct([
Layout.uint64('lastUpdateSlot'),
Layout.publicKey('lendingMarket'),
Layout.publicKey('liquidityMint'),
BufferLayout.u8('liquidityMintDecimals'),
Layout.publicKey('liquiditySupply'),
Layout.publicKey('collateralMint'),
Layout.publicKey('collateralSupply'),
Layout.publicKey('collateralFeesReceiver'),
// TODO: replace u32 option with generic quivalent
BufferLayout.u32('dexMarketOption'),
Layout.publicKey('dexMarket'),
BufferLayout.struct(
[
Layout.uint64('lastUpdateSlot'),
Layout.uint128('cumulativeBorrowRateWad'),
Layout.uint128('borrowedLiquidityWad'),
Layout.uint64('availableLiquidity'),
Layout.uint64('collateralMintSupply'),
],
'state'
),
BufferLayout.struct(
[
/// Optimal utilization rate as a percent
@ -41,39 +56,40 @@ export const LendingReserveLayout: typeof BufferLayout.Structure = BufferLayout.
/// Max borrow APY
BufferLayout.u8('maxBorrowRate'),
/// Fee assessed on `BorrowReserveLiquidity`, expressed as a Wad.
/// Must be between 0 and 10^18, such that 10^18 = 1. A few examples for
/// clarity:
/// 1% = 10_000_000_000_000_000
/// 0.01% (1 basis point) = 100_000_000_000_000
/// 0.00001% (Aave borrow fee) = 100_000_000_000
BufferLayout.uint64('borrowFeeWad'),
BufferLayout.struct(
[
/// Fee assessed on `BorrowReserveLiquidity`, expressed as a Wad.
/// Must be between 0 and 10^18, such that 10^18 = 1. A few examples for
/// clarity:
/// 1% = 10_000_000_000_000_000
/// 0.01% (1 basis point) = 100_000_000_000_000
/// 0.00001% (Aave borrow fee) = 100_000_000_000
Layout.uint64('borrowFeeWad'),
/// Amount of fee going to host account, if provided in liquidate and repay
BufferLayout.u8('hostFeePercentage'),
/// Amount of fee going to host account, if provided in liquidate and repay
BufferLayout.u8('hostFeePercentage'),
],
'fees'
),
],
'config'
),
Layout.uint128('cumulativeBorrowRateWad'),
Layout.uint128('borrowedLiquidityWad'),
Layout.uint64('availableLiquidity'),
Layout.uint64('collateralMintSupply'),
]);
export const isLendingReserve = (info: AccountInfo<Buffer>) => {
console.log('Lending Reserve: ', LendingReserveLayout.span)
return info.data.length === LendingReserveLayout.span;
};
export interface LendingReserve {
lastUpdateSlot: BN;
lendingMarket: PublicKey;
liquiditySupply: PublicKey;
liquidityMint: PublicKey;
collateralSupply: PublicKey;
collateralMint: PublicKey;
collateralSupply: PublicKey;
collateralFeesReceiver: PublicKey;
dexMarketOption: number;
dexMarket: PublicKey;
@ -87,21 +103,27 @@ export interface LendingReserve {
optimalBorrowRate: number;
maxBorrowRate: number;
borrowFeeWad: BN;
hostFeePercentage: number;
fees: {
borrowFeeWad: BN;
hostFeePercentage: number;
};
};
cumulativeBorrowRateWad: BN;
borrowedLiquidityWad: BN;
state: {
lastUpdateSlot: BN;
cumulativeBorrowRateWad: BN;
borrowedLiquidityWad: BN;
availableLiquidity: BN;
collateralMintSupply: BN;
availableLiquidity: BN;
collateralMintSupply: BN;
};
}
export const LendingReserveParser = (pubKey: PublicKey, info: AccountInfo<Buffer>) => {
const buffer = Buffer.from(info.data);
const data = LendingReserveLayout.decode(buffer);
if (data.lastUpdateSlot.toNumber() === 0) return;
const data = LendingReserveLayout.decode(buffer) as LendingReserve;
if (data.state.lastUpdateSlot.toNumber() === 0) return;
const details = {
pubkey: pubKey,
@ -111,6 +133,8 @@ export const LendingReserveParser = (pubKey: PublicKey, info: AccountInfo<Buffer
info: data,
};
return details;
};
@ -176,20 +200,22 @@ export const initReserveInstruction = (
};
export const calculateUtilizationRatio = (reserve: LendingReserve) => {
let borrowedLiquidity = wadToLamports(reserve.borrowedLiquidityWad).toNumber();
return borrowedLiquidity / (reserve.availableLiquidity.toNumber() + borrowedLiquidity);
const totalBorrows = wadToLamports(reserve.state.borrowedLiquidityWad).toNumber();
const currentUtilization = totalBorrows / (reserve.state.availableLiquidity.toNumber() + totalBorrows);
return currentUtilization;
};
export const reserveMarketCap = (reserve?: LendingReserve) => {
const available = reserve?.availableLiquidity.toNumber() || 0;
const borrowed = wadToLamports(reserve?.borrowedLiquidityWad).toNumber();
const available = reserve?.state.availableLiquidity.toNumber() || 0;
const borrowed = wadToLamports(reserve?.state.borrowedLiquidityWad).toNumber();
const total = available + borrowed;
return total;
};
export const collateralExchangeRate = (reserve?: LendingReserve) => {
return (reserve?.collateralMintSupply.toNumber() || 1) / reserveMarketCap(reserve);
return (reserve?.state.collateralMintSupply.toNumber() || 1) / reserveMarketCap(reserve);
};
export const collateralToLiquidity = (collateralAmount: BN | number, reserve?: LendingReserve) => {

View File

@ -51,7 +51,7 @@ export const HomeView = () => {
marketSize: fromLamports(marketCapLamports, liquidityMint?.info) *
price,
borrowed: fromLamports(
wadToLamports(item.info?.borrowedLiquidityWad).toNumber(),
wadToLamports(item.info?.state.borrowedLiquidityWad).toNumber(),
liquidityMint.info
) *
price,

View File

@ -27,14 +27,14 @@ export const LendingReserveItem = (props: {
const liquidityMint = useMint(props.reserve.liquidityMint);
const availableLiquidity = fromLamports(
props.reserve.availableLiquidity.toNumber(),
props.reserve.state.availableLiquidity,
liquidityMint
);
const totalBorrows = useMemo(
() =>
fromLamports(
wadToLamports(props.reserve.borrowedLiquidityWad),
wadToLamports(props.reserve.state.borrowedLiquidityWad),
liquidityMint
),
[props.reserve, liquidityMint]