2Branches0Tags
GL
glucryptoSync production with master template updates
dc969c112 days ago54Commits
typescript
import type { DeltaNeutralConfig } from "../config"; import { resolveDeltaScheduleMinutes } from "./schedule"; const HYPERLIQUID_PERP_VIP0_MAKER_FEE_RATE = 0.00015; const HYPERLIQUID_PERP_VIP0_TAKER_FEE_RATE = 0.00045; const HYPERLIQUID_SPOT_VIP0_MAKER_FEE_RATE = 0.0004; const HYPERLIQUID_SPOT_VIP0_TAKER_FEE_RATE = 0.0007; const HYPERLIQUID_BUILDER_FEE_RATE = 0.001; export function resolveHyperliquidExchangeFeeRate(params: { kind: "spot" | "perp"; feeModel?: "maker" | "taker"; }) { const feeModel = params.feeModel ?? "taker"; if (params.kind === "perp") { return feeModel === "maker" ? HYPERLIQUID_PERP_VIP0_MAKER_FEE_RATE : HYPERLIQUID_PERP_VIP0_TAKER_FEE_RATE; } return feeModel === "maker" ? HYPERLIQUID_SPOT_VIP0_MAKER_FEE_RATE : HYPERLIQUID_SPOT_VIP0_TAKER_FEE_RATE; } export function resolveHyperliquidBuilderFeeRate(params: { kind: "spot" | "perp"; side: "buy" | "sell"; }) { if (params.kind === "perp") { return HYPERLIQUID_BUILDER_FEE_RATE; } return params.side === "sell" ? HYPERLIQUID_BUILDER_FEE_RATE : 0; } export function resolveHyperliquidTotalFeeRate(params: { kind: "spot" | "perp"; side: "buy" | "sell"; feeModel?: "maker" | "taker"; }) { const exchangeFeeRate = resolveHyperliquidExchangeFeeRate(params); const builderFeeRate = resolveHyperliquidBuilderFeeRate(params); return { exchangeFeeRate, builderFeeRate, totalFeeRate: exchangeFeeRate + builderFeeRate, }; } export function estimateCarryEdgeUsd(params: { config: DeltaNeutralConfig; basisBps: number | null; fundingRateBps: number | null; hedgeNotionalUsd?: number; }) { const scheduleMinutes = resolveDeltaScheduleMinutes(params.config); const spotTurnoverUsd = Math.max(0, params.config.targetNotionalUsd); const hedgeNotionalUsd = Math.max( 0, params.hedgeNotionalUsd ?? spotTurnoverUsd * Math.max(params.config.hedgeRatio ?? 1, 0), ); const carryHours = Math.max( Math.max(1, params.config.expectedCarryHours ?? 0), (scheduleMinutes / 60) * 24, ); const expectedFundingUsd = params.fundingRateBps != null && params.fundingRateBps > 0 ? hedgeNotionalUsd * (params.fundingRateBps / 10_000) * carryHours : 0; const expectedBasisCaptureUsd = params.basisBps != null ? spotTurnoverUsd * (params.basisBps / 10_000) : 0; const slippageRate = Math.max(0, params.config.slippageBps) / 10_000; const estimatedPerpOpenCostUsd = hedgeNotionalUsd * (resolveHyperliquidTotalFeeRate({ kind: "perp", side: "sell", }).totalFeeRate + slippageRate); const estimatedPerpCloseCostUsd = hedgeNotionalUsd * (resolveHyperliquidTotalFeeRate({ kind: "perp", side: "buy", }).totalFeeRate + slippageRate); const estimatedOpenCostUsd = estimatedPerpOpenCostUsd; const estimatedRoundTripCostUsd = estimatedPerpOpenCostUsd + estimatedPerpCloseCostUsd; return { carryHours, expectedFundingUsd, expectedBasisCaptureUsd, estimatedOpenCostUsd, estimatedRoundTripCostUsd, netEdgeUsd: expectedFundingUsd + expectedBasisCaptureUsd - estimatedRoundTripCostUsd, }; }