@yuants/vendor-aster 0.9.3 → 0.9.5

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1 +1 @@
1
- {"version":3,"file":"private-api.js","sourceRoot":"","sources":["../../src/api/private-api.ts"],"names":[],"mappings":"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","sourcesContent":["import { encodeHex, HmacSHA256, newError } from '@yuants/utils';\n\nimport { GlobalPrometheusRegistry, Terminal } from '@yuants/protocol';\n\nconst MetricsAsterApiCallCounter = GlobalPrometheusRegistry.counter(\n 'aster_api_call',\n 'Number of aster api call',\n);\nconst terminal = Terminal.fromNodeEnv();\n\nexport interface ICredential {\n address: string;\n api_key: string;\n secret_key: string;\n}\n\nexport interface IAsterFutureOpenOrder {\n orderId: number;\n clientOrderId: string;\n price: string;\n origQty: string;\n executedQty: string;\n status: string;\n timeInForce: string;\n type: string;\n side: 'BUY' | 'SELL';\n updateTime: number;\n avgPrice: string;\n reduceOnly?: boolean;\n closePosition?: boolean;\n positionSide?: 'BOTH' | 'LONG' | 'SHORT';\n workingType?: string;\n priceProtect?: boolean;\n origType?: string;\n stopPrice?: string;\n symbol: string;\n}\n\nexport interface IAsterSpotOpenOrder {\n orderId: number;\n clientOrderId: string;\n price: string;\n origQty: string;\n executedQty: string;\n cummulativeQuoteQty?: string;\n status: string;\n timeInForce: string;\n type: string;\n side: 'BUY' | 'SELL';\n stopPrice?: string;\n icebergQty?: string;\n time: number;\n updateTime: number;\n isWorking?: boolean;\n avgPrice?: string;\n symbol: string;\n}\n\nconst request = async <T>(\n credential: ICredential,\n method: string,\n baseURL: string,\n endpoint: string,\n params: any = {},\n): Promise<T> => {\n const url = new URL(baseURL);\n url.pathname = endpoint;\n for (const [key, value] of Object.entries(params)) {\n if (value === undefined) continue;\n url.searchParams.set(key, `${value}`);\n }\n\n url.searchParams.set('timestamp', `${Date.now()}`);\n const msg = url.search.slice(1); // 去掉开头的 '?'\n const signature = encodeHex(\n await HmacSHA256(new TextEncoder().encode(msg), new TextEncoder().encode(credential.secret_key)),\n );\n url.searchParams.set('signature', signature);\n\n console.info(url.toString());\n MetricsAsterApiCallCounter.labels({ path: url.pathname, terminal_id: terminal.terminal_id }).inc();\n const response = await fetch(url.toString(), {\n method,\n headers: {\n 'X-MBX-APIKEY': credential.api_key,\n },\n });\n\n const resText = await response.text();\n\n try {\n const res = JSON.parse(resText);\n\n if (res.code && res.code !== 0) {\n throw resText;\n }\n return res;\n } catch (e) {\n throw newError(\n 'ASTER_API_ERROR',\n {\n status: response.status,\n statusText: response.statusText,\n resText,\n params,\n },\n e,\n );\n }\n};\n\nconst createApi =\n (baseURL: string) =>\n <TReq, TRes>(method: string, endpoint: string) =>\n (credential: ICredential, params: TReq) =>\n request<TRes>(credential, method, baseURL, endpoint, params);\n\nconst createFutureApi = createApi('https://fapi.asterdex.com');\nconst createSpotApi = createApi('https://sapi.asterdex.com');\n\n/**\n * 获取账户信息\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md#%E8%B4%A6%E6%88%B7%E4%BF%A1%E6%81%AFv4-user_data\n */\nexport const getFApiV4Account = createFutureApi<\n {},\n {\n feeTier: number;\n canTrade: boolean;\n canDeposit: boolean;\n canWithdraw: boolean;\n updateTime: number;\n totalInitialMargin: string;\n totalMaintMargin: string;\n totalWalletBalance: string;\n totalUnrealizedProfit: string;\n totalMarginBalance: string;\n totalPositionInitialMargin: string;\n totalOpenOrderInitialMargin: string;\n totalCrossWalletBalance: string;\n totalCrossUnPnl: string;\n availableBalance: string;\n maxWithdrawAmount: string;\n assets: {\n asset: string;\n walletBalance: string;\n unrealizedProfit: string;\n marginBalance: string;\n maintMargin: string;\n initialMargin: string;\n positionInitialMargin: string;\n openOrderInitialMargin: string;\n maxWithdrawAmount: string;\n crossWalletBalance: string;\n crossUnPnl: string;\n availableBalance: string;\n marginAvailable: boolean;\n updateTime: number;\n }[];\n positions: {\n symbol: string;\n initialMargin: string;\n maintMargin: string;\n unrealizedProfit: string;\n positionInitialMargin: string;\n openOrderInitialMargin: string;\n leverage: string;\n isolated: boolean;\n entryPrice: string;\n maxNotional: string;\n positionSide: 'BOTH' | 'LONG' | 'SHORT';\n positionAmt: string;\n notional: string;\n isolatedWallet: string;\n updateTime: number;\n }[];\n }\n>('GET', '/fapi/v4/account');\n\n/**\n * 用户持仓风险V2 (USER_DATA)\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md#%E7%94%A8%E6%88%B7%E6%8C%81%E4%BB%93%E9%A3%8E%E9%99%A9v2-user_data\n */\nexport const getFApiV2PositionRisk = createFutureApi<\n {\n symbol?: string;\n },\n {\n entryPrice: string;\n marginType: string;\n isAutoAddMargin: string;\n isolatedMargin: string;\n leverage: string;\n liquidationPrice: string;\n markPrice: string;\n maxNotionalValue: string;\n positionAmt: string;\n symbol: string;\n unRealizedProfit: string;\n positionSide: string;\n updateTime: number;\n }[]\n>('GET', '/fapi/v2/positionRisk');\n\nexport const getFApiV2Balance = createFutureApi<\n {},\n {\n accountAlias: string; // 账户唯一识别码\n asset: string; // 资产\n balance: string; // 总余额\n crossWalletBalance: string; // 全仓余额\n crossUnPnl: string; // 全仓持仓未实现盈亏\n availableBalance: string; // 下单可用余额\n maxWithdrawAmount: string; // 最大可转出余额\n marginAvailable: boolean; // 是否可用作联合保证金\n updateTime: number;\n }[]\n>('GET', '/fapi/v2/balance');\n\nexport const postFApiV1Order = createFutureApi<\n {\n symbol: string;\n side: 'BUY' | 'SELL';\n positionSide?: 'BOTH' | 'LONG' | 'SHORT';\n type:\n | 'MARKET'\n | 'LIMIT'\n | 'STOP'\n | 'STOP_MARKET'\n | 'TAKE_PROFIT'\n | 'TAKE_PROFIT_MARKET'\n | 'TRAILING_STOP_MARKET';\n reduceOnly?: 'true' | 'false';\n quantity?: number;\n price?: number;\n timeInForce?: 'GTC' | 'IOC' | 'FOK' | 'GTX' | 'HIDDEN';\n },\n {}\n>('POST', '/fapi/v1/order');\n\n/**\n * 查询当前挂单 (永续)\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md#L2728-L2766\n */\nexport const getFApiV1OpenOrders = createFutureApi<\n {\n symbol?: string;\n },\n IAsterFutureOpenOrder[]\n>('GET', '/fapi/v1/openOrders');\n\n/**\n * 查询当前挂单 (现货)\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-spot-api_CN.md#L1196-L1234\n */\nexport const getApiV1OpenOrders = createSpotApi<\n {\n symbol?: string;\n },\n IAsterSpotOpenOrder[]\n>('GET', '/api/v1/openOrders');\n\nexport const deleteFApiV1Order = createFutureApi<\n {\n symbol: string;\n orderId?: string | number;\n origClientOrderId?: string;\n },\n {}\n>('DELETE', '/fapi/v1/order');\n\n/**\n * 获取账户信息 (现货)\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-spot-api_CN.md#%E8%B4%A6%E6%88%B7%E4%BF%A1%E6%81%AF-user_data\n */\nexport const getApiV1Account = createSpotApi<\n {},\n {\n feeTier: number;\n canTrade: boolean;\n canDeposit: boolean;\n canWithdraw: boolean;\n canBurnAsset: boolean;\n updateTime: number;\n balances: {\n asset: string;\n free: string;\n locked: string;\n }[];\n }\n>('GET', '/api/v1/account');\n\n/**\n * 获取最新价格\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-spot-api_CN.md#%E6%9C%80%E6%96%B0%E4%BB%B7%E6%A0%BC\n */\nexport const getApiV1TickerPrice = createSpotApi<\n {},\n {\n symbol: string;\n price: string;\n time: number;\n }[]\n>('GET', '/api/v1/ticker/price');\n\nexport const postApiV1Order = createSpotApi<\n {\n symbol: string;\n side: 'BUY' | 'SELL';\n type: 'MARKET' | 'LIMIT' | 'STOP' | 'STOP_MARKET' | 'TAKE_PROFIT' | 'TAKE_PROFIT_MARKET';\n timeInForce?: 'GTC' | 'IOC' | 'FOK' | 'GTX';\n quantity?: number;\n quoteOrderQty?: number;\n price?: number;\n },\n {\n orderId: number; // 系统的订单ID\n }\n>('POST', '/api/v1/order');\n\n/**\n * 取消有效订单 (现货)\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-spot-api_CN.md#L1040-L1074\n */\nexport const deleteApiV1Order = createSpotApi<\n {\n symbol: string;\n orderId?: string | number;\n origClientOrderId?: string;\n },\n {}\n>('DELETE', '/api/v1/order');\n"]}
1
+ {"version":3,"file":"private-api.js","sourceRoot":"","sources":["../../src/api/private-api.ts"],"names":[],"mappings":"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","sourcesContent":["import { encodeHex, HmacSHA256, newError, scopeError, tokenBucket } from '@yuants/utils';\n\nimport { GlobalPrometheusRegistry, Terminal } from '@yuants/protocol';\n\nimport './client';\n\nconst MetricsAsterApiCallCounter = GlobalPrometheusRegistry.counter(\n 'aster_api_call',\n 'Number of aster api call',\n);\nconst terminal = Terminal.fromNodeEnv();\n\nexport interface ICredential {\n address: string;\n api_key: string;\n secret_key: string;\n}\n\nexport interface IAsterFutureOpenOrder {\n orderId: number;\n clientOrderId: string;\n price: string;\n origQty: string;\n executedQty: string;\n status: string;\n timeInForce: string;\n type: string;\n side: 'BUY' | 'SELL';\n updateTime: number;\n avgPrice: string;\n reduceOnly?: boolean;\n closePosition?: boolean;\n positionSide?: 'BOTH' | 'LONG' | 'SHORT';\n workingType?: string;\n priceProtect?: boolean;\n origType?: string;\n stopPrice?: string;\n symbol: string;\n}\n\nexport interface IAsterSpotOpenOrder {\n orderId: number;\n clientOrderId: string;\n price: string;\n origQty: string;\n executedQty: string;\n cummulativeQuoteQty?: string;\n status: string;\n timeInForce: string;\n type: string;\n side: 'BUY' | 'SELL';\n stopPrice?: string;\n icebergQty?: string;\n time: number;\n updateTime: number;\n isWorking?: boolean;\n avgPrice?: string;\n symbol: string;\n}\n\nconst request = async <T>(\n credential: ICredential,\n method: string,\n baseURL: string,\n endpoint: string,\n params: Record<string, unknown> = {},\n): Promise<T> => {\n const url = new URL(baseURL);\n url.pathname = endpoint;\n for (const [key, value] of Object.entries(params)) {\n if (value === undefined) continue;\n url.searchParams.set(key, `${value}`);\n }\n\n url.searchParams.set('timestamp', `${Date.now()}`);\n const msg = url.search.slice(1); // 去掉开头的 '?'\n const signature = encodeHex(\n await HmacSHA256(new TextEncoder().encode(msg), new TextEncoder().encode(credential.secret_key)),\n );\n url.searchParams.set('signature', signature);\n\n console.info(url.toString());\n MetricsAsterApiCallCounter.labels({ path: url.pathname, terminal_id: terminal.terminal_id }).inc();\n const response = await fetch(url.toString(), {\n method,\n headers: {\n 'X-MBX-APIKEY': credential.api_key,\n },\n });\n\n const resText = await response.text();\n\n try {\n const res = JSON.parse(resText);\n\n if (res.code && res.code !== 0) {\n throw resText;\n }\n return res;\n } catch (e) {\n throw newError(\n 'ASTER_API_ERROR',\n {\n status: response.status,\n statusText: response.statusText,\n resText,\n params,\n },\n e,\n );\n }\n};\n\nconst FutureBaseURL = 'https://fapi.asterdex.com';\nconst SpotBaseURL = 'https://sapi.asterdex.com';\n\n/**\n * 获取账户信息\n *\n * Weight: 5\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md#%E8%B4%A6%E6%88%B7%E4%BF%A1%E6%81%AFv4-user_data\n */\nexport const getFApiV4Account = (\n credential: ICredential,\n params: Record<string, never>,\n): Promise<{\n feeTier: number;\n canTrade: boolean;\n canDeposit: boolean;\n canWithdraw: boolean;\n updateTime: number;\n totalInitialMargin: string;\n totalMaintMargin: string;\n totalWalletBalance: string;\n totalUnrealizedProfit: string;\n totalMarginBalance: string;\n totalPositionInitialMargin: string;\n totalOpenOrderInitialMargin: string;\n totalCrossWalletBalance: string;\n totalCrossUnPnl: string;\n availableBalance: string;\n maxWithdrawAmount: string;\n assets: {\n asset: string;\n walletBalance: string;\n unrealizedProfit: string;\n marginBalance: string;\n maintMargin: string;\n initialMargin: string;\n positionInitialMargin: string;\n openOrderInitialMargin: string;\n maxWithdrawAmount: string;\n crossWalletBalance: string;\n crossUnPnl: string;\n availableBalance: string;\n marginAvailable: boolean;\n updateTime: number;\n }[];\n positions: {\n symbol: string;\n initialMargin: string;\n maintMargin: string;\n unrealizedProfit: string;\n positionInitialMargin: string;\n openOrderInitialMargin: string;\n leverage: string;\n isolated: boolean;\n entryPrice: string;\n maxNotional: string;\n positionSide: 'BOTH' | 'LONG' | 'SHORT';\n positionAmt: string;\n notional: string;\n isolatedWallet: string;\n updateTime: number;\n }[];\n}> => {\n const endpoint = '/fapi/v4/account';\n const url = new URL(FutureBaseURL);\n url.pathname = endpoint;\n const weight = 5;\n scopeError(\n 'ASTER_API_RATE_LIMIT',\n { method: 'GET', endpoint, host: url.host, path: url.pathname, bucketId: url.host, weight },\n () => tokenBucket(url.host).acquireSync(weight),\n );\n return request(credential, 'GET', FutureBaseURL, endpoint, params);\n};\n\n/**\n * 用户持仓风险V2 (USER_DATA)\n *\n * Weight: 5\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md#%E7%94%A8%E6%88%B7%E6%8C%81%E4%BB%93%E9%A3%8E%E9%99%A9v2-user_data\n */\nexport const getFApiV2PositionRisk = (\n credential: ICredential,\n params: {\n symbol?: string;\n },\n): Promise<\n {\n entryPrice: string;\n marginType: string;\n isAutoAddMargin: string;\n isolatedMargin: string;\n leverage: string;\n liquidationPrice: string;\n markPrice: string;\n maxNotionalValue: string;\n positionAmt: string;\n symbol: string;\n unRealizedProfit: string;\n positionSide: string;\n updateTime: number;\n }[]\n> => {\n const endpoint = '/fapi/v2/positionRisk';\n const url = new URL(FutureBaseURL);\n url.pathname = endpoint;\n const weight = 5;\n scopeError(\n 'ASTER_API_RATE_LIMIT',\n { method: 'GET', endpoint, host: url.host, path: url.pathname, bucketId: url.host, weight },\n () => tokenBucket(url.host).acquireSync(weight),\n );\n return request(credential, 'GET', FutureBaseURL, endpoint, params);\n};\n\n/**\n * Weight: 5\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md#L2840-L2855\n */\nexport const getFApiV2Balance = (\n credential: ICredential,\n params: Record<string, never>,\n): Promise<\n {\n accountAlias: string;\n asset: string;\n balance: string;\n crossWalletBalance: string;\n crossUnPnl: string;\n availableBalance: string;\n maxWithdrawAmount: string;\n marginAvailable: boolean;\n updateTime: number;\n }[]\n> => {\n const endpoint = '/fapi/v2/balance';\n const url = new URL(FutureBaseURL);\n url.pathname = endpoint;\n const weight = 5;\n scopeError(\n 'ASTER_API_RATE_LIMIT',\n { method: 'GET', endpoint, host: url.host, path: url.pathname, bucketId: url.host, weight },\n () => tokenBucket(url.host).acquireSync(weight),\n );\n return request(credential, 'GET', FutureBaseURL, endpoint, params);\n};\n\n/**\n * Weight: 1 by order\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md#post-fapiv1order-%E7%9A%84%E7%A4%BA%E4%BE%8B\n */\nexport const postFApiV1Order = (\n credential: ICredential,\n params: {\n symbol: string;\n side: 'BUY' | 'SELL';\n positionSide?: 'BOTH' | 'LONG' | 'SHORT';\n type:\n | 'MARKET'\n | 'LIMIT'\n | 'STOP'\n | 'STOP_MARKET'\n | 'TAKE_PROFIT'\n | 'TAKE_PROFIT_MARKET'\n | 'TRAILING_STOP_MARKET';\n reduceOnly?: 'true' | 'false';\n quantity?: number;\n price?: number;\n timeInForce?: 'GTC' | 'IOC' | 'FOK' | 'GTX' | 'HIDDEN';\n },\n): Promise<Record<string, never>> => {\n const endpoint = '/fapi/v1/order';\n const url = new URL(FutureBaseURL);\n url.pathname = endpoint;\n const weight = 1;\n scopeError(\n 'ASTER_FUTURE_ORDER_API_SECOND_RATE_LIMIT',\n { method: 'POST', endpoint, host: url.host, path: url.pathname, bucketId: url.host, weight },\n () => tokenBucket('order/future/second').acquireSync(weight),\n );\n scopeError(\n 'ASTER_FUTURE_ORDER_API_MINUTE_RATE_LIMIT',\n { method: 'POST', endpoint, host: url.host, path: url.pathname, bucketId: url.host, weight },\n () => tokenBucket('order/future/minute').acquireSync(weight),\n );\n return request(credential, 'POST', FutureBaseURL, endpoint, params);\n};\n\n/**\n * 查询当前挂单 (永续)\n *\n * Weight: with symbol 1, without symbol 40\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md#L2728-L2766\n */\nexport const getFApiV1OpenOrders = (\n credential: ICredential,\n params: {\n symbol?: string;\n },\n): Promise<IAsterFutureOpenOrder[]> => {\n const endpoint = '/fapi/v1/openOrders';\n const url = new URL(FutureBaseURL);\n url.pathname = endpoint;\n const weight = params?.symbol ? 1 : 40;\n scopeError(\n 'ASTER_API_RATE_LIMIT',\n {\n method: 'GET',\n endpoint,\n host: url.host,\n path: url.pathname,\n bucketId: url.host,\n weight,\n hasSymbol: !!params?.symbol,\n },\n () => tokenBucket(url.host).acquireSync(weight),\n );\n return request(credential, 'GET', FutureBaseURL, endpoint, params);\n};\n\n/**\n * 查询当前挂单 (现货)\n *\n * Weight: with symbol 1, without symbol 40\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-spot-api_CN.md#L1196-L1234\n */\nexport const getApiV1OpenOrders = (\n credential: ICredential,\n params: {\n symbol?: string;\n },\n): Promise<IAsterSpotOpenOrder[]> => {\n const endpoint = '/api/v1/openOrders';\n const url = new URL(SpotBaseURL);\n url.pathname = endpoint;\n const weight = params?.symbol ? 1 : 40;\n scopeError(\n 'ASTER_API_RATE_LIMIT',\n {\n method: 'GET',\n endpoint,\n host: url.host,\n path: url.pathname,\n bucketId: url.host,\n weight,\n hasSymbol: !!params?.symbol,\n },\n () => tokenBucket(url.host).acquireSync(weight),\n );\n return request(credential, 'GET', SpotBaseURL, endpoint, params);\n};\n\n/**\n * Weight: 1\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md#L2498-L2516\n */\nexport const deleteFApiV1Order = (\n credential: ICredential,\n params: {\n symbol: string;\n orderId?: string | number;\n origClientOrderId?: string;\n },\n): Promise<Record<string, never>> => {\n const endpoint = '/fapi/v1/order';\n const url = new URL(FutureBaseURL);\n url.pathname = endpoint;\n const weight = 1;\n scopeError(\n 'ASTER_FUTURE_ORDER_API_SECOND_RATE_LIMIT',\n { method: 'DELETE', endpoint, host: url.host, path: url.pathname, bucketId: url.host, weight },\n () => tokenBucket('order/future/second').acquireSync(weight),\n );\n scopeError(\n 'ASTER_FUTURE_ORDER_API_MINUTE_RATE_LIMIT',\n { method: 'DELETE', endpoint, host: url.host, path: url.pathname, bucketId: url.host, weight },\n () => tokenBucket('order/future/minute').acquireSync(weight),\n );\n return request(credential, 'DELETE', FutureBaseURL, endpoint, params);\n};\n\n/**\n * 获取账户信息 (现货)\n *\n * Weight: 5\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-spot-api_CN.md#%E8%B4%A6%E6%88%B7%E4%BF%A1%E6%81%AF-user_data\n */\nexport const getApiV1Account = (\n credential: ICredential,\n params: Record<string, never>,\n): Promise<{\n feeTier: number;\n canTrade: boolean;\n canDeposit: boolean;\n canWithdraw: boolean;\n canBurnAsset: boolean;\n updateTime: number;\n balances: {\n asset: string;\n free: string;\n locked: string;\n }[];\n}> => {\n const endpoint = '/api/v1/account';\n const url = new URL(SpotBaseURL);\n url.pathname = endpoint;\n const weight = 5;\n scopeError(\n 'ASTER_API_RATE_LIMIT',\n { method: 'GET', endpoint, host: url.host, path: url.pathname, bucketId: url.host, weight },\n () => tokenBucket(url.host).acquireSync(weight),\n );\n return request(credential, 'GET', SpotBaseURL, endpoint, params);\n};\n\n/**\n * 获取最新价格\n *\n * Weight: without symbol 2 (current implementation)\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-spot-api_CN.md#%E6%9C%80%E6%96%B0%E4%BB%B7%E6%A0%BC\n */\nexport const getApiV1TickerPrice = (\n credential: ICredential,\n params: Record<string, never>,\n): Promise<\n {\n symbol: string;\n price: string;\n time: number;\n }[]\n> => {\n const endpoint = '/api/v1/ticker/price';\n const url = new URL(SpotBaseURL);\n url.pathname = endpoint;\n const weight = 2;\n scopeError(\n 'ASTER_API_RATE_LIMIT',\n { method: 'GET', endpoint, host: url.host, path: url.pathname, bucketId: url.host, weight },\n () => tokenBucket(url.host).acquireSync(weight),\n );\n return request(credential, 'GET', SpotBaseURL, endpoint, params);\n};\n\n/**\n * Weight: 1\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-spot-api_CN.md#post-apiv1order-%E7%9A%84%E7%A4%BA%E4%BE%8B\n */\nexport const postApiV1Order = (\n credential: ICredential,\n params: {\n symbol: string;\n side: 'BUY' | 'SELL';\n type: 'MARKET' | 'LIMIT' | 'STOP' | 'STOP_MARKET' | 'TAKE_PROFIT' | 'TAKE_PROFIT_MARKET';\n timeInForce?: 'GTC' | 'IOC' | 'FOK' | 'GTX';\n quantity?: number;\n quoteOrderQty?: number;\n price?: number;\n },\n): Promise<{\n orderId: number;\n}> => {\n const endpoint = '/api/v1/order';\n const url = new URL(SpotBaseURL);\n url.pathname = endpoint;\n const weight = 1;\n scopeError(\n 'ASTER_SPOT_ORDER_API_SECOND_RATE_LIMIT',\n { method: 'POST', endpoint, host: url.host, path: url.pathname, bucketId: url.host, weight },\n () => tokenBucket('order/spot/second').acquireSync(weight),\n );\n scopeError(\n 'ASTER_SPOT_ORDER_API_MINUTE_RATE_LIMIT',\n { method: 'POST', endpoint, host: url.host, path: url.pathname, bucketId: url.host, weight },\n () => tokenBucket('order/spot/minute').acquireSync(weight),\n );\n return request(credential, 'POST', SpotBaseURL, endpoint, params);\n};\n\n/**\n * 取消有效订单 (现货)\n *\n * Weight: 1\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-spot-api_CN.md#L1040-L1074\n */\nexport const deleteApiV1Order = (\n credential: ICredential,\n params: {\n symbol: string;\n orderId?: string | number;\n origClientOrderId?: string;\n },\n): Promise<Record<string, never>> => {\n const endpoint = '/api/v1/order';\n const url = new URL(SpotBaseURL);\n url.pathname = endpoint;\n const weight = 1;\n scopeError(\n 'ASTER_SPOT_ORDER_API_SECOND_RATE_LIMIT',\n { method: 'DELETE', endpoint, host: url.host, path: url.pathname, bucketId: url.host, weight },\n () => tokenBucket('order/spot/second').acquireSync(weight),\n );\n scopeError(\n 'ASTER_SPOT_ORDER_API_MINUTE_RATE_LIMIT',\n { method: 'DELETE', endpoint, host: url.host, path: url.pathname, bucketId: url.host, weight },\n () => tokenBucket('order/spot/minute').acquireSync(weight),\n );\n return request(credential, 'DELETE', SpotBaseURL, endpoint, params);\n};\n"]}
@@ -1,13 +1,16 @@
1
+ import './client';
1
2
  /**
2
3
  * 获取资金费率历史
3
4
  *
5
+ * Weight: 1
6
+ *
4
7
  * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md#%E6%9F%A5%E8%AF%A2%E8%B5%84%E9%87%91%E8%B4%B9%E7%8E%87%E5%8E%86%E5%8F%B2
5
8
  */
6
9
  export declare const getFApiV1FundingRate: (params: {
7
- symbol?: string | undefined;
8
- startTime?: number | undefined;
9
- endTime?: number | undefined;
10
- limit?: number | undefined;
10
+ symbol?: string;
11
+ startTime?: number;
12
+ endTime?: number;
13
+ limit?: number;
11
14
  }) => Promise<{
12
15
  symbol: string;
13
16
  fundingRate: string;
@@ -39,12 +42,16 @@ export interface IAsterExchangeInfo {
39
42
  /**
40
43
  * 获取交易对信息
41
44
  *
45
+ * Weight: 1
46
+ *
42
47
  * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md#%E4%BA%A4%E6%98%93%E5%AF%B9%E4%BF%A1%E6%81%AF
43
48
  */
44
49
  export declare const getFApiV1ExchangeInfo: (params: Record<string, never>) => Promise<IAsterExchangeInfo>;
45
50
  /**
46
51
  * 获取现货交易对信息
47
52
  *
53
+ * Weight: 1
54
+ *
48
55
  * https://github.com/asterdex/api-docs/blob/master/aster-finance-spot-api_CN.md#L1080-L1145
49
56
  */
50
57
  export declare const getApiV1ExchangeInfo: (params: Record<string, never>) => Promise<IAsterExchangeInfo>;
@@ -52,6 +59,10 @@ export declare const getApiV1ExchangeInfo: (params: Record<string, never>) => Pr
52
59
  * 获取未平仓合约数量
53
60
  *
54
61
  * 无 API 文档 (weird)
62
+ * 参考 Binance 风格接口:/fapi/v1/openInterest
63
+ *
64
+ * Weight: 1
65
+ * https://developers.binance.com/docs/zh-CN/derivatives/usds-margined-futures/market-data/rest-api/Open-Interest
55
66
  */
56
67
  export declare const getFApiV1OpenInterest: (params: {
57
68
  symbol: string;
@@ -63,19 +74,24 @@ export declare const getFApiV1OpenInterest: (params: {
63
74
  /**
64
75
  * 获取最新价格
65
76
  *
77
+ * Weight: without symbol 2 (current implementation)
78
+ *
66
79
  * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md#%E6%9C%80%E6%96%B0%E4%BB%B7%E6%A0%BC
67
80
  */
68
81
  export declare const getFApiV1TickerPrice: (params: Record<string, never>) => Promise<{
69
82
  symbol: string;
70
83
  price: string;
71
- time?: number | undefined;
84
+ time?: number;
72
85
  }[]>;
73
86
  /**
74
87
  * 获取资金费率
88
+ *
89
+ * Weight: 1
90
+ *
75
91
  * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md
76
92
  */
77
93
  export declare const getFApiV1PremiumIndex: (params: {
78
- symbol?: string | undefined;
94
+ symbol?: string;
79
95
  }) => Promise<{
80
96
  symbol: string;
81
97
  markPrice: string;
@@ -113,27 +129,32 @@ export interface IAsterKline extends Array<string | number> {
113
129
  * 获取 K 线
114
130
  *
115
131
  * 参考 Binance 风格接口:/fapi/v1/klines
132
+ *
133
+ * Weight: by limit
134
+ *
116
135
  * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md#k%E7%BA%BF%E6%95%B0%E6%8D%AE
117
136
  */
118
137
  export declare const getFApiV1Klines: (params: {
119
138
  symbol: string;
120
139
  interval: string;
121
- startTime?: number | undefined;
122
- endTime?: number | undefined;
123
- limit?: number | undefined;
140
+ startTime?: number;
141
+ endTime?: number;
142
+ limit?: number;
124
143
  }) => Promise<IAsterKline[]>;
125
144
  /**
126
145
  * 获取现货 K 线
127
146
  *
128
147
  * 参考 Binance 风格接口:/api/v1/klines
129
148
  *
149
+ * Weight: not documented (temporary: follow futures limit table)
150
+ *
130
151
  * https://github.com/asterdex/api-docs/blob/master/aster-finance-spot-api_CN.md
131
152
  */
132
153
  export declare const getApiV1Klines: (params: {
133
154
  symbol: string;
134
155
  interval: string;
135
- startTime?: number | undefined;
136
- endTime?: number | undefined;
137
- limit?: number | undefined;
156
+ startTime?: number;
157
+ endTime?: number;
158
+ limit?: number;
138
159
  }) => Promise<IAsterKline[]>;
139
160
  //# sourceMappingURL=public-api.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"public-api.d.ts","sourceRoot":"","sources":["../../src/api/public-api.ts"],"names":[],"mappings":"AA0CA;;;;GAIG;AACH,eAAO,MAAM,oBAAoB;;;;;;YAQrB,MAAM;iBACD,MAAM;iBACN,MAAM;IAES,CAAC;AAEjC,MAAM,WAAW,eAAe;IAC9B,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,KAAK,CAAC,EAAE,MAAM,CAAC;CAChB;AAED,MAAM,WAAW,kBAAkB;IACjC,OAAO,EAAE;QACP,MAAM,EAAE,MAAM,CAAC;QACf,MAAM,EAAE,SAAS,GAAG,OAAO,GAAG,MAAM,CAAC;QACrC,SAAS,EAAE,MAAM,CAAC;QAClB,UAAU,EAAE,MAAM,CAAC;QACnB,cAAc,EAAE,MAAM,CAAC;QACvB,iBAAiB,EAAE,MAAM,CAAC;QAC1B,kBAAkB,EAAE,MAAM,CAAC;QAC3B,cAAc,EAAE,MAAM,CAAC;QACvB,OAAO,EAAE;YACP,UAAU,EAAE,MAAM,CAAC;YACnB,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC;SACxB,EAAE,CAAC;KACL,EAAE,CAAC;IACJ,UAAU,CAAC,EAAE,eAAe,EAAE,CAAC;CAChC;AAED;;;;GAIG;AACH,eAAO,MAAM,qBAAqB,gEAGjC,CAAC;AAEF;;;;GAIG;AACH,eAAO,MAAM,oBAAoB,gEAGhC,CAAC;AAEF;;;;GAIG;AACH,eAAO,MAAM,qBAAqB;YAEtB,MAAM;;YAGN,MAAM;kBACA,MAAM;UACd,MAAM;EAEiB,CAAC;AAElC;;;;GAIG;AACH,eAAO,MAAM,oBAAoB;YAGrB,MAAM;WACP,MAAM;;IAGgB,CAAC;AAElC;;;GAGG;AACH,eAAO,MAAM,qBAAqB;;;YAKpB,MAAM;eACH,MAAM;gBACL,MAAM;0BACI,MAAM;qBACX,MAAM;qBACN,MAAM;kBACT,MAAM;UACd,MAAM;;YAGJ,MAAM;eACH,MAAM;gBACL,MAAM;0BACI,MAAM;qBACX,MAAM;qBACN,MAAM;kBACT,MAAM;UACd,MAAM;IAEe,CAAC;AAElC,MAAM,WAAW,WAAY,SAAQ,KAAK,CAAC,MAAM,GAAG,MAAM,CAAC;IACzD,CAAC,EAAE,MAAM,CAAC;IACV,CAAC,EAAE,MAAM,CAAC;IACV,CAAC,EAAE,MAAM,CAAC;IACV,CAAC,EAAE,MAAM,CAAC;IACV,CAAC,EAAE,MAAM,CAAC;IACV,CAAC,EAAE,MAAM,CAAC;IACV,CAAC,EAAE,MAAM,CAAC;IACV,CAAC,EAAE,MAAM,CAAC;IACV,CAAC,EAAE,MAAM,CAAC;IACV,CAAC,EAAE,MAAM,CAAC;IACV,EAAE,EAAE,MAAM,CAAC;IACX,EAAE,EAAE,MAAM,CAAC;CACZ;AAED;;;;;GAKG;AACH,eAAO,MAAM,eAAe;YAEhB,MAAM;cACJ,MAAM;;;;4BAMO,CAAC;AAE5B;;;;;;GAMG;AACH,eAAO,MAAM,cAAc;YAEf,MAAM;cACJ,MAAM;;;;4BAMM,CAAC"}
1
+ {"version":3,"file":"public-api.d.ts","sourceRoot":"","sources":["../../src/api/public-api.ts"],"names":[],"mappings":"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"}
@@ -2,8 +2,22 @@
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.getApiV1Klines = exports.getFApiV1Klines = exports.getFApiV1PremiumIndex = exports.getFApiV1TickerPrice = exports.getFApiV1OpenInterest = exports.getApiV1ExchangeInfo = exports.getFApiV1ExchangeInfo = exports.getFApiV1FundingRate = void 0;
4
4
  const protocol_1 = require("@yuants/protocol");
5
+ const utils_1 = require("@yuants/utils");
6
+ require("./client");
5
7
  const MetricsAsterApiCallCounter = protocol_1.GlobalPrometheusRegistry.counter('aster_api_call', 'Number of aster api call');
6
8
  const terminal = protocol_1.Terminal.fromNodeEnv();
9
+ const FutureBaseURL = 'https://fapi.asterdex.com';
10
+ const SpotBaseURL = 'https://sapi.asterdex.com';
11
+ const getKlinesRequestWeight = (limit) => {
12
+ const resolvedLimit = limit !== null && limit !== void 0 ? limit : 500;
13
+ if (resolvedLimit < 100)
14
+ return 1;
15
+ if (resolvedLimit < 500)
16
+ return 2;
17
+ if (resolvedLimit <= 1000)
18
+ return 5;
19
+ return 10;
20
+ };
7
21
  const request = async (method, baseUrl, endpoint, params = {}) => {
8
22
  const url = new URL(baseUrl);
9
23
  url.pathname = endpoint;
@@ -23,57 +37,154 @@ const request = async (method, baseUrl, endpoint, params = {}) => {
23
37
  }
24
38
  return res;
25
39
  };
26
- const createApi = (baseUrl) => (method, endpoint) => (params) => request(method, baseUrl, endpoint, params);
27
- const createFutureApi = createApi('https://fapi.asterdex.com');
28
- const createSpotApi = createApi('https://sapi.asterdex.com');
29
40
  /**
30
41
  * 获取资金费率历史
31
42
  *
43
+ * Weight: 1
44
+ *
32
45
  * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md#%E6%9F%A5%E8%AF%A2%E8%B5%84%E9%87%91%E8%B4%B9%E7%8E%87%E5%8E%86%E5%8F%B2
33
46
  */
34
- exports.getFApiV1FundingRate = createFutureApi('GET', '/fapi/v1/fundingRate');
47
+ const getFApiV1FundingRate = (params) => {
48
+ const endpoint = '/fapi/v1/fundingRate';
49
+ const url = new URL(FutureBaseURL);
50
+ url.pathname = endpoint;
51
+ const weight = 1;
52
+ (0, utils_1.scopeError)('ASTER_API_RATE_LIMIT', { method: 'GET', endpoint, host: url.host, path: url.pathname, bucketId: url.host, weight }, () => (0, utils_1.tokenBucket)(url.host).acquireSync(weight));
53
+ return request('GET', FutureBaseURL, endpoint, params);
54
+ };
55
+ exports.getFApiV1FundingRate = getFApiV1FundingRate;
35
56
  /**
36
57
  * 获取交易对信息
37
58
  *
59
+ * Weight: 1
60
+ *
38
61
  * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md#%E4%BA%A4%E6%98%93%E5%AF%B9%E4%BF%A1%E6%81%AF
39
62
  */
40
- exports.getFApiV1ExchangeInfo = createFutureApi('GET', '/fapi/v1/exchangeInfo');
63
+ const getFApiV1ExchangeInfo = (params) => {
64
+ const endpoint = '/fapi/v1/exchangeInfo';
65
+ const url = new URL(FutureBaseURL);
66
+ url.pathname = endpoint;
67
+ const weight = 1;
68
+ (0, utils_1.scopeError)('ASTER_API_RATE_LIMIT', { method: 'GET', endpoint, host: url.host, path: url.pathname, bucketId: url.host, weight }, () => (0, utils_1.tokenBucket)(url.host).acquireSync(weight));
69
+ return request('GET', FutureBaseURL, endpoint, params);
70
+ };
71
+ exports.getFApiV1ExchangeInfo = getFApiV1ExchangeInfo;
41
72
  /**
42
73
  * 获取现货交易对信息
43
74
  *
75
+ * Weight: 1
76
+ *
44
77
  * https://github.com/asterdex/api-docs/blob/master/aster-finance-spot-api_CN.md#L1080-L1145
45
78
  */
46
- exports.getApiV1ExchangeInfo = createSpotApi('GET', '/api/v1/exchangeInfo');
79
+ const getApiV1ExchangeInfo = (params) => {
80
+ const endpoint = '/api/v1/exchangeInfo';
81
+ const url = new URL(SpotBaseURL);
82
+ url.pathname = endpoint;
83
+ const weight = 1;
84
+ (0, utils_1.scopeError)('ASTER_API_RATE_LIMIT', { method: 'GET', endpoint, host: url.host, path: url.pathname, bucketId: url.host, weight }, () => (0, utils_1.tokenBucket)(url.host).acquireSync(weight));
85
+ return request('GET', SpotBaseURL, endpoint, params);
86
+ };
87
+ exports.getApiV1ExchangeInfo = getApiV1ExchangeInfo;
47
88
  /**
48
89
  * 获取未平仓合约数量
49
90
  *
50
91
  * 无 API 文档 (weird)
92
+ * 参考 Binance 风格接口:/fapi/v1/openInterest
93
+ *
94
+ * Weight: 1
95
+ * https://developers.binance.com/docs/zh-CN/derivatives/usds-margined-futures/market-data/rest-api/Open-Interest
51
96
  */
52
- exports.getFApiV1OpenInterest = createFutureApi('GET', '/fapi/v1/openInterest');
97
+ const getFApiV1OpenInterest = (params) => {
98
+ const endpoint = '/fapi/v1/openInterest';
99
+ const url = new URL(FutureBaseURL);
100
+ url.pathname = endpoint;
101
+ const weight = 1;
102
+ (0, utils_1.scopeError)('ASTER_API_RATE_LIMIT', { method: 'GET', endpoint, host: url.host, path: url.pathname, bucketId: url.host, weight }, () => (0, utils_1.tokenBucket)(url.host).acquireSync(weight));
103
+ return request('GET', FutureBaseURL, endpoint, params);
104
+ };
105
+ exports.getFApiV1OpenInterest = getFApiV1OpenInterest;
53
106
  /**
54
107
  * 获取最新价格
55
108
  *
109
+ * Weight: without symbol 2 (current implementation)
110
+ *
56
111
  * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md#%E6%9C%80%E6%96%B0%E4%BB%B7%E6%A0%BC
57
112
  */
58
- exports.getFApiV1TickerPrice = createFutureApi('GET', '/fapi/v1/ticker/price');
113
+ const getFApiV1TickerPrice = (params) => {
114
+ const endpoint = '/fapi/v1/ticker/price';
115
+ const url = new URL(FutureBaseURL);
116
+ url.pathname = endpoint;
117
+ const weight = 2;
118
+ (0, utils_1.scopeError)('ASTER_API_RATE_LIMIT', { method: 'GET', endpoint, host: url.host, path: url.pathname, bucketId: url.host, weight }, () => (0, utils_1.tokenBucket)(url.host).acquireSync(weight));
119
+ return request('GET', FutureBaseURL, endpoint, params);
120
+ };
121
+ exports.getFApiV1TickerPrice = getFApiV1TickerPrice;
59
122
  /**
60
123
  * 获取资金费率
124
+ *
125
+ * Weight: 1
126
+ *
61
127
  * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md
62
128
  */
63
- exports.getFApiV1PremiumIndex = createFutureApi('GET', '/fapi/v1/premiumIndex');
129
+ const getFApiV1PremiumIndex = (params) => {
130
+ const endpoint = '/fapi/v1/premiumIndex';
131
+ const url = new URL(FutureBaseURL);
132
+ url.pathname = endpoint;
133
+ const weight = 1;
134
+ (0, utils_1.scopeError)('ASTER_API_RATE_LIMIT', { method: 'GET', endpoint, host: url.host, path: url.pathname, bucketId: url.host, weight }, () => (0, utils_1.tokenBucket)(url.host).acquireSync(weight));
135
+ return request('GET', FutureBaseURL, endpoint, params);
136
+ };
137
+ exports.getFApiV1PremiumIndex = getFApiV1PremiumIndex;
64
138
  /**
65
139
  * 获取 K 线
66
140
  *
67
141
  * 参考 Binance 风格接口:/fapi/v1/klines
142
+ *
143
+ * Weight: by limit
144
+ *
68
145
  * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md#k%E7%BA%BF%E6%95%B0%E6%8D%AE
69
146
  */
70
- exports.getFApiV1Klines = createFutureApi('GET', '/fapi/v1/klines');
147
+ const getFApiV1Klines = (params) => {
148
+ const endpoint = '/fapi/v1/klines';
149
+ const url = new URL(FutureBaseURL);
150
+ url.pathname = endpoint;
151
+ const weight = getKlinesRequestWeight(params === null || params === void 0 ? void 0 : params.limit);
152
+ (0, utils_1.scopeError)('ASTER_API_RATE_LIMIT', {
153
+ method: 'GET',
154
+ endpoint,
155
+ host: url.host,
156
+ path: url.pathname,
157
+ bucketId: url.host,
158
+ weight,
159
+ limit: params === null || params === void 0 ? void 0 : params.limit,
160
+ }, () => (0, utils_1.tokenBucket)(url.host).acquireSync(weight));
161
+ return request('GET', FutureBaseURL, endpoint, params);
162
+ };
163
+ exports.getFApiV1Klines = getFApiV1Klines;
71
164
  /**
72
165
  * 获取现货 K 线
73
166
  *
74
167
  * 参考 Binance 风格接口:/api/v1/klines
75
168
  *
169
+ * Weight: not documented (temporary: follow futures limit table)
170
+ *
76
171
  * https://github.com/asterdex/api-docs/blob/master/aster-finance-spot-api_CN.md
77
172
  */
78
- exports.getApiV1Klines = createSpotApi('GET', '/api/v1/klines');
173
+ const getApiV1Klines = (params) => {
174
+ const endpoint = '/api/v1/klines';
175
+ const url = new URL(SpotBaseURL);
176
+ url.pathname = endpoint;
177
+ const weight = getKlinesRequestWeight(params === null || params === void 0 ? void 0 : params.limit);
178
+ (0, utils_1.scopeError)('ASTER_API_RATE_LIMIT', {
179
+ method: 'GET',
180
+ endpoint,
181
+ host: url.host,
182
+ path: url.pathname,
183
+ bucketId: url.host,
184
+ weight,
185
+ limit: params === null || params === void 0 ? void 0 : params.limit,
186
+ }, () => (0, utils_1.tokenBucket)(url.host).acquireSync(weight));
187
+ return request('GET', SpotBaseURL, endpoint, params);
188
+ };
189
+ exports.getApiV1Klines = getApiV1Klines;
79
190
  //# sourceMappingURL=public-api.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"public-api.js","sourceRoot":"","sources":["../../src/api/public-api.ts"],"names":[],"mappings":";;;AAAA,+CAAsE;AAEtE,MAAM,0BAA0B,GAAG,mCAAwB,CAAC,OAAO,CACjE,gBAAgB,EAChB,0BAA0B,CAC3B,CAAC;AACF,MAAM,QAAQ,GAAG,mBAAQ,CAAC,WAAW,EAAE,CAAC;AACxC,MAAM,OAAO,GAAG,KAAK,EACnB,MAAc,EACd,OAAe,EACf,QAAgB,EAChB,SAAkC,EAAE,EACxB,EAAE;IACd,MAAM,GAAG,GAAG,IAAI,GAAG,CAAC,OAAO,CAAC,CAAC;IAC7B,GAAG,CAAC,QAAQ,GAAG,QAAQ,CAAC;IACxB,KAAK,MAAM,CAAC,GAAG,EAAE,KAAK,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,MAAM,CAAC,EAAE;QACjD,IAAI,KAAK,KAAK,SAAS;YAAE,SAAS;QAClC,GAAG,CAAC,YAAY,CAAC,GAAG,CAAC,GAAG,EAAE,GAAG,KAAK,EAAE,CAAC,CAAC;KACvC;IAED,OAAO,CAAC,IAAI,CAAC,GAAG,CAAC,QAAQ,EAAE,CAAC,CAAC;IAC7B,0BAA0B,CAAC,MAAM,CAAC,EAAE,IAAI,EAAE,GAAG,CAAC,QAAQ,EAAE,WAAW,EAAE,QAAQ,CAAC,WAAW,EAAE,CAAC,CAAC,GAAG,EAAE,CAAC;IACnG,MAAM,GAAG,GAAG,CAAC,MAAM,KAAK,CAAC,GAAG,CAAC,QAAQ,EAAE,EAAE;QACvC,MAAM;KACP,CAAC,CAAC,IAAI,CAAC,CAAC,QAAQ,EAAE,EAAE,CAAC,QAAQ,CAAC,IAAI,EAAE,CAAC,CAAY,CAAC;IAEnD,MAAM,UAAU,GAAG,GAAwB,CAAC;IAC5C,IAAI,OAAO,UAAU,CAAC,IAAI,KAAK,QAAQ,IAAI,UAAU,CAAC,IAAI,KAAK,CAAC,EAAE;QAChE,MAAM,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,CAAC;KAC3B;IACD,OAAO,GAAQ,CAAC;AAClB,CAAC,CAAC;AAEF,MAAM,SAAS,GACb,CAAC,OAAe,EAAE,EAAE,CACpB,CAA6C,MAAc,EAAE,QAAgB,EAAE,EAAE,CACjF,CAAC,MAAY,EAAE,EAAE,CACf,OAAO,CAAO,MAAM,EAAE,OAAO,EAAE,QAAQ,EAAE,MAAM,CAAC,CAAC;AAErD,MAAM,eAAe,GAAG,SAAS,CAAC,2BAA2B,CAAC,CAAC;AAC/D,MAAM,aAAa,GAAG,SAAS,CAAC,2BAA2B,CAAC,CAAC;AAE7D;;;;GAIG;AACU,QAAA,oBAAoB,GAAG,eAAe,CAYjD,KAAK,EAAE,sBAAsB,CAAC,CAAC;AA2BjC;;;;GAIG;AACU,QAAA,qBAAqB,GAAG,eAAe,CAClD,KAAK,EACL,uBAAuB,CACxB,CAAC;AAEF;;;;GAIG;AACU,QAAA,oBAAoB,GAAG,aAAa,CAC/C,KAAK,EACL,sBAAsB,CACvB,CAAC;AAEF;;;;GAIG;AACU,QAAA,qBAAqB,GAAG,eAAe,CASlD,KAAK,EAAE,uBAAuB,CAAC,CAAC;AAElC;;;;GAIG;AACU,QAAA,oBAAoB,GAAG,eAAe,CAOjD,KAAK,EAAE,uBAAuB,CAAC,CAAC;AAElC;;;GAGG;AACU,QAAA,qBAAqB,GAAG,eAAe,CAwBlD,KAAK,EAAE,uBAAuB,CAAC,CAAC;AAiBlC;;;;;GAKG;AACU,QAAA,eAAe,GAAG,eAAe,CAS5C,KAAK,EAAE,iBAAiB,CAAC,CAAC;AAE5B;;;;;;GAMG;AACU,QAAA,cAAc,GAAG,aAAa,CASzC,KAAK,EAAE,gBAAgB,CAAC,CAAC","sourcesContent":["import { GlobalPrometheusRegistry, Terminal } from '@yuants/protocol';\n\nconst MetricsAsterApiCallCounter = GlobalPrometheusRegistry.counter(\n 'aster_api_call',\n 'Number of aster api call',\n);\nconst terminal = Terminal.fromNodeEnv();\nconst request = async <T>(\n method: string,\n baseUrl: string,\n endpoint: string,\n params: Record<string, unknown> = {},\n): Promise<T> => {\n const url = new URL(baseUrl);\n url.pathname = endpoint;\n for (const [key, value] of Object.entries(params)) {\n if (value === undefined) continue;\n url.searchParams.set(key, `${value}`);\n }\n\n console.info(url.toString());\n MetricsAsterApiCallCounter.labels({ path: url.pathname, terminal_id: terminal.terminal_id }).inc();\n const res = (await fetch(url.toString(), {\n method,\n }).then((response) => response.json())) as unknown;\n\n const maybeError = res as { code?: number };\n if (typeof maybeError.code === 'number' && maybeError.code !== 0) {\n throw JSON.stringify(res);\n }\n return res as T;\n};\n\nconst createApi =\n (baseUrl: string) =>\n <TReq extends Record<string, unknown>, TRes>(method: string, endpoint: string) =>\n (params: TReq) =>\n request<TRes>(method, baseUrl, endpoint, params);\n\nconst createFutureApi = createApi('https://fapi.asterdex.com');\nconst createSpotApi = createApi('https://sapi.asterdex.com');\n\n/**\n * 获取资金费率历史\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md#%E6%9F%A5%E8%AF%A2%E8%B5%84%E9%87%91%E8%B4%B9%E7%8E%87%E5%8E%86%E5%8F%B2\n */\nexport const getFApiV1FundingRate = createFutureApi<\n {\n symbol?: string;\n startTime?: number;\n endTime?: number;\n limit?: number;\n },\n {\n symbol: string;\n fundingRate: string;\n fundingTime: number;\n }[]\n>('GET', '/fapi/v1/fundingRate');\n\nexport interface IAsterRateLimit {\n rateLimitType?: string;\n interval?: string;\n intervalNum?: number;\n limit?: number;\n}\n\nexport interface IAsterExchangeInfo {\n symbols: {\n symbol: string;\n status: 'TRADING' | 'BREAK' | 'HALT';\n baseAsset: string;\n quoteAsset: string;\n pricePrecision: number;\n quantityPrecision: number;\n baseAssetPrecision: number;\n quotePrecision: number;\n filters: {\n filterType: string;\n [key: string]: unknown;\n }[];\n }[];\n rateLimits?: IAsterRateLimit[];\n}\n\n/**\n * 获取交易对信息\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md#%E4%BA%A4%E6%98%93%E5%AF%B9%E4%BF%A1%E6%81%AF\n */\nexport const getFApiV1ExchangeInfo = createFutureApi<Record<string, never>, IAsterExchangeInfo>(\n 'GET',\n '/fapi/v1/exchangeInfo',\n);\n\n/**\n * 获取现货交易对信息\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-spot-api_CN.md#L1080-L1145\n */\nexport const getApiV1ExchangeInfo = createSpotApi<Record<string, never>, IAsterExchangeInfo>(\n 'GET',\n '/api/v1/exchangeInfo',\n);\n\n/**\n * 获取未平仓合约数量\n *\n * 无 API 文档 (weird)\n */\nexport const getFApiV1OpenInterest = createFutureApi<\n {\n symbol: string;\n },\n {\n symbol: string;\n openInterest: string;\n time: number;\n }\n>('GET', '/fapi/v1/openInterest');\n\n/**\n * 获取最新价格\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md#%E6%9C%80%E6%96%B0%E4%BB%B7%E6%A0%BC\n */\nexport const getFApiV1TickerPrice = createFutureApi<\n Record<string, never>,\n {\n symbol: string;\n price: string;\n time?: number;\n }[]\n>('GET', '/fapi/v1/ticker/price');\n\n/**\n * 获取资金费率\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md\n */\nexport const getFApiV1PremiumIndex = createFutureApi<\n {\n symbol?: string;\n },\n | {\n symbol: string; // 交易对\n markPrice: string; // 标记价格\n indexPrice: string; // 指数价格\n estimatedSettlePrice: string; // 预估结算价,仅在交割开始前最后一小时有意义\n lastFundingRate: string; // 最近更新的资金费率\n nextFundingTime: number; // 下次资金费时间\n interestRate: string; // 标的资产基础利率\n time: number; // 更新时间\n }\n | {\n symbol: string; // 交易对\n markPrice: string; // 标记价格\n indexPrice: string; // 指数价格\n estimatedSettlePrice: string; // 预估结算价,仅在交割开始前最后一小时有意义\n lastFundingRate: string; // 最近更新的资金费率\n nextFundingTime: number; // 下次资金费时间\n interestRate: string; // 标的资产基础利率\n time: number; // 更新时间\n }[]\n>('GET', '/fapi/v1/premiumIndex');\n\nexport interface IAsterKline extends Array<string | number> {\n 0: number; // Open time\n 1: string; // Open\n 2: string; // High\n 3: string; // Low\n 4: string; // Close\n 5: string; // Volume\n 6: number; // Close time\n 7: string; // Quote asset volume\n 8: number; // Number of trades\n 9: string; // Taker buy base asset volume\n 10: string; // Taker buy quote asset volume\n 11: string; // Ignore\n}\n\n/**\n * 获取 K 线\n *\n * 参考 Binance 风格接口:/fapi/v1/klines\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md#k%E7%BA%BF%E6%95%B0%E6%8D%AE\n */\nexport const getFApiV1Klines = createFutureApi<\n {\n symbol: string;\n interval: string;\n startTime?: number;\n endTime?: number;\n limit?: number;\n },\n IAsterKline[]\n>('GET', '/fapi/v1/klines');\n\n/**\n * 获取现货 K 线\n *\n * 参考 Binance 风格接口:/api/v1/klines\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-spot-api_CN.md\n */\nexport const getApiV1Klines = createSpotApi<\n {\n symbol: string;\n interval: string;\n startTime?: number;\n endTime?: number;\n limit?: number;\n },\n IAsterKline[]\n>('GET', '/api/v1/klines');\n"]}
1
+ {"version":3,"file":"public-api.js","sourceRoot":"","sources":["../../src/api/public-api.ts"],"names":[],"mappings":"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","sourcesContent":["import { GlobalPrometheusRegistry, Terminal } from '@yuants/protocol';\nimport { scopeError, tokenBucket } from '@yuants/utils';\n\nimport './client';\n\nconst MetricsAsterApiCallCounter = GlobalPrometheusRegistry.counter(\n 'aster_api_call',\n 'Number of aster api call',\n);\nconst terminal = Terminal.fromNodeEnv();\n\nconst FutureBaseURL = 'https://fapi.asterdex.com';\nconst SpotBaseURL = 'https://sapi.asterdex.com';\n\nconst getKlinesRequestWeight = (limit: number | undefined): number => {\n const resolvedLimit = limit ?? 500;\n if (resolvedLimit < 100) return 1;\n if (resolvedLimit < 500) return 2;\n if (resolvedLimit <= 1000) return 5;\n return 10;\n};\n\nconst request = async <T>(\n method: string,\n baseUrl: string,\n endpoint: string,\n params: Record<string, unknown> = {},\n): Promise<T> => {\n const url = new URL(baseUrl);\n url.pathname = endpoint;\n for (const [key, value] of Object.entries(params)) {\n if (value === undefined) continue;\n url.searchParams.set(key, `${value}`);\n }\n\n console.info(url.toString());\n MetricsAsterApiCallCounter.labels({ path: url.pathname, terminal_id: terminal.terminal_id }).inc();\n const res = (await fetch(url.toString(), {\n method,\n }).then((response) => response.json())) as unknown;\n\n const maybeError = res as { code?: number };\n if (typeof maybeError.code === 'number' && maybeError.code !== 0) {\n throw JSON.stringify(res);\n }\n return res as T;\n};\n\n/**\n * 获取资金费率历史\n *\n * Weight: 1\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md#%E6%9F%A5%E8%AF%A2%E8%B5%84%E9%87%91%E8%B4%B9%E7%8E%87%E5%8E%86%E5%8F%B2\n */\nexport const getFApiV1FundingRate = (params: {\n symbol?: string;\n startTime?: number;\n endTime?: number;\n limit?: number;\n}): Promise<\n {\n symbol: string;\n fundingRate: string;\n fundingTime: number;\n }[]\n> => {\n const endpoint = '/fapi/v1/fundingRate';\n const url = new URL(FutureBaseURL);\n url.pathname = endpoint;\n const weight = 1;\n scopeError(\n 'ASTER_API_RATE_LIMIT',\n { method: 'GET', endpoint, host: url.host, path: url.pathname, bucketId: url.host, weight },\n () => tokenBucket(url.host).acquireSync(weight),\n );\n return request('GET', FutureBaseURL, endpoint, params);\n};\n\nexport interface IAsterRateLimit {\n rateLimitType?: string;\n interval?: string;\n intervalNum?: number;\n limit?: number;\n}\n\nexport interface IAsterExchangeInfo {\n symbols: {\n symbol: string;\n status: 'TRADING' | 'BREAK' | 'HALT';\n baseAsset: string;\n quoteAsset: string;\n pricePrecision: number;\n quantityPrecision: number;\n baseAssetPrecision: number;\n quotePrecision: number;\n filters: {\n filterType: string;\n [key: string]: unknown;\n }[];\n }[];\n rateLimits?: IAsterRateLimit[];\n}\n\n/**\n * 获取交易对信息\n *\n * Weight: 1\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md#%E4%BA%A4%E6%98%93%E5%AF%B9%E4%BF%A1%E6%81%AF\n */\nexport const getFApiV1ExchangeInfo = (params: Record<string, never>): Promise<IAsterExchangeInfo> => {\n const endpoint = '/fapi/v1/exchangeInfo';\n const url = new URL(FutureBaseURL);\n url.pathname = endpoint;\n const weight = 1;\n scopeError(\n 'ASTER_API_RATE_LIMIT',\n { method: 'GET', endpoint, host: url.host, path: url.pathname, bucketId: url.host, weight },\n () => tokenBucket(url.host).acquireSync(weight),\n );\n return request('GET', FutureBaseURL, endpoint, params);\n};\n\n/**\n * 获取现货交易对信息\n *\n * Weight: 1\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-spot-api_CN.md#L1080-L1145\n */\nexport const getApiV1ExchangeInfo = (params: Record<string, never>): Promise<IAsterExchangeInfo> => {\n const endpoint = '/api/v1/exchangeInfo';\n const url = new URL(SpotBaseURL);\n url.pathname = endpoint;\n const weight = 1;\n scopeError(\n 'ASTER_API_RATE_LIMIT',\n { method: 'GET', endpoint, host: url.host, path: url.pathname, bucketId: url.host, weight },\n () => tokenBucket(url.host).acquireSync(weight),\n );\n return request('GET', SpotBaseURL, endpoint, params);\n};\n\n/**\n * 获取未平仓合约数量\n *\n * 无 API 文档 (weird)\n * 参考 Binance 风格接口:/fapi/v1/openInterest\n *\n * Weight: 1\n * https://developers.binance.com/docs/zh-CN/derivatives/usds-margined-futures/market-data/rest-api/Open-Interest\n */\nexport const getFApiV1OpenInterest = (params: {\n symbol: string;\n}): Promise<{\n symbol: string;\n openInterest: string;\n time: number;\n}> => {\n const endpoint = '/fapi/v1/openInterest';\n const url = new URL(FutureBaseURL);\n url.pathname = endpoint;\n const weight = 1;\n scopeError(\n 'ASTER_API_RATE_LIMIT',\n { method: 'GET', endpoint, host: url.host, path: url.pathname, bucketId: url.host, weight },\n () => tokenBucket(url.host).acquireSync(weight),\n );\n return request('GET', FutureBaseURL, endpoint, params);\n};\n\n/**\n * 获取最新价格\n *\n * Weight: without symbol 2 (current implementation)\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md#%E6%9C%80%E6%96%B0%E4%BB%B7%E6%A0%BC\n */\nexport const getFApiV1TickerPrice = (\n params: Record<string, never>,\n): Promise<\n {\n symbol: string;\n price: string;\n time?: number;\n }[]\n> => {\n const endpoint = '/fapi/v1/ticker/price';\n const url = new URL(FutureBaseURL);\n url.pathname = endpoint;\n const weight = 2;\n scopeError(\n 'ASTER_API_RATE_LIMIT',\n { method: 'GET', endpoint, host: url.host, path: url.pathname, bucketId: url.host, weight },\n () => tokenBucket(url.host).acquireSync(weight),\n );\n return request('GET', FutureBaseURL, endpoint, params);\n};\n\n/**\n * 获取资金费率\n *\n * Weight: 1\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md\n */\nexport const getFApiV1PremiumIndex = (params: {\n symbol?: string;\n}): Promise<\n | {\n symbol: string;\n markPrice: string;\n indexPrice: string;\n estimatedSettlePrice: string;\n lastFundingRate: string;\n nextFundingTime: number;\n interestRate: string;\n time: number;\n }\n | {\n symbol: string;\n markPrice: string;\n indexPrice: string;\n estimatedSettlePrice: string;\n lastFundingRate: string;\n nextFundingTime: number;\n interestRate: string;\n time: number;\n }[]\n> => {\n const endpoint = '/fapi/v1/premiumIndex';\n const url = new URL(FutureBaseURL);\n url.pathname = endpoint;\n const weight = 1;\n scopeError(\n 'ASTER_API_RATE_LIMIT',\n { method: 'GET', endpoint, host: url.host, path: url.pathname, bucketId: url.host, weight },\n () => tokenBucket(url.host).acquireSync(weight),\n );\n return request('GET', FutureBaseURL, endpoint, params);\n};\n\nexport interface IAsterKline extends Array<string | number> {\n 0: number; // Open time\n 1: string; // Open\n 2: string; // High\n 3: string; // Low\n 4: string; // Close\n 5: string; // Volume\n 6: number; // Close time\n 7: string; // Quote asset volume\n 8: number; // Number of trades\n 9: string; // Taker buy base asset volume\n 10: string; // Taker buy quote asset volume\n 11: string; // Ignore\n}\n\n/**\n * 获取 K 线\n *\n * 参考 Binance 风格接口:/fapi/v1/klines\n *\n * Weight: by limit\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-futures-api_CN.md#k%E7%BA%BF%E6%95%B0%E6%8D%AE\n */\nexport const getFApiV1Klines = (params: {\n symbol: string;\n interval: string;\n startTime?: number;\n endTime?: number;\n limit?: number;\n}): Promise<IAsterKline[]> => {\n const endpoint = '/fapi/v1/klines';\n const url = new URL(FutureBaseURL);\n url.pathname = endpoint;\n const weight = getKlinesRequestWeight(params?.limit);\n scopeError(\n 'ASTER_API_RATE_LIMIT',\n {\n method: 'GET',\n endpoint,\n host: url.host,\n path: url.pathname,\n bucketId: url.host,\n weight,\n limit: params?.limit,\n },\n () => tokenBucket(url.host).acquireSync(weight),\n );\n return request('GET', FutureBaseURL, endpoint, params);\n};\n\n/**\n * 获取现货 K 线\n *\n * 参考 Binance 风格接口:/api/v1/klines\n *\n * Weight: not documented (temporary: follow futures limit table)\n *\n * https://github.com/asterdex/api-docs/blob/master/aster-finance-spot-api_CN.md\n */\nexport const getApiV1Klines = (params: {\n symbol: string;\n interval: string;\n startTime?: number;\n endTime?: number;\n limit?: number;\n}): Promise<IAsterKline[]> => {\n const endpoint = '/api/v1/klines';\n const url = new URL(SpotBaseURL);\n url.pathname = endpoint;\n const weight = getKlinesRequestWeight(params?.limit);\n scopeError(\n 'ASTER_API_RATE_LIMIT',\n {\n method: 'GET',\n endpoint,\n host: url.host,\n path: url.pathname,\n bucketId: url.host,\n weight,\n limit: params?.limit,\n },\n () => tokenBucket(url.host).acquireSync(weight),\n );\n return request('GET', SpotBaseURL, endpoint, params);\n};\n"]}
@@ -8,6 +8,7 @@ const utils_1 = require("@yuants/utils");
8
8
  const rxjs_1 = require("rxjs");
9
9
  const public_api_1 = require("../../api/public-api");
10
10
  const terminal = protocol_1.Terminal.fromNodeEnv();
11
+ const DISABLE_OPEN_INTEREST = process.env.DISABLE_OPEN_INTEREST === 'true';
11
12
  const DEFAULT_OPEN_INTEREST_REQUEST_INTERVAL_MS = 500;
12
13
  const OPEN_INTEREST_TTL = process.env.OPEN_INTEREST_TTL ? Number(process.env.OPEN_INTEREST_TTL) : 120000;
13
14
  const toIntervalMs = (interval, intervalNum) => {
@@ -98,7 +99,7 @@ const quoteFromFundingRate$ = fundingRate$.pipe((0, rxjs_1.mergeMap)((premiumDat
98
99
  interest_rate_long: premiumData.lastFundingRate ? `${-+premiumData.lastFundingRate}` : undefined,
99
100
  interest_rate_short: premiumData.lastFundingRate,
100
101
  })));
101
- const quote$ = (0, rxjs_1.merge)(quoteFromTicker$, quoteFromOpenInterest$, quoteFromFundingRate$).pipe((0, rxjs_1.groupBy)((quote) => quote.product_id), (0, rxjs_1.mergeMap)((group$) => group$.pipe((0, rxjs_1.scan)((acc, cur) => Object.assign(acc, cur, {
102
+ const quote$ = (0, rxjs_1.merge)(quoteFromTicker$, quoteFromFundingRate$, DISABLE_OPEN_INTEREST ? (0, rxjs_1.of)() : quoteFromOpenInterest$).pipe((0, rxjs_1.groupBy)((quote) => quote.product_id), (0, rxjs_1.mergeMap)((group$) => group$.pipe((0, rxjs_1.scan)((acc, cur) => Object.assign(acc, cur, {
102
103
  datasource_id: 'ASTER',
103
104
  product_id: group$.key,
104
105
  }), {}))), (0, rxjs_1.shareReplay)({ bufferSize: 1, refCount: true }));
@@ -1 +1 @@
1
- {"version":3,"file":"quote.js","sourceRoot":"","sources":["../../../src/services/markets/quote.ts"],"names":[],"mappings":"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","sourcesContent":["import { createCache } from '@yuants/cache';\nimport { setMetricsQuoteState, type IQuote } from '@yuants/data-quote';\nimport { Terminal } from '@yuants/protocol';\nimport { writeToSQL } from '@yuants/sql';\nimport { decodePath, encodePath } from '@yuants/utils';\nimport {\n catchError,\n combineLatest,\n concatMap,\n defer,\n exhaustMap,\n filter,\n from,\n groupBy,\n map,\n merge,\n mergeMap,\n of,\n repeat,\n retry,\n scan,\n shareReplay,\n startWith,\n timer,\n} from 'rxjs';\nimport {\n getFApiV1ExchangeInfo,\n getFApiV1OpenInterest,\n getFApiV1PremiumIndex,\n getFApiV1TickerPrice,\n IAsterRateLimit,\n} from '../../api/public-api';\n\nconst terminal = Terminal.fromNodeEnv();\nconst DEFAULT_OPEN_INTEREST_REQUEST_INTERVAL_MS = 500;\nconst OPEN_INTEREST_TTL = process.env.OPEN_INTEREST_TTL ? Number(process.env.OPEN_INTEREST_TTL) : 120_000;\n\nconst toIntervalMs = (interval?: string, intervalNum?: number) => {\n switch (interval) {\n case 'SECOND':\n return (intervalNum ?? 1) * 1_000;\n case 'MINUTE':\n return (intervalNum ?? 1) * 60_000;\n case 'HOUR':\n return (intervalNum ?? 1) * 3_600_000;\n case 'DAY':\n return (intervalNum ?? 1) * 86_400_000;\n default:\n return undefined;\n }\n};\n\nconst getRequestIntervalMs = (rateLimits: IAsterRateLimit[] | undefined, fallbackMs: number) => {\n const intervals: number[] = [];\n for (const item of rateLimits ?? []) {\n if (item.rateLimitType !== 'REQUEST_WEIGHT' && item.rateLimitType !== 'RAW_REQUESTS') continue;\n const duration = toIntervalMs(item.interval, item.intervalNum);\n const limit = item.limit;\n if (duration == null || limit == null || limit <= 0) continue;\n intervals.push(Math.ceil(duration / limit));\n }\n if (!intervals.length) return fallbackMs;\n return Math.max(fallbackMs, Math.max(...intervals));\n};\n\nconst openInterestCache = createCache<string>(\n async (symbol: string) => {\n try {\n const data = await getFApiV1OpenInterest({ symbol });\n return data.openInterest;\n } catch (error) {\n console.warn('getFApiV1OpenInterest failed', symbol, error);\n return undefined;\n }\n },\n { expire: OPEN_INTEREST_TTL },\n);\n\nconst requestInterval$ = defer(() => getFApiV1ExchangeInfo({})).pipe(\n map((info) => getRequestIntervalMs(info.rateLimits, DEFAULT_OPEN_INTEREST_REQUEST_INTERVAL_MS)),\n catchError((err) => {\n console.warn('getFApiV1ExchangeInfo failed when calculating request interval', err);\n return of(DEFAULT_OPEN_INTEREST_REQUEST_INTERVAL_MS);\n }),\n startWith(DEFAULT_OPEN_INTEREST_REQUEST_INTERVAL_MS),\n retry({ delay: 60_000 }),\n shareReplay({ bufferSize: 1, refCount: true }),\n);\n\nconst ticker$ = defer(() => getFApiV1TickerPrice({})).pipe(\n map((tickers) => (Array.isArray(tickers) ? tickers : [])),\n repeat({ delay: 1000 }),\n retry({ delay: 5000 }),\n shareReplay({ bufferSize: 1, refCount: true }),\n);\n\nconst quoteFromTicker$ = ticker$.pipe(\n mergeMap((tickers) => tickers || []),\n map(\n (ticker): Partial<IQuote> => ({\n datasource_id: 'ASTER',\n product_id: encodePath('ASTER', 'PERP', ticker.symbol),\n last_price: `${ticker.price}`,\n bid_price: `${ticker.price}`,\n ask_price: `${ticker.price}`,\n }),\n ),\n);\n\n// Extract unique symbols from ticker stream\nconst symbolList$ = ticker$.pipe(\n map((tickers) => tickers.map((t) => t.symbol)),\n shareReplay({ bufferSize: 1, refCount: true }),\n);\n\n// Create a controlled rotation stream for fetching open interest\n// This cycles through all symbols with proper delays, independent of ticker updates\nconst OPEN_INTEREST_CYCLE_DELAY = process.env.OPEN_INTEREST_CYCLE_DELAY\n ? Number(process.env.OPEN_INTEREST_CYCLE_DELAY)\n : 60_000; // 60 seconds between full cycles\n\nconst openInterestRotation$ = combineLatest([symbolList$, requestInterval$]).pipe(\n exhaustMap(([symbols, requestInterval]) =>\n defer(() => {\n console.info(\n `Starting open interest rotation for ${symbols.length} symbols with ${requestInterval}ms interval`,\n );\n return from(symbols).pipe(\n concatMap((symbol, index) =>\n (index > 0 ? timer(requestInterval) : of(0)).pipe(\n mergeMap(() => from(openInterestCache.query(symbol))),\n map((openInterest) => ({\n symbol,\n openInterest: openInterest ?? '0',\n timestamp: Date.now(),\n })),\n catchError((err) => {\n console.warn(`Failed to fetch open interest for ${symbol}:`, err);\n return of(undefined);\n }),\n ),\n ),\n );\n }),\n ),\n filter((x) => !!x),\n shareReplay({ bufferSize: 1000, refCount: true }), // Cache open interest for all symbols\n);\n\n// Convert open interest rotation data to quote format\nconst quoteFromOpenInterest$ = openInterestRotation$.pipe(\n map(\n (data): Partial<IQuote> => ({\n datasource_id: 'ASTER',\n product_id: encodePath('ASTER', 'PERP', data?.symbol),\n open_interest: data?.openInterest,\n }),\n ),\n);\n\n// Funding rate stream - fetches all symbols at once (more efficient than per-symbol)\nconst fundingRate$ = defer(() => getFApiV1PremiumIndex({})).pipe(\n map((data) => {\n // Handle both single object and array responses\n const premiumDataArray = Array.isArray(data) ? data : [data];\n return premiumDataArray;\n }),\n repeat({ delay: OPEN_INTEREST_CYCLE_DELAY }),\n retry({ delay: 5000 }),\n shareReplay({ bufferSize: 1, refCount: true }),\n);\n\n// Convert funding rate data to quote format\nconst quoteFromFundingRate$ = fundingRate$.pipe(\n mergeMap((premiumDataArray) => premiumDataArray),\n map(\n (premiumData): Partial<IQuote> => ({\n datasource_id: 'ASTER',\n product_id: encodePath('ASTER', 'PERP', premiumData.symbol),\n interest_rate_long: premiumData.lastFundingRate ? `${-+premiumData.lastFundingRate}` : undefined,\n interest_rate_short: premiumData.lastFundingRate,\n }),\n ),\n);\n\nconst quote$ = merge(quoteFromTicker$, quoteFromOpenInterest$, quoteFromFundingRate$).pipe(\n groupBy((quote) => quote.product_id),\n mergeMap((group$) =>\n group$.pipe(\n scan(\n (acc, cur) =>\n Object.assign(acc, cur, {\n datasource_id: 'ASTER',\n product_id: group$.key,\n }),\n {} as Partial<IQuote>,\n ),\n ),\n ),\n shareReplay({ bufferSize: 1, refCount: true }),\n);\n\nif (process.env.WRITE_QUOTE_TO_SQL === 'true') {\n quote$\n .pipe(\n setMetricsQuoteState(terminal.terminal_id),\n writeToSQL({\n terminal,\n tableName: 'quote',\n writeInterval: 1000,\n conflictKeys: ['datasource_id', 'product_id'],\n }),\n )\n .subscribe();\n\n terminal.channel.publishChannel('quote', { pattern: '^ASTER/' }, (channel_id) => {\n const [datasourceId, productId] = decodePath(channel_id);\n if (!datasourceId || !productId) {\n throw new Error(`Invalid channel_id: ${channel_id}`);\n }\n return quote$.pipe(filter((quote) => quote.product_id === productId));\n });\n}\n"]}
1
+ {"version":3,"file":"quote.js","sourceRoot":"","sources":["../../../src/services/markets/quote.ts"],"names":[],"mappings":"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","sourcesContent":["import { createCache } from '@yuants/cache';\nimport { setMetricsQuoteState, type IQuote } from '@yuants/data-quote';\nimport { Terminal } from '@yuants/protocol';\nimport { writeToSQL } from '@yuants/sql';\nimport { decodePath, encodePath } from '@yuants/utils';\nimport {\n catchError,\n combineLatest,\n concatMap,\n defer,\n exhaustMap,\n filter,\n from,\n groupBy,\n map,\n merge,\n mergeMap,\n of,\n repeat,\n retry,\n scan,\n shareReplay,\n startWith,\n timer,\n} from 'rxjs';\nimport {\n getFApiV1ExchangeInfo,\n getFApiV1OpenInterest,\n getFApiV1PremiumIndex,\n getFApiV1TickerPrice,\n IAsterRateLimit,\n} from '../../api/public-api';\n\nconst terminal = Terminal.fromNodeEnv();\nconst DISABLE_OPEN_INTEREST = process.env.DISABLE_OPEN_INTEREST === 'true';\nconst DEFAULT_OPEN_INTEREST_REQUEST_INTERVAL_MS = 500;\nconst OPEN_INTEREST_TTL = process.env.OPEN_INTEREST_TTL ? Number(process.env.OPEN_INTEREST_TTL) : 120_000;\n\nconst toIntervalMs = (interval?: string, intervalNum?: number) => {\n switch (interval) {\n case 'SECOND':\n return (intervalNum ?? 1) * 1_000;\n case 'MINUTE':\n return (intervalNum ?? 1) * 60_000;\n case 'HOUR':\n return (intervalNum ?? 1) * 3_600_000;\n case 'DAY':\n return (intervalNum ?? 1) * 86_400_000;\n default:\n return undefined;\n }\n};\n\nconst getRequestIntervalMs = (rateLimits: IAsterRateLimit[] | undefined, fallbackMs: number) => {\n const intervals: number[] = [];\n for (const item of rateLimits ?? []) {\n if (item.rateLimitType !== 'REQUEST_WEIGHT' && item.rateLimitType !== 'RAW_REQUESTS') continue;\n const duration = toIntervalMs(item.interval, item.intervalNum);\n const limit = item.limit;\n if (duration == null || limit == null || limit <= 0) continue;\n intervals.push(Math.ceil(duration / limit));\n }\n if (!intervals.length) return fallbackMs;\n return Math.max(fallbackMs, Math.max(...intervals));\n};\n\nconst openInterestCache = createCache<string>(\n async (symbol: string) => {\n try {\n const data = await getFApiV1OpenInterest({ symbol });\n return data.openInterest;\n } catch (error) {\n console.warn('getFApiV1OpenInterest failed', symbol, error);\n return undefined;\n }\n },\n { expire: OPEN_INTEREST_TTL },\n);\n\nconst requestInterval$ = defer(() => getFApiV1ExchangeInfo({})).pipe(\n map((info) => getRequestIntervalMs(info.rateLimits, DEFAULT_OPEN_INTEREST_REQUEST_INTERVAL_MS)),\n catchError((err) => {\n console.warn('getFApiV1ExchangeInfo failed when calculating request interval', err);\n return of(DEFAULT_OPEN_INTEREST_REQUEST_INTERVAL_MS);\n }),\n startWith(DEFAULT_OPEN_INTEREST_REQUEST_INTERVAL_MS),\n retry({ delay: 60_000 }),\n shareReplay({ bufferSize: 1, refCount: true }),\n);\n\nconst ticker$ = defer(() => getFApiV1TickerPrice({})).pipe(\n map((tickers) => (Array.isArray(tickers) ? tickers : [])),\n repeat({ delay: 1000 }),\n retry({ delay: 5000 }),\n shareReplay({ bufferSize: 1, refCount: true }),\n);\n\nconst quoteFromTicker$ = ticker$.pipe(\n mergeMap((tickers) => tickers || []),\n map(\n (ticker): Partial<IQuote> => ({\n datasource_id: 'ASTER',\n product_id: encodePath('ASTER', 'PERP', ticker.symbol),\n last_price: `${ticker.price}`,\n bid_price: `${ticker.price}`,\n ask_price: `${ticker.price}`,\n }),\n ),\n);\n\n// Extract unique symbols from ticker stream\nconst symbolList$ = ticker$.pipe(\n map((tickers) => tickers.map((t) => t.symbol)),\n shareReplay({ bufferSize: 1, refCount: true }),\n);\n\n// Create a controlled rotation stream for fetching open interest\n// This cycles through all symbols with proper delays, independent of ticker updates\nconst OPEN_INTEREST_CYCLE_DELAY = process.env.OPEN_INTEREST_CYCLE_DELAY\n ? Number(process.env.OPEN_INTEREST_CYCLE_DELAY)\n : 60_000; // 60 seconds between full cycles\n\nconst openInterestRotation$ = combineLatest([symbolList$, requestInterval$]).pipe(\n exhaustMap(([symbols, requestInterval]) =>\n defer(() => {\n console.info(\n `Starting open interest rotation for ${symbols.length} symbols with ${requestInterval}ms interval`,\n );\n return from(symbols).pipe(\n concatMap((symbol, index) =>\n (index > 0 ? timer(requestInterval) : of(0)).pipe(\n mergeMap(() => from(openInterestCache.query(symbol))),\n map((openInterest) => ({\n symbol,\n openInterest: openInterest ?? '0',\n timestamp: Date.now(),\n })),\n catchError((err) => {\n console.warn(`Failed to fetch open interest for ${symbol}:`, err);\n return of(undefined);\n }),\n ),\n ),\n );\n }),\n ),\n filter((x) => !!x),\n shareReplay({ bufferSize: 1000, refCount: true }), // Cache open interest for all symbols\n);\n\n// Convert open interest rotation data to quote format\nconst quoteFromOpenInterest$ = openInterestRotation$.pipe(\n map(\n (data): Partial<IQuote> => ({\n datasource_id: 'ASTER',\n product_id: encodePath('ASTER', 'PERP', data?.symbol),\n open_interest: data?.openInterest,\n }),\n ),\n);\n\n// Funding rate stream - fetches all symbols at once (more efficient than per-symbol)\nconst fundingRate$ = defer(() => getFApiV1PremiumIndex({})).pipe(\n map((data) => {\n // Handle both single object and array responses\n const premiumDataArray = Array.isArray(data) ? data : [data];\n return premiumDataArray;\n }),\n repeat({ delay: OPEN_INTEREST_CYCLE_DELAY }),\n retry({ delay: 5000 }),\n shareReplay({ bufferSize: 1, refCount: true }),\n);\n\n// Convert funding rate data to quote format\nconst quoteFromFundingRate$ = fundingRate$.pipe(\n mergeMap((premiumDataArray) => premiumDataArray),\n map(\n (premiumData): Partial<IQuote> => ({\n datasource_id: 'ASTER',\n product_id: encodePath('ASTER', 'PERP', premiumData.symbol),\n interest_rate_long: premiumData.lastFundingRate ? `${-+premiumData.lastFundingRate}` : undefined,\n interest_rate_short: premiumData.lastFundingRate,\n }),\n ),\n);\n\nconst quote$ = merge(\n quoteFromTicker$,\n quoteFromFundingRate$,\n DISABLE_OPEN_INTEREST ? of() : quoteFromOpenInterest$,\n).pipe(\n groupBy((quote) => quote.product_id),\n mergeMap((group$) =>\n group$.pipe(\n scan(\n (acc, cur) =>\n Object.assign(acc, cur, {\n datasource_id: 'ASTER',\n product_id: group$.key,\n }),\n {} as Partial<IQuote>,\n ),\n ),\n ),\n shareReplay({ bufferSize: 1, refCount: true }),\n);\n\nif (process.env.WRITE_QUOTE_TO_SQL === 'true') {\n quote$\n .pipe(\n setMetricsQuoteState(terminal.terminal_id),\n writeToSQL({\n terminal,\n tableName: 'quote',\n writeInterval: 1000,\n conflictKeys: ['datasource_id', 'product_id'],\n }),\n )\n .subscribe();\n\n terminal.channel.publishChannel('quote', { pattern: '^ASTER/' }, (channel_id) => {\n const [datasourceId, productId] = decodePath(channel_id);\n if (!datasourceId || !productId) {\n throw new Error(`Invalid channel_id: ${channel_id}`);\n }\n return quote$.pipe(filter((quote) => quote.product_id === productId));\n });\n}\n"]}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@yuants/vendor-aster",
3
- "version": "0.9.3",
3
+ "version": "0.9.5",
4
4
  "main": "lib/index.js",
5
5
  "files": [
6
6
  "dist",
@@ -1,14 +1,15 @@
1
1
  {
2
2
  "apps/vendor-aster/AGENTS.md": "dcd006d19a5c3b73081525d7c0afea68cd6d058b",
3
- "apps/vendor-aster/CHANGELOG.json": "96227ad644f7d5f1b94ec4b205cb24b25c5fd37d",
4
- "apps/vendor-aster/CHANGELOG.md": "07e41457dfd67cb7e811e60e25c6ed6746d113d9",
5
- "apps/vendor-aster/SESSION_NOTES.md": "d91f7a251d148fab1715b6da62395455edcb3b93",
3
+ "apps/vendor-aster/CHANGELOG.json": "2395528bd7952c91622d69742a8ac77ef971d6a3",
4
+ "apps/vendor-aster/CHANGELOG.md": "006e513c4e7ada83ef54fc72ddff395bca6fcdf0",
5
+ "apps/vendor-aster/SESSION_NOTES.md": "8190e547bbff4338deee5a18b0657eb0c2e400c6",
6
6
  "apps/vendor-aster/config/jest.config.json": "4bb17bde3ee911163a3edb36a6eb71491d80b1bd",
7
7
  "apps/vendor-aster/config/rig.json": "f6c7b5537dc77a3170ba9f008bae3b6c3ee11956",
8
8
  "apps/vendor-aster/config/typescript.json": "854907e8a821f2050f6533368db160c649c25348",
9
- "apps/vendor-aster/package.json": "dbf5d97cc13eb9698ef2bbfc28ff17e9a040f01e",
10
- "apps/vendor-aster/src/api/private-api.ts": "b3288706373f8917be480210f8f02074890d5b34",
11
- "apps/vendor-aster/src/api/public-api.ts": "a20ac4c4465ab3e75e2dc024adc12ecc19422375",
9
+ "apps/vendor-aster/package.json": "3813a59587db9a645418f064a0ed7863425aaa66",
10
+ "apps/vendor-aster/src/api/client.ts": "9464e0c848a0a7f1525d5d4fecdbcc5586f8b051",
11
+ "apps/vendor-aster/src/api/private-api.ts": "50b7c4ddd321b7abedfa58a0562b6fce1930c9d3",
12
+ "apps/vendor-aster/src/api/public-api.ts": "23a8ca6eac3f046d4132b5e2be4911a72f4712bf",
12
13
  "apps/vendor-aster/src/index.ts": "1decd1aabd3e77bc7a678427a42a9fa5fa84cf29",
13
14
  "apps/vendor-aster/src/services/accounts/profile.ts": "fc57e7d2c865790dd257c043c8dd5cf5c641b7fd",
14
15
  "apps/vendor-aster/src/services/accounts/spot.ts": "49d045e5daae100ce9919ebd84723506806060ea",
@@ -16,7 +17,7 @@
16
17
  "apps/vendor-aster/src/services/interest-rate-service.ts": "1b6061601c8c3712c0c18174d997a5589adef02c",
17
18
  "apps/vendor-aster/src/services/markets/interest_rate.ts": "8512bb506f3d66b16aceb9d153d1b3a4671de5ef",
18
19
  "apps/vendor-aster/src/services/markets/product.ts": "cae86f69c6f019747ebad07569ed2bc862a78ac6",
19
- "apps/vendor-aster/src/services/markets/quote.ts": "01274f7a820656ad480cb80a1cf526ac3805982b",
20
+ "apps/vendor-aster/src/services/markets/quote.ts": "919314f9e146c11678205467fc2a6ad4cdb180ac",
20
21
  "apps/vendor-aster/src/services/ohlc-service.ts": "6856f141561d53ec709c15b66e36744ae99323dc",
21
22
  "apps/vendor-aster/src/services/orders/cancelOrder.ts": "09a6d3b10a218ad226346dd68d0ff0207083a7f1",
22
23
  "apps/vendor-aster/src/services/orders/listOrders.ts": "579e83c45f6c4435ad3f5a2d3fe163a036bb9fd1",