@finatic/client 0.0.139 → 0.0.140
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 +278 -461
- package/dist/index.d.ts +55 -515
- package/dist/index.js +326 -456
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +327 -456
- package/dist/index.mjs.map +1 -1
- package/dist/types/core/client/ApiClient.d.ts +12 -26
- package/dist/types/core/client/FinaticConnect.d.ts +20 -103
- package/dist/types/index.d.ts +1 -2
- package/dist/types/mocks/MockApiClient.d.ts +2 -4
- package/dist/types/mocks/utils.d.ts +0 -5
- package/dist/types/types/api/auth.d.ts +12 -30
- package/dist/types/types/api/broker.d.ts +1 -1
- package/package.json +7 -3
- package/src/core/client/ApiClient.ts +1721 -0
- package/src/core/client/FinaticConnect.ts +1476 -0
- package/src/core/portal/PortalUI.ts +300 -0
- package/src/index.d.ts +23 -0
- package/src/index.ts +87 -0
- package/src/mocks/MockApiClient.ts +1032 -0
- package/src/mocks/MockDataProvider.ts +986 -0
- package/src/mocks/MockFactory.ts +97 -0
- package/src/mocks/utils.ts +133 -0
- package/src/themes/portalPresets.ts +1307 -0
- package/src/types/api/auth.ts +112 -0
- package/src/types/api/broker.ts +330 -0
- package/src/types/api/core.ts +53 -0
- package/src/types/api/errors.ts +35 -0
- package/src/types/api/orders.ts +45 -0
- package/src/types/api/portfolio.ts +59 -0
- package/src/types/common/pagination.ts +138 -0
- package/src/types/connect.ts +56 -0
- package/src/types/index.ts +25 -0
- package/src/types/portal.ts +214 -0
- package/src/types/ui/theme.ts +105 -0
- package/src/utils/brokerUtils.ts +85 -0
- package/src/utils/errors.ts +104 -0
- package/src/utils/events.ts +54 -0
- package/src/utils/themeUtils.ts +146 -0
package/README.md
CHANGED
|
@@ -37,540 +37,357 @@ const finatic = await FinaticConnect.init('your-one-time-token', 'user-123', {
|
|
|
37
37
|
});
|
|
38
38
|
```
|
|
39
39
|
|
|
40
|
-
|
|
41
|
-
await finatic.openPortal({
|
|
42
|
-
onSuccess: (userId) => {
|
|
43
|
-
console.log('Authentication successful:', userId);
|
|
44
|
-
},
|
|
45
|
-
onError: (error) => {
|
|
46
|
-
console.error('Authentication failed:', error);
|
|
47
|
-
},
|
|
48
|
-
onClose: () => {
|
|
49
|
-
console.log('Portal closed');
|
|
50
|
-
}
|
|
51
|
-
});
|
|
52
|
-
|
|
53
|
-
// After successful authentication, you can use these methods:
|
|
54
|
-
|
|
55
|
-
// Get list of supported brokers
|
|
56
|
-
const brokers = await finatic.getBrokerList();
|
|
57
|
-
|
|
58
|
-
// Get broker accounts with pagination
|
|
59
|
-
const accountsPage = await finatic.getAccounts({
|
|
60
|
-
page: 1,
|
|
61
|
-
perPage: 100
|
|
62
|
-
});
|
|
63
|
-
|
|
64
|
-
// Navigate through pages
|
|
65
|
-
const nextPage = await accountsPage.nextPage();
|
|
66
|
-
const prevPage = await accountsPage.previousPage();
|
|
67
|
-
|
|
68
|
-
// Get all accounts (convenience method)
|
|
69
|
-
const allAccounts = await finatic.getAllAccounts();
|
|
70
|
-
|
|
71
|
-
// Get orders with filtering
|
|
72
|
-
const ordersPage = await finatic.getOrders({
|
|
73
|
-
page: 1,
|
|
74
|
-
perPage: 50,
|
|
75
|
-
filter: { status: 'filled', symbol: 'AAPL' }
|
|
76
|
-
});
|
|
40
|
+
## Portal Management
|
|
77
41
|
|
|
78
|
-
|
|
79
|
-
const positionsPage = await finatic.getPositions({
|
|
80
|
-
page: 1,
|
|
81
|
-
perPage: 100
|
|
82
|
-
});
|
|
42
|
+
### Opening the Portal
|
|
83
43
|
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
44
|
+
```typescript
|
|
45
|
+
// Open the portal with basic configuration
|
|
46
|
+
await finatic.openPortal({
|
|
47
|
+
onSuccess: userId => {
|
|
48
|
+
console.log('Authentication successful:', userId);
|
|
49
|
+
},
|
|
50
|
+
onError: error => {
|
|
51
|
+
console.error('Authentication failed:', error);
|
|
52
|
+
},
|
|
53
|
+
onClose: () => {
|
|
54
|
+
console.log('Portal closed');
|
|
55
|
+
},
|
|
91
56
|
});
|
|
92
57
|
|
|
93
58
|
// Open portal with broker filtering
|
|
94
59
|
await finatic.openPortal({
|
|
95
|
-
brokers: ['alpaca', 'robinhood'] // Only show these brokers
|
|
60
|
+
brokers: ['alpaca', 'robinhood'], // Only show these brokers
|
|
61
|
+
onSuccess: userId => {
|
|
62
|
+
console.log('Authentication successful:', userId);
|
|
63
|
+
},
|
|
96
64
|
});
|
|
97
65
|
|
|
98
|
-
//
|
|
99
|
-
const disconnectResponse = await finatic.disconnectCompany('connection-uuid-here');
|
|
100
|
-
console.log('Disconnect action:', disconnectResponse.response_data.action);
|
|
101
|
-
|
|
102
|
-
// Close the portal when done
|
|
103
|
-
finatic.closePortal();
|
|
104
|
-
|
|
105
|
-
````
|
|
106
|
-
|
|
107
|
-
## API Reference
|
|
108
|
-
|
|
109
|
-
### Initialization
|
|
110
|
-
|
|
111
|
-
#### `FinaticConnect.init(token, userId?, options?)`
|
|
112
|
-
|
|
113
|
-
Initialize the Finatic Client SDK.
|
|
114
|
-
|
|
115
|
-
- `token` (string): One-time token from your backend
|
|
116
|
-
- `userId` (string, optional): Pre-authenticated user ID from previous session
|
|
117
|
-
- `options` (object, optional): Configuration options
|
|
118
|
-
- `baseUrl` (string, optional): Custom API base URL
|
|
119
|
-
|
|
120
|
-
Returns: Promise<FinaticConnect>
|
|
121
|
-
|
|
122
|
-
### Portal Management
|
|
123
|
-
|
|
124
|
-
#### `openPortal(options?)`
|
|
125
|
-
|
|
126
|
-
Opens the authentication portal in an iframe.
|
|
127
|
-
|
|
128
|
-
- `options` (object, optional): Portal options
|
|
129
|
-
- `onSuccess` (function): Called when authentication succeeds
|
|
130
|
-
- `onError` (function): Called when authentication fails
|
|
131
|
-
- `onClose` (function): Called when portal is closed
|
|
132
|
-
- `onEvent` (function): Called when portal events occur
|
|
133
|
-
- `theme` (object, optional): Theme configuration
|
|
134
|
-
- `preset` (string, optional): Preset theme name ('dark', 'light', 'corporateBlue', 'purple', 'green', 'orange')
|
|
135
|
-
- `custom` (object, optional): Custom theme configuration object
|
|
136
|
-
- `brokers` (string[], optional): List of broker names to filter by (only these brokers will be shown)
|
|
137
|
-
|
|
138
|
-
#### `closePortal()`
|
|
139
|
-
|
|
140
|
-
Closes the authentication portal.
|
|
141
|
-
|
|
142
|
-
### Portal Theming
|
|
143
|
-
|
|
144
|
-
The Finatic Portal supports dynamic theme switching via URL parameters. You can customize the portal's appearance to match your application's branding.
|
|
145
|
-
|
|
146
|
-
#### Using Preset Themes
|
|
147
|
-
|
|
148
|
-
```javascript
|
|
149
|
-
// Use a preset theme
|
|
66
|
+
// Open portal with theming
|
|
150
67
|
await finatic.openPortal({
|
|
151
|
-
theme: {
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
// Available presets: 'dark', 'light', 'corporateBlue', 'purple', 'green', 'orange'
|
|
155
|
-
````
|
|
156
|
-
|
|
157
|
-
#### Using Custom Themes
|
|
158
|
-
|
|
159
|
-
```javascript
|
|
160
|
-
// Use a custom theme
|
|
161
|
-
const customTheme = {
|
|
162
|
-
mode: 'dark',
|
|
163
|
-
colors: {
|
|
164
|
-
background: {
|
|
165
|
-
primary: '#1a1a1a',
|
|
166
|
-
secondary: '#2a2a2a',
|
|
167
|
-
tertiary: '#3a3a3a',
|
|
168
|
-
accent: 'rgba(59, 130, 246, 0.1)',
|
|
169
|
-
glass: 'rgba(255, 255, 255, 0.05)',
|
|
170
|
-
},
|
|
171
|
-
status: {
|
|
172
|
-
connected: '#10B981',
|
|
173
|
-
disconnected: '#EF4444',
|
|
174
|
-
warning: '#F59E0B',
|
|
175
|
-
pending: '#8B5CF6',
|
|
176
|
-
error: '#EF4444',
|
|
177
|
-
success: '#10B981',
|
|
178
|
-
},
|
|
179
|
-
text: {
|
|
180
|
-
primary: '#F8FAFC',
|
|
181
|
-
secondary: '#CBD5E1',
|
|
182
|
-
muted: '#94A3B8',
|
|
183
|
-
inverse: '#1a1a1a',
|
|
184
|
-
},
|
|
185
|
-
border: {
|
|
186
|
-
primary: 'rgba(59, 130, 246, 0.2)',
|
|
187
|
-
secondary: 'rgba(255, 255, 255, 0.1)',
|
|
188
|
-
hover: 'rgba(59, 130, 246, 0.4)',
|
|
189
|
-
focus: 'rgba(59, 130, 246, 0.6)',
|
|
190
|
-
accent: '#3B82F6',
|
|
191
|
-
},
|
|
192
|
-
input: {
|
|
193
|
-
background: '#334155',
|
|
194
|
-
border: 'rgba(59, 130, 246, 0.2)',
|
|
195
|
-
borderFocus: '#3B82F6',
|
|
196
|
-
text: '#F8FAFC',
|
|
197
|
-
placeholder: '#94A3B8',
|
|
198
|
-
},
|
|
199
|
-
button: {
|
|
200
|
-
primary: {
|
|
201
|
-
background: '#3B82F6',
|
|
202
|
-
text: '#FFFFFF',
|
|
203
|
-
hover: '#2563EB',
|
|
204
|
-
active: '#1D4ED8',
|
|
205
|
-
},
|
|
206
|
-
secondary: {
|
|
207
|
-
background: 'transparent',
|
|
208
|
-
text: '#3B82F6',
|
|
209
|
-
border: '#3B82F6',
|
|
210
|
-
hover: 'rgba(59, 130, 246, 0.1)',
|
|
211
|
-
active: 'rgba(59, 130, 246, 0.2)',
|
|
212
|
-
},
|
|
213
|
-
},
|
|
214
|
-
},
|
|
215
|
-
branding: {
|
|
216
|
-
primaryColor: '#3B82F6',
|
|
68
|
+
theme: {
|
|
69
|
+
primaryColor: '#007bff',
|
|
70
|
+
logoUrl: 'https://example.com/logo.png',
|
|
217
71
|
},
|
|
218
|
-
};
|
|
219
|
-
|
|
220
|
-
await finatic.openPortal({
|
|
221
|
-
theme: { custom: customTheme },
|
|
222
72
|
});
|
|
223
73
|
```
|
|
224
74
|
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
```javascript
|
|
228
|
-
import {
|
|
229
|
-
generatePortalThemeURL,
|
|
230
|
-
appendThemeToURL,
|
|
231
|
-
getThemePreset,
|
|
232
|
-
validateCustomTheme,
|
|
233
|
-
createCustomThemeFromPreset,
|
|
234
|
-
portalThemePresets,
|
|
235
|
-
} from 'finatic-sdk';
|
|
236
|
-
|
|
237
|
-
// Generate a themed portal URL
|
|
238
|
-
const themedUrl = generatePortalThemeURL('http://localhost:5173/companies', {
|
|
239
|
-
preset: 'corporateBlue',
|
|
240
|
-
});
|
|
241
|
-
|
|
242
|
-
// Get a theme preset
|
|
243
|
-
const darkTheme = getThemePreset('dark');
|
|
244
|
-
|
|
245
|
-
// Validate a custom theme
|
|
246
|
-
const isValid = validateCustomTheme(customTheme);
|
|
75
|
+
### Closing the Portal
|
|
247
76
|
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
|
|
251
|
-
background: {
|
|
252
|
-
primary: '#000000',
|
|
253
|
-
},
|
|
254
|
-
},
|
|
255
|
-
});
|
|
77
|
+
```typescript
|
|
78
|
+
// Close the portal
|
|
79
|
+
await finatic.closePortal();
|
|
256
80
|
```
|
|
257
81
|
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
The Finatic Portal supports broker filtering via URL parameters. You can restrict which brokers are displayed in the portal by specifying a list of allowed broker names.
|
|
261
|
-
|
|
262
|
-
#### Supported Brokers
|
|
263
|
-
|
|
264
|
-
The following broker names are supported:
|
|
265
|
-
|
|
266
|
-
- `alpaca` - Alpaca Markets
|
|
267
|
-
- `robinhood` - Robinhood
|
|
268
|
-
- `tasty_trade` - TastyTrade
|
|
269
|
-
- `ninja_trader` - NinjaTrader
|
|
82
|
+
## Data Access
|
|
270
83
|
|
|
271
|
-
|
|
84
|
+
### Paginated Data Access
|
|
272
85
|
|
|
273
|
-
|
|
274
|
-
// Show only specific brokers
|
|
275
|
-
await finatic.openPortal({
|
|
276
|
-
brokers: ['alpaca', 'robinhood'],
|
|
277
|
-
});
|
|
86
|
+
The SDK provides a consistent pagination pattern using `get*()` methods with navigation:
|
|
278
87
|
|
|
279
|
-
|
|
280
|
-
|
|
281
|
-
|
|
88
|
+
```typescript
|
|
89
|
+
// Get orders with pagination
|
|
90
|
+
const ordersPage = await finatic.getOrders({
|
|
91
|
+
page: 1,
|
|
92
|
+
perPage: 50,
|
|
93
|
+
filter: { status: 'filled', symbol: 'AAPL' },
|
|
282
94
|
});
|
|
283
95
|
|
|
284
|
-
//
|
|
285
|
-
await
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
|
|
96
|
+
// Navigate through pages
|
|
97
|
+
const nextPage = await ordersPage.nextPage();
|
|
98
|
+
const prevPage = await ordersPage.previousPage();
|
|
99
|
+
|
|
100
|
+
// Check pagination status
|
|
101
|
+
console.log('Has next page:', ordersPage.hasNext);
|
|
102
|
+
console.log('Has previous page:', ordersPage.hasPrevious);
|
|
103
|
+
console.log('Current page:', ordersPage.page);
|
|
104
|
+
console.log('Total pages:', ordersPage.totalPages);
|
|
289
105
|
```
|
|
290
106
|
|
|
291
|
-
|
|
292
|
-
|
|
293
|
-
If you pass an unsupported broker name, it will be logged as a warning to the console, but the portal will still open with the supported brokers:
|
|
107
|
+
### Get All Data (Convenience Methods)
|
|
294
108
|
|
|
295
|
-
```
|
|
296
|
-
//
|
|
297
|
-
await finatic.
|
|
298
|
-
|
|
299
|
-
|
|
109
|
+
```typescript
|
|
110
|
+
// Get all data across all pages
|
|
111
|
+
const allOrders = await finatic.getAllOrders();
|
|
112
|
+
const allPositions = await finatic.getAllPositions();
|
|
113
|
+
const allAccounts = await finatic.getAllAccounts();
|
|
114
|
+
const allBalances = await finatic.getAllBalances();
|
|
300
115
|
```
|
|
301
116
|
|
|
302
|
-
|
|
303
|
-
|
|
304
|
-
```javascript
|
|
305
|
-
import {
|
|
306
|
-
convertBrokerNamesToIds,
|
|
307
|
-
appendBrokerFilterToURL,
|
|
308
|
-
getSupportedBrokerNames,
|
|
309
|
-
isBrokerSupported,
|
|
310
|
-
} from 'finatic-sdk';
|
|
311
|
-
|
|
312
|
-
// Convert broker names to IDs
|
|
313
|
-
const { brokerIds, warnings } = convertBrokerNamesToIds(['alpaca', 'robinhood']);
|
|
117
|
+
### Convenience Filter Methods
|
|
314
118
|
|
|
315
|
-
|
|
316
|
-
|
|
317
|
-
|
|
318
|
-
|
|
319
|
-
const
|
|
119
|
+
```typescript
|
|
120
|
+
// Get filtered data
|
|
121
|
+
const openPositions = await finatic.getOpenPositions();
|
|
122
|
+
const filledOrders = await finatic.getFilledOrders();
|
|
123
|
+
const pendingOrders = await finatic.getPendingOrders();
|
|
124
|
+
const activeAccounts = await finatic.getActiveAccounts();
|
|
125
|
+
|
|
126
|
+
// Get data by symbol
|
|
127
|
+
const aaplOrders = await finatic.getOrdersBySymbol('AAPL');
|
|
128
|
+
const aaplPositions = await finatic.getPositionsBySymbol('AAPL');
|
|
129
|
+
|
|
130
|
+
// Get data by broker
|
|
131
|
+
const robinhoodOrders = await finatic.getOrdersByBroker('robinhood');
|
|
132
|
+
const robinhoodPositions = await finatic.getPositionsByBroker('robinhood');
|
|
320
133
|
```
|
|
321
134
|
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
#### `getAccounts(params?)`
|
|
325
|
-
|
|
326
|
-
Returns paginated broker accounts.
|
|
327
|
-
|
|
328
|
-
- `params` (object, optional): Query parameters
|
|
329
|
-
- `page` (number, optional): Page number (default: 1)
|
|
330
|
-
- `perPage` (number, optional): Items per page (default: 100)
|
|
331
|
-
- `filter` (object, optional): Filter parameters
|
|
332
|
-
|
|
333
|
-
Returns: Promise<PaginatedResult<BrokerDataAccount[]>>
|
|
334
|
-
|
|
335
|
-
#### `getOrders(params?)`
|
|
336
|
-
|
|
337
|
-
Returns paginated order history.
|
|
338
|
-
|
|
339
|
-
- `params` (object, optional): Query parameters
|
|
340
|
-
- `page` (number, optional): Page number (default: 1)
|
|
341
|
-
- `perPage` (number, optional): Items per page (default: 100)
|
|
342
|
-
- `filter` (object, optional): Filter parameters
|
|
343
|
-
|
|
344
|
-
Returns: Promise<PaginatedResult<BrokerDataOrder[]>>
|
|
345
|
-
|
|
346
|
-
#### `getPositions(params?)`
|
|
347
|
-
|
|
348
|
-
Returns paginated positions.
|
|
349
|
-
|
|
350
|
-
- `params` (object, optional): Query parameters
|
|
351
|
-
- `page` (number, optional): Page number (default: 1)
|
|
352
|
-
- `perPage` (number, optional): Items per page (default: 100)
|
|
353
|
-
- `filter` (object, optional): Filter parameters
|
|
354
|
-
|
|
355
|
-
Returns: Promise<PaginatedResult<BrokerDataPosition[]>>
|
|
356
|
-
|
|
357
|
-
### Data Access (Get All - Convenience Methods)
|
|
358
|
-
|
|
359
|
-
#### `getAllAccounts(filter?)`
|
|
360
|
-
|
|
361
|
-
Returns all broker accounts across all pages.
|
|
362
|
-
|
|
363
|
-
- `filter` (object, optional): Filter parameters
|
|
364
|
-
|
|
365
|
-
Returns: Promise<BrokerDataAccount[]>
|
|
366
|
-
|
|
367
|
-
#### `getAllOrders(filter?)`
|
|
135
|
+
## Trading Operations
|
|
368
136
|
|
|
369
|
-
|
|
137
|
+
### General Order Placement
|
|
370
138
|
|
|
371
|
-
|
|
372
|
-
|
|
373
|
-
|
|
374
|
-
|
|
375
|
-
|
|
376
|
-
|
|
377
|
-
|
|
378
|
-
|
|
379
|
-
|
|
380
|
-
|
|
381
|
-
Returns: Promise<BrokerDataPosition[]>
|
|
382
|
-
|
|
383
|
-
### Convenience Methods
|
|
384
|
-
|
|
385
|
-
#### `getOpenPositions()`
|
|
386
|
-
|
|
387
|
-
Returns only open positions.
|
|
388
|
-
|
|
389
|
-
Returns: Promise<BrokerDataPosition[]>
|
|
390
|
-
|
|
391
|
-
#### `getFilledOrders()`
|
|
392
|
-
|
|
393
|
-
Returns only filled orders.
|
|
394
|
-
|
|
395
|
-
Returns: Promise<BrokerDataOrder[]>
|
|
396
|
-
|
|
397
|
-
#### `getPendingOrders()`
|
|
398
|
-
|
|
399
|
-
Returns only pending orders.
|
|
400
|
-
|
|
401
|
-
Returns: Promise<BrokerDataOrder[]>
|
|
402
|
-
|
|
403
|
-
#### `getActiveAccounts()`
|
|
404
|
-
|
|
405
|
-
Returns only active accounts.
|
|
406
|
-
|
|
407
|
-
Returns: Promise<BrokerDataAccount[]>
|
|
408
|
-
|
|
409
|
-
#### `getOrdersBySymbol(symbol)`
|
|
410
|
-
|
|
411
|
-
Returns orders for a specific symbol.
|
|
412
|
-
|
|
413
|
-
- `symbol` (string): Stock symbol
|
|
414
|
-
|
|
415
|
-
Returns: Promise<BrokerDataOrder[]>
|
|
416
|
-
|
|
417
|
-
#### `getPositionsBySymbol(symbol)`
|
|
418
|
-
|
|
419
|
-
Returns positions for a specific symbol.
|
|
420
|
-
|
|
421
|
-
- `symbol` (string): Stock symbol
|
|
422
|
-
|
|
423
|
-
Returns: Promise<BrokerDataPosition[]>
|
|
424
|
-
|
|
425
|
-
#### `getOrdersByBroker(brokerId)`
|
|
426
|
-
|
|
427
|
-
Returns orders for a specific broker.
|
|
428
|
-
|
|
429
|
-
- `brokerId` (string): Broker ID
|
|
430
|
-
|
|
431
|
-
Returns: Promise<BrokerDataOrder[]>
|
|
432
|
-
|
|
433
|
-
#### `getPositionsByBroker(brokerId)`
|
|
434
|
-
|
|
435
|
-
Returns positions for a specific broker.
|
|
436
|
-
|
|
437
|
-
- `brokerId` (string): Broker ID
|
|
438
|
-
|
|
439
|
-
Returns: Promise<BrokerDataPosition[]>
|
|
440
|
-
|
|
441
|
-
### Broker Information
|
|
442
|
-
|
|
443
|
-
#### `getBrokerList()`
|
|
139
|
+
```typescript
|
|
140
|
+
// Place a market order
|
|
141
|
+
const orderResponse = await finatic.placeOrder({
|
|
142
|
+
symbol: 'AAPL',
|
|
143
|
+
side: 'buy',
|
|
144
|
+
quantity: 10,
|
|
145
|
+
orderType: 'market',
|
|
146
|
+
timeInForce: 'day',
|
|
147
|
+
});
|
|
444
148
|
|
|
445
|
-
|
|
149
|
+
// Place a limit order
|
|
150
|
+
const limitOrderResponse = await finatic.placeOrder({
|
|
151
|
+
symbol: 'AAPL',
|
|
152
|
+
side: 'buy',
|
|
153
|
+
quantity: 10,
|
|
154
|
+
orderType: 'limit',
|
|
155
|
+
price: 150.0,
|
|
156
|
+
timeInForce: 'gtc',
|
|
157
|
+
});
|
|
158
|
+
```
|
|
446
159
|
|
|
447
|
-
|
|
160
|
+
### Asset-Specific Order Methods
|
|
448
161
|
|
|
449
|
-
####
|
|
162
|
+
#### Stock Orders
|
|
450
163
|
|
|
451
|
-
|
|
164
|
+
```typescript
|
|
165
|
+
// Stock market order
|
|
166
|
+
const response = await finatic.placeStockMarketOrder('AAPL', 10, 'buy', 'robinhood', '123456789');
|
|
167
|
+
|
|
168
|
+
// Stock limit order
|
|
169
|
+
const response = await finatic.placeStockLimitOrder(
|
|
170
|
+
'AAPL',
|
|
171
|
+
10,
|
|
172
|
+
'buy',
|
|
173
|
+
150.0,
|
|
174
|
+
'gtc',
|
|
175
|
+
'robinhood',
|
|
176
|
+
'123456789'
|
|
177
|
+
);
|
|
178
|
+
|
|
179
|
+
// Stock stop order
|
|
180
|
+
const response = await finatic.placeStockStopOrder(
|
|
181
|
+
'AAPL',
|
|
182
|
+
10,
|
|
183
|
+
'sell',
|
|
184
|
+
140.0,
|
|
185
|
+
'gtc',
|
|
186
|
+
'robinhood',
|
|
187
|
+
'123456789'
|
|
188
|
+
);
|
|
189
|
+
```
|
|
452
190
|
|
|
453
|
-
|
|
191
|
+
#### Crypto Orders
|
|
454
192
|
|
|
455
|
-
|
|
193
|
+
```typescript
|
|
194
|
+
// Crypto market order
|
|
195
|
+
const response = await finatic.placeCryptoMarketOrder(
|
|
196
|
+
'BTC-USD',
|
|
197
|
+
0.1,
|
|
198
|
+
'buy',
|
|
199
|
+
'coinbase',
|
|
200
|
+
'123456789'
|
|
201
|
+
);
|
|
202
|
+
|
|
203
|
+
// Crypto limit order
|
|
204
|
+
const response = await finatic.placeCryptoLimitOrder(
|
|
205
|
+
'BTC-USD',
|
|
206
|
+
0.1,
|
|
207
|
+
'buy',
|
|
208
|
+
50000.0,
|
|
209
|
+
'gtc',
|
|
210
|
+
'coinbase',
|
|
211
|
+
'123456789'
|
|
212
|
+
);
|
|
213
|
+
```
|
|
456
214
|
|
|
457
|
-
|
|
215
|
+
#### Options Orders
|
|
458
216
|
|
|
459
|
-
|
|
217
|
+
```typescript
|
|
218
|
+
// Options market order
|
|
219
|
+
const response = await finatic.placeOptionsMarketOrder(
|
|
220
|
+
'AAPL240315C00150000',
|
|
221
|
+
1,
|
|
222
|
+
'buy',
|
|
223
|
+
'tasty_trade',
|
|
224
|
+
'123456789'
|
|
225
|
+
);
|
|
226
|
+
|
|
227
|
+
// Options limit order
|
|
228
|
+
const response = await finatic.placeOptionsLimitOrder(
|
|
229
|
+
'AAPL240315C00150000',
|
|
230
|
+
1,
|
|
231
|
+
'buy',
|
|
232
|
+
5.0,
|
|
233
|
+
'gtc',
|
|
234
|
+
'tasty_trade',
|
|
235
|
+
'123456789'
|
|
236
|
+
);
|
|
237
|
+
```
|
|
460
238
|
|
|
461
|
-
|
|
239
|
+
#### Futures Orders
|
|
462
240
|
|
|
463
|
-
|
|
241
|
+
```typescript
|
|
242
|
+
// Futures market order
|
|
243
|
+
const response = await finatic.placeFuturesMarketOrder('ES', 1, 'buy', 'ninja_trader', '123456789');
|
|
244
|
+
|
|
245
|
+
// Futures limit order
|
|
246
|
+
const response = await finatic.placeFuturesLimitOrder(
|
|
247
|
+
'ES',
|
|
248
|
+
1,
|
|
249
|
+
'buy',
|
|
250
|
+
4500.0,
|
|
251
|
+
'gtc',
|
|
252
|
+
'ninja_trader',
|
|
253
|
+
'123456789'
|
|
254
|
+
);
|
|
255
|
+
```
|
|
464
256
|
|
|
465
|
-
|
|
466
|
-
- `response_data.action` (string): Either 'company_access_removed' or 'connection_deleted'
|
|
467
|
-
- `response_data.remaining_companies` (number, optional): Number of remaining companies if connection still exists
|
|
468
|
-
- `response_data.message` (string): Human-readable message about the action taken
|
|
257
|
+
### Order Management
|
|
469
258
|
|
|
470
|
-
|
|
259
|
+
```typescript
|
|
260
|
+
// Cancel an order
|
|
261
|
+
const response = await finatic.cancelOrder('order-123', 'robinhood', 'connection-456');
|
|
262
|
+
|
|
263
|
+
// Modify an order
|
|
264
|
+
const response = await finatic.modifyOrder(
|
|
265
|
+
'order-123',
|
|
266
|
+
{ price: 155.0, quantity: 5 },
|
|
267
|
+
'robinhood',
|
|
268
|
+
'connection-456'
|
|
269
|
+
);
|
|
270
|
+
```
|
|
471
271
|
|
|
472
|
-
|
|
272
|
+
## Broker Information
|
|
473
273
|
|
|
474
|
-
|
|
274
|
+
```typescript
|
|
275
|
+
// Get list of supported brokers
|
|
276
|
+
const brokers = await finatic.getBrokerList();
|
|
475
277
|
|
|
476
|
-
|
|
477
|
-
|
|
478
|
-
- `side` (string): 'buy' or 'sell'
|
|
479
|
-
- `quantity` (number): Number of shares
|
|
480
|
-
- `type` (string): 'market', 'limit', 'stop', or 'stop_limit'
|
|
481
|
-
- `timeInForce` (string): 'day', 'gtc', 'opg', 'cls', 'ioc', or 'fok'
|
|
482
|
-
- `price` (number, optional): Limit price
|
|
483
|
-
- `stopPrice` (number, optional): Stop price
|
|
278
|
+
// Get broker connections
|
|
279
|
+
const connections = await finatic.getBrokerConnections();
|
|
484
280
|
|
|
485
|
-
|
|
281
|
+
// Disconnect a company from a broker connection
|
|
282
|
+
const disconnectResponse = await finatic.disconnectCompany('connection-uuid-here');
|
|
283
|
+
console.log('Disconnect action:', disconnectResponse.response_data.action);
|
|
284
|
+
```
|
|
486
285
|
|
|
487
|
-
|
|
286
|
+
## Authentication
|
|
488
287
|
|
|
489
|
-
|
|
490
|
-
|
|
288
|
+
```typescript
|
|
289
|
+
// Check authentication status
|
|
290
|
+
const isAuthenticated = finatic.isAuthed();
|
|
291
|
+
const isAuthenticatedAlt = finatic.is_authenticated();
|
|
491
292
|
|
|
492
|
-
|
|
293
|
+
// Get user ID
|
|
294
|
+
const userId = finatic.getUserId();
|
|
493
295
|
|
|
494
|
-
|
|
296
|
+
// Set user ID (for returning users)
|
|
297
|
+
finatic.setUserId('user-123');
|
|
298
|
+
```
|
|
495
299
|
|
|
496
|
-
|
|
497
|
-
- `modifications` (object): Order modifications
|
|
498
|
-
- `broker` (string, optional): Broker name
|
|
300
|
+
## Error Handling
|
|
499
301
|
|
|
500
|
-
|
|
302
|
+
```typescript
|
|
303
|
+
import { AuthenticationError, ApiError, ValidationError } from '@finatic/client';
|
|
501
304
|
|
|
502
|
-
|
|
305
|
+
try {
|
|
306
|
+
const orders = await finatic.getOrders();
|
|
307
|
+
} catch (error) {
|
|
308
|
+
if (error instanceof AuthenticationError) {
|
|
309
|
+
console.error('Authentication failed:', error.message);
|
|
310
|
+
} else if (error instanceof ValidationError) {
|
|
311
|
+
console.error('Invalid request:', error.message);
|
|
312
|
+
} else if (error instanceof ApiError) {
|
|
313
|
+
console.error('API error:', error.message);
|
|
314
|
+
}
|
|
315
|
+
}
|
|
316
|
+
```
|
|
503
317
|
|
|
504
|
-
|
|
318
|
+
## Advanced Usage
|
|
505
319
|
|
|
506
|
-
|
|
320
|
+
### Custom Filters
|
|
507
321
|
|
|
508
|
-
|
|
322
|
+
```typescript
|
|
323
|
+
// Get orders with custom filters
|
|
324
|
+
const orders = await finatic.getOrders({
|
|
325
|
+
page: 1,
|
|
326
|
+
perPage: 50,
|
|
327
|
+
filter: {
|
|
328
|
+
status: 'filled',
|
|
329
|
+
symbol: 'AAPL',
|
|
330
|
+
broker: 'robinhood',
|
|
331
|
+
},
|
|
332
|
+
});
|
|
333
|
+
```
|
|
509
334
|
|
|
510
335
|
### Pagination Navigation
|
|
511
336
|
|
|
512
|
-
|
|
513
|
-
|
|
514
|
-
|
|
515
|
-
|
|
516
|
-
Returns the next page of results.
|
|
517
|
-
|
|
518
|
-
Returns: Promise<PaginatedResult<T> | null>
|
|
519
|
-
|
|
520
|
-
#### `previousPage()`
|
|
521
|
-
|
|
522
|
-
Returns the previous page of results.
|
|
523
|
-
|
|
524
|
-
Returns: Promise<PaginatedResult<T> | null>
|
|
525
|
-
|
|
526
|
-
#### `firstPage()`
|
|
527
|
-
|
|
528
|
-
Returns the first page of results.
|
|
337
|
+
```typescript
|
|
338
|
+
// Get paginated results with navigation
|
|
339
|
+
const ordersPage = await finatic.getOrders({ page: 1, perPage: 100 });
|
|
529
340
|
|
|
530
|
-
|
|
341
|
+
// Navigate through pages
|
|
342
|
+
if (ordersPage.hasNext) {
|
|
343
|
+
const nextPage = await ordersPage.nextPage();
|
|
344
|
+
}
|
|
531
345
|
|
|
532
|
-
|
|
346
|
+
if (ordersPage.hasPrevious) {
|
|
347
|
+
const prevPage = await ordersPage.previousPage();
|
|
348
|
+
}
|
|
349
|
+
```
|
|
533
350
|
|
|
534
|
-
|
|
351
|
+
### Session Management
|
|
535
352
|
|
|
536
|
-
|
|
353
|
+
```typescript
|
|
354
|
+
// The SDK automatically manages sessions
|
|
355
|
+
// Sessions are kept alive for 24 hours by default
|
|
356
|
+
// No manual session management required
|
|
357
|
+
```
|
|
537
358
|
|
|
538
|
-
|
|
359
|
+
## Type Definitions
|
|
539
360
|
|
|
540
|
-
|
|
361
|
+
The SDK includes comprehensive TypeScript definitions for all data structures:
|
|
541
362
|
|
|
542
|
-
|
|
363
|
+
- `BrokerDataOrder`: Order information
|
|
364
|
+
- `BrokerDataPosition`: Position information
|
|
365
|
+
- `BrokerDataAccount`: Account information
|
|
366
|
+
- `BrokerBalance`: Balance information
|
|
367
|
+
- `BrokerInfo`: Broker information
|
|
368
|
+
- `BrokerConnection`: Connection information
|
|
369
|
+
- `OrderResponse`: Order operation responses
|
|
370
|
+
- `PaginatedResult`: Paginated data responses
|
|
543
371
|
|
|
544
|
-
|
|
545
|
-
import {
|
|
546
|
-
ApiError,
|
|
547
|
-
SessionError,
|
|
548
|
-
AuthenticationError,
|
|
549
|
-
AuthorizationError,
|
|
550
|
-
RateLimitError,
|
|
551
|
-
CompanyAccessError,
|
|
552
|
-
} from '@finatic/client';
|
|
372
|
+
## Error Types
|
|
553
373
|
|
|
554
|
-
|
|
555
|
-
|
|
556
|
-
|
|
557
|
-
|
|
558
|
-
console.log('No broker connections found for this company');
|
|
559
|
-
} else if (error instanceof AuthenticationError) {
|
|
560
|
-
console.log('Authentication failed');
|
|
561
|
-
}
|
|
562
|
-
}
|
|
563
|
-
```
|
|
374
|
+
- `AuthenticationError`: Authentication failures
|
|
375
|
+
- `ApiError`: API request failures
|
|
376
|
+
- `ValidationError`: Invalid request parameters
|
|
377
|
+
- `ConnectionError`: Network connectivity issues
|
|
564
378
|
|
|
565
379
|
## Browser Support
|
|
566
380
|
|
|
567
|
-
|
|
381
|
+
- Chrome 80+
|
|
382
|
+
- Firefox 75+
|
|
383
|
+
- Safari 13+
|
|
384
|
+
- Edge 80+
|
|
385
|
+
|
|
386
|
+
## Requirements
|
|
568
387
|
|
|
569
|
-
-
|
|
570
|
-
-
|
|
571
|
-
- Promise support
|
|
572
|
-
- LocalStorage (for token caching)
|
|
388
|
+
- Modern browser with ES2018+ support
|
|
389
|
+
- No external dependencies
|
|
573
390
|
|
|
574
391
|
## License
|
|
575
392
|
|
|
576
|
-
MIT
|
|
393
|
+
MIT License
|