laplace-api 4.0.0 → 4.2.0
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/.github/workflows/publish.yml +37 -0
- package/.github/workflows/test.yml +25 -0
- package/README.md +461 -2
- package/package.json +1 -1
- package/src/client/broker.ts +9 -7
- package/src/client/capital_increase.ts +7 -12
- package/src/client/collections.ts +57 -28
- package/src/client/financial_fundamentals.ts +2 -5
- package/src/client/financial_ratios.ts +114 -95
- package/src/client/live-price-web-socket.ts +24 -9
- package/src/client/live-price.ts +228 -46
- package/src/client/politician.ts +75 -0
- package/src/client/stocks.ts +73 -0
- package/src/test/broker.test.ts +583 -148
- package/src/test/capital_increase.test.ts +186 -39
- package/src/test/collections.test.ts +445 -60
- package/src/test/custom_theme.test.ts +242 -60
- package/src/test/financial_fundamentals.test.ts +297 -56
- package/src/test/financial_ratios.test.ts +363 -92
- package/src/test/funds.test.ts +275 -68
- package/src/test/key-insight.test.ts +81 -19
- package/src/test/live-price.test.ts +425 -64
- package/src/test/politician.test.ts +253 -0
- package/src/test/readme.test.ts +481 -0
- package/src/test/search.test.ts +301 -65
- package/src/test/stocks.test.ts +764 -152
- package/src/utilities/configuration.ts +23 -10
- package/src/utilities/test.env +2 -2
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { Client } from './client';
|
|
2
|
-
import { Stock } from './stocks';
|
|
2
|
+
import { HistoricalPricePeriod, PriceDataPoint, Stock } from './stocks';
|
|
3
3
|
|
|
4
4
|
export enum CollectionType {
|
|
5
5
|
Sector = 'sector',
|
|
@@ -42,52 +42,81 @@ export interface CollectionDetail extends Collection {
|
|
|
42
42
|
stocks: Stock[];
|
|
43
43
|
}
|
|
44
44
|
|
|
45
|
+
export interface CollectionPriceGraph {
|
|
46
|
+
previous_close: number;
|
|
47
|
+
graph: PriceDataPoint[];
|
|
48
|
+
}
|
|
49
|
+
|
|
45
50
|
export class CollectionClient extends Client {
|
|
46
|
-
|
|
51
|
+
async getAllSectors(region: Region, locale: Locale): Promise<Collection[]> {
|
|
47
52
|
return this.sendRequest<Collection[]>({
|
|
48
53
|
method: 'GET',
|
|
49
|
-
url: `/api/v1
|
|
54
|
+
url: `/api/v1/sector`,
|
|
50
55
|
params: { region, locale },
|
|
51
56
|
});
|
|
52
57
|
}
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
return this.sendRequest<
|
|
58
|
+
|
|
59
|
+
async getAllIndustries(region: Region, locale: Locale): Promise<Collection[]> {
|
|
60
|
+
return this.sendRequest<Collection[]>({
|
|
56
61
|
method: 'GET',
|
|
57
|
-
url: `/api/v1
|
|
62
|
+
url: `/api/v1/industry`,
|
|
58
63
|
params: { region, locale },
|
|
59
64
|
});
|
|
60
65
|
}
|
|
61
|
-
|
|
62
|
-
async getAllSectors(region: Region, locale: Locale): Promise<Collection[]> {
|
|
63
|
-
return this.getAllCollectionsPrivate(CollectionType.Sector, region, locale);
|
|
64
|
-
}
|
|
65
|
-
|
|
66
|
-
async getAllIndustries(region: Region, locale: Locale): Promise<Collection[]> {
|
|
67
|
-
return this.getAllCollectionsPrivate(CollectionType.Industry, region, locale);
|
|
68
|
-
}
|
|
69
|
-
|
|
66
|
+
|
|
70
67
|
async getAllThemes(region: Region, locale: Locale): Promise<Collection[]> {
|
|
71
|
-
return this.
|
|
68
|
+
return this.sendRequest<Collection[]>({
|
|
69
|
+
method: 'GET',
|
|
70
|
+
url: `/api/v1/theme`,
|
|
71
|
+
params: { region, locale },
|
|
72
|
+
});
|
|
72
73
|
}
|
|
73
|
-
|
|
74
|
+
|
|
74
75
|
async getAllCollections(region: Region, locale: Locale): Promise<Collection[]> {
|
|
75
|
-
return this.
|
|
76
|
+
return this.sendRequest<Collection[]>({
|
|
77
|
+
method: 'GET',
|
|
78
|
+
url: `/api/v1/collection`,
|
|
79
|
+
params: { region, locale },
|
|
80
|
+
});
|
|
76
81
|
}
|
|
77
|
-
|
|
82
|
+
|
|
78
83
|
async getSectorDetail(id: string, region: Region, locale: Locale): Promise<CollectionDetail> {
|
|
79
|
-
return this.
|
|
84
|
+
return this.sendRequest<CollectionDetail>({
|
|
85
|
+
method: 'GET',
|
|
86
|
+
url: `/api/v1/sector/${id}`,
|
|
87
|
+
params: { region, locale },
|
|
88
|
+
});
|
|
80
89
|
}
|
|
81
|
-
|
|
90
|
+
|
|
82
91
|
async getIndustryDetail(id: string, region: Region, locale: Locale): Promise<CollectionDetail> {
|
|
83
|
-
return this.
|
|
92
|
+
return this.sendRequest<CollectionDetail>({
|
|
93
|
+
method: 'GET',
|
|
94
|
+
url: `/api/v1/industry/${id}`,
|
|
95
|
+
params: { region, locale },
|
|
96
|
+
});
|
|
84
97
|
}
|
|
85
|
-
|
|
98
|
+
|
|
86
99
|
async getThemeDetail(id: string, region: Region, locale: Locale): Promise<CollectionDetail> {
|
|
87
|
-
return this.
|
|
100
|
+
return this.sendRequest<CollectionDetail>({
|
|
101
|
+
method: 'GET',
|
|
102
|
+
url: `/api/v1/theme/${id}`,
|
|
103
|
+
params: { region, locale },
|
|
104
|
+
});
|
|
88
105
|
}
|
|
89
|
-
|
|
106
|
+
|
|
90
107
|
async getCollectionDetail(id: string, region: Region, locale: Locale): Promise<CollectionDetail> {
|
|
91
|
-
return this.
|
|
108
|
+
return this.sendRequest<CollectionDetail>({
|
|
109
|
+
method: 'GET',
|
|
110
|
+
url: `/api/v1/collection/${id}`,
|
|
111
|
+
params: { region, locale },
|
|
112
|
+
});
|
|
113
|
+
}
|
|
114
|
+
|
|
115
|
+
async getAggregateGraph(period: HistoricalPricePeriod, sectorId: string, industryId: string, collectionId: string, region: Region): Promise<CollectionPriceGraph> {
|
|
116
|
+
return this.sendRequest<CollectionPriceGraph>({
|
|
117
|
+
method: 'GET',
|
|
118
|
+
url: `/api/v1/aggregate/graph`,
|
|
119
|
+
params: { period, sectorId, industryId, collectionId, region },
|
|
120
|
+
});
|
|
92
121
|
}
|
|
93
|
-
}
|
|
122
|
+
}
|
|
@@ -75,13 +75,10 @@ export class FinancialFundamentalsClient extends Client {
|
|
|
75
75
|
symbol: string,
|
|
76
76
|
region: Region
|
|
77
77
|
): Promise<StockDividend[]> {
|
|
78
|
-
const url = new URL(`${this["baseUrl"]}/api/v2/stock/dividends`);
|
|
79
|
-
url.searchParams.append("symbol", symbol);
|
|
80
|
-
url.searchParams.append("region", region);
|
|
81
|
-
|
|
82
78
|
return this.sendRequest<StockDividend[]>({
|
|
83
79
|
method: 'GET',
|
|
84
|
-
url:
|
|
80
|
+
url: "/api/v2/stock/dividends",
|
|
81
|
+
params: { symbol, region }
|
|
85
82
|
});
|
|
86
83
|
}
|
|
87
84
|
|
|
@@ -3,7 +3,7 @@ import { Region, Locale } from "./collections";
|
|
|
3
3
|
|
|
4
4
|
export enum RatioComparisonPeerType {
|
|
5
5
|
Industry = "industry",
|
|
6
|
-
Sector = "sector"
|
|
6
|
+
Sector = "sector",
|
|
7
7
|
}
|
|
8
8
|
|
|
9
9
|
export interface StockPeerFinancialRatioComparison {
|
|
@@ -43,79 +43,79 @@ export enum HistoricalRatiosFormat {
|
|
|
43
43
|
}
|
|
44
44
|
|
|
45
45
|
export enum HistoricalRatiosKey {
|
|
46
|
-
Revenue =
|
|
47
|
-
EBITDA =
|
|
48
|
-
NetProfit =
|
|
49
|
-
GrossMargin =
|
|
50
|
-
NetMargin =
|
|
51
|
-
ReturnOnAssets =
|
|
52
|
-
ReturnOnEquity =
|
|
53
|
-
ReturnOnCapitalEmployed =
|
|
54
|
-
ReturnOnInvestedCapital =
|
|
55
|
-
PriceToEarningsRatio =
|
|
56
|
-
PriceToEarnings =
|
|
57
|
-
PriceToBookRatio =
|
|
58
|
-
EnterpriseValueToEBITDA =
|
|
59
|
-
EnterpriseValueToInvestedCapital =
|
|
60
|
-
InterestCoverage =
|
|
61
|
-
QuickRatio =
|
|
62
|
-
LeverageRatio =
|
|
63
|
-
DebtToEquity =
|
|
64
|
-
RevenueGrowth =
|
|
65
|
-
EBITDAGrowth =
|
|
66
|
-
NetProfitGrowth =
|
|
67
|
-
FreeCashFlowGrowth =
|
|
68
|
-
CashConversionCycle =
|
|
69
|
-
DaysSalesOutstanding =
|
|
70
|
-
DaysPayable =
|
|
71
|
-
DaysInventory =
|
|
72
|
-
|
|
73
|
-
EBITDAMargin =
|
|
74
|
-
InventoryTurnover =
|
|
75
|
-
DepositGrowth =
|
|
76
|
-
NetInterestMargin =
|
|
77
|
-
CompensationGrowth =
|
|
78
|
-
PremiumPerCompensation =
|
|
79
|
-
EnterpriseValueToOperatingCashFlow =
|
|
80
|
-
EarningsBeforeTax =
|
|
81
|
-
CapitalExpenditure =
|
|
82
|
-
FinancialInvestments =
|
|
83
|
-
RealtimeEarningsPerShare =
|
|
84
|
-
RealtimeMarketValue =
|
|
85
|
-
RealtimePriceToBookRatio =
|
|
86
|
-
RealtimePriceToEarningsRatio =
|
|
87
|
-
CurrentRatio =
|
|
88
|
-
AssetTurnover =
|
|
89
|
-
TotalOperationalExpense =
|
|
90
|
-
TotalOperationalExpenseToGrossProfit =
|
|
91
|
-
CashAndCashEquivalents =
|
|
92
|
-
CashToAssets =
|
|
93
|
-
CapexToNetProfit =
|
|
94
|
-
RealtimeEnterpriseValueToEBITDA =
|
|
95
|
-
ReceivablesTurnover =
|
|
96
|
-
EarningsPerShare =
|
|
97
|
-
CreditToAssetRatio =
|
|
98
|
-
CreditToDepositRatio =
|
|
99
|
-
TechnicalProfitGrowth =
|
|
100
|
-
NetEarnedPremiumGrowth =
|
|
101
|
-
EBITGrowth =
|
|
102
|
-
CashReturnOnInvestedCapital =
|
|
103
|
-
MarketCapitalization =
|
|
104
|
-
ShortTermToLongTermObligations =
|
|
105
|
-
RetainedEarnings =
|
|
106
|
-
ThreeYearCAGRFreeCashFlow =
|
|
107
|
-
LongTermLoansToPeriodicProfitRatio =
|
|
108
|
-
LongTermLoans =
|
|
109
|
-
CommercialReceivablesToTotalCurrentAssets =
|
|
110
|
-
StockGrowth =
|
|
111
|
-
FiveYearRetainedEarningsChange =
|
|
112
|
-
ThreeYearCAGRRetainedEarnings =
|
|
113
|
-
PotentialOperatingCashFlow =
|
|
114
|
-
FreeCashFlowToEnterpriseValue =
|
|
115
|
-
DebtToDeposit =
|
|
116
|
-
NetDebt =
|
|
117
|
-
PaidCapital =
|
|
118
|
-
FinancialExpensesToEBIT =
|
|
46
|
+
Revenue = "satislar",
|
|
47
|
+
EBITDA = "ebitda",
|
|
48
|
+
NetProfit = "net_kar",
|
|
49
|
+
GrossMargin = "gross-margin",
|
|
50
|
+
NetMargin = "net-margin",
|
|
51
|
+
ReturnOnAssets = "roa",
|
|
52
|
+
ReturnOnEquity = "roe",
|
|
53
|
+
ReturnOnCapitalEmployed = "roce",
|
|
54
|
+
ReturnOnInvestedCapital = "roic",
|
|
55
|
+
PriceToEarningsRatio = "pe-ratio",
|
|
56
|
+
PriceToEarnings = "poe",
|
|
57
|
+
PriceToBookRatio = "pb-ratio",
|
|
58
|
+
EnterpriseValueToEBITDA = "ev-to-ebitda",
|
|
59
|
+
EnterpriseValueToInvestedCapital = "evic",
|
|
60
|
+
InterestCoverage = "interestCoverage",
|
|
61
|
+
QuickRatio = "quick-ratio",
|
|
62
|
+
LeverageRatio = "leverage-ratio",
|
|
63
|
+
DebtToEquity = "debt-to-equity",
|
|
64
|
+
RevenueGrowth = "satis_buyumesi",
|
|
65
|
+
EBITDAGrowth = "favok_buyumesi",
|
|
66
|
+
NetProfitGrowth = "net_kar_buyumesi",
|
|
67
|
+
FreeCashFlowGrowth = "serbest_nakit_akisi_buyumesi",
|
|
68
|
+
CashConversionCycle = "cash-conversion-cycle",
|
|
69
|
+
DaysSalesOutstanding = "days-sales-outstanding",
|
|
70
|
+
DaysPayable = "days-payable",
|
|
71
|
+
DaysInventory = "days-inventory",
|
|
72
|
+
|
|
73
|
+
EBITDAMargin = "favok_marji",
|
|
74
|
+
InventoryTurnover = "inventory-turnover",
|
|
75
|
+
DepositGrowth = "mevduat_buyumesi",
|
|
76
|
+
NetInterestMargin = "net_faiz_marji",
|
|
77
|
+
CompensationGrowth = "gerceklesen_tazminatlar_buyumesi",
|
|
78
|
+
PremiumPerCompensation = "prim_basina_tazminat_orani",
|
|
79
|
+
EnterpriseValueToOperatingCashFlow = "evOcf",
|
|
80
|
+
EarningsBeforeTax = "ebt",
|
|
81
|
+
CapitalExpenditure = "capex",
|
|
82
|
+
FinancialInvestments = "financial_investments",
|
|
83
|
+
RealtimeEarningsPerShare = "realtime_eps-basic",
|
|
84
|
+
RealtimeMarketValue = "realtime_piyasa_degeri",
|
|
85
|
+
RealtimePriceToBookRatio = "realtime_pb-ratio",
|
|
86
|
+
RealtimePriceToEarningsRatio = "realtime_pe-ratio",
|
|
87
|
+
CurrentRatio = "current-ratio",
|
|
88
|
+
AssetTurnover = "asset-turnover",
|
|
89
|
+
TotalOperationalExpense = "total_operational_expense",
|
|
90
|
+
TotalOperationalExpenseToGrossProfit = "total_operational_expense_gross_profit_ratio",
|
|
91
|
+
CashAndCashEquivalents = "cash_and_cash_equivalents",
|
|
92
|
+
CashToAssets = "cash_to_assets",
|
|
93
|
+
CapexToNetProfit = "capex_to_net_profit",
|
|
94
|
+
RealtimeEnterpriseValueToEBITDA = "realtime_ev-to-ebitda",
|
|
95
|
+
ReceivablesTurnover = "alacak_devir_hizi",
|
|
96
|
+
EarningsPerShare = "eps-basic",
|
|
97
|
+
CreditToAssetRatio = "kredi_aktif_orani",
|
|
98
|
+
CreditToDepositRatio = "kredi_mevduat_orani",
|
|
99
|
+
TechnicalProfitGrowth = "teknik_kar_buyumesi",
|
|
100
|
+
NetEarnedPremiumGrowth = "net_kazanilan_prim_buyumesi",
|
|
101
|
+
EBITGrowth = "ebitGrowth",
|
|
102
|
+
CashReturnOnInvestedCapital = "croic",
|
|
103
|
+
MarketCapitalization = "piyasa_degeri",
|
|
104
|
+
ShortTermToLongTermObligations = "short_term_obligations_long_term_obligations",
|
|
105
|
+
RetainedEarnings = "retained_earnings",
|
|
106
|
+
ThreeYearCAGRFreeCashFlow = "three_year_cagr_free_cash_flow",
|
|
107
|
+
LongTermLoansToPeriodicProfitRatio = "long_term_loans_period_profit_ratio",
|
|
108
|
+
LongTermLoans = "long_term_loans",
|
|
109
|
+
CommercialReceivablesToTotalCurrentAssets = "commercial_receivables_total_current_assets",
|
|
110
|
+
StockGrowth = "stock_growth",
|
|
111
|
+
FiveYearRetainedEarningsChange = "five_year_retained_earnings_change",
|
|
112
|
+
ThreeYearCAGRRetainedEarnings = "three_year_cagr_retained_earnings",
|
|
113
|
+
PotentialOperatingCashFlow = "pocf",
|
|
114
|
+
FreeCashFlowToEnterpriseValue = "fcfEv",
|
|
115
|
+
DebtToDeposit = "dd",
|
|
116
|
+
NetDebt = "net_borc",
|
|
117
|
+
PaidCapital = "odenmis_sermaye",
|
|
118
|
+
FinancialExpensesToEBIT = "financial_expenses_ebit_ratio",
|
|
119
119
|
}
|
|
120
120
|
|
|
121
121
|
export interface StockHistoricalRatiosDescription {
|
|
@@ -148,21 +148,21 @@ export interface HistoricalFinancialSheetRow {
|
|
|
148
148
|
}
|
|
149
149
|
|
|
150
150
|
export enum FinancialSheetType {
|
|
151
|
-
IncomeStatement =
|
|
152
|
-
BalanceSheet =
|
|
153
|
-
CashFlow =
|
|
151
|
+
IncomeStatement = "incomeStatement",
|
|
152
|
+
BalanceSheet = "balanceSheet",
|
|
153
|
+
CashFlow = "cashFlowStatement",
|
|
154
154
|
}
|
|
155
155
|
|
|
156
156
|
export enum FinancialSheetPeriod {
|
|
157
|
-
Annual =
|
|
158
|
-
Quarterly =
|
|
159
|
-
Cumulative =
|
|
157
|
+
Annual = "annual",
|
|
158
|
+
Quarterly = "quarterly",
|
|
159
|
+
Cumulative = "cumulative",
|
|
160
160
|
}
|
|
161
161
|
|
|
162
162
|
export enum Currency {
|
|
163
|
-
USD =
|
|
164
|
-
TRY =
|
|
165
|
-
EUR =
|
|
163
|
+
USD = "USD",
|
|
164
|
+
TRY = "TRY",
|
|
165
|
+
EUR = "EUR",
|
|
166
166
|
}
|
|
167
167
|
|
|
168
168
|
export interface FinancialSheetDate {
|
|
@@ -203,7 +203,7 @@ export class FinancialClient extends Client {
|
|
|
203
203
|
url.searchParams.append("slugs", keys.join(","));
|
|
204
204
|
|
|
205
205
|
return this.sendRequest<StockHistoricalRatios[]>({
|
|
206
|
-
method:
|
|
206
|
+
method: "GET",
|
|
207
207
|
url: url.toString(),
|
|
208
208
|
});
|
|
209
209
|
}
|
|
@@ -219,7 +219,7 @@ export class FinancialClient extends Client {
|
|
|
219
219
|
url.searchParams.append("region", region);
|
|
220
220
|
|
|
221
221
|
return this.sendRequest<StockHistoricalRatiosDescription[]>({
|
|
222
|
-
method:
|
|
222
|
+
method: "GET",
|
|
223
223
|
url: url.toString(),
|
|
224
224
|
});
|
|
225
225
|
}
|
|
@@ -233,18 +233,37 @@ export class FinancialClient extends Client {
|
|
|
233
233
|
currency: Currency,
|
|
234
234
|
region: Region
|
|
235
235
|
): Promise<HistoricalFinancialSheets> {
|
|
236
|
-
const url = new URL(
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
url.searchParams.append(
|
|
240
|
-
url.searchParams.append(
|
|
241
|
-
|
|
242
|
-
|
|
243
|
-
|
|
236
|
+
const url = new URL(
|
|
237
|
+
`${this["baseUrl"]}/api/v3/stock/historical-financial-sheets`
|
|
238
|
+
);
|
|
239
|
+
url.searchParams.append("symbol", symbol);
|
|
240
|
+
url.searchParams.append(
|
|
241
|
+
"from",
|
|
242
|
+
`${from.year.toString().padStart(4, "0")}-${from.month
|
|
243
|
+
.toString()
|
|
244
|
+
.padStart(2, "0")}-${from.day.toString().padStart(2, "0")}`
|
|
245
|
+
);
|
|
246
|
+
url.searchParams.append(
|
|
247
|
+
"to",
|
|
248
|
+
`${to.year.toString().padStart(4, "0")}-${to.month
|
|
249
|
+
.toString()
|
|
250
|
+
.padStart(2, "0")}-${to.day.toString().padStart(2, "0")}`
|
|
251
|
+
);
|
|
252
|
+
url.searchParams.append("sheetType", sheetType);
|
|
253
|
+
url.searchParams.append("periodType", period);
|
|
254
|
+
url.searchParams.append("currency", currency);
|
|
255
|
+
url.searchParams.append("region", region);
|
|
256
|
+
|
|
257
|
+
if (
|
|
258
|
+
sheetType === FinancialSheetType.BalanceSheet &&
|
|
259
|
+
period !== FinancialSheetPeriod.Cumulative
|
|
260
|
+
) {
|
|
261
|
+
throw new Error("balance sheet is only available for cumulative period");
|
|
262
|
+
}
|
|
244
263
|
|
|
245
264
|
return this.sendRequest<HistoricalFinancialSheets>({
|
|
246
|
-
method:
|
|
265
|
+
method: "GET",
|
|
247
266
|
url: url.toString(),
|
|
248
267
|
});
|
|
249
268
|
}
|
|
250
|
-
}
|
|
269
|
+
}
|
|
@@ -1,4 +1,3 @@
|
|
|
1
|
-
|
|
2
1
|
interface RawBISTStockLiveData {
|
|
3
2
|
_id: number;
|
|
4
3
|
symbol: string;
|
|
@@ -99,7 +98,10 @@ export class LivePriceWebSocketClient {
|
|
|
99
98
|
feed: LivePriceFeed;
|
|
100
99
|
}
|
|
101
100
|
>();
|
|
102
|
-
private symbolLastData = new Map<
|
|
101
|
+
private symbolLastData = new Map<
|
|
102
|
+
string,
|
|
103
|
+
BISTStockLiveData | USStockLiveData
|
|
104
|
+
>();
|
|
103
105
|
private reconnectAttempts = 0;
|
|
104
106
|
private reconnectTimeout: NodeJS.Timeout | null = null;
|
|
105
107
|
private isClosed: boolean = false;
|
|
@@ -110,8 +112,16 @@ export class LivePriceWebSocketClient {
|
|
|
110
112
|
private lastMessageTimestamp: number = 0;
|
|
111
113
|
private inactivityCheckInterval: NodeJS.Timeout | null = null;
|
|
112
114
|
private readonly INACTIVITY_TIMEOUT = 15000;
|
|
115
|
+
private externalUserId: string | null = null;
|
|
116
|
+
private feeds: LivePriceFeed[] | null = null;
|
|
113
117
|
|
|
114
|
-
constructor(
|
|
118
|
+
constructor(
|
|
119
|
+
feeds: LivePriceFeed[],
|
|
120
|
+
externalUserId: string,
|
|
121
|
+
options: WebSocketOptions = {}
|
|
122
|
+
) {
|
|
123
|
+
this.feeds = feeds;
|
|
124
|
+
this.externalUserId = externalUserId;
|
|
115
125
|
this.options = {
|
|
116
126
|
enableLogging: true,
|
|
117
127
|
logLevel: LogLevel.Error,
|
|
@@ -128,17 +138,17 @@ export class LivePriceWebSocketClient {
|
|
|
128
138
|
clearInterval(this.inactivityCheckInterval);
|
|
129
139
|
this.inactivityCheckInterval = null;
|
|
130
140
|
}
|
|
131
|
-
|
|
132
|
-
this.inactivityCheckInterval = setInterval(async ()=> {
|
|
141
|
+
|
|
142
|
+
this.inactivityCheckInterval = setInterval(async () => {
|
|
133
143
|
if (Date.now() - this.lastMessageTimestamp >= this.INACTIVITY_TIMEOUT) {
|
|
134
144
|
this.stopInactivityInterval();
|
|
135
145
|
try {
|
|
136
146
|
this.attemptReconnect();
|
|
137
|
-
} catch(error) {
|
|
147
|
+
} catch (error) {
|
|
138
148
|
this.log(`Failed to reconnect: ${error}`, "error");
|
|
139
149
|
}
|
|
140
150
|
}
|
|
141
|
-
}, this.INACTIVITY_TIMEOUT)
|
|
151
|
+
}, this.INACTIVITY_TIMEOUT);
|
|
142
152
|
}
|
|
143
153
|
|
|
144
154
|
private stopInactivityInterval() {
|
|
@@ -177,10 +187,14 @@ export class LivePriceWebSocketClient {
|
|
|
177
187
|
|
|
178
188
|
async connect(url: string): Promise<WebSocket> {
|
|
179
189
|
this.log("Connecting to WebSocket...");
|
|
190
|
+
if (!this.externalUserId || !this.feeds) {
|
|
191
|
+
throw new Error("External user ID and feeds are required");
|
|
192
|
+
}
|
|
193
|
+
|
|
180
194
|
this.wsUrl = url;
|
|
181
195
|
|
|
182
196
|
if (!this.ws || this.ws.readyState === WebSocket.CLOSED) {
|
|
183
|
-
this.ws = new WebSocket(
|
|
197
|
+
this.ws = new WebSocket(this.wsUrl);
|
|
184
198
|
this.connectPromise = this.setupWebSocket();
|
|
185
199
|
|
|
186
200
|
await this.connectPromise;
|
|
@@ -419,7 +433,8 @@ export class LivePriceWebSocketClient {
|
|
|
419
433
|
if (symbolHandlers.length === 1) {
|
|
420
434
|
symbolsToAdd.push(symbol);
|
|
421
435
|
} else if (symbolHandlers.length > 1) {
|
|
422
|
-
const lastData: BISTStockLiveData | USStockLiveData | undefined =
|
|
436
|
+
const lastData: BISTStockLiveData | USStockLiveData | undefined =
|
|
437
|
+
this.symbolLastData.get(symbol);
|
|
423
438
|
if (lastData) {
|
|
424
439
|
typedHandler(lastData);
|
|
425
440
|
}
|