import { DERIVATIVES_TRADING_USDS_FUTURES_REST_API_PROD_URL, DerivativesTradingUsdsFutures, DerivativesTradingUsdsFuturesRestAPI, } from '@binance/derivatives-trading-usds-futures' export class FutureConnector { client: DerivativesTradingUsdsFutures constructor(apiKey: string, apiSecret: string) { const configurationRestAPI = { apiKey: apiKey, apiSecret: apiSecret, basePath: DERIVATIVES_TRADING_USDS_FUTURES_REST_API_PROD_URL, } this.client = new DerivativesTradingUsdsFutures({ configurationRestAPI }) } async getAssetsInfo() { try { const response = await this.client.restAPI.accountInformationV3() const data = await response.data() return data.assets.filter((asset: any) => Number(asset.walletBalance) > 0) } catch (error) { console.error('accountInformation() error:', error) return [] } } async getPositonInfo() { try { const response = await this.client.restAPI.accountInformationV3() const data = await response.data() return data.positions.filter((position: any) => Number(position.positionAmt) > 0) } catch (error) { console.error('futuresPositionInformation() error:', error) return [] } } async getPositionBalanceBySymbol(symbol: string) { try { const response = await this.client.restAPI.accountInformationV3() const data = await response.data() const position = data.positions.find((pos: any) => pos.symbol === symbol) if (position) { return position } else { return null } } catch (error) { console.error('getPositionBalanceBySymbol() error:', error) return null } } async openModifyPosition( symbol: string, side: DerivativesTradingUsdsFuturesRestAPI.ModifyOrderSideEnum, quantity: number, price: number, ) { try { const response = await this.client.restAPI.modifyOrder({ symbol: symbol, side: side, quantity: quantity, price: price, }) return await response.data() } catch (error) { console.error('openPosition() error:', error) return null } } async getCurrentAllOpenPosition() { try { const response = await this.client.restAPI.currentAllOpenOrders() const data = await response.data() console.log('当前所有开仓订单响应:', data) } catch (error) { console.error('currentAllOpenOrders() error:', error) } } async openPosition( symbol: string, side: DerivativesTradingUsdsFuturesRestAPI.NewOrderSideEnum, quantity: number, price: number, options?: any, ) { try { const orderParams: any = { symbol: symbol, side: side, type: options?.type || 'LIMIT', timeInForce: options?.timeInForce || DerivativesTradingUsdsFuturesRestAPI.NewOrderTimeInForceEnum.GTC, quantity: quantity, price: price, } if (options?.positionSide) { orderParams.positionSide = options.positionSide } if (options?.reduceOnly) { orderParams.reduceOnly = options.reduceOnly } if (options?.closePosition) { orderParams.closePosition = options.closePosition } if (options?.activationPrice) { orderParams.activationPrice = options.activationPrice } if (options?.callbackRate) { orderParams.callbackRate = options.callbackRate } if (options?.workingType) { orderParams.workingType = options.workingType } if (options?.priceProtect) { orderParams.priceProtect = options.priceProtect } if (options?.newOrderRespType) { orderParams.newOrderRespType = options.newOrderRespType } if (options?.newClientOrderId) { orderParams.newClientOrderId = options.newClientOrderId } if (options?.stopPrice) { orderParams.stopPrice = options.stopPrice } if (options?.icebergQty) { orderParams.icebergQty = options.icebergQty } if (options?.orderTag) { orderParams.orderTag = options.orderTag } console.log('下单参数:', orderParams) const response = await this.client.restAPI.newOrder(orderParams) const result = await response.data() console.log('下单成功:', result) return result } catch (error) { console.error('openPosition() 错误:', error) return null } } async openLimitOrder( symbol: string, side: 'long' | 'short', quantity: number, price: number, timeInForce: 'GTC' | 'IOC' | 'FOK' | 'GTX' | 'GTD' = 'GTC', ) { return this.openPosition( symbol, side === 'long' ? DerivativesTradingUsdsFuturesRestAPI.NewOrderSideEnum.BUY : DerivativesTradingUsdsFuturesRestAPI.NewOrderSideEnum.SELL, quantity, price, { type: 'LIMIT', timeInForce, positionSide: side === 'long' ? DerivativesTradingUsdsFuturesRestAPI.NewOrderPositionSideEnum.LONG : DerivativesTradingUsdsFuturesRestAPI.NewOrderPositionSideEnum.SHORT, }, ) } async openMarketOrder(symbol: string, side: 'long' | 'short', quantity: number) { return this.openPosition( symbol, side === 'long' ? DerivativesTradingUsdsFuturesRestAPI.NewOrderSideEnum.BUY : DerivativesTradingUsdsFuturesRestAPI.NewOrderSideEnum.SELL, quantity, 0, { type: 'MARKET', positionSide: side === 'long' ? DerivativesTradingUsdsFuturesRestAPI.NewOrderPositionSideEnum.LONG : DerivativesTradingUsdsFuturesRestAPI.NewOrderPositionSideEnum.SHORT, }, ) } async openStopOrder( symbol: string, side: 'long' | 'short', quantity: number, stopPrice: number, type: 'STOP' | 'STOP_MARKET' = 'STOP_MARKET', price?: number, timeInForce: 'GTC' | 'IOC' | 'FOK' | 'GTX' | 'GTD' = 'GTC', ) { const orderParams: any = { type, stopPrice, reduceOnly: 'true', positionSide: side === 'long' ? DerivativesTradingUsdsFuturesRestAPI.NewOrderPositionSideEnum.LONG : DerivativesTradingUsdsFuturesRestAPI.NewOrderPositionSideEnum.SHORT, } if (type === 'STOP') { orderParams.timeInForce = timeInForce } return this.openPosition( symbol, side === 'long' ? DerivativesTradingUsdsFuturesRestAPI.NewOrderSideEnum.BUY : DerivativesTradingUsdsFuturesRestAPI.NewOrderSideEnum.SELL, quantity, price || 0, orderParams, ) } async openTakeProfitOrder( symbol: string, side: 'long' | 'short', quantity: number, stopPrice: number, type: 'TAKE_PROFIT' | 'TAKE_PROFIT_MARKET' = 'TAKE_PROFIT_MARKET', price?: number, timeInForce: 'GTC' | 'IOC' | 'FOK' | 'GTX' | 'GTD' = 'GTC', ) { const orderParams: any = { type, stopPrice, reduceOnly: 'true', positionSide: side === 'long' ? DerivativesTradingUsdsFuturesRestAPI.NewOrderPositionSideEnum.LONG : DerivativesTradingUsdsFuturesRestAPI.NewOrderPositionSideEnum.SHORT, } if (type === 'TAKE_PROFIT') { orderParams.timeInForce = timeInForce } return this.openPosition( symbol, side === 'long' ? DerivativesTradingUsdsFuturesRestAPI.NewOrderSideEnum.BUY : DerivativesTradingUsdsFuturesRestAPI.NewOrderSideEnum.SELL, quantity, price || 0, orderParams, ) } async openTrailingStopOrder( symbol: string, side: 'long' | 'short', quantity: number, activationPrice: number, callbackRate: number, ) { return this.openPosition( symbol, side === 'long' ? DerivativesTradingUsdsFuturesRestAPI.NewOrderSideEnum.BUY : DerivativesTradingUsdsFuturesRestAPI.NewOrderSideEnum.SELL, quantity, 0, { type: 'TRAILING_STOP_MARKET', activationPrice, callbackRate, reduceOnly: 'true', positionSide: side === 'long' ? DerivativesTradingUsdsFuturesRestAPI.NewOrderPositionSideEnum.LONG : DerivativesTradingUsdsFuturesRestAPI.NewOrderPositionSideEnum.SHORT, }, ) } async openIcebergOrder( symbol: string, side: 'long' | 'short', quantity: number, price: number, icebergQty: number, timeInForce: 'GTC' | 'IOC' | 'FOK' | 'GTX' | 'GTD' = 'GTC', ) { return this.openPosition( symbol, side === 'long' ? DerivativesTradingUsdsFuturesRestAPI.NewOrderSideEnum.BUY : DerivativesTradingUsdsFuturesRestAPI.NewOrderSideEnum.SELL, quantity, price, { type: 'LIMIT', timeInForce, icebergQty, positionSide: side === 'long' ? DerivativesTradingUsdsFuturesRestAPI.NewOrderPositionSideEnum.LONG : DerivativesTradingUsdsFuturesRestAPI.NewOrderPositionSideEnum.SHORT, }, ) } async closeLongPosition(symbol: string, quantity: number) { return this.openPosition(symbol, DerivativesTradingUsdsFuturesRestAPI.NewOrderSideEnum.SELL, quantity, 0, { type: 'MARKET', reduceOnly: 'true', positionSide: DerivativesTradingUsdsFuturesRestAPI.NewOrderPositionSideEnum.LONG, }) } async closeShortPosition(symbol: string, quantity: number) { return this.openPosition(symbol, DerivativesTradingUsdsFuturesRestAPI.NewOrderSideEnum.BUY, quantity, 0, { type: 'MARKET', reduceOnly: 'true', positionSide: DerivativesTradingUsdsFuturesRestAPI.NewOrderPositionSideEnum.SHORT, }) } async closeAllPositions() { const positions = await this.getAllPositions() const results: any[] = [] for (const pos of positions as any[]) { const amt = Number((pos as any).positionAmt) if (amt > 0) { results.push(await this.closeLongPosition((pos as any).symbol, Math.abs(amt))) } else if (amt < 0) { results.push(await this.closeShortPosition((pos as any).symbol, Math.abs(amt))) } } return results } async cancelOrder(symbol: string, orderId?: number, origClientOrderId?: string) { return this.client.restAPI.cancelOrder({ symbol, orderId, origClientOrderId }) } async cancelAllOrders(symbol: string) { return this.client.restAPI.cancelAllOpenOrders({ symbol }) } async getOrderHistory(symbol: string, startTime?: number, endTime?: number, limit: number = 100) { const response = await this.client.restAPI.allOrders({ symbol, startTime, endTime, limit }) return response.data() } async getTradeHistory(symbol: string, startTime?: number, endTime?: number, limit: number = 100) { const response = await this.client.restAPI.accountTradeList({ symbol, startTime, endTime, limit }) return response.data() } async setLeverage(symbol: string, leverage: number) { return this.client.restAPI.changeInitialLeverage({ symbol, leverage }) } async setMarginType(symbol: string, marginType: DerivativesTradingUsdsFuturesRestAPI.ChangeMarginTypeMarginTypeEnum) { return this.client.restAPI.changeMarginType({ symbol, marginType }) } async getAllPositions() { const response = await this.client.restAPI.accountInformationV3() const data = await response.data() return data.positions || [] } async getExchangeInfo() { try { const response = await this.client.restAPI.exchangeInformation() return response.data() } catch (error) { console.error('getExchangeInfo() error:', error) return null } } async getSymbols(): Promise { try { const exchangeInfo = await this.getExchangeInfo() if (!exchangeInfo?.symbols) return [] return exchangeInfo.symbols.filter((s: any) => s.status === 'TRADING').map((s: any) => s.symbol) } catch (error) { console.error('getSymbols() error:', error) return [] } } async getDepth(symbol: string, limit = 100) { try { const response = await this.client.restAPI.orderBook({ symbol, limit }) return response.data() } catch (error) { console.error('getDepth() error:', error) return { bids: [], asks: [], lastUpdateId: 0 } } } async getCurrentAllOpenOrders(symbol?: string) { try { const response = await this.client.restAPI.currentAllOpenOrders({ symbol }) return response.data() } catch (error) { console.error('getCurrentAllOpenOrders() error:', error) return [] } } } // 移除重复导出,统一以本文件类为准