feat(trading): add risk factors leverage and update accordion panel (#5000)
Co-authored-by: Rado <szpiechrados@gmail.com>
This commit is contained in:
parent
4968b537b8
commit
0d14722c5d
@ -3,6 +3,7 @@ import type { MarketInfoWithData } from '@vegaprotocol/markets';
|
||||
import {
|
||||
LiquidityPriceRangeInfoPanel,
|
||||
LiquiditySLAParametersInfoPanel,
|
||||
MarginScalingFactorsPanel,
|
||||
PriceMonitoringBoundsInfoPanel,
|
||||
SuccessionLineInfoPanel,
|
||||
getDataSourceSpecForSettlementData,
|
||||
@ -17,7 +18,6 @@ import {
|
||||
OracleInfoPanel,
|
||||
RiskFactorsInfoPanel,
|
||||
RiskModelInfoPanel,
|
||||
RiskParametersInfoPanel,
|
||||
SettlementAssetInfoPanel,
|
||||
} from '@vegaprotocol/markets';
|
||||
import { MarketInfoTable } from '@vegaprotocol/markets';
|
||||
@ -69,8 +69,8 @@ export const MarketDetails = ({ market }: { market: MarketInfoWithData }) => {
|
||||
<MetadataInfoPanel market={market} />
|
||||
<h2 className={headerClassName}>{t('Risk model')}</h2>
|
||||
<RiskModelInfoPanel market={market} />
|
||||
<h2 className={headerClassName}>{t('Risk parameters')}</h2>
|
||||
<RiskParametersInfoPanel market={market} />
|
||||
<h2 className={headerClassName}>{t('Margin scaling factors')}</h2>
|
||||
<MarginScalingFactorsPanel market={market} />
|
||||
<h2 className={headerClassName}>{t('Risk factors')}</h2>
|
||||
<RiskFactorsInfoPanel market={market} />
|
||||
{(market.data?.priceMonitoringBounds || []).map((trigger, i) => (
|
||||
|
@ -12,12 +12,12 @@ import {
|
||||
PriceMonitoringBoundsInfoPanel,
|
||||
RiskFactorsInfoPanel,
|
||||
RiskModelInfoPanel,
|
||||
RiskParametersInfoPanel,
|
||||
SettlementAssetInfoPanel,
|
||||
getDataSourceSpecForSettlementSchedule,
|
||||
getDataSourceSpecForSettlementData,
|
||||
getDataSourceSpecForTradingTermination,
|
||||
getSigners,
|
||||
MarginScalingFactorsPanel,
|
||||
} from '@vegaprotocol/markets';
|
||||
import {
|
||||
Button,
|
||||
@ -219,8 +219,10 @@ export const ProposalMarketData = ({
|
||||
parentMarket={parentMarketData}
|
||||
/>
|
||||
|
||||
<h2 className={marketDataHeaderStyles}>{t('Risk parameters')}</h2>
|
||||
<RiskParametersInfoPanel
|
||||
<h2 className={marketDataHeaderStyles}>
|
||||
{t('Margin scaling factors')}
|
||||
</h2>
|
||||
<MarginScalingFactorsPanel
|
||||
market={marketData}
|
||||
parentMarket={parentMarketData}
|
||||
/>
|
||||
|
@ -138,6 +138,8 @@ query MarketInfo($marketId: ID!) {
|
||||
positionDecimalPlaces
|
||||
state
|
||||
tradingMode
|
||||
linearSlippageFactor
|
||||
quadraticSlippageFactor
|
||||
proposal {
|
||||
id
|
||||
rationale {
|
||||
|
File diff suppressed because one or more lines are too long
@ -44,8 +44,6 @@ export const Row = ({
|
||||
// a specific parentValue is missing. These values are only used when we
|
||||
// have successor market parent data.
|
||||
|
||||
const className = 'text-sm';
|
||||
|
||||
const getFormattedValue = (value: ReactNode) => {
|
||||
if (typeof value !== 'string' && typeof value !== 'number') return value;
|
||||
if (unformatted || isNaN(Number(value))) {
|
||||
@ -75,8 +73,8 @@ export const Row = ({
|
||||
key={field}
|
||||
inline={true}
|
||||
noBorder={noBorder}
|
||||
dtClassName={className}
|
||||
ddClassName={className}
|
||||
dtClassName="text-xs"
|
||||
ddClassName="text-xs"
|
||||
>
|
||||
<div className="flex items-center gap-3">
|
||||
<Tooltip description={tooltipMapping[field]} align="start">
|
||||
|
@ -32,6 +32,7 @@ import {
|
||||
LiquidityMonitoringParametersInfoPanel,
|
||||
LiquidityPriceRangeInfoPanel,
|
||||
LiquiditySLAParametersInfoPanel,
|
||||
MarginScalingFactorsPanel,
|
||||
MarketPriceInfoPanel,
|
||||
MarketVolumeInfoPanel,
|
||||
MetadataInfoPanel,
|
||||
@ -39,7 +40,6 @@ import {
|
||||
PriceMonitoringBoundsInfoPanel,
|
||||
RiskFactorsInfoPanel,
|
||||
RiskModelInfoPanel,
|
||||
RiskParametersInfoPanel,
|
||||
SettlementAssetInfoPanel,
|
||||
SuccessionLineInfoPanel,
|
||||
} from './market-info-panels';
|
||||
@ -236,9 +236,9 @@ export const MarketInfoAccordion = ({
|
||||
content={<RiskModelInfoPanel market={market} />}
|
||||
/>
|
||||
<AccordionItem
|
||||
itemId="risk-parameters"
|
||||
title={t('Risk parameters')}
|
||||
content={<RiskParametersInfoPanel market={market} />}
|
||||
itemId="margin-scaling-factors"
|
||||
title={t('Margin scaling factors')}
|
||||
content={<MarginScalingFactorsPanel market={market} />}
|
||||
/>
|
||||
<AccordionItem
|
||||
itemId="risk-factors"
|
||||
|
@ -45,6 +45,7 @@ import type {
|
||||
} from '@vegaprotocol/types';
|
||||
import {
|
||||
ConditionOperatorMapping,
|
||||
MarketStateMapping,
|
||||
MarketTradingModeMapping,
|
||||
} from '@vegaprotocol/types';
|
||||
import {
|
||||
@ -220,58 +221,78 @@ export const KeyDetailsInfoPanel = ({
|
||||
const assetDecimals = getAsset(market).decimals;
|
||||
|
||||
return (
|
||||
<MarketInfoTable
|
||||
data={
|
||||
FLAGS.SUCCESSOR_MARKETS
|
||||
? {
|
||||
name: market.tradableInstrument.instrument.name,
|
||||
marketID: market.id,
|
||||
parentMarketID: parentMarketIdData?.market?.parentMarketID || '-',
|
||||
insurancePoolFraction:
|
||||
(successorProposalDetails?.proposal?.terms.change.__typename ===
|
||||
'NewMarket' &&
|
||||
successorProposalDetails.proposal.terms.change
|
||||
.successorConfiguration?.insurancePoolFraction) ||
|
||||
'-',
|
||||
tradingMode:
|
||||
market.tradingMode &&
|
||||
MarketTradingModeMapping[market.tradingMode],
|
||||
marketDecimalPlaces: market.decimalPlaces,
|
||||
positionDecimalPlaces: market.positionDecimalPlaces,
|
||||
settlementAssetDecimalPlaces: assetDecimals,
|
||||
}
|
||||
: {
|
||||
name: market.tradableInstrument.instrument.name,
|
||||
marketID: market.id,
|
||||
tradingMode:
|
||||
market.tradingMode &&
|
||||
MarketTradingModeMapping[market.tradingMode],
|
||||
marketDecimalPlaces: market.decimalPlaces,
|
||||
positionDecimalPlaces: market.positionDecimalPlaces,
|
||||
settlementAssetDecimalPlaces: assetDecimals,
|
||||
}
|
||||
}
|
||||
parentData={
|
||||
parentMarket && {
|
||||
name: parentMarket?.tradableInstrument?.instrument?.name,
|
||||
marketID: parentMarket?.id,
|
||||
parentMarketID: grandparentMarketIdData?.market?.parentMarketID,
|
||||
insurancePoolFraction:
|
||||
parentSuccessorProposalDetails?.proposal?.terms.change
|
||||
.__typename === 'NewMarket' &&
|
||||
parentSuccessorProposalDetails.proposal.terms.change
|
||||
.successorConfiguration?.insurancePoolFraction,
|
||||
tradingMode:
|
||||
parentMarket?.tradingMode &&
|
||||
MarketTradingModeMapping[
|
||||
parentMarket.tradingMode as MarketTradingMode
|
||||
],
|
||||
marketDecimalPlaces: parentMarket?.decimalPlaces,
|
||||
positionDecimalPlaces: parentMarket?.positionDecimalPlaces,
|
||||
settlementAssetDecimalPlaces: assetDecimals,
|
||||
<>
|
||||
<KeyValueTable>
|
||||
<KeyValueTableRow noBorder>
|
||||
<div>{t('Market ID')}</div>
|
||||
<CopyWithTooltip text={market.id}>
|
||||
<button
|
||||
data-testid="copy-eth-oracle-address"
|
||||
className="uppercase text-right"
|
||||
>
|
||||
<span className="flex gap-1">
|
||||
{truncateMiddle(market.id)}
|
||||
<VegaIcon name={VegaIconNames.COPY} size={16} />
|
||||
</span>
|
||||
</button>
|
||||
</CopyWithTooltip>
|
||||
</KeyValueTableRow>
|
||||
</KeyValueTable>
|
||||
<MarketInfoTable
|
||||
data={
|
||||
FLAGS.SUCCESSOR_MARKETS
|
||||
? {
|
||||
name: market.tradableInstrument.instrument.name,
|
||||
parentMarketID:
|
||||
parentMarketIdData?.market?.parentMarketID || '-',
|
||||
insurancePoolFraction:
|
||||
(successorProposalDetails?.proposal?.terms.change
|
||||
.__typename === 'NewMarket' &&
|
||||
successorProposalDetails.proposal.terms.change
|
||||
.successorConfiguration?.insurancePoolFraction) ||
|
||||
'-',
|
||||
status: market.state && MarketStateMapping[market.state],
|
||||
tradingMode:
|
||||
market.tradingMode &&
|
||||
MarketTradingModeMapping[market.tradingMode],
|
||||
marketDecimalPlaces: market.decimalPlaces,
|
||||
positionDecimalPlaces: market.positionDecimalPlaces,
|
||||
settlementAssetDecimalPlaces: assetDecimals,
|
||||
}
|
||||
: {
|
||||
name: market.tradableInstrument.instrument.name,
|
||||
status: market.state && MarketStateMapping[market.state],
|
||||
tradingMode:
|
||||
market.tradingMode &&
|
||||
MarketTradingModeMapping[market.tradingMode],
|
||||
marketDecimalPlaces: market.decimalPlaces,
|
||||
positionDecimalPlaces: market.positionDecimalPlaces,
|
||||
settlementAssetDecimalPlaces: assetDecimals,
|
||||
}
|
||||
}
|
||||
}
|
||||
/>
|
||||
parentData={
|
||||
parentMarket && {
|
||||
name: parentMarket?.tradableInstrument?.instrument?.name,
|
||||
parentMarketID: grandparentMarketIdData?.market?.parentMarketID,
|
||||
insurancePoolFraction:
|
||||
parentSuccessorProposalDetails?.proposal?.terms.change
|
||||
.__typename === 'NewMarket' &&
|
||||
parentSuccessorProposalDetails.proposal.terms.change
|
||||
.successorConfiguration?.insurancePoolFraction,
|
||||
status:
|
||||
parentMarket?.state && MarketStateMapping[parentMarket.state],
|
||||
tradingMode:
|
||||
parentMarket?.tradingMode &&
|
||||
MarketTradingModeMapping[
|
||||
parentMarket.tradingMode as MarketTradingMode
|
||||
],
|
||||
marketDecimalPlaces: parentMarket?.decimalPlaces,
|
||||
positionDecimalPlaces: parentMarket?.positionDecimalPlaces,
|
||||
settlementAssetDecimalPlaces: assetDecimals,
|
||||
}
|
||||
}
|
||||
/>
|
||||
</>
|
||||
);
|
||||
};
|
||||
|
||||
@ -432,8 +453,8 @@ export const SettlementAssetInfoPanel = ({ market }: MarketInfoProps) => {
|
||||
asset={asset}
|
||||
inline={true}
|
||||
noBorder={true}
|
||||
dtClassName="text-black dark:text-white text-ui !px-0 !font-normal"
|
||||
ddClassName="text-black dark:text-white text-ui !px-0 !font-normal max-w-full"
|
||||
dtClassName="text-black dark:text-white text-ui !px-0 text-xs"
|
||||
ddClassName="text-black dark:text-white text-ui !px-0 max-w-full text-xs"
|
||||
/>
|
||||
<p className="mt-4 text-xs">
|
||||
{t(
|
||||
@ -505,18 +526,53 @@ export const RiskModelInfoPanel = ({
|
||||
}
|
||||
|
||||
return (
|
||||
<MarketInfoTable
|
||||
data={{ tau, riskAversionParameter }}
|
||||
parentData={parentData}
|
||||
unformatted
|
||||
/>
|
||||
<>
|
||||
<MarketInfoTable
|
||||
data={{ tau, riskAversionParameter }}
|
||||
parentData={parentData}
|
||||
unformatted
|
||||
/>
|
||||
<RiskParametersInfoPanel market={market} parentMarket={parentMarket} />
|
||||
</>
|
||||
);
|
||||
};
|
||||
|
||||
export const RiskParametersInfoPanel = ({
|
||||
export const MarginScalingFactorsPanel = ({
|
||||
market,
|
||||
parentMarket,
|
||||
}: MarketInfoProps) => {
|
||||
const data = {
|
||||
linearSlippageFactor: market.linearSlippageFactor,
|
||||
quadraticSlippageFactor: market.quadraticSlippageFactor,
|
||||
searchLevel:
|
||||
market.tradableInstrument.marginCalculator?.scalingFactors.searchLevel,
|
||||
initialMargin:
|
||||
market.tradableInstrument.marginCalculator?.scalingFactors.initialMargin,
|
||||
collateralRelease:
|
||||
market.tradableInstrument.marginCalculator?.scalingFactors
|
||||
.collateralRelease,
|
||||
};
|
||||
|
||||
const parentData = parentMarket
|
||||
? {
|
||||
linearSlippageFactor: parentMarket?.linearSlippageFactor,
|
||||
quadraticSlippageFactor: parentMarket?.quadraticSlippageFactor,
|
||||
searchLevel:
|
||||
parentMarket?.tradableInstrument.marginCalculator?.scalingFactors
|
||||
.searchLevel,
|
||||
initialMargin:
|
||||
parentMarket?.tradableInstrument.marginCalculator?.scalingFactors
|
||||
.initialMargin,
|
||||
collateralRelease:
|
||||
parentMarket?.tradableInstrument.marginCalculator?.scalingFactors
|
||||
.collateralRelease,
|
||||
}
|
||||
: undefined;
|
||||
|
||||
return <MarketInfoTable data={data} parentData={parentData} unformatted />;
|
||||
};
|
||||
|
||||
const RiskParametersInfoPanel = ({ market, parentMarket }: MarketInfoProps) => {
|
||||
const marketType = market.tradableInstrument.riskModel.__typename;
|
||||
|
||||
let data, parentData;
|
||||
@ -562,27 +618,66 @@ export const RiskFactorsInfoPanel = ({
|
||||
market,
|
||||
parentMarket,
|
||||
}: MarketInfoProps) => {
|
||||
if (!market.riskFactors) {
|
||||
return null;
|
||||
}
|
||||
const getLeverageFactors = (market: MarketInfo) => {
|
||||
if (!market.riskFactors) {
|
||||
return undefined;
|
||||
}
|
||||
|
||||
const { short, long } = market.riskFactors;
|
||||
const { short, long } = market.riskFactors;
|
||||
|
||||
let parentData;
|
||||
const maxLeverageLong = new BigNumber(1).dividedBy(
|
||||
new BigNumber(market.linearSlippageFactor).plus(long)
|
||||
);
|
||||
|
||||
if (parentMarket?.riskFactors) {
|
||||
const parentShort = parentMarket.riskFactors.short;
|
||||
const parentLong = parentMarket.riskFactors.long;
|
||||
parentData = { short: parentShort, long: parentLong };
|
||||
}
|
||||
const maxLeverageShort = new BigNumber(1).dividedBy(
|
||||
new BigNumber(market.linearSlippageFactor).plus(short)
|
||||
);
|
||||
|
||||
return (
|
||||
<MarketInfoTable
|
||||
data={{ short, long }}
|
||||
parentData={parentData}
|
||||
unformatted
|
||||
/>
|
||||
);
|
||||
const maxInitialLeverageLong = !market.tradableInstrument.marginCalculator
|
||||
? undefined
|
||||
: new BigNumber(1)
|
||||
.dividedBy(
|
||||
market.tradableInstrument.marginCalculator.scalingFactors
|
||||
.initialMargin
|
||||
)
|
||||
.times(maxLeverageLong);
|
||||
|
||||
const maxInitialLeverageShort = !market.tradableInstrument.marginCalculator
|
||||
? undefined
|
||||
: new BigNumber(1)
|
||||
.dividedBy(
|
||||
market.tradableInstrument.marginCalculator.scalingFactors
|
||||
.initialMargin
|
||||
)
|
||||
.times(maxLeverageShort);
|
||||
|
||||
const formatValue = (number: BigNumber | string | undefined) => {
|
||||
if (!number) return undefined;
|
||||
const value = new BigNumber(number);
|
||||
if (value.gte(10)) {
|
||||
return value.toFixed(3);
|
||||
} else {
|
||||
return value.toFixed(5);
|
||||
}
|
||||
};
|
||||
|
||||
const data = {
|
||||
long: formatValue(long),
|
||||
short: formatValue(short),
|
||||
maxLeverageLong: formatValue(maxLeverageLong),
|
||||
maxLeverageShort: formatValue(maxLeverageShort),
|
||||
maxInitialLeverageLong: formatValue(maxInitialLeverageLong),
|
||||
maxInitialLeverageShort: formatValue(maxInitialLeverageShort),
|
||||
};
|
||||
return data;
|
||||
};
|
||||
|
||||
const data = getLeverageFactors(market);
|
||||
const parentData = parentMarket
|
||||
? getLeverageFactors(parentMarket)
|
||||
: undefined;
|
||||
|
||||
return <MarketInfoTable data={data} parentData={parentData} unformatted />;
|
||||
};
|
||||
|
||||
export const PriceMonitoringBoundsInfoPanel = ({
|
||||
|
@ -23,6 +23,8 @@ export const marketInfoQuery = (
|
||||
description: '',
|
||||
},
|
||||
},
|
||||
linearSlippageFactor: '0.01',
|
||||
quadraticSlippageFactor: '0.0001',
|
||||
marketTimestamps: {
|
||||
__typename: 'MarketTimestamps',
|
||||
open: '2022-11-15T02:15:24.543614154Z',
|
||||
|
@ -74,9 +74,13 @@ export const KeyValueTableRow = ({
|
||||
{ 'flex-row items-center': inline },
|
||||
className
|
||||
);
|
||||
const dtClassNames = `break-words ${dtClassName}`;
|
||||
const dtClassNames = classNames(
|
||||
'break-words',
|
||||
dtClassName,
|
||||
'text-neutral-500 dark:text-neutral-300'
|
||||
);
|
||||
const ddClassNames = classNames(
|
||||
'break-words text-neutral-500 dark:text-neutral-300',
|
||||
'break-words',
|
||||
{
|
||||
'font-mono': numerical,
|
||||
},
|
||||
|
@ -90,12 +90,22 @@ When I look into market info I **Must** see following specification:
|
||||
- Risk model: (<a name="6002-MDET-209" href="#6002-MDET-209">6002-MDET-209</a>)
|
||||
- Tau
|
||||
- Risk Aversion Parameter
|
||||
- Risk parameters: (<a name="6002-MDET-210" href="#6002-MDET-210">6002-MDET-210</a>)
|
||||
- R
|
||||
- Sigma
|
||||
- Margin scaling factors (<a name="6002-MDET-210" href="#6002-MDET-210">6002-MDET-210</a>)
|
||||
- Linear Slippage Factor
|
||||
- Quadratic Slippage Factor
|
||||
- Search Level
|
||||
- Initial Margin
|
||||
- Collateral Release
|
||||
- Risk factors: (<a name="6002-MDET-211" href="#6002-MDET-211">6002-MDET-211</a>)
|
||||
- Short
|
||||
- Long
|
||||
- price monitoring bounds <i>(multiple bounds possible)</i>: (<a name="6002-MDET-212" href="#6002-MDET-212">6002-MDET-212</a>)
|
||||
- Short
|
||||
- Max Leverage Long
|
||||
- Max Leverage Short
|
||||
- Max Initial Leverage Long
|
||||
- Max Initial Leverage Short
|
||||
- Price monitoring bounds <i>(multiple bounds possible)</i>: (<a name="6002-MDET-212" href="#6002-MDET-212">6002-MDET-212</a>)
|
||||
- Highest Price
|
||||
- Lowest Price
|
||||
- Liquidity monitoring parameters: (<a name="6002-MDET-213" href="#6002-MDET-213">6002-MDET-213</a>)
|
||||
|
Loading…
Reference in New Issue
Block a user