chore: update schema for perpetuals and spots

This commit is contained in:
Madalina Raicu
2023-08-22 12:22:00 +01:00
parent b65697d096
commit 9c01a69e73
56 changed files with 938 additions and 343 deletions
@@ -13,6 +13,12 @@ query ExplorerMarket($id: ID!) {
decimals
}
}
... on Perpetual {
quoteName
settlementAsset {
decimals
}
}
}
}
}
@@ -8,7 +8,7 @@ export type ExplorerMarketQueryVariables = Types.Exact<{
}>;
export type ExplorerMarketQuery = { __typename?: 'Query', market?: { __typename?: 'Market', id: string, decimalPlaces: number, positionDecimalPlaces: number, state: Types.MarketState, tradableInstrument: { __typename?: 'TradableInstrument', instrument: { __typename?: 'Instrument', name: string, product: { __typename?: 'Future', quoteName: string, settlementAsset: { __typename?: 'Asset', decimals: number } } | { __typename?: 'Perpetual' } | { __typename?: 'Spot' } } } } | null };
export type ExplorerMarketQuery = { __typename?: 'Query', market?: { __typename?: 'Market', id: string, decimalPlaces: number, positionDecimalPlaces: number, state: Types.MarketState, tradableInstrument: { __typename?: 'TradableInstrument', instrument: { __typename?: 'Instrument', name: string, product: { __typename?: 'Future', quoteName: string, settlementAsset: { __typename?: 'Asset', decimals: number } } | { __typename?: 'Perpetual', quoteName: string, settlementAsset: { __typename?: 'Asset', decimals: number } } | { __typename?: 'Spot' } } } } | null };
export const ExplorerMarketDocument = gql`
@@ -27,6 +27,12 @@ export const ExplorerMarketDocument = gql`
decimals
}
}
... on Perpetual {
quoteName
settlementAsset {
decimals
}
}
}
}
}
@@ -24,14 +24,27 @@ import isEqual from 'lodash/isEqual';
export const MarketDetails = ({ market }: { market: MarketInfoWithData }) => {
if (!market) return null;
const settlementData = market.tradableInstrument.instrument.product
.dataSourceSpecForSettlementData.data as DataSourceDefinition;
const terminationData = market.tradableInstrument.instrument.product
.dataSourceSpecForTradingTermination.data as DataSourceDefinition;
// TODO - check settlementScheduleData for Perpetuals
const settlementData =
'dataSourceSpecForSettlementData' in
market.tradableInstrument.instrument.product
? (market.tradableInstrument.instrument.product
.dataSourceSpecForSettlementData.data as DataSourceDefinition)
: undefined;
const terminationData =
'dataSourceSpecForTradingTermination' in
market.tradableInstrument.instrument.product
? (market.tradableInstrument.instrument.product
.dataSourceSpecForTradingTermination.data as DataSourceDefinition)
: undefined;
const getSigners = (data: DataSourceDefinition) => {
if (data.sourceType.__typename === 'DataSourceDefinitionExternal') {
const signers = data.sourceType.sourceType.signers || [];
const signers =
('signers' in data.sourceType.sourceType &&
data.sourceType.sourceType.signers) ||
[];
return signers.map(({ signer }, i) => {
return (
@@ -43,10 +56,10 @@ export const MarketDetails = ({ market }: { market: MarketInfoWithData }) => {
return [];
};
const showTwoOracles = isEqual(
getSigners(settlementData),
getSigners(terminationData)
);
const showTwoOracles =
settlementData &&
terminationData &&
isEqual(getSigners(settlementData), getSigners(terminationData));
const headerClassName = 'font-alpha calt text-xl mt-4 border-b-2 pb-2';
@@ -73,8 +73,7 @@ export const MarketsTable = ({ data }: MarketsTableProps) => {
MarketFieldsFragment,
'tradableInstrument.instrument.product.settlementAsset.symbol'
>) => {
const value =
data?.tradableInstrument.instrument.product.settlementAsset;
const value = data && getAsset(data);
return value ? (
<ButtonLink
onClick={(e) => {
@@ -138,3 +137,20 @@ export const MarketsTable = ({ data }: MarketsTableProps) => {
/>
);
};
const getAsset = (
data: MarketFieldsFragment
): {
decimals: number | undefined;
symbol: string;
id: string;
} => {
// TODO to handle baseAsset for Spots
return 'settlementAsset' in data.tradableInstrument.instrument.product
? data?.tradableInstrument?.instrument?.product?.settlementAsset
: {
decimals: 0,
symbol: '',
id: '',
};
};
@@ -31,6 +31,9 @@ fragment ExplorerDeterministicOrderFields on Order {
... on Future {
quoteName
}
... on Perpetual {
quoteName
}
}
}
}
@@ -3,7 +3,7 @@ import * as Types from '@vegaprotocol/types';
import { gql } from '@apollo/client';
import * as Apollo from '@apollo/client';
const defaultOptions = {} as const;
export type ExplorerDeterministicOrderFieldsFragment = { __typename?: 'Order', id: string, type?: Types.OrderType | null, reference: string, status: Types.OrderStatus, version: string, createdAt: any, updatedAt?: any | null, expiresAt?: any | null, timeInForce: Types.OrderTimeInForce, price: string, side: Types.Side, remaining: string, size: string, rejectionReason?: Types.OrderRejectionReason | null, peggedOrder?: { __typename?: 'PeggedOrder', reference: Types.PeggedReference, offset: string } | null, party: { __typename?: 'Party', id: string }, market: { __typename?: 'Market', id: string, decimalPlaces: number, positionDecimalPlaces: number, state: Types.MarketState, tradableInstrument: { __typename?: 'TradableInstrument', instrument: { __typename?: 'Instrument', name: string, product: { __typename?: 'Future', quoteName: string } | { __typename?: 'Perpetual' } | { __typename?: 'Spot' } } } } };
export type ExplorerDeterministicOrderFieldsFragment = { __typename?: 'Order', id: string, type?: Types.OrderType | null, reference: string, status: Types.OrderStatus, version: string, createdAt: any, updatedAt?: any | null, expiresAt?: any | null, timeInForce: Types.OrderTimeInForce, price: string, side: Types.Side, remaining: string, size: string, rejectionReason?: Types.OrderRejectionReason | null, peggedOrder?: { __typename?: 'PeggedOrder', reference: Types.PeggedReference, offset: string } | null, party: { __typename?: 'Party', id: string }, market: { __typename?: 'Market', id: string, decimalPlaces: number, positionDecimalPlaces: number, state: Types.MarketState, tradableInstrument: { __typename?: 'TradableInstrument', instrument: { __typename?: 'Instrument', name: string, product: { __typename?: 'Future', quoteName: string } | { __typename?: 'Perpetual', quoteName: string } | { __typename?: 'Spot' } } } } };
export type ExplorerDeterministicOrderQueryVariables = Types.Exact<{
orderId: Types.Scalars['ID'];
@@ -11,7 +11,7 @@ export type ExplorerDeterministicOrderQueryVariables = Types.Exact<{
}>;
export type ExplorerDeterministicOrderQuery = { __typename?: 'Query', orderByID: { __typename?: 'Order', id: string, type?: Types.OrderType | null, reference: string, status: Types.OrderStatus, version: string, createdAt: any, updatedAt?: any | null, expiresAt?: any | null, timeInForce: Types.OrderTimeInForce, price: string, side: Types.Side, remaining: string, size: string, rejectionReason?: Types.OrderRejectionReason | null, peggedOrder?: { __typename?: 'PeggedOrder', reference: Types.PeggedReference, offset: string } | null, party: { __typename?: 'Party', id: string }, market: { __typename?: 'Market', id: string, decimalPlaces: number, positionDecimalPlaces: number, state: Types.MarketState, tradableInstrument: { __typename?: 'TradableInstrument', instrument: { __typename?: 'Instrument', name: string, product: { __typename?: 'Future', quoteName: string } | { __typename?: 'Perpetual' } | { __typename?: 'Spot' } } } } } };
export type ExplorerDeterministicOrderQuery = { __typename?: 'Query', orderByID: { __typename?: 'Order', id: string, type?: Types.OrderType | null, reference: string, status: Types.OrderStatus, version: string, createdAt: any, updatedAt?: any | null, expiresAt?: any | null, timeInForce: Types.OrderTimeInForce, price: string, side: Types.Side, remaining: string, size: string, rejectionReason?: Types.OrderRejectionReason | null, peggedOrder?: { __typename?: 'PeggedOrder', reference: Types.PeggedReference, offset: string } | null, party: { __typename?: 'Party', id: string }, market: { __typename?: 'Market', id: string, decimalPlaces: number, positionDecimalPlaces: number, state: Types.MarketState, tradableInstrument: { __typename?: 'TradableInstrument', instrument: { __typename?: 'Instrument', name: string, product: { __typename?: 'Future', quoteName: string } | { __typename?: 'Perpetual', quoteName: string } | { __typename?: 'Spot' } } } } } };
export const ExplorerDeterministicOrderFieldsFragmentDoc = gql`
fragment ExplorerDeterministicOrderFields on Order {
@@ -47,6 +47,9 @@ export const ExplorerDeterministicOrderFieldsFragmentDoc = gql`
... on Future {
quoteName
}
... on Perpetual {
quoteName
}
}
}
}
@@ -33,6 +33,8 @@ const PriceInMarket = ({
label = addDecimalsFormatNumber(price, data.market.decimalPlaces);
} else if (
decimalSource === 'SETTLEMENT_ASSET' &&
data.market &&
'settlementAsset' in data.market.tradableInstrument.instrument.product &&
data.market?.tradableInstrument.instrument.product.settlementAsset
) {
label = addDecimalsFormatNumber(
@@ -11,6 +11,14 @@ fragment ExplorerOracleForMarketsMarket on Market {
id
}
}
... on Perpetual {
dataSourceSpecForSettlementData {
id
}
dataSourceSpecForSettlementSchedule {
id
}
}
}
}
}
@@ -3,12 +3,12 @@ import * as Types from '@vegaprotocol/types';
import { gql } from '@apollo/client';
import * as Apollo from '@apollo/client';
const defaultOptions = {} as const;
export type ExplorerOracleForMarketsMarketFragment = { __typename?: 'Market', id: string, tradableInstrument: { __typename?: 'TradableInstrument', instrument: { __typename?: 'Instrument', product: { __typename?: 'Future', dataSourceSpecForSettlementData: { __typename?: 'DataSourceSpec', id: string }, dataSourceSpecForTradingTermination: { __typename?: 'DataSourceSpec', id: string } } | { __typename?: 'Perpetual' } | { __typename?: 'Spot' } } } };
export type ExplorerOracleForMarketsMarketFragment = { __typename?: 'Market', id: string, tradableInstrument: { __typename?: 'TradableInstrument', instrument: { __typename?: 'Instrument', product: { __typename?: 'Future', dataSourceSpecForSettlementData: { __typename?: 'DataSourceSpec', id: string }, dataSourceSpecForTradingTermination: { __typename?: 'DataSourceSpec', id: string } } | { __typename?: 'Perpetual', dataSourceSpecForSettlementData: { __typename?: 'DataSourceSpec', id: string }, dataSourceSpecForSettlementSchedule: { __typename?: 'DataSourceSpec', id: string } } | { __typename?: 'Spot' } } } };
export type ExplorerOracleFormMarketsQueryVariables = Types.Exact<{ [key: string]: never; }>;
export type ExplorerOracleFormMarketsQuery = { __typename?: 'Query', marketsConnection?: { __typename?: 'MarketConnection', edges: Array<{ __typename?: 'MarketEdge', node: { __typename?: 'Market', id: string, tradableInstrument: { __typename?: 'TradableInstrument', instrument: { __typename?: 'Instrument', product: { __typename?: 'Future', dataSourceSpecForSettlementData: { __typename?: 'DataSourceSpec', id: string }, dataSourceSpecForTradingTermination: { __typename?: 'DataSourceSpec', id: string } } | { __typename?: 'Perpetual' } | { __typename?: 'Spot' } } } } }> } | null };
export type ExplorerOracleFormMarketsQuery = { __typename?: 'Query', marketsConnection?: { __typename?: 'MarketConnection', edges: Array<{ __typename?: 'MarketEdge', node: { __typename?: 'Market', id: string, tradableInstrument: { __typename?: 'TradableInstrument', instrument: { __typename?: 'Instrument', product: { __typename?: 'Future', dataSourceSpecForSettlementData: { __typename?: 'DataSourceSpec', id: string }, dataSourceSpecForTradingTermination: { __typename?: 'DataSourceSpec', id: string } } | { __typename?: 'Perpetual', dataSourceSpecForSettlementData: { __typename?: 'DataSourceSpec', id: string }, dataSourceSpecForSettlementSchedule: { __typename?: 'DataSourceSpec', id: string } } | { __typename?: 'Spot' } } } } }> } | null };
export const ExplorerOracleForMarketsMarketFragmentDoc = gql`
fragment ExplorerOracleForMarketsMarket on Market {
@@ -24,6 +24,14 @@ export const ExplorerOracleForMarketsMarketFragmentDoc = gql`
id
}
}
... on Perpetual {
dataSourceSpecForSettlementData {
id
}
dataSourceSpecForSettlementSchedule {
id
}
}
}
}
}
@@ -10,7 +10,7 @@ interface OracleMarketsProps {
}
/**
* Slightly misleadlingly names, OracleMarkets lists the market (almost always singular)
* Slightly misleadingly names, OracleMarkets lists the market (almost always singular)
* to which an oracle is attached. It also checks what it triggers, by checking on the
* market whether it is attached to the dataSourceSpecForSettlementData or ..TradingTermination
*/
@@ -27,8 +27,10 @@ export function OracleMarkets({ id }: OracleMarketsProps) {
const m = markets.find((m) => {
const p = m.tradableInstrument.instrument.product;
if (
p.dataSourceSpecForSettlementData.id === id ||
p.dataSourceSpecForTradingTermination.id === id
('dataSourceSpecForSettlementData' in p &&
p.dataSourceSpecForSettlementData.id === id) ||
('dataSourceSpecForTradingTermination' in p &&
p.dataSourceSpecForTradingTermination.id === id)
) {
return true;
}
@@ -37,9 +39,11 @@ export function OracleMarkets({ id }: OracleMarketsProps) {
if (m && m.id) {
const type =
'dataSourceSpecForSettlementData' in
m.tradableInstrument.instrument.product &&
id ===
m.tradableInstrument.instrument.product.dataSourceSpecForSettlementData
.id
m.tradableInstrument.instrument.product
.dataSourceSpecForSettlementData.id
? 'Settlement for'
: 'Termination for';
return (
@@ -67,6 +67,9 @@ export function OracleSigners({ sourceType }: OracleDetailsSignersProps) {
if (sourceType.__typename !== 'DataSourceDefinitionExternal') {
return null;
}
if (!('signers' in sourceType.sourceType)) {
return null;
}
const signers = sourceType.sourceType.signers;
if (!signers || signers.length === 0) {
@@ -23,6 +23,9 @@ fragment ExplorerPartyAssetsAccounts on AccountBalance {
... on Future {
quoteName
}
... on Perpetual {
quoteName
}
}
}
}
@@ -3,14 +3,14 @@ import * as Types from '@vegaprotocol/types';
import { gql } from '@apollo/client';
import * as Apollo from '@apollo/client';
const defaultOptions = {} as const;
export type ExplorerPartyAssetsAccountsFragment = { __typename?: 'AccountBalance', type: Types.AccountType, balance: string, asset: { __typename?: 'Asset', name: string, id: string, decimals: number, symbol: string, source: { __typename: 'BuiltinAsset' } | { __typename: 'ERC20', contractAddress: string } }, market?: { __typename?: 'Market', id: string, decimalPlaces: number, tradableInstrument: { __typename?: 'TradableInstrument', instrument: { __typename?: 'Instrument', name: string, product: { __typename?: 'Future', quoteName: string } | { __typename?: 'Perpetual' } | { __typename?: 'Spot' } } } } | null };
export type ExplorerPartyAssetsAccountsFragment = { __typename?: 'AccountBalance', type: Types.AccountType, balance: string, asset: { __typename?: 'Asset', name: string, id: string, decimals: number, symbol: string, source: { __typename: 'BuiltinAsset' } | { __typename: 'ERC20', contractAddress: string } }, market?: { __typename?: 'Market', id: string, decimalPlaces: number, tradableInstrument: { __typename?: 'TradableInstrument', instrument: { __typename?: 'Instrument', name: string, product: { __typename?: 'Future', quoteName: string } | { __typename?: 'Perpetual', quoteName: string } | { __typename?: 'Spot' } } } } | null };
export type ExplorerPartyAssetsQueryVariables = Types.Exact<{
partyId: Types.Scalars['ID'];
}>;
export type ExplorerPartyAssetsQuery = { __typename?: 'Query', partiesConnection?: { __typename?: 'PartyConnection', edges: Array<{ __typename?: 'PartyEdge', node: { __typename?: 'Party', id: string, delegationsConnection?: { __typename?: 'DelegationsConnection', edges?: Array<{ __typename?: 'DelegationEdge', node: { __typename?: 'Delegation', amount: string, epoch: number, node: { __typename?: 'Node', id: string, name: string } } } | null> | null } | null, stakingSummary: { __typename?: 'StakingSummary', currentStakeAvailable: string, linkings: { __typename?: 'StakesConnection', edges?: Array<{ __typename?: 'StakeLinkingEdge', node: { __typename?: 'StakeLinking', amount: string } } | null> | null } }, accountsConnection?: { __typename?: 'AccountsConnection', edges?: Array<{ __typename?: 'AccountEdge', node: { __typename?: 'AccountBalance', type: Types.AccountType, balance: string, asset: { __typename?: 'Asset', name: string, id: string, decimals: number, symbol: string, source: { __typename: 'BuiltinAsset' } | { __typename: 'ERC20', contractAddress: string } }, market?: { __typename?: 'Market', id: string, decimalPlaces: number, tradableInstrument: { __typename?: 'TradableInstrument', instrument: { __typename?: 'Instrument', name: string, product: { __typename?: 'Future', quoteName: string } | { __typename?: 'Perpetual' } | { __typename?: 'Spot' } } } } | null } } | null> | null } | null } }> } | null };
export type ExplorerPartyAssetsQuery = { __typename?: 'Query', partiesConnection?: { __typename?: 'PartyConnection', edges: Array<{ __typename?: 'PartyEdge', node: { __typename?: 'Party', id: string, delegationsConnection?: { __typename?: 'DelegationsConnection', edges?: Array<{ __typename?: 'DelegationEdge', node: { __typename?: 'Delegation', amount: string, epoch: number, node: { __typename?: 'Node', id: string, name: string } } } | null> | null } | null, stakingSummary: { __typename?: 'StakingSummary', currentStakeAvailable: string, linkings: { __typename?: 'StakesConnection', edges?: Array<{ __typename?: 'StakeLinkingEdge', node: { __typename?: 'StakeLinking', amount: string } } | null> | null } }, accountsConnection?: { __typename?: 'AccountsConnection', edges?: Array<{ __typename?: 'AccountEdge', node: { __typename?: 'AccountBalance', type: Types.AccountType, balance: string, asset: { __typename?: 'Asset', name: string, id: string, decimals: number, symbol: string, source: { __typename: 'BuiltinAsset' } | { __typename: 'ERC20', contractAddress: string } }, market?: { __typename?: 'Market', id: string, decimalPlaces: number, tradableInstrument: { __typename?: 'TradableInstrument', instrument: { __typename?: 'Instrument', name: string, product: { __typename?: 'Future', quoteName: string } | { __typename?: 'Perpetual', quoteName: string } | { __typename?: 'Spot' } } } } | null } } | null> | null } | null } }> } | null };
export const ExplorerPartyAssetsAccountsFragmentDoc = gql`
fragment ExplorerPartyAssetsAccounts on AccountBalance {
@@ -38,6 +38,9 @@ export const ExplorerPartyAssetsAccountsFragmentDoc = gql`
... on Future {
quoteName
}
... on Perpetual {
quoteName
}
}
}
}
@@ -58,27 +58,46 @@ export const ProposalMarketData = ({
return null;
}
const settlementData = marketData.tradableInstrument.instrument.product
.dataSourceSpecForSettlementData.data as DataSourceDefinition;
const settlementData =
'dataSourceSpecForSettlementData' in
marketData.tradableInstrument.instrument.product &&
(marketData.tradableInstrument.instrument.product
.dataSourceSpecForSettlementData.data as DataSourceDefinition);
const parentSettlementData =
parentMarketData &&
'dataSourceSpecForSettlementData' in
parentMarketData.tradableInstrument.instrument.product &&
parentMarketData?.tradableInstrument.instrument?.product
?.dataSourceSpecForSettlementData?.data;
const terminationData = marketData.tradableInstrument.instrument.product
.dataSourceSpecForTradingTermination.data as DataSourceDefinition;
const terminationData =
'dataSourceSpecForTradingTermination' in
marketData.tradableInstrument.instrument.product &&
(marketData.tradableInstrument.instrument.product
.dataSourceSpecForTradingTermination.data as DataSourceDefinition);
const parentTerminationData =
parentMarketData &&
'dataSourceSpecForTradingTermination' in
parentMarketData.tradableInstrument.instrument.product &&
parentMarketData?.tradableInstrument.instrument?.product
?.dataSourceSpecForTradingTermination?.data;
// TODO add settlementScheduleData for Perp Proposal
const isParentSettlementDataEqual =
parentSettlementData !== undefined &&
isEqual(settlementData, parentSettlementData);
const isParentTerminationDataEqual =
parentTerminationData !== undefined &&
isEqual(terminationData, parentTerminationData);
const getSigners = (data: DataSourceDefinition) => {
if (data.sourceType.__typename === 'DataSourceDefinitionExternal') {
const signers = data.sourceType.sourceType.signers || [];
const signers =
('signers' in data.sourceType.sourceType &&
data.sourceType.sourceType.signers) ||
[];
return signers.map(({ signer }) => {
return (
@@ -129,7 +148,9 @@ export const ProposalMarketData = ({
/>
}
/>
{isEqual(
{settlementData &&
terminationData &&
isEqual(
getSigners(settlementData),
getSigners(terminationData)
) ? (
@@ -246,7 +267,7 @@ export const ProposalMarketData = ({
/>
))}
<AccordionItem
itemId="liqudity-monitoring-parameters"
itemId="liquidity-monitoring-parameters"
title={t('Liquidity monitoring parameters')}
content={
<LiquidityMonitoringParametersInfoPanel
@@ -35,6 +35,22 @@ import { HealthDialog } from '../../health-dialog';
import { Status } from '../../status';
import { intentForStatus } from '../../../lib/utils';
import { formatDistanceToNow } from 'date-fns';
import get from 'lodash/get';
export const getAsset = (
data: Market
): {
decimals?: number | undefined;
symbol?: string | undefined;
} => {
// TODO to handle baseAsset for Spots
return 'settlementAsset' in data.tradableInstrument.instrument.product
? data?.tradableInstrument?.instrument?.product?.settlementAsset
: {
decimals: undefined,
symbol: undefined,
};
};
export const MarketList = () => {
const { data, error, loading } = useMarketsLiquidity();
@@ -51,12 +67,7 @@ export const MarketList = () => {
return (
<>
<span className="leading-3">{value}</span>
<span className="leading-3">
{
data?.tradableInstrument?.instrument?.product?.settlementAsset
?.symbol
}
</span>
<span className="leading-3">{get(getAsset(data), 'symbol')}</span>
</>
);
},
@@ -87,12 +98,7 @@ export const MarketList = () => {
value,
data,
}: VegaValueFormatterParams<Market, 'data.markPrice'>) =>
value && data
? formatWithAsset(
value,
data.tradableInstrument.instrument.product.settlementAsset
)
: '-',
value && data ? formatWithAsset(value, getAsset(data)) : '-',
},
{
@@ -123,8 +129,7 @@ export const MarketList = () => {
value && data
? `${addDecimalsFormatNumber(
value,
data.tradableInstrument.instrument.product.settlementAsset
.decimals
getAsset(data).decimals || 0
)} (${displayChange(data.volumeChange)})`
: '-',
headerTooltip: t('The trade volume over the last 24h'),
@@ -138,10 +143,7 @@ export const MarketList = () => {
data,
}: VegaValueFormatterParams<Market, 'liquidityCommitted'>) =>
data && value
? formatWithAsset(
value.toString(),
data.tradableInstrument.instrument.product.settlementAsset
)
? formatWithAsset(value.toString(), getAsset(data))
: '-',
headerTooltip: t('The amount of funds allocated to provide liquidity'),
},
@@ -153,12 +155,7 @@ export const MarketList = () => {
value,
data,
}: VegaValueFormatterParams<Market, 'target'>) =>
data && value
? formatWithAsset(
value,
data.tradableInstrument.instrument.product.settlementAsset
)
: '-',
data && value ? formatWithAsset(value, getAsset(data)) : '-',
headerTooltip: t(
'The ideal committed liquidity to operate the market. If total commitment currently below this level then LPs can set the fee level with new commitment.'
),
@@ -230,10 +227,7 @@ export const MarketList = () => {
}) => (
<HealthBar
target={data.target}
decimals={
data.tradableInstrument.instrument.product.settlementAsset
.decimals
}
decimals={getAsset(data).decimals || 0}
levels={data.feeLevels}
intent={intentForStatus(value)}
/>
@@ -16,13 +16,26 @@ import { Market } from './market';
import { Header } from './header';
import { LPProvidersGrid } from './providers';
const getAsset = (
data: MarketWithData
): {
decimals?: number | undefined;
symbol?: string | undefined;
} => {
// TODO to handle baseAsset for Spots
return 'settlementAsset' in data.tradableInstrument.instrument.product
? data?.tradableInstrument?.instrument?.product?.settlementAsset
: {
decimals: 0,
symbol: '',
};
};
const formatMarket = (market: MarketWithData) => {
return {
name: market?.tradableInstrument.instrument.name,
symbol:
market?.tradableInstrument.instrument.product.settlementAsset.symbol,
settlementAsset:
market?.tradableInstrument.instrument.product.settlementAsset,
symbol: getAsset(market).symbol,
settlementAsset: getAsset(market),
targetStake: market?.data?.targetStake,
tradingMode: market?.data?.marketTradingMode,
trigger: market?.data?.trigger,
@@ -7,6 +7,7 @@ const marketTradingModeStyle = {
[Schema.MarketTradingMode.TRADING_MODE_OPENING_AUCTION]: '#0046CD',
[Schema.MarketTradingMode.TRADING_MODE_BATCH_AUCTION]: '#CF0064',
[Schema.MarketTradingMode.TRADING_MODE_NO_TRADING]: '#CF0064',
[Schema.MarketTradingMode.TRADING_MODE_SUSPENDED_VIA_GOVERNANCE]: '#CF0064',
};
export const getColorForStatus = (status: Schema.MarketTradingMode) =>
@@ -18,6 +19,8 @@ const marketTradingModeIntent = {
[Schema.MarketTradingMode.TRADING_MODE_OPENING_AUCTION]: Intent.Primary,
[Schema.MarketTradingMode.TRADING_MODE_BATCH_AUCTION]: Intent.Danger,
[Schema.MarketTradingMode.TRADING_MODE_NO_TRADING]: Intent.Danger,
[Schema.MarketTradingMode.TRADING_MODE_SUSPENDED_VIA_GOVERNANCE]:
Intent.Danger,
};
export const intentForStatus = (status: Schema.MarketTradingMode) => {
@@ -271,31 +271,34 @@ describe('Closed markets', { tags: '@smoke' }, () => {
.find('[col-id="state"]')
.should('have.text', MarketStateMapping[settledMarket.state]);
const terminationId =
'dataSourceSpecForTradingTermination' in product
? product.dataSourceSpecForTradingTermination.id
: '';
// 6001-MARK-004
// 6001-MARK-005
// 6001-MARK-009
// 6001-MARK-008
// 6001-MARK-010
cy.get(rowSelector)
.first()
.find('[col-id="settlementDate"]')
.find('[data-testid="link"]')
.should(($el) => {
const href = $el.attr('href');
expect(href).to.match(
new RegExp(
`/oracles/${product.dataSourceSpecForTradingTermination.id}`
terminationId &&
cy
.get(rowSelector)
.first()
.find('[col-id="settlementDate"]')
.find('[data-testid="link"]')
.should(($el) => {
const href = $el.attr('href');
expect(href).to.match(new RegExp(`/oracles/${terminationId}`));
})
.should('have.text', '4 days ago')
.should(
'have.attr',
'title',
getDateTimeFormat().format(
new Date(settledMarket.marketTimestamps.close)
)
);
})
.should('have.text', '4 days ago')
.should(
'have.attr',
'title',
getDateTimeFormat().format(
new Date(settledMarket.marketTimestamps.close)
)
);
// 6001-MARK-011
cy.get(rowSelector)
@@ -331,33 +334,43 @@ describe('Closed markets', { tags: '@smoke' }, () => {
)
);
const settlementDataId =
'dataSourceSpecForSettlementData' in product
? product.dataSourceSpecForSettlementData.id
: '';
// 6001-MARK-014
// 6001-MARK-015
// 6001-MARK-016
cy.get(rowSelector)
.first()
.find('[col-id="settlementDataOracleId"]')
.find('[data-testid="link"]')
.should(($el) => {
const href = $el.attr('href');
expect(href).to.match(
new RegExp(`/oracles/${product.dataSourceSpecForSettlementData.id}`)
settlementDataId &&
cy
.get(rowSelector)
.first()
.find('[col-id="settlementDataOracleId"]')
.find('[data-testid="link"]')
.should(($el) => {
const href = $el.attr('href');
expect(href).to.match(new RegExp(`/oracles/${settlementDataId}`));
})
.should(
'have.text',
addDecimalsFormatNumber(
// @ts-ignore cannot deep un-partial
specDataConnection.externalData.data.data[0].value,
settlementDataPropertyKey.numberDecimalPlaces
)
);
})
.should(
'have.text',
addDecimalsFormatNumber(
// @ts-ignore cannot deep un-partial
specDataConnection.externalData.data.data[0].value,
settlementDataPropertyKey.numberDecimalPlaces
)
);
const settlementAssetSymbol =
'settlementAsset' in product ? product.settlementAsset.symbol : '';
// 6001-MARK-018
cy.get(rowSelector)
.first()
.find('[col-id="settlementAsset"]')
.should('have.text', product.settlementAsset.symbol);
settlementAssetSymbol &&
cy
.get(rowSelector)
.first()
.find('[col-id="settlementAsset"]')
.should('have.text', settlementAssetSymbol);
// 6001-MARK-020
cy.get('.ag-pinned-right-cols-container')
@@ -2,7 +2,7 @@ import { useAssetDetailsDialogStore } from '@vegaprotocol/assets';
import { useEnvironment } from '@vegaprotocol/environment';
import { ButtonLink, Link } from '@vegaprotocol/ui-toolkit';
import { MarketProposalNotification } from '@vegaprotocol/proposals';
import type { Market } from '@vegaprotocol/markets';
import type { Market, MarketFieldsFragment } from '@vegaprotocol/markets';
import { getExpiryDate, getMarketExpiryDate } from '@vegaprotocol/utils';
import { t } from '@vegaprotocol/i18n';
import { Last24hPriceChange, Last24hVolume } from '@vegaprotocol/markets';
@@ -21,7 +21,8 @@ export const MarketHeaderStats = ({ market }: MarketHeaderStatsProps) => {
const { VEGA_EXPLORER_URL } = useEnvironment();
const { open: openAssetDetailsDialog } = useAssetDetailsDialogStore();
const asset = market?.tradableInstrument.instrument.product?.settlementAsset;
// TODO to handle baseAsset for Spots
const asset = market && getAsset(market);
return (
<>
@@ -114,8 +115,11 @@ const ExpiryTooltipContent = ({
}: ExpiryTooltipContentProps) => {
if (market?.marketTimestamps.close === null) {
const oracleId =
'dataSourceSpecForTradingTermination' in
market.tradableInstrument.instrument.product
.dataSourceSpecForTradingTermination?.id;
? market.tradableInstrument.instrument.product
.dataSourceSpecForTradingTermination?.id
: undefined;
const metadataExpiryDate = getMarketExpiryDate(
market.tradableInstrument.instrument.metadata.tags
@@ -152,3 +156,13 @@ const ExpiryTooltipContent = ({
return null;
};
const getAsset = (market: MarketFieldsFragment) => {
return 'settlementAsset' in market.tradableInstrument.instrument.product
? market?.tradableInstrument.instrument.product?.settlementAsset
: {
id: '',
symbol: '',
decimals: 0,
};
};
+18 -17
View File
@@ -4,6 +4,7 @@ import { t } from '@vegaprotocol/i18n';
import { useScreenDimensions } from '@vegaprotocol/react-helpers';
import { useThrottledDataProvider } from '@vegaprotocol/data-provider';
import { AsyncRenderer, ExternalLink, Splash } from '@vegaprotocol/ui-toolkit';
import type { MarketFieldsFragment } from '@vegaprotocol/markets';
import { marketDataProvider, useMarket } from '@vegaprotocol/markets';
import { useGlobalStore, usePageTitleStore } from '../../stores';
import { TradeGrid } from './trade-grid';
@@ -79,26 +80,14 @@ export const MarketPage = () => {
}
}, [init, view, setView]);
const pinnedAsset = getAsset(data);
const tradeView = useMemo(() => {
if (largeScreen) {
return (
<TradeGrid
market={data}
pinnedAsset={
data?.tradableInstrument.instrument.product.settlementAsset
}
/>
);
return <TradeGrid market={data} pinnedAsset={pinnedAsset} />;
}
return (
<TradePanels
market={data}
pinnedAsset={
data?.tradableInstrument.instrument.product.settlementAsset
}
/>
);
}, [largeScreen, data]);
return <TradePanels market={data} pinnedAsset={pinnedAsset} />;
}, [largeScreen, data, pinnedAsset]);
if (!data && marketId) {
return (
@@ -134,3 +123,15 @@ export const MarketPage = () => {
</AsyncRenderer>
);
};
const getAsset = (market: MarketFieldsFragment | null) => {
return market &&
'settlementAsset' in market.tradableInstrument.instrument.product
? market?.tradableInstrument.instrument.product?.settlementAsset
: {
id: '',
symbol: '',
decimals: 0,
name: '',
};
};
+30 -14
View File
@@ -11,15 +11,13 @@ import {
} from '@vegaprotocol/datagrid';
import { useMemo } from 'react';
import { t } from '@vegaprotocol/i18n';
import type { Asset } from '@vegaprotocol/types';
import { MarketState, MarketStateMapping } from '@vegaprotocol/types';
import {
addDecimalsFormatNumber,
getMarketExpiryDate,
} from '@vegaprotocol/utils';
import type {
DataSourceFilterFragment,
MarketMaybeWithData,
} from '@vegaprotocol/markets';
import type { DataSourceFilterFragment } from '@vegaprotocol/markets';
import {
MarketActionsDropdown,
closedMarketsWithDataProvider,
@@ -32,8 +30,10 @@ import { SettlementPriceCell } from './settlement-price-cell';
import { useDataProvider } from '@vegaprotocol/data-provider';
import { SuccessorMarketRenderer } from './successor-market-cell';
type SettlementAsset =
MarketMaybeWithData['tradableInstrument']['instrument']['product']['settlementAsset'];
type SettlementAsset = Pick<
Asset,
'decimals' | 'name' | 'quantum' | 'id' | 'symbol'
>;
interface Row {
id: string;
@@ -48,7 +48,7 @@ interface Row {
markPrice: string | undefined;
settlementDataOracleId: string;
settlementDataSpecBinding: string;
setlementDataSourceFilter: DataSourceFilterFragment | undefined;
settlementDataSourceFilter: DataSourceFilterFragment | undefined;
tradingTerminationOracleId: string;
settlementAsset: SettlementAsset;
productType: string;
@@ -64,15 +64,18 @@ export const Closed = () => {
const instrument = market.tradableInstrument.instrument;
const spec =
'dataSourceSpecForSettlementData' in instrument.product &&
instrument.product.dataSourceSpecForSettlementData.data.sourceType
.__typename === 'DataSourceDefinitionExternal'
? instrument.product.dataSourceSpecForSettlementData.data.sourceType
.sourceType
: undefined;
const filters = spec?.filters || [];
const filters = (spec && 'filters' in spec && spec.filters) || [];
const settlementDataSpecBinding =
instrument.product.dataSourceSpecBinding.settlementDataProperty;
'dataSourceSpecBinding' in instrument.product
? instrument.product.dataSourceSpecBinding.settlementDataProperty
: '';
const filter = filters?.find((filter) => {
return filter.key.name === settlementDataSpecBinding;
});
@@ -89,12 +92,25 @@ export const Closed = () => {
bestOfferPrice: market.data?.bestOfferPrice,
markPrice: market.data?.markPrice,
settlementDataOracleId:
instrument.product.dataSourceSpecForSettlementData.id,
'dataSourceSpecForSettlementData' in instrument.product
? instrument.product.dataSourceSpecForSettlementData.id
: '',
settlementDataSpecBinding,
setlementDataSourceFilter: filter,
settlementDataSourceFilter: filter,
tradingTerminationOracleId:
instrument.product.dataSourceSpecForTradingTermination.id,
settlementAsset: instrument.product.settlementAsset,
'dataSourceSpecForTradingTermination' in instrument.product
? instrument.product.dataSourceSpecForTradingTermination.id
: '',
settlementAsset:
'settlementAsset' in instrument.product
? instrument.product.settlementAsset
: {
id: '',
decimals: 0,
quantum: '0',
name: '',
symbol: '',
},
productType: instrument.product.__typename || '',
};
@@ -233,7 +249,7 @@ const ClosedMarketsDataGrid = ({
<SettlementPriceCell
oracleSpecId={value}
settlementDataSpecBinding={data?.settlementDataSpecBinding}
filter={data?.setlementDataSourceFilter}
filter={data?.settlementDataSourceFilter}
/>
),
},
@@ -130,11 +130,16 @@ const AccountHistoryManager = ({
DateRange.RANGE_1M
);
const [market, setMarket] = useState<Market | null>(null);
const marketFilterCb = useCallback(
(item: Market) =>
!asset?.id ||
item.tradableInstrument.instrument.product.settlementAsset.id ===
asset?.id,
(item: Market) => {
// TODO to handle baseAsset for Spots
const itemAsset =
'settlementAsset' in item.tradableInstrument.instrument.product
? item.tradableInstrument.instrument.product.settlementAsset
: undefined;
return !asset?.id || itemAsset?.id === asset?.id;
},
[asset?.id]
);
const markets = useMemo<Market[] | null>(() => {
@@ -153,8 +158,12 @@ const AccountHistoryManager = ({
const resolveMarket = useCallback(
(m: Market) => {
setMarket(m);
const newAssetId =
m.tradableInstrument.instrument.product.settlementAsset.id;
// TODO to handle baseAsset for Spots
const itemAsset =
'settlementAsset' in m.tradableInstrument.instrument.product
? m.tradableInstrument.instrument.product.settlementAsset
: undefined;
const newAssetId = itemAsset?.id;
const newAsset = assets.find((item) => item.id === newAssetId);
if ((!asset || (assets && newAssetId !== asset.id)) && newAsset) {
setAssetId(newAsset.id);
@@ -259,10 +268,15 @@ const AccountHistoryManager = ({
}, [markets, market, accountType, resolveMarket]);
useEffect(() => {
// TODO to handle baseAsset for Spots
const itemAsset =
market &&
'settlementAsset' in market.tradableInstrument.instrument.product
? market?.tradableInstrument.instrument.product.settlementAsset
: undefined;
if (
accountType !== Schema.AccountType.ACCOUNT_TYPE_MARGIN ||
market?.tradableInstrument.instrument.product.settlementAsset.id !==
asset?.id
itemAsset?.id !== asset?.id
) {
setMarket(null);
}
@@ -42,12 +42,15 @@ export const LiquidityContainer = ({
skip: !marketId,
});
const assetDecimalPlaces =
market?.tradableInstrument.instrument.product.settlementAsset.decimals || 0;
const quantum =
market?.tradableInstrument.instrument.product.settlementAsset.quantum || 0;
const symbol =
market?.tradableInstrument.instrument.product.settlementAsset.symbol;
// TODO to handle baseAsset for Spots
const itemAsset =
market && 'settlementAsset' in market.tradableInstrument.instrument.product
? market.tradableInstrument.instrument.product.settlementAsset
: undefined;
const assetDecimalPlaces = itemAsset?.decimals || 0;
const quantum = itemAsset?.quantum || 0;
const symbol = itemAsset?.symbol;
const { params } = useNetworkParams([
NetworkParams.market_liquidity_stakeToCcyVolume,
@@ -24,10 +24,15 @@ export const LiquidityHeader = () => {
const { data: marketData } = useStaticMarketData(marketId);
const targetStake = marketData?.targetStake;
const suppliedStake = marketData?.suppliedStake;
const assetDecimalPlaces =
market?.tradableInstrument.instrument.product.settlementAsset.decimals || 0;
const symbol =
market?.tradableInstrument.instrument.product.settlementAsset.symbol;
// TODO to handle baseAsset for Spots
const asset =
market && 'settlementAsset' in market.tradableInstrument.instrument.product
? market.tradableInstrument.instrument.product.settlementAsset
: undefined;
const assetDecimalPlaces = asset?.decimals || 0;
const symbol = asset?.symbol;
const { params } = useNetworkParams([
NetworkParams.market_liquidity_stakeToCcyVolume,
@@ -33,7 +33,7 @@ export const AssetDropdown = ({
}
>
<DropdownMenuContent>
{assets?.map((a) => {
{assets?.filter(Boolean).map((a) => {
return (
<DropdownMenuCheckboxItem
key={a.id}
@@ -66,7 +66,7 @@ const TriggerText = ({
if (checkedAssets.length === 1) {
const assetId = checkedAssets[0];
const asset = assets.find((a) => a.id === assetId);
const asset = assets.find((a) => a?.id === assetId);
text = asset ? asset.symbol : t('Asset (1)');
} else if (checkedAssets.length > 1) {
text = t(`${checkedAssets.length} Assets`);
@@ -108,14 +108,17 @@ const MarketData = ({
</p>
)}
</div>
<div
className="w-1/5 text-xs lg:text-sm whitespace-nowrap text-ellipsis overflow-hidden"
title={instrument.product.settlementAsset.symbol}
data-testid="market-selector-price"
role="gridcell"
>
{price} {instrument.product.settlementAsset.symbol}
</div>
{/* TODO to handle baseAsset for Spots */}
{instrument.product && 'settlementAsset' in instrument.product && (
<div
className="w-1/5 text-xs lg:text-sm whitespace-nowrap text-ellipsis overflow-hidden"
title={instrument.product.settlementAsset.symbol}
data-testid="market-selector-price"
role="gridcell"
>
{price} {instrument.product.settlementAsset.symbol}
</div>
)}
<div
className="w-1/5 text-xs lg:text-sm text-right whitespace-nowrap text-ellipsis overflow-hidden"
title={t('24h vol')}
@@ -71,9 +71,14 @@ export const MarketSelector = ({
</div>
<AssetDropdown
assets={uniqBy(
data?.map(
(d) => d.tradableInstrument.instrument.product.settlementAsset
),
data?.map((d) => {
// TODO to handle baseAsset for Spots
const asset =
'settlementAsset' in d.tradableInstrument.instrument.product
? d.tradableInstrument.instrument.product.settlementAsset
: { id: '', symbol: '' };
return asset;
}),
'id'
)}
checkedAssets={filter.assets}
@@ -39,9 +39,12 @@ export const useMarketSelectorList = ({
})
.filter((m) => {
if (assets.length === 0) return true;
return assets.includes(
m.tradableInstrument.instrument.product.settlementAsset.id
);
// TODO to handle baseAsset for Spots
const asset =
'settlementAsset' in m.tradableInstrument.instrument.product
? m.tradableInstrument.instrument.product.settlementAsset
: { id: '', symbol: '' };
return assets.includes(asset?.id);
})
// filter based on search term
.filter((m) => {
@@ -7,7 +7,7 @@ import { FeesBreakdown } from '@vegaprotocol/markets';
import type { OrderSubmissionBody } from '@vegaprotocol/wallet';
import { useVegaWallet } from '@vegaprotocol/wallet';
import type { Market } from '@vegaprotocol/markets';
import type { Market, MarketFieldsFragment } from '@vegaprotocol/markets';
import type { EstimatePositionQuery } from '@vegaprotocol/positions';
import { AccountBreakdownDialog } from '@vegaprotocol/accounts';
@@ -90,11 +90,10 @@ export const DealTicketFeeDetails = ({
notionalSize,
}: DealTicketFeeDetailsProps) => {
const feeEstimate = useEstimateFees(order);
const { settlementAsset: asset } =
market.tradableInstrument.instrument.product;
const asset = getAsset(market);
const { decimals: assetDecimals, quantum } = asset;
const marketDecimals = market.decimalPlaces;
const quoteName = market.tradableInstrument.instrument.product.quoteName;
const quoteName = getQuote(market);
return (
<>
@@ -164,8 +163,7 @@ export const DealTicketMarginDetails = ({
const marginEstimate = positionEstimate?.margin;
const totalBalance =
BigInt(generalAccountBalance || '0') + BigInt(marginAccountBalance || '0');
const { settlementAsset: asset } =
market.tradableInstrument.instrument.product;
const asset = getAsset(market);
const { decimals: assetDecimals, quantum } = asset;
let marginRequiredBestCase: string | undefined = undefined;
let marginRequiredWorstCase: string | undefined = undefined;
@@ -304,7 +302,7 @@ export const DealTicketMarginDetails = ({
[]
);
const quoteName = market.tradableInstrument.instrument.product.quoteName;
const quoteName = getQuote(market);
return (
<>
@@ -376,3 +374,22 @@ export const DealTicketMarginDetails = ({
</>
);
};
const getAsset = (market: MarketFieldsFragment) => {
// TODO update with baseAsset for Spots
return 'settlementAsset' in market.tradableInstrument.instrument.product
? market.tradableInstrument.instrument.product.settlementAsset
: {
quantum: '0',
decimals: 0,
symbol: '',
id: '',
};
};
const getQuote = (market: MarketFieldsFragment) => {
// TODO update with quoteAsset for Spots
return 'quoteName' in market.tradableInstrument.instrument.product
? market.tradableInstrument.instrument.product.quoteName
: '';
};
@@ -17,7 +17,10 @@ export const DealTicketLimitAmount = ({
}: DealTicketLimitAmountProps) => {
const priceStep = toDecimal(market?.decimalPlaces);
const sizeStep = toDecimal(market?.positionDecimalPlaces);
const quoteName = market.tradableInstrument.instrument.product.quoteName;
const quoteName =
'quoteName' in market.tradableInstrument.instrument.product
? market.tradableInstrument.instrument.product.quoteName
: '';
const renderError = () => {
if (sizeError) {
@@ -9,6 +9,7 @@ import { isMarketInAuction } from '@vegaprotocol/markets';
import type { DealTicketAmountProps } from './deal-ticket-amount';
import { Controller } from 'react-hook-form';
import classNames from 'classnames';
import get from 'lodash/get';
export type DealTicketMarketAmountProps = Omit<DealTicketAmountProps, 'type'>;
@@ -19,7 +20,10 @@ export const DealTicketMarketAmount = ({
marketPrice,
sizeError,
}: DealTicketMarketAmountProps) => {
const quoteName = market.tradableInstrument.instrument.product.quoteName;
const quoteName = get(
market.tradableInstrument.instrument.product,
'quoteName'
);
const sizeStep = toDecimal(market?.positionDecimalPlaces);
const price = marketPrice;
@@ -150,8 +150,30 @@ export const StopOrder = ({ market, marketPrice, submit }: StopOrderProps) => {
return () => subscription.unsubscribe();
}, [watch, market.id, updateStoredFormValues]);
const { quoteName, settlementAsset: asset } =
market.tradableInstrument.instrument.product;
let quoteName,
asset: {
id: string;
symbol: string;
name: string;
decimals: number;
quantum: string;
} | null = null;
if (market.tradableInstrument.instrument.product.__typename === 'Future') {
quoteName = market.tradableInstrument.instrument.product.quoteName;
asset = market.tradableInstrument.instrument.product.settlementAsset;
}
if (market.tradableInstrument.instrument.product.__typename === 'Perpetual') {
quoteName = market.tradableInstrument.instrument.product.quoteName;
asset = market.tradableInstrument.instrument.product.settlementAsset;
}
if (market.tradableInstrument.instrument.product.__typename === 'Spot') {
// TODO add baseAsset and quoteAsset for Spots
// quoteName = market.tradableInstrument.instrument.product.quoteAsset;
// asset = market.tradableInstrument.instrument.product.baseAsset;
}
const sizeStep = toDecimal(market?.positionDecimalPlaces);
const priceStep = toDecimal(market?.decimalPlaces);
@@ -254,7 +276,7 @@ export const StopOrder = ({ market, marketPrice, submit }: StopOrderProps) => {
data-testid="triggerPrice"
type="number"
step={priceStep}
appendElement={asset.symbol}
appendElement={asset?.symbol}
value={value || ''}
{...props}
/>
@@ -570,7 +592,7 @@ export const StopOrder = ({ market, marketPrice, submit }: StopOrderProps) => {
type,
}}
notionalSize={notionalSize}
assetSymbol={asset.symbol}
assetSymbol={asset?.symbol || ''}
market={market}
/>
</form>
@@ -45,6 +45,7 @@ import { SummaryValidationType } from '../../constants';
import type {
Market,
MarketData,
MarketFieldsFragment,
StaticMarketData,
} from '@vegaprotocol/markets';
import { MarginWarning } from '../deal-ticket-validation/margin-warning';
@@ -145,7 +146,7 @@ export const DealTicket = ({
});
const lastSubmitTime = useRef(0);
const asset = market.tradableInstrument.instrument.product.settlementAsset;
const asset = getAsset(market);
const {
accountBalance: marginAccountBalance,
loading: loadingMarginAccountBalance,
@@ -249,8 +250,7 @@ export const DealTicket = ({
fetchPolicy: 'no-cache',
});
const assetSymbol =
market.tradableInstrument.instrument.product.settlementAsset.symbol;
const assetSymbol = getAsset(market).symbol;
const summaryError = useMemo(() => {
if (!pubKey) {
@@ -658,3 +658,15 @@ const SummaryMessage = memo(
return null;
}
);
const getAsset = (market: MarketFieldsFragment) => {
// TODO add baseAsset for Spot
return 'settlementAsset' in market.tradableInstrument.instrument.product
? market.tradableInstrument.instrument.product.settlementAsset
: {
id: '',
symbol: '',
name: '',
decimals: 0,
};
};
@@ -8,7 +8,11 @@ import { Link as UILink } from '@vegaprotocol/ui-toolkit';
import type { SimpleGridProps } from '@vegaprotocol/ui-toolkit';
import type { ReactNode } from 'react';
import { Link } from 'react-router-dom';
import type { Market, MarketData } from '@vegaprotocol/markets';
import type {
Market,
MarketData,
MarketFieldsFragment,
} from '@vegaprotocol/markets';
export const compileGridData = (
market: Pick<
@@ -40,10 +44,9 @@ export const compileGridData = (
const formatStake = (value: string) => {
const formattedValue = addDecimalsFormatNumber(
value,
market.tradableInstrument.instrument.product.settlementAsset.decimals
getAsset(market).decimals
);
const asset =
market.tradableInstrument.instrument.product.settlementAsset.symbol;
const asset = getAsset(market).symbol;
return `${formattedValue} ${asset}`;
};
@@ -118,3 +121,20 @@ export const compileGridData = (
return grid;
};
const getAsset = (
market: Pick<
MarketFieldsFragment,
'id' | 'tradableInstrument' | 'decimalPlaces' | 'positionDecimalPlaces'
>
) => {
// TODO update with baseAsset for Spots
return 'settlementAsset' in market.tradableInstrument.instrument.product
? market.tradableInstrument.instrument.product.settlementAsset
: {
quantum: '0',
decimals: 0,
symbol: '',
id: '',
};
};
+13 -3
View File
@@ -142,7 +142,10 @@ const formatPrice = ({
return '-';
}
const asset =
data?.market.tradableInstrument.instrument.product.settlementAsset.symbol;
'settlementAsset' in data.market.tradableInstrument.instrument.product
? data?.market.tradableInstrument.instrument.product.settlementAsset
.symbol
: '';
const valueFormatted = addDecimalsFormatNumber(
value,
data?.market.decimalPlaces
@@ -193,7 +196,9 @@ const formatTotal = ({
return '-';
}
const { symbol: assetSymbol, decimals: assetDecimals } =
data?.market.tradableInstrument.instrument.product.settlementAsset ?? {};
('settlementAsset' in data.market.tradableInstrument.instrument.product
? data?.market.tradableInstrument.instrument.product.settlementAsset
: null) ?? {};
const size = new BigNumber(
addDecimal(data?.size, data?.market.positionDecimalPlaces)
);
@@ -219,7 +224,12 @@ const formatFee = (partyId: string) => {
Trade,
'market.tradableInstrument.instrument.product'
>) => {
if (!value?.settlementAsset || !data) {
if (
!value ||
!('settlementAsset' in value) ||
!value?.settlementAsset ||
!data
) {
return '-';
}
const asset = value.settlementAsset;
@@ -66,7 +66,11 @@ export const OrderbookManager = ({
asks={data?.depth.sell ?? []}
decimalPlaces={market?.decimalPlaces ?? 0}
positionDecimalPlaces={market?.positionDecimalPlaces ?? 0}
assetSymbol={market?.tradableInstrument.instrument.product.quoteName}
assetSymbol={
market && 'quoteName' in market.tradableInstrument.instrument.product
? market?.tradableInstrument.instrument.product.quoteName
: ''
}
onClick={onClick}
midPrice={marketData?.midPrice}
/>
@@ -26,6 +26,24 @@ fragment OracleMarketSpecFields on Market {
tradingTerminationProperty
}
}
... on Perpetual {
dataSourceSpecForSettlementData {
id
data {
...DataSourceSpec
}
}
dataSourceSpecForSettlementSchedule {
id
data {
...DataSourceSpec
}
}
dataSourceSpecBinding {
settlementDataProperty
settlementScheduleProperty
}
}
}
}
}
+20 -2
View File
@@ -4,12 +4,12 @@ import { gql } from '@apollo/client';
import { DataSourceSpecFragmentDoc } from './markets';
import * as Apollo from '@apollo/client';
const defaultOptions = {} as const;
export type OracleMarketSpecFieldsFragment = { __typename?: 'Market', id: string, state: Types.MarketState, tradingMode: Types.MarketTradingMode, tradableInstrument: { __typename?: 'TradableInstrument', instrument: { __typename?: 'Instrument', id: string, name: string, code: string, product: { __typename?: 'Future', dataSourceSpecForSettlementData: { __typename?: 'DataSourceSpec', id: string, data: { __typename?: 'DataSourceDefinition', sourceType: { __typename?: 'DataSourceDefinitionExternal', sourceType: { __typename?: 'DataSourceSpecConfiguration', signers?: Array<{ __typename?: 'Signer', signer: { __typename?: 'ETHAddress', address?: string | null } | { __typename?: 'PubKey', key?: string | null } }> | null, filters?: Array<{ __typename?: 'Filter', key: { __typename?: 'PropertyKey', name?: string | null, type: Types.PropertyKeyType, numberDecimalPlaces?: number | null } }> | null } | { __typename?: 'EthCallSpec' } } | { __typename?: 'DataSourceDefinitionInternal' } } }, dataSourceSpecForTradingTermination: { __typename?: 'DataSourceSpec', id: string, data: { __typename?: 'DataSourceDefinition', sourceType: { __typename?: 'DataSourceDefinitionExternal', sourceType: { __typename?: 'DataSourceSpecConfiguration', signers?: Array<{ __typename?: 'Signer', signer: { __typename?: 'ETHAddress', address?: string | null } | { __typename?: 'PubKey', key?: string | null } }> | null, filters?: Array<{ __typename?: 'Filter', key: { __typename?: 'PropertyKey', name?: string | null, type: Types.PropertyKeyType, numberDecimalPlaces?: number | null } }> | null } | { __typename?: 'EthCallSpec' } } | { __typename?: 'DataSourceDefinitionInternal' } } }, dataSourceSpecBinding: { __typename?: 'DataSourceSpecToFutureBinding', settlementDataProperty: string, tradingTerminationProperty: string } } | { __typename?: 'Perpetual' } | { __typename?: 'Spot' } } } };
export type OracleMarketSpecFieldsFragment = { __typename?: 'Market', id: string, state: Types.MarketState, tradingMode: Types.MarketTradingMode, tradableInstrument: { __typename?: 'TradableInstrument', instrument: { __typename?: 'Instrument', id: string, name: string, code: string, product: { __typename?: 'Future', dataSourceSpecForSettlementData: { __typename?: 'DataSourceSpec', id: string, data: { __typename?: 'DataSourceDefinition', sourceType: { __typename?: 'DataSourceDefinitionExternal', sourceType: { __typename?: 'DataSourceSpecConfiguration', signers?: Array<{ __typename?: 'Signer', signer: { __typename?: 'ETHAddress', address?: string | null } | { __typename?: 'PubKey', key?: string | null } }> | null, filters?: Array<{ __typename?: 'Filter', key: { __typename?: 'PropertyKey', name?: string | null, type: Types.PropertyKeyType, numberDecimalPlaces?: number | null } }> | null } | { __typename?: 'EthCallSpec' } } | { __typename?: 'DataSourceDefinitionInternal' } } }, dataSourceSpecForTradingTermination: { __typename?: 'DataSourceSpec', id: string, data: { __typename?: 'DataSourceDefinition', sourceType: { __typename?: 'DataSourceDefinitionExternal', sourceType: { __typename?: 'DataSourceSpecConfiguration', signers?: Array<{ __typename?: 'Signer', signer: { __typename?: 'ETHAddress', address?: string | null } | { __typename?: 'PubKey', key?: string | null } }> | null, filters?: Array<{ __typename?: 'Filter', key: { __typename?: 'PropertyKey', name?: string | null, type: Types.PropertyKeyType, numberDecimalPlaces?: number | null } }> | null } | { __typename?: 'EthCallSpec' } } | { __typename?: 'DataSourceDefinitionInternal' } } }, dataSourceSpecBinding: { __typename?: 'DataSourceSpecToFutureBinding', settlementDataProperty: string, tradingTerminationProperty: string } } | { __typename?: 'Perpetual', dataSourceSpecForSettlementData: { __typename?: 'DataSourceSpec', id: string, data: { __typename?: 'DataSourceDefinition', sourceType: { __typename?: 'DataSourceDefinitionExternal', sourceType: { __typename?: 'DataSourceSpecConfiguration', signers?: Array<{ __typename?: 'Signer', signer: { __typename?: 'ETHAddress', address?: string | null } | { __typename?: 'PubKey', key?: string | null } }> | null, filters?: Array<{ __typename?: 'Filter', key: { __typename?: 'PropertyKey', name?: string | null, type: Types.PropertyKeyType, numberDecimalPlaces?: number | null } }> | null } | { __typename?: 'EthCallSpec' } } | { __typename?: 'DataSourceDefinitionInternal' } } }, dataSourceSpecForSettlementSchedule: { __typename?: 'DataSourceSpec', id: string, data: { __typename?: 'DataSourceDefinition', sourceType: { __typename?: 'DataSourceDefinitionExternal', sourceType: { __typename?: 'DataSourceSpecConfiguration', signers?: Array<{ __typename?: 'Signer', signer: { __typename?: 'ETHAddress', address?: string | null } | { __typename?: 'PubKey', key?: string | null } }> | null, filters?: Array<{ __typename?: 'Filter', key: { __typename?: 'PropertyKey', name?: string | null, type: Types.PropertyKeyType, numberDecimalPlaces?: number | null } }> | null } | { __typename?: 'EthCallSpec' } } | { __typename?: 'DataSourceDefinitionInternal' } } }, dataSourceSpecBinding: { __typename?: 'DataSourceSpecPerpetualBinding', settlementDataProperty: string, settlementScheduleProperty: string } } | { __typename?: 'Spot' } } } };
export type OracleMarketsSpecQueryVariables = Types.Exact<{ [key: string]: never; }>;
export type OracleMarketsSpecQuery = { __typename?: 'Query', marketsConnection?: { __typename?: 'MarketConnection', edges: Array<{ __typename?: 'MarketEdge', node: { __typename?: 'Market', id: string, state: Types.MarketState, tradingMode: Types.MarketTradingMode, tradableInstrument: { __typename?: 'TradableInstrument', instrument: { __typename?: 'Instrument', id: string, name: string, code: string, product: { __typename?: 'Future', dataSourceSpecForSettlementData: { __typename?: 'DataSourceSpec', id: string, data: { __typename?: 'DataSourceDefinition', sourceType: { __typename?: 'DataSourceDefinitionExternal', sourceType: { __typename?: 'DataSourceSpecConfiguration', signers?: Array<{ __typename?: 'Signer', signer: { __typename?: 'ETHAddress', address?: string | null } | { __typename?: 'PubKey', key?: string | null } }> | null, filters?: Array<{ __typename?: 'Filter', key: { __typename?: 'PropertyKey', name?: string | null, type: Types.PropertyKeyType, numberDecimalPlaces?: number | null } }> | null } | { __typename?: 'EthCallSpec' } } | { __typename?: 'DataSourceDefinitionInternal' } } }, dataSourceSpecForTradingTermination: { __typename?: 'DataSourceSpec', id: string, data: { __typename?: 'DataSourceDefinition', sourceType: { __typename?: 'DataSourceDefinitionExternal', sourceType: { __typename?: 'DataSourceSpecConfiguration', signers?: Array<{ __typename?: 'Signer', signer: { __typename?: 'ETHAddress', address?: string | null } | { __typename?: 'PubKey', key?: string | null } }> | null, filters?: Array<{ __typename?: 'Filter', key: { __typename?: 'PropertyKey', name?: string | null, type: Types.PropertyKeyType, numberDecimalPlaces?: number | null } }> | null } | { __typename?: 'EthCallSpec' } } | { __typename?: 'DataSourceDefinitionInternal' } } }, dataSourceSpecBinding: { __typename?: 'DataSourceSpecToFutureBinding', settlementDataProperty: string, tradingTerminationProperty: string } } | { __typename?: 'Perpetual' } | { __typename?: 'Spot' } } } } }> } | null };
export type OracleMarketsSpecQuery = { __typename?: 'Query', marketsConnection?: { __typename?: 'MarketConnection', edges: Array<{ __typename?: 'MarketEdge', node: { __typename?: 'Market', id: string, state: Types.MarketState, tradingMode: Types.MarketTradingMode, tradableInstrument: { __typename?: 'TradableInstrument', instrument: { __typename?: 'Instrument', id: string, name: string, code: string, product: { __typename?: 'Future', dataSourceSpecForSettlementData: { __typename?: 'DataSourceSpec', id: string, data: { __typename?: 'DataSourceDefinition', sourceType: { __typename?: 'DataSourceDefinitionExternal', sourceType: { __typename?: 'DataSourceSpecConfiguration', signers?: Array<{ __typename?: 'Signer', signer: { __typename?: 'ETHAddress', address?: string | null } | { __typename?: 'PubKey', key?: string | null } }> | null, filters?: Array<{ __typename?: 'Filter', key: { __typename?: 'PropertyKey', name?: string | null, type: Types.PropertyKeyType, numberDecimalPlaces?: number | null } }> | null } | { __typename?: 'EthCallSpec' } } | { __typename?: 'DataSourceDefinitionInternal' } } }, dataSourceSpecForTradingTermination: { __typename?: 'DataSourceSpec', id: string, data: { __typename?: 'DataSourceDefinition', sourceType: { __typename?: 'DataSourceDefinitionExternal', sourceType: { __typename?: 'DataSourceSpecConfiguration', signers?: Array<{ __typename?: 'Signer', signer: { __typename?: 'ETHAddress', address?: string | null } | { __typename?: 'PubKey', key?: string | null } }> | null, filters?: Array<{ __typename?: 'Filter', key: { __typename?: 'PropertyKey', name?: string | null, type: Types.PropertyKeyType, numberDecimalPlaces?: number | null } }> | null } | { __typename?: 'EthCallSpec' } } | { __typename?: 'DataSourceDefinitionInternal' } } }, dataSourceSpecBinding: { __typename?: 'DataSourceSpecToFutureBinding', settlementDataProperty: string, tradingTerminationProperty: string } } | { __typename?: 'Perpetual', dataSourceSpecForSettlementData: { __typename?: 'DataSourceSpec', id: string, data: { __typename?: 'DataSourceDefinition', sourceType: { __typename?: 'DataSourceDefinitionExternal', sourceType: { __typename?: 'DataSourceSpecConfiguration', signers?: Array<{ __typename?: 'Signer', signer: { __typename?: 'ETHAddress', address?: string | null } | { __typename?: 'PubKey', key?: string | null } }> | null, filters?: Array<{ __typename?: 'Filter', key: { __typename?: 'PropertyKey', name?: string | null, type: Types.PropertyKeyType, numberDecimalPlaces?: number | null } }> | null } | { __typename?: 'EthCallSpec' } } | { __typename?: 'DataSourceDefinitionInternal' } } }, dataSourceSpecForSettlementSchedule: { __typename?: 'DataSourceSpec', id: string, data: { __typename?: 'DataSourceDefinition', sourceType: { __typename?: 'DataSourceDefinitionExternal', sourceType: { __typename?: 'DataSourceSpecConfiguration', signers?: Array<{ __typename?: 'Signer', signer: { __typename?: 'ETHAddress', address?: string | null } | { __typename?: 'PubKey', key?: string | null } }> | null, filters?: Array<{ __typename?: 'Filter', key: { __typename?: 'PropertyKey', name?: string | null, type: Types.PropertyKeyType, numberDecimalPlaces?: number | null } }> | null } | { __typename?: 'EthCallSpec' } } | { __typename?: 'DataSourceDefinitionInternal' } } }, dataSourceSpecBinding: { __typename?: 'DataSourceSpecPerpetualBinding', settlementDataProperty: string, settlementScheduleProperty: string } } | { __typename?: 'Spot' } } } } }> } | null };
export const OracleMarketSpecFieldsFragmentDoc = gql`
fragment OracleMarketSpecFields on Market {
@@ -40,6 +40,24 @@ export const OracleMarketSpecFieldsFragmentDoc = gql`
tradingTerminationProperty
}
}
... on Perpetual {
dataSourceSpecForSettlementData {
id
data {
...DataSourceSpec
}
}
dataSourceSpecForSettlementSchedule {
id
data {
...DataSourceSpec
}
}
dataSourceSpecBinding {
settlementDataProperty
settlementScheduleProperty
}
}
}
}
}
+28 -2
View File
@@ -7,12 +7,12 @@ export type DataSourceFilterFragment = { __typename?: 'Filter', key: { __typenam
export type DataSourceSpecFragment = { __typename?: 'DataSourceDefinition', sourceType: { __typename?: 'DataSourceDefinitionExternal', sourceType: { __typename?: 'DataSourceSpecConfiguration', signers?: Array<{ __typename?: 'Signer', signer: { __typename?: 'ETHAddress', address?: string | null } | { __typename?: 'PubKey', key?: string | null } }> | null, filters?: Array<{ __typename?: 'Filter', key: { __typename?: 'PropertyKey', name?: string | null, type: Types.PropertyKeyType, numberDecimalPlaces?: number | null } }> | null } | { __typename?: 'EthCallSpec' } } | { __typename?: 'DataSourceDefinitionInternal' } };
export type MarketFieldsFragment = { __typename?: 'Market', id: string, decimalPlaces: number, positionDecimalPlaces: number, state: Types.MarketState, tradingMode: Types.MarketTradingMode, fees: { __typename?: 'Fees', factors: { __typename?: 'FeeFactors', makerFee: string, infrastructureFee: string, liquidityFee: string } }, tradableInstrument: { __typename?: 'TradableInstrument', instrument: { __typename?: 'Instrument', id: string, name: string, code: string, metadata: { __typename?: 'InstrumentMetadata', tags?: Array<string> | null }, product: { __typename?: 'Future', quoteName: string, settlementAsset: { __typename?: 'Asset', id: string, symbol: string, name: string, decimals: number, quantum: string }, dataSourceSpecForTradingTermination: { __typename?: 'DataSourceSpec', id: string, data: { __typename?: 'DataSourceDefinition', sourceType: { __typename?: 'DataSourceDefinitionExternal', sourceType: { __typename?: 'DataSourceSpecConfiguration', signers?: Array<{ __typename?: 'Signer', signer: { __typename?: 'ETHAddress', address?: string | null } | { __typename?: 'PubKey', key?: string | null } }> | null, filters?: Array<{ __typename?: 'Filter', key: { __typename?: 'PropertyKey', name?: string | null, type: Types.PropertyKeyType, numberDecimalPlaces?: number | null } }> | null } | { __typename?: 'EthCallSpec' } } | { __typename?: 'DataSourceDefinitionInternal' } } }, dataSourceSpecForSettlementData: { __typename?: 'DataSourceSpec', id: string, data: { __typename?: 'DataSourceDefinition', sourceType: { __typename?: 'DataSourceDefinitionExternal', sourceType: { __typename?: 'DataSourceSpecConfiguration', signers?: Array<{ __typename?: 'Signer', signer: { __typename?: 'ETHAddress', address?: string | null } | { __typename?: 'PubKey', key?: string | null } }> | null, filters?: Array<{ __typename?: 'Filter', key: { __typename?: 'PropertyKey', name?: string | null, type: Types.PropertyKeyType, numberDecimalPlaces?: number | null } }> | null } | { __typename?: 'EthCallSpec' } } | { __typename?: 'DataSourceDefinitionInternal' } } }, dataSourceSpecBinding: { __typename?: 'DataSourceSpecToFutureBinding', settlementDataProperty: string, tradingTerminationProperty: string } } | { __typename?: 'Perpetual' } | { __typename?: 'Spot' } } }, marketTimestamps: { __typename?: 'MarketTimestamps', open: any, close: any } };
export type MarketFieldsFragment = { __typename?: 'Market', id: string, decimalPlaces: number, positionDecimalPlaces: number, state: Types.MarketState, tradingMode: Types.MarketTradingMode, fees: { __typename?: 'Fees', factors: { __typename?: 'FeeFactors', makerFee: string, infrastructureFee: string, liquidityFee: string } }, tradableInstrument: { __typename?: 'TradableInstrument', instrument: { __typename?: 'Instrument', id: string, name: string, code: string, metadata: { __typename?: 'InstrumentMetadata', tags?: Array<string> | null }, product: { __typename?: 'Future', quoteName: string, settlementAsset: { __typename?: 'Asset', id: string, symbol: string, name: string, decimals: number, quantum: string }, dataSourceSpecForTradingTermination: { __typename?: 'DataSourceSpec', id: string, data: { __typename?: 'DataSourceDefinition', sourceType: { __typename?: 'DataSourceDefinitionExternal', sourceType: { __typename?: 'DataSourceSpecConfiguration', signers?: Array<{ __typename?: 'Signer', signer: { __typename?: 'ETHAddress', address?: string | null } | { __typename?: 'PubKey', key?: string | null } }> | null, filters?: Array<{ __typename?: 'Filter', key: { __typename?: 'PropertyKey', name?: string | null, type: Types.PropertyKeyType, numberDecimalPlaces?: number | null } }> | null } | { __typename?: 'EthCallSpec' } } | { __typename?: 'DataSourceDefinitionInternal' } } }, dataSourceSpecForSettlementData: { __typename?: 'DataSourceSpec', id: string, data: { __typename?: 'DataSourceDefinition', sourceType: { __typename?: 'DataSourceDefinitionExternal', sourceType: { __typename?: 'DataSourceSpecConfiguration', signers?: Array<{ __typename?: 'Signer', signer: { __typename?: 'ETHAddress', address?: string | null } | { __typename?: 'PubKey', key?: string | null } }> | null, filters?: Array<{ __typename?: 'Filter', key: { __typename?: 'PropertyKey', name?: string | null, type: Types.PropertyKeyType, numberDecimalPlaces?: number | null } }> | null } | { __typename?: 'EthCallSpec' } } | { __typename?: 'DataSourceDefinitionInternal' } } }, dataSourceSpecBinding: { __typename?: 'DataSourceSpecToFutureBinding', settlementDataProperty: string, tradingTerminationProperty: string } } | { __typename?: 'Perpetual', quoteName: string, settlementAsset: { __typename?: 'Asset', id: string, symbol: string, name: string, decimals: number, quantum: string }, dataSourceSpecForSettlementSchedule: { __typename?: 'DataSourceSpec', id: string, data: { __typename?: 'DataSourceDefinition', sourceType: { __typename?: 'DataSourceDefinitionExternal', sourceType: { __typename?: 'DataSourceSpecConfiguration', signers?: Array<{ __typename?: 'Signer', signer: { __typename?: 'ETHAddress', address?: string | null } | { __typename?: 'PubKey', key?: string | null } }> | null, filters?: Array<{ __typename?: 'Filter', key: { __typename?: 'PropertyKey', name?: string | null, type: Types.PropertyKeyType, numberDecimalPlaces?: number | null } }> | null } | { __typename?: 'EthCallSpec' } } | { __typename?: 'DataSourceDefinitionInternal' } } }, dataSourceSpecForSettlementData: { __typename?: 'DataSourceSpec', id: string, data: { __typename?: 'DataSourceDefinition', sourceType: { __typename?: 'DataSourceDefinitionExternal', sourceType: { __typename?: 'DataSourceSpecConfiguration', signers?: Array<{ __typename?: 'Signer', signer: { __typename?: 'ETHAddress', address?: string | null } | { __typename?: 'PubKey', key?: string | null } }> | null, filters?: Array<{ __typename?: 'Filter', key: { __typename?: 'PropertyKey', name?: string | null, type: Types.PropertyKeyType, numberDecimalPlaces?: number | null } }> | null } | { __typename?: 'EthCallSpec' } } | { __typename?: 'DataSourceDefinitionInternal' } } }, dataSourceSpecBinding: { __typename?: 'DataSourceSpecPerpetualBinding', settlementDataProperty: string, settlementScheduleProperty: string } } | { __typename?: 'Spot' } } }, marketTimestamps: { __typename?: 'MarketTimestamps', open: any, close: any } };
export type MarketsQueryVariables = Types.Exact<{ [key: string]: never; }>;
export type MarketsQuery = { __typename?: 'Query', marketsConnection?: { __typename?: 'MarketConnection', edges: Array<{ __typename?: 'MarketEdge', node: { __typename?: 'Market', id: string, decimalPlaces: number, positionDecimalPlaces: number, state: Types.MarketState, tradingMode: Types.MarketTradingMode, fees: { __typename?: 'Fees', factors: { __typename?: 'FeeFactors', makerFee: string, infrastructureFee: string, liquidityFee: string } }, tradableInstrument: { __typename?: 'TradableInstrument', instrument: { __typename?: 'Instrument', id: string, name: string, code: string, metadata: { __typename?: 'InstrumentMetadata', tags?: Array<string> | null }, product: { __typename?: 'Future', quoteName: string, settlementAsset: { __typename?: 'Asset', id: string, symbol: string, name: string, decimals: number, quantum: string }, dataSourceSpecForTradingTermination: { __typename?: 'DataSourceSpec', id: string, data: { __typename?: 'DataSourceDefinition', sourceType: { __typename?: 'DataSourceDefinitionExternal', sourceType: { __typename?: 'DataSourceSpecConfiguration', signers?: Array<{ __typename?: 'Signer', signer: { __typename?: 'ETHAddress', address?: string | null } | { __typename?: 'PubKey', key?: string | null } }> | null, filters?: Array<{ __typename?: 'Filter', key: { __typename?: 'PropertyKey', name?: string | null, type: Types.PropertyKeyType, numberDecimalPlaces?: number | null } }> | null } | { __typename?: 'EthCallSpec' } } | { __typename?: 'DataSourceDefinitionInternal' } } }, dataSourceSpecForSettlementData: { __typename?: 'DataSourceSpec', id: string, data: { __typename?: 'DataSourceDefinition', sourceType: { __typename?: 'DataSourceDefinitionExternal', sourceType: { __typename?: 'DataSourceSpecConfiguration', signers?: Array<{ __typename?: 'Signer', signer: { __typename?: 'ETHAddress', address?: string | null } | { __typename?: 'PubKey', key?: string | null } }> | null, filters?: Array<{ __typename?: 'Filter', key: { __typename?: 'PropertyKey', name?: string | null, type: Types.PropertyKeyType, numberDecimalPlaces?: number | null } }> | null } | { __typename?: 'EthCallSpec' } } | { __typename?: 'DataSourceDefinitionInternal' } } }, dataSourceSpecBinding: { __typename?: 'DataSourceSpecToFutureBinding', settlementDataProperty: string, tradingTerminationProperty: string } } | { __typename?: 'Perpetual' } | { __typename?: 'Spot' } } }, marketTimestamps: { __typename?: 'MarketTimestamps', open: any, close: any } } }> } | null };
export type MarketsQuery = { __typename?: 'Query', marketsConnection?: { __typename?: 'MarketConnection', edges: Array<{ __typename?: 'MarketEdge', node: { __typename?: 'Market', id: string, decimalPlaces: number, positionDecimalPlaces: number, state: Types.MarketState, tradingMode: Types.MarketTradingMode, fees: { __typename?: 'Fees', factors: { __typename?: 'FeeFactors', makerFee: string, infrastructureFee: string, liquidityFee: string } }, tradableInstrument: { __typename?: 'TradableInstrument', instrument: { __typename?: 'Instrument', id: string, name: string, code: string, metadata: { __typename?: 'InstrumentMetadata', tags?: Array<string> | null }, product: { __typename?: 'Future', quoteName: string, settlementAsset: { __typename?: 'Asset', id: string, symbol: string, name: string, decimals: number, quantum: string }, dataSourceSpecForTradingTermination: { __typename?: 'DataSourceSpec', id: string, data: { __typename?: 'DataSourceDefinition', sourceType: { __typename?: 'DataSourceDefinitionExternal', sourceType: { __typename?: 'DataSourceSpecConfiguration', signers?: Array<{ __typename?: 'Signer', signer: { __typename?: 'ETHAddress', address?: string | null } | { __typename?: 'PubKey', key?: string | null } }> | null, filters?: Array<{ __typename?: 'Filter', key: { __typename?: 'PropertyKey', name?: string | null, type: Types.PropertyKeyType, numberDecimalPlaces?: number | null } }> | null } | { __typename?: 'EthCallSpec' } } | { __typename?: 'DataSourceDefinitionInternal' } } }, dataSourceSpecForSettlementData: { __typename?: 'DataSourceSpec', id: string, data: { __typename?: 'DataSourceDefinition', sourceType: { __typename?: 'DataSourceDefinitionExternal', sourceType: { __typename?: 'DataSourceSpecConfiguration', signers?: Array<{ __typename?: 'Signer', signer: { __typename?: 'ETHAddress', address?: string | null } | { __typename?: 'PubKey', key?: string | null } }> | null, filters?: Array<{ __typename?: 'Filter', key: { __typename?: 'PropertyKey', name?: string | null, type: Types.PropertyKeyType, numberDecimalPlaces?: number | null } }> | null } | { __typename?: 'EthCallSpec' } } | { __typename?: 'DataSourceDefinitionInternal' } } }, dataSourceSpecBinding: { __typename?: 'DataSourceSpecToFutureBinding', settlementDataProperty: string, tradingTerminationProperty: string } } | { __typename?: 'Perpetual', quoteName: string, settlementAsset: { __typename?: 'Asset', id: string, symbol: string, name: string, decimals: number, quantum: string }, dataSourceSpecForSettlementSchedule: { __typename?: 'DataSourceSpec', id: string, data: { __typename?: 'DataSourceDefinition', sourceType: { __typename?: 'DataSourceDefinitionExternal', sourceType: { __typename?: 'DataSourceSpecConfiguration', signers?: Array<{ __typename?: 'Signer', signer: { __typename?: 'ETHAddress', address?: string | null } | { __typename?: 'PubKey', key?: string | null } }> | null, filters?: Array<{ __typename?: 'Filter', key: { __typename?: 'PropertyKey', name?: string | null, type: Types.PropertyKeyType, numberDecimalPlaces?: number | null } }> | null } | { __typename?: 'EthCallSpec' } } | { __typename?: 'DataSourceDefinitionInternal' } } }, dataSourceSpecForSettlementData: { __typename?: 'DataSourceSpec', id: string, data: { __typename?: 'DataSourceDefinition', sourceType: { __typename?: 'DataSourceDefinitionExternal', sourceType: { __typename?: 'DataSourceSpecConfiguration', signers?: Array<{ __typename?: 'Signer', signer: { __typename?: 'ETHAddress', address?: string | null } | { __typename?: 'PubKey', key?: string | null } }> | null, filters?: Array<{ __typename?: 'Filter', key: { __typename?: 'PropertyKey', name?: string | null, type: Types.PropertyKeyType, numberDecimalPlaces?: number | null } }> | null } | { __typename?: 'EthCallSpec' } } | { __typename?: 'DataSourceDefinitionInternal' } } }, dataSourceSpecBinding: { __typename?: 'DataSourceSpecPerpetualBinding', settlementDataProperty: string, settlementScheduleProperty: string } } | { __typename?: 'Spot' } } }, marketTimestamps: { __typename?: 'MarketTimestamps', open: any, close: any } } }> } | null };
export const DataSourceFilterFragmentDoc = gql`
fragment DataSourceFilter on Filter {
@@ -97,6 +97,32 @@ export const MarketFieldsFragmentDoc = gql`
tradingTerminationProperty
}
}
... on Perpetual {
settlementAsset {
id
symbol
name
decimals
quantum
}
quoteName
dataSourceSpecForSettlementSchedule {
id
data {
...DataSourceSpec
}
}
dataSourceSpecForSettlementData {
id
data {
...DataSourceSpec
}
}
dataSourceSpecBinding {
settlementDataProperty
settlementScheduleProperty
}
}
}
}
}
@@ -125,6 +125,31 @@ query MarketInfo($marketId: ID!) {
tradingTerminationProperty
}
}
... on Perpetual {
quoteName
settlementAsset {
id
symbol
name
decimals
}
dataSourceSpecForSettlementData {
id
data {
...DataSource
}
}
dataSourceSpecForSettlementSchedule {
id
data {
...DataSource
}
}
dataSourceSpecBinding {
settlementDataProperty
settlementScheduleProperty
}
}
}
}
riskModel {
File diff suppressed because one or more lines are too long
@@ -88,14 +88,31 @@ export const MarketInfoAccordion = ({
market.accountsConnection?.edges
);
const settlementData = market.tradableInstrument.instrument.product
.dataSourceSpecForSettlementData.data as DataSourceDefinition;
const terminationData = market.tradableInstrument.instrument.product
.dataSourceSpecForTradingTermination.data as DataSourceDefinition;
const settlementData =
'dataSourceSpecForSettlementData' in
market.tradableInstrument.instrument.product
? (market.tradableInstrument.instrument.product
.dataSourceSpecForSettlementData.data as DataSourceDefinition)
: undefined;
const terminationData =
'dataSourceSpecForTradingTermination' in
market.tradableInstrument.instrument.product
? (market.tradableInstrument.instrument.product
.dataSourceSpecForTradingTermination.data as DataSourceDefinition)
: undefined;
const settlementScheduleData =
'dataSourceSpecForSettlementSchedule' in
market.tradableInstrument.instrument.product
? (market.tradableInstrument.instrument.product
.dataSourceSpecForSettlementSchedule.data as DataSourceDefinition)
: undefined;
const getSigners = (data: DataSourceDefinition) => {
if (data.sourceType.__typename === 'DataSourceDefinitionExternal') {
const signers = data.sourceType.sourceType.signers || [];
const signers =
('signers' in data.sourceType.sourceType &&
data.sourceType.sourceType.signers) ||
[];
return signers.map(({ signer }, i) => {
return (
@@ -158,7 +175,9 @@ export const MarketInfoAccordion = ({
title={t('Instrument')}
content={<InstrumentInfoPanel market={market} />}
/>
{isEqual(getSigners(settlementData), getSigners(terminationData)) ? (
{settlementData &&
terminationData &&
isEqual(getSigners(settlementData), getSigners(terminationData)) ? (
<AccordionItem
itemId="oracles"
title={t('Oracle')}
@@ -175,7 +194,6 @@ export const MarketInfoAccordion = ({
<OracleInfoPanel market={market} type="settlementData" />
}
/>
<AccordionItem
itemId="termination-oracle"
title={t('Termination Oracle')}
@@ -183,6 +201,37 @@ export const MarketInfoAccordion = ({
/>
</>
)}
{settlementData &&
settlementScheduleData &&
isEqual(
getSigners(settlementData),
getSigners(settlementScheduleData)
) ? (
<AccordionItem
itemId="oracles"
title={t('Oracle')}
content={
<OracleInfoPanel market={market} type="settlementData" />
}
/>
) : (
<>
<AccordionItem
itemId="settlement-oracle"
title={t('Settlement Oracle')}
content={
<OracleInfoPanel market={market} type="settlementData" />
}
/>
<AccordionItem
itemId="settlement-schedule-oracle"
title={t('Settlement Schedule Oracle')}
content={
<OracleInfoPanel market={market} type="settlementSchedule" />
}
/>
</>
)}
<AccordionItem
itemId="settlement-asset"
title={t('Settlement asset')}
@@ -227,7 +276,7 @@ export const MarketInfoAccordion = ({
}
)}
<AccordionItem
itemId="liqudity-monitoring-parameters"
itemId="liquidity-monitoring-parameters"
title={t('Liquidity monitoring parameters')}
content={<LiquidityMonitoringParametersInfoPanel market={market} />}
/>
@@ -52,6 +52,7 @@ import type { MarketTradingMode } from '@vegaprotocol/types';
import type { Signer } from '@vegaprotocol/types';
import classNames from 'classnames';
import compact from 'lodash/compact';
import get from 'lodash/get';
type MarketInfoProps = {
market: MarketInfo;
@@ -80,9 +81,17 @@ export const CurrentFeesInfoPanel = ({ market }: MarketInfoProps) => (
export const MarketPriceInfoPanel = ({ market }: MarketInfoProps) => {
const assetSymbol =
market?.tradableInstrument.instrument.product?.settlementAsset.symbol || '';
market?.tradableInstrument.instrument.product &&
'settlementAsset' in market.tradableInstrument.instrument.product
? market?.tradableInstrument.instrument.product?.settlementAsset.symbol
: market?.tradableInstrument.instrument.product &&
'baseAsset' in market.tradableInstrument.instrument.product
? get(market?.tradableInstrument.instrument.product?.baseAsset, 'symbol')
: '';
const quoteUnit =
market?.tradableInstrument.instrument.product?.quoteName || '';
'quoteName' in market.tradableInstrument.instrument.product
? market?.tradableInstrument.instrument.product?.quoteName
: '';
const { data } = useDataProvider({
dataProvider: marketDataProvider,
variables: { marketId: market.id },
@@ -94,7 +103,10 @@ export const MarketPriceInfoPanel = ({ market }: MarketInfoProps) => {
markPrice: data?.markPrice,
bestBidPrice: data?.bestBidPrice,
bestOfferPrice: data?.bestOfferPrice,
quoteUnit: market.tradableInstrument.instrument.product.quoteName,
quoteUnit: get(
market.tradableInstrument.instrument.product,
'quoteName'
),
}}
decimalPlaces={market.decimalPlaces}
/>
@@ -145,17 +157,16 @@ export const InsurancePoolInfoPanel = ({
Get<MarketInfoWithData, 'accountsConnection.edges[0].node'>
>;
} & MarketInfoProps) => {
const assetSymbol =
market?.tradableInstrument.instrument.product?.settlementAsset.symbol || '';
const assetSymbol = getAssetSymbol(market);
const assetDecimals = getAssetDecimals(market);
return (
<MarketInfoTable
data={{
balance: account.balance,
}}
assetSymbol={assetSymbol}
decimalPlaces={
market.tradableInstrument.instrument.product.settlementAsset.decimals
}
decimalPlaces={assetDecimals}
/>
);
};
@@ -197,8 +208,7 @@ export const KeyDetailsInfoPanel = ({
skip: !parentMarket?.proposal?.id,
});
const assetDecimals =
market.tradableInstrument.instrument.product.settlementAsset.decimals;
const assetDecimals = getAssetDecimals(market);
return (
<MarketInfoTable
@@ -249,9 +259,7 @@ export const KeyDetailsInfoPanel = ({
],
marketDecimalPlaces: parentMarket?.decimalPlaces,
positionDecimalPlaces: parentMarket?.positionDecimalPlaces,
settlementAssetDecimalPlaces:
parentMarket?.tradableInstrument?.instrument?.product
?.settlementAsset?.decimals,
settlementAssetDecimalPlaces: assetDecimals,
}
}
/>
@@ -387,7 +395,7 @@ export const InstrumentInfoPanel = ({
marketName: market.tradableInstrument.instrument.name,
code: market.tradableInstrument.instrument.code,
productType: market.tradableInstrument.instrument.product.__typename,
quoteName: market.tradableInstrument.instrument.product.quoteName,
quoteName: get(market.tradableInstrument.instrument.product, 'quoteName'),
}}
parentData={
parentMarket && {
@@ -395,22 +403,22 @@ export const InstrumentInfoPanel = ({
code: parentMarket?.tradableInstrument?.instrument?.code,
productType:
parentMarket?.tradableInstrument?.instrument?.product?.__typename,
quoteName:
parentMarket?.tradableInstrument?.instrument?.product?.quoteName,
quoteName: get(
parentMarket?.tradableInstrument?.instrument?.product,
'quoteName'
),
}
}
/>
);
export const SettlementAssetInfoPanel = ({ market }: MarketInfoProps) => {
const assetSymbol =
market?.tradableInstrument.instrument.product?.settlementAsset.symbol || '';
const quoteUnit =
market?.tradableInstrument.instrument.product?.quoteName || '';
const assetId = useMemo(
() => market?.tradableInstrument.instrument.product?.settlementAsset.id,
[market]
const assetSymbol = getAssetSymbol(market);
const quoteUnit = get(
market?.tradableInstrument.instrument.product,
'quoteName'
);
const assetId = useMemo(() => getAssetId(market), [market]);
const { data: asset } = useAssetDataProvider(assetId ?? '');
return asset ? (
@@ -594,10 +602,14 @@ export const PriceMonitoringBoundsInfoPanel = ({
],
});
const quoteUnit =
market?.tradableInstrument.instrument.product?.quoteName || '';
const parentQuoteUnit =
parentMarket?.tradableInstrument.instrument.product?.quoteName || '';
const quoteUnit = get(
market?.tradableInstrument.instrument.product,
'quoteName'
);
const parentQuoteUnit = get(
parentMarket?.tradableInstrument.instrument.product,
'quoteName'
);
const isParentQuoteUnitEqual = quoteUnit === parentQuoteUnit;
const trigger =
@@ -688,10 +700,8 @@ export const LiquidityMonitoringParametersInfoPanel = ({
};
export const LiquidityInfoPanel = ({ market, children }: MarketInfoProps) => {
const assetDecimals =
market.tradableInstrument.instrument.product.settlementAsset.decimals;
const assetSymbol =
market?.tradableInstrument.instrument.product?.settlementAsset.symbol || '';
const assetDecimals = getAssetDecimals(market);
const assetSymbol = getAssetSymbol(market);
const { data } = useDataProvider({
dataProvider: marketDataProvider,
variables: { marketId: market.id },
@@ -717,9 +727,14 @@ export const LiquidityPriceRangeInfoPanel = ({
parentMarket,
}: MarketInfoProps) => {
const quoteUnit =
market?.tradableInstrument.instrument.product?.quoteName || '';
('quoteName' in market.tradableInstrument.instrument.product &&
market?.tradableInstrument.instrument.product?.quoteName) ||
'';
const parentQuoteUnit =
parentMarket?.tradableInstrument.instrument.product?.quoteName || '';
(parentMarket &&
'quoteName' in parentMarket.tradableInstrument.instrument.product &&
parentMarket?.tradableInstrument.instrument.product?.quoteName) ||
'';
const liquidityPriceRange = formatNumberPercentage(
new BigNumber(market.lpPriceRange).times(100)
@@ -809,7 +824,9 @@ export const OracleInfoPanel = ({
market,
type,
parentMarket,
}: MarketInfoProps & { type: 'settlementData' | 'termination' }) => {
}: MarketInfoProps & {
type: 'settlementData' | 'termination' | 'settlementSchedule';
}) => {
// If this is a successor market, this component will only receive parent market
// data if the termination or settlement data is different from the parent.
const product = market.tradableInstrument.instrument.product;
@@ -818,26 +835,52 @@ export const OracleInfoPanel = ({
const { data } = useOracleProofs(ORACLE_PROOFS_URL);
const dataSourceSpecId =
type === 'settlementData'
type === 'settlementData' && 'dataSourceSpecForSettlementData' in product
? product.dataSourceSpecForSettlementData.id
: product.dataSourceSpecForTradingTermination.id;
: type === 'termination' &&
'dataSourceSpecForTradingTermination' in product
? product.dataSourceSpecForTradingTermination.id
: type === 'settlementSchedule' &&
'dataSourceSpecForSettlementScheduleData' in product
? get(product.dataSourceSpecForSettlementScheduleData, 'id')
: '';
const parentDataSourceSpecId =
type === 'settlementData'
? parentProduct?.dataSourceSpecForSettlementData?.id
: parentProduct?.dataSourceSpecForTradingTermination?.id;
const parentDataSourceSpecId = !parentProduct
? undefined
: type === 'settlementData' &&
'dataSourceSpecForSettlementData' in parentProduct
? parentProduct.dataSourceSpecForSettlementData.id
: type === 'termination' &&
'dataSourceSpecForTradingTermination' in parentProduct
? parentProduct.dataSourceSpecForTradingTermination.id
: type === 'settlementSchedule' &&
'dataSourceSpecForSettlementScheduleData' in parentProduct
? get(parentProduct.dataSourceSpecForSettlementScheduleData, 'id')
: '';
const dataSourceSpec = (
type === 'settlementData'
const dataSourceSpec =
type === 'settlementData' && 'dataSourceSpecForSettlementData' in product
? product.dataSourceSpecForSettlementData.data
: product.dataSourceSpecForTradingTermination.data
) as DataSourceDefinition;
: type === 'termination' &&
'dataSourceSpecForTradingTermination' in product
? product.dataSourceSpecForTradingTermination.data
: type === 'settlementSchedule' &&
'dataSourceSpecForSettlementScheduleData' in product
? get(product.dataSourceSpecForSettlementScheduleData, 'data')
: null;
const parentDataSourceSpec =
type === 'settlementData'
? parentProduct?.dataSourceSpecForSettlementData?.data
: (parentProduct?.dataSourceSpecForTradingTermination
?.data as DataSourceDefinition);
const parentDataSourceSpec = !parentProduct
? undefined
: type === 'settlementData' &&
'dataSourceSpecForSettlementData' in parentProduct
? parentProduct.dataSourceSpecForSettlementData.data
: type === 'termination' &&
'dataSourceSpecForTradingTermination' in parentProduct
? parentProduct.dataSourceSpecForTradingTermination.data
: type === 'settlementSchedule' &&
'dataSourceSpecForSettlementScheduleData' in parentProduct
? get(parentProduct.dataSourceSpecForSettlementScheduleData, 'data')
: null;
const isParentDataSourceSpecEqual =
parentDataSourceSpec !== undefined &&
@@ -867,11 +910,7 @@ export const OracleInfoPanel = ({
<ExternalLink
data-testid="oracle-spec-links"
href={`${VEGA_EXPLORER_URL}/oracles/${
type === 'settlementData'
? product.dataSourceSpecForSettlementData.id
: product.dataSourceSpecForTradingTermination.id
}`}
href={`${VEGA_EXPLORER_URL}/oracles/${dataSourceSpecId}`}
>
{type === 'settlementData'
? t('View settlement data specification')
@@ -891,7 +930,7 @@ export const DataSourceProof = ({
}: {
data: DataSourceDefinition;
providers: Provider[] | undefined;
type: 'settlementData' | 'termination';
type: 'settlementData' | 'termination' | 'settlementSchedule';
dataSourceSpecId: string;
parentData?: DataSourceDefinition;
parentDataSourceSpecId?: string;
@@ -899,14 +938,20 @@ export const DataSourceProof = ({
// If this is a successor market, we'll only pass parent data to child
// components for comparison if the data differs from the parent market.
if (data.sourceType.__typename === 'DataSourceDefinitionExternal') {
const signers = data.sourceType.sourceType.signers || [];
const signers =
('signers' in data.sourceType.sourceType &&
data.sourceType.sourceType.signers) ||
[];
let parentSigners: Signer[];
if (
parentData &&
parentData.sourceType.__typename === 'DataSourceDefinitionExternal'
) {
parentSigners = parentData.sourceType.sourceType?.signers || [];
parentSigners =
('signers' in parentData.sourceType.sourceType &&
parentData.sourceType.sourceType?.signers) ||
[];
}
if (!providers?.length) {
@@ -1007,7 +1052,7 @@ const OracleLink = ({
}: {
providers: Provider[];
signer: SignerKind;
type: 'settlementData' | 'termination';
type: 'settlementData' | 'termination' | 'settlementSchedule';
dataSourceSpecId: string;
parentSigner?: SignerKind;
parentDataSourceSpecId?: string;
@@ -1060,7 +1105,7 @@ const OracleLink = ({
const NoOracleProof = ({
type,
}: {
type: 'settlementData' | 'termination';
type: 'settlementData' | 'termination' | 'settlementSchedule';
}) => {
return (
<p>
@@ -1092,3 +1137,27 @@ const OracleProfile = (props: {
</div>
);
};
export const getAssetSymbol = (market: MarketInfo) => {
return 'settlementAsset' in market.tradableInstrument.instrument.product
? market?.tradableInstrument.instrument.product.settlementAsset.symbol
: 'baseAsset' in market.tradableInstrument.instrument.product
? get(market?.tradableInstrument.instrument.product.baseAsset, 'symbol')
: '';
};
export const getAssetDecimals = (market: MarketInfo) => {
return 'settlementAsset' in market.tradableInstrument.instrument.product
? market?.tradableInstrument.instrument.product.settlementAsset.decimals
: 'baseAsset' in market.tradableInstrument.instrument.product
? get(market?.tradableInstrument.instrument.product.baseAsset, 'decimals')
: '';
};
export const getAssetId = (market: MarketInfo) => {
return 'settlementAsset' in market.tradableInstrument.instrument.product
? market?.tradableInstrument.instrument.product.settlementAsset.id
: 'baseAsset' in market.tradableInstrument.instrument.product
? get(market?.tradableInstrument.instrument.product.baseAsset, 'id')
: '';
};
@@ -19,18 +19,7 @@ interface MarketNameCellProps {
const MarketName = (props: MarketNameCellProps) => (
<>
<MarketNameCell {...props} />
{props.data ? (
<OracleStatus
dataSourceSpecForSettlementData={
props.data.tradableInstrument.instrument.product
.dataSourceSpecForSettlementData
}
dataSourceSpecForTradingTermination={
props.data.tradableInstrument.instrument.product
.dataSourceSpecForTradingTermination
}
/>
) : null}
{props.data ? <OracleStatus market={props.data} /> : null}
</>
);
@@ -3,28 +3,29 @@ import { useEnvironment } from '@vegaprotocol/environment';
import { Icon } from '@vegaprotocol/ui-toolkit';
import type { IconName } from '@blueprintjs/icons';
import { getMatchingOracleProvider, useOracleProofs } from '../../hooks';
import type { Market } from '../../markets-provider';
import type { MarketMaybeWithData } from '../../markets-provider';
import { getVerifiedStatusIcon } from '../oracle-basic-profile';
export const OracleStatus = ({
dataSourceSpecForSettlementData,
dataSourceSpecForTradingTermination,
}: Pick<
Market['tradableInstrument']['instrument']['product'],
'dataSourceSpecForSettlementData' | 'dataSourceSpecForTradingTermination'
>) => {
export const OracleStatus = ({ market }: { market: MarketMaybeWithData }) => {
const product = market.tradableInstrument.instrument.product || undefined;
const { ORACLE_PROOFS_URL } = useEnvironment();
const { data: providers } = useOracleProofs(ORACLE_PROOFS_URL);
return useMemo(() => {
if (providers) {
const settlementDataProvider = getMatchingOracleProvider(
dataSourceSpecForSettlementData.data,
providers
);
const tradingTerminationDataProvider = getMatchingOracleProvider(
dataSourceSpecForTradingTermination.data,
providers
);
const settlementDataProvider =
product.__typename === 'Future'
? getMatchingOracleProvider(
product.dataSourceSpecForSettlementData.data,
providers
)
: undefined;
const tradingTerminationDataProvider =
product.__typename === 'Future'
? getMatchingOracleProvider(
product.dataSourceSpecForTradingTermination.data,
providers
)
: undefined;
let maliciousOracleProvider = null;
if (settlementDataProvider?.oracle.status !== 'GOOD') {
maliciousOracleProvider = settlementDataProvider;
@@ -36,9 +37,5 @@ export const OracleStatus = ({
return <Icon size={3} name={icon as IconName} className="ml-1" />;
}
return null;
}, [
providers,
dataSourceSpecForSettlementData,
dataSourceSpecForTradingTermination,
]);
}, [providers, product]);
};
@@ -167,7 +167,11 @@ export const useColumnDefs = ({ onMarketClick }: Props) => {
'tradableInstrument.instrument.product.settlementAsset.symbol'
>) => {
const value =
data?.tradableInstrument.instrument.product.settlementAsset;
data &&
'settlementAsset' in data.tradableInstrument.instrument.product
? data?.tradableInstrument.instrument.product.settlementAsset
: undefined;
return value ? (
<ButtonLink
onClick={(e) => {
@@ -193,7 +197,11 @@ export const useColumnDefs = ({ onMarketClick }: Props) => {
<MarketActionsDropdown
marketId={data.id}
assetId={
data.tradableInstrument.instrument.product.settlementAsset.id
'settlementAsset' in
data.tradableInstrument.instrument.product
? data.tradableInstrument.instrument.product.settlementAsset
.id
: ''
}
/>
);
@@ -252,26 +252,32 @@ export const OracleFullProfile = ({
>
{MarketStateMapping[market.state]}
</div>
<div className="col-span-1">
{
<ExternalLink
href={`${VEGA_EXPLORER_URL}/oracles/${market.tradableInstrument?.instrument.product?.dataSourceSpecForSettlementData.id}`}
data-testid="block-explorer-link-settlement"
>
{t('Settlement')}
</ExternalLink>
}
</div>
<div className="col-span-1">
{
<ExternalLink
href={`${VEGA_EXPLORER_URL}/oracles/${market.tradableInstrument?.instrument.product?.dataSourceSpecForTradingTermination.id}`}
data-testid="block-explorer-link-termination"
>
{t('Termination')}
</ExternalLink>
}
</div>
{'dataSourceSpecForSettlementData' in
market.tradableInstrument.instrument.product && (
<div className="col-span-1">
{
<ExternalLink
href={`${VEGA_EXPLORER_URL}/oracles/${market.tradableInstrument?.instrument.product?.dataSourceSpecForSettlementData.id}`}
data-testid="block-explorer-link-settlement"
>
{t('Settlement')}
</ExternalLink>
}
</div>
)}
{'dataSourceSpecForTradingTermination' in
market.tradableInstrument.instrument.product && (
<div className="col-span-1">
{
<ExternalLink
href={`${VEGA_EXPLORER_URL}/oracles/${market.tradableInstrument?.instrument.product?.dataSourceSpecForTradingTermination.id}`}
data-testid="block-explorer-link-termination"
>
{t('Termination')}
</ExternalLink>
}
</div>
)}
</div>
))}
</div>
@@ -5,6 +5,7 @@ import { useMarket } from '../markets-provider';
import { useMemo } from 'react';
import type { Provider } from '../oracle-schema';
import type { DataSourceSpecFragment } from '../__generated__';
import get from 'lodash/get';
export const getMatchingOracleProvider = (
dataSourceSpec: DataSourceSpecFragment,
@@ -20,7 +21,8 @@ export const getMatchingOracleProvider = (
}
if (
dataSourceSpec.sourceType.__typename === 'DataSourceDefinitionExternal'
dataSourceSpec.sourceType.__typename === 'DataSourceDefinitionExternal' &&
'signers' in dataSourceSpec.sourceType.sourceType
) {
return dataSourceSpec.sourceType.sourceType.signers?.some(
(signer) =>
@@ -38,7 +40,8 @@ export const useMarketOracle = (
marketId: string,
dataSourceType:
| 'dataSourceSpecForSettlementData'
| 'dataSourceSpecForTradingTermination' = 'dataSourceSpecForSettlementData'
| 'dataSourceSpecForTradingTermination'
| 'dataSourceSpecForSettlementSchedule' = 'dataSourceSpecForSettlementData'
): {
data?: {
provider: NonNullable<ReturnType<typeof getMatchingOracleProvider>>;
@@ -57,8 +60,11 @@ export const useMarketOracle = (
if (!providers || !market) {
return { data: undefined };
}
const dataSourceSpec =
market.tradableInstrument.instrument.product[dataSourceType];
const dataSourceSpec = get(
market.tradableInstrument.instrument.product,
dataSourceType
);
const provider = getMatchingOracleProvider(dataSourceSpec.data, providers);
if (provider) {
return { data: { provider, dataSourceSpecId: dataSourceSpec.id } };
@@ -20,11 +20,17 @@ export const useOracleMarkets = (
?.map((edge) => edge.node)
?.filter((node) => {
const p = node.tradableInstrument.instrument.product;
const sourceType = p.dataSourceSpecForSettlementData.data.sourceType;
if (sourceType.__typename !== 'DataSourceDefinitionExternal') {
const sourceType =
'dataSourceSpecForSettlementData' in p
? p.dataSourceSpecForSettlementData.data.sourceType
: undefined;
if (sourceType?.__typename !== 'DataSourceDefinitionExternal') {
return false;
}
const signers = sourceType?.sourceType.signers;
const signers =
'signers' in sourceType.sourceType
? sourceType?.sourceType.signers
: null;
const signerKeys = signers?.filter(Boolean).map((signer) => {
if (signer.signer.__typename === 'ETHAddress') {
return signer.signer.address;
+26
View File
@@ -78,6 +78,32 @@ fragment MarketFields on Market {
tradingTerminationProperty
}
}
... on Perpetual {
settlementAsset {
id
symbol
name
decimals
quantum
}
quoteName
dataSourceSpecForSettlementSchedule {
id
data {
...DataSourceSpec
}
}
dataSourceSpecForSettlementData {
id
data {
...DataSourceSpec
}
}
dataSourceSpecBinding {
settlementDataProperty
settlementScheduleProperty
}
}
}
}
}
+1 -1
View File
@@ -150,7 +150,7 @@ export const createMarketFragment = (
__typename: 'Market',
};
return merge(defaultFragment, override);
return merge(defaultFragment, override) as MarketFieldsFragment;
};
const marketFieldsFragments: MarketFieldsFragment[] = [
@@ -61,9 +61,17 @@ export const getMetrics = (
if (!data || !data?.length) {
return [];
}
const metrics: Position[] = [];
data.forEach((position) => {
const market = position.market;
if (
!market ||
!('settlementAsset' in market.tradableInstrument.instrument.product)
) {
return;
}
if (!market) {
return;
}
@@ -104,6 +104,7 @@ const fieldGetters = {
undefined;
return (
proposed &&
'quoteName' in change.updateMarketConfiguration.instrument.product &&
change.updateMarketConfiguration.instrument.product.quoteName.length > 0
);
}
+2
View File
@@ -1791,6 +1791,8 @@ export type Market = {
liquidityMonitoringParameters: LiquidityMonitoringParameters;
/** The list of the liquidity provision commitments for this market */
liquidityProvisionsConnection?: Maybe<LiquidityProvisionsConnection>;
/** Optional: Liquidity SLA parameters for the market */
liquiditySLAParameters?: Maybe<LiquiditySLAParameters>;
/** Liquidity Provision order price range */
lpPriceRange: Scalars['String'];
/** Timestamps for state changes in the market */
+31 -1
View File
@@ -1,6 +1,6 @@
import type { ConditionOperator, PeggedReference } from './__generated__/types';
import type { AccountType } from './__generated__/types';
import type {
AccountType,
AuctionTrigger,
DataSourceSpecStatus,
DepositStatus,
@@ -47,6 +47,7 @@ export const AccountTypeMapping: {
ACCOUNT_TYPE_SETTLEMENT: 'Settlement',
ACCOUNT_TYPE_HOLDING: 'Holding',
ACCOUNT_TYPE_LP_LIQUIDITY_FEES: 'LP Liquidity Fees',
ACCOUNT_TYPE_NETWORK_TREASURY: 'Network Treasury',
};
/**
@@ -73,6 +74,7 @@ export const AuctionTriggerMapping: {
AUCTION_TRIGGER_OPENING: 'opening',
AUCTION_TRIGGER_PRICE: 'price',
AUCTION_TRIGGER_UNSPECIFIED: 'unspecified',
AUCTION_TRIGGER_GOVERNANCE_SUSPENSION: 'governance suspension',
};
/**
@@ -117,6 +119,7 @@ export const MarketStateMapping: {
STATE_SETTLED: 'Settled',
STATE_SUSPENDED: 'Suspended',
STATE_TRADING_TERMINATED: 'Trading Terminated',
STATE_SUSPENDED_VIA_GOVERNANCE: 'Suspended via governance',
};
/**
@@ -130,6 +133,7 @@ export const MarketTradingModeMapping: {
TRADING_MODE_MONITORING_AUCTION: 'Monitoring auction',
TRADING_MODE_NO_TRADING: 'No trading',
TRADING_MODE_OPENING_AUCTION: 'Opening auction',
TRADING_MODE_SUSPENDED_VIA_GOVERNANCE: 'Suspended via governance',
};
export const NodeStatusMapping: {
@@ -348,6 +352,10 @@ export const ProposalRejectionReasonMapping: {
PROPOSAL_ERROR_INVALID_SPOT: 'Invalid spot',
PROPOSAL_ERROR_INVALID_SUCCESSOR_MARKET: 'Invalid successor market',
PROPOSAL_ERROR_SPOT_PRODUCT_DISABLED: 'Spot product disabled',
PROPOSAL_ERROR_INVALID_MARKET_STATE_UPDATE: 'Invalid market state update',
PROPOSAL_ERROR_INVALID_PERPETUAL_PRODUCT: 'Invalid perpetual product',
PROPOSAL_ERROR_INVALID_SLA_PARAMS: 'Invalid SLA params',
PROPOSAL_ERROR_MISSING_SLA_PARAMS: 'Missing SLA params',
};
/**
@@ -449,6 +457,17 @@ export const TransferTypeMapping: TransferTypeMap = {
TRANSFER_TYPE_HOLDING_LOCK: 'Holding locked',
TRANSFER_TYPE_HOLDING_RELEASE: 'Holding released',
TRANSFER_TYPE_SPOT: 'Spot',
TRANSFER_TYPE_LIQUIDITY_FEE_ALLOCATE: 'Liquidity fee allocated',
TRANSFER_TYPE_LIQUIDITY_FEE_NET_DISTRIBUTE: 'Liquidity fee net distributed',
TRANSFER_TYPE_LIQUIDITY_FEE_UNPAID_COLLECT: 'Liquidity fee unpaid collected',
TRANSFER_TYPE_PERPETUALS_FUNDING_WIN: 'Perpetuals funding gain',
TRANSFER_TYPE_PERPPETUALS_FUNDING_LOSS: 'Perpetuals funding loss',
TRANSFER_TYPE_REWARDS_VESTED: 'Rewards vested',
TRANSFER_TYPE_SLA_PENALTY_BOND_APPLY: 'SLA penalty bond applied',
TRANSFER_TYPE_SLA_PENALTY_LP_FEE_APPLY: 'SLA penalty LP fee applied',
TRANSFER_TYPE_SLA_PERFORMANCE_BONUS_DISTRIBUTE:
'SLA performance bonus distributed',
TRANSFER_TYPE_SUCCESSOR_INSURANCE_FRACTION: 'Successor insurance fraction',
};
export const DescriptionTransferTypeMapping: TransferTypeMap = {
@@ -479,6 +498,17 @@ export const DescriptionTransferTypeMapping: TransferTypeMap = {
TRANSFER_TYPE_HOLDING_LOCK: 'Holdings locked',
TRANSFER_TYPE_HOLDING_RELEASE: 'Holdings released',
TRANSFER_TYPE_SPOT: 'Spot',
TRANSFER_TYPE_LIQUIDITY_FEE_ALLOCATE: 'Liquidity fee allocated',
TRANSFER_TYPE_LIQUIDITY_FEE_NET_DISTRIBUTE: 'Liquidity fee net distributed',
TRANSFER_TYPE_LIQUIDITY_FEE_UNPAID_COLLECT: 'Liquidity fee unpaid collected',
TRANSFER_TYPE_PERPETUALS_FUNDING_WIN: 'Perpetuals funding gain',
TRANSFER_TYPE_PERPPETUALS_FUNDING_LOSS: 'Perpetuals funding loss',
TRANSFER_TYPE_REWARDS_VESTED: 'Rewards vested',
TRANSFER_TYPE_SLA_PENALTY_BOND_APPLY: 'SLA penalty bond applied',
TRANSFER_TYPE_SLA_PENALTY_LP_FEE_APPLY: 'SLA penalty LP fee applied',
TRANSFER_TYPE_SLA_PERFORMANCE_BONUS_DISTRIBUTE:
'SLA performance bonus distributed',
TRANSFER_TYPE_SUCCESSOR_INSURANCE_FRACTION: 'Successor insurance fraction',
};
type DispatchMetricLabel = {
@@ -49,6 +49,7 @@ import {
useOrderByIdQuery,
useStopOrderByIdQuery,
} from '@vegaprotocol/orders';
import type { MarketFieldsFragment } from '@vegaprotocol/markets';
import { useMarketsMapProvider } from '@vegaprotocol/markets';
import type { Side } from '@vegaprotocol/types';
import { OrderStatusMapping } from '@vegaprotocol/types';
@@ -131,6 +132,21 @@ const SizeAtPrice = ({ side, size, price, meta }: SizeAtPriceProps) => {
);
};
const getAsset = (
data: MarketFieldsFragment
): {
decimals: number | undefined;
symbol: string;
} => {
// TODO to handle baseAsset for Spots
return 'settlementAsset' in data.tradableInstrument.instrument.product
? data?.tradableInstrument?.instrument?.product?.settlementAsset
: {
decimals: 0,
symbol: '',
};
};
const SubmitOrderDetails = ({
data,
order,
@@ -161,9 +177,7 @@ const SubmitOrderDetails = ({
meta={{
positionDecimalPlaces: market.positionDecimalPlaces,
decimalPlaces: market.decimalPlaces,
asset:
market.tradableInstrument.instrument.product.settlementAsset
.symbol,
asset: getAsset(market).symbol,
}}
side={side}
size={size}
@@ -203,9 +217,7 @@ const SubmitStopOrderDetails = ({ data }: { data: StopOrdersSubmission }) => {
meta={{
positionDecimalPlaces: market.positionDecimalPlaces,
decimalPlaces: market.decimalPlaces,
asset:
market.tradableInstrument.instrument.product.settlementAsset
.symbol,
asset: getAsset(market).symbol,
}}
side={side}
size={size}
@@ -252,8 +264,7 @@ const EditOrderDetails = ({
meta={{
positionDecimalPlaces: market.positionDecimalPlaces,
decimalPlaces: market.decimalPlaces,
asset:
market.tradableInstrument.instrument.product.settlementAsset.symbol,
asset: getAsset(market).symbol,
}}
/>
);
@@ -266,8 +277,7 @@ const EditOrderDetails = ({
meta={{
positionDecimalPlaces: market.positionDecimalPlaces,
decimalPlaces: market.decimalPlaces,
asset:
market.tradableInstrument.instrument.product.settlementAsset.symbol,
asset: getAsset(market).symbol,
}}
/>
);
@@ -313,8 +323,7 @@ const CancelOrderDetails = ({
meta={{
positionDecimalPlaces: market.positionDecimalPlaces,
decimalPlaces: market.decimalPlaces,
asset:
market.tradableInstrument.instrument.product.settlementAsset.symbol,
asset: getAsset(market).symbol,
}}
/>
);
@@ -355,8 +364,7 @@ const CancelStopOrderDetails = ({ stopOrderId }: { stopOrderId: string }) => {
meta={{
positionDecimalPlaces: market.positionDecimalPlaces,
decimalPlaces: market.decimalPlaces,
asset:
market.tradableInstrument.instrument.product.settlementAsset.symbol,
asset: getAsset(market).symbol,
}}
/>
<br />