@cosmicdrift/kumiko-bundled-features 0.362.0 → 0.363.0

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 (307) hide show
  1. package/dist/admin-shell/feature.d.ts +3 -0
  2. package/dist/admin-shell/feature.js +6 -1
  3. package/dist/agent-tools/agent-manifest.js +2 -1
  4. package/dist/agent-tools/filter-ops.d.ts +1 -1
  5. package/dist/agent-tools/filter-ops.js +1 -3
  6. package/dist/agent-tools/tool-dispatch.js +2 -1
  7. package/dist/auth-email-password/email-templates.d.ts +4 -26
  8. package/dist/auth-email-password/email-templates.js +9 -101
  9. package/dist/auth-email-password/feature.js +24 -6
  10. package/dist/auth-email-password/handlers/invite-create.write.js +4 -4
  11. package/dist/auth-email-password/handlers/request-account-unlock.write.js +2 -4
  12. package/dist/auth-email-password/handlers/request-email-verification.write.js +2 -4
  13. package/dist/auth-email-password/handlers/request-password-reset.write.js +2 -4
  14. package/dist/auth-email-password/handlers/signup-confirm.write.js +3 -4
  15. package/dist/auth-email-password/handlers/token-request-handler.d.ts +1 -2
  16. package/dist/auth-email-password/handlers/token-request-handler.js +0 -1
  17. package/dist/auth-email-password/index.d.ts +2 -2
  18. package/dist/auth-email-password/index.js +1 -1
  19. package/dist/auth-email-password/magic-link-mail.d.ts +3 -2
  20. package/dist/auth-email-password/magic-link-mail.js +19 -14
  21. package/dist/auth-email-password/mail-notifications.d.ts +32 -0
  22. package/dist/auth-email-password/mail-notifications.js +116 -0
  23. package/dist/auth-email-password/signup-activation.d.ts +1 -1
  24. package/dist/auth-email-password/signup-activation.js +2 -3
  25. package/dist/auth-foundation/types.js +2 -8
  26. package/dist/auth-mfa/feature.js +4 -4
  27. package/dist/auth-mfa/hmac-token-codec.js +4 -4
  28. package/dist/auth-mfa/mfa-challenge-token.js +3 -3
  29. package/dist/auth-mfa/mfa-preauth-setup-token.js +3 -3
  30. package/dist/auth-mfa/mfa-setup-token.js +8 -8
  31. package/dist/billing-foundation/constants.d.ts +3 -3
  32. package/dist/billing-foundation/constants.js +5 -4
  33. package/dist/billing-foundation/consumer-protection/confirmation-mail.d.ts +32 -14
  34. package/dist/billing-foundation/consumer-protection/confirmation-mail.js +27 -32
  35. package/dist/billing-foundation/consumer-protection/issue-confirmation.js +3 -3
  36. package/dist/billing-foundation/consumer-protection/mail-notifications.d.ts +8 -0
  37. package/dist/billing-foundation/consumer-protection/mail-notifications.js +95 -0
  38. package/dist/billing-foundation/consumer-protection/register-consent.js +2 -0
  39. package/dist/billing-foundation/consumer-protection/termination-mail.d.ts +20 -10
  40. package/dist/billing-foundation/consumer-protection/termination-mail.js +10 -21
  41. package/dist/billing-foundation/consumer-protection/termination-notify.js +2 -2
  42. package/dist/billing-foundation/consumer-protection/termination-pages.js +1 -3
  43. package/dist/billing-foundation/consumer-protection/termination-request.js +2 -2
  44. package/dist/billing-foundation/handlers/process-event.write.js +2 -2
  45. package/dist/billing-foundation/handlers/process-payment-event.write.js +1 -1
  46. package/dist/billing-foundation/subscription-tier-sync.js +3 -4
  47. package/dist/cap-overview/handlers/tenant-caps-list.query.js +2 -1
  48. package/dist/cap-overview/web/cap-usage-cell.js +5 -4
  49. package/dist/channel-email/email-channel.d.ts +2 -2
  50. package/dist/channel-email/email-channel.js +89 -26
  51. package/dist/channel-email/feature.js +3 -3
  52. package/dist/channel-email/index.d.ts +1 -1
  53. package/dist/channel-email/index.js +1 -1
  54. package/dist/channel-email/pii-guard.js +10 -0
  55. package/dist/channel-email/smtp-transport.js +13 -0
  56. package/dist/channel-email/types.d.ts +8 -0
  57. package/dist/config/handlers/set.write.js +1 -2
  58. package/dist/custom-fields/lib/value-schema.js +10 -11
  59. package/dist/custom-fields/wire-user-data-rights.js +7 -6
  60. package/dist/data-retention/index.d.ts +1 -0
  61. package/dist/data-retention/index.js +1 -0
  62. package/dist/data-retention/run-retention-cleanup.js +6 -6
  63. package/dist/delivery/attachment-ref.d.ts +39 -0
  64. package/dist/delivery/attachment-ref.js +64 -0
  65. package/dist/delivery/channel-context.d.ts +8 -4
  66. package/dist/delivery/channel-context.js +76 -2
  67. package/dist/delivery/constants.d.ts +1 -0
  68. package/dist/delivery/constants.js +1 -0
  69. package/dist/delivery/delivery-service.d.ts +4 -1
  70. package/dist/delivery/delivery-service.js +38 -32
  71. package/dist/delivery/feature.js +1 -1
  72. package/dist/delivery/index.d.ts +5 -2
  73. package/dist/delivery/index.js +4 -1
  74. package/dist/delivery/jobs.js +25 -5
  75. package/dist/delivery/notify-factory.js +4 -1
  76. package/dist/delivery/testing.d.ts +4 -1
  77. package/dist/delivery/types.d.ts +20 -14
  78. package/dist/delivery/unsubscribe.js +4 -1
  79. package/dist/derivatives-sharp/render.js +1 -18
  80. package/dist/document-ingest-foundation/pages.js +4 -4
  81. package/dist/feature-toggles/toggle-sync-signal.js +4 -4
  82. package/dist/file-foundation/index.d.ts +1 -0
  83. package/dist/file-foundation/index.js +1 -0
  84. package/dist/file-foundation/read-file-ref-content.d.ts +27 -0
  85. package/dist/file-foundation/read-file-ref-content.js +49 -0
  86. package/dist/folders/web/folder-manager.js +3 -2
  87. package/dist/form-draft/db/queries/cleanup.js +4 -4
  88. package/dist/form-draft/db/queries/draft-count.js +2 -2
  89. package/dist/form-draft/db/queries/owned-file-refs.js +2 -2
  90. package/dist/form-draft/release-file-refs.js +3 -2
  91. package/dist/inbound-mail-foundation/handlers/connect-account.write.js +1 -1
  92. package/dist/inbound-mail-foundation/handlers/ingest-message.write.js +6 -6
  93. package/dist/inbound-mail-foundation/handlers/scope-visibility.d.ts +1 -1
  94. package/dist/inbound-mail-foundation/oauth-state.js +7 -7
  95. package/dist/inbound-mail-foundation/types.js +4 -4
  96. package/dist/inbound-mail-foundation/watch-supervisor.js +22 -13
  97. package/dist/inbound-provider-imap/imap-client.js +4 -3
  98. package/dist/ledger/recurring.js +1 -3
  99. package/dist/managed-pages/branding.d.ts +2 -0
  100. package/dist/managed-pages/branding.js +24 -2
  101. package/dist/managed-pages/feature.js +1 -0
  102. package/dist/managed-pages/i18n.js +1 -0
  103. package/dist/managed-pages/screens/branding-screen.js +8 -1
  104. package/dist/page-render/branding.d.ts +1 -0
  105. package/dist/page-render/branding.js +1 -0
  106. package/dist/page-render/markdown.js +1 -1
  107. package/dist/personal-access-tokens/feature.js +1 -1
  108. package/dist/personal-access-tokens/handlers/list.query.js +2 -1
  109. package/dist/personal-access-tokens/revoke-for-user.js +2 -1
  110. package/dist/renderer-foundation/api.d.ts +13 -13
  111. package/dist/renderer-foundation/api.js +1 -1
  112. package/dist/renderer-foundation/constants.js +2 -4
  113. package/dist/renderer-foundation/feature.js +7 -7
  114. package/dist/renderer-foundation/index.d.ts +2 -1
  115. package/dist/renderer-foundation/index.js +1 -0
  116. package/dist/renderer-foundation/types.d.ts +92 -32
  117. package/dist/renderer-pdf/feature.js +7 -1
  118. package/dist/sessions/db/queries/cleanup.js +2 -2
  119. package/dist/sessions/feature.js +1 -1
  120. package/dist/sessions/handlers/list.query.js +2 -1
  121. package/dist/shared/attachment-file-name.d.ts +3 -0
  122. package/dist/shared/attachment-file-name.js +35 -0
  123. package/dist/shared/index.d.ts +3 -0
  124. package/dist/shared/index.js +3 -0
  125. package/dist/shared/is-tenant-db.js +1 -1
  126. package/dist/shared/mail-template-body.d.ts +4 -0
  127. package/dist/shared/mail-template-body.js +17 -0
  128. package/dist/shared/sharp-input-limits.d.ts +6 -0
  129. package/dist/shared/sharp-input-limits.js +22 -0
  130. package/dist/shared/signup-handover.js +2 -2
  131. package/dist/tags/handlers/assign-tag.write.js +3 -1
  132. package/dist/tags/web/tag-chip.js +2 -0
  133. package/dist/template-resolver/api.d.ts +30 -2
  134. package/dist/template-resolver/api.js +40 -5
  135. package/dist/template-resolver/compile-document-body.d.ts +8 -0
  136. package/dist/template-resolver/compile-document-body.js +163 -0
  137. package/dist/template-resolver/constants.d.ts +13 -4
  138. package/dist/template-resolver/constants.js +30 -10
  139. package/dist/template-resolver/document-sanitizer.d.ts +32 -0
  140. package/dist/template-resolver/document-sanitizer.js +201 -0
  141. package/dist/template-resolver/document-schema.d.ts +21 -0
  142. package/dist/template-resolver/document-schema.js +296 -0
  143. package/dist/template-resolver/feature.d.ts +18 -0
  144. package/dist/template-resolver/feature.js +50 -6
  145. package/dist/template-resolver/handlers/bundle-import.d.ts +20 -0
  146. package/dist/template-resolver/handlers/bundle-import.js +147 -0
  147. package/dist/template-resolver/handlers/collection-set.write.js +25 -2
  148. package/dist/template-resolver/handlers/copy-locale.write.d.ts +19 -0
  149. package/dist/template-resolver/handlers/copy-locale.write.js +116 -0
  150. package/dist/template-resolver/handlers/diff-to-system.query.d.ts +22 -0
  151. package/dist/template-resolver/handlers/diff-to-system.query.js +64 -0
  152. package/dist/template-resolver/handlers/export-bundle.query.d.ts +35 -0
  153. package/dist/template-resolver/handlers/export-bundle.query.js +68 -0
  154. package/dist/template-resolver/handlers/find-by-id.query.d.ts +1 -0
  155. package/dist/template-resolver/handlers/find-by-id.query.js +3 -3
  156. package/dist/template-resolver/handlers/import-bundle-system.write.d.ts +39 -0
  157. package/dist/template-resolver/handlers/import-bundle-system.write.js +36 -0
  158. package/dist/template-resolver/handlers/import-bundle.write.d.ts +40 -0
  159. package/dist/template-resolver/handlers/import-bundle.write.js +19 -0
  160. package/dist/template-resolver/handlers/layout-source.query.d.ts +26 -0
  161. package/dist/template-resolver/handlers/layout-source.query.js +64 -0
  162. package/dist/template-resolver/handlers/list.query.d.ts +4 -1
  163. package/dist/template-resolver/handlers/list.query.js +5 -7
  164. package/dist/template-resolver/handlers/overview.query.d.ts +59 -0
  165. package/dist/template-resolver/handlers/overview.query.js +165 -0
  166. package/dist/template-resolver/handlers/preview.query.d.ts +12 -0
  167. package/dist/template-resolver/handlers/preview.query.js +24 -0
  168. package/dist/template-resolver/handlers/reset-to-system.write.d.ts +8 -0
  169. package/dist/template-resolver/handlers/reset-to-system.write.js +50 -0
  170. package/dist/template-resolver/handlers/resource-link-pdf.write.d.ts +8 -0
  171. package/dist/template-resolver/handlers/resource-link-pdf.write.js +32 -0
  172. package/dist/template-resolver/handlers/resource-remove.write.d.ts +9 -0
  173. package/dist/template-resolver/handlers/resource-remove.write.js +44 -0
  174. package/dist/template-resolver/handlers/resource-shared.d.ts +9 -0
  175. package/dist/template-resolver/handlers/resource-shared.js +14 -0
  176. package/dist/template-resolver/handlers/resource-upload.write.d.ts +13 -0
  177. package/dist/template-resolver/handlers/resource-upload.write.js +98 -0
  178. package/dist/template-resolver/handlers/send-test.write.d.ts +11 -0
  179. package/dist/template-resolver/handlers/send-test.write.js +81 -0
  180. package/dist/template-resolver/handlers/set.write.d.ts +4 -1
  181. package/dist/template-resolver/handlers/set.write.js +25 -3
  182. package/dist/template-resolver/handlers/shared.d.ts +9 -5
  183. package/dist/template-resolver/handlers/shared.js +6 -2
  184. package/dist/template-resolver/handlers/template-gates.d.ts +36 -0
  185. package/dist/template-resolver/handlers/template-gates.js +131 -0
  186. package/dist/template-resolver/handlers/template-write.d.ts +45 -0
  187. package/dist/template-resolver/handlers/template-write.js +109 -0
  188. package/dist/template-resolver/handlers/tenant-overrides.query.d.ts +17 -0
  189. package/dist/template-resolver/handlers/tenant-overrides.query.js +48 -0
  190. package/dist/template-resolver/handlers/toggle-status.write.d.ts +12 -0
  191. package/dist/template-resolver/handlers/toggle-status.write.js +27 -11
  192. package/dist/template-resolver/handlers/upsert-system.write.d.ts +5 -8
  193. package/dist/template-resolver/handlers/upsert-system.write.js +14 -59
  194. package/dist/template-resolver/handlers/upsert-tenant.write.d.ts +5 -8
  195. package/dist/template-resolver/handlers/upsert-tenant.write.js +10 -61
  196. package/dist/template-resolver/handlers/usage.query.d.ts +17 -0
  197. package/dist/template-resolver/handlers/usage.query.js +15 -0
  198. package/dist/template-resolver/handlers/validate.query.d.ts +74 -0
  199. package/dist/template-resolver/handlers/validate.query.js +80 -0
  200. package/dist/template-resolver/index.d.ts +18 -1
  201. package/dist/template-resolver/index.js +16 -1
  202. package/dist/template-resolver/layout-regions.d.ts +23 -0
  203. package/dist/template-resolver/layout-regions.js +125 -0
  204. package/dist/template-resolver/linked-resources.d.ts +17 -0
  205. package/dist/template-resolver/linked-resources.js +75 -0
  206. package/dist/template-resolver/preview-display-html.d.ts +7 -0
  207. package/dist/template-resolver/preview-display-html.js +27 -0
  208. package/dist/template-resolver/print-document.d.ts +1 -0
  209. package/dist/template-resolver/print-document.js +55 -0
  210. package/dist/template-resolver/qualified-names.d.ts +30 -0
  211. package/dist/template-resolver/qualified-names.js +30 -0
  212. package/dist/template-resolver/record-mapping.d.ts +2 -0
  213. package/dist/template-resolver/record-mapping.js +21 -0
  214. package/dist/template-resolver/resource-image.d.ts +15 -0
  215. package/dist/template-resolver/resource-image.js +34 -0
  216. package/dist/template-resolver/seeding.d.ts +14 -1
  217. package/dist/template-resolver/seeding.js +105 -15
  218. package/dist/template-resolver/store-template-resource.d.ts +64 -0
  219. package/dist/template-resolver/store-template-resource.js +264 -0
  220. package/dist/template-resolver/table.d.ts +47 -8
  221. package/dist/template-resolver/table.js +11 -0
  222. package/dist/template-resolver/template-bundle.d.ts +36 -0
  223. package/dist/template-resolver/template-bundle.js +60 -0
  224. package/dist/template-resolver/template-diff.d.ts +7 -0
  225. package/dist/template-resolver/template-diff.js +68 -0
  226. package/dist/template-resolver/template-meta.d.ts +60 -0
  227. package/dist/template-resolver/template-meta.js +101 -0
  228. package/dist/template-resolver/template-preview.d.ts +86 -0
  229. package/dist/template-resolver/template-preview.js +374 -0
  230. package/dist/template-resolver/template-resources.d.ts +14 -0
  231. package/dist/template-resolver/template-resources.js +42 -0
  232. package/dist/template-resolver/template-usage.d.ts +12 -0
  233. package/dist/template-resolver/template-usage.js +30 -0
  234. package/dist/template-resolver/template-validation.d.ts +22 -0
  235. package/dist/template-resolver/template-validation.js +172 -0
  236. package/dist/template-resolver/testing.js +5 -5
  237. package/dist/template-resolver/user-content-table.d.ts +14 -8
  238. package/dist/template-resolver/web/client-plugin.d.ts +1 -0
  239. package/dist/template-resolver/web/client-plugin.js +9 -6
  240. package/dist/template-resolver/web/document-editor-extensions.d.ts +15 -0
  241. package/dist/template-resolver/web/document-editor-extensions.js +107 -0
  242. package/dist/template-resolver/web/document-editor.d.ts +3 -0
  243. package/dist/template-resolver/web/document-editor.js +11 -0
  244. package/dist/template-resolver/web/document-tiptap-editor.d.ts +3 -0
  245. package/dist/template-resolver/web/document-tiptap-editor.js +376 -0
  246. package/dist/template-resolver/web/document-toolbar-blocks.d.ts +33 -0
  247. package/dist/template-resolver/web/document-toolbar-blocks.js +15 -0
  248. package/dist/template-resolver/web/editor-handle.d.ts +3 -0
  249. package/dist/template-resolver/web/editor-handle.js +24 -0
  250. package/dist/template-resolver/web/i18n.js +76 -0
  251. package/dist/template-resolver/web/index.d.ts +4 -0
  252. package/dist/template-resolver/web/index.js +4 -0
  253. package/dist/template-resolver/web/placeholder-line-editor-lazy.d.ts +4 -0
  254. package/dist/template-resolver/web/placeholder-line-editor-lazy.js +16 -0
  255. package/dist/template-resolver/web/placeholder-line-editor.d.ts +15 -0
  256. package/dist/template-resolver/web/placeholder-line-editor.js +94 -0
  257. package/dist/template-resolver/web/placeholder-text.d.ts +4 -0
  258. package/dist/template-resolver/web/placeholder-text.js +34 -0
  259. package/dist/template-resolver/web/use-stable-by-key.d.ts +1 -0
  260. package/dist/template-resolver/web/use-stable-by-key.js +13 -0
  261. package/dist/tenant/handlers/team-list.query.js +3 -2
  262. package/dist/tenant/seeding.js +31 -6
  263. package/dist/tenant-lifecycle/handlers/cancel-destruction.write.d.ts +1 -1
  264. package/dist/tenant-lifecycle/handlers/cancel-destruction.write.js +2 -1
  265. package/dist/user/db/queries/stream-tenant-backfill.js +4 -4
  266. package/dist/user/handlers/detail.query.js +2 -1
  267. package/dist/user-data-rights/db/queries/forget-cleanup.d.ts +2 -2
  268. package/dist/user-data-rights/email-templates.d.ts +1 -29
  269. package/dist/user-data-rights/email-templates.js +5 -106
  270. package/dist/user-data-rights/feature.js +53 -35
  271. package/dist/user-data-rights/handlers/cancel-deletion.write.d.ts +1 -1
  272. package/dist/user-data-rights/handlers/cancel-deletion.write.js +2 -1
  273. package/dist/user-data-rights/handlers/request-deletion.write.js +5 -7
  274. package/dist/user-data-rights/lib/default-mailers.d.ts +15 -7
  275. package/dist/user-data-rights/lib/default-mailers.js +100 -48
  276. package/dist/user-data-rights/lib/update-user-lifecycle.js +1 -1
  277. package/dist/user-data-rights/mail-notifications.d.ts +13 -0
  278. package/dist/user-data-rights/mail-notifications.js +118 -0
  279. package/dist/user-data-rights/web/privacy-center-screen.js +2 -1
  280. package/dist/user-profile/web/profile-screen.js +2 -1
  281. package/dist/waitlist/feature.js +10 -0
  282. package/dist/waitlist/handlers/submit.write.js +3 -4
  283. package/dist/waitlist/mail.d.ts +19 -6
  284. package/dist/waitlist/mail.js +50 -14
  285. package/package.json +28 -17
  286. package/src/admin-shell/changes.json +6 -0
  287. package/src/auth-email-password/changes.json +14 -0
  288. package/src/billing-foundation/changes.json +7 -0
  289. package/src/channel-email/changes.json +19 -0
  290. package/src/data-retention/changes.json +6 -0
  291. package/src/delivery/changes.json +48 -0
  292. package/src/managed-pages/changes.json +6 -0
  293. package/src/renderer-foundation/changes.json +39 -0
  294. package/src/template-resolver/changes.json +118 -0
  295. package/src/user-data-rights/changes.json +7 -0
  296. package/src/waitlist/changes.json +7 -0
  297. package/dist/renderer-simple/feature.d.ts +0 -10
  298. package/dist/renderer-simple/feature.js +0 -42
  299. package/dist/renderer-simple/index.d.ts +0 -3
  300. package/dist/renderer-simple/index.js +0 -2
  301. package/dist/renderer-simple/mail-blocks.d.ts +0 -21
  302. package/dist/renderer-simple/mail-blocks.js +0 -107
  303. package/dist/renderer-simple/resolve-variables.d.ts +0 -7
  304. package/dist/renderer-simple/resolve-variables.js +0 -47
  305. package/dist/renderer-simple/simple-renderer.d.ts +0 -24
  306. package/dist/renderer-simple/simple-renderer.js +0 -200
  307. package/src/renderer-simple/changes.json +0 -27
@@ -37,7 +37,7 @@ export async function assertConsumerHandlesNotFound(consumer, opts) {
37
37
  await consumer.resolve({
38
38
  tenantId,
39
39
  slug,
40
- kind: "mail-html",
40
+ kind: "mail",
41
41
  locale: "de",
42
42
  });
43
43
  }
@@ -60,7 +60,7 @@ export async function assertConsumerRespectsLocaleFallback(consumer, opts) {
60
60
  await seedTemplate(db, {
61
61
  tenantId: SYSTEM_TENANT_ID,
62
62
  slug,
63
- kind: "notification",
63
+ kind: "document-pdf",
64
64
  locale: FALLBACK_LOCALE,
65
65
  scope: "system",
66
66
  content: "conformance-fallback-content",
@@ -68,7 +68,7 @@ export async function assertConsumerRespectsLocaleFallback(consumer, opts) {
68
68
  const result = await consumer.resolve({
69
69
  tenantId,
70
70
  slug,
71
- kind: "notification",
71
+ kind: "document-pdf",
72
72
  locale: "tr",
73
73
  });
74
74
  if (result.locale !== FALLBACK_LOCALE) {
@@ -89,7 +89,7 @@ export async function assertConsumerHandlesMissingResourceKeys(consumer, opts) {
89
89
  await seedTemplate(db, {
90
90
  tenantId: SYSTEM_TENANT_ID,
91
91
  slug,
92
- kind: "mail-html",
92
+ kind: "mail",
93
93
  locale: "de",
94
94
  scope: "system",
95
95
  linkedResources: { logo: "file_missing" },
@@ -97,7 +97,7 @@ export async function assertConsumerHandlesMissingResourceKeys(consumer, opts) {
97
97
  const template = await consumer.resolve({
98
98
  tenantId,
99
99
  slug,
100
- kind: "mail-html",
100
+ kind: "mail",
101
101
  locale: "de",
102
102
  });
103
103
  try {
@@ -49,26 +49,29 @@ export declare const userContentEntryEntity: import("@cosmicdrift/kumiko-types/f
49
49
  kind: {
50
50
  readonly type: "select";
51
51
  readonly description?: string;
52
- readonly options: readonly ["notification", "mail-html", "document-pdf", "image-snapshot", "text-block", "ai-prompt"];
52
+ readonly options: readonly ["mail", "document-pdf", "image-snapshot", "notification", "text-block", "snippet", "ai-prompt", "mail-layout", "pdf-layout"];
53
53
  readonly required?: boolean;
54
54
  readonly sortable?: boolean;
55
55
  readonly filterable?: boolean;
56
56
  readonly sensitive?: boolean;
57
- readonly default?: "ai-prompt" | "document-pdf" | "image-snapshot" | "mail-html" | "notification" | "text-block" | undefined;
57
+ readonly default?: "ai-prompt" | "document-pdf" | "image-snapshot" | "mail" | "mail-layout" | "notification" | "pdf-layout" | "snippet" | "text-block" | undefined;
58
58
  readonly access?: import("@cosmicdrift/kumiko-types/fields").FieldAccess;
59
59
  readonly display?: "radio" | "dropdown";
60
60
  readonly optionTones?: {
61
61
  readonly "ai-prompt"?: "bad" | "neutral" | "ok" | "warn" | undefined;
62
62
  readonly "document-pdf"?: "bad" | "neutral" | "ok" | "warn" | undefined;
63
63
  readonly "image-snapshot"?: "bad" | "neutral" | "ok" | "warn" | undefined;
64
- readonly "mail-html"?: "bad" | "neutral" | "ok" | "warn" | undefined;
64
+ readonly mail?: "bad" | "neutral" | "ok" | "warn" | undefined;
65
+ readonly "mail-layout"?: "bad" | "neutral" | "ok" | "warn" | undefined;
65
66
  readonly notification?: "bad" | "neutral" | "ok" | "warn" | undefined;
67
+ readonly "pdf-layout"?: "bad" | "neutral" | "ok" | "warn" | undefined;
68
+ readonly snippet?: "bad" | "neutral" | "ok" | "warn" | undefined;
66
69
  readonly "text-block"?: "bad" | "neutral" | "ok" | "warn" | undefined;
67
70
  } | undefined;
68
71
  readonly optionsQuery?: string;
69
72
  readonly optionsQueryPayload?: import("@cosmicdrift/kumiko-types/fields").OptionsQueryPayload;
70
73
  readonly optionsAvailabilityQuery?: string;
71
- readonly conditionalOptions?: readonly import("@cosmicdrift/kumiko-types/fields").SelectConditionalOptions<"ai-prompt" | "document-pdf" | "image-snapshot" | "mail-html" | "notification" | "text-block">[] | undefined;
74
+ readonly conditionalOptions?: readonly import("@cosmicdrift/kumiko-types/fields").SelectConditionalOptions<"ai-prompt" | "document-pdf" | "image-snapshot" | "mail" | "mail-layout" | "notification" | "pdf-layout" | "snippet" | "text-block">[] | undefined;
72
75
  } & import("@cosmicdrift/kumiko-types/fields").ResolvedPiiFlags & {
73
76
  required: true;
74
77
  };
@@ -232,26 +235,29 @@ export declare const userContentEntriesTable: import("@cosmicdrift/kumiko-framew
232
235
  kind: {
233
236
  readonly type: "select";
234
237
  readonly description?: string;
235
- readonly options: readonly ["notification", "mail-html", "document-pdf", "image-snapshot", "text-block", "ai-prompt"];
238
+ readonly options: readonly ["mail", "document-pdf", "image-snapshot", "notification", "text-block", "snippet", "ai-prompt", "mail-layout", "pdf-layout"];
236
239
  readonly required?: boolean;
237
240
  readonly sortable?: boolean;
238
241
  readonly filterable?: boolean;
239
242
  readonly sensitive?: boolean;
240
- readonly default?: "ai-prompt" | "document-pdf" | "image-snapshot" | "mail-html" | "notification" | "text-block" | undefined;
243
+ readonly default?: "ai-prompt" | "document-pdf" | "image-snapshot" | "mail" | "mail-layout" | "notification" | "pdf-layout" | "snippet" | "text-block" | undefined;
241
244
  readonly access?: import("@cosmicdrift/kumiko-types/fields").FieldAccess;
242
245
  readonly display?: "radio" | "dropdown";
243
246
  readonly optionTones?: {
244
247
  readonly "ai-prompt"?: "bad" | "neutral" | "ok" | "warn" | undefined;
245
248
  readonly "document-pdf"?: "bad" | "neutral" | "ok" | "warn" | undefined;
246
249
  readonly "image-snapshot"?: "bad" | "neutral" | "ok" | "warn" | undefined;
247
- readonly "mail-html"?: "bad" | "neutral" | "ok" | "warn" | undefined;
250
+ readonly mail?: "bad" | "neutral" | "ok" | "warn" | undefined;
251
+ readonly "mail-layout"?: "bad" | "neutral" | "ok" | "warn" | undefined;
248
252
  readonly notification?: "bad" | "neutral" | "ok" | "warn" | undefined;
253
+ readonly "pdf-layout"?: "bad" | "neutral" | "ok" | "warn" | undefined;
254
+ readonly snippet?: "bad" | "neutral" | "ok" | "warn" | undefined;
249
255
  readonly "text-block"?: "bad" | "neutral" | "ok" | "warn" | undefined;
250
256
  } | undefined;
251
257
  readonly optionsQuery?: string;
252
258
  readonly optionsQueryPayload?: import("@cosmicdrift/kumiko-types/fields").OptionsQueryPayload;
253
259
  readonly optionsAvailabilityQuery?: string;
254
- readonly conditionalOptions?: readonly import("@cosmicdrift/kumiko-types/fields").SelectConditionalOptions<"ai-prompt" | "document-pdf" | "image-snapshot" | "mail-html" | "notification" | "text-block">[] | undefined;
260
+ readonly conditionalOptions?: readonly import("@cosmicdrift/kumiko-types/fields").SelectConditionalOptions<"ai-prompt" | "document-pdf" | "image-snapshot" | "mail" | "mail-layout" | "notification" | "pdf-layout" | "snippet" | "text-block">[] | undefined;
255
261
  } & import("@cosmicdrift/kumiko-types/fields").ResolvedPiiFlags & {
256
262
  required: true;
257
263
  };
@@ -9,6 +9,7 @@ export type BlockSummary = {
9
9
  readonly modifiedAt: string | null;
10
10
  };
11
11
  export declare function groupBlocksByFolder(blocks: readonly BlockSummary[], tenantIdOverride?: string, collectionId?: string): readonly TreeNode[];
12
+ export declare function resolveWriteContentFormat(collectionContentFormat: string | undefined, loadedContentFormat: string | undefined): string | undefined;
12
13
  export declare function textBlocksClient(opts?: {
13
14
  readonly navId?: string;
14
15
  readonly tenantId?: string;
@@ -16,6 +16,7 @@ import { ContentPreview, useAppFeatures, useContentEditor, useDispatcher, usePri
16
16
  import { PlainContentEditor, RichContentEditor, } from "@cosmicdrift/kumiko-renderer-web";
17
17
  import { useEffect, useId, useState } from "react";
18
18
  import { collectionHandlerName, collectionQueryName, TemplateResolverHandlers, TemplateResolverQueries, } from "../qualified-names.js";
19
+ import { DocumentContentEditor } from "./document-editor.js";
19
20
  import { defaultTranslations } from "./i18n.js";
20
21
  function newFolderNode() {
21
22
  return { leaves: [], subFolders: new Map() };
@@ -163,19 +164,20 @@ function findContentFormat(features, collectionId) {
163
164
  function findVariableExamples(features, collectionId) {
164
165
  return findCollection(features, collectionId)?.variableSchema ?? {};
165
166
  }
166
- // The collection's declared contentFormat ("plain" | "rich" | "markdown",
167
- // see ContentCollectionDefinition.contentFormat) uses a different vocabulary
167
+ // The collection's declared contentFormat ("plain" | "rich" | "markdown" |
168
+ // "document", see ContentCollectionDefinition.contentFormat) uses a different vocabulary
168
169
  // than the stored entry's contentFormat ("plain" | "html" | "markdown" |
169
- // "mjml", see CONTENT_FORMATS) — "rich" always stores HTML. Without this,
170
+ // "mjml", see CONTENT_FORMATS) — "rich" and "document" always store HTML. Without this,
170
171
  // handleSave omitting contentFormat let the write schema's
171
172
  // contentFormatSchema.default("markdown") silently stamp every save as
172
173
  // markdown, clobbering e.g. a "plain" entry. Undefined (no collection, or
173
174
  // the collection didn't declare a format) keeps whatever was already saved
174
175
  // instead of guessing.
175
- function resolveWriteContentFormat(collectionContentFormat, loadedContentFormat) {
176
+ // Exported for the unit test — resolveWriteContentFormat is a pure function.
177
+ export function resolveWriteContentFormat(collectionContentFormat, loadedContentFormat) {
176
178
  if (collectionContentFormat === "plain")
177
179
  return "plain";
178
- if (collectionContentFormat === "rich")
180
+ if (collectionContentFormat === "rich" || collectionContentFormat === "document")
179
181
  return "html";
180
182
  if (collectionContentFormat === "markdown")
181
183
  return "markdown";
@@ -301,12 +303,13 @@ export function textBlocksClient(opts) {
301
303
  resolvers: {
302
304
  "template-resolver:edit": TextBlockEditor,
303
305
  },
304
- // The default for every "plain" collection (ai-prompt, mail-html without
306
+ // The default for every "plain" collection (ai-prompt, mail without
305
307
  // an explicit rich override) — an app-registered "plain" editor on
306
308
  // another clientFeature still wins, last-wins same as columnRenderers.
307
309
  contentEditors: {
308
310
  plain: PlainContentEditor,
309
311
  rich: RichContentEditor,
312
+ document: DocumentContentEditor,
310
313
  // ponytail: same textarea+chips as "plain" — markdown is stored as
311
314
  // text either way. Shares PlainContentEditor's fixed-DOM-id ceiling
312
315
  // (see its own file comment); swap for a live-preview widget or a
@@ -0,0 +1,15 @@
1
+ import type { Extensions, NodeViewRenderer } from "@tiptap/core";
2
+ import type { DocumentResourcePreview } from "./document-toolbar-blocks.js";
3
+ export type DocumentEditorLabels = {
4
+ readonly placeholder: string;
5
+ readonly image: string;
6
+ readonly pageBreak: string;
7
+ readonly button?: string;
8
+ readonly variableLabels?: Readonly<Record<string, string>>;
9
+ readonly systemVariables?: readonly string[];
10
+ readonly resourcePreviews?: Readonly<Record<string, DocumentResourcePreview>>;
11
+ /** Canvas chrome labels every block with its type. */
12
+ readonly blockLabels?: boolean;
13
+ };
14
+ export declare function createVariableView(variableLabels: Readonly<Record<string, string>>, systemVariables: readonly string[]): NodeViewRenderer;
15
+ export declare function createDocumentEditorExtensions(labels: DocumentEditorLabels): Extensions;
@@ -0,0 +1,107 @@
1
+ import { ListKeymap } from "@tiptap/extension-list";
2
+ import { Dropcursor, Gapcursor, Placeholder, UndoRedo } from "@tiptap/extensions";
3
+ import { DocumentButton, DocumentPageBreak, DocumentResource, DocumentVariable, documentExtensions, } from "../document-schema.js";
4
+ function createElementWithClass(tag, className, text) {
5
+ const element = document.createElement(tag);
6
+ element.className = className;
7
+ if (text !== undefined)
8
+ element.textContent = text;
9
+ return element;
10
+ }
11
+ const CHIP_CLASS = "mx-0.5 inline-flex items-center gap-1 rounded border px-1.5 py-0.5 text-xs";
12
+ const USER_CHIP_CLASS = `${CHIP_CLASS} border-primary/30 bg-primary/10 text-primary`;
13
+ const SYSTEM_CHIP_CLASS = `${CHIP_CLASS} border-input bg-muted text-muted-foreground`;
14
+ // The chip is display only: the stored node carries just the name, so a
15
+ // label never reaches the document.
16
+ export function createVariableView(variableLabels, systemVariables) {
17
+ return ({ node }) => {
18
+ const name = String(node.attrs["name"]);
19
+ const label = Object.hasOwn(variableLabels, name) ? variableLabels[name] : undefined;
20
+ const dom = createElementWithClass("span", systemVariables.includes(name) ? SYSTEM_CHIP_CLASS : USER_CHIP_CLASS);
21
+ dom.contentEditable = "false";
22
+ dom.append(document.createTextNode(label !== undefined && label !== "" ? label : name));
23
+ if (label !== undefined && label !== "" && label !== name) {
24
+ dom.append(createElementWithClass("small", "font-mono text-[10px] opacity-75", name));
25
+ }
26
+ return { dom };
27
+ };
28
+ }
29
+ // Same rule the sanitizer's image handling follows: previews never carry a
30
+ // scriptable scheme.
31
+ const PREVIEW_SRC = /^(data:image\/(png|jpeg|gif|webp);|blob:|https:\/\/|\/)/;
32
+ function createBlockLabel(text) {
33
+ const label = createElementWithClass("span", "absolute -top-2 left-2 bg-card px-1 text-[10px] font-medium uppercase tracking-wide text-muted-foreground", text);
34
+ label.contentEditable = "false";
35
+ return label;
36
+ }
37
+ function createResourceView(labels) {
38
+ return ({ node }) => {
39
+ const key = String(node.attrs["resource"]);
40
+ const previews = labels.resourcePreviews ?? {};
41
+ const preview = Object.hasOwn(previews, key) ? previews[key] : undefined;
42
+ const dom = createElementWithClass("div", "relative my-3 flex items-center gap-3 rounded border border-dashed border-input px-3 py-3 text-sm text-muted-foreground");
43
+ dom.contentEditable = "false";
44
+ if (labels.blockLabels)
45
+ dom.append(createBlockLabel(labels.image));
46
+ if (preview !== undefined && PREVIEW_SRC.test(preview.src)) {
47
+ const image = createElementWithClass("img", "max-h-16 max-w-48 rounded");
48
+ image.src = preview.src;
49
+ image.alt = typeof node.attrs["alt"] === "string" ? node.attrs["alt"] : key;
50
+ dom.append(image);
51
+ dom.append(createElementWithClass("span", "text-xs", preview.caption ?? key));
52
+ }
53
+ else {
54
+ dom.append(createElementWithClass("span", "font-medium", labels.image), createElementWithClass("code", "text-xs", key));
55
+ }
56
+ return { dom };
57
+ };
58
+ }
59
+ function createButtonView(buttonLabel) {
60
+ return () => {
61
+ const dom = createElementWithClass("div", "relative my-3 rounded border border-dashed border-input p-3");
62
+ const button = document.createElement("a");
63
+ button.setAttribute("data-button", "");
64
+ dom.append(createBlockLabel(buttonLabel), button);
65
+ return { dom, contentDOM: button };
66
+ };
67
+ }
68
+ function createPageBreakView(pageBreakLabel) {
69
+ return () => {
70
+ const dom = createElementWithClass("div", "my-3 border-t border-dashed border-input pt-1 text-center text-xs text-muted-foreground", pageBreakLabel);
71
+ dom.contentEditable = "false";
72
+ return { dom };
73
+ };
74
+ }
75
+ // Replaced by name, not appended: the schema must keep exactly one node per
76
+ // name, and only the editor view differs from the shared document schema.
77
+ export function createDocumentEditorExtensions(labels) {
78
+ const base = documentExtensions.map((extension) => {
79
+ switch (extension.name) {
80
+ case DocumentVariable.name:
81
+ return DocumentVariable.extend({
82
+ addNodeView: () => createVariableView(labels.variableLabels ?? {}, labels.systemVariables ?? []),
83
+ });
84
+ case DocumentResource.name:
85
+ return DocumentResource.extend({ addNodeView: () => createResourceView(labels) });
86
+ case DocumentButton.name:
87
+ return labels.blockLabels
88
+ ? DocumentButton.extend({ addNodeView: () => createButtonView(labels.button ?? "") })
89
+ : extension;
90
+ case DocumentPageBreak.name:
91
+ return DocumentPageBreak.extend({
92
+ addNodeView: () => createPageBreakView(labels.pageBreak),
93
+ });
94
+ default:
95
+ return extension;
96
+ }
97
+ });
98
+ // No TrailingNode: it appends an empty paragraph that breaks the HTML roundtrip.
99
+ return [
100
+ ...base,
101
+ UndoRedo,
102
+ Gapcursor,
103
+ Dropcursor,
104
+ ListKeymap,
105
+ Placeholder.configure({ placeholder: labels.placeholder }),
106
+ ];
107
+ }
@@ -0,0 +1,3 @@
1
+ import { type ReactNode } from "react";
2
+ import type { DocumentEditorProps } from "./document-toolbar-blocks.js";
3
+ export declare function DocumentContentEditor(props: DocumentEditorProps): ReactNode;
@@ -0,0 +1,11 @@
1
+ import { jsx as _jsx } from "react/jsx-runtime";
2
+ // @runtime client
3
+ //
4
+ // Lazy boundary: tiptap only loads when a "document" collection is rendered.
5
+ // Never import document-tiptap-editor or document-editor-extensions statically here.
6
+ import { TextareaContentEditor } from "@cosmicdrift/kumiko-renderer";
7
+ import { lazy, Suspense } from "react";
8
+ const LazyDocumentTiptapEditor = lazy(() => import("./document-tiptap-editor.js"));
9
+ export function DocumentContentEditor(props) {
10
+ return (_jsx(Suspense, { fallback: _jsx(TextareaContentEditor, { id: props.id, value: props.value, onChange: props.onChange, variables: props.variables, readOnly: props.readOnly }), children: _jsx(LazyDocumentTiptapEditor, { ...props }) }));
11
+ }
@@ -0,0 +1,3 @@
1
+ import { type ReactNode } from "react";
2
+ import { type DocumentEditorProps } from "./document-toolbar-blocks.js";
3
+ export default function DocumentTiptapEditor({ id, value, onChange, variables, readOnly, blocks, variableLabels, systemVariables, resourcePreviews, chrome, toolbar, onEditorReady, }: DocumentEditorProps): ReactNode;