sidekick-shared 0.24.5 → 0.25.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +35 -0
- package/README.md +159 -52
- package/dist/accountChangeSignal.d.ts +3 -0
- package/dist/accountChangeSignal.js +19 -0
- package/dist/accountChanges.d.ts +21 -0
- package/dist/accountChanges.js +151 -0
- package/dist/accountRegistry.d.ts +3 -1
- package/dist/accountRegistry.js +5 -0
- package/dist/browser.d.ts +8 -3
- package/dist/browser.js +15 -1
- package/dist/codexQuotaWatcher.d.ts +6 -0
- package/dist/codexQuotaWatcher.js +101 -47
- package/dist/index.d.ts +23 -13
- package/dist/index.js +34 -10
- package/dist/modelAliases.d.ts +13 -0
- package/dist/modelAliases.js +58 -0
- package/dist/modelCatalog.d.ts +32 -0
- package/dist/modelCatalog.js +145 -0
- package/dist/modelContext.d.ts +36 -3
- package/dist/modelContext.js +109 -34
- package/dist/modelInfo.d.ts +30 -1
- package/dist/modelInfo.js +116 -26
- package/dist/multiProviderQuotaService.d.ts +8 -0
- package/dist/multiProviderQuotaService.js +64 -3
- package/dist/node.d.ts +4 -4
- package/dist/node.js +4 -1
- package/dist/observedSessionCollector.d.ts +75 -4
- package/dist/observedSessionCollector.js +452 -42
- package/dist/parsers/codexHistory.d.ts +4 -2
- package/dist/parsers/codexHistory.js +9 -2
- package/dist/parsers/sessionActivityDetector.d.ts +6 -0
- package/dist/parsers/sessionActivityDetector.js +17 -0
- package/dist/providerIds.d.ts +11 -0
- package/dist/providerIds.js +9 -0
- package/dist/providerQuota.d.ts +3 -1
- package/dist/providerQuota.js +3 -0
- package/dist/providers/claudeCode.d.ts +10 -1
- package/dist/providers/claudeCode.js +204 -39
- package/dist/providers/codex.d.ts +18 -1
- package/dist/providers/codex.js +269 -40
- package/dist/providers/codexDatabase.d.ts +9 -0
- package/dist/providers/codexDatabase.js +107 -2
- package/dist/providers/diagnostics.d.ts +13 -0
- package/dist/providers/diagnostics.js +88 -0
- package/dist/providers/factory.d.ts +14 -0
- package/dist/providers/factory.js +57 -0
- package/dist/providers/openCode.d.ts +20 -1
- package/dist/providers/openCode.js +361 -11
- package/dist/providers/openCodeDatabase.d.ts +10 -0
- package/dist/providers/openCodeDatabase.js +69 -0
- package/dist/providers/types.d.ts +52 -2
- package/dist/providers/types.js +4 -0
- package/dist/quota.d.ts +4 -1
- package/dist/quota.js +3 -7
- package/dist/quotaHistory.d.ts +2 -1
- package/dist/quotaPoller.d.ts +13 -1
- package/dist/quotaPoller.js +65 -3
- package/dist/schemas/accountManager.d.ts +2 -2
- package/dist/schemas/accountManager.js +2 -4
- package/dist/schemas/accountStatus.d.ts +3 -0
- package/dist/schemas/accountStatus.js +1 -0
- package/dist/schemas/index.d.ts +1 -0
- package/dist/schemas/index.js +7 -2
- package/dist/schemas/observedSessionV1.d.ts +27 -26
- package/dist/schemas/observedSessionV1.js +6 -4
- package/dist/schemas/quota.d.ts +2 -2
- package/dist/schemas/quota.js +3 -6
- package/dist/schemas/quotaHistory.d.ts +2 -2
- package/dist/schemas/tokenEstimation.d.ts +1 -1
- package/dist/sessionMonitor.d.ts +15 -0
- package/dist/sessionMonitor.js +142 -0
- package/dist/sessionPreviews.d.ts +26 -1
- package/dist/sessionPreviews.js +319 -4
- package/dist/types/observedSessionV1.d.ts +6 -2
- package/dist/types/observedSessionV1.js +14 -8
- package/package.json +22 -1
package/CHANGELOG.md
CHANGED
|
@@ -5,6 +5,41 @@ All notable changes to sidekick-shared will be documented in this file.
|
|
|
5
5
|
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/),
|
|
6
6
|
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
|
7
7
|
|
|
8
|
+
## [0.25.0] - 2026-08-18
|
|
9
|
+
|
|
10
|
+
### Added
|
|
11
|
+
|
|
12
|
+
- `listSessionPreviewsAsync()` and `readSessionPreviewAsync()` provide bounded-concurrency, cooperative session preview reads while preserving the synchronous APIs and their signatures
|
|
13
|
+
- Async preview labeling batches Codex and OpenCode database work into at most one `sqlite3` subprocess per provider per few hundred sessions listed (ids are chunked clear of argv limits); when `sqlite3` is absent, the same bounded file-scan fallback remains available
|
|
14
|
+
- `OpenCodeProvider.listAllSessionFiles()` completes native preview enumeration across Claude Code, Codex, and OpenCode
|
|
15
|
+
- `ObservedSessionCollector.subscribe()` and `SessionMonitor.subscribe()` emit debounced, coalesced session changes with the previous and current fingerprints, backed by filesystem watching plus a documented catch-up poll for unreliable filesystems
|
|
16
|
+
- `createSessionProviders({ onDiagnostic })` constructs every usable provider independently and reports unavailable providers without aborting the host
|
|
17
|
+
- `SessionProviderBase.findSessionById()` has provider-native implementations: filename lookup for Claude Code and Codex, and a database lookup with a bounded file-scan fallback for OpenCode
|
|
18
|
+
- `exportResolvedModelCatalog()` and `importResolvedModelCatalog()` transfer serializable context-window and pricing resolutions between Node and browser realms without private hooks
|
|
19
|
+
- `registerModelAlias()` lets hosts resolve short model names to canonical ids, and catalog provenance marks prefix-inherited context and pricing matches so callers can reject them
|
|
20
|
+
- Stable provider-id arrays are exported as runtime values alongside their derived TypeScript unions
|
|
21
|
+
- `onAccountsChanged()` reports process-local and filesystem-observed login, logout, and account-switch changes without account-state polling in each host
|
|
22
|
+
|
|
23
|
+
### Changed
|
|
24
|
+
|
|
25
|
+
- Provider constructors are environment-independent and perform no filesystem, configuration, database, or binary probing; environmental failures are deferred to first use and returned as structured diagnostics
|
|
26
|
+
- Repeated identical provider degradations are coalesced in the factory diagnostic result, keeping first-use reporting bounded in long-lived hosts
|
|
27
|
+
- `ObservedSessionCollector.collect()` caches parsed sessions by fingerprint, so a second collection over unchanged files performs no content reads
|
|
28
|
+
- Observed sessions expose `fingerprintParts: { sizeBytes, mtimeMs }` alongside the compatible opaque fingerprint string
|
|
29
|
+
- Collector reads accept bounded-concurrency and cooperative-yield hooks; cached observations refresh `observedAt` and activity state while retaining `contentObservedAt` to make the age of cached usage/model data explicit
|
|
30
|
+
- `ObservedSessionDiagnostic` now includes `severity` and `phase` while retaining every existing `kind` value
|
|
31
|
+
- Account and quota entry points guarantee results that validate against the same-release exported schemas, including additive schema fields, and their contract tests enforce the boundary
|
|
32
|
+
- Every documented package subpath now declares explicit `types`, `import`, `require`, and `default` export conditions and resolves in both Vite and TypeScript's legacy `moduleResolution: node` mode without aliases
|
|
33
|
+
- `readCodexHistory()` retains raw epoch-second `ts`, adds normalized `tsMs`, and sizes its tail read from `limit` unless an explicit byte bound is supplied
|
|
34
|
+
- Observed-session projection accepts `observationOnly: true`, which reports transcripts as read-only observations with `capabilities.resume` disabled
|
|
35
|
+
- `QuotaPoller`, `MultiProviderQuotaService`, and `CodexQuotaWatcher` stay dormant when their account is absent and wake on account changes instead of issuing empty polls
|
|
36
|
+
|
|
37
|
+
### Fixed
|
|
38
|
+
|
|
39
|
+
- Codex and OpenCode database-backed operations attach an availability diagnostic when the external `sqlite3` binary is missing, so an unavailable runtime is distinguishable from an empty workspace
|
|
40
|
+
- A wrong session id resolves to `null` through every provider instead of surfacing discovery or environment errors
|
|
41
|
+
- Exact model pricing/context entries are considered before prefix inheritance across all sources, and prefix-only matches are explicit in provenance rather than silently trusted as exact
|
|
42
|
+
|
|
8
43
|
## [0.24.5] - 2026-08-18
|
|
9
44
|
|
|
10
45
|
### Added
|
package/README.md
CHANGED
|
@@ -9,6 +9,7 @@ Types, parsers, providers, readers, formatters, aggregation, search, reporting,
|
|
|
9
9
|
|
|
10
10
|
## Recent additions
|
|
11
11
|
|
|
12
|
+
- **Host-safe APIs (0.25.0)** — `listSessionPreviewsAsync()` / `readSessionPreviewAsync()` read previews with bounded concurrency and cooperative yielding; `ObservedSessionCollector.subscribe()` and `SessionMonitor.subscribe()` replace host polling loops with debounced change batches; `createSessionProviders({ onDiagnostic })` constructs every usable provider with structured diagnostics instead of throwing; `findSessionById()` resolves one session without scanning; `exportResolvedModelCatalog()` / `importResolvedModelCatalog()` and `registerModelAlias()` transfer context/pricing resolutions across realms; `onAccountsChanged()` reports login/logout/switch events; provider constructors perform no environment I/O, and quota pollers stay dormant without an account.
|
|
12
13
|
- **Native session-file helpers** — `encodeClaudeWorkspacePath()` / `getClaudeSessionDirectory()` locate Claude Code's `~/.claude/projects/` directories with the real on-disk encoding, `findCodexRolloutFile()` resolves a Codex session id to its rollout path, `readCodexHistory()` tail-reads `~/.codex/history.jsonl`, `listSessionPreviews()` / `readSessionPreview()` build a cheap stat-first recent-sessions index across providers, and `parseMcpToolName()` splits `mcp__<server>__<tool>` identifiers (browser-safe).
|
|
13
14
|
- **Non-blocking account APIs & locked sync writers** — every login/switch entry point gains an async variant (`switchAccountAsync()`, `getAccountLoginStatusAsync()`, `finalizeAccountLoginAsync()`, `prepareCodexAccountAsync()`, `finalizeCodexAccountAsync()`, `switchToCodexAccountAsync()`) that keeps `codex` CLI probes off the event loop, and synchronous callers get the same cross-process store lock via `atomicWriteFileSync()` / `updateJsonStoreAtomicSync()` / `withFileLockSync()`, with progress-based timeouts and abandoned-lock reclaim.
|
|
14
15
|
- **Canonical usage and pricing** — provider-specific counters normalize into disjoint input/cache/output/reasoning categories with `normalizeProviderUsage()`; `calculateNormalizedUsageCost()` prevents cache/reasoning double counting and reports pricing provenance.
|
|
@@ -41,16 +42,19 @@ shelling out to an executable **`sqlite3` on `PATH`**. There is no bundled
|
|
|
41
42
|
driver. `CodexProvider` shells out to the same binary, but only for an optional
|
|
42
43
|
index.
|
|
43
44
|
|
|
44
|
-
Without it
|
|
45
|
-
|
|
46
|
-
|
|
45
|
+
Without it, database-backed reads still return results rather than throwing —
|
|
46
|
+
but as of 0.25.0 the missing binary is no longer invisible: Codex and OpenCode
|
|
47
|
+
attach a `sqlite_missing` diagnostic to affected operations, so an unavailable
|
|
48
|
+
runtime is distinguishable from an empty workspace. Construct providers through
|
|
49
|
+
`createSessionProviders({ onDiagnostic })` to receive those diagnostics, or ask
|
|
50
|
+
any provider directly — `getRuntimeStatus()` is implemented by all three:
|
|
47
51
|
|
|
48
52
|
```typescript
|
|
49
53
|
const status = provider.getRuntimeStatus?.();
|
|
50
54
|
// status.kind: 'available' | 'db_missing' | 'sqlite_missing'
|
|
51
|
-
// | 'sqlite_blocked' | 'query_failed'
|
|
55
|
+
// | 'sqlite_blocked' | 'query_failed' | ...
|
|
52
56
|
if (status && status.kind !== 'available') {
|
|
53
|
-
console.warn(`Session data
|
|
57
|
+
console.warn(`Session data degraded: ${status.kind}`);
|
|
54
58
|
}
|
|
55
59
|
```
|
|
56
60
|
|
|
@@ -78,56 +82,56 @@ returns the platform default that both overrides bypass.
|
|
|
78
82
|
|
|
79
83
|
## API Overview
|
|
80
84
|
|
|
81
|
-
| Module | Description
|
|
82
|
-
| ------------------------------- |
|
|
83
|
-
| **Types** | Session events, OpenCode/Codex format types, persistence schemas (tasks, decisions, notes, plans, historical data)
|
|
84
|
-
| **Paths** | Config directory resolution, project data paths, workspace encoding
|
|
85
|
-
| **Readers** | Read tasks, decisions, notes, history, handoff, and plans from `~/.config/sidekick/`
|
|
86
|
-
| **Writers** | Atomic persistence writers — `atomicWriteJson()` / `updateJsonStoreAtomic()` and their synchronous twins `atomicWriteJsonSync()` / `atomicWriteFileSync()` / `updateJsonStoreAtomicSync()` / `withFileLockSync()` (same cross-process lock file, progress-based timeouts, abandoned-lock reclaim), plus lock-coordinated capture helpers `addTask()`, `completeTask()`, `addDecision()`, `addNote()` that merge into the shared stores without clobbering concurrent writers
|
|
87
|
-
| **Providers** | Session provider abstraction with Claude Code, OpenCode, and Codex implementations; auto-detection via filesystem
|
|
88
|
-
| **Observed Sessions (V1)** | Versioned provider-neutral observation contracts — `createProviderSessionAdapterV1()` / `derivePendingUserRequestV1()` with `ObservedAgentSessionV1`, `ProviderCapabilitiesV1`, `PendingUserRequestV1`, `SessionEvidenceRefV1`, and provenance/confidence wrapper types (Zod schemas in `sidekick-shared/schemas`)
|
|
89
|
-
| **Parsers** | JSONL event parsing, OpenCode/Codex format normalization, subagent scanning, session path resolution, debug log parsing
|
|
90
|
-
| **Watchers** | Live session file watching with event bridging, plus `createJsonlTail()` for raw incremental JSONL consumers
|
|
91
|
-
| **Formatters** | Display helpers (`formatTokenCount()`, `formatDurationMs()`), tool summary, noise classification, session dump (text/markdown/JSON), event highlighting
|
|
92
|
-
| **Search** | Cross-session full-text search, advanced filtering (substring, fuzzy, regex, date)
|
|
93
|
-
| **Aggregation** | Event aggregation, frequency tracking, activity heatmaps, pattern extraction
|
|
94
|
-
| **Analytics** | Session-quality scoring (beta) with factor contributions and weekly trends (`scoreSessionQuality()`, `calculateQualityTrend()`), code-impact metrics including cost per changed line and per-model churn/cost (`calculateCodeImpact()`), and reported-vs-heuristic compaction accounting (`calculateCompactionLedger()`, `formatCompactionLedger()`)
|
|
95
|
-
| **Error History** | Shared error taxonomy (`categorizeError()`, `extractErrorMessage()`) plus append-only per-project failure history (`appendErrorHistory()`, `readErrorHistory()`, `getTopFailingTools()`) behind per-tool/hour/model error rollups
|
|
96
|
-
| **Session Context** | Provider-neutral context evidence snapshots (`buildSessionContextSnapshot()`, `calculateSessionContextPressure()`, `createSessionContextProjector()`, `readSessionContextSnapshot()`): layered evidence sources, low/medium/high context pressure, and observed capabilities (tools, MCP servers, permission mode, rate limits)
|
|
97
|
-
| **Assistant Turns** | Browser-safe timeline/process/answer projection for provider-normalized assistant turns (`segmentAssistantTurn()`, `assistantTurnEventsFromSessionEvents()`), including interleaved reasoning, compact tool groups, and Claude `Task` subagent refs without prompt leakage
|
|
98
|
-
| **Report** | Self-contained HTML session report generation
|
|
99
|
-
| **Credentials** | Claude Max OAuth credential reading from `~/.claude/.credentials.json`
|
|
100
|
-
| **Quota** | Claude Max subscription quota fetching (5-hour and 7-day windows), Codex rate-limit extraction from event streams (plus Codex reset credits via `fetchCodexResetCreditsFromApi()`, attached to quota state by `fetchCodexQuotaFromApi()`), and authoritative z.ai Coding Plan quota fetching via `resolveZaiQuota()` / `fetchZaiQuotaFromApi()` (reads z.ai's `api/monitor/usage/quota/limit` endpoint with cached-snapshot fallback). The observed-traffic z.ai estimator was removed from the package root exports in 0.23.0 and every remaining export of it is `@deprecated` — `resolveZaiQuota()` is the single supported z.ai quota API
|
|
101
|
-
| **Provider Status** | API health checking via status.claude.com and status.openai.com (indicator, components, incidents)
|
|
102
|
-
| **Doctor** | Typed cross-provider health diagnostics — `runDoctor()` checks project identity, sessions, accounts, providers, and dependencies into a `HealthReport`; `formatHealthReport()` renders it and `getSessionDiagnostics()` exposes the per-provider session probe
|
|
103
|
-
| **Schemas** | Zod schemas for runtime validation of data crossing process/IPC boundaries — JSONL session events (`sessionEventSchema`, `messageUsageSchema`, `sessionMessageSchema`), assistant turns, observed-session V1 records, quota, account status, and quota history — plus `extractSessionEvents()` to unwrap `progress`-wrapped events. Also published fs-free via the [`sidekick-shared/schemas`](#supported-import-paths) subpath
|
|
104
|
-
| **Extractors** | Pure functions for single-event processing: `extractTokenUsage()`, `extractToolCall()` (top-level `tool_use`), `extractToolCalls()` (assistant content blocks), plus Node-only session asset extraction (`gatherAssetsForCwd()`, `readClaudeAssets()`, `readCodexAssets()`) for URLs, file paths, commands, and plans
|
|
105
|
-
| **Model Info & Pricing** | Model family parsing (Anthropic / OpenAI / Google, including legacy `claude-3-opus-…` and `claude-3-5-sonnet-…` IDs), context-window lookup (including Fable 5 / Opus 4.8 / Opus 4.7 / Sonnet 4.7 1M and GPT-5.x variants), pricing tables with optional LiteLLM hydration, normalized non-double-counting cost (`calculateNormalizedUsageCost()`, fed by `normalizeProviderUsage()` / `extractNormalizedUsage()`), legacy cost helpers retained but deprecated (`calculateCost()`, `calculateCostWithProvenance()`), `mergeCostSources()`,
|
|
106
|
-
| **Quota Polling** | `QuotaPoller` class with exponential backoff, active/idle intervals, and cached fallback
|
|
107
|
-
| **Multi-Provider Quota** | `MultiProviderQuotaService` orchestrates Claude polling + peak-hours + account labels + Codex/z.ai quota updates behind one typed event stream. `CodexQuotaWatcher` watches the active Codex rollout for live rate limits with snapshot fallback; z.ai quota uses the API resolver with snapshot fallback
|
|
108
|
-
| **Accounts** | Multi-provider account registry (v2) with per-provider active account, save/switch/remove, v1 migration, `ensureDefaultAccounts()` for first-run bootstrap of the active system Claude/Codex credentials as a "Default" saved account, `getActiveAccountStatus()` for a single-pass active-account read across providers, and live-first `resolveActiveClaudeAccount()` / `resolveActiveCodexAccount()` that report the currently logged-in account (self-healing the saved pointer) for display
|
|
109
|
-
| **Account Management 2.0** | Provider-neutral acquisition + switching: `beginAccountLogin()` / `getAccountLoginStatus()` / `finalizeAccountLogin()` / `spawnAccountLogin()` drive a TTY-less, profile-isolated login that doesn't disturb the active account until finalization; `listAllAccounts()` and `switchAccount()` expose a shared switcher across Claude and Codex. Every status/finalize/switch entry point also has an `-Async` variant (`getAccountLoginStatusAsync()`, `finalizeAccountLoginAsync()`, `switchAccountAsync()`, …) that keeps `codex` CLI probes off the event loop — prefer those from hosts with a UI loop. Claude accounts get canonical profile homes with account-scoped macOS keychain suffixes and startup migration from legacy flat backups
|
|
110
|
-
| **Terminal sync & auto-switch** | Opt-in terminal profile pointers, shell-hook/launcher helpers, and a default-off `AutoSwitchController` (`decideAutoSwitch()`) that moves to a healthier saved account when quota crosses a configured threshold; its `switchAccount` callback may return a Promise and defaults to `switchAccountAsync()`
|
|
111
|
-
| **Codex Profiles** | Codex account lifecycle — prepare, finalize, switch, remove — switching atomically swaps the profile's backed-up credentials into the system `~/.codex/auth.json`, with rotated-token staleness protection, one-time dual-home migration, and legacy multi-home session monitoring
|
|
112
|
-
| **Quota Snapshots** | Persistent quota caching per provider/account for offline fallback
|
|
113
|
-
| **Statusline** | Cache-only one-line account/quota/burn footer — `formatStatusline()`, `selectStatuslineAccount()`, `BurnRateCalculator`, and `estimateTimeToQuota()`, also published via the [`sidekick-shared/statusline`](#supported-import-paths) subpath for fast per-prompt rendering
|
|
114
|
-
| **Phrases** | Curated humorous phrases for loading/idle states, available as a flat `ALL_PHRASES` array or grouped via `PHRASE_CATEGORIES` for category-aware UI
|
|
85
|
+
| Module | Description |
|
|
86
|
+
| ------------------------------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
|
|
87
|
+
| **Types** | Session events, OpenCode/Codex format types, persistence schemas (tasks, decisions, notes, plans, historical data) |
|
|
88
|
+
| **Paths** | Config directory resolution, project data paths, workspace encoding |
|
|
89
|
+
| **Readers** | Read tasks, decisions, notes, history, handoff, and plans from `~/.config/sidekick/` |
|
|
90
|
+
| **Writers** | Atomic persistence writers — `atomicWriteJson()` / `updateJsonStoreAtomic()` and their synchronous twins `atomicWriteJsonSync()` / `atomicWriteFileSync()` / `updateJsonStoreAtomicSync()` / `withFileLockSync()` (same cross-process lock file, progress-based timeouts, abandoned-lock reclaim), plus lock-coordinated capture helpers `addTask()`, `completeTask()`, `addDecision()`, `addNote()` that merge into the shared stores without clobbering concurrent writers |
|
|
91
|
+
| **Providers** | Session provider abstraction with Claude Code, OpenCode, and Codex implementations; auto-detection via filesystem. As of 0.25.0 constructors perform no environment I/O — build them all with `createSessionProviders({ onDiagnostic })`, which reports unavailable providers as structured diagnostics instead of failing; `findSessionById()` resolves one session through provider-native indexes; stable provider-id const arrays (`SESSION_PROVIDER_IDS`, `ACCOUNT_PROVIDER_IDS`, `QUOTA_PROVIDER_IDS`, `MODEL_PROVIDER_IDS`) accompany the derived unions |
|
|
92
|
+
| **Observed Sessions (V1)** | Versioned provider-neutral observation contracts — `createProviderSessionAdapterV1()` / `derivePendingUserRequestV1()` with `ObservedAgentSessionV1`, `ProviderCapabilitiesV1`, `PendingUserRequestV1`, `SessionEvidenceRefV1`, and provenance/confidence wrapper types (Zod schemas in `sidekick-shared/schemas`) |
|
|
93
|
+
| **Parsers** | JSONL event parsing, OpenCode/Codex format normalization, subagent scanning, session path resolution, debug log parsing |
|
|
94
|
+
| **Watchers** | Live session file watching with event bridging, plus `createJsonlTail()` for raw incremental JSONL consumers |
|
|
95
|
+
| **Formatters** | Display helpers (`formatTokenCount()`, `formatDurationMs()`), tool summary, noise classification, session dump (text/markdown/JSON), event highlighting |
|
|
96
|
+
| **Search** | Cross-session full-text search, advanced filtering (substring, fuzzy, regex, date) |
|
|
97
|
+
| **Aggregation** | Event aggregation, frequency tracking, activity heatmaps, pattern extraction |
|
|
98
|
+
| **Analytics** | Session-quality scoring (beta) with factor contributions and weekly trends (`scoreSessionQuality()`, `calculateQualityTrend()`), code-impact metrics including cost per changed line and per-model churn/cost (`calculateCodeImpact()`), and reported-vs-heuristic compaction accounting (`calculateCompactionLedger()`, `formatCompactionLedger()`) |
|
|
99
|
+
| **Error History** | Shared error taxonomy (`categorizeError()`, `extractErrorMessage()`) plus append-only per-project failure history (`appendErrorHistory()`, `readErrorHistory()`, `getTopFailingTools()`) behind per-tool/hour/model error rollups |
|
|
100
|
+
| **Session Context** | Provider-neutral context evidence snapshots (`buildSessionContextSnapshot()`, `calculateSessionContextPressure()`, `createSessionContextProjector()`, `readSessionContextSnapshot()`): layered evidence sources, low/medium/high context pressure, and observed capabilities (tools, MCP servers, permission mode, rate limits) |
|
|
101
|
+
| **Assistant Turns** | Browser-safe timeline/process/answer projection for provider-normalized assistant turns (`segmentAssistantTurn()`, `assistantTurnEventsFromSessionEvents()`), including interleaved reasoning, compact tool groups, and Claude `Task` subagent refs without prompt leakage |
|
|
102
|
+
| **Report** | Self-contained HTML session report generation |
|
|
103
|
+
| **Credentials** | Claude Max OAuth credential reading from `~/.claude/.credentials.json` |
|
|
104
|
+
| **Quota** | Claude Max subscription quota fetching (5-hour and 7-day windows), Codex rate-limit extraction from event streams (plus Codex reset credits via `fetchCodexResetCreditsFromApi()`, attached to quota state by `fetchCodexQuotaFromApi()`), and authoritative z.ai Coding Plan quota fetching via `resolveZaiQuota()` / `fetchZaiQuotaFromApi()` (reads z.ai's `api/monitor/usage/quota/limit` endpoint with cached-snapshot fallback). The observed-traffic z.ai estimator was removed from the package root exports in 0.23.0 and every remaining export of it is `@deprecated` — `resolveZaiQuota()` is the single supported z.ai quota API |
|
|
105
|
+
| **Provider Status** | API health checking via status.claude.com and status.openai.com (indicator, components, incidents) |
|
|
106
|
+
| **Doctor** | Typed cross-provider health diagnostics — `runDoctor()` checks project identity, sessions, accounts, providers, and dependencies into a `HealthReport`; `formatHealthReport()` renders it and `getSessionDiagnostics()` exposes the per-provider session probe |
|
|
107
|
+
| **Schemas** | Zod schemas for runtime validation of data crossing process/IPC boundaries — JSONL session events (`sessionEventSchema`, `messageUsageSchema`, `sessionMessageSchema`), assistant turns, observed-session V1 records, quota, account status, account management, and quota history — plus `extractSessionEvents()` to unwrap `progress`-wrapped events. Account and quota APIs guarantee results valid against the same-release schemas. Also published fs-free via the [`sidekick-shared/schemas`](#supported-import-paths) subpath |
|
|
108
|
+
| **Extractors** | Pure functions for single-event processing: `extractTokenUsage()`, `extractToolCall()` (top-level `tool_use`), `extractToolCalls()` (assistant content blocks), plus Node-only session asset extraction (`gatherAssetsForCwd()`, `readClaudeAssets()`, `readCodexAssets()`) for URLs, file paths, commands, and plans |
|
|
109
|
+
| **Model Info & Pricing** | Model family parsing (Anthropic / OpenAI / Google, including legacy `claude-3-opus-…` and `claude-3-5-sonnet-…` IDs), context-window lookup (including Fable 5 / Opus 4.8 / Opus 4.7 / Sonnet 4.7 1M and GPT-5.x variants), pricing tables with optional LiteLLM hydration, normalized non-double-counting cost (`calculateNormalizedUsageCost()`, fed by `normalizeProviderUsage()` / `extractNormalizedUsage()`), legacy cost helpers retained but deprecated (`calculateCost()`, `calculateCostWithProvenance()`), `mergeCostSources()`, display helpers (`shortModelName()`, `getModelDisplayInfo()`, `compareModelIds()`, `sortModelIds()`, `formatCost()`), and cross-realm catalog transfer — `exportResolvedModelCatalog()` / `importResolvedModelCatalog()` move resolved context windows and pricing (with provenance, prefix inheritance explicit) between Node and browser realms, and `registerModelAlias()` resolves short or host-specific names to canonical ids |
|
|
110
|
+
| **Quota Polling** | `QuotaPoller` class with exponential backoff, active/idle intervals, and cached fallback. Stays dormant while no account exists and wakes through the account-change signal |
|
|
111
|
+
| **Multi-Provider Quota** | `MultiProviderQuotaService` orchestrates Claude polling + peak-hours + account labels + Codex/z.ai quota updates behind one typed event stream. `CodexQuotaWatcher` watches the active Codex rollout for live rate limits with snapshot fallback; z.ai quota uses the API resolver with snapshot fallback. All three stay dormant without a matching account and wake on account changes |
|
|
112
|
+
| **Accounts** | Multi-provider account registry (v2) with per-provider active account, save/switch/remove, v1 migration, `ensureDefaultAccounts()` for first-run bootstrap of the active system Claude/Codex credentials as a "Default" saved account, `getActiveAccountStatus()` for a single-pass active-account read across providers, `onAccountsChanged()` for push-based login/logout/switch notification (process-local mutations, filesystem watches, and a catch-up poll), and live-first `resolveActiveClaudeAccount()` / `resolveActiveCodexAccount()` that report the currently logged-in account (self-healing the saved pointer) for display |
|
|
113
|
+
| **Account Management 2.0** | Provider-neutral acquisition + switching: `beginAccountLogin()` / `getAccountLoginStatus()` / `finalizeAccountLogin()` / `spawnAccountLogin()` drive a TTY-less, profile-isolated login that doesn't disturb the active account until finalization; `listAllAccounts()` and `switchAccount()` expose a shared switcher across Claude and Codex. Every status/finalize/switch entry point also has an `-Async` variant (`getAccountLoginStatusAsync()`, `finalizeAccountLoginAsync()`, `switchAccountAsync()`, …) that keeps `codex` CLI probes off the event loop — prefer those from hosts with a UI loop. Claude accounts get canonical profile homes with account-scoped macOS keychain suffixes and startup migration from legacy flat backups |
|
|
114
|
+
| **Terminal sync & auto-switch** | Opt-in terminal profile pointers, shell-hook/launcher helpers, and a default-off `AutoSwitchController` (`decideAutoSwitch()`) that moves to a healthier saved account when quota crosses a configured threshold; its `switchAccount` callback may return a Promise and defaults to `switchAccountAsync()` |
|
|
115
|
+
| **Codex Profiles** | Codex account lifecycle — prepare, finalize, switch, remove — switching atomically swaps the profile's backed-up credentials into the system `~/.codex/auth.json`, with rotated-token staleness protection, one-time dual-home migration, and legacy multi-home session monitoring |
|
|
116
|
+
| **Quota Snapshots** | Persistent quota caching per provider/account for offline fallback |
|
|
117
|
+
| **Statusline** | Cache-only one-line account/quota/burn footer — `formatStatusline()`, `selectStatuslineAccount()`, `BurnRateCalculator`, and `estimateTimeToQuota()`, also published via the [`sidekick-shared/statusline`](#supported-import-paths) subpath for fast per-prompt rendering |
|
|
118
|
+
| **Phrases** | Curated humorous phrases for loading/idle states, available as a flat `ALL_PHRASES` array or grouped via `PHRASE_CATEGORIES` for category-aware UI |
|
|
115
119
|
|
|
116
120
|
## Supported import paths
|
|
117
121
|
|
|
118
|
-
`sidekick-shared` ships three public entry points plus a few convenience subpaths. Pick the one that matches your runtime.
|
|
122
|
+
`sidekick-shared` ships three public entry points plus a few convenience subpaths. Pick the one that matches your runtime. As of 0.25.0 every documented subpath declares explicit `types` / `import` / `require` / `default` export conditions and resolves under Vite and TypeScript's legacy `moduleResolution: node` without consumer-side aliases.
|
|
119
123
|
|
|
120
|
-
| Path | Runtime | What it exposes
|
|
121
|
-
| ------------------------------ | -------------------------- |
|
|
122
|
-
| `sidekick-shared` | Node (CLI, extension host) | Full public API (readers, providers, parsers, pricing, …).
|
|
123
|
-
| `sidekick-shared/browser` | **Browser / webview** | Pure helpers: usage normalization/pricing, token estimation, transcript and assistant-turn projection, model/context math, `parseMcpToolName()`.
|
|
124
|
-
| `sidekick-shared/node` | Node only | LiteLLM pricing and context-window hydration, observed context-window persistence, recent-session/transcript reads, session previews (`listSessionPreviews()` / `readSessionPreview()`), Codex history/rollout lookup (`readCodexHistory()`, `findCodexRolloutFile()`), and resilient observed-session collection (`fs` + providers). |
|
|
125
|
-
| `sidekick-shared/phrases` | Any runtime | Phrase arrays + `getRandomPhrase()`.
|
|
126
|
-
| `sidekick-shared/modelContext` | Any runtime | Direct access to the context-window module.
|
|
127
|
-
| `sidekick-shared/modelInfo` | Any runtime | Direct access to model parsing and cost math.
|
|
128
|
-
| `sidekick-shared/formatting` | Any runtime | Direct access to pure token and duration display helpers.
|
|
129
|
-
| `sidekick-shared/schemas` | Any runtime | Pure Zod boundary schemas (session events, assistant turns, observed-session V1, quota, account status, quota history) — fs-free, no Node builtins.
|
|
130
|
-
| `sidekick-shared/statusline` | Node only | Cache-only statusline surface: account status + quota snapshot readers, `formatStatusline()`, and burn-rate estimates.
|
|
124
|
+
| Path | Runtime | What it exposes |
|
|
125
|
+
| ------------------------------ | -------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
|
|
126
|
+
| `sidekick-shared` | Node (CLI, extension host) | Full public API (readers, providers, parsers, pricing, …). |
|
|
127
|
+
| `sidekick-shared/browser` | **Browser / webview** | Pure helpers: usage normalization/pricing, token estimation, transcript and assistant-turn projection, model/context math, `parseMcpToolName()`. |
|
|
128
|
+
| `sidekick-shared/node` | Node only | LiteLLM pricing and context-window hydration, observed context-window persistence, recent-session/transcript reads, session previews (`listSessionPreviews()` / `readSessionPreview()` plus the bounded-concurrency `listSessionPreviewsAsync()` / `readSessionPreviewAsync()`), Codex history/rollout lookup (`readCodexHistory()`, `findCodexRolloutFile()`), and resilient observed-session collection (`fs` + providers). |
|
|
129
|
+
| `sidekick-shared/phrases` | Any runtime | Phrase arrays + `getRandomPhrase()`. |
|
|
130
|
+
| `sidekick-shared/modelContext` | Any runtime | Direct access to the context-window module. |
|
|
131
|
+
| `sidekick-shared/modelInfo` | Any runtime | Direct access to model parsing and cost math. |
|
|
132
|
+
| `sidekick-shared/formatting` | Any runtime | Direct access to pure token and duration display helpers. |
|
|
133
|
+
| `sidekick-shared/schemas` | Any runtime | Pure Zod boundary schemas (session events, assistant turns, observed-session V1, quota, account status, account management, quota history) — fs-free, no Node builtins. |
|
|
134
|
+
| `sidekick-shared/statusline` | Node only | Cache-only statusline surface: account status + quota snapshot readers, `formatStatusline()`, and burn-rate estimates. |
|
|
131
135
|
|
|
132
136
|
### Browser / webview runtimes
|
|
133
137
|
|
|
@@ -169,6 +173,31 @@ await loadObservedContextWindows();
|
|
|
169
173
|
|
|
170
174
|
Both calls always resolve; a network failure, missing cache, or malformed store leaves lookups on the static tables. To record a window a provider reports at runtime, call `recordObservedContextWindow(modelId, window)` — it persists only when the value changes.
|
|
171
175
|
|
|
176
|
+
### Transfer resolved model data across realms
|
|
177
|
+
|
|
178
|
+
A realm that can hydrate (extension host, CLI) can hand its resolved context
|
|
179
|
+
windows and pricing to one that cannot (webview, browser bundle) as one
|
|
180
|
+
serializable snapshot — no private hooks, no re-hydration:
|
|
181
|
+
|
|
182
|
+
```typescript
|
|
183
|
+
// Node side (after hydratePricingCatalog / loadObservedContextWindows):
|
|
184
|
+
import { exportResolvedModelCatalog } from 'sidekick-shared';
|
|
185
|
+
const snapshot = exportResolvedModelCatalog(); // or pass specific model ids
|
|
186
|
+
|
|
187
|
+
// Browser side:
|
|
188
|
+
import { importResolvedModelCatalog, registerModelAlias } from 'sidekick-shared/browser';
|
|
189
|
+
const { imported, diagnostics } = importResolvedModelCatalog(snapshot);
|
|
190
|
+
```
|
|
191
|
+
|
|
192
|
+
Entries carry provenance (`source`, `match`, `matchedModelId`, and
|
|
193
|
+
`inheritedByPrefix` for pricing), so consumers can reject prefix-inherited
|
|
194
|
+
guesses. Unresolved entries (`default` window / `none` pricing) are skipped on
|
|
195
|
+
import rather than pinned, successive partial imports merge, and imported data
|
|
196
|
+
ranks below anything the importing realm has observed first-hand.
|
|
197
|
+
`registerModelAlias('sonnet', 'claude-sonnet-5')` resolves short or
|
|
198
|
+
host-specific names everywhere lookups happen; data recorded under the alias id
|
|
199
|
+
itself keeps winning over the canonical fallback.
|
|
200
|
+
|
|
172
201
|
### Normalize and price provider usage
|
|
173
202
|
|
|
174
203
|
```typescript
|
|
@@ -274,6 +303,17 @@ const previews = listSessionPreviews([new ClaudeCodeProvider(), new CodexProvide
|
|
|
274
303
|
|
|
275
304
|
`readSessionPreview(provider, filePath)` reads the same bounded preview for one known session file — `null` when the file is missing or unreadable, `null` fields when its content is malformed.
|
|
276
305
|
|
|
306
|
+
Hosts with a UI loop should prefer the async variants from `sidekick-shared/node`. They read with bounded concurrency, yield between files, batch Codex/OpenCode label lookups into non-blocking `sqlite3` subprocesses, and — unlike their sync twins — return degradation status alongside the data:
|
|
307
|
+
|
|
308
|
+
```typescript
|
|
309
|
+
import { listSessionPreviewsAsync, readSessionPreviewAsync } from 'sidekick-shared/node';
|
|
310
|
+
|
|
311
|
+
const { previews, diagnostics } = await listSessionPreviewsAsync(providers, { limit: 10 });
|
|
312
|
+
const { preview } = await readSessionPreviewAsync(provider, filePath);
|
|
313
|
+
```
|
|
314
|
+
|
|
315
|
+
To resolve one session id to its file without scanning, every bundled provider implements `findSessionById(workspacePath, sessionId)` — a filename join for Claude Code and Codex, a database lookup for OpenCode — returning `null` for misses instead of reading transcripts. (It is optional on the `SessionProviderBase` interface so pre-0.25 external implementations keep compiling; fall back to `findAllSessions()` when absent.)
|
|
316
|
+
|
|
277
317
|
MCP tool identifiers (`mcp__<server>__<tool>`) split with `parseMcpToolName(name)` — first-double-underscore rule, `null` for malformed names, safe in browser bundles.
|
|
278
318
|
|
|
279
319
|
### Collect observed sessions with isolation and retry
|
|
@@ -299,10 +339,55 @@ applyReadOnlyProjection(source.capabilities);
|
|
|
299
339
|
|
|
300
340
|
Discovery and reads are isolated, retries use bounded 30-second-to-5-minute exponential backoff, file changes bypass delay, duplicate identical failures are suppressed, and recovery emits a content-free diagnostic. Clock and fingerprint callbacks are injectable for deterministic hosts/tests.
|
|
301
341
|
|
|
342
|
+
As of 0.25.0, parses are cached by fingerprint — a second `collect()` over unchanged files performs no content reads (cache hits refresh `observedAt` and activity state; `contentObservedAt` reports how old the cached usage/model data actually is, and `cacheHit` marks them). Observations expose structured `fingerprintParts: { sizeBytes, mtimeMs }` alongside the opaque fingerprint string, and diagnostics carry `severity` and `phase` in addition to their existing `kind`.
|
|
343
|
+
|
|
344
|
+
Instead of a host polling loop, subscribe to debounced change batches. Each change carries the previous and current fingerprints; filesystem watching is combined with a catch-up poll for filesystems that drop events:
|
|
345
|
+
|
|
346
|
+
```typescript
|
|
347
|
+
const subscription = collector.subscribe(
|
|
348
|
+
(batch) => {
|
|
349
|
+
for (const change of batch.changes) {
|
|
350
|
+
// change.type: 'added' | 'changed' | 'removed'
|
|
351
|
+
console.log(batch.providerId, change.type, change.reference.sessionId);
|
|
352
|
+
console.log(change.previousFingerprint, '→', change.fingerprint);
|
|
353
|
+
}
|
|
354
|
+
void collector.collect(); // consume changed sessions through the parse cache
|
|
355
|
+
},
|
|
356
|
+
{ debounceMs: 250, pollIntervalMs: 30_000 },
|
|
357
|
+
);
|
|
358
|
+
// later: subscription.dispose();
|
|
359
|
+
```
|
|
360
|
+
|
|
361
|
+
`SessionMonitor.subscribe()` offers the same push model at the session-event level.
|
|
362
|
+
|
|
302
363
|
## Usage Examples
|
|
303
364
|
|
|
365
|
+
### Construct session providers for a long-lived host
|
|
366
|
+
|
|
367
|
+
`createSessionProviders()` builds every requested provider without probing the
|
|
368
|
+
filesystem or binaries — constructors are I/O-free as of 0.25.0, so one
|
|
369
|
+
unavailable provider cannot abort host startup. Environmental failures surface
|
|
370
|
+
on first use as structured diagnostics instead:
|
|
371
|
+
|
|
372
|
+
```typescript
|
|
373
|
+
import { createSessionProviders } from 'sidekick-shared';
|
|
374
|
+
|
|
375
|
+
const { providers, diagnostics } = createSessionProviders({
|
|
376
|
+
onDiagnostic: (diagnostic) => {
|
|
377
|
+
// e.g. { providerId: 'opencode', kind: 'sqlite_missing',
|
|
378
|
+
// severity: 'warning', phase: 'query', message: '...' }
|
|
379
|
+
log(diagnostic);
|
|
380
|
+
},
|
|
381
|
+
});
|
|
382
|
+
```
|
|
383
|
+
|
|
384
|
+
Repeated identical degradations are coalesced, so the diagnostic stream stays
|
|
385
|
+
bounded across long-lived polling and subscription cycles.
|
|
386
|
+
|
|
304
387
|
### Detect the active session provider
|
|
305
388
|
|
|
389
|
+
For a single-provider surface, auto-detect and construct just one:
|
|
390
|
+
|
|
306
391
|
```typescript
|
|
307
392
|
import {
|
|
308
393
|
detectProvider,
|
|
@@ -518,7 +603,7 @@ const parser = new JsonlParser(
|
|
|
518
603
|
parser.processChunk(rawData);
|
|
519
604
|
```
|
|
520
605
|
|
|
521
|
-
The boundary schemas — `sessionEventSchema` plus the quota, account-status, and quota-history schemas — are also importable fs-free from `sidekick-shared/schemas`, which keeps Zod out of bundles that only need the pure math/formatting helpers. `extractSessionEvents()` from the same subpath unwraps Claude Code `progress`-wrapped events into canonical `SessionEvent[]`.
|
|
606
|
+
The boundary schemas — `sessionEventSchema` plus the quota, account-status, account-management, and quota-history schemas — are also importable fs-free from `sidekick-shared/schemas`, which keeps Zod out of bundles that only need the pure math/formatting helpers. Account and quota APIs are guaranteed to return values valid against the schemas exported in the same release, so consumers do not need to parse those library results again. Additive account or quota fields are added to the matching exported schema in the same release. `extractSessionEvents()` from the same subpath unwraps Claude Code `progress`-wrapped events into canonical `SessionEvent[]`.
|
|
522
607
|
|
|
523
608
|
### Tail raw JSONL events incrementally
|
|
524
609
|
|
|
@@ -594,6 +679,28 @@ console.log(status.claude.present, status.claude.email);
|
|
|
594
679
|
console.log(status.codex.present, status.codex.label);
|
|
595
680
|
```
|
|
596
681
|
|
|
682
|
+
To react to logins, logouts, and switches without polling that status yourself,
|
|
683
|
+
subscribe to `onAccountsChanged()`. It combines process-local mutation signals,
|
|
684
|
+
filesystem watches on the account stores, and a low-frequency catch-up poll —
|
|
685
|
+
and only emits when the status actually changed:
|
|
686
|
+
|
|
687
|
+
```typescript
|
|
688
|
+
import { onAccountsChanged } from 'sidekick-shared';
|
|
689
|
+
|
|
690
|
+
const subscription = onAccountsChanged(
|
|
691
|
+
({ reason, status }) => {
|
|
692
|
+
// reason: 'local' | 'filesystem' | 'poll'
|
|
693
|
+
render(status.claude, status.codex);
|
|
694
|
+
},
|
|
695
|
+
{ emitCurrent: true },
|
|
696
|
+
);
|
|
697
|
+
// later: subscription.dispose();
|
|
698
|
+
```
|
|
699
|
+
|
|
700
|
+
`QuotaPoller`, `MultiProviderQuotaService`, and `CodexQuotaWatcher` use the same
|
|
701
|
+
signal internally: they stay dormant while no matching account exists and wake
|
|
702
|
+
when one appears.
|
|
703
|
+
|
|
597
704
|
For display surfaces that must reflect the **currently logged-in** account — even after a native `claude /login` or `codex login` outside Sidekick — use the live-first resolvers. They prefer the live provider auth (`~/.claude/.claude.json` oauthAccount; the `~/.codex/auth.json` id_token JWT) over the saved `activeByProvider` pointer, fall back to the registry, and self-heal the saved pointer on an unambiguous match (best-effort, never creating or deleting profiles):
|
|
598
705
|
|
|
599
706
|
```typescript
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports._onRawAccountsChanged = _onRawAccountsChanged;
|
|
4
|
+
exports._emitAccountsChanged = _emitAccountsChanged;
|
|
5
|
+
const listeners = new Set();
|
|
6
|
+
function _onRawAccountsChanged(listener) {
|
|
7
|
+
listeners.add(listener);
|
|
8
|
+
return () => listeners.delete(listener);
|
|
9
|
+
}
|
|
10
|
+
function _emitAccountsChanged(reason) {
|
|
11
|
+
for (const listener of listeners) {
|
|
12
|
+
try {
|
|
13
|
+
listener(reason);
|
|
14
|
+
}
|
|
15
|
+
catch {
|
|
16
|
+
// Account notifications are observational and cannot break mutations.
|
|
17
|
+
}
|
|
18
|
+
}
|
|
19
|
+
}
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
import { type AccountChangeReason } from './accountChangeSignal';
|
|
2
|
+
import { type ActiveAccountStatus } from './accountStatus';
|
|
3
|
+
import type { Disposable } from './quotaPoller';
|
|
4
|
+
export interface AccountsChangedEvent {
|
|
5
|
+
reason: AccountChangeReason;
|
|
6
|
+
status: ActiveAccountStatus;
|
|
7
|
+
}
|
|
8
|
+
export interface OnAccountsChangedOptions {
|
|
9
|
+
/** Emit the current status immediately after subscribing. */
|
|
10
|
+
emitCurrent?: boolean;
|
|
11
|
+
/** Catch-up poll for filesystems where watch delivery is unreliable. Default: 30s. */
|
|
12
|
+
pollIntervalMs?: number;
|
|
13
|
+
}
|
|
14
|
+
/**
|
|
15
|
+
* Observe login, logout, and active-account switches. Local Sidekick mutations
|
|
16
|
+
* signal immediately; filesystem watchers cover external CLIs; a low-frequency
|
|
17
|
+
* catch-up poll protects network mounts and watcher-hostile filesystems.
|
|
18
|
+
*/
|
|
19
|
+
export declare function onAccountsChanged(listener: (event: AccountsChangedEvent) => void, options?: OnAccountsChangedOptions): Disposable;
|
|
20
|
+
/** Internal bridge for account mutations outside the registry module. */
|
|
21
|
+
export declare function _notifyAccountsChanged(): void;
|