@visiolab/effect-firebase 0.0.0-stage → 0.3.1

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.
Files changed (140) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +81 -2
  3. package/dist/_virtual/_rolldown/runtime.mjs +12 -0
  4. package/dist/app/App.d.mts +27 -0
  5. package/dist/app/App.mjs +27 -0
  6. package/dist/app/index.d.mts +2 -0
  7. package/dist/app/index.mjs +1 -0
  8. package/dist/firestore/Collection.d.mts +423 -0
  9. package/dist/firestore/Collection.mjs +133 -0
  10. package/dist/firestore/CollectionGroup.d.mts +164 -0
  11. package/dist/firestore/CollectionGroup.mjs +84 -0
  12. package/dist/firestore/DocumentPath.d.mts +95 -0
  13. package/dist/firestore/DocumentPath.mjs +71 -0
  14. package/dist/firestore/DocumentSnapshot.d.mts +239 -0
  15. package/dist/firestore/DocumentSnapshot.mjs +134 -0
  16. package/dist/firestore/FieldValue.d.mts +332 -0
  17. package/dist/firestore/FieldValue.mjs +256 -0
  18. package/dist/firestore/Firestore.d.mts +1165 -0
  19. package/dist/firestore/Firestore.mjs +274 -0
  20. package/dist/firestore/FirestoreModel.d.mts +1232 -0
  21. package/dist/firestore/FirestoreModel.mjs +586 -0
  22. package/dist/firestore/FirestoreSchema.d.mts +567 -0
  23. package/dist/firestore/FirestoreSchema.mjs +419 -0
  24. package/dist/firestore/FirestoreValue.d.mts +145 -0
  25. package/dist/firestore/FirestoreValue.mjs +87 -0
  26. package/dist/firestore/GeoPoint.d.mts +90 -0
  27. package/dist/firestore/GeoPoint.mjs +75 -0
  28. package/dist/firestore/Patch.d.mts +73 -0
  29. package/dist/firestore/Patch.mjs +57 -0
  30. package/dist/firestore/QuerySnapshot.d.mts +107 -0
  31. package/dist/firestore/QuerySnapshot.mjs +43 -0
  32. package/dist/firestore/Timestamp.d.mts +273 -0
  33. package/dist/firestore/Timestamp.mjs +255 -0
  34. package/dist/firestore/index.d.mts +14 -0
  35. package/dist/firestore/index.mjs +14 -0
  36. package/dist/firestore/internal/collection.mjs +156 -0
  37. package/dist/firestore/internal/collectionGroup.mjs +64 -0
  38. package/dist/firestore/internal/documentPath.d.mts +4 -0
  39. package/dist/firestore/internal/documentPath.mjs +42 -0
  40. package/dist/firestore/internal/documentSnapshot.mjs +63 -0
  41. package/dist/firestore/internal/fieldValue.d.mts +11 -0
  42. package/dist/firestore/internal/fieldValue.mjs +88 -0
  43. package/dist/firestore/internal/firestore.mjs +145 -0
  44. package/dist/firestore/internal/firestoreError.d.mts +29 -0
  45. package/dist/firestore/internal/firestoreError.mjs +30 -0
  46. package/dist/firestore/internal/firestoreModel.mjs +719 -0
  47. package/dist/firestore/internal/firestoreSchema.mjs +123 -0
  48. package/dist/firestore/internal/firestoreValue.mjs +108 -0
  49. package/dist/firestore/internal/firestoreValueWalk.d.mts +58 -0
  50. package/dist/firestore/internal/firestoreValueWalk.mjs +223 -0
  51. package/dist/firestore/internal/geoPoint.d.mts +4 -0
  52. package/dist/firestore/internal/geoPoint.mjs +39 -0
  53. package/dist/firestore/internal/patch.mjs +19 -0
  54. package/dist/firestore/internal/querySnapshot.mjs +24 -0
  55. package/dist/firestore/internal/schemaAST.mjs +35 -0
  56. package/dist/firestore/internal/snapshotExtra.mjs +35 -0
  57. package/dist/firestore/internal/streamFromListener.mjs +12 -0
  58. package/dist/firestore/internal/timestamp.d.mts +4 -0
  59. package/dist/firestore/internal/timestamp.mjs +66 -0
  60. package/dist/firestore/internal/timestampSchema.mjs +31 -0
  61. package/dist/firestore/internal/transactionFromCallback.mjs +66 -0
  62. package/dist/functions/Callable.d.mts +654 -0
  63. package/dist/functions/Callable.mjs +450 -0
  64. package/dist/functions/CallableError.d.mts +297 -0
  65. package/dist/functions/CallableError.mjs +256 -0
  66. package/dist/functions/CallableMiddleware.d.mts +213 -0
  67. package/dist/functions/CallableMiddleware.mjs +52 -0
  68. package/dist/functions/CallableRequest.d.mts +166 -0
  69. package/dist/functions/CallableRequest.mjs +18 -0
  70. package/dist/functions/Caller.d.mts +103 -0
  71. package/dist/functions/Caller.mjs +115 -0
  72. package/dist/functions/DocumentTrigger.d.mts +795 -0
  73. package/dist/functions/DocumentTrigger.mjs +566 -0
  74. package/dist/functions/FirebaseFunction.d.mts +79 -0
  75. package/dist/functions/FirebaseFunction.mjs +4 -0
  76. package/dist/functions/FunctionGroup.d.mts +175 -0
  77. package/dist/functions/FunctionGroup.mjs +64 -0
  78. package/dist/functions/index.d.mts +9 -0
  79. package/dist/functions/index.mjs +9 -0
  80. package/dist/functions/internal/callable.mjs +167 -0
  81. package/dist/functions/internal/callableMiddleware.d.mts +19 -0
  82. package/dist/functions/internal/callableMiddleware.mjs +15 -0
  83. package/dist/functions/internal/callableRequest.mjs +6 -0
  84. package/dist/functions/internal/documentTrigger.d.mts +10 -0
  85. package/dist/functions/internal/documentTrigger.mjs +73 -0
  86. package/dist/functions/internal/firebaseFunction.d.mts +5 -0
  87. package/dist/functions/internal/firebaseFunction.mjs +24 -0
  88. package/dist/functions/internal/functionGroup.mjs +36 -0
  89. package/package.json +72 -3
  90. package/src/app/App.ts +24 -0
  91. package/src/app/index.ts +7 -0
  92. package/src/firestore/Collection.ts +520 -0
  93. package/src/firestore/CollectionGroup.ts +245 -0
  94. package/src/firestore/DocumentPath.ts +114 -0
  95. package/src/firestore/DocumentSnapshot.ts +308 -0
  96. package/src/firestore/FieldValue.ts +375 -0
  97. package/src/firestore/Firestore.ts +1432 -0
  98. package/src/firestore/FirestoreModel.ts +1884 -0
  99. package/src/firestore/FirestoreSchema.ts +643 -0
  100. package/src/firestore/FirestoreValue.ts +207 -0
  101. package/src/firestore/GeoPoint.ts +105 -0
  102. package/src/firestore/Patch.ts +117 -0
  103. package/src/firestore/QuerySnapshot.ts +150 -0
  104. package/src/firestore/Timestamp.ts +302 -0
  105. package/src/firestore/index.ts +67 -0
  106. package/src/firestore/internal/collection.ts +246 -0
  107. package/src/firestore/internal/collectionGroup.ts +81 -0
  108. package/src/firestore/internal/documentPath.ts +53 -0
  109. package/src/firestore/internal/documentSnapshot.ts +117 -0
  110. package/src/firestore/internal/fieldValue.ts +119 -0
  111. package/src/firestore/internal/firestore.ts +322 -0
  112. package/src/firestore/internal/firestoreError.ts +36 -0
  113. package/src/firestore/internal/firestoreModel.ts +1242 -0
  114. package/src/firestore/internal/firestoreSchema.ts +218 -0
  115. package/src/firestore/internal/firestoreValue.ts +202 -0
  116. package/src/firestore/internal/firestoreValueWalk.ts +349 -0
  117. package/src/firestore/internal/geoPoint.ts +59 -0
  118. package/src/firestore/internal/patch.ts +21 -0
  119. package/src/firestore/internal/querySnapshot.ts +39 -0
  120. package/src/firestore/internal/schemaAST.ts +83 -0
  121. package/src/firestore/internal/snapshotExtra.ts +47 -0
  122. package/src/firestore/internal/streamFromListener.ts +27 -0
  123. package/src/firestore/internal/timestamp.ts +119 -0
  124. package/src/firestore/internal/timestampSchema.ts +42 -0
  125. package/src/firestore/internal/transactionFromCallback.ts +106 -0
  126. package/src/functions/Callable.ts +855 -0
  127. package/src/functions/CallableError.ts +348 -0
  128. package/src/functions/CallableMiddleware.ts +279 -0
  129. package/src/functions/CallableRequest.ts +207 -0
  130. package/src/functions/Caller.ts +141 -0
  131. package/src/functions/DocumentTrigger.ts +927 -0
  132. package/src/functions/FirebaseFunction.ts +96 -0
  133. package/src/functions/FunctionGroup.ts +225 -0
  134. package/src/functions/index.ts +62 -0
  135. package/src/functions/internal/callable.ts +272 -0
  136. package/src/functions/internal/callableMiddleware.ts +54 -0
  137. package/src/functions/internal/callableRequest.ts +8 -0
  138. package/src/functions/internal/documentTrigger.ts +143 -0
  139. package/src/functions/internal/firebaseFunction.ts +58 -0
  140. package/src/functions/internal/functionGroup.ts +47 -0
@@ -0,0 +1,274 @@
1
+ import { __exportAll } from "../_virtual/_rolldown/runtime.mjs";
2
+ import { FirestoreError, UndefinedCollectionError } from "./internal/firestoreError.mjs";
3
+ import { make as make$1 } from "./internal/firestore.mjs";
4
+ import { streamFromListener as streamFromListener$1 } from "./internal/streamFromListener.mjs";
5
+ import { transactionFromCallback as transactionFromCallback$1 } from "./internal/transactionFromCallback.mjs";
6
+ import { Context } from "effect";
7
+ // src/firestore/Firestore.ts
8
+ /**
9
+ * Reading and writing Firestore documents as an Effect service.
10
+ *
11
+ * {@link Firestore} is the portable service: it reads, listens to, writes and
12
+ * updates documents, and runs transactions, the same way on every backend.
13
+ * Every call is addressed by a reference built from a
14
+ * {@link Collection.Collection}, whose {@link FirestoreModel} encodes what is
15
+ * written and decodes what is read.
16
+ *
17
+ * - Define documents with {@link FirestoreModel.Class} and where they live with
18
+ * {@link Collection.make}.
19
+ * - Provide the service with {@link AdminFirestore.layer} on a server, or
20
+ * {@link ClientFirestore.layer} in a browser or app. Each layer also provides
21
+ * its richer service, {@link AdminFirestore.AdminFirestore} or
22
+ * {@link ClientFirestore.ClientFirestore}, as the same object.
23
+ * - Implement a backend of your own with {@link make}.
24
+ *
25
+ * @example Reading and writing a document
26
+ * ```ts
27
+ * import { Effect, Schema } from "effect";
28
+ * import { Collection, DocumentSnapshot, Firestore, FirestoreModel } from "@visiolab/effect-firebase/firestore";
29
+ *
30
+ * class User extends FirestoreModel.Class<User>("User")({ name: Schema.String }) {}
31
+ *
32
+ * const Users = Collection.make("users", User);
33
+ *
34
+ * const program = Effect.gen(function* () {
35
+ * const firestore = yield* Firestore.Firestore;
36
+ * const alice = Users.doc(Users.id.make("alice"));
37
+ *
38
+ * yield* firestore.setDoc(alice, { name: "Alice" });
39
+ *
40
+ * const snapshot = yield* firestore.getDoc(alice);
41
+ * if (DocumentSnapshot.isExisting(snapshot)) {
42
+ * const user = yield* snapshot.data;
43
+ * yield* Effect.log(user.name);
44
+ * }
45
+ * });
46
+ * ```
47
+ *
48
+ * @stability unstable
49
+ * @since 0.2.0
50
+ */
51
+ var Firestore_exports = /* @__PURE__ */ __exportAll({
52
+ Firestore: () => Firestore,
53
+ FirestoreError: () => FirestoreError,
54
+ Transaction: () => Transaction,
55
+ UndefinedCollectionError: () => UndefinedCollectionError,
56
+ make: () => make,
57
+ streamFromListener: () => streamFromListener,
58
+ transactionFromCallback: () => transactionFromCallback
59
+ });
60
+ /**
61
+ * Service key for the {@link Transaction} a {@link With.runTransaction} body
62
+ * runs in.
63
+ *
64
+ * @stability unstable
65
+ * @category services
66
+ * @since 0.2.0
67
+ */
68
+ const Transaction = Context.Service("@visiolab/effect-firebase/firestore/Firestore/Transaction");
69
+ /**
70
+ * Service key for the portable {@link Firestore}.
71
+ *
72
+ * Provide it with {@link AdminFirestore.layer} or
73
+ * {@link ClientFirestore.layer}.
74
+ *
75
+ * @stability unstable
76
+ * @category services
77
+ * @since 0.2.0
78
+ */
79
+ const Firestore = Context.Service("@visiolab/effect-firebase/firestore/Firestore");
80
+ /**
81
+ * Builds a Firestore service from one backend's hooks.
82
+ *
83
+ * **When to use**
84
+ *
85
+ * Use to implement a backend, such as a new SDK or an in-memory fake for
86
+ * tests. Applications use a backend's layer instead, such as
87
+ * {@link AdminFirestore.layer} or {@link ClientFirestore.layer}.
88
+ *
89
+ * **Details**
90
+ *
91
+ * The hooks only move Firestore Values to and from the backend. `make`
92
+ * handles everything above them, the same way for every backend:
93
+ *
94
+ * - encoding writes through the collection's model, in its `create` shape or
95
+ * the update shape for the requested mode
96
+ * - decoding reads into snapshots, with any extra the hooks return
97
+ * - matching each document of a Collection Group to its collection
98
+ * - tracing spans
99
+ * - providing the {@link Transaction} a transaction body runs in
100
+ *
101
+ * The return type is inferred from the hooks: a {@link With} whose reads and
102
+ * listens take the options the hooks take, whose snapshots carry the extra
103
+ * they return, and whose transaction bodies get the services the transaction
104
+ * hook's `context` offers. It is always the portable {@link Firestore} as
105
+ * well, so a backend can provide it under {@link Firestore}.
106
+ *
107
+ * A backend's richer service extends {@link With}, not {@link Firestore}, has a
108
+ * type id of its own, and its key's service type adds {@link Firestore} back,
109
+ * as {@link AdminFirestore.AdminFirestore} does. Its type then stays apart from
110
+ * {@link Firestore}, so providing a {@link Firestore} alone does not satisfy
111
+ * code that asks for the richer one.
112
+ *
113
+ * @see {@link transactionFromCallback} to build the `runTransaction` hook from an SDK callback
114
+ * @see {@link streamFromListener} to build the `streamDoc` and `streamDocs` hooks from an SDK listener
115
+ *
116
+ * @example An in-memory backend
117
+ * ```ts
118
+ * import { Effect, Layer, Stream } from "effect";
119
+ * import { Firestore } from "@visiolab/effect-firebase/firestore";
120
+ *
121
+ * const documents = new Map<string, Firestore.DocumentData>();
122
+ *
123
+ * const getDoc = (path: string) => Effect.sync(() => ({ data: documents.get(path) }));
124
+ * const setDoc = (path: string, data: Firestore.DocumentData) =>
125
+ * Effect.sync(() => void documents.set(path, data));
126
+ * const updateDoc = (path: string, data: Firestore.DocumentData) =>
127
+ * Effect.sync(() => void documents.set(path, { ...documents.get(path), ...data }));
128
+ * const getDocs = (selector: Firestore.CollectionSelector) =>
129
+ * Effect.sync(() => ({
130
+ * docs: [...documents]
131
+ * .filter(([path]) => selector._tag === "Collection" && path.startsWith(`${selector.path}/`))
132
+ * .map(([path, data]) => ({ path, data })),
133
+ * }));
134
+ *
135
+ * const firestore = Firestore.make({
136
+ * getDoc,
137
+ * getDocs,
138
+ * setDoc,
139
+ * updateDoc,
140
+ * addDoc: (path, data) => {
141
+ * const id = crypto.randomUUID();
142
+ * return Effect.as(setDoc(`${path}/${id}`, data), id);
143
+ * },
144
+ * streamDoc: (path) => Stream.fromEffect(getDoc(path)),
145
+ * streamDocs: (selector) => Stream.fromEffect(getDocs(selector)),
146
+ * runTransaction: { run: (body) => body({ getDoc, setDoc, updateDoc }) },
147
+ * });
148
+ *
149
+ * const FirestoreInMemory = Layer.succeed(Firestore.Firestore, firestore);
150
+ * ```
151
+ *
152
+ * @stability unstable
153
+ * @category constructors
154
+ * @since 0.3.0
155
+ */
156
+ const make = (options) => make$1(options, Transaction);
157
+ /**
158
+ * Builds the {@link MakeOptions.runTransaction} hook for an SDK that runs a
159
+ * transaction as a callback and retries it. It is the counterpart of Effect's
160
+ * `SqlClient.makeWithTransaction`.
161
+ *
162
+ * **When to use**
163
+ *
164
+ * Use when implementing a backend over an SDK with a
165
+ * `runTransaction(callback)` API, such as the Admin or client SDK.
166
+ *
167
+ * **Details**
168
+ *
169
+ * Each attempt runs the body over that attempt's operations. What the
170
+ * callback throws for a failed body decides whether the SDK retries it:
171
+ *
172
+ * - A {@link FirestoreError} with a `cause` throws that cause, so the SDK
173
+ * retries by its own rules, as for a read answered with `ABORTED`.
174
+ * - Any other failure throws a marker without a `code`, which the SDK never
175
+ * retries, even when the body's own error carries a `code`.
176
+ *
177
+ * A failure the SDK returns without retrying comes back as the body's own
178
+ * error, unwrapped. Anything else the SDK rejects with goes through
179
+ * `onError`. Interrupting the transaction interrupts the body and waits for
180
+ * the SDK to roll back.
181
+ *
182
+ * `Operations` is inferred from `operations`, so `context` receives a
183
+ * transaction with `getDocs` exactly when `operations` has one.
184
+ *
185
+ * @see {@link make} for the service this hook is part of
186
+ * @see {@link streamFromListener} for the matching helper for listeners
187
+ *
188
+ * @example Wrapping an SDK's runTransaction
189
+ * ```ts
190
+ * import { Effect } from "effect";
191
+ * import { Firestore } from "@visiolab/effect-firebase/firestore";
192
+ *
193
+ * interface SdkTransaction {
194
+ * get(path: string): Promise<Firestore.DocumentData | undefined>;
195
+ * set(path: string, data: Firestore.DocumentData): void;
196
+ * update(path: string, data: Firestore.DocumentData): void;
197
+ * }
198
+ *
199
+ * declare const db: {
200
+ * runTransaction<A>(callback: (tx: SdkTransaction) => Promise<A>, options?: object): Promise<A>;
201
+ * };
202
+ *
203
+ * const fail = (cause: unknown) => new Firestore.FirestoreError({ message: "Transaction failed", cause });
204
+ *
205
+ * const runTransaction = Firestore.transactionFromCallback({
206
+ * run: (callback, options) => db.runTransaction(callback, options),
207
+ * operations: (tx: SdkTransaction) => ({
208
+ * getDoc: (path: string) =>
209
+ * Effect.tryPromise({ try: () => tx.get(path), catch: fail }).pipe(
210
+ * Effect.map((data) => ({ data })),
211
+ * ),
212
+ * setDoc: (path: string, data: Firestore.DocumentData) => Effect.sync(() => tx.set(path, data)),
213
+ * updateDoc: (path: string, data: Firestore.DocumentData) =>
214
+ * Effect.sync(() => tx.update(path, data)),
215
+ * }),
216
+ * onError: fail,
217
+ * });
218
+ * ```
219
+ *
220
+ * @stability unstable
221
+ * @category constructors
222
+ * @since 0.3.0
223
+ */
224
+ const transactionFromCallback = transactionFromCallback$1;
225
+ /**
226
+ * Builds a listen hook's stream, such as {@link MakeOptions.streamDoc}, from
227
+ * an SDK listener that returns a function to stop listening.
228
+ *
229
+ * **When to use**
230
+ *
231
+ * Use when implementing a backend over an SDK with an `onSnapshot`-style
232
+ * listener.
233
+ *
234
+ * **Details**
235
+ *
236
+ * Each run of the stream attaches its own listener through `subscribe`, and
237
+ * detaches it when the run stops. A reader that falls behind only sees the
238
+ * latest snapshot.
239
+ *
240
+ * `map` turns each snapshot into what the stream emits. A snapshot it fails on
241
+ * fails the stream instead of throwing into the SDK. An error the listener
242
+ * receives fails the stream with what `onError` builds from it.
243
+ *
244
+ * @see {@link make} for the service this hook is part of
245
+ * @see {@link transactionFromCallback} for the matching helper for transactions
246
+ *
247
+ * @example Wrapping an SDK listener
248
+ * ```ts
249
+ * import { Result } from "effect";
250
+ * import { Firestore } from "@visiolab/effect-firebase/firestore";
251
+ *
252
+ * declare const sdk: {
253
+ * onSnapshot(
254
+ * path: string,
255
+ * onNext: (data: Firestore.DocumentData | undefined) => void,
256
+ * onError: (error: unknown) => void,
257
+ * ): () => void;
258
+ * };
259
+ *
260
+ * const streamDoc = (path: string) =>
261
+ * Firestore.streamFromListener({
262
+ * subscribe: (onNext, onError) => sdk.onSnapshot(path, onNext, onError),
263
+ * onError: (cause) =>
264
+ * new Firestore.FirestoreError({ message: `Failed to listen to "${path}"`, cause }),
265
+ * map: (data) => Result.succeed({ data }),
266
+ * });
267
+ * ```
268
+ *
269
+ * @stability unstable
270
+ * @category constructors
271
+ * @since 0.3.0
272
+ */
273
+ const streamFromListener = streamFromListener$1;
274
+ export { Firestore, FirestoreError, Firestore_exports, Transaction, UndefinedCollectionError, make, streamFromListener, transactionFromCallback };