@finatic/client 0.0.136 → 0.0.137
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/README.md +68 -64
- package/dist/index.d.ts +288 -88
- package/dist/index.js +1243 -258
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +1243 -258
- package/dist/index.mjs.map +1 -1
- package/dist/types/core/client/ApiClient.d.ts +21 -13
- package/dist/types/core/client/FinaticConnect.d.ts +39 -21
- package/dist/types/index.d.ts +1 -1
- package/dist/types/mocks/MockApiClient.d.ts +6 -9
- package/dist/types/mocks/MockDataProvider.d.ts +6 -9
- package/dist/types/types/api/broker.d.ts +47 -0
- package/dist/types/types/connect.d.ts +2 -0
- package/dist/types/types/portal.d.ts +178 -49
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -652,23 +652,6 @@ class ApiClient {
|
|
|
652
652
|
},
|
|
653
653
|
});
|
|
654
654
|
}
|
|
655
|
-
async validatePortalSession(sessionId, signature) {
|
|
656
|
-
return this.request('/portal/validate', {
|
|
657
|
-
method: 'GET',
|
|
658
|
-
headers: {
|
|
659
|
-
'Content-Type': 'application/json',
|
|
660
|
-
'X-Session-ID': sessionId,
|
|
661
|
-
'X-Device-Info': JSON.stringify({
|
|
662
|
-
ip_address: this.deviceInfo?.ip_address || '',
|
|
663
|
-
user_agent: this.deviceInfo?.user_agent || '',
|
|
664
|
-
fingerprint: this.deviceInfo?.fingerprint || '',
|
|
665
|
-
}),
|
|
666
|
-
},
|
|
667
|
-
params: {
|
|
668
|
-
signature,
|
|
669
|
-
},
|
|
670
|
-
});
|
|
671
|
-
}
|
|
672
655
|
async completePortalSession(sessionId) {
|
|
673
656
|
return this.request(`/portal/${sessionId}/complete`, {
|
|
674
657
|
method: 'POST',
|
|
@@ -678,34 +661,14 @@ class ApiClient {
|
|
|
678
661
|
});
|
|
679
662
|
}
|
|
680
663
|
// Portfolio Management
|
|
681
|
-
async getHoldings() {
|
|
682
|
-
const accessToken = await this.getValidAccessToken();
|
|
683
|
-
return this.request('/portfolio/holdings', {
|
|
684
|
-
method: 'GET',
|
|
685
|
-
headers: {
|
|
686
|
-
'Authorization': `Bearer ${accessToken}`,
|
|
687
|
-
},
|
|
688
|
-
});
|
|
689
|
-
}
|
|
690
664
|
async getOrders() {
|
|
691
665
|
const accessToken = await this.getValidAccessToken();
|
|
692
|
-
return this.request('/data/orders', {
|
|
693
|
-
method: 'GET',
|
|
694
|
-
headers: {
|
|
695
|
-
'Authorization': `Bearer ${accessToken}`,
|
|
696
|
-
},
|
|
697
|
-
});
|
|
698
|
-
}
|
|
699
|
-
async getPortfolio() {
|
|
700
|
-
const accessToken = await this.getValidAccessToken();
|
|
701
|
-
const response = await this.request('/portfolio/', {
|
|
666
|
+
return this.request('/brokers/data/orders', {
|
|
702
667
|
method: 'GET',
|
|
703
668
|
headers: {
|
|
704
669
|
'Authorization': `Bearer ${accessToken}`,
|
|
705
|
-
'Content-Type': 'application/json',
|
|
706
670
|
},
|
|
707
671
|
});
|
|
708
|
-
return response;
|
|
709
672
|
}
|
|
710
673
|
// Enhanced Trading Methods with Session Management
|
|
711
674
|
async placeBrokerOrder(params, extras = {}, connection_id) {
|
|
@@ -768,10 +731,7 @@ class ApiClient {
|
|
|
768
731
|
}
|
|
769
732
|
const accountNumber = this.tradingContext.accountNumber;
|
|
770
733
|
// Build query parameters as required by API documentation
|
|
771
|
-
const queryParams = {
|
|
772
|
-
broker: selectedBroker,
|
|
773
|
-
order_id: orderId,
|
|
774
|
-
};
|
|
734
|
+
const queryParams = {};
|
|
775
735
|
// Add optional parameters if available
|
|
776
736
|
if (accountNumber) {
|
|
777
737
|
queryParams.account_number = accountNumber.toString();
|
|
@@ -791,7 +751,7 @@ class ApiClient {
|
|
|
791
751
|
}
|
|
792
752
|
};
|
|
793
753
|
}
|
|
794
|
-
return this.request(
|
|
754
|
+
return this.request(`/brokers/orders/${orderId}`, {
|
|
795
755
|
method: 'DELETE',
|
|
796
756
|
headers: {
|
|
797
757
|
'Content-Type': 'application/json',
|
|
@@ -1061,19 +1021,9 @@ class ApiClient {
|
|
|
1061
1021
|
return extras;
|
|
1062
1022
|
}
|
|
1063
1023
|
}
|
|
1064
|
-
async
|
|
1065
|
-
const accessToken = await this.getValidAccessToken();
|
|
1066
|
-
await this.request('/auth/token/revoke', {
|
|
1067
|
-
method: 'POST',
|
|
1068
|
-
headers: {
|
|
1069
|
-
'Authorization': `Bearer ${accessToken}`,
|
|
1070
|
-
},
|
|
1071
|
-
});
|
|
1072
|
-
this.clearTokens();
|
|
1073
|
-
}
|
|
1074
|
-
async getUserToken(userId) {
|
|
1024
|
+
async getUserToken(sessionId) {
|
|
1075
1025
|
const accessToken = await this.getValidAccessToken();
|
|
1076
|
-
return this.request(`/auth/
|
|
1026
|
+
return this.request(`/auth/session/${sessionId}/user`, {
|
|
1077
1027
|
method: 'GET',
|
|
1078
1028
|
headers: {
|
|
1079
1029
|
'Authorization': `Bearer ${accessToken}`,
|
|
@@ -1104,7 +1054,7 @@ class ApiClient {
|
|
|
1104
1054
|
// Broker Data Management
|
|
1105
1055
|
async getBrokerList() {
|
|
1106
1056
|
const accessToken = await this.getValidAccessToken();
|
|
1107
|
-
return this.request('/brokers/
|
|
1057
|
+
return this.request('/brokers/', {
|
|
1108
1058
|
method: 'GET',
|
|
1109
1059
|
headers: {
|
|
1110
1060
|
'Authorization': `Bearer ${accessToken}`,
|
|
@@ -1171,6 +1121,26 @@ class ApiClient {
|
|
|
1171
1121
|
params,
|
|
1172
1122
|
});
|
|
1173
1123
|
}
|
|
1124
|
+
async getBrokerBalances(options) {
|
|
1125
|
+
const accessToken = await this.getValidAccessToken();
|
|
1126
|
+
const params = {};
|
|
1127
|
+
if (options?.broker_name) {
|
|
1128
|
+
params.broker_id = options.broker_name;
|
|
1129
|
+
}
|
|
1130
|
+
if (options?.account_id) {
|
|
1131
|
+
params.account_id = options.account_id;
|
|
1132
|
+
}
|
|
1133
|
+
if (options?.symbol) {
|
|
1134
|
+
params.symbol = options.symbol;
|
|
1135
|
+
}
|
|
1136
|
+
return this.request('/brokers/data/balances', {
|
|
1137
|
+
method: 'GET',
|
|
1138
|
+
headers: {
|
|
1139
|
+
'Authorization': `Bearer ${accessToken}`,
|
|
1140
|
+
},
|
|
1141
|
+
params,
|
|
1142
|
+
});
|
|
1143
|
+
}
|
|
1174
1144
|
async getBrokerConnections() {
|
|
1175
1145
|
const accessToken = await this.getValidAccessToken();
|
|
1176
1146
|
return this.request('/brokers/connections', {
|
|
@@ -1180,6 +1150,25 @@ class ApiClient {
|
|
|
1180
1150
|
},
|
|
1181
1151
|
});
|
|
1182
1152
|
}
|
|
1153
|
+
async getBalances(filters) {
|
|
1154
|
+
const accessToken = await this.getValidAccessToken();
|
|
1155
|
+
const params = new URLSearchParams();
|
|
1156
|
+
if (filters) {
|
|
1157
|
+
Object.entries(filters).forEach(([key, value]) => {
|
|
1158
|
+
if (value !== undefined && value !== null) {
|
|
1159
|
+
params.append(key, String(value));
|
|
1160
|
+
}
|
|
1161
|
+
});
|
|
1162
|
+
}
|
|
1163
|
+
const queryString = params.toString();
|
|
1164
|
+
const url = queryString ? `/brokers/data/balances?${queryString}` : '/brokers/data/balances';
|
|
1165
|
+
return this.request(url, {
|
|
1166
|
+
method: 'GET',
|
|
1167
|
+
headers: {
|
|
1168
|
+
'Authorization': `Bearer ${accessToken}`,
|
|
1169
|
+
},
|
|
1170
|
+
});
|
|
1171
|
+
}
|
|
1183
1172
|
// Page-based pagination methods
|
|
1184
1173
|
async getBrokerOrdersPage(page = 1, perPage = 100, filters) {
|
|
1185
1174
|
const accessToken = await this.getValidAccessToken();
|
|
@@ -1398,6 +1387,81 @@ class ApiClient {
|
|
|
1398
1387
|
limit: perPage,
|
|
1399
1388
|
}, navigationCallback);
|
|
1400
1389
|
}
|
|
1390
|
+
async getBrokerBalancesPage(page = 1, perPage = 100, filters) {
|
|
1391
|
+
const accessToken = await this.getValidAccessToken();
|
|
1392
|
+
const offset = (page - 1) * perPage;
|
|
1393
|
+
const params = {
|
|
1394
|
+
limit: perPage.toString(),
|
|
1395
|
+
offset: offset.toString(),
|
|
1396
|
+
};
|
|
1397
|
+
// Add filter parameters
|
|
1398
|
+
if (filters) {
|
|
1399
|
+
if (filters.broker_id)
|
|
1400
|
+
params.broker_id = filters.broker_id;
|
|
1401
|
+
if (filters.connection_id)
|
|
1402
|
+
params.connection_id = filters.connection_id;
|
|
1403
|
+
if (filters.account_id)
|
|
1404
|
+
params.account_id = filters.account_id;
|
|
1405
|
+
if (filters.is_end_of_day_snapshot !== undefined)
|
|
1406
|
+
params.is_end_of_day_snapshot = filters.is_end_of_day_snapshot.toString();
|
|
1407
|
+
if (filters.balance_created_after)
|
|
1408
|
+
params.balance_created_after = filters.balance_created_after;
|
|
1409
|
+
if (filters.balance_created_before)
|
|
1410
|
+
params.balance_created_before = filters.balance_created_before;
|
|
1411
|
+
if (filters.with_metadata !== undefined)
|
|
1412
|
+
params.with_metadata = filters.with_metadata.toString();
|
|
1413
|
+
}
|
|
1414
|
+
const response = await this.request('/brokers/data/balances', {
|
|
1415
|
+
method: 'GET',
|
|
1416
|
+
headers: {
|
|
1417
|
+
Authorization: `Bearer ${accessToken}`,
|
|
1418
|
+
},
|
|
1419
|
+
params,
|
|
1420
|
+
});
|
|
1421
|
+
// Create navigation callback for pagination
|
|
1422
|
+
const navigationCallback = async (newOffset, newLimit) => {
|
|
1423
|
+
const newParams = {
|
|
1424
|
+
limit: newLimit.toString(),
|
|
1425
|
+
offset: newOffset.toString(),
|
|
1426
|
+
};
|
|
1427
|
+
// Add filter parameters
|
|
1428
|
+
if (filters) {
|
|
1429
|
+
if (filters.broker_id)
|
|
1430
|
+
newParams.broker_id = filters.broker_id;
|
|
1431
|
+
if (filters.connection_id)
|
|
1432
|
+
newParams.connection_id = filters.connection_id;
|
|
1433
|
+
if (filters.account_id)
|
|
1434
|
+
newParams.account_id = filters.account_id;
|
|
1435
|
+
if (filters.is_end_of_day_snapshot !== undefined)
|
|
1436
|
+
newParams.is_end_of_day_snapshot = filters.is_end_of_day_snapshot.toString();
|
|
1437
|
+
if (filters.balance_created_after)
|
|
1438
|
+
newParams.balance_created_after = filters.balance_created_after;
|
|
1439
|
+
if (filters.balance_created_before)
|
|
1440
|
+
newParams.balance_created_before = filters.balance_created_before;
|
|
1441
|
+
if (filters.with_metadata !== undefined)
|
|
1442
|
+
newParams.with_metadata = filters.with_metadata.toString();
|
|
1443
|
+
}
|
|
1444
|
+
const newResponse = await this.request('/brokers/data/balances', {
|
|
1445
|
+
method: 'GET',
|
|
1446
|
+
headers: {
|
|
1447
|
+
Authorization: `Bearer ${accessToken}`,
|
|
1448
|
+
},
|
|
1449
|
+
params: newParams,
|
|
1450
|
+
});
|
|
1451
|
+
return new PaginatedResult(newResponse.response_data, newResponse.pagination || {
|
|
1452
|
+
has_more: false,
|
|
1453
|
+
next_offset: newOffset,
|
|
1454
|
+
current_offset: newOffset,
|
|
1455
|
+
limit: newLimit,
|
|
1456
|
+
}, navigationCallback);
|
|
1457
|
+
};
|
|
1458
|
+
return new PaginatedResult(response.response_data, response.pagination || {
|
|
1459
|
+
has_more: false,
|
|
1460
|
+
next_offset: offset,
|
|
1461
|
+
current_offset: offset,
|
|
1462
|
+
limit: perPage,
|
|
1463
|
+
}, navigationCallback);
|
|
1464
|
+
}
|
|
1401
1465
|
// Navigation methods
|
|
1402
1466
|
async getNextPage(previousResult, fetchFunction) {
|
|
1403
1467
|
if (!previousResult.hasNext) {
|
|
@@ -1419,7 +1483,7 @@ class ApiClient {
|
|
|
1419
1483
|
*/
|
|
1420
1484
|
async disconnectCompany(connectionId) {
|
|
1421
1485
|
const accessToken = await this.getValidAccessToken();
|
|
1422
|
-
return this.request(`/brokers/disconnect
|
|
1486
|
+
return this.request(`/brokers/disconnect/${connectionId}`, {
|
|
1423
1487
|
method: 'DELETE',
|
|
1424
1488
|
headers: {
|
|
1425
1489
|
'Authorization': `Bearer ${accessToken}`,
|
|
@@ -2074,109 +2138,6 @@ class MockDataProvider {
|
|
|
2074
2138
|
};
|
|
2075
2139
|
}
|
|
2076
2140
|
// Portfolio & Trading Mocks
|
|
2077
|
-
async mockGetHoldings() {
|
|
2078
|
-
await this.simulateDelay();
|
|
2079
|
-
const holdings = [
|
|
2080
|
-
{
|
|
2081
|
-
symbol: 'AAPL',
|
|
2082
|
-
quantity: 100,
|
|
2083
|
-
averagePrice: 150.25,
|
|
2084
|
-
currentPrice: 175.5,
|
|
2085
|
-
marketValue: 17550.0,
|
|
2086
|
-
unrealizedPnL: 2525.0,
|
|
2087
|
-
realizedPnL: 0,
|
|
2088
|
-
costBasis: 15025.0,
|
|
2089
|
-
currency: 'USD',
|
|
2090
|
-
},
|
|
2091
|
-
{
|
|
2092
|
-
symbol: 'TSLA',
|
|
2093
|
-
quantity: 50,
|
|
2094
|
-
averagePrice: 200.0,
|
|
2095
|
-
currentPrice: 220.75,
|
|
2096
|
-
marketValue: 11037.5,
|
|
2097
|
-
unrealizedPnL: 1037.5,
|
|
2098
|
-
realizedPnL: 0,
|
|
2099
|
-
costBasis: 10000.0,
|
|
2100
|
-
currency: 'USD',
|
|
2101
|
-
},
|
|
2102
|
-
{
|
|
2103
|
-
symbol: 'MSFT',
|
|
2104
|
-
quantity: 75,
|
|
2105
|
-
averagePrice: 300.0,
|
|
2106
|
-
currentPrice: 325.25,
|
|
2107
|
-
marketValue: 24393.75,
|
|
2108
|
-
unrealizedPnL: 1893.75,
|
|
2109
|
-
realizedPnL: 0,
|
|
2110
|
-
costBasis: 22500.0,
|
|
2111
|
-
currency: 'USD',
|
|
2112
|
-
},
|
|
2113
|
-
];
|
|
2114
|
-
return { data: holdings };
|
|
2115
|
-
}
|
|
2116
|
-
async mockGetPortfolio() {
|
|
2117
|
-
await this.simulateDelay();
|
|
2118
|
-
const portfolio = {
|
|
2119
|
-
id: uuid.v4(),
|
|
2120
|
-
name: 'Main Portfolio',
|
|
2121
|
-
type: 'individual',
|
|
2122
|
-
status: 'active',
|
|
2123
|
-
cash: 15000.5,
|
|
2124
|
-
buyingPower: 45000.0,
|
|
2125
|
-
equity: 52981.25,
|
|
2126
|
-
longMarketValue: 37981.25,
|
|
2127
|
-
shortMarketValue: 0,
|
|
2128
|
-
initialMargin: 0,
|
|
2129
|
-
maintenanceMargin: 0,
|
|
2130
|
-
lastEquity: 52000.0,
|
|
2131
|
-
positions: [
|
|
2132
|
-
{
|
|
2133
|
-
symbol: 'AAPL',
|
|
2134
|
-
quantity: 100,
|
|
2135
|
-
averagePrice: 150.25,
|
|
2136
|
-
currentPrice: 175.5,
|
|
2137
|
-
marketValue: 17550.0,
|
|
2138
|
-
unrealizedPnL: 2525.0,
|
|
2139
|
-
realizedPnL: 0,
|
|
2140
|
-
costBasis: 15025.0,
|
|
2141
|
-
currency: 'USD',
|
|
2142
|
-
},
|
|
2143
|
-
{
|
|
2144
|
-
symbol: 'TSLA',
|
|
2145
|
-
quantity: 50,
|
|
2146
|
-
averagePrice: 200.0,
|
|
2147
|
-
currentPrice: 220.75,
|
|
2148
|
-
marketValue: 11037.5,
|
|
2149
|
-
unrealizedPnL: 1037.5,
|
|
2150
|
-
realizedPnL: 0,
|
|
2151
|
-
costBasis: 10000.0,
|
|
2152
|
-
currency: 'USD',
|
|
2153
|
-
},
|
|
2154
|
-
{
|
|
2155
|
-
symbol: 'MSFT',
|
|
2156
|
-
quantity: 75,
|
|
2157
|
-
averagePrice: 300.0,
|
|
2158
|
-
currentPrice: 325.25,
|
|
2159
|
-
marketValue: 24393.75,
|
|
2160
|
-
unrealizedPnL: 1893.75,
|
|
2161
|
-
realizedPnL: 0,
|
|
2162
|
-
costBasis: 22500.0,
|
|
2163
|
-
currency: 'USD',
|
|
2164
|
-
},
|
|
2165
|
-
],
|
|
2166
|
-
performance: {
|
|
2167
|
-
totalReturn: 0.089,
|
|
2168
|
-
dailyReturn: 0.002,
|
|
2169
|
-
weeklyReturn: 0.015,
|
|
2170
|
-
monthlyReturn: 0.045,
|
|
2171
|
-
yearlyReturn: 0.089,
|
|
2172
|
-
maxDrawdown: -0.05,
|
|
2173
|
-
sharpeRatio: 1.2,
|
|
2174
|
-
beta: 0.95,
|
|
2175
|
-
alpha: 0.02,
|
|
2176
|
-
},
|
|
2177
|
-
};
|
|
2178
|
-
return { data: portfolio };
|
|
2179
|
-
}
|
|
2180
2141
|
async mockGetOrders(filter) {
|
|
2181
2142
|
await this.simulateDelay();
|
|
2182
2143
|
const mockOrders = [
|
|
@@ -2237,6 +2198,52 @@ class MockDataProvider {
|
|
|
2237
2198
|
data: filteredPositions,
|
|
2238
2199
|
};
|
|
2239
2200
|
}
|
|
2201
|
+
async mockGetBrokerBalances(filter) {
|
|
2202
|
+
await this.simulateDelay();
|
|
2203
|
+
// Determine how many balances to generate based on limit parameter
|
|
2204
|
+
const limit = filter?.limit || 100;
|
|
2205
|
+
const maxLimit = Math.min(limit, 1000); // Cap at 1000
|
|
2206
|
+
const mockBalances = [];
|
|
2207
|
+
for (let i = 0; i < maxLimit; i++) {
|
|
2208
|
+
const totalCashValue = Math.random() * 100000 + 10000; // $10k - $110k
|
|
2209
|
+
const netLiquidationValue = totalCashValue * (0.8 + Math.random() * 0.4); // ±20% variation
|
|
2210
|
+
const initialMargin = netLiquidationValue * 0.1; // 10% of net liquidation
|
|
2211
|
+
const maintenanceMargin = initialMargin * 0.8; // 80% of initial margin
|
|
2212
|
+
const availableToWithdraw = totalCashValue * 0.9; // 90% of cash available
|
|
2213
|
+
const totalRealizedPnl = (Math.random() - 0.5) * 10000; // -$5k to +$5k
|
|
2214
|
+
const balance = {
|
|
2215
|
+
id: `balance_${i + 1}`,
|
|
2216
|
+
account_id: `account_${Math.floor(Math.random() * 3) + 1}`,
|
|
2217
|
+
total_cash_value: totalCashValue,
|
|
2218
|
+
net_liquidation_value: netLiquidationValue,
|
|
2219
|
+
initial_margin: initialMargin,
|
|
2220
|
+
maintenance_margin: maintenanceMargin,
|
|
2221
|
+
available_to_withdraw: availableToWithdraw,
|
|
2222
|
+
total_realized_pnl: totalRealizedPnl,
|
|
2223
|
+
balance_created_at: new Date(Date.now() - Math.random() * 7 * 24 * 60 * 60 * 1000).toISOString(),
|
|
2224
|
+
balance_updated_at: new Date().toISOString(),
|
|
2225
|
+
is_end_of_day_snapshot: Math.random() > 0.7, // 30% chance of being EOD snapshot
|
|
2226
|
+
raw_payload: {
|
|
2227
|
+
broker_specific_data: {
|
|
2228
|
+
margin_ratio: netLiquidationValue / initialMargin,
|
|
2229
|
+
day_trading_buying_power: availableToWithdraw * 4,
|
|
2230
|
+
overnight_buying_power: availableToWithdraw * 2,
|
|
2231
|
+
},
|
|
2232
|
+
},
|
|
2233
|
+
created_at: new Date(Date.now() - Math.random() * 30 * 24 * 60 * 60 * 1000).toISOString(),
|
|
2234
|
+
updated_at: new Date().toISOString(),
|
|
2235
|
+
};
|
|
2236
|
+
mockBalances.push(balance);
|
|
2237
|
+
}
|
|
2238
|
+
// Apply filters if provided
|
|
2239
|
+
let filteredBalances = mockBalances;
|
|
2240
|
+
if (filter) {
|
|
2241
|
+
filteredBalances = this.applyBrokerBalanceFilters(mockBalances, filter);
|
|
2242
|
+
}
|
|
2243
|
+
return {
|
|
2244
|
+
data: filteredBalances,
|
|
2245
|
+
};
|
|
2246
|
+
}
|
|
2240
2247
|
async mockGetBrokerDataAccounts(filter) {
|
|
2241
2248
|
await this.simulateDelay();
|
|
2242
2249
|
// Determine how many accounts to generate based on limit parameter
|
|
@@ -2289,8 +2296,8 @@ class MockDataProvider {
|
|
|
2289
2296
|
/**
|
|
2290
2297
|
* Get stored user token
|
|
2291
2298
|
*/
|
|
2292
|
-
getUserToken(
|
|
2293
|
-
return this.userTokens.get(
|
|
2299
|
+
getUserToken(sessionId) {
|
|
2300
|
+
return this.userTokens.get(sessionId);
|
|
2294
2301
|
}
|
|
2295
2302
|
/**
|
|
2296
2303
|
* Clear all stored data
|
|
@@ -2382,6 +2389,19 @@ class MockDataProvider {
|
|
|
2382
2389
|
return true;
|
|
2383
2390
|
});
|
|
2384
2391
|
}
|
|
2392
|
+
applyBrokerBalanceFilters(balances, filter) {
|
|
2393
|
+
return balances.filter(balance => {
|
|
2394
|
+
if (filter.account_id && balance.account_id !== filter.account_id)
|
|
2395
|
+
return false;
|
|
2396
|
+
if (filter.is_end_of_day_snapshot !== undefined && balance.is_end_of_day_snapshot !== filter.is_end_of_day_snapshot)
|
|
2397
|
+
return false;
|
|
2398
|
+
if (filter.balance_created_after && balance.balance_created_at && new Date(balance.balance_created_at) < new Date(filter.balance_created_after))
|
|
2399
|
+
return false;
|
|
2400
|
+
if (filter.balance_created_before && balance.balance_created_at && new Date(balance.balance_created_at) > new Date(filter.balance_created_before))
|
|
2401
|
+
return false;
|
|
2402
|
+
return true;
|
|
2403
|
+
});
|
|
2404
|
+
}
|
|
2385
2405
|
/**
|
|
2386
2406
|
* Generate mock orders with diverse data
|
|
2387
2407
|
*/
|
|
@@ -2793,18 +2813,10 @@ class MockApiClient {
|
|
|
2793
2813
|
return this.mockDataProvider.mockCompletePortalSession(sessionId);
|
|
2794
2814
|
}
|
|
2795
2815
|
// Portfolio Management
|
|
2796
|
-
async getHoldings(filter) {
|
|
2797
|
-
await this.getValidAccessToken();
|
|
2798
|
-
return this.mockDataProvider.mockGetHoldings();
|
|
2799
|
-
}
|
|
2800
2816
|
async getOrders(filter) {
|
|
2801
2817
|
await this.getValidAccessToken();
|
|
2802
2818
|
return this.mockDataProvider.mockGetOrders(filter);
|
|
2803
2819
|
}
|
|
2804
|
-
async getPortfolio() {
|
|
2805
|
-
await this.getValidAccessToken();
|
|
2806
|
-
return this.mockDataProvider.mockGetPortfolio();
|
|
2807
|
-
}
|
|
2808
2820
|
async placeOrder(order) {
|
|
2809
2821
|
await this.getValidAccessToken();
|
|
2810
2822
|
await this.mockDataProvider.mockPlaceOrder(order);
|
|
@@ -3015,12 +3027,8 @@ class MockApiClient {
|
|
|
3015
3027
|
price,
|
|
3016
3028
|
}, extras);
|
|
3017
3029
|
}
|
|
3018
|
-
async
|
|
3019
|
-
|
|
3020
|
-
this.clearTokens();
|
|
3021
|
-
}
|
|
3022
|
-
async getUserToken(userId) {
|
|
3023
|
-
const token = this.mockDataProvider.getUserToken(userId);
|
|
3030
|
+
async getUserToken(sessionId) {
|
|
3031
|
+
const token = this.mockDataProvider.getUserToken(sessionId);
|
|
3024
3032
|
if (!token) {
|
|
3025
3033
|
throw new AuthenticationError('User token not found');
|
|
3026
3034
|
}
|
|
@@ -3069,6 +3077,9 @@ class MockApiClient {
|
|
|
3069
3077
|
async getBrokerPositionsWithFilter(filter) {
|
|
3070
3078
|
return this.mockDataProvider.mockGetBrokerPositions(filter);
|
|
3071
3079
|
}
|
|
3080
|
+
async getBrokerBalancesWithFilter(filter) {
|
|
3081
|
+
return this.mockDataProvider.mockGetBrokerBalances(filter);
|
|
3082
|
+
}
|
|
3072
3083
|
async getBrokerDataAccountsWithFilter(filter) {
|
|
3073
3084
|
return this.mockDataProvider.mockGetBrokerDataAccounts(filter);
|
|
3074
3085
|
}
|
|
@@ -3163,6 +3174,36 @@ class MockApiClient {
|
|
|
3163
3174
|
limit: perPage,
|
|
3164
3175
|
}, navigationCallback);
|
|
3165
3176
|
}
|
|
3177
|
+
async getBrokerBalancesPage(page = 1, perPage = 100, filters) {
|
|
3178
|
+
const mockBalances = await this.mockDataProvider.mockGetBrokerBalances(filters);
|
|
3179
|
+
const balances = mockBalances.data;
|
|
3180
|
+
// Simulate pagination
|
|
3181
|
+
const startIndex = (page - 1) * perPage;
|
|
3182
|
+
const endIndex = startIndex + perPage;
|
|
3183
|
+
const paginatedBalances = balances.slice(startIndex, endIndex);
|
|
3184
|
+
const hasMore = endIndex < balances.length;
|
|
3185
|
+
const nextOffset = hasMore ? endIndex : startIndex;
|
|
3186
|
+
// Create navigation callback for mock pagination
|
|
3187
|
+
const navigationCallback = async (newOffset, newLimit) => {
|
|
3188
|
+
const newStartIndex = newOffset;
|
|
3189
|
+
const newEndIndex = newStartIndex + newLimit;
|
|
3190
|
+
const newPaginatedBalances = balances.slice(newStartIndex, newEndIndex);
|
|
3191
|
+
const newHasMore = newEndIndex < balances.length;
|
|
3192
|
+
const newNextOffset = newHasMore ? newEndIndex : newStartIndex;
|
|
3193
|
+
return new PaginatedResult(newPaginatedBalances, {
|
|
3194
|
+
has_more: newHasMore,
|
|
3195
|
+
next_offset: newNextOffset,
|
|
3196
|
+
current_offset: newStartIndex,
|
|
3197
|
+
limit: newLimit,
|
|
3198
|
+
}, navigationCallback);
|
|
3199
|
+
};
|
|
3200
|
+
return new PaginatedResult(paginatedBalances, {
|
|
3201
|
+
has_more: hasMore,
|
|
3202
|
+
next_offset: nextOffset,
|
|
3203
|
+
current_offset: startIndex,
|
|
3204
|
+
limit: perPage,
|
|
3205
|
+
}, navigationCallback);
|
|
3206
|
+
}
|
|
3166
3207
|
async getBrokerConnections() {
|
|
3167
3208
|
await this.getValidAccessToken();
|
|
3168
3209
|
return this.mockDataProvider.mockGetBrokerConnections();
|
|
@@ -3401,9 +3442,135 @@ const darkTheme = {
|
|
|
3401
3442
|
},
|
|
3402
3443
|
},
|
|
3403
3444
|
},
|
|
3445
|
+
typography: {
|
|
3446
|
+
fontFamily: {
|
|
3447
|
+
primary: 'Orbitron, Futura, Inter, system-ui, sans-serif',
|
|
3448
|
+
secondary: 'Orbitron, Futura, Inter, system-ui, sans-serif',
|
|
3449
|
+
},
|
|
3450
|
+
fontSize: {
|
|
3451
|
+
xs: '0.75rem',
|
|
3452
|
+
sm: '0.875rem',
|
|
3453
|
+
base: '1rem',
|
|
3454
|
+
lg: '1.125rem',
|
|
3455
|
+
xl: '1.25rem',
|
|
3456
|
+
'2xl': '1.5rem',
|
|
3457
|
+
'3xl': '1.875rem',
|
|
3458
|
+
'4xl': '2.25rem',
|
|
3459
|
+
},
|
|
3460
|
+
fontWeight: {
|
|
3461
|
+
normal: 400,
|
|
3462
|
+
medium: 500,
|
|
3463
|
+
semibold: 600,
|
|
3464
|
+
bold: 700,
|
|
3465
|
+
extrabold: 800,
|
|
3466
|
+
},
|
|
3467
|
+
lineHeight: {
|
|
3468
|
+
tight: '1.25',
|
|
3469
|
+
normal: '1.5',
|
|
3470
|
+
relaxed: '1.75',
|
|
3471
|
+
},
|
|
3472
|
+
},
|
|
3473
|
+
spacing: {
|
|
3474
|
+
xs: '0.25rem',
|
|
3475
|
+
sm: '0.5rem',
|
|
3476
|
+
md: '1rem',
|
|
3477
|
+
lg: '1.5rem',
|
|
3478
|
+
xl: '2rem',
|
|
3479
|
+
'2xl': '3rem',
|
|
3480
|
+
'3xl': '4rem',
|
|
3481
|
+
},
|
|
3482
|
+
layout: {
|
|
3483
|
+
containerMaxWidth: '1440px',
|
|
3484
|
+
gridGap: '1rem',
|
|
3485
|
+
cardPadding: '1.5rem',
|
|
3486
|
+
borderRadius: {
|
|
3487
|
+
sm: '0.25rem',
|
|
3488
|
+
md: '0.5rem',
|
|
3489
|
+
lg: '0.75rem',
|
|
3490
|
+
xl: '1rem',
|
|
3491
|
+
'2xl': '1.5rem',
|
|
3492
|
+
full: '9999px',
|
|
3493
|
+
},
|
|
3494
|
+
},
|
|
3495
|
+
components: {
|
|
3496
|
+
brokerCard: {
|
|
3497
|
+
width: '100%',
|
|
3498
|
+
height: '180px',
|
|
3499
|
+
logoSize: '64px',
|
|
3500
|
+
padding: '1.5rem',
|
|
3501
|
+
},
|
|
3502
|
+
statusIndicator: {
|
|
3503
|
+
size: '22px',
|
|
3504
|
+
glowIntensity: 0.9,
|
|
3505
|
+
},
|
|
3506
|
+
modal: {
|
|
3507
|
+
background: 'rgba(0, 0, 0, 0.95)',
|
|
3508
|
+
backdrop: 'rgba(0, 0, 0, 0.8)',
|
|
3509
|
+
},
|
|
3510
|
+
brokerCardModern: {
|
|
3511
|
+
width: '150px',
|
|
3512
|
+
height: '150px',
|
|
3513
|
+
padding: '16px',
|
|
3514
|
+
logoSize: '48px',
|
|
3515
|
+
statusSize: '22px',
|
|
3516
|
+
},
|
|
3517
|
+
connectButton: {
|
|
3518
|
+
width: '120px',
|
|
3519
|
+
height: '120px',
|
|
3520
|
+
},
|
|
3521
|
+
themeSwitcher: {
|
|
3522
|
+
indicatorSize: '24px',
|
|
3523
|
+
},
|
|
3524
|
+
},
|
|
3525
|
+
effects: {
|
|
3526
|
+
glassmorphism: {
|
|
3527
|
+
enabled: true,
|
|
3528
|
+
blur: '12px',
|
|
3529
|
+
opacity: 0.15,
|
|
3530
|
+
border: 'rgba(0, 255, 255, 0.3)',
|
|
3531
|
+
},
|
|
3532
|
+
animations: {
|
|
3533
|
+
enabled: true,
|
|
3534
|
+
duration: {
|
|
3535
|
+
fast: '150ms',
|
|
3536
|
+
normal: '300ms',
|
|
3537
|
+
slow: '500ms',
|
|
3538
|
+
},
|
|
3539
|
+
easing: {
|
|
3540
|
+
default: 'cubic-bezier(0.4, 0, 0.2, 1)',
|
|
3541
|
+
smooth: 'cubic-bezier(0.25, 0.46, 0.45, 0.94)',
|
|
3542
|
+
bounce: 'cubic-bezier(0.68, -0.55, 0.265, 1.55)',
|
|
3543
|
+
},
|
|
3544
|
+
},
|
|
3545
|
+
shadows: {
|
|
3546
|
+
sm: '0 1px 2px rgba(0, 0, 0, 0.5)',
|
|
3547
|
+
md: '0 4px 6px rgba(0, 0, 0, 0.6)',
|
|
3548
|
+
lg: '0 10px 15px rgba(0, 0, 0, 0.7)',
|
|
3549
|
+
xl: '0 20px 25px rgba(0, 0, 0, 0.8)',
|
|
3550
|
+
card: '0px 4px 12px rgba(0, 0, 0, 0.6), 0 0 20px rgba(0, 255, 255, 0.2)',
|
|
3551
|
+
cardHover: '0px 4px 24px rgba(0, 255, 255, 0.3), 0 0 30px rgba(0, 255, 255, 0.25)',
|
|
3552
|
+
glow: '0 0 20px rgba(0, 255, 255, 0.8)',
|
|
3553
|
+
focus: '0 0 0 2px #00FFFF, 0 0 8px 2px rgba(0, 255, 255, 0.8)',
|
|
3554
|
+
},
|
|
3555
|
+
},
|
|
3404
3556
|
branding: {
|
|
3405
3557
|
primaryColor: '#00FFFF',
|
|
3406
3558
|
},
|
|
3559
|
+
glow: {
|
|
3560
|
+
primary: 'rgba(0, 255, 255, 0.4)',
|
|
3561
|
+
secondary: 'rgba(0, 255, 255, 0.6)',
|
|
3562
|
+
card: 'rgba(0, 255, 255, 0.2)',
|
|
3563
|
+
cardHover: 'rgba(0, 255, 255, 0.3)',
|
|
3564
|
+
button: 'rgba(0, 255, 255, 0.6)',
|
|
3565
|
+
focus: 'rgba(0, 255, 255, 0.8)',
|
|
3566
|
+
scrollbar: 'rgba(0, 255, 255, 0.4)',
|
|
3567
|
+
},
|
|
3568
|
+
gradients: {
|
|
3569
|
+
start: 'rgba(0, 255, 255, 0.08)',
|
|
3570
|
+
end: 'rgba(0, 255, 255, 0.03)',
|
|
3571
|
+
hoverStart: 'rgba(0, 255, 255, 0.15)',
|
|
3572
|
+
hoverEnd: 'rgba(0, 255, 255, 0.08)',
|
|
3573
|
+
},
|
|
3407
3574
|
};
|
|
3408
3575
|
// Light theme with cyan accents
|
|
3409
3576
|
const lightTheme = {
|
|
@@ -3460,9 +3627,121 @@ const lightTheme = {
|
|
|
3460
3627
|
},
|
|
3461
3628
|
},
|
|
3462
3629
|
},
|
|
3630
|
+
typography: {
|
|
3631
|
+
fontFamily: {
|
|
3632
|
+
primary: 'Orbitron, Futura, Inter, system-ui, sans-serif',
|
|
3633
|
+
secondary: 'Orbitron, Futura, Inter, system-ui, sans-serif',
|
|
3634
|
+
},
|
|
3635
|
+
fontSize: {
|
|
3636
|
+
xs: '0.75rem',
|
|
3637
|
+
sm: '0.875rem',
|
|
3638
|
+
base: '1rem',
|
|
3639
|
+
lg: '1.125rem',
|
|
3640
|
+
xl: '1.25rem',
|
|
3641
|
+
'2xl': '1.5rem',
|
|
3642
|
+
'3xl': '1.875rem',
|
|
3643
|
+
'4xl': '2.25rem',
|
|
3644
|
+
},
|
|
3645
|
+
fontWeight: {
|
|
3646
|
+
normal: 400,
|
|
3647
|
+
medium: 500,
|
|
3648
|
+
semibold: 600,
|
|
3649
|
+
bold: 700,
|
|
3650
|
+
extrabold: 800,
|
|
3651
|
+
},
|
|
3652
|
+
lineHeight: {
|
|
3653
|
+
tight: '1.25',
|
|
3654
|
+
normal: '1.5',
|
|
3655
|
+
relaxed: '1.75',
|
|
3656
|
+
},
|
|
3657
|
+
},
|
|
3658
|
+
spacing: {
|
|
3659
|
+
xs: '0.25rem',
|
|
3660
|
+
sm: '0.5rem',
|
|
3661
|
+
md: '1rem',
|
|
3662
|
+
lg: '1.5rem',
|
|
3663
|
+
xl: '2rem',
|
|
3664
|
+
'2xl': '3rem',
|
|
3665
|
+
'3xl': '4rem',
|
|
3666
|
+
},
|
|
3667
|
+
layout: {
|
|
3668
|
+
containerMaxWidth: '1440px',
|
|
3669
|
+
gridGap: '1rem',
|
|
3670
|
+
cardPadding: '1.5rem',
|
|
3671
|
+
borderRadius: {
|
|
3672
|
+
sm: '0.25rem',
|
|
3673
|
+
md: '0.5rem',
|
|
3674
|
+
lg: '0.75rem',
|
|
3675
|
+
xl: '1rem',
|
|
3676
|
+
'2xl': '1.5rem',
|
|
3677
|
+
full: '9999px',
|
|
3678
|
+
},
|
|
3679
|
+
},
|
|
3680
|
+
components: {
|
|
3681
|
+
brokerCard: {
|
|
3682
|
+
width: '100%',
|
|
3683
|
+
height: '180px',
|
|
3684
|
+
logoSize: '64px',
|
|
3685
|
+
padding: '1.5rem',
|
|
3686
|
+
},
|
|
3687
|
+
statusIndicator: {
|
|
3688
|
+
size: '22px',
|
|
3689
|
+
glowIntensity: 0.9,
|
|
3690
|
+
},
|
|
3691
|
+
modal: {
|
|
3692
|
+
background: 'rgba(255, 255, 255, 0.95)',
|
|
3693
|
+
backdrop: 'rgba(0, 0, 0, 0.5)',
|
|
3694
|
+
},
|
|
3695
|
+
},
|
|
3696
|
+
effects: {
|
|
3697
|
+
glassmorphism: {
|
|
3698
|
+
enabled: true,
|
|
3699
|
+
blur: '12px',
|
|
3700
|
+
opacity: 0.15,
|
|
3701
|
+
border: 'rgba(0, 255, 255, 0.3)',
|
|
3702
|
+
},
|
|
3703
|
+
animations: {
|
|
3704
|
+
enabled: true,
|
|
3705
|
+
duration: {
|
|
3706
|
+
fast: '150ms',
|
|
3707
|
+
normal: '300ms',
|
|
3708
|
+
slow: '500ms',
|
|
3709
|
+
},
|
|
3710
|
+
easing: {
|
|
3711
|
+
default: 'cubic-bezier(0.4, 0, 0.2, 1)',
|
|
3712
|
+
smooth: 'cubic-bezier(0.25, 0.46, 0.45, 0.94)',
|
|
3713
|
+
bounce: 'cubic-bezier(0.68, -0.55, 0.265, 1.55)',
|
|
3714
|
+
},
|
|
3715
|
+
},
|
|
3716
|
+
shadows: {
|
|
3717
|
+
sm: '0 1px 2px rgba(0, 0, 0, 0.1)',
|
|
3718
|
+
md: '0 4px 6px rgba(0, 0, 0, 0.1)',
|
|
3719
|
+
lg: '0 10px 15px rgba(0, 0, 0, 0.1)',
|
|
3720
|
+
xl: '0 20px 25px rgba(0, 0, 0, 0.1)',
|
|
3721
|
+
card: '0px 4px 12px rgba(0, 0, 0, 0.1), 0 0 20px rgba(0, 255, 255, 0.2)',
|
|
3722
|
+
cardHover: '0px 4px 24px rgba(0, 255, 255, 0.3), 0 0 30px rgba(0, 255, 255, 0.25)',
|
|
3723
|
+
glow: '0 0 20px rgba(0, 255, 255, 0.8)',
|
|
3724
|
+
focus: '0 0 0 2px #00FFFF, 0 0 8px 2px rgba(0, 255, 255, 0.8)',
|
|
3725
|
+
},
|
|
3726
|
+
},
|
|
3463
3727
|
branding: {
|
|
3464
3728
|
primaryColor: '#00FFFF',
|
|
3465
3729
|
},
|
|
3730
|
+
glow: {
|
|
3731
|
+
primary: 'rgba(0, 255, 255, 0.4)',
|
|
3732
|
+
secondary: 'rgba(0, 255, 255, 0.6)',
|
|
3733
|
+
card: 'rgba(0, 255, 255, 0.2)',
|
|
3734
|
+
cardHover: 'rgba(0, 255, 255, 0.3)',
|
|
3735
|
+
button: 'rgba(0, 255, 255, 0.6)',
|
|
3736
|
+
focus: 'rgba(0, 255, 255, 0.8)',
|
|
3737
|
+
scrollbar: 'rgba(0, 255, 255, 0.4)',
|
|
3738
|
+
},
|
|
3739
|
+
gradients: {
|
|
3740
|
+
start: 'rgba(0, 255, 255, 0.08)',
|
|
3741
|
+
end: 'rgba(0, 255, 255, 0.03)',
|
|
3742
|
+
hoverStart: 'rgba(0, 255, 255, 0.15)',
|
|
3743
|
+
hoverEnd: 'rgba(0, 255, 255, 0.08)',
|
|
3744
|
+
},
|
|
3466
3745
|
};
|
|
3467
3746
|
// Corporate blue theme
|
|
3468
3747
|
const corporateBlueTheme = {
|
|
@@ -3519,23 +3798,149 @@ const corporateBlueTheme = {
|
|
|
3519
3798
|
},
|
|
3520
3799
|
},
|
|
3521
3800
|
},
|
|
3522
|
-
|
|
3523
|
-
|
|
3524
|
-
|
|
3525
|
-
|
|
3526
|
-
// Purple theme
|
|
3527
|
-
const purpleTheme = {
|
|
3528
|
-
mode: 'dark',
|
|
3529
|
-
colors: {
|
|
3530
|
-
background: {
|
|
3531
|
-
primary: '#1a1a1a',
|
|
3532
|
-
secondary: '#2a2a2a',
|
|
3533
|
-
tertiary: '#3a3a3a',
|
|
3534
|
-
accent: 'rgba(168, 85, 247, 0.1)',
|
|
3535
|
-
glass: 'rgba(255, 255, 255, 0.05)',
|
|
3801
|
+
typography: {
|
|
3802
|
+
fontFamily: {
|
|
3803
|
+
primary: 'Orbitron, Futura, Inter, system-ui, sans-serif',
|
|
3804
|
+
secondary: 'Orbitron, Futura, Inter, system-ui, sans-serif',
|
|
3536
3805
|
},
|
|
3537
|
-
|
|
3538
|
-
|
|
3806
|
+
fontSize: {
|
|
3807
|
+
xs: '0.75rem',
|
|
3808
|
+
sm: '0.875rem',
|
|
3809
|
+
base: '1rem',
|
|
3810
|
+
lg: '1.125rem',
|
|
3811
|
+
xl: '1.25rem',
|
|
3812
|
+
'2xl': '1.5rem',
|
|
3813
|
+
'3xl': '1.875rem',
|
|
3814
|
+
'4xl': '2.25rem',
|
|
3815
|
+
},
|
|
3816
|
+
fontWeight: {
|
|
3817
|
+
normal: 400,
|
|
3818
|
+
medium: 500,
|
|
3819
|
+
semibold: 600,
|
|
3820
|
+
bold: 700,
|
|
3821
|
+
extrabold: 800,
|
|
3822
|
+
},
|
|
3823
|
+
lineHeight: {
|
|
3824
|
+
tight: '1.25',
|
|
3825
|
+
normal: '1.5',
|
|
3826
|
+
relaxed: '1.75',
|
|
3827
|
+
},
|
|
3828
|
+
},
|
|
3829
|
+
spacing: {
|
|
3830
|
+
xs: '0.25rem',
|
|
3831
|
+
sm: '0.5rem',
|
|
3832
|
+
md: '1rem',
|
|
3833
|
+
lg: '1.5rem',
|
|
3834
|
+
xl: '2rem',
|
|
3835
|
+
'2xl': '3rem',
|
|
3836
|
+
'3xl': '4rem',
|
|
3837
|
+
},
|
|
3838
|
+
layout: {
|
|
3839
|
+
containerMaxWidth: '1440px',
|
|
3840
|
+
gridGap: '1rem',
|
|
3841
|
+
cardPadding: '1.5rem',
|
|
3842
|
+
borderRadius: {
|
|
3843
|
+
sm: '0.25rem',
|
|
3844
|
+
md: '0.5rem',
|
|
3845
|
+
lg: '0.75rem',
|
|
3846
|
+
xl: '1rem',
|
|
3847
|
+
'2xl': '1.5rem',
|
|
3848
|
+
full: '9999px',
|
|
3849
|
+
},
|
|
3850
|
+
},
|
|
3851
|
+
components: {
|
|
3852
|
+
brokerCard: {
|
|
3853
|
+
width: '100%',
|
|
3854
|
+
height: '180px',
|
|
3855
|
+
logoSize: '64px',
|
|
3856
|
+
padding: '1.5rem',
|
|
3857
|
+
},
|
|
3858
|
+
statusIndicator: {
|
|
3859
|
+
size: '22px',
|
|
3860
|
+
glowIntensity: 0.9,
|
|
3861
|
+
},
|
|
3862
|
+
modal: {
|
|
3863
|
+
background: 'rgba(0, 0, 0, 0.95)',
|
|
3864
|
+
backdrop: 'rgba(0, 0, 0, 0.8)',
|
|
3865
|
+
},
|
|
3866
|
+
brokerCardModern: {
|
|
3867
|
+
width: '150px',
|
|
3868
|
+
height: '150px',
|
|
3869
|
+
padding: '16px',
|
|
3870
|
+
logoSize: '48px',
|
|
3871
|
+
statusSize: '22px',
|
|
3872
|
+
},
|
|
3873
|
+
connectButton: {
|
|
3874
|
+
width: '120px',
|
|
3875
|
+
height: '120px',
|
|
3876
|
+
},
|
|
3877
|
+
themeSwitcher: {
|
|
3878
|
+
indicatorSize: '24px',
|
|
3879
|
+
},
|
|
3880
|
+
},
|
|
3881
|
+
effects: {
|
|
3882
|
+
glassmorphism: {
|
|
3883
|
+
enabled: true,
|
|
3884
|
+
blur: '12px',
|
|
3885
|
+
opacity: 0.15,
|
|
3886
|
+
border: 'rgba(59, 130, 246, 0.3)',
|
|
3887
|
+
},
|
|
3888
|
+
animations: {
|
|
3889
|
+
enabled: true,
|
|
3890
|
+
duration: {
|
|
3891
|
+
fast: '150ms',
|
|
3892
|
+
normal: '300ms',
|
|
3893
|
+
slow: '500ms',
|
|
3894
|
+
},
|
|
3895
|
+
easing: {
|
|
3896
|
+
default: 'cubic-bezier(0.4, 0, 0.2, 1)',
|
|
3897
|
+
smooth: 'cubic-bezier(0.25, 0.46, 0.45, 0.94)',
|
|
3898
|
+
bounce: 'cubic-bezier(0.68, -0.55, 0.265, 1.55)',
|
|
3899
|
+
},
|
|
3900
|
+
},
|
|
3901
|
+
shadows: {
|
|
3902
|
+
sm: '0 1px 2px rgba(0, 0, 0, 0.5)',
|
|
3903
|
+
md: '0 4px 6px rgba(0, 0, 0, 0.6)',
|
|
3904
|
+
lg: '0 10px 15px rgba(0, 0, 0, 0.7)',
|
|
3905
|
+
xl: '0 20px 25px rgba(0, 0, 0, 0.8)',
|
|
3906
|
+
card: '0px 4px 12px rgba(0, 0, 0, 0.6), 0 0 20px rgba(59, 130, 246, 0.2)',
|
|
3907
|
+
cardHover: '0px 4px 24px rgba(59, 130, 246, 0.3), 0 0 30px rgba(59, 130, 246, 0.25)',
|
|
3908
|
+
glow: '0 0 20px rgba(59, 130, 246, 0.8)',
|
|
3909
|
+
focus: '0 0 0 2px #3B82F6, 0 0 8px 2px rgba(59, 130, 246, 0.8)',
|
|
3910
|
+
},
|
|
3911
|
+
},
|
|
3912
|
+
branding: {
|
|
3913
|
+
primaryColor: '#3B82F6',
|
|
3914
|
+
},
|
|
3915
|
+
glow: {
|
|
3916
|
+
primary: 'rgba(59, 130, 246, 0.4)',
|
|
3917
|
+
secondary: 'rgba(59, 130, 246, 0.6)',
|
|
3918
|
+
card: 'rgba(59, 130, 246, 0.2)',
|
|
3919
|
+
cardHover: 'rgba(59, 130, 246, 0.3)',
|
|
3920
|
+
button: 'rgba(59, 130, 246, 0.6)',
|
|
3921
|
+
focus: 'rgba(59, 130, 246, 0.8)',
|
|
3922
|
+
scrollbar: 'rgba(59, 130, 246, 0.4)',
|
|
3923
|
+
},
|
|
3924
|
+
gradients: {
|
|
3925
|
+
start: 'rgba(59, 130, 246, 0.08)',
|
|
3926
|
+
end: 'rgba(59, 130, 246, 0.03)',
|
|
3927
|
+
hoverStart: 'rgba(59, 130, 246, 0.15)',
|
|
3928
|
+
hoverEnd: 'rgba(59, 130, 246, 0.08)',
|
|
3929
|
+
},
|
|
3930
|
+
};
|
|
3931
|
+
// Purple theme
|
|
3932
|
+
const purpleTheme = {
|
|
3933
|
+
mode: 'dark',
|
|
3934
|
+
colors: {
|
|
3935
|
+
background: {
|
|
3936
|
+
primary: '#1a1a1a',
|
|
3937
|
+
secondary: '#2a2a2a',
|
|
3938
|
+
tertiary: '#3a3a3a',
|
|
3939
|
+
accent: 'rgba(168, 85, 247, 0.1)',
|
|
3940
|
+
glass: 'rgba(255, 255, 255, 0.05)',
|
|
3941
|
+
},
|
|
3942
|
+
status: {
|
|
3943
|
+
connected: '#A855F7',
|
|
3539
3944
|
disconnected: '#EF4444',
|
|
3540
3945
|
warning: '#F59E0B',
|
|
3541
3946
|
pending: '#8B5CF6',
|
|
@@ -3578,9 +3983,135 @@ const purpleTheme = {
|
|
|
3578
3983
|
},
|
|
3579
3984
|
},
|
|
3580
3985
|
},
|
|
3986
|
+
typography: {
|
|
3987
|
+
fontFamily: {
|
|
3988
|
+
primary: 'Orbitron, Futura, Inter, system-ui, sans-serif',
|
|
3989
|
+
secondary: 'Orbitron, Futura, Inter, system-ui, sans-serif',
|
|
3990
|
+
},
|
|
3991
|
+
fontSize: {
|
|
3992
|
+
xs: '0.75rem',
|
|
3993
|
+
sm: '0.875rem',
|
|
3994
|
+
base: '1rem',
|
|
3995
|
+
lg: '1.125rem',
|
|
3996
|
+
xl: '1.25rem',
|
|
3997
|
+
'2xl': '1.5rem',
|
|
3998
|
+
'3xl': '1.875rem',
|
|
3999
|
+
'4xl': '2.25rem',
|
|
4000
|
+
},
|
|
4001
|
+
fontWeight: {
|
|
4002
|
+
normal: 400,
|
|
4003
|
+
medium: 500,
|
|
4004
|
+
semibold: 600,
|
|
4005
|
+
bold: 700,
|
|
4006
|
+
extrabold: 800,
|
|
4007
|
+
},
|
|
4008
|
+
lineHeight: {
|
|
4009
|
+
tight: '1.25',
|
|
4010
|
+
normal: '1.5',
|
|
4011
|
+
relaxed: '1.75',
|
|
4012
|
+
},
|
|
4013
|
+
},
|
|
4014
|
+
spacing: {
|
|
4015
|
+
xs: '0.25rem',
|
|
4016
|
+
sm: '0.5rem',
|
|
4017
|
+
md: '1rem',
|
|
4018
|
+
lg: '1.5rem',
|
|
4019
|
+
xl: '2rem',
|
|
4020
|
+
'2xl': '3rem',
|
|
4021
|
+
'3xl': '4rem',
|
|
4022
|
+
},
|
|
4023
|
+
layout: {
|
|
4024
|
+
containerMaxWidth: '1440px',
|
|
4025
|
+
gridGap: '1rem',
|
|
4026
|
+
cardPadding: '1.5rem',
|
|
4027
|
+
borderRadius: {
|
|
4028
|
+
sm: '0.25rem',
|
|
4029
|
+
md: '0.5rem',
|
|
4030
|
+
lg: '0.75rem',
|
|
4031
|
+
xl: '1rem',
|
|
4032
|
+
'2xl': '1.5rem',
|
|
4033
|
+
full: '9999px',
|
|
4034
|
+
},
|
|
4035
|
+
},
|
|
4036
|
+
components: {
|
|
4037
|
+
brokerCard: {
|
|
4038
|
+
width: '100%',
|
|
4039
|
+
height: '180px',
|
|
4040
|
+
logoSize: '64px',
|
|
4041
|
+
padding: '1.5rem',
|
|
4042
|
+
},
|
|
4043
|
+
statusIndicator: {
|
|
4044
|
+
size: '22px',
|
|
4045
|
+
glowIntensity: 0.9,
|
|
4046
|
+
},
|
|
4047
|
+
modal: {
|
|
4048
|
+
background: 'rgba(0, 0, 0, 0.95)',
|
|
4049
|
+
backdrop: 'rgba(0, 0, 0, 0.8)',
|
|
4050
|
+
},
|
|
4051
|
+
brokerCardModern: {
|
|
4052
|
+
width: '150px',
|
|
4053
|
+
height: '150px',
|
|
4054
|
+
padding: '16px',
|
|
4055
|
+
logoSize: '48px',
|
|
4056
|
+
statusSize: '22px',
|
|
4057
|
+
},
|
|
4058
|
+
connectButton: {
|
|
4059
|
+
width: '120px',
|
|
4060
|
+
height: '120px',
|
|
4061
|
+
},
|
|
4062
|
+
themeSwitcher: {
|
|
4063
|
+
indicatorSize: '24px',
|
|
4064
|
+
},
|
|
4065
|
+
},
|
|
4066
|
+
effects: {
|
|
4067
|
+
glassmorphism: {
|
|
4068
|
+
enabled: true,
|
|
4069
|
+
blur: '12px',
|
|
4070
|
+
opacity: 0.15,
|
|
4071
|
+
border: 'rgba(168, 85, 247, 0.3)',
|
|
4072
|
+
},
|
|
4073
|
+
animations: {
|
|
4074
|
+
enabled: true,
|
|
4075
|
+
duration: {
|
|
4076
|
+
fast: '150ms',
|
|
4077
|
+
normal: '300ms',
|
|
4078
|
+
slow: '500ms',
|
|
4079
|
+
},
|
|
4080
|
+
easing: {
|
|
4081
|
+
default: 'cubic-bezier(0.4, 0, 0.2, 1)',
|
|
4082
|
+
smooth: 'cubic-bezier(0.25, 0.46, 0.45, 0.94)',
|
|
4083
|
+
bounce: 'cubic-bezier(0.68, -0.55, 0.265, 1.55)',
|
|
4084
|
+
},
|
|
4085
|
+
},
|
|
4086
|
+
shadows: {
|
|
4087
|
+
sm: '0 1px 2px rgba(0, 0, 0, 0.5)',
|
|
4088
|
+
md: '0 4px 6px rgba(0, 0, 0, 0.6)',
|
|
4089
|
+
lg: '0 10px 15px rgba(0, 0, 0, 0.7)',
|
|
4090
|
+
xl: '0 20px 25px rgba(0, 0, 0, 0.8)',
|
|
4091
|
+
card: '0px 4px 12px rgba(0, 0, 0, 0.6), 0 0 20px rgba(168, 85, 247, 0.2)',
|
|
4092
|
+
cardHover: '0px 4px 24px rgba(168, 85, 247, 0.3), 0 0 30px rgba(168, 85, 247, 0.25)',
|
|
4093
|
+
glow: '0 0 20px rgba(168, 85, 247, 0.8)',
|
|
4094
|
+
focus: '0 0 0 2px #A855F7, 0 0 8px 2px rgba(168, 85, 247, 0.8)',
|
|
4095
|
+
},
|
|
4096
|
+
},
|
|
3581
4097
|
branding: {
|
|
3582
4098
|
primaryColor: '#A855F7',
|
|
3583
4099
|
},
|
|
4100
|
+
glow: {
|
|
4101
|
+
primary: 'rgba(168, 85, 247, 0.4)',
|
|
4102
|
+
secondary: 'rgba(168, 85, 247, 0.6)',
|
|
4103
|
+
card: 'rgba(168, 85, 247, 0.2)',
|
|
4104
|
+
cardHover: 'rgba(168, 85, 247, 0.3)',
|
|
4105
|
+
button: 'rgba(168, 85, 247, 0.6)',
|
|
4106
|
+
focus: 'rgba(168, 85, 247, 0.8)',
|
|
4107
|
+
scrollbar: 'rgba(168, 85, 247, 0.4)',
|
|
4108
|
+
},
|
|
4109
|
+
gradients: {
|
|
4110
|
+
start: 'rgba(168, 85, 247, 0.08)',
|
|
4111
|
+
end: 'rgba(168, 85, 247, 0.03)',
|
|
4112
|
+
hoverStart: 'rgba(168, 85, 247, 0.15)',
|
|
4113
|
+
hoverEnd: 'rgba(168, 85, 247, 0.08)',
|
|
4114
|
+
},
|
|
3584
4115
|
};
|
|
3585
4116
|
// Green theme
|
|
3586
4117
|
const greenTheme = {
|
|
@@ -3637,9 +4168,135 @@ const greenTheme = {
|
|
|
3637
4168
|
},
|
|
3638
4169
|
},
|
|
3639
4170
|
},
|
|
4171
|
+
typography: {
|
|
4172
|
+
fontFamily: {
|
|
4173
|
+
primary: 'Orbitron, Futura, Inter, system-ui, sans-serif',
|
|
4174
|
+
secondary: 'Orbitron, Futura, Inter, system-ui, sans-serif',
|
|
4175
|
+
},
|
|
4176
|
+
fontSize: {
|
|
4177
|
+
xs: '0.75rem',
|
|
4178
|
+
sm: '0.875rem',
|
|
4179
|
+
base: '1rem',
|
|
4180
|
+
lg: '1.125rem',
|
|
4181
|
+
xl: '1.25rem',
|
|
4182
|
+
'2xl': '1.5rem',
|
|
4183
|
+
'3xl': '1.875rem',
|
|
4184
|
+
'4xl': '2.25rem',
|
|
4185
|
+
},
|
|
4186
|
+
fontWeight: {
|
|
4187
|
+
normal: 400,
|
|
4188
|
+
medium: 500,
|
|
4189
|
+
semibold: 600,
|
|
4190
|
+
bold: 700,
|
|
4191
|
+
extrabold: 800,
|
|
4192
|
+
},
|
|
4193
|
+
lineHeight: {
|
|
4194
|
+
tight: '1.25',
|
|
4195
|
+
normal: '1.5',
|
|
4196
|
+
relaxed: '1.75',
|
|
4197
|
+
},
|
|
4198
|
+
},
|
|
4199
|
+
spacing: {
|
|
4200
|
+
xs: '0.25rem',
|
|
4201
|
+
sm: '0.5rem',
|
|
4202
|
+
md: '1rem',
|
|
4203
|
+
lg: '1.5rem',
|
|
4204
|
+
xl: '2rem',
|
|
4205
|
+
'2xl': '3rem',
|
|
4206
|
+
'3xl': '4rem',
|
|
4207
|
+
},
|
|
4208
|
+
layout: {
|
|
4209
|
+
containerMaxWidth: '1440px',
|
|
4210
|
+
gridGap: '1rem',
|
|
4211
|
+
cardPadding: '1.5rem',
|
|
4212
|
+
borderRadius: {
|
|
4213
|
+
sm: '0.25rem',
|
|
4214
|
+
md: '0.5rem',
|
|
4215
|
+
lg: '0.75rem',
|
|
4216
|
+
xl: '1rem',
|
|
4217
|
+
'2xl': '1.5rem',
|
|
4218
|
+
full: '9999px',
|
|
4219
|
+
},
|
|
4220
|
+
},
|
|
4221
|
+
components: {
|
|
4222
|
+
brokerCard: {
|
|
4223
|
+
width: '100%',
|
|
4224
|
+
height: '180px',
|
|
4225
|
+
logoSize: '64px',
|
|
4226
|
+
padding: '1.5rem',
|
|
4227
|
+
},
|
|
4228
|
+
statusIndicator: {
|
|
4229
|
+
size: '22px',
|
|
4230
|
+
glowIntensity: 0.9,
|
|
4231
|
+
},
|
|
4232
|
+
modal: {
|
|
4233
|
+
background: 'rgba(0, 0, 0, 0.95)',
|
|
4234
|
+
backdrop: 'rgba(0, 0, 0, 0.8)',
|
|
4235
|
+
},
|
|
4236
|
+
brokerCardModern: {
|
|
4237
|
+
width: '150px',
|
|
4238
|
+
height: '150px',
|
|
4239
|
+
padding: '16px',
|
|
4240
|
+
logoSize: '48px',
|
|
4241
|
+
statusSize: '22px',
|
|
4242
|
+
},
|
|
4243
|
+
connectButton: {
|
|
4244
|
+
width: '120px',
|
|
4245
|
+
height: '120px',
|
|
4246
|
+
},
|
|
4247
|
+
themeSwitcher: {
|
|
4248
|
+
indicatorSize: '24px',
|
|
4249
|
+
},
|
|
4250
|
+
},
|
|
4251
|
+
effects: {
|
|
4252
|
+
glassmorphism: {
|
|
4253
|
+
enabled: true,
|
|
4254
|
+
blur: '12px',
|
|
4255
|
+
opacity: 0.15,
|
|
4256
|
+
border: 'rgba(34, 197, 94, 0.3)',
|
|
4257
|
+
},
|
|
4258
|
+
animations: {
|
|
4259
|
+
enabled: true,
|
|
4260
|
+
duration: {
|
|
4261
|
+
fast: '150ms',
|
|
4262
|
+
normal: '300ms',
|
|
4263
|
+
slow: '500ms',
|
|
4264
|
+
},
|
|
4265
|
+
easing: {
|
|
4266
|
+
default: 'cubic-bezier(0.4, 0, 0.2, 1)',
|
|
4267
|
+
smooth: 'cubic-bezier(0.25, 0.46, 0.45, 0.94)',
|
|
4268
|
+
bounce: 'cubic-bezier(0.68, -0.55, 0.265, 1.55)',
|
|
4269
|
+
},
|
|
4270
|
+
},
|
|
4271
|
+
shadows: {
|
|
4272
|
+
sm: '0 1px 2px rgba(0, 0, 0, 0.5)',
|
|
4273
|
+
md: '0 4px 6px rgba(0, 0, 0, 0.6)',
|
|
4274
|
+
lg: '0 10px 15px rgba(0, 0, 0, 0.7)',
|
|
4275
|
+
xl: '0 20px 25px rgba(0, 0, 0, 0.8)',
|
|
4276
|
+
card: '0px 4px 12px rgba(0, 0, 0, 0.6), 0 0 20px rgba(34, 197, 94, 0.2)',
|
|
4277
|
+
cardHover: '0px 4px 24px rgba(34, 197, 94, 0.3), 0 0 30px rgba(34, 197, 94, 0.25)',
|
|
4278
|
+
glow: '0 0 20px rgba(34, 197, 94, 0.8)',
|
|
4279
|
+
focus: '0 0 0 2px #22C55E, 0 0 8px 2px rgba(34, 197, 94, 0.8)',
|
|
4280
|
+
},
|
|
4281
|
+
},
|
|
3640
4282
|
branding: {
|
|
3641
4283
|
primaryColor: '#22C55E',
|
|
3642
4284
|
},
|
|
4285
|
+
glow: {
|
|
4286
|
+
primary: 'rgba(34, 197, 94, 0.4)',
|
|
4287
|
+
secondary: 'rgba(34, 197, 94, 0.6)',
|
|
4288
|
+
card: 'rgba(34, 197, 94, 0.2)',
|
|
4289
|
+
cardHover: 'rgba(34, 197, 94, 0.3)',
|
|
4290
|
+
button: 'rgba(34, 197, 94, 0.6)',
|
|
4291
|
+
focus: 'rgba(34, 197, 94, 0.8)',
|
|
4292
|
+
scrollbar: 'rgba(34, 197, 94, 0.4)',
|
|
4293
|
+
},
|
|
4294
|
+
gradients: {
|
|
4295
|
+
start: 'rgba(34, 197, 94, 0.08)',
|
|
4296
|
+
end: 'rgba(34, 197, 94, 0.03)',
|
|
4297
|
+
hoverStart: 'rgba(34, 197, 94, 0.15)',
|
|
4298
|
+
hoverEnd: 'rgba(34, 197, 94, 0.08)',
|
|
4299
|
+
},
|
|
3643
4300
|
};
|
|
3644
4301
|
// Orange theme
|
|
3645
4302
|
const orangeTheme = {
|
|
@@ -3696,9 +4353,135 @@ const orangeTheme = {
|
|
|
3696
4353
|
},
|
|
3697
4354
|
},
|
|
3698
4355
|
},
|
|
4356
|
+
typography: {
|
|
4357
|
+
fontFamily: {
|
|
4358
|
+
primary: 'Orbitron, Futura, Inter, system-ui, sans-serif',
|
|
4359
|
+
secondary: 'Orbitron, Futura, Inter, system-ui, sans-serif',
|
|
4360
|
+
},
|
|
4361
|
+
fontSize: {
|
|
4362
|
+
xs: '0.75rem',
|
|
4363
|
+
sm: '0.875rem',
|
|
4364
|
+
base: '1rem',
|
|
4365
|
+
lg: '1.125rem',
|
|
4366
|
+
xl: '1.25rem',
|
|
4367
|
+
'2xl': '1.5rem',
|
|
4368
|
+
'3xl': '1.875rem',
|
|
4369
|
+
'4xl': '2.25rem',
|
|
4370
|
+
},
|
|
4371
|
+
fontWeight: {
|
|
4372
|
+
normal: 400,
|
|
4373
|
+
medium: 500,
|
|
4374
|
+
semibold: 600,
|
|
4375
|
+
bold: 700,
|
|
4376
|
+
extrabold: 800,
|
|
4377
|
+
},
|
|
4378
|
+
lineHeight: {
|
|
4379
|
+
tight: '1.25',
|
|
4380
|
+
normal: '1.5',
|
|
4381
|
+
relaxed: '1.75',
|
|
4382
|
+
},
|
|
4383
|
+
},
|
|
4384
|
+
spacing: {
|
|
4385
|
+
xs: '0.25rem',
|
|
4386
|
+
sm: '0.5rem',
|
|
4387
|
+
md: '1rem',
|
|
4388
|
+
lg: '1.5rem',
|
|
4389
|
+
xl: '2rem',
|
|
4390
|
+
'2xl': '3rem',
|
|
4391
|
+
'3xl': '4rem',
|
|
4392
|
+
},
|
|
4393
|
+
layout: {
|
|
4394
|
+
containerMaxWidth: '1440px',
|
|
4395
|
+
gridGap: '1rem',
|
|
4396
|
+
cardPadding: '1.5rem',
|
|
4397
|
+
borderRadius: {
|
|
4398
|
+
sm: '0.25rem',
|
|
4399
|
+
md: '0.5rem',
|
|
4400
|
+
lg: '0.75rem',
|
|
4401
|
+
xl: '1rem',
|
|
4402
|
+
'2xl': '1.5rem',
|
|
4403
|
+
full: '9999px',
|
|
4404
|
+
},
|
|
4405
|
+
},
|
|
4406
|
+
components: {
|
|
4407
|
+
brokerCard: {
|
|
4408
|
+
width: '100%',
|
|
4409
|
+
height: '180px',
|
|
4410
|
+
logoSize: '64px',
|
|
4411
|
+
padding: '1.5rem',
|
|
4412
|
+
},
|
|
4413
|
+
statusIndicator: {
|
|
4414
|
+
size: '22px',
|
|
4415
|
+
glowIntensity: 0.9,
|
|
4416
|
+
},
|
|
4417
|
+
modal: {
|
|
4418
|
+
background: 'rgba(0, 0, 0, 0.95)',
|
|
4419
|
+
backdrop: 'rgba(0, 0, 0, 0.8)',
|
|
4420
|
+
},
|
|
4421
|
+
brokerCardModern: {
|
|
4422
|
+
width: '150px',
|
|
4423
|
+
height: '150px',
|
|
4424
|
+
padding: '16px',
|
|
4425
|
+
logoSize: '48px',
|
|
4426
|
+
statusSize: '22px',
|
|
4427
|
+
},
|
|
4428
|
+
connectButton: {
|
|
4429
|
+
width: '120px',
|
|
4430
|
+
height: '120px',
|
|
4431
|
+
},
|
|
4432
|
+
themeSwitcher: {
|
|
4433
|
+
indicatorSize: '24px',
|
|
4434
|
+
},
|
|
4435
|
+
},
|
|
4436
|
+
effects: {
|
|
4437
|
+
glassmorphism: {
|
|
4438
|
+
enabled: true,
|
|
4439
|
+
blur: '12px',
|
|
4440
|
+
opacity: 0.15,
|
|
4441
|
+
border: 'rgba(249, 115, 22, 0.3)',
|
|
4442
|
+
},
|
|
4443
|
+
animations: {
|
|
4444
|
+
enabled: true,
|
|
4445
|
+
duration: {
|
|
4446
|
+
fast: '150ms',
|
|
4447
|
+
normal: '300ms',
|
|
4448
|
+
slow: '500ms',
|
|
4449
|
+
},
|
|
4450
|
+
easing: {
|
|
4451
|
+
default: 'cubic-bezier(0.4, 0, 0.2, 1)',
|
|
4452
|
+
smooth: 'cubic-bezier(0.25, 0.46, 0.45, 0.94)',
|
|
4453
|
+
bounce: 'cubic-bezier(0.68, -0.55, 0.265, 1.55)',
|
|
4454
|
+
},
|
|
4455
|
+
},
|
|
4456
|
+
shadows: {
|
|
4457
|
+
sm: '0 1px 2px rgba(0, 0, 0, 0.5)',
|
|
4458
|
+
md: '0 4px 6px rgba(0, 0, 0, 0.6)',
|
|
4459
|
+
lg: '0 10px 15px rgba(0, 0, 0, 0.7)',
|
|
4460
|
+
xl: '0 20px 25px rgba(0, 0, 0, 0.8)',
|
|
4461
|
+
card: '0px 4px 12px rgba(0, 0, 0, 0.6), 0 0 20px rgba(249, 115, 22, 0.2)',
|
|
4462
|
+
cardHover: '0px 4px 24px rgba(249, 115, 22, 0.3), 0 0 30px rgba(249, 115, 22, 0.25)',
|
|
4463
|
+
glow: '0 0 20px rgba(249, 115, 22, 0.8)',
|
|
4464
|
+
focus: '0 0 0 2px #F97316, 0 0 8px 2px rgba(249, 115, 22, 0.8)',
|
|
4465
|
+
},
|
|
4466
|
+
},
|
|
3699
4467
|
branding: {
|
|
3700
4468
|
primaryColor: '#F97316',
|
|
3701
4469
|
},
|
|
4470
|
+
glow: {
|
|
4471
|
+
primary: 'rgba(249, 115, 22, 0.4)',
|
|
4472
|
+
secondary: 'rgba(249, 115, 22, 0.6)',
|
|
4473
|
+
card: 'rgba(249, 115, 22, 0.2)',
|
|
4474
|
+
cardHover: 'rgba(249, 115, 22, 0.3)',
|
|
4475
|
+
button: 'rgba(249, 115, 22, 0.6)',
|
|
4476
|
+
focus: 'rgba(249, 115, 22, 0.8)',
|
|
4477
|
+
scrollbar: 'rgba(249, 115, 22, 0.4)',
|
|
4478
|
+
},
|
|
4479
|
+
gradients: {
|
|
4480
|
+
start: 'rgba(249, 115, 22, 0.08)',
|
|
4481
|
+
end: 'rgba(249, 115, 22, 0.03)',
|
|
4482
|
+
hoverStart: 'rgba(249, 115, 22, 0.15)',
|
|
4483
|
+
hoverEnd: 'rgba(249, 115, 22, 0.08)',
|
|
4484
|
+
},
|
|
3702
4485
|
};
|
|
3703
4486
|
// Theme preset mapping
|
|
3704
4487
|
const portalThemePresets = {
|
|
@@ -3783,17 +4566,36 @@ function getThemePreset(preset) {
|
|
|
3783
4566
|
*/
|
|
3784
4567
|
function validateCustomTheme(theme) {
|
|
3785
4568
|
try {
|
|
3786
|
-
//
|
|
3787
|
-
if (
|
|
4569
|
+
// Only validate what's provided - everything else gets defaults
|
|
4570
|
+
if (theme.mode && !['dark', 'light', 'auto'].includes(theme.mode)) {
|
|
3788
4571
|
return false;
|
|
3789
4572
|
}
|
|
3790
|
-
|
|
3791
|
-
|
|
4573
|
+
// If colors are provided, validate the structure
|
|
4574
|
+
if (theme.colors) {
|
|
4575
|
+
// Check that any provided color sections have valid structure
|
|
4576
|
+
const colorSections = ['background', 'status', 'text', 'border', 'input', 'button'];
|
|
4577
|
+
for (const section of colorSections) {
|
|
4578
|
+
const colorSection = theme.colors[section];
|
|
4579
|
+
if (colorSection && typeof colorSection !== 'object') {
|
|
4580
|
+
return false;
|
|
4581
|
+
}
|
|
4582
|
+
}
|
|
3792
4583
|
}
|
|
3793
|
-
//
|
|
3794
|
-
|
|
3795
|
-
|
|
3796
|
-
|
|
4584
|
+
// If typography is provided, validate structure
|
|
4585
|
+
if (theme.typography) {
|
|
4586
|
+
if (theme.typography.fontSize && typeof theme.typography.fontSize !== 'object') {
|
|
4587
|
+
return false;
|
|
4588
|
+
}
|
|
4589
|
+
if (theme.typography.fontWeight && typeof theme.typography.fontWeight !== 'object') {
|
|
4590
|
+
return false;
|
|
4591
|
+
}
|
|
4592
|
+
}
|
|
4593
|
+
// If effects are provided, validate structure
|
|
4594
|
+
if (theme.effects) {
|
|
4595
|
+
if (theme.effects.animations && typeof theme.effects.animations !== 'object') {
|
|
4596
|
+
return false;
|
|
4597
|
+
}
|
|
4598
|
+
if (theme.effects.shadows && typeof theme.effects.shadows !== 'object') {
|
|
3797
4599
|
return false;
|
|
3798
4600
|
}
|
|
3799
4601
|
}
|
|
@@ -3825,12 +4627,14 @@ function createCustomThemeFromPreset(preset, modifications) {
|
|
|
3825
4627
|
/**
|
|
3826
4628
|
* Broker filtering utility functions
|
|
3827
4629
|
*/
|
|
3828
|
-
// Supported broker names and their corresponding IDs
|
|
4630
|
+
// Supported broker names and their corresponding IDs (including aliases)
|
|
3829
4631
|
const SUPPORTED_BROKERS = {
|
|
3830
4632
|
'alpaca': 'alpaca',
|
|
3831
4633
|
'robinhood': 'robinhood',
|
|
3832
4634
|
'tasty_trade': 'tasty_trade',
|
|
3833
|
-
'ninja_trader': 'ninja_trader'
|
|
4635
|
+
'ninja_trader': 'ninja_trader',
|
|
4636
|
+
'tradovate': 'tradovate', // Alias for ninja_trader
|
|
4637
|
+
'interactive_brokers': 'interactive_brokers',
|
|
3834
4638
|
};
|
|
3835
4639
|
/**
|
|
3836
4640
|
* Convert broker names to broker IDs, filtering out unsupported ones
|
|
@@ -3970,6 +4774,13 @@ class FinaticConnect extends EventEmitter {
|
|
|
3970
4774
|
this.userToken?.refreshToken &&
|
|
3971
4775
|
this.userToken?.user_id);
|
|
3972
4776
|
}
|
|
4777
|
+
/**
|
|
4778
|
+
* Check if the client is authenticated (alias for isAuthed for consistency)
|
|
4779
|
+
* @returns True if authenticated, false otherwise
|
|
4780
|
+
*/
|
|
4781
|
+
is_authenticated() {
|
|
4782
|
+
return this.isAuthed();
|
|
4783
|
+
}
|
|
3973
4784
|
/**
|
|
3974
4785
|
* Get user's orders with pagination and optional filtering
|
|
3975
4786
|
* @param params - Query parameters including page, perPage, and filters
|
|
@@ -4013,20 +4824,18 @@ class FinaticConnect extends EventEmitter {
|
|
|
4013
4824
|
return this.getAccountsPage(page, perPage, filter);
|
|
4014
4825
|
}
|
|
4015
4826
|
/**
|
|
4016
|
-
*
|
|
4827
|
+
* Get user's balances with pagination and optional filtering
|
|
4828
|
+
* @param params - Query parameters including page, perPage, and filters
|
|
4829
|
+
* @returns Promise with paginated result that supports navigation
|
|
4017
4830
|
*/
|
|
4018
|
-
async
|
|
4019
|
-
if (!this.
|
|
4020
|
-
|
|
4021
|
-
}
|
|
4022
|
-
try {
|
|
4023
|
-
await this.apiClient.revokeToken(this.userToken.accessToken);
|
|
4024
|
-
this.userToken = null;
|
|
4025
|
-
}
|
|
4026
|
-
catch (error) {
|
|
4027
|
-
this.emit('error', error);
|
|
4028
|
-
throw error;
|
|
4831
|
+
async getBalances(params) {
|
|
4832
|
+
if (!this.isAuthed()) {
|
|
4833
|
+
throw new AuthenticationError('User is not authenticated');
|
|
4029
4834
|
}
|
|
4835
|
+
const page = params?.page || 1;
|
|
4836
|
+
const perPage = params?.perPage || 100;
|
|
4837
|
+
const filter = params?.filter;
|
|
4838
|
+
return this.getBalancesPage(page, perPage, filter);
|
|
4030
4839
|
}
|
|
4031
4840
|
/**
|
|
4032
4841
|
* Initialize the Finatic Connect SDK
|
|
@@ -4115,9 +4924,33 @@ class FinaticConnect extends EventEmitter {
|
|
|
4115
4924
|
async setUserId(userId) {
|
|
4116
4925
|
await this.initializeWithUser(userId);
|
|
4117
4926
|
}
|
|
4927
|
+
/**
|
|
4928
|
+
* Get the user and tokens for a completed session
|
|
4929
|
+
* @returns Promise with user information and tokens
|
|
4930
|
+
*/
|
|
4931
|
+
async getSessionUser() {
|
|
4932
|
+
if (!this.isAuthed()) {
|
|
4933
|
+
throw new AuthenticationError('User is not authenticated');
|
|
4934
|
+
}
|
|
4935
|
+
if (!this.userToken) {
|
|
4936
|
+
throw new AuthenticationError('No user token available');
|
|
4937
|
+
}
|
|
4938
|
+
return {
|
|
4939
|
+
user_id: this.userToken.userId,
|
|
4940
|
+
access_token: this.userToken.accessToken,
|
|
4941
|
+
refresh_token: this.userToken.refreshToken,
|
|
4942
|
+
expires_in: this.userToken.expiresIn,
|
|
4943
|
+
token_type: this.userToken.tokenType,
|
|
4944
|
+
scope: this.userToken.scope,
|
|
4945
|
+
company_id: this.companyId
|
|
4946
|
+
};
|
|
4947
|
+
}
|
|
4118
4948
|
async initializeWithUser(userId) {
|
|
4119
4949
|
try {
|
|
4120
|
-
|
|
4950
|
+
if (!this.sessionId) {
|
|
4951
|
+
throw new SessionError('Session not initialized');
|
|
4952
|
+
}
|
|
4953
|
+
this.userToken = await this.apiClient.getUserToken(this.sessionId);
|
|
4121
4954
|
// Set tokens in ApiClient for automatic token management
|
|
4122
4955
|
if (this.userToken) {
|
|
4123
4956
|
const expiresAt = new Date(Date.now() + 3600 * 1000).toISOString(); // 1 hour from now
|
|
@@ -4161,20 +4994,8 @@ class FinaticConnect extends EventEmitter {
|
|
|
4161
4994
|
this.apiClient.setSessionContext(this.sessionId, this.companyId, startResponse.data.csrf_token // If available in response
|
|
4162
4995
|
);
|
|
4163
4996
|
}
|
|
4164
|
-
//
|
|
4165
|
-
|
|
4166
|
-
let attempts = 0;
|
|
4167
|
-
while (attempts < maxAttempts) {
|
|
4168
|
-
const sessionResponse = await this.apiClient.validatePortalSession(this.sessionId, '');
|
|
4169
|
-
if (sessionResponse.status === 'active') {
|
|
4170
|
-
break;
|
|
4171
|
-
}
|
|
4172
|
-
await new Promise(resolve => setTimeout(resolve, 1000)); // Wait 1 second between attempts
|
|
4173
|
-
attempts++;
|
|
4174
|
-
}
|
|
4175
|
-
if (attempts === maxAttempts) {
|
|
4176
|
-
throw new SessionError('Session failed to become active');
|
|
4177
|
-
}
|
|
4997
|
+
// Session is now active
|
|
4998
|
+
this.currentSessionState = SessionState.ACTIVE;
|
|
4178
4999
|
}
|
|
4179
5000
|
// Get portal URL
|
|
4180
5001
|
const portalResponse = await this.apiClient.getPortalUrl(this.sessionId);
|
|
@@ -4185,6 +5006,12 @@ class FinaticConnect extends EventEmitter {
|
|
|
4185
5006
|
let themedPortalUrl = appendThemeToURL(portalResponse.data.portal_url, options?.theme);
|
|
4186
5007
|
// Apply broker filter to portal URL if provided
|
|
4187
5008
|
themedPortalUrl = appendBrokerFilterToURL(themedPortalUrl, options?.brokers);
|
|
5009
|
+
// Apply email parameter to portal URL if provided
|
|
5010
|
+
if (options?.email) {
|
|
5011
|
+
const url = new URL(themedPortalUrl);
|
|
5012
|
+
url.searchParams.set('email', options.email);
|
|
5013
|
+
themedPortalUrl = url.toString();
|
|
5014
|
+
}
|
|
4188
5015
|
// Create portal UI if not exists
|
|
4189
5016
|
if (!this.portalUI) {
|
|
4190
5017
|
this.portalUI = new PortalUI(this.baseUrl);
|
|
@@ -4280,21 +5107,8 @@ class FinaticConnect extends EventEmitter {
|
|
|
4280
5107
|
}
|
|
4281
5108
|
// For non-direct auth, we need to wait for the session to be ACTIVE
|
|
4282
5109
|
if (response.data.state === SessionState.PENDING) {
|
|
4283
|
-
//
|
|
4284
|
-
|
|
4285
|
-
let attempts = 0;
|
|
4286
|
-
while (attempts < maxAttempts) {
|
|
4287
|
-
const sessionResponse = await this.apiClient.validatePortalSession(this.sessionId, '');
|
|
4288
|
-
if (sessionResponse.status === 'active') {
|
|
4289
|
-
this.currentSessionState = SessionState.ACTIVE;
|
|
4290
|
-
break;
|
|
4291
|
-
}
|
|
4292
|
-
await new Promise(resolve => setTimeout(resolve, 1000)); // Wait 1 second between attempts
|
|
4293
|
-
attempts++;
|
|
4294
|
-
}
|
|
4295
|
-
if (attempts === maxAttempts) {
|
|
4296
|
-
throw new SessionError('Session failed to become active');
|
|
4297
|
-
}
|
|
5110
|
+
// Session is now active
|
|
5111
|
+
this.currentSessionState = SessionState.ACTIVE;
|
|
4298
5112
|
}
|
|
4299
5113
|
}
|
|
4300
5114
|
catch (error) {
|
|
@@ -4452,6 +5266,138 @@ class FinaticConnect extends EventEmitter {
|
|
|
4452
5266
|
throw error;
|
|
4453
5267
|
}
|
|
4454
5268
|
}
|
|
5269
|
+
/**
|
|
5270
|
+
* Place a stock stop order (convenience method)
|
|
5271
|
+
*/
|
|
5272
|
+
async placeStockStopOrder(symbol, quantity, side, stopPrice, timeInForce = 'gtc', broker, accountNumber) {
|
|
5273
|
+
if (!this.userToken) {
|
|
5274
|
+
throw new Error('Not initialized with user');
|
|
5275
|
+
}
|
|
5276
|
+
try {
|
|
5277
|
+
return await this.apiClient.placeStockStopOrder(symbol, quantity, side === 'buy' ? 'Buy' : 'Sell', stopPrice, timeInForce, broker, accountNumber);
|
|
5278
|
+
}
|
|
5279
|
+
catch (error) {
|
|
5280
|
+
this.emit('error', error);
|
|
5281
|
+
throw error;
|
|
5282
|
+
}
|
|
5283
|
+
}
|
|
5284
|
+
/**
|
|
5285
|
+
* Place a crypto market order (convenience method)
|
|
5286
|
+
*/
|
|
5287
|
+
async placeCryptoMarketOrder(symbol, quantity, side, broker, accountNumber) {
|
|
5288
|
+
if (!this.userToken) {
|
|
5289
|
+
throw new Error('Not initialized with user');
|
|
5290
|
+
}
|
|
5291
|
+
try {
|
|
5292
|
+
return await this.apiClient.placeCryptoMarketOrder(symbol, quantity, side === 'buy' ? 'Buy' : 'Sell', broker, accountNumber);
|
|
5293
|
+
}
|
|
5294
|
+
catch (error) {
|
|
5295
|
+
this.emit('error', error);
|
|
5296
|
+
throw error;
|
|
5297
|
+
}
|
|
5298
|
+
}
|
|
5299
|
+
/**
|
|
5300
|
+
* Place a crypto limit order (convenience method)
|
|
5301
|
+
*/
|
|
5302
|
+
async placeCryptoLimitOrder(symbol, quantity, side, price, timeInForce = 'gtc', broker, accountNumber) {
|
|
5303
|
+
if (!this.userToken) {
|
|
5304
|
+
throw new Error('Not initialized with user');
|
|
5305
|
+
}
|
|
5306
|
+
try {
|
|
5307
|
+
return await this.apiClient.placeCryptoLimitOrder(symbol, quantity, side === 'buy' ? 'Buy' : 'Sell', price, timeInForce, broker, accountNumber);
|
|
5308
|
+
}
|
|
5309
|
+
catch (error) {
|
|
5310
|
+
this.emit('error', error);
|
|
5311
|
+
throw error;
|
|
5312
|
+
}
|
|
5313
|
+
}
|
|
5314
|
+
/**
|
|
5315
|
+
* Place an options market order (convenience method)
|
|
5316
|
+
*/
|
|
5317
|
+
async placeOptionsMarketOrder(symbol, quantity, side, broker, accountNumber) {
|
|
5318
|
+
if (!this.userToken) {
|
|
5319
|
+
throw new Error('Not initialized with user');
|
|
5320
|
+
}
|
|
5321
|
+
try {
|
|
5322
|
+
return await this.apiClient.placeOptionsMarketOrder(symbol, quantity, side === 'buy' ? 'Buy' : 'Sell', broker, accountNumber);
|
|
5323
|
+
}
|
|
5324
|
+
catch (error) {
|
|
5325
|
+
this.emit('error', error);
|
|
5326
|
+
throw error;
|
|
5327
|
+
}
|
|
5328
|
+
}
|
|
5329
|
+
/**
|
|
5330
|
+
* Place an options limit order (convenience method)
|
|
5331
|
+
*/
|
|
5332
|
+
async placeOptionsLimitOrder(symbol, quantity, side, price, timeInForce = 'gtc', broker, accountNumber) {
|
|
5333
|
+
if (!this.userToken) {
|
|
5334
|
+
throw new Error('Not initialized with user');
|
|
5335
|
+
}
|
|
5336
|
+
try {
|
|
5337
|
+
return await this.apiClient.placeOptionsLimitOrder(symbol, quantity, side === 'buy' ? 'Buy' : 'Sell', price, timeInForce, broker, accountNumber);
|
|
5338
|
+
}
|
|
5339
|
+
catch (error) {
|
|
5340
|
+
this.emit('error', error);
|
|
5341
|
+
throw error;
|
|
5342
|
+
}
|
|
5343
|
+
}
|
|
5344
|
+
/**
|
|
5345
|
+
* Place a futures market order (convenience method)
|
|
5346
|
+
*/
|
|
5347
|
+
async placeFuturesMarketOrder(symbol, quantity, side, broker, accountNumber) {
|
|
5348
|
+
if (!this.userToken) {
|
|
5349
|
+
throw new Error('Not initialized with user');
|
|
5350
|
+
}
|
|
5351
|
+
try {
|
|
5352
|
+
return await this.apiClient.placeFuturesMarketOrder(symbol, quantity, side === 'buy' ? 'Buy' : 'Sell', broker, accountNumber);
|
|
5353
|
+
}
|
|
5354
|
+
catch (error) {
|
|
5355
|
+
this.emit('error', error);
|
|
5356
|
+
throw error;
|
|
5357
|
+
}
|
|
5358
|
+
}
|
|
5359
|
+
/**
|
|
5360
|
+
* Place a futures limit order (convenience method)
|
|
5361
|
+
*/
|
|
5362
|
+
async placeFuturesLimitOrder(symbol, quantity, side, price, timeInForce = 'gtc', broker, accountNumber) {
|
|
5363
|
+
if (!this.userToken) {
|
|
5364
|
+
throw new Error('Not initialized with user');
|
|
5365
|
+
}
|
|
5366
|
+
try {
|
|
5367
|
+
return await this.apiClient.placeFuturesLimitOrder(symbol, quantity, side === 'buy' ? 'Buy' : 'Sell', price, timeInForce, broker, accountNumber);
|
|
5368
|
+
}
|
|
5369
|
+
catch (error) {
|
|
5370
|
+
this.emit('error', error);
|
|
5371
|
+
throw error;
|
|
5372
|
+
}
|
|
5373
|
+
}
|
|
5374
|
+
/**
|
|
5375
|
+
* Set the broker context for trading operations
|
|
5376
|
+
* @param broker - The broker to set as context
|
|
5377
|
+
*/
|
|
5378
|
+
setBroker(broker) {
|
|
5379
|
+
this.apiClient.setBroker(broker);
|
|
5380
|
+
}
|
|
5381
|
+
/**
|
|
5382
|
+
* Set the account context for trading operations
|
|
5383
|
+
* @param accountNumber - The account number to set as context
|
|
5384
|
+
*/
|
|
5385
|
+
setAccount(accountNumber) {
|
|
5386
|
+
this.apiClient.setAccount(accountNumber);
|
|
5387
|
+
}
|
|
5388
|
+
/**
|
|
5389
|
+
* Get the current trading context
|
|
5390
|
+
* @returns Object with current broker and account context
|
|
5391
|
+
*/
|
|
5392
|
+
getTradingContext() {
|
|
5393
|
+
return this.apiClient.getTradingContext();
|
|
5394
|
+
}
|
|
5395
|
+
/**
|
|
5396
|
+
* Clear the trading context
|
|
5397
|
+
*/
|
|
5398
|
+
clearTradingContext() {
|
|
5399
|
+
this.apiClient.clearTradingContext();
|
|
5400
|
+
}
|
|
4455
5401
|
/**
|
|
4456
5402
|
* Get the current user ID
|
|
4457
5403
|
* @returns The current user ID or undefined if not authenticated
|
|
@@ -4601,6 +5547,12 @@ class FinaticConnect extends EventEmitter {
|
|
|
4601
5547
|
}
|
|
4602
5548
|
return this.apiClient.getBrokerAccountsPage(page, perPage, filter);
|
|
4603
5549
|
}
|
|
5550
|
+
async getBalancesPage(page = 1, perPage = 100, filter) {
|
|
5551
|
+
if (!this.isAuthed()) {
|
|
5552
|
+
throw new AuthenticationError('User is not authenticated');
|
|
5553
|
+
}
|
|
5554
|
+
return this.apiClient.getBrokerBalancesPage(page, perPage, filter);
|
|
5555
|
+
}
|
|
4604
5556
|
/**
|
|
4605
5557
|
* Get the next page of orders
|
|
4606
5558
|
* @param previousResult - The previous paginated result
|
|
@@ -4643,6 +5595,15 @@ class FinaticConnect extends EventEmitter {
|
|
|
4643
5595
|
return this.apiClient.getBrokerAccountsPage(page, limit);
|
|
4644
5596
|
});
|
|
4645
5597
|
}
|
|
5598
|
+
async getNextBalancesPage(previousResult) {
|
|
5599
|
+
if (!this.isAuthed()) {
|
|
5600
|
+
throw new AuthenticationError('User is not authenticated');
|
|
5601
|
+
}
|
|
5602
|
+
return this.apiClient.getNextPage(previousResult, (offset, limit) => {
|
|
5603
|
+
const page = Math.floor(offset / limit) + 1;
|
|
5604
|
+
return this.apiClient.getBrokerBalancesPage(page, limit);
|
|
5605
|
+
});
|
|
5606
|
+
}
|
|
4646
5607
|
/**
|
|
4647
5608
|
* Get all orders across all pages (convenience method)
|
|
4648
5609
|
* @param filter - Optional filter parameters
|
|
@@ -4709,6 +5670,23 @@ class FinaticConnect extends EventEmitter {
|
|
|
4709
5670
|
}
|
|
4710
5671
|
return allData;
|
|
4711
5672
|
}
|
|
5673
|
+
async getAllBalances(filter) {
|
|
5674
|
+
if (!this.isAuthed()) {
|
|
5675
|
+
throw new AuthenticationError('User is not authenticated');
|
|
5676
|
+
}
|
|
5677
|
+
const allData = [];
|
|
5678
|
+
let currentResult = await this.getBalancesPage(1, 100, filter);
|
|
5679
|
+
while (currentResult) {
|
|
5680
|
+
allData.push(...currentResult.data);
|
|
5681
|
+
if (!currentResult.hasNext)
|
|
5682
|
+
break;
|
|
5683
|
+
const nextResult = await this.getNextBalancesPage(currentResult);
|
|
5684
|
+
if (!nextResult)
|
|
5685
|
+
break;
|
|
5686
|
+
currentResult = nextResult;
|
|
5687
|
+
}
|
|
5688
|
+
return allData;
|
|
5689
|
+
}
|
|
4712
5690
|
/**
|
|
4713
5691
|
* Register session management (but don't auto-cleanup for 24-hour sessions)
|
|
4714
5692
|
*/
|
|
@@ -4758,20 +5736,9 @@ class FinaticConnect extends EventEmitter {
|
|
|
4758
5736
|
await this.refreshSessionAutomatically();
|
|
4759
5737
|
return;
|
|
4760
5738
|
}
|
|
4761
|
-
//
|
|
4762
|
-
|
|
4763
|
-
|
|
4764
|
-
});
|
|
4765
|
-
const validationPromise = this.apiClient.validatePortalSession(this.sessionId, '');
|
|
4766
|
-
const response = await Promise.race([validationPromise, timeoutPromise]);
|
|
4767
|
-
if (response && response.status === 'active') {
|
|
4768
|
-
console.log('[FinaticConnect] Session keep-alive successful');
|
|
4769
|
-
this.currentSessionState = 'active';
|
|
4770
|
-
}
|
|
4771
|
-
else {
|
|
4772
|
-
console.warn('[FinaticConnect] Session keep-alive failed - session not active');
|
|
4773
|
-
this.currentSessionState = response?.status || 'unknown';
|
|
4774
|
-
}
|
|
5739
|
+
// Session keep-alive - assume session is active if we have a session ID
|
|
5740
|
+
console.log('[FinaticConnect] Session keep-alive successful');
|
|
5741
|
+
this.currentSessionState = 'active';
|
|
4775
5742
|
}
|
|
4776
5743
|
catch (error) {
|
|
4777
5744
|
console.warn('[FinaticConnect] Session keep-alive error:', error);
|
|
@@ -4900,6 +5867,24 @@ class FinaticConnect extends EventEmitter {
|
|
|
4900
5867
|
}
|
|
4901
5868
|
return this.apiClient.disconnectCompany(connectionId);
|
|
4902
5869
|
}
|
|
5870
|
+
/**
|
|
5871
|
+
* Get account balances for the authenticated user
|
|
5872
|
+
* @param filters - Optional filters for balances
|
|
5873
|
+
* @returns Promise with balance data
|
|
5874
|
+
*/
|
|
5875
|
+
async getBalances(filters) {
|
|
5876
|
+
if (!this.isAuthed()) {
|
|
5877
|
+
throw new AuthenticationError('User is not authenticated');
|
|
5878
|
+
}
|
|
5879
|
+
try {
|
|
5880
|
+
const response = await this.apiClient.getBalances(filters);
|
|
5881
|
+
return response.response_data || [];
|
|
5882
|
+
}
|
|
5883
|
+
catch (error) {
|
|
5884
|
+
this.emit('error', error);
|
|
5885
|
+
throw error;
|
|
5886
|
+
}
|
|
5887
|
+
}
|
|
4903
5888
|
}
|
|
4904
5889
|
FinaticConnect.instance = null;
|
|
4905
5890
|
|