@owlmeans/resource 0.1.18-rc.9 → 0.1.18

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 (56) hide show
  1. package/README.md +336 -135
  2. package/agent-meta/manifest.json +80 -4
  3. package/agent-meta/skills/resource/SKILL.md +24 -105
  4. package/agent-meta/skills/resource/parts/capabilities.md +23 -0
  5. package/agent-meta/skills/resource/parts/criteria.md +60 -0
  6. package/agent-meta/skills/resource/parts/memory-engine.md +27 -0
  7. package/agent-meta/skills/resource/parts/migrations.md +35 -0
  8. package/agent-meta/skills/resource-choice/SKILL.md +16 -9
  9. package/build/consts.d.ts +0 -3
  10. package/build/consts.d.ts.map +1 -1
  11. package/build/consts.js +0 -23
  12. package/build/consts.js.map +1 -1
  13. package/build/errors.d.ts +13 -0
  14. package/build/errors.d.ts.map +1 -1
  15. package/build/errors.js +15 -1
  16. package/build/errors.js.map +1 -1
  17. package/build/index.d.ts +2 -0
  18. package/build/index.d.ts.map +1 -1
  19. package/build/index.js +1 -0
  20. package/build/index.js.map +1 -1
  21. package/build/migration.js +0 -0
  22. package/build/migration.js.map +1 -1
  23. package/build/types.d.ts +3 -1
  24. package/build/types.d.ts.map +1 -1
  25. package/build/utils/consts.local.d.ts +2 -0
  26. package/build/utils/consts.local.d.ts.map +1 -0
  27. package/build/utils/consts.local.js +2 -0
  28. package/build/utils/consts.local.js.map +1 -0
  29. package/build/utils/name.d.ts.map +1 -1
  30. package/build/utils/name.js.map +1 -1
  31. package/build/utils/query/types.d.ts +35 -0
  32. package/build/utils/query/types.d.ts.map +1 -0
  33. package/build/utils/query/types.js +2 -0
  34. package/build/utils/query/types.js.map +1 -0
  35. package/build/utils/query.d.ts +8 -20
  36. package/build/utils/query.d.ts.map +1 -1
  37. package/build/utils/query.js +97 -103
  38. package/build/utils/query.js.map +1 -1
  39. package/build/utils.d.ts +4 -0
  40. package/build/utils.d.ts.map +1 -0
  41. package/build/utils.js +24 -0
  42. package/build/utils.js.map +1 -0
  43. package/package.json +7 -5
  44. package/src/consts.ts +0 -25
  45. package/src/errors.ts +16 -1
  46. package/src/index.ts +2 -0
  47. package/src/migration.ts +0 -0
  48. package/src/types.ts +1 -1
  49. package/src/utils/consts.local.ts +1 -0
  50. package/src/utils/name.ts +2 -2
  51. package/src/utils/query/types.ts +37 -0
  52. package/src/utils/query.ts +106 -98
  53. package/src/utils.ts +26 -0
  54. package/tests/errors.spec.ts +60 -0
  55. package/tests/tsconfig.json +17 -0
  56. package/tsconfig.json +1 -1
@@ -8,7 +8,7 @@ user-invocable: false
8
8
  # @owlmeans/resource
9
9
 
10
10
  **Layer:** Core
11
- **Install:** `"@owlmeans/resource": "^0.1.18-rc.9"` in `dependencies`
11
+ **Install:** `"@owlmeans/resource": "^0.1.18"` in `dependencies`
12
12
 
13
13
  ## Key Exports
14
14
 
@@ -19,7 +19,7 @@ user-invocable: false
19
19
  | `Criteria<T>`, `FieldCriteria<V>`, `FieldOperators<V>` | The query language, typed by the record — a mistyped field is a compile error. |
20
20
  | `Sort<T>`, `SortField<T>`, `FirstOptions<T>`, `ListOptions<T>`, `ListQuery<T>`, `ListResult<T>` | Ordering, the read options, the one-object form an API carries over the wire, and the answer shape `{ items, total, page?, size? }`. |
21
21
  | `WriteOptions`, `Ttl` | `{ ttl }` on `create`/`update`/`save`; seconds from now, or the instant to expire at. Backends without expiry refuse it. |
22
- | `matchCriteria`, `filterRecords`, `sortRecords`, `firstMatch`, `applyQuery` | The shared in-memory engine — one criteria object means the same thing in a browser store as it does in SQL. |
22
+ | `recordQueryHelper` — `matchCriteria`, `filterRecords`, `sortRecords`, `firstMatch`, `applyQuery` | The shared in-memory engine — one criteria object means the same thing in a browser store as it does in SQL. |
23
23
  | `PubSubResource<T>`, `WatchableResource<T>`, `StreamResource<T>`, `LockableResource<T>` | **Optional capabilities**, composed into a concrete resource interface alongside `Resource<T>`. `SubscribeOptions` (`{ channel, once, ttl }`) and `Unsubscribe` come with the first two. |
24
24
  | `MigratableResource<Tx, Self>` | **Optional migration capability** — `migration(name, apply, stage?)` (chainable) + `migrations()`. Optional the way pub/sub is on redis resources: mongo and postgres extend it, backends with nothing to migrate don't. |
25
25
  | `Migration`, `MigrationRegistry`, `MigrationStore`, `MigrationReport`, `MigrationRunOptions` | The framework's contracts. `MigrationStore` is the *migration register* a database implements to track applied migrations (`ensure`/`applied`/`baseline`/`run`). |
@@ -30,7 +30,7 @@ user-invocable: false
30
30
  | `ResourceDbService<Db, Client>`, `DbLocker<T>` | What a connection service implements: `db`/`client`/`clients`/`config`/`name`/`ensureConfigAlias`/`initialize`, plus `lock`/`unlock` when the backend encrypts fields. |
31
31
  | `ResourceMaker<R, T>` | `(dbAlias?, serviceAlias?) => T` — the signature every resource maker is typed with, so an app registers `makeXResource()` without repeating the argument list. |
32
32
  | `filterObject(obj, keep?)`, `createListSchema` | Drop null and undefined properties, keeping the names listed in `keep`; the AJV schema for a `ListResult<T>` envelope. |
33
- | Errors | `ResourceError`, `UnknownRecordError`, `MisshapedRecord`, `RecordExists`, `RecordUpdateFailed`, `UnsupportedArgumentError`, `UnsupportedMethodError`, `MigrationError`, `MigrationConflict`. |
33
+ | Errors | `ResourceError`, `UnknownRecordError` (404), `MisshapedRecord`, `RecordExists` (409), `RecordUpdateFailed`, `UnsupportedArgumentError`, `UnsupportedMethodError`, `MigrationError`, `MigrationConflict` — the unmarked ones are faults (500). `tests/errors.spec.ts` refuses an exported class whose status was not decided. `UnknownRecordError.id` is everything after the first `/`, so an id or criteria text holding one survives. |
34
34
  | `DbConfig`, `Config`, `Context` | Database config (`cfg.dbs`) types. |
35
35
 
36
36
  ## Usage
@@ -85,110 +85,18 @@ else; the criteria overload takes `{ sort }` to say which match is "the" one:
85
85
  Every method returns the record(s) themselves, never a driver result object — there is no
86
86
  `rowsAffected`/`rowCount` anywhere on this contract.
87
87
 
88
- ### The criteria language
88
+ ### What an escaped storage error answers
89
89
 
90
- `Criteria<T>` is keyed by the record's own fields, so a typo is a compile error. A dotted key
91
- reaches into a nested value (or a jsonb column) and stays open.
90
+ The two refusals declare their HTTP status (`static httpStatus`, the `error` skill's rule), so an
91
+ `@owlmeans/server-api` handler that lets one escape answers it: `UnknownRecordError` **404**,
92
+ `RecordExists` **409** (a unique-key violation, a taken id, and a `create` handed an id —
93
+ `id-present` — alike). Every other class of the family is a fault and answers 500. A development
94
+ body rebuilds into the same class on the client; a production body is the incident id alone and
95
+ arrives as `ApiStatusError` with that status (`@owlmeans/api`).
92
96
 
93
- | Written as | Means |
94
- |---|---|
95
- | `{ status: 'open' }` | equality |
96
- | `{ status: ['open', 'done'] }` | **any of these** — a bare array is never exact-array equality (that is `{ $eq: [...] }`) |
97
- | `{ archivedAt: null }` | the absence of a value |
98
- | `{ status: undefined }` | **skipped** — an untouched filter must never empty a list |
99
- | `{ 'profile.city': 'Kraków' }` | reach into a nested value or a jsonb column |
100
-
101
- Operators go in an object under the field: `$eq $ne $gt $gte $lt $lte $in $nin $exists $null
102
- $like $ilike $regex $startsWith $endsWith $between $contains $contained $overlaps`. Branches
103
- combine with `$and` / `$or` / `$not`, each taking criteria of the same shape.
104
-
105
- ```typescript
106
- await projects.list({
107
- entityId: 'abc',
108
- createdAt: { $gte: since },
109
- $or: [{ name: { $ilike: 'owl%' } }, { tags: { $overlaps: ['pinned'] } }]
110
- })
111
- ```
112
-
113
- Every backend answers the same object the same way — that is the point of the vocabulary. An
114
- operator a store cannot express raises `UnsupportedArgumentError` rather than being quietly
115
- dropped.
116
-
117
- `Sort<T>` is a bare field name (ascending) or `{ field, order: 'asc' | 'desc' }`, and `sort` takes
118
- a list of them. Where an **absent** value lands is the store's own rule, not the vocabulary's: the
119
- in-memory sorter puts it last ascending, Postgres emits a bare `ASC` and so leaves it last (the
120
- server's `NULLS LAST` default), and Mongo hands the sort document to the driver untouched, so BSON
121
- ordering puts null and missing first. Sort on a field the schema requires when the position of an
122
- absent value matters.
123
-
124
- ### Paging is a property of the backend
125
-
126
- `ListResult<T>` is `{ items, total, page?, size? }` — `total` always counts every match. Whether a
127
- missing `size` means "everything" depends on what the store can afford:
128
-
129
- | Backend | `list(where)` with no `size` |
130
- |---|---|
131
- | mongo, postgres | a page of `DEFAULT_PAGE_SIZE` (100) — an unbounded read of a growing table is an incident waiting to happen |
132
- | redis, static, client-resource, config, state | every match — answering the criteria already read the whole namespace, so an implied window would only hide records without saving work |
133
-
134
- `size: 0` means **no limit** on every backend — the explicit, greppable way to ask for a whole
135
- result set. `page` without `size` against an unpaged backend throws
136
- `UnsupportedArgumentError('page-without-size')`: there is no implied default to take a window of.
137
-
138
- ### The shared in-memory engine
139
-
140
- Every store without a query engine of its own — redis after its SCAN, the client and static
141
- stores, state — filters through the same helpers, so a criteria object written for an endpoint
142
- selects the same records when a screen applies it locally:
143
-
144
- | Helper | Answers |
145
- |---|---|
146
- | `matchCriteria(record, where)` | does this one record match |
147
- | `filterRecords(records, where)` | every match, in insertion order |
148
- | `sortRecords(records, sort)` | a sorted copy |
149
- | `firstMatch(records, where, { sort })` | the record `load(where)` / `get(where)` return |
150
- | `applyQuery(records, where, opts)` | the whole `ListResult` — filter, sort and page in one call |
151
-
152
- Reach for them when implementing a backend, and when narrowing a list already in hand rather than
153
- going back to the store.
154
-
155
- ### Optional capabilities
156
-
157
- A concrete resource interface composes the capabilities its backend actually has beside
158
- `Resource<T>`; a consumer types the **resource** once and gets exactly those methods.
159
-
160
- | Interface | Surface |
161
- |---|---|
162
- | `PubSubResource<T>` | `publish(value, channel?)` · `subscribe(handler, { channel?, once?, ttl? })` |
163
- | `WatchableResource<T>` | `watch(id, handler, { once?, ttl? })` — changes to ONE record |
164
- | `StreamResource<T>` | `stream(key, value)` · `consume(key, { group?, consumer?, block? })` |
165
- | `LockableResource<T>` | `lock`/`unlock` — field level encryption at rest |
166
- | `MigratableResource<Tx, Self>` | `migration(name, apply, stage?)` · `migrations()` |
167
-
168
- ## The migration framework
169
-
170
- Migrations are **automatic on app setup**: a backend runs them inside the resource's
171
- `init()` — registering one is all an app ever does. Every migration self-describes when it
172
- applies: the registry skips names the store has recorded, `baseline` covers structures
173
- created already at head, and bodies are written idempotent so an interrupted run can repeat.
174
-
175
- Adding migration support to a new database backend:
176
-
177
- 1. Extend the concrete resource interface with `MigratableResource<YourTx>` and design the
178
- `Tx` façade a migration receives.
179
- 2. Keep registrations in a **module-scope declaration keyed by alias** — the shape mongo and
180
- postgres both expose as `getDeclaration(alias)` / `resetDeclarations(alias?)`. A maker that
181
- runs more than once for the same alias (a custom maker, a test) then re-declares the same
182
- entries and loses nothing, where a registry held on the resource object would silently lose
183
- data transformations.
184
- 3. Implement `MigrationStore` over a durable ledger when the database can store one
185
- (`_owlmeans_migrations` in both mongo and postgres); a store-less backend may run
186
- migrations unconditionally if its bodies are self-checking.
187
- 4. In the resource's `init()`: probe structure → absent: `runMigrations(..., { baseline: true })`;
188
- present: run `Pre` → reconcile structure → run `Post`.
189
- 5. Make `run` atomic with the ledger write where the database allows it (postgres: same
190
- transaction). Where it doesn't (mongo: no multi-doc transactions on standalone), use
191
- claim-then-complete on a unique `(alias, name)` key and require idempotent bodies.
97
+ So `get` only what the REQUEST addressed. A missing row it did not name — a configuration record,
98
+ a session, an internal lookup — is not the caller's 404: `load` it and throw the fault or the
99
+ refusal that fits (an auth path throws `AuthorizationError`).
192
100
 
193
101
  ## Depends On
194
102
 
@@ -204,3 +112,14 @@ declares neither. Install both alongside it in any project that loads `createMig
204
112
 
205
113
  - [[mongo-resource]] · [[postgres-resource]] — the two `MigratableResource` implementations
206
114
  - [[redis-resource]] — a non-migratable backend (pub/sub capability instead)
115
+
116
+ ## Parts
117
+
118
+ Load a part on top of this core when its job is in play.
119
+
120
+ | Part | Load it when |
121
+ |---|---|
122
+ | [criteria](parts/criteria.md) | Writing a `where` (operators, `$or`, nested keys), a `sort`, or paging a `list` (`size`, `page`, `size: 0`) |
123
+ | [memory-engine](parts/memory-engine.md) | Implementing a store without a query engine, or narrowing a list already in hand (`recordQueryHelper`) |
124
+ | [capabilities](parts/capabilities.md) | Typing a resource with pub/sub, watch, stream, lock or migration capabilities |
125
+ | [migrations](parts/migrations.md) | Registering a migration or adding migration support to a database backend |
@@ -0,0 +1,23 @@
1
+ ---
2
+ name: capabilities
3
+ description: The optional capability interfaces a concrete resource composes beside Resource (pub/sub, watch, stream, lock, migrations).
4
+ metadata:
5
+ purposes: data
6
+ mentions: PubSubResource, WatchableResource, StreamResource, LockableResource, MigratableResource, SubscribeOptions
7
+ ---
8
+ <!-- AUTO-GENERATED — do not edit. Regenerate via sync-agent-meta. -->
9
+
10
+ # @owlmeans/resource — Optional capabilities
11
+
12
+ ## Optional capabilities
13
+
14
+ A concrete resource interface composes the capabilities its backend actually has beside
15
+ `Resource<T>`; a consumer types the **resource** once and gets exactly those methods.
16
+
17
+ | Interface | Surface |
18
+ |---|---|
19
+ | `PubSubResource<T>` | `publish(value, channel?)` · `subscribe(handler, { channel?, once?, ttl? })` |
20
+ | `WatchableResource<T>` | `watch(id, handler, { once?, ttl? })` — changes to ONE record |
21
+ | `StreamResource<T>` | `stream(key, value)` · `consume(key, { group?, consumer?, block? })` |
22
+ | `LockableResource<T>` | `lock`/`unlock` — field level encryption at rest |
23
+ | `MigratableResource<Tx, Self>` | `migration(name, apply, stage?)` · `migrations()` |
@@ -0,0 +1,60 @@
1
+ ---
2
+ name: criteria
3
+ description: The criteria language (equality, any-of arrays, operators, branches, nested keys), sort and where absent values land, and paging per backend.
4
+ metadata:
5
+ purposes: query, list
6
+ mentions: Criteria, FieldCriteria, FieldOperators, $or, $in, $ilike, $contains, $overlaps, Sort, ListOptions, ListResult, DEFAULT_PAGE_SIZE, page-without-size
7
+ ---
8
+ <!-- AUTO-GENERATED — do not edit. Regenerate via sync-agent-meta. -->
9
+
10
+ # @owlmeans/resource — Criteria, sort and paging
11
+
12
+ ## The criteria language
13
+
14
+ `Criteria<T>` is keyed by the record's own fields, so a typo is a compile error. A dotted key
15
+ reaches into a nested value (or a jsonb column) and stays open.
16
+
17
+ | Written as | Means |
18
+ |---|---|
19
+ | `{ status: 'open' }` | equality |
20
+ | `{ status: ['open', 'done'] }` | **any of these** — a bare array is never exact-array equality (that is `{ $eq: [...] }`) |
21
+ | `{ archivedAt: null }` | the absence of a value |
22
+ | `{ status: undefined }` | **skipped** — an untouched filter must never empty a list |
23
+ | `{ 'profile.city': 'Kraków' }` | reach into a nested value or a jsonb column |
24
+
25
+ Operators go in an object under the field: `$eq $ne $gt $gte $lt $lte $in $nin $exists $null
26
+ $like $ilike $regex $startsWith $endsWith $between $contains $contained $overlaps`. Branches
27
+ combine with `$and` / `$or` / `$not`, each taking criteria of the same shape.
28
+
29
+ ```typescript
30
+ await projects.list({
31
+ entityId: 'abc',
32
+ createdAt: { $gte: since },
33
+ $or: [{ name: { $ilike: 'owl%' } }, { tags: { $overlaps: ['pinned'] } }]
34
+ })
35
+ ```
36
+
37
+ Every backend answers the same object the same way — that is the point of the vocabulary. An
38
+ operator a store cannot express raises `UnsupportedArgumentError` rather than being quietly
39
+ dropped.
40
+
41
+ `Sort<T>` is a bare field name (ascending) or `{ field, order: 'asc' | 'desc' }`, and `sort` takes
42
+ a list of them. Where an **absent** value lands is the store's own rule, not the vocabulary's: the
43
+ in-memory sorter puts it last ascending, Postgres emits a bare `ASC` and so leaves it last (the
44
+ server's `NULLS LAST` default), and Mongo hands the sort document to the driver untouched, so BSON
45
+ ordering puts null and missing first. Sort on a field the schema requires when the position of an
46
+ absent value matters.
47
+
48
+ ## Paging is a property of the backend
49
+
50
+ `ListResult<T>` is `{ items, total, page?, size? }` — `total` always counts every match. Whether a
51
+ missing `size` means "everything" depends on what the store can afford:
52
+
53
+ | Backend | `list(where)` with no `size` |
54
+ |---|---|
55
+ | mongo, postgres | a page of `DEFAULT_PAGE_SIZE` (100) — an unbounded read of a growing table is an incident waiting to happen |
56
+ | redis, static, client-resource, config, state | every match — answering the criteria already read the whole namespace, so an implied window would only hide records without saving work |
57
+
58
+ `size: 0` means **no limit** on every backend — the explicit, greppable way to ask for a whole
59
+ result set. `page` without `size` against an unpaged backend throws
60
+ `UnsupportedArgumentError('page-without-size')`: there is no implied default to take a window of.
@@ -0,0 +1,27 @@
1
+ ---
2
+ name: memory-engine
3
+ description: recordQueryHelper, the shared in-memory engine every store without a query engine of its own filters, sorts and pages through.
4
+ metadata:
5
+ purposes: test
6
+ mentions: recordQueryHelper, matchCriteria, filterRecords, sortRecords, firstMatch, applyQuery
7
+ ---
8
+ <!-- AUTO-GENERATED — do not edit. Regenerate via sync-agent-meta. -->
9
+
10
+ # @owlmeans/resource — The shared in-memory engine
11
+
12
+ ## The shared in-memory engine
13
+
14
+ Every store without a query engine of its own — redis after its SCAN, the client and static stores,
15
+ state — filters through the same helper, `recordQueryHelper`, so a criteria object written for an
16
+ endpoint selects the same records when a screen applies it locally:
17
+
18
+ | Member | Answers |
19
+ |---|---|
20
+ | `recordQueryHelper.matchCriteria(record, where)` | does this one record match |
21
+ | `recordQueryHelper.filterRecords(records, where)` | every match, in insertion order |
22
+ | `recordQueryHelper.sortRecords(records, sort)` | a sorted copy |
23
+ | `recordQueryHelper.firstMatch(records, where, { sort })` | the record `load(where)` / `get(where)` return |
24
+ | `recordQueryHelper.applyQuery(records, where, opts)` | the whole `ListResult` — filter, sort and page in one call |
25
+
26
+ Reach for them when implementing a backend, and when narrowing a list already in hand rather than
27
+ going back to the store.
@@ -0,0 +1,35 @@
1
+ ---
2
+ name: migrations
3
+ description: The migration framework — automatic on init — and the five steps of adding migration support to a new database backend.
4
+ metadata:
5
+ purposes: migration
6
+ mentions: MigratableResource, MigrationStore, createMigrationRegistry, runMigrations, MigrationStage, mongoDeclarationHelper, pgDeclarationHelper, _owlmeans_migrations
7
+ ---
8
+ <!-- AUTO-GENERATED — do not edit. Regenerate via sync-agent-meta. -->
9
+
10
+ # @owlmeans/resource — Migrations
11
+
12
+ ## The migration framework
13
+
14
+ Migrations are **automatic on app setup**: a backend runs them inside the resource's
15
+ `init()` — registering one is all an app ever does. Every migration self-describes when it
16
+ applies: the registry skips names the store has recorded, `baseline` covers structures
17
+ created already at head, and bodies are written idempotent so an interrupted run can repeat.
18
+
19
+ Adding migration support to a new database backend:
20
+
21
+ 1. Extend the concrete resource interface with `MigratableResource<YourTx>` and design the
22
+ `Tx` façade a migration receives.
23
+ 2. Keep registrations in a **module-scope declaration keyed by alias** — the shape mongo and
24
+ postgres both expose as `mongoDeclarationHelper` / `pgDeclarationHelper` with
25
+ `.getDeclaration(alias)` / `.resetDeclarations(alias?)`. A maker that runs more than once for the
26
+ same alias (a custom maker, a test) then re-declares the same entries and loses nothing, where a
27
+ registry held on the resource object would silently lose data transformations.
28
+ 3. Implement `MigrationStore` over a durable ledger when the database can store one
29
+ (`_owlmeans_migrations` in both mongo and postgres); a store-less backend may run
30
+ migrations unconditionally if its bodies are self-checking.
31
+ 4. In the resource's `init()`: probe structure → absent: `runMigrations(..., { baseline: true })`;
32
+ present: run `Pre` → reconcile structure → run `Post`.
33
+ 5. Make `run` atomic with the ledger write where the database allows it (postgres: same
34
+ transaction). Where it doesn't (mongo: no multi-doc transactions on standalone), use
35
+ claim-then-complete on a unique `(alias, name)` key and require idempotent bodies.
@@ -142,10 +142,15 @@ When you do queue ([[queue]], driver [[redis-queue]]):
142
142
  successors: children complete before the parent runs and it reads their results through
143
143
  `children()`. Give the children of a cross-queue flow distinct ids.
144
144
 
145
- **There is no scheduler in the framework.** `JobOptions.delay` defers one job once; anything
146
- recurring — a nightly digest, an hourly reconciliation — is triggered from outside the process by
147
- a platform cron (a Kubernetes `CronJob` in a [[kluster]] deployment) that calls a normal entrypoint
148
- or enqueues a job. Do not simulate cron with a self-re-enqueueing job.
145
+ **Recurring work is a schedule.** `JobOptions.delay` defers one job once; anything recurring — a
146
+ nightly digest, an hourly reconciliation — is `declareSchedule(cfg, { id, queue, name, every |
147
+ pattern })` in the shared package plus a processor registered for that job name
148
+ ([[scheduled-jobs]]). Every worker that listens to the queue keeps the broker's schedulers in line
149
+ with the declarations, so adding, changing and deleting a schedule is a code change. A scheduled
150
+ run is a processor job, never a guarded entrypoint call. Reach for a platform cron (a Kubernetes
151
+ `CronJob` in a [[kluster]] deployment) calling an entrypoint only when no worker may be running:
152
+ the broker produces a schedule's next run only while a process consumes its queue. Never simulate
153
+ cron with a self-re-enqueueing job.
149
154
 
150
155
  ## Model-driven work
151
156
 
@@ -188,7 +193,7 @@ the matching `@owlmeans/*-resource` package, `state` and `config` the packages o
188
193
  | Settings / feature flags per organization entity | postgres | Few rows, read constantly, always by `entityId` — cache in Redis only after measuring, and only if a stale read is harmless. |
189
194
  | Search over the product's own records | postgres | Start with indexed columns and `jsonb` containment; move to a search engine when a measured query, not a guess, says so. |
190
195
  | Expensive aggregate on a dashboard | postgres, then redis | Compute it in SQL first. Cache in Redis with a TTL only once the measured query is genuinely slow — a miss must stay invisible. |
191
- | Analytics rollups | postgres + queue | The rollup is a scheduled batch write into its own table; the trigger is a platform cron, the work is a job because it survives restarts. |
196
+ | Analytics rollups | postgres + queue schedule | The rollup is a batch write into its own table; a declared schedule produces the run and a processor does it, surviving restarts. |
192
197
  | Leaderboard | postgres, redis if hot | A ranked query with an index is enough for most products; move the live top-N into a Redis counter set when it is read far more often than written. |
193
198
  | Invoice numbering | postgres | A gapless sequence is a transaction and a unique constraint, not a Redis counter — a lost increment is an accounting problem. |
194
199
  | Records the process was started with (plugins, seeded routes) | config | Already in `cfg`; reading them as a resource gives criteria and sorting without a second store, and every write is refused by design. |
@@ -237,10 +242,11 @@ the matching `@owlmeans/*-resource` package, `state` and `config` the packages o
237
242
  | Bulk email | queue | Thousands of provider calls, each retried independently; one bad address must not fail the batch. |
238
243
  | Transactional email (one recipient, one event) | inline | A single provider call inside the request; queue it only if the send is on a user's critical path and the provider is slow. |
239
244
  | Payment capture | queue with idempotent job ids | Retried against a third party, must survive a restart, must never double-charge — derive the job id from the payment. |
240
- | Third-party sync / reconciliation | queue, triggered by platform cron | Recurring, long, retried; the framework has no scheduler, so a `CronJob` enqueues it. |
245
+ | Third-party sync / reconciliation | queue schedule | Recurring, long, retried; a pattern schedule on a low-concurrency queue, and the processor re-reads the third party as the truth so a re-run is harmless. |
241
246
  | Webhook fan-out | queue, one job per subscriber | Per-endpoint retries and backoff; a slow subscriber must not delay the others. |
242
- | Scheduled digest | queue, triggered by platform cron | Same shape as any recurring batch — cron enqueues, the worker sends. |
243
- | Scheduled reminders | postgres row + cron sweep, or `JobOptions.delay` | Use `delay` for a one-shot minutes-away nudge; anything cancellable or far in the future is a row a periodic sweep picks up. |
247
+ | Scheduled digest | queue schedule | Same shape as any recurring batch — the schedule produces the run, the worker sends. |
248
+ | Scheduled reminders | postgres row + scheduled sweep, or `JobOptions.delay` | Use `delay` for a one-shot minutes-away nudge; anything cancellable or far in the future is a row a scheduled sweep picks up. |
249
+ | Recurring job where no worker process runs | platform `CronJob` calling an entrypoint | A schedule needs a consumer; a deployment with none triggers from outside and goes through the entrypoint's guards. |
244
250
  | Inbound webhook handling | inline ack, queue the work | Answer 2xx immediately, then process — a third party's retry policy is not a design input for your handler. |
245
251
  | Cache warmup after a deploy | queue, or nothing | Usually not worth it: let the first requests populate the cache unless a measured cold-start hurts. |
246
252
 
@@ -258,7 +264,8 @@ the matching `@owlmeans/*-resource` package, `state` and `config` the packages o
258
264
 
259
265
  - [[resource]] — the contract every option implements, and the criteria language they share
260
266
  - [[postgres-resource]], [[mongo-resource]], [[redis-resource]], [[static-resource]],
261
- [[state]], [[client-resource]], [[web-db]], [[config]], [[storage-resource]] — the backends
267
+ [[state]], [[client-resource]], [[web-db]], [[owlmeans-config]], [[storage-resource]] — the backends
262
268
  - [[queue]], [[redis-queue]] — job queues and the worker process
269
+ - [[scheduled-jobs]] — recurring work on a queue schedule
263
270
  - [[llm]], [[agent]] — model-driven work
264
271
  - [[reuse-code]] — find the `@owlmeans/*` package before designing anything new
package/build/consts.d.ts CHANGED
@@ -1,5 +1,3 @@
1
- import type { JSONSchemaType } from 'ajv';
2
- import type { ListResult, ResourceRecord } from './types.js';
3
1
  /**
4
2
  * When a migration runs relative to the structure reconciliation a db implementation
5
3
  * performs at resource initialization.
@@ -16,5 +14,4 @@ export declare enum MigrationStage {
16
14
  Pre = "pre",
17
15
  Post = "post"
18
16
  }
19
- export declare const createListSchema: <T extends ResourceRecord>(schema: JSONSchemaType<T>) => JSONSchemaType<ListResult<T>>;
20
17
  //# sourceMappingURL=consts.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"consts.d.ts","sourceRoot":"","sources":["../src/consts.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,KAAK,CAAA;AACzC,OAAO,KAAK,EAAE,UAAU,EAAE,cAAc,EAAE,MAAM,YAAY,CAAA;AAE5D;;;;;;;;;;;GAWG;AACH,oBAAY,cAAc;IACxB,GAAG,QAAQ;IACX,IAAI,SAAS;CACd;AAED,eAAO,MAAM,gBAAgB,GAAI,CAAC,SAAS,cAAc,UAAU,cAAc,CAAC,CAAC,CAAC,KAAG,cAAc,CAAC,UAAU,CAAC,CAAC,CAAC,CAsBjH,CAAA"}
1
+ {"version":3,"file":"consts.d.ts","sourceRoot":"","sources":["../src/consts.ts"],"names":[],"mappings":"AACA;;;;;;;;;;;GAWG;AACH,oBAAY,cAAc;IACxB,GAAG,QAAQ;IACX,IAAI,SAAS;CACd"}
package/build/consts.js CHANGED
@@ -15,27 +15,4 @@ export var MigrationStage;
15
15
  MigrationStage["Pre"] = "pre";
16
16
  MigrationStage["Post"] = "post";
17
17
  })(MigrationStage || (MigrationStage = {}));
18
- export const createListSchema = (schema) => ({
19
- type: 'object',
20
- properties: {
21
- items: {
22
- type: 'array',
23
- items: {
24
- ...schema,
25
- type: 'object',
26
- properties: {
27
- id: { type: 'string', nullable: true },
28
- ...schema.properties
29
- },
30
- ...(schema.required ? { required: [...schema.required] } : undefined),
31
- additionalProperties: false,
32
- }
33
- },
34
- total: { type: 'number' },
35
- page: { type: 'number', nullable: true },
36
- size: { type: 'number', nullable: true }
37
- },
38
- required: ['items', 'total'],
39
- additionalProperties: false,
40
- });
41
18
  //# sourceMappingURL=consts.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"consts.js","sourceRoot":"","sources":["../src/consts.ts"],"names":[],"mappings":"AAGA;;;;;;;;;;;GAWG;AACH,MAAM,CAAN,IAAY,cAGX;AAHD,WAAY,cAAc;IACxB,6BAAW,CAAA;IACX,+BAAa,CAAA;AACf,CAAC,EAHW,cAAc,KAAd,cAAc,QAGzB;AAED,MAAM,CAAC,MAAM,gBAAgB,GAAG,CAA2B,MAAyB,EAAiC,EAAE,CAAC,CAAC;IACvH,IAAI,EAAE,QAAQ;IACd,UAAU,EAAE;QACV,KAAK,EAAE;YACL,IAAI,EAAE,OAAO;YACb,KAAK,EAAE;gBACL,GAAG,MAAM;gBACT,IAAI,EAAE,QAAQ;gBACd,UAAU,EAAE;oBACV,EAAE,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,QAAQ,EAAE,IAAI,EAAE;oBACtC,GAAG,MAAM,CAAC,UAAU;iBACrB;gBACD,GAAG,CAAC,MAAM,CAAC,QAAQ,CAAC,CAAC,CAAC,EAAE,QAAQ,EAAE,CAAC,GAAG,MAAM,CAAC,QAAQ,CAAC,EAAE,CAAC,CAAC,CAAC,SAAS,CAAC;gBACrE,oBAAoB,EAAE,KAAK;aAC5B;SACF;QACD,KAAK,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE;QACzB,IAAI,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,QAAQ,EAAE,IAAI,EAAE;QACxC,IAAI,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,QAAQ,EAAE,IAAI,EAAE;KACzC;IACD,QAAQ,EAAE,CAAC,OAAO,EAAE,OAAO,CAAC;IAC5B,oBAAoB,EAAE,KAAK;CAC5B,CAAC,CAAA"}
1
+ {"version":3,"file":"consts.js","sourceRoot":"","sources":["../src/consts.ts"],"names":[],"mappings":"AACA;;;;;;;;;;;GAWG;AACH,MAAM,CAAN,IAAY,cAGX;AAHD,WAAY,cAAc;IACxB,6BAAW,CAAA;IACX,+BAAa,CAAA;AACf,CAAC,EAHW,cAAc,KAAd,cAAc,QAGzB"}
package/build/errors.d.ts CHANGED
@@ -1,20 +1,33 @@
1
1
  import { ResilientError } from '@owlmeans/error';
2
+ /**
3
+ * The storage refusal family. A class that answers the caller's request declares the HTTP status
4
+ * an `@owlmeans/server-api` boundary answers it with (`static httpStatus`, inherited through the
5
+ * constructor chain): an absent record 404, a taken id or unique key 409. A fault — a misshaped
6
+ * record, an unsupported argument, a failed migration — declares nothing and answers 500.
7
+ */
2
8
  export declare class ResourceError extends ResilientError {
3
9
  static typeName: string;
4
10
  constructor(message?: string);
5
11
  }
12
+ /** The addressed record does not exist (`get`, `update`, `take` of an absent id or criteria). */
6
13
  export declare class UnknownRecordError extends ResourceError {
7
14
  static typeName: string;
15
+ /** The addressed record is absent: answered 404. */
16
+ static httpStatus: number;
8
17
  static readonly idSeparator: string;
9
18
  constructor(id: string);
19
+ /** Everything after the first separator — an id or a criteria description may contain one. */
10
20
  get id(): string;
11
21
  }
12
22
  export declare class MisshapedRecord extends ResourceError {
13
23
  static typeName: string;
14
24
  constructor(msg: string);
15
25
  }
26
+ /** A record under that id or unique key is already stored (`create`, a unique-index violation). */
16
27
  export declare class RecordExists extends ResourceError {
17
28
  static typeName: string;
29
+ /** The id or unique key is taken: answered 409. */
30
+ static httpStatus: number;
18
31
  constructor(msg: string);
19
32
  }
20
33
  export declare class RecordUpdateFailed extends ResourceError {
@@ -1 +1 @@
1
- {"version":3,"file":"errors.d.ts","sourceRoot":"","sources":["../src/errors.ts"],"names":[],"mappings":"AACA,OAAO,EAAG,cAAc,EAAE,MAAM,iBAAiB,CAAA;AAEjD,qBAAa,aAAc,SAAQ,cAAc;IAC/C,OAAuB,QAAQ,SAAkB;IAEjD,YAAY,OAAO,GAAE,MAAgB,EAEpC;CACF;AAED,qBAAa,kBAAmB,SAAQ,aAAa;IACnD,OAAuB,QAAQ,SAAgD;IAE/E,gBAAuB,WAAW,EAAE,MAAM,CAAM;IAEhD,YAAY,EAAE,EAAE,MAAM,EAGrB;IAED,IAAI,EAAE,IAAI,MAAM,CAEf;CACF;AAED,qBAAa,eAAgB,SAAQ,aAAa;IAChD,OAAuB,QAAQ,SAA6C;IAE5E,YAAY,GAAG,EAAE,MAAM,EAGtB;CACF;AAED,qBAAa,YAAa,SAAQ,aAAa;IAC7C,OAAuB,QAAQ,SAA0C;IAEzE,YAAY,GAAG,EAAE,MAAM,EAGtB;CACF;AAED,qBAAa,kBAAmB,SAAQ,aAAa;IACnD,OAAuB,QAAQ,SAAgD;IAE/E,YAAY,GAAG,EAAE,MAAM,EAGtB;CACF;AAED,qBAAa,wBAAyB,SAAQ,aAAa;IACzD,OAAuB,QAAQ,SAAsD;IAErF,YAAY,QAAQ,EAAE,MAAM,EAG3B;CACF;AAED,qBAAa,sBAAuB,SAAQ,aAAa;IACvD,OAAuB,QAAQ,SAAoD;IAEnF,YAAY,MAAM,EAAE,MAAM,EAGzB;CACF;AAED;;;;GAIG;AACH,qBAAa,cAAe,SAAQ,aAAa;IAC/C,OAAuB,QAAQ,SAA4C;IAE3E,YAAY,GAAG,EAAE,MAAM,EAGtB;CACF;AAED;;;;GAIG;AACH,qBAAa,iBAAkB,SAAQ,aAAa;IAClD,OAAuB,QAAQ,SAA+C;IAE9E,YAAY,GAAG,EAAE,MAAM,EAGtB;CACF"}
1
+ {"version":3,"file":"errors.d.ts","sourceRoot":"","sources":["../src/errors.ts"],"names":[],"mappings":"AACA,OAAO,EAAG,cAAc,EAAE,MAAM,iBAAiB,CAAA;AAEjD;;;;;GAKG;AACH,qBAAa,aAAc,SAAQ,cAAc;IAC/C,OAAuB,QAAQ,SAAkB;IAEjD,YAAY,OAAO,GAAE,MAAgB,EAEpC;CACF;AAED,iGAAiG;AACjG,qBAAa,kBAAmB,SAAQ,aAAa;IACnD,OAAuB,QAAQ,SAAgD;IAC/E,oDAAoD;IACpD,OAAc,UAAU,SAAM;IAE9B,gBAAuB,WAAW,EAAE,MAAM,CAAM;IAEhD,YAAY,EAAE,EAAE,MAAM,EAGrB;IAED,8FAA8F;IAC9F,IAAI,EAAE,IAAI,MAAM,CAIf;CACF;AAED,qBAAa,eAAgB,SAAQ,aAAa;IAChD,OAAuB,QAAQ,SAA6C;IAE5E,YAAY,GAAG,EAAE,MAAM,EAGtB;CACF;AAED,mGAAmG;AACnG,qBAAa,YAAa,SAAQ,aAAa;IAC7C,OAAuB,QAAQ,SAA0C;IACzE,mDAAmD;IACnD,OAAc,UAAU,SAAM;IAE9B,YAAY,GAAG,EAAE,MAAM,EAGtB;CACF;AAED,qBAAa,kBAAmB,SAAQ,aAAa;IACnD,OAAuB,QAAQ,SAAgD;IAE/E,YAAY,GAAG,EAAE,MAAM,EAGtB;CACF;AAED,qBAAa,wBAAyB,SAAQ,aAAa;IACzD,OAAuB,QAAQ,SAAsD;IAErF,YAAY,QAAQ,EAAE,MAAM,EAG3B;CACF;AAED,qBAAa,sBAAuB,SAAQ,aAAa;IACvD,OAAuB,QAAQ,SAAoD;IAEnF,YAAY,MAAM,EAAE,MAAM,EAGzB;CACF;AAED;;;;GAIG;AACH,qBAAa,cAAe,SAAQ,aAAa;IAC/C,OAAuB,QAAQ,SAA4C;IAE3E,YAAY,GAAG,EAAE,MAAM,EAGtB;CACF;AAED;;;;GAIG;AACH,qBAAa,iBAAkB,SAAQ,aAAa;IAClD,OAAuB,QAAQ,SAA+C;IAE9E,YAAY,GAAG,EAAE,MAAM,EAGtB;CACF"}
package/build/errors.js CHANGED
@@ -1,19 +1,30 @@
1
1
  import { ResilientError } from '@owlmeans/error';
2
+ /**
3
+ * The storage refusal family. A class that answers the caller's request declares the HTTP status
4
+ * an `@owlmeans/server-api` boundary answers it with (`static httpStatus`, inherited through the
5
+ * constructor chain): an absent record 404, a taken id or unique key 409. A fault — a misshaped
6
+ * record, an unsupported argument, a failed migration — declares nothing and answers 500.
7
+ */
2
8
  export class ResourceError extends ResilientError {
3
9
  static typeName = 'ResourceError';
4
10
  constructor(message = 'error') {
5
11
  super(ResourceError.typeName, `resource:${message}`);
6
12
  }
7
13
  }
14
+ /** The addressed record does not exist (`get`, `update`, `take` of an absent id or criteria). */
8
15
  export class UnknownRecordError extends ResourceError {
9
16
  static typeName = `${ResourceError.typeName}UnknownRecordError`;
17
+ /** The addressed record is absent: answered 404. */
18
+ static httpStatus = 404;
10
19
  static idSeparator = '/';
11
20
  constructor(id) {
12
21
  super(`unknown-record${UnknownRecordError.idSeparator}${id}`);
13
22
  this.type = UnknownRecordError.typeName;
14
23
  }
24
+ /** Everything after the first separator — an id or a criteria description may contain one. */
15
25
  get id() {
16
- return this.message.split(UnknownRecordError.idSeparator)[1];
26
+ const at = this.message.indexOf(UnknownRecordError.idSeparator);
27
+ return at < 0 ? '' : this.message.slice(at + UnknownRecordError.idSeparator.length);
17
28
  }
18
29
  }
19
30
  export class MisshapedRecord extends ResourceError {
@@ -23,8 +34,11 @@ export class MisshapedRecord extends ResourceError {
23
34
  this.type = MisshapedRecord.typeName;
24
35
  }
25
36
  }
37
+ /** A record under that id or unique key is already stored (`create`, a unique-index violation). */
26
38
  export class RecordExists extends ResourceError {
27
39
  static typeName = `${ResourceError.typeName}RecordExists`;
40
+ /** The id or unique key is taken: answered 409. */
41
+ static httpStatus = 409;
28
42
  constructor(msg) {
29
43
  super(`record-exists:${msg}`);
30
44
  this.type = RecordExists.typeName;
@@ -1 +1 @@
1
- {"version":3,"file":"errors.js","sourceRoot":"","sources":["../src/errors.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"errors.js","sourceRoot":"","sources":["../src/errors.ts"],"names":[],"mappings":"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"}
package/build/index.d.ts CHANGED
@@ -1,8 +1,10 @@
1
1
  export * from './errors.js';
2
2
  export * from './consts.js';
3
+ export * from './utils.js';
3
4
  export * from './service.js';
4
5
  export * from './helper.js';
5
6
  export * from './utils/query.js';
7
+ export type * from './utils/query/types.js';
6
8
  export * from './migration.js';
7
9
  export type * from './types.js';
8
10
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AACA,cAAc,aAAa,CAAA;AAC3B,cAAc,aAAa,CAAA;AAC3B,cAAc,cAAc,CAAA;AAC5B,cAAc,aAAa,CAAA;AAC3B,cAAc,kBAAkB,CAAA;AAChC,cAAc,gBAAgB,CAAA;AAC9B,mBAAmB,YAAY,CAAA"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AACA,cAAc,aAAa,CAAA;AAC3B,cAAc,aAAa,CAAA;AAC3B,cAAc,YAAY,CAAA;AAC1B,cAAc,cAAc,CAAA;AAC5B,cAAc,aAAa,CAAA;AAC3B,cAAc,kBAAkB,CAAA;AAChC,mBAAmB,wBAAwB,CAAA;AAC3C,cAAc,gBAAgB,CAAA;AAC9B,mBAAmB,YAAY,CAAA"}
package/build/index.js CHANGED
@@ -1,5 +1,6 @@
1
1
  export * from './errors.js';
2
2
  export * from './consts.js';
3
+ export * from './utils.js';
3
4
  export * from './service.js';
4
5
  export * from './helper.js';
5
6
  export * from './utils/query.js';
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AACA,cAAc,aAAa,CAAA;AAC3B,cAAc,aAAa,CAAA;AAC3B,cAAc,cAAc,CAAA;AAC5B,cAAc,aAAa,CAAA;AAC3B,cAAc,kBAAkB,CAAA;AAChC,cAAc,gBAAgB,CAAA"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AACA,cAAc,aAAa,CAAA;AAC3B,cAAc,aAAa,CAAA;AAC3B,cAAc,YAAY,CAAA;AAC1B,cAAc,cAAc,CAAA;AAC5B,cAAc,aAAa,CAAA;AAC3B,cAAc,kBAAkB,CAAA;AAEhC,cAAc,gBAAgB,CAAA"}
Binary file
@@ -1 +1 @@
1
- {"version":3,"file":"migration.js","sourceRoot":"","sources":["../src/migration.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"migration.js","sourceRoot":"","sources":["../src/migration.ts"],"names":[],"mappings":"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"}
package/build/types.d.ts CHANGED
@@ -110,7 +110,9 @@ export interface Resource<T extends ResourceRecord> extends BasicResource {
110
110
  /** Bulk delete. Refuses an empty criteria object rather than emptying the resource. */
111
111
  purge(where: Criteria<T>): Promise<number>;
112
112
  }
113
- export type Unsubscribe = () => Promise<void>;
113
+ export interface Unsubscribe {
114
+ (): Promise<void>;
115
+ }
114
116
  export interface SubscribeOptions {
115
117
  channel?: string;
116
118
  once?: boolean;