@yuants/vendor-aster 0.5.7 → 0.6.0
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.
- package/dist/api/private-api.js +52 -0
- package/dist/api/private-api.js.map +1 -0
- package/dist/api/public-api.js +44 -0
- package/dist/api/public-api.js.map +1 -0
- package/dist/index.js +6 -8
- package/dist/index.js.map +1 -1
- package/dist/services/account-actions-with-credential.js +34 -0
- package/dist/services/account-actions-with-credential.js.map +1 -0
- package/dist/{account.js → services/accounts/perp.js} +5 -9
- package/dist/services/accounts/perp.js.map +1 -0
- package/dist/{account-spot.js → services/accounts/spot.js} +8 -9
- package/dist/services/accounts/spot.js.map +1 -0
- package/dist/services/legacy.js +54 -0
- package/dist/services/legacy.js.map +1 -0
- package/dist/{interest_rate.js → services/markets/interest_rate.js} +1 -1
- package/dist/services/markets/interest_rate.js.map +1 -0
- package/dist/{product.js → services/markets/product.js} +1 -1
- package/dist/services/markets/product.js.map +1 -0
- package/dist/{quote.js → services/markets/quote.js} +1 -1
- package/dist/services/markets/quote.js.map +1 -0
- package/dist/services/order-actions-with-credential.js +17 -0
- package/dist/services/order-actions-with-credential.js.map +1 -0
- package/dist/services/orders/cancelOrder.js +16 -0
- package/dist/services/orders/cancelOrder.js.map +1 -0
- package/dist/{pending-orders.js → services/orders/listOrders.js} +6 -10
- package/dist/services/orders/listOrders.js.map +1 -0
- package/dist/services/orders/submitOrder.js +84 -0
- package/dist/services/orders/submitOrder.js.map +1 -0
- package/dist/utils.js +1 -20
- package/dist/utils.js.map +1 -1
- package/lib/{api.d.ts → api/private-api.d.ts} +46 -46
- package/lib/api/private-api.d.ts.map +1 -0
- package/lib/api/private-api.js +55 -0
- package/lib/api/private-api.js.map +1 -0
- package/lib/api/public-api.d.ts +59 -0
- package/lib/api/public-api.d.ts.map +1 -0
- package/lib/api/public-api.js +47 -0
- package/lib/api/public-api.js.map +1 -0
- package/lib/index.d.ts +6 -8
- package/lib/index.d.ts.map +1 -1
- package/lib/index.js +6 -8
- package/lib/index.js.map +1 -1
- package/lib/services/account-actions-with-credential.d.ts +2 -0
- package/lib/services/account-actions-with-credential.d.ts.map +1 -0
- package/lib/services/account-actions-with-credential.js +36 -0
- package/lib/services/account-actions-with-credential.js.map +1 -0
- package/lib/services/accounts/perp.d.ts +4 -0
- package/lib/services/accounts/perp.d.ts.map +1 -0
- package/lib/{account.js → services/accounts/perp.js} +7 -10
- package/lib/services/accounts/perp.js.map +1 -0
- package/lib/services/accounts/spot.d.ts +4 -0
- package/lib/services/accounts/spot.d.ts.map +1 -0
- package/lib/{account-spot.js → services/accounts/spot.js} +10 -10
- package/lib/services/accounts/spot.js.map +1 -0
- package/lib/services/legacy.d.ts +2 -0
- package/lib/services/legacy.d.ts.map +1 -0
- package/lib/services/legacy.js +56 -0
- package/lib/services/legacy.js.map +1 -0
- package/lib/services/markets/interest_rate.d.ts.map +1 -0
- package/lib/{interest_rate.js → services/markets/interest_rate.js} +2 -2
- package/lib/services/markets/interest_rate.js.map +1 -0
- package/lib/services/markets/product.d.ts.map +1 -0
- package/lib/{product.js → services/markets/product.js} +2 -2
- package/lib/services/markets/product.js.map +1 -0
- package/lib/{quote.d.ts.map → services/markets/quote.d.ts.map} +1 -1
- package/lib/{quote.js → services/markets/quote.js} +3 -3
- package/lib/services/markets/quote.js.map +1 -0
- package/lib/services/order-actions-with-credential.d.ts +2 -0
- package/lib/services/order-actions-with-credential.d.ts.map +1 -0
- package/lib/services/order-actions-with-credential.js +19 -0
- package/lib/services/order-actions-with-credential.js.map +1 -0
- package/lib/services/orders/cancelOrder.d.ts +4 -0
- package/lib/services/orders/cancelOrder.d.ts.map +1 -0
- package/lib/services/orders/cancelOrder.js +20 -0
- package/lib/services/orders/cancelOrder.js.map +1 -0
- package/lib/services/orders/listOrders.d.ts +4 -0
- package/lib/services/orders/listOrders.d.ts.map +1 -0
- package/lib/{pending-orders.js → services/orders/listOrders.js} +8 -10
- package/lib/services/orders/listOrders.js.map +1 -0
- package/lib/services/orders/submitOrder.d.ts +4 -0
- package/lib/services/orders/submitOrder.d.ts.map +1 -0
- package/lib/services/orders/submitOrder.js +88 -0
- package/lib/services/orders/submitOrder.js.map +1 -0
- package/lib/utils.d.ts +1 -2
- package/lib/utils.d.ts.map +1 -1
- package/lib/utils.js +3 -23
- package/lib/utils.js.map +1 -1
- package/package.json +3 -4
- package/temp/package-deps.json +20 -18
- package/dist/account-spot.js.map +0 -1
- package/dist/account.js.map +0 -1
- package/dist/api.js +0 -55
- package/dist/api.js.map +0 -1
- package/dist/cli.js +0 -3
- package/dist/cli.js.map +0 -1
- package/dist/interest_rate.js.map +0 -1
- package/dist/order-spot.js +0 -38
- package/dist/order-spot.js.map +0 -1
- package/dist/order.js +0 -70
- package/dist/order.js.map +0 -1
- package/dist/pending-orders.js.map +0 -1
- package/dist/product.js.map +0 -1
- package/dist/quote.js.map +0 -1
- package/dist/sapi.js +0 -48
- package/dist/sapi.js.map +0 -1
- package/lib/account-spot.d.ts +0 -2
- package/lib/account-spot.d.ts.map +0 -1
- package/lib/account-spot.js.map +0 -1
- package/lib/account.d.ts +0 -2
- package/lib/account.d.ts.map +0 -1
- package/lib/account.js.map +0 -1
- package/lib/api.d.ts.map +0 -1
- package/lib/api.js +0 -58
- package/lib/api.js.map +0 -1
- package/lib/cli.d.ts +0 -3
- package/lib/cli.d.ts.map +0 -1
- package/lib/cli.js +0 -5
- package/lib/cli.js.map +0 -1
- package/lib/interest_rate.d.ts.map +0 -1
- package/lib/interest_rate.js.map +0 -1
- package/lib/order-spot.d.ts +0 -2
- package/lib/order-spot.d.ts.map +0 -1
- package/lib/order-spot.js +0 -40
- package/lib/order-spot.js.map +0 -1
- package/lib/order.d.ts +0 -2
- package/lib/order.d.ts.map +0 -1
- package/lib/order.js +0 -72
- package/lib/order.js.map +0 -1
- package/lib/pending-orders.d.ts +0 -2
- package/lib/pending-orders.d.ts.map +0 -1
- package/lib/pending-orders.js.map +0 -1
- package/lib/product.d.ts.map +0 -1
- package/lib/product.js.map +0 -1
- package/lib/quote.js.map +0 -1
- package/lib/sapi.d.ts +0 -37
- package/lib/sapi.d.ts.map +0 -1
- package/lib/sapi.js +0 -51
- package/lib/sapi.js.map +0 -1
- /package/lib/{interest_rate.d.ts → services/markets/interest_rate.d.ts} +0 -0
- /package/lib/{product.d.ts → services/markets/product.d.ts} +0 -0
- /package/lib/{quote.d.ts → services/markets/quote.d.ts} +0 -0
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
import { HmacSHA256 } from '@yuants/utils';
|
|
2
|
+
import { uint8ArrayToHex } from '../utils';
|
|
3
|
+
const request = async (credential, method, baseURL, endpoint, params = {}) => {
|
|
4
|
+
const url = new URL(baseURL);
|
|
5
|
+
url.pathname = endpoint;
|
|
6
|
+
for (const [key, value] of Object.entries(params)) {
|
|
7
|
+
if (value === undefined)
|
|
8
|
+
continue;
|
|
9
|
+
url.searchParams.set(key, `${value}`);
|
|
10
|
+
}
|
|
11
|
+
url.searchParams.set('timestamp', `${Date.now()}`);
|
|
12
|
+
const msg = url.search.slice(1); // 去掉开头的 '?'
|
|
13
|
+
const signature = uint8ArrayToHex(await HmacSHA256(new TextEncoder().encode(msg), new TextEncoder().encode(credential.secret_key)));
|
|
14
|
+
url.searchParams.set('signature', signature);
|
|
15
|
+
console.info(url.toString());
|
|
16
|
+
const res = await fetch(url.toString(), {
|
|
17
|
+
method,
|
|
18
|
+
headers: {
|
|
19
|
+
'X-MBX-APIKEY': credential.api_key,
|
|
20
|
+
},
|
|
21
|
+
}).then((response) => response.json());
|
|
22
|
+
if (res.code && res.code !== 0) {
|
|
23
|
+
throw JSON.stringify(res);
|
|
24
|
+
}
|
|
25
|
+
return res;
|
|
26
|
+
};
|
|
27
|
+
const createApi = (baseURL) => (method, endpoint) => (credential, params) => request(credential, method, baseURL, endpoint, params);
|
|
28
|
+
const createFutureApi = createApi('https://fapi.asterdex.com');
|
|
29
|
+
const createSpotApi = createApi('https://sapi.asterdex.com');
|
|
30
|
+
/**
|
|
31
|
+
* 获取账户信息
|
|
32
|
+
*
|
|
33
|
+
* 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
|
|
34
|
+
*/
|
|
35
|
+
export const getFApiV4Account = createFutureApi('GET', '/fapi/v4/account');
|
|
36
|
+
export const getFApiV2Balance = createFutureApi('GET', '/fapi/v2/balance');
|
|
37
|
+
export const postFApiV1Order = createFutureApi('POST', '/fapi/v1/order');
|
|
38
|
+
export const getFApiV1OpenOrders = createFutureApi('GET', '/fapi/v1/openOrders');
|
|
39
|
+
export const deleteFApiV1Order = createFutureApi('DELETE', '/fapi/v1/order');
|
|
40
|
+
/**
|
|
41
|
+
* 获取账户信息 (现货)
|
|
42
|
+
*
|
|
43
|
+
* 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
|
|
44
|
+
*/
|
|
45
|
+
export const getApiV1Account = createSpotApi('GET', '/api/v1/account');
|
|
46
|
+
/**
|
|
47
|
+
* 获取最新价格
|
|
48
|
+
* 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
|
|
49
|
+
*/
|
|
50
|
+
export const getApiV1TickerPrice = createSpotApi('GET', '/api/v1/ticker/price');
|
|
51
|
+
export const postApiV1Order = createSpotApi('POST', '/api/v1/order');
|
|
52
|
+
//# sourceMappingURL=private-api.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"private-api.js","sourceRoot":"","sources":["../../src/api/private-api.ts"],"names":[],"mappings":"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","sourcesContent":["import { HmacSHA256 } from '@yuants/utils';\nimport { uint8ArrayToHex } from '../utils';\n\nexport interface ICredential {\n address: string;\n api_key: string;\n secret_key: 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 = uint8ArrayToHex(\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 const res = await fetch(url.toString(), {\n method,\n headers: {\n 'X-MBX-APIKEY': credential.api_key,\n },\n }).then((response) => response.json());\n if (res.code && res.code !== 0) {\n throw JSON.stringify(res);\n }\n return res;\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\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\nexport const getFApiV1OpenOrders = createFutureApi<\n {\n symbol?: string;\n },\n {\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>('GET', '/fapi/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"]}
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
const BASE_URL = 'https://fapi.asterdex.com';
|
|
2
|
+
const request = async (method, endpoint, params = {}) => {
|
|
3
|
+
const url = new URL(BASE_URL);
|
|
4
|
+
url.pathname = endpoint;
|
|
5
|
+
for (const [key, value] of Object.entries(params)) {
|
|
6
|
+
if (value === undefined)
|
|
7
|
+
continue;
|
|
8
|
+
url.searchParams.set(key, `${value}`);
|
|
9
|
+
}
|
|
10
|
+
console.info(url.toString());
|
|
11
|
+
const res = await fetch(url.toString(), {
|
|
12
|
+
method,
|
|
13
|
+
}).then((response) => response.json());
|
|
14
|
+
if (res.code && res.code !== 0) {
|
|
15
|
+
throw JSON.stringify(res);
|
|
16
|
+
}
|
|
17
|
+
return res;
|
|
18
|
+
};
|
|
19
|
+
const createApi = (method, endpoint) => (params) => request(method, endpoint, params);
|
|
20
|
+
/**
|
|
21
|
+
* 获取资金费率历史
|
|
22
|
+
*
|
|
23
|
+
* 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
|
|
24
|
+
*/
|
|
25
|
+
export const getFApiV1FundingRate = createApi('GET', '/fapi/v1/fundingRate');
|
|
26
|
+
/**
|
|
27
|
+
* 获取交易对信息
|
|
28
|
+
*
|
|
29
|
+
* 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
|
|
30
|
+
*/
|
|
31
|
+
export const getFApiV1ExchangeInfo = createApi('GET', '/fapi/v1/exchangeInfo');
|
|
32
|
+
/**
|
|
33
|
+
* 获取未平仓合约数量
|
|
34
|
+
*
|
|
35
|
+
* 无 API 文档 (weird)
|
|
36
|
+
*/
|
|
37
|
+
export const getFApiV1OpenInterest = createApi('GET', '/fapi/v1/openInterest');
|
|
38
|
+
/**
|
|
39
|
+
* 获取最新价格
|
|
40
|
+
*
|
|
41
|
+
* 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
|
|
42
|
+
*/
|
|
43
|
+
export const getFApiV1TickerPrice = createApi('GET', '/fapi/v1/ticker/price');
|
|
44
|
+
//# sourceMappingURL=public-api.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"public-api.js","sourceRoot":"","sources":["../../src/api/public-api.ts"],"names":[],"mappings":"AAAA,MAAM,QAAQ,GAAG,2BAA2B,CAAC;AAE7C,MAAM,OAAO,GAAG,KAAK,EAAK,MAAc,EAAE,QAAgB,EAAE,SAAc,EAAE,EAAc,EAAE;IAC1F,MAAM,GAAG,GAAG,IAAI,GAAG,CAAC,QAAQ,CAAC,CAAC;IAC9B,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,MAAM,GAAG,GAAG,MAAM,KAAK,CAAC,GAAG,CAAC,QAAQ,EAAE,EAAE;QACtC,MAAM;KACP,CAAC,CAAC,IAAI,CAAC,CAAC,QAAQ,EAAE,EAAE,CAAC,QAAQ,CAAC,IAAI,EAAE,CAAC,CAAC;IACvC,IAAI,GAAG,CAAC,IAAI,IAAI,GAAG,CAAC,IAAI,KAAK,CAAC,EAAE;QAC9B,MAAM,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,CAAC;KAC3B;IACD,OAAO,GAAG,CAAC;AACb,CAAC,CAAC;AAEF,MAAM,SAAS,GACb,CAAa,MAAc,EAAE,QAAgB,EAAE,EAAE,CACjD,CAAC,MAAY,EAAE,EAAE,CACf,OAAO,CAAO,MAAM,EAAE,QAAQ,EAAE,MAAM,CAAC,CAAC;AAE5C;;;;GAIG;AACH,MAAM,CAAC,MAAM,oBAAoB,GAAG,SAAS,CAY3C,KAAK,EAAE,sBAAsB,CAAC,CAAC;AAEjC;;;;GAIG;AACH,MAAM,CAAC,MAAM,qBAAqB,GAAG,SAAS,CAkB5C,KAAK,EAAE,uBAAuB,CAAC,CAAC;AAElC;;;;GAIG;AACH,MAAM,CAAC,MAAM,qBAAqB,GAAG,SAAS,CAS5C,KAAK,EAAE,uBAAuB,CAAC,CAAC;AAElC;;;;GAIG;AACH,MAAM,CAAC,MAAM,oBAAoB,GAAG,SAAS,CAO3C,KAAK,EAAE,uBAAuB,CAAC,CAAC","sourcesContent":["const BASE_URL = 'https://fapi.asterdex.com';\n\nconst request = async <T>(method: string, endpoint: string, params: any = {}): Promise<T> => {\n const url = new URL(BASE_URL);\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 const res = await fetch(url.toString(), {\n method,\n }).then((response) => response.json());\n if (res.code && res.code !== 0) {\n throw JSON.stringify(res);\n }\n return res;\n};\n\nconst createApi =\n <TReq, TRes>(method: string, endpoint: string) =>\n (params: TReq) =>\n request<TRes>(method, endpoint, params);\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 = createApi<\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\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 = createApi<\n {},\n {\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]: any;\n }[];\n }[];\n }\n>('GET', '/fapi/v1/exchangeInfo');\n\n/**\n * 获取未平仓合约数量\n *\n * 无 API 文档 (weird)\n */\nexport const getFApiV1OpenInterest = createApi<\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 = createApi<\n {},\n {\n symbol: string;\n price: string;\n time?: number;\n }[]\n>('GET', '/fapi/v1/ticker/price');\n"]}
|
package/dist/index.js
CHANGED
|
@@ -1,9 +1,7 @@
|
|
|
1
|
-
import './
|
|
2
|
-
import './
|
|
3
|
-
import './
|
|
4
|
-
import './
|
|
5
|
-
import './
|
|
6
|
-
import './
|
|
7
|
-
import './pending-orders';
|
|
8
|
-
import './quote';
|
|
1
|
+
import './services/markets/interest_rate';
|
|
2
|
+
import './services/markets/product';
|
|
3
|
+
import './services/markets/quote';
|
|
4
|
+
import './services/account-actions-with-credential';
|
|
5
|
+
import './services/legacy';
|
|
6
|
+
import './services/order-actions-with-credential';
|
|
9
7
|
//# sourceMappingURL=index.js.map
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,kCAAkC,CAAC;AAC1C,OAAO,4BAA4B,CAAC;AACpC,OAAO,0BAA0B,CAAC;AAClC,OAAO,4CAA4C,CAAC;AACpD,OAAO,mBAAmB,CAAC;AAC3B,OAAO,0CAA0C,CAAC","sourcesContent":["import './services/markets/interest_rate';\nimport './services/markets/product';\nimport './services/markets/quote';\nimport './services/account-actions-with-credential';\nimport './services/legacy';\nimport './services/order-actions-with-credential';\n"]}
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
import { provideAccountActionsWithCredential } from '@yuants/data-account';
|
|
2
|
+
import { Terminal } from '@yuants/protocol';
|
|
3
|
+
import { getPerpAccountInfo } from './accounts/perp';
|
|
4
|
+
import { getSpotAccountInfo } from './accounts/spot';
|
|
5
|
+
provideAccountActionsWithCredential(Terminal.fromNodeEnv(), 'ASTER', {
|
|
6
|
+
type: 'object',
|
|
7
|
+
required: ['address', 'api_key', 'secret_key'],
|
|
8
|
+
properties: {
|
|
9
|
+
address: { type: 'string' },
|
|
10
|
+
api_key: { type: 'string' },
|
|
11
|
+
secret_key: { type: 'string' },
|
|
12
|
+
},
|
|
13
|
+
}, {
|
|
14
|
+
listAccounts: async (credential) => {
|
|
15
|
+
return [
|
|
16
|
+
{
|
|
17
|
+
account_id: `ASTER/${credential.address}/PERP`,
|
|
18
|
+
},
|
|
19
|
+
{
|
|
20
|
+
account_id: `ASTER/${credential.address}/SPOT`,
|
|
21
|
+
},
|
|
22
|
+
];
|
|
23
|
+
},
|
|
24
|
+
getAccountInfo: async (credential, account_id) => {
|
|
25
|
+
if (account_id.endsWith('/PERP')) {
|
|
26
|
+
return getPerpAccountInfo(credential, account_id);
|
|
27
|
+
}
|
|
28
|
+
if (account_id.endsWith('/SPOT')) {
|
|
29
|
+
return getSpotAccountInfo(credential, account_id);
|
|
30
|
+
}
|
|
31
|
+
throw new Error(`Unsupported account type for account_id: ${account_id}`);
|
|
32
|
+
},
|
|
33
|
+
});
|
|
34
|
+
//# sourceMappingURL=account-actions-with-credential.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"account-actions-with-credential.js","sourceRoot":"","sources":["../../src/services/account-actions-with-credential.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,mCAAmC,EAAE,MAAM,sBAAsB,CAAC;AAC3E,OAAO,EAAE,QAAQ,EAAE,MAAM,kBAAkB,CAAC;AAE5C,OAAO,EAAE,kBAAkB,EAAE,MAAM,iBAAiB,CAAC;AACrD,OAAO,EAAE,kBAAkB,EAAE,MAAM,iBAAiB,CAAC;AAErD,mCAAmC,CACjC,QAAQ,CAAC,WAAW,EAAE,EACtB,OAAO,EACP;IACE,IAAI,EAAE,QAAQ;IACd,QAAQ,EAAE,CAAC,SAAS,EAAE,SAAS,EAAE,YAAY,CAAC;IAC9C,UAAU,EAAE;QACV,OAAO,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE;QAC3B,OAAO,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE;QAC3B,UAAU,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE;KAC/B;CACF,EACD;IACE,YAAY,EAAE,KAAK,EAAE,UAAU,EAAE,EAAE;QACjC,OAAO;YACL;gBACE,UAAU,EAAE,SAAS,UAAU,CAAC,OAAO,OAAO;aAC/C;YACD;gBACE,UAAU,EAAE,SAAS,UAAU,CAAC,OAAO,OAAO;aAC/C;SACF,CAAC;IACJ,CAAC;IACD,cAAc,EAAE,KAAK,EAAE,UAAU,EAAE,UAAU,EAAE,EAAE;QAC/C,IAAI,UAAU,CAAC,QAAQ,CAAC,OAAO,CAAC,EAAE;YAChC,OAAO,kBAAkB,CAAC,UAAU,EAAE,UAAU,CAAC,CAAC;SACnD;QACD,IAAI,UAAU,CAAC,QAAQ,CAAC,OAAO,CAAC,EAAE;YAChC,OAAO,kBAAkB,CAAC,UAAU,EAAE,UAAU,CAAC,CAAC;SACnD;QACD,MAAM,IAAI,KAAK,CAAC,4CAA4C,UAAU,EAAE,CAAC,CAAC;IAC5E,CAAC;CACF,CACF,CAAC","sourcesContent":["import { provideAccountActionsWithCredential } from '@yuants/data-account';\nimport { Terminal } from '@yuants/protocol';\nimport { ICredential } from '../api/private-api';\nimport { getPerpAccountInfo } from './accounts/perp';\nimport { getSpotAccountInfo } from './accounts/spot';\n\nprovideAccountActionsWithCredential<ICredential>(\n Terminal.fromNodeEnv(),\n 'ASTER',\n {\n type: 'object',\n required: ['address', 'api_key', 'secret_key'],\n properties: {\n address: { type: 'string' },\n api_key: { type: 'string' },\n secret_key: { type: 'string' },\n },\n },\n {\n listAccounts: async (credential) => {\n return [\n {\n account_id: `ASTER/${credential.address}/PERP`,\n },\n {\n account_id: `ASTER/${credential.address}/SPOT`,\n },\n ];\n },\n getAccountInfo: async (credential, account_id) => {\n if (account_id.endsWith('/PERP')) {\n return getPerpAccountInfo(credential, account_id);\n }\n if (account_id.endsWith('/SPOT')) {\n return getSpotAccountInfo(credential, account_id);\n }\n throw new Error(`Unsupported account type for account_id: ${account_id}`);\n },\n },\n);\n"]}
|
|
@@ -1,11 +1,7 @@
|
|
|
1
|
-
import { provideAccountInfoService } from '@yuants/data-account';
|
|
2
|
-
import { Terminal } from '@yuants/protocol';
|
|
3
1
|
import { encodePath } from '@yuants/utils';
|
|
4
|
-
import { getFApiV4Account } from '
|
|
5
|
-
const
|
|
6
|
-
|
|
7
|
-
provideAccountInfoService(Terminal.fromNodeEnv(), ACCOUNT_ID, async () => {
|
|
8
|
-
const [a] = await Promise.all([getFApiV4Account({})]);
|
|
2
|
+
import { getFApiV4Account } from '../../api/private-api';
|
|
3
|
+
export const getPerpAccountInfo = async (credential) => {
|
|
4
|
+
const [a] = await Promise.all([getFApiV4Account(credential, {})]);
|
|
9
5
|
const equity = +a.totalWalletBalance + +a.totalUnrealizedProfit;
|
|
10
6
|
const free = +a.availableBalance;
|
|
11
7
|
const positions = a.positions
|
|
@@ -30,5 +26,5 @@ provideAccountInfoService(Terminal.fromNodeEnv(), ACCOUNT_ID, async () => {
|
|
|
30
26
|
},
|
|
31
27
|
positions,
|
|
32
28
|
};
|
|
33
|
-
}
|
|
34
|
-
//# sourceMappingURL=
|
|
29
|
+
};
|
|
30
|
+
//# sourceMappingURL=perp.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"perp.js","sourceRoot":"","sources":["../../../src/services/accounts/perp.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,UAAU,EAAE,MAAM,eAAe,CAAC;AAC3C,OAAO,EAAE,gBAAgB,EAAe,MAAM,uBAAuB,CAAC;AAEtE,MAAM,CAAC,MAAM,kBAAkB,GAAgD,KAAK,EAAE,UAAU,EAAE,EAAE;IAClG,MAAM,CAAC,CAAC,CAAC,GAAG,MAAM,OAAO,CAAC,GAAG,CAAC,CAAC,gBAAgB,CAAC,UAAU,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC;IAElE,MAAM,MAAM,GAAG,CAAC,CAAC,CAAC,kBAAkB,GAAG,CAAC,CAAC,CAAC,qBAAqB,CAAC;IAChE,MAAM,IAAI,GAAG,CAAC,CAAC,CAAC,gBAAgB,CAAC;IAEjC,MAAM,SAAS,GAAG,CAAC,CAAC,SAAS;SAC1B,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,WAAW,KAAK,CAAC,CAAC;SACnC,GAAG,CACF,CAAC,CAAC,EAAa,EAAE,CAAC,CAAC;QACjB,WAAW,EAAE,CAAC,CAAC,MAAM;QACrB,UAAU,EAAE,UAAU,CAAC,WAAW,EAAE,CAAC,CAAC,MAAM,CAAC;QAC7C,aAAa,EAAE,OAAO;QACtB,SAAS,EAAE,CAAC,CAAC,YAAY,KAAK,MAAM,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,WAAW,GAAG,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,YAAY;QAC/F,MAAM,EAAE,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,WAAW,CAAC;QAChC,WAAW,EAAE,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,WAAW,CAAC;QACrC,cAAc,EAAE,CAAC,CAAC,CAAC,UAAU;QAC7B,cAAc,EAAE,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,QAAQ,GAAG,CAAC,CAAC,CAAC,WAAW,CAAC;QACtD,eAAe,EAAE,CAAC,CAAC,CAAC,gBAAgB;QACpC,SAAS,EAAE,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,QAAQ,CAAC;KACjC,CAAC,CACH,CAAC;IACJ,OAAO;QACL,KAAK,EAAE;YACL,QAAQ,EAAE,KAAK;YACf,MAAM;YACN,IAAI;SACL;QACD,SAAS;KACV,CAAC;AACJ,CAAC,CAAC","sourcesContent":["import { IActionHandlerOfGetAccountInfo, IPosition } from '@yuants/data-account';\nimport { encodePath } from '@yuants/utils';\nimport { getFApiV4Account, ICredential } from '../../api/private-api';\n\nexport const getPerpAccountInfo: IActionHandlerOfGetAccountInfo<ICredential> = async (credential) => {\n const [a] = await Promise.all([getFApiV4Account(credential, {})]);\n\n const equity = +a.totalWalletBalance + +a.totalUnrealizedProfit;\n const free = +a.availableBalance;\n\n const positions = a.positions\n .filter((p) => +p.positionAmt !== 0)\n .map(\n (p): IPosition => ({\n position_id: p.symbol,\n product_id: encodePath('PERPETUAL', p.symbol),\n datasource_id: 'ASTER',\n direction: p.positionSide === 'BOTH' ? (+p.positionAmt > 0 ? 'LONG' : 'SHORT') : p.positionSide,\n volume: Math.abs(+p.positionAmt),\n free_volume: Math.abs(+p.positionAmt),\n position_price: +p.entryPrice,\n closable_price: Math.abs(+p.notional / +p.positionAmt),\n floating_profit: +p.unrealizedProfit,\n valuation: Math.abs(+p.notional),\n }),\n );\n return {\n money: {\n currency: 'USD',\n equity,\n free,\n },\n positions,\n };\n};\n"]}
|
|
@@ -1,10 +1,9 @@
|
|
|
1
|
-
import {
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
const [x, prices] = await Promise.all([getApiV1Account({}), getApiV1TickerPrice({})]);
|
|
1
|
+
import { getApiV1Account, getApiV1TickerPrice } from '../../api/private-api';
|
|
2
|
+
export const getSpotAccountInfo = async (credential, account_id) => {
|
|
3
|
+
const [x, prices] = await Promise.all([
|
|
4
|
+
getApiV1Account(credential, {}),
|
|
5
|
+
getApiV1TickerPrice(credential, {}),
|
|
6
|
+
]);
|
|
8
7
|
const positions = x.balances.map((b) => {
|
|
9
8
|
var _a, _b;
|
|
10
9
|
const thePrice = b.asset === 'USDT' ? 1 : (_b = (_a = prices.find((p) => p.symbol === b.asset + 'USDT')) === null || _a === void 0 ? void 0 : _a.price) !== null && _b !== void 0 ? _b : 0;
|
|
@@ -37,5 +36,5 @@ provideAccountInfoService(Terminal.fromNodeEnv(), SPOT_ACCOUNT_ID, async () => {
|
|
|
37
36
|
},
|
|
38
37
|
positions,
|
|
39
38
|
};
|
|
40
|
-
}
|
|
41
|
-
//# sourceMappingURL=
|
|
39
|
+
};
|
|
40
|
+
//# sourceMappingURL=spot.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"spot.js","sourceRoot":"","sources":["../../../src/services/accounts/spot.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,eAAe,EAAE,mBAAmB,EAAe,MAAM,uBAAuB,CAAC;AAE1F,MAAM,CAAC,MAAM,kBAAkB,GAAgD,KAAK,EAClF,UAAU,EACV,UAAU,EACV,EAAE;IACF,MAAM,CAAC,CAAC,EAAE,MAAM,CAAC,GAAG,MAAM,OAAO,CAAC,GAAG,CAAC;QACpC,eAAe,CAAC,UAAU,EAAE,EAAE,CAAC;QAC/B,mBAAmB,CAAC,UAAU,EAAE,EAAE,CAAC;KACpC,CAAC,CAAC;IAEH,MAAM,SAAS,GAAG,CAAC,CAAC,QAAQ,CAAC,GAAG,CAAC,CAAC,CAAC,EAAa,EAAE;;QAChD,MAAM,QAAQ,GAAG,CAAC,CAAC,KAAK,KAAK,MAAM,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,MAAA,MAAA,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,MAAM,KAAK,CAAC,CAAC,KAAK,GAAG,MAAM,CAAC,0CAAE,KAAK,mCAAI,CAAC,CAAC;QAExG,MAAM,MAAM,GAAG,CAAC,CAAC,CAAC,IAAI,GAAG,CAAC,CAAC,CAAC,MAAM,CAAC;QAEnC,MAAM,cAAc,GAAG,CAAC,QAAQ,CAAC;QACjC,MAAM,cAAc,GAAG,CAAC,QAAQ,CAAC;QACjC,MAAM,SAAS,GAAG,MAAM,GAAG,cAAc,CAAC;QAC1C,MAAM,eAAe,GAAG,CAAC,CAAC;QAE1B,OAAO;YACL,WAAW,EAAE,CAAC,CAAC,KAAK;YACpB,aAAa,EAAE,OAAO;YACtB,UAAU,EAAE,CAAC,CAAC,KAAK;YACnB,SAAS,EAAE,MAAM;YACjB,MAAM;YACN,WAAW,EAAE,CAAC,CAAC,CAAC,IAAI;YACpB,cAAc;YACd,cAAc;YACd,eAAe;YACf,SAAS;SACV,CAAC;IACJ,CAAC,CAAC,CAAC;IAEH,MAAM,SAAS,GAAG,CAAC,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,KAAK,KAAK,MAAM,CAAC,CAAC;IAC7D,MAAM,MAAM,GAAG,SAAS,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,GAAG,CAAC,CAAC,SAAS,EAAE,CAAC,CAAC,CAAC;IAC9D,MAAM,IAAI,GAAG,SAAS,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC;IAE7C,OAAO;QACL,KAAK,EAAE;YACL,QAAQ,EAAE,MAAM;YAChB,MAAM;YACN,IAAI;SACL;QACD,SAAS;KACV,CAAC;AACJ,CAAC,CAAC","sourcesContent":["import { IActionHandlerOfGetAccountInfo, IPosition } from '@yuants/data-account';\nimport { getApiV1Account, getApiV1TickerPrice, ICredential } from '../../api/private-api';\n\nexport const getSpotAccountInfo: IActionHandlerOfGetAccountInfo<ICredential> = async (\n credential,\n account_id,\n) => {\n const [x, prices] = await Promise.all([\n getApiV1Account(credential, {}),\n getApiV1TickerPrice(credential, {}),\n ]);\n\n const positions = x.balances.map((b): IPosition => {\n const thePrice = b.asset === 'USDT' ? 1 : prices.find((p) => p.symbol === b.asset + 'USDT')?.price ?? 0;\n\n const volume = +b.free + +b.locked;\n\n const position_price = +thePrice;\n const closable_price = +thePrice;\n const valuation = volume * closable_price;\n const floating_profit = 0;\n\n return {\n position_id: b.asset,\n datasource_id: 'ASTER',\n product_id: b.asset,\n direction: 'LONG',\n volume,\n free_volume: +b.free,\n position_price,\n closable_price,\n floating_profit,\n valuation,\n };\n });\n\n const usdtAsset = x.balances.find((b) => b.asset === 'USDT');\n const equity = positions.reduce((a, b) => a + b.valuation, 0);\n const free = usdtAsset ? +usdtAsset.free : 0;\n\n return {\n money: {\n currency: 'USDT',\n equity,\n free,\n },\n positions,\n };\n};\n"]}
|
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
import { provideAccountInfoService } from '@yuants/data-account';
|
|
2
|
+
import { providePendingOrdersService } from '@yuants/data-order';
|
|
3
|
+
import { Terminal } from '@yuants/protocol';
|
|
4
|
+
import { getPerpAccountInfo } from '../services/accounts/perp';
|
|
5
|
+
import { getSpotAccountInfo } from '../services/accounts/spot';
|
|
6
|
+
import { handleCancelOrder } from '../services/orders/cancelOrder';
|
|
7
|
+
import { handleSubmitOrder } from '../services/orders/submitOrder';
|
|
8
|
+
import { listOrders } from './orders/listOrders';
|
|
9
|
+
const getDefaultCredential = () => {
|
|
10
|
+
return {
|
|
11
|
+
address: process.env.API_ADDRESS || '',
|
|
12
|
+
api_key: process.env.API_KEY || '',
|
|
13
|
+
secret_key: process.env.SECRET_KEY || '',
|
|
14
|
+
};
|
|
15
|
+
};
|
|
16
|
+
const ADDRESS = process.env.ADDRESS;
|
|
17
|
+
const credential = getDefaultCredential();
|
|
18
|
+
const terminal = Terminal.fromNodeEnv();
|
|
19
|
+
const SPOT_ACCOUNT_ID = `ASTER/${ADDRESS}/SPOT`;
|
|
20
|
+
const PERP_ACCOUNT_ID = `ASTER/${ADDRESS}`;
|
|
21
|
+
provideAccountInfoService(Terminal.fromNodeEnv(), SPOT_ACCOUNT_ID, async () => getSpotAccountInfo(credential, SPOT_ACCOUNT_ID), { auto_refresh_interval: 1000 });
|
|
22
|
+
provideAccountInfoService(Terminal.fromNodeEnv(), PERP_ACCOUNT_ID, async () => getPerpAccountInfo(credential, PERP_ACCOUNT_ID), { auto_refresh_interval: 1000 });
|
|
23
|
+
providePendingOrdersService(terminal, PERP_ACCOUNT_ID, async () => listOrders(credential, PERP_ACCOUNT_ID), {
|
|
24
|
+
auto_refresh_interval: 2000,
|
|
25
|
+
});
|
|
26
|
+
Terminal.fromNodeEnv().server.provideService('SubmitOrder', { required: ['account_id'], properties: { account_id: { type: 'string', const: SPOT_ACCOUNT_ID } } }, async (msg) => {
|
|
27
|
+
const order = msg.req;
|
|
28
|
+
const data = await handleSubmitOrder(credential, order);
|
|
29
|
+
return { res: { code: 0, message: 'OK', data } };
|
|
30
|
+
});
|
|
31
|
+
terminal.server.provideService('SubmitOrder', { required: ['account_id'], properties: { account_id: { type: 'string', const: PERP_ACCOUNT_ID } } }, async (msg) => {
|
|
32
|
+
const order = msg.req;
|
|
33
|
+
const data = await handleSubmitOrder(credential, order);
|
|
34
|
+
return {
|
|
35
|
+
res: {
|
|
36
|
+
code: 0,
|
|
37
|
+
message: 'OK',
|
|
38
|
+
data,
|
|
39
|
+
},
|
|
40
|
+
};
|
|
41
|
+
});
|
|
42
|
+
terminal.server.provideService('CancelOrder', {
|
|
43
|
+
required: ['account_id', 'order_id', 'product_id'],
|
|
44
|
+
properties: {
|
|
45
|
+
account_id: { type: 'string', const: PERP_ACCOUNT_ID },
|
|
46
|
+
order_id: { type: ['string', 'number'] },
|
|
47
|
+
product_id: { type: 'string' },
|
|
48
|
+
},
|
|
49
|
+
}, async (msg) => {
|
|
50
|
+
const order = msg.req;
|
|
51
|
+
await handleCancelOrder(credential, order);
|
|
52
|
+
return { res: { code: 0, message: 'OK' } };
|
|
53
|
+
});
|
|
54
|
+
//# sourceMappingURL=legacy.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"legacy.js","sourceRoot":"","sources":["../../src/services/legacy.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,yBAAyB,EAAE,MAAM,sBAAsB,CAAC;AACjE,OAAO,EAAU,2BAA2B,EAAE,MAAM,oBAAoB,CAAC;AACzE,OAAO,EAAE,QAAQ,EAAE,MAAM,kBAAkB,CAAC;AAE5C,OAAO,EAAE,kBAAkB,EAAE,MAAM,2BAA2B,CAAC;AAC/D,OAAO,EAAE,kBAAkB,EAAE,MAAM,2BAA2B,CAAC;AAC/D,OAAO,EAAE,iBAAiB,EAAE,MAAM,gCAAgC,CAAC;AACnE,OAAO,EAAE,iBAAiB,EAAE,MAAM,gCAAgC,CAAC;AACnE,OAAO,EAAE,UAAU,EAAE,MAAM,qBAAqB,CAAC;AAEjD,MAAM,oBAAoB,GAAG,GAAgB,EAAE;IAC7C,OAAO;QACL,OAAO,EAAE,OAAO,CAAC,GAAG,CAAC,WAAW,IAAI,EAAE;QACtC,OAAO,EAAE,OAAO,CAAC,GAAG,CAAC,OAAO,IAAI,EAAE;QAClC,UAAU,EAAE,OAAO,CAAC,GAAG,CAAC,UAAU,IAAI,EAAE;KACzC,CAAC;AACJ,CAAC,CAAC;AAEF,MAAM,OAAO,GAAG,OAAO,CAAC,GAAG,CAAC,OAAQ,CAAC;AACrC,MAAM,UAAU,GAAG,oBAAoB,EAAE,CAAC;AAC1C,MAAM,QAAQ,GAAG,QAAQ,CAAC,WAAW,EAAE,CAAC;AAExC,MAAM,eAAe,GAAG,SAAS,OAAO,OAAO,CAAC;AAChD,MAAM,eAAe,GAAG,SAAS,OAAO,EAAE,CAAC;AAE3C,yBAAyB,CACvB,QAAQ,CAAC,WAAW,EAAE,EACtB,eAAe,EACf,KAAK,IAAI,EAAE,CAAC,kBAAkB,CAAC,UAAU,EAAE,eAAe,CAAC,EAC3D,EAAE,qBAAqB,EAAE,IAAI,EAAE,CAChC,CAAC;AAEF,yBAAyB,CACvB,QAAQ,CAAC,WAAW,EAAE,EACtB,eAAe,EACf,KAAK,IAAI,EAAE,CAAC,kBAAkB,CAAC,UAAU,EAAE,eAAe,CAAC,EAC3D,EAAE,qBAAqB,EAAE,IAAI,EAAE,CAChC,CAAC;AAEF,2BAA2B,CAAC,QAAQ,EAAE,eAAe,EAAE,KAAK,IAAI,EAAE,CAAC,UAAU,CAAC,UAAU,EAAE,eAAe,CAAC,EAAE;IAC1G,qBAAqB,EAAE,IAAI;CAC5B,CAAC,CAAC;AAEH,QAAQ,CAAC,WAAW,EAAE,CAAC,MAAM,CAAC,cAAc,CAC1C,aAAa,EACb,EAAE,QAAQ,EAAE,CAAC,YAAY,CAAC,EAAE,UAAU,EAAE,EAAE,UAAU,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,KAAK,EAAE,eAAe,EAAE,EAAE,EAAE,EACpG,KAAK,EAAE,GAAG,EAAE,EAAE;IACZ,MAAM,KAAK,GAAG,GAAG,CAAC,GAAG,CAAC;IAEtB,MAAM,IAAI,GAAG,MAAM,iBAAiB,CAAC,UAAU,EAAE,KAAK,CAAC,CAAC;IAExD,OAAO,EAAE,GAAG,EAAE,EAAE,IAAI,EAAE,CAAC,EAAE,OAAO,EAAE,IAAI,EAAE,IAAI,EAAE,EAAE,CAAC;AACnD,CAAC,CACF,CAAC;AAEF,QAAQ,CAAC,MAAM,CAAC,cAAc,CAC5B,aAAa,EACb,EAAE,QAAQ,EAAE,CAAC,YAAY,CAAC,EAAE,UAAU,EAAE,EAAE,UAAU,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,KAAK,EAAE,eAAe,EAAE,EAAE,EAAE,EACpG,KAAK,EAAE,GAAG,EAAE,EAAE;IACZ,MAAM,KAAK,GAAG,GAAG,CAAC,GAAG,CAAC;IACtB,MAAM,IAAI,GAAG,MAAM,iBAAiB,CAAC,UAAU,EAAE,KAAK,CAAC,CAAC;IAExD,OAAO;QACL,GAAG,EAAE;YACH,IAAI,EAAE,CAAC;YACP,OAAO,EAAE,IAAI;YACb,IAAI;SACL;KACF,CAAC;AACJ,CAAC,CACF,CAAC;AAEF,QAAQ,CAAC,MAAM,CAAC,cAAc,CAC5B,aAAa,EACb;IACE,QAAQ,EAAE,CAAC,YAAY,EAAE,UAAU,EAAE,YAAY,CAAC;IAClD,UAAU,EAAE;QACV,UAAU,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,KAAK,EAAE,eAAe,EAAE;QACtD,QAAQ,EAAE,EAAE,IAAI,EAAE,CAAC,QAAQ,EAAE,QAAQ,CAAC,EAAE;QACxC,UAAU,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE;KAC/B;CACF,EACD,KAAK,EAAE,GAAG,EAAE,EAAE;IACZ,MAAM,KAAK,GAAG,GAAG,CAAC,GAAG,CAAC;IAEtB,MAAM,iBAAiB,CAAC,UAAU,EAAE,KAAK,CAAC,CAAC;IAE3C,OAAO,EAAE,GAAG,EAAE,EAAE,IAAI,EAAE,CAAC,EAAE,OAAO,EAAE,IAAI,EAAE,EAAE,CAAC;AAC7C,CAAC,CACF,CAAC","sourcesContent":["import { provideAccountInfoService } from '@yuants/data-account';\nimport { IOrder, providePendingOrdersService } from '@yuants/data-order';\nimport { Terminal } from '@yuants/protocol';\nimport { ICredential } from '../api/private-api';\nimport { getPerpAccountInfo } from '../services/accounts/perp';\nimport { getSpotAccountInfo } from '../services/accounts/spot';\nimport { handleCancelOrder } from '../services/orders/cancelOrder';\nimport { handleSubmitOrder } from '../services/orders/submitOrder';\nimport { listOrders } from './orders/listOrders';\n\nconst getDefaultCredential = (): ICredential => {\n return {\n address: process.env.API_ADDRESS || '',\n api_key: process.env.API_KEY || '',\n secret_key: process.env.SECRET_KEY || '',\n };\n};\n\nconst ADDRESS = process.env.ADDRESS!;\nconst credential = getDefaultCredential();\nconst terminal = Terminal.fromNodeEnv();\n\nconst SPOT_ACCOUNT_ID = `ASTER/${ADDRESS}/SPOT`;\nconst PERP_ACCOUNT_ID = `ASTER/${ADDRESS}`;\n\nprovideAccountInfoService(\n Terminal.fromNodeEnv(),\n SPOT_ACCOUNT_ID,\n async () => getSpotAccountInfo(credential, SPOT_ACCOUNT_ID),\n { auto_refresh_interval: 1000 },\n);\n\nprovideAccountInfoService(\n Terminal.fromNodeEnv(),\n PERP_ACCOUNT_ID,\n async () => getPerpAccountInfo(credential, PERP_ACCOUNT_ID),\n { auto_refresh_interval: 1000 },\n);\n\nprovidePendingOrdersService(terminal, PERP_ACCOUNT_ID, async () => listOrders(credential, PERP_ACCOUNT_ID), {\n auto_refresh_interval: 2000,\n});\n\nTerminal.fromNodeEnv().server.provideService<IOrder, { order_id: string }>(\n 'SubmitOrder',\n { required: ['account_id'], properties: { account_id: { type: 'string', const: SPOT_ACCOUNT_ID } } },\n async (msg) => {\n const order = msg.req;\n\n const data = await handleSubmitOrder(credential, order);\n\n return { res: { code: 0, message: 'OK', data } };\n },\n);\n\nterminal.server.provideService<IOrder, { order_id?: string }>(\n 'SubmitOrder',\n { required: ['account_id'], properties: { account_id: { type: 'string', const: PERP_ACCOUNT_ID } } },\n async (msg) => {\n const order = msg.req;\n const data = await handleSubmitOrder(credential, order);\n\n return {\n res: {\n code: 0,\n message: 'OK',\n data,\n },\n };\n },\n);\n\nterminal.server.provideService<IOrder>(\n 'CancelOrder',\n {\n required: ['account_id', 'order_id', 'product_id'],\n properties: {\n account_id: { type: 'string', const: PERP_ACCOUNT_ID },\n order_id: { type: ['string', 'number'] },\n product_id: { type: 'string' },\n },\n },\n async (msg) => {\n const order = msg.req;\n\n await handleCancelOrder(credential, order);\n\n return { res: { code: 0, message: 'OK' } };\n },\n);\n"]}
|
|
@@ -15,7 +15,7 @@ import { Terminal } from '@yuants/protocol';
|
|
|
15
15
|
import { createSQLWriter } from '@yuants/sql';
|
|
16
16
|
import { decodePath, encodePath, formatTime } from '@yuants/utils';
|
|
17
17
|
import { firstValueFrom, map, mergeAll, timer } from 'rxjs';
|
|
18
|
-
import { getFApiV1FundingRate } from '
|
|
18
|
+
import { getFApiV1FundingRate } from '../../api/public-api';
|
|
19
19
|
import { productService } from './product';
|
|
20
20
|
const terminal = Terminal.fromNodeEnv();
|
|
21
21
|
createSQLWriter(terminal, {
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"interest_rate.js","sourceRoot":"","sources":["../../../src/services/markets/interest_rate.ts"],"names":[],"mappings":"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","sourcesContent":["import { IInterestRate } from '@yuants/data-interest-rate';\nimport { IProduct } from '@yuants/data-product';\nimport { createSeriesProvider, ISeriesCollectingTask } from '@yuants/data-series';\nimport { Terminal } from '@yuants/protocol';\nimport { createSQLWriter } from '@yuants/sql';\nimport { decodePath, encodePath, formatTime } from '@yuants/utils';\nimport { firstValueFrom, map, mergeAll, timer } from 'rxjs';\nimport { getFApiV1FundingRate } from '../../api/public-api';\nimport { productService } from './product';\n\nconst terminal = Terminal.fromNodeEnv();\n\ncreateSQLWriter<ISeriesCollectingTask>(terminal, {\n data$: productService.products$.pipe(\n map((products: IProduct[]) => products.filter((product) => product.no_interest_rate === false)),\n mergeAll(),\n map(\n (product: IProduct): ISeriesCollectingTask => ({\n series_id: encodePath(product.datasource_id, product.product_id),\n table_name: 'interest_rate',\n cron_pattern: '0 * * * *',\n cron_timezone: 'UTC',\n disabled: false,\n replay_count: 0,\n }),\n ),\n ),\n tableName: 'series_collecting_task',\n writeInterval: 1000,\n conflictKeys: ['series_id', 'table_name'],\n});\n\ncreateSeriesProvider<IInterestRate>(terminal, {\n tableName: 'interest_rate',\n series_id_prefix_parts: ['ASTER'],\n reversed: true,\n serviceOptions: { concurrent: 1 },\n queryFn: async function* ({ series_id, started_at, ended_at }) {\n const start = started_at ?? 0;\n const end = ended_at ?? Date.now();\n const [datasource_id, product_id] = decodePath(series_id);\n const [instType, instId] = decodePath(product_id);\n\n if (instType !== 'PERPETUAL') {\n return;\n }\n\n let currentStart = start;\n\n while (currentStart <= end) {\n const res = await getFApiV1FundingRate({\n symbol: instId,\n startTime: currentStart,\n endTime: end,\n limit: 1000,\n });\n\n if (!Array.isArray(res) || res.length === 0) {\n break;\n }\n\n const filtered = res.filter((item) => item.fundingTime >= currentStart && item.fundingTime <= end);\n\n if (filtered.length === 0) {\n const lastRecord = res[res.length - 1];\n const nextStart = lastRecord.fundingTime + 1;\n if (nextStart <= currentStart) {\n break;\n }\n currentStart = nextStart;\n await firstValueFrom(timer(1000));\n continue;\n }\n\n const data = filtered.map((item): IInterestRate => {\n const rate = Number(item.fundingRate);\n return {\n series_id,\n product_id,\n datasource_id,\n created_at: formatTime(item.fundingTime),\n long_rate: `${-rate}`,\n short_rate: `${rate}`,\n settlement_price: '',\n };\n });\n\n yield data;\n\n const lastTime = filtered[filtered.length - 1].fundingTime;\n if (lastTime >= end) {\n break;\n }\n\n currentStart = lastTime + 1;\n\n if (res.length < 1000) {\n break;\n }\n\n await firstValueFrom(timer(1000));\n }\n },\n});\n"]}
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { provideQueryProductsService } from '@yuants/data-product';
|
|
2
2
|
import { Terminal } from '@yuants/protocol';
|
|
3
3
|
import { encodePath } from '@yuants/utils';
|
|
4
|
-
import { getFApiV1ExchangeInfo } from '
|
|
4
|
+
import { getFApiV1ExchangeInfo } from '../../api/public-api';
|
|
5
5
|
const terminal = Terminal.fromNodeEnv();
|
|
6
6
|
// Provide QueryProducts service for ASTER
|
|
7
7
|
export const productService = provideQueryProductsService(terminal, 'ASTER', async (req) => {
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"product.js","sourceRoot":"","sources":["../../../src/services/markets/product.ts"],"names":[],"mappings":"AAAA,OAAO,EAAmC,2BAA2B,EAAE,MAAM,sBAAsB,CAAC;AACpG,OAAO,EAAE,QAAQ,EAAE,MAAM,kBAAkB,CAAC;AAC5C,OAAO,EAAE,UAAU,EAAE,MAAM,eAAe,CAAC;AAC3C,OAAO,EAAE,qBAAqB,EAAE,MAAM,sBAAsB,CAAC;AAE7D,MAAM,QAAQ,GAAG,QAAQ,CAAC,WAAW,EAAE,CAAC;AAExC,0CAA0C;AAC1C,MAAM,CAAC,MAAM,cAAc,GAAG,2BAA2B,CACvD,QAAQ,EACR,OAAO,EACP,KAAK,EAAE,GAA0B,EAAuB,EAAE;IACxD,qCAAqC;IACrC,MAAM,YAAY,GAAG,MAAM,qBAAqB,CAAC,EAAE,CAAC,CAAC;IAErD,qCAAqC;IACrC,OAAO,YAAY,CAAC,OAAO;SACxB,MAAM,CAAC,CAAC,MAAM,EAAE,EAAE,CAAC,MAAM,CAAC,MAAM,KAAK,SAAS,CAAC,CAAC,sCAAsC;SACtF,GAAG,CAAC,CAAC,MAAM,EAAY,EAAE;QACxB,mCAAmC;QACnC,MAAM,WAAW,GAAG,MAAM,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC,MAAM,EAAE,EAAE,CAAC,MAAM,CAAC,UAAU,KAAK,cAAc,CAAC,CAAC;QAC1F,MAAM,SAAS,GAAG,WAAW,CAAC,CAAC,CAAC,CAAC,WAAW,CAAC,QAAQ,CAAC,CAAC,CAAC,IAAI,CAAC;QAE7D,uCAAuC;QACvC,MAAM,aAAa,GAAG,MAAM,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC,MAAM,EAAE,EAAE,CAAC,MAAM,CAAC,UAAU,KAAK,UAAU,CAAC,CAAC;QACxF,MAAM,UAAU,GAAG,aAAa,CAAC,CAAC,CAAC,CAAC,aAAa,CAAC,QAAQ,CAAC,CAAC,CAAC,MAAM,CAAC,MAAM,MAAM,CAAC,iBAAiB,EAAE,CAAC,CAAC;QAEtG,OAAO;YACL,aAAa,EAAE,OAAO;YACtB,UAAU,EAAE,UAAU,CAAC,WAAW,EAAE,MAAM,CAAC,MAAM,CAAC;YAClD,IAAI,EAAE,GAAG,MAAM,CAAC,SAAS,IAAI,MAAM,CAAC,UAAU,OAAO;YACrD,cAAc,EAAE,MAAM,CAAC,UAAU;YACjC,aAAa,EAAE,MAAM,CAAC,SAAS;YAC/B,gBAAgB,EAAE,EAAE;YACpB,gBAAgB,EAAE,CAAC;YACnB,iBAAiB,EAAE,CAAC;YACpB,UAAU,EAAE,CAAC;YACb,UAAU,EAAE,SAAS;YACrB,WAAW,EAAE,UAAU;YACvB,WAAW,EAAE,CAAC;YACd,UAAU,EAAE,IAAI;YAChB,WAAW,EAAE,IAAI;YACjB,WAAW,EAAE,GAAG;YAChB,YAAY,EAAE,CAAC;YACf,SAAS,EAAE,iBAAiB;YAC5B,gBAAgB,EAAE,KAAK;SACxB,CAAC;IACJ,CAAC,CAAC,CAAC;AACP,CAAC,EACD;IACE,qBAAqB,EAAE,OAAQ,EAAE,iBAAiB;CACnD,CACF,CAAC","sourcesContent":["import { IProduct, IQueryProductsRequest, provideQueryProductsService } from '@yuants/data-product';\nimport { Terminal } from '@yuants/protocol';\nimport { encodePath } from '@yuants/utils';\nimport { getFApiV1ExchangeInfo } from '../../api/public-api';\n\nconst terminal = Terminal.fromNodeEnv();\n\n// Provide QueryProducts service for ASTER\nexport const productService = provideQueryProductsService(\n terminal,\n 'ASTER',\n async (req: IQueryProductsRequest): Promise<IProduct[]> => {\n // Fetch exchange info from ASTER API\n const exchangeInfo = await getFApiV1ExchangeInfo({});\n\n // Convert symbols to IProduct format\n return exchangeInfo.symbols\n .filter((symbol) => symbol.status === 'TRADING') // Only include active trading symbols\n .map((symbol): IProduct => {\n // Find price filter for price step\n const priceFilter = symbol.filters.find((filter) => filter.filterType === 'PRICE_FILTER');\n const priceStep = priceFilter ? +priceFilter.tickSize : 1e-2;\n\n // Find lot size filter for volume step\n const lotSizeFilter = symbol.filters.find((filter) => filter.filterType === 'LOT_SIZE');\n const volumeStep = lotSizeFilter ? +lotSizeFilter.stepSize : Number(`1e-${symbol.quantityPrecision}`);\n\n return {\n datasource_id: 'ASTER',\n product_id: encodePath('PERPETUAL', symbol.symbol),\n name: `${symbol.baseAsset}/${symbol.quoteAsset} PERP`,\n quote_currency: symbol.quoteAsset,\n base_currency: symbol.baseAsset,\n value_scale_unit: '',\n value_based_cost: 0,\n volume_based_cost: 0,\n max_volume: 0,\n price_step: priceStep,\n volume_step: volumeStep,\n value_scale: 1,\n allow_long: true,\n allow_short: true,\n margin_rate: 0.1, // Default margin rate, can be adjusted based on actual requirements\n max_position: 0,\n market_id: 'ASTER/PERPETUAL',\n no_interest_rate: false,\n };\n });\n },\n {\n auto_refresh_interval: 3600_000, // Refresh hourly\n },\n);\n"]}
|
|
@@ -3,7 +3,7 @@ import { Terminal } from '@yuants/protocol';
|
|
|
3
3
|
import { writeToSQL } from '@yuants/sql';
|
|
4
4
|
import { decodePath, encodePath } from '@yuants/utils';
|
|
5
5
|
import { defer, filter, from, map, mergeMap, repeat, retry, shareReplay } from 'rxjs';
|
|
6
|
-
import { getFApiV1OpenInterest, getFApiV1TickerPrice } from '
|
|
6
|
+
import { getFApiV1OpenInterest, getFApiV1TickerPrice } from '../../api/public-api';
|
|
7
7
|
const terminal = Terminal.fromNodeEnv();
|
|
8
8
|
const OPEN_INTEREST_TTL = process.env.OPEN_INTEREST_TTL ? Number(process.env.OPEN_INTEREST_TTL) : 120000;
|
|
9
9
|
const openInterestCache = createCache(async (symbol) => {
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"quote.js","sourceRoot":"","sources":["../../../src/services/markets/quote.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAE,MAAM,eAAe,CAAC;AAE5C,OAAO,EAAE,QAAQ,EAAE,MAAM,kBAAkB,CAAC;AAC5C,OAAO,EAAE,UAAU,EAAE,MAAM,aAAa,CAAC;AACzC,OAAO,EAAE,UAAU,EAAE,UAAU,EAAE,MAAM,eAAe,CAAC;AACvD,OAAO,EAAE,KAAK,EAAE,MAAM,EAAE,IAAI,EAAE,GAAG,EAAE,QAAQ,EAAE,MAAM,EAAE,KAAK,EAAE,WAAW,EAAE,MAAM,MAAM,CAAC;AACtF,OAAO,EAAE,qBAAqB,EAAE,oBAAoB,EAAE,MAAM,sBAAsB,CAAC;AAEnF,MAAM,QAAQ,GAAG,QAAQ,CAAC,WAAW,EAAE,CAAC;AACxC,MAAM,iBAAiB,GAAG,OAAO,CAAC,GAAG,CAAC,iBAAiB,CAAC,CAAC,CAAC,MAAM,CAAC,OAAO,CAAC,GAAG,CAAC,iBAAiB,CAAC,CAAC,CAAC,CAAC,MAAO,CAAC;AAE1G,MAAM,iBAAiB,GAAG,WAAW,CACnC,KAAK,EAAE,MAAc,EAAE,EAAE;IACvB,IAAI;QACF,MAAM,IAAI,GAAG,MAAM,qBAAqB,CAAC,EAAE,MAAM,EAAE,CAAC,CAAC;QACrD,OAAO,IAAI,CAAC,YAAY,CAAC;KAC1B;IAAC,OAAO,KAAK,EAAE;QACd,OAAO,CAAC,IAAI,CAAC,8BAA8B,EAAE,MAAM,EAAE,KAAK,CAAC,CAAC;QAC5D,OAAO,SAAS,CAAC;KAClB;AACH,CAAC,EACD,EAAE,MAAM,EAAE,iBAAiB,EAAE,CAC9B,CAAC;AAEF,MAAM,MAAM,GAAG,KAAK,CAAC,GAAG,EAAE,CAAC,oBAAoB,CAAC,EAAE,CAAC,CAAC,CAAC,IAAI,CACvD,QAAQ,CAAC,CAAC,OAAO,EAAE,EAAE,CAAC,OAAO,IAAI,EAAE,CAAC,EACpC,QAAQ,CACN,CAAC,MAAM,EAAE,EAAE,CACT,IAAI,CAAC,iBAAiB,CAAC,KAAK,CAAC,MAAM,CAAC,MAAM,CAAC,CAAC,CAAC,IAAI,CAC/C,GAAG,CACD,CAAC,YAAY,EAAmB,EAAE;;IAAC,OAAA,CAAC;QAClC,aAAa,EAAE,OAAO;QACtB,UAAU,EAAE,UAAU,CAAC,WAAW,EAAE,MAAM,CAAC,MAAM,CAAC;QAClD,UAAU,EAAE,GAAG,MAAM,CAAC,KAAK,EAAE;QAC7B,SAAS,EAAE,GAAG,MAAM,CAAC,KAAK,EAAE;QAC5B,SAAS,EAAE,GAAG,MAAM,CAAC,KAAK,EAAE;QAC5B,aAAa,EAAE,GAAG,YAAY,aAAZ,YAAY,cAAZ,YAAY,GAAI,CAAC,EAAE;QACrC,UAAU,EAAE,IAAI,IAAI,CAAC,MAAA,MAAM,CAAC,IAAI,mCAAI,IAAI,CAAC,GAAG,EAAE,CAAC,CAAC,WAAW,EAAE;KAC9D,CAAC,CAAA;CAAA,CACH,CACF,EACH,CAAC,CACF,EACD,MAAM,CAAC,EAAE,KAAK,EAAE,IAAI,EAAE,CAAC,EACvB,KAAK,CAAC,EAAE,KAAK,EAAE,IAAI,EAAE,CAAC,EACtB,WAAW,CAAC,EAAE,UAAU,EAAE,CAAC,EAAE,QAAQ,EAAE,IAAI,EAAE,CAAC,CAC/C,CAAC;AAEF,IAAI,OAAO,CAAC,GAAG,CAAC,kBAAkB,KAAK,MAAM,EAAE;IAC7C,MAAM;SACH,IAAI,CACH,UAAU,CAAC;QACT,QAAQ;QACR,SAAS,EAAE,OAAO;QAClB,aAAa,EAAE,IAAI;QACnB,YAAY,EAAE,CAAC,eAAe,EAAE,YAAY,CAAC;KAC9C,CAAC,CACH;SACA,SAAS,EAAE,CAAC;IAEf,QAAQ,CAAC,OAAO,CAAC,cAAc,CAAC,OAAO,EAAE,EAAE,OAAO,EAAE,SAAS,EAAE,EAAE,CAAC,UAAU,EAAE,EAAE;QAC9E,MAAM,CAAC,YAAY,EAAE,SAAS,CAAC,GAAG,UAAU,CAAC,UAAU,CAAC,CAAC;QACzD,IAAI,CAAC,YAAY,IAAI,CAAC,SAAS,EAAE;YAC/B,MAAM,IAAI,KAAK,CAAC,uBAAuB,UAAU,EAAE,CAAC,CAAC;SACtD;QACD,OAAO,MAAM,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC,KAAK,EAAE,EAAE,CAAC,KAAK,CAAC,UAAU,KAAK,SAAS,CAAC,CAAC,CAAC;IACxE,CAAC,CAAC,CAAC;CACJ","sourcesContent":["import { createCache } from '@yuants/cache';\nimport type { IQuote } from '@yuants/data-quote';\nimport { Terminal } from '@yuants/protocol';\nimport { writeToSQL } from '@yuants/sql';\nimport { decodePath, encodePath } from '@yuants/utils';\nimport { defer, filter, from, map, mergeMap, repeat, retry, shareReplay } from 'rxjs';\nimport { getFApiV1OpenInterest, getFApiV1TickerPrice } from '../../api/public-api';\n\nconst terminal = Terminal.fromNodeEnv();\nconst OPEN_INTEREST_TTL = process.env.OPEN_INTEREST_TTL ? Number(process.env.OPEN_INTEREST_TTL) : 120_000;\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 quote$ = defer(() => getFApiV1TickerPrice({})).pipe(\n mergeMap((tickers) => tickers || []),\n mergeMap(\n (ticker) =>\n from(openInterestCache.query(ticker.symbol)).pipe(\n map(\n (openInterest): Partial<IQuote> => ({\n datasource_id: 'ASTER',\n product_id: encodePath('PERPETUAL', ticker.symbol),\n last_price: `${ticker.price}`,\n bid_price: `${ticker.price}`,\n ask_price: `${ticker.price}`,\n open_interest: `${openInterest ?? 0}`,\n updated_at: new Date(ticker.time ?? Date.now()).toISOString(),\n }),\n ),\n ),\n 5,\n ),\n repeat({ delay: 1000 }),\n retry({ delay: 5000 }),\n shareReplay({ bufferSize: 1, refCount: true }),\n);\n\nif (process.env.WRITE_QUOTE_TO_SQL === 'true') {\n quote$\n .pipe(\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"]}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import { provideOrderActionsWithCredential } from '@yuants/data-order';
|
|
2
|
+
import { Terminal } from '@yuants/protocol';
|
|
3
|
+
import { handleCancelOrder } from './orders/cancelOrder';
|
|
4
|
+
import { handleSubmitOrder } from './orders/submitOrder';
|
|
5
|
+
provideOrderActionsWithCredential(Terminal.fromNodeEnv(), 'ASTER', {
|
|
6
|
+
type: 'object',
|
|
7
|
+
required: ['address', 'api_key', 'secret_key'],
|
|
8
|
+
properties: {
|
|
9
|
+
address: { type: 'string' },
|
|
10
|
+
api_key: { type: 'string' },
|
|
11
|
+
secret_key: { type: 'string' },
|
|
12
|
+
},
|
|
13
|
+
}, {
|
|
14
|
+
submitOrder: handleSubmitOrder,
|
|
15
|
+
cancelOrder: handleCancelOrder,
|
|
16
|
+
});
|
|
17
|
+
//# sourceMappingURL=order-actions-with-credential.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"order-actions-with-credential.js","sourceRoot":"","sources":["../../src/services/order-actions-with-credential.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,iCAAiC,EAAE,MAAM,oBAAoB,CAAC;AACvE,OAAO,EAAE,QAAQ,EAAE,MAAM,kBAAkB,CAAC;AAC5C,OAAO,EAAE,iBAAiB,EAAE,MAAM,sBAAsB,CAAC;AACzD,OAAO,EAAE,iBAAiB,EAAE,MAAM,sBAAsB,CAAC;AAEzD,iCAAiC,CAC/B,QAAQ,CAAC,WAAW,EAAE,EACtB,OAAO,EACP;IACE,IAAI,EAAE,QAAQ;IACd,QAAQ,EAAE,CAAC,SAAS,EAAE,SAAS,EAAE,YAAY,CAAC;IAC9C,UAAU,EAAE;QACV,OAAO,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE;QAC3B,OAAO,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE;QAC3B,UAAU,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE;KAC/B;CACF,EACD;IACE,WAAW,EAAE,iBAAiB;IAC9B,WAAW,EAAE,iBAAiB;CAC/B,CACF,CAAC","sourcesContent":["import { provideOrderActionsWithCredential } from '@yuants/data-order';\nimport { Terminal } from '@yuants/protocol';\nimport { handleCancelOrder } from './orders/cancelOrder';\nimport { handleSubmitOrder } from './orders/submitOrder';\n\nprovideOrderActionsWithCredential(\n Terminal.fromNodeEnv(),\n 'ASTER',\n {\n type: 'object',\n required: ['address', 'api_key', 'secret_key'],\n properties: {\n address: { type: 'string' },\n api_key: { type: 'string' },\n secret_key: { type: 'string' },\n },\n },\n {\n submitOrder: handleSubmitOrder,\n cancelOrder: handleCancelOrder,\n },\n);\n"]}
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import { deleteFApiV1Order } from '../../api/private-api';
|
|
2
|
+
import { decodePath } from '@yuants/utils';
|
|
3
|
+
export const handleCancelOrder = async (credential, order) => {
|
|
4
|
+
const [, decodedSymbol] = decodePath(order.product_id);
|
|
5
|
+
if (!decodedSymbol) {
|
|
6
|
+
throw new Error(`Invalid product_id: unable to decode symbol from "${order.product_id}"`);
|
|
7
|
+
}
|
|
8
|
+
if (!order.order_id) {
|
|
9
|
+
throw new Error('order_id is required for CancelOrder');
|
|
10
|
+
}
|
|
11
|
+
await deleteFApiV1Order(credential, {
|
|
12
|
+
symbol: decodedSymbol,
|
|
13
|
+
orderId: order.order_id,
|
|
14
|
+
});
|
|
15
|
+
};
|
|
16
|
+
//# sourceMappingURL=cancelOrder.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"cancelOrder.js","sourceRoot":"","sources":["../../../src/services/orders/cancelOrder.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,iBAAiB,EAAe,MAAM,uBAAuB,CAAC;AACvE,OAAO,EAAE,UAAU,EAAE,MAAM,eAAe,CAAC;AAE3C,MAAM,CAAC,MAAM,iBAAiB,GAA6C,KAAK,EAAE,UAAU,EAAE,KAAK,EAAE,EAAE;IACrG,MAAM,CAAC,EAAE,aAAa,CAAC,GAAG,UAAU,CAAC,KAAK,CAAC,UAAU,CAAC,CAAC;IACvD,IAAI,CAAC,aAAa,EAAE;QAClB,MAAM,IAAI,KAAK,CAAC,qDAAqD,KAAK,CAAC,UAAU,GAAG,CAAC,CAAC;KAC3F;IACD,IAAI,CAAC,KAAK,CAAC,QAAQ,EAAE;QACnB,MAAM,IAAI,KAAK,CAAC,sCAAsC,CAAC,CAAC;KACzD;IAED,MAAM,iBAAiB,CAAC,UAAU,EAAE;QAClC,MAAM,EAAE,aAAa;QACrB,OAAO,EAAE,KAAK,CAAC,QAAQ;KACxB,CAAC,CAAC;AACL,CAAC,CAAC","sourcesContent":["import { IActionHandlerOfCancelOrder } from '@yuants/data-order';\nimport { deleteFApiV1Order, ICredential } from '../../api/private-api';\nimport { decodePath } from '@yuants/utils';\n\nexport const handleCancelOrder: IActionHandlerOfCancelOrder<ICredential> = async (credential, order) => {\n const [, decodedSymbol] = decodePath(order.product_id);\n if (!decodedSymbol) {\n throw new Error(`Invalid product_id: unable to decode symbol from \"${order.product_id}\"`);\n }\n if (!order.order_id) {\n throw new Error('order_id is required for CancelOrder');\n }\n\n await deleteFApiV1Order(credential, {\n symbol: decodedSymbol,\n orderId: order.order_id,\n });\n};\n"]}
|
|
@@ -1,9 +1,5 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import { Terminal } from '@yuants/protocol';
|
|
1
|
+
import { getFApiV1OpenOrders } from '../../api/private-api';
|
|
3
2
|
import { encodePath } from '@yuants/utils';
|
|
4
|
-
import { ACCOUNT_ID } from './account';
|
|
5
|
-
import { getFApiV1OpenOrders } from './api';
|
|
6
|
-
const terminal = Terminal.fromNodeEnv();
|
|
7
3
|
const resolveOrderDirection = (asterOrder) => {
|
|
8
4
|
const reduceOnly = asterOrder.reduceOnly || asterOrder.closePosition;
|
|
9
5
|
if (asterOrder.positionSide === 'LONG') {
|
|
@@ -17,8 +13,8 @@ const resolveOrderDirection = (asterOrder) => {
|
|
|
17
13
|
}
|
|
18
14
|
return asterOrder.side === 'BUY' ? 'OPEN_LONG' : 'OPEN_SHORT';
|
|
19
15
|
};
|
|
20
|
-
|
|
21
|
-
const orders =
|
|
16
|
+
export const listOrders = async (credential, account_id) => {
|
|
17
|
+
const orders = await getFApiV1OpenOrders(credential, {});
|
|
22
18
|
return orders.map((order) => {
|
|
23
19
|
const volume = Number(order.origQty);
|
|
24
20
|
const tradedVolume = Number(order.executedQty);
|
|
@@ -26,7 +22,7 @@ providePendingOrdersService(terminal, ACCOUNT_ID, async () => {
|
|
|
26
22
|
const avgPrice = Number(order.avgPrice);
|
|
27
23
|
const mapped = {
|
|
28
24
|
order_id: `${order.orderId}`,
|
|
29
|
-
account_id:
|
|
25
|
+
account_id: account_id,
|
|
30
26
|
product_id: encodePath('PERPETUAL', order.symbol),
|
|
31
27
|
order_type: order.type,
|
|
32
28
|
order_direction: resolveOrderDirection(order),
|
|
@@ -39,5 +35,5 @@ providePendingOrdersService(terminal, ACCOUNT_ID, async () => {
|
|
|
39
35
|
};
|
|
40
36
|
return mapped;
|
|
41
37
|
});
|
|
42
|
-
}
|
|
43
|
-
//# sourceMappingURL=
|
|
38
|
+
};
|
|
39
|
+
//# sourceMappingURL=listOrders.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"listOrders.js","sourceRoot":"","sources":["../../../src/services/orders/listOrders.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,mBAAmB,EAAe,MAAM,uBAAuB,CAAC;AACzE,OAAO,EAAE,UAAU,EAAE,MAAM,eAAe,CAAC;AAoB3C,MAAM,qBAAqB,GAAG,CAAC,UAA2B,EAAkB,EAAE;IAC5E,MAAM,UAAU,GAAG,UAAU,CAAC,UAAU,IAAI,UAAU,CAAC,aAAa,CAAC;IAErE,IAAI,UAAU,CAAC,YAAY,KAAK,MAAM,EAAE;QACtC,OAAO,UAAU,CAAC,IAAI,KAAK,KAAK,CAAC,CAAC,CAAC,WAAW,CAAC,CAAC,CAAC,YAAY,CAAC;KAC/D;IACD,IAAI,UAAU,CAAC,YAAY,KAAK,OAAO,EAAE;QACvC,OAAO,UAAU,CAAC,IAAI,KAAK,KAAK,CAAC,CAAC,CAAC,aAAa,CAAC,CAAC,CAAC,YAAY,CAAC;KACjE;IACD,IAAI,UAAU,EAAE;QACd,OAAO,UAAU,CAAC,IAAI,KAAK,KAAK,CAAC,CAAC,CAAC,aAAa,CAAC,CAAC,CAAC,YAAY,CAAC;KACjE;IACD,OAAO,UAAU,CAAC,IAAI,KAAK,KAAK,CAAC,CAAC,CAAC,WAAW,CAAC,CAAC,CAAC,YAAY,CAAC;AAChE,CAAC,CAAC;AAEF,MAAM,CAAC,MAAM,UAAU,GAA4C,KAAK,EAAE,UAAU,EAAE,UAAU,EAAE,EAAE;IAClG,MAAM,MAAM,GAAG,MAAM,mBAAmB,CAAC,UAAU,EAAE,EAAE,CAAC,CAAC;IACzD,OAAO,MAAM,CAAC,GAAG,CAAC,CAAC,KAAK,EAAE,EAAE;QAC1B,MAAM,MAAM,GAAG,MAAM,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC;QACrC,MAAM,YAAY,GAAG,MAAM,CAAC,KAAK,CAAC,WAAW,CAAC,CAAC;QAC/C,MAAM,KAAK,GAAG,MAAM,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC;QAClC,MAAM,QAAQ,GAAG,MAAM,CAAC,KAAK,CAAC,QAAQ,CAAC,CAAC;QAExC,MAAM,MAAM,GAAW;YACrB,QAAQ,EAAE,GAAG,KAAK,CAAC,OAAO,EAAE;YAC5B,UAAU,EAAE,UAAU;YACtB,UAAU,EAAE,UAAU,CAAC,WAAW,EAAE,KAAK,CAAC,MAAM,CAAC;YACjD,UAAU,EAAE,KAAK,CAAC,IAAI;YACtB,eAAe,EAAE,qBAAqB,CAAC,KAAK,CAAC;YAC7C,MAAM,EAAE,MAAM,CAAC,QAAQ,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC;YAC5C,KAAK,EAAE,MAAM,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,SAAS;YACjD,SAAS,EAAE,KAAK,CAAC,UAAU;YAC3B,aAAa,EAAE,MAAM,CAAC,QAAQ,CAAC,YAAY,CAAC,CAAC,CAAC,CAAC,YAAY,CAAC,CAAC,CAAC,SAAS;YACvE,YAAY,EAAE,MAAM,CAAC,QAAQ,CAAC,QAAQ,CAAC,IAAI,QAAQ,GAAG,CAAC,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,CAAC,SAAS;YAC9E,YAAY,EAAE,KAAK,CAAC,MAAM;SAC3B,CAAC;QAEF,OAAO,MAAM,CAAC;IAChB,CAAC,CAAC,CAAC;AACL,CAAC,CAAC","sourcesContent":["import { IActionHandlerOfListOrders, IOrder } from '@yuants/data-order';\nimport { getFApiV1OpenOrders, ICredential } from '../../api/private-api';\nimport { encodePath } from '@yuants/utils';\n\ntype OrderDirection = 'OPEN_LONG' | 'OPEN_SHORT' | 'CLOSE_LONG' | 'CLOSE_SHORT';\n\ninterface IAsterOpenOrder {\n orderId: number;\n symbol: string;\n side: 'BUY' | 'SELL';\n positionSide?: 'BOTH' | 'LONG' | 'SHORT';\n reduceOnly?: boolean;\n closePosition?: boolean;\n type: string;\n origQty: string;\n executedQty: string;\n price: string;\n avgPrice: string;\n status: string;\n updateTime: number;\n}\n\nconst resolveOrderDirection = (asterOrder: IAsterOpenOrder): OrderDirection => {\n const reduceOnly = asterOrder.reduceOnly || asterOrder.closePosition;\n\n if (asterOrder.positionSide === 'LONG') {\n return asterOrder.side === 'BUY' ? 'OPEN_LONG' : 'CLOSE_LONG';\n }\n if (asterOrder.positionSide === 'SHORT') {\n return asterOrder.side === 'BUY' ? 'CLOSE_SHORT' : 'OPEN_SHORT';\n }\n if (reduceOnly) {\n return asterOrder.side === 'BUY' ? 'CLOSE_SHORT' : 'CLOSE_LONG';\n }\n return asterOrder.side === 'BUY' ? 'OPEN_LONG' : 'OPEN_SHORT';\n};\n\nexport const listOrders: IActionHandlerOfListOrders<ICredential> = async (credential, account_id) => {\n const orders = await getFApiV1OpenOrders(credential, {});\n return orders.map((order) => {\n const volume = Number(order.origQty);\n const tradedVolume = Number(order.executedQty);\n const price = Number(order.price);\n const avgPrice = Number(order.avgPrice);\n\n const mapped: IOrder = {\n order_id: `${order.orderId}`,\n account_id: account_id,\n product_id: encodePath('PERPETUAL', order.symbol),\n order_type: order.type,\n order_direction: resolveOrderDirection(order),\n volume: Number.isFinite(volume) ? volume : 0,\n price: Number.isFinite(price) ? price : undefined,\n submit_at: order.updateTime,\n traded_volume: Number.isFinite(tradedVolume) ? tradedVolume : undefined,\n traded_price: Number.isFinite(avgPrice) && avgPrice > 0 ? avgPrice : undefined,\n order_status: order.status,\n };\n\n return mapped;\n });\n};\n"]}
|
|
@@ -0,0 +1,84 @@
|
|
|
1
|
+
import { decodePath, roundToStep } from '@yuants/utils';
|
|
2
|
+
import { getApiV1TickerPrice, postApiV1Order, postFApiV1Order } from '../../api/private-api';
|
|
3
|
+
const handleSubmitOrderOfSpot = async (credential, order) => {
|
|
4
|
+
var _a;
|
|
5
|
+
const symbol = order.product_id;
|
|
6
|
+
const type = { MARKET: 'MARKET', LIMIT: 'LIMIT', MAKER: 'LIMIT' }[order.order_type];
|
|
7
|
+
if (!type)
|
|
8
|
+
throw new Error(`Unsupported order_type: ${order.order_type}`);
|
|
9
|
+
const side = { OPEN_LONG: 'BUY', OPEN_SHORT: 'SELL', CLOSE_LONG: 'SELL', CLOSE_SHORT: 'BUY' }[order.order_direction];
|
|
10
|
+
if (!side)
|
|
11
|
+
throw new Error(`Unsupported order_direction: ${order.order_direction}`);
|
|
12
|
+
const timeInForce = order.order_type === 'MAKER' ? 'GTX' : order.order_type === 'LIMIT' ? 'GTC' : undefined;
|
|
13
|
+
const price = order.price;
|
|
14
|
+
let quantity = order.volume;
|
|
15
|
+
let quoteOrderQty;
|
|
16
|
+
if (type === 'MARKET' && side === 'BUY') {
|
|
17
|
+
const spotPrice = await getApiV1TickerPrice(credential, {});
|
|
18
|
+
const thePrice = (_a = spotPrice.find((x) => x.symbol === symbol)) === null || _a === void 0 ? void 0 : _a.price;
|
|
19
|
+
if (!thePrice)
|
|
20
|
+
throw new Error(`Cannot get price for symbol ${symbol}`);
|
|
21
|
+
quantity = undefined;
|
|
22
|
+
quoteOrderQty = roundToStep(order.volume * +thePrice, 0.01);
|
|
23
|
+
}
|
|
24
|
+
const res = await postApiV1Order(credential, {
|
|
25
|
+
symbol,
|
|
26
|
+
type,
|
|
27
|
+
side,
|
|
28
|
+
timeInForce,
|
|
29
|
+
price,
|
|
30
|
+
quantity,
|
|
31
|
+
quoteOrderQty,
|
|
32
|
+
});
|
|
33
|
+
if (!res.orderId) {
|
|
34
|
+
throw new Error('Failed to retrieve order ID from response');
|
|
35
|
+
}
|
|
36
|
+
return { order_id: '' + res.orderId };
|
|
37
|
+
};
|
|
38
|
+
const handleSubmitOrderOfPerp = async (credential, order) => {
|
|
39
|
+
var _a, _b, _c, _d, _e;
|
|
40
|
+
const [, decodedSymbol] = decodePath(order.product_id);
|
|
41
|
+
if (!decodedSymbol) {
|
|
42
|
+
throw new Error(`Invalid product_id: unable to decode symbol from "${order.product_id}"`);
|
|
43
|
+
}
|
|
44
|
+
const symbol = decodedSymbol;
|
|
45
|
+
const side = { OPEN_LONG: 'BUY', OPEN_SHORT: 'SELL', CLOSE_LONG: 'SELL', CLOSE_SHORT: 'BUY' }[order.order_direction];
|
|
46
|
+
if (!side)
|
|
47
|
+
throw new Error(`Unsupported order_direction: ${order.order_direction}`);
|
|
48
|
+
const type = { MARKET: 'MARKET', LIMIT: 'LIMIT', MAKER: 'LIMIT' }[order.order_type];
|
|
49
|
+
if (!type)
|
|
50
|
+
throw new Error(`Unsupported order_type: ${order.order_type}`);
|
|
51
|
+
const quantity = order.volume;
|
|
52
|
+
const price = order.price;
|
|
53
|
+
const positionSide = order.order_direction === 'OPEN_LONG' || order.order_direction === 'CLOSE_LONG'
|
|
54
|
+
? 'LONG'
|
|
55
|
+
: order.order_direction === 'OPEN_SHORT' || order.order_direction === 'CLOSE_SHORT'
|
|
56
|
+
? 'SHORT'
|
|
57
|
+
: undefined;
|
|
58
|
+
const reduceOnly = order.order_direction === 'CLOSE_LONG' || order.order_direction === 'CLOSE_SHORT' ? 'true' : undefined;
|
|
59
|
+
const timeInForce = order.order_type === 'MAKER' ? 'GTX' : order.order_type === 'LIMIT' ? 'GTC' : undefined;
|
|
60
|
+
const res = await postFApiV1Order(credential, {
|
|
61
|
+
symbol,
|
|
62
|
+
side,
|
|
63
|
+
type,
|
|
64
|
+
quantity,
|
|
65
|
+
price,
|
|
66
|
+
timeInForce,
|
|
67
|
+
positionSide,
|
|
68
|
+
reduceOnly,
|
|
69
|
+
});
|
|
70
|
+
const orderId = (_d = (_b = (_a = res === null || res === void 0 ? void 0 : res.orderId) !== null && _a !== void 0 ? _a : res === null || res === void 0 ? void 0 : res.order_id) !== null && _b !== void 0 ? _b : (_c = res === null || res === void 0 ? void 0 : res.data) === null || _c === void 0 ? void 0 : _c.orderId) !== null && _d !== void 0 ? _d : (_e = res === null || res === void 0 ? void 0 : res.data) === null || _e === void 0 ? void 0 : _e.order_id;
|
|
71
|
+
if (!orderId)
|
|
72
|
+
throw new Error('Failed to retrieve order ID from response');
|
|
73
|
+
return { order_id: `${orderId}` };
|
|
74
|
+
};
|
|
75
|
+
export const handleSubmitOrder = async (credential, order) => {
|
|
76
|
+
if (order.account_id.includes('/SPOT')) {
|
|
77
|
+
return handleSubmitOrderOfSpot(credential, order);
|
|
78
|
+
}
|
|
79
|
+
if (order.account_id.includes('/PERP')) {
|
|
80
|
+
return handleSubmitOrderOfPerp(credential, order);
|
|
81
|
+
}
|
|
82
|
+
throw new Error(`Unsupported account_id for SubmitOrder: ${order.account_id}`);
|
|
83
|
+
};
|
|
84
|
+
//# sourceMappingURL=submitOrder.js.map
|