gloomberb 0.18.3 → 0.18.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +8 -8
- package/README.zh-CN.md +11 -11
- package/bin/{gloomberb → gloom} +3 -1
- package/package.json +6 -2
- package/src/account/checkout-handoff.tsx +225 -0
- package/src/account/device-signin-dialog.tsx +2 -2
- package/src/account/device-signin.ts +2 -2
- package/src/account/upgrade-dialog.tsx +1 -1
- package/src/api-client/askg.ts +2 -2
- package/src/api-client/auth.ts +2 -2
- package/src/api-client/central-bank-rates.ts +6 -0
- package/src/api-client/collections.ts +5 -1
- package/src/api-client/cot.ts +2 -0
- package/src/api-client/crypto-etf-flows.ts +37 -0
- package/src/api-client/crypto-markets.ts +60 -0
- package/src/api-client/data.ts +84 -5
- package/src/api-client/doe.ts +15 -0
- package/src/api-client/equity-screener.ts +28 -0
- package/src/api-client/exchange-announcements.ts +38 -0
- package/src/api-client/fund-facts.ts +39 -0
- package/src/api-client/futures-curve.ts +9 -1
- package/src/api-client/hiring.ts +301 -0
- package/src/api-client/index.ts +22 -5
- package/src/api-client/market-discovery.ts +14 -0
- package/src/api-client/members.ts +6 -0
- package/src/api-client/mna.ts +6 -0
- package/src/api-client/paths.ts +18 -1
- package/src/api-client/request.ts +21 -4
- package/src/api-client/short-side-publications.ts +37 -0
- package/src/api-client/socket.ts +64 -4
- package/src/api-client/swap-curve.ts +35 -0
- package/src/api-client/themes.ts +7 -1
- package/src/api-client/types.ts +90 -2
- package/src/app/pane-runtime/plugin-bindings.ts +9 -2
- package/src/app/runtime/desktop-deeplink.ts +5 -5
- package/src/app/runtime/plugin-bindings.ts +2 -2
- package/src/app/runtime/startup.ts +13 -0
- package/src/app/star-prompt/status-line.tsx +2 -2
- package/src/architecture/core-builtin-allowlist.json +5 -2
- package/src/architecture/ui-literals-allowlist.json +3 -3
- package/src/architecture/ui-tokens-allowlist.json +1 -1
- package/src/brokers/broker-portfolio-sync.ts +37 -0
- package/src/brokers/directory.ts +11 -0
- package/src/brokers/logos.ts +3 -1
- package/src/brokers/signed-in/adapter.ts +304 -26
- package/src/brokers/signed-in/client.ts +14 -2
- package/src/brokers/signed-in/connect.ts +10 -2
- package/src/brokers/sync-broker-instance.ts +9 -1
- package/src/capabilities/chart-series.ts +22 -6
- package/src/cli/bank-section.ts +1 -1
- package/src/cli/base-converter.ts +23 -14
- package/src/cli/central-bank-events.ts +1 -1
- package/src/cli/command-options.ts +59 -4
- package/src/cli/commands/api.ts +9 -6
- package/src/cli/commands/broker.ts +2 -2
- package/src/cli/commands/command-utils.ts +2 -2
- package/src/cli/commands/crypto-hints.ts +7 -20
- package/src/cli/commands/fred-series.ts +4 -2
- package/src/cli/commands/keybindings.ts +2 -2
- package/src/cli/commands/market.ts +1117 -264
- package/src/cli/commands/news-hints.ts +2 -2
- package/src/cli/commands/news-search.ts +59 -6
- package/src/cli/commands/options-leaps.ts +41 -26
- package/src/cli/commands/overview.ts +121 -48
- package/src/cli/commands/plugins.ts +9 -9
- package/src/cli/commands/remote.ts +13 -10
- package/src/cli/commands/search.ts +64 -44
- package/src/cli/commands/system.ts +27 -19
- package/src/cli/commands/themes.ts +1 -1
- package/src/cli/commands/ticker.ts +192 -47
- package/src/cli/context.ts +3 -2
- package/src/cli/desktop-pane-shot-view.ts +2 -2
- package/src/cli/desktop-pane-shot.ts +1 -1
- package/src/cli/earnings-calendar.ts +4 -4
- package/src/cli/entry.ts +18 -1
- package/src/cli/errors.ts +20 -2
- package/src/cli/exit-codes.ts +1 -1
- package/src/cli/export-source.ts +10 -4
- package/src/cli/freshness.ts +2 -8
- package/src/cli/fx-forward.ts +130 -0
- package/src/cli/fx-pair.ts +10 -9
- package/src/cli/glossary.ts +64 -20
- package/src/cli/help.ts +19 -13
- package/src/cli/history-export.ts +126 -0
- package/src/cli/history-rows.ts +196 -43
- package/src/cli/index-roots.ts +5 -45
- package/src/cli/index.ts +24 -18
- package/src/cli/known-gaps.ts +118 -25
- package/src/cli/listing-arg.ts +300 -41
- package/src/cli/name-entries.ts +30 -18
- package/src/cli/native-smoke.ts +2 -0
- package/src/cli/not-a-ticker.ts +19 -9
- package/src/cli/opentui-libc.ts +5 -0
- package/src/cli/options.ts +12 -0
- package/src/cli/pane-functions/capabilities.ts +75 -20
- package/src/cli/pane-functions/catalog.ts +24 -23
- package/src/cli/pane-functions/discovery.ts +1 -1
- package/src/cli/pane-functions/dom.ts +10 -7
- package/src/cli/pane-functions/financial-ratio-shot.ts +2 -2
- package/src/cli/pane-functions/freshness.ts +174 -23
- package/src/cli/pane-functions/function-help.ts +66 -27
- package/src/cli/pane-functions/headless.ts +24 -11
- package/src/cli/pane-functions/index.ts +18 -16
- package/src/cli/pane-functions/options.ts +22 -2
- package/src/cli/pane-functions/report-notices.ts +12 -4
- package/src/cli/pane-functions/report.ts +5 -5
- package/src/cli/pane-functions/resolver.ts +47 -10
- package/src/cli/pane-functions/screenshot-assessment.ts +322 -0
- package/src/cli/pane-functions/screenshot-bridge.ts +152 -0
- package/src/cli/pane-functions/screenshot-chart-evidence.ts +396 -0
- package/src/cli/pane-functions/screenshot-data-evidence.ts +383 -0
- package/src/cli/pane-functions/screenshot-evidence.ts +1 -1
- package/src/cli/pane-functions/screenshot-payload.ts +453 -0
- package/src/cli/pane-functions/screenshot-render.ts +316 -0
- package/src/cli/pane-functions/screenshot-types.ts +162 -0
- package/src/cli/pane-functions/shot-options.ts +8 -3
- package/src/cli/peso-dollar-rates.ts +79 -0
- package/src/cli/quote-answer.ts +38 -3
- package/src/cli/report-tables.ts +61 -16
- package/src/cli/restore-plugins.ts +29 -14
- package/src/cli/result.ts +111 -22
- package/src/cli/series-search.ts +5 -5
- package/src/cli/statement-filings.ts +19 -0
- package/src/cli/suffixed-listing-rows.ts +49 -0
- package/src/cli/symbol-args.ts +50 -15
- package/src/cli/symbol-cells.ts +120 -0
- package/src/cli/symbol-list.ts +198 -68
- package/src/cli/symbol-rows.ts +131 -25
- package/src/cli/ticker-resolution.ts +108 -11
- package/src/cli/treasury-yields.ts +5 -5
- package/src/cli/types.ts +2 -0
- package/src/cli/uncovered-instrument.ts +3 -3
- package/src/cli/unknown-command.ts +6 -6
- package/src/components/chart/composite/chart-layout.ts +131 -0
- package/src/components/chart/composite/composite-chart.tsx +373 -16
- package/src/components/chart/composite/interactions.ts +7 -2
- package/src/components/chart/composite/legend.tsx +75 -3
- package/src/components/chart/composite/levels.ts +5 -0
- package/src/components/chart/composite/panel-gestures.ts +41 -0
- package/src/components/chart/composite/panel-labels.ts +2 -1
- package/src/components/chart/composite/panel-surface.tsx +305 -11
- package/src/components/chart/composite/price-axis-labels.tsx +27 -3
- package/src/components/chart/composite/rasterizer.ts +44 -19
- package/src/components/chart/composite/scene.ts +16 -4
- package/src/components/chart/composite/text-renderer.ts +48 -21
- package/src/components/chart/composite/toolbar.tsx +52 -5
- package/src/components/chart/composite/types.ts +13 -0
- package/src/components/chart/composite/use-composite-chart-keyboard.ts +120 -13
- package/src/components/chart/composite/use-composite-value-scales.ts +44 -0
- package/src/components/chart/composite/use-composite-viewport.ts +12 -3
- package/src/components/chart/composite/value-scale.ts +149 -0
- package/src/components/chart/composite/volume-profile-paint.ts +6 -3
- package/src/components/chart/core/pointer.ts +2 -0
- package/src/components/chart-table/index.ts +2 -0
- package/src/components/chart-table/read.tsx +74 -0
- package/src/components/command-bar/commands/collection-list.ts +41 -19
- package/src/components/command-bar/commands/collection.ts +9 -3
- package/src/components/command-bar/commands/direct/index.ts +1 -1
- package/src/components/command-bar/commands/direct/runtime.ts +3 -2
- package/src/components/command-bar/pane-templates/items.ts +59 -6
- package/src/components/command-bar/pane-templates/workflow.ts +10 -1
- package/src/components/command-bar/routes/root/plugin-install.ts +1 -1
- package/src/components/command-bar/routes/root/provider-search.ts +42 -11
- package/src/components/command-bar/routes/root/results.ts +18 -4
- package/src/components/command-bar/routes/root/runtime.ts +15 -3
- package/src/components/command-bar/routes/root/search-providers.ts +25 -2
- package/src/components/command-bar/routes/root/selection.ts +6 -1
- package/src/components/command-bar/routes/root/shortcut-feedback.ts +4 -1
- package/src/components/command-bar/routes/root/shortcuts.ts +30 -3
- package/src/components/command-bar/routes/ticker-search/results.ts +73 -4
- package/src/components/command-bar/selection-runtime.ts +50 -10
- package/src/components/command-bar/surface/index.tsx +24 -2
- package/src/components/command-bar/view-model.ts +7 -0
- package/src/components/command-bar/workflow/broker.ts +2 -2
- package/src/components/command-bar/workflow/collection-actions.ts +46 -7
- package/src/components/command-bar/workflow/collection-ticker.ts +32 -4
- package/src/components/command-bar/workflow/fields.ts +8 -2
- package/src/components/command-bar/workflow/ops.ts +18 -4
- package/src/components/command-bar/workflow/portfolio-position.ts +53 -4
- package/src/components/command-bar/workflow/submit.ts +3 -2
- package/src/components/command-bar/workflow/tickers.ts +5 -1
- package/src/components/company-logo.tsx +39 -0
- package/src/components/data-table/sections.ts +4 -2
- package/src/components/form-modal/confirm.tsx +2 -1
- package/src/components/form-modal/request.ts +5 -0
- package/src/components/form-modal/routes.ts +4 -1
- package/src/components/index.ts +12 -6
- package/src/components/layout/header.tsx +7 -6
- package/src/components/layout/market-summary.ts +9 -6
- package/src/components/layout/pane/capture-status.ts +1 -1
- package/src/components/layout/pane/footer/model.ts +11 -5
- package/src/components/layout/shell/chrome.ts +19 -6
- package/src/components/layout/shell/index.tsx +2 -1
- package/src/components/layout/shell/pane/layers.tsx +19 -1
- package/src/components/layout/status-bar.tsx +2 -2
- package/src/components/market-board/index.tsx +11 -3
- package/src/components/onboarding/onboarding-wizard.tsx +1 -0
- package/src/components/onboarding/portfolio-step/broker-setup-panel.tsx +2 -2
- package/src/components/onboarding/wizard-broker-sync.ts +4 -1
- package/src/components/pane-settings-dialog/desktop.tsx +20 -7
- package/src/components/pane-settings-dialog/tui.tsx +17 -9
- package/src/components/pane-settings-dialog/value.ts +8 -1
- package/src/components/pane-settings-dialog.tsx +44 -13
- package/src/components/sign-in-code-panel.tsx +27 -19
- package/src/components/ui/column-grid.tsx +48 -4
- package/src/components/ui/country-flag-art.tsx +180 -0
- package/src/components/ui/country-flag.tsx +118 -12
- package/src/components/ui/data-table/opentui/index.tsx +61 -2
- package/src/components/ui/data-table/opentui/model.ts +109 -2
- package/src/components/ui/data-table/types.ts +1 -1
- package/src/components/ui/display.tsx +5 -1
- package/src/components/ui/index.ts +3 -1
- package/src/components/ui/logo-mark.tsx +11 -2
- package/src/components/ui/query-bar.tsx +1 -1
- package/src/components/ui/row-notes.ts +79 -0
- package/src/core/state/app/layout.ts +4 -4
- package/src/data/cached-query.ts +8 -1
- package/src/data/config/chart-settings.ts +3 -3
- package/src/data/config/home.ts +10 -2
- package/src/data/config/layout.ts +4 -1
- package/src/data/config/store/node.ts +4 -0
- package/src/data/config/store/normalize.ts +13 -3
- package/src/data/config/store/portfolio-as-of-column.ts +2 -2
- package/src/data/json-storage.ts +2 -0
- package/src/data/saved-copies.ts +84 -0
- package/src/docs/snapshot.json +65 -32
- package/src/i18n/es.ts +29 -12
- package/src/i18n/ja.ts +29 -12
- package/src/i18n/ko.ts +29 -12
- package/src/i18n/zh-cn.ts +29 -12
- package/src/i18n/zh-tw.ts +29 -12
- package/src/layout/desks.ts +1 -1
- package/src/layout/launch-layout.ts +1 -1
- package/src/layout/pane-manager/floating-actions.ts +5 -3
- package/src/layout/pane-manager/floating.ts +43 -1
- package/src/layout/pane-manager/index.ts +2 -0
- package/src/layout/selected-ticker.ts +74 -0
- package/src/market-data/depositary-pair.ts +251 -0
- package/src/market-data/futures-board.ts +1 -1
- package/src/market-data/futures-contract.ts +124 -40
- package/src/market-data/fx-closes.ts +17 -2
- package/src/market-data/hooks.tsx +19 -11
- package/src/market-data/market/change-basis.ts +49 -7
- package/src/market-data/market/freshness.ts +34 -5
- package/src/market-data/market/period-return.ts +163 -0
- package/src/market-data/market/trading-sessions.ts +13 -0
- package/src/market-data/market/year-to-date.ts +8 -13
- package/src/market-data/performance.ts +20 -14
- package/src/market-data/perpetual-premium.ts +32 -0
- package/src/market-data/published-apac-sessions.ts +2 -1
- package/src/market-data/published-futures-sessions.ts +69 -0
- package/src/market-data/quotes/contributions.ts +5 -1
- package/src/market-data/quotes/freshness.ts +42 -0
- package/src/market-data/quotes/intraday-bar.ts +37 -0
- package/src/market-data/quotes/regular-session-valuation.ts +13 -8
- package/src/market-data/quotes/resolution.ts +4 -2
- package/src/market-data/tax-equivalent.ts +1 -1
- package/src/market-data/ticker-price-returns.ts +3 -1
- package/src/news/aggregator.ts +5 -1
- package/src/news/news-model.ts +4 -0
- package/src/news/types.ts +11 -0
- package/src/notifications/app-notifier.ts +1 -1
- package/src/plugins/auto-update.ts +2 -2
- package/src/plugins/builtin/account-management/index.tsx +1 -0
- package/src/plugins/builtin/account-management/pane.tsx +9 -8
- package/src/plugins/builtin/alerts/alert-engine.ts +29 -19
- package/src/plugins/builtin/alerts/calendar-events.ts +378 -0
- package/src/plugins/builtin/alerts/cli.ts +485 -76
- package/src/plugins/builtin/alerts/command.ts +5 -10
- package/src/plugins/builtin/alerts/event-rows.ts +9 -5
- package/src/plugins/builtin/alerts/events-pane.tsx +71 -56
- package/src/plugins/builtin/alerts/events.ts +107 -5
- package/src/plugins/builtin/alerts/fired-log.ts +78 -0
- package/src/plugins/builtin/alerts/format.ts +2 -1
- package/src/plugins/builtin/alerts/headless.ts +100 -39
- package/src/plugins/builtin/alerts/history-pane.tsx +105 -62
- package/src/plugins/builtin/alerts/history-rows.ts +89 -0
- package/src/plugins/builtin/alerts/index.tsx +45 -18
- package/src/plugins/builtin/alerts/iv-level.ts +365 -0
- package/src/plugins/builtin/alerts/levels.ts +3 -3
- package/src/plugins/builtin/alerts/pane.tsx +97 -29
- package/src/plugins/builtin/alerts/price.ts +35 -0
- package/src/plugins/builtin/alerts/quotes.ts +24 -0
- package/src/plugins/builtin/alerts/research-builder.ts +84 -11
- package/src/plugins/builtin/alerts/research-rules.ts +76 -3
- package/src/plugins/builtin/alerts/scheduled-check.ts +206 -32
- package/src/plugins/builtin/alerts/scheduled-sources.ts +26 -3
- package/src/plugins/builtin/alerts/scheduled.ts +188 -29
- package/src/plugins/builtin/alerts/storage.ts +13 -10
- package/src/plugins/builtin/alerts/targets.ts +12 -3
- package/src/plugins/builtin/analytics/index.tsx +8 -2
- package/src/plugins/builtin/analytics/metrics.ts +1 -1
- package/src/plugins/builtin/analytics/risk-book.ts +215 -0
- package/src/plugins/builtin/analytics/risk-client.ts +13 -6
- package/src/plugins/builtin/analytics/risk-headless.ts +55 -21
- package/src/plugins/builtin/analytics/risk-math.ts +6 -3
- package/src/plugins/builtin/analytics/risk-model.ts +297 -104
- package/src/plugins/builtin/analytics/risk-options.ts +17 -2
- package/src/plugins/builtin/analytics/risk-pane.tsx +97 -36
- package/src/plugins/builtin/attention/pane.tsx +6 -2
- package/src/plugins/builtin/awards/headless.ts +7 -3
- package/src/plugins/builtin/awards/model.ts +18 -0
- package/src/plugins/builtin/awards/pane.tsx +6 -3
- package/src/plugins/builtin/backtest/headless.ts +3 -3
- package/src/plugins/builtin/backtest/rules.ts +41 -5
- package/src/plugins/builtin/broker-manager/add-flow.tsx +12 -7
- package/src/plugins/builtin/broker-manager/detail.tsx +47 -19
- package/src/plugins/builtin/broker-manager/footer.ts +27 -11
- package/src/plugins/builtin/broker-manager/index.tsx +21 -12
- package/src/plugins/builtin/broker-manager/keyboard.ts +1 -1
- package/src/plugins/builtin/broker-manager/model.ts +12 -2
- package/src/plugins/builtin/broker-manager/pane-actions.tsx +183 -57
- package/src/plugins/builtin/broker-manager/table.ts +28 -12
- package/src/plugins/builtin/broker-trading/account-picker.tsx +2 -1
- package/src/plugins/builtin/broker-trading/chart-levels.ts +82 -13
- package/src/plugins/builtin/broker-trading/controller.ts +45 -13
- package/src/plugins/builtin/broker-trading/dock.tsx +22 -4
- package/src/plugins/builtin/broker-trading/headless.ts +2 -1
- package/src/plugins/builtin/broker-trading/index.tsx +7 -1
- package/src/plugins/builtin/broker-trading/linked-orders.ts +148 -0
- package/src/plugins/builtin/broker-trading/order-feed.ts +75 -7
- package/src/plugins/builtin/broker-trading/orders.tsx +109 -31
- package/src/plugins/builtin/broker-trading/overview-orders.tsx +9 -3
- package/src/plugins/builtin/broker-trading/pane-model.ts +30 -2
- package/src/plugins/builtin/broker-trading/pane.tsx +110 -23
- package/src/plugins/builtin/broker-trading/ticket-parts.tsx +36 -7
- package/src/plugins/builtin/broker-trading/ticket.tsx +112 -31
- package/src/plugins/builtin/buildout/cells.tsx +4 -0
- package/src/plugins/builtin/buildout/detail/index.tsx +5 -1
- package/src/plugins/builtin/buildout/detail/ui.tsx +7 -4
- package/src/plugins/builtin/buildout/pane/index.tsx +25 -12
- package/src/plugins/builtin/buildout/pane/status.tsx +0 -4
- package/src/plugins/builtin/builtin-plugin-meta.ts +1 -1
- package/src/plugins/builtin/catalysts/detail.tsx +3 -2
- package/src/plugins/builtin/catalysts/index.tsx +1 -1
- package/src/plugins/builtin/catalysts/model.ts +49 -4
- package/src/plugins/builtin/catalysts/pane.tsx +6 -8
- package/src/plugins/builtin/central-bank-rates/client.ts +5 -0
- package/src/plugins/builtin/central-bank-rates/headless.ts +36 -10
- package/src/plugins/builtin/central-bank-rates/model.ts +33 -8
- package/src/plugins/builtin/changelog/index.tsx +1 -0
- package/src/plugins/builtin/chart-composer/catalog-inventory.ts +1 -0
- package/src/plugins/builtin/chart-composer/chart-spec-edit.ts +2 -1
- package/src/plugins/builtin/chart-composer/chart-spec.ts +7 -0
- package/src/plugins/builtin/chart-composer/cli-options.ts +2 -5
- package/src/plugins/builtin/chart-composer/data-catalog-pane.tsx +2 -1
- package/src/plugins/builtin/chart-composer/editor/controller.ts +2 -0
- package/src/plugins/builtin/chart-composer/editor.tsx +4 -1
- package/src/plugins/builtin/chart-composer/headless-schema.ts +28 -26
- package/src/plugins/builtin/chart-composer/headless.ts +253 -35
- package/src/plugins/builtin/chart-composer/index.tsx +12 -2
- package/src/plugins/builtin/chart-composer/leverage-overlay.ts +142 -0
- package/src/plugins/builtin/chart-composer/pane.tsx +127 -28
- package/src/plugins/builtin/chart-composer/series-catalog.ts +1 -0
- package/src/plugins/builtin/chart-composer/series-expression.ts +65 -6
- package/src/plugins/builtin/chart-composer/session-history.ts +15 -21
- package/src/plugins/builtin/chart-composer/session-range.ts +4 -2
- package/src/plugins/builtin/chart-composer/settings.ts +31 -19
- package/src/plugins/builtin/chart-composer/use-series-catalog.ts +5 -6
- package/src/plugins/builtin/chart-composer/viewport-labels.ts +18 -8
- package/src/plugins/builtin/chat/attachments/model.ts +3 -1
- package/src/plugins/builtin/chat/content/index.tsx +1 -1
- package/src/plugins/builtin/chat/pane-links/open.ts +1 -1
- package/src/plugins/builtin/chat/people.ts +1 -1
- package/src/plugins/builtin/clinical-trials/client.ts +5 -2
- package/src/plugins/builtin/clinical-trials/model.ts +13 -4
- package/src/plugins/builtin/clinical-trials/pane.tsx +32 -12
- package/src/plugins/builtin/clinical-trials/ticker-sponsor.ts +17 -0
- package/src/plugins/builtin/cloud/askg/controller.ts +1 -1
- package/src/plugins/builtin/cloud/askg/lock-note.ts +1 -1
- package/src/plugins/builtin/cloud/askg/tool-display.ts +1 -1
- package/src/plugins/builtin/cloud/auth-commands.ts +3 -3
- package/src/plugins/builtin/cloud/team/pane-sections.tsx +105 -47
- package/src/plugins/builtin/cloud/team/pane-ui.tsx +42 -4
- package/src/plugins/builtin/cloud/team/pane.tsx +204 -64
- package/src/plugins/builtin/cloud/thesis/store.ts +45 -22
- package/src/plugins/builtin/cloud-tweets/registration.ts +1 -0
- package/src/plugins/builtin/commodities-energy/index.tsx +29 -2
- package/src/plugins/builtin/commodities-energy/view-state.ts +2 -0
- package/src/plugins/builtin/commodity-balances/pane.tsx +11 -4
- package/src/plugins/builtin/company-attention/app-rank.tsx +7 -5
- package/src/plugins/builtin/company-attention/building-model.ts +222 -0
- package/src/plugins/builtin/company-attention/building.tsx +172 -0
- package/src/plugins/builtin/company-attention/client.ts +117 -1
- package/src/plugins/builtin/company-attention/evidence.ts +16 -3
- package/src/plugins/builtin/company-attention/headless.ts +101 -5
- package/src/plugins/builtin/company-attention/index.tsx +6 -3
- package/src/plugins/builtin/company-attention/model.ts +33 -7
- package/src/plugins/builtin/company-attention/moves-model.ts +253 -0
- package/src/plugins/builtin/company-attention/moves.tsx +159 -0
- package/src/plugins/builtin/company-attention/pane.tsx +79 -23
- package/src/plugins/builtin/company-attention/signals-model.ts +229 -0
- package/src/plugins/builtin/company-attention/signals.tsx +160 -0
- package/src/plugins/builtin/company-kpis/headless.ts +3 -2
- package/src/plugins/builtin/company-kpis/model.ts +2 -2
- package/src/plugins/builtin/company-kpis/pane.tsx +1 -1
- package/src/plugins/builtin/composite-plugins.ts +2 -1
- package/src/plugins/builtin/congress-trades/headless.ts +1 -1
- package/src/plugins/builtin/connections/index.ts +1 -0
- package/src/plugins/builtin/correlation/headless-schema.ts +3 -2
- package/src/plugins/builtin/correlation/headless.ts +5 -3
- package/src/plugins/builtin/cot/headless.ts +28 -6
- package/src/plugins/builtin/cot/model.ts +12 -0
- package/src/plugins/builtin/cot/pane.tsx +3 -2
- package/src/plugins/builtin/cpi/headless.ts +5 -1
- package/src/plugins/builtin/cpi/pane.tsx +11 -9
- package/src/plugins/builtin/credit-boards/model.ts +2 -0
- package/src/plugins/builtin/credit-documents/headless.ts +1 -1
- package/src/plugins/builtin/crypto-board/client.ts +86 -0
- package/src/plugins/builtin/crypto-board/defi-view.tsx +218 -0
- package/src/plugins/builtin/crypto-board/defi.ts +239 -0
- package/src/plugins/builtin/crypto-board/headless.ts +117 -6
- package/src/plugins/builtin/crypto-board/index.tsx +8 -3
- package/src/plugins/builtin/crypto-board/model.ts +40 -8
- package/src/plugins/builtin/crypto-board/pane.tsx +55 -21
- package/src/plugins/builtin/crypto-board/series.ts +19 -1
- package/src/plugins/builtin/crypto-etf-flows/client.ts +60 -0
- package/src/plugins/builtin/crypto-etf-flows/headless.ts +132 -0
- package/src/plugins/builtin/crypto-etf-flows/index.tsx +44 -0
- package/src/plugins/builtin/crypto-etf-flows/model.ts +121 -0
- package/src/plugins/builtin/crypto-etf-flows/pane.tsx +193 -0
- package/src/plugins/builtin/debug/index.tsx +1 -0
- package/src/plugins/builtin/dividend-yield/index.tsx +1 -1
- package/src/plugins/builtin/docs/index.tsx +1 -1
- package/src/plugins/builtin/docs/pane.tsx +2 -2
- package/src/plugins/builtin/docs/targets.ts +1 -1
- package/src/plugins/builtin/doe/client.ts +5 -1
- package/src/plugins/builtin/doe/headless.ts +12 -6
- package/src/plugins/builtin/doe/model.ts +43 -6
- package/src/plugins/builtin/doe/pane.tsx +18 -11
- package/src/plugins/builtin/earnings/board-model.ts +13 -6
- package/src/plugins/builtin/earnings/board-table.ts +4 -1
- package/src/plugins/builtin/earnings/board.tsx +253 -50
- package/src/plugins/builtin/earnings/calendar-model.ts +188 -0
- package/src/plugins/builtin/earnings/calendar.tsx +338 -0
- package/src/plugins/builtin/earnings/client.ts +4 -3
- package/src/plugins/builtin/earnings/headless.ts +53 -15
- package/src/plugins/builtin/earnings/history-model.ts +53 -36
- package/src/plugins/builtin/earnings/index.tsx +15 -22
- package/src/plugins/builtin/earnings/model.ts +17 -12
- package/src/plugins/builtin/earnings/scope.ts +89 -0
- package/src/plugins/builtin/earnings-calls/calendar.tsx +310 -0
- package/src/plugins/builtin/earnings-calls/data.ts +146 -2
- package/src/plugins/builtin/earnings-calls/headless.ts +151 -9
- package/src/plugins/builtin/earnings-calls/index.tsx +3 -3
- package/src/plugins/builtin/earnings-calls/lock-note.ts +1 -1
- package/src/plugins/builtin/earnings-calls/pane.tsx +149 -31
- package/src/plugins/builtin/earnings-calls/upcoming.ts +195 -0
- package/src/plugins/builtin/earnings-ripple/pane.tsx +10 -5
- package/src/plugins/builtin/econ/calendar-model.ts +132 -20
- package/src/plugins/builtin/econ/detail-view.tsx +48 -10
- package/src/plugins/builtin/econ/fred-catalog.ts +23 -6
- package/src/plugins/builtin/econ/fred-series-map.ts +4 -0
- package/src/plugins/builtin/econ/index.tsx +112 -25
- package/src/plugins/builtin/econ/print-watch.ts +2 -1
- package/src/plugins/builtin/econ/types.ts +32 -1
- package/src/plugins/builtin/econ-statistics/client.ts +16 -3
- package/src/plugins/builtin/econ-statistics/defs.ts +4 -0
- package/src/plugins/builtin/econ-statistics/detail.tsx +2 -2
- package/src/plugins/builtin/econ-statistics/headless.ts +13 -2
- package/src/plugins/builtin/econ-statistics/index.tsx +3 -3
- package/src/plugins/builtin/econ-statistics/pane.tsx +2 -1
- package/src/plugins/builtin/econ-statistics/stats.ts +103 -0
- package/src/plugins/builtin/econ-statistics/view.ts +16 -1
- package/src/plugins/builtin/equity-screener/client.ts +21 -3
- package/src/plugins/builtin/equity-screener/headless.ts +68 -6
- package/src/plugins/builtin/equity-screener/live.ts +1 -1
- package/src/plugins/builtin/equity-screener/model.ts +6 -0
- package/src/plugins/builtin/equity-screener/pane.tsx +45 -10
- package/src/plugins/builtin/equity-screener/screen-check.ts +90 -0
- package/src/plugins/builtin/equity-screener/ticker-check.tsx +148 -0
- package/src/plugins/builtin/estimate-revisions/headless.ts +3 -1
- package/src/plugins/builtin/estimate-revisions/lock-note.ts +3 -3
- package/src/plugins/builtin/estimate-revisions/model.ts +8 -10
- package/src/plugins/builtin/exposure/headless.ts +51 -6
- package/src/plugins/builtin/exposure/index.tsx +28 -2
- package/src/plugins/builtin/exposure/model.ts +7 -0
- package/src/plugins/builtin/exposure/pane.tsx +6 -1
- package/src/plugins/builtin/fear-greed/index.tsx +1 -1
- package/src/plugins/builtin/filing-events/index.tsx +1 -1
- package/src/plugins/builtin/futures/model.ts +10 -9
- package/src/plugins/builtin/futures/returns.ts +8 -36
- package/src/plugins/builtin/futures/table.tsx +1 -1
- package/src/plugins/builtin/futures-curve/client.ts +40 -9
- package/src/plugins/builtin/futures-curve/headless.ts +39 -17
- package/src/plugins/builtin/futures-curve/model.ts +258 -69
- package/src/plugins/builtin/futures-curve/pane.tsx +46 -17
- package/src/plugins/builtin/fx-matrix/client.ts +15 -8
- package/src/plugins/builtin/fx-matrix/headless.ts +32 -14
- package/src/plugins/builtin/fx-matrix/index.tsx +13 -11
- package/src/plugins/builtin/fx-matrix/live-legs.ts +22 -0
- package/src/plugins/builtin/fx-matrix/settings.ts +2 -1
- package/src/plugins/builtin/gpu/headless.ts +9 -4
- package/src/plugins/builtin/help/index.tsx +13 -3
- package/src/plugins/builtin/holders/beneficial-model.ts +8 -11
- package/src/plugins/builtin/holders/beneficial-report.ts +6 -5
- package/src/plugins/builtin/holders/beneficial-view.tsx +7 -3
- package/src/plugins/builtin/holders/client.ts +13 -1
- package/src/plugins/builtin/holders/format.ts +28 -17
- package/src/plugins/builtin/holders/headless.ts +46 -7
- package/src/plugins/builtin/holders/index-holders.ts +264 -0
- package/src/plugins/builtin/holders/pane.tsx +79 -15
- package/src/plugins/builtin/holders/report-rows.ts +35 -7
- package/src/plugins/builtin/holders/table-model.ts +2 -1
- package/src/plugins/builtin/holders/treemap.tsx +2 -2
- package/src/plugins/builtin/insider/headless.ts +1 -1
- package/src/plugins/builtin/insider/signals-client.ts +1 -1
- package/src/plugins/builtin/insider/signals.tsx +1 -1
- package/src/plugins/builtin/ipo-calendar/pane.tsx +7 -4
- package/src/plugins/builtin/iv-history/client.ts +20 -0
- package/src/plugins/builtin/iv-history/headless.ts +4 -4
- package/src/plugins/builtin/iv-history/index.tsx +1 -1
- package/src/plugins/builtin/iv-history/model.ts +13 -4
- package/src/plugins/builtin/iv-history/series.ts +3 -1
- package/src/plugins/builtin/jobs/lock-note.ts +1 -1
- package/src/plugins/builtin/jobs/model.ts +4 -15
- package/src/plugins/builtin/jobs/pane.tsx +7 -5
- package/src/plugins/builtin/jobs/share-bars.tsx +11 -5
- package/src/plugins/builtin/jodi/pane.tsx +10 -4
- package/src/plugins/builtin/layout-manager/index.tsx +1 -0
- package/src/plugins/builtin/macro-day/headless.ts +20 -7
- package/src/plugins/builtin/macro-day/index.tsx +3 -2
- package/src/plugins/builtin/macro-day/model.ts +29 -8
- package/src/plugins/builtin/macro-day/pane.tsx +46 -10
- package/src/plugins/builtin/macro-day/releases.ts +55 -13
- package/src/plugins/builtin/market-heatmap/data.ts +9 -2
- package/src/plugins/builtin/market-heatmap/evidence.ts +1 -1
- package/src/plugins/builtin/market-heatmap/headless.ts +9 -6
- package/src/plugins/builtin/market-heatmap/index.tsx +3 -3
- package/src/plugins/builtin/market-heatmap/model.ts +10 -7
- package/src/plugins/builtin/market-movers/client.ts +33 -19
- package/src/plugins/builtin/market-movers/headless.ts +8 -2
- package/src/plugins/builtin/market-movers/index.tsx +16 -10
- package/src/plugins/builtin/market-movers/screener.ts +29 -8
- package/src/plugins/builtin/market-movers/session-body.tsx +4 -2
- package/src/plugins/builtin/market-movers/session-table.ts +4 -2
- package/src/plugins/builtin/market-movers/table.ts +4 -1
- package/src/plugins/builtin/market-valuation/headless.ts +2 -0
- package/src/plugins/builtin/market-valuation/view.ts +5 -0
- package/src/plugins/builtin/members/headless.ts +6 -5
- package/src/plugins/builtin/members/pane.tsx +11 -4
- package/src/plugins/builtin/mna/client.ts +1 -0
- package/src/plugins/builtin/mna/detail.tsx +20 -32
- package/src/plugins/builtin/mna/distress/detail.tsx +16 -4
- package/src/plugins/builtin/mna/distress/model.ts +3 -2
- package/src/plugins/builtin/mna/distress/pane.tsx +7 -4
- package/src/plugins/builtin/mna/headless.ts +6 -13
- package/src/plugins/builtin/mna/model.ts +93 -15
- package/src/plugins/builtin/mna/pane.tsx +5 -4
- package/src/plugins/builtin/news/headless.ts +12 -6
- package/src/plugins/builtin/news/index.tsx +10 -1
- package/src/plugins/builtin/news/wire/index.tsx +3 -2
- package/src/plugins/builtin/news/wire/news/command-bar-search.ts +26 -10
- package/src/plugins/builtin/news/wire/news/query-presets.ts +6 -2
- package/src/plugins/builtin/news/wire/rss/cli.ts +3 -3
- package/src/plugins/builtin/notes/cli.ts +49 -14
- package/src/plugins/builtin/openfda/pane.tsx +1 -1
- package/src/plugins/builtin/options/carry.ts +2 -2
- package/src/plugins/builtin/options/index.tsx +1 -1
- package/src/plugins/builtin/options/view.tsx +10 -10
- package/src/plugins/builtin/options-calculator/headless.ts +46 -7
- package/src/plugins/builtin/options-scenario/client.ts +123 -28
- package/src/plugins/builtin/options-scenario/collar.ts +8 -6
- package/src/plugins/builtin/options-scenario/csp-screen-headless.ts +127 -0
- package/src/plugins/builtin/options-scenario/csp-screen-pane.tsx +165 -0
- package/src/plugins/builtin/options-scenario/csp-screen.ts +258 -0
- package/src/plugins/builtin/options-scenario/csp.ts +101 -21
- package/src/plugins/builtin/options-scenario/headless.ts +36 -15
- package/src/plugins/builtin/options-scenario/hedge.ts +20 -14
- package/src/plugins/builtin/options-scenario/index.tsx +28 -3
- package/src/plugins/builtin/options-scenario/model.ts +13 -0
- package/src/plugins/builtin/options-scenario/pane.tsx +9 -5
- package/src/plugins/builtin/perps/equity-row.tsx +11 -3
- package/src/plugins/builtin/perps/freshness.ts +8 -5
- package/src/plugins/builtin/perps/headless.ts +3 -1
- package/src/plugins/builtin/perps/list-perpetuals.ts +25 -4
- package/src/plugins/builtin/perps/live-rows.ts +161 -0
- package/src/plugins/builtin/perps/markets-section.tsx +154 -0
- package/src/plugins/builtin/perps/pane.tsx +36 -17
- package/src/plugins/builtin/perps/venue-markets.ts +96 -0
- package/src/plugins/builtin/plugin-marketplace/index.tsx +2 -1
- package/src/plugins/builtin/plugin-marketplace/pane.tsx +143 -59
- package/src/plugins/builtin/portfolio-list/cli/bulk-symbols.ts +72 -24
- package/src/plugins/builtin/portfolio-list/cli/portfolio-command.ts +158 -141
- package/src/plugins/builtin/portfolio-list/cli/render.ts +49 -20
- package/src/plugins/builtin/portfolio-list/cli/shared.ts +3 -3
- package/src/plugins/builtin/portfolio-list/cli/watchlist-command.ts +29 -24
- package/src/plugins/builtin/portfolio-list/headless.ts +6 -3
- package/src/plugins/builtin/portfolio-list/income.ts +13 -2
- package/src/plugins/builtin/portfolio-list/index.tsx +9 -2
- package/src/plugins/builtin/portfolio-list/pane/index.tsx +21 -8
- package/src/plugins/builtin/portfolio-list/pane/purchase-date-fx.ts +46 -0
- package/src/plugins/builtin/portfolio-list/summary/live-accounts.ts +16 -9
- package/src/plugins/builtin/portfolio-list/summary/totals.ts +2 -15
- package/src/plugins/builtin/power/client.ts +4 -1
- package/src/plugins/builtin/power/evidence.ts +22 -7
- package/src/plugins/builtin/power/gas.tsx +5 -1
- package/src/plugins/builtin/power/pane.tsx +8 -1
- package/src/plugins/builtin/power/prices.tsx +10 -3
- package/src/plugins/builtin/research/analyst-headless.ts +25 -8
- package/src/plugins/builtin/research/analyst-model.ts +68 -3
- package/src/plugins/builtin/research/corporate-actions-pane.tsx +63 -14
- package/src/plugins/builtin/research/event-model.ts +3 -1
- package/src/plugins/builtin/research/event-sources.ts +12 -4
- package/src/plugins/builtin/research/index.tsx +2 -1
- package/src/plugins/builtin/research/relative-valuation-basis.ts +58 -0
- package/src/plugins/builtin/research/relative-valuation-columns.ts +31 -2
- package/src/plugins/builtin/research/relative-valuation-currency.ts +12 -5
- package/src/plugins/builtin/research/relative-valuation-headless.ts +84 -26
- package/src/plugins/builtin/research/relative-valuation-model.ts +88 -19
- package/src/plugins/builtin/research/relative-valuation-pane.tsx +76 -9
- package/src/plugins/builtin/research/relative-valuation-peers.ts +1 -1
- package/src/plugins/builtin/reverse-dcf/model.ts +6 -2
- package/src/plugins/builtin/risk-factors/index.tsx +2 -2
- package/src/plugins/builtin/scanner/lock-note.ts +1 -1
- package/src/plugins/builtin/sec/forms.ts +13 -0
- package/src/plugins/builtin/sec/fund-abroad.ts +32 -0
- package/src/plugins/builtin/sec/fund-facts.ts +68 -8
- package/src/plugins/builtin/sec/headless.ts +85 -8
- package/src/plugins/builtin/sec/index.tsx +58 -12
- package/src/plugins/builtin/sectors/client.ts +2 -1
- package/src/plugins/builtin/sectors/sector-model.ts +11 -15
- package/src/plugins/builtin/series-inventory.ts +2 -0
- package/src/plugins/builtin/shared/broker-reconnect.ts +107 -22
- package/src/plugins/builtin/shared/cloud-upgrade.ts +34 -6
- package/src/plugins/builtin/shared/earnings-calendar.ts +375 -0
- package/src/plugins/builtin/{earnings/estimate-basis.ts → shared/earnings-estimate-basis.ts} +1 -1
- package/src/plugins/builtin/shared/earnings-report.ts +3 -3
- package/src/plugins/builtin/shared/fx-rate-freshness.ts +23 -1
- package/src/plugins/builtin/shared/job-posting.ts +129 -0
- package/src/plugins/builtin/shared/pro-lock-note.ts +3 -3
- package/src/plugins/builtin/shared/report-freshness.ts +3 -0
- package/src/plugins/builtin/shared/research-trading.tsx +21 -0
- package/src/plugins/builtin/shared/series-cache.ts +2 -0
- package/src/plugins/builtin/shared/ticker-surface.ts +2 -1
- package/src/plugins/builtin/short-interest/client.ts +2 -0
- package/src/plugins/builtin/short-interest/headless.ts +41 -12
- package/src/plugins/builtin/short-interest/index.tsx +23 -1
- package/src/plugins/builtin/short-interest/model.ts +70 -19
- package/src/plugins/builtin/short-interest/pane.tsx +19 -2
- package/src/plugins/builtin/short-interest/publications-client.ts +82 -0
- package/src/plugins/builtin/short-interest/publications-headless.ts +29 -0
- package/src/plugins/builtin/short-interest/publications-model.ts +50 -0
- package/src/plugins/builtin/short-interest/publications-pane.tsx +66 -0
- package/src/plugins/builtin/short-interest/schedule.ts +35 -2
- package/src/plugins/builtin/short-interest/surface.tsx +11 -4
- package/src/plugins/builtin/short-interest/types.ts +9 -0
- package/src/plugins/builtin/short-interest/watch-client.ts +14 -8
- package/src/plugins/builtin/short-interest/watch-model.ts +12 -25
- package/src/plugins/builtin/short-interest/watch-pane.tsx +5 -1
- package/src/plugins/builtin/supply-chain/flow.tsx +33 -9
- package/src/plugins/builtin/supply-chain/model.ts +51 -3
- package/src/plugins/builtin/supply-chain/pane.tsx +78 -39
- package/src/plugins/builtin/supply-chain/row-evidence.tsx +1 -1
- package/src/plugins/builtin/themes/headless.ts +8 -5
- package/src/plugins/builtin/themes/model.ts +14 -4
- package/src/plugins/builtin/themes/pane.tsx +24 -5
- package/src/plugins/builtin/thirteenf/headless.ts +5 -5
- package/src/plugins/builtin/thirteenf/signals.ts +3 -1
- package/src/plugins/builtin/ticker-detail/adr-pair/headless.ts +123 -0
- package/src/plugins/builtin/ticker-detail/adr-pair/model.ts +132 -0
- package/src/plugins/builtin/ticker-detail/adr-pair/tab.tsx +87 -0
- package/src/plugins/builtin/ticker-detail/data-panes/historical-prices.tsx +40 -26
- package/src/plugins/builtin/ticker-detail/data-panes/history-bars.ts +8 -4
- package/src/plugins/builtin/ticker-detail/data-panes/returns-history.ts +67 -3
- package/src/plugins/builtin/ticker-detail/data-panes/returns-model.ts +112 -5
- package/src/plugins/builtin/ticker-detail/data-panes/returns-pane.tsx +17 -2
- package/src/plugins/builtin/ticker-detail/financials/aggregation.ts +21 -7
- package/src/plugins/builtin/ticker-detail/financials/model.ts +36 -1
- package/src/plugins/builtin/ticker-detail/financials/offerings.ts +56 -0
- package/src/plugins/builtin/ticker-detail/financials/ratios.ts +62 -13
- package/src/plugins/builtin/ticker-detail/financials/tab.tsx +30 -4
- package/src/plugins/builtin/ticker-detail/headless-schema.ts +14 -2
- package/src/plugins/builtin/ticker-detail/headless.ts +148 -35
- package/src/plugins/builtin/ticker-detail/index.tsx +37 -5
- package/src/plugins/builtin/ticker-detail/overview/model.ts +65 -10
- package/src/plugins/builtin/ticker-detail/overview/pane.tsx +9 -1
- package/src/plugins/builtin/ticker-detail/overview-tab.tsx +68 -11
- package/src/plugins/builtin/ticker-detail/pane.tsx +11 -0
- package/src/plugins/builtin/ticker-detail/quote-footer.ts +8 -3
- package/src/plugins/builtin/ticker-detail/research-tabs.ts +11 -0
- package/src/plugins/builtin/vol-surface/client.ts +5 -4
- package/src/plugins/builtin/vol-surface/headless.ts +12 -3
- package/src/plugins/builtin/vol-surface/model.ts +4 -2
- package/src/plugins/builtin/volatility/model.ts +5 -10
- package/src/plugins/builtin/world-venue-map/basemap-layer.tsx +4 -3
- package/src/plugins/builtin/world-venue-map/basemap.ts +3 -1
- package/src/plugins/builtin/world-venue-map/chokepoint-chart.ts +40 -0
- package/src/plugins/builtin/world-venue-map/evidence.ts +1 -1
- package/src/plugins/builtin/world-venue-map/geo-series.ts +90 -11
- package/src/plugins/builtin/world-venue-map/headless.ts +1 -1
- package/src/plugins/builtin/world-venue-map/index.ts +3 -26
- package/src/plugins/builtin/world-venue-map/layers.ts +1 -1
- package/src/plugins/builtin/world-venue-map/map.tsx +2 -1
- package/src/plugins/builtin/world-venue-map/pane.tsx +4 -2
- package/src/plugins/builtin/world-venue-map/venue-header.tsx +15 -4
- package/src/plugins/builtin/yield-curve/client.ts +25 -0
- package/src/plugins/builtin/yield-curve/curves.ts +7 -4
- package/src/plugins/builtin/yield-curve/headless.ts +38 -4
- package/src/plugins/builtin/yield-curve/history.ts +4 -3
- package/src/plugins/builtin/yield-curve/index.tsx +12 -6
- package/src/plugins/builtin/yield-curve/swaps-model.ts +93 -0
- package/src/plugins/builtin/yield-curve/swaps.tsx +99 -0
- package/src/plugins/bundle.ts +1 -1
- package/src/plugins/catalog-browser.ts +2 -1
- package/src/plugins/compat.ts +3 -3
- package/src/plugins/dependencies.ts +75 -14
- package/src/plugins/extracted-plugins.ts +132 -34
- package/src/plugins/host-link.ts +149 -34
- package/src/plugins/installer.ts +35 -10
- package/src/plugins/loader.ts +206 -38
- package/src/plugins/manager-node.ts +2 -2
- package/src/plugins/marketplace/deactivation.ts +22 -0
- package/src/plugins/marketplace/model.ts +2 -2
- package/src/plugins/marketplace/packs.ts +1 -1
- package/src/plugins/ownership.ts +1 -1
- package/src/plugins/peer-retry.ts +155 -0
- package/src/plugins/registry/contributions.ts +3 -1
- package/src/plugins/registry/index.ts +4 -3
- package/src/plugins/registry/plugin-state.ts +3 -0
- package/src/plugins/seed-notice.ts +20 -0
- package/src/plugins/shortcut-argument.ts +39 -0
- package/src/portfolio/allocation.ts +1 -1
- package/src/portfolio/collection-name.ts +31 -0
- package/src/portfolio/column-values.ts +10 -8
- package/src/portfolio/cost-fx.ts +296 -19
- package/src/portfolio/manual-lots.ts +75 -0
- package/src/portfolio/mutations.ts +60 -22
- package/src/portfolio/suffixed-listings.ts +209 -0
- package/src/portfolio/totals-currency.ts +24 -0
- package/src/public/__snapshots__/public-api.test.ts.snap +14 -0
- package/src/public/time-series.ts +11 -8
- package/src/remote/schema.ts +1 -1
- package/src/renderers/browser/config-host.ts +3 -0
- package/src/renderers/browser/main.tsx +23 -3
- package/src/renderers/dom/boot-frame-page.ts +187 -0
- package/src/renderers/dom/boot-frame.ts +237 -0
- package/src/renderers/dom/build-assets.ts +46 -8
- package/src/renderers/dom/dom-ui-host.tsx +4 -29
- package/src/renderers/dom/host/ascii-text.ts +16 -2
- package/src/renderers/dom/host/box.tsx +43 -2
- package/src/renderers/dom/host/chart-surface.tsx +2 -0
- package/src/renderers/dom/host/hls.chunk.ts +3 -0
- package/src/renderers/dom/host/image-surface.tsx +49 -0
- package/src/renderers/dom/host/media-surface.tsx +24 -18
- package/src/renderers/dom/host/mouse.ts +30 -0
- package/src/renderers/dom/host/size-observer.ts +1 -1
- package/src/renderers/dom/host/style.ts +1 -1
- package/src/renderers/dom/styles.css +76 -0
- package/src/renderers/dom/test-utils.tsx +2 -1
- package/src/renderers/electrobun/bun/application-menu/index.ts +3 -3
- package/src/renderers/electrobun/bun/desktop/backend-requests.ts +3 -0
- package/src/renderers/electrobun/bun/desktop/backend.ts +46 -3
- package/src/renderers/electrobun/bun/desktop/detached-windows.ts +1 -1
- package/src/renderers/electrobun/bun/desktop/host-requests.ts +9 -3
- package/src/renderers/electrobun/bun/desktop/initialization.ts +81 -18
- package/src/renderers/electrobun/bun/external-plugins.ts +29 -7
- package/src/renderers/electrobun/bun/index.ts +11 -1
- package/src/renderers/electrobun/bun/window/boot-frame.ts +67 -0
- package/src/renderers/electrobun/bun/window/create.ts +4 -1
- package/src/renderers/electrobun/shared/boot-frame.ts +7 -0
- package/src/renderers/electrobun/shared/protocol.ts +6 -1
- package/src/renderers/electrobun/view/cli-pane-shot-entry.tsx +1 -1
- package/src/renderers/electrobun/view/config-host.ts +3 -0
- package/src/renderers/electrobun/view/fatal-screen.tsx +1 -1
- package/src/renderers/electrobun/view/main.tsx +30 -4
- package/src/renderers/electrobun/view/news-source.ts +5 -5
- package/src/renderers/electrobun/view/remote/asset-data-client.ts +1 -1
- package/src/renderers/electrobun/view/ui-host.tsx +1 -1
- package/src/renderers/opentui/browser-open.ts +88 -0
- package/src/renderers/opentui/host.tsx +5 -14
- package/src/renderers/opentui/image/loader.ts +3 -2
- package/src/renderers/opentui/native-smoke.ts +10 -1
- package/src/renderers/opentui/pane-image/index.ts +2 -1
- package/src/renderers/opentui/render-lib.ts +253 -0
- package/src/renderers/opentui/render-timing-smoke.ts +1 -1
- package/src/renderers/opentui/start.tsx +1 -1
- package/src/renderers/share/layout-view.tsx +2 -2
- package/src/renderers/share/main.tsx +4 -4
- package/src/renderers/share/view.tsx +1 -1
- package/src/series/resolve.ts +22 -6
- package/src/series/standalone.ts +30 -2
- package/src/series/types.ts +8 -1
- package/src/shares/api.ts +4 -1
- package/src/shares/pane.ts +1 -1
- package/src/sources/gloomberb-cloud/fred-series.ts +46 -1
- package/src/sources/gloomberb-cloud/index.ts +32 -16
- package/src/sources/gloomberb-cloud/news.ts +39 -0
- package/src/sources/gloomberb-cloud/normalizers.ts +14 -1
- package/src/sources/gloomberb-cloud/perpetuals.ts +49 -1
- package/src/sources/listing-symbols.ts +37 -0
- package/src/sources/provider-errors.ts +16 -2
- package/src/sources/provider-router/financial-routes.ts +21 -3
- package/src/sources/provider-router/financials.ts +15 -2
- package/src/sources/provider-router/history.ts +30 -8
- package/src/sources/provider-router/primary.ts +1 -1
- package/src/state/app/bootstrap.ts +23 -0
- package/src/state/hooks/inline-tickers.ts +30 -5
- package/src/sync/controller.ts +1 -1
- package/src/sync/core-contributors.ts +46 -14
- package/src/team/collections-sync.ts +2 -1
- package/src/team/collections.ts +178 -17
- package/src/telemetry/crash-reports.ts +17 -4
- package/src/test-support/builtin-panes.ts +1 -1
- package/src/theme/colors.ts +3 -30
- package/src/theme/ui-tokens.ts +37 -1
- package/src/tickers/company-name-listing.ts +210 -33
- package/src/tickers/index-roots.ts +47 -0
- package/src/tickers/instrument-label.ts +5 -1
- package/src/tickers/metadata.ts +10 -0
- package/src/tickers/perpetual-listing.ts +5 -2
- package/src/tickers/search/home-listing.ts +75 -0
- package/src/tickers/search/index.ts +76 -27
- package/src/tickers/search/ranking.ts +54 -4
- package/src/tickers/search/upsert.ts +29 -0
- package/src/tickers/terminal-codes.ts +416 -40
- package/src/time-series/bar-aggregation.ts +243 -0
- package/src/time-series/base-series.ts +307 -0
- package/src/time-series/chart-bounds.ts +349 -0
- package/src/time-series/chart-seed.ts +142 -0
- package/src/time-series/economic.ts +5 -0
- package/src/time-series/fundamentals.ts +18 -3
- package/src/time-series/history-acquisition.ts +499 -0
- package/src/time-series/leverage.ts +100 -0
- package/src/time-series/market-resolution.ts +4 -2
- package/src/time-series/market.ts +2 -1
- package/src/time-series/price-comparison.ts +175 -30
- package/src/time-series/range.ts +9 -1
- package/src/time-series/resolution.ts +174 -16
- package/src/time-series/resolve-context.ts +157 -0
- package/src/time-series/resolve.ts +126 -1577
- package/src/time-series/series-name.ts +38 -0
- package/src/time-series/series-presentation.ts +208 -0
- package/src/time-series/spec.ts +11 -6
- package/src/time-series/studies.ts +109 -12
- package/src/time-series/tail-reconcile.ts +121 -0
- package/src/time-series/types.ts +29 -2
- package/src/time-series/use-chart-resolution.ts +4 -5
- package/src/types/broker.ts +10 -0
- package/src/types/config.ts +14 -0
- package/src/types/data-provider.ts +14 -0
- package/src/types/exchange-rate.ts +6 -0
- package/src/types/financials.ts +104 -7
- package/src/types/headless.ts +76 -6
- package/src/types/instrument.ts +3 -0
- package/src/types/plugin.ts +65 -8
- package/src/types/price-history.ts +2 -0
- package/src/types/ticker.ts +13 -0
- package/src/types/trading.ts +59 -1
- package/src/ui/ascii-font.ts +13 -1
- package/src/ui/host.tsx +6 -1
- package/src/updater/command-names.ts +175 -0
- package/src/updater/index.ts +10 -5
- package/src/utils/calendar-date.ts +32 -15
- package/src/utils/cash-runway.ts +241 -0
- package/src/utils/central-banks.ts +42 -0
- package/src/utils/cli-output.ts +259 -80
- package/src/utils/contract-month.ts +16 -0
- package/src/utils/crypto-pair.ts +61 -3
- package/src/utils/currency-units.ts +29 -0
- package/src/utils/datetime-format.ts +10 -0
- package/src/utils/debug-log.ts +1 -1
- package/src/utils/decimal-comma.ts +39 -6
- package/src/utils/exchange-announcements.ts +71 -0
- package/src/utils/exchange-rate-snapshot.ts +10 -0
- package/src/utils/financial-statements.ts +83 -4
- package/src/utils/format.ts +34 -16
- package/src/utils/fundamentals.ts +150 -34
- package/src/utils/fx-market-hours.ts +10 -1
- package/src/utils/latest-financial-period.ts +8 -0
- package/src/utils/linux-libc.ts +54 -0
- package/src/utils/market-capitalization.ts +111 -15
- package/src/utils/max-drawdown.ts +64 -0
- package/src/utils/network-failure.ts +83 -0
- package/src/utils/option-expiry.ts +139 -7
- package/src/utils/price-earnings.ts +11 -5
- package/src/utils/price-history.ts +18 -8
- package/src/utils/price-window.ts +131 -0
- package/src/utils/release-date.ts +47 -0
- package/src/utils/sec.ts +3 -0
- package/src/utils/throttled-fetch.ts +11 -4
- package/src/utils/trailing-eps.ts +67 -0
- package/src/utils/typed-text.ts +21 -0
- package/src/utils/utc-time.ts +24 -1
- package/src/version.ts +6 -0
- package/src/cli/pane-functions/screenshot.ts +0 -2122
|
@@ -10,12 +10,15 @@ import { ApiRequestError } from "../../api-client/errors";
|
|
|
10
10
|
import { openUrl } from "../../components/ui/external-link";
|
|
11
11
|
import type { BrokerAdapter, BrokerConnectionStatus, BrokerPosition } from "../../types/broker";
|
|
12
12
|
import type { BrokerInstanceConfig } from "../../types/config";
|
|
13
|
+
import type { Quote } from "../../types/financials";
|
|
13
14
|
import type {
|
|
14
15
|
BrokerAccount,
|
|
15
16
|
BrokerExecution,
|
|
16
17
|
BrokerOrder,
|
|
18
|
+
BrokerOrderPreview,
|
|
17
19
|
BrokerOrderRequest,
|
|
18
20
|
BrokerPortfolioPerformance,
|
|
21
|
+
BrokerTradingCapabilities,
|
|
19
22
|
} from "../../types/trading";
|
|
20
23
|
import { findSignedInBroker, refreshSignedInBrokers } from "./catalog";
|
|
21
24
|
import type { SignedInBroker, SignedInBrokerConnection } from "./client";
|
|
@@ -47,16 +50,50 @@ function brokerReason(lastError: string | null | undefined): string | null {
|
|
|
47
50
|
return described.replace(/[\s.]+$/, "").slice(0, 200) || null;
|
|
48
51
|
}
|
|
49
52
|
|
|
50
|
-
/**
|
|
51
|
-
|
|
53
|
+
/** Gloom holds no live sign-in for the broker: only connecting again helps. */
|
|
54
|
+
class SignInNeededError extends Error {}
|
|
55
|
+
|
|
56
|
+
/**
|
|
57
|
+
* What to tell the user when Gloom answers a broker call with an error, and
|
|
58
|
+
* whether only a new sign-in, to Gloom or the broker, gets the profile going.
|
|
59
|
+
*/
|
|
60
|
+
function describeSignedInBrokerError(error: unknown, brokerName: string): { message: string; needsSignIn: boolean } {
|
|
52
61
|
const status = error instanceof ApiRequestError ? error.status : undefined;
|
|
53
|
-
if (status === 401) return `Sign in to Gloom first, then connect ${brokerName}
|
|
62
|
+
if (status === 401) return { message: `Sign in to Gloom first, then connect ${brokerName}.`, needsSignIn: true };
|
|
54
63
|
const signInAgain = `${brokerName} needs you to sign in again. Press Connect in Brokers.`;
|
|
55
64
|
// A sign-in the broker ended says why, in Gloom's words.
|
|
56
|
-
if (status === 409) return (error instanceof ApiRequestError && writtenMessage(error)) || signInAgain;
|
|
57
|
-
if (status === 404) return signInAgain;
|
|
58
|
-
if (status === 502) return `${brokerName} is not responding. Try again shortly
|
|
59
|
-
|
|
65
|
+
if (status === 409) return { message: (error instanceof ApiRequestError && writtenMessage(error)) || signInAgain, needsSignIn: true };
|
|
66
|
+
if (status === 404) return { message: signInAgain, needsSignIn: true };
|
|
67
|
+
if (status === 502) return { message: `${brokerName} is not responding. Try again shortly.`, needsSignIn: false };
|
|
68
|
+
// A refused order or a busy broker says why without its error code.
|
|
69
|
+
if (error instanceof ApiRequestError && (status === 403 || status === 422 || status === 503)) {
|
|
70
|
+
return { message: writtenMessage(error) ?? error.message, needsSignIn: false };
|
|
71
|
+
}
|
|
72
|
+
return {
|
|
73
|
+
message: error instanceof Error && error.message ? error.message : String(error),
|
|
74
|
+
needsSignIn: error instanceof SignInNeededError,
|
|
75
|
+
};
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
/**
|
|
79
|
+
* Gloom answered an order action and nothing was placed, changed or
|
|
80
|
+
* cancelled: the broker refused it, its check lapsed, trading is not granted,
|
|
81
|
+
* the broker was too busy to take it, or the sign-in has to be renewed. A
|
|
82
|
+
* 502 or a lost answer may have reached the broker, so it is not one.
|
|
83
|
+
*/
|
|
84
|
+
function refusedOrderAction(error: unknown): boolean {
|
|
85
|
+
if (!(error instanceof ApiRequestError)) return false;
|
|
86
|
+
return error.status !== undefined && error.status >= 400 && error.status < 500 || error.status === 503;
|
|
87
|
+
}
|
|
88
|
+
|
|
89
|
+
/** A sign-in that ended or was never made, as opposed to a refused order: the profile's status says so. */
|
|
90
|
+
function signInLost(error: unknown): boolean {
|
|
91
|
+
if (!(error instanceof ApiRequestError)) return false;
|
|
92
|
+
return error.status === 401 || error.status === 404 || error.status === 409 && error.code === "reauth_required";
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
function refused(message: string): Error {
|
|
96
|
+
return Object.assign(new Error(message), { refused: true });
|
|
60
97
|
}
|
|
61
98
|
|
|
62
99
|
/** The broker does not offer this. A broker tool that failed is also a 422, but a failure. */
|
|
@@ -67,7 +104,7 @@ function isUnsupported(error: unknown): boolean {
|
|
|
67
104
|
type BrokerRequest = <T>(
|
|
68
105
|
broker: string,
|
|
69
106
|
path: string,
|
|
70
|
-
options?: { method?: "GET" | "POST" | "DELETE"; body?: unknown },
|
|
107
|
+
options?: { method?: "GET" | "POST" | "PUT" | "DELETE"; body?: unknown },
|
|
71
108
|
) => Promise<T>;
|
|
72
109
|
|
|
73
110
|
export interface SignedInBrokerAdapterDeps {
|
|
@@ -84,6 +121,60 @@ interface PortfolioSnapshot {
|
|
|
84
121
|
fetchedAt?: number;
|
|
85
122
|
}
|
|
86
123
|
|
|
124
|
+
/** Gloom's answer to a direct-mode order, before the user confirms it. */
|
|
125
|
+
interface DirectOrderPreview {
|
|
126
|
+
status: "preview";
|
|
127
|
+
previewId: string;
|
|
128
|
+
expiresAt: string;
|
|
129
|
+
impact: {
|
|
130
|
+
source: "broker" | "unavailable";
|
|
131
|
+
sourceLabel: string;
|
|
132
|
+
currency?: string;
|
|
133
|
+
estimatedCost?: number;
|
|
134
|
+
cashBefore?: number;
|
|
135
|
+
cashAfter?: number;
|
|
136
|
+
commission?: number;
|
|
137
|
+
fees?: number;
|
|
138
|
+
disclosure: string;
|
|
139
|
+
};
|
|
140
|
+
}
|
|
141
|
+
|
|
142
|
+
interface PlacedOrder { status: "placed"; order: BrokerOrder }
|
|
143
|
+
|
|
144
|
+
/** The quote a direct-mode broker gives the ticket. */
|
|
145
|
+
interface SignedInBrokerQuote {
|
|
146
|
+
symbol: string;
|
|
147
|
+
name?: string;
|
|
148
|
+
currency?: string;
|
|
149
|
+
price: number;
|
|
150
|
+
bid?: number;
|
|
151
|
+
ask?: number;
|
|
152
|
+
bidSize?: number;
|
|
153
|
+
askSize?: number;
|
|
154
|
+
lastTradePrice?: number;
|
|
155
|
+
lastUpdated: number;
|
|
156
|
+
dataSource: "live" | "delayed";
|
|
157
|
+
}
|
|
158
|
+
|
|
159
|
+
/** The same order always keys the same, whatever order its fields arrive in. */
|
|
160
|
+
function canonical(value: unknown): string {
|
|
161
|
+
if (Array.isArray(value)) return `[${value.map(canonical).join(",")}]`;
|
|
162
|
+
if (value && typeof value === "object") {
|
|
163
|
+
return `{${Object.entries(value).filter(([, entry]) => entry !== undefined).sort(([a], [b]) => (a < b ? -1 : a > b ? 1 : 0))
|
|
164
|
+
.map(([key, entry]) => `${JSON.stringify(key)}:${canonical(entry)}`).join(",")}}`;
|
|
165
|
+
}
|
|
166
|
+
return JSON.stringify(value) ?? "null";
|
|
167
|
+
}
|
|
168
|
+
|
|
169
|
+
/** The ticket's fields, without the profile's own, as Gloom checks and places the order. */
|
|
170
|
+
function orderBody(request: BrokerOrderRequest): BrokerOrderRequest {
|
|
171
|
+
const { brokerInstanceId: _profile, ...body } = request;
|
|
172
|
+
const { brokerInstanceId: _contractProfile, ...contract } = body.contract;
|
|
173
|
+
return { ...body, contract };
|
|
174
|
+
}
|
|
175
|
+
|
|
176
|
+
const DIRECT_TIF = ["DAY"];
|
|
177
|
+
|
|
87
178
|
export function createSignedInBrokerAdapter(overrides: Partial<SignedInBrokerAdapterDeps> = {}): BrokerAdapter {
|
|
88
179
|
const deps: SignedInBrokerAdapterDeps = {
|
|
89
180
|
request: (broker, path, options) => apiClient.brokerRequest(broker, path, options),
|
|
@@ -95,12 +186,29 @@ export function createSignedInBrokerAdapter(overrides: Partial<SignedInBrokerAda
|
|
|
95
186
|
};
|
|
96
187
|
const statuses = new Map<string, BrokerConnectionStatus>();
|
|
97
188
|
const listeners = new Map<string, Set<() => void>>();
|
|
189
|
+
/** Whether each profile's sign-in granted trading, as its last connect read it. */
|
|
190
|
+
const canTrade = new Map<string, boolean>();
|
|
191
|
+
/** Direct mode: the check the user is reviewing, per profile, by the exact order it was for. */
|
|
192
|
+
const previews = new Map<string, { order: string; previewId: string; expiresAt: number }>();
|
|
193
|
+
/** Direct mode: the broker's own id behind each order number the app holds, per profile. */
|
|
194
|
+
const handles = new Map<string, Map<number, { accountId: string; brokerOrderId: string }>>();
|
|
98
195
|
|
|
99
196
|
const brokerName = (instance: BrokerInstanceConfig) =>
|
|
100
197
|
deps.findBroker(signedInBrokerId(instance))?.name ?? instance.label;
|
|
101
198
|
|
|
102
|
-
|
|
103
|
-
|
|
199
|
+
/** The broker's direct-mode orders, or null for one that keeps orders for review or takes none. */
|
|
200
|
+
const directOrders = (instance: BrokerInstanceConfig) => {
|
|
201
|
+
const orders = deps.findBroker(signedInBrokerId(instance))?.capabilities.orders;
|
|
202
|
+
return orders && orders.mode === "direct" ? orders : null;
|
|
203
|
+
};
|
|
204
|
+
|
|
205
|
+
const setStatus = (instance: BrokerInstanceConfig, state: "connected" | "error", message?: string, needsSignIn = false) => {
|
|
206
|
+
statuses.set(instance.id, {
|
|
207
|
+
state, message, mode: METHOD, updatedAt: deps.now(),
|
|
208
|
+
...(needsSignIn ? { needsSignIn } : {}),
|
|
209
|
+
// A direct-mode broker says per quote whether it is real-time.
|
|
210
|
+
...(directOrders(instance) ? { quoteData: "realtime" as const } : {}),
|
|
211
|
+
});
|
|
104
212
|
for (const listener of listeners.get(instance.id) ?? []) listener();
|
|
105
213
|
};
|
|
106
214
|
|
|
@@ -111,8 +219,8 @@ export function createSignedInBrokerAdapter(overrides: Partial<SignedInBrokerAda
|
|
|
111
219
|
setStatus(instance, "connected");
|
|
112
220
|
return result;
|
|
113
221
|
} catch (error) {
|
|
114
|
-
const message = describeSignedInBrokerError(error, brokerName(instance));
|
|
115
|
-
setStatus(instance, "error", message);
|
|
222
|
+
const { message, needsSignIn } = describeSignedInBrokerError(error, brokerName(instance));
|
|
223
|
+
setStatus(instance, "error", message, needsSignIn);
|
|
116
224
|
throw new Error(message);
|
|
117
225
|
}
|
|
118
226
|
};
|
|
@@ -130,7 +238,51 @@ export function createSignedInBrokerAdapter(overrides: Partial<SignedInBrokerAda
|
|
|
130
238
|
const snapshot = (instance: BrokerInstanceConfig) =>
|
|
131
239
|
track(instance, () => get<PortfolioSnapshot>(instance, "/snapshot"));
|
|
132
240
|
|
|
133
|
-
/**
|
|
241
|
+
/**
|
|
242
|
+
* An order as the app holds it: this profile's, under this adapter, and
|
|
243
|
+
* remembered by its number so a change or cancel can name it to the broker.
|
|
244
|
+
*/
|
|
245
|
+
const ownOrder = (instance: BrokerInstanceConfig, order: BrokerOrder): BrokerOrder => {
|
|
246
|
+
if (order.brokerOrderId && order.accountId) {
|
|
247
|
+
const known = handles.get(instance.id) ?? new Map();
|
|
248
|
+
known.set(order.orderId, { accountId: order.accountId, brokerOrderId: order.brokerOrderId });
|
|
249
|
+
handles.set(instance.id, known);
|
|
250
|
+
}
|
|
251
|
+
return { ...order, brokerInstanceId: instance.id, contract: { ...order.contract, brokerId: SIGNED_IN_BROKER_TYPE, brokerInstanceId: instance.id } };
|
|
252
|
+
};
|
|
253
|
+
|
|
254
|
+
/**
|
|
255
|
+
* One order action. A refusal leaves the profile's status alone (the
|
|
256
|
+
* broker is fine; the order is not) and is marked refused; a sign-in that
|
|
257
|
+
* ended shows on the profile as any failed call does.
|
|
258
|
+
*/
|
|
259
|
+
const orderAction = async <T>(instance: BrokerInstanceConfig, run: () => Promise<T>): Promise<T> => {
|
|
260
|
+
try {
|
|
261
|
+
const result = await run();
|
|
262
|
+
setStatus(instance, "connected");
|
|
263
|
+
return result;
|
|
264
|
+
} catch (error) {
|
|
265
|
+
const { message, needsSignIn } = describeSignedInBrokerError(error, brokerName(instance));
|
|
266
|
+
if (signInLost(error)) setStatus(instance, "error", message, needsSignIn);
|
|
267
|
+
throw refusedOrderAction(error) ? refused(message) : new Error(message);
|
|
268
|
+
}
|
|
269
|
+
};
|
|
270
|
+
|
|
271
|
+
/** The broker's id for an order number; nothing is sent when it cannot be found. */
|
|
272
|
+
const brokerOrderHandle = async (instance: BrokerInstanceConfig, orderId: number) => {
|
|
273
|
+
const known = handles.get(instance.id)?.get(orderId);
|
|
274
|
+
if (known) return known;
|
|
275
|
+
try {
|
|
276
|
+
for (const order of await get<BrokerOrder[]>(instance, "/orders")) ownOrder(instance, order);
|
|
277
|
+
} catch (error) {
|
|
278
|
+
throw refused(describeSignedInBrokerError(error, brokerName(instance)).message);
|
|
279
|
+
}
|
|
280
|
+
const found = handles.get(instance.id)?.get(orderId);
|
|
281
|
+
if (!found) throw refused("This order is no longer listed. Refresh your orders.");
|
|
282
|
+
return found;
|
|
283
|
+
};
|
|
284
|
+
|
|
285
|
+
/** Checks an order against what the broker takes, before Gloom sees it: a failure sent nothing. */
|
|
134
286
|
const checkOrder = async (instance: BrokerInstanceConfig, request: BrokerOrderRequest) => {
|
|
135
287
|
const id = signedInBrokerId(instance);
|
|
136
288
|
let broker = deps.findBroker(id);
|
|
@@ -140,14 +292,25 @@ export function createSignedInBrokerAdapter(overrides: Partial<SignedInBrokerAda
|
|
|
140
292
|
}
|
|
141
293
|
const name = broker?.name ?? instance.label;
|
|
142
294
|
const orders = broker?.capabilities.orders;
|
|
143
|
-
if (!orders) throw
|
|
295
|
+
if (!orders) throw refused(`${name} does not take orders from Gloom.`);
|
|
144
296
|
if (!orders.types.includes(request.orderType)) {
|
|
145
|
-
throw
|
|
297
|
+
throw refused(`${name} does not take ${request.orderType} orders from Gloom.`);
|
|
298
|
+
}
|
|
299
|
+
// A server that does not say it takes a bracket, an OCO pair or a trailing stop would drop its fields and place a bare
|
|
300
|
+
// order: never send one it has not named.
|
|
301
|
+
if (!request.orderClass && (request.takeProfitPrice !== undefined || request.stopLossPrice !== undefined)) {
|
|
302
|
+
throw refused("A take profit or stop loss needs a bracket or OCO order.");
|
|
303
|
+
}
|
|
304
|
+
if (request.orderClass && !orders.orderClasses?.includes(request.orderClass)) {
|
|
305
|
+
throw refused(`${name} does not take ${request.orderClass === "oco" ? "OCO" : "bracket"} orders from Gloom.`);
|
|
306
|
+
}
|
|
307
|
+
if (request.orderType === "TRAIL" && !orders.trailing?.includes(request.trailingPercent !== undefined ? "percent" : "amount")) {
|
|
308
|
+
throw refused(`${name} does not take this trailing stop from Gloom.`);
|
|
146
309
|
}
|
|
147
|
-
if (!(request.quantity > 0)) throw
|
|
310
|
+
if (!(request.quantity > 0)) throw refused("Quantity must be positive.");
|
|
148
311
|
const needsLimit = request.orderType === "LMT" || request.orderType === "STP LMT";
|
|
149
312
|
if (needsLimit && !(typeof request.limitPrice === "number" && request.limitPrice > 0)) {
|
|
150
|
-
throw
|
|
313
|
+
throw refused("A limit order needs a limit price.");
|
|
151
314
|
}
|
|
152
315
|
return { name, mode: orders.mode };
|
|
153
316
|
};
|
|
@@ -156,6 +319,8 @@ export function createSignedInBrokerAdapter(overrides: Partial<SignedInBrokerAda
|
|
|
156
319
|
id: SIGNED_IN_BROKER_TYPE,
|
|
157
320
|
name: "Signed-in broker",
|
|
158
321
|
configSchema: [],
|
|
322
|
+
// A signed-in broker's quotes come through Gloom and count against the broker's allowance.
|
|
323
|
+
ticketQuotesOnly: true,
|
|
159
324
|
|
|
160
325
|
async validate() {
|
|
161
326
|
return true;
|
|
@@ -191,17 +356,51 @@ export function createSignedInBrokerAdapter(overrides: Partial<SignedInBrokerAda
|
|
|
191
356
|
return getOptional<BrokerExecution[]>(instance, "/executions?period=DAYS_90", []);
|
|
192
357
|
},
|
|
193
358
|
|
|
194
|
-
listOpenOrders(instance) {
|
|
195
|
-
return getOptional<BrokerOrder[]>(instance, "/orders", []);
|
|
359
|
+
async listOpenOrders(instance) {
|
|
360
|
+
return (await getOptional<BrokerOrder[]>(instance, "/orders", [])).map((order) => ownOrder(instance, order));
|
|
196
361
|
},
|
|
197
362
|
|
|
198
363
|
async previewOrder(instance, request) {
|
|
199
364
|
const { name, mode } = await checkOrder(instance, request);
|
|
200
|
-
|
|
365
|
+
if (mode === "review") return { warningText: `${name} opens this order for you to review and submit.` };
|
|
366
|
+
const answer = await orderAction(instance, () => deps.request<DirectOrderPreview>(
|
|
367
|
+
signedInBrokerId(instance),
|
|
368
|
+
"/orders",
|
|
369
|
+
{ method: "POST", body: orderBody(request) },
|
|
370
|
+
));
|
|
371
|
+
previews.set(instance.id, { order: canonical(orderBody(request)), previewId: answer.previewId, expiresAt: Date.parse(answer.expiresAt) });
|
|
372
|
+
const { impact } = answer;
|
|
373
|
+
const preview: BrokerOrderPreview = {
|
|
374
|
+
impactSource: impact.source,
|
|
375
|
+
impactSourceLabel: impact.sourceLabel,
|
|
376
|
+
disclosure: impact.disclosure,
|
|
377
|
+
currency: impact.currency,
|
|
378
|
+
estimatedCost: impact.estimatedCost,
|
|
379
|
+
commission: impact.commission,
|
|
380
|
+
commissionCurrency: impact.commission === undefined ? undefined : impact.currency,
|
|
381
|
+
fees: impact.fees,
|
|
382
|
+
cashBefore: impact.cashBefore,
|
|
383
|
+
cashAfter: impact.cashAfter,
|
|
384
|
+
};
|
|
385
|
+
return Object.fromEntries(Object.entries(preview).filter(([, value]) => value !== undefined)) as BrokerOrderPreview;
|
|
201
386
|
},
|
|
202
387
|
|
|
203
388
|
async placeOrder(instance, request) {
|
|
204
|
-
const { name } = await checkOrder(instance, request);
|
|
389
|
+
const { name, mode } = await checkOrder(instance, request);
|
|
390
|
+
if (mode === "direct") {
|
|
391
|
+
// Only the order the user reviewed, while its check stands.
|
|
392
|
+
const preview = previews.get(instance.id);
|
|
393
|
+
if (!preview || preview.order !== canonical(orderBody(request)) || !(preview.expiresAt > deps.now())) {
|
|
394
|
+
throw refused("Review this order again before placing it.");
|
|
395
|
+
}
|
|
396
|
+
const placed = await orderAction(instance, () => deps.request<PlacedOrder>(
|
|
397
|
+
signedInBrokerId(instance),
|
|
398
|
+
"/orders",
|
|
399
|
+
{ method: "POST", body: { ...orderBody(request), previewId: preview.previewId } },
|
|
400
|
+
));
|
|
401
|
+
previews.delete(instance.id);
|
|
402
|
+
return ownOrder(instance, placed.order);
|
|
403
|
+
}
|
|
205
404
|
const placed = await track(instance, () => deps.request<{ status: string; id: string; reviewUrl: string }>(
|
|
206
405
|
signedInBrokerId(instance),
|
|
207
406
|
"/orders",
|
|
@@ -228,23 +427,102 @@ export function createSignedInBrokerAdapter(overrides: Partial<SignedInBrokerAda
|
|
|
228
427
|
};
|
|
229
428
|
},
|
|
230
429
|
|
|
231
|
-
async modifyOrder(instance) {
|
|
430
|
+
async modifyOrder(instance, orderId, request) {
|
|
431
|
+
const { name, mode } = await checkOrder(instance, request);
|
|
432
|
+
if (mode !== "direct") throw refused(`Orders sent to ${name} are managed in ${name}.`);
|
|
433
|
+
const handle = await brokerOrderHandle(instance, orderId);
|
|
434
|
+
const changed = await orderAction(instance, () => deps.request<PlacedOrder>(
|
|
435
|
+
signedInBrokerId(instance),
|
|
436
|
+
`/orders/${encodeURIComponent(handle.brokerOrderId)}`,
|
|
437
|
+
{ method: "PUT", body: { ...orderBody(request), accountId: handle.accountId } },
|
|
438
|
+
));
|
|
439
|
+
return ownOrder(instance, changed.order);
|
|
440
|
+
},
|
|
441
|
+
|
|
442
|
+
async cancelOrder(instance, orderId) {
|
|
232
443
|
const name = brokerName(instance);
|
|
233
|
-
throw
|
|
444
|
+
if (!directOrders(instance)) throw refused(`Orders sent to ${name} are managed in ${name}.`);
|
|
445
|
+
const handle = await brokerOrderHandle(instance, orderId);
|
|
446
|
+
await orderAction(instance, () => deps.request<{ cancelled: boolean }>(
|
|
447
|
+
signedInBrokerId(instance),
|
|
448
|
+
`/orders/${encodeURIComponent(handle.brokerOrderId)}?accountId=${encodeURIComponent(handle.accountId)}`,
|
|
449
|
+
{ method: "DELETE" },
|
|
450
|
+
));
|
|
234
451
|
},
|
|
235
452
|
|
|
236
|
-
|
|
453
|
+
/**
|
|
454
|
+
* Direct mode only: what the ticket offers. Trading needs the profile
|
|
455
|
+
* switched on and a sign-in that granted it; the broker's linked
|
|
456
|
+
* account may still be read-only, which its check then says.
|
|
457
|
+
*/
|
|
458
|
+
getTradingCapabilities(instance) {
|
|
237
459
|
const name = brokerName(instance);
|
|
238
|
-
|
|
460
|
+
const orders = directOrders(instance);
|
|
461
|
+
if (!orders) {
|
|
462
|
+
return { enabled: false, disabledReason: `${name} does not take orders from the ticket.`, orderTypes: [], tif: [] };
|
|
463
|
+
}
|
|
464
|
+
const granted = canTrade.get(instance.id) === true;
|
|
465
|
+
const switchedOn = instance.config.tradingEnabled === true;
|
|
466
|
+
const capabilities: BrokerTradingCapabilities = {
|
|
467
|
+
enabled: granted && switchedOn,
|
|
468
|
+
orderTypes: [...orders.types],
|
|
469
|
+
tif: orders.tif?.length ? [...orders.tif] : DIRECT_TIF,
|
|
470
|
+
...(orders.orderClasses?.length ? { orderClasses: [...orders.orderClasses] } : {}),
|
|
471
|
+
...(orders.trailing?.length ? { trailing: [...orders.trailing] } : {}),
|
|
472
|
+
minQuantity: 1,
|
|
473
|
+
quantityStep: 1,
|
|
474
|
+
modify: true,
|
|
475
|
+
cancel: true,
|
|
476
|
+
executionKind: "order-summaries",
|
|
477
|
+
};
|
|
478
|
+
if (!granted) capabilities.disabledReason = `${name} is connected read-only. Connect it again in Brokers to allow trading.`;
|
|
479
|
+
else if (!switchedOn) capabilities.disabledReason = "Trading is off for this profile.";
|
|
480
|
+
return capabilities;
|
|
481
|
+
},
|
|
482
|
+
|
|
483
|
+
getTradingConfigUpdate(_instance, enabled) {
|
|
484
|
+
return { tradingEnabled: enabled };
|
|
485
|
+
},
|
|
486
|
+
|
|
487
|
+
// The ticket's quote. A symbol the broker cannot price, or its request
|
|
488
|
+
// allowance spent, is the ticket's to say; only a lost sign-in is the profile's.
|
|
489
|
+
async getQuote(ticker, instance) {
|
|
490
|
+
const id = signedInBrokerId(instance);
|
|
491
|
+
if (!directOrders(instance)) throw new Error(`${brokerName(instance)} gives no quotes to the ticket.`);
|
|
492
|
+
const answer = await orderAction(instance, () => deps.request<SignedInBrokerQuote>(
|
|
493
|
+
id,
|
|
494
|
+
`/quote?symbol=${encodeURIComponent(ticker.trim().toUpperCase())}`,
|
|
495
|
+
));
|
|
496
|
+
const quote: Quote = {
|
|
497
|
+
symbol: answer.symbol,
|
|
498
|
+
name: answer.name,
|
|
499
|
+
price: answer.price,
|
|
500
|
+
bid: answer.bid,
|
|
501
|
+
ask: answer.ask,
|
|
502
|
+
bidSize: answer.bidSize,
|
|
503
|
+
askSize: answer.askSize,
|
|
504
|
+
currency: answer.currency ?? "USD",
|
|
505
|
+
// The broker gives no prior close: no change to show.
|
|
506
|
+
change: Number.NaN,
|
|
507
|
+
changePercent: Number.NaN,
|
|
508
|
+
changeBasis: "none",
|
|
509
|
+
lastUpdated: answer.lastUpdated,
|
|
510
|
+
receivedAt: deps.now(),
|
|
511
|
+
dataSource: answer.dataSource,
|
|
512
|
+
delivery: "poll",
|
|
513
|
+
providerId: id,
|
|
514
|
+
};
|
|
515
|
+
return quote;
|
|
239
516
|
},
|
|
240
517
|
|
|
241
518
|
async connect(instance) {
|
|
242
519
|
await track(instance, async () => {
|
|
243
520
|
const connection = await get<SignedInBrokerConnection>(instance, "");
|
|
521
|
+
canTrade.set(instance.id, connection.status === "connected" && connection.canTrade === true);
|
|
244
522
|
if (connection.status !== "connected") {
|
|
245
523
|
const name = brokerName(instance);
|
|
246
524
|
const reason = brokerReason(connection.lastError);
|
|
247
|
-
throw new
|
|
525
|
+
throw new SignInNeededError(reason
|
|
248
526
|
? `${name} needs you to sign in again: ${reason}. Press Connect in Brokers.`
|
|
249
527
|
: `Press Connect in Brokers to sign in to ${name}.`);
|
|
250
528
|
}
|
|
@@ -4,12 +4,22 @@
|
|
|
4
4
|
* appears here without an app release.
|
|
5
5
|
*/
|
|
6
6
|
import { apiClient } from "../../api-client";
|
|
7
|
-
import type { BrokerOrderType } from "../../types/trading";
|
|
7
|
+
import type { BrokerOrderClass, BrokerOrderType, BrokerTrailingUnit } from "../../types/trading";
|
|
8
8
|
|
|
9
9
|
interface SignedInBrokerCapabilities {
|
|
10
10
|
history: boolean;
|
|
11
11
|
executions: boolean;
|
|
12
|
-
|
|
12
|
+
/**
|
|
13
|
+
* Review: the broker keeps each order for the user to submit there. Direct: Gloom checks the
|
|
14
|
+
* order with the broker, the user confirms that check in the ticket, and Gloom places it.
|
|
15
|
+
*/
|
|
16
|
+
orders: false | {
|
|
17
|
+
mode: "review" | "direct"; types: BrokerOrderType[]; tif?: string[];
|
|
18
|
+
/** Brackets and OCO pairs the broker places and runs itself; absent from a server that sends none. */
|
|
19
|
+
orderClasses?: BrokerOrderClass[];
|
|
20
|
+
/** How a trailing stop (`TRAIL` in `types`) is set. */
|
|
21
|
+
trailing?: BrokerTrailingUnit[];
|
|
22
|
+
};
|
|
13
23
|
/** Connecting Gloom replaces this broker's link to other AI apps. */
|
|
14
24
|
singleConnection: boolean;
|
|
15
25
|
/** Shown before connecting, e.g. an account the user must create first. */
|
|
@@ -19,6 +29,8 @@ interface SignedInBrokerCapabilities {
|
|
|
19
29
|
export interface SignedInBroker {
|
|
20
30
|
id: string;
|
|
21
31
|
name: string;
|
|
32
|
+
/** Under the name where brokers are listed, for one that is not itself a broker (SnapTrade). */
|
|
33
|
+
description?: string;
|
|
22
34
|
capabilities: SignedInBrokerCapabilities;
|
|
23
35
|
}
|
|
24
36
|
|
|
@@ -31,6 +31,8 @@ export function signedInBrokerForProfile(instance: BrokerInstanceConfig, fallbac
|
|
|
31
31
|
export interface ConnectSignedInBrokerDeps<T> {
|
|
32
32
|
getConfig(): AppConfig;
|
|
33
33
|
createBrokerInstance(brokerType: string, label: string, values: Record<string, unknown>): Promise<BrokerInstanceConfig>;
|
|
34
|
+
/** Turns a profile that was turned off back on. */
|
|
35
|
+
enableBrokerInstance(instanceId: string): Promise<void>;
|
|
34
36
|
syncBrokerInstance(instanceId: string): Promise<T>;
|
|
35
37
|
/** Asks the user to connect: a form's own connect step, or the connect dialog when missing. */
|
|
36
38
|
requestSignIn?: (broker: SignedInBroker) => Promise<boolean>;
|
|
@@ -39,6 +41,9 @@ export interface ConnectSignedInBrokerDeps<T> {
|
|
|
39
41
|
/**
|
|
40
42
|
* Asks the user to connect `broker`, then syncs its profile, creating it the
|
|
41
43
|
* first time. Resolves null when the broker was not connected.
|
|
44
|
+
*
|
|
45
|
+
* Connecting a broker whose profile is turned off turns it back on first:
|
|
46
|
+
* nothing syncs a disabled profile, and connecting it again is asking for it.
|
|
42
47
|
*/
|
|
43
48
|
export async function connectSignedInBrokerProfile<T>(
|
|
44
49
|
broker: SignedInBroker,
|
|
@@ -46,8 +51,11 @@ export async function connectSignedInBrokerProfile<T>(
|
|
|
46
51
|
): Promise<{ instance: BrokerInstanceConfig; synced: T } | null> {
|
|
47
52
|
const connected = await (deps.requestSignIn ?? requestBrokerSignIn)(broker);
|
|
48
53
|
if (!connected) return null;
|
|
49
|
-
const
|
|
50
|
-
|
|
54
|
+
const existing = findSignedInBrokerProfile(deps.getConfig().brokerInstances, broker.id);
|
|
55
|
+
if (existing?.enabled === false) await deps.enableBrokerInstance(existing.id);
|
|
56
|
+
const instance = existing
|
|
57
|
+
? { ...existing, enabled: true }
|
|
58
|
+
: await deps.createBrokerInstance(SIGNED_IN_BROKER_TYPE, broker.name, { connectionMode: broker.id, broker: broker.id });
|
|
51
59
|
return { instance, synced: await deps.syncBrokerInstance(instance.id) };
|
|
52
60
|
}
|
|
53
61
|
|
|
@@ -7,6 +7,7 @@ import type { BrokerAccount } from "../types/trading";
|
|
|
7
7
|
import type { TickerRecord } from "../types/ticker";
|
|
8
8
|
import { getBrokerInstance } from "../utils/broker-instances";
|
|
9
9
|
import {
|
|
10
|
+
accountsHeldUnderOwnNumber,
|
|
10
11
|
clearBrokerInstanceTickerData,
|
|
11
12
|
clearLeftoverBrokerHoldings,
|
|
12
13
|
ensureBrokerPortfolio,
|
|
@@ -248,6 +249,13 @@ export async function syncBrokerInstance({
|
|
|
248
249
|
throwIfBrokerImportCancelled(signal);
|
|
249
250
|
}
|
|
250
251
|
|
|
252
|
+
// An account another profile holds under its own number stays with it.
|
|
253
|
+
const heldUnderOwnNumber = accountsHeldUnderOwnNumber(config, instance, brokerAccounts);
|
|
254
|
+
if (heldUnderOwnNumber.size > 0) {
|
|
255
|
+
brokerAccounts = brokerAccounts.filter((account) => !heldUnderOwnNumber.has(account.accountId));
|
|
256
|
+
positions = positions.filter((position) => !position.accountId || !heldUnderOwnNumber.has(position.accountId));
|
|
257
|
+
}
|
|
258
|
+
|
|
251
259
|
const accountMetadata = new Map(
|
|
252
260
|
brokerAccounts.map((account) => [
|
|
253
261
|
account.accountId,
|
|
@@ -301,7 +309,7 @@ export async function syncBrokerInstance({
|
|
|
301
309
|
const account = accountMetadata.get(accountId);
|
|
302
310
|
claimPortfolio(portfolioId, account?.name || accountId, account?.currency || "USD", accountId);
|
|
303
311
|
}
|
|
304
|
-
} else {
|
|
312
|
+
} else if (heldUnderOwnNumber.size === 0) {
|
|
305
313
|
const defaultAccount = brokerAccounts[0];
|
|
306
314
|
const portfolioId = findReusableBrokerPortfolioId(nextConfig, instance, defaultAccount?.accountId, portfolioBrokerId);
|
|
307
315
|
const fallbackName = defaultAccount?.name || defaultAccount?.accountId || instance.label || broker.name;
|
|
@@ -9,7 +9,8 @@ import type {
|
|
|
9
9
|
SeriesTransform,
|
|
10
10
|
TimeSeriesPoint,
|
|
11
11
|
} from "../time-series/types";
|
|
12
|
-
import {
|
|
12
|
+
import { TIME_RANGES } from "../time-series/range";
|
|
13
|
+
import { isChartResolution } from "../time-series/resolution";
|
|
13
14
|
import type {
|
|
14
15
|
CapabilityInvoker,
|
|
15
16
|
CapabilitySchema,
|
|
@@ -26,7 +27,6 @@ const CAPABILITY_ID_PATTERN = /^[A-Za-z0-9][A-Za-z0-9._-]{0,79}$/;
|
|
|
26
27
|
const SERIES_ID_PATTERN = /^[A-Za-z0-9][A-Za-z0-9._~%:/-]{0,239}$/;
|
|
27
28
|
const chartSeriesLog = debugLog.createLogger("chart-series");
|
|
28
29
|
const ranges = new Set<string>(TIME_RANGES);
|
|
29
|
-
const resolutions = new Set<string>(CHART_RESOLUTIONS);
|
|
30
30
|
const periods = new Set(["auto", "daily", "weekly", "monthly", "quarterly", "annual", "ttm"]);
|
|
31
31
|
const styles = new Set(["line", "area", "step", "columns", "points", "candles", "ohlc", "hlc"]);
|
|
32
32
|
const transforms = new Set(["raw", "percent", "index100", "yoy", "qoq", "log"]);
|
|
@@ -103,7 +103,8 @@ function viewport(value: unknown): ChartViewportSpec {
|
|
|
103
103
|
const input = object(value, "resolve viewport");
|
|
104
104
|
onlyKeys(input, "resolve viewport", ["range", "resolution", "dateWindow", "maxPoints"]);
|
|
105
105
|
const range = enumValue<ChartViewportSpec["range"]>(input.range, "viewport range", ranges);
|
|
106
|
-
|
|
106
|
+
if (!isChartResolution(input.resolution)) fail("viewport resolution", `unsupported value ${String(input.resolution)}.`);
|
|
107
|
+
const resolution = input.resolution;
|
|
107
108
|
let dateWindow: ChartViewportSpec["dateWindow"];
|
|
108
109
|
if (input.dateWindow !== undefined) {
|
|
109
110
|
const window = object(input.dateWindow, "viewport date window");
|
|
@@ -276,12 +277,15 @@ function searchableChartSeriesManifests(invoker: CapabilityInvoker) {
|
|
|
276
277
|
return chartSeriesCapabilityManifests(invoker).filter((manifest) => manifest.sourceId !== REGISTERED_SERIES_SOURCE_ID);
|
|
277
278
|
}
|
|
278
279
|
|
|
279
|
-
|
|
280
|
+
type CatalogSuggestion = ChartSeriesCatalogItem & { capabilityId: string; capabilityName: string };
|
|
281
|
+
|
|
282
|
+
/** Partial search results retain failures for the shared picker error state. */
|
|
283
|
+
export async function searchChartSeriesCatalogs(
|
|
280
284
|
invoker: CapabilityInvoker,
|
|
281
285
|
query: string,
|
|
282
286
|
limit = 8,
|
|
283
287
|
signal?: AbortSignal,
|
|
284
|
-
): Promise<
|
|
288
|
+
): Promise<{ items: CatalogSuggestion[]; errors: string[] }> {
|
|
285
289
|
const manifests = searchableChartSeriesManifests(invoker);
|
|
286
290
|
const results = await Promise.allSettled(manifests.map(async (manifest) => {
|
|
287
291
|
const items = await invoker.invokeCapability<ChartSeriesCatalogItem[]>(
|
|
@@ -297,15 +301,27 @@ export async function searchChartSeriesCapabilities(
|
|
|
297
301
|
}));
|
|
298
302
|
}));
|
|
299
303
|
if (signal?.aborted) throw signal.reason ?? new DOMException("Aborted", "AbortError");
|
|
304
|
+
const errors: string[] = [];
|
|
300
305
|
for (const [index, result] of results.entries()) {
|
|
301
306
|
if (result.status === "rejected") {
|
|
307
|
+
errors.push(`${manifests[index]!.name} search unavailable.`);
|
|
302
308
|
chartSeriesLog.warn("Chart series provider catalog failed", {
|
|
303
309
|
capabilityId: manifests[index]?.id,
|
|
304
310
|
error: result.reason instanceof Error ? result.reason.message : String(result.reason),
|
|
305
311
|
});
|
|
306
312
|
}
|
|
307
313
|
}
|
|
308
|
-
return results.flatMap((result) => result.status === "fulfilled" ? result.value : []).slice(0, limit);
|
|
314
|
+
return { items: results.flatMap((result) => result.status === "fulfilled" ? result.value : []).slice(0, limit), errors };
|
|
315
|
+
}
|
|
316
|
+
|
|
317
|
+
/** The public list-only API keeps its existing partial-results contract. */
|
|
318
|
+
export async function searchChartSeriesCapabilities(
|
|
319
|
+
invoker: CapabilityInvoker,
|
|
320
|
+
query: string,
|
|
321
|
+
limit = 8,
|
|
322
|
+
signal?: AbortSignal,
|
|
323
|
+
): Promise<CatalogSuggestion[]> {
|
|
324
|
+
return (await searchChartSeriesCatalogs(invoker, query, limit, signal)).items;
|
|
309
325
|
}
|
|
310
326
|
|
|
311
327
|
export function chartSeriesSourceKey(
|
package/src/cli/bank-section.ts
CHANGED
|
@@ -31,7 +31,7 @@ export function nimCommand(symbol: string): string {
|
|
|
31
31
|
const definition = JSON.stringify({
|
|
32
32
|
version: 1, currency: null, criteria: [{ field: "symbol", op: "in", value: [symbol] }], sort: { field: "symbol", direction: "asc" },
|
|
33
33
|
});
|
|
34
|
-
return `
|
|
34
|
+
return `gloom fn EQS --metric kpiNimPercent --definition '${definition}'`;
|
|
35
35
|
}
|
|
36
36
|
|
|
37
37
|
/** Gloom Cloud's note for a company with no US GAAP deposits tag, which reads as if it filed 10-Qs; a foreign issuer files neither. */
|