iq-option-client 1.3.3 → 1.3.4
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/LICENSE +1 -0
- package/README.md +73 -2
- package/dist/bin/MultiMarketExample.d.ts +1 -0
- package/dist/bin/MultiMarketExample.js +204 -0
- package/dist/bin/QuickExample.d.ts +1 -0
- package/dist/bin/QuickExample.js +139 -0
- package/dist/bin/TestGetCandles.d.ts +1 -0
- package/dist/bin/TestGetCandles.js +211 -0
- package/dist/lib/Service/IQOptionService/Helper/CandleValidator.d.ts +21 -0
- package/dist/lib/Service/IQOptionService/Helper/CandleValidator.js +110 -0
- package/dist/lib/Service/IQOptionService/Helper/CurrencyValidator.d.ts +21 -0
- package/dist/lib/Service/IQOptionService/Helper/CurrencyValidator.js +127 -0
- package/dist/lib/Service/IQOptionService/Helper/index.d.ts +2 -0
- package/dist/lib/Service/IQOptionService/Helper/index.js +3 -1
- package/dist/lib/Service/IQOptionService/IQOptionApi.d.ts +12 -0
- package/dist/lib/Service/IQOptionService/IQOptionApi.js +84 -1
- package/dist/lib/Service/IQOptionService/IQOptionStreamCandleGenerated.js +13 -4
- package/dist/lib/Service/IQOptionService/IQOptionWs.js +2 -1
- package/dist/lib/Service/IQOptionService/Model/IQOptionAction.d.ts +4 -1
- package/dist/lib/Service/IQOptionService/Model/IQOptionAction.js +4 -1
- package/dist/lib/Service/IQOptionService/Model/IQOptionCurrencyUpdated.d.ts +77 -0
- package/dist/lib/Service/IQOptionService/Model/IQOptionCurrencyUpdated.js +11 -0
- package/dist/lib/Service/IQOptionService/Model/index.d.ts +1 -0
- package/dist/lib/Service/IQOptionService/Model/index.js +2 -1
- package/dist/lib/Service/IQOptionService/Repository/IQOptionRepository.d.ts +4 -0
- package/dist/lib/Service/IQOptionService/Repository/WebSocketRepository.d.ts +13 -0
- package/dist/lib/Service/IQOptionService/Repository/WebSocketRepository.js +40 -1
- package/package.json +4 -2
package/LICENSE
CHANGED
package/README.md
CHANGED
|
@@ -11,6 +11,7 @@ A robust TypeScript client library for interacting with the **IQ Option WebSocke
|
|
|
11
11
|
- 🔐 **Secure Authentication** - Environment-based credential management
|
|
12
12
|
- 📊 **Real-time Data Streaming** - WebSocket-based candle data, trader sentiment, and option events
|
|
13
13
|
- 📈 **Order Management** - Binary and digital option order execution
|
|
14
|
+
- 📜 **Historical Data** - Retrieve historical candles for backtesting and analysis
|
|
14
15
|
- 🎯 **Type-Safe** - Full TypeScript support with comprehensive type definitions
|
|
15
16
|
- 🏗️ **SOLID Architecture** - Clean code with design patterns (Strategy, Repository, Factory, Command, Builder)
|
|
16
17
|
- 🔄 **Error Handling** - Comprehensive error handling with retry logic
|
|
@@ -36,7 +37,7 @@ yarn add iq-option-client
|
|
|
36
37
|
|
|
37
38
|
1. **Install the package:**
|
|
38
39
|
```bash
|
|
39
|
-
npm install iq
|
|
40
|
+
npm install iq-option-client
|
|
40
41
|
```
|
|
41
42
|
|
|
42
43
|
2. **Create a `.env` file** (or set environment variables):
|
|
@@ -98,6 +99,16 @@ const initData = await api.getInitializationData();
|
|
|
98
99
|
// Get digital option instruments
|
|
99
100
|
const instruments = await api.getDigitalOptionInstruments(IQOptionMarket.EURUSD);
|
|
100
101
|
|
|
102
|
+
// Get historical candles
|
|
103
|
+
const historicalCandles = await api.getCandles(
|
|
104
|
+
activeId, // Market/Active ID (e.g., 1 for EURUSD)
|
|
105
|
+
size, // Candle size in seconds (60 = 1 min, 120 = 2 min)
|
|
106
|
+
fromId, // Starting candle ID
|
|
107
|
+
toId, // Ending candle ID
|
|
108
|
+
true, // split_normalization (optional, default: true)
|
|
109
|
+
true // only_closed (optional, default: true)
|
|
110
|
+
);
|
|
111
|
+
|
|
101
112
|
// Send binary order
|
|
102
113
|
await api.sendOrderBinary(
|
|
103
114
|
market,
|
|
@@ -197,6 +208,39 @@ alertsStream.on('data', (alert) => {
|
|
|
197
208
|
});
|
|
198
209
|
```
|
|
199
210
|
|
|
211
|
+
#### Get Historical Candles
|
|
212
|
+
|
|
213
|
+
```typescript
|
|
214
|
+
import { IQOptionApi } from 'iq-option-client';
|
|
215
|
+
|
|
216
|
+
// Get historical candles
|
|
217
|
+
const candles = await api.getCandles(
|
|
218
|
+
activeId, // Market/Active ID (e.g., 1 for EURUSD, 76, 1874, etc.)
|
|
219
|
+
size, // Candle size in seconds (60 = 1 min, 120 = 2 min)
|
|
220
|
+
fromId, // Starting candle ID
|
|
221
|
+
toId, // Ending candle ID
|
|
222
|
+
true, // split_normalization (optional, default: true)
|
|
223
|
+
true // only_closed (optional, default: true)
|
|
224
|
+
);
|
|
225
|
+
|
|
226
|
+
console.log(`Received ${candles.length} historical candles`);
|
|
227
|
+
candles.forEach(candle => {
|
|
228
|
+
console.log('Candle:', {
|
|
229
|
+
id: candle.id,
|
|
230
|
+
open: candle.open,
|
|
231
|
+
close: candle.close,
|
|
232
|
+
high: candle.max,
|
|
233
|
+
low: candle.min,
|
|
234
|
+
timestamp: new Date(candle.from * 1000)
|
|
235
|
+
});
|
|
236
|
+
});
|
|
237
|
+
```
|
|
238
|
+
|
|
239
|
+
**Note:** To get real candle IDs, you can:
|
|
240
|
+
1. Get them from the candle stream (each candle has an `id` field)
|
|
241
|
+
2. Calculate them based on timestamps and candle size
|
|
242
|
+
3. Use IDs from previous API responses
|
|
243
|
+
|
|
200
244
|
### Advanced Usage
|
|
201
245
|
|
|
202
246
|
#### Using Design Patterns
|
|
@@ -351,6 +395,9 @@ await api.sendOrderBinary(
|
|
|
351
395
|
- `IQOptionStreamOptionClose` - Option close events stream
|
|
352
396
|
- `IQOptionStreamOptionTradersSentiment` - Traders sentiment stream
|
|
353
397
|
- `IQOptionStreamUserAlerts` - User alerts stream
|
|
398
|
+
- `WebSocketRepository` - Repository for WebSocket operations
|
|
399
|
+
- `BinaryOrderStrategy` - Strategy for binary orders
|
|
400
|
+
- `DigitalOrderStrategy` - Strategy for digital orders
|
|
354
401
|
|
|
355
402
|
### Helper Functions
|
|
356
403
|
|
|
@@ -358,6 +405,8 @@ await api.sendOrderBinary(
|
|
|
358
405
|
- `LoggerFactory` - Create logger instances
|
|
359
406
|
- `RequestIdGenerator` - Generate unique request IDs
|
|
360
407
|
- `InputValidator` - Validate input parameters
|
|
408
|
+
- `CandleValidator` - Validate candle data structure
|
|
409
|
+
- `CurrencyValidator` - Validate currency update messages
|
|
361
410
|
|
|
362
411
|
## 🔧 Configuration
|
|
363
412
|
|
|
@@ -393,6 +442,12 @@ npm run test:coverage
|
|
|
393
442
|
|
|
394
443
|
# Run sample application
|
|
395
444
|
npm run sample:iqoption
|
|
445
|
+
|
|
446
|
+
# Run quick example (3 markets)
|
|
447
|
+
npm run sample:quick
|
|
448
|
+
|
|
449
|
+
# Test historical candles functionality
|
|
450
|
+
npm run test:candles
|
|
396
451
|
```
|
|
397
452
|
|
|
398
453
|
**Note:** Tests require valid IQ Option credentials set in environment variables:
|
|
@@ -489,9 +544,25 @@ const candleStream = new IQOptionStreamCandleGenerated(
|
|
|
489
544
|
);
|
|
490
545
|
await candleStream.startStream();
|
|
491
546
|
|
|
492
|
-
candleStream.on('data', (candle) => {
|
|
547
|
+
candleStream.on('data', async (candle) => {
|
|
493
548
|
// Perform technical analysis
|
|
494
549
|
logger.debug('New candle received', { candle });
|
|
550
|
+
|
|
551
|
+
// Get historical candles for backtesting
|
|
552
|
+
try {
|
|
553
|
+
const historicalCandles = await api.getCandles(
|
|
554
|
+
candle.active_id,
|
|
555
|
+
candle.size,
|
|
556
|
+
candle.id - 100, // Last 100 candles
|
|
557
|
+
candle.id,
|
|
558
|
+
true,
|
|
559
|
+
true
|
|
560
|
+
);
|
|
561
|
+
|
|
562
|
+
logger.info(`Retrieved ${historicalCandles.length} historical candles for analysis`);
|
|
563
|
+
} catch (error) {
|
|
564
|
+
logger.error('Failed to get historical candles', {}, error);
|
|
565
|
+
}
|
|
495
566
|
});
|
|
496
567
|
```
|
|
497
568
|
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1,204 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
/*
|
|
4
|
+
* Copyright (C) 2020 Wellington Rocha
|
|
5
|
+
* All Rights Reserved.
|
|
6
|
+
*
|
|
7
|
+
* Unauthorized copying of this file, via any medium is strictly prohibited.
|
|
8
|
+
*
|
|
9
|
+
* Proprietary and confidential.
|
|
10
|
+
*/
|
|
11
|
+
// Load environment variables from .env file if it exists
|
|
12
|
+
try {
|
|
13
|
+
require("dotenv").config();
|
|
14
|
+
}
|
|
15
|
+
catch (e) {
|
|
16
|
+
// dotenv is optional, continue without it
|
|
17
|
+
}
|
|
18
|
+
const Core = require("../lib");
|
|
19
|
+
const Logger_1 = require("../lib/Helper/Logger");
|
|
20
|
+
const IQOptionExpired_1 = require("../lib/Service/IQOptionService/IQOptionExpired");
|
|
21
|
+
// Get credentials from environment variables
|
|
22
|
+
const email = process.env.IQ_OPTION_EMAIL;
|
|
23
|
+
const password = process.env.IQ_OPTION_PASSWORD;
|
|
24
|
+
if (!email || !password) {
|
|
25
|
+
// eslint-disable-next-line no-console
|
|
26
|
+
console.error("Error: IQ_OPTION_EMAIL and IQ_OPTION_PASSWORD environment variables are required");
|
|
27
|
+
process.exit(1);
|
|
28
|
+
}
|
|
29
|
+
const logger = Logger_1.LoggerFactory.getDefault();
|
|
30
|
+
const iqOptionApi = new Core.IQOptionApi(email, password);
|
|
31
|
+
// Armazenar candles de múltiplos mercados
|
|
32
|
+
const marketCandles = new Map();
|
|
33
|
+
iqOptionApi
|
|
34
|
+
.connectAsync()
|
|
35
|
+
.then(async (profile) => {
|
|
36
|
+
logger.info("Connected successfully", { operation: "connect", userId: profile.user_id });
|
|
37
|
+
const testBalance = profile.balances.find(b => b.type === Core.IQOptionCurrencyType.TEST);
|
|
38
|
+
if (!testBalance) {
|
|
39
|
+
throw new Error("Test balance not found");
|
|
40
|
+
}
|
|
41
|
+
// ============================================
|
|
42
|
+
// EXEMPLO 1: Múltiplos Streams de Candles
|
|
43
|
+
// ============================================
|
|
44
|
+
const markets = [
|
|
45
|
+
Core.IQOptionMarket.EURUSD,
|
|
46
|
+
Core.IQOptionMarket.GBPUSD,
|
|
47
|
+
Core.IQOptionMarket.USDJPY,
|
|
48
|
+
];
|
|
49
|
+
const time = Core.IQOptionTime.ONE_MINUTE;
|
|
50
|
+
// Criar e iniciar streams para múltiplos mercados
|
|
51
|
+
const candleStreams = markets.map(market => {
|
|
52
|
+
const stream = new Core.IQOptionStreamCandleGenerated(iqOptionApi.getIQOptionWs(), market, time);
|
|
53
|
+
// Inicializar storage para este mercado
|
|
54
|
+
marketCandles.set(market, {
|
|
55
|
+
open: [],
|
|
56
|
+
close: [],
|
|
57
|
+
high: [],
|
|
58
|
+
low: [],
|
|
59
|
+
});
|
|
60
|
+
// Listener para cada mercado
|
|
61
|
+
stream.on("data", (data) => {
|
|
62
|
+
const candles = marketCandles.get(market);
|
|
63
|
+
candles.open.unshift(data.open);
|
|
64
|
+
candles.close.unshift(data.close);
|
|
65
|
+
candles.high.unshift(data.max);
|
|
66
|
+
candles.low.unshift(data.min);
|
|
67
|
+
// Manter apenas últimos 100 candles
|
|
68
|
+
candles.open = candles.open.slice(0, 100);
|
|
69
|
+
candles.close = candles.close.slice(0, 100);
|
|
70
|
+
candles.high = candles.high.slice(0, 100);
|
|
71
|
+
candles.low = candles.low.slice(0, 100);
|
|
72
|
+
logger.debug(`Candle received for ${market}`, {
|
|
73
|
+
market,
|
|
74
|
+
metadata: {
|
|
75
|
+
open: data.open,
|
|
76
|
+
close: data.close,
|
|
77
|
+
count: candles.close.length,
|
|
78
|
+
},
|
|
79
|
+
});
|
|
80
|
+
});
|
|
81
|
+
return stream;
|
|
82
|
+
});
|
|
83
|
+
// Iniciar todos os streams em paralelo
|
|
84
|
+
await Promise.all(candleStreams.map(stream => stream.startStream()));
|
|
85
|
+
logger.info("Multiple candle streams started", {
|
|
86
|
+
metadata: {
|
|
87
|
+
markets: markets.length,
|
|
88
|
+
marketList: markets,
|
|
89
|
+
},
|
|
90
|
+
});
|
|
91
|
+
// ============================================
|
|
92
|
+
// EXEMPLO 2: Múltiplos Streams de Sentiment
|
|
93
|
+
// ============================================
|
|
94
|
+
const sentimentStreams = markets.map(market => {
|
|
95
|
+
const stream = new Core.IQOptionStreamOptionTradersSentiment(iqOptionApi.getIQOptionWs(), market);
|
|
96
|
+
stream.on("data", (data) => {
|
|
97
|
+
logger.info(`Sentiment for ${market}`, {
|
|
98
|
+
market,
|
|
99
|
+
metadata: { value: data.value },
|
|
100
|
+
});
|
|
101
|
+
// Lógica de trading baseada em sentiment para cada mercado
|
|
102
|
+
if (data.value > 0.8) {
|
|
103
|
+
logger.info(`Strong BUY signal for ${market}`, { market });
|
|
104
|
+
}
|
|
105
|
+
else if (data.value < 0.22) {
|
|
106
|
+
logger.info(`Strong SELL signal for ${market}`, { market });
|
|
107
|
+
}
|
|
108
|
+
});
|
|
109
|
+
return stream;
|
|
110
|
+
});
|
|
111
|
+
await Promise.all(sentimentStreams.map(stream => stream.startStream()));
|
|
112
|
+
logger.info("Multiple sentiment streams started", {
|
|
113
|
+
metadata: { markets: markets.length },
|
|
114
|
+
});
|
|
115
|
+
// ============================================
|
|
116
|
+
// EXEMPLO 3: Enviar Ordens em Múltiplos Mercados
|
|
117
|
+
// ============================================
|
|
118
|
+
// Nota: O rate limiter atual (maxConcurrent: 1) faz as ordens serem sequenciais
|
|
119
|
+
// Mas você pode enviar para diferentes mercados
|
|
120
|
+
// Exemplo: Enviar ordem em EURUSD
|
|
121
|
+
setTimeout(async () => {
|
|
122
|
+
try {
|
|
123
|
+
const result1 = await iqOptionApi.sendOrderBinary(Core.IQOptionMarket.EURUSD_OTC, Core.IQOptionModel.BUY, (0, IQOptionExpired_1.iqOptionExpired)(1), testBalance.id, 90, 10);
|
|
124
|
+
logger.info("Order 1 placed", { market: "EURUSD", metadata: { result: result1 } });
|
|
125
|
+
}
|
|
126
|
+
catch (error) {
|
|
127
|
+
const err = error instanceof Error ? error : new Error(String(error));
|
|
128
|
+
logger.error("Failed to place order 1", { market: "EURUSD" }, err);
|
|
129
|
+
}
|
|
130
|
+
}, 5000);
|
|
131
|
+
// Exemplo: Enviar ordem em GBPUSD (após a primeira)
|
|
132
|
+
setTimeout(async () => {
|
|
133
|
+
try {
|
|
134
|
+
const result2 = await iqOptionApi.sendOrderBinary(Core.IQOptionMarket.GBPUSD_OTC, Core.IQOptionModel.BUY, (0, IQOptionExpired_1.iqOptionExpired)(1), testBalance.id, 90, 10);
|
|
135
|
+
logger.info("Order 2 placed", { market: "GBPUSD", metadata: { result: result2 } });
|
|
136
|
+
}
|
|
137
|
+
catch (error) {
|
|
138
|
+
const err = error instanceof Error ? error : new Error(String(error));
|
|
139
|
+
logger.error("Failed to place order 2", { market: "GBPUSD" }, err);
|
|
140
|
+
}
|
|
141
|
+
}, 7000);
|
|
142
|
+
// ============================================
|
|
143
|
+
// EXEMPLO 4: Monitorar Múltiplas Moedas (Balances)
|
|
144
|
+
// ============================================
|
|
145
|
+
profile.balances.forEach(balance => {
|
|
146
|
+
logger.info("Balance available", {
|
|
147
|
+
metadata: {
|
|
148
|
+
currency: balance.currency,
|
|
149
|
+
type: balance.type,
|
|
150
|
+
amount: balance.amount,
|
|
151
|
+
id: balance.id,
|
|
152
|
+
},
|
|
153
|
+
});
|
|
154
|
+
});
|
|
155
|
+
// ============================================
|
|
156
|
+
// EXEMPLO 5: Stream de Option Close para Todos os Mercados
|
|
157
|
+
// ============================================
|
|
158
|
+
const optionCloseStream = new Core.IQOptionStreamOptionClose(iqOptionApi.getIQOptionWs());
|
|
159
|
+
await optionCloseStream.startStream();
|
|
160
|
+
optionCloseStream.on("data", (data) => {
|
|
161
|
+
logger.info("Option closed", {
|
|
162
|
+
metadata: {
|
|
163
|
+
optionId: data.option_id,
|
|
164
|
+
win: data.win,
|
|
165
|
+
profit: data.profit,
|
|
166
|
+
},
|
|
167
|
+
});
|
|
168
|
+
});
|
|
169
|
+
logger.info("Option close stream started for all markets");
|
|
170
|
+
// ============================================
|
|
171
|
+
// EXEMPLO 6: Processar Dados de Múltiplos Mercados
|
|
172
|
+
// ============================================
|
|
173
|
+
setInterval(() => {
|
|
174
|
+
markets.forEach(market => {
|
|
175
|
+
const candles = marketCandles.get(market);
|
|
176
|
+
if (candles && candles.close.length > 20) {
|
|
177
|
+
// Calcular média móvel simples para cada mercado
|
|
178
|
+
const sma = candles.close
|
|
179
|
+
.slice(0, 20)
|
|
180
|
+
.reduce((sum, val) => sum + val, 0) / 20;
|
|
181
|
+
logger.debug(`SMA(20) for ${market}`, {
|
|
182
|
+
market,
|
|
183
|
+
metadata: { sma },
|
|
184
|
+
});
|
|
185
|
+
}
|
|
186
|
+
});
|
|
187
|
+
}, 60000); // A cada minuto
|
|
188
|
+
logger.info("Multi-market monitoring started", {
|
|
189
|
+
metadata: {
|
|
190
|
+
markets: markets.length,
|
|
191
|
+
streams: {
|
|
192
|
+
candles: candleStreams.length,
|
|
193
|
+
sentiment: sentimentStreams.length,
|
|
194
|
+
optionClose: 1,
|
|
195
|
+
},
|
|
196
|
+
},
|
|
197
|
+
});
|
|
198
|
+
})
|
|
199
|
+
.catch((e) => {
|
|
200
|
+
const error = e instanceof Error ? e : new Error(String(e));
|
|
201
|
+
logger.error("Application error", { operation: "main" }, error);
|
|
202
|
+
process.exit(1);
|
|
203
|
+
});
|
|
204
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiTXVsdGlNYXJrZXRFeGFtcGxlLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vc3JjL2Jpbi9NdWx0aU1hcmtldEV4YW1wbGUudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6Ijs7QUFBQTs7Ozs7OztHQU9HO0FBQ0gseURBQXlEO0FBQ3pELElBQUksQ0FBQztJQUNELE9BQU8sQ0FBQyxRQUFRLENBQUMsQ0FBQyxNQUFNLEVBQUUsQ0FBQztBQUMvQixDQUFDO0FBQUMsT0FBTyxDQUFDLEVBQUUsQ0FBQztJQUNULDBDQUEwQztBQUM5QyxDQUFDO0FBRUQsK0JBQStCO0FBQy9CLGlEQUFxRDtBQUNyRCxvRkFBaUY7QUFFakYsNkNBQTZDO0FBQzdDLE1BQU0sS0FBSyxHQUFHLE9BQU8sQ0FBQyxHQUFHLENBQUMsZUFBZSxDQUFDO0FBQzFDLE1BQU0sUUFBUSxHQUFHLE9BQU8sQ0FBQyxHQUFHLENBQUMsa0JBQWtCLENBQUM7QUFFaEQsSUFBSSxDQUFDLEtBQUssSUFBSSxDQUFDLFFBQVEsRUFBRSxDQUFDO0lBQ3RCLHNDQUFzQztJQUN0QyxPQUFPLENBQUMsS0FBSyxDQUFDLGtGQUFrRixDQUFDLENBQUM7SUFDbEcsT0FBTyxDQUFDLElBQUksQ0FBQyxDQUFDLENBQUMsQ0FBQztBQUNwQixDQUFDO0FBRUQsTUFBTSxNQUFNLEdBQUcsc0JBQWEsQ0FBQyxVQUFVLEVBQUUsQ0FBQztBQUMxQyxNQUFNLFdBQVcsR0FBRyxJQUFJLElBQUksQ0FBQyxXQUFXLENBQUMsS0FBSyxFQUFFLFFBQVEsQ0FBQyxDQUFDO0FBRTFELDBDQUEwQztBQUMxQyxNQUFNLGFBQWEsR0FLZCxJQUFJLEdBQUcsRUFBRSxDQUFDO0FBRWYsV0FBVztLQUNOLFlBQVksRUFBRTtLQUNkLElBQUksQ0FBQyxLQUFLLEVBQUUsT0FBTyxFQUFFLEVBQUU7SUFDcEIsTUFBTSxDQUFDLElBQUksQ0FBQyx3QkFBd0IsRUFBRSxFQUFFLFNBQVMsRUFBRSxTQUFTLEVBQUUsTUFBTSxFQUFF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
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1,139 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
/*
|
|
4
|
+
* Copyright (C) 2020 Wellington Rocha
|
|
5
|
+
* All Rights Reserved.
|
|
6
|
+
*
|
|
7
|
+
* Unauthorized copying of this file, via any medium is strictly prohibited.
|
|
8
|
+
*
|
|
9
|
+
* Proprietary and confidential.
|
|
10
|
+
*/
|
|
11
|
+
// Load environment variables from .env file if it exists
|
|
12
|
+
try {
|
|
13
|
+
require("dotenv").config();
|
|
14
|
+
}
|
|
15
|
+
catch (e) {
|
|
16
|
+
// dotenv is optional, continue without it
|
|
17
|
+
}
|
|
18
|
+
const Core = require("../lib");
|
|
19
|
+
const Logger_1 = require("../lib/Helper/Logger");
|
|
20
|
+
// Get credentials from environment variables
|
|
21
|
+
const email = process.env.IQ_OPTION_EMAIL;
|
|
22
|
+
const password = process.env.IQ_OPTION_PASSWORD;
|
|
23
|
+
if (!email || !password) {
|
|
24
|
+
// eslint-disable-next-line no-console
|
|
25
|
+
console.error("Error: IQ_OPTION_EMAIL and IQ_OPTION_PASSWORD environment variables are required");
|
|
26
|
+
process.exit(1);
|
|
27
|
+
}
|
|
28
|
+
const logger = Logger_1.LoggerFactory.getDefault();
|
|
29
|
+
const api = new Core.IQOptionApi(email, password);
|
|
30
|
+
logger.info("=== IQ Option Client - Exemplo Rápido ===");
|
|
31
|
+
api.connectAsync()
|
|
32
|
+
.then(async (profile) => {
|
|
33
|
+
logger.info("✅ Conectado com sucesso!", {
|
|
34
|
+
metadata: {
|
|
35
|
+
userId: profile.user_id,
|
|
36
|
+
email: profile.email,
|
|
37
|
+
balance: profile.balance,
|
|
38
|
+
},
|
|
39
|
+
});
|
|
40
|
+
// Mostrar balances disponíveis
|
|
41
|
+
logger.info("💰 Balances disponíveis:", {
|
|
42
|
+
metadata: {
|
|
43
|
+
count: profile.balances.length,
|
|
44
|
+
balances: profile.balances.map(b => ({
|
|
45
|
+
currency: b.currency,
|
|
46
|
+
type: b.type,
|
|
47
|
+
amount: b.amount,
|
|
48
|
+
})),
|
|
49
|
+
},
|
|
50
|
+
});
|
|
51
|
+
// Exemplo 1: Obter dados de inicialização
|
|
52
|
+
logger.info("📊 Obtendo dados de inicialização...");
|
|
53
|
+
try {
|
|
54
|
+
const initData = await api.getInitializationData();
|
|
55
|
+
logger.info("✅ Dados de inicialização obtidos", {
|
|
56
|
+
metadata: {
|
|
57
|
+
hasTurbo: !!initData.turbo,
|
|
58
|
+
hasBinary: !!initData.binary,
|
|
59
|
+
},
|
|
60
|
+
});
|
|
61
|
+
}
|
|
62
|
+
catch (error) {
|
|
63
|
+
const err = error instanceof Error ? error : new Error(String(error));
|
|
64
|
+
logger.error("❌ Erro ao obter dados de inicialização", {}, err);
|
|
65
|
+
}
|
|
66
|
+
// Exemplo 2: Stream de candles para 3 mercados simultaneamente
|
|
67
|
+
logger.info("📈 Iniciando streams de candles para 3 mercados simultaneamente...");
|
|
68
|
+
const markets = [
|
|
69
|
+
Core.IQOptionMarket.EURUSD,
|
|
70
|
+
Core.IQOptionMarket.GBPUSD,
|
|
71
|
+
Core.IQOptionMarket.USDJPY,
|
|
72
|
+
];
|
|
73
|
+
const time = Core.IQOptionTime.ONE_MINUTE;
|
|
74
|
+
// Contador de candles por mercado
|
|
75
|
+
const candleCounts = new Map();
|
|
76
|
+
markets.forEach(market => candleCounts.set(market, 0));
|
|
77
|
+
// Criar streams para cada mercado
|
|
78
|
+
const candleStreams = markets.map(market => {
|
|
79
|
+
const stream = new Core.IQOptionStreamCandleGenerated(api.getIQOptionWs(), market, time);
|
|
80
|
+
stream.on("data", (candle) => {
|
|
81
|
+
const count = (candleCounts.get(market) || 0) + 1;
|
|
82
|
+
candleCounts.set(market, count);
|
|
83
|
+
logger.info(`🕯️ Candle #${count} recebido para ${market}`, {
|
|
84
|
+
market,
|
|
85
|
+
metadata: {
|
|
86
|
+
open: candle.open,
|
|
87
|
+
close: candle.close,
|
|
88
|
+
high: candle.max,
|
|
89
|
+
low: candle.min,
|
|
90
|
+
id: candle.id,
|
|
91
|
+
},
|
|
92
|
+
});
|
|
93
|
+
// Verificar se todos os mercados receberam pelo menos 2 candles
|
|
94
|
+
const allReceived = markets.every(m => (candleCounts.get(m) || 0) >= 2);
|
|
95
|
+
if (allReceived) {
|
|
96
|
+
logger.info("✅ Exemplo concluído! Todos os mercados receberam candles.");
|
|
97
|
+
logger.info("📊 Resumo:", {
|
|
98
|
+
metadata: {
|
|
99
|
+
candles: Array.from(candleCounts.entries()).map(([m, c]) => ({
|
|
100
|
+
market: m,
|
|
101
|
+
count: c,
|
|
102
|
+
})),
|
|
103
|
+
},
|
|
104
|
+
});
|
|
105
|
+
candleStreams.forEach(s => s.destroy());
|
|
106
|
+
process.exit(0);
|
|
107
|
+
}
|
|
108
|
+
});
|
|
109
|
+
return stream;
|
|
110
|
+
});
|
|
111
|
+
// Iniciar todos os streams em paralelo
|
|
112
|
+
await Promise.all(candleStreams.map(stream => stream.startStream()));
|
|
113
|
+
logger.info("✅ Streams de candles iniciados para 3 mercados", {
|
|
114
|
+
metadata: {
|
|
115
|
+
markets: markets.map(m => m),
|
|
116
|
+
time: "1 minuto",
|
|
117
|
+
},
|
|
118
|
+
});
|
|
119
|
+
// Timeout de segurança (60 segundos)
|
|
120
|
+
setTimeout(() => {
|
|
121
|
+
logger.warn("⏱️ Timeout - encerrando exemplo");
|
|
122
|
+
logger.info("📊 Resumo final:", {
|
|
123
|
+
metadata: {
|
|
124
|
+
candles: Array.from(candleCounts.entries()).map(([m, c]) => ({
|
|
125
|
+
market: m,
|
|
126
|
+
count: c,
|
|
127
|
+
})),
|
|
128
|
+
},
|
|
129
|
+
});
|
|
130
|
+
candleStreams.forEach(s => s.destroy());
|
|
131
|
+
process.exit(0);
|
|
132
|
+
}, 60000);
|
|
133
|
+
})
|
|
134
|
+
.catch((e) => {
|
|
135
|
+
const error = e instanceof Error ? e : new Error(String(e));
|
|
136
|
+
logger.error("❌ Erro na aplicação", { operation: "main" }, error);
|
|
137
|
+
process.exit(1);
|
|
138
|
+
});
|
|
139
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiUXVpY2tFeGFtcGxlLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vc3JjL2Jpbi9RdWlja0V4YW1wbGUudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6Ijs7QUFBQTs7Ozs7OztHQU9HO0FBQ0gseURBQXlEO0FBQ3pELElBQUksQ0FBQztJQUNELE9BQU8sQ0FBQyxRQUFRLENBQUMsQ0FBQyxNQUFNLEVBQUUsQ0FBQztBQUMvQixDQUFDO0FBQUMsT0FBTyxDQUFDLEVBQUUsQ0FBQztJQUNULDBDQUEwQztBQUM5QyxDQUFDO0FBRUQsK0JBQStCO0FBQy9CLGlEQUFxRDtBQUVyRCw2Q0FBNkM7QUFDN0MsTUFBTSxLQUFLLEdBQUcsT0FBTyxDQUFDLEdBQUcsQ0FBQyxlQUFlLENBQUM7QUFDMUMsTUFBTSxRQUFRLEdBQUcsT0FBTyxDQUFDLEdBQUcsQ0FBQyxrQkFBa0IsQ0FBQztBQUVoRCxJQUFJLENBQUMsS0FBSyxJQUFJLENBQUMsUUFBUSxFQUFFLENBQUM7SUFDdEIsc0NBQXNDO0lBQ3RDLE9BQU8sQ0FBQyxLQUFLLENBQUMsa0ZBQWtGLENBQUMsQ0FBQztJQUNsRyxPQUFPLENBQUMsSUFBSSxDQUFDLENBQUMsQ0FBQyxDQUFDO0FBQ3BCLENBQUM7QUFFRCxNQUFNLE1BQU0sR0FBRyxzQkFBYSxDQUFDLFVBQVUsRUFBRSxDQUFDO0FBQzFDLE1BQU0sR0FBRyxHQUFHLElBQUksSUFBSSxDQUFDLFdBQVcsQ0FBQyxLQUFLLEVBQUUsUUFBUSxDQUFDLENBQUM7QUFFbEQsTUFBTSxDQUFDLElBQUksQ0FBQywyQ0FBMkMsQ0FBQyxDQUFDO0FBRXpELEdBQUcsQ0FBQyxZQUFZLEVBQUU7S0FDYixJQUFJLENBQUMsS0FBSyxFQUFFLE9BQU8sRUFBRSxFQUFFO0lBQ3BCLE1BQU0sQ0FBQyxJQUFJLENBQUMsMEJBQTBCLEVBQUU7UUFDcEMsUUFBUSxFQUFFO1lBQ04sTUFBTSxFQUFFLE9BQU8sQ0FBQyxPQUFPO1lBQ3ZCLEtBQUssRUFBRSxPQUFPLENB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
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|