Merge pull request #107 from drift-labs/cache-topmakers

cache top makers
This commit is contained in:
Nour Alharithi
2024-03-06 11:35:18 -08:00
committed by GitHub
2 changed files with 76 additions and 21 deletions

View File

@@ -4,6 +4,7 @@ import {
DLOBSubscriptionConfig,
L2OrderBookGenerator,
MarketType,
PositionDirection,
groupL2,
isVariant,
} from '@drift-labs/sdk';
@@ -248,6 +249,35 @@ export class DLOBSubscriberIO extends DLOBSubscriber {
`last_update_orderbook_${marketType}_${marketArgs.marketIndex}_depth_5`,
JSON.stringify(l2Formatted_depth5)
);
const oraclePriceData =
marketType === 'spot'
? this.driftClient.getOracleDataForSpotMarket(marketArgs.marketIndex)
: this.driftClient.getOracleDataForPerpMarket(marketArgs.marketIndex);
const bids = this.dlob
.getBestMakers({
marketIndex: marketArgs.marketIndex,
marketType: marketArgs.marketType,
direction: PositionDirection.LONG,
slot: slot,
oraclePriceData,
numMakers: 4,
})
.map((x) => x.toString());
const asks = this.dlob
.getBestMakers({
marketIndex: marketArgs.marketIndex,
marketType: marketArgs.marketType,
direction: PositionDirection.SHORT,
slot,
oraclePriceData,
numMakers: 4,
})
.map((x) => x.toString());
this.redisClient.client.set(
`last_update_orderbook_best_makers_${marketType}_${marketArgs.marketIndex}`,
JSON.stringify({ bids, asks, slot })
);
}
getL3AndSendMsg(marketArgs: wsMarketArgs): void {

View File

@@ -19,7 +19,6 @@ import {
DriftEnv,
SlotSubscriber,
Wallet,
getUserStatsAccountPublicKey,
getVariant,
initialize,
isVariant,
@@ -720,8 +719,7 @@ const main = async (): Promise<void> => {
marketIndex,
marketType,
side, // bid or ask
limit, // number of unique makers to return, if undefined will return all
includeUserStats,
limit,
} = req.query;
const { normedMarketType, normedMarketIndex, error } = validateDlobQuery(
@@ -752,9 +750,46 @@ const main = async (): Promise<void> => {
return;
}
normedLimit = parseInt(limit as string);
} else {
normedLimit = 4;
}
const topMakers = new Set();
let topMakers: string[];
if (useRedis) {
const redisClient = isVariant(normedMarketType, 'perp')
? perpMarketRedisMap.get(normedMarketIndex).client
: spotMarketRedisMap.get(normedMarketIndex).client;
const redisResponse = await redisClient.client.get(
`last_update_orderbook_best_makers_${getVariant(
normedMarketType
)}_${marketIndex}`
);
if (redisResponse) {
const parsedResponse = JSON.parse(redisResponse);
if (
parsedResponse &&
Math.abs(dlobProvider.getSlot() - parsedResponse.slot) <
SLOT_STALENESS_TOLERANCE
) {
if (side === 'bid') {
topMakers = parsedResponse.bids;
} else {
topMakers = parsedResponse.asks;
}
}
}
}
if (topMakers) {
cacheHitCounter.add(1, {
miss: false,
});
res.writeHead(200);
res.end(JSON.stringify(topMakers));
return;
}
const topMakersSet = new Set<string>();
let foundMakers = 0;
const findMakers = async (sideGenerator: Generator<DLOBNode>) => {
for (const side of sideGenerator) {
@@ -763,23 +798,10 @@ const main = async (): Promise<void> => {
}
if (side.userAccount) {
const maker = side.userAccount;
if (topMakers.has(maker)) {
if (topMakersSet.has(maker)) {
continue;
} else {
if (`${includeUserStats}`.toLowerCase() === 'true') {
const userAccount = dlobProvider.getUserAccount(
new PublicKey(side.userAccount)
);
topMakers.add([
userAccount,
getUserStatsAccountPublicKey(
driftClient.program.programId,
userAccount.authority
),
]);
} else {
topMakers.add(side.userAccount);
}
topMakersSet.add(side.userAccount);
foundMakers++;
}
} else {
@@ -811,9 +833,12 @@ const main = async (): Promise<void> => {
)
);
}
topMakers = [...topMakersSet];
cacheHitCounter.add(1, {
miss: true,
});
res.writeHead(200);
res.end(JSON.stringify([...topMakers]));
res.end(JSON.stringify(topMakers));
} catch (err) {
next(err);
}