gloomberb 0.18.2 → 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/patches/electrobun@1.18.1.patch +106 -5
- 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 +99 -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 +24 -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 +26 -7
- 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/telemetry.ts +17 -0
- package/src/api-client/themes.ts +7 -1
- package/src/api-client/types.ts +90 -2
- package/src/app/global-shortcuts.ts +1 -16
- 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/runtime/update.ts +28 -8
- package/src/app/star-prompt/status-line.tsx +2 -2
- package/src/architecture/core-builtin-allowlist.json +5 -2
- package/src/architecture/pane-tabs-allowlist.json +65 -0
- 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 +1189 -296
- 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 +272 -70
- 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 +20 -14
- 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 +32 -18
- package/src/cli/issuer-membership.ts +103 -0
- package/src/cli/known-gaps.ts +118 -25
- package/src/cli/listing-arg.ts +315 -43
- package/src/cli/name-entries.ts +73 -22
- 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 +77 -20
- package/src/cli/pane-functions/catalog.ts +40 -23
- package/src/cli/pane-functions/discovery.ts +1 -1
- package/src/cli/pane-functions/dom.ts +12 -8
- 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 +48 -16
- package/src/cli/pane-functions/index.ts +82 -21
- 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 +65 -14
- 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 +190 -27
- package/src/cli/restore-plugins.ts +29 -14
- package/src/cli/result.ts +122 -25
- 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 +226 -60
- 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 +387 -21
- package/src/components/chart/composite/drawing-store.ts +26 -6
- package/src/components/chart/composite/interactions.ts +9 -3
- 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 +316 -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 +19 -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/command-items.ts +32 -6
- 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/data-table/view.tsx +23 -3
- 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 +13 -6
- package/src/components/layout/detached-pane-shell.tsx +1 -0
- package/src/components/layout/floating-pane.tsx +1 -0
- package/src/components/layout/header.tsx +234 -60
- 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/pane/header.tsx +10 -3
- package/src/components/layout/pane/index.tsx +1 -0
- package/src/components/layout/pane/pane-tabs.tsx +9 -1
- 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/components/ui/stat-grid.tsx +28 -3
- package/src/components/ui/status.tsx +3 -1
- package/src/core/app-services.ts +4 -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 +51 -12
- package/src/i18n/ja.ts +51 -12
- package/src/i18n/ko.ts +51 -12
- package/src/i18n/zh-cn.ts +51 -12
- package/src/i18n/zh-tw.ts +51 -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 +30 -18
- 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 +108 -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 +77 -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 +107 -43
- package/src/plugins/builtin/attention/pane.tsx +22 -16
- 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 +12 -9
- package/src/plugins/builtin/backtest/export.ts +1 -1
- 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 +24 -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 +115 -26
- package/src/plugins/builtin/broker-trading/ticket-parts.tsx +36 -7
- package/src/plugins/builtin/broker-trading/ticket.tsx +122 -36
- 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 +34 -18
- 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/client.ts +2 -2
- 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 +9 -11
- 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 +128 -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 +14 -8
- package/src/plugins/builtin/company-attention/app-rank.tsx +11 -10
- 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 +89 -31
- 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 +5 -4
- 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 +7 -4
- package/src/plugins/builtin/correlation/relationship/model.ts +1 -0
- package/src/plugins/builtin/correlation/settings.ts +1 -0
- 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 +7 -5
- 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/credit-documents/pane.tsx +8 -7
- 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/debt-maturities/pane.tsx +4 -3
- 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 +19 -12
- 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 +77 -5
- package/src/plugins/builtin/equity-screener/live.ts +1 -1
- package/src/plugins/builtin/equity-screener/model.ts +34 -0
- package/src/plugins/builtin/equity-screener/pane.tsx +148 -106
- 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 +16 -10
- 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/board.tsx +4 -1
- package/src/plugins/builtin/gpu/changes.tsx +10 -10
- package/src/plugins/builtin/gpu/equities.tsx +4 -1
- package/src/plugins/builtin/gpu/headless.ts +9 -4
- package/src/plugins/builtin/gpu/history.tsx +4 -2
- package/src/plugins/builtin/gpu/pane.tsx +5 -3
- 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 +15 -2
- package/src/plugins/builtin/holders/format.ts +28 -17
- package/src/plugins/builtin/holders/headless.ts +48 -8
- 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/thirteenf-match.ts +3 -1
- package/src/plugins/builtin/holders/treemap.tsx +2 -2
- package/src/plugins/builtin/insider/base-values.ts +11 -7
- package/src/plugins/builtin/insider/client.ts +3 -0
- package/src/plugins/builtin/insider/headless.ts +20 -7
- package/src/plugins/builtin/insider/index.tsx +17 -8
- package/src/plugins/builtin/insider/issuer.ts +34 -4
- package/src/plugins/builtin/insider/signals-client.ts +3 -3
- package/src/plugins/builtin/insider/signals.tsx +1 -1
- package/src/plugins/builtin/insider/table-model.ts +35 -13
- package/src/plugins/builtin/insider/table.tsx +5 -2
- 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/events.ts +145 -0
- package/src/plugins/builtin/iv-history/format.ts +3 -0
- package/src/plugins/builtin/iv-history/headless.ts +91 -7
- 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 +14 -8
- 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 +36 -21
- 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 +33 -11
- 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 +50 -15
- package/src/plugins/builtin/notes/export.ts +17 -6
- package/src/plugins/builtin/notes/files.ts +16 -5
- package/src/plugins/builtin/openfda/pane.tsx +1 -1
- package/src/plugins/builtin/options/carry.ts +2 -2
- package/src/plugins/builtin/options/enrichment-model.ts +10 -9
- package/src/plugins/builtin/options/index.tsx +1 -1
- package/src/plugins/builtin/options/model-spot.ts +70 -4
- package/src/plugins/builtin/options/view.tsx +51 -23
- package/src/plugins/builtin/options-calculator/headless.ts +46 -7
- package/src/plugins/builtin/options-calculator/pane.tsx +3 -2
- package/src/plugins/builtin/options-positioning/headless.ts +11 -3
- package/src/plugins/builtin/options-positioning/model.ts +24 -0
- package/src/plugins/builtin/options-positioning/pane.tsx +10 -12
- package/src/plugins/builtin/options-scenario/client.ts +142 -29
- 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 +49 -21
- 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 +22 -10
- 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 +145 -60
- package/src/plugins/builtin/portfolio-list/cli/bulk-symbols.ts +78 -27
- 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 +6 -3
- 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 +44 -32
- 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/client.ts +2 -1
- package/src/plugins/builtin/reverse-dcf/model.ts +10 -5
- package/src/plugins/builtin/risk-factors/index.tsx +2 -2
- package/src/plugins/builtin/scanner/lock-note.ts +1 -1
- package/src/plugins/builtin/seasonality/client.ts +2 -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 +6 -4
- 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-resource.ts +15 -2
- 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 +23 -0
- package/src/plugins/builtin/shared/series-cache.ts +2 -0
- package/src/plugins/builtin/shared/series-list-detail.tsx +3 -1
- package/src/plugins/builtin/shared/ticker-surface.ts +2 -1
- package/src/plugins/builtin/shared/volatility/options.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/social-mentions/client.ts +2 -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 +28 -7
- package/src/plugins/builtin/vol-surface/headless.ts +43 -15
- package/src/plugins/builtin/vol-surface/model.ts +34 -12
- package/src/plugins/builtin/vol-surface/pane.tsx +33 -13
- package/src/plugins/builtin/vol-surface/stored.ts +34 -3
- package/src/plugins/builtin/vol-surface/tables.ts +14 -0
- 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/desktop/controls.tsx +1 -1
- package/src/renderers/dom/desktop/query-bar.tsx +2 -0
- 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/host/tabs.tsx +16 -5
- package/src/renderers/dom/host/top-surface.ts +127 -0
- package/src/renderers/dom/styles.css +115 -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/core-capabilities.ts +9 -1
- package/src/renderers/electrobun/bun/desktop/backend-requests.ts +3 -0
- package/src/renderers/electrobun/bun/desktop/backend.ts +56 -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/desktop/update.ts +210 -30
- 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 +9 -7
- package/src/renderers/electrobun/view/remote/asset-data-client.ts +9 -2
- 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 +8 -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 +39 -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/index.ts +16 -0
- 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 +21 -4
- package/src/telemetry/update-failures-node.ts +59 -0
- package/src/telemetry/update-failures.ts +307 -0
- 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 +215 -36
- package/src/tickers/company-name.ts +43 -0
- package/src/tickers/index-roots.ts +47 -0
- package/src/tickers/instrument-label.ts +5 -1
- package/src/tickers/listing-fate.ts +30 -0
- 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 +20 -0
- package/src/types/exchange-rate.ts +6 -0
- package/src/types/financials.ts +104 -7
- package/src/types/headless.ts +83 -6
- package/src/types/instrument.ts +3 -0
- package/src/types/issuer-listings.ts +28 -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/failure.ts +163 -0
- package/src/updater/index.ts +97 -28
- 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-pair.ts +26 -0
- 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 +71 -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
|
@@ -8,13 +8,16 @@ import {
|
|
|
8
8
|
DataTableStackView,
|
|
9
9
|
EmptyState,
|
|
10
10
|
PaneStatusBody, QueryBar,
|
|
11
|
+
StatGrid,
|
|
11
12
|
usePaneFooter,
|
|
12
13
|
useQueryBarSearch,
|
|
13
14
|
useTableLoadMore,
|
|
14
15
|
type DataTableCell,
|
|
15
16
|
type DataTableKeyEvent,
|
|
16
17
|
type DataTableRootKeyContext,
|
|
17
|
-
type PaneFooterSegment
|
|
18
|
+
type PaneFooterSegment,
|
|
19
|
+
type QueryBarView,
|
|
20
|
+
type StatItem,
|
|
18
21
|
} from "../../../components";
|
|
19
22
|
import { handleRefreshKey } from "../../../components/data-table/table-pane";
|
|
20
23
|
import { AudioPlayer, useCanPlayAudio } from "../../../components/ui";
|
|
@@ -35,7 +38,9 @@ import { usePluginPaneState } from "../../runtime";
|
|
|
35
38
|
import { ProWall, SignInWall } from "../cloud/auth-actions";
|
|
36
39
|
import { usePlanAccess } from "../../../api-client/plan-access";
|
|
37
40
|
import { listingAbroad } from "../../../api-client/paths";
|
|
41
|
+
import { useAgeClock } from "../../../react/auto-refresh";
|
|
38
42
|
import { useBoundTicker as useSymbolBinding } from "../shared/ticker-request";
|
|
43
|
+
import { CALLS_VIEWS, UpcomingCallsView, type CallsView } from "./calendar";
|
|
39
44
|
import {
|
|
40
45
|
cachedEarningsCalls,
|
|
41
46
|
callStatusLabel,
|
|
@@ -48,6 +53,7 @@ import { callTitle, formatCallDate, formatDuration, formatPeriod, formatSentimen
|
|
|
48
53
|
import { findCallForQuarter, findInLines, MIN_FIND_LENGTH, turnParagraphs } from "./model";
|
|
49
54
|
import { READER_TABS, TranscriptView, type ReaderTab, type TranscriptPlayback } from "./transcript-view";
|
|
50
55
|
import { PLAYBACK_RATES, SEEK_STEP_SECONDS, useCallPlayback } from "./use-call-playback";
|
|
56
|
+
import { callAway, callCountdown, callStartText, isUpcomingCall, nextCall } from "./upcoming";
|
|
51
57
|
|
|
52
58
|
export const EARNINGS_CALLS_PANE_ID = "earnings-calls";
|
|
53
59
|
|
|
@@ -86,7 +92,7 @@ function buildColumns(width: number, showTicker: boolean): CallColumn[] {
|
|
|
86
92
|
return columns;
|
|
87
93
|
}
|
|
88
94
|
|
|
89
|
-
function renderCell(call: CloudEarningsCallPayload, column: CallColumn): DataTableCell {
|
|
95
|
+
function renderCell(call: CloudEarningsCallPayload, column: CallColumn, now: number): DataTableCell {
|
|
90
96
|
switch (column.id) {
|
|
91
97
|
case "ticker":
|
|
92
98
|
return { text: call.ticker };
|
|
@@ -99,7 +105,9 @@ function renderCell(call: CloudEarningsCallPayload, column: CallColumn): DataTab
|
|
|
99
105
|
case "length":
|
|
100
106
|
return { text: formatDuration(call.durationSeconds), color: colors.textDim };
|
|
101
107
|
case "sentiment": {
|
|
102
|
-
|
|
108
|
+
// A call still to come says how far away it is, not that it is queued.
|
|
109
|
+
if (isUpcomingCall(call, now)) return { text: callCountdown(call, now), color: colors.text };
|
|
110
|
+
if (!call.hasTranscript) return { text: callStatusLabel(call, now), color: colors.textDim };
|
|
103
111
|
const tone =
|
|
104
112
|
call.sentiment === null
|
|
105
113
|
? colors.textDim
|
|
@@ -180,13 +188,86 @@ interface EarningsCallsViewProps {
|
|
|
180
188
|
height: number;
|
|
181
189
|
}
|
|
182
190
|
|
|
191
|
+
/** The next call's own line: when it starts here and in New York, and how far away it is. */
|
|
192
|
+
function nextCallFigure(call: CloudEarningsCallPayload, now: number): StatItem {
|
|
193
|
+
const { start, newYork } = callStartText(call, now);
|
|
194
|
+
// A countdown that is a day's name repeats the start's; it says something within a day.
|
|
195
|
+
const away = callAway(call, now);
|
|
196
|
+
const detail = [newYork, away].filter(Boolean).join(" · ");
|
|
197
|
+
return {
|
|
198
|
+
id: "next-call",
|
|
199
|
+
label: "Next call",
|
|
200
|
+
value: start,
|
|
201
|
+
...(detail ? { detail, detailVariants: [away ?? newYork ?? ""] } : {}),
|
|
202
|
+
tone: "accent",
|
|
203
|
+
};
|
|
204
|
+
}
|
|
205
|
+
|
|
206
|
+
/**
|
|
207
|
+
* CALLS: with a ticker, that company's calls, its next one on its own line;
|
|
208
|
+
* alone, the calendar of every company's calls this week, or the shelf of
|
|
209
|
+
* transcripts.
|
|
210
|
+
*/
|
|
183
211
|
export function EarningsCallsPane({ focused, width, height }: EarningsCallsViewProps) {
|
|
184
212
|
const { symbol, exchange, ticker: boundTicker } = useSymbolBinding();
|
|
213
|
+
// `shot CALLS --view transcripts` (a pane setting) opens on the shelf; a choice made in the pane wins.
|
|
214
|
+
const [requestedView] = usePaneSettingValue<string>("view", "");
|
|
215
|
+
const [chosenView, setView] = usePluginPaneState<CallsView | null>("view", null);
|
|
216
|
+
const view: CallsView = chosenView ?? (CALLS_VIEWS.some((option) => option.value === requestedView) ? requestedView as CallsView : "upcoming");
|
|
217
|
+
const viewChoice = useMemo<QueryBarView<CallsView>>(() => ({ value: view, options: CALLS_VIEWS, onChange: setView }), [setView, view]);
|
|
218
|
+
|
|
219
|
+
if (symbol) {
|
|
220
|
+
return (
|
|
221
|
+
<CallsListView
|
|
222
|
+
focused={focused} width={width} height={height}
|
|
223
|
+
symbol={symbol} exchange={exchange} listingName={boundTicker?.metadata.name}
|
|
224
|
+
/>
|
|
225
|
+
);
|
|
226
|
+
}
|
|
227
|
+
if (view === "transcripts") {
|
|
228
|
+
return <CallsListView focused={focused} width={width} height={height} symbol={null} view={viewChoice} />;
|
|
229
|
+
}
|
|
230
|
+
return (
|
|
231
|
+
<UpcomingCallsView
|
|
232
|
+
focused={focused} width={width} height={height} view={viewChoice}
|
|
233
|
+
renderCompany={({ ticker, focused: companyFocused, height: companyHeight, onHoldsKeys }) => (
|
|
234
|
+
<CallsListView
|
|
235
|
+
key={ticker}
|
|
236
|
+
focused={companyFocused} width={width} height={companyHeight}
|
|
237
|
+
symbol={ticker} stateKey="company:" footerId={`${EARNINGS_CALLS_PANE_ID}:company`}
|
|
238
|
+
openFromSettings={false} onHoldsKeys={onHoldsKeys}
|
|
239
|
+
/>
|
|
240
|
+
)}
|
|
241
|
+
/>
|
|
242
|
+
);
|
|
243
|
+
}
|
|
244
|
+
|
|
245
|
+
interface CallsListProps extends EarningsCallsViewProps {
|
|
246
|
+
/** The company whose calls these are; null for the shelf of every company's transcripts. */
|
|
247
|
+
symbol: string | null;
|
|
248
|
+
exchange?: string;
|
|
249
|
+
/** The listing's company name, so a listing abroad reads its own calls. */
|
|
250
|
+
listingName?: string;
|
|
251
|
+
/** Prefix of the pane state this view keeps, so a company opened from the calendar keeps its own. */
|
|
252
|
+
stateKey?: string;
|
|
253
|
+
footerId?: string;
|
|
254
|
+
/** The calendar or the shelf, chosen in the query bar of CALLS alone. */
|
|
255
|
+
view?: QueryBarView<CallsView>;
|
|
256
|
+
/** Whether the pane's `quarter` and `reader` settings open a call here (a layout or a shot). */
|
|
257
|
+
openFromSettings?: boolean;
|
|
258
|
+
/** Told when this view holds the keys a stack around it would take: a call open, or its search focused. */
|
|
259
|
+
onHoldsKeys?: (holds: boolean) => void;
|
|
260
|
+
}
|
|
261
|
+
|
|
262
|
+
function CallsListView({
|
|
263
|
+
focused, width, height, symbol, exchange, listingName: boundName, stateKey = "", footerId = EARNINGS_CALLS_PANE_ID,
|
|
264
|
+
view, openFromSettings = true, onHoldsKeys,
|
|
265
|
+
}: CallsListProps) {
|
|
185
266
|
const access = usePlanAccess();
|
|
186
267
|
// Read once per mount: a binding change reads the cache again in its own effect.
|
|
187
268
|
const [initialShelf] = useState(() => {
|
|
188
269
|
const initialTicker = symbol ? symbol.toUpperCase() : null;
|
|
189
|
-
const initialAbroad = initialTicker ? listingAbroad(initialTicker, exchange,
|
|
270
|
+
const initialAbroad = initialTicker ? listingAbroad(initialTicker, exchange, boundName) : null;
|
|
190
271
|
return cachedEarningsCalls(initialTicker, {
|
|
191
272
|
limit: CALL_PAGE_SIZE, exchange: initialAbroad?.exchange, name: initialAbroad?.name,
|
|
192
273
|
});
|
|
@@ -206,8 +287,8 @@ export function EarningsCallsPane({ focused, width, height }: EarningsCallsViewP
|
|
|
206
287
|
const [nextOffset, setNextOffset] = useState(initialShelf?.calls.length ?? 0);
|
|
207
288
|
const tableScrollRef = useRef<ScrollBoxRenderable | null>(null);
|
|
208
289
|
|
|
209
|
-
const [selectedId, setSelectedId] = usePluginPaneState<string | null>(
|
|
210
|
-
const [detailOpen, setDetailOpen] = usePluginPaneState<boolean>(
|
|
290
|
+
const [selectedId, setSelectedId] = usePluginPaneState<string | null>(`${stateKey}selectedId`, null);
|
|
291
|
+
const [detailOpen, setDetailOpen] = usePluginPaneState<boolean>(`${stateKey}detailOpen`, false);
|
|
211
292
|
const [transcript, setTranscript] = useState<CloudEarningsTranscriptPayload | null>(null);
|
|
212
293
|
useEffect(() => {
|
|
213
294
|
if (focused && transcript && detailOpen) recordResearchActivity("pro_feature_used", "transcripts");
|
|
@@ -217,13 +298,15 @@ export function EarningsCallsPane({ focused, width, height }: EarningsCallsViewP
|
|
|
217
298
|
message: string;
|
|
218
299
|
status?: number;
|
|
219
300
|
} | null>(null);
|
|
220
|
-
const [readerTab, setReaderTab] = usePluginPaneState<ReaderTab>(
|
|
221
|
-
// A layout or `
|
|
301
|
+
const [readerTab, setReaderTab] = usePluginPaneState<ReaderTab>(`${stateKey}readerTab`, "summary");
|
|
302
|
+
// A layout or `gloom shot CALLS NVDA --quarter latest --reader summary`
|
|
222
303
|
// can land straight on a transcript instead of the shelf. `quarter` takes
|
|
223
304
|
// the same tokens as the headless option; only transcribed calls qualify,
|
|
224
305
|
// since opening a call without one asks the server to produce it.
|
|
225
|
-
const [
|
|
226
|
-
const [
|
|
306
|
+
const [quarterSetting] = usePaneSettingValue<string>("quarter", "");
|
|
307
|
+
const [readerSetting] = usePaneSettingValue<string>("reader", "");
|
|
308
|
+
const openQuarter = openFromSettings ? quarterSetting : "";
|
|
309
|
+
const openReader = openFromSettings ? readerSetting : "";
|
|
227
310
|
const openedQuarter = useRef<string | null>(null);
|
|
228
311
|
const [sort, setSort] = useState<CallSort>(DEFAULT_SORT);
|
|
229
312
|
const [searchQuery, setSearchQuery] = useState("");
|
|
@@ -240,7 +323,7 @@ export function EarningsCallsPane({ focused, width, height }: EarningsCallsViewP
|
|
|
240
323
|
|
|
241
324
|
const ticker = symbol ? symbol.toUpperCase() : null;
|
|
242
325
|
// A listing abroad asks for its own calls by venue and company, never a US namesake's.
|
|
243
|
-
const abroad = ticker ? listingAbroad(ticker, exchange,
|
|
326
|
+
const abroad = ticker ? listingAbroad(ticker, exchange, boundName) : null;
|
|
244
327
|
const listingVenue = abroad?.exchange;
|
|
245
328
|
const listingName = abroad?.name;
|
|
246
329
|
|
|
@@ -429,10 +512,16 @@ export function EarningsCallsPane({ focused, width, height }: EarningsCallsViewP
|
|
|
429
512
|
];
|
|
430
513
|
}, [calls, lookup, listFetchedAt]);
|
|
431
514
|
|
|
515
|
+
// Countdowns move on a coarse clock that rests while the pane is hidden.
|
|
516
|
+
const now = useAgeClock(listFetchedAt || null);
|
|
517
|
+
// A company's next call is its own line above its calls, not one of the rows.
|
|
518
|
+
const next = useMemo(() => (ticker ? nextCall(allCalls, now) : null), [allCalls, now, ticker]);
|
|
519
|
+
const listedCalls = useMemo(() => (next ? allCalls.filter((call) => call.id !== next.id) : allCalls), [allCalls, next]);
|
|
520
|
+
|
|
432
521
|
const rows = useMemo(() => {
|
|
433
522
|
const query = searchQuery.trim().toLowerCase();
|
|
434
523
|
const matched = query
|
|
435
|
-
?
|
|
524
|
+
? listedCalls.filter((call) =>
|
|
436
525
|
[
|
|
437
526
|
call.ticker,
|
|
438
527
|
call.companyName ?? "",
|
|
@@ -443,7 +532,7 @@ export function EarningsCallsPane({ focused, width, height }: EarningsCallsViewP
|
|
|
443
532
|
.toLowerCase()
|
|
444
533
|
.includes(query),
|
|
445
534
|
)
|
|
446
|
-
:
|
|
535
|
+
: listedCalls;
|
|
447
536
|
const sorted = [...matched].sort((a, b) => {
|
|
448
537
|
const left = sortValue(a, sort.columnId);
|
|
449
538
|
const right = sortValue(b, sort.columnId);
|
|
@@ -452,7 +541,7 @@ export function EarningsCallsPane({ focused, width, height }: EarningsCallsViewP
|
|
|
452
541
|
return sort.direction === "asc" ? order : -order;
|
|
453
542
|
});
|
|
454
543
|
return sorted;
|
|
455
|
-
}, [
|
|
544
|
+
}, [listedCalls, sort, searchQuery]);
|
|
456
545
|
|
|
457
546
|
useEffect(() => {
|
|
458
547
|
const quarter = openQuarter.trim();
|
|
@@ -474,6 +563,9 @@ export function EarningsCallsPane({ focused, width, height }: EarningsCallsViewP
|
|
|
474
563
|
);
|
|
475
564
|
const selectedCallId = selected?.id ?? null;
|
|
476
565
|
const selectedHasTranscript = selected?.hasTranscript ?? false;
|
|
566
|
+
// A call still to come has nothing to read, and asking for its transcript
|
|
567
|
+
// would ask the server to produce one before the call has happened.
|
|
568
|
+
const selectedUpcoming = !!selected && isUpcomingCall(selected, now);
|
|
477
569
|
// The reader shows only a call the pane can find. A restored call that is not
|
|
478
570
|
// on the reloaded shelf (a lookup result, or one that aged off) closes once
|
|
479
571
|
// the shelf has loaded, rather than leave the keys pointing at a reader that
|
|
@@ -544,7 +636,7 @@ export function EarningsCallsPane({ focused, width, height }: EarningsCallsViewP
|
|
|
544
636
|
// a call that has none asks the server to produce it, then checks back
|
|
545
637
|
// until it arrives.
|
|
546
638
|
useEffect(() => {
|
|
547
|
-
if (!detailOpen || !selectedCallId || !access.emailVerified || !access.hasProAccess) return;
|
|
639
|
+
if (!detailOpen || !selectedCallId || selectedUpcoming || !access.emailVerified || !access.hasProAccess) return;
|
|
548
640
|
// A binding change clears selection in an effect; do not start a request
|
|
549
641
|
// for that previous selection during the same render's effect pass.
|
|
550
642
|
if (ticker && selected?.ticker.toUpperCase() !== ticker) return;
|
|
@@ -592,7 +684,7 @@ export function EarningsCallsPane({ focused, width, height }: EarningsCallsViewP
|
|
|
592
684
|
};
|
|
593
685
|
// The call's identity is what matters; list refreshes must not restart this.
|
|
594
686
|
// eslint-disable-next-line react-hooks/exhaustive-deps
|
|
595
|
-
}, [detailOpen, selectedCallId, ticker, access.emailVerified, access.hasProAccess]);
|
|
687
|
+
}, [detailOpen, selectedCallId, selectedUpcoming, ticker, access.emailVerified, access.hasProAccess]);
|
|
596
688
|
|
|
597
689
|
const scrollTranscriptBy = useCallback((delta: number) => {
|
|
598
690
|
if (transcriptScrollRef.current) scrollByLines(transcriptScrollRef.current, delta);
|
|
@@ -629,6 +721,7 @@ export function EarningsCallsPane({ focused, width, height }: EarningsCallsViewP
|
|
|
629
721
|
const transcriptProRequired = transcriptError?.status === 402;
|
|
630
722
|
|
|
631
723
|
const columns = useMemo(() => buildColumns(width, !ticker), [width, ticker]);
|
|
724
|
+
const renderRow = useCallback((call: CloudEarningsCallPayload, column: CallColumn) => renderCell(call, column, now), [now]);
|
|
632
725
|
|
|
633
726
|
const handleRootKey = useCallback(
|
|
634
727
|
(event: DataTableKeyEvent, context: DataTableRootKeyContext) => {
|
|
@@ -664,6 +757,13 @@ export function EarningsCallsPane({ focused, width, height }: EarningsCallsViewP
|
|
|
664
757
|
// Only a loaded transcript has a find field; a wall, an upsell or a first
|
|
665
758
|
// load has no list or reader for the search keys to reach.
|
|
666
759
|
const readerSearchable = readerOpen && !!selectedTranscript && !transcriptProRequired;
|
|
760
|
+
// A calendar around this view gives it Back, Esc and Backspace while a call
|
|
761
|
+
// is open here or the search has the keys.
|
|
762
|
+
const holdsKeys = readerOpen || searchFocused;
|
|
763
|
+
useEffect(() => {
|
|
764
|
+
onHoldsKeys?.(holdsKeys);
|
|
765
|
+
}, [holdsKeys, onHoldsKeys]);
|
|
766
|
+
useEffect(() => () => onHoldsKeys?.(false), [onHoldsKeys]);
|
|
667
767
|
// Mirrors the bodies below: the list renders unless a wall, an upsell, or an
|
|
668
768
|
// empty shelf's loading, failed or research-tab state takes its place.
|
|
669
769
|
const listShown = !signInRequired && !verificationRequired && !proRequired
|
|
@@ -717,7 +817,7 @@ export function EarningsCallsPane({ focused, width, height }: EarningsCallsViewP
|
|
|
717
817
|
);
|
|
718
818
|
|
|
719
819
|
usePaneFooter(
|
|
720
|
-
|
|
820
|
+
footerId,
|
|
721
821
|
() => {
|
|
722
822
|
const info: PaneFooterSegment[] = [];
|
|
723
823
|
if (listStatus === "loading") {
|
|
@@ -847,7 +947,7 @@ export function EarningsCallsPane({ focused, width, height }: EarningsCallsViewP
|
|
|
847
947
|
placement="calls-wall"
|
|
848
948
|
width={width} height={height} symbol={symbol} exchange={exchange}
|
|
849
949
|
title="Earnings call transcripts are part of Gloom Cloud Pro."
|
|
850
|
-
message="
|
|
950
|
+
message="Full transcripts of each earnings call with speaker attribution, analyst Q&A, and extracted guidance, risks and tone."
|
|
851
951
|
/>
|
|
852
952
|
);
|
|
853
953
|
}
|
|
@@ -884,6 +984,8 @@ export function EarningsCallsPane({ focused, width, height }: EarningsCallsViewP
|
|
|
884
984
|
title="Earnings call transcripts are part of Gloom Cloud Pro."
|
|
885
985
|
message="Full transcripts with speaker attribution, analyst Q&A, guidance and risk extraction, transcribed from the call itself."
|
|
886
986
|
/>
|
|
987
|
+
) : selected && selectedUpcoming ? (
|
|
988
|
+
<UpcomingCallState call={selected} now={now} />
|
|
887
989
|
) : selected && !selectedTranscript && (producing || (!selected.hasTranscript && !transcriptError)) ? (
|
|
888
990
|
<PaneStatusBody loading loadingLabel="Producing the transcript. This usually takes two to three minutes." />
|
|
889
991
|
) : (
|
|
@@ -945,17 +1047,21 @@ export function EarningsCallsPane({ focused, width, height }: EarningsCallsViewP
|
|
|
945
1047
|
detailContent={detailContent}
|
|
946
1048
|
detailTitle={selected ? callTitle(selected) : undefined}
|
|
947
1049
|
rootBefore={
|
|
948
|
-
<
|
|
949
|
-
|
|
950
|
-
|
|
951
|
-
|
|
952
|
-
|
|
953
|
-
|
|
954
|
-
|
|
955
|
-
|
|
956
|
-
|
|
957
|
-
|
|
958
|
-
|
|
1050
|
+
<Box flexDirection="column" flexShrink={0}>
|
|
1051
|
+
<QueryBar
|
|
1052
|
+
width={width}
|
|
1053
|
+
search={{
|
|
1054
|
+
value: searchQuery,
|
|
1055
|
+
onChange: setSearchQuery,
|
|
1056
|
+
placeholder: "ticker, company, or period",
|
|
1057
|
+
focused: focused && !readerOpen,
|
|
1058
|
+
...searchProps,
|
|
1059
|
+
debounceMs: 80,
|
|
1060
|
+
}}
|
|
1061
|
+
view={view}
|
|
1062
|
+
/>
|
|
1063
|
+
{next ? <StatGrid items={[nextCallFigure(next, now)]} width={width} /> : null}
|
|
1064
|
+
</Box>
|
|
959
1065
|
}
|
|
960
1066
|
onRootKeyDown={handleRootKey}
|
|
961
1067
|
onDetailKeyDown={handleDetailKey}
|
|
@@ -986,7 +1092,7 @@ export function EarningsCallsPane({ focused, width, height }: EarningsCallsViewP
|
|
|
986
1092
|
setSort((current) => nextHeaderSort(current, columnId, { firstDirection: "desc" }))
|
|
987
1093
|
}
|
|
988
1094
|
getItemKey={(call) => call.id}
|
|
989
|
-
renderCell={
|
|
1095
|
+
renderCell={renderRow}
|
|
990
1096
|
emptyStateTitle={
|
|
991
1097
|
lookupTicker && lookupState
|
|
992
1098
|
? lookupState === "unknown"
|
|
@@ -998,9 +1104,21 @@ export function EarningsCallsPane({ focused, width, height }: EarningsCallsViewP
|
|
|
998
1104
|
: `Looking up ${lookupTicker}...`
|
|
999
1105
|
: searchQuery.trim()
|
|
1000
1106
|
? "No matching calls."
|
|
1001
|
-
: "No calls yet."
|
|
1107
|
+
: next ? "No calls before this one yet." : "No calls yet."
|
|
1002
1108
|
}
|
|
1003
1109
|
emptyStateHint={searchQuery.trim() ? "Clear the search to see all calls." : undefined}
|
|
1004
1110
|
/>
|
|
1005
1111
|
);
|
|
1006
1112
|
}
|
|
1113
|
+
|
|
1114
|
+
/** An open call still to come: when it starts, here and in New York, and how far away. */
|
|
1115
|
+
function UpcomingCallState({ call, now }: { call: CloudEarningsCallPayload; now: number }) {
|
|
1116
|
+
const { start, newYork } = callStartText(call, now);
|
|
1117
|
+
const away = callAway(call, now);
|
|
1118
|
+
return (
|
|
1119
|
+
<EmptyState
|
|
1120
|
+
title={`Starts ${start}${newYork ? ` (${newYork})` : ""}${away ? `, ${away}` : ""}.`}
|
|
1121
|
+
message="The transcript follows once the call is over."
|
|
1122
|
+
/>
|
|
1123
|
+
);
|
|
1124
|
+
}
|
|
@@ -0,0 +1,195 @@
|
|
|
1
|
+
import type { CloudEarningsCallPayload } from "../../../api-client";
|
|
2
|
+
import type { TableSection } from "../../../components";
|
|
3
|
+
import { formatCountdown } from "../../../utils/datetime-format";
|
|
4
|
+
import { addDays, marketDays, newYorkToday, type MarketDay } from "../earnings/board-model";
|
|
5
|
+
import { shortDate, weekday } from "../earnings/format";
|
|
6
|
+
|
|
7
|
+
const DAY_MS = 86_400_000;
|
|
8
|
+
|
|
9
|
+
/**
|
|
10
|
+
* Whether a call's `callAt` is its start. A call known by its day alone is
|
|
11
|
+
* stored at 00:00 UTC of that New York day; a server that does not say which
|
|
12
|
+
* is read the same way.
|
|
13
|
+
*/
|
|
14
|
+
export function callTimeKnown(call: Pick<CloudEarningsCallPayload, "callAt" | "callTimeKnown">): boolean {
|
|
15
|
+
const at = call.callAt ? Date.parse(call.callAt) : Number.NaN;
|
|
16
|
+
if (!Number.isFinite(at)) return false;
|
|
17
|
+
if (typeof call.callTimeKnown === "boolean") return call.callTimeKnown;
|
|
18
|
+
return at % DAY_MS !== 0;
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
/** The New York day a call is on (YYYY-MM-DD): its start's, or the day it is known by. */
|
|
22
|
+
export function callDay(call: Pick<CloudEarningsCallPayload, "callAt" | "callTimeKnown">): string | null {
|
|
23
|
+
const at = call.callAt ? Date.parse(call.callAt) : Number.NaN;
|
|
24
|
+
if (!Number.isFinite(at)) return null;
|
|
25
|
+
return callTimeKnown(call) ? newYorkToday(new Date(at)) : new Date(at).toISOString().slice(0, 10);
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
/**
|
|
29
|
+
* A call still to come: no transcript yet, and its start ahead, or, known by
|
|
30
|
+
* its day alone, that day today or later in New York. A transcribed call has
|
|
31
|
+
* happened, whatever its date says.
|
|
32
|
+
*/
|
|
33
|
+
export function isUpcomingCall(call: CloudEarningsCallPayload, now = Date.now()): boolean {
|
|
34
|
+
if (call.hasTranscript) return false;
|
|
35
|
+
if (callTimeKnown(call)) return Date.parse(call.callAt!) > now;
|
|
36
|
+
const day = callDay(call);
|
|
37
|
+
return day !== null && day >= newYorkToday(new Date(now));
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
/** Earliest first: by New York day, then the calls with a start, in order, then those known by the day. */
|
|
41
|
+
export function compareCallStarts(left: CloudEarningsCallPayload, right: CloudEarningsCallPayload): number {
|
|
42
|
+
const leftDay = callDay(left) ?? "9999-12-31";
|
|
43
|
+
const rightDay = callDay(right) ?? "9999-12-31";
|
|
44
|
+
if (leftDay !== rightDay) return leftDay < rightDay ? -1 : 1;
|
|
45
|
+
const leftKnown = callTimeKnown(left);
|
|
46
|
+
const rightKnown = callTimeKnown(right);
|
|
47
|
+
if (leftKnown !== rightKnown) return leftKnown ? -1 : 1;
|
|
48
|
+
return (Date.parse(left.callAt ?? "") || 0) - (Date.parse(right.callAt ?? "") || 0) || left.ticker.localeCompare(right.ticker);
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
/** A company's next call: the soonest of its calls still to come. */
|
|
52
|
+
export function nextCall(calls: readonly CloudEarningsCallPayload[], now = Date.now()): CloudEarningsCallPayload | null {
|
|
53
|
+
return calls.filter((call) => isUpcomingCall(call, now)).sort(compareCallStarts)[0] ?? null;
|
|
54
|
+
}
|
|
55
|
+
|
|
56
|
+
const localDay = (at: number) => {
|
|
57
|
+
const date = new Date(at);
|
|
58
|
+
return Date.UTC(date.getFullYear(), date.getMonth(), date.getDate());
|
|
59
|
+
};
|
|
60
|
+
|
|
61
|
+
/**
|
|
62
|
+
* How far away a call is. With its start: "in 25m" and "in 3h" within a day
|
|
63
|
+
* (the countdown econ events use), then its weekday on this machine's clock
|
|
64
|
+
* within the week ("Thu"), then its date ("Oct 30"); "started" once it has.
|
|
65
|
+
* Known by its day alone: "today", "tomorrow", then the same.
|
|
66
|
+
*/
|
|
67
|
+
export function callCountdown(call: CloudEarningsCallPayload, now = Date.now()): string {
|
|
68
|
+
const day = callDay(call);
|
|
69
|
+
if (!day) return "";
|
|
70
|
+
if (!callTimeKnown(call)) {
|
|
71
|
+
const today = newYorkToday(new Date(now));
|
|
72
|
+
if (day < today) return shortDate(day);
|
|
73
|
+
if (day === today) return "today";
|
|
74
|
+
if (day === addDays(today, 1)) return "tomorrow";
|
|
75
|
+
return day <= addDays(today, 6) ? weekday(day) : shortDate(day);
|
|
76
|
+
}
|
|
77
|
+
const at = Date.parse(call.callAt!);
|
|
78
|
+
const ahead = at - now;
|
|
79
|
+
if (ahead <= 0) return "started";
|
|
80
|
+
if (ahead < DAY_MS) return formatCountdown(ahead);
|
|
81
|
+
const days = Math.round((localDay(at) - localDay(now)) / DAY_MS);
|
|
82
|
+
const date = new Date(at);
|
|
83
|
+
const local = `${date.getFullYear()}-${String(date.getMonth() + 1).padStart(2, "0")}-${String(date.getDate()).padStart(2, "0")}`;
|
|
84
|
+
return days <= 6 ? weekday(local) : shortDate(local);
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
/**
|
|
88
|
+
* The countdown when it says more than the call's day does: "in 3h", "today",
|
|
89
|
+
* "tomorrow". Null when it would only name the day ("Thu", "Oct 30").
|
|
90
|
+
*/
|
|
91
|
+
export function callAway(call: CloudEarningsCallPayload, now = Date.now()): string | null {
|
|
92
|
+
const countdown = callCountdown(call, now);
|
|
93
|
+
return /^(in |today$|tomorrow$)/.test(countdown) ? countdown : null;
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
const clockFormatters = new Map<string, Intl.DateTimeFormat>();
|
|
97
|
+
|
|
98
|
+
function clockFormatter(timeZone: string | undefined, withDay: boolean): Intl.DateTimeFormat {
|
|
99
|
+
const key = `${timeZone ?? ""}:${withDay}`;
|
|
100
|
+
let formatter = clockFormatters.get(key);
|
|
101
|
+
if (!formatter) {
|
|
102
|
+
formatter = new Intl.DateTimeFormat("en-US", {
|
|
103
|
+
timeZone,
|
|
104
|
+
hour: "2-digit",
|
|
105
|
+
minute: "2-digit",
|
|
106
|
+
hourCycle: "h23",
|
|
107
|
+
...(withDay ? { weekday: "short", month: "short", day: "numeric" } : {}),
|
|
108
|
+
});
|
|
109
|
+
clockFormatters.set(key, formatter);
|
|
110
|
+
}
|
|
111
|
+
return formatter;
|
|
112
|
+
}
|
|
113
|
+
|
|
114
|
+
function clock(at: number, timeZone: string | undefined, withDay: boolean): string {
|
|
115
|
+
const parts = Object.fromEntries(clockFormatter(timeZone, withDay).formatToParts(new Date(at)).map((part) => [part.type, part.value]));
|
|
116
|
+
const time = `${parts.hour}:${parts.minute}`;
|
|
117
|
+
return withDay ? `${parts.weekday} ${parts.month} ${parts.day} ${time}` : time;
|
|
118
|
+
}
|
|
119
|
+
|
|
120
|
+
const NEW_YORK = "America/New_York";
|
|
121
|
+
|
|
122
|
+
/** Its start on this machine's clock ("22:30"), or null for a call known by its day alone. */
|
|
123
|
+
export function callLocalClock(call: CloudEarningsCallPayload): string | null {
|
|
124
|
+
return callTimeKnown(call) ? clock(Date.parse(call.callAt!), undefined, false) : null;
|
|
125
|
+
}
|
|
126
|
+
|
|
127
|
+
/** Its start on New York's clock ("16:30"), or null for a call known by its day alone. */
|
|
128
|
+
export function callNewYorkClock(call: CloudEarningsCallPayload): string | null {
|
|
129
|
+
return callTimeKnown(call) ? clock(Date.parse(call.callAt!), NEW_YORK, false) : null;
|
|
130
|
+
}
|
|
131
|
+
|
|
132
|
+
/** Whether this machine's clock reads New York's at every one of these starts, so one time says both. */
|
|
133
|
+
export function clockIsNewYork(calls: readonly CloudEarningsCallPayload[], now = Date.now()): boolean {
|
|
134
|
+
const starts = [now, ...calls.filter(callTimeKnown).map((call) => Date.parse(call.callAt!))];
|
|
135
|
+
return starts.every((at) => clock(at, undefined, true) === clock(at, NEW_YORK, true));
|
|
136
|
+
}
|
|
137
|
+
|
|
138
|
+
/**
|
|
139
|
+
* When the next call starts, as its own line names it: the day and time here,
|
|
140
|
+
* then New York's ("Thu Oct 22 22:30", "16:30 ET"), New York's alone when the
|
|
141
|
+
* two agree ("Thu Oct 22 16:30 ET"), or the day alone ("Thu Oct 22").
|
|
142
|
+
*/
|
|
143
|
+
export function callStartText(call: CloudEarningsCallPayload, now = Date.now()): { start: string; newYork: string | null } {
|
|
144
|
+
const day = callDay(call);
|
|
145
|
+
if (!day) return { start: "", newYork: null };
|
|
146
|
+
if (!callTimeKnown(call)) return { start: `${weekday(day)} ${shortDate(day)}`, newYork: null };
|
|
147
|
+
const at = Date.parse(call.callAt!);
|
|
148
|
+
if (clockIsNewYork([call], now)) return { start: `${clock(at, NEW_YORK, true)} ET`, newYork: null };
|
|
149
|
+
return { start: clock(at, undefined, true), newYork: `${clock(at, NEW_YORK, false)} ET` };
|
|
150
|
+
}
|
|
151
|
+
|
|
152
|
+
/** The calendar's days: today when the market trades, the next session, then the rest of that week (ERN's board). */
|
|
153
|
+
export function calendarDays(now = Date.now()): MarketDay[] {
|
|
154
|
+
return marketDays(newYorkToday(new Date(now)));
|
|
155
|
+
}
|
|
156
|
+
|
|
157
|
+
export type CalendarSort = { column: "time" | "ticker" | "company"; direction: "asc" | "desc" };
|
|
158
|
+
|
|
159
|
+
export const DEFAULT_CALENDAR_SORT: CalendarSort = { column: "time", direction: "asc" };
|
|
160
|
+
|
|
161
|
+
function compareRows(left: CloudEarningsCallPayload, right: CloudEarningsCallPayload, sort: CalendarSort): number {
|
|
162
|
+
const order = sort.column === "ticker"
|
|
163
|
+
? left.ticker.localeCompare(right.ticker)
|
|
164
|
+
: sort.column === "company"
|
|
165
|
+
? (left.companyName ?? left.ticker).localeCompare(right.companyName ?? right.ticker, undefined, { sensitivity: "base" })
|
|
166
|
+
: compareCallStarts(left, right);
|
|
167
|
+
return (sort.direction === "asc" ? order : -order) || compareCallStarts(left, right);
|
|
168
|
+
}
|
|
169
|
+
|
|
170
|
+
/**
|
|
171
|
+
* The calendar's sections: one per day with calls on it, its calls in start
|
|
172
|
+
* order (or the sort's), one per company and start.
|
|
173
|
+
*/
|
|
174
|
+
export function calendarSections(
|
|
175
|
+
calls: readonly CloudEarningsCallPayload[],
|
|
176
|
+
days: readonly MarketDay[],
|
|
177
|
+
sort: CalendarSort = DEFAULT_CALENDAR_SORT,
|
|
178
|
+
): Array<TableSection<CloudEarningsCallPayload>> {
|
|
179
|
+
const seen = new Set<string>();
|
|
180
|
+
const unique = calls.filter((call) => {
|
|
181
|
+
const key = `${call.ticker}:${call.callAt}`;
|
|
182
|
+
if (seen.has(key)) return false;
|
|
183
|
+
seen.add(key);
|
|
184
|
+
return true;
|
|
185
|
+
});
|
|
186
|
+
return days.map((day) => ({
|
|
187
|
+
label: day.label,
|
|
188
|
+
items: unique
|
|
189
|
+
.filter((call) => {
|
|
190
|
+
const on = callDay(call);
|
|
191
|
+
return on !== null && on >= day.from && on <= day.to;
|
|
192
|
+
})
|
|
193
|
+
.sort((left, right) => compareRows(left, right, sort)),
|
|
194
|
+
}));
|
|
195
|
+
}
|
|
@@ -46,11 +46,16 @@ const HOP_SEPARATOR = " › ";
|
|
|
46
46
|
|
|
47
47
|
/**
|
|
48
48
|
* Holding to via, then via to the company that reports. The first hop is
|
|
49
|
-
* padded with no-break spaces, which the desktop does not collapse.
|
|
49
|
+
* padded with no-break spaces, which the desktop does not collapse. A column
|
|
50
|
+
* too narrow for the route keeps each share whole or leaves it out (`8% of
|
|
51
|
+
* NVDA purchases › …`), never a figure cut off from whose it is.
|
|
50
52
|
*/
|
|
51
|
-
function shareText(row: SecondHopRow, firstHopWidth: number) {
|
|
52
|
-
const first = hopLabel(row.hops[0]);
|
|
53
|
-
|
|
53
|
+
function shareText(row: SecondHopRow, firstHopWidth: number, cells = Infinity) {
|
|
54
|
+
const first = hopLabel(row.hops[0]), second = hopLabel(row.hops[1]);
|
|
55
|
+
const lined = `${first}${"\u00a0".repeat(Math.max(0, firstHopWidth - displayWidth(first)))}${HOP_SEPARATOR}${second}`;
|
|
56
|
+
if (displayWidth(lined) <= cells) return lined;
|
|
57
|
+
const whole = `${first}${HOP_SEPARATOR}${second}`;
|
|
58
|
+
return displayWidth(whole) <= cells ? whole : `${first}${HOP_SEPARATOR}…`;
|
|
54
59
|
}
|
|
55
60
|
|
|
56
61
|
/**
|
|
@@ -113,7 +118,7 @@ function renderSecondHopCell(row: SecondHopRow, column: DataTableColumn, firstHo
|
|
|
113
118
|
case "link": return { text: row.link === "customer" ? "customer's customer" : "supplier's supplier" };
|
|
114
119
|
case "via": return { text: row.via };
|
|
115
120
|
case "holding": return { text: row.holding };
|
|
116
|
-
case "shares": return { text: shareText(row, firstHopWidth), value: shareText(row, 0) };
|
|
121
|
+
case "shares": return { text: shareText(row, firstHopWidth, column.width), value: shareText(row, 0) };
|
|
117
122
|
case "move": return move(row);
|
|
118
123
|
default: return { text: row.holdingDate ?? "--" };
|
|
119
124
|
}
|