Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

V7 #16

Merged
merged 4 commits into from
Oct 14, 2024
Merged

V7 #16

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
101 changes: 83 additions & 18 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,15 +6,20 @@

This package allows you to batch OHLCV candlesticks or create them from trade (tick) datasets.

#### Breaking Changes

Version 7.x introduces many breaking changes compared to version 6.x.x.

#### Supported formats:

- OHLCV (CCXT format) `[[time,open,high,low,close,volume]]`
- OHLCV JSON `[{time: number,open: number, high: number, low: number close: number, volume: number}]`
- Trade JSON `[{price: number, quantity: number, time:number}]`
- Tick JSON `[{price: number, quantity: number, time:number}]`
- Trade JSON `[{price: number, quantity: number, time:number, side: number}]`

#### Features:

- Typescript support!
- Typescript
- CCXT support
- No Dependencies
- Performance single loop used
Expand All @@ -34,22 +39,25 @@ npm install candlestick-convert
#### Available functions:

```javascript
import {batchCandleArray, batchCandleArrayCustomInterval, batchCandleJSON, batchTicksToCandle, ticksToTickChart} from "candlestick-convert";
import {batchCandles, batchCandlesWithCustomInterval, batchCandlesJSON, batchTicksToCandle, ticksToTickChart} from "candlestick-convert";

batchCandleArray(candledata: OHLCV[], baseInterval = 60, targetInterval = 300, includeOpenCandle = false)
batchCandles(candledata: OHLCV[], baseInterval = 60, targetInterval = 300, includeOpenCandle = false)
//return OHLCV[]

batchCandleArrayCustomInterval(candleData: OHLCV[], intervalFunction: IntervalFunction, includeOpenCandle = false)
batchCandlesWithCustomInterval(candleData: OHLCV[], intervalFunction: IntervalFunction, includeOpenCandle = false)
//return OHLCV[]

batchCandleJSON(candledata: IOHLCV [], baseInterval = 60, argetInterval = 300)
batchCandlesJSON(candledata: IOHLCV [], baseInterval = 60, argetInterval = 300)
// return IOHLCV[]

batchTicksToCandle(tradedata: TradeTick[], interval = 60, includeOpenCandle = false)
// return IOHLCV[]

ticksToTickChart(tradedata: TradeTick[], numberOfTicks = 5)
// return IOHLCV[]

batchTradeToExtCandle(tradedata: Trade[], interval = 60, includeOpenCandle = false)
// return ExtIOHLCV[]
```

\*\* includeOpenCandle allow non-complete candles in the result, useful for not normalized input data
Expand All @@ -66,17 +74,44 @@ export type IOHLCV = {
volume: number,
};

export type OHLCV = [number, number, number, number, number, number];
// OpenTime, Open, High, Low, Close, Volume
export type ExtIOHLCV = {
time: number,
open: number,
high: number,
low: number,
close: number,
volume: number,
buyVolume: number,
tx: number,
buyTx: number,
};

export type IntervalFunction = (timeStamp: number) => number;
// return the OpenTime for the given timestamp
export const TradeSide = {
BUY: 0,
SELL: 1,
};

export type TradeTick = {
price: number,
quantity: number,
time: number,
price: number;
quantity: number;
time: number;
};

export type Trade = {
price: number;
quantity: number;
time: number;
side: number;
};

export enum OHLCVField {
TIME = 0,
OPEN = 1,
HIGH = 2,
LOW = 3,
CLOSE = 4,
VOLUME = 5,
}
```

## Examples
Expand Down Expand Up @@ -113,10 +148,10 @@ const newFrame = 120; // 120 seconds
const link_btc_2m = batchCandleJSON(link_btc_1m, baseFrame, newFrame);
```

**Tick Chart:**
**Extended Candles from Trades:**

```javascript
import { ticksToTickChart, TradeTick } from "candlestick-convert";
import { batchTradeToExtCandle, Trade } from "candlestick-convert";

const adabnb_trades = [
{
Expand All @@ -140,14 +175,44 @@ const adabnb_trades = [
price: "0.002248",
tradeId: "1221274",
},
// ... more data
];

const filtered_adabnb_trades: TradeTick[] = adabnb_trades.map((trade: any) => ({
const filtered_adabnb_trades: Trade[] = adabnb_trades.map((trade: any) => ({
time: trade.time,
quantity: trade.quantity,
price: trade.price,
side: trade.side === "buy" ? 0 : 1,
}));

const batchSize = 2; // Every TickCandle consist 2 trade
const tickChart = ticksToTickChart(filtered_adabnb_trades, batchSize);
// 1 minute (60 second) Candles
const candles1m = batchTradeToExtCandle(filtered_adabnb_trades, 60);

/* Result:
[
{
time: 1564502580000, // 2019-07-30T16:03:00.000Z
open: 0.00224,
high: 0.00224,
low: 0.00224,
close: 0.00224,
volume: 4458,
buyVolume: 0,
tx: 1,
buyTx: 0,
},
{
time: 1564503120000,
open: 0.00224,
high: 0.002248,
low: 0.002242,
close: 0.002248,
volume: 4949,
buyVolume: 103,
tx: 3,
buyTx: 2,
}
]


```
20 changes: 13 additions & 7 deletions __tests__/Candlestick.test.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,12 @@
"use strict";

import CConverter, { IOHLCV, batchCandleArray, OHLCV } from "../src/index";
import {
OHLCV,
batchCandlesWithCustomInterval,
batchCandles,
IOHLCV,
batchCandlesJSON,
} from "../src";

// From Binance
const btc_usdt_1m: OHLCV[] = [
Expand Down Expand Up @@ -50,7 +56,7 @@ test("Candle Convert array CustomInterval", () => {
}
};

let result = CConverter.arrayCustomInterval(
let result = batchCandlesWithCustomInterval(
btc_usdt_1m,
intervalFunction,
true
Expand All @@ -66,15 +72,15 @@ test("Candle Convert array CustomInterval", () => {
});

test("Candle Convert 1m to 5m", () => {
const result = batchCandleArray(btc_usdt_1m, 60, 5 * 60);
const result = batchCandles(btc_usdt_1m, 60, 5 * 60);

expect(result[4]).toEqual(btc_usdt_5m[0]);

expect(result).toHaveLength(6);
});

test("Candle Convert 1m to 5m#withOpenCandles", () => {
const result = batchCandleArray(btc_usdt_1m, 60, 5 * 60, true);
const result = batchCandles(btc_usdt_1m, 60, 5 * 60, true);

expect(result[4]).toEqual(btc_usdt_5m[0]);

Expand All @@ -90,7 +96,7 @@ test("Candle Convert 1m to 5m with missing values", () => {
incompleteArray.splice(13, 1);
incompleteArray.splice(22, 1);

const result = batchCandleArray(incompleteArray, 60, 5 * 60);
const result = batchCandles(incompleteArray, 60, 5 * 60);

expect(incompleteArray.length).toBeLessThan(btc_usdt_1m.length);
expect(result).toHaveLength(6);
Expand Down Expand Up @@ -124,7 +130,7 @@ const candle4h: OHLCV[] = [
];

test("Candle Convert 1Day", () => {
let result = batchCandleArray(candle4h, 4 * 60 * 60, 24 * 60 * 60);
let result = batchCandles(candle4h, 4 * 60 * 60, 24 * 60 * 60);

expect(result[0]).toEqual([
1588204800000, 215.42830423, 227.13385486, 202.0834746, 206.35436145,
Expand Down Expand Up @@ -200,7 +206,7 @@ const link_btc_1m: Array<IOHLCV> = [
];

test("Candle Convert json 2 min", () => {
let result = CConverter.json(link_btc_1m, 60, 120);
let result = batchCandlesJSON(link_btc_1m, 60, 120);

expect(result[0]).toEqual({
close: 0.00024828,
Expand Down
14 changes: 7 additions & 7 deletions __tests__/Tickdata.test.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
"use strict";

import Converter, { Trade } from "../src/index";
import { batchTicksToCandle, ticksToTickChart, TradeTick } from "../src";

const adabnb_trades = [
{
Expand Down Expand Up @@ -362,14 +362,14 @@ const adabnb_trades = [
},
];

const filtered_adabnb_trades: Trade[] = adabnb_trades.map((trade: any) => ({
const filtered_adabnb_trades: TradeTick[] = adabnb_trades.map((trade: any) => ({
time: trade.time,
quantity: trade.quantity,
price: trade.price,
}));

test("Tick Chart Convert 5 tick", () => {
let result = Converter.tick_chart(filtered_adabnb_trades, 5);
let result = ticksToTickChart(filtered_adabnb_trades, 5);

expect(result[0]).toEqual({
time: 1564503137490,
Expand All @@ -382,7 +382,7 @@ test("Tick Chart Convert 5 tick", () => {
});

test("Trades convert to Candlestick", () => {
let result = Converter.trade_to_candle(filtered_adabnb_trades, 60);
let result = batchTicksToCandle(filtered_adabnb_trades, 60);

expect(result[0]).toEqual({
time: 1564502580000, // 2019-07-30T16:03:00.000Z
Expand All @@ -400,11 +400,11 @@ test("Trades convert to Candlestick", () => {
});

test("Trades convert to Candlestick, with filter", () => {
let result = Converter.trade_to_candle(
let result = batchTicksToCandle(
filtered_adabnb_trades,
60,
false,
(trade: Trade) => {
(trade: TradeTick) => {
return trade.quantity > 100;
}
);
Expand All @@ -425,7 +425,7 @@ test("Trades convert to Candlestick, with filter", () => {
});

test("Trades convert to Candlestick – including open candle", () => {
let result = Converter.trade_to_candle(filtered_adabnb_trades, 60, true);
let result = batchTicksToCandle(filtered_adabnb_trades, 60, true);

// 27+1 candles, including open (unfinished) candle
expect(result.length).toBe(28);
Expand Down
Loading
Loading