From 993a01b687694995b5982d882ce19c5e57b9afb8 Mon Sep 17 00:00:00 2001 From: Tom Robiquet Date: Wed, 8 Nov 2023 10:48:51 +0100 Subject: [PATCH 1/8] check neoPools for liquidity --- lib/hooks/queries/useInfiniteMarkets.ts | 51 +++++++++++++++++-------- 1 file changed, 36 insertions(+), 15 deletions(-) diff --git a/lib/hooks/queries/useInfiniteMarkets.ts b/lib/hooks/queries/useInfiniteMarkets.ts index cfb004890..9b4acae78 100644 --- a/lib/hooks/queries/useInfiniteMarkets.ts +++ b/lib/hooks/queries/useInfiniteMarkets.ts @@ -13,6 +13,7 @@ import { MarketOutcomes } from "lib/types/markets"; import { MarketStatus } from "@zeitgeistpm/indexer"; import { hiddenMarketIds } from "lib/constants/markets"; import { marketMetaFilter } from "./constants"; +import { ScoringRule } from "@zeitgeistpm/indexer"; export const rootKey = "markets-filtered"; @@ -62,29 +63,49 @@ export const useInfiniteMarkets = ( const markets: Market[] = await sdk.model.markets.list({ where: { - ...validMarketWhereInput, - status_not_in: [MarketStatus.Destroyed], - status_in: statuses.length === 0 ? undefined : statuses, - tags_containsAny: tags?.length === 0 ? undefined : tags, - pool_isNull: withLiquidityOnly ? false : undefined, - baseAsset_in: currencies?.length !== 0 ? currencies : undefined, - ...(withLiquidityOnly - ? { - pool: { - account: { - balances_some: { - balance_gt: 0, + AND: [ + validMarketWhereInput, + { status_not_in: [MarketStatus.Destroyed] }, + { status_in: statuses.length === 0 ? undefined : statuses }, + { tags_containsAny: tags?.length === 0 ? undefined : tags }, + { baseAsset_in: currencies?.length !== 0 ? currencies : undefined }, + { + OR: [ + { + AND: [ + { scoringRule_eq: ScoringRule.Cpmm }, + { + pool_isNull: withLiquidityOnly ? false : undefined, + ...(withLiquidityOnly + ? { + pool: { + account: { + balances_some: { + balance_gt: 0, + }, + }, + }, + } + : {}), }, - }, + ], }, - } - : {}), + { + AND: [ + { scoringRule_eq: ScoringRule.Lmsr }, + { neoPool_isNull: withLiquidityOnly ? false : undefined }, + ], + }, + ], + }, + ], }, offset: !pageParam ? 0 : limit * pageParam, limit: limit, order: orderByMap[orderBy], }); + //todo: this can be fetched with the market schema const outcomes = await getOutcomesForMarkets(sdk.indexer.client, markets); let resMarkets: Array = []; From 7291f957f6a87e1628c6745ac2d50a0aaa9e8d0a Mon Sep 17 00:00:00 2001 From: Tom Robiquet Date: Wed, 8 Nov 2023 10:51:47 +0100 Subject: [PATCH 2/8] todos --- lib/gql/featured-markets.ts | 3 ++- lib/gql/trending-markets.ts | 4 +++- lib/hooks/queries/useInfiniteMarkets.ts | 2 ++ 3 files changed, 7 insertions(+), 2 deletions(-) diff --git a/lib/gql/featured-markets.ts b/lib/gql/featured-markets.ts index a77119945..58f813a03 100644 --- a/lib/gql/featured-markets.ts +++ b/lib/gql/featured-markets.ts @@ -52,6 +52,7 @@ const marketQuery = gql` } `; +//switch to search with marketid const assetsQuery = gql` query Assets($poolId: Int) { assets(where: { pool: { poolId_eq: $poolId } }) { @@ -154,7 +155,7 @@ const getFeaturedMarkets = async ( creation: market.creation, creator: market.creator, img: market.img, - prediction: prediction, + prediction: prediction, //here volume: new Decimal(pool.volume).div(ZTG).toNumber(), baseAsset: market.baseAsset, outcomes: marketCategories, diff --git a/lib/gql/trending-markets.ts b/lib/gql/trending-markets.ts index 554fc28fa..a79000bc4 100644 --- a/lib/gql/trending-markets.ts +++ b/lib/gql/trending-markets.ts @@ -77,6 +77,7 @@ const marketQuery = gql` } `; +//switch to search with marketid const assetsQuery = gql` query Assets($poolId: Int) { assets(where: { pool: { poolId_eq: $poolId } }) { @@ -149,6 +150,7 @@ const getTrendingMarkets = async ( const market = marketsRes.markets[0]; + // todo can be fetched with markets const assetsRes = await client.request<{ assets: { pool: { poolId: number }; @@ -181,7 +183,7 @@ const getTrendingMarkets = async ( question: market.question, creation: market.creation, img: market.img, - prediction: prediction, + prediction: prediction, //here creator: market.creator, volume: Number(new Decimal(market.pool.volume).div(ZTG).toFixed(0)), baseAsset: market.baseAsset, diff --git a/lib/hooks/queries/useInfiniteMarkets.ts b/lib/hooks/queries/useInfiniteMarkets.ts index 9b4acae78..95aa5524b 100644 --- a/lib/hooks/queries/useInfiniteMarkets.ts +++ b/lib/hooks/queries/useInfiniteMarkets.ts @@ -107,6 +107,8 @@ export const useInfiniteMarkets = ( //todo: this can be fetched with the market schema const outcomes = await getOutcomesForMarkets(sdk.indexer.client, markets); + console.log(outcomes); + console.log(markets); let resMarkets: Array = []; From 532349e27d4020d51e2ba1b4dc2c8a4ed0022826 Mon Sep 17 00:00:00 2001 From: Tom Robiquet Date: Wed, 8 Nov 2023 11:32:52 +0100 Subject: [PATCH 3/8] simplify query --- lib/hooks/queries/useInfiniteMarkets.ts | 46 +++++++++++-------------- 1 file changed, 21 insertions(+), 25 deletions(-) diff --git a/lib/hooks/queries/useInfiniteMarkets.ts b/lib/hooks/queries/useInfiniteMarkets.ts index 95aa5524b..657432b50 100644 --- a/lib/hooks/queries/useInfiniteMarkets.ts +++ b/lib/hooks/queries/useInfiniteMarkets.ts @@ -64,37 +64,33 @@ export const useInfiniteMarkets = ( const markets: Market[] = await sdk.model.markets.list({ where: { AND: [ - validMarketWhereInput, - { status_not_in: [MarketStatus.Destroyed] }, - { status_in: statuses.length === 0 ? undefined : statuses }, - { tags_containsAny: tags?.length === 0 ? undefined : tags }, - { baseAsset_in: currencies?.length !== 0 ? currencies : undefined }, + { + ...validMarketWhereInput, + status_not_in: [MarketStatus.Destroyed], + status_in: statuses.length === 0 ? undefined : statuses, + tags_containsAny: tags?.length === 0 ? undefined : tags, + baseAsset_in: currencies?.length !== 0 ? currencies : undefined, + }, { OR: [ { - AND: [ - { scoringRule_eq: ScoringRule.Cpmm }, - { - pool_isNull: withLiquidityOnly ? false : undefined, - ...(withLiquidityOnly - ? { - pool: { - account: { - balances_some: { - balance_gt: 0, - }, - }, + scoringRule_eq: ScoringRule.Cpmm, + pool_isNull: withLiquidityOnly ? false : undefined, + ...(withLiquidityOnly + ? { + pool: { + account: { + balances_some: { + balance_gt: 0, }, - } - : {}), - }, - ], + }, + }, + } + : {}), }, { - AND: [ - { scoringRule_eq: ScoringRule.Lmsr }, - { neoPool_isNull: withLiquidityOnly ? false : undefined }, - ], + scoringRule_eq: ScoringRule.Lmsr, + neoPool_isNull: withLiquidityOnly ? false : undefined, }, ], }, From 3352248ee37cbd3a45069bd58169c6248e30a3d0 Mon Sep 17 00:00:00 2001 From: Tom Robiquet Date: Fri, 10 Nov 2023 11:28:07 +0100 Subject: [PATCH 4/8] request market list in a single call + amm2 support --- .env.example | 2 +- lib/hooks/queries/useInfiniteMarkets.ts | 33 +++++++++++----------- package.json | 4 +-- yarn.lock | 37 ++++++++++++++++--------- 4 files changed, 43 insertions(+), 33 deletions(-) diff --git a/.env.example b/.env.example index 8752a9076..04e49f347 100644 --- a/.env.example +++ b/.env.example @@ -24,7 +24,7 @@ NEXT_PUBLIC_AVATAR_COLLECTION_ID="2e55d4bf2e85715b63-ZEITASTAGE" NEXT_PUBLIC_SINGULAR_URL="https://singular-rmrk2-dev.vercel.app" NEXT_PUBLIC_RMRK_INDEXER_API="https://gql2.rmrk.dev/v1/graphql" NEXT_PUBLIC_IPFS_NODE="http://ipfs.zeitgeist.pm:5001" -NEXT_PUBLIC_RMRK_CHAIN_RPC_NODE="wss://staging.node.rmrk.app" +NEXT_PUBLIC_RMRK_CHAIN_RPC_NODE="wss://kusama-node-staging.rmrk.link/" NEXT_PUBLIC_AVATAR_API_HOST="https://avatar-bsr.zeitgeist.pm/" NEXT_PUBLIC_MIGRATION_IN_PROGRESS=false diff --git a/lib/hooks/queries/useInfiniteMarkets.ts b/lib/hooks/queries/useInfiniteMarkets.ts index 657432b50..6eb7aea5b 100644 --- a/lib/hooks/queries/useInfiniteMarkets.ts +++ b/lib/hooks/queries/useInfiniteMarkets.ts @@ -101,25 +101,24 @@ export const useInfiniteMarkets = ( order: orderByMap[orderBy], }); - //todo: this can be fetched with the market schema - const outcomes = await getOutcomesForMarkets(sdk.indexer.client, markets); - console.log(outcomes); - console.log(markets); + const resMarkets: Array = markets.map((market) => { + const outcomes: MarketOutcomes = market.assets.map((asset, index) => { + return { + price: asset.price, + name: market.categories?.[index].name ?? "", + assetId: asset.assetId, + amountInPool: asset.amountInPool, + }; + }); - let resMarkets: Array = []; + const prediction = getCurrentPrediction(outcomes, market); - for (const m of markets) { - const marketOutcomes = outcomes[m.marketId]; - const prediction = - m.pool != null - ? getCurrentPrediction(marketOutcomes, m as any) - : { name: "None", price: 0 }; - - resMarkets = [ - ...resMarkets, - { ...m, outcomes: marketOutcomes, prediction }, - ]; - } + return { + ...market, + outcomes, + prediction, + }; + }); return { data: resMarkets, diff --git a/package.json b/package.json index 25acdcd45..24776496d 100644 --- a/package.json +++ b/package.json @@ -39,11 +39,11 @@ "@web3auth/modal": "^7.0.4", "@yornaath/batshit": "^0.7.1", "@yornaath/batshit-devtools-react": "^0.5.4", - "@zeitgeistpm/augment-api": "2.22.0", + "@zeitgeistpm/augment-api": "2.23.1", "@zeitgeistpm/avatara-nft-sdk": "^1.3.1", "@zeitgeistpm/avatara-react": "^1.3.2", "@zeitgeistpm/avatara-util": "^1.2.0", - "@zeitgeistpm/sdk": "2.46.0", + "@zeitgeistpm/sdk": "2.47.1", "@zeitgeistpm/utility": "^2.20.0", "axios": "^0.21.4", "boring-avatars": "^1.6.1", diff --git a/yarn.lock b/yarn.lock index 5a0287886..5cfb8d846 100644 --- a/yarn.lock +++ b/yarn.lock @@ -4438,7 +4438,18 @@ __metadata: languageName: node linkType: hard -"@zeitgeistpm/augment-api@npm:2.22.0, @zeitgeistpm/augment-api@npm:^2.21.0, @zeitgeistpm/augment-api@npm:^2.22.0": +"@zeitgeistpm/augment-api@npm:2.23.1, @zeitgeistpm/augment-api@npm:^2.23.1": + version: 2.23.1 + resolution: "@zeitgeistpm/augment-api@npm:2.23.1" + peerDependencies: + "@polkadot/api-base": "*" + "@polkadot/rpc-core": "*" + "@polkadot/types": "*" + checksum: 87751b2b100b5bc304e0a4a925cd7bbb15fb90eb03b6ea229d8f9ec4043a33c5ee20a5a915d9576daf73cfd1b2692c2945455b2c6e43592e3be9e4d14632991f + languageName: node + linkType: hard + +"@zeitgeistpm/augment-api@npm:^2.21.0": version: 2.22.0 resolution: "@zeitgeistpm/augment-api@npm:2.22.0" peerDependencies: @@ -4515,14 +4526,14 @@ __metadata: languageName: node linkType: hard -"@zeitgeistpm/indexer@npm:^3.17.0": - version: 3.17.0 - resolution: "@zeitgeistpm/indexer@npm:3.17.0" +"@zeitgeistpm/indexer@npm:^3.18.1": + version: 3.18.1 + resolution: "@zeitgeistpm/indexer@npm:3.18.1" dependencies: graphql: ^16.6.0 graphql-request: ^5.0.0 graphql-tag: ^2.12.6 - checksum: 5ac0556457dc50bb3eaea51eb77d727ad88bb34a775b4ca88ecc396a078ecd6705dfd6d022647b3fae592acea48f6f3ab6760c730fa8d3198c8700c25f773597 + checksum: 8dd36e336f74fee95ad09c7f94f0cd0217fbc68820b661982e381fa8102fe547239ae955cc21355e94f26d6276cf4d4ee074b90715ecee00634bf9bfd4bcbc0f languageName: node linkType: hard @@ -4540,12 +4551,12 @@ __metadata: languageName: node linkType: hard -"@zeitgeistpm/sdk@npm:2.46.0": - version: 2.46.0 - resolution: "@zeitgeistpm/sdk@npm:2.46.0" +"@zeitgeistpm/sdk@npm:2.47.1": + version: 2.47.1 + resolution: "@zeitgeistpm/sdk@npm:2.47.1" dependencies: - "@zeitgeistpm/augment-api": ^2.22.0 - "@zeitgeistpm/indexer": ^3.17.0 + "@zeitgeistpm/augment-api": ^2.23.1 + "@zeitgeistpm/indexer": ^3.18.1 "@zeitgeistpm/rpc": ^2.14.0 "@zeitgeistpm/utility": ^2.24.0 "@zeitgeistpm/web3.storage": ^2.15.0 @@ -4562,7 +4573,7 @@ __metadata: "@polkadot/api": "*" "@polkadot/types": "*" "@polkadot/util": "*" - checksum: ea611d8b0b71cefb0e7cb893e0e93b18924639160ea1fff43a2a67b23e236bf1d6be55b42634ea0d98e549c6ec6dc38c2ac124d95e4c39949901b9294c0b06ef + checksum: 44186464d5d99301ac9dd3af5732fbac7aa6bde8ce38f6b2f7f49f51f7577f188af794af030107738b2e5c5dfafe798ac4809ad38950c4276717ad59aa9a71c7 languageName: node linkType: hard @@ -4620,11 +4631,11 @@ __metadata: "@web3auth/modal": ^7.0.4 "@yornaath/batshit": ^0.7.1 "@yornaath/batshit-devtools-react": ^0.5.4 - "@zeitgeistpm/augment-api": 2.22.0 + "@zeitgeistpm/augment-api": 2.23.1 "@zeitgeistpm/avatara-nft-sdk": ^1.3.1 "@zeitgeistpm/avatara-react": ^1.3.2 "@zeitgeistpm/avatara-util": ^1.2.0 - "@zeitgeistpm/sdk": 2.46.0 + "@zeitgeistpm/sdk": 2.47.1 "@zeitgeistpm/utility": ^2.20.0 autoprefixer: 10.2.5 axios: ^0.21.4 From 127fc6da0c051832ce2f6ea3874bb2916b173882 Mon Sep 17 00:00:00 2001 From: Tom Robiquet Date: Fri, 10 Nov 2023 12:00:30 +0100 Subject: [PATCH 5/8] featured market refactor --- .env.development | 2 +- components/markets/market-card/index.tsx | 17 +- lib/gql/featured-markets.ts | 209 ++++++----------------- 3 files changed, 59 insertions(+), 169 deletions(-) diff --git a/.env.development b/.env.development index 9178fe5c0..c8feca14a 100644 --- a/.env.development +++ b/.env.development @@ -23,7 +23,7 @@ NEXT_PUBLIC_AVATAR_COLLECTION_ID="2e55d4bf2e85715b63-ZEITASTAGE" NEXT_PUBLIC_SINGULAR_URL="https://singular-rmrk2-dev.vercel.app" NEXT_PUBLIC_RMRK_INDEXER_API="https://gql2.rmrk.dev/v1/graphql" NEXT_PUBLIC_IPFS_NODE="http://ipfs.zeitgeist.pm:5001" -NEXT_PUBLIC_RMRK_CHAIN_RPC_NODE="wss://staging.node.rmrk.app" +NEXT_PUBLIC_RMRK_CHAIN_RPC_NODE="wss://kusama-node-staging.rmrk.link/" NEXT_PUBLIC_AVATAR_API_HOST="https://avatar-bsr.zeitgeist.pm/" #enable in dev/staging to inspect react-query cache and query handling. diff --git a/components/markets/market-card/index.tsx b/components/markets/market-card/index.tsx index d9c85b8c5..74a2c9865 100644 --- a/components/markets/market-card/index.tsx +++ b/components/markets/market-card/index.tsx @@ -1,6 +1,5 @@ import type { ScalarRangeType } from "@zeitgeistpm/sdk"; import Skeleton from "components/ui/Skeleton"; -import { motion } from "framer-motion"; import Decimal from "decimal.js"; import { ZTG } from "lib/constants"; import { MarketOutcomes } from "lib/types/markets"; @@ -18,8 +17,6 @@ import { } from "@zeitgeistpm/sdk"; import { lookupAssetImagePath } from "lib/constants/foreign-asset"; import Image from "next/image"; -import MarketImage from "components/ui/MarketImage"; -import { useHover } from "lib/hooks/events/useHover"; export interface IndexedMarketCardData { marketId: number; @@ -28,11 +25,11 @@ export interface IndexedMarketCardData { creation: string; creator: string; outcomes: MarketOutcomes; - marketType: { categorical?: string; scalar?: string[] }; - scalarType: ScalarRangeType; + marketType: MarketType; + scalarType: ScalarRangeType | null; prediction: { name: string; price: number }; volume: number; - pool: { poolId?: number; volume: string } | null; + pool?: { poolId?: number; volume: string } | null; baseAsset: string; tags?: string[]; status: string; @@ -40,6 +37,12 @@ export interface IndexedMarketCardData { liquidity?: string; numParticipants?: number; } + +export interface MarketType { + categorical?: string; + scalar?: string[]; +} + export interface MarketCardProps extends IndexedMarketCardData { className?: string; disableLink?: boolean; @@ -256,7 +259,7 @@ export const MarketCard = ({ ) : pool && marketType?.categorical ? ( - ) : pool && Object.keys(pool).length !== 0 ? ( + ) : pool && scalarType && Object.keys(pool).length !== 0 ? ( => { const ids = await getFeaturedMarketIds(); - const featuredMarkets = await Promise.all( - ids.map(async (id) => { - const marketRes = await client.request<{ - markets: { - pool: { - poolId: number; - volume: string; - } | null; - marketId: number; - baseAsset: string; - img: string; - question: string; - creator: string; - creation: ZeitgeistPrimitivesMarketMarketCreation["type"]; - marketType: { [key: string]: string }; - scalarType: ScalarRangeType; - categories: { color: string; name: string }[]; - outcomeAssets: string[]; - tags: []; - status: string; - period: { end: string }; - }[]; - }>(marketQuery, { - marketId: id, - }); - - const market = marketRes.markets[0]; - - if (!market) return; - const pool = market.pool; - - if (!pool) { - const noPoolMarket: IndexedMarketCardData = { - marketId: market.marketId, - question: market.question, - creation: market.creation, - creator: market.creator, - pool: market.pool, - img: market.img, - prediction: { name: "None", price: 0 }, - marketType: market.marketType, - scalarType: market.scalarType, - volume: 0, - baseAsset: market.baseAsset, - outcomes: [], - tags: [], - status: market.status, - endDate: market.period.end, + const { markets } = await sdk.indexer.markets({ + where: { + marketId_in: ids, + }, + }); + + const featuredMarkets: IndexedMarketCardData[] = markets.map((market) => { + const marketCategories: MarketOutcomes = + market.categories?.map((category, index) => { + const asset = market.assets[index]; + console.log(market.marketId); + + const marketCategory: MarketOutcome = { + name: category.name ?? "", + assetId: market.outcomeAssets[index], + price: asset?.price ?? 0, }; - return noPoolMarket; - } - const assetsRes = await client.request<{ - assets: { - pool: { poolId: number }; - price: number; - assetId: string; - }[]; - }>(assetsQuery, { - poolId: pool.poolId, - }); - - const assets = assetsRes.assets; - - const prediction = getCurrentPrediction(assets, market); - - const marketCategories: MarketOutcomes = market.categories.map( - (category, index) => { - const asset = assets[index]; - const marketCategory: MarketOutcome = { - ...category, - assetId: market.outcomeAssets[index], - price: asset.price, - }; - - return marketCategory; - }, - ); - const featuredMarket: IndexedMarketCardData = { - marketId: market.marketId, - question: market.question, - creation: market.creation, - creator: market.creator, - img: market.img, - prediction: prediction, //here - volume: new Decimal(pool.volume).div(ZTG).toNumber(), - baseAsset: market.baseAsset, - outcomes: marketCategories, - pool: market.pool, - marketType: market.marketType, - scalarType: market.scalarType, - tags: market.tags, - status: market.status, - endDate: market.period.end, - }; - - return featuredMarket; - }), - ); - - const filterMarkets = featuredMarkets.filter(isPresent); - - return filterMarkets; + return marketCategory; + }) ?? []; + + const prediction = getCurrentPrediction(market.assets, market); + + const cardMarket: IndexedMarketCardData = { + marketId: market.marketId, + question: market.question ?? "", + creation: market.creation, + creator: market.creator, + img: market.img ?? "", + prediction: prediction, + volume: new Decimal(market.pool?.volume ?? 0).div(ZTG).toNumber(), + baseAsset: market.baseAsset, + outcomes: marketCategories, + pool: market.pool, + marketType: market.marketType as MarketType, + scalarType: (market.scalarType ?? null) as ScalarRangeType, + tags: market.tags?.filter(isPresent) ?? [], + status: market.status, + endDate: market.period.end, + }; + return cardMarket; + }); + + return featuredMarkets; }; export default getFeaturedMarkets; From f5da253f961351aac3d22a6397d5e4d2ded3764a Mon Sep 17 00:00:00 2001 From: Tom Robiquet Date: Fri, 10 Nov 2023 15:34:15 +0100 Subject: [PATCH 6/8] display amm2 positions on portfolio --- components/account/AccountButton.tsx | 1 - lib/hooks/queries/useAmm2MarketSpotPrices.ts | 58 +++++++++++++++ lib/hooks/queries/usePortfolioPositions.ts | 74 +++++++++++++------- 3 files changed, 108 insertions(+), 25 deletions(-) create mode 100644 lib/hooks/queries/useAmm2MarketSpotPrices.ts diff --git a/components/account/AccountButton.tsx b/components/account/AccountButton.tsx index 2395a3a2c..353b76b92 100644 --- a/components/account/AccountButton.tsx +++ b/components/account/AccountButton.tsx @@ -14,7 +14,6 @@ import { useWallet } from "lib/state/wallet"; import { formatNumberLocalized, shortenAddress } from "lib/util"; import { FaNetworkWired } from "react-icons/fa"; -import dynamic from "next/dynamic"; import Link from "next/link"; import { useRouter } from "next/router"; import React, { FC, Fragment, PropsWithChildren, useState } from "react"; diff --git a/lib/hooks/queries/useAmm2MarketSpotPrices.ts b/lib/hooks/queries/useAmm2MarketSpotPrices.ts new file mode 100644 index 000000000..37933d76b --- /dev/null +++ b/lib/hooks/queries/useAmm2MarketSpotPrices.ts @@ -0,0 +1,58 @@ +import { useQuery } from "@tanstack/react-query"; +import { AssetId, isRpcSdk } from "@zeitgeistpm/sdk"; +import Decimal from "decimal.js"; +import { calculateSpotPrice } from "lib/util/amm2"; +import { getApiAtBlock } from "lib/util/get-api-at"; +import { useSdkv2 } from "../useSdkv2"; + +export const amm2MarketSpotPricesRootKey = "amm2-market-spot-prices"; + +export const useAmm2MarketSpotPrices = ( + marketIds?: number[], + blockNumber?: number, +) => { + const [sdk, id] = useSdkv2(); + + const enabled = !!sdk && !!marketIds && isRpcSdk(sdk); + const query = useQuery( + [id, amm2MarketSpotPricesRootKey, blockNumber], + + async () => { + if (!enabled) return; + const api = await getApiAtBlock(sdk.api, blockNumber); + + const pools = await Promise.all( + marketIds.map((marketId) => api.query.neoSwaps.pools(marketId)), + ); + + const prices: { [key: string]: Decimal } = {}; + + pools.forEach((wrappedPool) => { + const pool = wrappedPool.unwrapOr(null); + if (pool) { + pool.reserves.forEach((reserve, asset) => { + prices[asset.toString().toLowerCase()] = calculateSpotPrice( + new Decimal(reserve.toString()), + new Decimal(pool.liquidityParameter.toString()), + ); + }); + } + }); + + return prices; + }, + { + enabled: enabled, + staleTime: 10_000, + }, + ); + + return query; +}; + +export const lookupAssetPrice = ( + assetId: AssetId, + prices?: { [key: string]: Decimal }, +): Decimal | undefined => { + return prices?.[JSON.stringify(assetId).toLowerCase()]; +}; diff --git a/lib/hooks/queries/usePortfolioPositions.ts b/lib/hooks/queries/usePortfolioPositions.ts index 923724ebf..c9e3985aa 100644 --- a/lib/hooks/queries/usePortfolioPositions.ts +++ b/lib/hooks/queries/usePortfolioPositions.ts @@ -44,6 +44,11 @@ import { ForeignAssetPrices, useAllForeignAssetUsdPrices, } from "./useAssetUsdPrice"; +import { ScoringRule } from "@zeitgeistpm/indexer"; +import { + lookupAssetPrice, + useAmm2MarketSpotPrices, +} from "./useAmm2MarketSpotPrices"; export type UsePortfolioPositions = { /** @@ -74,9 +79,9 @@ export type Position = { */ market: FullMarketFragment; /** - * The pool related to the position. + * The cpmm pool related to the position. */ - pool: IndexedPool; + pool?: IndexedPool; /** * The outcome of the position. Name of the outcome. */ @@ -113,7 +118,7 @@ export type Position = { * The total issuance of the positions pool shares. * @nb This is only available for pool share positions. */ - totalIssuance: Decimal; + totalIssuance?: Decimal; /** * The change in the price of the position the last 24 hours. */ @@ -195,6 +200,16 @@ export const usePortfolioPositions = ( const pools = usePoolsByIds(filter); const markets = useMarketsByIds(filter); + const amm2MarketIds = markets.data + ?.filter((market) => market.scoringRule === ScoringRule.Lmsr) + .map((m) => m.marketId); + + const { data: amm2SpotPrices } = useAmm2MarketSpotPrices(amm2MarketIds); + + const { data: amm2SpotPrices24HoursAgo } = useAmm2MarketSpotPrices( + amm2MarketIds, + block24HoursAgo, + ); const poolAccountIds = usePoolAccountIds(pools.data); @@ -322,21 +337,23 @@ export const usePortfolioPositions = ( pool = pools.data?.find((pool) => pool.marketId === marketId); } - if (!market || !pool) { + if (!market) { continue; } const balance = address ? userAssetBalances?.get(address, assetId)?.data?.balance : undefined; - const totalIssuanceForPoolQuery = poolsTotalIssuance[pool.poolId]; - const totalIssuanceData = poolsTotalIssuance[pool.poolId]?.data; + const totalIssuanceForPoolQuery = pool && poolsTotalIssuance[pool.poolId]; + const totalIssuanceData = pool && poolsTotalIssuance[pool.poolId]?.data; const userBalance = new Decimal(balance?.free.toNumber() ?? 0); - const totalIssuance = new Decimal( - totalIssuanceForPoolQuery.data?.totalIssuance.toString() ?? 0, - ); + const totalIssuance = + totalIssuanceForPoolQuery && + new Decimal( + totalIssuanceForPoolQuery.data?.totalIssuance.toString() ?? 0, + ); let price: Decimal | undefined; let price24HoursAgo: Decimal | undefined; @@ -346,23 +363,32 @@ export const usePortfolioPositions = ( price = calcResolvedMarketPrices(market).get(getIndexOf(assetId)); price24HoursAgo = price; } else { - price = - calculatePrice( - pool, + if (market.scoringRule === ScoringRule.Cpmm && pool) { + price = + calculatePrice( + pool, + assetId, + poolsZtgBalances.data, + poolAssetBalances, + ) ?? undefined; + + price24HoursAgo = + calculatePrice( + pool, + assetId, + poolsZtgBalances24HoursAgo.data, + poolAssetBalances24HoursAgo, + ) ?? undefined; + } else if (market.scoringRule === ScoringRule.Lmsr) { + price = lookupAssetPrice(assetId, amm2SpotPrices); + + price24HoursAgo = lookupAssetPrice( assetId, - poolsZtgBalances.data, - poolAssetBalances, - ) ?? undefined; - - price24HoursAgo = - calculatePrice( - pool, - assetId, - poolsZtgBalances24HoursAgo.data, - poolAssetBalances24HoursAgo, - ) ?? undefined; + amm2SpotPrices24HoursAgo, + ); + } } - } else if (IOPoolShareAssetId.is(assetId)) { + } else if (IOPoolShareAssetId.is(assetId) && pool) { const poolAssetIds = pool.weights .map((w) => parseAssetId(w.assetId).unwrap()) .filter(IOMarketOutcomeAssetId.is.bind(IOMarketOutcomeAssetId)); From d2eaf27ec53685869e46cde094063645a9a3d7ea Mon Sep 17 00:00:00 2001 From: Tom Robiquet Date: Fri, 10 Nov 2023 15:38:49 +0100 Subject: [PATCH 7/8] remove comments --- lib/gql/trending-markets.ts | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/lib/gql/trending-markets.ts b/lib/gql/trending-markets.ts index a79000bc4..554fc28fa 100644 --- a/lib/gql/trending-markets.ts +++ b/lib/gql/trending-markets.ts @@ -77,7 +77,6 @@ const marketQuery = gql` } `; -//switch to search with marketid const assetsQuery = gql` query Assets($poolId: Int) { assets(where: { pool: { poolId_eq: $poolId } }) { @@ -150,7 +149,6 @@ const getTrendingMarkets = async ( const market = marketsRes.markets[0]; - // todo can be fetched with markets const assetsRes = await client.request<{ assets: { pool: { poolId: number }; @@ -183,7 +181,7 @@ const getTrendingMarkets = async ( question: market.question, creation: market.creation, img: market.img, - prediction: prediction, //here + prediction: prediction, creator: market.creator, volume: Number(new Decimal(market.pool.volume).div(ZTG).toFixed(0)), baseAsset: market.baseAsset, From 8214721a252555511be6fda7288ea245ef8b791b Mon Sep 17 00:00:00 2001 From: Tom Robiquet Date: Mon, 13 Nov 2023 14:16:47 +0100 Subject: [PATCH 8/8] remove console.log --- lib/gql/featured-markets.ts | 2 -- 1 file changed, 2 deletions(-) diff --git a/lib/gql/featured-markets.ts b/lib/gql/featured-markets.ts index 1eeb5c9bf..ba9e12e71 100644 --- a/lib/gql/featured-markets.ts +++ b/lib/gql/featured-markets.ts @@ -27,8 +27,6 @@ const getFeaturedMarkets = async ( const marketCategories: MarketOutcomes = market.categories?.map((category, index) => { const asset = market.assets[index]; - console.log(market.marketId); - const marketCategory: MarketOutcome = { name: category.name ?? "", assetId: market.outcomeAssets[index],