@asaidimu/utils-workspace 5.0.0 → 6.1.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/index.d.mts CHANGED
@@ -42,7 +42,7 @@ declare class TransactionContext {
42
42
  * Stages a single write operation against a store.
43
43
  * Does NOT touch the store — no I/O happens until commit().
44
44
  */
45
- addOp<T extends Record<string, any>>(store: Store<T>, type: "put" | "delete" | "add", data: any): Promise<void>;
45
+ addOp<T extends Record<string, any>>(store: Store$1<T>, type: "put" | "delete" | "add", data: any): Promise<void>;
46
46
  /**
47
47
  * Commits all staged operations atomically.
48
48
  *
@@ -122,7 +122,7 @@ type BufferedOperation<T> = {
122
122
  *
123
123
  * @template T - The type of objects stored. Must include the key path property.
124
124
  */
125
- interface Store<T extends Record<string, any> = Record<string, any>> {
125
+ interface Store$1<T extends Record<string, any> = Record<string, any>> {
126
126
  /**
127
127
  * Returns the name of this store (the IDB object store / collection name).
128
128
  * Used by TransactionContext to group operations and open a correctly-scoped
@@ -944,6 +944,9 @@ interface SessionMetadata {
944
944
  created?: Timestamp;
945
945
  /** UTC timestamp of the last activity within the session. */
946
946
  updated?: Timestamp;
947
+ /** The current model being use by the session */
948
+ model?: string;
949
+ [key: string]: any;
947
950
  };
948
951
  /** The current chronological leaf-node of the conversation DAG. */
949
952
  head?: {
@@ -1018,8 +1021,9 @@ interface TopicIndex {
1018
1021
  entries?: number;
1019
1022
  };
1020
1023
  }
1021
- /** The complete in-memory read-model of the Workspace state. */
1022
- interface Index {
1024
+ type IndexExtensions = Record<string, Record<string, any>>;
1025
+ interface Index<T extends IndexExtensions = IndexExtensions> {
1026
+ /** The complete in-memory read-model of the Workspace state. */
1023
1027
  /** Lookup dictionary of Roles by their string name. */
1024
1028
  roles: Record<string, RoleSummary>;
1025
1029
  /** Lookup dictionary of Preferences by their UUID. */
@@ -1034,9 +1038,10 @@ interface Index {
1034
1038
  blobs: Record<SHA256, BlobRecord>;
1035
1039
  /** Lookup dictionary of registered Tool capabilities by their string name. */
1036
1040
  tools: Record<string, ToolSummary>;
1041
+ extensions: T;
1037
1042
  }
1038
1043
  /** The root container for a user's workspace. */
1039
- interface Workspace<ProjectMetadata extends Record<string, any> = Record<string, any>> {
1044
+ interface Workspace<ProjectMetadata extends Record<string, any> = Record<string, any>, Extentions extends Record<string, Record<string, any>> = IndexExtensions> {
1040
1045
  /** Unique identifier for the entire workspace environment. */
1041
1046
  id: UUID;
1042
1047
  /** Global user and systemic settings. */
@@ -1044,7 +1049,7 @@ interface Workspace<ProjectMetadata extends Record<string, any> = Record<string,
1044
1049
  /** High-level project metadata. */
1045
1050
  project: Project<ProjectMetadata>;
1046
1051
  /** The in-memory read-projection of all underlying stores. */
1047
- index: Index;
1052
+ index: Index<Extentions>;
1048
1053
  }
1049
1054
  /**
1050
1055
  * Format used for exporting/importing a complete workspace state,
@@ -1092,6 +1097,15 @@ interface CreateWorkspace extends BaseCommand {
1092
1097
  project: Project;
1093
1098
  };
1094
1099
  }
1100
+ interface SyncWorkspace extends BaseCommand {
1101
+ type: "workspace:sync";
1102
+ /** If provided, updates these root properties during sync. */
1103
+ payload: {
1104
+ id?: UUID;
1105
+ settings?: Settings;
1106
+ project?: Project;
1107
+ } | undefined;
1108
+ }
1095
1109
  interface AddRole extends BaseCommand {
1096
1110
  type: "role:add";
1097
1111
  /** The complete role object to inject into the workspace. */
@@ -1373,7 +1387,7 @@ interface ToolCallCommand extends BaseCommand {
1373
1387
  payload: ToolCall;
1374
1388
  }
1375
1389
  /** Union of all possible commands that can be dispatched to the Workspace Manager. */
1376
- type Command = CreateWorkspace | AddRole | UpdateRole | DeleteRole | AddPreference | UpdatePreference | DeletePreference | CreateSession | UpdateSession | ForkSession | DeleteSession | SwitchSessionRole | AddSessionTopics | OverrideSessionPreferences | AddContext | UpdateContext | DeleteContext | UpdateTurn | AddTurn | EditTurn | BranchTurn | DeleteTurn | RegisterBlob | RetainBlob | ReleaseBlob | PurgeBlob | RecordBlobRemoteId | AddTopic | UpdateTopic | DeleteTopic | MergeTopics | ToolCallCommand;
1390
+ type Command = CreateWorkspace | SyncWorkspace | AddRole | UpdateRole | DeleteRole | AddPreference | UpdatePreference | DeletePreference | CreateSession | UpdateSession | ForkSession | DeleteSession | SwitchSessionRole | AddSessionTopics | OverrideSessionPreferences | AddContext | UpdateContext | DeleteContext | UpdateTurn | AddTurn | EditTurn | BranchTurn | DeleteTurn | RegisterBlob | RetainBlob | ReleaseBlob | PurgeBlob | RecordBlobRemoteId | AddTopic | UpdateTopic | DeleteTopic | MergeTopics | ToolCallCommand;
1377
1391
  /**
1378
1392
  * Standard reducer pattern for updating workspace state.
1379
1393
  * @template T - Custom contextual additions for the reducer parameters.
@@ -1419,6 +1433,8 @@ interface ResolvedSession {
1419
1433
  interface WorkspaceEvents {
1420
1434
  /** Emitted when the index or core settings change. */
1421
1435
  "workspace:changed": DeepPartial<Workspace>;
1436
+ /** Emitted when a full sync has completed. */
1437
+ "workspace:synced": void;
1422
1438
  /** Emitted when a blob is registered, updated, or removed. */
1423
1439
  "blobs:changed": {
1424
1440
  /** Hash of the affected blob. */
@@ -1433,6 +1449,8 @@ interface SessionSnapshot {
1433
1449
  id: UUID;
1434
1450
  /** Top-level session definition fields. */
1435
1451
  meta: SessionMetadata;
1452
+ /** Model identifier (e.g., "claude-sonnet-4-6", "gemini-2.0-flash"). */
1453
+ model?: string;
1436
1454
  /** The active role — persona, instructions, role-level constraints. */
1437
1455
  role: Role;
1438
1456
  /** Unfiltered, unranked preferences attached strictly to the role or session. */
@@ -1467,6 +1485,8 @@ interface SessionSnapshot {
1467
1485
  * - Uploading inline blobs to the provider where required.
1468
1486
  */
1469
1487
  interface Prompt {
1488
+ /** Model identifier (e.g., "claude-sonnet-4-6", "gemini-2.0-flash"). */
1489
+ model?: string;
1470
1490
  /** Correlates this prompt to its session for logging and evaluation. */
1471
1491
  session: UUID;
1472
1492
  /** System-level instructions, context, and preferences. */
@@ -1540,7 +1560,7 @@ interface AdapterStatus {
1540
1560
  };
1541
1561
  /** Pricing tiers for this model. */
1542
1562
  pricing: Array<{
1543
- unit: 'token' | 'call';
1563
+ unit: 'token' | 'call' | "image";
1544
1564
  /** Exponent: price is per 10^scale units. */
1545
1565
  scale: number;
1546
1566
  /** Price per unit in USD. */
@@ -1561,7 +1581,7 @@ interface AdapterStatus {
1561
1581
  timeout?: number;
1562
1582
  /** The hard limits enforced by the provider. */
1563
1583
  capacity: Array<{
1564
- unit: 'token' | 'call';
1584
+ unit: 'token' | 'call' | string;
1565
1585
  /** Maximum units allowed per period. */
1566
1586
  max: number;
1567
1587
  /** Period length in seconds. */
@@ -1580,20 +1600,33 @@ interface ExecuteResult {
1580
1600
  /** Side-effect commands to dispatch against the workspace. */
1581
1601
  effects: BaseCommand[];
1582
1602
  }
1603
+ /**
1604
+ * A single labelled section of the system prompt.
1605
+ * Mirrors PreparedPrompt.system exactly — the assembler's output is stored
1606
+ * there directly, giving callers full inspection without re-parsing the string.
1607
+ */
1608
+ interface PromptSection {
1609
+ /**
1610
+ * Origin label for this section.
1611
+ * Core sections use fixed labels: 'operating-system' | 'persona' |
1612
+ * 'preferences' | 'context' | 'instructions'.
1613
+ * Extensions carry whatever label the injector provides.
1614
+ */
1615
+ label: string;
1616
+ /** Text content exactly as it will be sent to the model. */
1617
+ content: string;
1618
+ /** Optional structured metadata for richer UI display or tooling. */
1619
+ metadata?: Record<string, any>;
1620
+ }
1583
1621
  /**
1584
1622
  * The complete, final prompt exactly as the model will receive it.
1585
1623
  * Generic, provider-agnostic, fully inspectable, and executable.
1586
1624
  */
1587
1625
  interface PreparedPrompt {
1626
+ /** Model identifier (e.g., "claude-sonnet-4-6", "gemini-2.0-flash"). */
1627
+ model: string;
1588
1628
  /** The complete system instruction broken into labelled sections for inspection. */
1589
- system: Array<{
1590
- /** Origin label for this section (e.g., "persona", "context:project-brief"). */
1591
- label: string;
1592
- /** Text content exactly as it will be sent to the model. */
1593
- content: string;
1594
- /** Optional structured metadata for richer UI display. */
1595
- metadata?: Record<string, any>;
1596
- }>;
1629
+ instructions: Array<PromptSection>;
1597
1630
  /** Final transcript turns that will be sent after adapter-level truncation. */
1598
1631
  transcript: Turn[];
1599
1632
  /** Final context entries included after adapter-level truncation. */
@@ -1627,6 +1660,238 @@ interface PreparedPrompt {
1627
1660
  executeStream?(): AsyncIterable<Partial<Turn> | ExecuteResult>;
1628
1661
  }
1629
1662
 
1663
+ /**
1664
+ * Optional filter passed to schema(), description(), and rules() to control
1665
+ * which block definitions are included in the output.
1666
+ *
1667
+ * Resolution order:
1668
+ * 1. `emittable` gate is always applied first — non-emittable blocks never
1669
+ * appear in schema/description/rules regardless of other filters.
1670
+ * 2. If `only` is provided, only those types are included. `exclude` is ignored.
1671
+ * 3. If `exclude` is provided (and `only` is not), those types are removed.
1672
+ */
1673
+ interface BlockFilter {
1674
+ /**
1675
+ * Whitelist of block type strings to include.
1676
+ * When present, `exclude` is ignored entirely.
1677
+ */
1678
+ only?: string[];
1679
+ /**
1680
+ * Blacklist of block type strings to remove.
1681
+ * Ignored when `only` is present.
1682
+ */
1683
+ exclude?: string[];
1684
+ }
1685
+
1686
+ declare class ContentBlockRegistry {
1687
+ private readonly store;
1688
+ constructor();
1689
+ /** Register a new block type. Throws if type already exists. */
1690
+ register(definition: ContentBlockDefinition): void;
1691
+ /** Remove a block type and its mappings. */
1692
+ unregister(type: string): void;
1693
+ /** Replace an existing block definition entirely, or upsert. */
1694
+ update(type: string, partial: Partial<ContentBlockDefinition>): void;
1695
+ /** Get a single definition by type string. */
1696
+ get(type: string): ContentBlockDefinition | undefined;
1697
+ /** Return all registered definitions. */
1698
+ list(): ContentBlockDefinition[];
1699
+ isType<T extends BaseContentBlock<any> = BaseContentBlock<any>>(block: BaseContentBlock<any>, type: string): block is T;
1700
+ guard<T extends BaseContentBlock<any> = BaseContentBlock<any>>(type: string): (block: BaseContentBlock<any>) => block is T;
1701
+ /**
1702
+ * Returns a plain JSON Schema object scoped to emittable block definitions.
1703
+ * The adapter converts this to a provider-specific format (e.g. Gemini Type enum).
1704
+ */
1705
+ schema(filter?: BlockFilter): Record<string, unknown>;
1706
+ /**
1707
+ * Returns the system-prompt section describing all emittable block types.
1708
+ * Per-block rules are rendered as bullet points beneath each block's description.
1709
+ */
1710
+ description(filter?: BlockFilter): string;
1711
+ /**
1712
+ * Returns all rules across the filtered set of emittable block definitions,
1713
+ * keyed by block type. Blocks with no rules are included with an empty array.
1714
+ *
1715
+ * The prompt assembler uses this to build a consolidated constraints section
1716
+ * or to reason about per-block policies before dispatching to the model.
1717
+ */
1718
+ rules(filter?: BlockFilter): Record<string, string[]>;
1719
+ /**
1720
+ * Replace the rules for a specific block type.
1721
+ * Convenience over update(type, { rules }) — more explicit at call sites.
1722
+ * Throws if the type is not registered.
1723
+ */
1724
+ setRules(type: string, rules: string[]): void;
1725
+ /**
1726
+ * Converts a raw JSON object from a model response into a workspace block.
1727
+ *
1728
+ * Resolution order:
1729
+ * 1. If a provider mapping exists for providerId, delegate to mapping.from(raw).
1730
+ * 2. Otherwise, naive field-copy with a fresh UUID.
1731
+ *
1732
+ * Returns null if the type is unregistered or the mapping explicitly rejects the input.
1733
+ */
1734
+ parse(raw: {
1735
+ type: string;
1736
+ [key: string]: any;
1737
+ }, providerId?: string): BaseContentBlock<any> | null;
1738
+ /**
1739
+ * Constructs a new block instance of the given type with a fresh UUID.
1740
+ * Throws if the type is not registered.
1741
+ */
1742
+ create<T extends BaseContentBlock<any> = BaseContentBlock<any>>(type: string, defaults?: Partial<T>): T;
1743
+ /**
1744
+ * Deep clones an existing block, assigning a new UUID and applying any overrides.
1745
+ */
1746
+ clone<T extends BaseContentBlock<any> = BaseContentBlock<any>>(block: T, overrides?: Partial<T>): T;
1747
+ }
1748
+
1749
+ /**
1750
+ * An additional section injected by the adapter or application layer.
1751
+ * Slots relative to a named core section anchor.
1752
+ *
1753
+ * Core section labels (fixed order):
1754
+ * 'operating-system' → 'persona' → 'preferences' → 'context' → 'instructions'
1755
+ *
1756
+ * Anchor format:
1757
+ * 'before:<label>' — inserted immediately before the named core section
1758
+ * 'after:<label>' — inserted immediately after the named core section
1759
+ * 'prepend' — inserted before all core sections
1760
+ * 'append' — inserted after all core sections (default when omitted)
1761
+ */
1762
+ interface AssemblerExtension extends PromptSection {
1763
+ /**
1764
+ * Where to slot this section relative to the core sections.
1765
+ * Defaults to 'append' when omitted.
1766
+ *
1767
+ * @example 'after:instructions' // place registry description after instructions
1768
+ * @example 'before:context' // place tool list before context
1769
+ * @example 'prepend' // place before everything
1770
+ * @example 'append' // place after everything (default)
1771
+ */
1772
+ position?: `before:${string}` | `after:${string}` | "prepend" | "append";
1773
+ }
1774
+ /**
1775
+ * Provider-agnostic system prompt assembler.
1776
+ *
1777
+ * Builds an ordered array of labelled sections from a Prompt plus any
1778
+ * adapter-injected extensions. The adapter calls join() to produce the
1779
+ * final string it wraps in its provider envelope.
1780
+ *
1781
+ * Responsibilities:
1782
+ * - Render core sections from Prompt fields in canonical order.
1783
+ * - Slot extensions at their declared anchor positions.
1784
+ * - Produce a consistent, inspectable section array.
1785
+ * - Join sections into a single string on demand.
1786
+ *
1787
+ * Not responsible for:
1788
+ * - Provider-specific wrapping (Content, system message, etc.).
1789
+ * - Block architecture text — the adapter injects that as an extension.
1790
+ * - Truncation — that is the adapter's concern.
1791
+ */
1792
+ interface SystemPromptAssembler {
1793
+ /**
1794
+ * Builds the ordered array of prompt sections.
1795
+ *
1796
+ * Core sections are always rendered in this order:
1797
+ * 1. operating-system — static workspace operating constraints
1798
+ * 2. persona — role.persona string
1799
+ * 3. preferences — active user preferences
1800
+ * 4. context — injected context entries
1801
+ * 5. instructions — global or session-level instructions (if present)
1802
+ *
1803
+ * Extensions are slotted relative to their declared `position` anchor.
1804
+ * Multiple extensions targeting the same anchor are inserted in the order
1805
+ * they appear in the extensions array.
1806
+ *
1807
+ * Core sections with no content (e.g. empty preferences, absent instructions)
1808
+ * are omitted from the output entirely.
1809
+ *
1810
+ * @param prompt - The fully built Prompt from PromptBuilder.
1811
+ * @param extensions - Additional sections injected by the adapter or app layer.
1812
+ */
1813
+ build(prompt: Prompt, extensions?: AssemblerExtension[]): PromptSection[];
1814
+ /**
1815
+ * Joins an array of PromptSections into a single string suitable for
1816
+ * passing to the model. Uses a consistent separator that works across providers.
1817
+ *
1818
+ * @param sections - The output of build().
1819
+ */
1820
+ join(sections: PromptSection[]): string;
1821
+ }
1822
+ /**
1823
+ * A registered content block — self-contained and provider-agnostic.
1824
+ */
1825
+ interface ContentBlockDefinition {
1826
+ /** Discriminator used in the "type" field of the block. */
1827
+ type: string;
1828
+ /** JSON Schema fragment for this block's shape (used in responseSchema). */
1829
+ schema: Record<string, unknown>;
1830
+ /** Human/LLM-readable description of the block, injected into the system prompt. */
1831
+ description: string;
1832
+ /**
1833
+ * Whether the model can produce this block type via structured JSON output.
1834
+ *
1835
+ * - `true` → included in schema(), description(), and rules()
1836
+ * - `false` → workspace-internal only; invisible to the model
1837
+ */
1838
+ emittable: boolean;
1839
+ /**
1840
+ * Ordered list of behavioural rules for this block type.
1841
+ * Rendered as bullet points beneath the block's description in the system prompt,
1842
+ * and also available separately via registry.rules().
1843
+ *
1844
+ * Examples:
1845
+ * - 'Never emit more than one summary block per turn.'
1846
+ * - 'Only emit when explicitly instructed by the system.'
1847
+ */
1848
+ rules: string[];
1849
+ /**
1850
+ * Provider-specific mapping functions, keyed by provider ID (e.g. "google", "openai").
1851
+ * Each entry tells the adapter how to serialise/deserialise this block.
1852
+ */
1853
+ mappings?: Record<string, {
1854
+ /**
1855
+ * Convert a workspace block into a provider-specific part.
1856
+ * The return type is `unknown` — the adapter casts it internally.
1857
+ */
1858
+ to(block: BaseContentBlock<string>): unknown;
1859
+ /**
1860
+ * Convert a provider-extracted raw JSON object into a workspace block.
1861
+ * Return `null` if parsing fails.
1862
+ */
1863
+ from(raw: any): BaseContentBlock<any> | null;
1864
+ }>;
1865
+ }
1866
+ /**
1867
+ * Application-layer services injected into every LLMAdapter.
1868
+ * All services operate on workspace domain types only — no provider SDKs.
1869
+ */
1870
+ interface WorkspaceServices {
1871
+ /**
1872
+ * Assembles the system prompt from a Prompt and adapter-injected extensions.
1873
+ * The adapter calls assembler.build() to get the inspectable section array,
1874
+ * then assembler.join() to get the string it wraps in its provider envelope.
1875
+ */
1876
+ assembler: SystemPromptAssembler;
1877
+ /**
1878
+ * Scans an assistant turn for actionable blocks and emits workspace commands.
1879
+ */
1880
+ processor: TurnProcessor;
1881
+ /**
1882
+ * Resolves BlobRefs to inline data or remote file mappings.
1883
+ */
1884
+ blobResolver: BlobResolver;
1885
+ /**
1886
+ * Self-describing catalogue of all known content block types.
1887
+ */
1888
+ blockRegistry: ContentBlockRegistry;
1889
+ /**
1890
+ * Model registry
1891
+ */
1892
+ models: ModelRegistry;
1893
+ }
1894
+
1630
1895
  /**
1631
1896
  * A simple LRU (Least Recently Used) cache implementation.
1632
1897
  * Used for caching frequently accessed entities in memory.
@@ -1728,7 +1993,64 @@ declare class BlobStore {
1728
1993
  resolveMany(refs: BlobRef[], adapter?: string): Promise<Result<Map<SHA256, ResolvedBlob>, WorkspaceError>>;
1729
1994
  }
1730
1995
 
1731
- declare class ContextStore {
1996
+ interface WorkspaceDatabase {
1997
+ /**
1998
+ * Open the database. Registers core schemas followed by any extension
1999
+ * schemas supplied by the caller (domain plugins).
2000
+ *
2001
+ * Idempotent — safe to call multiple times; subsequent calls are no-ops
2002
+ * if the database is already open.
2003
+ */
2004
+ open(extensionSchemas?: SchemaDefinition[]): Promise<void>;
2005
+ /**
2006
+ * Access a collection by schema name.
2007
+ * Throws if the schema has not been registered.
2008
+ */
2009
+ collection<T>(schemaName: string): Promise<Collection<T>>;
2010
+ /**
2011
+ * Close the database connection.
2012
+ */
2013
+ close(): void;
2014
+ /** get the underlying database connection. */
2015
+ database(): Database;
2016
+ }
2017
+ /**
2018
+ * Standard interface for all workspace entity stores.
2019
+ * @template T - The full entity type.
2020
+ * @template S - The summary type used for indexing.
2021
+ * @template K - The primary key type.
2022
+ */
2023
+ interface Store<T, S = T, K = string> {
2024
+ get(key: K): Promise<T | null>;
2025
+ add(entity: T): Promise<void>;
2026
+ update(key: K, updates: Partial<T>): Promise<T | null>;
2027
+ delete(key: K): Promise<boolean>;
2028
+ list(): Promise<T[]>;
2029
+ /**
2030
+ * Distills a full entity into a lightweight summary for the index.
2031
+ */
2032
+ summarize(entity: T): S;
2033
+ }
2034
+ declare function createWorkspaceDatabase(db: Database): WorkspaceDatabase;
2035
+ /**
2036
+ * Collection name constants
2037
+ * Defines the names of the collections used in the Workspace database.
2038
+ * Use these instead of raw strings throughout the codebase so a typo is a
2039
+ * compile-time error rather than a silent runtime miss.
2040
+ */
2041
+ declare const COLLECTIONS: {
2042
+ readonly WORKSPACE: "workspace";
2043
+ readonly ROLE: "role";
2044
+ readonly PREFERENCE: "preference";
2045
+ readonly CONTEXT: "context";
2046
+ readonly SESSION: "session";
2047
+ readonly TURN: "turn";
2048
+ readonly BLOB: "blob";
2049
+ readonly TOPIC: "topic";
2050
+ };
2051
+ type Collections = typeof COLLECTIONS[keyof typeof COLLECTIONS];
2052
+
2053
+ declare class ContextStore implements Store<Context, ContextSummary, string> {
1732
2054
  private readonly collection;
1733
2055
  private readonly cache;
1734
2056
  constructor(collection: Collection<Context>, cache: LRUCache<string, Context>);
@@ -1741,9 +2063,10 @@ declare class ContextStore {
1741
2063
  * Retrieves all context items referenced by the given topics using the in-memory index.
1742
2064
  */
1743
2065
  getByTopics(index: Index, topics: string[]): Promise<Context[]>;
2066
+ summarize(context: Context): ContextSummary;
1744
2067
  }
1745
2068
 
1746
- declare class PreferenceStore {
2069
+ declare class PreferenceStore implements Store<Preference, PreferenceSummary, UUID> {
1747
2070
  private readonly collection;
1748
2071
  private readonly cache;
1749
2072
  constructor(collection: Collection<Preference>, cache: LRUCache<UUID, Preference>);
@@ -1753,13 +2076,14 @@ declare class PreferenceStore {
1753
2076
  delete(id: UUID): Promise<boolean>;
1754
2077
  load(ids: UUID[]): Promise<Preference[]>;
1755
2078
  list(): Promise<Preference[]>;
2079
+ summarize(preference: Preference): PreferenceSummary;
1756
2080
  }
1757
2081
 
1758
2082
  /**
1759
2083
  * Atomic store for Role entities.
1760
2084
  * Receives a pre-resolved Collection and manages its own LRU cache.
1761
2085
  */
1762
- declare class RoleStore {
2086
+ declare class RoleStore implements Store<Role, RoleSummary> {
1763
2087
  private readonly collection;
1764
2088
  private readonly cache;
1765
2089
  constructor(collection: Collection<Role>, cache: LRUCache<string, Role>);
@@ -1783,9 +2107,13 @@ declare class RoleStore {
1783
2107
  * Lists all roles.
1784
2108
  */
1785
2109
  list(): Promise<Role[]>;
2110
+ /**
2111
+ * Distills a full role into a lightweight summary for the index.
2112
+ */
2113
+ summarize(role: Role): RoleSummary;
1786
2114
  }
1787
2115
 
1788
- declare class SessionStore {
2116
+ declare class SessionStore implements Store<SessionMetadata, SessionMetadata, UUID> {
1789
2117
  private readonly collection;
1790
2118
  private readonly cache;
1791
2119
  constructor(collection: Collection<SessionMetadata>, cache: LRUCache<UUID, SessionMetadata>);
@@ -1793,9 +2121,14 @@ declare class SessionStore {
1793
2121
  add(session: SessionMetadata): Promise<void>;
1794
2122
  update(id: UUID, updates: Partial<SessionMetadata>): Promise<SessionMetadata | null>;
1795
2123
  delete(id: UUID): Promise<boolean>;
2124
+ /**
2125
+ * Lists all sessions.
2126
+ */
2127
+ list(): Promise<SessionMetadata[]>;
2128
+ summarize(session: SessionMetadata): SessionMetadata;
1796
2129
  }
1797
2130
 
1798
- declare class TopicStore {
2131
+ declare class TopicStore implements Store<Topic, TopicIndex, string> {
1799
2132
  private readonly collection;
1800
2133
  private readonly cache;
1801
2134
  constructor(collection: Collection<Topic>, cache: LRUCache<string, Topic>);
@@ -1804,10 +2137,12 @@ declare class TopicStore {
1804
2137
  update(name: string, updates: Partial<Topic>): Promise<Topic | null>;
1805
2138
  delete(name: string): Promise<boolean>;
1806
2139
  getMany(names: string[]): Promise<Topic[]>;
2140
+ list(): Promise<Topic[]>;
1807
2141
  /**
1808
2142
  * Checks if a topic is referenced by any entity in the workspace index.
1809
2143
  */
1810
2144
  referencedBy(name: string, index: Index): boolean;
2145
+ summarize(topic: Topic): TopicIndex;
1811
2146
  }
1812
2147
 
1813
2148
  declare class TurnStore {
@@ -1827,50 +2162,52 @@ declare class TurnStore {
1827
2162
  delete(key: TurnKey): Promise<boolean>;
1828
2163
  }
1829
2164
 
1830
- interface WorkspaceDatabase {
1831
- /**
1832
- * Open the database. Registers core schemas followed by any extension
1833
- * schemas supplied by the caller (domain plugins).
1834
- *
1835
- * Idempotent — safe to call multiple times; subsequent calls are no-ops
1836
- * if the database is already open.
1837
- */
1838
- open(extensionSchemas?: SchemaDefinition[]): Promise<void>;
1839
- /**
1840
- * Access a collection by schema name.
1841
- * Throws if the schema has not been registered.
1842
- */
1843
- collection<T>(schemaName: string): Promise<Collection<T>>;
1844
- /**
1845
- * Close the database connection.
1846
- */
1847
- close(): void;
1848
- /** get the underlying database connection. */
1849
- database(): Database;
2165
+ interface WorkspaceMetadata {
2166
+ id: UUID;
2167
+ settings: Settings;
2168
+ project: Project;
1850
2169
  }
1851
- declare function createWorkspaceDatabase(db: Database): WorkspaceDatabase;
2170
+ declare class WorkspaceStore implements Store<WorkspaceMetadata, WorkspaceMetadata> {
2171
+ private readonly collection;
2172
+ private readonly cache;
2173
+ constructor(collection: Collection<WorkspaceMetadata>, cache: LRUCache<UUID, WorkspaceMetadata>);
2174
+ get(id: UUID): Promise<WorkspaceMetadata | null>;
2175
+ add(meta: WorkspaceMetadata): Promise<void>;
2176
+ update(id: UUID, updates: Partial<WorkspaceMetadata>): Promise<WorkspaceMetadata | null>;
2177
+ delete(id: UUID): Promise<boolean>;
2178
+ list(): Promise<WorkspaceMetadata[]>;
2179
+ summarize(meta: WorkspaceMetadata): WorkspaceMetadata;
2180
+ }
2181
+
1852
2182
  /**
1853
- * Collection name constants
1854
- * Defines the names of the collections used in the Workspace database.
1855
- * Use these instead of raw strings throughout the codebase so a typo is a
1856
- * compile-time error rather than a silent runtime miss.
2183
+ * A function that rebuilds a portion of the workspace index from persistent storage.
1857
2184
  */
1858
- declare const COLLECTIONS: {
1859
- readonly ROLE: "role";
1860
- readonly PREFERENCE: "preference";
1861
- readonly CONTEXT: "context";
1862
- readonly SESSION: "session";
1863
- readonly TURN: "turn";
1864
- readonly BLOB: "blob";
1865
- readonly TOPIC: "topic";
1866
- };
1867
- type Collections = typeof COLLECTIONS[keyof typeof COLLECTIONS];
1868
-
2185
+ type Indexer = (ctx: WorkspaceContext) => Promise<DeepPartial<Workspace>>;
2186
+ /**
2187
+ * A bundle of domain-specific logic that can be plugged into the workspace.
2188
+ * Allows app builders to group related schemas, reducers, stores, and blocks.
2189
+ */
2190
+ interface WorkspaceExtension {
2191
+ /** Schema definitions for new database collections. */
2192
+ schemas?: SchemaDefinition[];
2193
+ /** Reducers for handling custom commands. */
2194
+ reducers?: Record<string, WorkspaceReducer<any>>;
2195
+ /** Middleware for intercepting or observing workspace changes. */
2196
+ middleware?: WorkspaceMiddleware[];
2197
+ /** Indexers for rebuilding custom portions of the workspace index. */
2198
+ indexers?: Indexer[];
2199
+ /** Factory for custom entity stores. */
2200
+ stores?: (ctx: Omit<WorkspaceContext, "workspace">) => Record<string, Store<any>> | Promise<Record<string, Store<any>>>;
2201
+ /** Content block definitions for the LLM adapter. */
2202
+ blocks?: ContentBlockDefinition[];
2203
+ }
1869
2204
  /**
1870
2205
  * The full set of stores passed to every reducer and middleware call.
1871
2206
  * Applications extend this with their own stores (e.g., `interface AppContext extends WorkspaceContext`).
1872
2207
  */
1873
- interface WorkspaceContext {
2208
+ type WorkspaceContext<ProjectMetadata extends Record<string, any> = Record<string, any>, IndexExtentions extends Record<string, Record<string, any>> = Record<string, Record<string, any>>, StoreExtensions = any> = {
2209
+ /** Store for managing workspace metadata (settings, project). */
2210
+ workspaceStore: WorkspaceStore;
1874
2211
  /** Store for managing system personas and roles. */
1875
2212
  roles: RoleStore;
1876
2213
  /** Store for managing global and session-level user preferences. */
@@ -1888,10 +2225,12 @@ interface WorkspaceContext {
1888
2225
  /** Optional registry for managing available tools. */
1889
2226
  tools?: ToolRegistry;
1890
2227
  /** The current state of the workspace. */
1891
- workspace: Workspace;
2228
+ workspace: Workspace<ProjectMetadata, IndexExtentions>;
1892
2229
  /** The underlying database used by the workspace */
1893
2230
  db: WorkspaceDatabase;
1894
- }
2231
+ /** Registry of functions to rebuild the workspace index. */
2232
+ indexers: Indexer[];
2233
+ } & StoreExtensions;
1895
2234
  /**
1896
2235
  * Ranks and filters context entries by relevance to the current conversation.
1897
2236
  * The default implementation uses token overlap and recency weighting, but
@@ -1954,9 +2293,10 @@ interface LLMAdapter<TRequestParams extends Record<string, any> = {}> {
1954
2293
  /**
1955
2294
  * Returns the current state of the adapter. Callable at any time without a prompt.
1956
2295
  *
2296
+ * @param model - The model whose params we want to query.
1957
2297
  * @returns The adapter's status, including context windows and rate limits.
1958
2298
  */
1959
- status(): Promise<AdapterStatus>;
2299
+ status(model?: string): Promise<AdapterStatus>;
1960
2300
  /**
1961
2301
  * Processes a Prompt into a PreparedPrompt — the complete, final representation of what the model will receive.
1962
2302
  *
@@ -1967,6 +2307,42 @@ interface LLMAdapter<TRequestParams extends Record<string, any> = {}> {
1967
2307
  prompt: Prompt;
1968
2308
  } & TRequestParams): Promise<PreparedPrompt>;
1969
2309
  }
2310
+ interface LLMAdapterStatic<TRequestParams extends Record<string, any> = {}> {
2311
+ /** Lists all model profiles that can be used with this adapter. */
2312
+ models(): ModelProfile[];
2313
+ new (...args: any[]): LLMAdapter<TRequestParams>;
2314
+ }
2315
+ interface ModelProfile {
2316
+ /** Provider identifier, e.g. "google". */
2317
+ provider: string;
2318
+ /** Canonical model string as accepted by the API, e.g. "gemini-2.0-flash". */
2319
+ name: string;
2320
+ /** Context window and output limits. */
2321
+ window: AdapterStatus["window"];
2322
+ /** Capability flags. */
2323
+ feature: AdapterStatus["feature"];
2324
+ /** Pricing tiers. */
2325
+ pricing: AdapterStatus["pricing"];
2326
+ /**
2327
+ * Hard rate limit capacity as enforced by the provider.
2328
+ * Does not include runtime state (load, timeout).
2329
+ */
2330
+ capacity: AdapterStatus["rate"]["capacity"];
2331
+ }
2332
+ interface ModelRegistry {
2333
+ /**
2334
+ * Returns the profile for a model, or undefined if the model is unknown.
2335
+ * Callers should treat an undefined return as a configuration error.
2336
+ */
2337
+ get(model: string): ModelProfile | undefined;
2338
+ /** Lists all registered profiles, optionally filtered by provider. */
2339
+ list(provider?: string): ModelProfile[];
2340
+ /**
2341
+ * Registers or replaces a model profile. Useful for preview models,
2342
+ * fine-tunes, or updated specs that postdate the bundled defaults.
2343
+ */
2344
+ register(profile: ModelProfile): void;
2345
+ }
1970
2346
  /**
1971
2347
  * Analyzes assistant turn output for workspace side effects.
1972
2348
  * Implementations scan blocks and emit Commands that the Session dispatches.
@@ -1976,12 +2352,12 @@ interface TurnProcessor {
1976
2352
  * Scans an assistant turn for actionable blocks.
1977
2353
  *
1978
2354
  * @param turn - The turn containing blocks to process.
1979
- * @param sessionId - The UUID of the session the turn belongs to.
2355
+ * @param session - The UUID of the session the turn belongs to.
1980
2356
  * @returns Commands to dispatch against the workspace.
1981
2357
  */
1982
2358
  process(turn: {
1983
2359
  blocks: BaseContentBlock<string>[];
1984
- }, sessionId?: UUID): BaseCommand[];
2360
+ }, session: UUID): BaseCommand[];
1985
2361
  }
1986
2362
  /**
1987
2363
  * Compresses old transcript turns to reclaim token budget.
@@ -2080,18 +2456,7 @@ declare class WorkspaceManager {
2080
2456
  * @returns unsubscribe
2081
2457
  */
2082
2458
  subscribe<K extends keyof WorkspaceEvents>(event: K, listener: (payload: WorkspaceEvents[K]) => void): () => void;
2083
- ctx(): {
2084
- context: ContextStore;
2085
- roles: RoleStore;
2086
- preferences: PreferenceStore;
2087
- sessions: SessionStore;
2088
- topics: TopicStore;
2089
- blobs: BlobStore;
2090
- turns: TurnStore;
2091
- tools?: ToolRegistry | undefined;
2092
- db: WorkspaceDatabase;
2093
- workspace: Workspace<Record<string, any>>;
2094
- };
2459
+ ctx(): WorkspaceContext;
2095
2460
  }
2096
2461
 
2097
2462
  declare class WorkspaceApi {
@@ -2123,8 +2488,18 @@ declare class Session {
2123
2488
  private _role;
2124
2489
  private _preferences;
2125
2490
  private tree;
2491
+ private unsubscribe?;
2126
2492
  private constructor();
2127
2493
  static create(sessionId: UUID, manager: WorkspaceManager, processor: TurnProcessor): Promise<Session>;
2494
+ /**
2495
+ * Synchronizes the session's in-memory state with the persistent stores.
2496
+ * Useful after a workspace-wide sync or if state becomes stale.
2497
+ */
2498
+ sync(): Promise<void>;
2499
+ /**
2500
+ * Closes the session and cleans up subscriptions.
2501
+ */
2502
+ close(): void;
2128
2503
  private _setRole;
2129
2504
  private _setPreference;
2130
2505
  id(): UUID;
@@ -2251,6 +2626,12 @@ declare function computeSHA256(data: Uint8Array): Promise<SHA256>;
2251
2626
  * implementation for Browsers and Edge environments to avoid stack overflows.
2252
2627
  */
2253
2628
  declare function bufferToBase64(buffer: Uint8Array): string;
2629
+ /**
2630
+ * Short, deterministic hash of a string (4 chars in base36).
2631
+ * Suitable for AI-friendly reference tokens.
2632
+ */
2633
+ declare function shortHash(s: string, length?: number): string;
2634
+ declare function getExtension<K extends string, V>(index: Index, key: K): Record<string, V>;
2254
2635
 
2255
2636
  interface CreateWorkspaceParams {
2256
2637
  db: Database;
@@ -2261,9 +2642,18 @@ interface CreateWorkspaceParams {
2261
2642
  processor: TurnProcessor;
2262
2643
  guard?: PermissionGuard;
2263
2644
  toolRegistry?: ToolRegistry;
2645
+ models?: ModelProfile[];
2646
+ extensions?: WorkspaceExtension[];
2647
+ /** @deprecated use extensions instead */
2264
2648
  extensionSchemas?: SchemaDefinition[];
2649
+ /** @deprecated use extensions instead */
2265
2650
  extensionReducers?: Record<string, WorkspaceReducer<any>>;
2651
+ /** @deprecated use extensions instead */
2266
2652
  extensionMiddleware?: WorkspaceMiddleware[];
2653
+ /** @deprecated use extensions instead */
2654
+ extensionIndexers?: Indexer[];
2655
+ /** @deprecated use extensions instead */
2656
+ extensionStores?: (ctx: Omit<WorkspaceContext, "workspace">) => Record<string, any>;
2267
2657
  }
2268
2658
  /**
2269
2659
  * Boot factory for the Workspace library.
@@ -2272,7 +2662,8 @@ interface CreateWorkspaceParams {
2272
2662
  declare function createWorkspace(params: CreateWorkspaceParams): Promise<{
2273
2663
  manager: WorkspaceManager;
2274
2664
  sessions: SessionManager;
2275
- ctx: Omit<WorkspaceContext, "workspace">;
2665
+ ctx: Omit<any, "workspace">;
2666
+ services: WorkspaceServices;
2276
2667
  }>;
2277
2668
 
2278
- export { type AddContext, type AddPreference, type AddRole, type AddSessionTopics, type AddTopic, type AddTurn, type AuthRequest, type BackendError, type BaseCommand, type BaseContentBlock, type BlobCommand, type BlobError, type BlobMediaType, type BlobRecord, type BlobRef, type BlobResolver, type BranchInfo, type BranchTurn, COLLECTIONS, type Collections, type Command, type ContentBlock, type Context, type ContextContent, type ContextRetriever, type ContextSummary, type CreateSession, type CreateWorkspace, type CreateWorkspaceParams, type DeepPartial, type DeleteContext, type DeletePreference, type DeleteRole, type DeleteSession, type DeleteTopic, type DeleteTurn, type DocumentBlock, type DocumentMediaType, type DuplicateKeyError, EMPTY_SYSTEM_ROLE, type EditTurn, type ForkSession, type ImageBlock, type ImageMediaType, type Index, type InvalidCommandError, type LLMAdapter, LRUCache, type MergeTopics, type ModelConstraint, type ModelConstraintMap, type ModelName, type NotFoundError, type OverrideSessionPreferences, type PermissionDeniedError, type PermissionGuard, type Preference, type PreferenceSummary, type Project, type PromptBuilder, type PromptBuilderOptions, type PurgeBlob, type RecordBlobRemoteId, type RegisterBlob, type ReleaseBlob, type ResolvedBlob, type ResolvedSession, type Result, type RetainBlob, type Role, type RoleSummary, type RoleTransitionBlock, type SHA256, Session, SessionManager, type SessionMetadata, type SessionSnapshot, type Settings, type Summarizer, type SummaryBlock, type SwitchSessionRole, type SystemActor, type TextBlock, type ThinkingBlock, type Timestamp, type ToolCall, type ToolCallCommand, type ToolRegistry, type ToolResultBlock, type ToolSummary, type ToolUseBlock, type Topic, type TopicIndex, type Turn, TurnBuilder, type TurnKey, type TurnNode, type TurnProcessor, type TurnRef, TurnTree, type URI, type UUID, type UpdateContext, type UpdatePreference, type UpdateRole, type UpdateSession, type UpdateTopic, type UpdateTurn, type Workspace, type WorkspaceBundle, type WorkspaceContext, type WorkspaceDatabase, type WorkspaceError, type WorkspaceEvents, WorkspaceManager, type WorkspaceMiddleware, type WorkspaceReducer, bufferToBase64, computeSHA256, createWorkspace, createWorkspaceDatabase, del, error, merge, ok, omitNullUndefined, success };
2669
+ export { type AddContext, type AddPreference, type AddRole, type AddSessionTopics, type AddTopic, type AddTurn, type AuthRequest, type BackendError, type BaseCommand, type BaseContentBlock, type BlobCommand, type BlobError, type BlobMediaType, type BlobRecord, type BlobRef, type BlobResolver, type BranchInfo, type BranchTurn, COLLECTIONS, type Collections, type Command, type ContentBlock, type Context, type ContextContent, type ContextRetriever, type ContextSummary, type CreateSession, type CreateWorkspace, type CreateWorkspaceParams, type DeepPartial, type DeleteContext, type DeletePreference, type DeleteRole, type DeleteSession, type DeleteTopic, type DeleteTurn, type DocumentBlock, type DocumentMediaType, type DuplicateKeyError, EMPTY_SYSTEM_ROLE, type EditTurn, type ForkSession, type ImageBlock, type ImageMediaType, type Index, type IndexExtensions, type Indexer, type InvalidCommandError, type LLMAdapter, type LLMAdapterStatic, LRUCache, type MergeTopics, type ModelConstraint, type ModelConstraintMap, type ModelName, type ModelProfile, type ModelRegistry, type NotFoundError, type OverrideSessionPreferences, type PermissionDeniedError, type PermissionGuard, type Preference, type PreferenceSummary, type Project, type PromptBuilder, type PromptBuilderOptions, type PurgeBlob, type RecordBlobRemoteId, type RegisterBlob, type ReleaseBlob, type ResolvedBlob, type ResolvedSession, type Result, type RetainBlob, type Role, type RoleSummary, type RoleTransitionBlock, type SHA256, Session, SessionManager, type SessionMetadata, type SessionSnapshot, type Settings, type Store, type Summarizer, type SummaryBlock, type SwitchSessionRole, type SyncWorkspace, type SystemActor, type TextBlock, type ThinkingBlock, type Timestamp, type ToolCall, type ToolCallCommand, type ToolRegistry, type ToolResultBlock, type ToolSummary, type ToolUseBlock, type Topic, type TopicIndex, type Turn, TurnBuilder, type TurnKey, type TurnNode, type TurnProcessor, type TurnRef, TurnTree, type URI, type UUID, type UpdateContext, type UpdatePreference, type UpdateRole, type UpdateSession, type UpdateTopic, type UpdateTurn, type Workspace, type WorkspaceBundle, type WorkspaceContext, type WorkspaceDatabase, type WorkspaceError, type WorkspaceEvents, type WorkspaceExtension, WorkspaceManager, type WorkspaceMiddleware, type WorkspaceReducer, bufferToBase64, computeSHA256, createWorkspace, createWorkspaceDatabase, del, error, getExtension, merge, ok, omitNullUndefined, shortHash, success };