@ketvietlab/ketjs 0.1.2 → 0.1.3

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 (299) hide show
  1. package/LICENSE +1 -1
  2. package/README.md +8 -2
  3. package/dist/agent/capabilities.d.ts +1 -3
  4. package/dist/agent/capabilities.d.ts.map +1 -1
  5. package/dist/agent/capabilities.js +10 -1
  6. package/dist/agent/capabilities.js.map +1 -1
  7. package/dist/agent/permissions.d.ts +43 -1
  8. package/dist/agent/permissions.d.ts.map +1 -1
  9. package/dist/agent/permissions.js +50 -2
  10. package/dist/agent/permissions.js.map +1 -1
  11. package/dist/cli.js +246 -97
  12. package/dist/cli.js.map +1 -1
  13. package/dist/codegen/dts.d.ts.map +1 -1
  14. package/dist/codegen/dts.js +1 -0
  15. package/dist/codegen/dts.js.map +1 -1
  16. package/dist/data/changeset.d.ts +12 -0
  17. package/dist/data/changeset.d.ts.map +1 -1
  18. package/dist/data/changeset.js +73 -17
  19. package/dist/data/changeset.js.map +1 -1
  20. package/dist/data/expr.d.ts +16 -0
  21. package/dist/data/expr.d.ts.map +1 -1
  22. package/dist/data/expr.js +33 -5
  23. package/dist/data/expr.js.map +1 -1
  24. package/dist/data/fleet.d.ts +41 -1
  25. package/dist/data/fleet.d.ts.map +1 -1
  26. package/dist/data/fleet.js +100 -11
  27. package/dist/data/fleet.js.map +1 -1
  28. package/dist/data/migrate.d.ts +20 -0
  29. package/dist/data/migrate.d.ts.map +1 -1
  30. package/dist/data/migrate.js +86 -3
  31. package/dist/data/migrate.js.map +1 -1
  32. package/dist/data/physical.d.ts +5 -0
  33. package/dist/data/physical.d.ts.map +1 -0
  34. package/dist/data/physical.js +196 -0
  35. package/dist/data/physical.js.map +1 -0
  36. package/dist/data/pool.d.ts +2 -1
  37. package/dist/data/pool.d.ts.map +1 -1
  38. package/dist/data/pool.js +159 -31
  39. package/dist/data/pool.js.map +1 -1
  40. package/dist/data/query.d.ts +10 -1
  41. package/dist/data/query.d.ts.map +1 -1
  42. package/dist/data/query.js +136 -27
  43. package/dist/data/query.js.map +1 -1
  44. package/dist/data/sqlite.d.ts.map +1 -1
  45. package/dist/data/sqlite.js +350 -52
  46. package/dist/data/sqlite.js.map +1 -1
  47. package/dist/data/time.d.ts +13 -0
  48. package/dist/data/time.d.ts.map +1 -1
  49. package/dist/data/time.js +61 -17
  50. package/dist/data/time.js.map +1 -1
  51. package/dist/index.d.ts +43 -22
  52. package/dist/index.d.ts.map +1 -1
  53. package/dist/index.js +32 -16
  54. package/dist/index.js.map +1 -1
  55. package/dist/kernel/audit.d.ts +27 -0
  56. package/dist/kernel/audit.d.ts.map +1 -0
  57. package/dist/kernel/audit.js +67 -0
  58. package/dist/kernel/audit.js.map +1 -0
  59. package/dist/kernel/classification.d.ts +26 -0
  60. package/dist/kernel/classification.d.ts.map +1 -0
  61. package/dist/kernel/classification.js +73 -0
  62. package/dist/kernel/classification.js.map +1 -0
  63. package/dist/kernel/compose.d.ts +6 -2
  64. package/dist/kernel/compose.d.ts.map +1 -1
  65. package/dist/kernel/compose.js +269 -15
  66. package/dist/kernel/compose.js.map +1 -1
  67. package/dist/kernel/define.d.ts +2 -3
  68. package/dist/kernel/define.d.ts.map +1 -1
  69. package/dist/kernel/define.js +22 -12
  70. package/dist/kernel/define.js.map +1 -1
  71. package/dist/kernel/diff.d.ts.map +1 -1
  72. package/dist/kernel/diff.js +28 -4
  73. package/dist/kernel/diff.js.map +1 -1
  74. package/dist/kernel/graph.js +1 -1
  75. package/dist/kernel/graph.js.map +1 -1
  76. package/dist/kernel/i18n.d.ts +10 -1
  77. package/dist/kernel/i18n.d.ts.map +1 -1
  78. package/dist/kernel/i18n.js +34 -1
  79. package/dist/kernel/i18n.js.map +1 -1
  80. package/dist/kernel/layout.d.ts +97 -0
  81. package/dist/kernel/layout.d.ts.map +1 -1
  82. package/dist/kernel/layout.js +294 -12
  83. package/dist/kernel/layout.js.map +1 -1
  84. package/dist/kernel/menu.d.ts +33 -2
  85. package/dist/kernel/menu.d.ts.map +1 -1
  86. package/dist/kernel/menu.js +99 -7
  87. package/dist/kernel/menu.js.map +1 -1
  88. package/dist/kernel/modules.d.ts +3 -3
  89. package/dist/kernel/modules.d.ts.map +1 -1
  90. package/dist/kernel/modules.js +21 -21
  91. package/dist/kernel/modules.js.map +1 -1
  92. package/dist/kernel/permissions.d.ts +10 -0
  93. package/dist/kernel/permissions.d.ts.map +1 -0
  94. package/dist/kernel/permissions.js +365 -0
  95. package/dist/kernel/permissions.js.map +1 -0
  96. package/dist/kernel/schedule.d.ts +23 -0
  97. package/dist/kernel/schedule.d.ts.map +1 -0
  98. package/dist/kernel/schedule.js +83 -0
  99. package/dist/kernel/schedule.js.map +1 -0
  100. package/dist/kernel/types.d.ts.map +1 -1
  101. package/dist/kernel/types.js +5 -4
  102. package/dist/kernel/types.js.map +1 -1
  103. package/dist/kernel/workspace.d.ts +92 -14
  104. package/dist/kernel/workspace.d.ts.map +1 -1
  105. package/dist/kernel/workspace.js +128 -49
  106. package/dist/kernel/workspace.js.map +1 -1
  107. package/dist/pdf/assets/Inter-Bold.ttf +0 -0
  108. package/dist/pdf/assets/Inter-Regular.ttf +0 -0
  109. package/dist/pdf/assets/Inter-SemiBold.ttf +0 -0
  110. package/dist/pdf/assets/LICENSE.txt +92 -0
  111. package/dist/pdf/font.d.ts +10 -0
  112. package/dist/pdf/font.d.ts.map +1 -0
  113. package/dist/pdf/font.js +83 -0
  114. package/dist/pdf/font.js.map +1 -0
  115. package/dist/pdf/image.d.ts +8 -0
  116. package/dist/pdf/image.d.ts.map +1 -0
  117. package/dist/pdf/image.js +94 -0
  118. package/dist/pdf/image.js.map +1 -0
  119. package/dist/pdf/index.d.ts +15 -0
  120. package/dist/pdf/index.d.ts.map +1 -0
  121. package/dist/pdf/index.js +17 -0
  122. package/dist/pdf/index.js.map +1 -0
  123. package/dist/pdf/markup.d.ts +19 -0
  124. package/dist/pdf/markup.d.ts.map +1 -0
  125. package/dist/pdf/markup.js +146 -0
  126. package/dist/pdf/markup.js.map +1 -0
  127. package/dist/pdf/render.d.ts +14 -0
  128. package/dist/pdf/render.d.ts.map +1 -0
  129. package/dist/pdf/render.js +387 -0
  130. package/dist/pdf/render.js.map +1 -0
  131. package/dist/scaffold/index.js +6 -6
  132. package/dist/scaffold/index.js.map +1 -1
  133. package/dist/scaffold/templates/{app.test.ts.tmpl → deployment.test.ts.tmpl} +3 -3
  134. package/dist/scaffold/templates/ket.workspace.ts.tmpl +4 -6
  135. package/dist/scaffold/templates/module.ts.tmpl +1 -4
  136. package/dist/server/assets.d.ts +23 -0
  137. package/dist/server/assets.d.ts.map +1 -0
  138. package/dist/server/assets.js +97 -0
  139. package/dist/server/assets.js.map +1 -0
  140. package/dist/server/boot.d.ts +157 -38
  141. package/dist/server/boot.d.ts.map +1 -1
  142. package/dist/server/boot.js +360 -138
  143. package/dist/server/boot.js.map +1 -1
  144. package/dist/server/config.d.ts +30 -10
  145. package/dist/server/config.d.ts.map +1 -1
  146. package/dist/server/config.js +73 -17
  147. package/dist/server/config.js.map +1 -1
  148. package/dist/server/ctx.d.ts +10 -0
  149. package/dist/server/ctx.d.ts.map +1 -1
  150. package/dist/server/ctx.js +266 -48
  151. package/dist/server/ctx.js.map +1 -1
  152. package/dist/server/development.d.ts +10 -0
  153. package/dist/server/development.d.ts.map +1 -0
  154. package/dist/server/development.js +15 -0
  155. package/dist/server/development.js.map +1 -0
  156. package/dist/server/fn.d.ts +22 -3
  157. package/dist/server/fn.d.ts.map +1 -1
  158. package/dist/server/fn.js +116 -32
  159. package/dist/server/fn.js.map +1 -1
  160. package/dist/server/form.d.ts +33 -0
  161. package/dist/server/form.d.ts.map +1 -0
  162. package/dist/server/form.js +47 -0
  163. package/dist/server/form.js.map +1 -0
  164. package/dist/server/http.d.ts +55 -3
  165. package/dist/server/http.d.ts.map +1 -1
  166. package/dist/server/http.js +306 -22
  167. package/dist/server/http.js.map +1 -1
  168. package/dist/server/idem.d.ts +3 -2
  169. package/dist/server/idem.d.ts.map +1 -1
  170. package/dist/server/idem.js +12 -4
  171. package/dist/server/idem.js.map +1 -1
  172. package/dist/server/jobs.js +1 -1
  173. package/dist/server/jobs.js.map +1 -1
  174. package/dist/server/log/combinators.d.ts +42 -0
  175. package/dist/server/log/combinators.d.ts.map +1 -0
  176. package/dist/server/log/combinators.js +270 -0
  177. package/dist/server/log/combinators.js.map +1 -0
  178. package/dist/server/log/console.d.ts +12 -0
  179. package/dist/server/log/console.d.ts.map +1 -0
  180. package/dist/server/log/console.js +96 -0
  181. package/dist/server/log/console.js.map +1 -0
  182. package/dist/server/log/file.d.ts +11 -0
  183. package/dist/server/log/file.d.ts.map +1 -0
  184. package/dist/server/log/file.js +61 -0
  185. package/dist/server/log/file.js.map +1 -0
  186. package/dist/server/log/index.d.ts +23 -0
  187. package/dist/server/log/index.d.ts.map +1 -0
  188. package/dist/server/log/index.js +45 -0
  189. package/dist/server/log/index.js.map +1 -0
  190. package/dist/server/log/logger.d.ts +53 -0
  191. package/dist/server/log/logger.d.ts.map +1 -0
  192. package/dist/server/log/logger.js +94 -0
  193. package/dist/server/log/logger.js.map +1 -0
  194. package/dist/server/log/memory.d.ts +11 -0
  195. package/dist/server/log/memory.d.ts.map +1 -0
  196. package/dist/server/log/memory.js +25 -0
  197. package/dist/server/log/memory.js.map +1 -0
  198. package/dist/server/log/types.d.ts +112 -0
  199. package/dist/server/log/types.d.ts.map +1 -0
  200. package/dist/server/log/types.js +58 -0
  201. package/dist/server/log/types.js.map +1 -0
  202. package/dist/server/policy.d.ts +29 -0
  203. package/dist/server/policy.d.ts.map +1 -0
  204. package/dist/server/policy.js +29 -0
  205. package/dist/server/policy.js.map +1 -0
  206. package/dist/server/queue.d.ts +1 -1
  207. package/dist/server/queue.d.ts.map +1 -1
  208. package/dist/server/queue.js.map +1 -1
  209. package/dist/server/ratelimit.d.ts +48 -0
  210. package/dist/server/ratelimit.d.ts.map +1 -0
  211. package/dist/server/ratelimit.js +102 -0
  212. package/dist/server/ratelimit.js.map +1 -0
  213. package/dist/server/respond.d.ts.map +1 -1
  214. package/dist/server/respond.js +16 -1
  215. package/dist/server/respond.js.map +1 -1
  216. package/dist/server/runtime.d.ts +18 -3
  217. package/dist/server/runtime.d.ts.map +1 -1
  218. package/dist/server/runtime.js +32 -2
  219. package/dist/server/runtime.js.map +1 -1
  220. package/dist/server/schedule.d.ts +18 -0
  221. package/dist/server/schedule.d.ts.map +1 -0
  222. package/dist/server/schedule.js +70 -0
  223. package/dist/server/schedule.js.map +1 -0
  224. package/dist/server/sequence.d.ts +42 -0
  225. package/dist/server/sequence.d.ts.map +1 -0
  226. package/dist/server/sequence.js +97 -0
  227. package/dist/server/sequence.js.map +1 -0
  228. package/dist/server/session.d.ts +21 -0
  229. package/dist/server/session.d.ts.map +1 -1
  230. package/dist/server/session.js +84 -10
  231. package/dist/server/session.js.map +1 -1
  232. package/dist/server/sessionstore.d.ts +3 -1
  233. package/dist/server/sessionstore.d.ts.map +1 -1
  234. package/dist/server/sessionstore.js +7 -3
  235. package/dist/server/sessionstore.js.map +1 -1
  236. package/dist/server/storage/index.d.ts +1 -1
  237. package/dist/server/storage/index.d.ts.map +1 -1
  238. package/dist/server/storage/index.js +61 -1
  239. package/dist/server/storage/index.js.map +1 -1
  240. package/dist/server/storage/types.d.ts +8 -0
  241. package/dist/server/storage/types.d.ts.map +1 -1
  242. package/dist/server/storage/types.js +58 -0
  243. package/dist/server/storage/types.js.map +1 -1
  244. package/dist/server/tenants.d.ts +20 -18
  245. package/dist/server/tenants.d.ts.map +1 -1
  246. package/dist/server/tenants.js +133 -84
  247. package/dist/server/tenants.js.map +1 -1
  248. package/dist/server/transport/types.js +2 -2
  249. package/dist/server/transport/types.js.map +1 -1
  250. package/dist/server/worker.d.ts +19 -3
  251. package/dist/server/worker.d.ts.map +1 -1
  252. package/dist/server/worker.js +168 -21
  253. package/dist/server/worker.js.map +1 -1
  254. package/dist/testing.d.ts +26 -10
  255. package/dist/testing.d.ts.map +1 -1
  256. package/dist/testing.js +41 -14
  257. package/dist/testing.js.map +1 -1
  258. package/dist/theme/contracts.d.ts +14 -1
  259. package/dist/theme/contracts.d.ts.map +1 -1
  260. package/dist/theme/contracts.js +35 -6
  261. package/dist/theme/contracts.js.map +1 -1
  262. package/dist/theme/index.d.ts +1 -1
  263. package/dist/theme/index.d.ts.map +1 -1
  264. package/dist/theme/index.js +1 -1
  265. package/dist/theme/index.js.map +1 -1
  266. package/dist/theme/joint-runtime.d.ts +33 -0
  267. package/dist/theme/joint-runtime.d.ts.map +1 -0
  268. package/dist/theme/joint-runtime.js +121 -0
  269. package/dist/theme/joint-runtime.js.map +1 -0
  270. package/dist/theme/joints.d.ts.map +1 -1
  271. package/dist/theme/joints.js +15 -97
  272. package/dist/theme/joints.js.map +1 -1
  273. package/dist/theme/ktl/compile.d.ts +4 -0
  274. package/dist/theme/ktl/compile.d.ts.map +1 -1
  275. package/dist/theme/ktl/compile.js +54 -1
  276. package/dist/theme/ktl/compile.js.map +1 -1
  277. package/dist/theme/ktl/parser.d.ts +4 -0
  278. package/dist/theme/ktl/parser.d.ts.map +1 -1
  279. package/dist/theme/ktl/parser.js +8 -0
  280. package/dist/theme/ktl/parser.js.map +1 -1
  281. package/dist/theme/render.d.ts +8 -0
  282. package/dist/theme/render.d.ts.map +1 -1
  283. package/dist/theme/render.js +88 -118
  284. package/dist/theme/render.js.map +1 -1
  285. package/dist/theme/tokens.d.ts +6 -0
  286. package/dist/theme/tokens.d.ts.map +1 -1
  287. package/dist/theme/tokens.js +6 -0
  288. package/dist/theme/tokens.js.map +1 -1
  289. package/dist/theme/viewmodel.d.ts +24 -0
  290. package/dist/theme/viewmodel.d.ts.map +1 -1
  291. package/dist/theme/viewmodel.js +75 -6
  292. package/dist/theme/viewmodel.js.map +1 -1
  293. package/dist/types.d.ts +304 -56
  294. package/dist/types.d.ts.map +1 -1
  295. package/package.json +6 -2
  296. package/dist/kernel/apps.d.ts +0 -43
  297. package/dist/kernel/apps.d.ts.map +0 -1
  298. package/dist/kernel/apps.js +0 -234
  299. package/dist/kernel/apps.js.map +0 -1
@@ -1,24 +1,15 @@
1
1
  // Rendering a page through a theme: templates are KTL, joints are filled by
2
2
  // whatever modules published fills for them, and the scope is a sealed set of drops.
3
3
  import { compileKtl } from './ktl/compile.js';
4
- import { renderIsland } from '@ketvietlab/ketjs-view';
5
4
  import { sealScope } from './viewmodel.js';
6
- import { contractProps } from './contracts.js';
5
+ import { sectionSettings } from './contracts.js';
6
+ import { assertFillReach, createJointWiring } from './joint-runtime.js';
7
+ import { tokensToCss } from './tokens.js';
7
8
  import { KetError } from '../kernel/errors.js';
8
9
  export function createTheme(manifest, modules, opts = {}) {
9
- // A theme is written against what the DEPLOYMENT ships, not against what a
10
- // particular database has switched on. So the strict check belongs to the full
11
- // manifest — where a typo is a build error — while a restricted manifest, which
12
- // is a runtime view, degrades to rendering nothing. Uninstalling an app must not
13
- // take the whole theme down with it.
14
- const atRuntime = manifest.disabledModules !== undefined;
15
- const off = new Set(manifest.disabledModules ?? []);
16
- const disabledSections = new Set(manifest.disabledSections ?? []);
17
10
  // Islands come from modules; the theme only names them.
18
11
  const islands = {};
19
12
  for (const m of modules) {
20
- if (off.has(m.name))
21
- continue;
22
13
  for (const [name, def] of Object.entries(m.islands))
23
14
  islands[name] = def.view;
24
15
  }
@@ -26,14 +17,34 @@ export function createTheme(manifest, modules, opts = {}) {
26
17
  .filter(([, island]) => island.client !== undefined)
27
18
  .map(([name, island]) => [name, island.client]));
28
19
  const sources = {};
20
+ const templateOwner = {};
21
+ // Tokens follow the templates exactly: whatever renders this page is what gets to
22
+ // name a colour. Reading manifest.tokens instead would hand a deployment with two
23
+ // themes installed the tokens of whichever one composed last.
24
+ const tokens = {};
29
25
  for (const m of modules) {
30
- if (off.has(m.name))
31
- continue; // a removed theme contributes no templates
32
26
  if (m.kind === 'theme' && opts.theme && m.name !== opts.theme)
33
27
  continue;
34
- for (const [name, src] of Object.entries(m.templates))
28
+ Object.assign(tokens, m.tokens);
29
+ for (const [name, src] of Object.entries(m.templates)) {
30
+ const previous = templateOwner[name];
31
+ // A theme overriding a module's template is the whole point of a theme. Two
32
+ // modules claiming one name is not an override, it is a collision, and it used
33
+ // to resolve silently by composition order — so which markup rendered depended
34
+ // on the dependency graph rather than on anybody's decision.
35
+ if (previous && previous.kind !== 'theme' && m.kind !== 'theme') {
36
+ throw new KetError({
37
+ code: 'E_TEMPLATE_DUPLICATE',
38
+ module: m.name,
39
+ message: `template "${name}" is already provided by "${previous.name}"`,
40
+ hint: 'rename one of them, or move the shared markup into a template both render',
41
+ });
42
+ }
43
+ templateOwner[name] = m;
35
44
  sources[name] = src;
45
+ }
36
46
  }
47
+ const tokensCss = Object.keys(tokens).length ? tokensToCss(tokens) : '';
37
48
  const fillSources = {};
38
49
  for (const fill of manifest.fills) {
39
50
  const owner = manifest.modules[fill.by];
@@ -43,40 +54,29 @@ export function createTheme(manifest, modules, opts = {}) {
43
54
  }
44
55
  const templates = {};
45
56
  const fills = {};
46
- const jointStack = [];
47
- const renderJoint = (joint, scope) => {
48
- const definition = manifest.joints[joint];
49
- if (!definition) {
50
- throw new KetError({
51
- code: 'E_TEMPLATE_UNKNOWN_JOINT',
52
- message: `renders joint "${joint}", which no installed module publishes`,
53
- });
54
- }
55
- if (definition.omittedBy.length)
56
- return '';
57
- if (jointStack.includes(joint)) {
58
- throw new KetError({
59
- code: 'E_JOINT_CYCLE',
60
- message: `joint recursion: ${[...jointStack, joint].join(' -> ')}`,
61
- hint: 'a fill may render another joint, but never itself through any chain',
62
- });
63
- }
64
- if (jointStack.length >= 16) {
65
- throw new KetError({ code: 'E_JOINT_TOO_DEEP', message: 'joint rendering exceeds 16 levels' });
66
- }
67
- jointStack.push(joint);
68
- try {
69
- const props = contractProps(manifest, 'joint', joint, definition.props, scope);
70
- return (fills[joint] ?? []).map((compiled) => compiled.render(props)).join('');
71
- }
72
- finally {
73
- jointStack.pop();
74
- }
75
- };
57
+ const wiring = createJointWiring(manifest, {
58
+ fillsFor: (joint) => fills[joint] ?? [],
59
+ islands,
60
+ });
61
+ /**
62
+ * Which placement is being rendered, so that a `slot` tag inside its template
63
+ * can find its children.
64
+ *
65
+ * A stack rather than a scope key: children are already-rendered markup, and
66
+ * a scope carries values a template may print. Putting markup where `{{ }}`
67
+ * can reach it would either escape it into visible tag soup or open a hole,
68
+ * and reserving a scope name would collide with a section that wanted it.
69
+ * Rendering is synchronous, so a stack is exact.
70
+ */
71
+ const openSlots = [];
76
72
  /**
77
73
  * A page's body is its layout: an ordered list of placements, each rendered by
78
74
  * the template named after its section type. The theme decides how a section
79
75
  * looks; the data decides which sections there are and in what order.
76
+ *
77
+ * A placement may carry children under the slot names its section declares.
78
+ * They render through this same path, so a nested section is rendered by the
79
+ * same template and checked against the same manifest as a top-level one.
80
80
  */
81
81
  const renderSectionsAt = (scope) => {
82
82
  const layout = scope['sections'];
@@ -88,41 +88,44 @@ export function createTheme(manifest, modules, opts = {}) {
88
88
  if (!placement?.type)
89
89
  continue;
90
90
  if (!manifest.sections[placement.type]) {
91
- // A page saved while an app was installed still names its sections after it
92
- // is removed. Skip those; re-installing brings them back with their data.
93
- if (atRuntime && disabledSections.has(placement.type))
94
- continue;
95
- if (atRuntime) {
96
- // Named by no app this deployment has ever shipped: leave a mark rather
97
- // than pretend the page was always this length.
98
- out.push(`<!-- ket: unknown section "${placement.type}" -->`);
99
- continue;
100
- }
101
91
  throw new KetError({
102
92
  code: 'E_UNKNOWN_SECTION',
103
- message: `the page places section "${placement.type}", which no installed module provides`,
93
+ message: `the page places section "${placement.type}", which no composed module provides`,
104
94
  hint: `available sections: ${Object.keys(manifest.sections).join(', ') || '(none)'}`,
105
95
  });
106
96
  }
107
- out.push(renderRegion(placement.type, { ...(placement.settings ?? {}), page: scope['page'] }));
97
+ const slots = placement.slots && typeof placement.slots === 'object' && !Array.isArray(placement.slots)
98
+ ? placement.slots
99
+ : {};
100
+ openSlots.push({ slots, page: scope['page'] });
101
+ try {
102
+ out.push(renderRegion(placement.type, {
103
+ ...sectionSettings(manifest.sections[placement.type]?.settings ?? {}, placement.settings ?? {}),
104
+ // The one key a section gets that is not one of its settings: which page
105
+ // it sits on. Declared nowhere because it is not the author's to declare.
106
+ page: scope['page'],
107
+ }));
108
+ }
109
+ finally {
110
+ openSlots.pop();
111
+ }
108
112
  }
109
113
  return out.join('');
110
114
  };
111
- const renderIslandAt = (name, scope) => {
112
- const factory = islands[name];
113
- const definition = manifest.islands[name];
114
- if (!factory || !definition) {
115
- if (atRuntime)
116
- return '';
117
- throw new KetError({
118
- code: 'E_UNKNOWN_ISLAND',
119
- message: `a template places island "${name}", which no installed module provides`,
120
- hint: `available islands: ${Object.keys(islands).join(', ') || '(none)'}`,
121
- });
122
- }
123
- return renderIsland(name, factory, contractProps(manifest, 'island', name, definition.props, scope), {
124
- key: definition.key,
125
- });
115
+ /**
116
+ * The children a placement put in one of its slots.
117
+ *
118
+ * An empty slot renders nothing rather than raising: a container with an
119
+ * empty column is an ordinary state of a page being built, not a fault. A
120
+ * slot the section never declared is caught at the write by validateLayout,
121
+ * which is where an author can still do something about it.
122
+ */
123
+ const renderSlotAt = (name, _scope) => {
124
+ const open = openSlots[openSlots.length - 1];
125
+ const children = open?.slots?.[name];
126
+ if (!Array.isArray(children) || !children.length)
127
+ return '';
128
+ return renderSectionsAt({ sections: children, page: open?.page });
126
129
  };
127
130
  const renderRegion = (name, scope) => {
128
131
  const t = templates[name];
@@ -147,7 +150,7 @@ export function createTheme(manifest, modules, opts = {}) {
147
150
  if (!t) {
148
151
  throw new KetError({
149
152
  code: 'E_TEMPLATE_NOT_FOUND',
150
- message: `${from} renders "${name}", which no installed module provides`,
153
+ message: `${from} renders "${name}", which no composed module provides`,
151
154
  hint: `available templates: ${Object.keys(templates).sort().join(', ') || '(none)'}`,
152
155
  });
153
156
  }
@@ -166,56 +169,23 @@ export function createTheme(manifest, modules, opts = {}) {
166
169
  depth--;
167
170
  }
168
171
  };
169
- const wiring = {
170
- renderJoint,
172
+ const compileOpts = {
173
+ renderJoint: wiring.renderJoint,
174
+ renderIsland: wiring.renderIsland,
171
175
  renderRegion,
172
- renderIsland: renderIslandAt,
173
176
  renderSections: renderSectionsAt,
177
+ renderSlot: renderSlotAt,
174
178
  renderTemplate,
175
179
  };
176
180
  for (const [joint, sourcesForJoint] of Object.entries(fillSources)) {
177
181
  fills[joint] = sourcesForJoint.map((fill, i) => {
178
- const compiled = compileKtl(fill.template, { ...opts, name: `${joint}#${i}`, ...wiring });
179
- const module = manifest.modules[fill.by];
180
- for (const used of compiled.jointsUsed) {
181
- const target = manifest.joints[used];
182
- if (!target) {
183
- throw new KetError({
184
- code: 'E_FILL_UNKNOWN_JOINT',
185
- module: fill.by,
186
- message: `fill for "${joint}" renders unknown joint "${used}"`,
187
- });
188
- }
189
- if (target.owner !== fill.by && !module?.depends?.includes(target.owner)) {
190
- throw new KetError({
191
- code: 'E_FILL_NOT_DEPENDED',
192
- module: fill.by,
193
- message: `fill for "${joint}" renders "${used}" without depending on "${target.owner}"`,
194
- });
195
- }
196
- }
197
- for (const used of compiled.islandsUsed) {
198
- const target = manifest.islands[used];
199
- if (!target) {
200
- throw new KetError({
201
- code: 'E_FILL_UNKNOWN_ISLAND',
202
- module: fill.by,
203
- message: `fill for "${joint}" places unknown island "${used}"`,
204
- });
205
- }
206
- if (target.by !== fill.by && !module?.depends?.includes(target.by)) {
207
- throw new KetError({
208
- code: 'E_FILL_NOT_DEPENDED',
209
- module: fill.by,
210
- message: `fill for "${joint}" places "${used}" without depending on "${target.by}"`,
211
- });
212
- }
213
- }
214
- return compiled;
182
+ const compiled = compileKtl(fill.template, { ...opts, name: `${joint}#${i}`, ...compileOpts });
183
+ assertFillReach(manifest, { joint, by: fill.by }, compiled);
184
+ return { by: fill.by, compiled };
215
185
  });
216
186
  }
217
187
  for (const [name, src] of Object.entries(sources)) {
218
- templates[name] = compileKtl(src, { ...opts, name, ...wiring });
188
+ templates[name] = compileKtl(src, { ...opts, name, ...compileOpts });
219
189
  }
220
190
  // A theme that points at a joint nobody publishes is a build error, not a blank spot.
221
191
  for (const [name, t] of Object.entries(templates)) {
@@ -223,7 +193,7 @@ export function createTheme(manifest, modules, opts = {}) {
223
193
  if (!manifest.joints[j]) {
224
194
  throw new KetError({
225
195
  code: 'E_TEMPLATE_UNKNOWN_JOINT',
226
- message: `template "${name}" renders joint "${j}", which no installed module publishes`,
196
+ message: `template "${name}" renders joint "${j}", which no composed module publishes`,
227
197
  hint: `published joints: ${Object.keys(manifest.joints).join(', ') || '(none)'}`,
228
198
  });
229
199
  }
@@ -231,16 +201,16 @@ export function createTheme(manifest, modules, opts = {}) {
231
201
  }
232
202
  // Placing an island nobody provides is a build error, exactly like a missing joint.
233
203
  for (const [name, t] of Object.entries(templates)) {
234
- for (const island of atRuntime ? [] : t.islandsUsed) {
204
+ for (const island of t.islandsUsed) {
235
205
  if (!manifest.islands[island]) {
236
206
  throw new KetError({
237
207
  code: 'E_TEMPLATE_UNKNOWN_ISLAND',
238
- message: `template "${name}" places island "${island}", which no installed module provides`,
208
+ message: `template "${name}" places island "${island}", which no composed module provides`,
239
209
  hint: `provided islands: ${Object.keys(manifest.islands).join(', ') || '(none)'}`,
240
210
  });
241
211
  }
242
212
  }
243
213
  }
244
- return { renderRegion, templates, islands, clients };
214
+ return { renderRegion, templates, islands, clients, tokensCss };
245
215
  }
246
216
  //# sourceMappingURL=render.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"render.js","sourceRoot":"","sources":["../../../../../../packages/ketjs/src/theme/render.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"render.js","sourceRoot":"","sources":["../../../../../../packages/ketjs/src/theme/render.ts"],"names":[],"mappings":"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"}
@@ -1,4 +1,10 @@
1
1
  export declare const LAYER_ORDER: readonly ['ket.reset', 'ket.theme', 'ket.app', 'ket.user'];
2
+ /**
3
+ * The statement that fixes the order, for the document to emit before the first
4
+ * stylesheet loads. `@layer a, b, c;` establishes precedence on its own; where the
5
+ * layers are then written no longer matters.
6
+ */
7
+ export declare const LAYER_ORDER_CSS: string;
2
8
  export declare function tokensToCss(tokens: Record<string, string>, layer?: (typeof LAYER_ORDER)[number]): string;
3
9
  export declare function scopedCss(section: string, css: string): string;
4
10
  //# sourceMappingURL=tokens.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"tokens.d.ts","sourceRoot":"","sources":["../../../../../packages/ketjs/src/theme/tokens.ts"],"names":[],"mappings":"AAKA,eAAO,MAAM,WAAW,YAAI,WAAW,EAAE,WAAW,EAAE,SAAS,EAAE,UAAU,CAAU,CAAA;AAErF,wBAAgB,WAAW,CACzB,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,EAC9B,KAAK,GAAE,CAAC,OAAO,WAAW,CAAC,CAAC,MAAM,CAAe,GAChD,MAAM,CAKR;AAED,wBAAgB,SAAS,CAAC,OAAO,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,GAAG,MAAM,CAE9D"}
1
+ {"version":3,"file":"tokens.d.ts","sourceRoot":"","sources":["../../../../../packages/ketjs/src/theme/tokens.ts"],"names":[],"mappings":"AAKA,eAAO,MAAM,WAAW,YAAI,WAAW,EAAE,WAAW,EAAE,SAAS,EAAE,UAAU,CAAU,CAAA;AAErF;;;;GAIG;AACH,eAAO,MAAM,eAAe,QAAsC,CAAA;AAElE,wBAAgB,WAAW,CACzB,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,EAC9B,KAAK,GAAE,CAAC,OAAO,WAAW,CAAC,CAAC,MAAM,CAAe,GAChD,MAAM,CAKR;AAED,wBAAgB,SAAS,CAAC,OAAO,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,GAAG,MAAM,CAE9D"}
@@ -3,6 +3,12 @@
3
3
  // ket.reset < ket.theme < ket.app < ket.user
4
4
  // Native CSS only — no preprocessor, no CSS-in-JS, nothing to install.
5
5
  export const LAYER_ORDER = ['ket.reset', 'ket.theme', 'ket.app', 'ket.user'];
6
+ /**
7
+ * The statement that fixes the order, for the document to emit before the first
8
+ * stylesheet loads. `@layer a, b, c;` establishes precedence on its own; where the
9
+ * layers are then written no longer matters.
10
+ */
11
+ export const LAYER_ORDER_CSS = `@layer ${LAYER_ORDER.join(', ')};`;
6
12
  export function tokensToCss(tokens, layer = 'ket.theme') {
7
13
  const decls = Object.entries(tokens)
8
14
  .map(([k, v]) => ` --ket-${k.replace(/[^a-zA-Z0-9-]/g, '-')}: ${v};`)
@@ -1 +1 @@
1
- {"version":3,"file":"tokens.js","sourceRoot":"","sources":["../../../../../../packages/ketjs/src/theme/tokens.ts"],"names":[],"mappings":"AAAA,iFAAiF;AACjF,4EAA4E;AAC5E,+CAA+C;AAC/C,uEAAuE;AAEvE,MAAM,CAAC,MAAM,WAAW,GAAG,CAAC,WAAW,EAAE,WAAW,EAAE,SAAS,EAAE,UAAU,CAAU,CAAA;AAErF,MAAM,UAAU,WAAW,CACzB,MAA8B,EAC9B,KAAK,GAAiC,WAAW;IAEjD,MAAM,KAAK,GAAG,MAAM,CAAC,OAAO,CAAC,MAAM,CAAC;SACjC,GAAG,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,WAAW,CAAC,CAAC,OAAO,CAAC,gBAAgB,EAAE,GAAG,CAAC,KAAK,CAAC,GAAG,CAAC;SACrE,IAAI,CAAC,IAAI,CAAC,CAAA;IACb,OAAO,UAAU,WAAW,CAAC,IAAI,CAAC,IAAI,CAAC,eAAe,KAAK,kBAAkB,KAAK,YAAY,CAAA;AAChG,CAAC;AAED,MAAM,UAAU,SAAS,CAAC,OAAe,EAAE,GAAW;IACpD,OAAO,oDAAoD,OAAO,UAAU,GAAG,YAAY,CAAA;AAC7F,CAAC"}
1
+ {"version":3,"file":"tokens.js","sourceRoot":"","sources":["../../../../../../packages/ketjs/src/theme/tokens.ts"],"names":[],"mappings":"AAAA,iFAAiF;AACjF,4EAA4E;AAC5E,+CAA+C;AAC/C,uEAAuE;AAEvE,MAAM,CAAC,MAAM,WAAW,GAAG,CAAC,WAAW,EAAE,WAAW,EAAE,SAAS,EAAE,UAAU,CAAU,CAAA;AAErF;;;;GAIG;AACH,MAAM,CAAC,MAAM,eAAe,GAAG,UAAU,WAAW,CAAC,IAAI,CAAC,IAAI,CAAC,GAAG,CAAA;AAElE,MAAM,UAAU,WAAW,CACzB,MAA8B,EAC9B,KAAK,GAAiC,WAAW;IAEjD,MAAM,KAAK,GAAG,MAAM,CAAC,OAAO,CAAC,MAAM,CAAC;SACjC,GAAG,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,EAAE,CAAC,WAAW,CAAC,CAAC,OAAO,CAAC,gBAAgB,EAAE,GAAG,CAAC,KAAK,CAAC,GAAG,CAAC;SACrE,IAAI,CAAC,IAAI,CAAC,CAAA;IACb,OAAO,UAAU,WAAW,CAAC,IAAI,CAAC,IAAI,CAAC,eAAe,KAAK,kBAAkB,KAAK,YAAY,CAAA;AAChG,CAAC;AAED,MAAM,UAAU,SAAS,CAAC,OAAe,EAAE,GAAW;IACpD,OAAO,oDAAoD,OAAO,UAAU,GAAG,YAAY,CAAA;AAC7F,CAAC"}
@@ -1,6 +1,30 @@
1
1
  import type { Manifest, Row } from '../types.ts';
2
2
  export type Drop = Record<string, unknown>;
3
+ /** The projection itself, once the fields have been decided. */
4
+ export declare function projectFields(row: Row, fields: readonly string[]): Drop;
3
5
  export declare function makeDrop(manifest: Manifest, viewKey: string, row: Row): Drop;
6
+ /**
7
+ * Which fields of a view-typed prop one module may read: the ones the view's owner
8
+ * declared, plus the ones that module declared itself over the same model.
9
+ *
10
+ * Not simply the named view. A module that adds a field with `extend` and then
11
+ * publishes a view over it has declared that field theme-visible, and it is the one
12
+ * module entitled to say so — refusing it here would mean the extension pillar and
13
+ * the view boundary could not both be true, and `inventory` adding `leadTimeDays`
14
+ * to `catalog.Product` and reading it back in a fill is the example the framework
15
+ * leads with. What still cannot cross is a field nobody declared anywhere.
16
+ */
17
+ export declare function visibleFields(manifest: Manifest, viewKey: string, reader?: string): readonly string[];
4
18
  export declare function makeDrops(manifest: Manifest, viewKey: string, rows: Row[]): Drop[];
19
+ /**
20
+ * Where a function hides inside a value, as a readable path, or null when there is
21
+ * none.
22
+ *
23
+ * One walker, because "a theme receives data only" has to mean the same thing at
24
+ * every door into a theme. It used to be checked one level deep at the region door
25
+ * and recursively at the joint door, so `{ order: { total: () => … } }` was refused
26
+ * by one and waved through by the other.
27
+ */
28
+ export declare function findCallable(value: unknown, path?: string, seen?: WeakSet<object>): string | null;
5
29
  export declare function sealScope(scope: Record<string, unknown>): Record<string, unknown>;
6
30
  //# sourceMappingURL=viewmodel.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"viewmodel.d.ts","sourceRoot":"","sources":["../../../../../packages/ketjs/src/theme/viewmodel.ts"],"names":[],"mappings":"AAOA,OAAO,KAAK,EAAE,QAAQ,EAAE,GAAG,EAAE,MAAM,aAAa,CAAA;AAEhD,MAAM,MAAM,IAAI,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAA;AAE1C,wBAAgB,QAAQ,CAAC,QAAQ,EAAE,QAAQ,EAAE,OAAO,EAAE,MAAM,EAAE,GAAG,EAAE,GAAG,GAAG,IAAI,CAY5E;AAED,wBAAgB,SAAS,CAAC,QAAQ,EAAE,QAAQ,EAAE,OAAO,EAAE,MAAM,EAAE,IAAI,EAAE,GAAG,EAAE,GAAG,IAAI,EAAE,CAElF;AAID,wBAAgB,SAAS,CAAC,KAAK,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAajF"}
1
+ {"version":3,"file":"viewmodel.d.ts","sourceRoot":"","sources":["../../../../../packages/ketjs/src/theme/viewmodel.ts"],"names":[],"mappings":"AAOA,OAAO,KAAK,EAAE,QAAQ,EAAE,GAAG,EAAE,MAAM,aAAa,CAAA;AAEhD,MAAM,MAAM,IAAI,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAA;AAE1C,gEAAgE;AAChE,wBAAgB,aAAa,CAAC,GAAG,EAAE,GAAG,EAAE,MAAM,EAAE,SAAS,MAAM,EAAE,GAAG,IAAI,CAIvE;AAED,wBAAgB,QAAQ,CAAC,QAAQ,EAAE,QAAQ,EAAE,OAAO,EAAE,MAAM,EAAE,GAAG,EAAE,GAAG,GAAG,IAAI,CAU5E;AAED;;;;;;;;;;GAUG;AACH,wBAAgB,aAAa,CAAC,QAAQ,EAAE,QAAQ,EAAE,OAAO,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE,MAAM,GAAG,SAAS,MAAM,EAAE,CAQrG;AAED,wBAAgB,SAAS,CAAC,QAAQ,EAAE,QAAQ,EAAE,OAAO,EAAE,MAAM,EAAE,IAAI,EAAE,GAAG,EAAE,GAAG,IAAI,EAAE,CAElF;AAED;;;;;;;;GAQG;AACH,wBAAgB,YAAY,CAAC,KAAK,EAAE,OAAO,EAAE,IAAI,SAAK,EAAE,IAAI,kBAAwB,GAAG,MAAM,GAAG,IAAI,CAuBnG;AAID,wBAAgB,SAAS,CAAC,KAAK,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAcjF"}
@@ -4,6 +4,13 @@
4
4
  // module declared in `views`. The ORM, the adapter and every server function stay
5
5
  // on the other side of this boundary — a theme literally has no reference to reach.
6
6
  import { KetError } from '../kernel/errors.js';
7
+ /** The projection itself, once the fields have been decided. */
8
+ export function projectFields(row, fields) {
9
+ const drop = Object.create(null);
10
+ for (const f of fields)
11
+ drop[f] = row[f] ?? null;
12
+ return Object.freeze(drop);
13
+ }
7
14
  export function makeDrop(manifest, viewKey, row) {
8
15
  const view = manifest.views[viewKey];
9
16
  if (!view) {
@@ -13,23 +20,85 @@ export function makeDrop(manifest, viewKey, row) {
13
20
  hint: `declared views: ${Object.keys(manifest.views).join(', ') || '(none)'}`,
14
21
  });
15
22
  }
16
- const drop = Object.create(null);
17
- for (const f of view.fields)
18
- drop[f] = row[f] ?? null;
19
- return Object.freeze(drop);
23
+ return projectFields(row, view.fields);
24
+ }
25
+ /**
26
+ * Which fields of a view-typed prop one module may read: the ones the view's owner
27
+ * declared, plus the ones that module declared itself over the same model.
28
+ *
29
+ * Not simply the named view. A module that adds a field with `extend` and then
30
+ * publishes a view over it has declared that field theme-visible, and it is the one
31
+ * module entitled to say so — refusing it here would mean the extension pillar and
32
+ * the view boundary could not both be true, and `inventory` adding `leadTimeDays`
33
+ * to `catalog.Product` and reading it back in a fill is the example the framework
34
+ * leads with. What still cannot cross is a field nobody declared anywhere.
35
+ */
36
+ export function visibleFields(manifest, viewKey, reader) {
37
+ const view = manifest.views[viewKey];
38
+ if (!view)
39
+ return [];
40
+ if (reader === undefined || reader === view.by)
41
+ return view.fields;
42
+ const fields = new Set(view.fields);
43
+ for (const other of Object.values(manifest.views))
44
+ if (other.by === reader && other.of === view.of)
45
+ for (const f of other.fields)
46
+ fields.add(f);
47
+ return [...fields];
20
48
  }
21
49
  export function makeDrops(manifest, viewKey, rows) {
22
50
  return rows.map((r) => makeDrop(manifest, viewKey, r));
23
51
  }
52
+ /**
53
+ * Where a function hides inside a value, as a readable path, or null when there is
54
+ * none.
55
+ *
56
+ * One walker, because "a theme receives data only" has to mean the same thing at
57
+ * every door into a theme. It used to be checked one level deep at the region door
58
+ * and recursively at the joint door, so `{ order: { total: () => … } }` was refused
59
+ * by one and waved through by the other.
60
+ */
61
+ export function findCallable(value, path = '', seen = new WeakSet()) {
62
+ if (typeof value === 'function')
63
+ return path;
64
+ if (value == null || typeof value !== 'object')
65
+ return null;
66
+ if (value instanceof Date)
67
+ return null;
68
+ // A cycle cannot hide a function the walk has not already passed through.
69
+ if (seen.has(value))
70
+ return null;
71
+ seen.add(value);
72
+ try {
73
+ if (Array.isArray(value)) {
74
+ for (let i = 0; i < value.length; i++) {
75
+ const found = findCallable(value[i], `${path}[${i}]`, seen);
76
+ if (found !== null)
77
+ return found;
78
+ }
79
+ return null;
80
+ }
81
+ for (const [key, item] of Object.entries(value)) {
82
+ const found = findCallable(item, path ? `${path}.${key}` : key, seen);
83
+ if (found !== null)
84
+ return found;
85
+ }
86
+ return null;
87
+ }
88
+ finally {
89
+ seen.delete(value);
90
+ }
91
+ }
24
92
  // Any value handed to a theme passes through here. Anything that is not plain data
25
93
  // is refused rather than silently stringified.
26
94
  export function sealScope(scope) {
27
95
  const out = Object.create(null);
28
96
  for (const [k, v] of Object.entries(scope)) {
29
- if (typeof v === 'function') {
97
+ const callable = findCallable(v, k);
98
+ if (callable !== null) {
30
99
  throw new KetError({
31
100
  code: 'E_SCOPE_CALLABLE',
32
- message: `scope key "${k}" is a function`,
101
+ message: `scope key "${callable}" is a function`,
33
102
  hint: 'themes receive data only; move behaviour into a server function',
34
103
  });
35
104
  }
@@ -1 +1 @@
1
- {"version":3,"file":"viewmodel.js","sourceRoot":"","sources":["../../../../../../packages/ketjs/src/theme/viewmodel.ts"],"names":[],"mappings":"AAAA,4DAA4D;AAC5D,EAAE;AACF,iFAAiF;AACjF,kFAAkF;AAClF,oFAAoF;AAEpF,OAAO,EAAE,QAAQ,EAAE,MAAM,qBAAqB,CAAA;AAK9C,MAAM,UAAU,QAAQ,CAAC,QAAkB,EAAE,OAAe,EAAE,GAAQ;IACpE,MAAM,IAAI,GAAG,QAAQ,CAAC,KAAK,CAAC,OAAO,CAAC,CAAA;IACpC,IAAI,CAAC,IAAI,EAAE,CAAC;QACV,MAAM,IAAI,QAAQ,CAAC;YACjB,IAAI,EAAE,gBAAgB;YACtB,OAAO,EAAE,kBAAkB,OAAO,GAAG;YACrC,IAAI,EAAE,mBAAmB,MAAM,CAAC,IAAI,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,IAAI,QAAQ,EAAE;SAC9E,CAAC,CAAA;IACJ,CAAC;IACD,MAAM,IAAI,GAAG,MAAM,CAAC,MAAM,CAAC,IAAI,CAAS,CAAA;IACxC,KAAK,MAAM,CAAC,IAAI,IAAI,CAAC,MAAM;QAAE,IAAI,CAAC,CAAC,CAAC,GAAG,GAAG,CAAC,CAAC,CAAC,IAAI,IAAI,CAAA;IACrD,OAAO,MAAM,CAAC,MAAM,CAAC,IAAI,CAAC,CAAA;AAC5B,CAAC;AAED,MAAM,UAAU,SAAS,CAAC,QAAkB,EAAE,OAAe,EAAE,IAAW;IACxE,OAAO,IAAI,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,QAAQ,CAAC,QAAQ,EAAE,OAAO,EAAE,CAAC,CAAC,CAAC,CAAA;AACxD,CAAC;AAED,mFAAmF;AACnF,+CAA+C;AAC/C,MAAM,UAAU,SAAS,CAAC,KAA8B;IACtD,MAAM,GAAG,GAAG,MAAM,CAAC,MAAM,CAAC,IAAI,CAA4B,CAAA;IAC1D,KAAK,MAAM,CAAC,CAAC,EAAE,CAAC,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,KAAK,CAAC,EAAE,CAAC;QAC3C,IAAI,OAAO,CAAC,KAAK,UAAU,EAAE,CAAC;YAC5B,MAAM,IAAI,QAAQ,CAAC;gBACjB,IAAI,EAAE,kBAAkB;gBACxB,OAAO,EAAE,cAAc,CAAC,iBAAiB;gBACzC,IAAI,EAAE,iEAAiE;aACxE,CAAC,CAAA;QACJ,CAAC;QACD,GAAG,CAAC,CAAC,CAAC,GAAG,CAAC,CAAA;IACZ,CAAC;IACD,OAAO,MAAM,CAAC,MAAM,CAAC,GAAG,CAAC,CAAA;AAC3B,CAAC"}
1
+ {"version":3,"file":"viewmodel.js","sourceRoot":"","sources":["../../../../../../packages/ketjs/src/theme/viewmodel.ts"],"names":[],"mappings":"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"}