@korajs/core 0.4.0 → 0.6.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/dist/bindings/index.cjs +105 -0
- package/dist/bindings/index.cjs.map +1 -0
- package/dist/bindings/index.d.cts +101 -0
- package/dist/bindings/index.d.ts +101 -0
- package/dist/bindings/index.js +78 -0
- package/dist/bindings/index.js.map +1 -0
- package/dist/build-scope-map-B1CcncZN.d.cts +33 -0
- package/dist/build-scope-map-BmgAT82h.d.ts +33 -0
- package/dist/{chunk-CFP5YFXC.js → chunk-3VIOZT7D.js} +50 -5
- package/dist/chunk-3VIOZT7D.js.map +1 -0
- package/dist/{events-BMulupSB.d.cts → events-D-FWfFg8.d.cts} +46 -94
- package/dist/{events-BMulupSB.d.ts → events-D-FWfFg8.d.ts} +46 -94
- package/dist/index.cjs +378 -15
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +178 -50
- package/dist/index.d.ts +178 -50
- package/dist/index.js +321 -12
- package/dist/index.js.map +1 -1
- package/dist/internal.cjs +37 -4
- package/dist/internal.cjs.map +1 -1
- package/dist/internal.d.cts +2 -2
- package/dist/internal.d.ts +2 -2
- package/dist/internal.js +1 -1
- package/dist/operation-3-ZJJf3w.d.cts +94 -0
- package/dist/operation-CygOwIjZ.d.ts +94 -0
- package/package.json +12 -1
- package/dist/chunk-CFP5YFXC.js.map +0 -1
package/dist/index.cjs.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/index.ts","../src/types.ts","../src/errors/errors.ts","../src/clock/hlc.ts","../src/identifiers/uuid-v7.ts","../src/operations/content-hash.ts","../src/operations/operation.ts","../src/operations/atomic-ops.ts","../src/state-machine/state-machine.ts","../src/schema/define.ts","../src/schema/sql-gen.ts","../src/schema/types.ts","../src/schema/validation.ts","../src/version-vector/topological-sort.ts","../src/version-vector/version-vector.ts","../src/scopes/build-scope-map.ts","../src/sequences/sequence-format.ts","../src/migrations/migration-builder.ts","../src/migrations/migration-rollback.ts","../src/migrations/migration-sql.ts","../src/codegen/proto-generator.ts"],"sourcesContent":["// @korajs/core — public API\n// Every export here is a public API commitment. Be explicit.\n\n// === Types ===\nexport type {\n\tAtomicOp,\n\tAtomicOpType,\n\tCollectionDefinition,\n\tConnectionQuality,\n\tConstraint,\n\tCustomResolver,\n\tFieldDescriptor,\n\tFieldKind,\n\tFieldMergeStrategy,\n\tHLCTimestamp,\n\tMergeStrategy,\n\tOnDeleteAction,\n\tOperation,\n\tOperationInput,\n\tOperationType,\n\tRandomSource,\n\tRelationDefinition,\n\tRelationType,\n\tSchemaDefinition,\n\tSequenceConfig,\n\tStateMachineConstraint,\n\tStateMachineDefinition,\n\tSyncDiagnosticsSnapshot,\n\tTimeSource,\n\tTransitionMap,\n\tTransitionValidationResult,\n\tVersionVector,\n} from './types'\n\nexport { CONNECTION_QUALITIES, MERGE_STRATEGIES } from './types'\n\n// === Errors ===\nexport {\n\tClockDriftError,\n\tKoraError,\n\tMergeConflictError,\n\tOperationError,\n\tSchemaValidationError,\n\tStorageError,\n\tSyncError,\n} from './errors/errors'\n\n// === Clock ===\nexport { HybridLogicalClock } from './clock/hlc'\n\n// === Identifiers ===\nexport { extractTimestamp, generateUUIDv7, isValidUUIDv7 } from './identifiers/uuid-v7'\n\n// === Operations ===\nexport {\n\tcreateOperation,\n\tisValidOperation,\n\tverifyOperationIntegrity,\n} from './operations/operation'\n\n// === Atomic Operations ===\nexport {\n\tisAtomicOp,\n\top,\n\tresolveAtomicOp,\n\ttoAtomicOp,\n} from './operations/atomic-ops'\nexport type { AtomicOpSentinel } from './operations/atomic-ops'\n\n// === Schema ===\nexport { defineSchema } from './schema/define'\nexport type {\n\tCollectionInput,\n\tConstraintInput,\n\tRelationInput,\n\tSchemaInput,\n\tStateMachineInput,\n\tTypedSchemaDefinition,\n} from './schema/define'\nexport { generateFullDDL, generateSQL } from './schema/sql-gen'\nexport { ArrayFieldBuilder, EnumFieldBuilder, FieldBuilder, t } from './schema/types'\nexport { validateRecord } from './schema/validation'\n\n// === Type Inference ===\nexport type {\n\tFieldKindToType,\n\tInferFieldType,\n\tInferInsertInput,\n\tInferRecord,\n\tInferUpdateInput,\n} from './schema/infer'\n\n// === Version Vectors ===\nexport {\n\tadvanceVector,\n\tcomputeDelta,\n\tcreateVersionVector,\n\tdeserializeVector,\n\tdominates,\n\tmergeVectors,\n\tserializeVector,\n\tvectorsEqual,\n} from './version-vector/version-vector'\nexport type { OperationLog } from './version-vector/version-vector'\n\n// === Scopes ===\nexport { buildScopeMap } from './scopes/build-scope-map'\nexport type { ScopeMap } from './scopes/build-scope-map'\n\n// === Sequences ===\nexport { defaultSequenceFormat, formatSequenceValue } from './sequences/sequence-format'\n\n// === Migrations ===\nexport { MigrationBuilder, RollbackBuilder, migrate } from './migrations/migration-builder'\nexport type { MigrationDefinition, MigrationStep } from './migrations/migration-builder'\nexport { migrationStepsToSQL, rollbackStepsToSQL } from './migrations/migration-sql'\nexport {\n\tMigrationRollbackError,\n\tcanAutoRollback,\n\tcreateReversibleMigration,\n\tgenerateRollbackSteps,\n} from './migrations/migration-rollback'\nexport type { ReversibleMigration } from './migrations/migration-rollback'\n\n// === State Machine ===\nexport {\n\tbuildStateMachineConstraints,\n\tgetTransitionMap,\n\tvalidateTransition,\n} from './state-machine/state-machine'\n\n// === Events ===\nexport type {\n\tKoraEvent,\n\tKoraEventByType,\n\tKoraEventEmitter,\n\tKoraEventListener,\n\tKoraEventType,\n\tMergeTrace,\n} from './events/events'\n\n// === Codegen ===\nexport { generateProtoDefinitions } from './codegen/proto-generator'\nexport type { ProtoOutput } from './codegen/proto-generator'\n","/**\n * Hybrid Logical Clock timestamp.\n * Provides a total order that respects causality without requiring synchronized clocks.\n */\nexport interface HLCTimestamp {\n\t/** Physical wall-clock time in milliseconds */\n\twallTime: number\n\t/** Logical counter. Increments when wallTime hasn't changed since last event. */\n\tlogical: number\n\t/** Node ID for tie-breaking. Ensures total order even with identical wall+logical. */\n\tnodeId: string\n}\n\n/** The three mutation types an operation can represent */\nexport type OperationType = 'insert' | 'update' | 'delete'\n\n/** Supported atomic operation types for intent-preserving field updates */\nexport type AtomicOpType = 'increment' | 'max' | 'min' | 'append' | 'remove'\n\n/**\n * Atomic operation stored in an Operation's atomicOps field.\n * This is the serializable form that persists in the operation log.\n */\nexport interface AtomicOp {\n\treadonly type: AtomicOpType\n\treadonly value: unknown\n}\n\n/**\n * The atomic unit of the entire system. Every mutation produces an Operation.\n * Operations are IMMUTABLE and CONTENT-ADDRESSED.\n */\nexport interface Operation {\n\t/** SHA-256 hash of (type + collection + recordId + data + timestamp + nodeId). Content-addressed. */\n\tid: string\n\t/** UUID v7 of the originating device. Time-sortable. */\n\tnodeId: string\n\t/** What happened */\n\ttype: OperationType\n\t/** Which collection (from schema) */\n\tcollection: string\n\t/** ID of the affected record. UUID v7 for inserts, existing ID for update/delete. */\n\trecordId: string\n\t/** Field values. null for delete. For updates, contains ONLY changed fields. */\n\tdata: Record<string, unknown> | null\n\t/** For updates: previous values of changed fields (enables 3-way merge). null for insert/delete. */\n\tpreviousData: Record<string, unknown> | null\n\t/** Hybrid Logical Clock timestamp. Used for causal ordering. */\n\ttimestamp: HLCTimestamp\n\t/** Monotonically increasing per node. Used in version vectors. */\n\tsequenceNumber: number\n\t/** Operation IDs this operation causally depends on (direct parents in the DAG). */\n\tcausalDeps: string[]\n\t/** Schema version at time of creation. Used for migration transforms. */\n\tschemaVersion: number\n\t/** Atomic operation intents for fields in data (e.g., increment, max). Present only when atomic ops were used. */\n\tatomicOps?: Record<string, AtomicOp>\n\t/** Groups this operation with others in an atomic transaction. Not part of the content hash. */\n\ttransactionId?: string\n\t/** Human-readable name for the mutation group (e.g., 'complete-sale'). For DevTools display. */\n\tmutationName?: string\n}\n\n/**\n * Input for creating an operation (before id and timestamp are assigned).\n */\nexport interface OperationInput {\n\tnodeId: string\n\ttype: OperationType\n\tcollection: string\n\trecordId: string\n\tdata: Record<string, unknown> | null\n\tpreviousData: Record<string, unknown> | null\n\tsequenceNumber: number\n\tcausalDeps: string[]\n\tschemaVersion: number\n\t/** Atomic operation intents for fields in data (e.g., increment, max). */\n\tatomicOps?: Record<string, AtomicOp>\n\t/** Groups this operation with others in an atomic transaction. Not part of the content hash. */\n\ttransactionId?: string\n\t/** Human-readable name for the mutation group (e.g., 'complete-sale'). For DevTools display. */\n\tmutationName?: string\n}\n\n/** Version vector: maps nodeId to the max sequence number seen from that node */\nexport type VersionVector = Map<string, number>\n\n/** Field kinds supported by the schema system */\nexport type FieldKind =\n\t| 'string'\n\t| 'number'\n\t| 'boolean'\n\t| 'timestamp'\n\t| 'richtext'\n\t| 'enum'\n\t| 'array'\n\n/**\n * Comprehensive sync diagnostics snapshot.\n * Provides connection, latency, throughput, queue, and error metrics\n * for monitoring and DevTools integration.\n */\nexport interface SyncDiagnosticsSnapshot {\n\t// Connection\n\t/** Current developer-facing sync status */\n\tstatus: 'connected' | 'syncing' | 'synced' | 'offline' | 'error'\n\t/** Timestamp when the current connection was established, or null if disconnected */\n\tconnectedAt: number | null\n\t/** Timestamp when the last disconnection occurred, or null if never disconnected */\n\tdisconnectedAt: number | null\n\t/** Number of reconnection attempts since last successful connection */\n\treconnectAttempts: number\n\n\t// Latency\n\t/** Current round-trip time in milliseconds */\n\trttMs: number\n\t/** Median (50th percentile) RTT over the sliding window */\n\trttP50Ms: number\n\t/** 95th percentile RTT over the sliding window */\n\trttP95Ms: number\n\t/** 99th percentile RTT over the sliding window */\n\trttP99Ms: number\n\n\t// Throughput\n\t/** Total operations sent during this session */\n\toperationsSent: number\n\t/** Total operations received during this session */\n\toperationsReceived: number\n\t/** Total bytes sent during this session */\n\tbytesSent: number\n\t/** Total bytes received during this session */\n\tbytesReceived: number\n\n\t// Queue\n\t/** Number of operations waiting to be sent */\n\tpendingOperations: number\n\t/** Estimated bytes in the outbound queue */\n\toutboundQueueSize: number\n\n\t// Sync Progress\n\t/** Timestamp of the last successful sync, or null if never synced */\n\tlastSyncedAt: number | null\n\t/** Duration of the last complete sync cycle in ms, or null if no cycle completed */\n\tsyncDuration: number | null\n\t/** Whether the initial sync (full delta exchange) has completed */\n\tinitialSyncComplete: boolean\n\t/** Progress of the initial sync as a 0-1 ratio */\n\tinitialSyncProgress: number\n\n\t// Errors\n\t/** Description of the last error, or null if no error occurred */\n\tlastError: string | null\n\t/** Total number of errors during this session */\n\terrorCount: number\n\n\t// Connection Quality\n\t/** Assessed connection quality level */\n\tquality: 'excellent' | 'good' | 'fair' | 'poor' | 'offline'\n\t/** Estimated effective bandwidth in bytes per second, or null if not yet measured */\n\teffectiveBandwidth: number | null\n}\n\n/** Built-in field merge strategies that can be declared in the schema. */\nexport type FieldMergeStrategy =\n\t| 'lww'\n\t| 'counter'\n\t| 'max'\n\t| 'min'\n\t| 'union'\n\t| 'append-only'\n\t| 'server-authoritative'\n\n/** Map of state to allowed next states for state machine constraints */\nexport type TransitionMap = Record<string, string[]>\n\n/**\n * A state machine constraint extracted from the schema.\n * Used by merge and validation to enforce valid state transitions.\n */\nexport interface StateMachineConstraint {\n\t/** The enum field this constraint controls */\n\tfield: string\n\t/** The collection this constraint applies to */\n\tcollection: string\n\t/** Map of state to allowed next states */\n\ttransitions: TransitionMap\n}\n\n/**\n * Result of validating a state transition.\n */\nexport interface TransitionValidationResult {\n\t/** Whether the transition is allowed */\n\tvalid: boolean\n\t/** The source state */\n\tfrom: string\n\t/** The target state */\n\tto: string\n\t/** The field being transitioned */\n\tfield: string\n\t/** The collection containing the field */\n\tcollection: string\n\t/** All allowed target states from the source state */\n\tallowedTargets: string[]\n}\n\n/**\n * Descriptor produced by the type builder (t.string(), t.number(), etc.).\n * Represents a fully configured field definition.\n */\nexport interface FieldDescriptor {\n\tkind: FieldKind\n\trequired: boolean\n\tdefaultValue: unknown\n\tauto: boolean\n\tenumValues: readonly string[] | null\n\titemKind: FieldKind | null\n\t/** Declared merge strategy. Defaults to kind-appropriate strategy when undefined. */\n\tmergeStrategy: FieldMergeStrategy | null\n\t/** State machine transition map for enum fields. Null if no transitions declared. */\n\ttransitions: TransitionMap | null\n}\n\n/**\n * Defines a state machine on an enum field, constraining valid state transitions.\n *\n * When a state machine is defined on a collection, mutations and merges\n * enforce that the controlled field only moves along declared transitions.\n *\n * @example\n * ```typescript\n * stateMachine: {\n * field: 'status',\n * transitions: {\n * draft: ['pending', 'cancelled'],\n * pending: ['confirmed', 'cancelled'],\n * confirmed: ['shipped'],\n * shipped: ['delivered'],\n * delivered: [],\n * cancelled: [],\n * },\n * onInvalidTransition: 'reject',\n * }\n * ```\n */\nexport interface StateMachineDefinition {\n\t/** The enum field this state machine controls */\n\tfield: string\n\t/** Map of state to allowed next states */\n\ttransitions: Record<string, string[]>\n\t/** What to do when an invalid transition is attempted */\n\tonInvalidTransition: 'reject' | 'last-valid-state'\n}\n\n/**\n * Definition of a collection within the schema.\n */\nexport interface CollectionDefinition {\n\tfields: Record<string, FieldDescriptor>\n\tindexes: string[]\n\tconstraints: Constraint[]\n\tresolvers: Record<string, CustomResolver>\n\t/** Scope fields for sync filtering. Only records matching the client's scope values are synced. */\n\tscope: string[]\n\t/** Optional state machine constraining transitions on an enum field */\n\tstateMachine?: StateMachineDefinition\n}\n\n/** Custom resolver function for tier 3 merge resolution */\nexport type CustomResolver = (local: unknown, remote: unknown, base: unknown) => unknown\n\n/**\n * Constraint for tier 2 conflict resolution.\n */\nexport interface Constraint {\n\ttype: 'unique' | 'capacity' | 'referential'\n\tfields: string[]\n\twhere?: Record<string, unknown>\n\tonConflict:\n\t\t| 'first-write-wins'\n\t\t| 'last-write-wins'\n\t\t| 'priority-field'\n\t\t| 'server-decides'\n\t\t| 'custom'\n\tpriorityField?: string\n\tresolve?: (local: unknown, remote: unknown, base: unknown) => unknown\n}\n\n/** Relation type between collections */\nexport type RelationType = 'one-to-one' | 'one-to-many' | 'many-to-one' | 'many-to-many'\n\n/** On-delete behavior for relations */\nexport type OnDeleteAction = 'cascade' | 'set-null' | 'restrict' | 'no-action'\n\n/**\n * Definition of a relation between two collections.\n */\nexport interface RelationDefinition {\n\tfrom: string\n\tto: string\n\ttype: RelationType\n\tfield: string\n\tonDelete: OnDeleteAction\n}\n\n/**\n * The complete schema definition produced by defineSchema().\n */\nexport interface SchemaDefinition {\n\tversion: number\n\tcollections: Record<string, CollectionDefinition>\n\trelations: Record<string, RelationDefinition>\n\t/** Schema migrations keyed by target version. */\n\tmigrations: Record<number, import('./migrations/migration-builder').MigrationDefinition>\n}\n\n/**\n * Merge strategies available for auto-merge and constraints.\n */\nexport const MERGE_STRATEGIES = [\n\t'auto-merge',\n\t'lww',\n\t'first-write-wins',\n\t'server-decides',\n\t'custom',\n] as const\nexport type MergeStrategy = (typeof MERGE_STRATEGIES)[number]\n\n/**\n * Connection quality levels for adaptive sync.\n */\nexport const CONNECTION_QUALITIES = ['excellent', 'good', 'fair', 'poor', 'offline'] as const\nexport type ConnectionQuality = (typeof CONNECTION_QUALITIES)[number]\n\n/**\n * Injectable time source for deterministic testing of clocks.\n */\nexport interface TimeSource {\n\tnow(): number\n}\n\n/**\n * Injectable random source for deterministic testing of UUID generation.\n */\nexport interface RandomSource {\n\tgetRandomValues<T extends ArrayBufferView>(array: T): T\n}\n\n/**\n * Configuration for an offline-safe sequence.\n *\n * Sequences produce monotonically increasing, collision-free identifiers\n * that work across offline devices. Each device maintains its own counter\n * scoped by (name, scope, nodeId).\n *\n * Format tokens available:\n * - `{date}` → YYYYMMDD\n * - `{node4}` → first 4 chars of nodeId\n * - `{node8}` → first 8 chars of nodeId\n * - `{seq}` → zero-padded counter (4 digits)\n * - `{seq:N}` → zero-padded counter with N digits\n *\n * @example\n * ```typescript\n * await app.sequences.next('receipt', {\n * scope: storeId,\n * format: 'S-{date}-{node4}-{seq}',\n * })\n * // → \"S-20260508-a1b2-0042\"\n * ```\n */\nexport interface SequenceConfig {\n\t/** Namespace within the sequence (e.g., a storeId or orgId). Defaults to ''. */\n\tscope?: string\n\t/** Format template. Defaults to `{name}-{seq:4}`. */\n\tformat?: string\n\t/** Starting counter value. Defaults to 1. */\n\tstartAt?: number\n}\n","/**\n * Base error class for all Kora errors.\n * Every error includes a machine-readable code and optional context for debugging.\n */\nexport class KoraError extends Error {\n\tconstructor(\n\t\tmessage: string,\n\t\tpublic readonly code: string,\n\t\tpublic readonly context?: Record<string, unknown>,\n\t) {\n\t\tsuper(message)\n\t\tthis.name = 'KoraError'\n\t}\n}\n\n/**\n * Thrown when schema validation fails during defineSchema() or at app initialization.\n */\nexport class SchemaValidationError extends KoraError {\n\tconstructor(message: string, context?: Record<string, unknown>) {\n\t\tsuper(message, 'SCHEMA_VALIDATION', context)\n\t\tthis.name = 'SchemaValidationError'\n\t}\n}\n\n/**\n * Thrown when an operation is invalid or cannot be created.\n */\nexport class OperationError extends KoraError {\n\tconstructor(message: string, context?: Record<string, unknown>) {\n\t\tsuper(message, 'OPERATION_ERROR', context)\n\t\tthis.name = 'OperationError'\n\t}\n}\n\n/**\n * Thrown when a merge conflict cannot be automatically resolved.\n */\nexport class MergeConflictError extends KoraError {\n\tconstructor(\n\t\tpublic readonly operationA: { id: string; collection: string },\n\t\tpublic readonly operationB: { id: string; collection: string },\n\t\tpublic readonly field: string,\n\t) {\n\t\tsuper(\n\t\t\t`Merge conflict on field \"${field}\" in collection \"${operationA.collection}\"`,\n\t\t\t'MERGE_CONFLICT',\n\t\t\t{ operationA: operationA.id, operationB: operationB.id, field },\n\t\t)\n\t\tthis.name = 'MergeConflictError'\n\t}\n}\n\n/**\n * Thrown when a sync error occurs.\n */\nexport class SyncError extends KoraError {\n\tconstructor(message: string, context?: Record<string, unknown>) {\n\t\tsuper(message, 'SYNC_ERROR', context)\n\t\tthis.name = 'SyncError'\n\t}\n}\n\n/**\n * Thrown when a storage operation fails.\n */\nexport class StorageError extends KoraError {\n\tconstructor(message: string, context?: Record<string, unknown>) {\n\t\tsuper(message, 'STORAGE_ERROR', context)\n\t\tthis.name = 'StorageError'\n\t}\n}\n\n/**\n * Thrown when the HLC detects excessive clock drift.\n * Drift > 60s: warning. Drift > 5min: this error is thrown, refusing to generate timestamps.\n */\nexport class ClockDriftError extends KoraError {\n\tconstructor(\n\t\tpublic readonly currentHlcTime: number,\n\t\tpublic readonly physicalTime: number,\n\t) {\n\t\tconst driftSeconds = Math.round((currentHlcTime - physicalTime) / 1000)\n\t\tsuper(\n\t\t\t`Clock drift of ${driftSeconds}s detected. Physical time is behind HLC by more than 5 minutes. This indicates a severe clock issue.`,\n\t\t\t'CLOCK_DRIFT',\n\t\t\t{ currentHlcTime, physicalTime, driftSeconds },\n\t\t)\n\t\tthis.name = 'ClockDriftError'\n\t}\n}\n","import { ClockDriftError } from '../errors/errors'\nimport type { HLCTimestamp, TimeSource } from '../types'\n\n/** Default time source using the system clock */\nconst systemTimeSource: TimeSource = { now: () => Date.now() }\n\n/** Maximum allowed drift before warning (60 seconds) */\nconst DRIFT_WARN_MS = 60_000\n\n/** Maximum allowed drift before refusing to generate timestamps (5 minutes) */\nconst DRIFT_ERROR_MS = 5 * 60_000\n\n/**\n * Hybrid Logical Clock implementation based on Kulkarni et al.\n *\n * Provides a total order that respects causality without requiring synchronized clocks.\n * Each call to now() returns a timestamp strictly greater than the previous one.\n *\n * @example\n * ```typescript\n * const clock = new HybridLogicalClock('node-1')\n * const ts1 = clock.now()\n * const ts2 = clock.now()\n * // HybridLogicalClock.compare(ts1, ts2) < 0 (ts1 is earlier)\n * ```\n */\nexport class HybridLogicalClock {\n\tprivate wallTime = 0\n\tprivate logical = 0\n\n\tconstructor(\n\t\tprivate readonly nodeId: string,\n\t\tprivate readonly timeSource: TimeSource = systemTimeSource,\n\t\tprivate readonly onDriftWarning?: (driftMs: number) => void,\n\t) {}\n\n\t/**\n\t * Generate a new timestamp for a local event.\n\t * Guarantees monotonicity: each call returns a timestamp strictly greater than the previous.\n\t *\n\t * @throws {ClockDriftError} If physical time is more than 5 minutes behind the HLC wallTime\n\t */\n\tnow(): HLCTimestamp {\n\t\tconst physicalTime = this.timeSource.now()\n\t\tthis.checkDrift(physicalTime)\n\n\t\tif (physicalTime > this.wallTime) {\n\t\t\tthis.wallTime = physicalTime\n\t\t\tthis.logical = 0\n\t\t} else {\n\t\t\tthis.logical++\n\t\t}\n\n\t\treturn { wallTime: this.wallTime, logical: this.logical, nodeId: this.nodeId }\n\t}\n\n\t/**\n\t * Update clock on receiving a remote timestamp.\n\t * Merges the remote clock state with the local state to maintain causal ordering.\n\t *\n\t * @throws {ClockDriftError} If physical time is more than 5 minutes behind the resulting wallTime\n\t */\n\treceive(remote: HLCTimestamp): HLCTimestamp {\n\t\tconst physicalTime = this.timeSource.now()\n\n\t\tif (physicalTime > this.wallTime && physicalTime > remote.wallTime) {\n\t\t\tthis.wallTime = physicalTime\n\t\t\tthis.logical = 0\n\t\t} else if (remote.wallTime > this.wallTime) {\n\t\t\tthis.wallTime = remote.wallTime\n\t\t\tthis.logical = remote.logical + 1\n\t\t} else if (this.wallTime === remote.wallTime) {\n\t\t\tthis.logical = Math.max(this.logical, remote.logical) + 1\n\t\t} else {\n\t\t\t// this.wallTime > remote.wallTime && this.wallTime >= physicalTime\n\t\t\tthis.logical++\n\t\t}\n\n\t\tthis.checkDrift(physicalTime)\n\n\t\treturn { wallTime: this.wallTime, logical: this.logical, nodeId: this.nodeId }\n\t}\n\n\t/**\n\t * Compare two timestamps. Returns negative if a < b, positive if a > b, zero if equal.\n\t * Total order: wallTime first, then logical, then nodeId (lexicographic).\n\t */\n\tstatic compare(a: HLCTimestamp, b: HLCTimestamp): number {\n\t\tif (a.wallTime !== b.wallTime) return a.wallTime - b.wallTime\n\t\tif (a.logical !== b.logical) return a.logical - b.logical\n\t\tif (a.nodeId < b.nodeId) return -1\n\t\tif (a.nodeId > b.nodeId) return 1\n\t\treturn 0\n\t}\n\n\t/**\n\t * Serialize an HLC timestamp to a string that sorts lexicographically.\n\t * Format: zero-padded wallTime:logical:nodeId\n\t */\n\tstatic serialize(ts: HLCTimestamp): string {\n\t\tconst wall = ts.wallTime.toString().padStart(15, '0')\n\t\tconst log = ts.logical.toString().padStart(5, '0')\n\t\treturn `${wall}:${log}:${ts.nodeId}`\n\t}\n\n\t/**\n\t * Deserialize an HLC timestamp from its serialized string form.\n\t */\n\tstatic deserialize(s: string): HLCTimestamp {\n\t\tconst parts = s.split(':')\n\t\tif (parts.length < 3) {\n\t\t\tthrow new Error(`Invalid HLC timestamp string: \"${s}\"`)\n\t\t}\n\t\treturn {\n\t\t\twallTime: Number.parseInt(parts[0] ?? '0', 10),\n\t\t\tlogical: Number.parseInt(parts[1] ?? '0', 10),\n\t\t\t// nodeId may contain colons, so rejoin remaining parts\n\t\t\tnodeId: parts.slice(2).join(':'),\n\t\t}\n\t}\n\n\tprivate checkDrift(physicalTime: number): void {\n\t\tconst drift = this.wallTime - physicalTime\n\t\tif (drift > DRIFT_ERROR_MS) {\n\t\t\tthrow new ClockDriftError(this.wallTime, physicalTime)\n\t\t}\n\t\tif (drift > DRIFT_WARN_MS) {\n\t\t\tthis.onDriftWarning?.(drift)\n\t\t}\n\t}\n}\n","import type { RandomSource } from '../types'\n\nconst defaultRandom: RandomSource = globalThis.crypto as RandomSource\n\n/**\n * Generates a UUID v7 per RFC 9562.\n * UUID v7 encodes a Unix timestamp in milliseconds in the most significant 48 bits,\n * making UUIDs time-sortable while remaining globally unique.\n *\n * @param timestamp - Unix timestamp in milliseconds (defaults to Date.now())\n * @param randomSource - Injectable random source for deterministic testing\n * @returns A UUID v7 string in standard 8-4-4-4-12 format\n *\n * @example\n * ```typescript\n * const id = generateUUIDv7()\n * // \"018f3a5c-7e00-7123-abcd-1234567890ab\"\n * ```\n */\nexport function generateUUIDv7(\n\ttimestamp: number = Date.now(),\n\trandomSource: RandomSource = defaultRandom,\n): string {\n\tconst bytes = new Uint8Array(16)\n\trandomSource.getRandomValues(bytes)\n\n\t// Encode 48-bit timestamp in bytes 0-5\n\tconst ms = Math.max(0, Math.floor(timestamp))\n\tbytes[0] = (ms / 2 ** 40) & 0xff\n\tbytes[1] = (ms / 2 ** 32) & 0xff\n\tbytes[2] = (ms / 2 ** 24) & 0xff\n\tbytes[3] = (ms / 2 ** 16) & 0xff\n\tbytes[4] = (ms / 2 ** 8) & 0xff\n\tbytes[5] = ms & 0xff\n\n\t// Set version 7 (0111) in bits 48-51\n\tbytes[6] = ((bytes[6] ?? 0) & 0x0f) | 0x70\n\n\t// Set variant 10 in bits 64-65\n\tbytes[8] = ((bytes[8] ?? 0) & 0x3f) | 0x80\n\n\treturn formatUUID(bytes)\n}\n\n/**\n * Extracts the Unix timestamp in milliseconds from a UUID v7.\n *\n * @param uuid - A UUID v7 string\n * @returns The encoded Unix timestamp in milliseconds\n */\nexport function extractTimestamp(uuid: string): number {\n\tconst hex = uuid.replace(/-/g, '')\n\t// First 12 hex chars = 48 bits of timestamp\n\tconst high = Number.parseInt(hex.slice(0, 8), 16)\n\tconst low = Number.parseInt(hex.slice(8, 12), 16)\n\treturn high * 2 ** 16 + low\n}\n\n/**\n * Validates whether a string is a valid UUID v7.\n * Checks format, version (7), and variant (10xx).\n *\n * @param uuid - String to validate\n * @returns true if the string is a valid UUID v7\n */\nexport function isValidUUIDv7(uuid: string): boolean {\n\tif (!/^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/i.test(uuid)) {\n\t\treturn false\n\t}\n\tconst hex = uuid.replace(/-/g, '')\n\t// Version must be 7 (nibble at position 12)\n\tif (hex[12] !== '7') return false\n\t// Variant must be 10xx (nibble at position 16 must be 8, 9, a, or b)\n\tconst variantNibble = Number.parseInt(hex[16] ?? '0', 16)\n\treturn variantNibble >= 0x8 && variantNibble <= 0xb\n}\n\nfunction formatUUID(bytes: Uint8Array): string {\n\tconst hex = Array.from(bytes, (b) => b.toString(16).padStart(2, '0')).join('')\n\treturn `${hex.slice(0, 8)}-${hex.slice(8, 12)}-${hex.slice(12, 16)}-${hex.slice(16, 20)}-${hex.slice(20, 32)}`\n}\n","import type { OperationInput } from '../types'\n\n/**\n * Compute the content-addressed ID for an operation using SHA-256.\n * The same operation content always produces the same hash, ensuring deduplication.\n *\n * @param input - The operation input (without id/timestamp, which are assigned separately)\n * @param timestamp - The HLC timestamp serialized as a string\n * @returns A hex-encoded SHA-256 hash\n */\nexport async function computeOperationId(\n\tinput: OperationInput,\n\ttimestamp: string,\n): Promise<string> {\n\t// Only include atomicOps when present — ensures backward compatibility\n\t// (existing operations without atomicOps produce identical hashes).\n\tconst hashInput: Record<string, unknown> = {\n\t\ttype: input.type,\n\t\tcollection: input.collection,\n\t\trecordId: input.recordId,\n\t\tdata: input.data,\n\t\ttimestamp,\n\t\tnodeId: input.nodeId,\n\t}\n\tif (input.atomicOps !== undefined && Object.keys(input.atomicOps).length > 0) {\n\t\thashInput.atomicOps = input.atomicOps\n\t}\n\tconst canonical = canonicalize(hashInput)\n\tconst encoded = new TextEncoder().encode(canonical)\n\tconst hashBuffer = await globalThis.crypto.subtle.digest('SHA-256', encoded)\n\treturn bufferToHex(hashBuffer)\n}\n\n/**\n * Deterministic JSON serialization with sorted keys.\n * Ensures identical objects always produce identical strings regardless of property insertion order.\n *\n * @param obj - The value to serialize\n * @returns A deterministic JSON string\n */\nexport function canonicalize(obj: unknown): string {\n\tif (obj === null || obj === undefined) {\n\t\treturn JSON.stringify(obj)\n\t}\n\n\tif (typeof obj !== 'object') {\n\t\treturn JSON.stringify(obj)\n\t}\n\n\tif (Array.isArray(obj)) {\n\t\tconst items = obj.map((item) => canonicalize(item))\n\t\treturn `[${items.join(',')}]`\n\t}\n\n\tconst keys = Object.keys(obj as Record<string, unknown>).sort()\n\tconst pairs = keys.map((key) => {\n\t\tconst value = (obj as Record<string, unknown>)[key]\n\t\treturn `${JSON.stringify(key)}:${canonicalize(value)}`\n\t})\n\treturn `{${pairs.join(',')}}`\n}\n\nfunction bufferToHex(buffer: ArrayBuffer): string {\n\tconst bytes = new Uint8Array(buffer)\n\treturn Array.from(bytes, (b) => b.toString(16).padStart(2, '0')).join('')\n}\n","import { HybridLogicalClock } from '../clock/hlc'\nimport { OperationError } from '../errors/errors'\nimport type { HLCTimestamp, Operation, OperationInput } from '../types'\nimport { computeOperationId } from './content-hash'\n\n/**\n * Creates an immutable, content-addressed Operation from the given parameters.\n * The operation is deep-frozen after creation — it cannot be modified.\n *\n * @param input - The operation parameters (without id, which is computed)\n * @param clock - The HLC clock to generate the timestamp\n * @returns A frozen Operation with a content-addressed id\n *\n * @example\n * ```typescript\n * const op = await createOperation({\n * nodeId: 'device-1',\n * type: 'insert',\n * collection: 'todos',\n * recordId: 'rec-1',\n * data: { title: 'Ship it' },\n * previousData: null,\n * sequenceNumber: 1,\n * causalDeps: [],\n * schemaVersion: 1,\n * }, clock)\n * ```\n */\nexport async function createOperation(\n\tinput: OperationInput,\n\tclock: HybridLogicalClock,\n): Promise<Operation> {\n\tvalidateOperationParams(input)\n\n\tconst timestamp = clock.now()\n\tconst serializedTs = HybridLogicalClock.serialize(timestamp)\n\tconst id = await computeOperationId(input, serializedTs)\n\n\tconst operation: Operation = {\n\t\tid,\n\t\tnodeId: input.nodeId,\n\t\ttype: input.type,\n\t\tcollection: input.collection,\n\t\trecordId: input.recordId,\n\t\tdata: input.data ? { ...input.data } : null,\n\t\tpreviousData: input.previousData ? { ...input.previousData } : null,\n\t\ttimestamp,\n\t\tsequenceNumber: input.sequenceNumber,\n\t\tcausalDeps: [...input.causalDeps],\n\t\tschemaVersion: input.schemaVersion,\n\t\t...(input.atomicOps !== undefined && Object.keys(input.atomicOps).length > 0\n\t\t\t? { atomicOps: { ...input.atomicOps } }\n\t\t\t: {}),\n\t\t...(input.transactionId !== undefined ? { transactionId: input.transactionId } : {}),\n\t\t...(input.mutationName !== undefined ? { mutationName: input.mutationName } : {}),\n\t}\n\n\treturn deepFreeze(operation)\n}\n\n/**\n * Validates operation input parameters. Throws OperationError with\n * contextual information on validation failure.\n */\nexport function validateOperationParams(input: OperationInput): void {\n\tif (!input.nodeId || typeof input.nodeId !== 'string') {\n\t\tthrow new OperationError('nodeId is required and must be a non-empty string', {\n\t\t\treceived: input.nodeId,\n\t\t})\n\t}\n\n\tif (!input.type || !['insert', 'update', 'delete'].includes(input.type)) {\n\t\tthrow new OperationError('type must be \"insert\", \"update\", or \"delete\"', {\n\t\t\treceived: input.type,\n\t\t})\n\t}\n\n\tif (!input.collection || typeof input.collection !== 'string') {\n\t\tthrow new OperationError('collection is required and must be a non-empty string', {\n\t\t\treceived: input.collection,\n\t\t})\n\t}\n\n\tif (!input.recordId || typeof input.recordId !== 'string') {\n\t\tthrow new OperationError('recordId is required and must be a non-empty string', {\n\t\t\treceived: input.recordId,\n\t\t})\n\t}\n\n\tif (input.type === 'insert' && input.data === null) {\n\t\tthrow new OperationError('insert operations must include data', {\n\t\t\ttype: input.type,\n\t\t\tcollection: input.collection,\n\t\t})\n\t}\n\n\tif (input.type === 'update' && input.data === null) {\n\t\tthrow new OperationError('update operations must include data with changed fields', {\n\t\t\ttype: input.type,\n\t\t\tcollection: input.collection,\n\t\t})\n\t}\n\n\tif (input.type === 'update' && input.previousData === null) {\n\t\tthrow new OperationError(\n\t\t\t'update operations must include previousData for 3-way merge support',\n\t\t\t{\n\t\t\t\ttype: input.type,\n\t\t\t\tcollection: input.collection,\n\t\t\t},\n\t\t)\n\t}\n\n\tif (input.type === 'delete' && input.data !== null) {\n\t\tthrow new OperationError('delete operations must have null data', {\n\t\t\ttype: input.type,\n\t\t\tcollection: input.collection,\n\t\t})\n\t}\n\n\tif (typeof input.sequenceNumber !== 'number' || input.sequenceNumber < 0) {\n\t\tthrow new OperationError('sequenceNumber must be a non-negative number', {\n\t\t\treceived: input.sequenceNumber,\n\t\t})\n\t}\n\n\tif (!Array.isArray(input.causalDeps)) {\n\t\tthrow new OperationError('causalDeps must be an array of operation IDs', {\n\t\t\treceived: typeof input.causalDeps,\n\t\t})\n\t}\n\n\tif (typeof input.schemaVersion !== 'number' || input.schemaVersion < 1) {\n\t\tthrow new OperationError('schemaVersion must be a positive number', {\n\t\t\treceived: input.schemaVersion,\n\t\t})\n\t}\n}\n\n/**\n * Verify the integrity of an operation by recomputing its content hash.\n * Returns true if the id matches the recomputed hash.\n */\nexport async function verifyOperationIntegrity(op: Operation): Promise<boolean> {\n\tconst input: OperationInput = {\n\t\tnodeId: op.nodeId,\n\t\ttype: op.type,\n\t\tcollection: op.collection,\n\t\trecordId: op.recordId,\n\t\tdata: op.data,\n\t\tpreviousData: op.previousData,\n\t\tsequenceNumber: op.sequenceNumber,\n\t\tcausalDeps: op.causalDeps,\n\t\tschemaVersion: op.schemaVersion,\n\t\t...(op.atomicOps !== undefined ? { atomicOps: op.atomicOps } : {}),\n\t}\n\tconst serializedTs = HybridLogicalClock.serialize(op.timestamp)\n\tconst expectedId = await computeOperationId(input, serializedTs)\n\treturn op.id === expectedId\n}\n\n/**\n * Type guard for Operation interface.\n */\nexport function isValidOperation(value: unknown): value is Operation {\n\tif (typeof value !== 'object' || value === null) return false\n\tconst op = value as Record<string, unknown>\n\treturn (\n\t\ttypeof op.id === 'string' &&\n\t\ttypeof op.nodeId === 'string' &&\n\t\t(op.type === 'insert' || op.type === 'update' || op.type === 'delete') &&\n\t\ttypeof op.collection === 'string' &&\n\t\ttypeof op.recordId === 'string' &&\n\t\ttypeof op.sequenceNumber === 'number' &&\n\t\tArray.isArray(op.causalDeps) &&\n\t\ttypeof op.schemaVersion === 'number' &&\n\t\ttypeof op.timestamp === 'object' &&\n\t\top.timestamp !== null\n\t)\n}\n\nfunction deepFreeze<T>(obj: T): T {\n\tif (typeof obj !== 'object' || obj === null) return obj\n\tObject.freeze(obj)\n\tfor (const value of Object.values(obj)) {\n\t\tif (typeof value === 'object' && value !== null && !Object.isFrozen(value)) {\n\t\t\tdeepFreeze(value)\n\t\t}\n\t}\n\treturn obj\n}\n","/**\n * Atomic field operations for intent-preserving updates.\n *\n * Instead of read-modify-write patterns, developers express intent:\n * ```typescript\n * await app.stock.update(id, { quantity: op.increment(-5) })\n * ```\n *\n * The operation intent is preserved in the Operation for merge:\n * concurrent increments compose (sum of deltas) instead of LWW.\n */\n\nimport type { AtomicOp, AtomicOpType } from '../types'\n\n// Re-export for convenience\nexport type { AtomicOp, AtomicOpType }\n\n/**\n * Sentinel marker for detecting atomic op objects in update data.\n * Uses Symbol.for() so the sentinel survives module boundary crossings.\n */\nconst KORA_ATOMIC_OP = Symbol.for('kora.atomic_op')\n\n/** String key used for the sentinel symbol — exported for internal use */\nexport const KORA_ATOMIC_OP_KEY: typeof KORA_ATOMIC_OP = KORA_ATOMIC_OP\n\n/**\n * Sentinel object returned by op.* helpers.\n * Detected by Collection.update() and resolved to concrete values.\n */\nexport interface AtomicOpSentinel {\n\treadonly [KORA_ATOMIC_OP_KEY]: true\n\treadonly type: AtomicOpType\n\treadonly value: unknown\n}\n\n/**\n * Type guard: checks whether a value is an atomic op sentinel.\n *\n * @param value - Any value to check\n * @returns true if the value is an AtomicOpSentinel\n */\nexport function isAtomicOp(value: unknown): value is AtomicOpSentinel {\n\treturn (\n\t\ttypeof value === 'object' &&\n\t\tvalue !== null &&\n\t\tKORA_ATOMIC_OP in value &&\n\t\t(value as Record<symbol, unknown>)[KORA_ATOMIC_OP] === true\n\t)\n}\n\n/**\n * Resolve an atomic op sentinel against a current value to produce a concrete result.\n *\n * @param currentValue - The current value of the field in the database\n * @param sentinel - The atomic op sentinel from the developer's update call\n * @returns The resolved concrete value\n */\nexport function resolveAtomicOp(currentValue: unknown, sentinel: AtomicOpSentinel): unknown {\n\tswitch (sentinel.type) {\n\t\tcase 'increment': {\n\t\t\tconst current = typeof currentValue === 'number' ? currentValue : 0\n\t\t\tconst operand = sentinel.value as number\n\t\t\treturn current + operand\n\t\t}\n\t\tcase 'max': {\n\t\t\tconst current = typeof currentValue === 'number' ? currentValue : Number.NEGATIVE_INFINITY\n\t\t\treturn Math.max(current, sentinel.value as number)\n\t\t}\n\t\tcase 'min': {\n\t\t\tconst current = typeof currentValue === 'number' ? currentValue : Number.POSITIVE_INFINITY\n\t\t\treturn Math.min(current, sentinel.value as number)\n\t\t}\n\t\tcase 'append': {\n\t\t\tconst current = Array.isArray(currentValue) ? [...currentValue] : []\n\t\t\tcurrent.push(sentinel.value)\n\t\t\treturn current\n\t\t}\n\t\tcase 'remove': {\n\t\t\tif (!Array.isArray(currentValue)) return []\n\t\t\treturn currentValue.filter((item) => item !== sentinel.value)\n\t\t}\n\t}\n}\n\nfunction createSentinel(type: AtomicOpType, value: unknown): AtomicOpSentinel {\n\treturn Object.freeze({\n\t\t[KORA_ATOMIC_OP]: true as const,\n\t\ttype,\n\t\tvalue,\n\t})\n}\n\n/**\n * Atomic operation helpers. Use these in collection.update() calls\n * to express intent-preserving mutations.\n *\n * @example\n * ```typescript\n * import { op } from 'korajs'\n *\n * // Increment a counter (works correctly with concurrent updates)\n * await app.stock.update(id, { quantity: op.increment(-5) })\n *\n * // Keep the maximum value\n * await app.scores.update(id, { highScore: op.max(newScore) })\n *\n * // Append to an array\n * await app.todos.update(id, { tags: op.append('urgent') })\n * ```\n */\nexport const op = {\n\t/**\n\t * Increment a number field by the given amount.\n\t * Concurrent increments compose: the sum of all deltas is applied to the base.\n\t *\n\t * @param n - The amount to increment (use negative values to decrement)\n\t */\n\tincrement(n: number): AtomicOpSentinel {\n\t\treturn createSentinel('increment', n)\n\t},\n\n\t/**\n\t * Decrement a number field by the given amount.\n\t * Syntactic sugar for `op.increment(-n)`.\n\t *\n\t * @param n - The amount to decrement\n\t */\n\tdecrement(n: number): AtomicOpSentinel {\n\t\treturn createSentinel('increment', -n)\n\t},\n\n\t/**\n\t * Set the field to the maximum of the current value and the given value.\n\t * Concurrent max operations take the maximum of all values.\n\t *\n\t * @param n - The value to compare against the current value\n\t */\n\tmax(n: number): AtomicOpSentinel {\n\t\treturn createSentinel('max', n)\n\t},\n\n\t/**\n\t * Set the field to the minimum of the current value and the given value.\n\t * Concurrent min operations take the minimum of all values.\n\t *\n\t * @param n - The value to compare against the current value\n\t */\n\tmin(n: number): AtomicOpSentinel {\n\t\treturn createSentinel('min', n)\n\t},\n\n\t/**\n\t * Append an item to an array field.\n\t * Concurrent appends include all appended items.\n\t *\n\t * @param item - The item to append to the array\n\t */\n\tappend(item: unknown): AtomicOpSentinel {\n\t\treturn createSentinel('append', item)\n\t},\n\n\t/**\n\t * Remove an item from an array field (by value equality).\n\t * Concurrent removes of the same item are idempotent.\n\t *\n\t * @param item - The item to remove from the array\n\t */\n\tremove(item: unknown): AtomicOpSentinel {\n\t\treturn createSentinel('remove', item)\n\t},\n}\n\n/**\n * Extract the serializable AtomicOp from a sentinel (strips the Symbol marker).\n *\n * @param sentinel - The atomic op sentinel\n * @returns A plain object suitable for JSON serialization\n */\nexport function toAtomicOp(sentinel: AtomicOpSentinel): AtomicOp {\n\treturn { type: sentinel.type, value: sentinel.value }\n}\n","import { SchemaValidationError } from '../errors/errors'\nimport type {\n\tFieldDescriptor,\n\tSchemaDefinition,\n\tStateMachineConstraint,\n\tTransitionMap,\n\tTransitionValidationResult,\n} from '../types'\n\n/**\n * Validates whether a transition from one state to another is allowed\n * by the given state machine constraint.\n *\n * @param constraint - The state machine constraint defining allowed transitions\n * @param fromValue - The current state value (before the transition)\n * @param toValue - The target state value (after the transition)\n * @returns A TransitionValidationResult describing whether the transition is valid\n *\n * @example\n * ```typescript\n * const constraint: StateMachineConstraint = {\n * field: 'status',\n * collection: 'orders',\n * transitions: {\n * draft: ['submitted', 'cancelled'],\n * submitted: ['approved'],\n * approved: [],\n * },\n * }\n *\n * const result = validateTransition(constraint, 'draft', 'submitted')\n * // { valid: true, from: 'draft', to: 'submitted', field: 'status',\n * // collection: 'orders', allowedTargets: ['submitted', 'cancelled'] }\n * ```\n */\nexport function validateTransition(\n\tconstraint: StateMachineConstraint,\n\tfromValue: unknown,\n\ttoValue: unknown,\n): TransitionValidationResult {\n\tconst from = String(fromValue)\n\tconst to = String(toValue)\n\tconst allowedTargets = constraint.transitions[from] ?? []\n\n\treturn {\n\t\tvalid: allowedTargets.includes(to),\n\t\tfrom,\n\t\tto,\n\t\tfield: constraint.field,\n\t\tcollection: constraint.collection,\n\t\tallowedTargets,\n\t}\n}\n\n/**\n * Extracts all state machine constraints from a schema definition.\n * Scans every collection for enum fields that have transition rules declared\n * via the `.transitions()` builder method.\n *\n * @param schema - The schema definition to extract constraints from\n * @returns An array of StateMachineConstraint objects, one per enum field with transitions\n *\n * @example\n * ```typescript\n * const schema = defineSchema({\n * version: 1,\n * collections: {\n * orders: {\n * fields: {\n * status: t.enum(['draft', 'submitted']).transitions({\n * draft: ['submitted'],\n * submitted: [],\n * }),\n * },\n * },\n * },\n * })\n *\n * const constraints = buildStateMachineConstraints(schema)\n * // [{ field: 'status', collection: 'orders', transitions: { draft: ['submitted'], submitted: [] } }]\n * ```\n */\nexport function buildStateMachineConstraints(schema: SchemaDefinition): StateMachineConstraint[] {\n\tconst constraints: StateMachineConstraint[] = []\n\n\tfor (const [collectionName, collection] of Object.entries(schema.collections)) {\n\t\tfor (const [fieldName, descriptor] of Object.entries(collection.fields)) {\n\t\t\tif (descriptor.kind === 'enum' && descriptor.transitions !== null) {\n\t\t\t\tconstraints.push({\n\t\t\t\t\tfield: fieldName,\n\t\t\t\t\tcollection: collectionName,\n\t\t\t\t\ttransitions: descriptor.transitions,\n\t\t\t\t})\n\t\t\t}\n\t\t}\n\t}\n\n\treturn constraints\n}\n\n/**\n * Finds the state machine constraint for a specific field in a specific collection,\n * if one exists.\n *\n * @param schema - The schema definition to search\n * @param collection - The collection name\n * @param field - The field name\n * @returns The TransitionMap if the field has transitions declared, or null otherwise\n */\nexport function getTransitionMap(\n\tschema: SchemaDefinition,\n\tcollection: string,\n\tfield: string,\n): TransitionMap | null {\n\tconst collectionDef = schema.collections[collection]\n\tif (!collectionDef) {\n\t\treturn null\n\t}\n\tconst fieldDef = collectionDef.fields[field]\n\tif (!fieldDef || fieldDef.kind !== 'enum') {\n\t\treturn null\n\t}\n\treturn fieldDef.transitions\n}\n\n/**\n * Validates a state machine definition against a collection's fields during schema building.\n * Called by defineSchema() to ensure the state machine is well-formed.\n *\n * @param collectionName - Name of the collection for error messages\n * @param sm - The state machine input definition\n * @param fields - The built field descriptors for the collection\n * @throws {SchemaValidationError} If the state machine definition is invalid\n */\nexport function validateStateMachineDefinition(\n\tcollectionName: string,\n\tsm: { field: string; transitions: Record<string, string[]>; onInvalidTransition: string },\n\tfields: Record<string, FieldDescriptor>,\n): void {\n\tconst fieldDef = fields[sm.field]\n\tif (!fieldDef) {\n\t\tthrow new SchemaValidationError(\n\t\t\t`State machine field \"${sm.field}\" does not exist in collection \"${collectionName}\". Available fields: ${Object.keys(fields).join(', ')}`,\n\t\t\t{ collection: collectionName, field: sm.field },\n\t\t)\n\t}\n\tif (fieldDef.kind !== 'enum') {\n\t\tthrow new SchemaValidationError(\n\t\t\t`State machine field \"${sm.field}\" in collection \"${collectionName}\" must be an enum field, but got \"${fieldDef.kind}\"`,\n\t\t\t{ collection: collectionName, field: sm.field, kind: fieldDef.kind },\n\t\t)\n\t}\n\tconst enumValues = fieldDef.enumValues\n\tif (!enumValues || enumValues.length === 0) {\n\t\tthrow new SchemaValidationError(\n\t\t\t`State machine field \"${sm.field}\" in collection \"${collectionName}\" has no enum values defined`,\n\t\t\t{ collection: collectionName, field: sm.field },\n\t\t)\n\t}\n\tconst validValues = new Set(enumValues)\n\tfor (const [state, targets] of Object.entries(sm.transitions)) {\n\t\tif (!validValues.has(state)) {\n\t\t\tthrow new SchemaValidationError(\n\t\t\t\t`State machine transition source \"${state}\" is not a valid enum value for field \"${sm.field}\" in collection \"${collectionName}\". Valid values: ${[...validValues].join(', ')}`,\n\t\t\t\t{ collection: collectionName, field: sm.field, state },\n\t\t\t)\n\t\t}\n\t\tfor (const target of targets) {\n\t\t\tif (!validValues.has(target)) {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`State machine transition target \"${target}\" is not a valid enum value for field \"${sm.field}\" in collection \"${collectionName}\". Valid values: ${[...validValues].join(', ')}`,\n\t\t\t\t\t{ collection: collectionName, field: sm.field, state, target },\n\t\t\t\t)\n\t\t\t}\n\t\t}\n\t}\n\tif (sm.onInvalidTransition !== 'reject' && sm.onInvalidTransition !== 'last-valid-state') {\n\t\tthrow new SchemaValidationError(\n\t\t\t`State machine onInvalidTransition must be \"reject\" or \"last-valid-state\", got \"${sm.onInvalidTransition}\" in collection \"${collectionName}\"`,\n\t\t\t{ collection: collectionName, onInvalidTransition: sm.onInvalidTransition },\n\t\t)\n\t}\n}\n","import { SchemaValidationError } from '../errors/errors'\nimport type { MigrationDefinition } from '../migrations/migration-builder'\nimport { validateStateMachineDefinition } from '../state-machine/state-machine'\nimport type {\n\tCollectionDefinition,\n\tConstraint,\n\tCustomResolver,\n\tFieldDescriptor,\n\tRelationDefinition,\n\tSchemaDefinition,\n\tStateMachineDefinition,\n} from '../types'\nimport type { FieldBuilder } from './types'\n\n/** Valid collection name pattern: lowercase, alphanumeric + underscore, starting with letter */\nconst COLLECTION_NAME_RE = /^[a-z][a-z0-9_]*$/\n\n/** Valid field name pattern: camelCase allowed (e.g. createdAt, dueDate) */\nconst FIELD_NAME_RE = /^[a-z][a-zA-Z0-9_]*$/\n\n/** Reserved field names that cannot be used in schemas */\nconst RESERVED_FIELDS = new Set(['id', '_created_at', '_updated_at', '_deleted'])\n\n/**\n * Input shape for defineSchema() — what the developer writes.\n */\nexport interface SchemaInput {\n\tversion: number\n\tcollections: Record<string, CollectionInput>\n\trelations?: Record<string, RelationInput>\n\t/** Schema migrations keyed by target version number. */\n\tmigrations?: Record<number, MigrationDefinition>\n}\n\nexport interface StateMachineInput {\n\t/** The enum field this state machine controls */\n\tfield: string\n\t/** Map of state to allowed next states */\n\ttransitions: Record<string, string[]>\n\t/** What to do when an invalid transition is attempted */\n\tonInvalidTransition: 'reject' | 'last-valid-state'\n}\n\nexport interface CollectionInput {\n\t// biome-ignore lint/suspicious/noExplicitAny: Required for TypeScript conditional type inference\n\tfields: Record<string, FieldBuilder<any, any, any>>\n\tindexes?: string[]\n\tconstraints?: ConstraintInput[]\n\tresolve?: Record<string, CustomResolver>\n\t/** Scope fields for sync filtering. Only records matching the client's scope values are synced. */\n\tscope?: string[]\n\t/** State machine definition constraining transitions on an enum field */\n\tstateMachine?: StateMachineInput\n}\n\nexport interface ConstraintInput {\n\ttype: 'unique' | 'capacity' | 'referential'\n\tfields: string[]\n\twhere?: Record<string, unknown>\n\tonConflict:\n\t\t| 'first-write-wins'\n\t\t| 'last-write-wins'\n\t\t| 'priority-field'\n\t\t| 'server-decides'\n\t\t| 'custom'\n\tpriorityField?: string\n\tresolve?: (local: unknown, remote: unknown, base: unknown) => unknown\n}\n\nexport interface RelationInput {\n\tfrom: string\n\tto: string\n\ttype: 'one-to-one' | 'one-to-many' | 'many-to-one' | 'many-to-many'\n\tfield: string\n\tonDelete: 'cascade' | 'set-null' | 'restrict' | 'no-action'\n}\n\n/**\n * Validates and builds a SchemaDefinition from developer input.\n * This is the primary developer-facing function for defining a schema.\n *\n * @param input - The schema definition using type builders\n * @returns A validated SchemaDefinition ready for use by the framework\n * @throws {SchemaValidationError} If the schema is invalid\n *\n * @example\n * ```typescript\n * import { defineSchema, t } from '@korajs/core'\n *\n * const schema = defineSchema({\n * version: 1,\n * collections: {\n * todos: {\n * fields: {\n * title: t.string(),\n * completed: t.boolean().default(false),\n * }\n * }\n * }\n * })\n * ```\n */\n/**\n * Schema definition with a phantom type brand preserving the original input shape.\n * The `__input` property exists only at the type level for inference — no runtime cost.\n */\nexport type TypedSchemaDefinition<T extends SchemaInput = SchemaInput> = SchemaDefinition & {\n\treadonly __input: T\n}\n\nexport function defineSchema<const T extends SchemaInput>(input: T): TypedSchemaDefinition<T> {\n\tvalidateVersion(input.version)\n\n\tconst collections: Record<string, CollectionDefinition> = {}\n\n\tfor (const [name, collectionInput] of Object.entries(input.collections)) {\n\t\tvalidateCollectionName(name)\n\t\tcollections[name] = buildCollection(name, collectionInput)\n\t}\n\n\tif (Object.keys(collections).length === 0) {\n\t\tthrow new SchemaValidationError('Schema must define at least one collection')\n\t}\n\n\tconst relations: Record<string, RelationDefinition> = {}\n\tif (input.relations) {\n\t\tfor (const [name, relationInput] of Object.entries(input.relations)) {\n\t\t\tvalidateRelation(name, relationInput, collections)\n\t\t\trelations[name] = { ...relationInput }\n\t\t}\n\t}\n\n\tconst migrations: Record<number, MigrationDefinition> = {}\n\tif (input.migrations) {\n\t\tfor (const [versionStr, migration] of Object.entries(input.migrations)) {\n\t\t\tconst version = Number(versionStr)\n\t\t\tif (!Number.isInteger(version) || version < 2) {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Migration key \"${versionStr}\" is invalid. Must be an integer >= 2 (version 1 is the initial schema).`,\n\t\t\t\t\t{ version: versionStr },\n\t\t\t\t)\n\t\t\t}\n\t\t\tif (version > input.version) {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Migration version ${version} exceeds schema version ${input.version}. Migrations must target versions <= schema version.`,\n\t\t\t\t\t{ migrationVersion: version, schemaVersion: input.version },\n\t\t\t\t)\n\t\t\t}\n\t\t\tif (!migration.steps || migration.steps.length === 0) {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Migration for version ${version} has no steps. Use migrate() to define at least one step.`,\n\t\t\t\t\t{ version },\n\t\t\t\t)\n\t\t\t}\n\t\t\tmigrations[version] = migration\n\t\t}\n\t}\n\n\treturn { version: input.version, collections, relations, migrations } as TypedSchemaDefinition<T>\n}\n\nfunction validateVersion(version: number): void {\n\tif (typeof version !== 'number' || !Number.isInteger(version) || version < 1) {\n\t\tthrow new SchemaValidationError('Schema version must be a positive integer', {\n\t\t\treceived: version,\n\t\t})\n\t}\n}\n\nfunction validateCollectionName(name: string): void {\n\tif (!COLLECTION_NAME_RE.test(name)) {\n\t\tthrow new SchemaValidationError(\n\t\t\t`Collection name \"${name}\" is invalid. Must be lowercase, start with a letter, and contain only letters, numbers, and underscores.`,\n\t\t\t{ collection: name },\n\t\t)\n\t}\n}\n\nfunction buildCollection(name: string, input: CollectionInput): CollectionDefinition {\n\tconst fields: Record<string, FieldDescriptor> = {}\n\n\tif (!input.fields || Object.keys(input.fields).length === 0) {\n\t\tthrow new SchemaValidationError(`Collection \"${name}\" must define at least one field`, {\n\t\t\tcollection: name,\n\t\t})\n\t}\n\n\tfor (const [fieldName, builder] of Object.entries(input.fields)) {\n\t\tvalidateFieldName(name, fieldName)\n\t\tfields[fieldName] = builder._build()\n\t}\n\n\tconst indexes = input.indexes ?? []\n\tfor (const indexField of indexes) {\n\t\tif (!(indexField in fields)) {\n\t\t\tthrow new SchemaValidationError(\n\t\t\t\t`Index field \"${indexField}\" does not exist in collection \"${name}\". Available fields: ${Object.keys(fields).join(', ')}`,\n\t\t\t\t{ collection: name, field: indexField },\n\t\t\t)\n\t\t}\n\t}\n\n\tconst constraints: Constraint[] = []\n\tif (input.constraints) {\n\t\tfor (const constraintInput of input.constraints) {\n\t\t\tvalidateConstraint(name, constraintInput, fields)\n\t\t\tconstraints.push({ ...constraintInput })\n\t\t}\n\t}\n\n\tconst resolvers: Record<string, CustomResolver> = {}\n\tif (input.resolve) {\n\t\tfor (const [fieldName, resolver] of Object.entries(input.resolve)) {\n\t\t\tif (!(fieldName in fields)) {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Resolver for field \"${fieldName}\" does not exist in collection \"${name}\". Available fields: ${Object.keys(fields).join(', ')}`,\n\t\t\t\t\t{ collection: name, field: fieldName },\n\t\t\t\t)\n\t\t\t}\n\t\t\tif (typeof resolver !== 'function') {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Resolver for field \"${fieldName}\" in collection \"${name}\" must be a function`,\n\t\t\t\t\t{ collection: name, field: fieldName },\n\t\t\t\t)\n\t\t\t}\n\t\t\tresolvers[fieldName] = resolver\n\t\t}\n\t}\n\n\tconst scope: string[] = []\n\tif (input.scope) {\n\t\tfor (const scopeField of input.scope) {\n\t\t\tif (!(scopeField in fields)) {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Scope field \"${scopeField}\" does not exist in collection \"${name}\". Available fields: ${Object.keys(fields).join(', ')}`,\n\t\t\t\t\t{ collection: name, field: scopeField },\n\t\t\t\t)\n\t\t\t}\n\t\t\tscope.push(scopeField)\n\t\t}\n\t}\n\n\tlet stateMachine: StateMachineDefinition | undefined\n\tif (input.stateMachine) {\n\t\tvalidateStateMachineDefinition(name, input.stateMachine, fields)\n\t\tstateMachine = { ...input.stateMachine }\n\t}\n\n\treturn { fields, indexes, constraints, resolvers, scope, stateMachine }\n}\n\nfunction validateFieldName(collection: string, fieldName: string): void {\n\tif (RESERVED_FIELDS.has(fieldName)) {\n\t\tthrow new SchemaValidationError(\n\t\t\t`Field name \"${fieldName}\" is reserved in collection \"${collection}\". Reserved fields: ${[...RESERVED_FIELDS].join(', ')}`,\n\t\t\t{ collection, field: fieldName },\n\t\t)\n\t}\n\tif (!FIELD_NAME_RE.test(fieldName)) {\n\t\tthrow new SchemaValidationError(\n\t\t\t`Field name \"${fieldName}\" in collection \"${collection}\" is invalid. Must start with a lowercase letter and contain only letters, numbers, and underscores.`,\n\t\t\t{ collection, field: fieldName },\n\t\t)\n\t}\n}\n\nfunction validateConstraint(\n\tcollection: string,\n\tconstraint: ConstraintInput,\n\tfields: Record<string, FieldDescriptor>,\n): void {\n\tfor (const field of constraint.fields) {\n\t\tif (!(field in fields)) {\n\t\t\tthrow new SchemaValidationError(\n\t\t\t\t`Constraint references field \"${field}\" which does not exist in collection \"${collection}\". Available fields: ${Object.keys(fields).join(', ')}`,\n\t\t\t\t{ collection, field },\n\t\t\t)\n\t\t}\n\t}\n\n\tif (constraint.onConflict === 'priority-field' && !constraint.priorityField) {\n\t\tthrow new SchemaValidationError(\n\t\t\t`Constraint with \"priority-field\" onConflict strategy in collection \"${collection}\" requires a priorityField`,\n\t\t\t{ collection },\n\t\t)\n\t}\n\n\tif (constraint.onConflict === 'priority-field' && constraint.priorityField) {\n\t\tif (!(constraint.priorityField in fields)) {\n\t\t\tthrow new SchemaValidationError(\n\t\t\t\t`Constraint priorityField \"${constraint.priorityField}\" does not exist in collection \"${collection}\"`,\n\t\t\t\t{ collection, field: constraint.priorityField },\n\t\t\t)\n\t\t}\n\t}\n\n\tif (constraint.onConflict === 'custom' && typeof constraint.resolve !== 'function') {\n\t\tthrow new SchemaValidationError(\n\t\t\t`Constraint with \"custom\" onConflict strategy in collection \"${collection}\" requires a resolve function`,\n\t\t\t{ collection },\n\t\t)\n\t}\n}\n\nfunction validateRelation(\n\tname: string,\n\trelation: RelationInput,\n\tcollections: Record<string, CollectionDefinition>,\n): void {\n\tif (!(relation.from in collections)) {\n\t\tthrow new SchemaValidationError(\n\t\t\t`Relation \"${name}\" references source collection \"${relation.from}\" which does not exist. Available collections: ${Object.keys(collections).join(', ')}`,\n\t\t\t{ relation: name, collection: relation.from },\n\t\t)\n\t}\n\n\tif (!(relation.to in collections)) {\n\t\tthrow new SchemaValidationError(\n\t\t\t`Relation \"${name}\" references target collection \"${relation.to}\" which does not exist. Available collections: ${Object.keys(collections).join(', ')}`,\n\t\t\t{ relation: name, collection: relation.to },\n\t\t)\n\t}\n\n\tconst fromCollection = collections[relation.from]\n\tif (fromCollection && !(relation.field in fromCollection.fields)) {\n\t\tthrow new SchemaValidationError(\n\t\t\t`Relation \"${name}\" references field \"${relation.field}\" which does not exist in collection \"${relation.from}\". Available fields: ${Object.keys(fromCollection.fields).join(', ')}`,\n\t\t\t{ relation: name, collection: relation.from, field: relation.field },\n\t\t)\n\t}\n}\n","import type {\n\tCollectionDefinition,\n\tFieldDescriptor,\n\tRelationDefinition,\n\tSchemaDefinition,\n} from '../types'\n\n/**\n * Generate CREATE TABLE and CREATE INDEX SQL for a single collection.\n *\n * @param collectionName - The collection name\n * @param collection - The collection definition\n * @param relations - Optional relations for FK references\n * @returns An array of SQL statements (CREATE TABLE + CREATE INDEX)\n */\nexport function generateSQL(\n\tcollectionName: string,\n\tcollection: CollectionDefinition,\n\trelations?: Record<string, RelationDefinition>,\n): string[] {\n\tconst statements: string[] = []\n\tconst columns: string[] = ['id TEXT PRIMARY KEY NOT NULL']\n\n\t// Track which fields already have indexes\n\tconst indexedFields = new Set(collection.indexes)\n\n\t// Collect FK fields for auto-indexing\n\tconst fkFields: string[] = []\n\n\tfor (const [fieldName, descriptor] of Object.entries(collection.fields)) {\n\t\tlet colDef = columnDefinition(fieldName, descriptor)\n\n\t\t// Add FK reference if a relation exists for this field\n\t\tif (relations) {\n\t\t\tfor (const rel of Object.values(relations)) {\n\t\t\t\tif (rel.from === collectionName && rel.field === fieldName) {\n\t\t\t\t\tcolDef += ` REFERENCES ${rel.to}(id)`\n\t\t\t\t\tfkFields.push(fieldName)\n\t\t\t\t\tbreak\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tcolumns.push(colDef)\n\t}\n\n\t// Auto metadata columns\n\tcolumns.push('_created_at INTEGER NOT NULL')\n\tcolumns.push('_updated_at INTEGER NOT NULL')\n\tcolumns.push('_deleted INTEGER NOT NULL DEFAULT 0')\n\n\tstatements.push(`CREATE TABLE IF NOT EXISTS ${collectionName} (\\n ${columns.join(',\\n ')}\\n)`)\n\n\t// Add ALTER TABLE statements so new columns are added to existing tables.\n\t// These are tagged with --kora:safe-alter so the runtime can ignore \"duplicate column\" errors.\n\tfor (const [fieldName, descriptor] of Object.entries(collection.fields)) {\n\t\tconst colDef = columnDefinition(fieldName, descriptor)\n\t\tstatements.push(`--kora:safe-alter\\nALTER TABLE ${collectionName} ADD COLUMN ${colDef}`)\n\t}\n\n\t// Create indexes\n\tfor (const indexField of collection.indexes) {\n\t\tstatements.push(\n\t\t\t`CREATE INDEX IF NOT EXISTS idx_${collectionName}_${indexField} ON ${collectionName} (${indexField})`,\n\t\t)\n\t}\n\n\t// Auto-create indexes on FK columns not already indexed\n\tfor (const fkField of fkFields) {\n\t\tif (!indexedFields.has(fkField)) {\n\t\t\tstatements.push(\n\t\t\t\t`CREATE INDEX IF NOT EXISTS idx_${collectionName}_${fkField} ON ${collectionName} (${fkField})`,\n\t\t\t)\n\t\t}\n\t}\n\n\t// Per-collection operations log table\n\tstatements.push(\n\t\t`CREATE TABLE IF NOT EXISTS _kora_ops_${collectionName} (\n id TEXT PRIMARY KEY NOT NULL,\n node_id TEXT NOT NULL,\n type TEXT NOT NULL,\n record_id TEXT NOT NULL,\n data TEXT,\n previous_data TEXT,\n timestamp TEXT NOT NULL,\n sequence_number INTEGER NOT NULL,\n causal_deps TEXT NOT NULL,\n schema_version INTEGER NOT NULL\n)`,\n\t)\n\n\treturn statements\n}\n\n/**\n * Generate the full DDL for all collections plus metadata tables.\n *\n * @param schema - The complete schema definition\n * @returns An array of all SQL statements needed to initialize the database\n */\nexport function generateFullDDL(schema: SchemaDefinition): string[] {\n\tconst statements: string[] = []\n\n\t// Metadata table\n\tstatements.push(\n\t\t'CREATE TABLE IF NOT EXISTS _kora_meta (\\n' +\n\t\t\t' key TEXT PRIMARY KEY NOT NULL,\\n' +\n\t\t\t' value TEXT NOT NULL\\n' +\n\t\t\t')',\n\t)\n\n\t// Version vector table\n\tstatements.push(\n\t\t'CREATE TABLE IF NOT EXISTS _kora_version_vector (\\n' +\n\t\t\t' node_id TEXT PRIMARY KEY NOT NULL,\\n' +\n\t\t\t' sequence_number INTEGER NOT NULL\\n' +\n\t\t\t')',\n\t)\n\n\t// Sequence counters table (offline-safe sequences)\n\tstatements.push(\n\t\t'CREATE TABLE IF NOT EXISTS _kora_sequences (\\n' +\n\t\t\t' name TEXT NOT NULL,\\n' +\n\t\t\t\" scope TEXT NOT NULL DEFAULT '',\\n\" +\n\t\t\t' node_id TEXT NOT NULL,\\n' +\n\t\t\t' counter INTEGER NOT NULL DEFAULT 0,\\n' +\n\t\t\t' PRIMARY KEY (name, scope, node_id)\\n' +\n\t\t\t')',\n\t)\n\n\tfor (const [name, collection] of Object.entries(schema.collections)) {\n\t\tstatements.push(...generateSQL(name, collection, schema.relations))\n\t}\n\n\treturn statements\n}\n\nfunction columnDefinition(fieldName: string, descriptor: FieldDescriptor): string {\n\tconst sqlType = mapFieldType(descriptor)\n\tconst parts = [fieldName, sqlType]\n\n\tif (descriptor.required && descriptor.defaultValue === undefined && !descriptor.auto) {\n\t\tparts.push('NOT NULL')\n\t}\n\n\tif (descriptor.defaultValue !== undefined) {\n\t\tparts.push(`DEFAULT ${sqlDefault(descriptor.defaultValue)}`)\n\t}\n\n\t// CHECK constraint for enum fields\n\tif (descriptor.kind === 'enum' && descriptor.enumValues) {\n\t\tconst values = descriptor.enumValues.map((v) => `'${v}'`).join(', ')\n\t\tparts.push(`CHECK (${fieldName} IN (${values}))`)\n\t}\n\n\treturn parts.join(' ')\n}\n\nfunction mapFieldType(descriptor: FieldDescriptor): string {\n\tswitch (descriptor.kind) {\n\t\tcase 'string':\n\t\t\treturn 'TEXT'\n\t\tcase 'number':\n\t\t\treturn 'REAL'\n\t\tcase 'boolean':\n\t\t\treturn 'INTEGER'\n\t\tcase 'enum':\n\t\t\treturn 'TEXT'\n\t\tcase 'timestamp':\n\t\t\treturn 'INTEGER'\n\t\tcase 'array':\n\t\t\treturn 'TEXT' // JSON-serialized\n\t\tcase 'richtext':\n\t\t\treturn 'BLOB' // Yjs state\n\t}\n}\n\nfunction sqlDefault(value: unknown): string {\n\tif (value === null) return 'NULL'\n\tif (typeof value === 'string') return `'${value}'`\n\tif (typeof value === 'number') return String(value)\n\tif (typeof value === 'boolean') return value ? '1' : '0'\n\t// Arrays and objects are stored as JSON strings\n\treturn `'${JSON.stringify(value)}'`\n}\n","import { SchemaValidationError } from '../errors/errors'\nimport type { FieldDescriptor, FieldKind, FieldMergeStrategy, TransitionMap } from '../types'\n\n/**\n * Base field builder implementing the builder pattern for schema field definitions.\n * Each builder is immutable — modifier methods return new builder instances.\n *\n * Type parameters track field metadata at the type level for inference:\n * - Kind: the field kind ('string', 'number', etc.)\n * - Req: whether the field is required (true = required on insert)\n * - Auto: whether the field is auto-populated (true = excluded from insert input)\n *\n * @example\n * ```typescript\n * t.string() // required string field\n * t.string().optional() // optional string field\n * t.string().default('hello') // string with default value\n * t.timestamp().auto() // auto-populated timestamp\n * ```\n */\nexport class FieldBuilder<\n\tKind extends FieldKind = FieldKind,\n\tReq extends boolean = true,\n\tAuto extends boolean = false,\n> {\n\tprotected readonly _kind: Kind\n\tprotected readonly _required: boolean\n\tprotected readonly _defaultValue: unknown\n\tprotected readonly _auto: boolean\n\tprotected readonly _mergeStrategy: FieldMergeStrategy | null\n\n\tconstructor(\n\t\tkind: Kind,\n\t\trequired = true as unknown as Req,\n\t\tdefaultValue: unknown = undefined,\n\t\tauto = false as unknown as Auto,\n\t\tmergeStrategy: FieldMergeStrategy | null = null,\n\t) {\n\t\tthis._kind = kind\n\t\tthis._required = required as unknown as boolean\n\t\tthis._defaultValue = defaultValue\n\t\tthis._auto = auto as unknown as boolean\n\t\tthis._mergeStrategy = mergeStrategy\n\t}\n\n\t/** Mark this field as optional (not required on insert) */\n\toptional(): FieldBuilder<Kind, false, Auto> {\n\t\treturn new FieldBuilder(this._kind, false, this._defaultValue, this._auto, this._mergeStrategy)\n\t}\n\n\t/** Set a default value for this field. Implicitly makes the field optional. */\n\tdefault(value: unknown): FieldBuilder<Kind, false, Auto> {\n\t\treturn new FieldBuilder(this._kind, false, value, this._auto, this._mergeStrategy)\n\t}\n\n\t/** Mark this field as auto-populated (e.g., createdAt timestamps). Developers cannot set auto fields. */\n\tauto(): FieldBuilder<Kind, false, true> {\n\t\treturn new FieldBuilder(this._kind, false, undefined, true, this._mergeStrategy)\n\t}\n\n\t/**\n\t * Declare a merge strategy for this field.\n\t * Controls how concurrent modifications are resolved during sync.\n\t *\n\t * @param strategy - The merge strategy to use:\n\t * - `'lww'`: Last-write-wins (default for scalar fields)\n\t * - `'counter'`: Sum of deltas from base (for numbers)\n\t * - `'max'`: Keep the maximum value (for numbers/timestamps)\n\t * - `'min'`: Keep the minimum value (for numbers/timestamps)\n\t * - `'union'`: Set-union merge (default for arrays)\n\t * - `'append-only'`: Concatenate additions (for arrays)\n\t * - `'server-authoritative'`: Always prefer the remote/server value\n\t */\n\tmerge(strategy: FieldMergeStrategy): FieldBuilder<Kind, Req, Auto> {\n\t\treturn new FieldBuilder(\n\t\t\tthis._kind,\n\t\t\tthis._required as unknown as Req,\n\t\t\tthis._defaultValue,\n\t\t\tthis._auto as unknown as Auto,\n\t\t\tstrategy,\n\t\t)\n\t}\n\n\t/** @internal Build the final FieldDescriptor. Used by defineSchema(). */\n\t_build(): FieldDescriptor {\n\t\treturn {\n\t\t\tkind: this._kind,\n\t\t\trequired: this._required as unknown as boolean,\n\t\t\tdefaultValue: this._defaultValue,\n\t\t\tauto: this._auto as unknown as boolean,\n\t\t\tenumValues: null,\n\t\t\titemKind: null,\n\t\t\tmergeStrategy: this._mergeStrategy,\n\t\t\ttransitions: null,\n\t\t}\n\t}\n}\n\n/**\n * Field builder for enum fields with constrained string values.\n * Preserves the literal enum tuple type for inference.\n */\nexport class EnumFieldBuilder<\n\tValues extends readonly string[] = readonly string[],\n\tReq extends boolean = true,\n\tAuto extends boolean = false,\n> extends FieldBuilder<'enum', Req, Auto> {\n\tprivate readonly _enumValues: Values\n\tprivate readonly _transitions: TransitionMap | null\n\n\tconstructor(\n\t\tvalues: Values,\n\t\trequired = true as unknown as Req,\n\t\tdefaultValue: unknown = undefined,\n\t\tauto = false as unknown as Auto,\n\t\tmergeStrategy: FieldMergeStrategy | null = null,\n\t\ttransitions: TransitionMap | null = null,\n\t) {\n\t\tsuper('enum', required, defaultValue, auto, mergeStrategy)\n\t\tthis._enumValues = values\n\t\tthis._transitions = transitions\n\t}\n\n\toverride optional(): EnumFieldBuilder<Values, false, Auto> {\n\t\treturn new EnumFieldBuilder(\n\t\t\tthis._enumValues,\n\t\t\tfalse,\n\t\t\tthis._defaultValue,\n\t\t\tthis._auto,\n\t\t\tthis._mergeStrategy,\n\t\t\tthis._transitions,\n\t\t)\n\t}\n\n\toverride default(value: Values[number]): EnumFieldBuilder<Values, false, Auto> {\n\t\treturn new EnumFieldBuilder(this._enumValues, false, value, this._auto, this._mergeStrategy, this._transitions)\n\t}\n\n\toverride auto(): EnumFieldBuilder<Values, false, true> {\n\t\treturn new EnumFieldBuilder(this._enumValues, false, undefined, true, this._mergeStrategy, this._transitions)\n\t}\n\n\toverride merge(strategy: FieldMergeStrategy): EnumFieldBuilder<Values, Req, Auto> {\n\t\treturn new EnumFieldBuilder(\n\t\t\tthis._enumValues,\n\t\t\tthis._required as unknown as Req,\n\t\t\tthis._defaultValue,\n\t\t\tthis._auto as unknown as Auto,\n\t\t\tstrategy,\n\t\t\tthis._transitions,\n\t\t)\n\t}\n\n\t/**\n\t * Declare allowed state transitions for this enum field.\n\t * Enables state machine validation during mutations and merges.\n\t *\n\t * @param map - Map of state to allowed next states\n\t *\n\t * @example\n\t * ```typescript\n\t * t.enum(['draft', 'pending', 'confirmed', 'cancelled']).transitions({\n\t * draft: ['pending', 'cancelled'],\n\t * pending: ['confirmed', 'cancelled'],\n\t * confirmed: [],\n\t * cancelled: [],\n\t * })\n\t * ```\n\t */\n\ttransitions(map: Record<Values[number], Values[number][]>): EnumFieldBuilder<Values, Req, Auto> {\n\t\t// Validate that all source and target states are valid enum values\n\t\tconst validValues = new Set(this._enumValues as readonly string[])\n\t\tfor (const [state, targets] of Object.entries(map)) {\n\t\t\tif (!validValues.has(state)) {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Invalid source state \"${state}\" in transition map. Valid values: ${[...validValues].join(', ')}`,\n\t\t\t\t\t{ state, validValues: [...validValues] },\n\t\t\t\t)\n\t\t\t}\n\t\t\tfor (const target of targets as string[]) {\n\t\t\t\tif (!validValues.has(target)) {\n\t\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t\t`Invalid target state \"${target}\" in transition from \"${state}\". Valid values: ${[...validValues].join(', ')}`,\n\t\t\t\t\t\t{ state, target, validValues: [...validValues] },\n\t\t\t\t\t)\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn new EnumFieldBuilder(\n\t\t\tthis._enumValues,\n\t\t\tthis._required as unknown as Req,\n\t\t\tthis._defaultValue,\n\t\t\tthis._auto as unknown as Auto,\n\t\t\tthis._mergeStrategy,\n\t\t\tmap as TransitionMap,\n\t\t)\n\t}\n\n\toverride _build(): FieldDescriptor {\n\t\treturn {\n\t\t\tkind: 'enum',\n\t\t\trequired: this._required as unknown as boolean,\n\t\t\tdefaultValue: this._defaultValue,\n\t\t\tauto: this._auto as unknown as boolean,\n\t\t\tenumValues: this._enumValues,\n\t\t\titemKind: null,\n\t\t\tmergeStrategy: this._mergeStrategy,\n\t\t\ttransitions: this._transitions,\n\t\t}\n\t}\n}\n\n/**\n * Field builder for array fields with a typed item kind.\n * Preserves the item kind type parameter for inference.\n */\nexport class ArrayFieldBuilder<\n\tItemKind extends FieldKind = FieldKind,\n\tReq extends boolean = true,\n\tAuto extends boolean = false,\n> extends FieldBuilder<'array', Req, Auto> {\n\tprivate readonly _itemKind: ItemKind\n\n\tconstructor(\n\t\titemBuilder: FieldBuilder<ItemKind>,\n\t\trequired = true as unknown as Req,\n\t\tdefaultValue: unknown = undefined,\n\t\tauto = false as unknown as Auto,\n\t\tmergeStrategy: FieldMergeStrategy | null = null,\n\t) {\n\t\tsuper('array', required, defaultValue, auto, mergeStrategy)\n\t\tthis._itemKind = itemBuilder._build().kind as ItemKind\n\t}\n\n\toverride optional(): ArrayFieldBuilder<ItemKind, false, Auto> {\n\t\treturn new ArrayFieldBuilder(\n\t\t\tnew FieldBuilder(this._itemKind),\n\t\t\tfalse,\n\t\t\tthis._defaultValue,\n\t\t\tthis._auto,\n\t\t\tthis._mergeStrategy,\n\t\t)\n\t}\n\n\toverride default(value: unknown[]): ArrayFieldBuilder<ItemKind, false, Auto> {\n\t\treturn new ArrayFieldBuilder(\n\t\t\tnew FieldBuilder(this._itemKind),\n\t\t\tfalse,\n\t\t\tvalue,\n\t\t\tthis._auto,\n\t\t\tthis._mergeStrategy,\n\t\t)\n\t}\n\n\toverride auto(): ArrayFieldBuilder<ItemKind, false, true> {\n\t\treturn new ArrayFieldBuilder(\n\t\t\tnew FieldBuilder(this._itemKind),\n\t\t\tfalse,\n\t\t\tundefined,\n\t\t\ttrue,\n\t\t\tthis._mergeStrategy,\n\t\t)\n\t}\n\n\toverride merge(strategy: FieldMergeStrategy): ArrayFieldBuilder<ItemKind, Req, Auto> {\n\t\treturn new ArrayFieldBuilder(\n\t\t\tnew FieldBuilder(this._itemKind),\n\t\t\tthis._required as unknown as Req,\n\t\t\tthis._defaultValue,\n\t\t\tthis._auto as unknown as Auto,\n\t\t\tstrategy,\n\t\t)\n\t}\n\n\toverride _build(): FieldDescriptor {\n\t\treturn {\n\t\t\tkind: 'array',\n\t\t\trequired: this._required as unknown as boolean,\n\t\t\tdefaultValue: this._defaultValue,\n\t\t\tauto: this._auto as unknown as boolean,\n\t\t\tenumValues: null,\n\t\t\titemKind: this._itemKind,\n\t\t\tmergeStrategy: this._mergeStrategy,\n\t\t\ttransitions: null,\n\t\t}\n\t}\n}\n\n/**\n * Type builder namespace. The developer's primary interface for defining field types.\n *\n * @example\n * ```typescript\n * import { t } from '@korajs/core'\n *\n * const fields = {\n * title: t.string(),\n * count: t.number(),\n * active: t.boolean().default(true),\n * notes: t.richtext(),\n * tags: t.array(t.string()).default([]),\n * priority: t.enum(['low', 'medium', 'high']).default('medium'),\n * createdAt: t.timestamp().auto(),\n * }\n * ```\n */\nexport const t = {\n\tstring(): FieldBuilder<'string', true, false> {\n\t\treturn new FieldBuilder('string', true, undefined, false)\n\t},\n\n\tnumber(): FieldBuilder<'number', true, false> {\n\t\treturn new FieldBuilder('number', true, undefined, false)\n\t},\n\n\tboolean(): FieldBuilder<'boolean', true, false> {\n\t\treturn new FieldBuilder('boolean', true, undefined, false)\n\t},\n\n\ttimestamp(): FieldBuilder<'timestamp', true, false> {\n\t\treturn new FieldBuilder('timestamp', true, undefined, false)\n\t},\n\n\trichtext(): FieldBuilder<'richtext', true, false> {\n\t\treturn new FieldBuilder('richtext', true, undefined, false)\n\t},\n\n\tenum<const V extends readonly string[]>(values: V): EnumFieldBuilder<V, true, false> {\n\t\treturn new EnumFieldBuilder(values, true, undefined, false)\n\t},\n\n\tarray<K extends FieldKind>(itemBuilder: FieldBuilder<K>): ArrayFieldBuilder<K, true, false> {\n\t\treturn new ArrayFieldBuilder(itemBuilder, true, undefined, false)\n\t},\n}\n","import { SchemaValidationError } from '../errors/errors'\nimport { isAtomicOp } from '../operations/atomic-ops'\nimport type { CollectionDefinition, FieldDescriptor, OperationType } from '../types'\n\n/**\n * Validates a record's data against a collection's field definitions.\n * Applies defaults, rejects auto fields, and type-checks each value.\n *\n * @param collection - The collection name (for error messages)\n * @param collectionDef - The collection definition from the schema\n * @param data - The record data to validate\n * @param operationType - The operation type ('insert', 'update', 'delete')\n * @returns The validated and normalized data (with defaults applied)\n * @throws {SchemaValidationError} If validation fails\n */\nexport function validateRecord(\n\tcollection: string,\n\tcollectionDef: CollectionDefinition,\n\tdata: Record<string, unknown>,\n\toperationType: OperationType,\n): Record<string, unknown> {\n\tif (operationType === 'delete') {\n\t\treturn {}\n\t}\n\n\tconst result: Record<string, unknown> = {}\n\tconst fieldNames = Object.keys(collectionDef.fields)\n\n\t// Check for extra fields not in the schema\n\tfor (const key of Object.keys(data)) {\n\t\tif (!(key in collectionDef.fields)) {\n\t\t\tthrow new SchemaValidationError(\n\t\t\t\t`Unknown field \"${key}\" in collection \"${collection}\". Available fields: ${fieldNames.join(', ')}`,\n\t\t\t\t{ collection, field: key },\n\t\t\t)\n\t\t}\n\t}\n\n\tfor (const [fieldName, descriptor] of Object.entries(collectionDef.fields)) {\n\t\tconst value = data[fieldName]\n\t\tconst hasValue = fieldName in data\n\n\t\t// Auto fields cannot be set by the developer\n\t\tif (descriptor.auto && hasValue) {\n\t\t\tthrow new SchemaValidationError(\n\t\t\t\t`Field \"${fieldName}\" in collection \"${collection}\" is auto-populated and cannot be set manually`,\n\t\t\t\t{ collection, field: fieldName },\n\t\t\t)\n\t\t}\n\n\t\t// For updates, only validate fields that are present (partial updates)\n\t\tif (operationType === 'update') {\n\t\t\tif (hasValue) {\n\t\t\t\t// Atomic op sentinels pass through validation — they are resolved\n\t\t\t\t// to concrete values by Collection.update() before the Operation is created.\n\t\t\t\tif (isAtomicOp(value)) {\n\t\t\t\t\tresult[fieldName] = value\n\t\t\t\t} else if (value !== undefined && value !== null) {\n\t\t\t\t\tvalidateFieldValue(collection, fieldName, descriptor, value)\n\t\t\t\t\tresult[fieldName] = value\n\t\t\t\t} else {\n\t\t\t\t\tresult[fieldName] = value\n\t\t\t\t}\n\t\t\t}\n\t\t\tcontinue\n\t\t}\n\n\t\t// For inserts, apply defaults and check required fields\n\t\tif (descriptor.auto) {\n\t\t\t// Skip auto fields — they are populated by the framework\n\t\t\tcontinue\n\t\t}\n\n\t\tif (!hasValue || value === undefined) {\n\t\t\tif (descriptor.defaultValue !== undefined) {\n\t\t\t\t// Deep-copy default arrays/objects to prevent shared mutations\n\t\t\t\tresult[fieldName] =\n\t\t\t\t\ttypeof descriptor.defaultValue === 'object' && descriptor.defaultValue !== null\n\t\t\t\t\t\t? JSON.parse(JSON.stringify(descriptor.defaultValue))\n\t\t\t\t\t\t: descriptor.defaultValue\n\t\t\t\tcontinue\n\t\t\t}\n\n\t\t\tif (descriptor.required) {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Required field \"${fieldName}\" is missing in collection \"${collection}\"`,\n\t\t\t\t\t{ collection, field: fieldName },\n\t\t\t\t)\n\t\t\t}\n\n\t\t\t// Optional field with no default — omit from result\n\t\t\tcontinue\n\t\t}\n\n\t\tvalidateFieldValue(collection, fieldName, descriptor, value)\n\t\tresult[fieldName] = value\n\t}\n\n\treturn result\n}\n\nfunction validateFieldValue(\n\tcollection: string,\n\tfieldName: string,\n\tdescriptor: FieldDescriptor,\n\tvalue: unknown,\n): void {\n\tswitch (descriptor.kind) {\n\t\tcase 'string': {\n\t\t\tif (typeof value !== 'string') {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Field \"${fieldName}\" in collection \"${collection}\" must be a string, got ${typeof value}`,\n\t\t\t\t\t{ collection, field: fieldName, expectedType: 'string', receivedType: typeof value },\n\t\t\t\t)\n\t\t\t}\n\t\t\tbreak\n\t\t}\n\n\t\tcase 'number': {\n\t\t\tif (typeof value !== 'number' || Number.isNaN(value)) {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Field \"${fieldName}\" in collection \"${collection}\" must be a number, got ${typeof value}`,\n\t\t\t\t\t{ collection, field: fieldName, expectedType: 'number', receivedType: typeof value },\n\t\t\t\t)\n\t\t\t}\n\t\t\tbreak\n\t\t}\n\n\t\tcase 'boolean': {\n\t\t\tif (typeof value !== 'boolean') {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Field \"${fieldName}\" in collection \"${collection}\" must be a boolean, got ${typeof value}`,\n\t\t\t\t\t{ collection, field: fieldName, expectedType: 'boolean', receivedType: typeof value },\n\t\t\t\t)\n\t\t\t}\n\t\t\tbreak\n\t\t}\n\n\t\tcase 'timestamp': {\n\t\t\tif (typeof value !== 'number' || !Number.isFinite(value)) {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Field \"${fieldName}\" in collection \"${collection}\" must be a timestamp (number), got ${typeof value}`,\n\t\t\t\t\t{\n\t\t\t\t\t\tcollection,\n\t\t\t\t\t\tfield: fieldName,\n\t\t\t\t\t\texpectedType: 'timestamp',\n\t\t\t\t\t\treceivedType: typeof value,\n\t\t\t\t\t},\n\t\t\t\t)\n\t\t\t}\n\t\t\tbreak\n\t\t}\n\n\t\tcase 'enum': {\n\t\t\tif (typeof value !== 'string') {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Field \"${fieldName}\" in collection \"${collection}\" must be a string (enum), got ${typeof value}`,\n\t\t\t\t\t{ collection, field: fieldName, expectedType: 'enum', receivedType: typeof value },\n\t\t\t\t)\n\t\t\t}\n\t\t\tif (descriptor.enumValues && !descriptor.enumValues.includes(value)) {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Field \"${fieldName}\" in collection \"${collection}\" must be one of: ${descriptor.enumValues.join(', ')}. Got \"${value}\"`,\n\t\t\t\t\t{\n\t\t\t\t\t\tcollection,\n\t\t\t\t\t\tfield: fieldName,\n\t\t\t\t\t\tallowedValues: [...descriptor.enumValues],\n\t\t\t\t\t\treceived: value,\n\t\t\t\t\t},\n\t\t\t\t)\n\t\t\t}\n\t\t\tbreak\n\t\t}\n\n\t\tcase 'array': {\n\t\t\tif (!Array.isArray(value)) {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Field \"${fieldName}\" in collection \"${collection}\" must be an array, got ${typeof value}`,\n\t\t\t\t\t{ collection, field: fieldName, expectedType: 'array', receivedType: typeof value },\n\t\t\t\t)\n\t\t\t}\n\t\t\tif (descriptor.itemKind) {\n\t\t\t\tconst expectedType = jsTypeForKind(descriptor.itemKind)\n\t\t\t\tfor (let i = 0; i < value.length; i++) {\n\t\t\t\t\tconst item = value[i]\n\t\t\t\t\tif (!matchesJsType(item, expectedType)) {\n\t\t\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t\t\t`Field \"${fieldName}[${i}]\" in collection \"${collection}\" must be a ${descriptor.itemKind}, got ${typeof item}`,\n\t\t\t\t\t\t\t{\n\t\t\t\t\t\t\t\tcollection,\n\t\t\t\t\t\t\t\tfield: `${fieldName}[${i}]`,\n\t\t\t\t\t\t\t\texpectedType: descriptor.itemKind,\n\t\t\t\t\t\t\t\treceivedType: typeof item,\n\t\t\t\t\t\t\t},\n\t\t\t\t\t\t)\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\tbreak\n\t\t}\n\n\t\tcase 'richtext': {\n\t\t\t// Richtext fields accept Uint8Array (Yjs state) or string (plain text initial value)\n\t\t\tif (!(value instanceof Uint8Array) && typeof value !== 'string') {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Field \"${fieldName}\" in collection \"${collection}\" must be a Uint8Array or string for richtext, got ${typeof value}`,\n\t\t\t\t\t{\n\t\t\t\t\t\tcollection,\n\t\t\t\t\t\tfield: fieldName,\n\t\t\t\t\t\texpectedType: 'richtext',\n\t\t\t\t\t\treceivedType: typeof value,\n\t\t\t\t\t},\n\t\t\t\t)\n\t\t\t}\n\t\t\tbreak\n\t\t}\n\t}\n}\n\nfunction jsTypeForKind(kind: string): string {\n\tswitch (kind) {\n\t\tcase 'string':\n\t\tcase 'enum':\n\t\t\treturn 'string'\n\t\tcase 'number':\n\t\tcase 'timestamp':\n\t\t\treturn 'number'\n\t\tcase 'boolean':\n\t\t\treturn 'boolean'\n\t\tdefault:\n\t\t\treturn 'object'\n\t}\n}\n\nfunction matchesJsType(value: unknown, expected: string): boolean {\n\t// Using explicit comparisons to satisfy Biome's useValidTypeof rule,\n\t// which requires typeof to be compared against string literals.\n\tswitch (expected) {\n\t\tcase 'string':\n\t\t\treturn typeof value === 'string'\n\t\tcase 'number':\n\t\t\treturn typeof value === 'number'\n\t\tcase 'boolean':\n\t\t\treturn typeof value === 'boolean'\n\t\tcase 'object':\n\t\t\treturn typeof value === 'object'\n\t\tdefault:\n\t\t\treturn false\n\t}\n}\n","import { HybridLogicalClock } from '../clock/hlc'\nimport { OperationError } from '../errors/errors'\nimport type { Operation } from '../types'\n\n/**\n * Topological sort of operations based on their causal dependency DAG.\n * Uses Kahn's algorithm with a binary heap for O(V log V + E) performance.\n * Deterministic tie-breaking via HLC timestamp ensures identical output\n * regardless of input order.\n *\n * @param operations - The operations to sort\n * @returns Operations in causal order (dependencies before dependents)\n * @throws {OperationError} If a cycle is detected in the dependency graph\n */\nexport function topologicalSort(operations: Operation[]): Operation[] {\n\tif (operations.length <= 1) return [...operations]\n\n\t// Build adjacency list and in-degree map\n\tconst opMap = new Map<string, Operation>()\n\tfor (const op of operations) {\n\t\topMap.set(op.id, op)\n\t}\n\n\t// Only count edges where both ends are in the operation set\n\tconst inDegree = new Map<string, number>()\n\tconst dependents = new Map<string, string[]>()\n\n\tfor (const op of operations) {\n\t\tif (!inDegree.has(op.id)) {\n\t\t\tinDegree.set(op.id, 0)\n\t\t}\n\t\tif (!dependents.has(op.id)) {\n\t\t\tdependents.set(op.id, [])\n\t\t}\n\n\t\tfor (const depId of op.causalDeps) {\n\t\t\tif (opMap.has(depId)) {\n\t\t\t\t// depId -> op.id edge (depId must come before op.id)\n\t\t\t\tinDegree.set(op.id, (inDegree.get(op.id) ?? 0) + 1)\n\t\t\t\tconst deps = dependents.get(depId)\n\t\t\t\tif (deps) {\n\t\t\t\t\tdeps.push(op.id)\n\t\t\t\t} else {\n\t\t\t\t\tdependents.set(depId, [op.id])\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t// Initialize min-heap with nodes that have no in-set dependencies\n\tconst heap = new MinHeap(compareByTimestamp)\n\tfor (const op of operations) {\n\t\tif ((inDegree.get(op.id) ?? 0) === 0) {\n\t\t\theap.push(op)\n\t\t}\n\t}\n\n\tconst result: Operation[] = []\n\n\twhile (heap.size > 0) {\n\t\t// Extract the earliest operation (deterministic tie-breaking by HLC)\n\t\tconst current = heap.pop()\n\t\tresult.push(current)\n\n\t\tconst deps = dependents.get(current.id) ?? []\n\n\t\tfor (const depId of deps) {\n\t\t\tconst deg = (inDegree.get(depId) ?? 0) - 1\n\t\t\tinDegree.set(depId, deg)\n\t\t\tif (deg === 0) {\n\t\t\t\tconst op = opMap.get(depId)\n\t\t\t\tif (op) heap.push(op)\n\t\t\t}\n\t\t}\n\t}\n\n\tif (result.length !== operations.length) {\n\t\tthrow new OperationError(\n\t\t\t`Cycle detected in operation dependency graph. Sorted ${result.length} of ${operations.length} operations.`,\n\t\t\t{\n\t\t\t\tsortedCount: result.length,\n\t\t\t\ttotalCount: operations.length,\n\t\t\t},\n\t\t)\n\t}\n\n\treturn result\n}\n\nfunction compareByTimestamp(a: Operation, b: Operation): number {\n\treturn HybridLogicalClock.compare(a.timestamp, b.timestamp)\n}\n\n/**\n * Binary min-heap for efficient priority queue operations.\n * push: O(log n), pop: O(log n) — replaces the O(n) sorted array approach.\n */\nclass MinHeap {\n\tprivate readonly data: Operation[] = []\n\tprivate readonly cmp: (a: Operation, b: Operation) => number\n\n\tconstructor(comparator: (a: Operation, b: Operation) => number) {\n\t\tthis.cmp = comparator\n\t}\n\n\tget size(): number {\n\t\treturn this.data.length\n\t}\n\n\tpush(item: Operation): void {\n\t\tthis.data.push(item)\n\t\tthis.bubbleUp(this.data.length - 1)\n\t}\n\n\tpop(): Operation {\n\t\tconst top = this.data[0] as Operation\n\t\tconst last = this.data.pop() as Operation\n\t\tif (this.data.length > 0) {\n\t\t\tthis.data[0] = last\n\t\t\tthis.sinkDown(0)\n\t\t}\n\t\treturn top\n\t}\n\n\tprivate bubbleUp(index: number): void {\n\t\tlet current = index\n\t\twhile (current > 0) {\n\t\t\tconst parentIndex = (current - 1) >> 1\n\t\t\tif (this.cmp(this.data[current] as Operation, this.data[parentIndex] as Operation) >= 0) break\n\t\t\tthis.swap(current, parentIndex)\n\t\t\tcurrent = parentIndex\n\t\t}\n\t}\n\n\tprivate sinkDown(index: number): void {\n\t\tconst length = this.data.length\n\t\tlet current = index\n\t\twhile (true) {\n\t\t\tlet smallest = current\n\t\t\tconst left = 2 * current + 1\n\t\t\tconst right = 2 * current + 2\n\n\t\t\tif (\n\t\t\t\tleft < length &&\n\t\t\t\tthis.cmp(this.data[left] as Operation, this.data[smallest] as Operation) < 0\n\t\t\t) {\n\t\t\t\tsmallest = left\n\t\t\t}\n\t\t\tif (\n\t\t\t\tright < length &&\n\t\t\t\tthis.cmp(this.data[right] as Operation, this.data[smallest] as Operation) < 0\n\t\t\t) {\n\t\t\t\tsmallest = right\n\t\t\t}\n\n\t\t\tif (smallest === current) break\n\t\t\tthis.swap(current, smallest)\n\t\t\tcurrent = smallest\n\t\t}\n\t}\n\n\tprivate swap(i: number, j: number): void {\n\t\tconst tmp = this.data[i] as Operation\n\t\tthis.data[i] = this.data[j] as Operation\n\t\tthis.data[j] = tmp\n\t}\n}\n","import type { Operation, VersionVector } from '../types'\nimport { topologicalSort } from './topological-sort'\n\n/**\n * Create an empty version vector.\n */\nexport function createVersionVector(): VersionVector {\n\treturn new Map()\n}\n\n/**\n * Merge two version vectors by taking the max sequence number for each node.\n * This is commutative, associative, and idempotent.\n */\nexport function mergeVectors(a: VersionVector, b: VersionVector): VersionVector {\n\tconst merged = new Map(a)\n\tfor (const [nodeId, seq] of b) {\n\t\tmerged.set(nodeId, Math.max(merged.get(nodeId) ?? 0, seq))\n\t}\n\treturn merged\n}\n\n/**\n * Advance a version vector for a specific node to a new sequence number.\n * Only advances forward — if the current value is higher, no change is made.\n */\nexport function advanceVector(vector: VersionVector, nodeId: string, seq: number): VersionVector {\n\tconst updated = new Map(vector)\n\tupdated.set(nodeId, Math.max(updated.get(nodeId) ?? 0, seq))\n\treturn updated\n}\n\n/**\n * Returns true if vector `a` dominates vector `b` — meaning `a` has seen\n * everything `b` has seen. Formally: for every nodeId in b, a[nodeId] >= b[nodeId].\n */\nexport function dominates(a: VersionVector, b: VersionVector): boolean {\n\tfor (const [nodeId, bSeq] of b) {\n\t\tif ((a.get(nodeId) ?? 0) < bSeq) return false\n\t}\n\treturn true\n}\n\n/**\n * Returns true if two version vectors are exactly equal.\n */\nexport function vectorsEqual(a: VersionVector, b: VersionVector): boolean {\n\tif (a.size !== b.size) return false\n\tfor (const [nodeId, aSeq] of a) {\n\t\tif (b.get(nodeId) !== aSeq) return false\n\t}\n\treturn true\n}\n\n/**\n * Operation log interface for computing deltas.\n */\nexport interface OperationLog {\n\tgetRange(nodeId: string, fromSeq: number, toSeq: number): Operation[]\n}\n\n/**\n * Compute the operations that `local` has but `remote` does not.\n * Returns operations in causal (topological) order.\n *\n * @param localVector - The local version vector\n * @param remoteVector - The remote version vector\n * @param operationLog - The operation log to fetch operations from\n * @returns Operations sorted in causal order\n */\nexport function computeDelta(\n\tlocalVector: VersionVector,\n\tremoteVector: VersionVector,\n\toperationLog: OperationLog,\n): Operation[] {\n\tconst missing: Operation[] = []\n\tfor (const [nodeId, localSeq] of localVector) {\n\t\tconst remoteSeq = remoteVector.get(nodeId) ?? 0\n\t\tif (localSeq > remoteSeq) {\n\t\t\tmissing.push(...operationLog.getRange(nodeId, remoteSeq + 1, localSeq))\n\t\t}\n\t}\n\treturn topologicalSort(missing)\n}\n\n/**\n * Serialize a version vector to a JSON-compatible string.\n */\nexport function serializeVector(vector: VersionVector): string {\n\tconst entries = [...vector.entries()].sort(([a], [b]) => (a < b ? -1 : a > b ? 1 : 0))\n\treturn JSON.stringify(entries)\n}\n\n/**\n * Deserialize a version vector from its serialized string form.\n */\nexport function deserializeVector(s: string): VersionVector {\n\tconst entries = JSON.parse(s) as [string, number][]\n\treturn new Map(entries)\n}\n","import type { SchemaDefinition } from '../types'\n\n/**\n * Per-collection scope map: `{ collectionName: { field: value, ... } }`\n *\n * Used to filter which operations a client should receive during sync.\n */\nexport type ScopeMap = Record<string, Record<string, unknown>>\n\n/**\n * Build a per-collection scope map from the schema's scope declarations\n * and the client's flat scope values.\n *\n * For each collection:\n * - If it declares scope fields, build a filter from the matching flat values.\n * - If it declares no scope fields, include it with an empty filter (no restriction).\n *\n * @param schema - The schema definition with scope declarations\n * @param scopeValues - Flat key-value scope values from the client\n * @returns A per-collection scope map\n *\n * @example\n * ```typescript\n * // Schema declares: sales.scope = ['orgId', 'storeId']\n * // Client provides: { orgId: 'org-123', storeId: 'store-456' }\n * // Result: { sales: { orgId: 'org-123', storeId: 'store-456' }, products: {} }\n * ```\n */\nexport function buildScopeMap(\n\tschema: SchemaDefinition,\n\tscopeValues: Record<string, unknown>,\n): ScopeMap {\n\tconst result: ScopeMap = {}\n\n\tfor (const [collName, collDef] of Object.entries(schema.collections)) {\n\t\tif (collDef.scope.length > 0) {\n\t\t\tconst collScope: Record<string, unknown> = {}\n\t\t\tfor (const field of collDef.scope) {\n\t\t\t\tif (field in scopeValues) {\n\t\t\t\t\tcollScope[field] = scopeValues[field]\n\t\t\t\t}\n\t\t\t}\n\t\t\tresult[collName] = collScope\n\t\t} else {\n\t\t\t// Collections without scope declarations are fully visible\n\t\t\tresult[collName] = {}\n\t\t}\n\t}\n\n\treturn result\n}\n","/**\n * Offline-safe sequence formatting.\n *\n * Format tokens:\n * - `{date}` → YYYYMMDD (current date)\n * - `{node4}` → first 4 characters of nodeId\n * - `{node8}` → first 8 characters of nodeId\n * - `{seq}` → zero-padded counter (default 4 digits)\n * - `{seq:N}` → zero-padded counter with N digits\n *\n * @example\n * ```typescript\n * formatSequenceValue('INV-{date}-{node4}-{seq}', 42, 'a1b2c3d4e5f6')\n * // → \"INV-20260508-a1b2-0042\"\n *\n * formatSequenceValue('ORDER-{seq:6}', 7, 'node-id')\n * // → \"ORDER-000007\"\n * ```\n */\nexport function formatSequenceValue(\n\ttemplate: string,\n\tcounter: number,\n\tnodeId: string,\n\tnow?: Date,\n): string {\n\tconst date = now ?? new Date()\n\tconst yyyy = String(date.getUTCFullYear())\n\tconst mm = String(date.getUTCMonth() + 1).padStart(2, '0')\n\tconst dd = String(date.getUTCDate()).padStart(2, '0')\n\tconst dateStr = `${yyyy}${mm}${dd}`\n\n\treturn template.replace(/\\{([^}]+)\\}/g, (_match, token: string) => {\n\t\tif (token === 'date') return dateStr\n\t\tif (token === 'node4') return nodeId.slice(0, 4)\n\t\tif (token === 'node8') return nodeId.slice(0, 8)\n\t\tif (token === 'seq') return String(counter).padStart(4, '0')\n\t\tif (token.startsWith('seq:')) {\n\t\t\tconst width = Number.parseInt(token.slice(4), 10)\n\t\t\tif (Number.isNaN(width) || width < 1) {\n\t\t\t\treturn String(counter).padStart(4, '0')\n\t\t\t}\n\t\t\treturn String(counter).padStart(width, '0')\n\t\t}\n\t\t// Unknown token — leave as-is\n\t\treturn `{${token}}`\n\t})\n}\n\n/**\n * Default format when none is provided: `{name}-{seq:4}`.\n */\nexport function defaultSequenceFormat(name: string): string {\n\treturn `${name}-{seq:4}`\n}\n","import type { FieldBuilder } from '../schema/types'\nimport type { FieldDescriptor } from '../types'\n\n/**\n * A single migration step describing a schema change.\n */\nexport type MigrationStep =\n\t| { type: 'addField'; collection: string; field: string; descriptor: FieldDescriptor }\n\t| { type: 'removeField'; collection: string; field: string; descriptor?: FieldDescriptor }\n\t| { type: 'renameField'; collection: string; from: string; to: string }\n\t| { type: 'addIndex'; collection: string; field: string }\n\t| { type: 'removeIndex'; collection: string; field: string }\n\t| {\n\t\t\ttype: 'backfill'\n\t\t\tcollection: string\n\t\t\ttransform: (record: Record<string, unknown>) => Record<string, unknown>\n\t\t\t/** Reverse transform for rollback. If not provided, backfill is not safely reversible. */\n\t\t\treverseTransform?: (record: Record<string, unknown>) => Record<string, unknown>\n\t }\n\n/**\n * A completed migration definition containing ordered steps and optional rollback steps.\n */\nexport interface MigrationDefinition {\n\treadonly steps: readonly MigrationStep[]\n\t/** Explicitly defined rollback steps. If undefined, inverse steps are auto-generated. */\n\treadonly rollbackSteps: readonly MigrationStep[] | undefined\n\t/** Whether this migration can be safely rolled back. */\n\treadonly safelyReversible: boolean\n}\n\n/**\n * Builder for defining rollback steps explicitly.\n * Used with the `.down()` method on MigrationBuilder.\n *\n * @example\n * ```typescript\n * migrate()\n * .addField('todos', 'priority', t.enum(['low', 'medium', 'high']).default('medium'))\n * .addIndex('todos', 'priority')\n * .down((rollback) => {\n * rollback\n * .removeIndex('todos', 'priority')\n * .removeField('todos', 'priority')\n * })\n * ```\n */\nexport class RollbackBuilder {\n\tprivate _steps: MigrationStep[] = []\n\n\t/**\n\t * Add a field during rollback (to reverse a removeField).\n\t */\n\taddField(collection: string, field: string, builder: FieldBuilder): RollbackBuilder {\n\t\tthis._steps.push({ type: 'addField', collection, field, descriptor: builder._build() })\n\t\treturn this\n\t}\n\n\t/**\n\t * Remove a field during rollback (to reverse an addField).\n\t */\n\tremoveField(collection: string, field: string): RollbackBuilder {\n\t\tthis._steps.push({ type: 'removeField', collection, field })\n\t\treturn this\n\t}\n\n\t/**\n\t * Rename a field during rollback (to reverse a renameField).\n\t */\n\trenameField(collection: string, from: string, to: string): RollbackBuilder {\n\t\tthis._steps.push({ type: 'renameField', collection, from, to })\n\t\treturn this\n\t}\n\n\t/**\n\t * Add an index during rollback (to reverse a removeIndex).\n\t */\n\taddIndex(collection: string, field: string): RollbackBuilder {\n\t\tthis._steps.push({ type: 'addIndex', collection, field })\n\t\treturn this\n\t}\n\n\t/**\n\t * Remove an index during rollback (to reverse an addIndex).\n\t */\n\tremoveIndex(collection: string, field: string): RollbackBuilder {\n\t\tthis._steps.push({ type: 'removeIndex', collection, field })\n\t\treturn this\n\t}\n\n\t/**\n\t * Run a backfill during rollback (to reverse a previous backfill).\n\t */\n\tbackfill(\n\t\tcollection: string,\n\t\ttransform: (record: Record<string, unknown>) => Record<string, unknown>,\n\t): RollbackBuilder {\n\t\tthis._steps.push({ type: 'backfill', collection, transform })\n\t\treturn this\n\t}\n\n\t/**\n\t * Get the accumulated rollback steps.\n\t */\n\t_getSteps(): readonly MigrationStep[] {\n\t\treturn [...this._steps]\n\t}\n}\n\n/**\n * Fluent builder for defining schema migrations.\n *\n * Each method returns a new builder instance (immutable).\n *\n * @example\n * ```typescript\n * migrate()\n * .addField('products', 'taxInclusive', t.boolean().default(false))\n * .renameField('products', 'cost', 'costPrice')\n * .backfill('products', (record) => ({\n * taxInclusive: record.taxRate > 0,\n * }))\n * ```\n */\nexport class MigrationBuilder implements MigrationDefinition {\n\treadonly steps: readonly MigrationStep[]\n\treadonly rollbackSteps: readonly MigrationStep[] | undefined\n\treadonly safelyReversible: boolean\n\n\tconstructor(\n\t\tsteps: readonly MigrationStep[] = [],\n\t\trollbackSteps?: readonly MigrationStep[],\n\t\tsafelyReversible?: boolean,\n\t) {\n\t\tthis.steps = steps\n\t\tthis.rollbackSteps = rollbackSteps\n\t\t// Default: safely reversible if no backfill steps without reverseTransform\n\t\tthis.safelyReversible =\n\t\t\tsafelyReversible ?? this._computeSafelyReversible(steps, rollbackSteps)\n\t}\n\n\t/**\n\t * Add a new field to a collection.\n\t * The field builder provides the type and default value.\n\t */\n\taddField(collection: string, field: string, builder: FieldBuilder): MigrationBuilder {\n\t\treturn new MigrationBuilder([\n\t\t\t...this.steps,\n\t\t\t{ type: 'addField', collection, field, descriptor: builder._build() },\n\t\t])\n\t}\n\n\t/**\n\t * Remove a field from a collection.\n\t * Optionally accepts a field builder to preserve the descriptor for rollback.\n\t * Without the descriptor, rollback of this step requires a custom `.down()`.\n\t *\n\t * @param collection - The collection name\n\t * @param field - The field name to remove\n\t * @param builder - Optional field builder preserving the type info for rollback\n\t */\n\tremoveField(collection: string, field: string, builder?: FieldBuilder): MigrationBuilder {\n\t\tconst step: MigrationStep = builder\n\t\t\t? { type: 'removeField', collection, field, descriptor: builder._build() }\n\t\t\t: { type: 'removeField', collection, field }\n\t\treturn new MigrationBuilder([...this.steps, step])\n\t}\n\n\t/**\n\t * Rename a field in a collection.\n\t * Implemented as ALTER TABLE RENAME COLUMN (SQLite 3.25+).\n\t */\n\trenameField(collection: string, from: string, to: string): MigrationBuilder {\n\t\treturn new MigrationBuilder([...this.steps, { type: 'renameField', collection, from, to }])\n\t}\n\n\t/**\n\t * Add an index on a field.\n\t */\n\taddIndex(collection: string, field: string): MigrationBuilder {\n\t\treturn new MigrationBuilder([...this.steps, { type: 'addIndex', collection, field }])\n\t}\n\n\t/**\n\t * Remove an index on a field.\n\t */\n\tremoveIndex(collection: string, field: string): MigrationBuilder {\n\t\treturn new MigrationBuilder([...this.steps, { type: 'removeIndex', collection, field }])\n\t}\n\n\t/**\n\t * Backfill records in a collection using a transform function.\n\t * The transform receives each record and returns the fields to update.\n\t * Runs after structural changes (addField, renameField, etc.).\n\t *\n\t * @param collection - The collection name\n\t * @param transform - Forward transform function\n\t * @param reverseTransform - Optional reverse transform for rollback support\n\t */\n\tbackfill(\n\t\tcollection: string,\n\t\ttransform: (record: Record<string, unknown>) => Record<string, unknown>,\n\t\treverseTransform?: (record: Record<string, unknown>) => Record<string, unknown>,\n\t): MigrationBuilder {\n\t\treturn new MigrationBuilder([\n\t\t\t...this.steps,\n\t\t\t{ type: 'backfill', collection, transform, reverseTransform },\n\t\t])\n\t}\n\n\t/**\n\t * Define explicit rollback steps for this migration.\n\t * If not called, inverse steps are auto-generated from forward steps.\n\t *\n\t * @param fn - Function that receives a RollbackBuilder to define rollback steps\n\t * @returns A new MigrationBuilder with the rollback steps attached\n\t *\n\t * @example\n\t * ```typescript\n\t * migrate()\n\t * .addField('todos', 'priority', t.enum(['low', 'medium', 'high']).default('medium'))\n\t * .addIndex('todos', 'priority')\n\t * .down((rollback) => {\n\t * rollback\n\t * .removeIndex('todos', 'priority')\n\t * .removeField('todos', 'priority')\n\t * })\n\t * ```\n\t */\n\tdown(fn: (rollback: RollbackBuilder) => void): MigrationBuilder {\n\t\tconst rollbackBuilder = new RollbackBuilder()\n\t\tfn(rollbackBuilder)\n\t\tconst rbSteps = rollbackBuilder._getSteps()\n\t\treturn new MigrationBuilder(this.steps, rbSteps, true)\n\t}\n\n\t/**\n\t * Determine if a migration is safely reversible based on its steps.\n\t * A migration is not safely reversible if:\n\t * - It has a backfill step without a reverseTransform and no explicit rollback\n\t * - It has a removeField without a stored descriptor and no explicit rollback\n\t */\n\tprivate _computeSafelyReversible(\n\t\tsteps: readonly MigrationStep[],\n\t\trollbackSteps: readonly MigrationStep[] | undefined,\n\t): boolean {\n\t\t// Explicit rollback steps override auto-detection\n\t\tif (rollbackSteps !== undefined) {\n\t\t\treturn true\n\t\t}\n\n\t\tfor (const step of steps) {\n\t\t\tif (step.type === 'backfill' && !step.reverseTransform) {\n\t\t\t\treturn false\n\t\t\t}\n\t\t\tif (step.type === 'removeField' && !step.descriptor) {\n\t\t\t\treturn false\n\t\t\t}\n\t\t}\n\n\t\treturn true\n\t}\n}\n\n/**\n * Start building a migration.\n *\n * @returns A new MigrationBuilder\n *\n * @example\n * ```typescript\n * import { migrate, t } from '@korajs/core'\n *\n * const migration = migrate()\n * .addField('products', 'taxInclusive', t.boolean().default(false))\n * .renameField('products', 'cost', 'costPrice')\n * ```\n */\nexport function migrate(): MigrationBuilder {\n\treturn new MigrationBuilder()\n}\n","import { KoraError } from '../errors/errors'\nimport type { FieldDescriptor } from '../types'\nimport type { MigrationStep } from './migration-builder'\n\n/**\n * A migration that includes both forward (up) and backward (down) steps.\n * Rollback steps are applied in reverse order of the forward steps.\n */\nexport interface ReversibleMigration {\n\treadonly up: readonly MigrationStep[]\n\treadonly down: readonly MigrationStep[]\n\treadonly fromVersion: number\n\treadonly toVersion: number\n}\n\n/**\n * Error thrown when a migration step cannot be automatically rolled back\n * and no explicit down step has been provided.\n */\nexport class MigrationRollbackError extends KoraError {\n\tconstructor(step: MigrationStep) {\n\t\tsuper(\n\t\t\t`Cannot auto-generate rollback for \"${step.type}\" step on collection \"${step.collection}\". Provide an explicit .down() definition for this migration.`,\n\t\t\t'MIGRATION_ROLLBACK',\n\t\t\t{ stepType: step.type, collection: step.collection },\n\t\t)\n\t\tthis.name = 'MigrationRollbackError'\n\t}\n}\n\n/**\n * Determines whether a migration step can be automatically rolled back\n * without explicit developer-provided down steps.\n *\n * Auto-rollback is possible when the inverse operation is deterministic:\n * - addField -> removeField (drop the added column)\n * - addIndex -> removeIndex (drop the added index)\n * - removeIndex -> addIndex (re-create the index)\n * - renameField -> renameField (swap from/to names)\n *\n * Steps that CANNOT auto-rollback:\n * - removeField: the field descriptor is lost (need it to re-create the column)\n * - backfill: data transforms are not reversible\n *\n * @param step - The forward migration step to check\n * @returns true if the step can be auto-rolled back\n */\nexport function canAutoRollback(step: MigrationStep): boolean {\n\tswitch (step.type) {\n\t\tcase 'addField':\n\t\tcase 'addIndex':\n\t\tcase 'removeIndex':\n\t\tcase 'renameField':\n\t\t\treturn true\n\t\tcase 'removeField':\n\t\tcase 'backfill':\n\t\t\treturn false\n\t}\n}\n\n/**\n * Generates rollback steps for a list of forward migration steps.\n * Steps are reversed in order (last forward step becomes first rollback step).\n *\n * For steps that cannot be auto-rolled back, throws a MigrationRollbackError.\n * Use canAutoRollback() to check before calling, or provide explicit down steps\n * via the MigrationBuilder .down() API.\n *\n * @param forwardSteps - The forward migration steps to generate rollbacks for\n * @returns Array of rollback steps in reverse execution order\n * @throws MigrationRollbackError if any step cannot be auto-rolled back\n */\nexport function generateRollbackSteps(forwardSteps: readonly MigrationStep[]): MigrationStep[] {\n\tconst rollbackSteps: MigrationStep[] = []\n\n\t// Process in reverse order so rollback undoes changes in the opposite sequence\n\tfor (let i = forwardSteps.length - 1; i >= 0; i--) {\n\t\tconst step = forwardSteps[i]\n\t\tif (step === undefined) continue\n\n\t\tconst rollback = generateSingleRollbackStep(step)\n\t\trollbackSteps.push(rollback)\n\t}\n\n\treturn rollbackSteps\n}\n\n/**\n * Generate the inverse of a single migration step.\n * @internal\n */\nfunction generateSingleRollbackStep(step: MigrationStep): MigrationStep {\n\tswitch (step.type) {\n\t\tcase 'addField':\n\t\t\treturn { type: 'removeField', collection: step.collection, field: step.field }\n\n\t\tcase 'removeField':\n\t\t\t// removeField lacks the descriptor needed to re-create the column.\n\t\t\t// The developer must provide an explicit down step.\n\t\t\tif (step.descriptor) {\n\t\t\t\treturn {\n\t\t\t\t\ttype: 'addField',\n\t\t\t\t\tcollection: step.collection,\n\t\t\t\t\tfield: step.field,\n\t\t\t\t\tdescriptor: step.descriptor,\n\t\t\t\t}\n\t\t\t}\n\t\t\tthrow new MigrationRollbackError(step)\n\n\t\tcase 'renameField':\n\t\t\t// Reverse the rename: swap from and to\n\t\t\treturn { type: 'renameField', collection: step.collection, from: step.to, to: step.from }\n\n\t\tcase 'addIndex':\n\t\t\treturn { type: 'removeIndex', collection: step.collection, field: step.field }\n\n\t\tcase 'removeIndex':\n\t\t\treturn { type: 'addIndex', collection: step.collection, field: step.field }\n\n\t\tcase 'backfill':\n\t\t\t// Backfills with a reverseTransform can be auto-reversed\n\t\t\tif (step.reverseTransform) {\n\t\t\t\treturn {\n\t\t\t\t\ttype: 'backfill',\n\t\t\t\t\tcollection: step.collection,\n\t\t\t\t\ttransform: step.reverseTransform,\n\t\t\t\t}\n\t\t\t}\n\t\t\tthrow new MigrationRollbackError(step)\n\t}\n}\n\n/**\n * Create a ReversibleMigration from forward steps, explicit down steps, and version info.\n *\n * If explicit down steps are provided, they are used as-is.\n * If no explicit down steps are provided, auto-generation is attempted.\n *\n * @param upSteps - The forward migration steps\n * @param downSteps - Optional explicit rollback steps (overrides auto-generation)\n * @param fromVersion - The schema version before the migration\n * @param toVersion - The schema version after the migration\n * @returns A complete ReversibleMigration\n * @throws MigrationRollbackError if auto-generation fails and no explicit down steps provided\n */\nexport function createReversibleMigration(\n\tupSteps: readonly MigrationStep[],\n\tdownSteps: readonly MigrationStep[] | null,\n\tfromVersion: number,\n\ttoVersion: number,\n): ReversibleMigration {\n\tconst down = downSteps !== null ? [...downSteps] : generateRollbackSteps(upSteps)\n\n\treturn {\n\t\tup: [...upSteps],\n\t\tdown,\n\t\tfromVersion,\n\t\ttoVersion,\n\t}\n}\n","import type { FieldDescriptor } from '../types'\nimport type { MigrationDefinition, MigrationStep } from './migration-builder'\nimport { generateRollbackSteps } from './migration-rollback'\n\n/**\n * Convert migration steps to SQL statements.\n *\n * Structural steps (addField, removeField, renameField, addIndex, removeIndex)\n * produce SQL. Backfill steps are skipped (handled at the application layer\n * by reading rows and applying the transform function).\n *\n * @param steps - The migration steps from a MigrationBuilder\n * @returns Array of SQL statements for structural changes\n */\nexport function migrationStepsToSQL(steps: readonly MigrationStep[]): string[] {\n\tconst statements: string[] = []\n\n\tfor (const step of steps) {\n\t\tswitch (step.type) {\n\t\t\tcase 'addField':\n\t\t\t\tstatements.push(addFieldSQL(step.collection, step.field, step.descriptor))\n\t\t\t\tbreak\n\t\t\tcase 'removeField':\n\t\t\t\t// SQLite 3.35+ supports DROP COLUMN. For broader compat, we mark\n\t\t\t\t// the column as nullable so it can be ignored in queries.\n\t\t\t\t// Drop is preferred when available.\n\t\t\t\tstatements.push(`ALTER TABLE ${step.collection} DROP COLUMN ${step.field}`)\n\t\t\t\tbreak\n\t\t\tcase 'renameField':\n\t\t\t\t// SQLite 3.25+ supports RENAME COLUMN\n\t\t\t\tstatements.push(`ALTER TABLE ${step.collection} RENAME COLUMN ${step.from} TO ${step.to}`)\n\t\t\t\tbreak\n\t\t\tcase 'addIndex':\n\t\t\t\tstatements.push(\n\t\t\t\t\t`CREATE INDEX IF NOT EXISTS idx_${step.collection}_${step.field} ON ${step.collection} (${step.field})`,\n\t\t\t\t)\n\t\t\t\tbreak\n\t\t\tcase 'removeIndex':\n\t\t\t\tstatements.push(`DROP INDEX IF EXISTS idx_${step.collection}_${step.field}`)\n\t\t\t\tbreak\n\t\t\tcase 'backfill':\n\t\t\t\t// Backfills are handled by the store at runtime, not via SQL.\n\t\t\t\tbreak\n\t\t}\n\t}\n\n\treturn statements\n}\n\n/**\n * Generate SQL statements to roll back a migration.\n *\n * Uses the migration's explicit rollback steps if available,\n * otherwise auto-generates inverse steps from the forward steps.\n *\n * Backfill steps in the rollback are skipped (handled at the application layer).\n *\n * @param migration - The migration definition to generate rollback SQL for\n * @returns Array of SQL statements that undo the migration's structural changes\n *\n * @example\n * ```typescript\n * const migration = migrate()\n * .addField('todos', 'priority', t.enum(['low', 'medium', 'high']).default('medium'))\n * .addIndex('todos', 'priority')\n *\n * const rollbackSQL = rollbackStepsToSQL(migration)\n * // ['DROP INDEX IF EXISTS idx_todos_priority',\n * // 'ALTER TABLE todos DROP COLUMN priority']\n * ```\n */\nexport function rollbackStepsToSQL(migration: MigrationDefinition): string[] {\n\t// Use explicit rollback steps if provided, otherwise auto-generate from forward steps\n\tconst rollbackSteps = migration.rollbackSteps ?? generateRollbackSteps(migration.steps)\n\treturn migrationStepsToSQL(rollbackSteps)\n}\n\n/**\n * Produce an ALTER TABLE ADD COLUMN statement for a new field.\n */\nfunction addFieldSQL(collection: string, field: string, descriptor: FieldDescriptor): string {\n\tconst sqlType = mapFieldType(descriptor)\n\tconst parts = [`ALTER TABLE ${collection} ADD COLUMN ${field}`, sqlType]\n\n\tif (descriptor.defaultValue !== undefined) {\n\t\tparts.push(`DEFAULT ${sqlDefault(descriptor.defaultValue)}`)\n\t}\n\n\tif (descriptor.kind === 'enum' && descriptor.enumValues) {\n\t\tconst values = descriptor.enumValues.map((v) => `'${v}'`).join(', ')\n\t\tparts.push(`CHECK (${field} IN (${values}))`)\n\t}\n\n\treturn parts.join(' ')\n}\n\nfunction mapFieldType(descriptor: FieldDescriptor): string {\n\tswitch (descriptor.kind) {\n\t\tcase 'string':\n\t\t\treturn 'TEXT'\n\t\tcase 'number':\n\t\t\treturn 'REAL'\n\t\tcase 'boolean':\n\t\t\treturn 'INTEGER'\n\t\tcase 'enum':\n\t\t\treturn 'TEXT'\n\t\tcase 'timestamp':\n\t\t\treturn 'INTEGER'\n\t\tcase 'array':\n\t\t\treturn 'TEXT'\n\t\tcase 'richtext':\n\t\t\treturn 'BLOB'\n\t}\n}\n\nfunction sqlDefault(value: unknown): string {\n\tif (value === null) return 'NULL'\n\tif (typeof value === 'string') return `'${value}'`\n\tif (typeof value === 'number') return String(value)\n\tif (typeof value === 'boolean') return value ? '1' : '0'\n\treturn `'${JSON.stringify(value)}'`\n}\n","import type { CollectionDefinition, FieldDescriptor, FieldKind, SchemaDefinition } from '../types'\n\n/**\n * Output of the proto definition generator.\n * Contains the .proto file text, a type mapping, and a JSON descriptor\n * compatible with protobufjs's `Root.fromJSON()`.\n */\nexport interface ProtoOutput {\n\t/** The generated .proto file content as a string */\n\tproto: string\n\t/** TypeScript type map: field name -> protobuf type */\n\ttypeMap: Map<string, string>\n\t/** JSON descriptor for dynamic protobufjs usage (no .proto file needed) */\n\tjsonDescriptor: Record<string, unknown>\n}\n\n/**\n * Maps a Kora FieldKind to its protobuf scalar type string.\n * Array and enum kinds are handled separately because they\n * produce composite types (repeated, generated enum).\n */\nconst SCALAR_TYPE_MAP: Record<Exclude<FieldKind, 'array' | 'enum'>, string> = {\n\tstring: 'string',\n\tnumber: 'double',\n\tboolean: 'bool',\n\ttimestamp: 'int64',\n\trichtext: 'bytes',\n}\n\n/**\n * Maps a Kora FieldKind (when used as an array item) to its protobuf scalar type.\n * Only scalar kinds can be array items.\n */\nconst ARRAY_ITEM_TYPE_MAP: Record<string, string> = {\n\tstring: 'string',\n\tnumber: 'double',\n\tboolean: 'bool',\n\ttimestamp: 'int64',\n}\n\n/**\n * Converts a collection name (snake_case) to PascalCase for protobuf message names.\n * E.g., \"todo_items\" becomes \"TodoItems\", \"todos\" becomes \"Todos\".\n */\nfunction toPascalCase(name: string): string {\n\treturn name\n\t\t.split('_')\n\t\t.map((part) => part.charAt(0).toUpperCase() + part.slice(1))\n\t\t.join('')\n}\n\n/**\n * Converts a camelCase field name to snake_case for protobuf field names.\n * E.g., \"dueDate\" becomes \"due_date\", \"createdAt\" becomes \"created_at\".\n */\nfunction toSnakeCase(name: string): string {\n\treturn name.replace(/[A-Z]/g, (letter) => `_${letter.toLowerCase()}`)\n}\n\n/**\n * Resolves the protobuf type for a single field descriptor.\n *\n * @param fieldName - The field name (used for enum type naming)\n * @param descriptor - The Kora field descriptor\n * @param messageName - Parent message name (used for scoping enum type names)\n * @returns The protobuf type string\n */\nfunction resolveProtoType(\n\tfieldName: string,\n\tdescriptor: FieldDescriptor,\n\tmessageName: string,\n): string {\n\tif (descriptor.kind === 'enum') {\n\t\treturn `${messageName}${toPascalCase(fieldName)}`\n\t}\n\tif (descriptor.kind === 'array') {\n\t\tconst itemType = descriptor.itemKind\n\t\t\t? (ARRAY_ITEM_TYPE_MAP[descriptor.itemKind] ?? 'string')\n\t\t\t: 'string'\n\t\treturn itemType\n\t}\n\treturn SCALAR_TYPE_MAP[descriptor.kind as Exclude<FieldKind, 'array' | 'enum'>]\n}\n\n/**\n * Generates a protobuf enum definition for a Kora enum field.\n * Protobuf enums require the first value to be 0, so we add\n * an UNSPECIFIED sentinel as field 0.\n */\nfunction generateEnumBlock(\n\tenumTypeName: string,\n\tenumValues: readonly string[],\n\tindent: string,\n): string {\n\tconst lines: string[] = []\n\tlines.push(`${indent}enum ${enumTypeName} {`)\n\t// Proto3 requires field number 0 as a default/unspecified value\n\tlines.push(`${indent}\\t${enumTypeName.toUpperCase()}_UNSPECIFIED = 0;`)\n\tfor (let i = 0; i < enumValues.length; i++) {\n\t\tconst value = enumValues[i]\n\t\tif (value === undefined) continue\n\t\tlines.push(`${indent}\\t${enumTypeName.toUpperCase()}_${value.toUpperCase()} = ${i + 1};`)\n\t}\n\tlines.push(`${indent}}`)\n\treturn lines.join('\\n')\n}\n\n/**\n * Generates a protobuf message definition for a single Kora collection.\n * Includes nested enum types for any enum fields.\n *\n * @param collectionName - The collection name from the schema\n * @param collection - The collection definition\n * @param typeMap - Accumulator map for field->type mappings\n * @returns The proto message block as a string\n */\nfunction generateCollectionMessage(\n\tcollectionName: string,\n\tcollection: CollectionDefinition,\n\ttypeMap: Map<string, string>,\n): string {\n\tconst messageName = `${toPascalCase(collectionName)}Record`\n\tconst lines: string[] = []\n\tconst nestedEnums: string[] = []\n\n\tlines.push(`message ${messageName} {`)\n\n\t// Field 1 is always \"id\"\n\tlines.push('\\tstring id = 1;')\n\ttypeMap.set(`${collectionName}.id`, 'string')\n\n\tlet fieldNumber = 2\n\tconst entries = Object.entries(collection.fields)\n\n\tfor (const [fieldName, descriptor] of entries) {\n\t\tconst protoFieldName = toSnakeCase(fieldName)\n\t\tconst protoType = resolveProtoType(fieldName, descriptor, messageName)\n\t\tconst mapKey = `${collectionName}.${fieldName}`\n\n\t\tif (descriptor.kind === 'enum' && descriptor.enumValues) {\n\t\t\tconst enumTypeName = `${messageName}${toPascalCase(fieldName)}`\n\t\t\tnestedEnums.push(generateEnumBlock(enumTypeName, descriptor.enumValues, '\\t'))\n\t\t\ttypeMap.set(mapKey, enumTypeName)\n\t\t\tlines.push(`\\t${enumTypeName} ${protoFieldName} = ${fieldNumber};`)\n\t\t} else if (descriptor.kind === 'array') {\n\t\t\ttypeMap.set(mapKey, `repeated ${protoType}`)\n\t\t\tlines.push(`\\trepeated ${protoType} ${protoFieldName} = ${fieldNumber};`)\n\t\t} else {\n\t\t\ttypeMap.set(mapKey, protoType)\n\t\t\tlines.push(`\\t${protoType} ${protoFieldName} = ${fieldNumber};`)\n\t\t}\n\n\t\tfieldNumber++\n\t}\n\n\t// Insert nested enums before the closing brace\n\tif (nestedEnums.length > 0) {\n\t\t// Place enum definitions after the last field\n\t\tlines.push('')\n\t\tfor (const enumBlock of nestedEnums) {\n\t\t\tlines.push(enumBlock)\n\t\t}\n\t}\n\n\tlines.push('}')\n\treturn lines.join('\\n')\n}\n\n/**\n * The KoraOperation message — the wire format for individual operations.\n * Field assignments match the sync protocol specification from CLAUDE.md.\n */\nconst KORA_OPERATION_MESSAGE = `message KoraOperation {\n\\tstring id = 1;\n\\tstring node_id = 2;\n\\tstring type = 3;\n\\tstring collection = 4;\n\\tstring record_id = 5;\n\\tbytes data = 6;\n\\tbytes previous_data = 7;\n\\tint64 wall_time = 8;\n\\tint32 logical = 9;\n\\tstring timestamp_node_id = 10;\n\\tint64 sequence_number = 11;\n\\trepeated string causal_deps = 12;\n\\tint32 schema_version = 13;\n}`\n\n/**\n * The OperationBatch message — batches operations for sync transfer.\n */\nconst OPERATION_BATCH_MESSAGE = `message OperationBatch {\n\\trepeated KoraOperation operations = 1;\n\\tbool is_final = 2;\n}`\n\n/**\n * The HandshakeMessage — initiates a sync session with version vector exchange.\n */\nconst HANDSHAKE_MESSAGE = `message HandshakeMessage {\n\\tmap<string, int64> version_vector = 1;\n\\tint32 schema_version = 2;\n\\tstring node_id = 3;\n}`\n\n/**\n * The HandshakeResponse — server acknowledges and returns its version vector.\n */\nconst HANDSHAKE_RESPONSE_MESSAGE = `message HandshakeResponse {\n\\tmap<string, int64> version_vector = 1;\n\\tint32 schema_version = 2;\n}`\n\n/**\n * The Acknowledgment message — confirms receipt of an operation batch.\n */\nconst ACKNOWLEDGMENT_MESSAGE = `message Acknowledgment {\n\\tint64 sequence_number = 1;\n\\tstring node_id = 2;\n}`\n\n/**\n * Builds a JSON descriptor object compatible with protobufjs Root.fromJSON().\n * This allows runtime usage of the proto definitions without parsing .proto text.\n */\nfunction buildJsonDescriptor(schema: SchemaDefinition): Record<string, unknown> {\n\tconst nested: Record<string, unknown> = {}\n\n\t// Per-collection record messages\n\tfor (const [collectionName, collection] of Object.entries(schema.collections)) {\n\t\tconst messageName = `${toPascalCase(collectionName)}Record`\n\t\tconst fields: Record<string, unknown> = {\n\t\t\tid: { type: 'string', id: 1 },\n\t\t}\n\t\tconst nestedTypes: Record<string, unknown> = {}\n\n\t\tlet fieldNumber = 2\n\t\tfor (const [fieldName, descriptor] of Object.entries(collection.fields)) {\n\t\t\tconst protoFieldName = toSnakeCase(fieldName)\n\t\t\tconst fieldDef: Record<string, unknown> = { id: fieldNumber }\n\n\t\t\tif (descriptor.kind === 'enum' && descriptor.enumValues) {\n\t\t\t\tconst enumTypeName = `${messageName}${toPascalCase(fieldName)}`\n\t\t\t\tfieldDef.type = enumTypeName\n\n\t\t\t\t// Build enum values object for protobufjs\n\t\t\t\tconst enumValuesObj: Record<string, number> = {\n\t\t\t\t\t[`${enumTypeName.toUpperCase()}_UNSPECIFIED`]: 0,\n\t\t\t\t}\n\t\t\t\tfor (let i = 0; i < descriptor.enumValues.length; i++) {\n\t\t\t\t\tconst val = descriptor.enumValues[i]\n\t\t\t\t\tif (val === undefined) continue\n\t\t\t\t\tenumValuesObj[`${enumTypeName.toUpperCase()}_${val.toUpperCase()}`] = i + 1\n\t\t\t\t}\n\t\t\t\tnestedTypes[enumTypeName] = { values: enumValuesObj }\n\t\t\t} else if (descriptor.kind === 'array') {\n\t\t\t\tconst itemType = descriptor.itemKind\n\t\t\t\t\t? (ARRAY_ITEM_TYPE_MAP[descriptor.itemKind] ?? 'string')\n\t\t\t\t\t: 'string'\n\t\t\t\tfieldDef.type = itemType\n\t\t\t\tfieldDef.rule = 'repeated'\n\t\t\t} else {\n\t\t\t\tfieldDef.type = SCALAR_TYPE_MAP[descriptor.kind as Exclude<FieldKind, 'array' | 'enum'>]\n\t\t\t}\n\n\t\t\tfields[protoFieldName] = fieldDef\n\t\t\tfieldNumber++\n\t\t}\n\n\t\tconst messageDescriptor: Record<string, unknown> = { fields }\n\t\tif (Object.keys(nestedTypes).length > 0) {\n\t\t\tmessageDescriptor.nested = nestedTypes\n\t\t}\n\t\tnested[messageName] = messageDescriptor\n\t}\n\n\t// KoraOperation\n\tnested.KoraOperation = {\n\t\tfields: {\n\t\t\tid: { type: 'string', id: 1 },\n\t\t\tnode_id: { type: 'string', id: 2 },\n\t\t\ttype: { type: 'string', id: 3 },\n\t\t\tcollection: { type: 'string', id: 4 },\n\t\t\trecord_id: { type: 'string', id: 5 },\n\t\t\tdata: { type: 'bytes', id: 6 },\n\t\t\tprevious_data: { type: 'bytes', id: 7 },\n\t\t\twall_time: { type: 'int64', id: 8 },\n\t\t\tlogical: { type: 'int32', id: 9 },\n\t\t\ttimestamp_node_id: { type: 'string', id: 10 },\n\t\t\tsequence_number: { type: 'int64', id: 11 },\n\t\t\tcausal_deps: { type: 'string', id: 12, rule: 'repeated' },\n\t\t\tschema_version: { type: 'int32', id: 13 },\n\t\t},\n\t}\n\n\t// OperationBatch\n\tnested.OperationBatch = {\n\t\tfields: {\n\t\t\toperations: { type: 'KoraOperation', id: 1, rule: 'repeated' },\n\t\t\tis_final: { type: 'bool', id: 2 },\n\t\t},\n\t}\n\n\t// HandshakeMessage\n\tnested.HandshakeMessage = {\n\t\tfields: {\n\t\t\tversion_vector: { keyType: 'string', type: 'int64', id: 1 },\n\t\t\tschema_version: { type: 'int32', id: 2 },\n\t\t\tnode_id: { type: 'string', id: 3 },\n\t\t},\n\t}\n\n\t// HandshakeResponse\n\tnested.HandshakeResponse = {\n\t\tfields: {\n\t\t\tversion_vector: { keyType: 'string', type: 'int64', id: 1 },\n\t\t\tschema_version: { type: 'int32', id: 2 },\n\t\t},\n\t}\n\n\t// Acknowledgment\n\tnested.Acknowledgment = {\n\t\tfields: {\n\t\t\tsequence_number: { type: 'int64', id: 1 },\n\t\t\tnode_id: { type: 'string', id: 2 },\n\t\t},\n\t}\n\n\treturn {\n\t\tnested: {\n\t\t\tkora: { nested },\n\t\t},\n\t}\n}\n\n/**\n * Generates Protocol Buffer definitions from a Kora schema.\n *\n * Produces three outputs:\n * 1. A `.proto` file string conforming to proto3 syntax\n * 2. A type map linking Kora field paths to protobuf types\n * 3. A JSON descriptor for runtime protobufjs usage via `Root.fromJSON()`\n *\n * The generated definitions include:\n * - Per-collection record messages with proper type mappings\n * - Nested enum types for enum fields\n * - `KoraOperation` wrapper for the sync wire format\n * - `OperationBatch` for batched sync transfers\n * - `HandshakeMessage` / `HandshakeResponse` for sync session initiation\n * - `Acknowledgment` for delivery confirmation\n *\n * @param schema - A validated SchemaDefinition from defineSchema()\n * @returns ProtoOutput with proto text, type map, and JSON descriptor\n *\n * @example\n * ```typescript\n * import { defineSchema, t, generateProtoDefinitions } from '@korajs/core'\n *\n * const schema = defineSchema({\n * version: 1,\n * collections: {\n * todos: {\n * fields: {\n * title: t.string(),\n * completed: t.boolean().default(false),\n * }\n * }\n * }\n * })\n *\n * const { proto, typeMap, jsonDescriptor } = generateProtoDefinitions(schema)\n * // proto is a valid .proto file string\n * // typeMap maps \"todos.title\" -> \"string\", \"todos.completed\" -> \"bool\"\n * // jsonDescriptor can be loaded with protobuf.Root.fromJSON()\n * ```\n */\nexport function generateProtoDefinitions(schema: SchemaDefinition): ProtoOutput {\n\tconst typeMap = new Map<string, string>()\n\tconst sections: string[] = []\n\n\t// Proto3 header\n\tsections.push('syntax = \"proto3\";')\n\tsections.push('')\n\tsections.push('package kora;')\n\n\t// Per-collection messages\n\tconst collectionEntries = Object.entries(schema.collections)\n\tif (collectionEntries.length > 0) {\n\t\tsections.push('')\n\t\tsections.push('// Collection record messages')\n\t\tfor (const [collectionName, collection] of collectionEntries) {\n\t\t\tsections.push('')\n\t\t\tsections.push(generateCollectionMessage(collectionName, collection, typeMap))\n\t\t}\n\t}\n\n\t// Sync protocol messages\n\tsections.push('')\n\tsections.push('// Sync protocol messages')\n\tsections.push('')\n\tsections.push(KORA_OPERATION_MESSAGE)\n\tsections.push('')\n\tsections.push(OPERATION_BATCH_MESSAGE)\n\tsections.push('')\n\tsections.push(HANDSHAKE_MESSAGE)\n\tsections.push('')\n\tsections.push(HANDSHAKE_RESPONSE_MESSAGE)\n\tsections.push('')\n\tsections.push(ACKNOWLEDGMENT_MESSAGE)\n\n\tconst proto = `${sections.join('\\n')}\\n`\n\tconst jsonDescriptor = buildJsonDescriptor(schema)\n\n\treturn { proto, typeMap, jsonDescriptor }\n}\n"],"mappings":"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","names":["op","op","mapFieldType","sqlDefault"]}
|
|
1
|
+
{"version":3,"sources":["../src/index.ts","../src/types.ts","../src/errors/error-fixes.ts","../src/errors/errors.ts","../src/clock/hlc.ts","../src/causal/causal-tracker.ts","../src/identifiers/uuid-v7.ts","../src/operations/apply-result.ts","../src/operations/content-hash.ts","../src/operations/operation.ts","../src/operations/atomic-ops.ts","../src/scopes/sync-scope-bindings.ts","../src/state-machine/state-machine.ts","../src/schema/define.ts","../src/schema/sql-gen.ts","../src/schema/types.ts","../src/schema/validation.ts","../src/version-vector/topological-sort.ts","../src/version-vector/version-vector.ts","../src/scopes/build-scope-map.ts","../src/scopes/extract-scope-from-claims.ts","../src/sequences/sequence-format.ts","../src/migration/apply-operation-transforms.ts","../src/migrations/migration-builder.ts","../src/migrations/migration-rollback.ts","../src/migrations/migration-sql.ts","../src/codegen/proto-generator.ts"],"sourcesContent":["// @korajs/core — public API\n// Every export here is a public API commitment. Be explicit.\n\n// === Types ===\nexport type {\n\tAtomicOp,\n\tAtomicOpType,\n\tCollectionDefinition,\n\tConnectionQuality,\n\tConstraint,\n\tCustomResolver,\n\tFieldDescriptor,\n\tFieldKind,\n\tFieldMergeStrategy,\n\tHLCTimestamp,\n\tMergeStrategy,\n\tOnDeleteAction,\n\tOperation,\n\tOperationInput,\n\tOperationType,\n\tRandomSource,\n\tRelationDefinition,\n\tRelationType,\n\tSchemaDefinition,\n\tSequenceConfig,\n\tStateMachineConstraint,\n\tStateMachineDefinition,\n\tSyncRuleDefinition,\n\tSyncDiagnosticsSnapshot,\n\tTimeSource,\n\tTransitionMap,\n\tTransitionValidationResult,\n\tVersionVector,\n} from './types'\n\nexport { CONNECTION_QUALITIES, MERGE_STRATEGIES } from './types'\n\n// === Errors ===\nexport {\n\tAppNotReadyError,\n\tClockDriftError,\n\tKoraError,\n\tMergeConflictError,\n\tOperationError,\n\tSchemaValidationError,\n\tStorageError,\n\tSyncError,\n} from './errors/errors'\nexport { getKoraErrorFix, KORA_ERROR_FIX_SUGGESTIONS } from './errors/error-fixes'\n\n// === Clock ===\nexport { HybridLogicalClock } from './clock/hlc'\n\n// === Causal tracking ===\nexport { CausalTracker } from './causal/causal-tracker'\n\n// === Identifiers ===\nexport { extractTimestamp, generateUUIDv7, isValidUUIDv7 } from './identifiers/uuid-v7'\n\n// === Operations ===\nexport {\n\tAPPLY_FAILURE_CODES,\n\tAPPLY_RESULTS,\n\tdefaultApplyFailureReason,\n\tisApplyFailure,\n} from './operations/apply-result'\nexport type { ApplyFailureReason, ApplyResult } from './operations/apply-result'\nexport {\n\tcreateOperation,\n\tisValidOperation,\n\tverifyOperationIntegrity,\n} from './operations/operation'\n\n// === Atomic Operations ===\nexport {\n\tisAtomicOp,\n\top,\n\tresolveAtomicOp,\n\ttoAtomicOp,\n} from './operations/atomic-ops'\nexport type { AtomicOpSentinel } from './operations/atomic-ops'\n\n// === Schema ===\nexport { defineSchema } from './schema/define'\nexport type {\n\tCollectionInput,\n\tConstraintInput,\n\tRelationInput,\n\tSchemaInput,\n\tStateMachineInput,\n\tTypedSchemaDefinition,\n} from './schema/define'\nexport { generateFullDDL, generateSQL } from './schema/sql-gen'\nexport { ArrayFieldBuilder, EnumFieldBuilder, FieldBuilder, t } from './schema/types'\nexport { validateRecord } from './schema/validation'\n\n// === Type Inference ===\nexport type {\n\tFieldKindToType,\n\tInferFieldType,\n\tInferInsertInput,\n\tInferRecord,\n\tInferUpdateInput,\n} from './schema/infer'\n\n// === Version Vectors ===\nexport {\n\tadvanceVector,\n\tcomputeDelta,\n\tcreateVersionVector,\n\tdeserializeVector,\n\tdominates,\n\tmergeVectors,\n\tserializeVector,\n\tvectorsEqual,\n} from './version-vector/version-vector'\nexport type { OperationLog } from './version-vector/version-vector'\n\n// === Scopes ===\nexport { buildScopeMap } from './scopes/build-scope-map'\nexport type { ScopeMap } from './scopes/build-scope-map'\nexport {\n\tcollectSchemaScopeFields,\n\textractScopeValuesFromClaims,\n} from './scopes/extract-scope-from-claims'\nexport {\n\tcollectSchemaScopeValueKeys,\n\tgetCollectionScopeBindings,\n\thasSchemaSyncRules,\n\tisCollectionSyncScoped,\n} from './scopes/sync-scope-bindings'\n\n// === Sequences ===\nexport { defaultSequenceFormat, formatSequenceValue } from './sequences/sequence-format'\n\n// === Migrations ===\nexport type { OperationTransform } from './migration/operation-transform'\nexport { applyOperationTransforms } from './migration/apply-operation-transforms'\nexport { MigrationBuilder, RollbackBuilder, migrate } from './migrations/migration-builder'\nexport type { MigrationDefinition, MigrationStep } from './migrations/migration-builder'\nexport { migrationStepsToSQL, rollbackStepsToSQL } from './migrations/migration-sql'\nexport {\n\tMigrationRollbackError,\n\tcanAutoRollback,\n\tcreateReversibleMigration,\n\tgenerateRollbackSteps,\n} from './migrations/migration-rollback'\nexport type { ReversibleMigration } from './migrations/migration-rollback'\n\n// === State Machine ===\nexport {\n\tbuildStateMachineConstraints,\n\tgetTransitionMap,\n\tvalidateTransition,\n} from './state-machine/state-machine'\n\n// === Events ===\nexport type {\n\tKoraEvent,\n\tKoraEventByType,\n\tKoraEventEmitter,\n\tKoraEventListener,\n\tKoraEventType,\n\tMergeTrace,\n} from './events/events'\n\n// === Codegen ===\nexport { generateProtoDefinitions } from './codegen/proto-generator'\nexport type { ProtoOutput } from './codegen/proto-generator'\n","/**\n * Hybrid Logical Clock timestamp.\n * Provides a total order that respects causality without requiring synchronized clocks.\n */\nexport interface HLCTimestamp {\n\t/** Physical wall-clock time in milliseconds */\n\twallTime: number\n\t/** Logical counter. Increments when wallTime hasn't changed since last event. */\n\tlogical: number\n\t/** Node ID for tie-breaking. Ensures total order even with identical wall+logical. */\n\tnodeId: string\n}\n\n/** The three mutation types an operation can represent */\nexport type OperationType = 'insert' | 'update' | 'delete'\n\n/** Supported atomic operation types for intent-preserving field updates */\nexport type AtomicOpType = 'increment' | 'max' | 'min' | 'append' | 'remove'\n\n/**\n * Atomic operation stored in an Operation's atomicOps field.\n * This is the serializable form that persists in the operation log.\n */\nexport interface AtomicOp {\n\treadonly type: AtomicOpType\n\treadonly value: unknown\n}\n\n/**\n * The atomic unit of the entire system. Every mutation produces an Operation.\n * Operations are IMMUTABLE and CONTENT-ADDRESSED.\n */\nexport interface Operation {\n\t/** SHA-256 hash of (type + collection + recordId + data + timestamp + nodeId). Content-addressed. */\n\tid: string\n\t/** UUID v7 of the originating device. Time-sortable. */\n\tnodeId: string\n\t/** What happened */\n\ttype: OperationType\n\t/** Which collection (from schema) */\n\tcollection: string\n\t/** ID of the affected record. UUID v7 for inserts, existing ID for update/delete. */\n\trecordId: string\n\t/** Field values. null for delete. For updates, contains ONLY changed fields. */\n\tdata: Record<string, unknown> | null\n\t/** For updates: previous values of changed fields (enables 3-way merge). null for insert/delete. */\n\tpreviousData: Record<string, unknown> | null\n\t/** Hybrid Logical Clock timestamp. Used for causal ordering. */\n\ttimestamp: HLCTimestamp\n\t/** Monotonically increasing per node. Used in version vectors. */\n\tsequenceNumber: number\n\t/** Operation IDs this operation causally depends on (direct parents in the DAG). */\n\tcausalDeps: string[]\n\t/** Schema version at time of creation. Used for migration transforms. */\n\tschemaVersion: number\n\t/** Atomic operation intents for fields in data (e.g., increment, max). Present only when atomic ops were used. */\n\tatomicOps?: Record<string, AtomicOp>\n\t/** Groups this operation with others in an atomic transaction. Not part of the content hash. */\n\ttransactionId?: string\n\t/** Human-readable name for the mutation group (e.g., 'complete-sale'). For DevTools display. */\n\tmutationName?: string\n}\n\n/**\n * Input for creating an operation (before id and timestamp are assigned).\n */\nexport interface OperationInput {\n\tnodeId: string\n\ttype: OperationType\n\tcollection: string\n\trecordId: string\n\tdata: Record<string, unknown> | null\n\tpreviousData: Record<string, unknown> | null\n\tsequenceNumber: number\n\tcausalDeps: string[]\n\tschemaVersion: number\n\t/** Atomic operation intents for fields in data (e.g., increment, max). */\n\tatomicOps?: Record<string, AtomicOp>\n\t/** Groups this operation with others in an atomic transaction. Not part of the content hash. */\n\ttransactionId?: string\n\t/** Human-readable name for the mutation group (e.g., 'complete-sale'). For DevTools display. */\n\tmutationName?: string\n}\n\n/** Version vector: maps nodeId to the max sequence number seen from that node */\nexport type VersionVector = Map<string, number>\n\n/** Field kinds supported by the schema system */\nexport type FieldKind =\n\t| 'string'\n\t| 'number'\n\t| 'boolean'\n\t| 'timestamp'\n\t| 'richtext'\n\t| 'enum'\n\t| 'array'\n\n/**\n * Comprehensive sync diagnostics snapshot.\n * Provides connection, latency, throughput, queue, and error metrics\n * for monitoring and DevTools integration.\n */\nexport interface SyncDiagnosticsSnapshot {\n\t// Connection\n\t/** Current developer-facing sync status */\n\tstatus: 'connected' | 'syncing' | 'synced' | 'offline' | 'error' | 'schema-mismatch'\n\t/** Timestamp when the current connection was established, or null if disconnected */\n\tconnectedAt: number | null\n\t/** Timestamp when the last disconnection occurred, or null if never disconnected */\n\tdisconnectedAt: number | null\n\t/** Number of reconnection attempts since last successful connection */\n\treconnectAttempts: number\n\n\t// Latency\n\t/** Current round-trip time in milliseconds */\n\trttMs: number\n\t/** Median (50th percentile) RTT over the sliding window */\n\trttP50Ms: number\n\t/** 95th percentile RTT over the sliding window */\n\trttP95Ms: number\n\t/** 99th percentile RTT over the sliding window */\n\trttP99Ms: number\n\n\t// Throughput\n\t/** Total operations sent during this session */\n\toperationsSent: number\n\t/** Total operations received during this session */\n\toperationsReceived: number\n\t/** Total bytes sent during this session */\n\tbytesSent: number\n\t/** Total bytes received during this session */\n\tbytesReceived: number\n\n\t// Queue\n\t/** Number of operations waiting to be sent */\n\tpendingOperations: number\n\t/** Estimated bytes in the outbound queue */\n\toutboundQueueSize: number\n\n\t// Sync Progress\n\t/** Timestamp of the last successful sync, or null if never synced */\n\tlastSyncedAt: number | null\n\t/** Duration of the last complete sync cycle in ms, or null if no cycle completed */\n\tsyncDuration: number | null\n\t/** Whether the initial sync (full delta exchange) has completed */\n\tinitialSyncComplete: boolean\n\t/** Progress of the initial sync as a 0-1 ratio */\n\tinitialSyncProgress: number\n\n\t// Errors\n\t/** Description of the last error, or null if no error occurred */\n\tlastError: string | null\n\t/** Total number of errors during this session */\n\terrorCount: number\n\n\t// Connection Quality\n\t/** Assessed connection quality level */\n\tquality: 'excellent' | 'good' | 'fair' | 'poor' | 'offline'\n\t/** Estimated effective bandwidth in bytes per second, or null if not yet measured */\n\teffectiveBandwidth: number | null\n}\n\n/** Built-in field merge strategies that can be declared in the schema. */\nexport type FieldMergeStrategy =\n\t| 'lww'\n\t| 'counter'\n\t| 'max'\n\t| 'min'\n\t| 'union'\n\t| 'append-only'\n\t| 'server-authoritative'\n\n/** Map of state to allowed next states for state machine constraints */\nexport type TransitionMap = Record<string, string[]>\n\n/**\n * A state machine constraint extracted from the schema.\n * Used by merge and validation to enforce valid state transitions.\n */\nexport interface StateMachineConstraint {\n\t/** The enum field this constraint controls */\n\tfield: string\n\t/** The collection this constraint applies to */\n\tcollection: string\n\t/** Map of state to allowed next states */\n\ttransitions: TransitionMap\n}\n\n/**\n * Result of validating a state transition.\n */\nexport interface TransitionValidationResult {\n\t/** Whether the transition is allowed */\n\tvalid: boolean\n\t/** The source state */\n\tfrom: string\n\t/** The target state */\n\tto: string\n\t/** The field being transitioned */\n\tfield: string\n\t/** The collection containing the field */\n\tcollection: string\n\t/** All allowed target states from the source state */\n\tallowedTargets: string[]\n}\n\n/**\n * Descriptor produced by the type builder (t.string(), t.number(), etc.).\n * Represents a fully configured field definition.\n */\nexport interface FieldDescriptor {\n\tkind: FieldKind\n\trequired: boolean\n\tdefaultValue: unknown\n\tauto: boolean\n\tenumValues: readonly string[] | null\n\titemKind: FieldKind | null\n\t/** Declared merge strategy. Defaults to kind-appropriate strategy when undefined. */\n\tmergeStrategy: FieldMergeStrategy | null\n\t/** State machine transition map for enum fields. Null if no transitions declared. */\n\ttransitions: TransitionMap | null\n}\n\n/**\n * Defines a state machine on an enum field, constraining valid state transitions.\n *\n * When a state machine is defined on a collection, mutations and merges\n * enforce that the controlled field only moves along declared transitions.\n *\n * @example\n * ```typescript\n * stateMachine: {\n * field: 'status',\n * transitions: {\n * draft: ['pending', 'cancelled'],\n * pending: ['confirmed', 'cancelled'],\n * confirmed: ['shipped'],\n * shipped: ['delivered'],\n * delivered: [],\n * cancelled: [],\n * },\n * onInvalidTransition: 'reject',\n * }\n * ```\n */\nexport interface StateMachineDefinition {\n\t/** The enum field this state machine controls */\n\tfield: string\n\t/** Map of state to allowed next states */\n\ttransitions: Record<string, string[]>\n\t/** What to do when an invalid transition is attempted */\n\tonInvalidTransition: 'reject' | 'last-valid-state'\n}\n\n/**\n * Definition of a collection within the schema.\n */\nexport interface CollectionDefinition {\n\tfields: Record<string, FieldDescriptor>\n\tindexes: string[]\n\tconstraints: Constraint[]\n\tresolvers: Record<string, CustomResolver>\n\t/** Scope fields for sync filtering. Only records matching the client's scope values are synced. */\n\tscope: string[]\n\t/** Optional state machine constraining transitions on an enum field */\n\tstateMachine?: StateMachineDefinition\n}\n\n/** Custom resolver function for tier 3 merge resolution */\nexport type CustomResolver = (local: unknown, remote: unknown, base: unknown) => unknown\n\n/**\n * Constraint for tier 2 conflict resolution.\n */\nexport interface Constraint {\n\ttype: 'unique' | 'capacity' | 'referential'\n\tfields: string[]\n\twhere?: Record<string, unknown>\n\tonConflict:\n\t\t| 'first-write-wins'\n\t\t| 'last-write-wins'\n\t\t| 'priority-field'\n\t\t| 'server-decides'\n\t\t| 'custom'\n\tpriorityField?: string\n\tresolve?: (local: unknown, remote: unknown, base: unknown) => unknown\n}\n\n/** Relation type between collections */\nexport type RelationType = 'one-to-one' | 'one-to-many' | 'many-to-one' | 'many-to-many'\n\n/** On-delete behavior for relations */\nexport type OnDeleteAction = 'cascade' | 'set-null' | 'restrict' | 'no-action'\n\n/**\n * Definition of a relation between two collections.\n */\nexport interface RelationDefinition {\n\tfrom: string\n\tto: string\n\ttype: RelationType\n\tfield: string\n\tonDelete: OnDeleteAction\n}\n\n/**\n * Declarative sync filter for a collection.\n *\n * `where` maps record field names to scope value keys. Use `true` to bind a field\n * to a scope value with the same name (e.g. `{ userId: true }`).\n */\nexport interface SyncRuleDefinition {\n\twhere: Record<string, string>\n}\n\n/**\n * The complete schema definition produced by defineSchema().\n */\nexport interface SchemaDefinition {\n\tversion: number\n\tcollections: Record<string, CollectionDefinition>\n\trelations: Record<string, RelationDefinition>\n\t/** Schema migrations keyed by target version. */\n\tmigrations: Record<number, import('./migrations/migration-builder').MigrationDefinition>\n\t/**\n\t * Declarative partial-sync rules per collection.\n\t * When present, only listed collections (plus legacy `scope` collections) sync.\n\t */\n\tsync?: Record<string, SyncRuleDefinition>\n}\n\n/**\n * Merge strategies available for auto-merge and constraints.\n */\nexport const MERGE_STRATEGIES = [\n\t'auto-merge',\n\t'lww',\n\t'first-write-wins',\n\t'server-decides',\n\t'custom',\n] as const\nexport type MergeStrategy = (typeof MERGE_STRATEGIES)[number]\n\n/**\n * Connection quality levels for adaptive sync.\n */\nexport const CONNECTION_QUALITIES = ['excellent', 'good', 'fair', 'poor', 'offline'] as const\nexport type ConnectionQuality = (typeof CONNECTION_QUALITIES)[number]\n\n/**\n * Injectable time source for deterministic testing of clocks.\n */\nexport interface TimeSource {\n\tnow(): number\n}\n\n/**\n * Injectable random source for deterministic testing of UUID generation.\n */\nexport interface RandomSource {\n\tgetRandomValues<T extends ArrayBufferView>(array: T): T\n}\n\n/**\n * Configuration for an offline-safe sequence.\n *\n * Sequences produce monotonically increasing, collision-free identifiers\n * that work across offline devices. Each device maintains its own counter\n * scoped by (name, scope, nodeId).\n *\n * Format tokens available:\n * - `{date}` → YYYYMMDD\n * - `{node4}` → first 4 chars of nodeId\n * - `{node8}` → first 8 chars of nodeId\n * - `{seq}` → zero-padded counter (4 digits)\n * - `{seq:N}` → zero-padded counter with N digits\n *\n * @example\n * ```typescript\n * await app.sequences.next('receipt', {\n * scope: storeId,\n * format: 'S-{date}-{node4}-{seq}',\n * })\n * // → \"S-20260508-a1b2-0042\"\n * ```\n */\nexport interface SequenceConfig {\n\t/** Namespace within the sequence (e.g., a storeId or orgId). Defaults to ''. */\n\tscope?: string\n\t/** Format template. Defaults to `{name}-{seq:4}`. */\n\tformat?: string\n\t/** Starting counter value. Defaults to 1. */\n\tstartAt?: number\n}\n","/**\n * Human-readable remediation hints keyed by {@link KoraError} `code`.\n */\nexport const KORA_ERROR_FIX_SUGGESTIONS: Record<string, string> = {\n\tSCHEMA_VALIDATION:\n\t\t'Review your defineSchema() definition: every collection needs at least one field and a positive version.',\n\tOPERATION_ERROR:\n\t\t'Check the operation payload matches your schema field types and required fields.',\n\tMERGE_CONFLICT:\n\t\t'Add a custom resolver for the conflicting field in defineSchema(), or adjust constraint onConflict rules.',\n\tSYNC_ERROR:\n\t\t'Verify the sync server URL, auth token, and that the server accepts your schema version.',\n\tSTORAGE_ERROR:\n\t\t'Confirm the storage adapter is supported in this environment and the database path is writable.',\n\tCLOCK_DRIFT:\n\t\t'Sync device wall-clock time (NTP). Kora refuses new timestamps when drift exceeds five minutes.',\n\tPERSISTENCE_ERROR:\n\t\t'IndexedDB persistence failed; check browser storage settings and available disk quota.',\n\tMISSING_WORKER_URL:\n\t\t'Pass store.workerUrl pointing to sqlite-wasm-worker.js (see create-kora-app templates).',\n\tINVALID_SYNC_URL:\n\t\t'Use ws:// or wss:// for WebSocket transport, or http(s):// for HTTP long-polling.',\n\tAPP_NOT_READY:\n\t\t'Await app.ready before querying or mutating collections, or wrap the tree in <KoraProvider app={app}>.',\n}\n\n/**\n * Returns a suggested fix for a Kora error code, if one is known.\n */\nexport function getKoraErrorFix(code: string): string | undefined {\n\treturn KORA_ERROR_FIX_SUGGESTIONS[code]\n}\n","import { getKoraErrorFix } from './error-fixes'\n\n/**\n * Base error class for all Kora errors.\n * Every error includes a machine-readable code and optional context for debugging.\n */\nexport class KoraError extends Error {\n\tconstructor(\n\t\tmessage: string,\n\t\tpublic readonly code: string,\n\t\tpublic readonly context?: Record<string, unknown>,\n\t) {\n\t\tsuper(message)\n\t\tthis.name = 'KoraError'\n\t}\n\n\t/**\n\t * Actionable hint for resolving this error (from registry or error context).\n\t */\n\tget fix(): string | undefined {\n\t\tconst fromContext = this.context?.fix\n\t\tif (typeof fromContext === 'string' && fromContext.length > 0) {\n\t\t\treturn fromContext\n\t\t}\n\t\treturn getKoraErrorFix(this.code)\n\t}\n}\n\n/**\n * Thrown when schema validation fails during defineSchema() or at app initialization.\n */\nexport class SchemaValidationError extends KoraError {\n\tconstructor(message: string, context?: Record<string, unknown>) {\n\t\tsuper(message, 'SCHEMA_VALIDATION', context)\n\t\tthis.name = 'SchemaValidationError'\n\t}\n}\n\n/**\n * Thrown when an operation is invalid or cannot be created.\n */\nexport class OperationError extends KoraError {\n\tconstructor(message: string, context?: Record<string, unknown>) {\n\t\tsuper(message, 'OPERATION_ERROR', context)\n\t\tthis.name = 'OperationError'\n\t}\n}\n\n/**\n * Thrown when a merge conflict cannot be automatically resolved.\n */\nexport class MergeConflictError extends KoraError {\n\tconstructor(\n\t\tpublic readonly operationA: { id: string; collection: string },\n\t\tpublic readonly operationB: { id: string; collection: string },\n\t\tpublic readonly field: string,\n\t) {\n\t\tsuper(\n\t\t\t`Merge conflict on field \"${field}\" in collection \"${operationA.collection}\"`,\n\t\t\t'MERGE_CONFLICT',\n\t\t\t{ operationA: operationA.id, operationB: operationB.id, field },\n\t\t)\n\t\tthis.name = 'MergeConflictError'\n\t}\n}\n\n/**\n * Thrown when a sync error occurs.\n */\nexport class SyncError extends KoraError {\n\tconstructor(message: string, context?: Record<string, unknown>) {\n\t\tsuper(message, 'SYNC_ERROR', context)\n\t\tthis.name = 'SyncError'\n\t}\n}\n\n/**\n * Thrown when a storage operation fails.\n */\nexport class StorageError extends KoraError {\n\tconstructor(message: string, context?: Record<string, unknown>) {\n\t\tsuper(message, 'STORAGE_ERROR', context)\n\t\tthis.name = 'StorageError'\n\t}\n}\n\n/**\n * Thrown when collection/query APIs are used before {@link KoraApp.ready} resolves.\n */\nexport class AppNotReadyError extends KoraError {\n\tconstructor(detail: string) {\n\t\tsuper(detail, 'APP_NOT_READY', {\n\t\t\tfix: 'Await app.ready, or wrap your UI in <KoraProvider app={app}> before calling useQuery().',\n\t\t})\n\t\tthis.name = 'AppNotReadyError'\n\t}\n}\n\n/**\n * Thrown when the HLC detects excessive clock drift.\n * Drift > 60s: warning. Drift > 5min: this error is thrown, refusing to generate timestamps.\n */\nexport class ClockDriftError extends KoraError {\n\tconstructor(\n\t\tpublic readonly currentHlcTime: number,\n\t\tpublic readonly physicalTime: number,\n\t) {\n\t\tconst driftSeconds = Math.round((currentHlcTime - physicalTime) / 1000)\n\t\tsuper(\n\t\t\t`Clock drift of ${driftSeconds}s detected. Physical time is behind HLC by more than 5 minutes. This indicates a severe clock issue.`,\n\t\t\t'CLOCK_DRIFT',\n\t\t\t{ currentHlcTime, physicalTime, driftSeconds },\n\t\t)\n\t\tthis.name = 'ClockDriftError'\n\t}\n}\n","import { ClockDriftError } from '../errors/errors'\nimport type { HLCTimestamp, TimeSource } from '../types'\n\n/** Default time source using the system clock */\nconst systemTimeSource: TimeSource = { now: () => Date.now() }\n\n/** Maximum allowed drift before warning (60 seconds) */\nconst DRIFT_WARN_MS = 60_000\n\n/** Maximum allowed drift before refusing to generate timestamps (5 minutes) */\nconst DRIFT_ERROR_MS = 5 * 60_000\n\n/**\n * Hybrid Logical Clock implementation based on Kulkarni et al.\n *\n * Provides a total order that respects causality without requiring synchronized clocks.\n * Each call to now() returns a timestamp strictly greater than the previous one.\n *\n * @example\n * ```typescript\n * const clock = new HybridLogicalClock('node-1')\n * const ts1 = clock.now()\n * const ts2 = clock.now()\n * // HybridLogicalClock.compare(ts1, ts2) < 0 (ts1 is earlier)\n * ```\n */\nexport class HybridLogicalClock {\n\tprivate wallTime = 0\n\tprivate logical = 0\n\n\tconstructor(\n\t\tprivate readonly nodeId: string,\n\t\tprivate readonly timeSource: TimeSource = systemTimeSource,\n\t\tprivate readonly onDriftWarning?: (driftMs: number) => void,\n\t) {}\n\n\t/**\n\t * Generate a new timestamp for a local event.\n\t * Guarantees monotonicity: each call returns a timestamp strictly greater than the previous.\n\t *\n\t * @throws {ClockDriftError} If physical time is more than 5 minutes behind the HLC wallTime\n\t */\n\tnow(): HLCTimestamp {\n\t\tconst physicalTime = this.timeSource.now()\n\t\tthis.checkDrift(physicalTime)\n\n\t\tif (physicalTime > this.wallTime) {\n\t\t\tthis.wallTime = physicalTime\n\t\t\tthis.logical = 0\n\t\t} else {\n\t\t\tthis.logical++\n\t\t}\n\n\t\treturn { wallTime: this.wallTime, logical: this.logical, nodeId: this.nodeId }\n\t}\n\n\t/**\n\t * Update clock on receiving a remote timestamp.\n\t * Merges the remote clock state with the local state to maintain causal ordering.\n\t *\n\t * @throws {ClockDriftError} If physical time is more than 5 minutes behind the resulting wallTime\n\t */\n\treceive(remote: HLCTimestamp): HLCTimestamp {\n\t\tconst physicalTime = this.timeSource.now()\n\t\tconst wasColdStart = this.wallTime === 0\n\n\t\tif (physicalTime > this.wallTime && physicalTime > remote.wallTime) {\n\t\t\tthis.wallTime = physicalTime\n\t\t\tthis.logical = 0\n\t\t} else if (remote.wallTime > this.wallTime) {\n\t\t\tthis.wallTime = remote.wallTime\n\t\t\tthis.logical = remote.logical + 1\n\t\t} else if (this.wallTime === remote.wallTime) {\n\t\t\tthis.logical = Math.max(this.logical, remote.logical) + 1\n\t\t} else {\n\t\t\t// this.wallTime > remote.wallTime && this.wallTime >= physicalTime\n\t\t\tthis.logical++\n\t\t}\n\n\t\t// Skip drift check on cold start (wallTime was 0, uninitialized) to avoid\n\t\t// false positives when the first event is a remote timestamp with a wallTime\n\t\t// that differs significantly from local physical time. After initialization,\n\t\t// all subsequent calls to now() and receive() enforce drift protection normally.\n\t\tif (!wasColdStart) {\n\t\t\tthis.checkDrift(physicalTime)\n\t\t}\n\n\t\treturn { wallTime: this.wallTime, logical: this.logical, nodeId: this.nodeId }\n\t}\n\n\t/**\n\t * Compare two timestamps. Returns negative if a < b, positive if a > b, zero if equal.\n\t * Total order: wallTime first, then logical, then nodeId (lexicographic).\n\t */\n\tstatic compare(a: HLCTimestamp, b: HLCTimestamp): number {\n\t\tif (a.wallTime !== b.wallTime) return a.wallTime - b.wallTime\n\t\tif (a.logical !== b.logical) return a.logical - b.logical\n\t\tif (a.nodeId < b.nodeId) return -1\n\t\tif (a.nodeId > b.nodeId) return 1\n\t\treturn 0\n\t}\n\n\t/**\n\t * Serialize an HLC timestamp to a string that sorts lexicographically.\n\t * Format: zero-padded wallTime:logical:nodeId\n\t */\n\tstatic serialize(ts: HLCTimestamp): string {\n\t\tconst wall = ts.wallTime.toString().padStart(15, '0')\n\t\tconst log = ts.logical.toString().padStart(5, '0')\n\t\treturn `${wall}:${log}:${ts.nodeId}`\n\t}\n\n\t/**\n\t * Deserialize an HLC timestamp from its serialized string form.\n\t */\n\tstatic deserialize(s: string): HLCTimestamp {\n\t\tconst parts = s.split(':')\n\t\tif (parts.length < 3) {\n\t\t\tthrow new Error(`Invalid HLC timestamp string: \"${s}\"`)\n\t\t}\n\t\treturn {\n\t\t\twallTime: Number.parseInt(parts[0] ?? '0', 10),\n\t\t\tlogical: Number.parseInt(parts[1] ?? '0', 10),\n\t\t\t// nodeId may contain colons, so rejoin remaining parts\n\t\t\tnodeId: parts.slice(2).join(':'),\n\t\t}\n\t}\n\n\tprivate checkDrift(physicalTime: number): void {\n\t\tconst drift = this.wallTime - physicalTime\n\t\tif (drift > DRIFT_ERROR_MS) {\n\t\t\tthrow new ClockDriftError(this.wallTime, physicalTime)\n\t\t}\n\t\tif (drift > DRIFT_WARN_MS) {\n\t\t\tthis.onDriftWarning?.(drift)\n\t\t}\n\t}\n}\n","/**\n * Tracks the latest operation per collection and within an open transaction\n * to populate {@link Operation.causalDeps} for local mutations.\n */\nexport class CausalTracker {\n\tprivate readonly lastOpIdByCollection = new Map<string, string>()\n\tprivate lastTransactionOpId: string | null = null\n\n\t/**\n\t * Start a new transaction boundary. Clears in-transaction op ids.\n\t */\n\tbeginTransaction(): void {\n\t\tthis.lastTransactionOpId = null\n\t}\n\n\t/**\n\t * Clear the transaction boundary without recording ops (after rollback).\n\t */\n\tclearTransaction(): void {\n\t\tthis.lastTransactionOpId = null\n\t}\n\n\t/**\n\t * Compute causal dependencies for the next operation in a collection.\n\t * Uses direct parents only: collection head and the previous op in the open transaction.\n\t */\n\tnextCausalDeps(collection: string, inTransaction: boolean): string[] {\n\t\tconst deps: string[] = []\n\t\tconst lastInCollection = this.lastOpIdByCollection.get(collection)\n\t\tif (lastInCollection !== undefined) {\n\t\t\tdeps.push(lastInCollection)\n\t\t}\n\t\tif (inTransaction && this.lastTransactionOpId !== null) {\n\t\t\tif (!deps.includes(this.lastTransactionOpId)) {\n\t\t\t\tdeps.push(this.lastTransactionOpId)\n\t\t\t}\n\t\t}\n\t\treturn deps\n\t}\n\n\t/**\n\t * Record an operation after it has been created and assigned an id.\n\t */\n\tafterOperation(collection: string, operationId: string, inTransaction: boolean): void {\n\t\tthis.lastOpIdByCollection.set(collection, operationId)\n\t\tif (inTransaction) {\n\t\t\tthis.lastTransactionOpId = operationId\n\t\t}\n\t}\n}\n","import type { RandomSource } from '../types'\n\nconst defaultRandom: RandomSource = globalThis.crypto as RandomSource\n\n/**\n * Generates a UUID v7 per RFC 9562.\n * UUID v7 encodes a Unix timestamp in milliseconds in the most significant 48 bits,\n * making UUIDs time-sortable while remaining globally unique.\n *\n * @param timestamp - Unix timestamp in milliseconds (defaults to Date.now())\n * @param randomSource - Injectable random source for deterministic testing\n * @returns A UUID v7 string in standard 8-4-4-4-12 format\n *\n * @example\n * ```typescript\n * const id = generateUUIDv7()\n * // \"018f3a5c-7e00-7123-abcd-1234567890ab\"\n * ```\n */\nexport function generateUUIDv7(\n\ttimestamp: number = Date.now(),\n\trandomSource: RandomSource = defaultRandom,\n): string {\n\tconst bytes = new Uint8Array(16)\n\trandomSource.getRandomValues(bytes)\n\n\t// Encode 48-bit timestamp in bytes 0-5\n\tconst ms = Math.max(0, Math.floor(timestamp))\n\tbytes[0] = (ms / 2 ** 40) & 0xff\n\tbytes[1] = (ms / 2 ** 32) & 0xff\n\tbytes[2] = (ms / 2 ** 24) & 0xff\n\tbytes[3] = (ms / 2 ** 16) & 0xff\n\tbytes[4] = (ms / 2 ** 8) & 0xff\n\tbytes[5] = ms & 0xff\n\n\t// Set version 7 (0111) in bits 48-51\n\tbytes[6] = ((bytes[6] ?? 0) & 0x0f) | 0x70\n\n\t// Set variant 10 in bits 64-65\n\tbytes[8] = ((bytes[8] ?? 0) & 0x3f) | 0x80\n\n\treturn formatUUID(bytes)\n}\n\n/**\n * Extracts the Unix timestamp in milliseconds from a UUID v7.\n *\n * @param uuid - A UUID v7 string\n * @returns The encoded Unix timestamp in milliseconds\n */\nexport function extractTimestamp(uuid: string): number {\n\tconst hex = uuid.replace(/-/g, '')\n\t// First 12 hex chars = 48 bits of timestamp\n\tconst high = Number.parseInt(hex.slice(0, 8), 16)\n\tconst low = Number.parseInt(hex.slice(8, 12), 16)\n\treturn high * 2 ** 16 + low\n}\n\n/**\n * Validates whether a string is a valid UUID v7.\n * Checks format, version (7), and variant (10xx).\n *\n * @param uuid - String to validate\n * @returns true if the string is a valid UUID v7\n */\nexport function isValidUUIDv7(uuid: string): boolean {\n\tif (!/^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/i.test(uuid)) {\n\t\treturn false\n\t}\n\tconst hex = uuid.replace(/-/g, '')\n\t// Version must be 7 (nibble at position 12)\n\tif (hex[12] !== '7') return false\n\t// Variant must be 10xx (nibble at position 16 must be 8, 9, a, or b)\n\tconst variantNibble = Number.parseInt(hex[16] ?? '0', 16)\n\treturn variantNibble >= 0x8 && variantNibble <= 0xb\n}\n\nfunction formatUUID(bytes: Uint8Array): string {\n\tconst hex = Array.from(bytes, (b) => b.toString(16).padStart(2, '0')).join('')\n\treturn `${hex.slice(0, 8)}-${hex.slice(8, 12)}-${hex.slice(12, 16)}-${hex.slice(16, 20)}-${hex.slice(20, 32)}`\n}\n","/**\n * Outcome of applying a single operation to materialized storage (local or remote).\n */\nexport const APPLY_RESULTS = ['applied', 'duplicate', 'skipped', 'rejected', 'deferred'] as const\n\nexport type ApplyResult = (typeof APPLY_RESULTS)[number]\n\n/**\n * Structured failure metadata when apply returns `skipped`, `rejected`, or `deferred`.\n */\nexport interface ApplyFailureReason {\n\tcode: string\n\tmessage: string\n\tretriable: boolean\n}\n\n/** Well-known apply failure codes for DevTools and `sync:apply-failed` events. */\nexport const APPLY_FAILURE_CODES = {\n\tAPPLY_FAILED: 'APPLY_FAILED',\n\tAPPLY_SKIPPED: 'APPLY_SKIPPED',\n\tAPPLY_REJECTED: 'APPLY_REJECTED',\n\tAPPLY_DEFERRED: 'APPLY_DEFERRED',\n\tCLOCK_DRIFT: 'CLOCK_DRIFT',\n\tREFERENTIAL_INTEGRITY: 'REFERENTIAL_INTEGRITY',\n\tSCHEMA_MISMATCH: 'SCHEMA_MISMATCH',\n} as const\n\n/**\n * Returns true when the apply outcome should surface as a failure to the developer.\n */\nexport function isApplyFailure(result: ApplyResult): boolean {\n\treturn result === 'skipped' || result === 'rejected' || result === 'deferred'\n}\n\n/**\n * Default failure metadata when the store does not attach a specific reason.\n */\nexport function defaultApplyFailureReason(\n\tresult: Exclude<ApplyResult, 'applied' | 'duplicate'>,\n\toverrides?: Partial<ApplyFailureReason>,\n): ApplyFailureReason {\n\tconst base: ApplyFailureReason =\n\t\tresult === 'deferred'\n\t\t\t? {\n\t\t\t\t\tcode: APPLY_FAILURE_CODES.APPLY_DEFERRED,\n\t\t\t\t\tmessage: 'Operation apply was deferred.',\n\t\t\t\t\tretriable: true,\n\t\t\t\t}\n\t\t\t: result === 'rejected'\n\t\t\t\t? {\n\t\t\t\t\t\tcode: APPLY_FAILURE_CODES.APPLY_REJECTED,\n\t\t\t\t\t\tmessage: 'Operation apply was rejected.',\n\t\t\t\t\t\tretriable: false,\n\t\t\t\t\t}\n\t\t\t\t: {\n\t\t\t\t\t\tcode: APPLY_FAILURE_CODES.APPLY_SKIPPED,\n\t\t\t\t\t\tmessage: 'Operation apply was skipped.',\n\t\t\t\t\t\tretriable: false,\n\t\t\t\t\t}\n\n\treturn { ...base, ...overrides }\n}\n","import type { OperationInput } from '../types'\n\n/**\n * Compute the content-addressed ID for an operation using SHA-256.\n * The same operation content always produces the same hash, ensuring deduplication.\n *\n * @param input - The operation input (without id/timestamp, which are assigned separately)\n * @param timestamp - The HLC timestamp serialized as a string\n * @returns A hex-encoded SHA-256 hash\n */\nexport async function computeOperationId(\n\tinput: OperationInput,\n\ttimestamp: string,\n): Promise<string> {\n\t// Only include atomicOps when present — ensures backward compatibility\n\t// (existing operations without atomicOps produce identical hashes).\n\tconst hashInput: Record<string, unknown> = {\n\t\ttype: input.type,\n\t\tcollection: input.collection,\n\t\trecordId: input.recordId,\n\t\tdata: input.data,\n\t\ttimestamp,\n\t\tnodeId: input.nodeId,\n\t}\n\tif (input.atomicOps !== undefined && Object.keys(input.atomicOps).length > 0) {\n\t\thashInput.atomicOps = input.atomicOps\n\t}\n\tconst canonical = canonicalize(hashInput)\n\tconst encoded = new TextEncoder().encode(canonical)\n\tconst hashBuffer = await globalThis.crypto.subtle.digest('SHA-256', encoded)\n\treturn bufferToHex(hashBuffer)\n}\n\n/**\n * Deterministic JSON serialization with sorted keys.\n * Ensures identical objects always produce identical strings regardless of property insertion order.\n *\n * @param obj - The value to serialize\n * @returns A deterministic JSON string\n */\nexport function canonicalize(obj: unknown): string {\n\tif (obj === null) {\n\t\treturn 'null'\n\t}\n\n\tif (obj === undefined) {\n\t\treturn 'null'\n\t}\n\n\tif (typeof obj !== 'object') {\n\t\treturn JSON.stringify(obj)\n\t}\n\n\tif (Array.isArray(obj)) {\n\t\tconst items = obj.map((item) => canonicalize(item))\n\t\treturn `[${items.join(',')}]`\n\t}\n\n\tconst keys = Object.keys(obj as Record<string, unknown>).sort()\n\tconst pairs = keys.map((key) => {\n\t\tconst value = (obj as Record<string, unknown>)[key]\n\t\t// Serialize undefined values as null for deterministic output\n\t\treturn `${JSON.stringify(key)}:${canonicalize(value === undefined ? null : value)}`\n\t})\n\treturn `{${pairs.join(',')}}`\n}\n\nfunction bufferToHex(buffer: ArrayBuffer): string {\n\tconst bytes = new Uint8Array(buffer)\n\treturn Array.from(bytes, (b) => b.toString(16).padStart(2, '0')).join('')\n}\n","import { HybridLogicalClock } from '../clock/hlc'\nimport { OperationError } from '../errors/errors'\nimport type { HLCTimestamp, Operation, OperationInput } from '../types'\nimport { computeOperationId } from './content-hash'\n\n/**\n * Creates an immutable, content-addressed Operation from the given parameters.\n * The operation is deep-frozen after creation — it cannot be modified.\n *\n * @param input - The operation parameters (without id, which is computed)\n * @param clock - The HLC clock to generate the timestamp\n * @returns A frozen Operation with a content-addressed id\n *\n * @example\n * ```typescript\n * const op = await createOperation({\n * nodeId: 'device-1',\n * type: 'insert',\n * collection: 'todos',\n * recordId: 'rec-1',\n * data: { title: 'Ship it' },\n * previousData: null,\n * sequenceNumber: 1,\n * causalDeps: [],\n * schemaVersion: 1,\n * }, clock)\n * ```\n */\nexport async function createOperation(\n\tinput: OperationInput,\n\tclock: HybridLogicalClock,\n): Promise<Operation> {\n\tvalidateOperationParams(input)\n\n\tconst timestamp = clock.now()\n\tconst serializedTs = HybridLogicalClock.serialize(timestamp)\n\tconst id = await computeOperationId(input, serializedTs)\n\n\tconst operation: Operation = {\n\t\tid,\n\t\tnodeId: input.nodeId,\n\t\ttype: input.type,\n\t\tcollection: input.collection,\n\t\trecordId: input.recordId,\n\t\tdata: input.data ? { ...input.data } : null,\n\t\tpreviousData: input.previousData ? { ...input.previousData } : null,\n\t\ttimestamp,\n\t\tsequenceNumber: input.sequenceNumber,\n\t\tcausalDeps: [...input.causalDeps],\n\t\tschemaVersion: input.schemaVersion,\n\t\t...(input.atomicOps !== undefined && Object.keys(input.atomicOps).length > 0\n\t\t\t? { atomicOps: { ...input.atomicOps } }\n\t\t\t: {}),\n\t\t...(input.transactionId !== undefined ? { transactionId: input.transactionId } : {}),\n\t\t...(input.mutationName !== undefined ? { mutationName: input.mutationName } : {}),\n\t}\n\n\treturn deepFreeze(operation)\n}\n\n/**\n * Validates operation input parameters. Throws OperationError with\n * contextual information on validation failure.\n */\nexport function validateOperationParams(input: OperationInput): void {\n\tif (!input.nodeId || typeof input.nodeId !== 'string') {\n\t\tthrow new OperationError('nodeId is required and must be a non-empty string', {\n\t\t\treceived: input.nodeId,\n\t\t})\n\t}\n\n\tif (!input.type || !['insert', 'update', 'delete'].includes(input.type)) {\n\t\tthrow new OperationError('type must be \"insert\", \"update\", or \"delete\"', {\n\t\t\treceived: input.type,\n\t\t})\n\t}\n\n\tif (!input.collection || typeof input.collection !== 'string') {\n\t\tthrow new OperationError('collection is required and must be a non-empty string', {\n\t\t\treceived: input.collection,\n\t\t})\n\t}\n\n\tif (!input.recordId || typeof input.recordId !== 'string') {\n\t\tthrow new OperationError('recordId is required and must be a non-empty string', {\n\t\t\treceived: input.recordId,\n\t\t})\n\t}\n\n\tif (input.type === 'insert' && input.data === null) {\n\t\tthrow new OperationError('insert operations must include data', {\n\t\t\ttype: input.type,\n\t\t\tcollection: input.collection,\n\t\t})\n\t}\n\n\tif (input.type === 'update' && input.data === null) {\n\t\tthrow new OperationError('update operations must include data with changed fields', {\n\t\t\ttype: input.type,\n\t\t\tcollection: input.collection,\n\t\t})\n\t}\n\n\tif (input.type === 'update' && input.previousData === null) {\n\t\tthrow new OperationError(\n\t\t\t'update operations must include previousData for 3-way merge support',\n\t\t\t{\n\t\t\t\ttype: input.type,\n\t\t\t\tcollection: input.collection,\n\t\t\t},\n\t\t)\n\t}\n\n\tif (input.type === 'delete' && input.data !== null) {\n\t\tthrow new OperationError('delete operations must have null data', {\n\t\t\ttype: input.type,\n\t\t\tcollection: input.collection,\n\t\t})\n\t}\n\n\tif (typeof input.sequenceNumber !== 'number' || input.sequenceNumber < 0) {\n\t\tthrow new OperationError('sequenceNumber must be a non-negative number', {\n\t\t\treceived: input.sequenceNumber,\n\t\t})\n\t}\n\n\tif (!Array.isArray(input.causalDeps)) {\n\t\tthrow new OperationError('causalDeps must be an array of operation IDs', {\n\t\t\treceived: typeof input.causalDeps,\n\t\t})\n\t}\n\n\tif (typeof input.schemaVersion !== 'number' || input.schemaVersion < 1) {\n\t\tthrow new OperationError('schemaVersion must be a positive number', {\n\t\t\treceived: input.schemaVersion,\n\t\t})\n\t}\n}\n\n/**\n * Verify the integrity of an operation by recomputing its content hash.\n * Returns true if the id matches the recomputed hash.\n */\nexport async function verifyOperationIntegrity(op: Operation): Promise<boolean> {\n\tconst input: OperationInput = {\n\t\tnodeId: op.nodeId,\n\t\ttype: op.type,\n\t\tcollection: op.collection,\n\t\trecordId: op.recordId,\n\t\tdata: op.data,\n\t\tpreviousData: op.previousData,\n\t\tsequenceNumber: op.sequenceNumber,\n\t\tcausalDeps: op.causalDeps,\n\t\tschemaVersion: op.schemaVersion,\n\t\t...(op.atomicOps !== undefined ? { atomicOps: op.atomicOps } : {}),\n\t}\n\tconst serializedTs = HybridLogicalClock.serialize(op.timestamp)\n\tconst expectedId = await computeOperationId(input, serializedTs)\n\treturn op.id === expectedId\n}\n\n/**\n * Type guard for Operation interface.\n */\nexport function isValidOperation(value: unknown): value is Operation {\n\tif (typeof value !== 'object' || value === null) return false\n\tconst op = value as Record<string, unknown>\n\treturn (\n\t\ttypeof op.id === 'string' &&\n\t\ttypeof op.nodeId === 'string' &&\n\t\t(op.type === 'insert' || op.type === 'update' || op.type === 'delete') &&\n\t\ttypeof op.collection === 'string' &&\n\t\ttypeof op.recordId === 'string' &&\n\t\ttypeof op.sequenceNumber === 'number' &&\n\t\tArray.isArray(op.causalDeps) &&\n\t\ttypeof op.schemaVersion === 'number' &&\n\t\ttypeof op.timestamp === 'object' &&\n\t\top.timestamp !== null\n\t)\n}\n\nfunction deepFreeze<T>(obj: T): T {\n\tif (typeof obj !== 'object' || obj === null) return obj\n\t// Typed arrays (e.g. richtext Yjs blobs) cannot be frozen in JS engines.\n\tif (ArrayBuffer.isView(obj)) return obj\n\tObject.freeze(obj)\n\tfor (const value of Object.values(obj)) {\n\t\tif (typeof value === 'object' && value !== null && !Object.isFrozen(value)) {\n\t\t\tdeepFreeze(value)\n\t\t}\n\t}\n\treturn obj\n}\n","/**\n * Atomic field operations for intent-preserving updates.\n *\n * Instead of read-modify-write patterns, developers express intent:\n * ```typescript\n * await app.stock.update(id, { quantity: op.increment(-5) })\n * ```\n *\n * The operation intent is preserved in the Operation for merge:\n * concurrent increments compose (sum of deltas) instead of LWW.\n */\n\nimport type { AtomicOp, AtomicOpType } from '../types'\n\n// Re-export for convenience\nexport type { AtomicOp, AtomicOpType }\n\n/**\n * Sentinel marker for detecting atomic op objects in update data.\n * Uses Symbol.for() so the sentinel survives module boundary crossings.\n */\nconst KORA_ATOMIC_OP = Symbol.for('kora.atomic_op')\n\n/** String key used for the sentinel symbol — exported for internal use */\nexport const KORA_ATOMIC_OP_KEY: typeof KORA_ATOMIC_OP = KORA_ATOMIC_OP\n\n/**\n * Sentinel object returned by op.* helpers.\n * Detected by Collection.update() and resolved to concrete values.\n */\nexport interface AtomicOpSentinel {\n\treadonly [KORA_ATOMIC_OP_KEY]: true\n\treadonly type: AtomicOpType\n\treadonly value: unknown\n}\n\n/**\n * Type guard: checks whether a value is an atomic op sentinel.\n *\n * @param value - Any value to check\n * @returns true if the value is an AtomicOpSentinel\n */\nexport function isAtomicOp(value: unknown): value is AtomicOpSentinel {\n\treturn (\n\t\ttypeof value === 'object' &&\n\t\tvalue !== null &&\n\t\tKORA_ATOMIC_OP in value &&\n\t\t(value as Record<symbol, unknown>)[KORA_ATOMIC_OP] === true\n\t)\n}\n\n/**\n * Resolve an atomic op sentinel against a current value to produce a concrete result.\n *\n * @param currentValue - The current value of the field in the database\n * @param sentinel - The atomic op sentinel from the developer's update call\n * @returns The resolved concrete value\n */\nexport function resolveAtomicOp(currentValue: unknown, sentinel: AtomicOpSentinel): unknown {\n\tswitch (sentinel.type) {\n\t\tcase 'increment': {\n\t\t\tconst current = typeof currentValue === 'number' ? currentValue : 0\n\t\t\tconst operand = sentinel.value as number\n\t\t\treturn current + operand\n\t\t}\n\t\tcase 'max': {\n\t\t\tconst current = typeof currentValue === 'number' ? currentValue : Number.NEGATIVE_INFINITY\n\t\t\treturn Math.max(current, sentinel.value as number)\n\t\t}\n\t\tcase 'min': {\n\t\t\tconst current = typeof currentValue === 'number' ? currentValue : Number.POSITIVE_INFINITY\n\t\t\treturn Math.min(current, sentinel.value as number)\n\t\t}\n\t\tcase 'append': {\n\t\t\tconst current = Array.isArray(currentValue) ? [...currentValue] : []\n\t\t\tcurrent.push(sentinel.value)\n\t\t\treturn current\n\t\t}\n\t\tcase 'remove': {\n\t\t\tif (!Array.isArray(currentValue)) return []\n\t\t\treturn currentValue.filter((item) => item !== sentinel.value)\n\t\t}\n\t}\n}\n\nfunction createSentinel(type: AtomicOpType, value: unknown): AtomicOpSentinel {\n\treturn Object.freeze({\n\t\t[KORA_ATOMIC_OP]: true as const,\n\t\ttype,\n\t\tvalue,\n\t})\n}\n\n/**\n * Atomic operation helpers. Use these in collection.update() calls\n * to express intent-preserving mutations.\n *\n * @example\n * ```typescript\n * import { op } from 'korajs'\n *\n * // Increment a counter (works correctly with concurrent updates)\n * await app.stock.update(id, { quantity: op.increment(-5) })\n *\n * // Keep the maximum value\n * await app.scores.update(id, { highScore: op.max(newScore) })\n *\n * // Append to an array\n * await app.todos.update(id, { tags: op.append('urgent') })\n * ```\n */\nexport const op = {\n\t/**\n\t * Increment a number field by the given amount.\n\t * Concurrent increments compose: the sum of all deltas is applied to the base.\n\t *\n\t * @param n - The amount to increment (use negative values to decrement)\n\t */\n\tincrement(n: number): AtomicOpSentinel {\n\t\treturn createSentinel('increment', n)\n\t},\n\n\t/**\n\t * Decrement a number field by the given amount.\n\t * Syntactic sugar for `op.increment(-n)`.\n\t *\n\t * @param n - The amount to decrement\n\t */\n\tdecrement(n: number): AtomicOpSentinel {\n\t\treturn createSentinel('increment', -n)\n\t},\n\n\t/**\n\t * Set the field to the maximum of the current value and the given value.\n\t * Concurrent max operations take the maximum of all values.\n\t *\n\t * @param n - The value to compare against the current value\n\t */\n\tmax(n: number): AtomicOpSentinel {\n\t\treturn createSentinel('max', n)\n\t},\n\n\t/**\n\t * Set the field to the minimum of the current value and the given value.\n\t * Concurrent min operations take the minimum of all values.\n\t *\n\t * @param n - The value to compare against the current value\n\t */\n\tmin(n: number): AtomicOpSentinel {\n\t\treturn createSentinel('min', n)\n\t},\n\n\t/**\n\t * Append an item to an array field.\n\t * Concurrent appends include all appended items.\n\t *\n\t * @param item - The item to append to the array\n\t */\n\tappend(item: unknown): AtomicOpSentinel {\n\t\treturn createSentinel('append', item)\n\t},\n\n\t/**\n\t * Remove an item from an array field (by value equality).\n\t * Concurrent removes of the same item are idempotent.\n\t *\n\t * @param item - The item to remove from the array\n\t */\n\tremove(item: unknown): AtomicOpSentinel {\n\t\treturn createSentinel('remove', item)\n\t},\n}\n\n/**\n * Extract the serializable AtomicOp from a sentinel (strips the Symbol marker).\n *\n * @param sentinel - The atomic op sentinel\n * @returns A plain object suitable for JSON serialization\n */\nexport function toAtomicOp(sentinel: AtomicOpSentinel): AtomicOp {\n\treturn { type: sentinel.type, value: sentinel.value }\n}\n","import type { SchemaDefinition, SyncRuleDefinition } from '../types'\n\n/**\n * Returns true when the schema declares partial sync rules at the root level.\n */\nexport function hasSchemaSyncRules(schema: SchemaDefinition): boolean {\n\treturn schema.sync !== undefined && Object.keys(schema.sync).length > 0\n}\n\n/**\n * Resolve field → scope-value-key bindings for a collection.\n *\n * Sync rules take precedence over legacy `collection.scope` arrays.\n * Returns `null` when the collection has no sync filtering configured.\n */\nexport function getCollectionScopeBindings(\n\tschema: SchemaDefinition,\n\tcollectionName: string,\n): Record<string, string> | null {\n\tconst syncRule = schema.sync?.[collectionName]\n\tif (syncRule && Object.keys(syncRule.where).length > 0) {\n\t\treturn { ...syncRule.where }\n\t}\n\n\tconst scopeFields = schema.collections[collectionName]?.scope ?? []\n\tif (scopeFields.length === 0) {\n\t\treturn null\n\t}\n\n\tconst bindings: Record<string, string> = {}\n\tfor (const field of scopeFields) {\n\t\tbindings[field] = field\n\t}\n\treturn bindings\n}\n\n/**\n * Returns whether a collection participates in sync filtering for this schema.\n */\nexport function isCollectionSyncScoped(schema: SchemaDefinition, collectionName: string): boolean {\n\tif (hasSchemaSyncRules(schema)) {\n\t\tif (schema.sync?.[collectionName]) {\n\t\t\treturn true\n\t\t}\n\t\tconst legacyScope = schema.collections[collectionName]?.scope ?? []\n\t\treturn legacyScope.length > 0\n\t}\n\n\treturn getCollectionScopeBindings(schema, collectionName) !== null\n}\n\n/**\n * Collect unique scope value keys referenced by sync rules and legacy scope fields.\n */\nexport function collectSchemaScopeValueKeys(schema: SchemaDefinition): string[] {\n\tconst keys = new Set<string>()\n\n\tfor (const collection of Object.values(schema.collections)) {\n\t\tfor (const field of collection.scope) {\n\t\t\tkeys.add(field)\n\t\t}\n\t}\n\n\tif (schema.sync) {\n\t\tfor (const rule of Object.values(schema.sync)) {\n\t\t\tfor (const scopeKey of Object.values(rule.where)) {\n\t\t\t\tkeys.add(scopeKey)\n\t\t\t}\n\t\t}\n\t}\n\n\treturn [...keys]\n}\n\n/**\n * Normalize developer sync rule input into internal bindings.\n */\nexport function normalizeSyncRuleWhere(\n\tcollectionName: string,\n\twhere: Record<string, boolean | string>,\n): SyncRuleDefinition['where'] {\n\tconst normalized: Record<string, string> = {}\n\n\tfor (const [field, scopeKey] of Object.entries(where)) {\n\t\tif (scopeKey === true) {\n\t\t\tnormalized[field] = field\n\t\t\tcontinue\n\t\t}\n\n\t\tif (typeof scopeKey === 'string' && scopeKey.length > 0) {\n\t\t\tnormalized[field] = scopeKey\n\t\t\tcontinue\n\t\t}\n\n\t\tthrow new Error(\n\t\t\t`Invalid sync rule for collection \"${collectionName}\": where.${field} must be true or a non-empty scope key string`,\n\t\t)\n\t}\n\n\treturn normalized\n}\n","import { SchemaValidationError } from '../errors/errors'\nimport type {\n\tFieldDescriptor,\n\tSchemaDefinition,\n\tStateMachineConstraint,\n\tTransitionMap,\n\tTransitionValidationResult,\n} from '../types'\n\n/**\n * Validates whether a transition from one state to another is allowed\n * by the given state machine constraint.\n *\n * @param constraint - The state machine constraint defining allowed transitions\n * @param fromValue - The current state value (before the transition)\n * @param toValue - The target state value (after the transition)\n * @returns A TransitionValidationResult describing whether the transition is valid\n *\n * @example\n * ```typescript\n * const constraint: StateMachineConstraint = {\n * field: 'status',\n * collection: 'orders',\n * transitions: {\n * draft: ['submitted', 'cancelled'],\n * submitted: ['approved'],\n * approved: [],\n * },\n * }\n *\n * const result = validateTransition(constraint, 'draft', 'submitted')\n * // { valid: true, from: 'draft', to: 'submitted', field: 'status',\n * // collection: 'orders', allowedTargets: ['submitted', 'cancelled'] }\n * ```\n */\nexport function validateTransition(\n\tconstraint: StateMachineConstraint,\n\tfromValue: unknown,\n\ttoValue: unknown,\n): TransitionValidationResult {\n\tconst from = String(fromValue)\n\tconst to = String(toValue)\n\tconst allowedTargets = constraint.transitions[from] ?? []\n\n\treturn {\n\t\tvalid: allowedTargets.includes(to),\n\t\tfrom,\n\t\tto,\n\t\tfield: constraint.field,\n\t\tcollection: constraint.collection,\n\t\tallowedTargets,\n\t}\n}\n\n/**\n * Extracts all state machine constraints from a schema definition.\n * Scans every collection for enum fields that have transition rules declared\n * via the `.transitions()` builder method.\n *\n * @param schema - The schema definition to extract constraints from\n * @returns An array of StateMachineConstraint objects, one per enum field with transitions\n *\n * @example\n * ```typescript\n * const schema = defineSchema({\n * version: 1,\n * collections: {\n * orders: {\n * fields: {\n * status: t.enum(['draft', 'submitted']).transitions({\n * draft: ['submitted'],\n * submitted: [],\n * }),\n * },\n * },\n * },\n * })\n *\n * const constraints = buildStateMachineConstraints(schema)\n * // [{ field: 'status', collection: 'orders', transitions: { draft: ['submitted'], submitted: [] } }]\n * ```\n */\nexport function buildStateMachineConstraints(schema: SchemaDefinition): StateMachineConstraint[] {\n\tconst constraints: StateMachineConstraint[] = []\n\n\tfor (const [collectionName, collection] of Object.entries(schema.collections)) {\n\t\tfor (const [fieldName, descriptor] of Object.entries(collection.fields)) {\n\t\t\tif (descriptor.kind === 'enum' && descriptor.transitions !== null) {\n\t\t\t\tconstraints.push({\n\t\t\t\t\tfield: fieldName,\n\t\t\t\t\tcollection: collectionName,\n\t\t\t\t\ttransitions: descriptor.transitions,\n\t\t\t\t})\n\t\t\t}\n\t\t}\n\t}\n\n\treturn constraints\n}\n\n/**\n * Finds the state machine constraint for a specific field in a specific collection,\n * if one exists.\n *\n * @param schema - The schema definition to search\n * @param collection - The collection name\n * @param field - The field name\n * @returns The TransitionMap if the field has transitions declared, or null otherwise\n */\nexport function getTransitionMap(\n\tschema: SchemaDefinition,\n\tcollection: string,\n\tfield: string,\n): TransitionMap | null {\n\tconst collectionDef = schema.collections[collection]\n\tif (!collectionDef) {\n\t\treturn null\n\t}\n\tconst fieldDef = collectionDef.fields[field]\n\tif (!fieldDef || fieldDef.kind !== 'enum') {\n\t\treturn null\n\t}\n\treturn fieldDef.transitions\n}\n\n/**\n * Validates a state machine definition against a collection's fields during schema building.\n * Called by defineSchema() to ensure the state machine is well-formed.\n *\n * @param collectionName - Name of the collection for error messages\n * @param sm - The state machine input definition\n * @param fields - The built field descriptors for the collection\n * @throws {SchemaValidationError} If the state machine definition is invalid\n */\nexport function validateStateMachineDefinition(\n\tcollectionName: string,\n\tsm: { field: string; transitions: Record<string, string[]>; onInvalidTransition: string },\n\tfields: Record<string, FieldDescriptor>,\n): void {\n\tconst fieldDef = fields[sm.field]\n\tif (!fieldDef) {\n\t\tthrow new SchemaValidationError(\n\t\t\t`State machine field \"${sm.field}\" does not exist in collection \"${collectionName}\". Available fields: ${Object.keys(fields).join(', ')}`,\n\t\t\t{ collection: collectionName, field: sm.field },\n\t\t)\n\t}\n\tif (fieldDef.kind !== 'enum') {\n\t\tthrow new SchemaValidationError(\n\t\t\t`State machine field \"${sm.field}\" in collection \"${collectionName}\" must be an enum field, but got \"${fieldDef.kind}\"`,\n\t\t\t{ collection: collectionName, field: sm.field, kind: fieldDef.kind },\n\t\t)\n\t}\n\tconst enumValues = fieldDef.enumValues\n\tif (!enumValues || enumValues.length === 0) {\n\t\tthrow new SchemaValidationError(\n\t\t\t`State machine field \"${sm.field}\" in collection \"${collectionName}\" has no enum values defined`,\n\t\t\t{ collection: collectionName, field: sm.field },\n\t\t)\n\t}\n\tconst validValues = new Set(enumValues)\n\tfor (const [state, targets] of Object.entries(sm.transitions)) {\n\t\tif (!validValues.has(state)) {\n\t\t\tthrow new SchemaValidationError(\n\t\t\t\t`State machine transition source \"${state}\" is not a valid enum value for field \"${sm.field}\" in collection \"${collectionName}\". Valid values: ${[...validValues].join(', ')}`,\n\t\t\t\t{ collection: collectionName, field: sm.field, state },\n\t\t\t)\n\t\t}\n\t\tfor (const target of targets) {\n\t\t\tif (!validValues.has(target)) {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`State machine transition target \"${target}\" is not a valid enum value for field \"${sm.field}\" in collection \"${collectionName}\". Valid values: ${[...validValues].join(', ')}`,\n\t\t\t\t\t{ collection: collectionName, field: sm.field, state, target },\n\t\t\t\t)\n\t\t\t}\n\t\t}\n\t}\n\tif (sm.onInvalidTransition !== 'reject' && sm.onInvalidTransition !== 'last-valid-state') {\n\t\tthrow new SchemaValidationError(\n\t\t\t`State machine onInvalidTransition must be \"reject\" or \"last-valid-state\", got \"${sm.onInvalidTransition}\" in collection \"${collectionName}\"`,\n\t\t\t{ collection: collectionName, onInvalidTransition: sm.onInvalidTransition },\n\t\t)\n\t}\n}\n","import { SchemaValidationError } from '../errors/errors'\nimport type { MigrationDefinition } from '../migrations/migration-builder'\nimport { normalizeSyncRuleWhere } from '../scopes/sync-scope-bindings'\nimport { validateStateMachineDefinition } from '../state-machine/state-machine'\nimport type {\n\tCollectionDefinition,\n\tConstraint,\n\tCustomResolver,\n\tFieldDescriptor,\n\tRelationDefinition,\n\tSchemaDefinition,\n\tStateMachineDefinition,\n\tSyncRuleDefinition,\n} from '../types'\nimport type { FieldBuilder } from './types'\n\n/** Valid collection name pattern: lowercase, alphanumeric + underscore, starting with letter */\nconst COLLECTION_NAME_RE = /^[a-z][a-z0-9_]*$/\n\n/** Valid field name pattern: camelCase allowed (e.g. createdAt, dueDate) */\nconst FIELD_NAME_RE = /^[a-z][a-zA-Z0-9_]*$/\n\n/** Reserved field names that cannot be used in schemas */\nconst RESERVED_FIELDS = new Set(['id', '_created_at', '_updated_at', '_version', '_deleted'])\n\n/**\n * Input shape for defineSchema() — what the developer writes.\n */\nexport interface SchemaInput {\n\tversion: number\n\tcollections: Record<string, CollectionInput>\n\trelations?: Record<string, RelationInput>\n\t/** Schema migrations keyed by target version number. */\n\tmigrations?: Record<number, MigrationDefinition>\n\t/**\n\t * Declarative partial-sync rules.\n\t *\n\t * @example\n\t * ```typescript\n\t * sync: {\n\t * todos: { where: { userId: true, orgId: true } },\n\t * projects: { where: { orgId: true } },\n\t * }\n\t * ```\n\t */\n\tsync?: Record<string, SyncRuleInput>\n}\n\n/**\n * Developer input for a collection sync rule.\n */\nexport interface SyncRuleInput {\n\t/**\n\t * Field filters bound to scope values.\n\t * Use `true` to bind a field to a scope value with the same name.\n\t * Use a string to bind to a different scope value key.\n\t */\n\twhere: Record<string, boolean | string>\n}\n\nexport interface StateMachineInput {\n\t/** The enum field this state machine controls */\n\tfield: string\n\t/** Map of state to allowed next states */\n\ttransitions: Record<string, string[]>\n\t/** What to do when an invalid transition is attempted */\n\tonInvalidTransition: 'reject' | 'last-valid-state'\n}\n\nexport interface CollectionInput {\n\t// biome-ignore lint/suspicious/noExplicitAny: Required for TypeScript conditional type inference\n\tfields: Record<string, FieldBuilder<any, any, any>>\n\tindexes?: string[]\n\tconstraints?: ConstraintInput[]\n\tresolve?: Record<string, CustomResolver>\n\t/** Scope fields for sync filtering. Only records matching the client's scope values are synced. */\n\tscope?: string[]\n\t/** State machine definition constraining transitions on an enum field */\n\tstateMachine?: StateMachineInput\n}\n\nexport interface ConstraintInput {\n\ttype: 'unique' | 'capacity' | 'referential'\n\tfields: string[]\n\twhere?: Record<string, unknown>\n\tonConflict:\n\t\t| 'first-write-wins'\n\t\t| 'last-write-wins'\n\t\t| 'priority-field'\n\t\t| 'server-decides'\n\t\t| 'custom'\n\tpriorityField?: string\n\tresolve?: (local: unknown, remote: unknown, base: unknown) => unknown\n}\n\nexport interface RelationInput {\n\tfrom: string\n\tto: string\n\ttype: 'one-to-one' | 'one-to-many' | 'many-to-one' | 'many-to-many'\n\tfield: string\n\tonDelete: 'cascade' | 'set-null' | 'restrict' | 'no-action'\n}\n\n/**\n * Validates and builds a SchemaDefinition from developer input.\n * This is the primary developer-facing function for defining a schema.\n *\n * @param input - The schema definition using type builders\n * @returns A validated SchemaDefinition ready for use by the framework\n * @throws {SchemaValidationError} If the schema is invalid\n *\n * @example\n * ```typescript\n * import { defineSchema, t } from '@korajs/core'\n *\n * const schema = defineSchema({\n * version: 1,\n * collections: {\n * todos: {\n * fields: {\n * title: t.string(),\n * completed: t.boolean().default(false),\n * }\n * }\n * }\n * })\n * ```\n */\n/**\n * Schema definition with a phantom type brand preserving the original input shape.\n * The `__input` property exists only at the type level for inference — no runtime cost.\n */\nexport type TypedSchemaDefinition<T extends SchemaInput = SchemaInput> = SchemaDefinition & {\n\treadonly __input: T\n}\n\nexport function defineSchema<const T extends SchemaInput>(input: T): TypedSchemaDefinition<T> {\n\tvalidateVersion(input.version)\n\n\tconst collections: Record<string, CollectionDefinition> = {}\n\n\tfor (const [name, collectionInput] of Object.entries(input.collections)) {\n\t\tvalidateCollectionName(name)\n\t\tcollections[name] = buildCollection(name, collectionInput)\n\t}\n\n\tif (Object.keys(collections).length === 0) {\n\t\tthrow new SchemaValidationError('Schema must define at least one collection')\n\t}\n\n\tconst relations: Record<string, RelationDefinition> = {}\n\tif (input.relations) {\n\t\tfor (const [name, relationInput] of Object.entries(input.relations)) {\n\t\t\tvalidateRelation(name, relationInput, collections)\n\t\t\trelations[name] = { ...relationInput }\n\t\t}\n\t}\n\n\tconst migrations: Record<number, MigrationDefinition> = {}\n\tif (input.migrations) {\n\t\tfor (const [versionStr, migration] of Object.entries(input.migrations)) {\n\t\t\tconst version = Number(versionStr)\n\t\t\tif (!Number.isInteger(version) || version < 2) {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Migration key \"${versionStr}\" is invalid. Must be an integer >= 2 (version 1 is the initial schema).`,\n\t\t\t\t\t{ version: versionStr },\n\t\t\t\t)\n\t\t\t}\n\t\t\tif (version > input.version) {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Migration version ${version} exceeds schema version ${input.version}. Migrations must target versions <= schema version.`,\n\t\t\t\t\t{ migrationVersion: version, schemaVersion: input.version },\n\t\t\t\t)\n\t\t\t}\n\t\t\tif (!migration.steps || migration.steps.length === 0) {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Migration for version ${version} has no steps. Use migrate() to define at least one step.`,\n\t\t\t\t\t{ version },\n\t\t\t\t)\n\t\t\t}\n\t\t\tmigrations[version] = migration\n\t\t}\n\t}\n\n\tconst sync = buildSyncRules(input.sync, collections)\n\tapplySyncRulesToCollectionScope(collections, sync)\n\n\treturn {\n\t\tversion: input.version,\n\t\tcollections,\n\t\trelations,\n\t\tmigrations,\n\t\t...(sync ? { sync } : {}),\n\t} as TypedSchemaDefinition<T>\n}\n\nfunction validateVersion(version: number): void {\n\tif (typeof version !== 'number' || !Number.isInteger(version) || version < 1) {\n\t\tthrow new SchemaValidationError('Schema version must be a positive integer', {\n\t\t\treceived: version,\n\t\t})\n\t}\n}\n\nfunction validateCollectionName(name: string): void {\n\tif (!COLLECTION_NAME_RE.test(name)) {\n\t\tthrow new SchemaValidationError(\n\t\t\t`Collection name \"${name}\" is invalid. Must be lowercase, start with a letter, and contain only letters, numbers, and underscores.`,\n\t\t\t{ collection: name },\n\t\t)\n\t}\n}\n\nfunction buildCollection(name: string, input: CollectionInput): CollectionDefinition {\n\tconst fields: Record<string, FieldDescriptor> = {}\n\n\tif (!input.fields || Object.keys(input.fields).length === 0) {\n\t\tthrow new SchemaValidationError(`Collection \"${name}\" must define at least one field`, {\n\t\t\tcollection: name,\n\t\t})\n\t}\n\n\tfor (const [fieldName, builder] of Object.entries(input.fields)) {\n\t\tvalidateFieldName(name, fieldName)\n\t\tfields[fieldName] = builder._build()\n\t}\n\n\tconst indexes = input.indexes ?? []\n\tfor (const indexField of indexes) {\n\t\tif (!(indexField in fields)) {\n\t\t\tthrow new SchemaValidationError(\n\t\t\t\t`Index field \"${indexField}\" does not exist in collection \"${name}\". Available fields: ${Object.keys(fields).join(', ')}`,\n\t\t\t\t{ collection: name, field: indexField },\n\t\t\t)\n\t\t}\n\t}\n\n\tconst constraints: Constraint[] = []\n\tif (input.constraints) {\n\t\tfor (const constraintInput of input.constraints) {\n\t\t\tvalidateConstraint(name, constraintInput, fields)\n\t\t\tconstraints.push({ ...constraintInput })\n\t\t}\n\t}\n\n\tconst resolvers: Record<string, CustomResolver> = {}\n\tif (input.resolve) {\n\t\tfor (const [fieldName, resolver] of Object.entries(input.resolve)) {\n\t\t\tif (!(fieldName in fields)) {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Resolver for field \"${fieldName}\" does not exist in collection \"${name}\". Available fields: ${Object.keys(fields).join(', ')}`,\n\t\t\t\t\t{ collection: name, field: fieldName },\n\t\t\t\t)\n\t\t\t}\n\t\t\tif (typeof resolver !== 'function') {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Resolver for field \"${fieldName}\" in collection \"${name}\" must be a function`,\n\t\t\t\t\t{ collection: name, field: fieldName },\n\t\t\t\t)\n\t\t\t}\n\t\t\tresolvers[fieldName] = resolver\n\t\t}\n\t}\n\n\tconst scope: string[] = []\n\tif (input.scope) {\n\t\tfor (const scopeField of input.scope) {\n\t\t\tif (!(scopeField in fields)) {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Scope field \"${scopeField}\" does not exist in collection \"${name}\". Available fields: ${Object.keys(fields).join(', ')}`,\n\t\t\t\t\t{ collection: name, field: scopeField },\n\t\t\t\t)\n\t\t\t}\n\t\t\tscope.push(scopeField)\n\t\t}\n\t}\n\n\tlet stateMachine: StateMachineDefinition | undefined\n\tif (input.stateMachine) {\n\t\tvalidateStateMachineDefinition(name, input.stateMachine, fields)\n\t\tstateMachine = { ...input.stateMachine }\n\t}\n\n\treturn { fields, indexes, constraints, resolvers, scope, stateMachine }\n}\n\nfunction buildSyncRules(\n\tsyncInput: SchemaInput['sync'],\n\tcollections: Record<string, CollectionDefinition>,\n): Record<string, SyncRuleDefinition> | undefined {\n\tif (!syncInput) {\n\t\treturn undefined\n\t}\n\n\tconst sync: Record<string, SyncRuleDefinition> = {}\n\n\tfor (const [collectionName, ruleInput] of Object.entries(syncInput)) {\n\t\tif (!(collectionName in collections)) {\n\t\t\tthrow new SchemaValidationError(\n\t\t\t\t`Sync rule references collection \"${collectionName}\" which does not exist. Available collections: ${Object.keys(collections).join(', ')}`,\n\t\t\t\t{ collection: collectionName },\n\t\t\t)\n\t\t}\n\n\t\tif (!ruleInput.where || Object.keys(ruleInput.where).length === 0) {\n\t\t\tthrow new SchemaValidationError(\n\t\t\t\t`Sync rule for collection \"${collectionName}\" must declare at least one where binding`,\n\t\t\t\t{ collection: collectionName },\n\t\t\t)\n\t\t}\n\n\t\tconst collection = collections[collectionName]\n\t\tif (!collection) {\n\t\t\tcontinue\n\t\t}\n\n\t\tfor (const fieldName of Object.keys(ruleInput.where)) {\n\t\t\tif (!(fieldName in collection.fields)) {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Sync rule where field \"${fieldName}\" does not exist in collection \"${collectionName}\". Available fields: ${Object.keys(collection.fields).join(', ')}`,\n\t\t\t\t\t{ collection: collectionName, field: fieldName },\n\t\t\t\t)\n\t\t\t}\n\t\t}\n\n\t\ttry {\n\t\t\tsync[collectionName] = { where: normalizeSyncRuleWhere(collectionName, ruleInput.where) }\n\t\t} catch (error) {\n\t\t\tthrow new SchemaValidationError(\n\t\t\t\terror instanceof Error ? error.message : 'Invalid sync rule',\n\t\t\t\t{ collection: collectionName },\n\t\t\t)\n\t\t}\n\t}\n\n\treturn sync\n}\n\nfunction applySyncRulesToCollectionScope(\n\tcollections: Record<string, CollectionDefinition>,\n\tsync: Record<string, SyncRuleDefinition> | undefined,\n): void {\n\tif (!sync) {\n\t\treturn\n\t}\n\n\tfor (const [collectionName, rule] of Object.entries(sync)) {\n\t\tconst collection = collections[collectionName]\n\t\tif (!collection) {\n\t\t\tcontinue\n\t\t}\n\n\t\tfor (const fieldName of Object.keys(rule.where)) {\n\t\t\tif (!collection.scope.includes(fieldName)) {\n\t\t\t\tcollection.scope.push(fieldName)\n\t\t\t}\n\t\t}\n\t}\n}\n\nfunction validateFieldName(collection: string, fieldName: string): void {\n\tif (RESERVED_FIELDS.has(fieldName)) {\n\t\tthrow new SchemaValidationError(\n\t\t\t`Field name \"${fieldName}\" is reserved in collection \"${collection}\". Reserved fields: ${[...RESERVED_FIELDS].join(', ')}`,\n\t\t\t{ collection, field: fieldName },\n\t\t)\n\t}\n\tif (!FIELD_NAME_RE.test(fieldName)) {\n\t\tthrow new SchemaValidationError(\n\t\t\t`Field name \"${fieldName}\" in collection \"${collection}\" is invalid. Must start with a lowercase letter and contain only letters, numbers, and underscores.`,\n\t\t\t{ collection, field: fieldName },\n\t\t)\n\t}\n}\n\nfunction validateConstraint(\n\tcollection: string,\n\tconstraint: ConstraintInput,\n\tfields: Record<string, FieldDescriptor>,\n): void {\n\tfor (const field of constraint.fields) {\n\t\tif (!(field in fields)) {\n\t\t\tthrow new SchemaValidationError(\n\t\t\t\t`Constraint references field \"${field}\" which does not exist in collection \"${collection}\". Available fields: ${Object.keys(fields).join(', ')}`,\n\t\t\t\t{ collection, field },\n\t\t\t)\n\t\t}\n\t}\n\n\tif (constraint.onConflict === 'priority-field' && !constraint.priorityField) {\n\t\tthrow new SchemaValidationError(\n\t\t\t`Constraint with \"priority-field\" onConflict strategy in collection \"${collection}\" requires a priorityField`,\n\t\t\t{ collection },\n\t\t)\n\t}\n\n\tif (constraint.onConflict === 'priority-field' && constraint.priorityField) {\n\t\tif (!(constraint.priorityField in fields)) {\n\t\t\tthrow new SchemaValidationError(\n\t\t\t\t`Constraint priorityField \"${constraint.priorityField}\" does not exist in collection \"${collection}\"`,\n\t\t\t\t{ collection, field: constraint.priorityField },\n\t\t\t)\n\t\t}\n\t}\n\n\tif (constraint.onConflict === 'custom' && typeof constraint.resolve !== 'function') {\n\t\tthrow new SchemaValidationError(\n\t\t\t`Constraint with \"custom\" onConflict strategy in collection \"${collection}\" requires a resolve function`,\n\t\t\t{ collection },\n\t\t)\n\t}\n}\n\nfunction validateRelation(\n\tname: string,\n\trelation: RelationInput,\n\tcollections: Record<string, CollectionDefinition>,\n): void {\n\tif (!(relation.from in collections)) {\n\t\tthrow new SchemaValidationError(\n\t\t\t`Relation \"${name}\" references source collection \"${relation.from}\" which does not exist. Available collections: ${Object.keys(collections).join(', ')}`,\n\t\t\t{ relation: name, collection: relation.from },\n\t\t)\n\t}\n\n\tif (!(relation.to in collections)) {\n\t\tthrow new SchemaValidationError(\n\t\t\t`Relation \"${name}\" references target collection \"${relation.to}\" which does not exist. Available collections: ${Object.keys(collections).join(', ')}`,\n\t\t\t{ relation: name, collection: relation.to },\n\t\t)\n\t}\n\n\tconst fromCollection = collections[relation.from]\n\tif (fromCollection && !(relation.field in fromCollection.fields)) {\n\t\tthrow new SchemaValidationError(\n\t\t\t`Relation \"${name}\" references field \"${relation.field}\" which does not exist in collection \"${relation.from}\". Available fields: ${Object.keys(fromCollection.fields).join(', ')}`,\n\t\t\t{ relation: name, collection: relation.from, field: relation.field },\n\t\t)\n\t}\n}\n","import type {\n\tCollectionDefinition,\n\tFieldDescriptor,\n\tRelationDefinition,\n\tSchemaDefinition,\n} from '../types'\n\n/**\n * Generate CREATE TABLE and CREATE INDEX SQL for a single collection.\n *\n * @param collectionName - The collection name\n * @param collection - The collection definition\n * @param relations - Optional relations for FK references\n * @returns An array of SQL statements (CREATE TABLE + CREATE INDEX)\n */\nexport function generateSQL(\n\tcollectionName: string,\n\tcollection: CollectionDefinition,\n\trelations?: Record<string, RelationDefinition>,\n): string[] {\n\tconst statements: string[] = []\n\tconst columns: string[] = ['id TEXT PRIMARY KEY NOT NULL']\n\n\t// Track which fields already have indexes\n\tconst indexedFields = new Set(collection.indexes)\n\n\t// Collect FK fields for auto-indexing\n\tconst fkFields: string[] = []\n\n\tfor (const [fieldName, descriptor] of Object.entries(collection.fields)) {\n\t\tlet colDef = columnDefinition(fieldName, descriptor)\n\n\t\t// Add FK reference if a relation exists for this field\n\t\tif (relations) {\n\t\t\tfor (const rel of Object.values(relations)) {\n\t\t\t\tif (rel.from === collectionName && rel.field === fieldName) {\n\t\t\t\t\tcolDef += ` REFERENCES ${rel.to}(id)`\n\t\t\t\t\tfkFields.push(fieldName)\n\t\t\t\t\tbreak\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tcolumns.push(colDef)\n\t}\n\n\t// Auto metadata columns\n\tcolumns.push('_created_at INTEGER NOT NULL')\n\tcolumns.push('_updated_at INTEGER NOT NULL')\n\tcolumns.push(\"_version TEXT NOT NULL DEFAULT ''\")\n\tcolumns.push('_deleted INTEGER NOT NULL DEFAULT 0')\n\n\tstatements.push(`CREATE TABLE IF NOT EXISTS ${collectionName} (\\n ${columns.join(',\\n ')}\\n)`)\n\n\t// Add ALTER TABLE statements so new columns are added to existing tables.\n\t// These are tagged with --kora:safe-alter so the runtime can ignore \"duplicate column\" errors.\n\tfor (const [fieldName, descriptor] of Object.entries(collection.fields)) {\n\t\tconst colDef = columnDefinition(fieldName, descriptor)\n\t\tstatements.push(`--kora:safe-alter\\nALTER TABLE ${collectionName} ADD COLUMN ${colDef}`)\n\t}\n\tstatements.push(\n\t\t`--kora:safe-alter\\nALTER TABLE ${collectionName} ADD COLUMN _version TEXT NOT NULL DEFAULT ''`,\n\t)\n\n\t// Create indexes\n\tfor (const indexField of collection.indexes) {\n\t\tstatements.push(\n\t\t\t`CREATE INDEX IF NOT EXISTS idx_${collectionName}_${indexField} ON ${collectionName} (${indexField})`,\n\t\t)\n\t}\n\n\t// Auto-create indexes on FK columns not already indexed\n\tfor (const fkField of fkFields) {\n\t\tif (!indexedFields.has(fkField)) {\n\t\t\tstatements.push(\n\t\t\t\t`CREATE INDEX IF NOT EXISTS idx_${collectionName}_${fkField} ON ${collectionName} (${fkField})`,\n\t\t\t)\n\t\t}\n\t}\n\n\t// Per-collection operations log table\n\tstatements.push(\n\t\t`CREATE TABLE IF NOT EXISTS _kora_ops_${collectionName} (\n id TEXT PRIMARY KEY NOT NULL,\n node_id TEXT NOT NULL,\n type TEXT NOT NULL,\n record_id TEXT NOT NULL,\n data TEXT,\n previous_data TEXT,\n timestamp TEXT NOT NULL,\n sequence_number INTEGER NOT NULL,\n causal_deps TEXT NOT NULL,\n schema_version INTEGER NOT NULL\n)`,\n\t)\n\n\treturn statements\n}\n\n/**\n * Generate the full DDL for all collections plus metadata tables.\n *\n * @param schema - The complete schema definition\n * @returns An array of all SQL statements needed to initialize the database\n */\nexport function generateFullDDL(schema: SchemaDefinition): string[] {\n\tconst statements: string[] = []\n\n\t// Metadata table\n\tstatements.push(\n\t\t'CREATE TABLE IF NOT EXISTS _kora_meta (\\n' +\n\t\t\t' key TEXT PRIMARY KEY NOT NULL,\\n' +\n\t\t\t' value TEXT NOT NULL\\n' +\n\t\t\t')',\n\t)\n\n\t// Version vector table\n\tstatements.push(\n\t\t'CREATE TABLE IF NOT EXISTS _kora_version_vector (\\n' +\n\t\t\t' node_id TEXT PRIMARY KEY NOT NULL,\\n' +\n\t\t\t' sequence_number INTEGER NOT NULL\\n' +\n\t\t\t')',\n\t)\n\n\t// Sequence counters table (offline-safe sequences)\n\tstatements.push(\n\t\t'CREATE TABLE IF NOT EXISTS _kora_sequences (\\n' +\n\t\t\t' name TEXT NOT NULL,\\n' +\n\t\t\t\" scope TEXT NOT NULL DEFAULT '',\\n\" +\n\t\t\t' node_id TEXT NOT NULL,\\n' +\n\t\t\t' counter INTEGER NOT NULL DEFAULT 0,\\n' +\n\t\t\t' PRIMARY KEY (name, scope, node_id)\\n' +\n\t\t\t')',\n\t)\n\n\t// Durable outbound sync queue (survives page refresh)\n\tstatements.push(\n\t\t'CREATE TABLE IF NOT EXISTS _kora_sync_queue (\\n' +\n\t\t\t' id TEXT PRIMARY KEY NOT NULL,\\n' +\n\t\t\t' payload TEXT NOT NULL\\n' +\n\t\t\t')',\n\t)\n\n\t// Durable merge / constraint audit trail (enterprise audit export)\n\tstatements.push(\n\t\t'CREATE TABLE IF NOT EXISTS _kora_audit_traces (\\n' +\n\t\t\t' id TEXT PRIMARY KEY NOT NULL,\\n' +\n\t\t\t' recorded_at INTEGER NOT NULL,\\n' +\n\t\t\t' event_type TEXT NOT NULL,\\n' +\n\t\t\t' collection TEXT NOT NULL,\\n' +\n\t\t\t' record_id TEXT NOT NULL,\\n' +\n\t\t\t' field TEXT NOT NULL,\\n' +\n\t\t\t' strategy TEXT NOT NULL,\\n' +\n\t\t\t' tier INTEGER NOT NULL,\\n' +\n\t\t\t' constraint_name TEXT,\\n' +\n\t\t\t' trace_json TEXT NOT NULL\\n' +\n\t\t\t')',\n\t)\n\tstatements.push(\n\t\t'CREATE INDEX IF NOT EXISTS idx_kora_audit_traces_recorded_at ON _kora_audit_traces (recorded_at)',\n\t)\n\tstatements.push(\n\t\t'CREATE INDEX IF NOT EXISTS idx_kora_audit_traces_collection ON _kora_audit_traces (collection)',\n\t)\n\n\tfor (const [name, collection] of Object.entries(schema.collections)) {\n\t\tstatements.push(...generateSQL(name, collection, schema.relations))\n\t}\n\n\treturn statements\n}\n\nfunction columnDefinition(fieldName: string, descriptor: FieldDescriptor): string {\n\tconst sqlType = mapFieldType(descriptor)\n\tconst parts = [fieldName, sqlType]\n\n\tif (descriptor.required && descriptor.defaultValue === undefined && !descriptor.auto) {\n\t\tparts.push('NOT NULL')\n\t}\n\n\tif (descriptor.defaultValue !== undefined) {\n\t\tparts.push(`DEFAULT ${sqlDefault(descriptor.defaultValue)}`)\n\t}\n\n\t// CHECK constraint for enum fields\n\tif (descriptor.kind === 'enum' && descriptor.enumValues) {\n\t\tconst values = descriptor.enumValues.map((v) => `'${v}'`).join(', ')\n\t\tparts.push(`CHECK (${fieldName} IN (${values}))`)\n\t}\n\n\treturn parts.join(' ')\n}\n\nfunction mapFieldType(descriptor: FieldDescriptor): string {\n\tswitch (descriptor.kind) {\n\t\tcase 'string':\n\t\t\treturn 'TEXT'\n\t\tcase 'number':\n\t\t\treturn 'REAL'\n\t\tcase 'boolean':\n\t\t\treturn 'INTEGER'\n\t\tcase 'enum':\n\t\t\treturn 'TEXT'\n\t\tcase 'timestamp':\n\t\t\treturn 'INTEGER'\n\t\tcase 'array':\n\t\t\treturn 'TEXT' // JSON-serialized\n\t\tcase 'richtext':\n\t\t\treturn 'BLOB' // Yjs state\n\t}\n}\n\nfunction sqlDefault(value: unknown): string {\n\tif (value === null) return 'NULL'\n\tif (typeof value === 'string') return `'${value}'`\n\tif (typeof value === 'number') return String(value)\n\tif (typeof value === 'boolean') return value ? '1' : '0'\n\t// Arrays and objects are stored as JSON strings\n\treturn `'${JSON.stringify(value)}'`\n}\n","import { SchemaValidationError } from '../errors/errors'\nimport type { FieldDescriptor, FieldKind, FieldMergeStrategy, TransitionMap } from '../types'\n\n/**\n * Base field builder implementing the builder pattern for schema field definitions.\n * Each builder is immutable — modifier methods return new builder instances.\n *\n * Type parameters track field metadata at the type level for inference:\n * - Kind: the field kind ('string', 'number', etc.)\n * - Req: whether the field is required (true = required on insert)\n * - Auto: whether the field is auto-populated (true = excluded from insert input)\n *\n * @example\n * ```typescript\n * t.string() // required string field\n * t.string().optional() // optional string field\n * t.string().default('hello') // string with default value\n * t.timestamp().auto() // auto-populated timestamp\n * ```\n */\nexport class FieldBuilder<\n\tKind extends FieldKind = FieldKind,\n\tReq extends boolean = true,\n\tAuto extends boolean = false,\n> {\n\tprotected readonly _kind: Kind\n\tprotected readonly _required: boolean\n\tprotected readonly _defaultValue: unknown\n\tprotected readonly _auto: boolean\n\tprotected readonly _mergeStrategy: FieldMergeStrategy | null\n\n\tconstructor(\n\t\tkind: Kind,\n\t\trequired = true as unknown as Req,\n\t\tdefaultValue: unknown = undefined,\n\t\tauto = false as unknown as Auto,\n\t\tmergeStrategy: FieldMergeStrategy | null = null,\n\t) {\n\t\tthis._kind = kind\n\t\tthis._required = required as unknown as boolean\n\t\tthis._defaultValue = defaultValue\n\t\tthis._auto = auto as unknown as boolean\n\t\tthis._mergeStrategy = mergeStrategy\n\t}\n\n\t/** Mark this field as optional (not required on insert) */\n\toptional(): FieldBuilder<Kind, false, Auto> {\n\t\treturn new FieldBuilder(this._kind, false, this._defaultValue, this._auto, this._mergeStrategy)\n\t}\n\n\t/** Set a default value for this field. Implicitly makes the field optional. */\n\tdefault(value: unknown): FieldBuilder<Kind, false, Auto> {\n\t\treturn new FieldBuilder(this._kind, false, value, this._auto, this._mergeStrategy)\n\t}\n\n\t/** Mark this field as auto-populated (e.g., createdAt timestamps). Developers cannot set auto fields. */\n\tauto(): FieldBuilder<Kind, false, true> {\n\t\treturn new FieldBuilder(this._kind, false, undefined, true, this._mergeStrategy)\n\t}\n\n\t/**\n\t * Declare a merge strategy for this field.\n\t * Controls how concurrent modifications are resolved during sync.\n\t *\n\t * @param strategy - The merge strategy to use:\n\t * - `'lww'`: Last-write-wins (default for scalar fields)\n\t * - `'counter'`: Sum of deltas from base (for numbers)\n\t * - `'max'`: Keep the maximum value (for numbers/timestamps)\n\t * - `'min'`: Keep the minimum value (for numbers/timestamps)\n\t * - `'union'`: Set-union merge (default for arrays)\n\t * - `'append-only'`: Concatenate additions (for arrays)\n\t * - `'server-authoritative'`: Always prefer the remote/server value\n\t */\n\tmerge(strategy: FieldMergeStrategy): FieldBuilder<Kind, Req, Auto> {\n\t\treturn new FieldBuilder(\n\t\t\tthis._kind,\n\t\t\tthis._required as unknown as Req,\n\t\t\tthis._defaultValue,\n\t\t\tthis._auto as unknown as Auto,\n\t\t\tstrategy,\n\t\t)\n\t}\n\n\t/** @internal Build the final FieldDescriptor. Used by defineSchema(). */\n\t_build(): FieldDescriptor {\n\t\treturn {\n\t\t\tkind: this._kind,\n\t\t\trequired: this._required as unknown as boolean,\n\t\t\tdefaultValue: this._defaultValue,\n\t\t\tauto: this._auto as unknown as boolean,\n\t\t\tenumValues: null,\n\t\t\titemKind: null,\n\t\t\tmergeStrategy: this._mergeStrategy,\n\t\t\ttransitions: null,\n\t\t}\n\t}\n}\n\n/**\n * Field builder for enum fields with constrained string values.\n * Preserves the literal enum tuple type for inference.\n */\nexport class EnumFieldBuilder<\n\tValues extends readonly string[] = readonly string[],\n\tReq extends boolean = true,\n\tAuto extends boolean = false,\n> extends FieldBuilder<'enum', Req, Auto> {\n\tprivate readonly _enumValues: Values\n\tprivate readonly _transitions: TransitionMap | null\n\n\tconstructor(\n\t\tvalues: Values,\n\t\trequired = true as unknown as Req,\n\t\tdefaultValue: unknown = undefined,\n\t\tauto = false as unknown as Auto,\n\t\tmergeStrategy: FieldMergeStrategy | null = null,\n\t\ttransitions: TransitionMap | null = null,\n\t) {\n\t\tsuper('enum', required, defaultValue, auto, mergeStrategy)\n\t\tthis._enumValues = values\n\t\tthis._transitions = transitions\n\t}\n\n\toverride optional(): EnumFieldBuilder<Values, false, Auto> {\n\t\treturn new EnumFieldBuilder(\n\t\t\tthis._enumValues,\n\t\t\tfalse,\n\t\t\tthis._defaultValue,\n\t\t\tthis._auto,\n\t\t\tthis._mergeStrategy,\n\t\t\tthis._transitions,\n\t\t)\n\t}\n\n\toverride default(value: Values[number]): EnumFieldBuilder<Values, false, Auto> {\n\t\treturn new EnumFieldBuilder(\n\t\t\tthis._enumValues,\n\t\t\tfalse,\n\t\t\tvalue,\n\t\t\tthis._auto,\n\t\t\tthis._mergeStrategy,\n\t\t\tthis._transitions,\n\t\t)\n\t}\n\n\toverride auto(): EnumFieldBuilder<Values, false, true> {\n\t\treturn new EnumFieldBuilder(\n\t\t\tthis._enumValues,\n\t\t\tfalse,\n\t\t\tundefined,\n\t\t\ttrue,\n\t\t\tthis._mergeStrategy,\n\t\t\tthis._transitions,\n\t\t)\n\t}\n\n\toverride merge(strategy: FieldMergeStrategy): EnumFieldBuilder<Values, Req, Auto> {\n\t\treturn new EnumFieldBuilder(\n\t\t\tthis._enumValues,\n\t\t\tthis._required as unknown as Req,\n\t\t\tthis._defaultValue,\n\t\t\tthis._auto as unknown as Auto,\n\t\t\tstrategy,\n\t\t\tthis._transitions,\n\t\t)\n\t}\n\n\t/**\n\t * Declare allowed state transitions for this enum field.\n\t * Enables state machine validation during mutations and merges.\n\t *\n\t * @param map - Map of state to allowed next states\n\t *\n\t * @example\n\t * ```typescript\n\t * t.enum(['draft', 'pending', 'confirmed', 'cancelled']).transitions({\n\t * draft: ['pending', 'cancelled'],\n\t * pending: ['confirmed', 'cancelled'],\n\t * confirmed: [],\n\t * cancelled: [],\n\t * })\n\t * ```\n\t */\n\ttransitions(\n\t\tmap: Partial<Record<Values[number], Values[number][]>>,\n\t): EnumFieldBuilder<Values, Req, Auto> {\n\t\t// Validate that all source and target states are valid enum values\n\t\tconst validValues = new Set(this._enumValues as readonly string[])\n\t\tfor (const [state, targets] of Object.entries(map)) {\n\t\t\tif (!validValues.has(state)) {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Invalid source state \"${state}\" in transition map. Valid values: ${[...validValues].join(', ')}`,\n\t\t\t\t\t{ state, validValues: [...validValues] },\n\t\t\t\t)\n\t\t\t}\n\t\t\tfor (const target of targets as string[]) {\n\t\t\t\tif (!validValues.has(target)) {\n\t\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t\t`Invalid target state \"${target}\" in transition from \"${state}\". Valid values: ${[...validValues].join(', ')}`,\n\t\t\t\t\t\t{ state, target, validValues: [...validValues] },\n\t\t\t\t\t)\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn new EnumFieldBuilder(\n\t\t\tthis._enumValues,\n\t\t\tthis._required as unknown as Req,\n\t\t\tthis._defaultValue,\n\t\t\tthis._auto as unknown as Auto,\n\t\t\tthis._mergeStrategy,\n\t\t\tmap as TransitionMap,\n\t\t)\n\t}\n\n\toverride _build(): FieldDescriptor {\n\t\treturn {\n\t\t\tkind: 'enum',\n\t\t\trequired: this._required as unknown as boolean,\n\t\t\tdefaultValue: this._defaultValue,\n\t\t\tauto: this._auto as unknown as boolean,\n\t\t\tenumValues: this._enumValues,\n\t\t\titemKind: null,\n\t\t\tmergeStrategy: this._mergeStrategy,\n\t\t\ttransitions: this._transitions,\n\t\t}\n\t}\n}\n\n/**\n * Field builder for array fields with a typed item kind.\n * Preserves the item kind type parameter for inference.\n */\nexport class ArrayFieldBuilder<\n\tItemKind extends FieldKind = FieldKind,\n\tReq extends boolean = true,\n\tAuto extends boolean = false,\n> extends FieldBuilder<'array', Req, Auto> {\n\tprivate readonly _itemKind: ItemKind\n\n\tconstructor(\n\t\titemBuilder: FieldBuilder<ItemKind>,\n\t\trequired = true as unknown as Req,\n\t\tdefaultValue: unknown = undefined,\n\t\tauto = false as unknown as Auto,\n\t\tmergeStrategy: FieldMergeStrategy | null = null,\n\t) {\n\t\tsuper('array', required, defaultValue, auto, mergeStrategy)\n\t\tthis._itemKind = itemBuilder._build().kind as ItemKind\n\t}\n\n\toverride optional(): ArrayFieldBuilder<ItemKind, false, Auto> {\n\t\treturn new ArrayFieldBuilder(\n\t\t\tnew FieldBuilder(this._itemKind),\n\t\t\tfalse,\n\t\t\tthis._defaultValue,\n\t\t\tthis._auto,\n\t\t\tthis._mergeStrategy,\n\t\t)\n\t}\n\n\toverride default(value: unknown[]): ArrayFieldBuilder<ItemKind, false, Auto> {\n\t\treturn new ArrayFieldBuilder(\n\t\t\tnew FieldBuilder(this._itemKind),\n\t\t\tfalse,\n\t\t\tvalue,\n\t\t\tthis._auto,\n\t\t\tthis._mergeStrategy,\n\t\t)\n\t}\n\n\toverride auto(): ArrayFieldBuilder<ItemKind, false, true> {\n\t\treturn new ArrayFieldBuilder(\n\t\t\tnew FieldBuilder(this._itemKind),\n\t\t\tfalse,\n\t\t\tundefined,\n\t\t\ttrue,\n\t\t\tthis._mergeStrategy,\n\t\t)\n\t}\n\n\toverride merge(strategy: FieldMergeStrategy): ArrayFieldBuilder<ItemKind, Req, Auto> {\n\t\treturn new ArrayFieldBuilder(\n\t\t\tnew FieldBuilder(this._itemKind),\n\t\t\tthis._required as unknown as Req,\n\t\t\tthis._defaultValue,\n\t\t\tthis._auto as unknown as Auto,\n\t\t\tstrategy,\n\t\t)\n\t}\n\n\toverride _build(): FieldDescriptor {\n\t\treturn {\n\t\t\tkind: 'array',\n\t\t\trequired: this._required as unknown as boolean,\n\t\t\tdefaultValue: this._defaultValue,\n\t\t\tauto: this._auto as unknown as boolean,\n\t\t\tenumValues: null,\n\t\t\titemKind: this._itemKind,\n\t\t\tmergeStrategy: this._mergeStrategy,\n\t\t\ttransitions: null,\n\t\t}\n\t}\n}\n\n/**\n * Type builder namespace. The developer's primary interface for defining field types.\n *\n * @example\n * ```typescript\n * import { t } from '@korajs/core'\n *\n * const fields = {\n * title: t.string(),\n * count: t.number(),\n * active: t.boolean().default(true),\n * notes: t.richtext(),\n * tags: t.array(t.string()).default([]),\n * priority: t.enum(['low', 'medium', 'high']).default('medium'),\n * createdAt: t.timestamp().auto(),\n * }\n * ```\n */\nexport const t = {\n\tstring(): FieldBuilder<'string', true, false> {\n\t\treturn new FieldBuilder('string', true, undefined, false)\n\t},\n\n\tnumber(): FieldBuilder<'number', true, false> {\n\t\treturn new FieldBuilder('number', true, undefined, false)\n\t},\n\n\tboolean(): FieldBuilder<'boolean', true, false> {\n\t\treturn new FieldBuilder('boolean', true, undefined, false)\n\t},\n\n\ttimestamp(): FieldBuilder<'timestamp', true, false> {\n\t\treturn new FieldBuilder('timestamp', true, undefined, false)\n\t},\n\n\trichtext(): FieldBuilder<'richtext', true, false> {\n\t\treturn new FieldBuilder('richtext', true, undefined, false)\n\t},\n\n\tenum<const V extends readonly string[]>(values: V): EnumFieldBuilder<V, true, false> {\n\t\treturn new EnumFieldBuilder(values, true, undefined, false)\n\t},\n\n\tarray<K extends FieldKind>(itemBuilder: FieldBuilder<K>): ArrayFieldBuilder<K, true, false> {\n\t\treturn new ArrayFieldBuilder(itemBuilder, true, undefined, false)\n\t},\n}\n","import { SchemaValidationError } from '../errors/errors'\nimport { isAtomicOp } from '../operations/atomic-ops'\nimport type { CollectionDefinition, FieldDescriptor, OperationType } from '../types'\n\n/**\n * Validates a record's data against a collection's field definitions.\n * Applies defaults, rejects auto fields, and type-checks each value.\n *\n * @param collection - The collection name (for error messages)\n * @param collectionDef - The collection definition from the schema\n * @param data - The record data to validate\n * @param operationType - The operation type ('insert', 'update', 'delete')\n * @returns The validated and normalized data (with defaults applied)\n * @throws {SchemaValidationError} If validation fails\n */\nexport function validateRecord(\n\tcollection: string,\n\tcollectionDef: CollectionDefinition,\n\tdata: Record<string, unknown>,\n\toperationType: OperationType,\n): Record<string, unknown> {\n\tif (operationType === 'delete') {\n\t\treturn {}\n\t}\n\n\tconst result: Record<string, unknown> = {}\n\tconst fieldNames = Object.keys(collectionDef.fields)\n\n\t// Check for extra fields not in the schema\n\tfor (const key of Object.keys(data)) {\n\t\tif (!(key in collectionDef.fields)) {\n\t\t\tthrow new SchemaValidationError(\n\t\t\t\t`Unknown field \"${key}\" in collection \"${collection}\". Available fields: ${fieldNames.join(', ')}`,\n\t\t\t\t{ collection, field: key },\n\t\t\t)\n\t\t}\n\t}\n\n\tfor (const [fieldName, descriptor] of Object.entries(collectionDef.fields)) {\n\t\tconst value = data[fieldName]\n\t\tconst hasValue = fieldName in data\n\n\t\t// Auto fields cannot be set by the developer\n\t\tif (descriptor.auto && hasValue) {\n\t\t\tthrow new SchemaValidationError(\n\t\t\t\t`Field \"${fieldName}\" in collection \"${collection}\" is auto-populated and cannot be set manually`,\n\t\t\t\t{ collection, field: fieldName },\n\t\t\t)\n\t\t}\n\n\t\t// For updates, only validate fields that are present (partial updates)\n\t\tif (operationType === 'update') {\n\t\t\tif (hasValue) {\n\t\t\t\t// Atomic op sentinels pass through validation — they are resolved\n\t\t\t\t// to concrete values by Collection.update() before the Operation is created.\n\t\t\t\tif (isAtomicOp(value)) {\n\t\t\t\t\tresult[fieldName] = value\n\t\t\t\t} else if (value !== undefined && value !== null) {\n\t\t\t\t\tvalidateFieldValue(collection, fieldName, descriptor, value)\n\t\t\t\t\tresult[fieldName] = value\n\t\t\t\t} else {\n\t\t\t\t\tresult[fieldName] = value\n\t\t\t\t}\n\t\t\t}\n\t\t\tcontinue\n\t\t}\n\n\t\t// For inserts, apply defaults and check required fields\n\t\tif (descriptor.auto) {\n\t\t\t// Skip auto fields — they are populated by the framework\n\t\t\tcontinue\n\t\t}\n\n\t\tif (!hasValue || value === undefined) {\n\t\t\tif (descriptor.defaultValue !== undefined) {\n\t\t\t\t// Deep-copy default arrays/objects to prevent shared mutations\n\t\t\t\tresult[fieldName] =\n\t\t\t\t\ttypeof descriptor.defaultValue === 'object' && descriptor.defaultValue !== null\n\t\t\t\t\t\t? JSON.parse(JSON.stringify(descriptor.defaultValue))\n\t\t\t\t\t\t: descriptor.defaultValue\n\t\t\t\tcontinue\n\t\t\t}\n\n\t\t\tif (descriptor.required) {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Required field \"${fieldName}\" is missing in collection \"${collection}\"`,\n\t\t\t\t\t{ collection, field: fieldName },\n\t\t\t\t)\n\t\t\t}\n\n\t\t\t// Optional field with no default — omit from result\n\t\t\tcontinue\n\t\t}\n\n\t\tvalidateFieldValue(collection, fieldName, descriptor, value)\n\t\tresult[fieldName] = value\n\t}\n\n\treturn result\n}\n\nfunction validateFieldValue(\n\tcollection: string,\n\tfieldName: string,\n\tdescriptor: FieldDescriptor,\n\tvalue: unknown,\n): void {\n\tswitch (descriptor.kind) {\n\t\tcase 'string': {\n\t\t\tif (typeof value !== 'string') {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Field \"${fieldName}\" in collection \"${collection}\" must be a string, got ${typeof value}`,\n\t\t\t\t\t{ collection, field: fieldName, expectedType: 'string', receivedType: typeof value },\n\t\t\t\t)\n\t\t\t}\n\t\t\tbreak\n\t\t}\n\n\t\tcase 'number': {\n\t\t\tif (typeof value !== 'number' || Number.isNaN(value)) {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Field \"${fieldName}\" in collection \"${collection}\" must be a number, got ${typeof value}`,\n\t\t\t\t\t{ collection, field: fieldName, expectedType: 'number', receivedType: typeof value },\n\t\t\t\t)\n\t\t\t}\n\t\t\tbreak\n\t\t}\n\n\t\tcase 'boolean': {\n\t\t\tif (typeof value !== 'boolean') {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Field \"${fieldName}\" in collection \"${collection}\" must be a boolean, got ${typeof value}`,\n\t\t\t\t\t{ collection, field: fieldName, expectedType: 'boolean', receivedType: typeof value },\n\t\t\t\t)\n\t\t\t}\n\t\t\tbreak\n\t\t}\n\n\t\tcase 'timestamp': {\n\t\t\tif (typeof value !== 'number' || !Number.isFinite(value)) {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Field \"${fieldName}\" in collection \"${collection}\" must be a timestamp (number), got ${typeof value}`,\n\t\t\t\t\t{\n\t\t\t\t\t\tcollection,\n\t\t\t\t\t\tfield: fieldName,\n\t\t\t\t\t\texpectedType: 'timestamp',\n\t\t\t\t\t\treceivedType: typeof value,\n\t\t\t\t\t},\n\t\t\t\t)\n\t\t\t}\n\t\t\tbreak\n\t\t}\n\n\t\tcase 'enum': {\n\t\t\tif (typeof value !== 'string') {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Field \"${fieldName}\" in collection \"${collection}\" must be a string (enum), got ${typeof value}`,\n\t\t\t\t\t{ collection, field: fieldName, expectedType: 'enum', receivedType: typeof value },\n\t\t\t\t)\n\t\t\t}\n\t\t\tif (descriptor.enumValues && !descriptor.enumValues.includes(value)) {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Field \"${fieldName}\" in collection \"${collection}\" must be one of: ${descriptor.enumValues.join(', ')}. Got \"${value}\"`,\n\t\t\t\t\t{\n\t\t\t\t\t\tcollection,\n\t\t\t\t\t\tfield: fieldName,\n\t\t\t\t\t\tallowedValues: [...descriptor.enumValues],\n\t\t\t\t\t\treceived: value,\n\t\t\t\t\t},\n\t\t\t\t)\n\t\t\t}\n\t\t\tbreak\n\t\t}\n\n\t\tcase 'array': {\n\t\t\tif (!Array.isArray(value)) {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Field \"${fieldName}\" in collection \"${collection}\" must be an array, got ${typeof value}`,\n\t\t\t\t\t{ collection, field: fieldName, expectedType: 'array', receivedType: typeof value },\n\t\t\t\t)\n\t\t\t}\n\t\t\tif (descriptor.itemKind) {\n\t\t\t\tconst expectedType = jsTypeForKind(descriptor.itemKind)\n\t\t\t\tfor (let i = 0; i < value.length; i++) {\n\t\t\t\t\tconst item = value[i]\n\t\t\t\t\tif (!matchesJsType(item, expectedType)) {\n\t\t\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t\t\t`Field \"${fieldName}[${i}]\" in collection \"${collection}\" must be a ${descriptor.itemKind}, got ${typeof item}`,\n\t\t\t\t\t\t\t{\n\t\t\t\t\t\t\t\tcollection,\n\t\t\t\t\t\t\t\tfield: `${fieldName}[${i}]`,\n\t\t\t\t\t\t\t\texpectedType: descriptor.itemKind,\n\t\t\t\t\t\t\t\treceivedType: typeof item,\n\t\t\t\t\t\t\t},\n\t\t\t\t\t\t)\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\tbreak\n\t\t}\n\n\t\tcase 'richtext': {\n\t\t\t// Richtext fields accept Uint8Array (Yjs state) or string (plain text initial value)\n\t\t\tif (!(value instanceof Uint8Array) && typeof value !== 'string') {\n\t\t\t\tthrow new SchemaValidationError(\n\t\t\t\t\t`Field \"${fieldName}\" in collection \"${collection}\" must be a Uint8Array or string for richtext, got ${typeof value}`,\n\t\t\t\t\t{\n\t\t\t\t\t\tcollection,\n\t\t\t\t\t\tfield: fieldName,\n\t\t\t\t\t\texpectedType: 'richtext',\n\t\t\t\t\t\treceivedType: typeof value,\n\t\t\t\t\t},\n\t\t\t\t)\n\t\t\t}\n\t\t\tbreak\n\t\t}\n\t}\n}\n\nfunction jsTypeForKind(kind: string): string {\n\tswitch (kind) {\n\t\tcase 'string':\n\t\tcase 'enum':\n\t\t\treturn 'string'\n\t\tcase 'number':\n\t\tcase 'timestamp':\n\t\t\treturn 'number'\n\t\tcase 'boolean':\n\t\t\treturn 'boolean'\n\t\tdefault:\n\t\t\treturn 'object'\n\t}\n}\n\nfunction matchesJsType(value: unknown, expected: string): boolean {\n\t// Using explicit comparisons to satisfy Biome's useValidTypeof rule,\n\t// which requires typeof to be compared against string literals.\n\tswitch (expected) {\n\t\tcase 'string':\n\t\t\treturn typeof value === 'string'\n\t\tcase 'number':\n\t\t\treturn typeof value === 'number'\n\t\tcase 'boolean':\n\t\t\treturn typeof value === 'boolean'\n\t\tcase 'object':\n\t\t\treturn typeof value === 'object'\n\t\tdefault:\n\t\t\treturn false\n\t}\n}\n","import { HybridLogicalClock } from '../clock/hlc'\nimport { OperationError } from '../errors/errors'\nimport type { Operation } from '../types'\n\n/**\n * Topological sort of operations based on their causal dependency DAG.\n * Uses Kahn's algorithm with a binary heap for O(V log V + E) performance.\n * Deterministic tie-breaking via HLC timestamp ensures identical output\n * regardless of input order.\n *\n * @param operations - The operations to sort\n * @returns Operations in causal order (dependencies before dependents)\n * @throws {OperationError} If a cycle is detected in the dependency graph\n */\nexport function topologicalSort(operations: Operation[]): Operation[] {\n\tif (operations.length <= 1) return [...operations]\n\n\t// Build adjacency list and in-degree map\n\tconst opMap = new Map<string, Operation>()\n\tfor (const op of operations) {\n\t\topMap.set(op.id, op)\n\t}\n\n\t// Only count edges where both ends are in the operation set\n\tconst inDegree = new Map<string, number>()\n\tconst dependents = new Map<string, string[]>()\n\n\tfor (const op of operations) {\n\t\tif (!inDegree.has(op.id)) {\n\t\t\tinDegree.set(op.id, 0)\n\t\t}\n\t\tif (!dependents.has(op.id)) {\n\t\t\tdependents.set(op.id, [])\n\t\t}\n\n\t\tfor (const depId of op.causalDeps) {\n\t\t\tif (opMap.has(depId)) {\n\t\t\t\t// depId -> op.id edge (depId must come before op.id)\n\t\t\t\tinDegree.set(op.id, (inDegree.get(op.id) ?? 0) + 1)\n\t\t\t\tconst deps = dependents.get(depId)\n\t\t\t\tif (deps) {\n\t\t\t\t\tdeps.push(op.id)\n\t\t\t\t} else {\n\t\t\t\t\tdependents.set(depId, [op.id])\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t// Initialize min-heap with nodes that have no in-set dependencies\n\tconst heap = new MinHeap(compareByTimestamp)\n\tfor (const op of operations) {\n\t\tif ((inDegree.get(op.id) ?? 0) === 0) {\n\t\t\theap.push(op)\n\t\t}\n\t}\n\n\tconst result: Operation[] = []\n\n\twhile (heap.size > 0) {\n\t\t// Extract the earliest operation (deterministic tie-breaking by HLC)\n\t\tconst current = heap.pop()\n\t\tresult.push(current)\n\n\t\tconst deps = dependents.get(current.id) ?? []\n\n\t\tfor (const depId of deps) {\n\t\t\tconst deg = (inDegree.get(depId) ?? 0) - 1\n\t\t\tinDegree.set(depId, deg)\n\t\t\tif (deg === 0) {\n\t\t\t\tconst op = opMap.get(depId)\n\t\t\t\tif (op) heap.push(op)\n\t\t\t}\n\t\t}\n\t}\n\n\tif (result.length !== operations.length) {\n\t\tthrow new OperationError(\n\t\t\t`Cycle detected in operation dependency graph. Sorted ${result.length} of ${operations.length} operations.`,\n\t\t\t{\n\t\t\t\tsortedCount: result.length,\n\t\t\t\ttotalCount: operations.length,\n\t\t\t},\n\t\t)\n\t}\n\n\treturn result\n}\n\nfunction compareByTimestamp(a: Operation, b: Operation): number {\n\treturn HybridLogicalClock.compare(a.timestamp, b.timestamp)\n}\n\n/**\n * Binary min-heap for efficient priority queue operations.\n * push: O(log n), pop: O(log n) — replaces the O(n) sorted array approach.\n */\nclass MinHeap {\n\tprivate readonly data: Operation[] = []\n\tprivate readonly cmp: (a: Operation, b: Operation) => number\n\n\tconstructor(comparator: (a: Operation, b: Operation) => number) {\n\t\tthis.cmp = comparator\n\t}\n\n\tget size(): number {\n\t\treturn this.data.length\n\t}\n\n\tpush(item: Operation): void {\n\t\tthis.data.push(item)\n\t\tthis.bubbleUp(this.data.length - 1)\n\t}\n\n\tpop(): Operation {\n\t\tconst top = this.data[0] as Operation\n\t\tconst last = this.data.pop() as Operation\n\t\tif (this.data.length > 0) {\n\t\t\tthis.data[0] = last\n\t\t\tthis.sinkDown(0)\n\t\t}\n\t\treturn top\n\t}\n\n\tprivate bubbleUp(index: number): void {\n\t\tlet current = index\n\t\twhile (current > 0) {\n\t\t\tconst parentIndex = (current - 1) >> 1\n\t\t\tif (this.cmp(this.data[current] as Operation, this.data[parentIndex] as Operation) >= 0) break\n\t\t\tthis.swap(current, parentIndex)\n\t\t\tcurrent = parentIndex\n\t\t}\n\t}\n\n\tprivate sinkDown(index: number): void {\n\t\tconst length = this.data.length\n\t\tlet current = index\n\t\twhile (true) {\n\t\t\tlet smallest = current\n\t\t\tconst left = 2 * current + 1\n\t\t\tconst right = 2 * current + 2\n\n\t\t\tif (\n\t\t\t\tleft < length &&\n\t\t\t\tthis.cmp(this.data[left] as Operation, this.data[smallest] as Operation) < 0\n\t\t\t) {\n\t\t\t\tsmallest = left\n\t\t\t}\n\t\t\tif (\n\t\t\t\tright < length &&\n\t\t\t\tthis.cmp(this.data[right] as Operation, this.data[smallest] as Operation) < 0\n\t\t\t) {\n\t\t\t\tsmallest = right\n\t\t\t}\n\n\t\t\tif (smallest === current) break\n\t\t\tthis.swap(current, smallest)\n\t\t\tcurrent = smallest\n\t\t}\n\t}\n\n\tprivate swap(i: number, j: number): void {\n\t\tconst tmp = this.data[i] as Operation\n\t\tthis.data[i] = this.data[j] as Operation\n\t\tthis.data[j] = tmp\n\t}\n}\n","import type { Operation, VersionVector } from '../types'\nimport { topologicalSort } from './topological-sort'\n\n/**\n * Create an empty version vector.\n */\nexport function createVersionVector(): VersionVector {\n\treturn new Map()\n}\n\n/**\n * Merge two version vectors by taking the max sequence number for each node.\n * This is commutative, associative, and idempotent.\n */\nexport function mergeVectors(a: VersionVector, b: VersionVector): VersionVector {\n\tconst merged = new Map(a)\n\tfor (const [nodeId, seq] of b) {\n\t\tmerged.set(nodeId, Math.max(merged.get(nodeId) ?? 0, seq))\n\t}\n\treturn merged\n}\n\n/**\n * Advance a version vector for a specific node to a new sequence number.\n * Only advances forward — if the current value is higher, no change is made.\n */\nexport function advanceVector(vector: VersionVector, nodeId: string, seq: number): VersionVector {\n\tconst updated = new Map(vector)\n\tupdated.set(nodeId, Math.max(updated.get(nodeId) ?? 0, seq))\n\treturn updated\n}\n\n/**\n * Returns true if vector `a` dominates vector `b` — meaning `a` has seen\n * everything `b` has seen. Formally: for every nodeId in b, a[nodeId] >= b[nodeId].\n */\nexport function dominates(a: VersionVector, b: VersionVector): boolean {\n\tfor (const [nodeId, bSeq] of b) {\n\t\tif ((a.get(nodeId) ?? 0) < bSeq) return false\n\t}\n\treturn true\n}\n\n/**\n * Returns true if two version vectors are exactly equal.\n */\nexport function vectorsEqual(a: VersionVector, b: VersionVector): boolean {\n\tif (a.size !== b.size) return false\n\tfor (const [nodeId, aSeq] of a) {\n\t\tif (b.get(nodeId) !== aSeq) return false\n\t}\n\treturn true\n}\n\n/**\n * Operation log interface for computing deltas.\n * getRange may be async (for DB-backed implementations) or sync (for in-memory).\n */\nexport interface OperationLog {\n\tgetRange(nodeId: string, fromSeq: number, toSeq: number): Operation[] | Promise<Operation[]>\n}\n\n/**\n * Compute the operations that `local` has but `remote` does not.\n * Returns operations in causal (topological) order.\n *\n * @param localVector - The local version vector\n * @param remoteVector - The remote version vector\n * @param operationLog - The operation log to fetch operations from\n * @returns Operations sorted in causal order\n */\nexport async function computeDelta(\n\tlocalVector: VersionVector,\n\tremoteVector: VersionVector,\n\toperationLog: OperationLog,\n): Promise<Operation[]> {\n\tconst missing: Operation[] = []\n\tfor (const [nodeId, localSeq] of localVector) {\n\t\tconst remoteSeq = remoteVector.get(nodeId) ?? 0\n\t\tif (localSeq > remoteSeq) {\n\t\t\tconst ops = await operationLog.getRange(nodeId, remoteSeq + 1, localSeq)\n\t\t\tmissing.push(...ops)\n\t\t}\n\t}\n\treturn topologicalSort(missing)\n}\n\n/**\n * Serialize a version vector to a JSON-compatible string.\n */\nexport function serializeVector(vector: VersionVector): string {\n\tconst entries = [...vector.entries()].sort(([a], [b]) => (a < b ? -1 : a > b ? 1 : 0))\n\treturn JSON.stringify(entries)\n}\n\n/**\n * Deserialize a version vector from its serialized string form.\n */\nexport function deserializeVector(s: string): VersionVector {\n\tconst entries = JSON.parse(s) as [string, number][]\n\treturn new Map(entries)\n}\n","import type { SchemaDefinition } from '../types'\nimport {\n\tcollectSchemaScopeValueKeys,\n\tgetCollectionScopeBindings,\n\thasSchemaSyncRules,\n\tisCollectionSyncScoped,\n} from './sync-scope-bindings'\n\n/**\n * Per-collection scope map: `{ collectionName: { field: value, ... } }`\n *\n * Used to filter which operations a client should receive during sync.\n */\nexport type ScopeMap = Record<string, Record<string, unknown>>\n\n/**\n * Build a per-collection scope map from the schema's scope declarations\n * and the client's flat scope values.\n *\n * Supports both legacy `collection.scope` arrays and declarative `schema.sync`\n * rules (`sync: { todos: { where: { userId: true } } }`).\n *\n * When `schema.sync` is present, only collections with sync rules or legacy\n * scope fields are included in the result. Other collections are omitted so\n * sync engines treat them as out of scope (partial sync).\n *\n * @param schema - The schema definition with scope declarations\n * @param scopeValues - Flat key-value scope values from the client\n * @returns A per-collection scope map\n *\n * @example\n * ```typescript\n * // Schema declares: sales.scope = ['orgId', 'storeId']\n * // Client provides: { orgId: 'org-123', storeId: 'store-456' }\n * // Result: { sales: { orgId: 'org-123', storeId: 'store-456' }, products: {} }\n * ```\n */\nexport function buildScopeMap(\n\tschema: SchemaDefinition,\n\tscopeValues: Record<string, unknown>,\n): ScopeMap {\n\tconst result: ScopeMap = {}\n\tconst partialSync = hasSchemaSyncRules(schema)\n\n\tfor (const collName of Object.keys(schema.collections)) {\n\t\tif (partialSync && !isCollectionSyncScoped(schema, collName)) {\n\t\t\tcontinue\n\t\t}\n\n\t\tconst bindings = getCollectionScopeBindings(schema, collName)\n\t\tif (bindings) {\n\t\t\tconst collScope: Record<string, unknown> = {}\n\t\t\tfor (const [field, scopeKey] of Object.entries(bindings)) {\n\t\t\t\tif (scopeKey in scopeValues) {\n\t\t\t\t\tcollScope[field] = scopeValues[scopeKey]\n\t\t\t\t}\n\t\t\t}\n\t\t\tresult[collName] = collScope\n\t\t} else {\n\t\t\t// Collections without scope declarations are fully visible\n\t\t\tresult[collName] = {}\n\t\t}\n\t}\n\n\treturn result\n}\n\nexport { collectSchemaScopeValueKeys as collectSchemaScopeFields } from './sync-scope-bindings'\n","import type { SchemaDefinition } from '../types'\nimport { collectSchemaScopeValueKeys } from './sync-scope-bindings'\n\n/**\n * Collect every unique scope field name declared across all collections.\n *\n * @deprecated Use {@link collectSchemaScopeValueKeys} instead.\n */\nexport function collectSchemaScopeFields(schema: SchemaDefinition): string[] {\n\treturn collectSchemaScopeValueKeys(schema)\n}\n\n/**\n * Extract flat scope values from JWT (or auth) claims using schema scope field names.\n *\n * Resolution order for each scope field:\n * 1. Top-level claim with the same name\n * 2. Nested `claims.scope[field]` object\n * 3. `userId` falls back to the standard JWT `sub` claim\n *\n * @param schema - Schema with per-collection scope declarations\n * @param claims - Decoded JWT claims (unverified; client-side scope hints only)\n * @returns Flat key-value map suitable for {@link buildScopeMap}\n */\nexport function extractScopeValuesFromClaims(\n\tschema: SchemaDefinition,\n\tclaims: Record<string, unknown>,\n): Record<string, unknown> {\n\tconst scopeFields = collectSchemaScopeValueKeys(schema)\n\tif (scopeFields.length === 0) {\n\t\treturn {}\n\t}\n\n\tconst nestedScope = claims.scope\n\tconst scopeObject =\n\t\ttypeof nestedScope === 'object' && nestedScope !== null && !Array.isArray(nestedScope)\n\t\t\t? (nestedScope as Record<string, unknown>)\n\t\t\t: {}\n\n\tconst result: Record<string, unknown> = {}\n\n\tfor (const field of scopeFields) {\n\t\tif (field in claims) {\n\t\t\tresult[field] = claims[field]\n\t\t\tcontinue\n\t\t}\n\n\t\tif (field in scopeObject) {\n\t\t\tresult[field] = scopeObject[field]\n\t\t\tcontinue\n\t\t}\n\n\t\tif (field === 'userId' && typeof claims.sub === 'string') {\n\t\t\tresult.userId = claims.sub\n\t\t}\n\t}\n\n\treturn result\n}\n","/**\n * Offline-safe sequence formatting.\n *\n * Format tokens:\n * - `{date}` → YYYYMMDD (current date)\n * - `{node4}` → first 4 characters of nodeId\n * - `{node8}` → first 8 characters of nodeId\n * - `{seq}` → zero-padded counter (default 4 digits)\n * - `{seq:N}` → zero-padded counter with N digits\n *\n * @example\n * ```typescript\n * formatSequenceValue('INV-{date}-{node4}-{seq}', 42, 'a1b2c3d4e5f6')\n * // → \"INV-20260508-a1b2-0042\"\n *\n * formatSequenceValue('ORDER-{seq:6}', 7, 'node-id')\n * // → \"ORDER-000007\"\n * ```\n */\nexport function formatSequenceValue(\n\ttemplate: string,\n\tcounter: number,\n\tnodeId: string,\n\tnow?: Date,\n): string {\n\tconst date = now ?? new Date()\n\tconst yyyy = String(date.getUTCFullYear())\n\tconst mm = String(date.getUTCMonth() + 1).padStart(2, '0')\n\tconst dd = String(date.getUTCDate()).padStart(2, '0')\n\tconst dateStr = `${yyyy}${mm}${dd}`\n\n\treturn template.replace(/\\{([^}]+)\\}/g, (_match, token: string) => {\n\t\tif (token === 'date') return dateStr\n\t\tif (token === 'node4') return nodeId.slice(0, 4)\n\t\tif (token === 'node8') return nodeId.slice(0, 8)\n\t\tif (token === 'seq') return String(counter).padStart(4, '0')\n\t\tif (token.startsWith('seq:')) {\n\t\t\tconst width = Number.parseInt(token.slice(4), 10)\n\t\t\tif (Number.isNaN(width) || width < 1) {\n\t\t\t\treturn String(counter).padStart(4, '0')\n\t\t\t}\n\t\t\treturn String(counter).padStart(width, '0')\n\t\t}\n\t\t// Unknown token — leave as-is\n\t\treturn `{${token}}`\n\t})\n}\n\n/**\n * Default format when none is provided: `{name}-{seq:4}`.\n */\nexport function defaultSequenceFormat(name: string): string {\n\treturn `${name}-{seq:4}`\n}\n","import type { Operation } from '../types'\nimport type { OperationTransform } from './operation-transform'\n\nconst MAX_TRANSFORM_STEPS = 32\n\n/**\n * Apply registered transforms until the operation matches `targetSchemaVersion`.\n * Returns null when a transform drops the operation or no path exists.\n */\nexport function applyOperationTransforms(\n\toperation: Operation,\n\ttargetSchemaVersion: number,\n\ttransforms: readonly OperationTransform[],\n): Operation | null {\n\tlet current: Operation = operation\n\n\tfor (let step = 0; step < MAX_TRANSFORM_STEPS; step++) {\n\t\tif (current.schemaVersion === targetSchemaVersion) {\n\t\t\treturn current\n\t\t}\n\n\t\tconst transform = transforms.find(\n\t\t\t(candidate) => candidate.fromVersion === current.schemaVersion,\n\t\t)\n\t\tif (!transform) {\n\t\t\treturn null\n\t\t}\n\n\t\tconst next = transform.transform(current)\n\t\tif (next === null) {\n\t\t\treturn null\n\t\t}\n\t\tcurrent = next\n\t}\n\n\treturn null\n}\n","import type { FieldBuilder } from '../schema/types'\nimport type { FieldDescriptor } from '../types'\n\n/**\n * A single migration step describing a schema change.\n */\nexport type MigrationStep =\n\t| { type: 'addField'; collection: string; field: string; descriptor: FieldDescriptor }\n\t| { type: 'removeField'; collection: string; field: string; descriptor?: FieldDescriptor }\n\t| { type: 'renameField'; collection: string; from: string; to: string }\n\t| { type: 'addIndex'; collection: string; field: string }\n\t| { type: 'removeIndex'; collection: string; field: string }\n\t| {\n\t\t\ttype: 'backfill'\n\t\t\tcollection: string\n\t\t\ttransform: (record: Record<string, unknown>) => Record<string, unknown>\n\t\t\t/** Reverse transform for rollback. If not provided, backfill is not safely reversible. */\n\t\t\treverseTransform?: (record: Record<string, unknown>) => Record<string, unknown>\n\t }\n\n/**\n * A completed migration definition containing ordered steps and optional rollback steps.\n */\nexport interface MigrationDefinition {\n\treadonly steps: readonly MigrationStep[]\n\t/** Explicitly defined rollback steps. If undefined, inverse steps are auto-generated. */\n\treadonly rollbackSteps: readonly MigrationStep[] | undefined\n\t/** Whether this migration can be safely rolled back. */\n\treadonly safelyReversible: boolean\n}\n\n/**\n * Builder for defining rollback steps explicitly.\n * Used with the `.down()` method on MigrationBuilder.\n *\n * @example\n * ```typescript\n * migrate()\n * .addField('todos', 'priority', t.enum(['low', 'medium', 'high']).default('medium'))\n * .addIndex('todos', 'priority')\n * .down((rollback) => {\n * rollback\n * .removeIndex('todos', 'priority')\n * .removeField('todos', 'priority')\n * })\n * ```\n */\nexport class RollbackBuilder {\n\tprivate _steps: MigrationStep[] = []\n\n\t/**\n\t * Add a field during rollback (to reverse a removeField).\n\t */\n\taddField(collection: string, field: string, builder: FieldBuilder): RollbackBuilder {\n\t\tthis._steps.push({ type: 'addField', collection, field, descriptor: builder._build() })\n\t\treturn this\n\t}\n\n\t/**\n\t * Remove a field during rollback (to reverse an addField).\n\t */\n\tremoveField(collection: string, field: string): RollbackBuilder {\n\t\tthis._steps.push({ type: 'removeField', collection, field })\n\t\treturn this\n\t}\n\n\t/**\n\t * Rename a field during rollback (to reverse a renameField).\n\t */\n\trenameField(collection: string, from: string, to: string): RollbackBuilder {\n\t\tthis._steps.push({ type: 'renameField', collection, from, to })\n\t\treturn this\n\t}\n\n\t/**\n\t * Add an index during rollback (to reverse a removeIndex).\n\t */\n\taddIndex(collection: string, field: string): RollbackBuilder {\n\t\tthis._steps.push({ type: 'addIndex', collection, field })\n\t\treturn this\n\t}\n\n\t/**\n\t * Remove an index during rollback (to reverse an addIndex).\n\t */\n\tremoveIndex(collection: string, field: string): RollbackBuilder {\n\t\tthis._steps.push({ type: 'removeIndex', collection, field })\n\t\treturn this\n\t}\n\n\t/**\n\t * Run a backfill during rollback (to reverse a previous backfill).\n\t */\n\tbackfill(\n\t\tcollection: string,\n\t\ttransform: (record: Record<string, unknown>) => Record<string, unknown>,\n\t): RollbackBuilder {\n\t\tthis._steps.push({ type: 'backfill', collection, transform })\n\t\treturn this\n\t}\n\n\t/**\n\t * Get the accumulated rollback steps.\n\t */\n\t_getSteps(): readonly MigrationStep[] {\n\t\treturn [...this._steps]\n\t}\n}\n\n/**\n * Fluent builder for defining schema migrations.\n *\n * Each method returns a new builder instance (immutable).\n *\n * @example\n * ```typescript\n * migrate()\n * .addField('products', 'taxInclusive', t.boolean().default(false))\n * .renameField('products', 'cost', 'costPrice')\n * .backfill('products', (record) => ({\n * taxInclusive: record.taxRate > 0,\n * }))\n * ```\n */\nexport class MigrationBuilder implements MigrationDefinition {\n\treadonly steps: readonly MigrationStep[]\n\treadonly rollbackSteps: readonly MigrationStep[] | undefined\n\treadonly safelyReversible: boolean\n\n\tconstructor(\n\t\tsteps: readonly MigrationStep[] = [],\n\t\trollbackSteps?: readonly MigrationStep[],\n\t\tsafelyReversible?: boolean,\n\t) {\n\t\tthis.steps = steps\n\t\tthis.rollbackSteps = rollbackSteps\n\t\t// Default: safely reversible if no backfill steps without reverseTransform\n\t\tthis.safelyReversible = safelyReversible ?? this._computeSafelyReversible(steps, rollbackSteps)\n\t}\n\n\t/**\n\t * Add a new field to a collection.\n\t * The field builder provides the type and default value.\n\t */\n\taddField(collection: string, field: string, builder: FieldBuilder): MigrationBuilder {\n\t\treturn new MigrationBuilder([\n\t\t\t...this.steps,\n\t\t\t{ type: 'addField', collection, field, descriptor: builder._build() },\n\t\t])\n\t}\n\n\t/**\n\t * Remove a field from a collection.\n\t * Optionally accepts a field builder to preserve the descriptor for rollback.\n\t * Without the descriptor, rollback of this step requires a custom `.down()`.\n\t *\n\t * @param collection - The collection name\n\t * @param field - The field name to remove\n\t * @param builder - Optional field builder preserving the type info for rollback\n\t */\n\tremoveField(collection: string, field: string, builder?: FieldBuilder): MigrationBuilder {\n\t\tconst step: MigrationStep = builder\n\t\t\t? { type: 'removeField', collection, field, descriptor: builder._build() }\n\t\t\t: { type: 'removeField', collection, field }\n\t\treturn new MigrationBuilder([...this.steps, step])\n\t}\n\n\t/**\n\t * Rename a field in a collection.\n\t * Implemented as ALTER TABLE RENAME COLUMN (SQLite 3.25+).\n\t */\n\trenameField(collection: string, from: string, to: string): MigrationBuilder {\n\t\treturn new MigrationBuilder([...this.steps, { type: 'renameField', collection, from, to }])\n\t}\n\n\t/**\n\t * Add an index on a field.\n\t */\n\taddIndex(collection: string, field: string): MigrationBuilder {\n\t\treturn new MigrationBuilder([...this.steps, { type: 'addIndex', collection, field }])\n\t}\n\n\t/**\n\t * Remove an index on a field.\n\t */\n\tremoveIndex(collection: string, field: string): MigrationBuilder {\n\t\treturn new MigrationBuilder([...this.steps, { type: 'removeIndex', collection, field }])\n\t}\n\n\t/**\n\t * Backfill records in a collection using a transform function.\n\t * The transform receives each record and returns the fields to update.\n\t * Runs after structural changes (addField, renameField, etc.).\n\t *\n\t * @param collection - The collection name\n\t * @param transform - Forward transform function\n\t * @param reverseTransform - Optional reverse transform for rollback support\n\t */\n\tbackfill(\n\t\tcollection: string,\n\t\ttransform: (record: Record<string, unknown>) => Record<string, unknown>,\n\t\treverseTransform?: (record: Record<string, unknown>) => Record<string, unknown>,\n\t): MigrationBuilder {\n\t\treturn new MigrationBuilder([\n\t\t\t...this.steps,\n\t\t\t{ type: 'backfill', collection, transform, reverseTransform },\n\t\t])\n\t}\n\n\t/**\n\t * Define explicit rollback steps for this migration.\n\t * If not called, inverse steps are auto-generated from forward steps.\n\t *\n\t * @param fn - Function that receives a RollbackBuilder to define rollback steps\n\t * @returns A new MigrationBuilder with the rollback steps attached\n\t *\n\t * @example\n\t * ```typescript\n\t * migrate()\n\t * .addField('todos', 'priority', t.enum(['low', 'medium', 'high']).default('medium'))\n\t * .addIndex('todos', 'priority')\n\t * .down((rollback) => {\n\t * rollback\n\t * .removeIndex('todos', 'priority')\n\t * .removeField('todos', 'priority')\n\t * })\n\t * ```\n\t */\n\tdown(fn: (rollback: RollbackBuilder) => void): MigrationBuilder {\n\t\tconst rollbackBuilder = new RollbackBuilder()\n\t\tfn(rollbackBuilder)\n\t\tconst rbSteps = rollbackBuilder._getSteps()\n\t\treturn new MigrationBuilder(this.steps, rbSteps, true)\n\t}\n\n\t/**\n\t * Determine if a migration is safely reversible based on its steps.\n\t * A migration is not safely reversible if:\n\t * - It has a backfill step without a reverseTransform and no explicit rollback\n\t * - It has a removeField without a stored descriptor and no explicit rollback\n\t */\n\tprivate _computeSafelyReversible(\n\t\tsteps: readonly MigrationStep[],\n\t\trollbackSteps: readonly MigrationStep[] | undefined,\n\t): boolean {\n\t\t// Explicit rollback steps override auto-detection\n\t\tif (rollbackSteps !== undefined) {\n\t\t\treturn true\n\t\t}\n\n\t\tfor (const step of steps) {\n\t\t\tif (step.type === 'backfill' && !step.reverseTransform) {\n\t\t\t\treturn false\n\t\t\t}\n\t\t\tif (step.type === 'removeField' && !step.descriptor) {\n\t\t\t\treturn false\n\t\t\t}\n\t\t}\n\n\t\treturn true\n\t}\n}\n\n/**\n * Start building a migration.\n *\n * @returns A new MigrationBuilder\n *\n * @example\n * ```typescript\n * import { migrate, t } from '@korajs/core'\n *\n * const migration = migrate()\n * .addField('products', 'taxInclusive', t.boolean().default(false))\n * .renameField('products', 'cost', 'costPrice')\n * ```\n */\nexport function migrate(): MigrationBuilder {\n\treturn new MigrationBuilder()\n}\n","import { KoraError } from '../errors/errors'\nimport type { FieldDescriptor } from '../types'\nimport type { MigrationStep } from './migration-builder'\n\n/**\n * A migration that includes both forward (up) and backward (down) steps.\n * Rollback steps are applied in reverse order of the forward steps.\n */\nexport interface ReversibleMigration {\n\treadonly up: readonly MigrationStep[]\n\treadonly down: readonly MigrationStep[]\n\treadonly fromVersion: number\n\treadonly toVersion: number\n}\n\n/**\n * Error thrown when a migration step cannot be automatically rolled back\n * and no explicit down step has been provided.\n */\nexport class MigrationRollbackError extends KoraError {\n\tconstructor(step: MigrationStep) {\n\t\tsuper(\n\t\t\t`Cannot auto-generate rollback for \"${step.type}\" step on collection \"${step.collection}\". Provide an explicit .down() definition for this migration.`,\n\t\t\t'MIGRATION_ROLLBACK',\n\t\t\t{ stepType: step.type, collection: step.collection },\n\t\t)\n\t\tthis.name = 'MigrationRollbackError'\n\t}\n}\n\n/**\n * Determines whether a migration step can be automatically rolled back\n * without explicit developer-provided down steps.\n *\n * Auto-rollback is possible when the inverse operation is deterministic:\n * - addField -> removeField (drop the added column)\n * - addIndex -> removeIndex (drop the added index)\n * - removeIndex -> addIndex (re-create the index)\n * - renameField -> renameField (swap from/to names)\n *\n * Steps that CANNOT auto-rollback:\n * - removeField: the field descriptor is lost (need it to re-create the column)\n * - backfill: data transforms are not reversible\n *\n * @param step - The forward migration step to check\n * @returns true if the step can be auto-rolled back\n */\nexport function canAutoRollback(step: MigrationStep): boolean {\n\tswitch (step.type) {\n\t\tcase 'addField':\n\t\tcase 'addIndex':\n\t\tcase 'removeIndex':\n\t\tcase 'renameField':\n\t\t\treturn true\n\t\tcase 'removeField':\n\t\tcase 'backfill':\n\t\t\treturn false\n\t}\n}\n\n/**\n * Generates rollback steps for a list of forward migration steps.\n * Steps are reversed in order (last forward step becomes first rollback step).\n *\n * For steps that cannot be auto-rolled back, throws a MigrationRollbackError.\n * Use canAutoRollback() to check before calling, or provide explicit down steps\n * via the MigrationBuilder .down() API.\n *\n * @param forwardSteps - The forward migration steps to generate rollbacks for\n * @returns Array of rollback steps in reverse execution order\n * @throws MigrationRollbackError if any step cannot be auto-rolled back\n */\nexport function generateRollbackSteps(forwardSteps: readonly MigrationStep[]): MigrationStep[] {\n\tconst rollbackSteps: MigrationStep[] = []\n\n\t// Process in reverse order so rollback undoes changes in the opposite sequence\n\tfor (let i = forwardSteps.length - 1; i >= 0; i--) {\n\t\tconst step = forwardSteps[i]\n\t\tif (step === undefined) continue\n\n\t\tconst rollback = generateSingleRollbackStep(step)\n\t\trollbackSteps.push(rollback)\n\t}\n\n\treturn rollbackSteps\n}\n\n/**\n * Generate the inverse of a single migration step.\n * @internal\n */\nfunction generateSingleRollbackStep(step: MigrationStep): MigrationStep {\n\tswitch (step.type) {\n\t\tcase 'addField':\n\t\t\treturn { type: 'removeField', collection: step.collection, field: step.field }\n\n\t\tcase 'removeField':\n\t\t\t// removeField lacks the descriptor needed to re-create the column.\n\t\t\t// The developer must provide an explicit down step.\n\t\t\tif (step.descriptor) {\n\t\t\t\treturn {\n\t\t\t\t\ttype: 'addField',\n\t\t\t\t\tcollection: step.collection,\n\t\t\t\t\tfield: step.field,\n\t\t\t\t\tdescriptor: step.descriptor,\n\t\t\t\t}\n\t\t\t}\n\t\t\tthrow new MigrationRollbackError(step)\n\n\t\tcase 'renameField':\n\t\t\t// Reverse the rename: swap from and to\n\t\t\treturn { type: 'renameField', collection: step.collection, from: step.to, to: step.from }\n\n\t\tcase 'addIndex':\n\t\t\treturn { type: 'removeIndex', collection: step.collection, field: step.field }\n\n\t\tcase 'removeIndex':\n\t\t\treturn { type: 'addIndex', collection: step.collection, field: step.field }\n\n\t\tcase 'backfill':\n\t\t\t// Backfills with a reverseTransform can be auto-reversed\n\t\t\tif (step.reverseTransform) {\n\t\t\t\treturn {\n\t\t\t\t\ttype: 'backfill',\n\t\t\t\t\tcollection: step.collection,\n\t\t\t\t\ttransform: step.reverseTransform,\n\t\t\t\t}\n\t\t\t}\n\t\t\tthrow new MigrationRollbackError(step)\n\t}\n}\n\n/**\n * Create a ReversibleMigration from forward steps, explicit down steps, and version info.\n *\n * If explicit down steps are provided, they are used as-is.\n * If no explicit down steps are provided, auto-generation is attempted.\n *\n * @param upSteps - The forward migration steps\n * @param downSteps - Optional explicit rollback steps (overrides auto-generation)\n * @param fromVersion - The schema version before the migration\n * @param toVersion - The schema version after the migration\n * @returns A complete ReversibleMigration\n * @throws MigrationRollbackError if auto-generation fails and no explicit down steps provided\n */\nexport function createReversibleMigration(\n\tupSteps: readonly MigrationStep[],\n\tdownSteps: readonly MigrationStep[] | null,\n\tfromVersion: number,\n\ttoVersion: number,\n): ReversibleMigration {\n\tconst down = downSteps !== null ? [...downSteps] : generateRollbackSteps(upSteps)\n\n\treturn {\n\t\tup: [...upSteps],\n\t\tdown,\n\t\tfromVersion,\n\t\ttoVersion,\n\t}\n}\n","import type { FieldDescriptor } from '../types'\nimport type { MigrationDefinition, MigrationStep } from './migration-builder'\nimport { generateRollbackSteps } from './migration-rollback'\n\n/**\n * Convert migration steps to SQL statements.\n *\n * Structural steps (addField, removeField, renameField, addIndex, removeIndex)\n * produce SQL. Backfill steps are skipped (handled at the application layer\n * by reading rows and applying the transform function).\n *\n * @param steps - The migration steps from a MigrationBuilder\n * @returns Array of SQL statements for structural changes\n */\nexport function migrationStepsToSQL(steps: readonly MigrationStep[]): string[] {\n\tconst statements: string[] = []\n\n\tfor (const step of steps) {\n\t\tswitch (step.type) {\n\t\t\tcase 'addField':\n\t\t\t\tstatements.push(addFieldSQL(step.collection, step.field, step.descriptor))\n\t\t\t\tbreak\n\t\t\tcase 'removeField':\n\t\t\t\t// SQLite 3.35+ supports DROP COLUMN. For broader compat, we mark\n\t\t\t\t// the column as nullable so it can be ignored in queries.\n\t\t\t\t// Drop is preferred when available.\n\t\t\t\tstatements.push(`ALTER TABLE ${step.collection} DROP COLUMN ${step.field}`)\n\t\t\t\tbreak\n\t\t\tcase 'renameField':\n\t\t\t\t// SQLite 3.25+ supports RENAME COLUMN\n\t\t\t\tstatements.push(`ALTER TABLE ${step.collection} RENAME COLUMN ${step.from} TO ${step.to}`)\n\t\t\t\tbreak\n\t\t\tcase 'addIndex':\n\t\t\t\tstatements.push(\n\t\t\t\t\t`CREATE INDEX IF NOT EXISTS idx_${step.collection}_${step.field} ON ${step.collection} (${step.field})`,\n\t\t\t\t)\n\t\t\t\tbreak\n\t\t\tcase 'removeIndex':\n\t\t\t\tstatements.push(`DROP INDEX IF EXISTS idx_${step.collection}_${step.field}`)\n\t\t\t\tbreak\n\t\t\tcase 'backfill':\n\t\t\t\t// Backfills are handled by the store at runtime, not via SQL.\n\t\t\t\tbreak\n\t\t}\n\t}\n\n\treturn statements\n}\n\n/**\n * Generate SQL statements to roll back a migration.\n *\n * Uses the migration's explicit rollback steps if available,\n * otherwise auto-generates inverse steps from the forward steps.\n *\n * Backfill steps in the rollback are skipped (handled at the application layer).\n *\n * @param migration - The migration definition to generate rollback SQL for\n * @returns Array of SQL statements that undo the migration's structural changes\n *\n * @example\n * ```typescript\n * const migration = migrate()\n * .addField('todos', 'priority', t.enum(['low', 'medium', 'high']).default('medium'))\n * .addIndex('todos', 'priority')\n *\n * const rollbackSQL = rollbackStepsToSQL(migration)\n * // ['DROP INDEX IF EXISTS idx_todos_priority',\n * // 'ALTER TABLE todos DROP COLUMN priority']\n * ```\n */\nexport function rollbackStepsToSQL(migration: MigrationDefinition): string[] {\n\t// Use explicit rollback steps if provided, otherwise auto-generate from forward steps\n\tconst rollbackSteps = migration.rollbackSteps ?? generateRollbackSteps(migration.steps)\n\treturn migrationStepsToSQL(rollbackSteps)\n}\n\n/**\n * Produce an ALTER TABLE ADD COLUMN statement for a new field.\n */\nfunction addFieldSQL(collection: string, field: string, descriptor: FieldDescriptor): string {\n\tconst sqlType = mapFieldType(descriptor)\n\tconst parts = [`ALTER TABLE ${collection} ADD COLUMN ${field}`, sqlType]\n\n\tif (descriptor.defaultValue !== undefined) {\n\t\tparts.push(`DEFAULT ${sqlDefault(descriptor.defaultValue)}`)\n\t}\n\n\tif (descriptor.kind === 'enum' && descriptor.enumValues) {\n\t\tconst values = descriptor.enumValues.map((v) => `'${v}'`).join(', ')\n\t\tparts.push(`CHECK (${field} IN (${values}))`)\n\t}\n\n\treturn parts.join(' ')\n}\n\nfunction mapFieldType(descriptor: FieldDescriptor): string {\n\tswitch (descriptor.kind) {\n\t\tcase 'string':\n\t\t\treturn 'TEXT'\n\t\tcase 'number':\n\t\t\treturn 'REAL'\n\t\tcase 'boolean':\n\t\t\treturn 'INTEGER'\n\t\tcase 'enum':\n\t\t\treturn 'TEXT'\n\t\tcase 'timestamp':\n\t\t\treturn 'INTEGER'\n\t\tcase 'array':\n\t\t\treturn 'TEXT'\n\t\tcase 'richtext':\n\t\t\treturn 'BLOB'\n\t}\n}\n\nfunction sqlDefault(value: unknown): string {\n\tif (value === null) return 'NULL'\n\tif (typeof value === 'string') return `'${value}'`\n\tif (typeof value === 'number') return String(value)\n\tif (typeof value === 'boolean') return value ? '1' : '0'\n\treturn `'${JSON.stringify(value)}'`\n}\n","import type { CollectionDefinition, FieldDescriptor, FieldKind, SchemaDefinition } from '../types'\n\n/**\n * Output of the proto definition generator.\n * Contains the .proto file text, a type mapping, and a JSON descriptor\n * compatible with protobufjs's `Root.fromJSON()`.\n */\nexport interface ProtoOutput {\n\t/** The generated .proto file content as a string */\n\tproto: string\n\t/** TypeScript type map: field name -> protobuf type */\n\ttypeMap: Map<string, string>\n\t/** JSON descriptor for dynamic protobufjs usage (no .proto file needed) */\n\tjsonDescriptor: Record<string, unknown>\n}\n\n/**\n * Maps a Kora FieldKind to its protobuf scalar type string.\n * Array and enum kinds are handled separately because they\n * produce composite types (repeated, generated enum).\n */\nconst SCALAR_TYPE_MAP: Record<Exclude<FieldKind, 'array' | 'enum'>, string> = {\n\tstring: 'string',\n\tnumber: 'double',\n\tboolean: 'bool',\n\ttimestamp: 'int64',\n\trichtext: 'bytes',\n}\n\n/**\n * Maps a Kora FieldKind (when used as an array item) to its protobuf scalar type.\n * Only scalar kinds can be array items.\n */\nconst ARRAY_ITEM_TYPE_MAP: Record<string, string> = {\n\tstring: 'string',\n\tnumber: 'double',\n\tboolean: 'bool',\n\ttimestamp: 'int64',\n}\n\n/**\n * Converts a collection name (snake_case) to PascalCase for protobuf message names.\n * E.g., \"todo_items\" becomes \"TodoItems\", \"todos\" becomes \"Todos\".\n */\nfunction toPascalCase(name: string): string {\n\treturn name\n\t\t.split('_')\n\t\t.map((part) => part.charAt(0).toUpperCase() + part.slice(1))\n\t\t.join('')\n}\n\n/**\n * Converts a camelCase field name to snake_case for protobuf field names.\n * E.g., \"dueDate\" becomes \"due_date\", \"createdAt\" becomes \"created_at\".\n */\nfunction toSnakeCase(name: string): string {\n\treturn name.replace(/[A-Z]/g, (letter) => `_${letter.toLowerCase()}`)\n}\n\n/**\n * Resolves the protobuf type for a single field descriptor.\n *\n * @param fieldName - The field name (used for enum type naming)\n * @param descriptor - The Kora field descriptor\n * @param messageName - Parent message name (used for scoping enum type names)\n * @returns The protobuf type string\n */\nfunction resolveProtoType(\n\tfieldName: string,\n\tdescriptor: FieldDescriptor,\n\tmessageName: string,\n): string {\n\tif (descriptor.kind === 'enum') {\n\t\treturn `${messageName}${toPascalCase(fieldName)}`\n\t}\n\tif (descriptor.kind === 'array') {\n\t\tconst itemType = descriptor.itemKind\n\t\t\t? (ARRAY_ITEM_TYPE_MAP[descriptor.itemKind] ?? 'string')\n\t\t\t: 'string'\n\t\treturn itemType\n\t}\n\treturn SCALAR_TYPE_MAP[descriptor.kind as Exclude<FieldKind, 'array' | 'enum'>]\n}\n\n/**\n * Generates a protobuf enum definition for a Kora enum field.\n * Protobuf enums require the first value to be 0, so we add\n * an UNSPECIFIED sentinel as field 0.\n */\nfunction generateEnumBlock(\n\tenumTypeName: string,\n\tenumValues: readonly string[],\n\tindent: string,\n): string {\n\tconst lines: string[] = []\n\tlines.push(`${indent}enum ${enumTypeName} {`)\n\t// Proto3 requires field number 0 as a default/unspecified value\n\tlines.push(`${indent}\\t${enumTypeName.toUpperCase()}_UNSPECIFIED = 0;`)\n\tfor (let i = 0; i < enumValues.length; i++) {\n\t\tconst value = enumValues[i]\n\t\tif (value === undefined) continue\n\t\tlines.push(`${indent}\\t${enumTypeName.toUpperCase()}_${value.toUpperCase()} = ${i + 1};`)\n\t}\n\tlines.push(`${indent}}`)\n\treturn lines.join('\\n')\n}\n\n/**\n * Generates a protobuf message definition for a single Kora collection.\n * Includes nested enum types for any enum fields.\n *\n * @param collectionName - The collection name from the schema\n * @param collection - The collection definition\n * @param typeMap - Accumulator map for field->type mappings\n * @returns The proto message block as a string\n */\nfunction generateCollectionMessage(\n\tcollectionName: string,\n\tcollection: CollectionDefinition,\n\ttypeMap: Map<string, string>,\n): string {\n\tconst messageName = `${toPascalCase(collectionName)}Record`\n\tconst lines: string[] = []\n\tconst nestedEnums: string[] = []\n\n\tlines.push(`message ${messageName} {`)\n\n\t// Field 1 is always \"id\"\n\tlines.push('\\tstring id = 1;')\n\ttypeMap.set(`${collectionName}.id`, 'string')\n\n\tlet fieldNumber = 2\n\tconst entries = Object.entries(collection.fields)\n\n\tfor (const [fieldName, descriptor] of entries) {\n\t\tconst protoFieldName = toSnakeCase(fieldName)\n\t\tconst protoType = resolveProtoType(fieldName, descriptor, messageName)\n\t\tconst mapKey = `${collectionName}.${fieldName}`\n\n\t\tif (descriptor.kind === 'enum' && descriptor.enumValues) {\n\t\t\tconst enumTypeName = `${messageName}${toPascalCase(fieldName)}`\n\t\t\tnestedEnums.push(generateEnumBlock(enumTypeName, descriptor.enumValues, '\\t'))\n\t\t\ttypeMap.set(mapKey, enumTypeName)\n\t\t\tlines.push(`\\t${enumTypeName} ${protoFieldName} = ${fieldNumber};`)\n\t\t} else if (descriptor.kind === 'array') {\n\t\t\ttypeMap.set(mapKey, `repeated ${protoType}`)\n\t\t\tlines.push(`\\trepeated ${protoType} ${protoFieldName} = ${fieldNumber};`)\n\t\t} else {\n\t\t\ttypeMap.set(mapKey, protoType)\n\t\t\tlines.push(`\\t${protoType} ${protoFieldName} = ${fieldNumber};`)\n\t\t}\n\n\t\tfieldNumber++\n\t}\n\n\t// Insert nested enums before the closing brace\n\tif (nestedEnums.length > 0) {\n\t\t// Place enum definitions after the last field\n\t\tlines.push('')\n\t\tfor (const enumBlock of nestedEnums) {\n\t\t\tlines.push(enumBlock)\n\t\t}\n\t}\n\n\tlines.push('}')\n\treturn lines.join('\\n')\n}\n\n/**\n * The KoraOperation message — the wire format for individual operations.\n * Field assignments match the sync protocol specification from CLAUDE.md.\n */\nconst KORA_OPERATION_MESSAGE = `message KoraOperation {\n\\tstring id = 1;\n\\tstring node_id = 2;\n\\tstring type = 3;\n\\tstring collection = 4;\n\\tstring record_id = 5;\n\\tbytes data = 6;\n\\tbytes previous_data = 7;\n\\tint64 wall_time = 8;\n\\tint32 logical = 9;\n\\tstring timestamp_node_id = 10;\n\\tint64 sequence_number = 11;\n\\trepeated string causal_deps = 12;\n\\tint32 schema_version = 13;\n}`\n\n/**\n * The OperationBatch message — batches operations for sync transfer.\n */\nconst OPERATION_BATCH_MESSAGE = `message OperationBatch {\n\\trepeated KoraOperation operations = 1;\n\\tbool is_final = 2;\n}`\n\n/**\n * The HandshakeMessage — initiates a sync session with version vector exchange.\n */\nconst HANDSHAKE_MESSAGE = `message HandshakeMessage {\n\\tmap<string, int64> version_vector = 1;\n\\tint32 schema_version = 2;\n\\tstring node_id = 3;\n}`\n\n/**\n * The HandshakeResponse — server acknowledges and returns its version vector.\n */\nconst HANDSHAKE_RESPONSE_MESSAGE = `message HandshakeResponse {\n\\tmap<string, int64> version_vector = 1;\n\\tint32 schema_version = 2;\n}`\n\n/**\n * The Acknowledgment message — confirms receipt of an operation batch.\n */\nconst ACKNOWLEDGMENT_MESSAGE = `message Acknowledgment {\n\\tint64 sequence_number = 1;\n\\tstring node_id = 2;\n}`\n\n/**\n * Builds a JSON descriptor object compatible with protobufjs Root.fromJSON().\n * This allows runtime usage of the proto definitions without parsing .proto text.\n */\nfunction buildJsonDescriptor(schema: SchemaDefinition): Record<string, unknown> {\n\tconst nested: Record<string, unknown> = {}\n\n\t// Per-collection record messages\n\tfor (const [collectionName, collection] of Object.entries(schema.collections)) {\n\t\tconst messageName = `${toPascalCase(collectionName)}Record`\n\t\tconst fields: Record<string, unknown> = {\n\t\t\tid: { type: 'string', id: 1 },\n\t\t}\n\t\tconst nestedTypes: Record<string, unknown> = {}\n\n\t\tlet fieldNumber = 2\n\t\tfor (const [fieldName, descriptor] of Object.entries(collection.fields)) {\n\t\t\tconst protoFieldName = toSnakeCase(fieldName)\n\t\t\tconst fieldDef: Record<string, unknown> = { id: fieldNumber }\n\n\t\t\tif (descriptor.kind === 'enum' && descriptor.enumValues) {\n\t\t\t\tconst enumTypeName = `${messageName}${toPascalCase(fieldName)}`\n\t\t\t\tfieldDef.type = enumTypeName\n\n\t\t\t\t// Build enum values object for protobufjs\n\t\t\t\tconst enumValuesObj: Record<string, number> = {\n\t\t\t\t\t[`${enumTypeName.toUpperCase()}_UNSPECIFIED`]: 0,\n\t\t\t\t}\n\t\t\t\tfor (let i = 0; i < descriptor.enumValues.length; i++) {\n\t\t\t\t\tconst val = descriptor.enumValues[i]\n\t\t\t\t\tif (val === undefined) continue\n\t\t\t\t\tenumValuesObj[`${enumTypeName.toUpperCase()}_${val.toUpperCase()}`] = i + 1\n\t\t\t\t}\n\t\t\t\tnestedTypes[enumTypeName] = { values: enumValuesObj }\n\t\t\t} else if (descriptor.kind === 'array') {\n\t\t\t\tconst itemType = descriptor.itemKind\n\t\t\t\t\t? (ARRAY_ITEM_TYPE_MAP[descriptor.itemKind] ?? 'string')\n\t\t\t\t\t: 'string'\n\t\t\t\tfieldDef.type = itemType\n\t\t\t\tfieldDef.rule = 'repeated'\n\t\t\t} else {\n\t\t\t\tfieldDef.type = SCALAR_TYPE_MAP[descriptor.kind as Exclude<FieldKind, 'array' | 'enum'>]\n\t\t\t}\n\n\t\t\tfields[protoFieldName] = fieldDef\n\t\t\tfieldNumber++\n\t\t}\n\n\t\tconst messageDescriptor: Record<string, unknown> = { fields }\n\t\tif (Object.keys(nestedTypes).length > 0) {\n\t\t\tmessageDescriptor.nested = nestedTypes\n\t\t}\n\t\tnested[messageName] = messageDescriptor\n\t}\n\n\t// KoraOperation\n\tnested.KoraOperation = {\n\t\tfields: {\n\t\t\tid: { type: 'string', id: 1 },\n\t\t\tnode_id: { type: 'string', id: 2 },\n\t\t\ttype: { type: 'string', id: 3 },\n\t\t\tcollection: { type: 'string', id: 4 },\n\t\t\trecord_id: { type: 'string', id: 5 },\n\t\t\tdata: { type: 'bytes', id: 6 },\n\t\t\tprevious_data: { type: 'bytes', id: 7 },\n\t\t\twall_time: { type: 'int64', id: 8 },\n\t\t\tlogical: { type: 'int32', id: 9 },\n\t\t\ttimestamp_node_id: { type: 'string', id: 10 },\n\t\t\tsequence_number: { type: 'int64', id: 11 },\n\t\t\tcausal_deps: { type: 'string', id: 12, rule: 'repeated' },\n\t\t\tschema_version: { type: 'int32', id: 13 },\n\t\t},\n\t}\n\n\t// OperationBatch\n\tnested.OperationBatch = {\n\t\tfields: {\n\t\t\toperations: { type: 'KoraOperation', id: 1, rule: 'repeated' },\n\t\t\tis_final: { type: 'bool', id: 2 },\n\t\t},\n\t}\n\n\t// HandshakeMessage\n\tnested.HandshakeMessage = {\n\t\tfields: {\n\t\t\tversion_vector: { keyType: 'string', type: 'int64', id: 1 },\n\t\t\tschema_version: { type: 'int32', id: 2 },\n\t\t\tnode_id: { type: 'string', id: 3 },\n\t\t},\n\t}\n\n\t// HandshakeResponse\n\tnested.HandshakeResponse = {\n\t\tfields: {\n\t\t\tversion_vector: { keyType: 'string', type: 'int64', id: 1 },\n\t\t\tschema_version: { type: 'int32', id: 2 },\n\t\t},\n\t}\n\n\t// Acknowledgment\n\tnested.Acknowledgment = {\n\t\tfields: {\n\t\t\tsequence_number: { type: 'int64', id: 1 },\n\t\t\tnode_id: { type: 'string', id: 2 },\n\t\t},\n\t}\n\n\treturn {\n\t\tnested: {\n\t\t\tkora: { nested },\n\t\t},\n\t}\n}\n\n/**\n * Generates Protocol Buffer definitions from a Kora schema.\n *\n * Produces three outputs:\n * 1. A `.proto` file string conforming to proto3 syntax\n * 2. A type map linking Kora field paths to protobuf types\n * 3. A JSON descriptor for runtime protobufjs usage via `Root.fromJSON()`\n *\n * The generated definitions include:\n * - Per-collection record messages with proper type mappings\n * - Nested enum types for enum fields\n * - `KoraOperation` wrapper for the sync wire format\n * - `OperationBatch` for batched sync transfers\n * - `HandshakeMessage` / `HandshakeResponse` for sync session initiation\n * - `Acknowledgment` for delivery confirmation\n *\n * @param schema - A validated SchemaDefinition from defineSchema()\n * @returns ProtoOutput with proto text, type map, and JSON descriptor\n *\n * @example\n * ```typescript\n * import { defineSchema, t, generateProtoDefinitions } from '@korajs/core'\n *\n * const schema = defineSchema({\n * version: 1,\n * collections: {\n * todos: {\n * fields: {\n * title: t.string(),\n * completed: t.boolean().default(false),\n * }\n * }\n * }\n * })\n *\n * const { proto, typeMap, jsonDescriptor } = generateProtoDefinitions(schema)\n * // proto is a valid .proto file string\n * // typeMap maps \"todos.title\" -> \"string\", \"todos.completed\" -> \"bool\"\n * // jsonDescriptor can be loaded with protobuf.Root.fromJSON()\n * ```\n */\nexport function generateProtoDefinitions(schema: SchemaDefinition): ProtoOutput {\n\tconst typeMap = new Map<string, string>()\n\tconst sections: string[] = []\n\n\t// Proto3 header\n\tsections.push('syntax = \"proto3\";')\n\tsections.push('')\n\tsections.push('package kora;')\n\n\t// Per-collection messages\n\tconst collectionEntries = Object.entries(schema.collections)\n\tif (collectionEntries.length > 0) {\n\t\tsections.push('')\n\t\tsections.push('// Collection record messages')\n\t\tfor (const [collectionName, collection] of collectionEntries) {\n\t\t\tsections.push('')\n\t\t\tsections.push(generateCollectionMessage(collectionName, collection, typeMap))\n\t\t}\n\t}\n\n\t// Sync protocol messages\n\tsections.push('')\n\tsections.push('// Sync protocol messages')\n\tsections.push('')\n\tsections.push(KORA_OPERATION_MESSAGE)\n\tsections.push('')\n\tsections.push(OPERATION_BATCH_MESSAGE)\n\tsections.push('')\n\tsections.push(HANDSHAKE_MESSAGE)\n\tsections.push('')\n\tsections.push(HANDSHAKE_RESPONSE_MESSAGE)\n\tsections.push('')\n\tsections.push(ACKNOWLEDGMENT_MESSAGE)\n\n\tconst proto = `${sections.join('\\n')}\\n`\n\tconst jsonDescriptor = buildJsonDescriptor(schema)\n\n\treturn { proto, typeMap, jsonDescriptor }\n}\n"],"mappings":"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","names":["op","op","mapFieldType","sqlDefault"]}
|