Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Openbook V2 #423

Draft
wants to merge 54 commits into
base: main
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
54 commits
Select commit Hold shift + click to select a range
53d8b39
wip openbook v2 support
riordanp Jan 2, 2024
49b3bf1
use git dependency for mango-v4 client
riordanp Jan 4, 2024
a359b76
fix pkg.json
tlrjs Jan 5, 2024
a926955
wip
tlrjs Feb 12, 2024
88b2989
more wip
tlrjs Feb 13, 2024
de5d04e
fix orderbook
tlrjs Feb 29, 2024
f7d946e
update client, fix parameter types
riordanp Mar 7, 2024
a9f58f6
wip2
tlrjs Mar 14, 2024
ef5c017
hard code size for now
tlrjs Mar 14, 2024
631b8cc
Update packages, new group, add openbook info to dashboard
riordanp May 14, 2024
7c6d2ba
dedupe packages
riordanp May 14, 2024
033aa83
make it prettier
riordanp May 14, 2024
fcce712
remove network concurrency to get build passing
riordanp May 14, 2024
f294a7f
big stupid merge
riordanp May 15, 2024
3728cb0
Merge branch 'main' into pan/openbook-v2
riordanp May 15, 2024
2e6469f
more shit
riordanp May 15, 2024
32f647f
Merge branch 'pan/openbook-v2' of github.com:blockworks-foundation/ma…
riordanp May 15, 2024
87ed53f
yarn install & yarn-deduplicate
riordanp May 15, 2024
766f9a6
run prettier
riordanp May 15, 2024
c3944c7
update openbook
riordanp May 15, 2024
c3867b6
remove testnet option
riordanp May 15, 2024
d63aad5
deduplicate AGAIN
riordanp May 15, 2024
7e06562
remove anchor resolution
riordanp May 15, 2024
0156618
FUCKING DEDUPE AGAIN
riordanp May 15, 2024
9a4686b
group is hardcoded in way too many places
riordanp May 15, 2024
f47828e
new group
riordanp May 15, 2024
04b5e92
use client feature branch, order form and trade history fixes
riordanp May 16, 2024
e0e776f
dedupe
riordanp May 16, 2024
a2f2be7
update clients, use the same bn type everywhere
riordanp May 17, 2024
4b1c821
add MarketAdaper interface
mschneider May 17, 2024
b31c8d7
use marketAdapter for orderbook
mschneider May 17, 2024
df3c346
fix typescript compiler issue that can not resolve static methods pro…
mschneider May 17, 2024
5b0fa47
MarketAdapter now supports all 3 CLOBs
mschneider May 18, 2024
646b695
remove old book decoding helpers
mschneider May 18, 2024
867d8b5
reload all open orders when viewing unowned account
mschneider May 20, 2024
39378d2
simplify type checks a bit and make ui load
mschneider May 20, 2024
9585f18
start using marketAdapter more
mschneider May 20, 2024
cb63e57
more marketAdapter
mschneider May 20, 2024
f9e05a6
add unsettled balances to store and clean up MarketAdapter
mschneider May 20, 2024
e798c43
Use correct mango-v4 branch
riordanp May 23, 2024
9c5b95e
market adapter place order implementation checkpoint
abrzezinski94 May 24, 2024
ae59339
reload openorders
abrzezinski94 May 27, 2024
030b16e
reload orders in market adapter
abrzezinski94 May 27, 2024
615c493
fix max amount
abrzezinski94 May 30, 2024
0ac8f0a
buy/sell btn fix
abrzezinski94 May 30, 2024
371c630
fix spot markets match
abrzezinski94 May 30, 2024
e9dc178
prevent some app crashes
riordanp May 31, 2024
8519a84
cancel order
abrzezinski94 Jun 3, 2024
9dc5929
fix order filtering
riordanp Jun 3, 2024
5341aae
cancel all openbook orders
abrzezinski94 Jun 4, 2024
61fd3c1
fix
abrzezinski94 Jun 4, 2024
760b686
cancel openbook order on trading view
abrzezinski94 Jun 4, 2024
dc72f6d
fixes
abrzezinski94 Jun 5, 2024
0709d29
deduplicate
abrzezinski94 Jun 7, 2024
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
22 changes: 12 additions & 10 deletions components/MangoProvider.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -184,15 +184,17 @@ const HydrateStore = () => {

// don't fetch serum3OpenOrders if the slot is old
if (context.slot > mangoStore.getState().mangoAccount.lastSlot) {
if (newMangoAccount.serum3Active().length > 0) {
await newMangoAccount.reloadSerum3OpenOrders(client)
// check again that the slot is still the most recent after the reloading open orders
if (context.slot > mangoStore.getState().mangoAccount.lastSlot) {
set((s) => {
s.mangoAccount.current = newMangoAccount
s.mangoAccount.lastSlot = context.slot
})
}
try {
await newMangoAccount.reloadAllOpenOrders(client)
} catch (e) {
console.error('error reloading open orders', e)
}
// check again that the slot is still the most recent after the reloading open orders
if (context.slot > mangoStore.getState().mangoAccount.lastSlot) {
set((s) => {
s.mangoAccount.current = newMangoAccount
s.mangoAccount.lastSlot = context.slot
})
}
actions.fetchOpenOrders()
}
Expand Down Expand Up @@ -236,7 +238,7 @@ const ReadOnlyMangoAccount = () => {
if (!readOnlyMangoAccount.group.equals(group.publicKey)) {
throw 'Mango account not from current group'
}
await readOnlyMangoAccount.reloadSerum3OpenOrders(client)
await readOnlyMangoAccount.reloadAllOpenOrders(client)
set((state) => {
state.mangoAccount.current = readOnlyMangoAccount
state.mangoAccount.initialLoad = false
Expand Down
18 changes: 12 additions & 6 deletions components/SideNav.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -153,6 +153,16 @@ const SideNav = ({ collapsed }: { collapsed: boolean }) => {
return themeData.sideImagePath
}, [mangoNfts, theme, themeData])

const healthRatio = useMemo(() => {
try {
if (!mangoAccount || !group) return 0
return mangoAccount.getHealthRatioUi(group, HealthType.maint)
} catch (e) {
console.error('error getting health ratio for account', e)
return 0
}
}, [mangoAccount])

return (
<>
<div
Expand Down Expand Up @@ -315,7 +325,7 @@ const SideNav = ({ collapsed }: { collapsed: boolean }) => {
collapsed={false}
icon={<PerpIcon className="h-4 w-4" />}
title={t('perp')}
pagePath="/trade?name=SOL-PERP"
pagePath="/trade?name=BTC-PERP"
hideIconBg
/>
<MenuItem
Expand Down Expand Up @@ -438,11 +448,7 @@ const SideNav = ({ collapsed }: { collapsed: boolean }) => {
collapsed={collapsed}
icon={
<HealthHeart
health={
group && mangoAccount
? mangoAccount.getHealthRatioUi(group, HealthType.maint)
: 0
}
health={group && mangoAccount ? healthRatio : 0}
size={32}
/>
}
Expand Down
12 changes: 6 additions & 6 deletions components/explore/RecentGainersLosers.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import Change from '@components/shared/Change'
import FormatNumericValue from '@components/shared/FormatNumericValue'
import TokenLogo from '@components/shared/TokenLogo'
import useListedMarketsWithMarketData, {
SerumMarketWithMarketData,
SpotMarketWithMarketData,
} from 'hooks/useListedMarketsWithMarketData'
import useMangoGroup from 'hooks/useMangoGroup'
import { useRouter } from 'next/router'
Expand All @@ -29,7 +29,7 @@ dayjs.extend(relativeTime)

export type BankWithMarketData = {
bank: Bank
market: SerumMarketWithMarketData | undefined
market: SpotMarketWithMarketData | undefined
}

const CALLOUT_TILES_WRAPPER_CLASSES =
Expand All @@ -41,16 +41,16 @@ const RecentGainersLosers = () => {
const { group } = useMangoGroup()
const { banks } = useBanks()
const {
serumMarketsWithData,
spotMarketsWithData,
perpMarketsWithData,
isLoading: loadingSerumMarkets,
} = useListedMarketsWithMarketData()
const groupLoaded = mangoStore((s) => s.groupLoaded)

const banksWithMarketData = useMemo(() => {
if (!banks.length || !group || !serumMarketsWithData.length) return []
if (!banks.length || !group || !spotMarketsWithData.length) return []
const banksWithMarketData = []
const usdcQuoteMarkets = serumMarketsWithData.filter(
const usdcQuoteMarkets = spotMarketsWithData.filter(
(market) => market.quoteTokenIndex === 0,
)
for (const bank of banks) {
Expand All @@ -64,7 +64,7 @@ const RecentGainersLosers = () => {
}
}
return banksWithMarketData
}, [banks, group, serumMarketsWithData])
}, [banks, group, spotMarketsWithData])

const newlyListedMintInfo = useMemo(() => {
if (!group) return []
Expand Down
12 changes: 6 additions & 6 deletions components/explore/Spot.tsx
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import useListedMarketsWithMarketData, {
SerumMarketWithMarketData,
SpotMarketWithMarketData,
} from 'hooks/useListedMarketsWithMarketData'
import useMangoGroup from 'hooks/useMangoGroup'
import { ChangeEvent, useMemo, useState } from 'react'
Expand All @@ -24,7 +24,7 @@ import { TOKEN_WATCHLIST_KEY } from 'utils/constants'

export type BankWithMarketData = {
bank: Bank
market: SerumMarketWithMarketData | undefined
market: SpotMarketWithMarketData | undefined
}

const generateSearchTerm = (item: BankWithMarketData, searchValue: string) => {
Expand Down Expand Up @@ -99,16 +99,16 @@ const Spot = () => {
const { group } = useMangoGroup()
const { banks } = useBanks()
const { isDesktop } = useViewport()
const { serumMarketsWithData, isLoading: loadingMarketsData } =
const { spotMarketsWithData, isLoading: loadingMarketsData } =
useListedMarketsWithMarketData()
const [sortByKey, setSortByKey] = useState<AllowedKeys>('quote_volume_24h')
const [search, setSearch] = useState('')
const [showTableView, setShowTableView] = useState(true)

const banksWithMarketData = useMemo(() => {
if (!banks.length || !group || !serumMarketsWithData.length) return []
if (!banks.length || !group || !spotMarketsWithData.length) return []
const banksWithMarketData = []
const usdcQuoteMarkets = serumMarketsWithData.filter(
const usdcQuoteMarkets = spotMarketsWithData.filter(
(market) => market.quoteTokenIndex === 0,
)
for (const bank of banks) {
Expand All @@ -122,7 +122,7 @@ const Spot = () => {
}
}
return banksWithMarketData
}, [banks, group, serumMarketsWithData])
}, [banks, group, spotMarketsWithData])

const sortedTokensToShow = useMemo(() => {
if (!banksWithMarketData.length) return []
Expand Down
4 changes: 2 additions & 2 deletions components/explore/SpotTable.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ import { useRouter } from 'next/router'
import Decimal from 'decimal.js'
import BankAmountWithValue from '@components/shared/BankAmountWithValue'
import { BankWithMarketData } from './Spot'
import { SerumMarketWithMarketData } from 'hooks/useListedMarketsWithMarketData'
import { SpotMarketWithMarketData } from 'hooks/useListedMarketsWithMarketData'
import Tooltip from '@components/shared/Tooltip'
import TableTokenName from '@components/shared/TableTokenName'
import { LinkButton } from '@components/shared/Button'
Expand All @@ -47,7 +47,7 @@ type TableData = {
change: number
depositRate: number
tokenName: string
market: SerumMarketWithMarketData | undefined
market: SpotMarketWithMarketData | undefined
price: number
priceHistory: {
price: number
Expand Down
6 changes: 6 additions & 0 deletions components/governance/GovernancePageWrapper.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -20,20 +20,26 @@ const GovernancePageWrapper = ({
const resetVoter = GovernanceStore((s) => s.resetVoter)
const realm = GovernanceStore((s) => s.realm)
const connection = mangoStore((s) => s.connection)
const isMainnet =
!connection.rpcEndpoint.includes('devnet') &&
!connection.rpcEndpoint.includes('testnet')

useEffect(() => {
if (!isMainnet) return
if (connection.rpcEndpoint) {
initConnection(connection)
}
}, [connection.rpcEndpoint])

useEffect(() => {
if (!isMainnet) return
if (connectionContext?.endpoint && realm === null) {
initRealm(connectionContext)
}
}, [connectionContext?.endpoint, realm === null])

useEffect(() => {
if (!isMainnet) return
if (
publicKey?.toBase58() &&
connectionContext?.endpoint &&
Expand Down
8 changes: 7 additions & 1 deletion components/modals/CloseAccountModal.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ import useUnsettledPerpPositions from 'hooks/useUnsettledPerpPositions'
import { getMultipleAccounts } from '@project-serum/anchor/dist/cjs/utils/rpc'
import { formatCurrencyValue } from 'utils/numbers'
import TopBarStore from '@store/topBarStore'
import { OpenOrders } from '@project-serum/serum'

const CloseAccountModal = ({ isOpen, onClose }: ModalProps) => {
const { t } = useTranslation(['close-account'])
Expand Down Expand Up @@ -84,9 +85,14 @@ const CloseAccountModal = ({ isOpen, onClose }: ModalProps) => {
if (!mangoAccount?.current) {
return
}
// TODO: add openbook v2 support
// difficult bc. we are not directly storing the addresses
// but only parsed account data
const accountKeys = [
mangoAccount.current!.publicKey,
...mangoAccount.openOrderAccounts.map((x) => x.address),
...mangoAccount.openOrderAccounts
.filter((oo) => oo instanceof OpenOrders)
.map((x) => (x as OpenOrders).address),
]
const accounts = await getMultipleAccounts(connection, accountKeys)
const lamports =
Expand Down
2 changes: 1 addition & 1 deletion components/modals/DashboardSuggestedValuesModal.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ import {
toUiDecimals,
} from '@blockworks-foundation/mango-v4'
import { AccountMeta, Transaction } from '@solana/web3.js'
import { BN } from '@project-serum/anchor'
import { BN } from '@coral-xyz/anchor'
import {
MANGO_DAO_WALLET,
MANGO_DAO_WALLET_GOVERNANCE,
Expand Down
11 changes: 7 additions & 4 deletions components/modals/MangoAccountsListModal.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -121,10 +121,13 @@ const MangoAccountsListModal = ({
toUiDecimalsForQuote(Number(acc.getEquity(group!))),
2,
)
const maintHealth = acc.getHealthRatioUi(
group!,
HealthType.maint,
)
let maintHealth
try {
maintHealth = acc.getHealthRatioUi(group!, HealthType.maint)
} catch (e) {
console.error('error getting maint health for account', e)
maintHealth = 0
}
return (
<div
className="flex h-16 w-full items-center text-th-fgd-1"
Expand Down
18 changes: 12 additions & 6 deletions components/modals/ModifyTvOrderModal.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -13,12 +13,12 @@ import {
Serum3SelfTradeBehavior,
Serum3Side,
} from '@blockworks-foundation/mango-v4'
import mangoStore from '@store/mangoStore'
import mangoStore, { OpenbookOrder } from '@store/mangoStore'
import { PublicKey } from '@solana/web3.js'
import { notify } from 'utils/notifications'
import { isMangoError } from 'types'
import Button, { LinkButton } from '@components/shared/Button'
import { findSerum3MarketPkInOpenOrders } from '@components/trade/OpenOrders'
import { findSpotMarketPkInOpenOrders } from '@components/trade/OpenOrders'
import useSelectedMarket from 'hooks/useSelectedMarket'
import {
floorToDecimal,
Expand All @@ -36,7 +36,7 @@ import SideBadge from '@components/shared/SideBadge'
import { ArrowRightIcon } from '@heroicons/react/20/solid'

interface ModifyModalProps {
order: Order | PerpOrder
order: Order | PerpOrder | OpenbookOrder
price: string
}

Expand Down Expand Up @@ -74,7 +74,7 @@ const ModifyTvOrderModal = ({
}, [serumOrPerpMarket])

const modifyOrder = useCallback(
async (o: PerpOrder | Order) => {
async (o: PerpOrder | Order | OpenbookOrder) => {
const client = mangoStore.getState().client
const group = mangoStore.getState().group
const mangoAccount = mangoStore.getState().mangoAccount.current
Expand Down Expand Up @@ -102,8 +102,14 @@ const ModifyTvOrderModal = ({
undefined,
)
} else {
const marketPk = findSerum3MarketPkInOpenOrders(o)
const marketPk = findSpotMarketPkInOpenOrders(o)
if (!marketPk) return

if (o instanceof OpenbookOrder) {
console.error('not implemented!')
return
}

const market = group.getSerum3MarketByExternalMarket(
new PublicKey(marketPk),
)
Expand Down Expand Up @@ -140,7 +146,7 @@ const ModifyTvOrderModal = ({
}
},
[
findSerum3MarketPkInOpenOrders,
findSpotMarketPkInOpenOrders,
modifiedOrderPrice,
modifiedOrderSize,
tickDecimals,
Expand Down
4 changes: 2 additions & 2 deletions components/modals/SpotMarketDetailsModal.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import { ModalProps } from '../../types/modal'
import Modal from '../shared/Modal'
import { useTranslation } from 'next-i18next'
import useSelectedMarket from 'hooks/useSelectedMarket'
import { Serum3Market } from '@blockworks-foundation/mango-v4'
import { OpenbookV2Market, Serum3Market } from '@blockworks-foundation/mango-v4'
import Button from '@components/shared/Button'
import { ExclamationTriangleIcon } from '@heroicons/react/20/solid'
import { useMemo } from 'react'
Expand All @@ -11,7 +11,7 @@ import OracleProvider from '@components/shared/OracleProvider'
import mangoStore from '@store/mangoStore'

interface SpotMarketDetailsModalProps {
market: Serum3Market | undefined
market: Serum3Market | OpenbookV2Market | undefined
}

type ModalCombinedProps = SpotMarketDetailsModalProps & ModalProps
Expand Down
6 changes: 5 additions & 1 deletion components/nftMarket/AssetBidsModal.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ import NftMarketButton from './NftMarketButton'
import Loading from '@components/shared/Loading'
import { useState } from 'react'
import { notify } from 'utils/notifications'
import { BN } from '@coral-xyz/anchor'

const AssetBidsModal = ({
isOpen,
Expand Down Expand Up @@ -79,7 +80,10 @@ const AssetBidsModal = ({
)}
</p>
<span className="font-display text-th-fgd-2">
{toUiDecimals(x.price.basisPoints, MANGO_MINT_DECIMALS)}{' '}
{toUiDecimals(
new BN(x.price.basisPoints.toString()),
MANGO_MINT_DECIMALS,
)}{' '}
MNGO
</span>
</div>
Expand Down
6 changes: 5 additions & 1 deletion components/nftMarket/MyBidsModal.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ import { useState } from 'react'
import Loading from '@components/shared/Loading'
import EmptyState from './EmptyState'
import { notify } from 'utils/notifications'
import { BN } from '@coral-xyz/anchor'

const MyBidsModal = ({ isOpen, onClose }: ModalProps) => {
const { publicKey } = useWallet()
Expand Down Expand Up @@ -81,8 +82,11 @@ const MyBidsModal = ({ isOpen, onClose }: ModalProps) => {
<p className="text-xs">
{x.asset?.json?.collection?.family || 'Unknown'}
</p>
{toUiDecimals(
new BN(x.price.basisPoints.toString()),
MANGO_MINT_DECIMALS,
)}{' '}
<span className="font-display text-th-fgd-2">
{toUiDecimals(x.price.basisPoints, MANGO_MINT_DECIMALS)}{' '}
<span className="font-body">MNGO</span>
</span>
</div>
Expand Down
Loading
Loading