Skip to content

Commit

Permalink
[Liquidity Proxy] Simplification & add quote observable (#607)
Browse files Browse the repository at this point in the history
* liqudiity proxy usage simplification

* add swap quote observable
  • Loading branch information
Nikita-Polyakov authored Sep 5, 2023
1 parent 00a4fd9 commit 6f33de3
Show file tree
Hide file tree
Showing 11 changed files with 182 additions and 185 deletions.
4 changes: 2 additions & 2 deletions packages/api/package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "@sora-substrate/api",
"version": "1.21.6",
"version": "1.21.7",
"license": "Apache-2.0",
"main": "./build/index.js",
"typings": "./build/index.d.ts",
Expand All @@ -10,6 +10,6 @@
"dependencies": {
"@open-web3/orml-api-derive": "1.1.4",
"@polkadot/api": "9.14.2",
"@sora-substrate/types": "1.21.6"
"@sora-substrate/types": "1.21.7"
}
}
4 changes: 2 additions & 2 deletions packages/connection/package.json
Original file line number Diff line number Diff line change
@@ -1,13 +1,13 @@
{
"name": "@sora-substrate/connection",
"version": "1.21.6",
"version": "1.21.7",
"license": "Apache-2.0",
"main": "./build/index.js",
"typings": "./build/index.d.ts",
"publishConfig": {
"access": "public"
},
"dependencies": {
"@sora-substrate/api": "1.21.6"
"@sora-substrate/api": "1.21.7"
}
}
4 changes: 2 additions & 2 deletions packages/liquidity-proxy/package.json
Original file line number Diff line number Diff line change
@@ -1,13 +1,13 @@
{
"name": "@sora-substrate/liquidity-proxy",
"version": "1.21.6",
"version": "1.21.7",
"license": "Apache-2.0",
"main": "./build/index.js",
"typings": "./build/index.d.ts",
"publishConfig": {
"access": "public"
},
"dependencies": {
"@sora-substrate/math": "1.21.6"
"@sora-substrate/math": "1.21.7"
}
}
102 changes: 31 additions & 71 deletions packages/liquidity-proxy/src/liquidityProxy.ts
Original file line number Diff line number Diff line change
Expand Up @@ -134,7 +134,7 @@ export const newTrivial = (
*/
const getAssetLiquiditySources = (
address: string,
payload: QuotePayload,
xykReserves: QuotePayload['reserves']['xyk'],
enabledAssets: PrimaryMarketsEnabledAssets,
baseAssetId: string,
syntheticBaseAssetId: string
Expand All @@ -143,7 +143,7 @@ const getAssetLiquiditySources = (
[LiquiditySourceTypes.MulticollateralBondingCurvePool]: () =>
baseAssetId === Consts.XOR && [...enabledAssets.tbc, Consts.XOR].includes(address),
[LiquiditySourceTypes.XYKPool]: () =>
baseAssetId === address || payload.reserves.xyk[address].every((tokenReserve) => !!Number(tokenReserve)),
baseAssetId === address || xykReserves[address].every((tokenReserve) => !!Number(tokenReserve)),
[LiquiditySourceTypes.XSTPool]: () =>
baseAssetId === Consts.XOR && (address === syntheticBaseAssetId || !!enabledAssets.xst[address]),
};
Expand All @@ -160,17 +160,17 @@ const getAssetLiquiditySources = (
* Liquidity sources for direct exchange between two asssets
* @param inputAssetId input asset id
* @param outputAssetId output asset id
* @param paths liquidity sources for assets
* @param assetPaths liquidity sources for assets
* @param baseAssetId Dex base asset id
*/
const listLiquiditySources = (
inputAssetId: string,
outputAssetId: string,
paths: QuotePaths,
assetPaths: QuotePaths,
baseAssetId: string,
selectedSources: LiquiditySourceTypes[] = []
): Array<LiquiditySourceTypes> => {
const getSource = (asset: string) => paths[asset] ?? [];
const getSource = (asset: string) => assetPaths[asset] ?? [];
const commonSources = intersection(getSource(inputAssetId), getSource(outputAssetId));
const directSources = commonSources.filter((source) => {
return (
Expand All @@ -187,45 +187,36 @@ const listLiquiditySources = (
* Get available liquidity sources for the tokens & exchange pair\
* @param inputAssetId Input asset address
* @param outputAssetId Output asset address
* @param payload Quote payload
* @param enabledAssets List of enabled assets
* @param xykReserves Xyk reserves of assets in exchange paths
* @param baseAssetId Dex base asset id
* @param syntheticBaseAssetId Dex synthetic base asset id
*/
export const getPathsAndPairLiquiditySources = (
inputAssetId: string,
outputAssetId: string,
payload: QuotePayload,
export const getAssetsLiquiditySources = (
exchangePaths: string[][],
enabledAssets: PrimaryMarketsEnabledAssets,
xykReserves: QuotePayload['reserves']['xyk'],
baseAssetId: string,
syntheticBaseAssetId: string
): PathsAndPairLiquiditySources => {
const assetPaths: QuotePaths = {};
let liquiditySources: Array<LiquiditySourceTypes> = [];

const exchangePaths = newTrivial(
baseAssetId,
syntheticBaseAssetId,
Object.keys(enabledAssets.xst),
inputAssetId,
outputAssetId
);

for (const exchangePath of exchangePaths) {
let exchangePathSources: Array<LiquiditySourceTypes> = [];

exchangePath.forEach((asset, index) => {
const assetSources = (assetPaths[asset] =
assetPaths[asset] ||
getAssetLiquiditySources(asset, payload, enabledAssets, baseAssetId, syntheticBaseAssetId));
getAssetLiquiditySources(asset, xykReserves, enabledAssets, baseAssetId, syntheticBaseAssetId));

exchangePathSources = index === 0 ? assetSources : intersection(exchangePathSources, assetSources);
});

liquiditySources = [...new Set([...liquiditySources, ...exchangePathSources])];
}

return { paths: assetPaths, liquiditySources };
return { assetPaths, liquiditySources };
};

// AGGREGATOR
Expand All @@ -235,11 +226,10 @@ const quotePrimaryMarket = (
amount: FPNumber,
isDesiredInput: boolean,
payload: QuotePayload,
enabledAssets: PrimaryMarketsEnabledAssets,
deduceFee: boolean
): QuoteResult => {
if ([inputAssetAddress, outputAssetAddress].includes(Consts.XSTUSD)) {
return xstQuote(inputAssetAddress, outputAssetAddress, amount, isDesiredInput, payload, deduceFee, enabledAssets);
return xstQuote(inputAssetAddress, outputAssetAddress, amount, isDesiredInput, payload, deduceFee);
} else {
return tbcQuote(inputAssetAddress, outputAssetAddress, amount, isDesiredInput, payload, deduceFee);
}
Expand All @@ -257,14 +247,13 @@ const primaryMarketAmountBuyingBaseAsset = (
isDesiredInput: boolean,
baseReserve: FPNumber,
otherReserve: FPNumber,
payload: QuotePayload,
enabledAssets: PrimaryMarketsEnabledAssets
payload: QuotePayload
): FPNumber => {
try {
const secondaryPrice = isGreaterThanZero(baseReserve) ? safeDivide(otherReserve, baseReserve) : Consts.MAX;

const primaryBuyPrice = isAssetAddress(collateralAsset, Consts.XSTUSD)
? xstBuyPriceNoVolume(collateralAsset, payload, enabledAssets)
? xstBuyPriceNoVolume(collateralAsset, payload)
: tbcBuyPriceNoVolume(collateralAsset, payload);

const k = baseReserve.mul(otherReserve);
Expand Down Expand Up @@ -315,14 +304,13 @@ const primaryMarketAmountSellingBaseAsset = (
isDesiredInput: boolean,
xorReserve: FPNumber,
otherReserve: FPNumber,
payload: QuotePayload,
enabledAssets: PrimaryMarketsEnabledAssets
payload: QuotePayload
): FPNumber => {
try {
const secondaryPrice = isGreaterThanZero(xorReserve) ? safeDivide(otherReserve, xorReserve) : FPNumber.ZERO;

const primarySellPrice = isAssetAddress(collateralAsset, Consts.XSTUSD)
? xstSellPriceNoVolume(collateralAsset, payload, enabledAssets)
? xstSellPriceNoVolume(collateralAsset, payload)
: tbcSellPriceNoVolume(collateralAsset, payload);

const k = xorReserve.mul(otherReserve);
Expand Down Expand Up @@ -370,7 +358,6 @@ const smartSplit = (
amount: FPNumber,
isDesiredInput: boolean,
payload: QuotePayload,
enabledAssets: PrimaryMarketsEnabledAssets,
deduceFee: boolean,
baseAssetId = Consts.XOR
): QuoteResult => {
Expand All @@ -386,24 +373,8 @@ const smartSplit = (
: [outputReserves, inputReserves];

const primaryAmount = isBaseAssetInput
? primaryMarketAmountSellingBaseAsset(
outputAsset,
amount,
isDesiredInput,
baseReserve,
otherReserve,
payload,
enabledAssets
)
: primaryMarketAmountBuyingBaseAsset(
inputAsset,
amount,
isDesiredInput,
baseReserve,
otherReserve,
payload,
enabledAssets
);
? primaryMarketAmountSellingBaseAsset(outputAsset, amount, isDesiredInput, baseReserve, otherReserve, payload)
: primaryMarketAmountBuyingBaseAsset(inputAsset, amount, isDesiredInput, baseReserve, otherReserve, payload);

if (isGreaterThanZero(primaryAmount)) {
const outcomePrimary = quotePrimaryMarket(
Expand All @@ -412,7 +383,6 @@ const smartSplit = (
primaryAmount,
isDesiredInput,
payload,
enabledAssets,
deduceFee
);
// check that outcomePrimary is not zero
Expand Down Expand Up @@ -474,14 +444,18 @@ const quoteSingle = (
amount: FPNumber,
isDesiredInput: boolean,
selectedSources: Array<LiquiditySourceTypes>,
paths: QuotePaths,
payload: QuotePayload,
enabledAssets: PrimaryMarketsEnabledAssets,
deduceFee: boolean,
baseAssetId = Consts.XOR
): QuoteResult => {
const allSources = listLiquiditySources(inputAsset, outputAsset, paths, baseAssetId, selectedSources);
const sources = allSources.filter((source) => !payload.lockedSources.includes(source));
const allSources = listLiquiditySources(
inputAsset,
outputAsset,
payload.sources.assetPaths,
baseAssetId,
selectedSources
);
const sources = allSources.filter((source) => !payload.enabledAssets.lockedSources.includes(source));

if (!sources.length) {
throw new Error(`[liquidityProxy] Path doesn't exist: [${inputAsset}, ${outputAsset}]`);
Expand All @@ -496,7 +470,7 @@ const quoteSingle = (
return tbcQuote(inputAsset, outputAsset, amount, isDesiredInput, payload, deduceFee);
}
case LiquiditySourceTypes.XSTPool: {
return xstQuote(inputAsset, outputAsset, amount, isDesiredInput, payload, deduceFee, enabledAssets);
return xstQuote(inputAsset, outputAsset, amount, isDesiredInput, payload, deduceFee);
}
default: {
throw new Error(`[liquidityProxy] Unexpected liquidity source: ${sources[0]}`);
Expand All @@ -510,16 +484,7 @@ const quoteSingle = (
// We can't use XST as primary market for smart split, because it use XST asset as base
sources.includes(LiquiditySourceTypes.MulticollateralBondingCurvePool)
) {
return smartSplit(
inputAsset,
outputAsset,
amount,
isDesiredInput,
payload,
enabledAssets,
deduceFee,
baseAssetId
);
return smartSplit(inputAsset, outputAsset, amount, isDesiredInput, payload, deduceFee, baseAssetId);
}
}

Expand All @@ -532,8 +497,6 @@ export const quote = (
amount: FPNumber,
isDesiredInput: boolean,
selectedSources: Array<LiquiditySourceTypes>,
enabledAssets: PrimaryMarketsEnabledAssets,
paths: QuotePaths,
payload: QuotePayload,
deduceFee: boolean,
baseAssetId = Consts.XOR,
Expand All @@ -548,10 +511,11 @@ export const quote = (
distribution: [],
};

// directed exchange paths
const exchangePaths = newTrivial(
baseAssetId,
syntheticBaseAssetId,
Object.keys(enabledAssets.xst),
Object.keys(payload.enabledAssets.xst),
firstAssetAddress,
secondAssetAddress
);
Expand Down Expand Up @@ -579,9 +543,7 @@ export const quote = (
buffer.amount,
isDesiredInput,
selectedSources,
paths,
payload,
enabledAssets,
deduceFee,
baseAssetId
);
Expand All @@ -603,7 +565,6 @@ export const quote = (
isDesiredInput,
distributionAmounts,
payload,
enabledAssets,
deduceFee,
baseAssetId
);
Expand Down Expand Up @@ -679,7 +640,6 @@ const quoteWithoutImpactSingle = (
isDesiredInput: boolean,
distribution: Array<{ market: LiquiditySourceTypes; amount: FPNumber }>,
payload: QuotePayload,
enabledAssets: PrimaryMarketsEnabledAssets,
deduceFee: boolean,
baseAssetId = Consts.XOR
): FPNumber => {
Expand All @@ -691,7 +651,7 @@ const quoteWithoutImpactSingle = (
} else if (market === LiquiditySourceTypes.MulticollateralBondingCurvePool) {
value = tbcQuoteWithoutImpact(inputAsset, outputAsset, amount, isDesiredInput, payload, deduceFee);
} else if (market === LiquiditySourceTypes.XSTPool) {
value = xstQuoteWithoutImpact(inputAsset, outputAsset, amount, isDesiredInput, payload, deduceFee, enabledAssets);
value = xstQuoteWithoutImpact(inputAsset, outputAsset, amount, isDesiredInput, payload, deduceFee);
}

return result.add(value);
Expand Down
Loading

0 comments on commit 6f33de3

Please sign in to comment.