hedgequantx 1.2.115 → 1.2.117

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.
Files changed (2) hide show
  1. package/package.json +1 -1
  2. package/src/pages/algo.js +21 -116
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "hedgequantx",
3
- "version": "1.2.115",
3
+ "version": "1.2.117",
4
4
  "description": "Prop Futures Algo Trading CLI - Connect to Topstep, Alpha Futures, and other prop firms",
5
5
  "main": "src/app.js",
6
6
  "bin": {
package/src/pages/algo.js CHANGED
@@ -174,142 +174,47 @@ const selectSymbolMenu = async (service, account) => {
174
174
  ];
175
175
 
176
176
  try {
177
+ const seenIds = new Set();
178
+
177
179
  for (const search of commonSearches) {
178
180
  const result = await service.searchContracts(search, false);
179
181
  if (result.success && result.contracts && result.contracts.length > 0) {
180
182
  for (const contract of result.contracts) {
181
- // ProjectX API returns:
182
- // id: "CON.F.US.ENQ.H26" (contract ID)
183
- // name: "NQH6" (short symbol with month/year)
184
- // description: "E-mini NASDAQ-100: March 2026"
185
-
186
- const contractId = contract.id || contract.contractId;
187
- if (!contractId) continue;
188
-
189
- const existing = availableSymbols.find(s => s.id === contractId);
190
- if (existing) continue;
183
+ // Skip if already added (by contract ID)
184
+ const contractId = contract.id || '';
185
+ if (!contractId || seenIds.has(contractId)) continue;
186
+ seenIds.add(contractId);
191
187
 
192
- // Use 'name' field which contains the symbol code like "NQH6", "ESH6", "MNQH6"
193
- const symbolCode = contract.name || contract.symbol || '';
194
- if (!symbolCode) continue;
195
-
196
- availableSymbols.push({
197
- id: contractId,
198
- name: symbolCode,
199
- symbol: symbolCode,
200
- description: contract.description || '',
201
- tickSize: contract.tickSize,
202
- tickValue: contract.tickValue,
203
- exchange: contract.exchange || 'CME',
204
- activeContract: contract.activeContract || false
205
- });
188
+ // Add the raw contract data from API
189
+ availableSymbols.push(contract);
206
190
  }
207
191
  }
208
192
  }
209
193
  } catch (e) {
210
- // Fallback to static list
211
- }
212
-
213
- for (const micro of microContracts) {
214
- const hasMicro = availableSymbols.some(s =>
215
- (s.symbol && s.symbol.toUpperCase().startsWith(micro.symbol)) ||
216
- (s.name && s.name.toUpperCase().includes(micro.symbol))
217
- );
218
- if (!hasMicro) {
219
- // Add micro contract with front month
220
- availableSymbols.push({
221
- id: `${micro.symbol}${currentMonthCode}${yearCode}`,
222
- name: `${micro.symbol}${currentMonthCode}${yearCode}`,
223
- symbol: `${micro.symbol}${currentMonthCode}${yearCode}`,
224
- description: micro.name,
225
- exchange: 'CME'
226
- });
227
- }
194
+ spinner.fail('Failed to load symbols from API: ' + e.message);
195
+ return;
228
196
  }
229
197
 
230
- // If no symbols found from API, use static list
198
+ // Only use REAL data from API - no mock/static data
231
199
  if (availableSymbols.length === 0) {
232
- spinner.warn('Using default symbol list');
233
- availableSymbols = FUTURES_SYMBOLS.map(s => ({
234
- id: s.value,
235
- name: s.name,
236
- symbol: s.value,
237
- searchText: s.searchText
238
- }));
239
- } else {
240
- spinner.succeed(`Found ${availableSymbols.length} available contracts`);
200
+ spinner.fail('No contracts available from API');
201
+ console.log(chalk.red(' Please check your connection and try again'));
202
+ return;
241
203
  }
242
204
 
243
- console.log();
205
+ spinner.succeed(`Found ${availableSymbols.length} available contracts`);
244
206
 
245
- // Symbol name descriptions
246
- const symbolDescriptions = {
247
- 'NQ': 'E-mini NASDAQ-100',
248
- 'MNQ': 'Micro E-mini NASDAQ-100',
249
- 'ES': 'E-mini S&P 500',
250
- 'MES': 'Micro E-mini S&P 500',
251
- 'YM': 'E-mini Dow Jones',
252
- 'MYM': 'Micro E-mini Dow Jones',
253
- 'RTY': 'E-mini Russell 2000',
254
- 'M2K': 'Micro E-mini Russell 2000',
255
- 'CL': 'Crude Oil WTI',
256
- 'MCL': 'Micro Crude Oil',
257
- 'NG': 'Natural Gas',
258
- 'QG': 'E-mini Natural Gas',
259
- 'QM': 'E-mini Crude Oil',
260
- 'GC': 'Gold',
261
- 'MGC': 'Micro Gold',
262
- 'SI': 'Silver',
263
- 'SIL': 'Micro Silver',
264
- 'HG': 'Copper',
265
- 'PL': 'Platinum',
266
- '6E': 'Euro FX',
267
- 'M6E': 'Micro Euro FX',
268
- '6B': 'British Pound',
269
- '6J': 'Japanese Yen',
270
- '6A': 'Australian Dollar',
271
- '6C': 'Canadian Dollar',
272
- '6M': 'Mexican Peso',
273
- '6S': 'Swiss Franc',
274
- 'ZB': '30-Year T-Bond',
275
- 'ZN': '10-Year T-Note',
276
- 'ZF': '5-Year T-Note',
277
- 'ZT': '2-Year T-Note',
278
- 'ZC': 'Corn',
279
- 'ZS': 'Soybeans',
280
- 'ZW': 'Wheat'
281
- };
207
+ console.log();
282
208
 
283
- // Format symbols for display - show ALL contracts from API
284
- const seenIds = new Set();
209
+ // Format symbols for display - show ALL contracts from API (REAL DATA ONLY)
285
210
  const symbolChoices = [];
286
211
 
287
212
  for (const contract of availableSymbols) {
288
- // Skip duplicates by contract ID
289
- const contractId = contract.id || '';
290
- if (seenIds.has(contractId)) continue;
291
- seenIds.add(contractId);
292
-
293
- // Get the symbol code - API returns 'name' field with code like "NQH6"
294
- const symbolCode = contract.name || contract.symbol || '';
295
- if (!symbolCode) continue;
296
-
297
- // Get description from API or our mapping
298
- let description = '';
299
- if (contract.description) {
300
- // API format: "E-mini NASDAQ-100: March 2026" -> extract instrument name
301
- description = contract.description.split(':')[0].trim();
302
- }
303
-
304
- // Fallback to our symbol descriptions
305
- if (!description) {
306
- // Extract base symbol (NQ from NQH6)
307
- const baseMatch = symbolCode.match(/^([A-Z0-9]{1,4})[FGHJKMNQUVXZ]\d{1,2}$/i);
308
- const baseSymbol = baseMatch ? baseMatch[1] : symbolCode;
309
- description = symbolDescriptions[baseSymbol] || symbolCode;
310
- }
213
+ // Get symbol code and description directly from API
214
+ const symbolCode = contract.name || contract.id || 'Unknown';
215
+ const description = contract.description || symbolCode;
311
216
 
312
- // Format: "NQH6 E-mini NASDAQ-100"
217
+ // Format: "NQH6 E-mini NASDAQ-100: March 2026"
313
218
  symbolChoices.push({
314
219
  name: chalk.yellow(symbolCode.padEnd(12)) + chalk.white(description),
315
220
  value: contract