@uasyraf/helm 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 (223) hide show
  1. package/dashboard/build/client/_app/immutable/assets/0.C_U6EcGX.css +1 -0
  2. package/dashboard/build/client/_app/immutable/assets/0.C_U6EcGX.css.br +0 -0
  3. package/dashboard/build/client/_app/immutable/assets/0.C_U6EcGX.css.gz +0 -0
  4. package/dashboard/build/client/_app/immutable/chunks/9-QirXaE.js +1 -0
  5. package/dashboard/build/client/_app/immutable/chunks/9-QirXaE.js.br +0 -0
  6. package/dashboard/build/client/_app/immutable/chunks/9-QirXaE.js.gz +0 -0
  7. package/dashboard/build/client/_app/immutable/chunks/BO5y_GWf.js +1 -0
  8. package/dashboard/build/client/_app/immutable/chunks/BO5y_GWf.js.br +0 -0
  9. package/dashboard/build/client/_app/immutable/chunks/BO5y_GWf.js.gz +0 -0
  10. package/dashboard/build/client/_app/immutable/chunks/BPuAFY6p.js +1 -0
  11. package/dashboard/build/client/_app/immutable/chunks/BPuAFY6p.js.br +0 -0
  12. package/dashboard/build/client/_app/immutable/chunks/BPuAFY6p.js.gz +0 -0
  13. package/dashboard/build/client/_app/immutable/chunks/BVbhX7IV.js +2 -0
  14. package/dashboard/build/client/_app/immutable/chunks/BVbhX7IV.js.br +0 -0
  15. package/dashboard/build/client/_app/immutable/chunks/BVbhX7IV.js.gz +0 -0
  16. package/dashboard/build/client/_app/immutable/chunks/C2WLVwTD.js +3 -0
  17. package/dashboard/build/client/_app/immutable/chunks/C2WLVwTD.js.br +0 -0
  18. package/dashboard/build/client/_app/immutable/chunks/C2WLVwTD.js.gz +0 -0
  19. package/dashboard/build/client/_app/immutable/chunks/C7hYKz2M.js +1 -0
  20. package/dashboard/build/client/_app/immutable/chunks/C7hYKz2M.js.br +0 -0
  21. package/dashboard/build/client/_app/immutable/chunks/C7hYKz2M.js.gz +0 -0
  22. package/dashboard/build/client/_app/immutable/chunks/{DYkFpqG7.js → Crvlw6v6.js} +1 -1
  23. package/dashboard/build/client/_app/immutable/chunks/Crvlw6v6.js.br +0 -0
  24. package/dashboard/build/client/_app/immutable/chunks/Crvlw6v6.js.gz +0 -0
  25. package/dashboard/build/client/_app/immutable/chunks/Cw9Pdt2b.js +1 -0
  26. package/dashboard/build/client/_app/immutable/chunks/Cw9Pdt2b.js.br +0 -0
  27. package/dashboard/build/client/_app/immutable/chunks/Cw9Pdt2b.js.gz +0 -0
  28. package/dashboard/build/client/_app/immutable/chunks/DM7ZjyFs.js +1 -0
  29. package/dashboard/build/client/_app/immutable/chunks/DM7ZjyFs.js.br +0 -0
  30. package/dashboard/build/client/_app/immutable/chunks/DM7ZjyFs.js.gz +0 -0
  31. package/dashboard/build/client/_app/immutable/chunks/{bJX5vhEj.js → DXH1e0MC.js} +1 -1
  32. package/dashboard/build/client/_app/immutable/chunks/DXH1e0MC.js.br +0 -0
  33. package/dashboard/build/client/_app/immutable/chunks/DXH1e0MC.js.gz +0 -0
  34. package/dashboard/build/client/_app/immutable/chunks/i4nhiUnk.js +1 -0
  35. package/dashboard/build/client/_app/immutable/chunks/i4nhiUnk.js.br +0 -0
  36. package/dashboard/build/client/_app/immutable/chunks/i4nhiUnk.js.gz +0 -0
  37. package/dashboard/build/client/_app/immutable/entry/app.Dy41QFU8.js +2 -0
  38. package/dashboard/build/client/_app/immutable/entry/app.Dy41QFU8.js.br +0 -0
  39. package/dashboard/build/client/_app/immutable/entry/app.Dy41QFU8.js.gz +0 -0
  40. package/dashboard/build/client/_app/immutable/entry/start.BcPFfpW6.js +1 -0
  41. package/dashboard/build/client/_app/immutable/entry/start.BcPFfpW6.js.br +2 -0
  42. package/dashboard/build/client/_app/immutable/entry/start.BcPFfpW6.js.gz +0 -0
  43. package/dashboard/build/client/_app/immutable/nodes/0.gT1IrBAt.js +1 -0
  44. package/dashboard/build/client/_app/immutable/nodes/0.gT1IrBAt.js.br +0 -0
  45. package/dashboard/build/client/_app/immutable/nodes/0.gT1IrBAt.js.gz +0 -0
  46. package/dashboard/build/client/_app/immutable/nodes/1.C1pxwGz8.js +1 -0
  47. package/dashboard/build/client/_app/immutable/nodes/1.C1pxwGz8.js.br +0 -0
  48. package/dashboard/build/client/_app/immutable/nodes/1.C1pxwGz8.js.gz +0 -0
  49. package/dashboard/build/client/_app/immutable/nodes/2.PAkYASQF.js +1 -0
  50. package/dashboard/build/client/_app/immutable/nodes/2.PAkYASQF.js.br +0 -0
  51. package/dashboard/build/client/_app/immutable/nodes/2.PAkYASQF.js.gz +0 -0
  52. package/dashboard/build/client/_app/immutable/nodes/3.qPGHwS98.js +1 -0
  53. package/dashboard/build/client/_app/immutable/nodes/3.qPGHwS98.js.br +0 -0
  54. package/dashboard/build/client/_app/immutable/nodes/3.qPGHwS98.js.gz +0 -0
  55. package/dashboard/build/client/_app/immutable/nodes/4.BY3c2oP3.js +1 -0
  56. package/dashboard/build/client/_app/immutable/nodes/4.BY3c2oP3.js.br +0 -0
  57. package/dashboard/build/client/_app/immutable/nodes/4.BY3c2oP3.js.gz +0 -0
  58. package/dashboard/build/client/_app/immutable/nodes/5.BJmkMCzP.js +1 -0
  59. package/dashboard/build/client/_app/immutable/nodes/5.BJmkMCzP.js.br +0 -0
  60. package/dashboard/build/client/_app/immutable/nodes/5.BJmkMCzP.js.gz +0 -0
  61. package/dashboard/build/client/_app/immutable/nodes/6.BQBCuyRo.js +1 -0
  62. package/dashboard/build/client/_app/immutable/nodes/6.BQBCuyRo.js.br +0 -0
  63. package/dashboard/build/client/_app/immutable/nodes/6.BQBCuyRo.js.gz +0 -0
  64. package/dashboard/build/client/_app/immutable/nodes/7.CGn9hdJ7.js +1 -0
  65. package/dashboard/build/client/_app/immutable/nodes/7.CGn9hdJ7.js.br +0 -0
  66. package/dashboard/build/client/_app/immutable/nodes/7.CGn9hdJ7.js.gz +0 -0
  67. package/dashboard/build/client/_app/immutable/nodes/8.CbXx0M8r.js +1 -0
  68. package/dashboard/build/client/_app/immutable/nodes/8.CbXx0M8r.js.br +0 -0
  69. package/dashboard/build/client/_app/immutable/nodes/8.CbXx0M8r.js.gz +0 -0
  70. package/dashboard/build/client/_app/version.json +1 -1
  71. package/dashboard/build/client/_app/version.json.br +0 -0
  72. package/dashboard/build/client/_app/version.json.gz +0 -0
  73. package/dashboard/build/server/chunks/0-CuCI8vso.js +33 -0
  74. package/dashboard/build/server/chunks/0-CuCI8vso.js.map +1 -0
  75. package/dashboard/build/server/chunks/1-BRujd2KF.js +9 -0
  76. package/dashboard/build/server/chunks/{1-BDkdOGL6.js.map → 1-BRujd2KF.js.map} +1 -1
  77. package/dashboard/build/server/chunks/2-CdivLqAU.js +36 -0
  78. package/dashboard/build/server/chunks/2-CdivLqAU.js.map +1 -0
  79. package/dashboard/build/server/chunks/3-D2TMWb8-.js +41 -0
  80. package/dashboard/build/server/chunks/3-D2TMWb8-.js.map +1 -0
  81. package/dashboard/build/server/chunks/{2-BLt1vNET.js → 4-CATS6czN.js} +17 -13
  82. package/dashboard/build/server/chunks/4-CATS6czN.js.map +1 -0
  83. package/dashboard/build/server/chunks/5-DmUG37hB.js +45 -0
  84. package/dashboard/build/server/chunks/5-DmUG37hB.js.map +1 -0
  85. package/dashboard/build/server/chunks/6--04CRhxN.js +43 -0
  86. package/dashboard/build/server/chunks/6--04CRhxN.js.map +1 -0
  87. package/dashboard/build/server/chunks/7--ahyXjMz.js +34 -0
  88. package/dashboard/build/server/chunks/7--ahyXjMz.js.map +1 -0
  89. package/dashboard/build/server/chunks/8-B8pO7UFU.js +56 -0
  90. package/dashboard/build/server/chunks/8-B8pO7UFU.js.map +1 -0
  91. package/dashboard/build/server/chunks/_layout.svelte-gEHTl1KG.js +36 -0
  92. package/dashboard/build/server/chunks/_layout.svelte-gEHTl1KG.js.map +1 -0
  93. package/dashboard/build/server/chunks/_layout.svelte-vH4YFBaG.js +45 -0
  94. package/dashboard/build/server/chunks/_layout.svelte-vH4YFBaG.js.map +1 -0
  95. package/dashboard/build/server/chunks/_page.svelte-2co8EQvy.js +25 -0
  96. package/dashboard/build/server/chunks/_page.svelte-2co8EQvy.js.map +1 -0
  97. package/dashboard/build/server/chunks/{_page.svelte-C_NO0kPy.js → _page.svelte-BF5kOI2R.js} +2 -2
  98. package/dashboard/build/server/chunks/_page.svelte-BF5kOI2R.js.map +1 -0
  99. package/dashboard/build/server/chunks/_page.svelte-BGS-bwra.js.map +1 -1
  100. package/dashboard/build/server/chunks/_page.svelte-BiRjdIbl.js.map +1 -1
  101. package/dashboard/build/server/chunks/_page.svelte-DvSQBjcA.js.map +1 -1
  102. package/dashboard/build/server/chunks/_page.svelte-ZUq8J-ew.js.map +1 -1
  103. package/dashboard/build/server/chunks/db-GHaWnz-k.js +806 -0
  104. package/dashboard/build/server/chunks/db-GHaWnz-k.js.map +1 -0
  105. package/dashboard/build/server/chunks/{error.svelte-DJ3O9Tia.js → error.svelte-B8bxgmvK.js} +3 -3
  106. package/dashboard/build/server/chunks/{error.svelte-DJ3O9Tia.js.map → error.svelte-B8bxgmvK.js.map} +1 -1
  107. package/dashboard/build/server/chunks/{exports-BnaAAAnL.js → exports-CzH4-eZs.js} +41 -9
  108. package/dashboard/build/server/chunks/exports-CzH4-eZs.js.map +1 -0
  109. package/dashboard/build/server/chunks/{index-DwR_KaNY.js → index-CfWSWN1f.js} +8 -3
  110. package/dashboard/build/server/chunks/index-CfWSWN1f.js.map +1 -0
  111. package/dashboard/build/server/chunks/{index-lhTMmBNn.js → index-NcxaM188.js} +31 -2
  112. package/dashboard/build/server/chunks/{index-lhTMmBNn.js.map → index-NcxaM188.js.map} +1 -1
  113. package/dashboard/build/server/chunks/queries-OsSUm9xY.js +58 -0
  114. package/dashboard/build/server/chunks/queries-OsSUm9xY.js.map +1 -0
  115. package/dashboard/build/server/index.js +3 -3
  116. package/dashboard/build/server/index.js.map +1 -1
  117. package/dashboard/build/server/manifest.js +34 -25
  118. package/dashboard/build/server/manifest.js.map +1 -1
  119. package/dist/bin/helm.js +20 -1
  120. package/dist/bin/helm.js.map +1 -1
  121. package/dist/server/src/db/bootstrap.js +19 -0
  122. package/dist/server/src/db/bootstrap.js.map +1 -1
  123. package/dist/server/src/db/open-repo.js +2 -2
  124. package/dist/server/src/db/open-repo.js.map +1 -1
  125. package/dist/server/src/db/pg-bootstrap.js +14 -0
  126. package/dist/server/src/db/pg-bootstrap.js.map +1 -1
  127. package/dist/server/src/db/repo-pg.js +6 -2
  128. package/dist/server/src/db/repo-pg.js.map +1 -1
  129. package/dist/server/src/db/repo-sqlite.js +5 -2
  130. package/dist/server/src/db/repo-sqlite.js.map +1 -1
  131. package/dist/server/src/db/repo.d.ts +1 -0
  132. package/dist/server/src/db/schema-pg.d.ts +34 -0
  133. package/dist/server/src/db/schema-pg.js +1 -0
  134. package/dist/server/src/db/schema-pg.js.map +1 -1
  135. package/dist/server/src/db/schema.d.ts +34 -0
  136. package/dist/server/src/db/schema.js +1 -0
  137. package/dist/server/src/db/schema.js.map +1 -1
  138. package/dist/server/src/install.js +6 -7
  139. package/dist/server/src/install.js.map +1 -1
  140. package/dist/server/src/migrate.d.ts +13 -0
  141. package/dist/server/src/migrate.js +99 -0
  142. package/dist/server/src/migrate.js.map +1 -0
  143. package/dist/server/src/tools/story.js +1 -0
  144. package/dist/server/src/tools/story.js.map +1 -1
  145. package/dist/server/src/util/paths.d.ts +2 -1
  146. package/dist/server/src/util/paths.js +4 -1
  147. package/dist/server/src/util/paths.js.map +1 -1
  148. package/hooks/hooks.json +0 -5
  149. package/package.json +1 -1
  150. package/dashboard/build/client/_app/immutable/assets/0.DPthOi2j.css +0 -1
  151. package/dashboard/build/client/_app/immutable/assets/0.DPthOi2j.css.br +0 -0
  152. package/dashboard/build/client/_app/immutable/assets/0.DPthOi2j.css.gz +0 -0
  153. package/dashboard/build/client/_app/immutable/chunks/B3NJzl7g.js +0 -1
  154. package/dashboard/build/client/_app/immutable/chunks/B3NJzl7g.js.br +0 -0
  155. package/dashboard/build/client/_app/immutable/chunks/B3NJzl7g.js.gz +0 -0
  156. package/dashboard/build/client/_app/immutable/chunks/Bvgn0Gys.js +0 -1
  157. package/dashboard/build/client/_app/immutable/chunks/Bvgn0Gys.js.br +0 -0
  158. package/dashboard/build/client/_app/immutable/chunks/Bvgn0Gys.js.gz +0 -0
  159. package/dashboard/build/client/_app/immutable/chunks/C72aErMY.js +0 -3
  160. package/dashboard/build/client/_app/immutable/chunks/C72aErMY.js.br +0 -0
  161. package/dashboard/build/client/_app/immutable/chunks/C72aErMY.js.gz +0 -0
  162. package/dashboard/build/client/_app/immutable/chunks/CjpPs8iz.js +0 -1
  163. package/dashboard/build/client/_app/immutable/chunks/CjpPs8iz.js.br +0 -0
  164. package/dashboard/build/client/_app/immutable/chunks/CjpPs8iz.js.gz +0 -0
  165. package/dashboard/build/client/_app/immutable/chunks/DNLp8810.js +0 -1
  166. package/dashboard/build/client/_app/immutable/chunks/DNLp8810.js.br +0 -0
  167. package/dashboard/build/client/_app/immutable/chunks/DNLp8810.js.gz +0 -0
  168. package/dashboard/build/client/_app/immutable/chunks/DYkFpqG7.js.br +0 -0
  169. package/dashboard/build/client/_app/immutable/chunks/DYkFpqG7.js.gz +0 -0
  170. package/dashboard/build/client/_app/immutable/chunks/DsiL0ppy.js +0 -2
  171. package/dashboard/build/client/_app/immutable/chunks/DsiL0ppy.js.br +0 -0
  172. package/dashboard/build/client/_app/immutable/chunks/DsiL0ppy.js.gz +0 -0
  173. package/dashboard/build/client/_app/immutable/chunks/bJX5vhEj.js.br +0 -0
  174. package/dashboard/build/client/_app/immutable/chunks/bJX5vhEj.js.gz +0 -0
  175. package/dashboard/build/client/_app/immutable/chunks/gQDp4_Ul.js +0 -1
  176. package/dashboard/build/client/_app/immutable/chunks/gQDp4_Ul.js.br +0 -0
  177. package/dashboard/build/client/_app/immutable/chunks/gQDp4_Ul.js.gz +0 -0
  178. package/dashboard/build/client/_app/immutable/entry/app.D4j9hUjJ.js +0 -2
  179. package/dashboard/build/client/_app/immutable/entry/app.D4j9hUjJ.js.br +0 -0
  180. package/dashboard/build/client/_app/immutable/entry/app.D4j9hUjJ.js.gz +0 -0
  181. package/dashboard/build/client/_app/immutable/entry/start.D59wIHuS.js +0 -1
  182. package/dashboard/build/client/_app/immutable/entry/start.D59wIHuS.js.br +0 -2
  183. package/dashboard/build/client/_app/immutable/entry/start.D59wIHuS.js.gz +0 -0
  184. package/dashboard/build/client/_app/immutable/nodes/0.HocD0HAQ.js +0 -1
  185. package/dashboard/build/client/_app/immutable/nodes/0.HocD0HAQ.js.br +0 -0
  186. package/dashboard/build/client/_app/immutable/nodes/0.HocD0HAQ.js.gz +0 -0
  187. package/dashboard/build/client/_app/immutable/nodes/1.xo_a-jPh.js +0 -1
  188. package/dashboard/build/client/_app/immutable/nodes/1.xo_a-jPh.js.br +0 -0
  189. package/dashboard/build/client/_app/immutable/nodes/1.xo_a-jPh.js.gz +0 -0
  190. package/dashboard/build/client/_app/immutable/nodes/2.BwywD4n3.js +0 -1
  191. package/dashboard/build/client/_app/immutable/nodes/2.BwywD4n3.js.br +0 -0
  192. package/dashboard/build/client/_app/immutable/nodes/2.BwywD4n3.js.gz +0 -0
  193. package/dashboard/build/client/_app/immutable/nodes/3.BGY0bNfC.js +0 -1
  194. package/dashboard/build/client/_app/immutable/nodes/3.BGY0bNfC.js.br +0 -0
  195. package/dashboard/build/client/_app/immutable/nodes/3.BGY0bNfC.js.gz +0 -0
  196. package/dashboard/build/client/_app/immutable/nodes/4.C7uIivCS.js +0 -1
  197. package/dashboard/build/client/_app/immutable/nodes/4.C7uIivCS.js.br +0 -0
  198. package/dashboard/build/client/_app/immutable/nodes/4.C7uIivCS.js.gz +0 -0
  199. package/dashboard/build/client/_app/immutable/nodes/5.YszfczJW.js +0 -1
  200. package/dashboard/build/client/_app/immutable/nodes/5.YszfczJW.js.br +0 -0
  201. package/dashboard/build/client/_app/immutable/nodes/5.YszfczJW.js.gz +0 -0
  202. package/dashboard/build/client/_app/immutable/nodes/6.7fhKcbBK.js +0 -1
  203. package/dashboard/build/client/_app/immutable/nodes/6.7fhKcbBK.js.br +0 -0
  204. package/dashboard/build/client/_app/immutable/nodes/6.7fhKcbBK.js.gz +0 -0
  205. package/dashboard/build/server/chunks/0-DUUsxI66.js +0 -40
  206. package/dashboard/build/server/chunks/0-DUUsxI66.js.map +0 -1
  207. package/dashboard/build/server/chunks/1-BDkdOGL6.js +0 -9
  208. package/dashboard/build/server/chunks/2-BLt1vNET.js.map +0 -1
  209. package/dashboard/build/server/chunks/3-B-4sxMk4.js +0 -41
  210. package/dashboard/build/server/chunks/3-B-4sxMk4.js.map +0 -1
  211. package/dashboard/build/server/chunks/4-CRZIwHJO.js +0 -39
  212. package/dashboard/build/server/chunks/4-CRZIwHJO.js.map +0 -1
  213. package/dashboard/build/server/chunks/5-CwiVOtz6.js +0 -30
  214. package/dashboard/build/server/chunks/5-CwiVOtz6.js.map +0 -1
  215. package/dashboard/build/server/chunks/6-mID2_gX2.js +0 -53
  216. package/dashboard/build/server/chunks/6-mID2_gX2.js.map +0 -1
  217. package/dashboard/build/server/chunks/_layout.svelte-DeOKequ-.js +0 -31
  218. package/dashboard/build/server/chunks/_layout.svelte-DeOKequ-.js.map +0 -1
  219. package/dashboard/build/server/chunks/_page.svelte-C_NO0kPy.js.map +0 -1
  220. package/dashboard/build/server/chunks/exports-BnaAAAnL.js.map +0 -1
  221. package/dashboard/build/server/chunks/index-DwR_KaNY.js.map +0 -1
  222. package/dashboard/build/server/chunks/queries-DGWi-KlP.js +0 -198
  223. package/dashboard/build/server/chunks/queries-DGWi-KlP.js.map +0 -1
@@ -0,0 +1,806 @@
1
+ import { createClient } from '@libsql/client';
2
+ import { drizzle } from 'drizzle-orm/libsql';
3
+ import { join } from 'node:path';
4
+ import { homedir } from 'node:os';
5
+ import { sqliteTable, text as text$1, integer as integer$1 } from 'drizzle-orm/sqlite-core';
6
+ import { pgTable, text, integer, boolean } from 'drizzle-orm/pg-core';
7
+ import { and, eq, desc, sql, isNull, ne } from 'drizzle-orm';
8
+
9
+ const project$1 = sqliteTable("project", {
10
+ id: text$1("id").primaryKey(),
11
+ slug: text$1("slug").notNull().unique(),
12
+ name: text$1("name").notNull(),
13
+ gitRemote: text$1("git_remote"),
14
+ dod: text$1("dod"),
15
+ sprintLengthDays: integer$1("sprint_length_days").notNull().default(14),
16
+ wipEnabled: integer$1("wip_enabled", { mode: "boolean" }).notNull().default(false),
17
+ estimationEnabled: integer$1("estimation_enabled", { mode: "boolean" }).notNull().default(true),
18
+ createdAt: text$1("created_at").notNull()
19
+ });
20
+ const developer$1 = sqliteTable("developer", {
21
+ id: text$1("id").primaryKey(),
22
+ projectId: text$1("project_id").notNull().references(() => project$1.id),
23
+ handle: text$1("handle").notNull(),
24
+ email: text$1("email"),
25
+ lastSeenAt: text$1("last_seen_at").notNull()
26
+ });
27
+ const sprint$1 = sqliteTable("sprint", {
28
+ id: text$1("id").primaryKey(),
29
+ projectId: text$1("project_id").notNull().references(() => project$1.id),
30
+ name: text$1("name").notNull(),
31
+ goal: text$1("goal"),
32
+ startedAt: text$1("started_at").notNull(),
33
+ endedAt: text$1("ended_at"),
34
+ status: text$1("status").notNull(),
35
+ wipLimit: integer$1("wip_limit")
36
+ });
37
+ const epic$1 = sqliteTable("epic", {
38
+ id: text$1("id").primaryKey(),
39
+ projectId: text$1("project_id").notNull().references(() => project$1.id),
40
+ title: text$1("title").notNull(),
41
+ description: text$1("description"),
42
+ status: text$1("status").notNull().default("open"),
43
+ priority: integer$1("priority").notNull().default(3),
44
+ targetSprintId: text$1("target_sprint_id").references(() => sprint$1.id),
45
+ createdAt: text$1("created_at").notNull()
46
+ });
47
+ const story$1 = sqliteTable("story", {
48
+ id: text$1("id").primaryKey(),
49
+ projectId: text$1("project_id").notNull().references(() => project$1.id),
50
+ epicId: text$1("epic_id").references(() => epic$1.id),
51
+ sprintId: text$1("sprint_id").references(() => sprint$1.id),
52
+ title: text$1("title").notNull(),
53
+ description: text$1("description"),
54
+ acceptance: text$1("acceptance"),
55
+ status: text$1("status").notNull().default("backlog"),
56
+ size: text$1("size"),
57
+ assigneeId: text$1("assignee_id").references(() => developer$1.id),
58
+ priority: integer$1("priority").notNull().default(3),
59
+ startedAt: text$1("started_at"),
60
+ completedAt: text$1("completed_at"),
61
+ createdAt: text$1("created_at").notNull()
62
+ });
63
+ const task$1 = sqliteTable("task", {
64
+ id: text$1("id").primaryKey(),
65
+ storyId: text$1("story_id").notNull().references(() => story$1.id),
66
+ assigneeId: text$1("assignee_id").references(() => developer$1.id),
67
+ title: text$1("title").notNull(),
68
+ status: text$1("status").notNull().default("todo"),
69
+ blockedBy: text$1("blocked_by"),
70
+ createdAt: text$1("created_at").notNull()
71
+ });
72
+ const techDebt$1 = sqliteTable("tech_debt", {
73
+ id: text$1("id").primaryKey(),
74
+ projectId: text$1("project_id").notNull().references(() => project$1.id),
75
+ title: text$1("title").notNull(),
76
+ description: text$1("description"),
77
+ severity: text$1("severity").notNull().default("med"),
78
+ location: text$1("location"),
79
+ ownerId: text$1("owner_id").references(() => developer$1.id),
80
+ expiresAt: text$1("expires_at"),
81
+ openedAt: text$1("opened_at").notNull(),
82
+ closedAt: text$1("closed_at"),
83
+ linkedStoryId: text$1("linked_story_id").references(() => story$1.id)
84
+ });
85
+ const decision$1 = sqliteTable("decision", {
86
+ id: text$1("id").primaryKey(),
87
+ projectId: text$1("project_id").notNull().references(() => project$1.id),
88
+ title: text$1("title").notNull(),
89
+ context: text$1("context"),
90
+ decision: text$1("decision").notNull(),
91
+ status: text$1("status").notNull().default("accepted"),
92
+ decidedAt: text$1("decided_at").notNull()
93
+ });
94
+ const progressEvent$1 = sqliteTable("progress_event", {
95
+ id: text$1("id").primaryKey(),
96
+ projectId: text$1("project_id").notNull().references(() => project$1.id),
97
+ developerId: text$1("developer_id").references(() => developer$1.id),
98
+ sprintId: text$1("sprint_id").references(() => sprint$1.id),
99
+ kind: text$1("kind").notNull(),
100
+ refId: text$1("ref_id"),
101
+ summary: text$1("summary").notNull(),
102
+ ts: text$1("ts").notNull()
103
+ });
104
+ const schema$1 = {
105
+ project: project$1,
106
+ developer: developer$1,
107
+ sprint: sprint$1,
108
+ epic: epic$1,
109
+ story: story$1,
110
+ task: task$1,
111
+ techDebt: techDebt$1,
112
+ decision: decision$1,
113
+ progressEvent: progressEvent$1
114
+ };
115
+ const project = pgTable("project", {
116
+ id: text("id").primaryKey(),
117
+ slug: text("slug").notNull().unique(),
118
+ name: text("name").notNull(),
119
+ gitRemote: text("git_remote"),
120
+ dod: text("dod"),
121
+ sprintLengthDays: integer("sprint_length_days").notNull().default(14),
122
+ wipEnabled: boolean("wip_enabled").notNull().default(false),
123
+ estimationEnabled: boolean("estimation_enabled").notNull().default(true),
124
+ createdAt: text("created_at").notNull()
125
+ });
126
+ const developer = pgTable("developer", {
127
+ id: text("id").primaryKey(),
128
+ projectId: text("project_id").notNull().references(() => project.id),
129
+ handle: text("handle").notNull(),
130
+ email: text("email"),
131
+ lastSeenAt: text("last_seen_at").notNull()
132
+ });
133
+ const sprint = pgTable("sprint", {
134
+ id: text("id").primaryKey(),
135
+ projectId: text("project_id").notNull().references(() => project.id),
136
+ name: text("name").notNull(),
137
+ goal: text("goal"),
138
+ startedAt: text("started_at").notNull(),
139
+ endedAt: text("ended_at"),
140
+ status: text("status").notNull(),
141
+ wipLimit: integer("wip_limit")
142
+ });
143
+ const epic = pgTable("epic", {
144
+ id: text("id").primaryKey(),
145
+ projectId: text("project_id").notNull().references(() => project.id),
146
+ title: text("title").notNull(),
147
+ description: text("description"),
148
+ status: text("status").notNull().default("open"),
149
+ priority: integer("priority").notNull().default(3),
150
+ targetSprintId: text("target_sprint_id").references(() => sprint.id),
151
+ createdAt: text("created_at").notNull()
152
+ });
153
+ const story = pgTable("story", {
154
+ id: text("id").primaryKey(),
155
+ projectId: text("project_id").notNull().references(() => project.id),
156
+ epicId: text("epic_id").references(() => epic.id),
157
+ sprintId: text("sprint_id").references(() => sprint.id),
158
+ title: text("title").notNull(),
159
+ description: text("description"),
160
+ acceptance: text("acceptance"),
161
+ status: text("status").notNull().default("backlog"),
162
+ size: text("size"),
163
+ assigneeId: text("assignee_id").references(() => developer.id),
164
+ priority: integer("priority").notNull().default(3),
165
+ startedAt: text("started_at"),
166
+ completedAt: text("completed_at"),
167
+ createdAt: text("created_at").notNull()
168
+ });
169
+ const task = pgTable("task", {
170
+ id: text("id").primaryKey(),
171
+ storyId: text("story_id").notNull().references(() => story.id),
172
+ assigneeId: text("assignee_id").references(() => developer.id),
173
+ title: text("title").notNull(),
174
+ status: text("status").notNull().default("todo"),
175
+ blockedBy: text("blocked_by"),
176
+ createdAt: text("created_at").notNull()
177
+ });
178
+ const techDebt = pgTable("tech_debt", {
179
+ id: text("id").primaryKey(),
180
+ projectId: text("project_id").notNull().references(() => project.id),
181
+ title: text("title").notNull(),
182
+ description: text("description"),
183
+ severity: text("severity").notNull().default("med"),
184
+ location: text("location"),
185
+ ownerId: text("owner_id").references(() => developer.id),
186
+ expiresAt: text("expires_at"),
187
+ openedAt: text("opened_at").notNull(),
188
+ closedAt: text("closed_at"),
189
+ linkedStoryId: text("linked_story_id").references(() => story.id)
190
+ });
191
+ const decision = pgTable("decision", {
192
+ id: text("id").primaryKey(),
193
+ projectId: text("project_id").notNull().references(() => project.id),
194
+ title: text("title").notNull(),
195
+ context: text("context"),
196
+ decision: text("decision").notNull(),
197
+ status: text("status").notNull().default("accepted"),
198
+ decidedAt: text("decided_at").notNull()
199
+ });
200
+ const progressEvent = pgTable("progress_event", {
201
+ id: text("id").primaryKey(),
202
+ projectId: text("project_id").notNull().references(() => project.id),
203
+ developerId: text("developer_id").references(() => developer.id),
204
+ sprintId: text("sprint_id").references(() => sprint.id),
205
+ kind: text("kind").notNull(),
206
+ refId: text("ref_id"),
207
+ summary: text("summary").notNull(),
208
+ ts: text("ts").notNull()
209
+ });
210
+ const schema = {
211
+ project,
212
+ developer,
213
+ sprint,
214
+ epic,
215
+ story,
216
+ task,
217
+ techDebt,
218
+ decision,
219
+ progressEvent
220
+ };
221
+ function makeSqliteRepo(db) {
222
+ return {
223
+ async findProjectBySlug(slug) {
224
+ const rows = await db.select().from(project$1).where(eq(project$1.slug, slug)).limit(1);
225
+ return rows[0] ?? null;
226
+ },
227
+ async findAllProjects() {
228
+ return db.select().from(project$1).orderBy(project$1.name);
229
+ },
230
+ async insertProject(row) {
231
+ await db.insert(project$1).values(row);
232
+ },
233
+ async findDeveloperByHandle(projectId, handle) {
234
+ const rows = await db.select().from(developer$1).where(and(eq(developer$1.projectId, projectId), eq(developer$1.handle, handle))).limit(1);
235
+ return rows[0] ?? null;
236
+ },
237
+ async insertDeveloper(row) {
238
+ await db.insert(developer$1).values(row);
239
+ },
240
+ async touchDeveloper(id, lastSeenAt) {
241
+ await db.update(developer$1).set({ lastSeenAt }).where(eq(developer$1.id, id));
242
+ },
243
+ async findDevelopersByProject(projectId) {
244
+ return db.select().from(developer$1).where(eq(developer$1.projectId, projectId)).orderBy(desc(developer$1.lastSeenAt));
245
+ },
246
+ async findActiveSprint(projectId) {
247
+ const rows = await db.select().from(sprint$1).where(and(eq(sprint$1.projectId, projectId), eq(sprint$1.status, "active"))).limit(1);
248
+ return rows[0] ?? null;
249
+ },
250
+ async findSprintById(id) {
251
+ const rows = await db.select().from(sprint$1).where(eq(sprint$1.id, id)).limit(1);
252
+ return rows[0] ?? null;
253
+ },
254
+ async findSprintsByProject(projectId) {
255
+ return db.select().from(sprint$1).where(eq(sprint$1.projectId, projectId)).orderBy(desc(sprint$1.startedAt));
256
+ },
257
+ async insertSprint(row) {
258
+ await db.insert(sprint$1).values(row);
259
+ },
260
+ async updateSprint(id, updates) {
261
+ await db.update(sprint$1).set(updates).where(eq(sprint$1.id, id));
262
+ },
263
+ async closeActiveSprints(projectId, endedAt) {
264
+ await db.update(sprint$1).set({ status: "closed", endedAt }).where(and(eq(sprint$1.projectId, projectId), eq(sprint$1.status, "active")));
265
+ },
266
+ async countSprintsByProject(projectId) {
267
+ const rows = await db.select({ c: sql`count(*)` }).from(sprint$1).where(eq(sprint$1.projectId, projectId));
268
+ return rows[0]?.c ?? 0;
269
+ },
270
+ async insertEpic(row) {
271
+ await db.insert(epic$1).values(row);
272
+ },
273
+ async updateEpic(id, updates) {
274
+ await db.update(epic$1).set(updates).where(eq(epic$1.id, id));
275
+ },
276
+ async findEpicsByProject(projectId) {
277
+ return db.select().from(epic$1).where(eq(epic$1.projectId, projectId)).orderBy(epic$1.priority);
278
+ },
279
+ async insertStory(row) {
280
+ await db.insert(story$1).values(row);
281
+ },
282
+ async updateStory(id, updates) {
283
+ await db.update(story$1).set(updates).where(eq(story$1.id, id));
284
+ },
285
+ async findStoryById(id) {
286
+ const rows = await db.select().from(story$1).where(eq(story$1.id, id)).limit(1);
287
+ return rows[0] ?? null;
288
+ },
289
+ async findStoriesInSprint(sprintId) {
290
+ return db.select().from(story$1).where(eq(story$1.sprintId, sprintId)).orderBy(story$1.priority);
291
+ },
292
+ async findStoriesInSprintNotDoneOrDropped(sprintId) {
293
+ return db.select().from(story$1).where(and(eq(story$1.sprintId, sprintId), ne(story$1.status, "done"), ne(story$1.status, "dropped")));
294
+ },
295
+ async rolloverIncompleteStoriesToBacklog(sprintId) {
296
+ const incomplete = await db.select({ id: story$1.id }).from(story$1).where(and(eq(story$1.sprintId, sprintId), ne(story$1.status, "done"), ne(story$1.status, "dropped")));
297
+ if (incomplete.length === 0) return 0;
298
+ await db.update(story$1).set({ sprintId: null, status: "backlog" }).where(and(eq(story$1.sprintId, sprintId), ne(story$1.status, "done"), ne(story$1.status, "dropped")));
299
+ return incomplete.length;
300
+ },
301
+ async findBacklogStories(projectId, limit) {
302
+ return db.select().from(story$1).where(and(eq(story$1.projectId, projectId), isNull(story$1.sprintId), eq(story$1.status, "backlog"))).orderBy(sql`priority asc, created_at asc`).limit(limit);
303
+ },
304
+ async countStoriesInSprintByStatus(sprintId) {
305
+ const rows = await db.select({ status: story$1.status, count: sql`count(*)` }).from(story$1).where(eq(story$1.sprintId, sprintId)).groupBy(story$1.status);
306
+ const out = {};
307
+ for (const r of rows) out[r.status] = r.count;
308
+ return out;
309
+ },
310
+ async countBacklog(projectId) {
311
+ const rows = await db.select({ c: sql`count(*)` }).from(story$1).where(and(eq(story$1.projectId, projectId), eq(story$1.status, "backlog"), isNull(story$1.sprintId)));
312
+ return rows[0]?.c ?? 0;
313
+ },
314
+ async countDoneStoriesInSprint(sprintId) {
315
+ const rows = await db.select({ c: sql`count(*)` }).from(story$1).where(and(eq(story$1.sprintId, sprintId), eq(story$1.status, "done")));
316
+ return rows[0]?.c ?? 0;
317
+ },
318
+ async insertTask(row) {
319
+ await db.insert(task$1).values(row);
320
+ },
321
+ async updateTask(id, updates) {
322
+ await db.update(task$1).set(updates).where(eq(task$1.id, id));
323
+ },
324
+ async insertDebt(row) {
325
+ await db.insert(techDebt$1).values(row);
326
+ },
327
+ async closeDebt(id, closedAt) {
328
+ await db.update(techDebt$1).set({ closedAt }).where(eq(techDebt$1.id, id));
329
+ },
330
+ async findOpenDebtByProject(projectId, limit) {
331
+ return db.select().from(techDebt$1).where(and(eq(techDebt$1.projectId, projectId), isNull(techDebt$1.closedAt))).orderBy(sql`severity desc, opened_at desc`).limit(limit);
332
+ },
333
+ async findAllDebtByProject(projectId, limit) {
334
+ return db.select().from(techDebt$1).where(eq(techDebt$1.projectId, projectId)).orderBy(sql`closed_at is null desc, severity desc, opened_at desc`).limit(limit);
335
+ },
336
+ async findOpenDebtAtLocation(projectId, location) {
337
+ const rows = await db.select().from(techDebt$1).where(and(eq(techDebt$1.projectId, projectId), eq(techDebt$1.location, location), isNull(techDebt$1.closedAt))).limit(1);
338
+ return rows[0] ?? null;
339
+ },
340
+ async countOpenDebtByProject(projectId) {
341
+ const rows = await db.select({ c: sql`count(*)` }).from(techDebt$1).where(and(eq(techDebt$1.projectId, projectId), isNull(techDebt$1.closedAt)));
342
+ return rows[0]?.c ?? 0;
343
+ },
344
+ async insertDecision(row) {
345
+ await db.insert(decision$1).values(row);
346
+ },
347
+ async findDecisionsByProject(projectId, limit) {
348
+ return db.select().from(decision$1).where(eq(decision$1.projectId, projectId)).orderBy(desc(decision$1.decidedAt)).limit(limit);
349
+ },
350
+ async emitEvent(row) {
351
+ await db.insert(progressEvent$1).values(row);
352
+ },
353
+ async findRecentEvents(projectId, limit) {
354
+ return db.select().from(progressEvent$1).where(eq(progressEvent$1.projectId, projectId)).orderBy(desc(progressEvent$1.ts)).limit(limit);
355
+ },
356
+ async findEventsForSprint(sprintId, limit) {
357
+ return db.select().from(progressEvent$1).where(eq(progressEvent$1.sprintId, sprintId)).orderBy(desc(progressEvent$1.ts)).limit(limit);
358
+ },
359
+ async countEventsByKindInSprint(sprintId, kind) {
360
+ const rows = await db.select({ c: sql`count(*)` }).from(progressEvent$1).where(and(eq(progressEvent$1.sprintId, sprintId), eq(progressEvent$1.kind, kind)));
361
+ return rows[0]?.c ?? 0;
362
+ },
363
+ async findEventsByDeveloper(projectId, developerId, limit) {
364
+ return db.select().from(progressEvent$1).where(and(eq(progressEvent$1.projectId, projectId), eq(progressEvent$1.developerId, developerId))).orderBy(desc(progressEvent$1.ts)).limit(limit);
365
+ }
366
+ };
367
+ }
368
+ function makePgRepo(db) {
369
+ const pg = db;
370
+ return {
371
+ async findProjectBySlug(slug) {
372
+ const rows = await pg.select().from(project).where(eq(project.slug, slug)).limit(1);
373
+ return rows[0] ?? null;
374
+ },
375
+ async findAllProjects() {
376
+ const rows = await pg.select().from(project).orderBy(project.name);
377
+ return rows;
378
+ },
379
+ async insertProject(row) {
380
+ await pg.insert(project).values(row);
381
+ },
382
+ async findDeveloperByHandle(projectId, handle) {
383
+ const rows = await pg.select().from(developer).where(and(eq(developer.projectId, projectId), eq(developer.handle, handle))).limit(1);
384
+ return rows[0] ?? null;
385
+ },
386
+ async insertDeveloper(row) {
387
+ await pg.insert(developer).values(row);
388
+ },
389
+ async touchDeveloper(id, lastSeenAt) {
390
+ await pg.update(developer).set({ lastSeenAt }).where(eq(developer.id, id));
391
+ },
392
+ async findDevelopersByProject(projectId) {
393
+ const rows = await pg.select().from(developer).where(eq(developer.projectId, projectId)).orderBy(desc(developer.lastSeenAt));
394
+ return rows;
395
+ },
396
+ async findActiveSprint(projectId) {
397
+ const rows = await pg.select().from(sprint).where(and(eq(sprint.projectId, projectId), eq(sprint.status, "active"))).limit(1);
398
+ return rows[0] ?? null;
399
+ },
400
+ async findSprintById(id) {
401
+ const rows = await pg.select().from(sprint).where(eq(sprint.id, id)).limit(1);
402
+ return rows[0] ?? null;
403
+ },
404
+ async findSprintsByProject(projectId) {
405
+ const rows = await pg.select().from(sprint).where(eq(sprint.projectId, projectId)).orderBy(desc(sprint.startedAt));
406
+ return rows;
407
+ },
408
+ async insertSprint(row) {
409
+ await pg.insert(sprint).values(row);
410
+ },
411
+ async updateSprint(id, updates) {
412
+ await pg.update(sprint).set(updates).where(eq(sprint.id, id));
413
+ },
414
+ async closeActiveSprints(projectId, endedAt) {
415
+ await pg.update(sprint).set({ status: "closed", endedAt }).where(and(eq(sprint.projectId, projectId), eq(sprint.status, "active")));
416
+ },
417
+ async countSprintsByProject(projectId) {
418
+ const rows = await pg.select({ c: sql`count(*)::int` }).from(sprint).where(eq(sprint.projectId, projectId));
419
+ return Number(rows[0]?.c ?? 0);
420
+ },
421
+ async insertEpic(row) {
422
+ await pg.insert(epic).values(row);
423
+ },
424
+ async updateEpic(id, updates) {
425
+ await pg.update(epic).set(updates).where(eq(epic.id, id));
426
+ },
427
+ async findEpicsByProject(projectId) {
428
+ const rows = await pg.select().from(epic).where(eq(epic.projectId, projectId)).orderBy(epic.priority);
429
+ return rows;
430
+ },
431
+ async insertStory(row) {
432
+ await pg.insert(story).values(row);
433
+ },
434
+ async updateStory(id, updates) {
435
+ await pg.update(story).set(updates).where(eq(story.id, id));
436
+ },
437
+ async findStoryById(id) {
438
+ const rows = await pg.select().from(story).where(eq(story.id, id)).limit(1);
439
+ return rows[0] ?? null;
440
+ },
441
+ async findStoriesInSprint(sprintId) {
442
+ const rows = await pg.select().from(story).where(eq(story.sprintId, sprintId)).orderBy(story.priority);
443
+ return rows;
444
+ },
445
+ async findStoriesInSprintNotDoneOrDropped(sprintId) {
446
+ const rows = await pg.select().from(story).where(and(eq(story.sprintId, sprintId), ne(story.status, "done"), ne(story.status, "dropped")));
447
+ return rows;
448
+ },
449
+ async rolloverIncompleteStoriesToBacklog(sprintId) {
450
+ const incomplete = await pg.select({ id: story.id }).from(story).where(and(eq(story.sprintId, sprintId), ne(story.status, "done"), ne(story.status, "dropped")));
451
+ if (incomplete.length === 0) return 0;
452
+ await pg.update(story).set({ sprintId: null, status: "backlog" }).where(and(eq(story.sprintId, sprintId), ne(story.status, "done"), ne(story.status, "dropped")));
453
+ return incomplete.length;
454
+ },
455
+ async findBacklogStories(projectId, limit) {
456
+ const rows = await pg.select().from(story).where(and(eq(story.projectId, projectId), isNull(story.sprintId), eq(story.status, "backlog"))).orderBy(sql`priority asc, created_at asc`).limit(limit);
457
+ return rows;
458
+ },
459
+ async countStoriesInSprintByStatus(sprintId) {
460
+ const rows = await pg.select({ status: story.status, count: sql`count(*)::int` }).from(story).where(eq(story.sprintId, sprintId)).groupBy(story.status);
461
+ const out = {};
462
+ for (const r of rows) out[r.status] = Number(r.count);
463
+ return out;
464
+ },
465
+ async countBacklog(projectId) {
466
+ const rows = await pg.select({ c: sql`count(*)::int` }).from(story).where(and(eq(story.projectId, projectId), eq(story.status, "backlog"), isNull(story.sprintId)));
467
+ return Number(rows[0]?.c ?? 0);
468
+ },
469
+ async countDoneStoriesInSprint(sprintId) {
470
+ const rows = await pg.select({ c: sql`count(*)::int` }).from(story).where(and(eq(story.sprintId, sprintId), eq(story.status, "done")));
471
+ return Number(rows[0]?.c ?? 0);
472
+ },
473
+ async insertTask(row) {
474
+ await pg.insert(task).values(row);
475
+ },
476
+ async updateTask(id, updates) {
477
+ await pg.update(task).set(updates).where(eq(task.id, id));
478
+ },
479
+ async insertDebt(row) {
480
+ await pg.insert(techDebt).values(row);
481
+ },
482
+ async closeDebt(id, closedAt) {
483
+ await pg.update(techDebt).set({ closedAt }).where(eq(techDebt.id, id));
484
+ },
485
+ async findOpenDebtByProject(projectId, limit) {
486
+ const rows = await pg.select().from(techDebt).where(and(eq(techDebt.projectId, projectId), isNull(techDebt.closedAt))).orderBy(sql`severity desc, opened_at desc`).limit(limit);
487
+ return rows;
488
+ },
489
+ async findAllDebtByProject(projectId, limit) {
490
+ const rows = await pg.select().from(techDebt).where(eq(techDebt.projectId, projectId)).orderBy(sql`closed_at is null desc, severity desc, opened_at desc`).limit(limit);
491
+ return rows;
492
+ },
493
+ async findOpenDebtAtLocation(projectId, location) {
494
+ const rows = await pg.select().from(techDebt).where(and(eq(techDebt.projectId, projectId), eq(techDebt.location, location), isNull(techDebt.closedAt))).limit(1);
495
+ return rows[0] ?? null;
496
+ },
497
+ async countOpenDebtByProject(projectId) {
498
+ const rows = await pg.select({ c: sql`count(*)::int` }).from(techDebt).where(and(eq(techDebt.projectId, projectId), isNull(techDebt.closedAt)));
499
+ return Number(rows[0]?.c ?? 0);
500
+ },
501
+ async insertDecision(row) {
502
+ await pg.insert(decision).values(row);
503
+ },
504
+ async findDecisionsByProject(projectId, limit) {
505
+ const rows = await pg.select().from(decision).where(eq(decision.projectId, projectId)).orderBy(desc(decision.decidedAt)).limit(limit);
506
+ return rows;
507
+ },
508
+ async emitEvent(row) {
509
+ await pg.insert(progressEvent).values(row);
510
+ },
511
+ async findRecentEvents(projectId, limit) {
512
+ const rows = await pg.select().from(progressEvent).where(eq(progressEvent.projectId, projectId)).orderBy(desc(progressEvent.ts)).limit(limit);
513
+ return rows;
514
+ },
515
+ async findEventsForSprint(sprintId, limit) {
516
+ const rows = await pg.select().from(progressEvent).where(eq(progressEvent.sprintId, sprintId)).orderBy(desc(progressEvent.ts)).limit(limit);
517
+ return rows;
518
+ },
519
+ async countEventsByKindInSprint(sprintId, kind) {
520
+ const rows = await pg.select({ c: sql`count(*)::int` }).from(progressEvent).where(and(eq(progressEvent.sprintId, sprintId), eq(progressEvent.kind, kind)));
521
+ return Number(rows[0]?.c ?? 0);
522
+ },
523
+ async findEventsByDeveloper(projectId, developerId, limit) {
524
+ const rows = await pg.select().from(progressEvent).where(and(eq(progressEvent.projectId, projectId), eq(progressEvent.developerId, developerId))).orderBy(desc(progressEvent.ts)).limit(limit);
525
+ return rows;
526
+ }
527
+ };
528
+ }
529
+ const STATEMENTS$1 = [
530
+ `CREATE TABLE IF NOT EXISTS project (
531
+ id TEXT PRIMARY KEY,
532
+ slug TEXT NOT NULL UNIQUE,
533
+ name TEXT NOT NULL,
534
+ git_remote TEXT,
535
+ dod TEXT,
536
+ sprint_length_days INTEGER NOT NULL DEFAULT 14,
537
+ wip_enabled INTEGER NOT NULL DEFAULT 0,
538
+ estimation_enabled INTEGER NOT NULL DEFAULT 1,
539
+ created_at TEXT NOT NULL
540
+ )`,
541
+ `CREATE TABLE IF NOT EXISTS developer (
542
+ id TEXT PRIMARY KEY,
543
+ project_id TEXT NOT NULL REFERENCES project(id),
544
+ handle TEXT NOT NULL,
545
+ email TEXT,
546
+ last_seen_at TEXT NOT NULL
547
+ )`,
548
+ `CREATE TABLE IF NOT EXISTS sprint (
549
+ id TEXT PRIMARY KEY,
550
+ project_id TEXT NOT NULL REFERENCES project(id),
551
+ name TEXT NOT NULL,
552
+ goal TEXT,
553
+ started_at TEXT NOT NULL,
554
+ ended_at TEXT,
555
+ status TEXT NOT NULL,
556
+ wip_limit INTEGER
557
+ )`,
558
+ `CREATE TABLE IF NOT EXISTS epic (
559
+ id TEXT PRIMARY KEY,
560
+ project_id TEXT NOT NULL REFERENCES project(id),
561
+ title TEXT NOT NULL,
562
+ description TEXT,
563
+ status TEXT NOT NULL DEFAULT 'open',
564
+ priority INTEGER NOT NULL DEFAULT 3,
565
+ target_sprint_id TEXT REFERENCES sprint(id),
566
+ created_at TEXT NOT NULL
567
+ )`,
568
+ `CREATE TABLE IF NOT EXISTS story (
569
+ id TEXT PRIMARY KEY,
570
+ project_id TEXT NOT NULL REFERENCES project(id),
571
+ epic_id TEXT REFERENCES epic(id),
572
+ sprint_id TEXT REFERENCES sprint(id),
573
+ title TEXT NOT NULL,
574
+ description TEXT,
575
+ acceptance TEXT,
576
+ status TEXT NOT NULL DEFAULT 'backlog',
577
+ size TEXT,
578
+ assignee_id TEXT REFERENCES developer(id),
579
+ priority INTEGER NOT NULL DEFAULT 3,
580
+ started_at TEXT,
581
+ completed_at TEXT,
582
+ created_at TEXT NOT NULL
583
+ )`,
584
+ `CREATE TABLE IF NOT EXISTS task (
585
+ id TEXT PRIMARY KEY,
586
+ story_id TEXT NOT NULL REFERENCES story(id),
587
+ assignee_id TEXT REFERENCES developer(id),
588
+ title TEXT NOT NULL,
589
+ status TEXT NOT NULL DEFAULT 'todo',
590
+ blocked_by TEXT,
591
+ created_at TEXT NOT NULL
592
+ )`,
593
+ `CREATE TABLE IF NOT EXISTS tech_debt (
594
+ id TEXT PRIMARY KEY,
595
+ project_id TEXT NOT NULL REFERENCES project(id),
596
+ title TEXT NOT NULL,
597
+ description TEXT,
598
+ severity TEXT NOT NULL DEFAULT 'med',
599
+ location TEXT,
600
+ owner_id TEXT REFERENCES developer(id),
601
+ expires_at TEXT,
602
+ opened_at TEXT NOT NULL,
603
+ closed_at TEXT,
604
+ linked_story_id TEXT REFERENCES story(id)
605
+ )`,
606
+ `CREATE TABLE IF NOT EXISTS decision (
607
+ id TEXT PRIMARY KEY,
608
+ project_id TEXT NOT NULL REFERENCES project(id),
609
+ title TEXT NOT NULL,
610
+ context TEXT,
611
+ decision TEXT NOT NULL,
612
+ status TEXT NOT NULL DEFAULT 'accepted',
613
+ decided_at TEXT NOT NULL
614
+ )`,
615
+ `CREATE TABLE IF NOT EXISTS progress_event (
616
+ id TEXT PRIMARY KEY,
617
+ project_id TEXT NOT NULL REFERENCES project(id),
618
+ developer_id TEXT REFERENCES developer(id),
619
+ sprint_id TEXT REFERENCES sprint(id),
620
+ kind TEXT NOT NULL,
621
+ ref_id TEXT,
622
+ summary TEXT NOT NULL,
623
+ ts TEXT NOT NULL
624
+ )`,
625
+ `CREATE INDEX IF NOT EXISTS idx_progress_event_ts ON progress_event(ts DESC)`,
626
+ `CREATE INDEX IF NOT EXISTS idx_story_sprint ON story(sprint_id)`,
627
+ `CREATE INDEX IF NOT EXISTS idx_story_status ON story(status)`,
628
+ `CREATE INDEX IF NOT EXISTS idx_story_project ON story(project_id)`,
629
+ `CREATE INDEX IF NOT EXISTS idx_tech_debt_closed ON tech_debt(closed_at)`
630
+ ];
631
+ async function ensureStoryProjectColumn(client) {
632
+ const info = await client.execute("PRAGMA table_info(story)");
633
+ const hasProject = info.rows.some((r) => String(r.name) === "project_id");
634
+ if (hasProject) return;
635
+ await client.execute("ALTER TABLE story ADD COLUMN project_id TEXT REFERENCES project(id)");
636
+ await client.execute(`
637
+ UPDATE story SET project_id = COALESCE(
638
+ (SELECT s.project_id FROM sprint s WHERE s.id = story.sprint_id),
639
+ (SELECT e.project_id FROM epic e WHERE e.id = story.epic_id),
640
+ (SELECT p.id FROM project p ORDER BY p.created_at LIMIT 1)
641
+ )
642
+ WHERE project_id IS NULL
643
+ `);
644
+ await client.execute("CREATE INDEX IF NOT EXISTS idx_story_project ON story(project_id)");
645
+ }
646
+ async function bootstrap(client) {
647
+ for (const sql2 of STATEMENTS$1) {
648
+ await client.execute(sql2);
649
+ }
650
+ await ensureStoryProjectColumn(client);
651
+ }
652
+ const STATEMENTS = [
653
+ `CREATE TABLE IF NOT EXISTS project (
654
+ id TEXT PRIMARY KEY,
655
+ slug TEXT NOT NULL UNIQUE,
656
+ name TEXT NOT NULL,
657
+ git_remote TEXT,
658
+ dod TEXT,
659
+ sprint_length_days INTEGER NOT NULL DEFAULT 14,
660
+ wip_enabled BOOLEAN NOT NULL DEFAULT FALSE,
661
+ estimation_enabled BOOLEAN NOT NULL DEFAULT TRUE,
662
+ created_at TEXT NOT NULL
663
+ )`,
664
+ `CREATE TABLE IF NOT EXISTS developer (
665
+ id TEXT PRIMARY KEY,
666
+ project_id TEXT NOT NULL REFERENCES project(id),
667
+ handle TEXT NOT NULL,
668
+ email TEXT,
669
+ last_seen_at TEXT NOT NULL
670
+ )`,
671
+ `CREATE TABLE IF NOT EXISTS sprint (
672
+ id TEXT PRIMARY KEY,
673
+ project_id TEXT NOT NULL REFERENCES project(id),
674
+ name TEXT NOT NULL,
675
+ goal TEXT,
676
+ started_at TEXT NOT NULL,
677
+ ended_at TEXT,
678
+ status TEXT NOT NULL,
679
+ wip_limit INTEGER
680
+ )`,
681
+ `CREATE TABLE IF NOT EXISTS epic (
682
+ id TEXT PRIMARY KEY,
683
+ project_id TEXT NOT NULL REFERENCES project(id),
684
+ title TEXT NOT NULL,
685
+ description TEXT,
686
+ status TEXT NOT NULL DEFAULT 'open',
687
+ priority INTEGER NOT NULL DEFAULT 3,
688
+ target_sprint_id TEXT REFERENCES sprint(id),
689
+ created_at TEXT NOT NULL
690
+ )`,
691
+ `CREATE TABLE IF NOT EXISTS story (
692
+ id TEXT PRIMARY KEY,
693
+ project_id TEXT NOT NULL REFERENCES project(id),
694
+ epic_id TEXT REFERENCES epic(id),
695
+ sprint_id TEXT REFERENCES sprint(id),
696
+ title TEXT NOT NULL,
697
+ description TEXT,
698
+ acceptance TEXT,
699
+ status TEXT NOT NULL DEFAULT 'backlog',
700
+ size TEXT,
701
+ assignee_id TEXT REFERENCES developer(id),
702
+ priority INTEGER NOT NULL DEFAULT 3,
703
+ started_at TEXT,
704
+ completed_at TEXT,
705
+ created_at TEXT NOT NULL
706
+ )`,
707
+ `CREATE TABLE IF NOT EXISTS task (
708
+ id TEXT PRIMARY KEY,
709
+ story_id TEXT NOT NULL REFERENCES story(id),
710
+ assignee_id TEXT REFERENCES developer(id),
711
+ title TEXT NOT NULL,
712
+ status TEXT NOT NULL DEFAULT 'todo',
713
+ blocked_by TEXT,
714
+ created_at TEXT NOT NULL
715
+ )`,
716
+ `CREATE TABLE IF NOT EXISTS tech_debt (
717
+ id TEXT PRIMARY KEY,
718
+ project_id TEXT NOT NULL REFERENCES project(id),
719
+ title TEXT NOT NULL,
720
+ description TEXT,
721
+ severity TEXT NOT NULL DEFAULT 'med',
722
+ location TEXT,
723
+ owner_id TEXT REFERENCES developer(id),
724
+ expires_at TEXT,
725
+ opened_at TEXT NOT NULL,
726
+ closed_at TEXT,
727
+ linked_story_id TEXT REFERENCES story(id)
728
+ )`,
729
+ `CREATE TABLE IF NOT EXISTS decision (
730
+ id TEXT PRIMARY KEY,
731
+ project_id TEXT NOT NULL REFERENCES project(id),
732
+ title TEXT NOT NULL,
733
+ context TEXT,
734
+ decision TEXT NOT NULL,
735
+ status TEXT NOT NULL DEFAULT 'accepted',
736
+ decided_at TEXT NOT NULL
737
+ )`,
738
+ `CREATE TABLE IF NOT EXISTS progress_event (
739
+ id TEXT PRIMARY KEY,
740
+ project_id TEXT NOT NULL REFERENCES project(id),
741
+ developer_id TEXT REFERENCES developer(id),
742
+ sprint_id TEXT REFERENCES sprint(id),
743
+ kind TEXT NOT NULL,
744
+ ref_id TEXT,
745
+ summary TEXT NOT NULL,
746
+ ts TEXT NOT NULL
747
+ )`,
748
+ `CREATE INDEX IF NOT EXISTS idx_progress_event_ts ON progress_event(ts DESC)`,
749
+ `CREATE INDEX IF NOT EXISTS idx_story_sprint ON story(sprint_id)`,
750
+ `CREATE INDEX IF NOT EXISTS idx_story_status ON story(status)`,
751
+ `CREATE INDEX IF NOT EXISTS idx_story_project ON story(project_id)`,
752
+ `CREATE INDEX IF NOT EXISTS idx_tech_debt_closed ON tech_debt(closed_at)`
753
+ ];
754
+ const MIGRATIONS = [
755
+ `ALTER TABLE story ADD COLUMN IF NOT EXISTS project_id TEXT REFERENCES project(id)`,
756
+ `UPDATE story SET project_id = COALESCE(
757
+ (SELECT s.project_id FROM sprint s WHERE s.id = story.sprint_id),
758
+ (SELECT e.project_id FROM epic e WHERE e.id = story.epic_id),
759
+ (SELECT p.id FROM project p ORDER BY p.created_at LIMIT 1)
760
+ )
761
+ WHERE project_id IS NULL`
762
+ ];
763
+ async function bootstrapPg(runner) {
764
+ for (const sql2 of STATEMENTS) {
765
+ await runner.query(sql2);
766
+ }
767
+ for (const sql2 of MIGRATIONS) {
768
+ await runner.query(sql2);
769
+ }
770
+ }
771
+ let cached = null;
772
+ function helmHome() {
773
+ return process.env.HELM_HOME ?? join(homedir(), ".helm");
774
+ }
775
+ function unifiedDbPath() {
776
+ return process.env.HELM_DB_PATH ?? join(helmHome(), "helm.db");
777
+ }
778
+ function defaultSlug() {
779
+ return process.env.HELM_PROJECT_SLUG ?? null;
780
+ }
781
+ async function repo() {
782
+ if (cached) return cached;
783
+ const dbUrl = process.env.HELM_DB_URL ?? "";
784
+ if (dbUrl.startsWith("postgres://") || dbUrl.startsWith("postgresql://")) {
785
+ const [{ Pool }, { drizzle: drizzle2 }] = await Promise.all([
786
+ import('pg'),
787
+ import('drizzle-orm/node-postgres')
788
+ ]);
789
+ const pool = new Pool({ connectionString: dbUrl });
790
+ await bootstrapPg({ query: async (sql2) => {
791
+ await pool.query(sql2);
792
+ } });
793
+ const pg = drizzle2(pool, { schema });
794
+ cached = makePgRepo(pg);
795
+ return cached;
796
+ }
797
+ const path = unifiedDbPath();
798
+ const client = createClient({ url: `file:${path}` });
799
+ await bootstrap(client);
800
+ const drizzled = drizzle(client, { schema: schema$1 });
801
+ cached = makeSqliteRepo(drizzled);
802
+ return cached;
803
+ }
804
+
805
+ export { defaultSlug as d, repo as r };
806
+ //# sourceMappingURL=db-GHaWnz-k.js.map