@mongrov/analytics 0.5.0 → 0.7.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 (224) hide show
  1. package/README.md +23 -10
  2. package/UPGRADING.md +370 -0
  3. package/dist/core/device-events.d.ts +14 -0
  4. package/dist/core/device-events.d.ts.map +1 -0
  5. package/dist/core/device-events.js +13 -0
  6. package/dist/core/device-events.js.map +1 -0
  7. package/dist/core/errors.d.ts +1 -1
  8. package/dist/core/errors.d.ts.map +1 -1
  9. package/dist/core/errors.js.map +1 -1
  10. package/dist/core/extensions.d.ts +21 -4
  11. package/dist/core/extensions.d.ts.map +1 -1
  12. package/dist/core/extensions.js +21 -4
  13. package/dist/core/extensions.js.map +1 -1
  14. package/dist/core/factory.d.ts.map +1 -1
  15. package/dist/core/factory.js +124 -18
  16. package/dist/core/factory.js.map +1 -1
  17. package/dist/core/hooks.js +1 -1
  18. package/dist/core/hooks.js.map +1 -1
  19. package/dist/core/index.d.ts +11 -1
  20. package/dist/core/index.d.ts.map +1 -1
  21. package/dist/core/index.js +14 -0
  22. package/dist/core/index.js.map +1 -1
  23. package/dist/core/insight.d.ts +44 -0
  24. package/dist/core/insight.d.ts.map +1 -0
  25. package/dist/core/insight.js +62 -0
  26. package/dist/core/insight.js.map +1 -0
  27. package/dist/core/machine.d.ts.map +1 -1
  28. package/dist/core/machine.js +9 -1
  29. package/dist/core/machine.js.map +1 -1
  30. package/dist/core/metric_metadata.d.ts +57 -2
  31. package/dist/core/metric_metadata.d.ts.map +1 -1
  32. package/dist/core/metric_metadata.js +36 -8
  33. package/dist/core/metric_metadata.js.map +1 -1
  34. package/dist/core/migrations.d.ts +6 -0
  35. package/dist/core/migrations.d.ts.map +1 -1
  36. package/dist/core/migrations.js +92 -4
  37. package/dist/core/migrations.js.map +1 -1
  38. package/dist/core/retention.d.ts +44 -13
  39. package/dist/core/retention.d.ts.map +1 -1
  40. package/dist/core/retention.js +50 -22
  41. package/dist/core/retention.js.map +1 -1
  42. package/dist/core/schemas.d.ts +74 -3
  43. package/dist/core/schemas.d.ts.map +1 -1
  44. package/dist/core/schemas.js +168 -5
  45. package/dist/core/schemas.js.map +1 -1
  46. package/dist/core/table_metadata.d.ts.map +1 -1
  47. package/dist/core/table_metadata.js +4 -0
  48. package/dist/core/table_metadata.js.map +1 -1
  49. package/dist/core/types.d.ts +45 -10
  50. package/dist/core/types.d.ts.map +1 -1
  51. package/dist/core/warehouse.d.ts +28 -0
  52. package/dist/core/warehouse.d.ts.map +1 -1
  53. package/dist/core/warehouse.js +44 -0
  54. package/dist/core/warehouse.js.map +1 -1
  55. package/dist/core/watermark-cache.d.ts +75 -0
  56. package/dist/core/watermark-cache.d.ts.map +1 -0
  57. package/dist/core/watermark-cache.js +0 -0
  58. package/dist/core/watermark-cache.js.map +1 -0
  59. package/dist/rules/__fakes__/fakeEngine.d.ts +2 -0
  60. package/dist/rules/__fakes__/fakeEngine.d.ts.map +1 -1
  61. package/dist/rules/__fakes__/fakeEngine.js +4 -0
  62. package/dist/rules/__fakes__/fakeEngine.js.map +1 -1
  63. package/dist/rules/baseline-reader.d.ts +55 -0
  64. package/dist/rules/baseline-reader.d.ts.map +1 -0
  65. package/dist/rules/baseline-reader.js +111 -0
  66. package/dist/rules/baseline-reader.js.map +1 -0
  67. package/dist/rules/compiler.d.ts +36 -1
  68. package/dist/rules/compiler.d.ts.map +1 -1
  69. package/dist/rules/compiler.js +185 -39
  70. package/dist/rules/compiler.js.map +1 -1
  71. package/dist/rules/defaults/luminx.d.ts.map +1 -1
  72. package/dist/rules/defaults/luminx.js +8 -0
  73. package/dist/rules/defaults/luminx.js.map +1 -1
  74. package/dist/rules/defaults/viva.d.ts.map +1 -1
  75. package/dist/rules/defaults/viva.js +7 -0
  76. package/dist/rules/defaults/viva.js.map +1 -1
  77. package/dist/rules/defaults/yogaring.d.ts.map +1 -1
  78. package/dist/rules/defaults/yogaring.js +7 -0
  79. package/dist/rules/defaults/yogaring.js.map +1 -1
  80. package/dist/rules/defaults/ziva.d.ts.map +1 -1
  81. package/dist/rules/defaults/ziva.js +100 -24
  82. package/dist/rules/defaults/ziva.js.map +1 -1
  83. package/dist/rules/evaluator.d.ts +14 -3
  84. package/dist/rules/evaluator.d.ts.map +1 -1
  85. package/dist/rules/evaluator.js +157 -5
  86. package/dist/rules/evaluator.js.map +1 -1
  87. package/dist/rules/factory.d.ts.map +1 -1
  88. package/dist/rules/factory.js +5 -1
  89. package/dist/rules/factory.js.map +1 -1
  90. package/dist/rules/index.d.ts +2 -1
  91. package/dist/rules/index.d.ts.map +1 -1
  92. package/dist/rules/index.js +2 -1
  93. package/dist/rules/index.js.map +1 -1
  94. package/dist/rules/schema.d.ts +78 -7
  95. package/dist/rules/schema.d.ts.map +1 -1
  96. package/dist/rules/schema.js +44 -0
  97. package/dist/rules/schema.js.map +1 -1
  98. package/dist/rules/types.d.ts +16 -1
  99. package/dist/rules/types.d.ts.map +1 -1
  100. package/dist/rules/validator.d.ts.map +1 -1
  101. package/dist/rules/validator.js +56 -0
  102. package/dist/rules/validator.js.map +1 -1
  103. package/dist/sync/baseline-compute.d.ts +63 -0
  104. package/dist/sync/baseline-compute.d.ts.map +1 -0
  105. package/dist/sync/baseline-compute.js +211 -0
  106. package/dist/sync/baseline-compute.js.map +1 -0
  107. package/dist/sync/events.d.ts +19 -5
  108. package/dist/sync/events.d.ts.map +1 -1
  109. package/dist/sync/events.js +17 -0
  110. package/dist/sync/events.js.map +1 -1
  111. package/dist/sync/factory.d.ts +25 -4
  112. package/dist/sync/factory.d.ts.map +1 -1
  113. package/dist/sync/factory.js +109 -15
  114. package/dist/sync/factory.js.map +1 -1
  115. package/dist/sync/fetcher.d.ts +15 -2
  116. package/dist/sync/fetcher.d.ts.map +1 -1
  117. package/dist/sync/fetcher.js +59 -11
  118. package/dist/sync/fetcher.js.map +1 -1
  119. package/dist/sync/flusher.d.ts +52 -2
  120. package/dist/sync/flusher.d.ts.map +1 -1
  121. package/dist/sync/flusher.js +78 -9
  122. package/dist/sync/flusher.js.map +1 -1
  123. package/dist/sync/index.d.ts +4 -2
  124. package/dist/sync/index.d.ts.map +1 -1
  125. package/dist/sync/index.js +1 -0
  126. package/dist/sync/index.js.map +1 -1
  127. package/dist/sync/mapper/activity.d.ts.map +1 -1
  128. package/dist/sync/mapper/activity.js +2 -1
  129. package/dist/sync/mapper/activity.js.map +1 -1
  130. package/dist/sync/mapper/battery.d.ts +14 -7
  131. package/dist/sync/mapper/battery.d.ts.map +1 -1
  132. package/dist/sync/mapper/battery.js +13 -7
  133. package/dist/sync/mapper/battery.js.map +1 -1
  134. package/dist/sync/mapper/firmware.d.ts.map +1 -1
  135. package/dist/sync/mapper/firmware.js +4 -1
  136. package/dist/sync/mapper/firmware.js.map +1 -1
  137. package/dist/sync/mapper/ring-config.js +1 -1
  138. package/dist/sync/mapper/ring-config.js.map +1 -1
  139. package/dist/sync/mapper/schema.d.ts +411 -0
  140. package/dist/sync/mapper/schema.d.ts.map +1 -0
  141. package/dist/sync/mapper/schema.js +128 -0
  142. package/dist/sync/mapper/schema.js.map +1 -0
  143. package/dist/sync/mapper/sleep.d.ts +58 -13
  144. package/dist/sync/mapper/sleep.d.ts.map +1 -1
  145. package/dist/sync/mapper/sleep.js +141 -44
  146. package/dist/sync/mapper/sleep.js.map +1 -1
  147. package/dist/sync/mapper/types.d.ts +75 -10
  148. package/dist/sync/mapper/types.d.ts.map +1 -1
  149. package/dist/sync/scheduler.d.ts +7 -0
  150. package/dist/sync/scheduler.d.ts.map +1 -1
  151. package/dist/sync/scheduler.js +14 -0
  152. package/dist/sync/scheduler.js.map +1 -1
  153. package/dist/tools/__fakes__/engine.d.ts +2 -0
  154. package/dist/tools/__fakes__/engine.d.ts.map +1 -1
  155. package/dist/tools/__fakes__/engine.js +10 -0
  156. package/dist/tools/__fakes__/engine.js.map +1 -1
  157. package/dist/tools/authorize.d.ts +19 -12
  158. package/dist/tools/authorize.d.ts.map +1 -1
  159. package/dist/tools/authorize.js +31 -40
  160. package/dist/tools/authorize.js.map +1 -1
  161. package/dist/tools/factory.d.ts +2 -0
  162. package/dist/tools/factory.d.ts.map +1 -1
  163. package/dist/tools/factory.js +12 -1
  164. package/dist/tools/factory.js.map +1 -1
  165. package/dist/tools/formatters/copy-guidelines.d.ts +57 -0
  166. package/dist/tools/formatters/copy-guidelines.d.ts.map +1 -0
  167. package/dist/tools/formatters/copy-guidelines.js +110 -0
  168. package/dist/tools/formatters/copy-guidelines.js.map +1 -0
  169. package/dist/tools/formatters/index.d.ts +14 -0
  170. package/dist/tools/formatters/index.d.ts.map +1 -0
  171. package/dist/tools/formatters/index.js +14 -0
  172. package/dist/tools/formatters/index.js.map +1 -0
  173. package/dist/tools/formatters/spo2.d.ts +21 -0
  174. package/dist/tools/formatters/spo2.d.ts.map +1 -0
  175. package/dist/tools/formatters/spo2.js +79 -0
  176. package/dist/tools/formatters/spo2.js.map +1 -0
  177. package/dist/tools/{formatters.d.ts → formatters/text.d.ts} +1 -1
  178. package/dist/tools/formatters/text.d.ts.map +1 -0
  179. package/dist/tools/{formatters.js → formatters/text.js} +1 -1
  180. package/dist/tools/formatters/text.js.map +1 -0
  181. package/dist/tools/impls/activity.d.ts +2 -2
  182. package/dist/tools/impls/activity.js +7 -3
  183. package/dist/tools/impls/activity.js.map +1 -1
  184. package/dist/tools/impls/anomaly.d.ts +2 -2
  185. package/dist/tools/impls/anomaly.js +8 -4
  186. package/dist/tools/impls/anomaly.js.map +1 -1
  187. package/dist/tools/impls/compare.d.ts +2 -2
  188. package/dist/tools/impls/compare.js +8 -4
  189. package/dist/tools/impls/compare.js.map +1 -1
  190. package/dist/tools/impls/hrv.d.ts +2 -2
  191. package/dist/tools/impls/hrv.js +6 -2
  192. package/dist/tools/impls/hrv.js.map +1 -1
  193. package/dist/tools/impls/insights.d.ts +4 -4
  194. package/dist/tools/impls/insights.d.ts.map +1 -1
  195. package/dist/tools/impls/insights.js +10 -3
  196. package/dist/tools/impls/insights.js.map +1 -1
  197. package/dist/tools/impls/sleep.d.ts +2 -2
  198. package/dist/tools/impls/sleep.js +6 -2
  199. package/dist/tools/impls/sleep.js.map +1 -1
  200. package/dist/tools/impls/spo2.d.ts +52 -0
  201. package/dist/tools/impls/spo2.d.ts.map +1 -0
  202. package/dist/tools/impls/spo2.js +65 -0
  203. package/dist/tools/impls/spo2.js.map +1 -0
  204. package/dist/tools/index.d.ts +1 -0
  205. package/dist/tools/index.d.ts.map +1 -1
  206. package/dist/tools/index.js +4 -0
  207. package/dist/tools/index.js.map +1 -1
  208. package/dist/tools/mcp/guard.d.ts +28 -11
  209. package/dist/tools/mcp/guard.d.ts.map +1 -1
  210. package/dist/tools/mcp/guard.js +45 -15
  211. package/dist/tools/mcp/guard.js.map +1 -1
  212. package/dist/tools/mcp/index.d.ts +1 -1
  213. package/dist/tools/mcp/index.d.ts.map +1 -1
  214. package/dist/tools/mcp/index.js +1 -1
  215. package/dist/tools/mcp/index.js.map +1 -1
  216. package/dist/tools/mcp/server.d.ts.map +1 -1
  217. package/dist/tools/mcp/server.js +4 -0
  218. package/dist/tools/mcp/server.js.map +1 -1
  219. package/dist/tools/mcp/transports/http.d.ts.map +1 -1
  220. package/dist/tools/mcp/transports/http.js +4 -0
  221. package/dist/tools/mcp/transports/http.js.map +1 -1
  222. package/package.json +8 -5
  223. package/dist/tools/formatters.d.ts.map +0 -1
  224. package/dist/tools/formatters.js.map +0 -1
@@ -1,7 +1,7 @@
1
1
  /**
2
2
  * Table DDL for the analytics warehouse (spec §Table schema).
3
3
  *
4
- * Fourteen tables, verbatim from `.specifica/features/analytics-core/spec.md`.
4
+ * Fifteen tables, verbatim from `.specifica/features/analytics-core/spec.md`.
5
5
  * DDL strings are frozen — apps must not mutate them; migrations (T-08) own
6
6
  * schema evolution.
7
7
  *
@@ -23,13 +23,82 @@
23
23
  */
24
24
  import type { HybridDuckDB } from './engine';
25
25
  /** Ordered list of every warehouse table. Order = creation order. */
26
- export declare const TABLE_NAMES: readonly ["hrv", "heart_rate", "spo2", "temperature", "activity", "activity_bucket", "sleep_session", "sleep_stage", "sleep_raw", "device_event", "device_config", "insight", "sync_watermark", "tool_call_audit"];
26
+ export declare const TABLE_NAMES: readonly ["hrv", "heart_rate", "spo2", "temperature", "activity", "activity_bucket", "sleep_session", "sleep_stage", "sleep_raw", "device_event", "device_battery", "device_config", "insight", "sync_watermark", "tool_call_audit", "user_baseline"];
27
27
  export type TableName = (typeof TABLE_NAMES)[number];
28
+ /**
29
+ * Tables that exist only in the local catalog and are never created in the
30
+ * attached R2 zone.
31
+ *
32
+ * `user_baseline` is derived data: it is recomputed from the union views
33
+ * after each sync cycle and is cheap to rebuild, so pushing it would add an
34
+ * Iceberg table nobody reads and invite two devices in the same family to
35
+ * race on the same composite PK.
36
+ *
37
+ * `sync_watermark` is deliberately NOT here, despite being per-device
38
+ * bookkeeping that is never pushed (`TABLE_METADATA.syncable: false`).
39
+ * Excluding it broke the T-18 retention integration cases, which exercise
40
+ * the sweep against the real attached Iceberg catalog and need the table
41
+ * present there. An empty remote copy is harmless; a failing sweep is not.
42
+ */
43
+ export declare const LOCAL_ONLY_TABLES: ReadonlySet<TableName>;
28
44
  /**
29
45
  * Frozen DDL for every warehouse table. Copied verbatim from spec §Table
30
46
  * schema; rewrite happens in `ensureSchemas` at issue time.
31
47
  */
32
48
  export declare const SCHEMAS: Readonly<Record<TableName, string>>;
49
+ /**
50
+ * Lookup index for the `insight` table (spec §Table schema). Local catalog
51
+ * only — Iceberg has no CREATE INDEX; remote-side query pruning comes from
52
+ * the `day(ts)` partition instead. Issued by migration step 3.
53
+ */
54
+ export declare function insightIndexDdl(catalog: string): string;
55
+ /**
56
+ * Sensor tables exposed through a `v_{table}` union view (Sprint 5 §3).
57
+ *
58
+ * Registry queries, rule SQL, and tool SQL all target `v_{table}` and never
59
+ * `local.{table}` or `r2.default.{table}` directly (principle 19). Internal
60
+ * tables are absent deliberately: `insight`, `sync_watermark`,
61
+ * `tool_call_audit`, `user_baseline` and `device_config` are local-authoritative
62
+ * or local-only, so a union would either duplicate rows or read a remote
63
+ * copy that is never authoritative.
64
+ */
65
+ export declare const VIEWED_TABLES: readonly ["hrv", "heart_rate", "spo2", "temperature", "activity", "activity_bucket", "sleep_session", "sleep_stage", "device_event", "device_battery"];
66
+ export type ViewedTable = (typeof VIEWED_TABLES)[number];
67
+ /** Timestamp column the watermark partitions on, per table. */
68
+ export declare function watermarkColumnFor(table: ViewedTable): string;
69
+ /**
70
+ * Build the `CREATE OR REPLACE VIEW v_{table}` DDL for one sensor table.
71
+ *
72
+ * The view is what makes freshness honest: rows the device has flushed
73
+ * locally but not yet pushed to R2 are invisible in `r2.default.{table}`,
74
+ * and rows already pushed exist in BOTH catalogs. The push watermark
75
+ * partitions the two sources exactly —
76
+ *
77
+ * local: rows strictly AFTER the watermark (not yet pushed)
78
+ * remote: everything (pushed)
79
+ *
80
+ * — so the union is complete with no duplicates at the boundary, and a row
81
+ * becomes remote-visible at the same instant it stops being local-visible.
82
+ *
83
+ * The watermark subquery reads `sync_watermark` rather than taking a bound
84
+ * parameter because DuckDB views cannot close over query-time params; the
85
+ * view must resolve the current cursor on every scan. `$brand` /
86
+ * `$family_id` are likewise unavailable inside a view body, so the tenant
87
+ * filter is baked in at creation time from the attach context — which is
88
+ * safe precisely because views are dropped and recreated on every attach
89
+ * (T-06), so a brand switch cannot leave a view scoped to the old tenant.
90
+ *
91
+ * `remoteCatalog` omitted (local mode) produces a local-only view with no
92
+ * UNION, so consumers write one SQL string that works in both modes.
93
+ */
94
+ export declare function generateViewDdl(table: ViewedTable, ctx: {
95
+ brand: string;
96
+ familyId: string;
97
+ localCatalog: string;
98
+ remoteCatalog?: string;
99
+ }): string;
100
+ /** `DROP VIEW IF EXISTS v_{table}` for detach + brand switch. */
101
+ export declare function dropViewDdl(table: ViewedTable): string;
33
102
  /**
34
103
  * Rewrite one base DDL to `CREATE TABLE IF NOT EXISTS <catalog>.<table>`.
35
104
  *
@@ -62,5 +131,7 @@ export declare const LOCAL_SCHEMAS: Readonly<Record<TableName, string>>;
62
131
  * catalog (without). Default is `SCHEMAS` for back-compat with 0.4.x
63
132
  * callers that only wrote to the attached remote.
64
133
  */
65
- export declare function ensureSchemas(db: HybridDuckDB, catalog: string, schemas?: Readonly<Record<TableName, string>>): Promise<void>;
134
+ export declare function ensureSchemas(db: HybridDuckDB, catalog: string, schemas?: Readonly<Record<TableName, string>>, opts?: {
135
+ skipLocalOnly?: boolean;
136
+ }): Promise<void>;
66
137
  //# sourceMappingURL=schemas.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"schemas.d.ts","sourceRoot":"","sources":["../../src/core/schemas.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;GAsBG;AAGH,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,UAAU,CAAA;AAE5C,qEAAqE;AACrE,eAAO,MAAM,WAAW,oNAed,CAAA;AAEV,MAAM,MAAM,SAAS,GAAG,CAAC,OAAO,WAAW,CAAC,CAAC,MAAM,CAAC,CAAA;AAEpD;;;GAGG;AACH,eAAO,MAAM,OAAO,EAAE,QAAQ,CAAC,MAAM,CAAC,SAAS,EAAE,MAAM,CAAC,CAiKtD,CAAA;AAEF;;;;GAIG;AACH,wBAAgB,UAAU,CAAC,OAAO,EAAE,MAAM,EAAE,KAAK,EAAE,SAAS,EAAE,OAAO,EAAE,MAAM,GAAG,MAAM,CAKrF;AAED;;;;;;GAMG;AACH,wBAAgB,UAAU,CAAC,OAAO,EAAE,MAAM,GAAG,MAAM,CAElD;AAED;;;;;GAKG;AACH,eAAO,MAAM,aAAa,EAAE,QAAQ,CAAC,MAAM,CAAC,SAAS,EAAE,MAAM,CAAC,CAI7D,CAAA;AAED;;;;;;;;;;GAUG;AACH,wBAAsB,aAAa,CACjC,EAAE,EAAE,YAAY,EAChB,OAAO,EAAE,MAAM,EACf,OAAO,GAAE,QAAQ,CAAC,MAAM,CAAC,SAAS,EAAE,MAAM,CAAC,CAAW,GACrD,OAAO,CAAC,IAAI,CAAC,CAcf"}
1
+ {"version":3,"file":"schemas.d.ts","sourceRoot":"","sources":["../../src/core/schemas.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;GAsBG;AAGH,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,UAAU,CAAA;AAE5C,qEAAqE;AACrE,eAAO,MAAM,WAAW,uPAiBd,CAAA;AAEV,MAAM,MAAM,SAAS,GAAG,CAAC,OAAO,WAAW,CAAC,CAAC,MAAM,CAAC,CAAA;AAEpD;;;;;;;;;;;;;;GAcG;AACH,eAAO,MAAM,iBAAiB,EAAE,WAAW,CAAC,SAAS,CAEnD,CAAA;AAEF;;;GAGG;AACH,eAAO,MAAM,OAAO,EAAE,QAAQ,CAAC,MAAM,CAAC,SAAS,EAAE,MAAM,CAAC,CAwMtD,CAAA;AAEF;;;;GAIG;AACH,wBAAgB,eAAe,CAAC,OAAO,EAAE,MAAM,GAAG,MAAM,CAEvD;AAED;;;;;;;;;GASG;AACH,eAAO,MAAM,aAAa,wJAWhB,CAAA;AAEV,MAAM,MAAM,WAAW,GAAG,CAAC,OAAO,aAAa,CAAC,CAAC,MAAM,CAAC,CAAA;AAExD,+DAA+D;AAC/D,wBAAgB,kBAAkB,CAAC,KAAK,EAAE,WAAW,GAAG,MAAM,CAE7D;AAED;;;;;;;;;;;;;;;;;;;;;;;;GAwBG;AACH,wBAAgB,eAAe,CAC7B,KAAK,EAAE,WAAW,EAClB,GAAG,EAAE;IAAE,KAAK,EAAE,MAAM,CAAC;IAAC,QAAQ,EAAE,MAAM,CAAC;IAAC,YAAY,EAAE,MAAM,CAAC;IAAC,aAAa,CAAC,EAAE,MAAM,CAAA;CAAE,GACrF,MAAM,CA0BR;AAkBD,iEAAiE;AACjE,wBAAgB,WAAW,CAAC,KAAK,EAAE,WAAW,GAAG,MAAM,CAEtD;AAED;;;;GAIG;AACH,wBAAgB,UAAU,CAAC,OAAO,EAAE,MAAM,EAAE,KAAK,EAAE,SAAS,EAAE,OAAO,EAAE,MAAM,GAAG,MAAM,CAKrF;AAED;;;;;;GAMG;AACH,wBAAgB,UAAU,CAAC,OAAO,EAAE,MAAM,GAAG,MAAM,CAKlD;AAED;;;;;GAKG;AACH,eAAO,MAAM,aAAa,EAAE,QAAQ,CAAC,MAAM,CAAC,SAAS,EAAE,MAAM,CAAC,CAI7D,CAAA;AAED;;;;;;;;;;GAUG;AACH,wBAAsB,aAAa,CACjC,EAAE,EAAE,YAAY,EAChB,OAAO,EAAE,MAAM,EACf,OAAO,GAAE,QAAQ,CAAC,MAAM,CAAC,SAAS,EAAE,MAAM,CAAC,CAAW,EACtD,IAAI,GAAE;IAAE,aAAa,CAAC,EAAE,OAAO,CAAA;CAAO,GACrC,OAAO,CAAC,IAAI,CAAC,CAmBf"}
@@ -1,7 +1,7 @@
1
1
  /**
2
2
  * Table DDL for the analytics warehouse (spec §Table schema).
3
3
  *
4
- * Fourteen tables, verbatim from `.specifica/features/analytics-core/spec.md`.
4
+ * Fifteen tables, verbatim from `.specifica/features/analytics-core/spec.md`.
5
5
  * DDL strings are frozen — apps must not mutate them; migrations (T-08) own
6
6
  * schema evolution.
7
7
  *
@@ -34,11 +34,31 @@ export const TABLE_NAMES = [
34
34
  'sleep_stage',
35
35
  'sleep_raw',
36
36
  'device_event',
37
+ 'device_battery',
37
38
  'device_config',
38
39
  'insight',
39
40
  'sync_watermark',
40
41
  'tool_call_audit',
42
+ 'user_baseline',
41
43
  ];
44
+ /**
45
+ * Tables that exist only in the local catalog and are never created in the
46
+ * attached R2 zone.
47
+ *
48
+ * `user_baseline` is derived data: it is recomputed from the union views
49
+ * after each sync cycle and is cheap to rebuild, so pushing it would add an
50
+ * Iceberg table nobody reads and invite two devices in the same family to
51
+ * race on the same composite PK.
52
+ *
53
+ * `sync_watermark` is deliberately NOT here, despite being per-device
54
+ * bookkeeping that is never pushed (`TABLE_METADATA.syncable: false`).
55
+ * Excluding it broke the T-18 retention integration cases, which exercise
56
+ * the sweep against the real attached Iceberg catalog and need the table
57
+ * present there. An empty remote copy is harmless; a failing sweep is not.
58
+ */
59
+ export const LOCAL_ONLY_TABLES = new Set([
60
+ 'user_baseline',
61
+ ]);
42
62
  /**
43
63
  * Frozen DDL for every warehouse table. Copied verbatim from spec §Table
44
64
  * schema; rewrite happens in `ensureSchemas` at issue time.
@@ -142,6 +162,14 @@ export const SCHEMAS = Object.freeze({
142
162
  event_type VARCHAR NOT NULL,
143
163
  payload VARCHAR
144
164
  ) PARTITIONED BY (day(ts));`,
165
+ device_battery: `CREATE TABLE device_battery (
166
+ ts TIMESTAMP NOT NULL,
167
+ brand VARCHAR NOT NULL,
168
+ family_id VARCHAR NOT NULL,
169
+ user_id VARCHAR NOT NULL,
170
+ device_id VARCHAR NOT NULL,
171
+ battery_pct DOUBLE NOT NULL
172
+ ) PARTITIONED BY (day(ts), device_id);`,
145
173
  device_config: `CREATE TABLE device_config (
146
174
  device_id VARCHAR NOT NULL,
147
175
  brand VARCHAR NOT NULL,
@@ -157,17 +185,20 @@ export const SCHEMAS = Object.freeze({
157
185
  PRIMARY KEY (device_id, data_type, valid_from)
158
186
  );`,
159
187
  insight: `CREATE TABLE insight (
160
- id VARCHAR PRIMARY KEY,
188
+ insight_id VARCHAR PRIMARY KEY,
161
189
  ts TIMESTAMP NOT NULL,
162
190
  brand VARCHAR NOT NULL,
163
191
  family_id VARCHAR NOT NULL,
164
192
  user_id VARCHAR NOT NULL,
165
193
  rule_id VARCHAR,
194
+ metric VARCHAR NOT NULL,
195
+ kind VARCHAR NOT NULL,
166
196
  severity VARCHAR NOT NULL,
167
197
  title VARCHAR NOT NULL,
168
198
  body TEXT,
169
199
  evidence VARCHAR,
170
- acknowledged_at TIMESTAMP
200
+ acknowledged_at TIMESTAMP,
201
+ dismissed_at TIMESTAMP
171
202
  ) PARTITIONED BY (day(ts));`,
172
203
  sync_watermark: `CREATE TABLE sync_watermark (
173
204
  brand VARCHAR NOT NULL,
@@ -191,7 +222,131 @@ export const SCHEMAS = Object.freeze({
191
222
  outcome VARCHAR NOT NULL,
192
223
  error_message VARCHAR
193
224
  ) PARTITIONED BY (day(ts));`,
225
+ // Sprint 5 §7 — shared baseline source of truth for rules, tools, and
226
+ // screens. Quantiles are computed DAY-FIRST (principle 27): readings
227
+ // collapse to one value per local day, then quantiles run across days.
228
+ // `sample_count` therefore counts DAYS, not readings — a row is only
229
+ // written at >= 20 days (BASELINE_MIN_DAYS).
230
+ //
231
+ // Not partitioned: the table holds at most
232
+ // (metrics x windows) = 21 rows per user, and the composite PK is the
233
+ // only access path any consumer uses.
234
+ user_baseline: `CREATE TABLE user_baseline (
235
+ brand VARCHAR NOT NULL,
236
+ family_id VARCHAR NOT NULL,
237
+ user_id VARCHAR NOT NULL,
238
+ metric VARCHAR NOT NULL,
239
+ window_days SMALLINT NOT NULL,
240
+ p05 DOUBLE,
241
+ p10 DOUBLE,
242
+ p50 DOUBLE,
243
+ p90 DOUBLE,
244
+ p95 DOUBLE,
245
+ mean DOUBLE,
246
+ stddev DOUBLE,
247
+ sample_count INTEGER,
248
+ computed_at TIMESTAMP NOT NULL,
249
+ PRIMARY KEY (brand, family_id, user_id, metric, window_days)
250
+ );`,
194
251
  });
252
+ /**
253
+ * Lookup index for the `insight` table (spec §Table schema). Local catalog
254
+ * only — Iceberg has no CREATE INDEX; remote-side query pruning comes from
255
+ * the `day(ts)` partition instead. Issued by migration step 3.
256
+ */
257
+ export function insightIndexDdl(catalog) {
258
+ return `CREATE INDEX IF NOT EXISTS idx_insight_lookup ON ${catalog}.insight (user_id, metric, dismissed_at, ts);`;
259
+ }
260
+ /**
261
+ * Sensor tables exposed through a `v_{table}` union view (Sprint 5 §3).
262
+ *
263
+ * Registry queries, rule SQL, and tool SQL all target `v_{table}` and never
264
+ * `local.{table}` or `r2.default.{table}` directly (principle 19). Internal
265
+ * tables are absent deliberately: `insight`, `sync_watermark`,
266
+ * `tool_call_audit`, `user_baseline` and `device_config` are local-authoritative
267
+ * or local-only, so a union would either duplicate rows or read a remote
268
+ * copy that is never authoritative.
269
+ */
270
+ export const VIEWED_TABLES = [
271
+ 'hrv',
272
+ 'heart_rate',
273
+ 'spo2',
274
+ 'temperature',
275
+ 'activity',
276
+ 'activity_bucket',
277
+ 'sleep_session',
278
+ 'sleep_stage',
279
+ 'device_event',
280
+ 'device_battery',
281
+ ];
282
+ /** Timestamp column the watermark partitions on, per table. */
283
+ export function watermarkColumnFor(table) {
284
+ return table === 'sleep_session' ? 'ts_start' : 'ts';
285
+ }
286
+ /**
287
+ * Build the `CREATE OR REPLACE VIEW v_{table}` DDL for one sensor table.
288
+ *
289
+ * The view is what makes freshness honest: rows the device has flushed
290
+ * locally but not yet pushed to R2 are invisible in `r2.default.{table}`,
291
+ * and rows already pushed exist in BOTH catalogs. The push watermark
292
+ * partitions the two sources exactly —
293
+ *
294
+ * local: rows strictly AFTER the watermark (not yet pushed)
295
+ * remote: everything (pushed)
296
+ *
297
+ * — so the union is complete with no duplicates at the boundary, and a row
298
+ * becomes remote-visible at the same instant it stops being local-visible.
299
+ *
300
+ * The watermark subquery reads `sync_watermark` rather than taking a bound
301
+ * parameter because DuckDB views cannot close over query-time params; the
302
+ * view must resolve the current cursor on every scan. `$brand` /
303
+ * `$family_id` are likewise unavailable inside a view body, so the tenant
304
+ * filter is baked in at creation time from the attach context — which is
305
+ * safe precisely because views are dropped and recreated on every attach
306
+ * (T-06), so a brand switch cannot leave a view scoped to the old tenant.
307
+ *
308
+ * `remoteCatalog` omitted (local mode) produces a local-only view with no
309
+ * UNION, so consumers write one SQL string that works in both modes.
310
+ */
311
+ export function generateViewDdl(table, ctx) {
312
+ const tsCol = watermarkColumnFor(table);
313
+ const brand = sqlLiteral(ctx.brand);
314
+ const familyId = sqlLiteral(ctx.familyId);
315
+ const local = `${ctx.localCatalog}.${table}`;
316
+ const watermark = `COALESCE((SELECT cursor_ts FROM ${ctx.localCatalog}.sync_watermark `
317
+ + `WHERE table_name = '${table}' AND kind = 'push' `
318
+ + `AND brand = ${brand} AND family_id = ${familyId}), `
319
+ + `'1970-01-01'::TIMESTAMP)`;
320
+ if (!ctx.remoteCatalog) {
321
+ // Local mode: nothing is ever pushed, so every local row is visible and
322
+ // the watermark filter would be a no-op that only costs a scan.
323
+ return `CREATE OR REPLACE VIEW v_${table} AS SELECT * FROM ${local};`;
324
+ }
325
+ const remote = `${ctx.remoteCatalog}.${REMOTE_NAMESPACE_VIEW}.${table}`;
326
+ return (`CREATE OR REPLACE VIEW v_${table} AS\n`
327
+ + ` SELECT * FROM ${local}\n`
328
+ + ` WHERE ${tsCol} > ${watermark}\n`
329
+ + ` UNION ALL\n`
330
+ + ` SELECT * FROM ${remote};`);
331
+ }
332
+ /**
333
+ * Iceberg namespace remote tables live under. Duplicated from
334
+ * `migrations.ts` rather than imported to keep `schemas.ts` free of a
335
+ * migrations dependency (migrations already imports schemas).
336
+ */
337
+ const REMOTE_NAMESPACE_VIEW = 'default';
338
+ /**
339
+ * Single-quote a SQL string literal. View bodies cannot take bound
340
+ * parameters, so brand/familyId are inlined — escaping is mandatory, not
341
+ * optional, even though both values are server-issued.
342
+ */
343
+ function sqlLiteral(value) {
344
+ return `'${value.replace(/'/g, `''`)}'`;
345
+ }
346
+ /** `DROP VIEW IF EXISTS v_{table}` for detach + brand switch. */
347
+ export function dropViewDdl(table) {
348
+ return `DROP VIEW IF EXISTS v_${table};`;
349
+ }
195
350
  /**
196
351
  * Rewrite one base DDL to `CREATE TABLE IF NOT EXISTS <catalog>.<table>`.
197
352
  *
@@ -208,7 +363,10 @@ export function qualifyDdl(baseDdl, table, catalog) {
208
363
  * Exported for tests; call sites should prefer `LOCAL_SCHEMAS`.
209
364
  */
210
365
  export function toLocalDdl(baseDdl) {
211
- return baseDdl.replace(/\)\s*PARTITIONED BY\s*\([^)]*\);?/g, ');');
366
+ // The clause always terminates the DDL, and its column list contains
367
+ // nested parens (`day(ts)`), so strip from the closing table paren to
368
+ // end-of-string rather than trying to match the paren group.
369
+ return baseDdl.replace(/\)\s*PARTITIONED BY[\s\S]*$/, ');');
212
370
  }
213
371
  /**
214
372
  * Local-catalog DDL variants of `SCHEMAS` — same tables, same columns,
@@ -228,8 +386,13 @@ export const LOCAL_SCHEMAS = Object.freeze(Object.fromEntries(TABLE_NAMES.map(ta
228
386
  * catalog (without). Default is `SCHEMAS` for back-compat with 0.4.x
229
387
  * callers that only wrote to the attached remote.
230
388
  */
231
- export async function ensureSchemas(db, catalog, schemas = SCHEMAS) {
389
+ export async function ensureSchemas(db, catalog, schemas = SCHEMAS, opts = {}) {
232
390
  for (const table of TABLE_NAMES) {
391
+ // Remote passes `skipLocalOnly` so derived/bookkeeping tables never get
392
+ // created in the user's R2 zone.
393
+ if (opts.skipLocalOnly && LOCAL_ONLY_TABLES.has(table)) {
394
+ continue;
395
+ }
233
396
  const sql = qualifyDdl(schemas[table], table, catalog);
234
397
  try {
235
398
  await db.execute(sql);
@@ -1 +1 @@
1
- {"version":3,"file":"schemas.js","sourceRoot":"","sources":["../../src/core/schemas.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;GAsBG;AAEH,OAAO,EAAE,cAAc,EAAE,MAAM,UAAU,CAAA;AAGzC,qEAAqE;AACrE,MAAM,CAAC,MAAM,WAAW,GAAG;IACzB,KAAK;IACL,YAAY;IACZ,MAAM;IACN,aAAa;IACb,UAAU;IACV,iBAAiB;IACjB,eAAe;IACf,aAAa;IACb,WAAW;IACX,cAAc;IACd,eAAe;IACf,SAAS;IACT,gBAAgB;IAChB,iBAAiB;CACT,CAAA;AAIV;;;GAGG;AACH,MAAM,CAAC,MAAM,OAAO,GAAwC,MAAM,CAAC,MAAM,CAAC;IACxE,GAAG,EAAE;;;;;;;;;;;qCAW8B;IAEnC,UAAU,EAAE;;;;;;;qCAOuB;IAEnC,IAAI,EAAE;;;;;;;qCAO6B;IAEnC,WAAW,EAAE;;;;;;;qCAOsB;IAEnC,QAAQ,EAAE;;;;;;;qCAOyB;IAEnC,eAAe,EAAE;;;;;;;;qCAQkB;IAEnC,aAAa,EAAE;;;;;;;;;;;;;;;2CAe0B;IAEzC,WAAW,EAAE;;;;;;;;;qCASsB;IAEnC,SAAS,EAAE;;;;;;;;;mDASsC;IAEjD,YAAY,EAAE;;;;;;;;4BAQY;IAE1B,aAAa,EAAE;;;;;;;;;;;;;GAad;IAED,OAAO,EAAE;;;;;;;;;;;;4BAYiB;IAE1B,cAAc,EAAE;;;;;;;;GAQf;IAED,eAAe,EAAE;;;;;;;;;;;;4BAYS;CAC3B,CAAC,CAAA;AAEF;;;;GAIG;AACH,MAAM,UAAU,UAAU,CAAC,OAAe,EAAE,KAAgB,EAAE,OAAe;IAC3E,OAAO,OAAO,CAAC,OAAO,CACpB,gBAAgB,KAAK,EAAE,EACvB,8BAA8B,OAAO,IAAI,KAAK,EAAE,CACjD,CAAA;AACH,CAAC;AAED;;;;;;GAMG;AACH,MAAM,UAAU,UAAU,CAAC,OAAe;IACxC,OAAO,OAAO,CAAC,OAAO,CAAC,oCAAoC,EAAE,IAAI,CAAC,CAAA;AACpE,CAAC;AAED;;;;;GAKG;AACH,MAAM,CAAC,MAAM,aAAa,GAAwC,MAAM,CAAC,MAAM,CAC7E,MAAM,CAAC,WAAW,CAChB,WAAW,CAAC,GAAG,CAAC,KAAK,CAAC,EAAE,CAAC,CAAC,KAAK,EAAE,UAAU,CAAC,OAAO,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,CACjC,CAC/B,CAAA;AAED;;;;;;;;;;GAUG;AACH,MAAM,CAAC,KAAK,UAAU,aAAa,CACjC,EAAgB,EAChB,OAAe,EACf,UAA+C,OAAO;IAEtD,KAAK,MAAM,KAAK,IAAI,WAAW,EAAE,CAAC;QAChC,MAAM,GAAG,GAAG,UAAU,CAAC,OAAO,CAAC,KAAK,CAAC,EAAE,KAAK,EAAE,OAAO,CAAC,CAAA;QACtD,IAAI,CAAC;YACH,MAAM,EAAE,CAAC,OAAO,CAAC,GAAG,CAAC,CAAA;QACvB,CAAC;QACD,OAAO,KAAK,EAAE,CAAC;YACb,MAAM,IAAI,cAAc,CACtB,kBAAkB,EAClB,iCAAiC,KAAK,EAAE,EACxC,KAAK,CACN,CAAA;QACH,CAAC;IACH,CAAC;AACH,CAAC"}
1
+ {"version":3,"file":"schemas.js","sourceRoot":"","sources":["../../src/core/schemas.ts"],"names":[],"mappings":"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"}
@@ -1 +1 @@
1
- {"version":3,"file":"table_metadata.d.ts","sourceRoot":"","sources":["../../src/core/table_metadata.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;GAgBG;AAEH,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,WAAW,CAAA;AAE1C,MAAM,WAAW,iBAAiB;IAChC,UAAU,EAAE,MAAM,CAAA;IAClB,QAAQ,EAAE,OAAO,CAAA;CAClB;AAED,eAAO,MAAM,cAAc,EAAE,QAAQ,CAAC,MAAM,CAAC,SAAS,EAAE,iBAAiB,CAAC,CAexE,CAAA;AAEF;;;;;GAKG;AACH,wBAAgB,aAAa,CAAC,KAAK,EAAE,SAAS,GAAG,MAAM,GAAG,MAAM,CAE/D;AAED;;;;GAIG;AACH,wBAAgB,UAAU,CAAC,KAAK,EAAE,SAAS,GAAG,MAAM,GAAG,OAAO,CAE7D"}
1
+ {"version":3,"file":"table_metadata.d.ts","sourceRoot":"","sources":["../../src/core/table_metadata.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;GAgBG;AAEH,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,WAAW,CAAA;AAE1C,MAAM,WAAW,iBAAiB;IAChC,UAAU,EAAE,MAAM,CAAA;IAClB,QAAQ,EAAE,OAAO,CAAA;CAClB;AAED,eAAO,MAAM,cAAc,EAAE,QAAQ,CAAC,MAAM,CAAC,SAAS,EAAE,iBAAiB,CAAC,CAmBxE,CAAA;AAEF;;;;;GAKG;AACH,wBAAgB,aAAa,CAAC,KAAK,EAAE,SAAS,GAAG,MAAM,GAAG,MAAM,CAE/D;AAED;;;;GAIG;AACH,wBAAgB,UAAU,CAAC,KAAK,EAAE,SAAS,GAAG,MAAM,GAAG,OAAO,CAE7D"}
@@ -26,9 +26,13 @@ export const TABLE_METADATA = Object.freeze({
26
26
  sleep_stage: { timeColumn: 'ts', syncable: true },
27
27
  sleep_raw: { timeColumn: 'ts', syncable: true },
28
28
  device_event: { timeColumn: 'ts', syncable: true },
29
+ device_battery: { timeColumn: 'ts', syncable: true },
29
30
  device_config: { timeColumn: 'valid_from', syncable: true },
30
31
  insight: { timeColumn: 'ts', syncable: true },
31
32
  sync_watermark: { timeColumn: 'updated_at', syncable: false },
33
+ // Derived, local-only, and UPSERTed in place — never pushed, and its
34
+ // `computed_at` is a recompute stamp rather than a sync cursor.
35
+ user_baseline: { timeColumn: 'computed_at', syncable: false },
32
36
  tool_call_audit: { timeColumn: 'ts', syncable: false },
33
37
  });
34
38
  /**
@@ -1 +1 @@
1
- {"version":3,"file":"table_metadata.js","sourceRoot":"","sources":["../../src/core/table_metadata.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;GAgBG;AASH,MAAM,CAAC,MAAM,cAAc,GAAmD,MAAM,CAAC,MAAM,CAAC;IAC1F,GAAG,EAAE,EAAE,UAAU,EAAE,IAAI,EAAE,QAAQ,EAAE,IAAI,EAAE;IACzC,UAAU,EAAE,EAAE,UAAU,EAAE,IAAI,EAAE,QAAQ,EAAE,IAAI,EAAE;IAChD,IAAI,EAAE,EAAE,UAAU,EAAE,IAAI,EAAE,QAAQ,EAAE,IAAI,EAAE;IAC1C,WAAW,EAAE,EAAE,UAAU,EAAE,IAAI,EAAE,QAAQ,EAAE,IAAI,EAAE;IACjD,QAAQ,EAAE,EAAE,UAAU,EAAE,IAAI,EAAE,QAAQ,EAAE,IAAI,EAAE;IAC9C,eAAe,EAAE,EAAE,UAAU,EAAE,IAAI,EAAE,QAAQ,EAAE,IAAI,EAAE;IACrD,aAAa,EAAE,EAAE,UAAU,EAAE,UAAU,EAAE,QAAQ,EAAE,IAAI,EAAE;IACzD,WAAW,EAAE,EAAE,UAAU,EAAE,IAAI,EAAE,QAAQ,EAAE,IAAI,EAAE;IACjD,SAAS,EAAE,EAAE,UAAU,EAAE,IAAI,EAAE,QAAQ,EAAE,IAAI,EAAE;IAC/C,YAAY,EAAE,EAAE,UAAU,EAAE,IAAI,EAAE,QAAQ,EAAE,IAAI,EAAE;IAClD,aAAa,EAAE,EAAE,UAAU,EAAE,YAAY,EAAE,QAAQ,EAAE,IAAI,EAAE;IAC3D,OAAO,EAAE,EAAE,UAAU,EAAE,IAAI,EAAE,QAAQ,EAAE,IAAI,EAAE;IAC7C,cAAc,EAAE,EAAE,UAAU,EAAE,YAAY,EAAE,QAAQ,EAAE,KAAK,EAAE;IAC7D,eAAe,EAAE,EAAE,UAAU,EAAE,IAAI,EAAE,QAAQ,EAAE,KAAK,EAAE;CACvD,CAAC,CAAA;AAEF;;;;;GAKG;AACH,MAAM,UAAU,aAAa,CAAC,KAAyB;IACrD,OAAQ,cAAoD,CAAC,KAAK,CAAC,EAAE,UAAU,IAAI,IAAI,CAAA;AACzF,CAAC;AAED;;;;GAIG;AACH,MAAM,UAAU,UAAU,CAAC,KAAyB;IAClD,OAAQ,cAAoD,CAAC,KAAK,CAAC,EAAE,QAAQ,IAAI,KAAK,CAAA;AACxF,CAAC"}
1
+ {"version":3,"file":"table_metadata.js","sourceRoot":"","sources":["../../src/core/table_metadata.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;GAgBG;AASH,MAAM,CAAC,MAAM,cAAc,GAAmD,MAAM,CAAC,MAAM,CAAC;IAC1F,GAAG,EAAE,EAAE,UAAU,EAAE,IAAI,EAAE,QAAQ,EAAE,IAAI,EAAE;IACzC,UAAU,EAAE,EAAE,UAAU,EAAE,IAAI,EAAE,QAAQ,EAAE,IAAI,EAAE;IAChD,IAAI,EAAE,EAAE,UAAU,EAAE,IAAI,EAAE,QAAQ,EAAE,IAAI,EAAE;IAC1C,WAAW,EAAE,EAAE,UAAU,EAAE,IAAI,EAAE,QAAQ,EAAE,IAAI,EAAE;IACjD,QAAQ,EAAE,EAAE,UAAU,EAAE,IAAI,EAAE,QAAQ,EAAE,IAAI,EAAE;IAC9C,eAAe,EAAE,EAAE,UAAU,EAAE,IAAI,EAAE,QAAQ,EAAE,IAAI,EAAE;IACrD,aAAa,EAAE,EAAE,UAAU,EAAE,UAAU,EAAE,QAAQ,EAAE,IAAI,EAAE;IACzD,WAAW,EAAE,EAAE,UAAU,EAAE,IAAI,EAAE,QAAQ,EAAE,IAAI,EAAE;IACjD,SAAS,EAAE,EAAE,UAAU,EAAE,IAAI,EAAE,QAAQ,EAAE,IAAI,EAAE;IAC/C,YAAY,EAAE,EAAE,UAAU,EAAE,IAAI,EAAE,QAAQ,EAAE,IAAI,EAAE;IAClD,cAAc,EAAE,EAAE,UAAU,EAAE,IAAI,EAAE,QAAQ,EAAE,IAAI,EAAE;IACpD,aAAa,EAAE,EAAE,UAAU,EAAE,YAAY,EAAE,QAAQ,EAAE,IAAI,EAAE;IAC3D,OAAO,EAAE,EAAE,UAAU,EAAE,IAAI,EAAE,QAAQ,EAAE,IAAI,EAAE;IAC7C,cAAc,EAAE,EAAE,UAAU,EAAE,YAAY,EAAE,QAAQ,EAAE,KAAK,EAAE;IAC7D,qEAAqE;IACrE,gEAAgE;IAChE,aAAa,EAAE,EAAE,UAAU,EAAE,aAAa,EAAE,QAAQ,EAAE,KAAK,EAAE;IAC7D,eAAe,EAAE,EAAE,UAAU,EAAE,IAAI,EAAE,QAAQ,EAAE,KAAK,EAAE;CACvD,CAAC,CAAA;AAEF;;;;;GAKG;AACH,MAAM,UAAU,aAAa,CAAC,KAAyB;IACrD,OAAQ,cAAoD,CAAC,KAAK,CAAC,EAAE,UAAU,IAAI,IAAI,CAAA;AACzF,CAAC;AAED;;;;GAIG;AACH,MAAM,UAAU,UAAU,CAAC,KAAyB;IAClD,OAAQ,cAAoD,CAAC,KAAK,CAAC,EAAE,QAAQ,IAAI,KAAK,CAAA;AACxF,CAAC"}
@@ -139,6 +139,31 @@ export interface AnalyticsEngine {
139
139
  */
140
140
  readonly mode: AnalyticsMode;
141
141
  subscribe(listener: (s: AnalyticsState) => void): Unsubscribe;
142
+ /**
143
+ * Family member userIds for the current attach context (principle 39 —
144
+ * "Rules engine and AI tools share the same source of truth").
145
+ *
146
+ * Delegates to the `familyMembersProvider` configured at
147
+ * `createAnalytics`, so rules + tools never reach for RxDB or auth state
148
+ * themselves. Result is cached in-engine for 60s and invalidated on
149
+ * `family:update` (analytics-core/spec.md §Family membership resolution).
150
+ *
151
+ * Returns `[]` when not attached, when `tenantScope === 'org'`, or in
152
+ * local mode (no family fanout) — callers treat empty as "no fanout",
153
+ * never as "denied".
154
+ */
155
+ getFamilyMembers(): Promise<string[]>;
156
+ /**
157
+ * Stamp `dismissed_at` on one insight (Sprint 5 §7b). Backs the app
158
+ * registry's `insight.dismiss` mutation — `@mongrov/data-access` types
159
+ * this exact shape on `MutationContext.analytics`.
160
+ *
161
+ * Authorized by ownership: `userId` must match the insight's owner.
162
+ */
163
+ dismissInsight(args: {
164
+ insightId: string;
165
+ userId: string;
166
+ }): Promise<void>;
142
167
  setRetention(days: number): Promise<void>;
143
168
  /**
144
169
  * Return the last successfully-attached ctx (persisted via KVStore) if it
@@ -148,22 +173,32 @@ export interface AnalyticsEngine {
148
173
  getLastAttach(brand: string): Promise<AttachContext | null>;
149
174
  close(): Promise<void>;
150
175
  }
176
+ /** Insight categories per spec §Table schema (`insight.kind`). */
177
+ export type InsightKind = 'threshold' | 'pattern' | 'baseline_shift' | 'factor';
178
+ /** Insight severity per spec §Table schema (`insight.severity`). */
179
+ export type InsightSeverity = 'info' | 'warn' | 'urgent';
151
180
  /**
152
- * Insight row shape as read from the `insight` DuckDB table.
153
- * The full schema is frozen in T-06 (schemas.ts); this stub matches the
154
- * columns needed by `useInsight()` in v0.1.0.
181
+ * Insight row shape as read from the `insight` DuckDB table — mirrors the
182
+ * DDL in schemas.ts (camelCase field names, snake_case columns).
155
183
  */
156
184
  export interface Insight {
157
- id: string;
185
+ insightId: string;
186
+ /** fired_at semantic; adapters may surface TIMESTAMP as ISO string. */
187
+ ts: Date | string;
158
188
  brand: string;
159
189
  familyId: string;
160
190
  userId: string;
161
- ruleId?: string;
162
- severity: 'info' | 'warn' | 'critical';
163
- observedAt: Date;
164
- observedValue?: number;
165
- thresholdValue?: number;
166
- payload?: Record<string, unknown>;
191
+ /** Nullable — non-rule insights (patterns, factors) carry no rule_id. */
192
+ ruleId?: string | null;
193
+ metric: string;
194
+ kind: InsightKind;
195
+ severity: InsightSeverity;
196
+ title: string;
197
+ body?: string | null;
198
+ /** JSON payload (readings, thresholds, …) serialized as VARCHAR. */
199
+ evidence?: string | null;
200
+ acknowledgedAt?: Date | string | null;
201
+ dismissedAt?: Date | string | null;
167
202
  }
168
203
  export {};
169
204
  //# sourceMappingURL=types.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../src/core/types.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../src/core/types.ts"],"names":[],"mappings":"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"}
@@ -105,4 +105,32 @@ export declare function probeLocalCatalog(db: HybridDuckDB): Promise<string>;
105
105
  * the state machine's `detachEngine` actor can dispatch symmetrically.
106
106
  */
107
107
  export declare function detachLocal(_db: HybridDuckDB, _tenantId: string): Promise<void>;
108
+ /**
109
+ * Create every `v_{table}` union view for the current attach.
110
+ *
111
+ * Called after migrations, so the underlying tables are guaranteed to
112
+ * exist — a view over a missing table fails at creation in DuckDB, not
113
+ * lazily at scan.
114
+ *
115
+ * The view bodies bake in `brand` + `family_id` (see `generateViewDdl` for
116
+ * why they cannot be bound parameters), which makes recreation on every
117
+ * attach a correctness requirement rather than housekeeping: a brand
118
+ * switch that reused the previous attach's views would serve the previous
119
+ * tenant's rows. `CREATE OR REPLACE` handles the overwrite; `dropViews` on
120
+ * detach closes the window where a stale view exists with no attach behind
121
+ * it.
122
+ */
123
+ export declare function createViews(db: HybridDuckDB, ctx: {
124
+ brand: string;
125
+ familyId: string;
126
+ localCatalog: string;
127
+ remoteCatalog?: string;
128
+ }): Promise<void>;
129
+ /**
130
+ * Drop every union view. Idempotent (`DROP VIEW IF EXISTS`), and tolerant
131
+ * of individual failures: detach must not be blockable by a view that is
132
+ * already gone or whose catalog vanished first, or the engine would strand
133
+ * in `detaching`.
134
+ */
135
+ export declare function dropViews(db: HybridDuckDB): Promise<void>;
108
136
  //# sourceMappingURL=warehouse.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"warehouse.d.ts","sourceRoot":"","sources":["../../src/core/warehouse.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAiCG;AAGH,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,UAAU,CAAA;AAC5C,OAAO,KAAK,EACV,aAAa,EACb,qBAAqB,EACrB,WAAW,EAEX,WAAW,EACZ,MAAM,SAAS,CAAA;AAchB,mFAAmF;AACnF,MAAM,WAAW,UAAU;IACzB,mBAAmB,EAAE,CACnB,KAAK,EAAE,MAAM,EACb,WAAW,EAAE,WAAW,EACxB,QAAQ,EAAE,MAAM,KACb,MAAM,CAAA;IACX,WAAW,EAAE,WAAW,CAAA;IACxB,qBAAqB,EAAE,qBAAqB,CAAA;IAC5C,eAAe,EAAE,MAAM,CAAA;CACxB;AAED,8EAA8E;AAC9E,MAAM,WAAW,YAAY;IAC3B,yDAAyD;IACzD,eAAe,EAAE,MAAM,CAAA;IACvB,8CAA8C;IAC9C,YAAY,EAAE,MAAM,CAAA;IACpB,sEAAsE;IACtE,cAAc,EAAE,IAAI,CAAA;IACpB,sDAAsD;IACtD,eAAe,CAAC,EAAE,MAAM,EAAE,CAAA;CAC3B;AAED;;;;GAIG;AACH,wBAAgB,mBAAmB,CAAC,QAAQ,EAAE,MAAM,GAAG,MAAM,CAE5D;AAED;;;;;GAKG;AACH,wBAAsB,eAAe,CACnC,EAAE,EAAE,YAAY,EAChB,GAAG,EAAE,aAAa,EAClB,IAAI,EAAE,UAAU,GACf,OAAO,CAAC,YAAY,CAAC,CA0FvB;AAED;;;;;;;;;GASG;AACH,wBAAsB,eAAe,CACnC,EAAE,EAAE,YAAY,EAChB,QAAQ,EAAE,MAAM,GACf,OAAO,CAAC,IAAI,CAAC,CAaf;AAID;;;;;;;;;;;;;GAaG;AACH,wBAAsB,WAAW,CAC/B,EAAE,EAAE,YAAY,EAChB,IAAI,EAAE,aAAa,GAClB,OAAO,CAAC,YAAY,CAAC,CA8BvB;AAED;;;;;;GAMG;AACH,wBAAsB,iBAAiB,CAAC,EAAE,EAAE,YAAY,GAAG,OAAO,CAAC,MAAM,CAAC,CAczE;AAED;;;;GAIG;AACH,wBAAsB,WAAW,CAC/B,GAAG,EAAE,YAAY,EACjB,SAAS,EAAE,MAAM,GAChB,OAAO,CAAC,IAAI,CAAC,CAEf"}
1
+ {"version":3,"file":"warehouse.d.ts","sourceRoot":"","sources":["../../src/core/warehouse.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAiCG;AAGH,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,UAAU,CAAA;AAE5C,OAAO,KAAK,EACV,aAAa,EACb,qBAAqB,EACrB,WAAW,EAEX,WAAW,EACZ,MAAM,SAAS,CAAA;AAchB,mFAAmF;AACnF,MAAM,WAAW,UAAU;IACzB,mBAAmB,EAAE,CACnB,KAAK,EAAE,MAAM,EACb,WAAW,EAAE,WAAW,EACxB,QAAQ,EAAE,MAAM,KACb,MAAM,CAAA;IACX,WAAW,EAAE,WAAW,CAAA;IACxB,qBAAqB,EAAE,qBAAqB,CAAA;IAC5C,eAAe,EAAE,MAAM,CAAA;CACxB;AAED,8EAA8E;AAC9E,MAAM,WAAW,YAAY;IAC3B,yDAAyD;IACzD,eAAe,EAAE,MAAM,CAAA;IACvB,8CAA8C;IAC9C,YAAY,EAAE,MAAM,CAAA;IACpB,sEAAsE;IACtE,cAAc,EAAE,IAAI,CAAA;IACpB,sDAAsD;IACtD,eAAe,CAAC,EAAE,MAAM,EAAE,CAAA;CAC3B;AAED;;;;GAIG;AACH,wBAAgB,mBAAmB,CAAC,QAAQ,EAAE,MAAM,GAAG,MAAM,CAE5D;AAED;;;;;GAKG;AACH,wBAAsB,eAAe,CACnC,EAAE,EAAE,YAAY,EAChB,GAAG,EAAE,aAAa,EAClB,IAAI,EAAE,UAAU,GACf,OAAO,CAAC,YAAY,CAAC,CA0FvB;AAED;;;;;;;;;GASG;AACH,wBAAsB,eAAe,CACnC,EAAE,EAAE,YAAY,EAChB,QAAQ,EAAE,MAAM,GACf,OAAO,CAAC,IAAI,CAAC,CAaf;AAID;;;;;;;;;;;;;GAaG;AACH,wBAAsB,WAAW,CAC/B,EAAE,EAAE,YAAY,EAChB,IAAI,EAAE,aAAa,GAClB,OAAO,CAAC,YAAY,CAAC,CA8BvB;AAED;;;;;;GAMG;AACH,wBAAsB,iBAAiB,CAAC,EAAE,EAAE,YAAY,GAAG,OAAO,CAAC,MAAM,CAAC,CAczE;AAED;;;;GAIG;AACH,wBAAsB,WAAW,CAC/B,GAAG,EAAE,YAAY,EACjB,SAAS,EAAE,MAAM,GAChB,OAAO,CAAC,IAAI,CAAC,CAEf;AAID;;;;;;;;;;;;;;GAcG;AACH,wBAAsB,WAAW,CAC/B,EAAE,EAAE,YAAY,EAChB,GAAG,EAAE;IACH,KAAK,EAAE,MAAM,CAAA;IACb,QAAQ,EAAE,MAAM,CAAA;IAChB,YAAY,EAAE,MAAM,CAAA;IACpB,aAAa,CAAC,EAAE,MAAM,CAAA;CACvB,GACA,OAAO,CAAC,IAAI,CAAC,CAaf;AAED;;;;;GAKG;AACH,wBAAsB,SAAS,CAAC,EAAE,EAAE,YAAY,GAAG,OAAO,CAAC,IAAI,CAAC,CAU/D"}
@@ -33,6 +33,7 @@
33
33
  * <phase>, cause)`.
34
34
  */
35
35
  import { AnalyticsError } from './errors';
36
+ import { dropViewDdl, generateViewDdl, VIEWED_TABLES } from './schemas';
36
37
  /**
37
38
  * Peel one layer of `AnalyticsError('query_failed')` off engine-wrapped
38
39
  * errors so the outer `attach_failed` error's `cause` chain surfaces the
@@ -200,4 +201,47 @@ export async function probeLocalCatalog(db) {
200
201
  export async function detachLocal(_db, _tenantId) {
201
202
  // intentional no-op
202
203
  }
204
+ // -------------------- union views (Sprint 5 T-06) --------------------
205
+ /**
206
+ * Create every `v_{table}` union view for the current attach.
207
+ *
208
+ * Called after migrations, so the underlying tables are guaranteed to
209
+ * exist — a view over a missing table fails at creation in DuckDB, not
210
+ * lazily at scan.
211
+ *
212
+ * The view bodies bake in `brand` + `family_id` (see `generateViewDdl` for
213
+ * why they cannot be bound parameters), which makes recreation on every
214
+ * attach a correctness requirement rather than housekeeping: a brand
215
+ * switch that reused the previous attach's views would serve the previous
216
+ * tenant's rows. `CREATE OR REPLACE` handles the overwrite; `dropViews` on
217
+ * detach closes the window where a stale view exists with no attach behind
218
+ * it.
219
+ */
220
+ export async function createViews(db, ctx) {
221
+ for (const table of VIEWED_TABLES) {
222
+ try {
223
+ await db.execute(generateViewDdl(table, ctx));
224
+ }
225
+ catch (cause) {
226
+ throw new AnalyticsError('attach_failed', `CREATE VIEW v_${table} failed`, rootCause(cause));
227
+ }
228
+ }
229
+ }
230
+ /**
231
+ * Drop every union view. Idempotent (`DROP VIEW IF EXISTS`), and tolerant
232
+ * of individual failures: detach must not be blockable by a view that is
233
+ * already gone or whose catalog vanished first, or the engine would strand
234
+ * in `detaching`.
235
+ */
236
+ export async function dropViews(db) {
237
+ for (const table of VIEWED_TABLES) {
238
+ try {
239
+ await db.execute(dropViewDdl(table));
240
+ }
241
+ catch {
242
+ // Best-effort: a failed DROP VIEW IF EXISTS means the catalog is
243
+ // already unreachable, which is the state we were aiming for.
244
+ }
245
+ }
246
+ }
203
247
  //# sourceMappingURL=warehouse.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"warehouse.js","sourceRoot":"","sources":["../../src/core/warehouse.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"warehouse.js","sourceRoot":"","sources":["../../src/core/warehouse.ts"],"names":[],"mappings":"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"}