Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
89 changes: 78 additions & 11 deletions src/node-binance-api.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3718,6 +3718,25 @@ export default class Binance {
return await this.publicSpotRequest('v3/ping', {});
}

parseAggTrades(symbol: string, trades: any[]): AggregatedTrade[] {
const parsedTrades: AggregatedTrade[] = [];
for (const trade of trades) {
const aggT: AggregatedTrade = {
aggId: trade.a,
symbol: symbol,
price: trade.p,
quantity: trade.q,
firstId: trade.f,
lastId: trade.l,
timestamp: trade.T,
isBuyerMaker: trade.m,
};
if (trade.M) aggT.wasBestPrice = trade.M;
parsedTrades.push(aggT);
}
return parsedTrades;
}

/**
* Get agg trades for given symbol
* @see https://developers.binance.com/docs/binance-spot-api-docs/rest-api/market-data-endpoints#compressedaggregate-trades-list
Expand All @@ -3727,7 +3746,8 @@ export default class Binance {
*/
async aggTrades(symbol: string, params: Dict = {}): Promise<AggregatedTrade[]> { //fromId startTime endTime limit
const parameters = Object.assign({ symbol }, params);
return await this.publicSpotRequest('v3/aggTrades', parameters);
const res = await this.publicSpotRequest('v3/aggTrades', parameters);
return this.parseAggTrades(symbol, res);
}

/**
Expand Down Expand Up @@ -3809,7 +3829,8 @@ export default class Binance {
async candlesticks(symbol: string, interval: Interval = '5m', params: Dict = {}): Promise<Candle[]> {
if (!params.limit) params.limit = 500;
params = Object.assign({ symbol: symbol, interval: interval }, params);
return await this.publicSpotRequest('v3/klines', params);
const res = await this.publicSpotRequest('v3/klines', params);
return this.parseCandles(res);
}

/**
Expand All @@ -3825,6 +3846,42 @@ export default class Binance {
return await this.candlesticks(symbol, interval, params); // make name consistent with futures
}

parseCandles(candles: any[]): Candle[] {
const res: Candle[] = [];
// spot
// [
// [
// 1499040000000, // Open time
// "0.01634790", // Open
// "0.80000000", // High
// "0.01575800", // Low
// "0.01577100", // Close
// "148976.11427815", // Volume
// 1499644799999, // Close time
// "2434.19055334", // Quote asset volume
// 308, // Number of trades
// "1756.87402397", // Taker buy base asset volume
// "28.46694368", // Taker buy quote asset volume
// "17928899.62484339" // Ignore.
// ]
// ]
for (const rawCandle of candles) {
const candle: Candle = {
openTime: rawCandle[0],
open: rawCandle[1],
high: rawCandle[2],
low: rawCandle[3],
close: rawCandle[4],
volume: rawCandle[5],
closeTime: rawCandle[6],
quoteAssetVolume: rawCandle[7],
trades: rawCandle[8],
};
res.push(candle);
}
return res;
}

// /**
// * Queries the public api
// * @param {string} url - the public api endpoint
Expand Down Expand Up @@ -3958,16 +4015,15 @@ export default class Binance {
async futuresCandles(symbol: string, interval: Interval = "30m", params: Dict = {}): Promise<Candle[]> {
params.symbol = symbol;
params.interval = interval;
return await this.publicFuturesRequest('v1/klines', params);
const res = await this.publicFuturesRequest('v1/klines', params);
return this.parseCandles(res);
}

/**
* @see https://developers.binance.com/docs/derivatives/usds-margined-futures/market-data/rest-api/Kline-Candlestick-Data
*/
async futuresCandlesticks(symbol: string, interval: Interval = "30m", params: Dict = {}): Promise<Candle[]> {
params.symbol = symbol;
params.interval = interval;
return await this.publicFuturesRequest('v1/klines', params);
return await this.futuresCandles(symbol, interval, params); // make name consistent with spot
}

/**
Expand Down Expand Up @@ -4480,10 +4536,18 @@ export default class Binance {
return res;
}

/**
* @see https://developers.binance.com/docs/derivatives/coin-margined-futures/market-data/rest-api/Kline-Candlestick-Data
* @param symbol
* @param interval
* @param params
* @returns
*/
async deliveryCandles(symbol: string, interval: Interval = "30m", params: Dict = {}): Promise<Candle[]> {
params.symbol = symbol;
params.interval = interval;
return await this.publicDeliveryRequest('v1/klines', params);
const res = await this.publicDeliveryRequest('v1/klines', params);
return this.parseCandles(res);
}

async deliveryContinuousKlines(pair: string, contractType = "CURRENT_QUARTER", interval: Interval = "30m", params: Dict = {}) {
Expand Down Expand Up @@ -5739,10 +5803,11 @@ export default class Binance {
}
};

const getSymbolDepthSnapshot = async (symbol: string, cb: Function) => {
const getSymbolDepthSnapshot = async (symbol: string) => {
const json = await this.publicSpotRequest('v3/depth', { symbol: symbol, limit: limit });
json.symbol = symbol;
cb(null, json);
// cb(null, json);
return json;
};

const updateSymbolDepthCache = json => {
Expand Down Expand Up @@ -5778,12 +5843,13 @@ export default class Binance {
const streams = symbols.map(function (symbol) {
return symbol.toLowerCase() + `@depth@100ms`;
});
const mapLimit = this.mapLimit.bind(this);
subscription = this.subscribeCombined(streams, handleDepthStreamData, reconnect, function () {
// async.mapLimit(symbols, 50, getSymbolDepthSnapshot, (err, results) => {
// if (err) throw err;
// results.forEach(updateSymbolDepthCache);
// });
this.mapLimit(symbols, 50, getSymbolDepthSnapshot)
mapLimit(symbols, 50, getSymbolDepthSnapshot)
.then(results => {
results.forEach(updateSymbolDepthCache);
})
Expand All @@ -5795,12 +5861,13 @@ export default class Binance {
} else {
const symbol = symbols;
symbolDepthInit(symbol);
const mapLimit = this.mapLimit.bind(this);
subscription = this.subscribe(symbol.toLowerCase() + `@depth@100ms`, handleDepthStreamData, reconnect, function () {
// async.mapLimit([symbol], 1, getSymbolDepthSnapshot, (err, results) => {
// if (err) throw err;
// results.forEach(updateSymbolDepthCache);
// });
this.mapLimit([symbol], 1, getSymbolDepthSnapshot)
mapLimit([symbol], 1, getSymbolDepthSnapshot)
.then(results => {
results.forEach(updateSymbolDepthCache);
})
Expand Down
6 changes: 3 additions & 3 deletions src/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -52,9 +52,9 @@ export interface Candle {
close: string
volume: string
closeTime: number
quoteVolume: string
quoteVolume?: string
trades: number
baseAssetVolume: string
baseAssetVolume?: string
quoteAssetVolume: string
}

Expand Down Expand Up @@ -258,7 +258,7 @@ export interface AggregatedTrade {
lastId: number
timestamp: number
isBuyerMaker: boolean
wasBestPrice: boolean
wasBestPrice?: boolean
}

export interface Trade {
Expand Down
37 changes: 33 additions & 4 deletions tests/binance-class-static.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -65,27 +65,56 @@ describe( 'Static tests', async function () {
})

it( 'OHLCVS', async function ( ) {
await binance.candlesticks( 'BTCUSDT' )
try {
await binance.candlesticks( 'BTCUSDT' )
} catch (e) {
// console.log(e)
}
assert.equal( interceptedUrl, 'https://api.binance.com/api/v3/klines?symbol=BTCUSDT&interval=5m&limit=500' )

})

it( 'Futures OHLCVS', async function ( ) {
await binance.futuresCandles( 'BTCUSDT' )
try {
await binance.futuresCandles( 'BTCUSDT' )
} catch (e) {
// console.log(e)
}
assert.equal( interceptedUrl, 'https://fapi.binance.com/fapi/v1/klines?symbol=BTCUSDT&interval=30m' )

})

it( 'Trades', async function ( ) {
await binance.aggTrades( 'BTCUSDT' )
it( 'Recent Trades', async function ( ) {
try {
await binance.recentTrades( 'BTCUSDT' )
} catch (e) {
// console.log(e)
}
assert.equal( interceptedUrl, 'https://api.binance.com/api/v3/trades?symbol=BTCUSDT&limit=500' )
})

it( 'Agg Trades', async function ( ) {
try {
await binance.aggTrades( 'BTCUSDT' )
} catch (e) {
// console.log(e)
}
assert.equal( interceptedUrl, 'https://api.binance.com/api/v3/aggTrades?symbol=BTCUSDT' )

})

it( 'FuturesTrades', async function ( ) {
await binance.futuresTrades( 'BTCUSDT' )
assert.equal( interceptedUrl, 'https://fapi.binance.com/fapi/v1/trades?symbol=BTCUSDT' )
})

it( 'FuturesAggTrades', async function ( ) {
try {
await binance.futuresAggTrades( 'BTCUSDT' )
} catch (e) {
// console.log(e)
}
assert.equal( interceptedUrl, 'https://fapi.binance.com/fapi/v1/aggTrades?symbol=BTCUSDT' )
})

it( 'PositionRisk V3', async function ( ) {
Expand Down
18 changes: 15 additions & 3 deletions tests/static-tests.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -75,19 +75,31 @@ describe( 'Static tests', async function () {
})

it( 'OHLCVS', async function ( ) {
await binance.candlesticks( 'BTCUSDT' )
try {
await binance.candlesticks( 'BTCUSDT' )
} catch (e) {
// console.log(e)
}
assert.equal( interceptedUrl, 'https://api.binance.com/api/v3/klines?symbol=BTCUSDT&interval=5m&limit=500' )

})

it( 'Futures OHLCVS', async function ( ) {
await binance.futuresCandles( 'BTCUSDT' )
try {
await binance.futuresCandles( 'BTCUSDT' )
} catch (e) {
// console.log(e)
}
assert.equal( interceptedUrl, 'https://fapi.binance.com/fapi/v1/klines?symbol=BTCUSDT&interval=30m' )

})

it( 'Trades', async function ( ) {
await binance.aggTrades( 'BTCUSDT' )
try {
await binance.aggTrades( 'BTCUSDT' )
} catch (e) {
// console.log(e)
}
assert.equal( interceptedUrl, 'https://api.binance.com/api/v3/aggTrades?symbol=BTCUSDT' )

})
Expand Down