@gettersethya/mira-collection 0.1.0-alpha.3 → 0.1.0-alpha.30

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 (73) hide show
  1. package/README.md +173 -164
  2. package/dist/src/collection/auth.d.ts +4 -34
  3. package/dist/src/collection/auth.d.ts.map +1 -1
  4. package/dist/src/collection/auth.js +19 -22
  5. package/dist/src/collection/auth.js.map +1 -1
  6. package/dist/src/collection/base.d.ts +7 -31
  7. package/dist/src/collection/base.d.ts.map +1 -1
  8. package/dist/src/collection/base.js +12 -15
  9. package/dist/src/collection/base.js.map +1 -1
  10. package/dist/src/collection/field.d.ts +41 -1
  11. package/dist/src/collection/field.d.ts.map +1 -1
  12. package/dist/src/collection/field.js +26 -1
  13. package/dist/src/collection/field.js.map +1 -1
  14. package/dist/src/collection/index.d.ts +5 -1
  15. package/dist/src/collection/index.d.ts.map +1 -1
  16. package/dist/src/collection/index.js.map +1 -1
  17. package/dist/src/collection/infer.d.ts +228 -0
  18. package/dist/src/collection/infer.d.ts.map +1 -0
  19. package/dist/src/collection/infer.js +2 -0
  20. package/dist/src/collection/infer.js.map +1 -0
  21. package/dist/src/collection/serialize.d.ts +0 -2
  22. package/dist/src/collection/serialize.d.ts.map +1 -1
  23. package/dist/src/collection/serialize.js +19 -6
  24. package/dist/src/collection/serialize.js.map +1 -1
  25. package/dist/src/collection/types.d.ts +15 -4
  26. package/dist/src/collection/types.d.ts.map +1 -1
  27. package/dist/src/collection/view.d.ts +4 -11
  28. package/dist/src/collection/view.d.ts.map +1 -1
  29. package/dist/src/collection/view.js +10 -10
  30. package/dist/src/collection/view.js.map +1 -1
  31. package/dist/src/filter/builder.d.ts.map +1 -1
  32. package/dist/src/filter/builder.js.map +1 -1
  33. package/dist/src/filter/compiler.d.ts +1 -1
  34. package/dist/src/filter/compiler.d.ts.map +1 -1
  35. package/dist/src/filter/compiler.js.map +1 -1
  36. package/dist/src/filter/index.d.ts +2 -2
  37. package/dist/src/filter/index.d.ts.map +1 -1
  38. package/dist/src/filter/index.js.map +1 -1
  39. package/dist/src/filter/types.d.ts +3 -3
  40. package/dist/src/filter/types.d.ts.map +1 -1
  41. package/dist/src/filter/types.js +32 -26
  42. package/dist/src/filter/types.js.map +1 -1
  43. package/dist/src/index.d.ts +1 -1
  44. package/dist/src/index.d.ts.map +1 -1
  45. package/dist/src/index.js.map +1 -1
  46. package/dist/src/rule/builder.d.ts +32 -36
  47. package/dist/src/rule/builder.d.ts.map +1 -1
  48. package/dist/src/rule/builder.js +21 -8
  49. package/dist/src/rule/builder.js.map +1 -1
  50. package/dist/src/rule/index.d.ts +1 -1
  51. package/dist/src/rule/index.d.ts.map +1 -1
  52. package/dist/src/rule/index.js +1 -1
  53. package/dist/src/rule/index.js.map +1 -1
  54. package/dist/src/rule/types.d.ts +23 -0
  55. package/dist/src/rule/types.d.ts.map +1 -1
  56. package/dist/tests/collection/auth.test.js +5 -5
  57. package/dist/tests/collection/auth.test.js.map +1 -1
  58. package/dist/tests/collection/base.test.js +4 -21
  59. package/dist/tests/collection/base.test.js.map +1 -1
  60. package/dist/tests/collection/field.test.js +25 -0
  61. package/dist/tests/collection/field.test.js.map +1 -1
  62. package/dist/tests/collection/index-type.test.js +1 -1
  63. package/dist/tests/collection/index-type.test.js.map +1 -1
  64. package/dist/tests/collection/serialize.test.js +47 -19
  65. package/dist/tests/collection/serialize.test.js.map +1 -1
  66. package/dist/tests/collection/view.test.js +1 -1
  67. package/dist/tests/collection/view.test.js.map +1 -1
  68. package/dist/tests/filter/compiler.test.js +10 -11
  69. package/dist/tests/filter/compiler.test.js.map +1 -1
  70. package/dist/tests/rule/builder.test.js +52 -0
  71. package/dist/tests/rule/builder.test.js.map +1 -1
  72. package/dist/tsconfig.tsbuildinfo +1 -1
  73. package/package.json +5 -4
package/README.md CHANGED
@@ -1,164 +1,173 @@
1
- # @gettersethya/mira-collection
2
-
3
- > **Early pre-alpha.** Breaking changes may occur without notice.
4
-
5
- Collection definitions, filter DSL, and access rule builder for [Mira](https://github.com/gettersethya/mira). Shared between server and client — isomorphic, no runtime dependencies beyond `effect`.
6
-
7
- ## Installation
8
-
9
- ```bash
10
- npm install @gettersethya/mira-collection effect
11
- # or
12
- pnpm add @gettersethya/mira-collection effect
13
- ```
14
-
15
- ## Collection types
16
-
17
- ### Base collection
18
-
19
- Standard CRUD collection. System fields `id`, `seqId`, `created`, and `updated` are added automatically.
20
-
21
- ```typescript
22
- import { BaseCollection, Bytes, Field, Rule } from "@gettersethya/mira-collection"
23
-
24
- const Posts = BaseCollection.define("posts", {
25
- title: Field.text({ maxLength: 200 }),
26
- slug: Field.text({ unique: true }),
27
- content: Field.text(),
28
- published: Field.boolean({ default: false }),
29
- authorId: Field.relation(Users),
30
- thumbnail: Field.file({ maxSize: Bytes.fromMB(5), mimeTypes: ["image/*"] }),
31
- })
32
- .indexes((I) => [
33
- I.on("authorId"),
34
- I.unique("slug"),
35
- ])
36
- .rules((R) => ({
37
- list: R.field("published").eq(R.literal(true)),
38
- view: Rule.or(R.field("published").eq(R.literal(true)), R.field("authorId").eq(R.authId(Users))),
39
- create: R.authId(Users).neq(R.literal(null)),
40
- update: R.field("authorId").eq(R.authId(Users)),
41
- delete: R.field("authorId").eq(R.authId(Users)),
42
- }))
43
- ```
44
-
45
- ### Auth collection
46
-
47
- Adds `email`, `password` (hashed), and `emailVerified` system fields. Exposes an `authWithPassword` endpoint.
48
-
49
- ```typescript
50
- import { AuthCollection, Field, Rule } from "@gettersethya/mira-collection"
51
-
52
- const Users = AuthCollection.define("users", {
53
- displayName: Field.text(),
54
- username: Field.text({ unique: true }),
55
- role: Field.text({ default: "user" }),
56
- })
57
- .rules((R) => ({
58
- list: Rule.public(),
59
- view: Rule.public(),
60
- create: Rule.public(),
61
- update: R.selfId().eq(R.authId(Users)), // users can only edit themselves
62
- }))
63
- ```
64
-
65
- ### View collection
66
-
67
- Read-only, backed by a SQL `VIEW`. Supports `list` and `view` only. Every field must be marked `.view()`.
68
-
69
- ```typescript
70
- import { Field, Rule, ViewCollection } from "@gettersethya/mira-collection"
71
-
72
- const PostsWithAuthors = ViewCollection.define(
73
- "posts_with_authors",
74
- `SELECT p.id, p.seqId, p.title, u.displayName AS authorName
75
- FROM posts p LEFT JOIN users u ON p.authorId = u.id`,
76
- {
77
- id: Field.text().view(),
78
- seqId: Field.integer().view(),
79
- title: Field.text().view(),
80
- authorName: Field.text().view(),
81
- }
82
- )
83
- .rules((R) => ({ list: Rule.public(), view: Rule.public() }))
84
- ```
85
-
86
- ## Field types
87
-
88
- ```typescript
89
- Field.text({ minLength?, maxLength?, unique?, indexed?, required?, default? })
90
- Field.email()
91
- Field.integer({ min?, max?, unique?, indexed?, default? })
92
- Field.number({ min?, max? })
93
- Field.boolean({ default? })
94
- Field.date()
95
- Field.json()
96
- Field.file({ maxSize?, mimeTypes?, protected? })
97
- Field.relation(Collection)
98
-
99
- // File size helpers
100
- Bytes.fromKB(n)
101
- Bytes.fromMB(n)
102
- Bytes.fromGB(n)
103
- ```
104
-
105
- ## Indexes
106
-
107
- ```typescript
108
- // Field-level (single column)
109
- Field.text({ unique: true }) // unique index
110
- Field.text({ indexed: true }) // non-unique index
111
-
112
- // Callback (composite or explicit)
113
- .indexes((I) => [
114
- I.on("authorId"), // non-unique
115
- I.on("authorId", "published"), // composite
116
- I.unique("slug"), // unique constraint
117
- I.unique("teamId", "userId"), // composite unique
118
- ])
119
- ```
120
-
121
- ## Rules
122
-
123
- Rules are evaluated server-side on every request. A missing key means **deny all** for that action.
124
-
125
- ```typescript
126
- Rule.public() // allow all
127
- R.authId(Users).neq(R.literal(null)) // logged-in users only
128
- R.field("ownerId").eq(R.authId(Users)) // owner-only
129
- R.field("role").in(R.literal(["admin", "mod"])) // role check
130
- R.auth(Users, "role").eq(R.literal("admin")) // check a field on the auth record
131
- Rule.not(R.field("archived").eq(R.literal(true))) // negation
132
- Rule.or(R.field("isPublic").eq(R.literal(true)), R.field("ownerId").eq(R.authId(Users)))
133
- Rule.and(R.field("published").eq(R.literal(true)), R.field("ownerId").eq(R.authId(Users)))
134
-
135
- // Date arithmetic
136
- R.field("created").gte(Rule.dateAdd(Rule.now(), -30, "day"))
137
-
138
- // Request values (header, query param, or body field)
139
- Rule.request("header", "x-api-key").eq(R.literal("secret"))
140
-
141
- // Subquery membership check
142
- Rule.subquery(Members, "teamId").where(R.field("userId").eq(R.authId(Users)))
143
- ```
144
-
145
- ## Filters
146
-
147
- Used in client queries. Type-checked against the collection's field types.
148
-
149
- ```typescript
150
- f.field("published").eq(true)
151
- f.field("viewCount").gte(100)
152
- f.field("status").in(["draft", "published"])
153
- f.field("title").like("%effect%")
154
- f.field("deletedAt").null()
155
- f.field("price").between(10, 100)
156
-
157
- f.and(f.field("published").eq(true), f.field("viewCount").gte(100))
158
- f.or(f.field("category").eq("tech"), f.field("category").eq("science"))
159
- f.not(f.field("archived").eq(true))
160
- ```
161
-
162
- ## More
163
-
164
- See the [Mira root README](https://github.com/gettersethya/mira) for full documentation.
1
+ # @gettersethya/mira-collection
2
+
3
+ [![npm](https://img.shields.io/npm/v/@gettersethya/mira-collection)](https://www.npmjs.com/package/@gettersethya/mira-collection)
4
+
5
+ > **Early pre-alpha.** Breaking changes may occur without notice.
6
+
7
+ Collection definitions, filter DSL, and access rule builder for [Mira](https://github.com/gettersethya/mira). Shared between server and client — isomorphic, no runtime dependencies beyond `effect`.
8
+
9
+ ## Installation
10
+
11
+ ```bash
12
+ npm install @gettersethya/mira-collection effect
13
+ # or
14
+ pnpm add @gettersethya/mira-collection effect
15
+ ```
16
+
17
+ ## Collection types
18
+
19
+ ### Base collection
20
+
21
+ Standard CRUD collection. System fields `id`, `seqId`, `created`, and `updated` are added automatically.
22
+
23
+ ```typescript
24
+ import { BaseCollection, Bytes, Field } from "@gettersethya/mira-collection"
25
+
26
+ export const Posts = BaseCollection.define("posts", {
27
+ title: Field.text({ maxLength: 200 }),
28
+ slug: Field.text({ unique: true }),
29
+ content: Field.text(),
30
+ published: Field.boolean({ default: false }),
31
+ authorId: Field.relation(Users),
32
+ thumbnail: Field.file({ maxSize: Bytes.fromMB(5), mimeTypes: ["image/*"] }),
33
+ })
34
+ .indexes((I) => [
35
+ I.on("authorId"),
36
+ I.unique("slug"),
37
+ ])
38
+ ```
39
+
40
+ ### Auth collection
41
+
42
+ Adds `email`, `password` (hashed with scrypt on create/update), and `emailVerified` system fields. Exposes an `authWithPassword` endpoint.
43
+
44
+ ```typescript
45
+ import { AuthCollection, Field } from "@gettersethya/mira-collection"
46
+
47
+ export const Users = AuthCollection.define("users", {
48
+ displayName: Field.text(),
49
+ username: Field.text({ unique: true }),
50
+ role: Field.text({ default: "user" }),
51
+ })
52
+ ```
53
+
54
+ ### View collection
55
+
56
+ Read-only, backed by a SQL `VIEW`. Supports `list` and `view` access rules. Every field must be marked `.view()`.
57
+
58
+ ```typescript
59
+ import { Field, ViewCollection } from "@gettersethya/mira-collection"
60
+
61
+ export const PostsWithAuthors = ViewCollection.define(
62
+ "posts_with_authors",
63
+ `SELECT p.id, p.seqId, p.title, u.displayName AS authorName
64
+ FROM posts p LEFT JOIN users u ON p.authorId = u.id`,
65
+ {
66
+ id: Field.text().view(),
67
+ seqId: Field.integer().view(),
68
+ title: Field.text().view(),
69
+ authorName: Field.text().view(),
70
+ }
71
+ )
72
+ ```
73
+
74
+ Rules for collections are defined server-side using `defineRule()` from `@gettersethya/mira`.
75
+
76
+ ## Type inference
77
+
78
+ The record and input inference types are exported from `@gettersethya/mira-collection`, so no
79
+ server or client package is required to derive TypeScript types from a collection definition.
80
+
81
+ ```typescript
82
+ import type { InferRecord, InferCreateInput, InferMutationInput } from "@gettersethya/mira-collection"
83
+ import { Posts } from "./collections.js"
84
+
85
+ type Post = InferRecord<typeof Posts> // full record incl. system fields
86
+ type NewPost = InferCreateInput<typeof Posts> // create input, no system fields
87
+ type Edit = InferMutationInput<typeof Posts> // mutation input; file fields are File | Blob
88
+ ```
89
+
90
+ Also exported: `RelationKeys`, `FileKeys`, `WithExpand`, `CollectionKind`, `CreateInput`,
91
+ `UpdateInput`, `AuthCreateInput`, `AuthUpdateInput`, `RegisterInput`, and `AnyAuthCollectionDef`.
92
+
93
+ ## Field types
94
+
95
+ ```typescript
96
+ Field.text({ minLength?, maxLength?, unique?, indexed?, required?, default? })
97
+ Field.literalText({ literal: ["a", "b"], default? })
98
+ Field.email()
99
+ Field.integer({ min?, max?, unique?, indexed?, default? })
100
+ Field.number({ min?, max? })
101
+ Field.boolean({ default? })
102
+ Field.date()
103
+ Field.json()
104
+ Field.file({ maxSize?, mimeTypes?, protected? })
105
+ Field.relation(Collection)
106
+
107
+ // File size helpers
108
+ Bytes.fromKB(n)
109
+ Bytes.fromMB(n)
110
+ Bytes.fromGB(n)
111
+ Bytes.fromTB(n)
112
+ ```
113
+
114
+ ## Indexes
115
+
116
+ ```typescript
117
+ // Field-level (single column)
118
+ Field.text({ unique: true }) // unique index
119
+ Field.text({ indexed: true }) // non-unique index
120
+
121
+ // Callback (composite or explicit)
122
+ .indexes((I) => [
123
+ I.on("authorId"), // non-unique
124
+ I.on("authorId", "published"), // composite
125
+ I.unique("slug"), // unique constraint
126
+ I.unique("teamId", "userId"), // composite unique
127
+ ])
128
+ ```
129
+
130
+ ## Rules
131
+
132
+ Rules are evaluated server-side on every request. A missing key means **deny all** for that action.
133
+
134
+ ```typescript
135
+ Rule.public() // allow all
136
+ R.authId(Users).neq(R.literal("")) // logged-in users only
137
+ R.field("ownerId").eq(R.authId(Users)) // owner-only
138
+ R.field("role").in(R.literal(["admin", "mod"])) // role check
139
+ R.auth(Users, "role").eq(R.literal("admin")) // check a field on the auth record
140
+ Rule.not(R.field("archived").eq(R.literal(true))) // negation
141
+ Rule.or(R.field("isPublic").eq(R.literal(true)), R.field("ownerId").eq(R.authId(Users)))
142
+ Rule.and(R.field("published").eq(R.literal(true)), R.field("ownerId").eq(R.authId(Users)))
143
+
144
+ // Date arithmetic
145
+ R.field("created").gte(Rule.dateAdd(Rule.now(), -30, "day"))
146
+
147
+ // Request values (header, query param, or body field)
148
+ Rule.request("header", "x-api-key").eq(R.literal("secret"))
149
+
150
+ // Subquery membership check
151
+ Rule.subquery(Members, "teamId").where(R.field("userId").eq(R.authId(Users)))
152
+ ```
153
+
154
+ ## Filters
155
+
156
+ Used in client queries. Type-checked against the collection's field types.
157
+
158
+ ```typescript
159
+ f.field("published").eq(true)
160
+ f.field("viewCount").gte(100)
161
+ f.field("status").in(["draft", "published"])
162
+ f.field("title").like("%effect%")
163
+ f.field("deletedAt").null()
164
+ f.field("price").between(10, 100)
165
+
166
+ f.and(f.field("published").eq(true), f.field("viewCount").gte(100))
167
+ f.or(f.field("category").eq("tech"), f.field("category").eq("science"))
168
+ f.not(f.field("archived").eq(true))
169
+ ```
170
+
171
+ ## More
172
+
173
+ See the [Mira root README](https://github.com/gettersethya/mira) for full documentation.
@@ -1,46 +1,26 @@
1
- import type { RuleBuilder } from "../rule/builder.js";
2
- import type { RuleMap } from "../rule/types.js";
3
- import type { OperandNode } from "../rule/types.js";
4
1
  import type { IndexBuilder, IndexEntry } from "./index-builder.js";
5
2
  import type { CollectionSchema, FieldDef, FieldsMap } from "./types.js";
6
3
  type AuthSystemField = "id" | "email" | "password" | "emailVerified" | "created" | "updated" | "seqId";
7
4
  type AuthRuleField = "id" | "email" | "emailVerified" | "created" | "updated" | "seqId";
8
- type AuthSystemFieldDefs = {
9
- id: FieldDef & {
10
- kind: "text";
11
- };
5
+ /** Only the auth-specific fields not already provided by InferRecord's base type. */
6
+ type AuthPublicFieldDefs = {
12
7
  email: FieldDef & {
13
8
  kind: "email";
14
9
  };
15
10
  emailVerified: FieldDef & {
16
11
  kind: "boolean";
17
12
  };
18
- created: FieldDef & {
19
- kind: "date";
20
- };
21
- updated: FieldDef & {
22
- kind: "date";
23
- };
24
- seqId: FieldDef & {
25
- kind: "seqId";
26
- };
27
- };
28
- /** Rule builder for auth collections — extends RuleBuilder with `selfId()`. */
29
- type AuthRuleBuilder<F extends FieldsMap> = RuleBuilder<F> & {
30
- /** authId operand for this collection. Use instead of `Rule.authId(ThisCollection)` to avoid circular references. */
31
- selfId(): OperandNode<any, string>;
32
13
  };
33
14
  type IndexCb<F extends FieldsMap> = (I: IndexBuilder<(keyof F & string) | AuthRuleField>) => Array<IndexEntry<(keyof F & string) | AuthRuleField>>;
34
- type RuleCb<F extends FieldsMap> = (R: AuthRuleBuilder<F & AuthSystemFieldDefs>) => RuleMap;
35
15
  /**
36
16
  * Builder returned by `AuthCollection.define()`.
37
17
  * Immediately satisfies `AnyCollectionDef` — no terminal `.build()` needed.
38
- * Chain `.indexes()` and/or `.rules()` to add optional concerns.
18
+ * Chain `.indexes()` to add optional indexes.
39
19
  * Each chained method returns a new builder; the original is unchanged.
40
20
  */
41
21
  export type AuthCollectionBuilder<F extends FieldsMap> = {
42
22
  name: string;
43
- fields: F;
23
+ fields: F & AuthPublicFieldDefs;
44
24
  schema: CollectionSchema & {
45
25
  "x-collection-kind": "auth";
46
26
  };
@@ -50,12 +30,6 @@ export type AuthCollectionBuilder<F extends FieldsMap> = {
50
30
  * Pass a callback to get a typed index builder with auto-completion over field names.
51
31
  */
52
32
  indexes(cb: IndexCb<F>): AuthCollectionBuilder<F>;
53
- /**
54
- * Add per-action access rules. No rule means deny all.
55
- * The rule builder includes `.selfId()` as a shorthand for the authenticated user's id
56
- * on this collection — use it instead of `Rule.authId(ThisCollection)` to avoid circular references.
57
- */
58
- rules(cb: RuleCb<F>): AuthCollectionBuilder<F>;
59
33
  };
60
34
  /**
61
35
  * Defines an auth collection for user authentication.
@@ -67,10 +41,6 @@ export type AuthCollectionBuilder<F extends FieldsMap> = {
67
41
  * name: Field.text(),
68
42
  * avatar: Field.file({ maxSize: Bytes.fromMB(2) })
69
43
  * })
70
- * .rules((R) => ({
71
- * list: R.field("id").eq(R.selfId()),
72
- * create: R.public()
73
- * }))
74
44
  */
75
45
  export declare const AuthCollection: {
76
46
  define<F extends FieldsMap & { [K in keyof F & AuthSystemField]?: never; }>(name: string, extraFields: F): AuthCollectionBuilder<F>;
@@ -1 +1 @@
1
- {"version":3,"file":"auth.d.ts","sourceRoot":"","sources":["../../../src/collection/auth.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAA;AACpD,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,iBAAiB,CAAA;AAC9C,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,iBAAiB,CAAA;AAElD,OAAO,KAAK,EAAE,YAAY,EAAE,UAAU,EAAE,MAAM,oBAAoB,CAAA;AAElE,OAAO,KAAK,EAAE,gBAAgB,EAAE,QAAQ,EAAE,SAAS,EAAgC,MAAM,YAAY,CAAA;AAErG,KAAK,eAAe,GAAG,IAAI,GAAG,OAAO,GAAG,UAAU,GAAG,eAAe,GAAG,SAAS,GAAG,SAAS,GAAG,OAAO,CAAA;AACtG,KAAK,aAAa,GAAG,IAAI,GAAG,OAAO,GAAG,eAAe,GAAG,SAAS,GAAG,SAAS,GAAG,OAAO,CAAA;AAEvF,KAAK,mBAAmB,GAAG;IACzB,EAAE,EAAa,QAAQ,GAAG;QAAE,IAAI,EAAE,MAAM,CAAA;KAAE,CAAA;IAC1C,KAAK,EAAU,QAAQ,GAAG;QAAE,IAAI,EAAE,OAAO,CAAA;KAAE,CAAA;IAC3C,aAAa,EAAE,QAAQ,GAAG;QAAE,IAAI,EAAE,SAAS,CAAA;KAAE,CAAA;IAC7C,OAAO,EAAQ,QAAQ,GAAG;QAAE,IAAI,EAAE,MAAM,CAAA;KAAE,CAAA;IAC1C,OAAO,EAAQ,QAAQ,GAAG;QAAE,IAAI,EAAE,MAAM,CAAA;KAAE,CAAA;IAC1C,KAAK,EAAU,QAAQ,GAAG;QAAE,IAAI,EAAE,OAAO,CAAA;KAAE,CAAA;CAC5C,CAAA;AAED,+EAA+E;AAC/E,KAAK,eAAe,CAAC,CAAC,SAAS,SAAS,IAAI,WAAW,CAAC,CAAC,CAAC,GAAG;IAC3D,qHAAqH;IACrH,MAAM,IAAI,WAAW,CAAC,GAAG,EAAE,MAAM,CAAC,CAAA;CACnC,CAAA;AAED,KAAK,OAAO,CAAC,CAAC,SAAS,SAAS,IAAI,CAClC,CAAC,EAAE,YAAY,CAAC,CAAC,MAAM,CAAC,GAAG,MAAM,CAAC,GAAG,aAAa,CAAC,KAChD,KAAK,CAAC,UAAU,CAAC,CAAC,MAAM,CAAC,GAAG,MAAM,CAAC,GAAG,aAAa,CAAC,CAAC,CAAA;AAE1D,KAAK,MAAM,CAAC,CAAC,SAAS,SAAS,IAAI,CACjC,CAAC,EAAE,eAAe,CAAC,CAAC,GAAG,mBAAmB,CAAC,KACxC,OAAO,CAAA;AAEZ;;;;;GAKG;AACH,MAAM,MAAM,qBAAqB,CAAC,CAAC,SAAS,SAAS,IAAI;IACvD,IAAI,EAAE,MAAM,CAAA;IACZ,MAAM,EAAE,CAAC,CAAA;IACT,MAAM,EAAE,gBAAgB,GAAG;QAAE,mBAAmB,EAAE,MAAM,CAAA;KAAE,CAAA;IAC1D;;;;OAIG;IACH,OAAO,CAAC,EAAE,EAAE,OAAO,CAAC,CAAC,CAAC,GAAG,qBAAqB,CAAC,CAAC,CAAC,CAAA;IACjD;;;;OAIG;IACH,KAAK,CAAC,EAAE,EAAE,MAAM,CAAC,CAAC,CAAC,GAAG,qBAAqB,CAAC,CAAC,CAAC,CAAA;CAC/C,CAAA;AAqCD;;;;;;;;;;;;;;GAcG;AACH,eAAO,MAAM,cAAc;WAClB,CAAC,SAAS,SAAS,GAAG,GAAG,CAAC,IAAI,MAAM,CAAC,GAAG,eAAe,CAAC,CAAC,EAAE,KAAK,GAAE,QACjE,MAAM,eACC,CAAC,GACb,qBAAqB,CAAC,CAAC,CAAC;CAG5B,CAAA"}
1
+ {"version":3,"file":"auth.d.ts","sourceRoot":"","sources":["../../../src/collection/auth.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,YAAY,EAAE,UAAU,EAAE,MAAM,oBAAoB,CAAA;AAGlE,OAAO,KAAK,EAAE,gBAAgB,EAAE,QAAQ,EAAE,SAAS,EAAgC,MAAM,YAAY,CAAA;AAErG,KAAK,eAAe,GAAG,IAAI,GAAG,OAAO,GAAG,UAAU,GAAG,eAAe,GAAG,SAAS,GAAG,SAAS,GAAG,OAAO,CAAA;AACtG,KAAK,aAAa,GAAG,IAAI,GAAG,OAAO,GAAG,eAAe,GAAG,SAAS,GAAG,SAAS,GAAG,OAAO,CAAA;AAEvF,qFAAqF;AACrF,KAAK,mBAAmB,GAAG;IACzB,KAAK,EAAU,QAAQ,GAAG;QAAE,IAAI,EAAE,OAAO,CAAA;KAAE,CAAA;IAC3C,aAAa,EAAE,QAAQ,GAAG;QAAE,IAAI,EAAE,SAAS,CAAA;KAAE,CAAA;CAC9C,CAAA;AAED,KAAK,OAAO,CAAC,CAAC,SAAS,SAAS,IAAI,CAClC,CAAC,EAAE,YAAY,CAAC,CAAC,MAAM,CAAC,GAAG,MAAM,CAAC,GAAG,aAAa,CAAC,KAChD,KAAK,CAAC,UAAU,CAAC,CAAC,MAAM,CAAC,GAAG,MAAM,CAAC,GAAG,aAAa,CAAC,CAAC,CAAA;AAE1D;;;;;GAKG;AACH,MAAM,MAAM,qBAAqB,CAAC,CAAC,SAAS,SAAS,IAAI;IACvD,IAAI,EAAE,MAAM,CAAA;IACZ,MAAM,EAAE,CAAC,GAAG,mBAAmB,CAAA;IAC/B,MAAM,EAAE,gBAAgB,GAAG;QAAE,mBAAmB,EAAE,MAAM,CAAA;KAAE,CAAA;IAC1D;;;;OAIG;IACH,OAAO,CAAC,EAAE,EAAE,OAAO,CAAC,CAAC,CAAC,GAAG,qBAAqB,CAAC,CAAC,CAAC,CAAA;CAClD,CAAA;AAuCD;;;;;;;;;;GAUG;AACH,eAAO,MAAM,cAAc;WAClB,CAAC,SAAS,SAAS,GAAG,GAAG,CAAC,IAAI,MAAM,CAAC,GAAG,eAAe,CAAC,CAAC,EAAE,KAAK,GAAE,QACjE,MAAM,eACC,CAAC,GACb,qBAAqB,CAAC,CAAC,CAAC;CAG5B,CAAA"}
@@ -1,30 +1,31 @@
1
- import { makeRuleBuilder } from "../rule/builder.js";
2
1
  import { Index } from "./index-builder.js";
3
2
  import { toJSONSchema } from "./serialize.js";
4
3
  const AUTH_SYSTEM_PROPERTIES = {
5
4
  email: { type: "string", format: "email", "x-system": true },
6
- password: { type: "string", "x-system": true, "x-hidden": true },
5
+ password: { type: "string", "x-system": true, "x-hidden": true, "x-kind": "password" },
7
6
  emailVerified: { type: "boolean", "x-system": true, default: false }
8
7
  };
8
+ const AUTH_SYSTEM_FIELD_DEFS = {
9
+ email: { _tag: "FieldDef", kind: "email" },
10
+ emailVerified: { _tag: "FieldDef", kind: "boolean" },
11
+ };
9
12
  const AUTH_SYSTEM_INDEXES = [{ fields: ["email"], unique: true }];
10
- function makeAuthBuilder(name, extraFields, indexesCb, rulesCb) {
11
- const indexes = indexesCb?.(Index);
12
- const authRuleBuilder = {
13
- ...makeRuleBuilder(),
14
- selfId() { return { kind: "authId", collection: name }; }
15
- };
16
- const rules = rulesCb?.(authRuleBuilder);
17
- const schema = toJSONSchema("auth", name, extraFields, {
18
- indexes: [...AUTH_SYSTEM_INDEXES, ...(indexes ?? [])],
19
- systemFields: AUTH_SYSTEM_PROPERTIES,
20
- ...(rules !== undefined ? { rules } : {})
21
- });
13
+ function makeAuthBuilder(name, extraFields, indexesCb) {
14
+ let _schema;
22
15
  return {
23
16
  name,
24
- fields: extraFields,
25
- schema,
26
- indexes: (cb) => makeAuthBuilder(name, extraFields, cb, rulesCb),
27
- rules: (cb) => makeAuthBuilder(name, extraFields, indexesCb, cb)
17
+ fields: Object.assign({}, AUTH_SYSTEM_FIELD_DEFS, extraFields),
18
+ get schema() {
19
+ if (_schema === undefined) {
20
+ const indexes = indexesCb?.(Index);
21
+ _schema = toJSONSchema("auth", name, extraFields, {
22
+ indexes: [...AUTH_SYSTEM_INDEXES, ...(indexes ?? [])],
23
+ systemFields: AUTH_SYSTEM_PROPERTIES,
24
+ });
25
+ }
26
+ return _schema;
27
+ },
28
+ indexes: (cb) => makeAuthBuilder(name, extraFields, cb)
28
29
  };
29
30
  }
30
31
  /**
@@ -37,10 +38,6 @@ function makeAuthBuilder(name, extraFields, indexesCb, rulesCb) {
37
38
  * name: Field.text(),
38
39
  * avatar: Field.file({ maxSize: Bytes.fromMB(2) })
39
40
  * })
40
- * .rules((R) => ({
41
- * list: R.field("id").eq(R.selfId()),
42
- * create: R.public()
43
- * }))
44
41
  */
45
42
  export const AuthCollection = {
46
43
  define(name, extraFields) {
@@ -1 +1 @@
1
- {"version":3,"file":"auth.js","sourceRoot":"","sources":["../../../src/collection/auth.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,eAAe,EAAE,MAAM,mBAAmB,CAAA;AAInD,OAAO,EAAE,KAAK,EAAE,MAAM,oBAAoB,CAAA;AAE1C,OAAO,EAAE,YAAY,EAAE,MAAM,gBAAgB,CAAA;AAqD7C,MAAM,sBAAsB,GAAuC;IACjE,KAAK,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,MAAM,EAAE,OAAO,EAAE,UAAU,EAAE,IAAI,EAAE;IAC5D,QAAQ,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,UAAU,EAAE,IAAI,EAAE,UAAU,EAAE,IAAI,EAAE;IAChE,aAAa,EAAE,EAAE,IAAI,EAAE,SAAS,EAAE,UAAU,EAAE,IAAI,EAAE,OAAO,EAAE,KAAK,EAAE;CACrE,CAAA;AAED,MAAM,mBAAmB,GAAoB,CAAC,EAAE,MAAM,EAAE,CAAC,OAAO,CAAC,EAAE,MAAM,EAAE,IAAI,EAAE,CAAC,CAAA;AAElF,SAAS,eAAe,CACtB,IAAY,EACZ,WAAc,EACd,SAAsB,EACtB,OAAmB;IAGnB,MAAM,OAAO,GAAG,SAAS,EAAE,CAAC,KAAyB,CAAC,CAAA;IACtD,MAAM,eAAe,GAA6C;QAChE,GAAG,eAAe,EAA2B;QAC7C,MAAM,KAA+B,OAAO,EAAE,IAAI,EAAE,QAAQ,EAAE,UAAU,EAAE,IAAI,EAAE,CAAA,CAAC,CAAC;KACnF,CAAA;IACD,MAAM,KAAK,GAAG,OAAO,EAAE,CAAC,eAAe,CAAC,CAAA;IACxC,MAAM,MAAM,GAAG,YAAY,CAAC,MAAM,EAAE,IAAI,EAAE,WAAW,EAAE;QACrD,OAAO,EAAE,CAAC,GAAG,mBAAmB,EAAE,GAAG,CAAC,OAAO,IAAI,EAAE,CAAC,CAAC;QACrD,YAAY,EAAE,sBAAsB;QACpC,GAAG,CAAC,KAAK,KAAK,SAAS,CAAC,CAAC,CAAC,EAAE,KAAK,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;KAC1C,CAAC,CAAA;IACF,OAAO;QACL,IAAI;QACJ,MAAM,EAAE,WAAW;QACnB,MAAM;QACN,OAAO,EAAE,CAAC,EAAE,EAAE,EAAE,CAAC,eAAe,CAAC,IAAI,EAAE,WAAW,EAAE,EAAE,EAAE,OAAO,CAAC;QAChE,KAAK,EAAE,CAAC,EAAE,EAAE,EAAE,CAAC,eAAe,CAAC,IAAI,EAAE,WAAW,EAAE,SAAS,EAAE,EAAE,CAAC;KACjE,CAAA;AACH,CAAC;AAED;;;;;;;;;;;;;;GAcG;AACH,MAAM,CAAC,MAAM,cAAc,GAAG;IAC5B,MAAM,CACJ,IAAY,EACZ,WAAc;QAEd,OAAO,eAAe,CAAC,IAAI,EAAE,WAAW,CAAC,CAAA;IAC3C,CAAC;CACF,CAAA"}
1
+ {"version":3,"file":"auth.js","sourceRoot":"","sources":["../../../src/collection/auth.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,KAAK,EAAE,MAAM,oBAAoB,CAAA;AAC1C,OAAO,EAAE,YAAY,EAAE,MAAM,gBAAgB,CAAA;AAkC7C,MAAM,sBAAsB,GAAuC;IACjE,KAAK,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,MAAM,EAAE,OAAO,EAAE,UAAU,EAAE,IAAI,EAAE;IAC5D,QAAQ,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,UAAU,EAAE,IAAI,EAAE,UAAU,EAAE,IAAI,EAAE,QAAQ,EAAE,UAAU,EAAE;IACtF,aAAa,EAAE,EAAE,IAAI,EAAE,SAAS,EAAE,UAAU,EAAE,IAAI,EAAE,OAAO,EAAE,KAAK,EAAE;CACrE,CAAA;AAED,MAAM,sBAAsB,GAAwB;IAClD,KAAK,EAAU,EAAE,IAAI,EAAE,UAAU,EAAE,IAAI,EAAE,OAAO,EAAE;IAClD,aAAa,EAAE,EAAE,IAAI,EAAE,UAAU,EAAE,IAAI,EAAE,SAAS,EAAE;CACrD,CAAA;AAED,MAAM,mBAAmB,GAAoB,CAAC,EAAE,MAAM,EAAE,CAAC,OAAO,CAAC,EAAE,MAAM,EAAE,IAAI,EAAE,CAAC,CAAA;AAElF,SAAS,eAAe,CACtB,IAAY,EACZ,WAAc,EACd,SAAsB;IAGtB,IAAI,OAAyE,CAAA;IAC7E,OAAO;QACL,IAAI;QACJ,MAAM,EAAE,MAAM,CAAC,MAAM,CAAC,EAAE,EAAE,sBAAsB,EAAE,WAAW,CAAC;QAC9D,IAAI,MAAM;YACR,IAAI,OAAO,KAAK,SAAS,EAAE,CAAC;gBAC1B,MAAM,OAAO,GAAG,SAAS,EAAE,CAAC,KAAyB,CAAC,CAAA;gBACtD,OAAO,GAAG,YAAY,CAAC,MAAM,EAAE,IAAI,EAAE,WAAW,EAAE;oBAChD,OAAO,EAAE,CAAC,GAAG,mBAAmB,EAAE,GAAG,CAAC,OAAO,IAAI,EAAE,CAAC,CAAC;oBACrD,YAAY,EAAE,sBAAsB;iBACrC,CAAuD,CAAA;YAC1D,CAAC;YACD,OAAO,OAAQ,CAAA;QACjB,CAAC;QACD,OAAO,EAAE,CAAC,EAAE,EAAE,EAAE,CAAC,eAAe,CAAC,IAAI,EAAE,WAAW,EAAE,EAAE,CAAC;KACxD,CAAA;AACH,CAAC;AAED;;;;;;;;;;GAUG;AACH,MAAM,CAAC,MAAM,cAAc,GAAG;IAC5B,MAAM,CACJ,IAAY,EACZ,WAAc;QAEd,OAAO,eAAe,CAAC,IAAI,EAAE,WAAW,CAAC,CAAA;IAC3C,CAAC;CACF,CAAA"}
@@ -1,45 +1,25 @@
1
- import type { RuleBuilder } from "../rule/builder.js";
2
- import type { RuleMap } from "../rule/types.js";
3
1
  import type { IndexBuilder, IndexEntry } from "./index-builder.js";
4
- import type { CollectionSchema, FieldDef, FieldsMap } from "./types.js";
2
+ import type { CollectionSchema, FieldsMap } from "./types.js";
5
3
  type BaseForbiddenField = "id" | "seqId";
6
4
  type BaseSystemField = "id" | "seqId" | "created" | "updated";
7
- type BaseSystemFieldDefs = {
8
- id: FieldDef & {
9
- kind: "text";
10
- };
11
- created: FieldDef & {
12
- kind: "date";
13
- };
14
- updated: FieldDef & {
15
- kind: "date";
16
- };
17
- seqId: FieldDef & {
18
- kind: "seqId";
19
- };
20
- };
21
5
  type IndexCb<F extends FieldsMap> = (I: IndexBuilder<(keyof F & string) | BaseSystemField>) => Array<IndexEntry<(keyof F & string) | BaseSystemField>>;
22
- type RuleCb<F extends FieldsMap> = (R: RuleBuilder<F & BaseSystemFieldDefs>) => RuleMap;
23
6
  /**
24
7
  * Builder returned by `BaseCollection.define()`.
25
8
  * Immediately satisfies `AnyCollectionDef` — no terminal `.build()` needed.
26
- * Chain `.indexes()` and/or `.rules()` to add optional concerns.
9
+ * Chain `.indexes()` to add optional indexes.
27
10
  * Each chained method returns a new builder; the original is unchanged.
28
11
  */
29
12
  export type BaseCollectionBuilder<F extends FieldsMap> = {
30
- name: string;
31
- fields: F;
32
- schema: CollectionSchema;
13
+ readonly name: string;
14
+ readonly fields: F;
15
+ readonly schema: CollectionSchema & {
16
+ "x-collection-kind": "base";
17
+ };
33
18
  /**
34
19
  * Add collection-level indexes (in addition to field-level `unique`/`indexed` flags).
35
20
  * Pass a callback to get a typed index builder with auto-completion over field names.
36
21
  */
37
22
  indexes(cb: IndexCb<F>): BaseCollectionBuilder<F>;
38
- /**
39
- * Add per-action access rules. No rule means deny all.
40
- * Pass a callback to get a typed rule builder with auto-completion over field names.
41
- */
42
- rules(cb: RuleCb<F>): BaseCollectionBuilder<F>;
43
23
  };
44
24
  /**
45
25
  * Defines a standard data collection.
@@ -52,10 +32,6 @@ export type BaseCollectionBuilder<F extends FieldsMap> = {
52
32
  * ownerId: Field.text()
53
33
  * })
54
34
  * .indexes((I) => [I.on("ownerId")])
55
- * .rules((R) => ({
56
- * list: Rule.public(),
57
- * view: R.field("ownerId").eq(R.authId(Users))
58
- * }))
59
35
  */
60
36
  export declare const BaseCollection: {
61
37
  define<F extends FieldsMap & { [K in keyof F & BaseForbiddenField]?: never; }>(name: string, fields: F): BaseCollectionBuilder<F>;
@@ -1 +1 @@
1
- {"version":3,"file":"base.d.ts","sourceRoot":"","sources":["../../../src/collection/base.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAA;AACpD,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,iBAAiB,CAAA;AAE9C,OAAO,KAAK,EAAE,YAAY,EAAE,UAAU,EAAE,MAAM,oBAAoB,CAAA;AAElE,OAAO,KAAK,EAAE,gBAAgB,EAAE,QAAQ,EAAE,SAAS,EAAE,MAAM,YAAY,CAAA;AAEvE,KAAK,kBAAkB,GAAG,IAAI,GAAG,OAAO,CAAA;AACxC,KAAK,eAAe,GAAG,IAAI,GAAG,OAAO,GAAG,SAAS,GAAG,SAAS,CAAA;AAE7D,KAAK,mBAAmB,GAAG;IACzB,EAAE,EAAO,QAAQ,GAAG;QAAE,IAAI,EAAE,MAAM,CAAA;KAAE,CAAA;IACpC,OAAO,EAAE,QAAQ,GAAG;QAAE,IAAI,EAAE,MAAM,CAAA;KAAE,CAAA;IACpC,OAAO,EAAE,QAAQ,GAAG;QAAE,IAAI,EAAE,MAAM,CAAA;KAAE,CAAA;IACpC,KAAK,EAAI,QAAQ,GAAG;QAAE,IAAI,EAAE,OAAO,CAAA;KAAE,CAAA;CACtC,CAAA;AAED,KAAK,OAAO,CAAC,CAAC,SAAS,SAAS,IAAI,CAClC,CAAC,EAAE,YAAY,CAAC,CAAC,MAAM,CAAC,GAAG,MAAM,CAAC,GAAG,eAAe,CAAC,KAClD,KAAK,CAAC,UAAU,CAAC,CAAC,MAAM,CAAC,GAAG,MAAM,CAAC,GAAG,eAAe,CAAC,CAAC,CAAA;AAE5D,KAAK,MAAM,CAAC,CAAC,SAAS,SAAS,IAAI,CACjC,CAAC,EAAE,WAAW,CAAC,CAAC,GAAG,mBAAmB,CAAC,KACpC,OAAO,CAAA;AAEZ;;;;;GAKG;AACH,MAAM,MAAM,qBAAqB,CAAC,CAAC,SAAS,SAAS,IAAI;IACvD,IAAI,EAAE,MAAM,CAAA;IACZ,MAAM,EAAE,CAAC,CAAA;IACT,MAAM,EAAE,gBAAgB,CAAA;IACxB;;;OAGG;IACH,OAAO,CAAC,EAAE,EAAE,OAAO,CAAC,CAAC,CAAC,GAAG,qBAAqB,CAAC,CAAC,CAAC,CAAA;IACjD;;;OAGG;IACH,KAAK,CAAC,EAAE,EAAE,MAAM,CAAC,CAAC,CAAC,GAAG,qBAAqB,CAAC,CAAC,CAAC,CAAA;CAC/C,CAAA;AAwBD;;;;;;;;;;;;;;;GAeG;AACH,eAAO,MAAM,cAAc;WAClB,CAAC,SAAS,SAAS,GAAG,GAAG,CAAC,IAAI,MAAM,CAAC,GAAG,kBAAkB,CAAC,CAAC,EAAE,KAAK,GAAE,QACpE,MAAM,UACJ,CAAC,GACR,qBAAqB,CAAC,CAAC,CAAC;CAG5B,CAAA"}
1
+ {"version":3,"file":"base.d.ts","sourceRoot":"","sources":["../../../src/collection/base.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,YAAY,EAAE,UAAU,EAAE,MAAM,oBAAoB,CAAA;AAGlE,OAAO,KAAK,EAAE,gBAAgB,EAAE,SAAS,EAAE,MAAM,YAAY,CAAA;AAE7D,KAAK,kBAAkB,GAAG,IAAI,GAAG,OAAO,CAAA;AACxC,KAAK,eAAe,GAAG,IAAI,GAAG,OAAO,GAAG,SAAS,GAAG,SAAS,CAAA;AAE7D,KAAK,OAAO,CAAC,CAAC,SAAS,SAAS,IAAI,CAClC,CAAC,EAAE,YAAY,CAAC,CAAC,MAAM,CAAC,GAAG,MAAM,CAAC,GAAG,eAAe,CAAC,KAClD,KAAK,CAAC,UAAU,CAAC,CAAC,MAAM,CAAC,GAAG,MAAM,CAAC,GAAG,eAAe,CAAC,CAAC,CAAA;AAE5D;;;;;GAKG;AACH,MAAM,MAAM,qBAAqB,CAAC,CAAC,SAAS,SAAS,IAAI;IACvD,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAA;IACrB,QAAQ,CAAC,MAAM,EAAE,CAAC,CAAA;IAClB,QAAQ,CAAC,MAAM,EAAE,gBAAgB,GAAG;QAAE,mBAAmB,EAAE,MAAM,CAAA;KAAE,CAAA;IACnE;;;OAGG;IACH,OAAO,CAAC,EAAE,EAAE,OAAO,CAAC,CAAC,CAAC,GAAG,qBAAqB,CAAC,CAAC,CAAC,CAAA;CAClD,CAAA;AAyBD;;;;;;;;;;;GAWG;AACH,eAAO,MAAM,cAAc;WAClB,CAAC,SAAS,SAAS,GAAG,GAAG,CAAC,IAAI,MAAM,CAAC,GAAG,kBAAkB,CAAC,CAAC,EAAE,KAAK,GAAE,QACpE,MAAM,UACJ,CAAC,GACR,qBAAqB,CAAC,CAAC,CAAC;CAG5B,CAAA"}
@@ -1,19 +1,20 @@
1
- import { makeRuleBuilder } from "../rule/builder.js";
2
1
  import { Index } from "./index-builder.js";
3
2
  import { toJSONSchema } from "./serialize.js";
4
- function makeBaseBuilder(name, fields, indexesCb, rulesCb) {
5
- const indexes = indexesCb?.(Index);
6
- const rules = rulesCb?.(makeRuleBuilder());
7
- const schema = toJSONSchema("base", name, fields, {
8
- ...(indexes !== undefined ? { indexes } : {}),
9
- ...(rules !== undefined ? { rules } : {})
10
- });
3
+ function makeBaseBuilder(name, fields, indexesCb) {
4
+ let _schema;
11
5
  return {
12
6
  name,
13
7
  fields,
14
- schema,
15
- indexes: (cb) => makeBaseBuilder(name, fields, cb, rulesCb),
16
- rules: (cb) => makeBaseBuilder(name, fields, indexesCb, cb)
8
+ get schema() {
9
+ if (_schema === undefined) {
10
+ const indexes = indexesCb?.(Index);
11
+ _schema = toJSONSchema("base", name, fields, {
12
+ ...(indexes !== undefined ? { indexes } : {})
13
+ });
14
+ }
15
+ return _schema;
16
+ },
17
+ indexes: (cb) => makeBaseBuilder(name, fields, cb)
17
18
  };
18
19
  }
19
20
  /**
@@ -27,10 +28,6 @@ function makeBaseBuilder(name, fields, indexesCb, rulesCb) {
27
28
  * ownerId: Field.text()
28
29
  * })
29
30
  * .indexes((I) => [I.on("ownerId")])
30
- * .rules((R) => ({
31
- * list: Rule.public(),
32
- * view: R.field("ownerId").eq(R.authId(Users))
33
- * }))
34
31
  */
35
32
  export const BaseCollection = {
36
33
  define(name, fields) {
@@ -1 +1 @@
1
- {"version":3,"file":"base.js","sourceRoot":"","sources":["../../../src/collection/base.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,eAAe,EAAE,MAAM,mBAAmB,CAAA;AAGnD,OAAO,EAAE,KAAK,EAAE,MAAM,oBAAoB,CAAA;AAE1C,OAAO,EAAE,YAAY,EAAE,MAAM,gBAAgB,CAAA;AA2C7C,SAAS,eAAe,CACtB,IAAY,EACZ,MAAS,EACT,SAAsB,EACtB,OAAmB;IAGnB,MAAM,OAAO,GAAG,SAAS,EAAE,CAAC,KAAyB,CAAC,CAAA;IACtD,MAAM,KAAK,GAAG,OAAO,EAAE,CAAC,eAAe,EAA2B,CAAC,CAAA;IACnE,MAAM,MAAM,GAAG,YAAY,CAAC,MAAM,EAAE,IAAI,EAAE,MAAM,EAAE;QAChD,GAAG,CAAC,OAAO,KAAK,SAAS,CAAC,CAAC,CAAC,EAAE,OAAO,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;QAC7C,GAAG,CAAC,KAAK,KAAK,SAAS,CAAC,CAAC,CAAC,EAAE,KAAK,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;KAC1C,CAAC,CAAA;IACF,OAAO;QACL,IAAI;QACJ,MAAM;QACN,MAAM;QACN,OAAO,EAAE,CAAC,EAAE,EAAE,EAAE,CAAC,eAAe,CAAC,IAAI,EAAE,MAAM,EAAE,EAAE,EAAE,OAAO,CAAC;QAC3D,KAAK,EAAE,CAAC,EAAE,EAAE,EAAE,CAAC,eAAe,CAAC,IAAI,EAAE,MAAM,EAAE,SAAS,EAAE,EAAE,CAAC;KAC5D,CAAA;AACH,CAAC;AAED;;;;;;;;;;;;;;;GAeG;AACH,MAAM,CAAC,MAAM,cAAc,GAAG;IAC5B,MAAM,CACJ,IAAY,EACZ,MAAS;QAET,OAAO,eAAe,CAAC,IAAI,EAAE,MAAM,CAAC,CAAA;IACtC,CAAC;CACF,CAAA"}
1
+ {"version":3,"file":"base.js","sourceRoot":"","sources":["../../../src/collection/base.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,KAAK,EAAE,MAAM,oBAAoB,CAAA;AAC1C,OAAO,EAAE,YAAY,EAAE,MAAM,gBAAgB,CAAA;AA2B7C,SAAS,eAAe,CACtB,IAAY,EACZ,MAAS,EACT,SAAsB;IAGtB,IAAI,OAAyE,CAAA;IAC7E,OAAO;QACL,IAAI;QACJ,MAAM;QACN,IAAI,MAAM;YACR,IAAI,OAAO,KAAK,SAAS,EAAE,CAAC;gBAC1B,MAAM,OAAO,GAAG,SAAS,EAAE,CAAC,KAAyB,CAAC,CAAA;gBACtD,OAAO,GAAG,YAAY,CAAC,MAAM,EAAE,IAAI,EAAE,MAAM,EAAE;oBAC3C,GAAG,CAAC,OAAO,KAAK,SAAS,CAAC,CAAC,CAAC,EAAE,OAAO,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;iBAC9C,CAAC,CAAA;YACJ,CAAC;YACD,OAAO,OAAQ,CAAA;QACjB,CAAC;QACD,OAAO,EAAE,CAAC,EAAE,EAAE,EAAE,CAAC,eAAe,CAAC,IAAI,EAAE,MAAM,EAAE,EAAE,CAAC;KACnD,CAAA;AACH,CAAC;AAED;;;;;;;;;;;GAWG;AACH,MAAM,CAAC,MAAM,cAAc,GAAG;IAC5B,MAAM,CACJ,IAAY,EACZ,MAAS;QAET,OAAO,eAAe,CAAC,IAAI,EAAE,MAAM,CAAC,CAAA;IACtC,CAAC;CACF,CAAA"}