@objectstack/plugin-webhooks 16.1.0 → 17.0.0-rc.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 (41) hide show
  1. package/CHANGELOG.md +626 -0
  2. package/dist/{chunk-RBCYKJVL.js → chunk-6EPMRZ7I.js} +28 -2
  3. package/dist/chunk-6EPMRZ7I.js.map +1 -0
  4. package/dist/{chunk-PTMJ5BLL.cjs → chunk-QUTQSOQC.cjs} +28 -2
  5. package/dist/chunk-QUTQSOQC.cjs.map +1 -0
  6. package/dist/index.cjs +250 -33
  7. package/dist/index.cjs.map +1 -1
  8. package/dist/index.d.cts +25 -0
  9. package/dist/index.d.ts +25 -0
  10. package/dist/index.js +231 -14
  11. package/dist/index.js.map +1 -1
  12. package/dist/schema.cjs +2 -2
  13. package/dist/schema.d.cts +515 -304
  14. package/dist/schema.d.ts +515 -304
  15. package/dist/schema.js +1 -1
  16. package/dist/translations-CBQRUIS5.cjs +383 -0
  17. package/dist/translations-CBQRUIS5.cjs.map +1 -0
  18. package/dist/translations-Y3CXWOTM.js +383 -0
  19. package/dist/translations-Y3CXWOTM.js.map +1 -0
  20. package/package.json +11 -5
  21. package/.turbo/turbo-build.log +0 -36
  22. package/dist/chunk-PTMJ5BLL.cjs.map +0 -1
  23. package/dist/chunk-RBCYKJVL.js.map +0 -1
  24. package/dist/translations-EPJYANXJ.js +0 -727
  25. package/dist/translations-EPJYANXJ.js.map +0 -1
  26. package/dist/translations-L2JAQDJB.cjs +0 -727
  27. package/dist/translations-L2JAQDJB.cjs.map +0 -1
  28. package/scripts/i18n-extract.config.ts +0 -32
  29. package/src/auto-enqueuer.test.ts +0 -431
  30. package/src/auto-enqueuer.ts +0 -383
  31. package/src/index.ts +0 -29
  32. package/src/schema.ts +0 -21
  33. package/src/sys-webhook.object.ts +0 -193
  34. package/src/translations/en.objects.generated.ts +0 -187
  35. package/src/translations/es-ES.objects.generated.ts +0 -187
  36. package/src/translations/index.ts +0 -23
  37. package/src/translations/ja-JP.objects.generated.ts +0 -187
  38. package/src/translations/zh-CN.objects.generated.ts +0 -187
  39. package/src/webhook-outbox-plugin.ts +0 -259
  40. package/tsconfig.json +0 -10
  41. package/tsup.config.ts +0 -14
package/CHANGELOG.md CHANGED
@@ -1,5 +1,631 @@
1
1
  # @objectstack/plugin-webhooks
2
2
 
3
+ ## 17.0.0-rc.1
4
+
5
+ ### Minor Changes
6
+
7
+ - f5a4ef0: refactor!: ADR-0112 batch 2 — sweep the lowercase error-code emitters (#4003)
8
+
9
+ Continues #3841 per ADR-0112. Batch 1 (#3988) settled the vocabulary and closed
10
+ the set; this batch moves the emitters that still spoke lowercase `snake_case`
11
+ onto it.
12
+
13
+ **Wire-visible change.** Error codes on these surfaces change spelling. Generic
14
+ conditions collapse onto the standard catalog rather than keeping a synonym:
15
+ `unauthorized`/`unauthenticated` → `UNAUTHENTICATED`, `forbidden` →
16
+ `PERMISSION_DENIED`, `not_found` → `RESOURCE_NOT_FOUND`, `internal` →
17
+ `INTERNAL_ERROR`, `unavailable` → `SERVICE_UNAVAILABLE`, `not_supported` →
18
+ `NOT_IMPLEMENTED`, `bad_request` → `INVALID_REQUEST`. Domain conditions get codes
19
+ registered in `ERROR_CODE_LEDGER` (`MARKETPLACE_STORAGE_FAILED`,
20
+ `PLUGIN_MANIFEST_INVALID`, `ITEM_LOCKED`, `DELIVERY_NOT_ELIGIBLE`, …). Swept:
21
+ `cloud-connection`, `plugin-auth`, `hono`, `metadata-protocol`, `rest`,
22
+ `service-messaging`, `service-automation`, `trigger-api`.
23
+
24
+ Branch on `error.code` values rather than pattern-matching their case: the
25
+ console's fix for the same rename (objectui#2977) reads codes case-insensitively
26
+ for exactly this reason, and that is the pattern to copy in your own consumers if
27
+ you support servers on both sides of the change.
28
+
29
+ **Four routes stop putting a code in the message slot.** The webhook redeliver
30
+ route, the API-trigger webhook, and two `rest` routes answered
31
+ `{ success: false, error: '<code>', message }` — the code occupying `error`, the
32
+ declared object envelope nowhere. They now emit `error: { code, message }`, and
33
+ three API-trigger branches gained a message they never had. Clients reading
34
+ `body.error` as a string on those routes must read `body.error.code`.
35
+
36
+ **`ConnectorErrorCategory` / `ConnectorRetryStrategy`** (ADR-0112 D9a):
37
+ `@objectstack/spec` exported two mutually incompatible `ErrorCategory` types and
38
+ two `RetryStrategy` types. The connector-side pair is renamed; importers of the
39
+ `integration` subpath update the name. Side effect: the api-side `ErrorCategory`
40
+ and `RetryStrategy` now appear in the generated API reference at all — the name
41
+ collision had been silently dropping them.
42
+
43
+ **`OAUTH_REGISTER_FAILED` replaces an unbounded code source.** The OAuth client
44
+ registration route put better-auth's arbitrary `body.error` string straight into
45
+ `error.code`. The code is now ours and the upstream discriminator moved to
46
+ `details.upstreamError`.
47
+
48
+ **Not swept, deliberately.** `sys_metadata_audit.code` keeps its lowercase values
49
+ (ADR-0112 D6b): it is persisted audit history, and the same column holds
50
+ non-error outcomes (`ok`, `lock_override`). Diagnostics records that ship inside a
51
+ 200 keep theirs (D6c), as do field-level codes (D6, #3977) and the CLI's
52
+ `--json` output contract.
53
+
54
+ A `check:error-code-casing` CI guard now fails on a new lowercase literal in a
55
+ code position, since the ledger's casing rule can only police codes that someone
56
+ registers.
57
+
58
+ ### Patch Changes
59
+
60
+ - bb1ce2e: fix(plugin-auth,plugin-webhooks): retire a dead degrade branch and an implicit transitive dependency (ADR-0116 follow-ups, #4187)
61
+
62
+ Two concrete findings from the ADR-0116 consumer-side audit, plus the
63
+ authoring rule that would have prevented both.
64
+
65
+ **`plugin-auth` claimed a fallback it did not have.** `init()` ran
66
+ `const dataEngine = ctx.getService('data'); if (!dataEngine) { warn('No data
67
+ engine service found - auth will use in-memory storage') }`. That branch could
68
+ never execute: `getService` **throws** for an unregistered service rather than
69
+ returning `undefined`, and this plugin declares a hard dependency on ObjectQL
70
+ (which registers `data` unconditionally), so a kernel without the engine fails
71
+ even earlier with `Dependency … not found`. The branch is removed and the real
72
+ contract is declared — `requiresServices: ['data', 'manifest']` — which also
73
+ replaces a trailing `// manifest service required` comment with the
74
+ machine-checked form of the same claim. `AuthManager` keeps its own optional
75
+ `dataEngine` guards: it is usable outside the plugin.
76
+
77
+ **`plugin-webhook-outbox` was protected only transitively.** It resolves
78
+ `manifest` in `init()` with no fallback while depending on
79
+ `com.objectstack.service.messaging`, which in turn depends on ObjectQL, the
80
+ actual provider. That works today and would have broken silently the day
81
+ messaging stopped depending on the engine — surfacing as a crash inside an
82
+ unrelated plugin's init. It now declares `requiresServices: ['manifest']`
83
+ directly.
84
+
85
+ Neither change alters ordering or boot outcomes on any current composition:
86
+ both plugins were already ordered correctly. What changes is what a broken
87
+ composition _says_, and that the guarantees are now checked rather than
88
+ inherited.
89
+
90
+ Docs: `content/docs/plugins/anatomy.mdx` gains the three ADR-0116 fields and
91
+ the decision rule for resolving a service inside `init()` (hard dependency vs
92
+ `optionalDependencies` + `requiresServices`), including the two traps behind
93
+ these fixes — don't rely on a transitive provider, and don't write an
94
+ `if (!svc)` fallback after a bare `getService`. The api-registry example
95
+ declares the contract on all seven of its plugins instead of relying on
96
+ `kernel.use()` order.
97
+
98
+ - 2e836de: chore(packaging): CHANGELOG.md ships in every npm tarball (#4261)
99
+
100
+ The AGENTS.md post-task checklist requires breaking changesets to carry their
101
+ FROM → TO migration because "this text ships to consumers as `CHANGELOG.md`
102
+ inside the npm package and is what an upgrading agent greps after the tombstone
103
+ error." That delivery path was severed for 68 of the 69 publishable packages:
104
+ npm packs `package.json` / `README*` / `LICENSE*` unconditionally but — unlike
105
+ older npm versions — not `CHANGELOG.md`, and the canonical
106
+ `"files": ["dist", "README.md"]` whitelist never named it. Measured on npm
107
+ 10.9.7: `npm pack --dry-run` on `@objectstack/types` shipped 3 files while its
108
+ 70KB `CHANGELOG.md` stayed behind. Only `@objectstack/spec` listed it
109
+ explicitly.
110
+
111
+ The tombstone-error scenario is precisely the one where the repo is out of
112
+ reach — the upgrading agent has `node_modules` and nothing else — so the
113
+ migration text has to ride in the tarball. Every publishable package now
114
+ declares `CHANGELOG.md` in `files`, and the canonical whitelist is
115
+ `["dist", "README.md", "CHANGELOG.md"]`.
116
+
117
+ The other half is the gate: `check:published-files` gains a fifth invariant,
118
+ COMPLETE — a whitelist that fails to cover `CHANGELOG.md` fails the
119
+ always-required lint job, so the next package cannot silently sever the path
120
+ again. `@objectstack/spec`'s per-package EXTRA_ENTRIES exemption dissolves
121
+ into the canonical set.
122
+
123
+ Consumer-visible change: one more file per install (the package's changelog,
124
+ e.g. 70.8KB for `@objectstack/types`), and `grep -r "removed key"
125
+ node_modules/@objectstack/*/CHANGELOG.md` now finds the migration it was
126
+ promised.
127
+
128
+ - a225ef5: fix(runtime,webhooks): the path object wins on /data/:object/query, and the webhook envelope owns its keys (#3946)
129
+
130
+ Follow-up sweep for the shape behind #3897 and #3933 — a trusted, server-derived
131
+ value written into an object literal with a caller-controlled bag spread OVER
132
+ it. Both of those were in the same block of REST code, so the pattern was swept
133
+ across all 1313 non-test TypeScript files in `packages/`. Nine candidate sites;
134
+ one real, one worth hardening, seven verified clean (recorded in #3946 so the
135
+ next sweep does not re-litigate them).
136
+
137
+ **`POST /data/:object/query` (runtime dispatcher).** The `/data` domain built
138
+ `{ object: objectName, ...body }`, so `{"object":"other", …}` in the body moved
139
+ the read to a different object than the URL named.
140
+
141
+ This is NOT an authorization bypass, and the tests pin why: `callData` gates
142
+ API exposure on `params.object`, so the gate followed the body and agreed with
143
+ the read — an object hidden by `apiEnabled: false` was refused either way. What
144
+ broke is that the URL stopped describing the operation (audit trails, logs, and
145
+ anything keyed on the request path saw object A while object B was read), and
146
+ that one endpoint spoke a second dialect of the contract the REST side had just
147
+ standardised on: the path object wins. The other handlers in that file never had
148
+ the problem — they nest caller data (`data: body`, `query: normalized`) instead
149
+ of splatting it, and the GET-by-id branch already allowlists its query params
150
+ against exactly this pollution.
151
+
152
+ **Webhook delivery envelope.** `auto-enqueuer` built
153
+ `{ object, recordId, action, timestamp, ...payload }`, letting an event payload
154
+ rewrite the envelope a subscriber receives. Behaviour-neutral for the engine's
155
+ own publishers — `data.record.*` payloads are `{ recordId, after, changes }`
156
+ with record fields nested under `after`, so none of those four keys collide
157
+ today — but the shape was wrong, and the `payload.id` fallback right above it
158
+ suggests publishers that flatten record fields do exist. Envelope keys are
159
+ written last now.
160
+
161
+ - b5f9397: fix(sharing,runtime): a `sort` passed straight to the engine never ordered anything; migrate every in-repo engine call to canonical QueryAST keys (#4346)
162
+
163
+ Two changes with different weights, from one sweep of every in-repo engine
164
+ call site that still speaks a deprecated alias.
165
+
166
+ **The bug — three dropped sorts.** #4346 made the engine fold `filter`→`where`
167
+ and `top`→`limit` on all six methods. The other four pairs in
168
+ `RPC_QUERY_ALIAS_SLOTS` (`select`, `sort`, `skip`, `populate`) are folded at
169
+ the RPC/wire layer only — their values need shape lowering that belongs to
170
+ those layers — and a **direct `engine.find()` never crosses that layer**. Three
171
+ call sites passed `sort` there, so it rode onto the AST untouched, every
172
+ driver's `Array.isArray(query.orderBy)` guard declined to emit an ORDER BY, and
173
+ the query returned an ordinary-looking, arbitrarily-ordered result:
174
+
175
+ | call site | asked for | actually got |
176
+ | ----------------------------------- | ------------------------------------------------- | --------------------------- |
177
+ | `share-link-routes.ts` | shared AI conversation messages, `created_at asc` | messages in arbitrary order |
178
+ | `runtime/domains/share-links.ts` | same route, runtime-domain copy | same |
179
+ | `share-link-service.ts` `listLinks` | the 200 most recent share links | an arbitrary 200 |
180
+
181
+ All three combine the dropped sort with a `limit` — the "latest N" shape whose
182
+ failure #4226 spelled out: an unapplied sort returns rows in arbitrary order,
183
+ which `limit` then slices into an arbitrary page. #4226 fixed that in the wire
184
+ normalizer; these calls sit one layer below it. `listLinks` had no test at all,
185
+ which is why it went unnoticed. Now pinned — on the option bag the engine
186
+ receives, not on row order, because the failure is that the key never becomes
187
+ `orderBy` and a fake engine honouring either spelling would pass either way.
188
+
189
+ **The cleanup — 27 no-op renames.** Every remaining in-repo engine call passing
190
+ `filter` now passes `where` (approvals 5, auth 2, reports 6, sharing 11,
191
+ webhooks 2, plus the one `filters` in a spec doc example). These are strict
192
+ no-ops since #4346 folds the alias — the point is that the framework stops
193
+ depending on a spelling it asks users to migrate off, which is a prerequisite
194
+ for ever retiring the aliases. Service-level `filter` PARAMETERS (each
195
+ service's own public API, e.g. `listRequests(filter)`) are deliberately
196
+ untouched — those are not engine option bags.
197
+
198
+ Two of the renamed calls were live victims of the #4346 bug rather than
199
+ cosmetic: `auth-manager`'s `stampIdentitySource` read the table's first row via
200
+ `findOne({filter})` and counted the whole table via `count({filter})`, so a
201
+ federated sign-in never stamped `source: 'idp_provisioned'`. #4346 already
202
+ corrected the behaviour; this makes the call say what it means.
203
+
204
+ - cc2de0e: chore(packaging): 20 packages stop publishing their sources, tests and build tooling (#4248)
205
+
206
+ These 20 packages declared no `files` field, so npm fell back to packing the
207
+ whole package directory. `npm pack --dry-run` on `@objectstack/plugin-webhooks`
208
+ listed **21 files** — 15 under `src/`, three of them unit tests
209
+ (`auto-enqueuer.test.ts`, `bootstrap-declared-webhooks.test.ts`, …), plus the
210
+ build-time `scripts/i18n-extract.config.ts`. `dist/` lands on top of that at
211
+ publish time rather than instead of it, so consumers were installing the
212
+ TypeScript sources and the test suite alongside the artifact they asked for.
213
+
214
+ Each now declares `"files": ["dist", "README.md"]`, matching the 29 packages
215
+ that already did. Nothing a consumer imports moves: every `main` / `types` /
216
+ `exports` target in all 20 already resolved inside `dist/`, which the new
217
+ `check:published-files` guard verifies rather than assumes. The visible change
218
+ is a smaller install and a smaller dependency-scanning surface — `npm pack` on
219
+ `@objectstack/plugin-webhooks` now yields 2 files plus `dist/`.
220
+
221
+ The other half of the fix is the gate. Half the packages declaring `files` and
222
+ half not was the #3786 shape — a hand-copied convention with nothing enforcing
223
+ it, where whoever forgets the line gets no signal at all. `check:published-files`
224
+ (new, wired into the always-required `lint` job) holds every non-private
225
+ workspace package to four invariants: `files` is **declared**; it is
226
+ **sufficient** (covers every entry point, so tightening a whitelist cannot ship
227
+ a package that fails to resolve); it is **minimal** (admits no test, test-harness
228
+ config or build script); and anything beyond `dist` + `README.md` is
229
+ **registered** with a reason, reconciled in both directions so a stale exemption
230
+ is an error rather than dead text. `@objectstack/spec` is the one package with
231
+ registered extras — its `.zod.ts` sources, JSON Schemas, liveness ledgers and
232
+ `CHANGELOG.md` are product, not build input.
233
+
234
+ This also closes an assumption #4206 was resting on. Excluding `<pkg>/scripts/**`
235
+ from the docs-drift implementation test is sound only while no package publishes
236
+ `scripts/` as runtime code; that held, but it held because someone read all three
237
+ offenders by hand. It is now checked on every PR.
238
+
239
+ - Updated dependencies [6a67d7a]
240
+ - Updated dependencies [0ecc656]
241
+ - Updated dependencies [06772eb]
242
+ - Updated dependencies [270650f]
243
+ - Updated dependencies [3aef718]
244
+ - Updated dependencies [1ea6bce]
245
+ - Updated dependencies [c1dcacd]
246
+ - Updated dependencies [ad303ed]
247
+ - Updated dependencies [32ccb23]
248
+ - Updated dependencies [f5a4ef0]
249
+ - Updated dependencies [2d3e255]
250
+ - Updated dependencies [7d7521f]
251
+ - Updated dependencies [5dc4d02]
252
+ - Updated dependencies [05154a1]
253
+ - Updated dependencies [9b6fe7c]
254
+ - Updated dependencies [8c711fb]
255
+ - Updated dependencies [09e4547]
256
+ - Updated dependencies [91f4c78]
257
+ - Updated dependencies [820eff9]
258
+ - Updated dependencies [8d895ff]
259
+ - Updated dependencies [f6472d7]
260
+ - Updated dependencies [78caf51]
261
+ - Updated dependencies [62a789b]
262
+ - Updated dependencies [789ad63]
263
+ - Updated dependencies [2af1988]
264
+ - Updated dependencies [0af50a3]
265
+ - Updated dependencies [2e836de]
266
+ - Updated dependencies [12a19a8]
267
+ - Updated dependencies [41dcda3]
268
+ - Updated dependencies [c8124e5]
269
+ - Updated dependencies [a1a4140]
270
+ - Updated dependencies [217e2e6]
271
+ - Updated dependencies [86a71d1]
272
+ - Updated dependencies [d5c75e2]
273
+ - Updated dependencies [03d26f7]
274
+ - Updated dependencies [4384921]
275
+ - Updated dependencies [3c628ce]
276
+ - Updated dependencies [7cb922e]
277
+ - Updated dependencies [1d22114]
278
+ - Updated dependencies [b5f9397]
279
+ - Updated dependencies [ed77493]
280
+ - Updated dependencies [58a03d2]
281
+ - Updated dependencies [dc530b4]
282
+ - Updated dependencies [e59786e]
283
+ - Updated dependencies [bcf1112]
284
+ - Updated dependencies [9774b78]
285
+ - Updated dependencies [b07d829]
286
+ - Updated dependencies [a648e96]
287
+ - Updated dependencies [a47ac06]
288
+ - Updated dependencies [e4c61a7]
289
+ - Updated dependencies [cc60165]
290
+ - Updated dependencies [081aa6f]
291
+ - Updated dependencies [91f4c78]
292
+ - Updated dependencies [e8d0c21]
293
+ - Updated dependencies [45dc446]
294
+ - Updated dependencies [c1d44f7]
295
+ - Updated dependencies [ab9fb5c]
296
+ - Updated dependencies [f985b3f]
297
+ - Updated dependencies [9a4932a]
298
+ - Updated dependencies [f9fc874]
299
+ - Updated dependencies [011b386]
300
+ - Updated dependencies [7777e8f]
301
+ - Updated dependencies [507b92a]
302
+ - Updated dependencies [7309c81]
303
+ - Updated dependencies [a8dcc37]
304
+ - Updated dependencies [20bc1ec]
305
+ - Updated dependencies [90c2b15]
306
+ - Updated dependencies [42eeb7d]
307
+ - Updated dependencies [01e124d]
308
+ - Updated dependencies [7ce02eb]
309
+ - Updated dependencies [a13827e]
310
+ - Updated dependencies [7733604]
311
+ - Updated dependencies [40e420f]
312
+ - Updated dependencies [d13004a]
313
+ - Updated dependencies [be7360c]
314
+ - Updated dependencies [5b47ab5]
315
+ - Updated dependencies [b09d8d9]
316
+ - Updated dependencies [b09d8d9]
317
+ - Updated dependencies [8675db6]
318
+ - Updated dependencies [b09d8d9]
319
+ - Updated dependencies [3eb1b2b]
320
+ - Updated dependencies [59b85c0]
321
+ - Updated dependencies [6e357ed]
322
+ - Updated dependencies [d6938bf]
323
+ - Updated dependencies [31e0be9]
324
+ - Updated dependencies [4bfd455]
325
+ - Updated dependencies [ffd2ce2]
326
+ - Updated dependencies [62f8017]
327
+ - Updated dependencies [a831df1]
328
+ - Updated dependencies [f752ee3]
329
+ - Updated dependencies [a1b61e0]
330
+ - Updated dependencies [cd6b9f2]
331
+ - Updated dependencies [2cb6d3c]
332
+ - Updated dependencies [af2a095]
333
+ - Updated dependencies [ec796d5]
334
+ - Updated dependencies [e87fea1]
335
+ - Updated dependencies [c65e529]
336
+ - Updated dependencies [3ca34c1]
337
+ - Updated dependencies [239c3a3]
338
+ - Updated dependencies [94a0bbc]
339
+ - Updated dependencies [d6bfb3d]
340
+ - Updated dependencies [a2266a6]
341
+ - Updated dependencies [d25a0ec]
342
+ - Updated dependencies [667b83e]
343
+ - Updated dependencies [627b188]
344
+ - Updated dependencies [8d4eae7]
345
+ - Updated dependencies [857a6cf]
346
+ - Updated dependencies [65a3a84]
347
+ - Updated dependencies [ccd9397]
348
+ - Updated dependencies [bca935b]
349
+ - Updated dependencies [d92c72d]
350
+ - Updated dependencies [c54c822]
351
+ - Updated dependencies [8dcc0f5]
352
+ - Updated dependencies [75b9e51]
353
+ - Updated dependencies [0a2f233]
354
+ - Updated dependencies [8621cdd]
355
+ - Updated dependencies [6f23667]
356
+ - Updated dependencies [5d21a48]
357
+ - Updated dependencies [19365b7]
358
+ - Updated dependencies [b7ed26d]
359
+ - Updated dependencies [b3a3d83]
360
+ - Updated dependencies [7a55913]
361
+ - Updated dependencies [35accbf]
362
+ - Updated dependencies [6038de7]
363
+ - Updated dependencies [eb95d97]
364
+ - Updated dependencies [e4c2dc8]
365
+ - Updated dependencies [1bd2795]
366
+ - Updated dependencies [8186a70]
367
+ - Updated dependencies [a329cca]
368
+ - Updated dependencies [6eec18c]
369
+ - Updated dependencies [4d7bebf]
370
+ - Updated dependencies [821ac7a]
371
+ - Updated dependencies [8f81731]
372
+ - Updated dependencies [8b50cb3]
373
+ - Updated dependencies [8c2db68]
374
+ - Updated dependencies [22b5e54]
375
+ - Updated dependencies [0166bd5]
376
+ - Updated dependencies [9b702dc]
377
+ - Updated dependencies [ab16331]
378
+ - @objectstack/spec@17.0.0-rc.1
379
+ - @objectstack/core@17.0.0-rc.1
380
+ - @objectstack/service-messaging@17.0.0-rc.1
381
+
382
+ ## 17.0.0-rc.0
383
+
384
+ ### Minor Changes
385
+
386
+ - 69f1dfd: fix(webhooks): materialize stack-declared webhooks into the dispatcher (#3461)
387
+
388
+ A webhook authored declaratively — `defineStack({ webhooks })` / `defineWebhook()`,
389
+ validated against the spec `WebhookSchema` — was a **silent no-op**. The runtime
390
+ dispatcher (`AutoEnqueuer`) fans out off `sys_webhook` DATA rows (`object_name` /
391
+ `active`), which until now were only ever written by hand through the object's
392
+ CRUD UI. Nothing turned a declared webhook (`object` / `isActive`) into a
393
+ dispatchable row, so authoring `webhooks:` on a stack produced `webhook` metadata
394
+ that never fired (ADR-0078). The showcase app itself shipped a `webhooks:` entry
395
+ that did nothing.
396
+
397
+ `@objectstack/plugin-webhooks` now bridges the two on boot:
398
+
399
+ - **`bootstrapDeclaredWebhooks`** reads declared `webhook` metadata from the
400
+ ObjectQL registry (where the manifest decomposition already parks
401
+ `stack.webhooks`), validates each through `WebhookSchema.parse()` — the spec
402
+ schema finally has a real consumer — and materializes it into a `sys_webhook`
403
+ row, mapping `object → object_name`, `isActive → active`, and stashing the full
404
+ envelope (headers / secret / retry / timeout) in `definition_json`. The
405
+ auto-enqueuer's first cache refresh then picks the row up and dispatches it.
406
+ - **Seed-not-clobber provenance** (mirrors `sys_sharing_rule`, #2909): `sys_webhook`
407
+ gains `managed_by` / `customized` columns. Declared webhooks re-seed every boot
408
+ as `managed_by: 'package'`, but a row an admin created (`managed_by: 'admin'`) or
409
+ edited in Setup (`customized: true`, stamped by a `beforeUpdate` hook) is never
410
+ overwritten — a deactivated noisy webhook survives redeploys.
411
+
412
+ Connector-declared `webhooks` remain not-yet-enforced (that is a separate seam,
413
+ #3197). Registering `webhook` as a first-class metadata type + enrolling it in the
414
+ liveness `GOVERNED` set is a tracked follow-up.
415
+
416
+ Migration: none required. Existing hand-authored `sys_webhook` rows default to
417
+ `managed_by: 'admin'` and are never touched by the seeder. Anyone who authored
418
+ `webhooks:` on a stack expecting it to fire will find it now does — review those
419
+ declarations (especially `url` / `isActive`) before upgrading.
420
+
421
+ ### Patch Changes
422
+
423
+ - aff9e56: fix(i18n): translate the platform packages' declared surface, and gate all nine bundles instead of one (#3762)
424
+
425
+ Only `platform-objects` was wired into a translation-drift check. The other
426
+ **eight** packages shipped a `scripts/i18n-extract.config.ts` that nothing ever
427
+ ran — and four of them had already drifted out of sync with the schema, exactly
428
+ the rot `pnpm check:i18n` exists to catch, one directory over.
429
+
430
+ **Translated.** `plugin-security` (45 strings per locale), `plugin-webhooks`
431
+ (15), `plugin-audit` (8), `plugin-sharing` (7) and `service-storage` (7) are now
432
+ at **zero** untranslated declared strings in zh-CN / ja-JP / es-ES — 246
433
+ translations. Most were newly _visible_ rather than newly missing: #3753 taught
434
+ the coverage detector to walk action `params`, `resultDialog`, `listViews` and
435
+ the rest of the declared surface, and these are what it found.
436
+
437
+ Wording was harvested from the repo's own bundles wherever a string was already
438
+ translated somewhere (1382 unambiguous source strings), so `Created At` reads
439
+ `创建时间` here because that is what it reads everywhere else, rather than a
440
+ fresh invention. Protocol tokens are deliberately left identical across locales:
441
+ `GET` / `POST` / `PUT` / `PATCH` / `DELETE`, `ETag`, `ACL`, `URL`.
442
+
443
+ **Gated.** `scripts/check-i18n-bundles.mjs` replaces the single-package
444
+ `pnpm check:i18n` and checks all nine. It does not restate each package's
445
+ command — it parses the one already documented in that config's own docstring
446
+ and runs it, so the documented regenerate command and the gate cannot diverge.
447
+ The coverage ratchet grows the same way, from `examples/*` to twelve configs;
448
+ eight of them sit at zero, which makes it the strict gate there.
449
+
450
+ **Fixed a real truncation bug it exposed.** `os lint --json` on a large config
451
+ came out of a pipe cut off at exactly 65536 bytes — `console.log(big)` followed
452
+ by `process.exit(1)` tears the process down before an async pipe write drains,
453
+ while an interactive run (stdout is a TTY, written synchronously) looks perfect.
454
+ Every scripted consumer silently got invalid JSON. `emitJson` in
455
+ `packages/cli/src/utils/format.ts` waits for the write to drain and sets
456
+ `process.exitCode` instead; `lint`, `i18n check` and `i18n extract` use it.
457
+ Roughly 30 other CLI commands share the pattern and are not touched here.
458
+
459
+ The nine documented regenerate commands also gain `--no-metadata-forms` (added
460
+ in #3768), since the Studio metadata-form baseline belongs to `platform-objects`
461
+ alone, not to a copy in every plugin.
462
+
463
+ Not fixed here: `platform-objects`' own 77-per-locale gap is `apps.*` /
464
+ `dashboards.*` navigation and widget labels, which live outside the `objects`
465
+ subtree and cannot be scaffolded while the package extracts with
466
+ `--objects-only`. That needs an emit decision first — tracked in #3762.
467
+
468
+ - 52281b0: chore(i18n): purge the dead sys_webhook_delivery translation block and guard against recurrence
469
+
470
+ `sys_webhook_delivery` was removed when webhook delivery moved to
471
+ `@objectstack/service-messaging` (`sys_http_delivery`, ADR-0018 M3), but a full
472
+ translation block for it lingered in the four generated plugin-webhooks i18n
473
+ bundles (en/zh-CN/ja-JP/es-ES) — dead weight bound to an object that no longer
474
+ exists, and destined to be dropped silently (with any curated strings) on the
475
+ next `os i18n extract`.
476
+
477
+ - Removed the stale `sys_webhook_delivery` block from all four locale bundles
478
+ (surgical; the `sys_webhook` block is untouched).
479
+ - Corrected three stale `sys_webhook_delivery` doc comments (platform-objects
480
+ `integration/index.ts` + `setup.app.ts`, plugin-webhooks `sys-webhook.object.ts`)
481
+ that still named it as a plugin-webhooks-owned object.
482
+ - Rolled out the platform-objects `bundle-ownership` test guard (#2834 ⑤ /
483
+ ADR-0029 D8) to the eight packages that own i18n bundles, so a stray object
484
+ block in a generated bundle now fails the build instead of dying silently.
485
+ - That guard immediately surfaced a live-object omission: `sys_capability` was
486
+ present in plugin-security's bundles with curated translations but had been
487
+ dropped from its extract config — re-added to the config so the strings are
488
+ preserved, rather than deleted.
489
+
490
+ - c95ac80: chore(plugin-webhooks): drop the dead sys_webhook_delivery i18n blocks
491
+
492
+ `sys_webhook_delivery` was removed from `@objectstack/plugin-webhooks` when
493
+ outbound delivery moved to `@objectstack/service-messaging` (`sys_http_delivery`,
494
+ ADR-0018 M3), but its translation blocks lingered in all four generated locale
495
+ bundles (en / zh-CN / ja-JP / es-ES) — loaded at runtime yet referenced by
496
+ nothing, since the object no longer exists in this plugin.
497
+
498
+ - Removed the `sys_webhook_delivery` node from each `*.objects.generated.ts`
499
+ bundle; `WebhooksTranslations` now carries only `sys_webhook`.
500
+ - Corrected the stale ownership comment on `SysWebhook` that still named
501
+ `sys_webhook_delivery` as a live sibling.
502
+
503
+ (The dangling `SysWebhookDelivery` import in `scripts/i18n-extract.config.ts`
504
+ was fixed independently on `main` by #3489, so it is not part of this change.)
505
+
506
+ - Updated dependencies [50616d9]
507
+ - Updated dependencies [08b5a3d]
508
+ - Updated dependencies [d99aeb3]
509
+ - Updated dependencies [4727eb8]
510
+ - Updated dependencies [f63cd09]
511
+ - Updated dependencies [fa3d0cf]
512
+ - Updated dependencies [af5a224]
513
+ - Updated dependencies [71f76e1]
514
+ - Updated dependencies [37b1346]
515
+ - Updated dependencies [99736a0]
516
+ - Updated dependencies [fe67e34]
517
+ - Updated dependencies [fdb4f50]
518
+ - Updated dependencies [1bd5652]
519
+ - Updated dependencies [14252d3]
520
+ - Updated dependencies [7fb436c]
521
+ - Updated dependencies [879ea13]
522
+ - Updated dependencies [201b31f]
523
+ - Updated dependencies [e2616e0]
524
+ - Updated dependencies [6fdc5c6]
525
+ - Updated dependencies [8b9d71e]
526
+ - Updated dependencies [33f5e23]
527
+ - Updated dependencies [259af21]
528
+ - Updated dependencies [587fc91]
529
+ - Updated dependencies [1986594]
530
+ - Updated dependencies [ad4af62]
531
+ - Updated dependencies [d44dbfa]
532
+ - Updated dependencies [474fe39]
533
+ - Updated dependencies [0bc685a]
534
+ - Updated dependencies [b949059]
535
+ - Updated dependencies [be1c52c]
536
+ - Updated dependencies [c5ff96d]
537
+ - Updated dependencies [84e7be9]
538
+ - Updated dependencies [a6c3f38]
539
+ - Updated dependencies [debc23a]
540
+ - Updated dependencies [0f8ad09]
541
+ - Updated dependencies [8f9689f]
542
+ - Updated dependencies [57a3bb3]
543
+ - Updated dependencies [5f9a987]
544
+ - Updated dependencies [db02d47]
545
+ - Updated dependencies [0bfdf46]
546
+ - Updated dependencies [376a061]
547
+ - Updated dependencies [7c7e246]
548
+ - Updated dependencies [f35cdc5]
549
+ - Updated dependencies [9ea2bc5]
550
+ - Updated dependencies [c2d9098]
551
+ - Updated dependencies [a227ed7]
552
+ - Updated dependencies [9613396]
553
+ - Updated dependencies [e47b342]
554
+ - Updated dependencies [4ed7ed4]
555
+ - Updated dependencies [2fa4ca1]
556
+ - Updated dependencies [f5a2320]
557
+ - Updated dependencies [deb538f]
558
+ - Updated dependencies [5b89711]
559
+ - Updated dependencies [0c8a22f]
560
+ - Updated dependencies [763931e]
561
+ - Updated dependencies [de9af8a]
562
+ - Updated dependencies [c4df271]
563
+ - Updated dependencies [a41ba5c]
564
+ - Updated dependencies [189854c]
565
+ - Updated dependencies [0e3a226]
566
+ - Updated dependencies [1d4756e]
567
+ - Updated dependencies [720c5ad]
568
+ - Updated dependencies [a8d1e24]
569
+ - Updated dependencies [41642b0]
570
+ - Updated dependencies [4cca74c]
571
+ - Updated dependencies [88ef03e]
572
+ - Updated dependencies [9e2caf3]
573
+ - Updated dependencies [81ce41a]
574
+ - Updated dependencies [85e1e4e]
575
+ - Updated dependencies [dac6a08]
576
+ - Updated dependencies [394b7a1]
577
+ - Updated dependencies [677b591]
578
+ - Updated dependencies [d77d1b7]
579
+ - Updated dependencies [5b79a34]
580
+ - Updated dependencies [c757854]
581
+ - Updated dependencies [0045682]
582
+ - Updated dependencies [2a5f04a]
583
+ - Updated dependencies [4f740b0]
584
+ - Updated dependencies [67452d1]
585
+ - Updated dependencies [0fc6219]
586
+ - Updated dependencies [605e190]
587
+ - Updated dependencies [c6c59f1]
588
+ - Updated dependencies [b0e78a8]
589
+ - Updated dependencies [f31cc8d]
590
+ - Updated dependencies [f343dc4]
591
+ - Updated dependencies [8269e32]
592
+ - Updated dependencies [74f7339]
593
+ - Updated dependencies [a6c35a2]
594
+ - Updated dependencies [c2f1002]
595
+ - Updated dependencies [f163028]
596
+ - Updated dependencies [f07808c]
597
+ - Updated dependencies [7ffc3d3]
598
+ - Updated dependencies [88346ba]
599
+ - Updated dependencies [4631592]
600
+ - Updated dependencies [32ff033]
601
+ - Updated dependencies [5ac93d4]
602
+ - Updated dependencies [93f267f]
603
+ - Updated dependencies [0024abf]
604
+ - Updated dependencies [acbf364]
605
+ - Updated dependencies [7687f7b]
606
+ - Updated dependencies [1659072]
607
+ - Updated dependencies [abceb0d]
608
+ - Updated dependencies [0c302a7]
609
+ - Updated dependencies [6633337]
610
+ - Updated dependencies [f00d8d4]
611
+ - Updated dependencies [503be86]
612
+ - Updated dependencies [cde1975]
613
+ - Updated dependencies [0bc685a]
614
+ - Updated dependencies [11949fc]
615
+ - Updated dependencies [b098b0e]
616
+ - Updated dependencies [4d00b13]
617
+ - Updated dependencies [57bab76]
618
+ - Updated dependencies [b90086a]
619
+ - Updated dependencies [b95577a]
620
+ - Updated dependencies [83c161f]
621
+ - Updated dependencies [d8c4957]
622
+ - Updated dependencies [f24cb83]
623
+ - Updated dependencies [5dbbb92]
624
+ - Updated dependencies [69f1dfd]
625
+ - @objectstack/spec@17.0.0-rc.0
626
+ - @objectstack/core@17.0.0-rc.0
627
+ - @objectstack/service-messaging@17.0.0-rc.0
628
+
3
629
  ## 16.1.0
4
630
 
5
631
  ### Patch Changes
@@ -13,7 +13,7 @@ var SysWebhook = ObjectSchema.create({
13
13
  // create/edit/delete so admins can at least toggle `active` and edit
14
14
  // simple URL/method fields without round-tripping through code.
15
15
  userActions: { create: true, edit: true, delete: true, import: false },
16
- description: "Outbound HTTP webhook subscription. Authored via defineWebhook() in code or the Studio editor; executed by the HTTP connector plugin.",
16
+ description: "Outbound HTTP webhook subscription. Declared in code via defineStack({ webhooks }) / defineWebhook() (materialized into rows on boot) or authored directly in the Studio editor; dispatched by the webhook auto-enqueuer onto the shared HTTP outbox.",
17
17
  displayNameField: "name",
18
18
  nameField: "name",
19
19
  // [ADR-0079] canonical primary-title pointer (mirrors deprecated displayNameField)
@@ -133,6 +133,32 @@ var SysWebhook = ObjectSchema.create({
133
133
  description: "Serialised Webhook JSON (see @objectstack/spec/automation/webhook) \u2014 full headers/auth/retry/payload config",
134
134
  group: "Definition"
135
135
  }),
136
+ // ── Provenance (#3461 — record-authoritative seed-not-clobber) ──
137
+ // Mirrors sys_sharing_rule (#2909). Both columns are `readonly`: the
138
+ // engine strips them from non-system payloads (forge/clear-proof), while
139
+ // bootstrapDeclaredWebhooks and the provenance stamp hook write with
140
+ // isSystem. Deliberately NOT a write gate: webhooks are a first-class admin
141
+ // authoring/tuning surface — admins may edit or deactivate a package row;
142
+ // the seeder simply stops overwriting it once `customized` is stamped.
143
+ managed_by: Field.select(
144
+ ["platform", "package", "admin"],
145
+ {
146
+ label: "Managed By",
147
+ required: false,
148
+ readonly: true,
149
+ defaultValue: "admin",
150
+ description: "Record provenance: platform = framework built-in / package = app/package-declared (boot-seeded from defineStack webhooks) / admin = created in Setup.",
151
+ group: "System"
152
+ }
153
+ ),
154
+ customized: Field.boolean({
155
+ label: "Customized",
156
+ required: false,
157
+ readonly: true,
158
+ defaultValue: false,
159
+ description: "Set when an admin edits a package-declared webhook; boot seeding will no longer overwrite the row (a deactivated noisy webhook survives redeploys). Meaningless on admin rows.",
160
+ group: "System"
161
+ }),
136
162
  created_at: Field.datetime({
137
163
  label: "Created At",
138
164
  required: true,
@@ -152,4 +178,4 @@ var SysWebhook = ObjectSchema.create({
152
178
  export {
153
179
  SysWebhook
154
180
  };
155
- //# sourceMappingURL=chunk-RBCYKJVL.js.map
181
+ //# sourceMappingURL=chunk-6EPMRZ7I.js.map