@@ -13,8 +13,10 @@ import {
1313 TimeoutWaitingForTxIdError ,
1414} from "./errors"
1515import type {
16+ BaseCollectionConfig ,
1617 CollectionConfig ,
1718 DeleteMutationFnParams ,
19+ Fn ,
1820 InsertMutationFnParams ,
1921 SyncConfig ,
2022 UpdateMutationFnParams ,
@@ -53,176 +55,17 @@ type InferSchemaOutput<T> = T extends StandardSchemaV1
5355export interface ElectricCollectionConfig <
5456 T extends Row < unknown > = Row < unknown > ,
5557 TSchema extends StandardSchemaV1 = never ,
56- > {
58+ > extends BaseCollectionConfig <
59+ T ,
60+ string | number ,
61+ TSchema ,
62+ Record < string , Fn > ,
63+ { txid : Txid | Array < Txid > }
64+ > {
5765 /**
5866 * Configuration options for the ElectricSQL ShapeStream
5967 */
6068 shapeOptions : ShapeStreamOptions < GetExtensions < T > >
61-
62- /**
63- * All standard Collection configuration properties
64- */
65- id ?: string
66- schema ?: TSchema
67- getKey : CollectionConfig < T , string | number , TSchema > [ `getKey`]
68- sync ?: CollectionConfig < T , string | number , TSchema > [ `sync`]
69-
70- /**
71- * Optional asynchronous handler function called before an insert operation
72- * Must return an object containing a txid number or array of txids
73- * @param params Object containing transaction and collection information
74- * @returns Promise resolving to an object with txid or txids
75- * @example
76- * // Basic Electric insert handler - MUST return { txid: number }
77- * onInsert: async ({ transaction }) => {
78- * const newItem = transaction.mutations[0].modified
79- * const result = await api.todos.create({
80- * data: newItem
81- * })
82- * return { txid: result.txid } // Required for Electric sync matching
83- * }
84- *
85- * @example
86- * // Insert handler with multiple items - return array of txids
87- * onInsert: async ({ transaction }) => {
88- * const items = transaction.mutations.map(m => m.modified)
89- * const results = await Promise.all(
90- * items.map(item => api.todos.create({ data: item }))
91- * )
92- * return { txid: results.map(r => r.txid) } // Array of txids
93- * }
94- *
95- * @example
96- * // Insert handler with error handling
97- * onInsert: async ({ transaction }) => {
98- * try {
99- * const newItem = transaction.mutations[0].modified
100- * const result = await api.createTodo(newItem)
101- * return { txid: result.txid }
102- * } catch (error) {
103- * console.error('Insert failed:', error)
104- * throw error // This will cause the transaction to fail
105- * }
106- * }
107- *
108- * @example
109- * // Insert handler with batch operation - single txid
110- * onInsert: async ({ transaction }) => {
111- * const items = transaction.mutations.map(m => m.modified)
112- * const result = await api.todos.createMany({
113- * data: items
114- * })
115- * return { txid: result.txid } // Single txid for batch operation
116- * }
117- */
118- onInsert ?: (
119- params : InsertMutationFnParams < T >
120- ) => Promise < { txid : Txid | Array < Txid > } >
121-
122- /**
123- * Optional asynchronous handler function called before an update operation
124- * Must return an object containing a txid number or array of txids
125- * @param params Object containing transaction and collection information
126- * @returns Promise resolving to an object with txid or txids
127- * @example
128- * // Basic Electric update handler - MUST return { txid: number }
129- * onUpdate: async ({ transaction }) => {
130- * const { original, changes } = transaction.mutations[0]
131- * const result = await api.todos.update({
132- * where: { id: original.id },
133- * data: changes // Only the changed fields
134- * })
135- * return { txid: result.txid } // Required for Electric sync matching
136- * }
137- *
138- * @example
139- * // Update handler with multiple items - return array of txids
140- * onUpdate: async ({ transaction }) => {
141- * const updates = await Promise.all(
142- * transaction.mutations.map(m =>
143- * api.todos.update({
144- * where: { id: m.original.id },
145- * data: m.changes
146- * })
147- * )
148- * )
149- * return { txid: updates.map(u => u.txid) } // Array of txids
150- * }
151- *
152- * @example
153- * // Update handler with optimistic rollback
154- * onUpdate: async ({ transaction }) => {
155- * const mutation = transaction.mutations[0]
156- * try {
157- * const result = await api.updateTodo(mutation.original.id, mutation.changes)
158- * return { txid: result.txid }
159- * } catch (error) {
160- * // Transaction will automatically rollback optimistic changes
161- * console.error('Update failed, rolling back:', error)
162- * throw error
163- * }
164- * }
165- */
166- onUpdate ?: (
167- params : UpdateMutationFnParams < T >
168- ) => Promise < { txid : Txid | Array < Txid > } >
169-
170- /**
171- * Optional asynchronous handler function called before a delete operation
172- * Must return an object containing a txid number or array of txids
173- * @param params Object containing transaction and collection information
174- * @returns Promise resolving to an object with txid or txids
175- * @example
176- * // Basic Electric delete handler - MUST return { txid: number }
177- * onDelete: async ({ transaction }) => {
178- * const mutation = transaction.mutations[0]
179- * const result = await api.todos.delete({
180- * id: mutation.original.id
181- * })
182- * return { txid: result.txid } // Required for Electric sync matching
183- * }
184- *
185- * @example
186- * // Delete handler with multiple items - return array of txids
187- * onDelete: async ({ transaction }) => {
188- * const deletes = await Promise.all(
189- * transaction.mutations.map(m =>
190- * api.todos.delete({
191- * where: { id: m.key }
192- * })
193- * )
194- * )
195- * return { txid: deletes.map(d => d.txid) } // Array of txids
196- * }
197- *
198- * @example
199- * // Delete handler with batch operation - single txid
200- * onDelete: async ({ transaction }) => {
201- * const idsToDelete = transaction.mutations.map(m => m.original.id)
202- * const result = await api.todos.deleteMany({
203- * ids: idsToDelete
204- * })
205- * return { txid: result.txid } // Single txid for batch operation
206- * }
207- *
208- * @example
209- * // Delete handler with optimistic rollback
210- * onDelete: async ({ transaction }) => {
211- * const mutation = transaction.mutations[0]
212- * try {
213- * const result = await api.deleteTodo(mutation.original.id)
214- * return { txid: result.txid }
215- * } catch (error) {
216- * // Transaction will automatically rollback optimistic changes
217- * console.error('Delete failed, rolling back:', error)
218- * throw error
219- * }
220- * }
221- *
222- */
223- onDelete ?: (
224- params : DeleteMutationFnParams < T >
225- ) => Promise < { txid : Txid | Array < Txid > } >
22669}
22770
22871function isUpToDateMessage < T extends Row < unknown > > (
0 commit comments