Skip to content

Commit 3fbd69d

Browse files
authored
Merge pull request #529 from JJ-Cro/majorTypeUpdate
feat(v2.15.15): Major type updates
2 parents b817668 + b4e705a commit 3fbd69d

17 files changed

+1143
-789
lines changed

.gitignore

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,3 +11,4 @@ privaterepotracker
1111
restClientRegex.ts
1212
.DS_Store
1313
dist
14+
localtest.ts

docs/endpointFunctionList.md

Lines changed: 607 additions & 608 deletions
Large diffs are not rendered by default.

examples/apidoc/MainClient/get24hrChangeStatististics.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ const { MainClient } = require('binance');
22

33
// This example shows how to call this Binance API endpoint with either node.js, javascript (js) or typescript (ts) with the npm module "binance" for Binance exchange
44
// This Binance API SDK is available on npm via "npm install binance"
5-
// ENDPOINT: api/v3/ticker/24hr
5+
// ENDPOINT: api/v3/ticker/24hr?symbols=
66
// METHOD: GET
77
// PUBLIC: YES
88

examples/apidoc/MainClient/getSymbolOrderBookTicker.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ const { MainClient } = require('binance');
22

33
// This example shows how to call this Binance API endpoint with either node.js, javascript (js) or typescript (ts) with the npm module "binance" for Binance exchange
44
// This Binance API SDK is available on npm via "npm install binance"
5-
// ENDPOINT: api/v3/ticker/bookTicker
5+
// ENDPOINT: api/v3/ticker/bookTicker?symbols=
66
// METHOD: GET
77
// PUBLIC: YES
88

examples/apidoc/MainClient/getSymbolPriceTicker.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ const { MainClient } = require('binance');
22

33
// This example shows how to call this Binance API endpoint with either node.js, javascript (js) or typescript (ts) with the npm module "binance" for Binance exchange
44
// This Binance API SDK is available on npm via "npm install binance"
5-
// ENDPOINT: api/v3/ticker/price
5+
// ENDPOINT: api/v3/ticker/price?symbols=
66
// METHOD: GET
77
// PUBLIC: YES
88

examples/apidoc/MainClient/getTradingDayTicker.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ const { MainClient } = require('binance');
22

33
// This example shows how to call this Binance API endpoint with either node.js, javascript (js) or typescript (ts) with the npm module "binance" for Binance exchange
44
// This Binance API SDK is available on npm via "npm install binance"
5-
// ENDPOINT: api/v3/ticker/tradingDay
5+
// ENDPOINT: api/v3/ticker/tradingDay?symbols=
66
// METHOD: GET
77
// PUBLIC: YES
88

examples/apidoc/USDMClient/get24hrChangeStatististics.js

Lines changed: 0 additions & 20 deletions
This file was deleted.
Lines changed: 223 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,223 @@
1+
import { numberInString } from '../lib';
2+
import { ExchangeInfo, MainClient } from '../src/index';
3+
4+
// or
5+
// import { MainClient } from 'binance';
6+
7+
const client = new MainClient({
8+
// Optional (default: false) - when true, response strings are parsed to floats (only for known keys).
9+
// beautifyResponses: true,
10+
});
11+
12+
interface SymbolInfo {
13+
tickSize: numberInString;
14+
qtyStepSize: numberInString;
15+
minOrderQty: numberInString;
16+
maxOrderQty: numberInString;
17+
maxMarketQty: numberInString;
18+
maxNumOfOrders: number;
19+
minNotional: numberInString;
20+
maxNotional: numberInString;
21+
maxBasePrecisionDecimals: number;
22+
maxQuotePrecisionDecimals: number;
23+
}
24+
25+
// Get full exchange info so we can cache it and use it for other functions without making request every time
26+
async function getExchangeInfo() {
27+
try {
28+
const exchangeInfo = await client.getExchangeInfo();
29+
return exchangeInfo;
30+
} catch (error) {
31+
throw new Error(`Failed to get exchange info: ${error.message}`);
32+
}
33+
}
34+
35+
const symbol = 'SOLUSDT';
36+
const exchangeInfo = getExchangeInfo();
37+
38+
async function getSymbolInfo(
39+
exchangeInfo: ExchangeInfo,
40+
symbol: string,
41+
): Promise<SymbolInfo> {
42+
try {
43+
// Find the symbol information once
44+
const symbolInfo = exchangeInfo.symbols.find((s) => s.symbol === symbol);
45+
// console.log(symbolInfo);
46+
47+
if (!symbolInfo) {
48+
throw new Error(`Symbol ${symbol} not found in exchange info`);
49+
}
50+
51+
// Extract filters from the symbol info
52+
const priceFilter = symbolInfo.filters.find(
53+
(f) => f.filterType === 'PRICE_FILTER',
54+
);
55+
const lotSizeFilter = symbolInfo.filters.find(
56+
(f) => f.filterType === 'LOT_SIZE',
57+
);
58+
const marketLotSizeFilter = symbolInfo.filters.find(
59+
(f) => f.filterType === 'MARKET_LOT_SIZE',
60+
);
61+
const maxNumOrdersFilter = symbolInfo.filters.find(
62+
(f) => f.filterType === 'MAX_NUM_ORDERS',
63+
);
64+
const notionalFilter = symbolInfo.filters.find(
65+
(f) => f.filterType === 'NOTIONAL',
66+
);
67+
68+
const symbolFilters = {
69+
tickSize: priceFilter?.tickSize,
70+
qtyStepSize: lotSizeFilter?.stepSize,
71+
minOrderQty: lotSizeFilter?.minQty,
72+
maxOrderQty: lotSizeFilter?.maxQty,
73+
maxMarketQty: marketLotSizeFilter?.maxQty,
74+
maxNumOfOrders: maxNumOrdersFilter?.maxNumOrders,
75+
minNotional: notionalFilter?.minNotional,
76+
maxNotional: notionalFilter?.maxNotional,
77+
maxBasePrecisionDecimals: symbolInfo.baseAssetPrecision,
78+
maxQuotePrecisionDecimals: symbolInfo.quoteAssetPrecision,
79+
};
80+
console.log(symbolFilters);
81+
82+
return symbolFilters;
83+
} catch (error) {
84+
throw new Error(`Failed to get symbol info: ${error.message}`);
85+
}
86+
}
87+
88+
/**
89+
* Rounds a price to the correct number of decimal places based on the symbol's tick size
90+
*/
91+
function roundToTickSize(price: number, tickSize: string): string {
92+
if (!tickSize) return price.toString();
93+
94+
// Calculate precision from tick size (e.g., 0.00010000 → 4 decimal places)
95+
const precision = tickSize.indexOf('1') - 1;
96+
if (precision < 0) return Math.floor(price).toString();
97+
98+
// Round to the nearest tick
99+
const tickSizeNum = parseFloat(tickSize);
100+
const rounded = Math.floor(price / tickSizeNum) * tickSizeNum;
101+
102+
// Format with correct precision
103+
return rounded.toFixed(precision);
104+
}
105+
106+
/**
107+
* Rounds a quantity to the correct step size
108+
*/
109+
function roundToStepSize(quantity: number, stepSize: string): string {
110+
if (!stepSize) return quantity.toString();
111+
112+
// Calculate precision from step size
113+
const precision = stepSize.indexOf('1') - 1;
114+
if (precision < 0) return Math.floor(quantity).toString();
115+
116+
// Round to the nearest step
117+
const stepSizeNum = parseFloat(stepSize);
118+
const rounded = Math.floor(quantity / stepSizeNum) * stepSizeNum;
119+
120+
// Format with correct precision
121+
return rounded.toFixed(precision);
122+
}
123+
124+
/**
125+
* Validates and formats an order based on symbol constraints
126+
*/
127+
function formatOrderParams(
128+
symbol: string,
129+
price: number,
130+
quantity: number,
131+
symbolInfo: any,
132+
): { symbol: string; price: string; quantity: string } {
133+
try {
134+
// Check if price is within allowed range
135+
const minPrice = parseFloat(symbolInfo.tickSize || '0');
136+
if (price < minPrice) {
137+
throw new Error(`Price ${price} is below minimum ${minPrice}`);
138+
}
139+
140+
// Check if quantity is within allowed range
141+
const minQty = parseFloat(symbolInfo.minOrderQty || '0');
142+
const maxQty = parseFloat(symbolInfo.maxOrderQty || Infinity);
143+
144+
if (quantity < minQty) {
145+
throw new Error(`Quantity ${quantity} is below minimum ${minQty}`);
146+
}
147+
148+
if (quantity > maxQty) {
149+
throw new Error(`Quantity ${quantity} exceeds maximum ${maxQty}`);
150+
}
151+
152+
// Check notional value (price * quantity)
153+
const notional = price * quantity;
154+
const minNotional = parseFloat(symbolInfo.minNotional || '0');
155+
156+
if (notional < minNotional) {
157+
throw new Error(
158+
`Order value ${notional} is below minimum ${minNotional}`,
159+
);
160+
}
161+
162+
// Format price and quantity according to exchange requirements
163+
const formattedPrice = roundToTickSize(price, symbolInfo.tickSize);
164+
const formattedQty = roundToStepSize(quantity, symbolInfo.qtyStepSize);
165+
166+
return {
167+
symbol,
168+
price: formattedPrice,
169+
quantity: formattedQty,
170+
};
171+
} catch (error) {
172+
throw new Error(`Failed to format order: ${error.message}`);
173+
}
174+
}
175+
176+
// Example usage
177+
async function testSymbolUtils() {
178+
const info = await exchangeInfo;
179+
if (!info) return;
180+
181+
const symbolFilters = await getSymbolInfo(info, symbol);
182+
if (!symbolFilters) return;
183+
184+
// Test price formatting
185+
const testPrice = 23.45678;
186+
console.log(`Original price: ${testPrice}`);
187+
console.log(
188+
`Formatted price: ${roundToTickSize(testPrice, symbolFilters.tickSize.toString())}`,
189+
);
190+
191+
// Test quantity formatting
192+
const testQty = 1.23456;
193+
console.log(`Original quantity: ${testQty}`);
194+
console.log(
195+
`Formatted quantity: ${roundToStepSize(
196+
testQty,
197+
symbolFilters.qtyStepSize.toString(),
198+
)}`,
199+
);
200+
201+
// Test full order formatting
202+
const orderParams = formatOrderParams(
203+
symbol,
204+
testPrice,
205+
testQty,
206+
symbolFilters,
207+
);
208+
console.log('Formatted order parameters:');
209+
console.log(orderParams);
210+
// example how to use the order params
211+
const order = await client.submitNewOrder({
212+
symbol: orderParams.symbol,
213+
side: 'BUY',
214+
type: 'LIMIT',
215+
quantity: Number(orderParams.quantity),
216+
price: Number(orderParams.price),
217+
timeInForce: 'GTC',
218+
});
219+
220+
console.log(order);
221+
}
222+
223+
testSymbolUtils();

package-lock.json

Lines changed: 2 additions & 2 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"name": "binance",
3-
"version": "2.15.14",
3+
"version": "2.15.15",
44
"description": "Node.js & JavaScript SDK for Binance REST APIs & WebSockets, with TypeScript & end-to-end tests.",
55
"main": "lib/index.js",
66
"types": "lib/index.d.ts",

0 commit comments

Comments
 (0)