@qotaq/lalphgram 0.1.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 (517) hide show
  1. package/Events/package.json +6 -0
  2. package/LICENSE +21 -0
  3. package/Main/package.json +6 -0
  4. package/README.md +1 -0
  5. package/dist/cjs/Events.js +55 -0
  6. package/dist/cjs/Events.js.map +1 -0
  7. package/dist/cjs/LalphMain.js +59 -0
  8. package/dist/cjs/LalphMain.js.map +1 -0
  9. package/dist/cjs/Main.js +115 -0
  10. package/dist/cjs/Main.js.map +1 -0
  11. package/dist/cjs/index.js +281 -0
  12. package/dist/cjs/index.js.map +1 -0
  13. package/dist/cjs/lib/AnalysisPrompts.js +61 -0
  14. package/dist/cjs/lib/AnalysisPrompts.js.map +1 -0
  15. package/dist/cjs/lib/BranchParser.js +45 -0
  16. package/dist/cjs/lib/BranchParser.js.map +1 -0
  17. package/dist/cjs/lib/MermaidToPlantUml.js +96 -0
  18. package/dist/cjs/lib/MermaidToPlantUml.js.map +1 -0
  19. package/dist/cjs/lib/SpecHtmlGenerator.js +160 -0
  20. package/dist/cjs/lib/SpecHtmlGenerator.js.map +1 -0
  21. package/dist/cjs/lib/StreamJsonParser.js +88 -0
  22. package/dist/cjs/lib/StreamJsonParser.js.map +1 -0
  23. package/dist/cjs/lib/TelegramFormatter.js +122 -0
  24. package/dist/cjs/lib/TelegramFormatter.js.map +1 -0
  25. package/dist/cjs/lib/TelegraphHtml.js +65 -0
  26. package/dist/cjs/lib/TelegraphHtml.js.map +1 -0
  27. package/dist/cjs/lib/TelegraphMarkdown.js +346 -0
  28. package/dist/cjs/lib/TelegraphMarkdown.js.map +1 -0
  29. package/dist/cjs/schemas/CredentialSchemas.js +31 -0
  30. package/dist/cjs/schemas/CredentialSchemas.js.map +1 -0
  31. package/dist/cjs/schemas/GitHubSchemas.js +60 -0
  32. package/dist/cjs/schemas/GitHubSchemas.js.map +1 -0
  33. package/dist/cjs/schemas/LinearSchemas.js +63 -0
  34. package/dist/cjs/schemas/LinearSchemas.js.map +1 -0
  35. package/dist/cjs/schemas/ProjectSchemas.js +26 -0
  36. package/dist/cjs/schemas/ProjectSchemas.js.map +1 -0
  37. package/dist/cjs/schemas/TrackerSchemas.js +35 -0
  38. package/dist/cjs/schemas/TrackerSchemas.js.map +1 -0
  39. package/dist/cjs/services/AppContext.js +57 -0
  40. package/dist/cjs/services/AppContext.js.map +1 -0
  41. package/dist/cjs/services/AppRuntimeConfig.js +35 -0
  42. package/dist/cjs/services/AppRuntimeConfig.js.map +1 -0
  43. package/dist/cjs/services/AutoMerge.js +140 -0
  44. package/dist/cjs/services/AutoMerge.js.map +1 -0
  45. package/dist/cjs/services/ChatMachine.js +873 -0
  46. package/dist/cjs/services/ChatMachine.js.map +1 -0
  47. package/dist/cjs/services/CommentTimer.js +81 -0
  48. package/dist/cjs/services/CommentTimer.js.map +1 -0
  49. package/dist/cjs/services/CredentialStore.js +68 -0
  50. package/dist/cjs/services/CredentialStore.js.map +1 -0
  51. package/dist/cjs/services/CredentialWatcher.js +76 -0
  52. package/dist/cjs/services/CredentialWatcher.js.map +1 -0
  53. package/dist/cjs/services/Credentials.js +130 -0
  54. package/dist/cjs/services/Credentials.js.map +1 -0
  55. package/dist/cjs/services/EventLoop.js +203 -0
  56. package/dist/cjs/services/EventLoop.js.map +1 -0
  57. package/dist/cjs/services/GitHubClient/GitHubClient.js +236 -0
  58. package/dist/cjs/services/GitHubClient/GitHubClient.js.map +1 -0
  59. package/dist/cjs/services/GitHubClient/OctokitClient.js +329 -0
  60. package/dist/cjs/services/GitHubClient/OctokitClient.js.map +1 -0
  61. package/dist/cjs/services/GitHubClient.js +236 -0
  62. package/dist/cjs/services/GitHubClient.js.map +1 -0
  63. package/dist/cjs/services/GitHubEventSource.js +145 -0
  64. package/dist/cjs/services/GitHubEventSource.js.map +1 -0
  65. package/dist/cjs/services/GitHubIssueTracker.js +118 -0
  66. package/dist/cjs/services/GitHubIssueTracker.js.map +1 -0
  67. package/dist/cjs/services/LalphConfig.js +139 -0
  68. package/dist/cjs/services/LalphConfig.js.map +1 -0
  69. package/dist/cjs/services/LalphConfigReader.js +82 -0
  70. package/dist/cjs/services/LalphConfigReader.js.map +1 -0
  71. package/dist/cjs/services/LalphDirectory.js +45 -0
  72. package/dist/cjs/services/LalphDirectory.js.map +1 -0
  73. package/dist/cjs/services/LinearSdkClient.js +149 -0
  74. package/dist/cjs/services/LinearSdkClient.js.map +1 -0
  75. package/dist/cjs/services/LinearTracker.js +89 -0
  76. package/dist/cjs/services/LinearTracker.js.map +1 -0
  77. package/dist/cjs/services/MessengerAdapter/MessengerAdapter.js +30 -0
  78. package/dist/cjs/services/MessengerAdapter/MessengerAdapter.js.map +1 -0
  79. package/dist/cjs/services/MessengerAdapter/TelegramAdapter.js +131 -0
  80. package/dist/cjs/services/MessengerAdapter/TelegramAdapter.js.map +1 -0
  81. package/dist/cjs/services/MessengerAdapter/TelegramConfig.js +81 -0
  82. package/dist/cjs/services/MessengerAdapter/TelegramConfig.js.map +1 -0
  83. package/dist/cjs/services/MessengerAdapter.js +30 -0
  84. package/dist/cjs/services/MessengerAdapter.js.map +1 -0
  85. package/dist/cjs/services/OctokitClient.js +350 -0
  86. package/dist/cjs/services/OctokitClient.js.map +1 -0
  87. package/dist/cjs/services/PlanOverviewUploader.js +119 -0
  88. package/dist/cjs/services/PlanOverviewUploader.js.map +1 -0
  89. package/dist/cjs/services/PlanOverviewUploaderMap.js +25 -0
  90. package/dist/cjs/services/PlanOverviewUploaderMap.js.map +1 -0
  91. package/dist/cjs/services/PlanSession.js +489 -0
  92. package/dist/cjs/services/PlanSession.js.map +1 -0
  93. package/dist/cjs/services/ProjectStore.js +107 -0
  94. package/dist/cjs/services/ProjectStore.js.map +1 -0
  95. package/dist/cjs/services/PullRequestTracker.js +186 -0
  96. package/dist/cjs/services/PullRequestTracker.js.map +1 -0
  97. package/dist/cjs/services/SpecUploader.js +111 -0
  98. package/dist/cjs/services/SpecUploader.js.map +1 -0
  99. package/dist/cjs/services/SpecUploaderMap.js +25 -0
  100. package/dist/cjs/services/SpecUploaderMap.js.map +1 -0
  101. package/dist/cjs/services/TaskEventSource.js +58 -0
  102. package/dist/cjs/services/TaskEventSource.js.map +1 -0
  103. package/dist/cjs/services/TaskTracker/GitHubIssueTracker.js +155 -0
  104. package/dist/cjs/services/TaskTracker/GitHubIssueTracker.js.map +1 -0
  105. package/dist/cjs/services/TaskTracker/LinearSdkClient.js +149 -0
  106. package/dist/cjs/services/TaskTracker/LinearSdkClient.js.map +1 -0
  107. package/dist/cjs/services/TaskTracker/LinearTracker.js +126 -0
  108. package/dist/cjs/services/TaskTracker/LinearTracker.js.map +1 -0
  109. package/dist/cjs/services/TaskTracker/TaskTracker.js +20 -0
  110. package/dist/cjs/services/TaskTracker/TaskTracker.js.map +1 -0
  111. package/dist/cjs/services/TaskTracker/TrackerLayerMap.js +27 -0
  112. package/dist/cjs/services/TaskTracker/TrackerLayerMap.js.map +1 -0
  113. package/dist/cjs/services/TaskTracker/buildEventStream.js +55 -0
  114. package/dist/cjs/services/TaskTracker/buildEventStream.js.map +1 -0
  115. package/dist/cjs/services/TaskTracker.js +20 -0
  116. package/dist/cjs/services/TaskTracker.js.map +1 -0
  117. package/dist/cjs/services/TelegramAdapter.js +125 -0
  118. package/dist/cjs/services/TelegramAdapter.js.map +1 -0
  119. package/dist/cjs/services/TelegramConfig.js +81 -0
  120. package/dist/cjs/services/TelegramConfig.js.map +1 -0
  121. package/dist/cjs/services/TelegramConfigStore.js +81 -0
  122. package/dist/cjs/services/TelegramConfigStore.js.map +1 -0
  123. package/dist/cjs/services/TelegramNotifier.js +50 -0
  124. package/dist/cjs/services/TelegramNotifier.js.map +1 -0
  125. package/dist/cjs/services/TrackerLayerMap.js +27 -0
  126. package/dist/cjs/services/TrackerLayerMap.js.map +1 -0
  127. package/dist/cjs/services/TrackerResolver.js +45 -0
  128. package/dist/cjs/services/TrackerResolver.js.map +1 -0
  129. package/dist/cjs/services/messenger/MessengerAdapter.js +30 -0
  130. package/dist/cjs/services/messenger/MessengerAdapter.js.map +1 -0
  131. package/dist/cjs/services/messenger/TelegramAdapter.js +125 -0
  132. package/dist/cjs/services/messenger/TelegramAdapter.js.map +1 -0
  133. package/dist/cjs/services/task-tracker/GitHubIssueTracker.js +157 -0
  134. package/dist/cjs/services/task-tracker/GitHubIssueTracker.js.map +1 -0
  135. package/dist/cjs/services/task-tracker/LinearTracker.js +127 -0
  136. package/dist/cjs/services/task-tracker/LinearTracker.js.map +1 -0
  137. package/dist/cjs/services/task-tracker/TaskTracker.js +20 -0
  138. package/dist/cjs/services/task-tracker/TaskTracker.js.map +1 -0
  139. package/dist/cjs/services/task-tracker/TrackerLayerMap.js +27 -0
  140. package/dist/cjs/services/task-tracker/TrackerLayerMap.js.map +1 -0
  141. package/dist/cjs/shim/bin.js +31 -0
  142. package/dist/cjs/shim/bin.js.map +1 -0
  143. package/dist/cjs/shim/main.js +217 -0
  144. package/dist/cjs/shim/main.js.map +1 -0
  145. package/dist/cjs/shim/parseArgs.js +45 -0
  146. package/dist/cjs/shim/parseArgs.js.map +1 -0
  147. package/dist/cjs/shim/schemas.js +35 -0
  148. package/dist/cjs/shim/schemas.js.map +1 -0
  149. package/dist/dts/Events.d.ts +108 -0
  150. package/dist/dts/Events.d.ts.map +1 -0
  151. package/dist/dts/LalphMain.d.ts +2 -0
  152. package/dist/dts/LalphMain.d.ts.map +1 -0
  153. package/dist/dts/Main.d.ts +2 -0
  154. package/dist/dts/Main.d.ts.map +1 -0
  155. package/dist/dts/index.d.ts +101 -0
  156. package/dist/dts/index.d.ts.map +1 -0
  157. package/dist/dts/lib/AnalysisPrompts.d.ts +12 -0
  158. package/dist/dts/lib/AnalysisPrompts.d.ts.map +1 -0
  159. package/dist/dts/lib/BranchParser.d.ts +40 -0
  160. package/dist/dts/lib/BranchParser.d.ts.map +1 -0
  161. package/dist/dts/lib/MermaidToPlantUml.d.ts +19 -0
  162. package/dist/dts/lib/MermaidToPlantUml.d.ts.map +1 -0
  163. package/dist/dts/lib/SpecHtmlGenerator.d.ts +18 -0
  164. package/dist/dts/lib/SpecHtmlGenerator.d.ts.map +1 -0
  165. package/dist/dts/lib/StreamJsonParser.d.ts +147 -0
  166. package/dist/dts/lib/StreamJsonParser.d.ts.map +1 -0
  167. package/dist/dts/lib/TelegramFormatter.d.ts +35 -0
  168. package/dist/dts/lib/TelegramFormatter.d.ts.map +1 -0
  169. package/dist/dts/lib/TelegraphHtml.d.ts +11 -0
  170. package/dist/dts/lib/TelegraphHtml.d.ts.map +1 -0
  171. package/dist/dts/lib/TelegraphMarkdown.d.ts +21 -0
  172. package/dist/dts/lib/TelegraphMarkdown.d.ts.map +1 -0
  173. package/dist/dts/schemas/CredentialSchemas.d.ts +41 -0
  174. package/dist/dts/schemas/CredentialSchemas.d.ts.map +1 -0
  175. package/dist/dts/schemas/GitHubSchemas.d.ts +130 -0
  176. package/dist/dts/schemas/GitHubSchemas.d.ts.map +1 -0
  177. package/dist/dts/schemas/LinearSchemas.d.ts +121 -0
  178. package/dist/dts/schemas/LinearSchemas.d.ts.map +1 -0
  179. package/dist/dts/schemas/ProjectSchemas.d.ts +40 -0
  180. package/dist/dts/schemas/ProjectSchemas.d.ts.map +1 -0
  181. package/dist/dts/schemas/TrackerSchemas.d.ts +57 -0
  182. package/dist/dts/schemas/TrackerSchemas.d.ts.map +1 -0
  183. package/dist/dts/services/AppContext.d.ts +40 -0
  184. package/dist/dts/services/AppContext.d.ts.map +1 -0
  185. package/dist/dts/services/AppRuntimeConfig.d.ts +51 -0
  186. package/dist/dts/services/AppRuntimeConfig.d.ts.map +1 -0
  187. package/dist/dts/services/AutoMerge.d.ts +42 -0
  188. package/dist/dts/services/AutoMerge.d.ts.map +1 -0
  189. package/dist/dts/services/ChatMachine.d.ts +478 -0
  190. package/dist/dts/services/ChatMachine.d.ts.map +1 -0
  191. package/dist/dts/services/CommentTimer.d.ts +44 -0
  192. package/dist/dts/services/CommentTimer.d.ts.map +1 -0
  193. package/dist/dts/services/CredentialStore.d.ts +43 -0
  194. package/dist/dts/services/CredentialStore.d.ts.map +1 -0
  195. package/dist/dts/services/CredentialWatcher.d.ts +41 -0
  196. package/dist/dts/services/CredentialWatcher.d.ts.map +1 -0
  197. package/dist/dts/services/Credentials.d.ts +44 -0
  198. package/dist/dts/services/Credentials.d.ts.map +1 -0
  199. package/dist/dts/services/EventLoop.d.ts +26 -0
  200. package/dist/dts/services/EventLoop.d.ts.map +1 -0
  201. package/dist/dts/services/GitHubClient/GitHubClient.d.ts +69 -0
  202. package/dist/dts/services/GitHubClient/GitHubClient.d.ts.map +1 -0
  203. package/dist/dts/services/GitHubClient/OctokitClient.d.ts +214 -0
  204. package/dist/dts/services/GitHubClient/OctokitClient.d.ts.map +1 -0
  205. package/dist/dts/services/GitHubClient.d.ts +69 -0
  206. package/dist/dts/services/GitHubClient.d.ts.map +1 -0
  207. package/dist/dts/services/GitHubEventSource.d.ts +43 -0
  208. package/dist/dts/services/GitHubEventSource.d.ts.map +1 -0
  209. package/dist/dts/services/GitHubIssueTracker.d.ts +9 -0
  210. package/dist/dts/services/GitHubIssueTracker.d.ts.map +1 -0
  211. package/dist/dts/services/LalphConfig.d.ts +44 -0
  212. package/dist/dts/services/LalphConfig.d.ts.map +1 -0
  213. package/dist/dts/services/LalphConfigReader.d.ts +66 -0
  214. package/dist/dts/services/LalphConfigReader.d.ts.map +1 -0
  215. package/dist/dts/services/LalphDirectory.d.ts +39 -0
  216. package/dist/dts/services/LalphDirectory.d.ts.map +1 -0
  217. package/dist/dts/services/LinearSdkClient.d.ts +71 -0
  218. package/dist/dts/services/LinearSdkClient.d.ts.map +1 -0
  219. package/dist/dts/services/LinearTracker.d.ts +9 -0
  220. package/dist/dts/services/LinearTracker.d.ts.map +1 -0
  221. package/dist/dts/services/MessengerAdapter/MessengerAdapter.d.ts +69 -0
  222. package/dist/dts/services/MessengerAdapter/MessengerAdapter.d.ts.map +1 -0
  223. package/dist/dts/services/MessengerAdapter/TelegramAdapter.d.ts +13 -0
  224. package/dist/dts/services/MessengerAdapter/TelegramAdapter.d.ts.map +1 -0
  225. package/dist/dts/services/MessengerAdapter/TelegramConfig.d.ts +58 -0
  226. package/dist/dts/services/MessengerAdapter/TelegramConfig.d.ts.map +1 -0
  227. package/dist/dts/services/MessengerAdapter.d.ts +69 -0
  228. package/dist/dts/services/MessengerAdapter.d.ts.map +1 -0
  229. package/dist/dts/services/OctokitClient.d.ts +232 -0
  230. package/dist/dts/services/OctokitClient.d.ts.map +1 -0
  231. package/dist/dts/services/PlanOverviewUploader.d.ts +55 -0
  232. package/dist/dts/services/PlanOverviewUploader.d.ts.map +1 -0
  233. package/dist/dts/services/PlanOverviewUploaderMap.d.ts +14 -0
  234. package/dist/dts/services/PlanOverviewUploaderMap.d.ts.map +1 -0
  235. package/dist/dts/services/PlanSession.d.ts +169 -0
  236. package/dist/dts/services/PlanSession.d.ts.map +1 -0
  237. package/dist/dts/services/ProjectStore.d.ts +50 -0
  238. package/dist/dts/services/ProjectStore.d.ts.map +1 -0
  239. package/dist/dts/services/PullRequestTracker.d.ts +42 -0
  240. package/dist/dts/services/PullRequestTracker.d.ts.map +1 -0
  241. package/dist/dts/services/SpecUploader.d.ts +51 -0
  242. package/dist/dts/services/SpecUploader.d.ts.map +1 -0
  243. package/dist/dts/services/SpecUploaderMap.d.ts +14 -0
  244. package/dist/dts/services/SpecUploaderMap.d.ts.map +1 -0
  245. package/dist/dts/services/TaskEventSource.d.ts +21 -0
  246. package/dist/dts/services/TaskEventSource.d.ts.map +1 -0
  247. package/dist/dts/services/TaskTracker/GitHubIssueTracker.d.ts +10 -0
  248. package/dist/dts/services/TaskTracker/GitHubIssueTracker.d.ts.map +1 -0
  249. package/dist/dts/services/TaskTracker/LinearSdkClient.d.ts +71 -0
  250. package/dist/dts/services/TaskTracker/LinearSdkClient.d.ts.map +1 -0
  251. package/dist/dts/services/TaskTracker/LinearTracker.d.ts +10 -0
  252. package/dist/dts/services/TaskTracker/LinearTracker.d.ts.map +1 -0
  253. package/dist/dts/services/TaskTracker/TaskTracker.d.ts +39 -0
  254. package/dist/dts/services/TaskTracker/TaskTracker.d.ts.map +1 -0
  255. package/dist/dts/services/TaskTracker/TrackerLayerMap.d.ts +14 -0
  256. package/dist/dts/services/TaskTracker/TrackerLayerMap.d.ts.map +1 -0
  257. package/dist/dts/services/TaskTracker/buildEventStream.d.ts +16 -0
  258. package/dist/dts/services/TaskTracker/buildEventStream.d.ts.map +1 -0
  259. package/dist/dts/services/TaskTracker.d.ts +38 -0
  260. package/dist/dts/services/TaskTracker.d.ts.map +1 -0
  261. package/dist/dts/services/TelegramAdapter.d.ts +13 -0
  262. package/dist/dts/services/TelegramAdapter.d.ts.map +1 -0
  263. package/dist/dts/services/TelegramConfig.d.ts +58 -0
  264. package/dist/dts/services/TelegramConfig.d.ts.map +1 -0
  265. package/dist/dts/services/TelegramConfigStore.d.ts +57 -0
  266. package/dist/dts/services/TelegramConfigStore.d.ts.map +1 -0
  267. package/dist/dts/services/TelegramNotifier.d.ts +40 -0
  268. package/dist/dts/services/TelegramNotifier.d.ts.map +1 -0
  269. package/dist/dts/services/TrackerLayerMap.d.ts +14 -0
  270. package/dist/dts/services/TrackerLayerMap.d.ts.map +1 -0
  271. package/dist/dts/services/TrackerResolver.d.ts +43 -0
  272. package/dist/dts/services/TrackerResolver.d.ts.map +1 -0
  273. package/dist/dts/services/messenger/MessengerAdapter.d.ts +69 -0
  274. package/dist/dts/services/messenger/MessengerAdapter.d.ts.map +1 -0
  275. package/dist/dts/services/messenger/TelegramAdapter.d.ts +13 -0
  276. package/dist/dts/services/messenger/TelegramAdapter.d.ts.map +1 -0
  277. package/dist/dts/services/task-tracker/GitHubIssueTracker.d.ts +10 -0
  278. package/dist/dts/services/task-tracker/GitHubIssueTracker.d.ts.map +1 -0
  279. package/dist/dts/services/task-tracker/LinearTracker.d.ts +10 -0
  280. package/dist/dts/services/task-tracker/LinearTracker.d.ts.map +1 -0
  281. package/dist/dts/services/task-tracker/TaskTracker.d.ts +38 -0
  282. package/dist/dts/services/task-tracker/TaskTracker.d.ts.map +1 -0
  283. package/dist/dts/services/task-tracker/TrackerLayerMap.d.ts +14 -0
  284. package/dist/dts/services/task-tracker/TrackerLayerMap.d.ts.map +1 -0
  285. package/dist/dts/shim/bin.d.ts +3 -0
  286. package/dist/dts/shim/bin.d.ts.map +1 -0
  287. package/dist/dts/shim/main.d.ts +36 -0
  288. package/dist/dts/shim/main.d.ts.map +1 -0
  289. package/dist/dts/shim/parseArgs.d.ts +11 -0
  290. package/dist/dts/shim/parseArgs.d.ts.map +1 -0
  291. package/dist/dts/shim/schemas.d.ts +55 -0
  292. package/dist/dts/shim/schemas.d.ts.map +1 -0
  293. package/dist/esm/Events.js +41 -0
  294. package/dist/esm/Events.js.map +1 -0
  295. package/dist/esm/LalphMain.js +56 -0
  296. package/dist/esm/LalphMain.js.map +1 -0
  297. package/dist/esm/Main.js +112 -0
  298. package/dist/esm/Main.js.map +1 -0
  299. package/dist/esm/index.js +101 -0
  300. package/dist/esm/index.js.map +1 -0
  301. package/dist/esm/lib/AnalysisPrompts.js +54 -0
  302. package/dist/esm/lib/AnalysisPrompts.js.map +1 -0
  303. package/dist/esm/lib/BranchParser.js +36 -0
  304. package/dist/esm/lib/BranchParser.js.map +1 -0
  305. package/dist/esm/lib/MermaidToPlantUml.js +89 -0
  306. package/dist/esm/lib/MermaidToPlantUml.js.map +1 -0
  307. package/dist/esm/lib/SpecHtmlGenerator.js +153 -0
  308. package/dist/esm/lib/SpecHtmlGenerator.js.map +1 -0
  309. package/dist/esm/lib/StreamJsonParser.js +79 -0
  310. package/dist/esm/lib/StreamJsonParser.js.map +1 -0
  311. package/dist/esm/lib/TelegramFormatter.js +114 -0
  312. package/dist/esm/lib/TelegramFormatter.js.map +1 -0
  313. package/dist/esm/lib/TelegraphHtml.js +57 -0
  314. package/dist/esm/lib/TelegraphHtml.js.map +1 -0
  315. package/dist/esm/lib/TelegraphMarkdown.js +338 -0
  316. package/dist/esm/lib/TelegraphMarkdown.js.map +1 -0
  317. package/dist/esm/package.json +4 -0
  318. package/dist/esm/schemas/CredentialSchemas.js +22 -0
  319. package/dist/esm/schemas/CredentialSchemas.js.map +1 -0
  320. package/dist/esm/schemas/GitHubSchemas.js +50 -0
  321. package/dist/esm/schemas/GitHubSchemas.js.map +1 -0
  322. package/dist/esm/schemas/LinearSchemas.js +52 -0
  323. package/dist/esm/schemas/LinearSchemas.js.map +1 -0
  324. package/dist/esm/schemas/ProjectSchemas.js +18 -0
  325. package/dist/esm/schemas/ProjectSchemas.js.map +1 -0
  326. package/dist/esm/schemas/TrackerSchemas.js +26 -0
  327. package/dist/esm/schemas/TrackerSchemas.js.map +1 -0
  328. package/dist/esm/services/AppContext.js +48 -0
  329. package/dist/esm/services/AppContext.js.map +1 -0
  330. package/dist/esm/services/AppRuntimeConfig.js +26 -0
  331. package/dist/esm/services/AppRuntimeConfig.js.map +1 -0
  332. package/dist/esm/services/AutoMerge.js +131 -0
  333. package/dist/esm/services/AutoMerge.js.map +1 -0
  334. package/dist/esm/services/ChatMachine.js +855 -0
  335. package/dist/esm/services/ChatMachine.js.map +1 -0
  336. package/dist/esm/services/CommentTimer.js +72 -0
  337. package/dist/esm/services/CommentTimer.js.map +1 -0
  338. package/dist/esm/services/CredentialStore.js +59 -0
  339. package/dist/esm/services/CredentialStore.js.map +1 -0
  340. package/dist/esm/services/CredentialWatcher.js +67 -0
  341. package/dist/esm/services/CredentialWatcher.js.map +1 -0
  342. package/dist/esm/services/Credentials.js +121 -0
  343. package/dist/esm/services/Credentials.js.map +1 -0
  344. package/dist/esm/services/EventLoop.js +128 -0
  345. package/dist/esm/services/EventLoop.js.map +1 -0
  346. package/dist/esm/services/GitHubClient/GitHubClient.js +227 -0
  347. package/dist/esm/services/GitHubClient/GitHubClient.js.map +1 -0
  348. package/dist/esm/services/GitHubClient/OctokitClient.js +320 -0
  349. package/dist/esm/services/GitHubClient/OctokitClient.js.map +1 -0
  350. package/dist/esm/services/GitHubClient.js +227 -0
  351. package/dist/esm/services/GitHubClient.js.map +1 -0
  352. package/dist/esm/services/GitHubEventSource.js +136 -0
  353. package/dist/esm/services/GitHubEventSource.js.map +1 -0
  354. package/dist/esm/services/GitHubIssueTracker.js +111 -0
  355. package/dist/esm/services/GitHubIssueTracker.js.map +1 -0
  356. package/dist/esm/services/LalphConfig.js +130 -0
  357. package/dist/esm/services/LalphConfig.js.map +1 -0
  358. package/dist/esm/services/LalphConfigReader.js +71 -0
  359. package/dist/esm/services/LalphConfigReader.js.map +1 -0
  360. package/dist/esm/services/LalphDirectory.js +36 -0
  361. package/dist/esm/services/LalphDirectory.js.map +1 -0
  362. package/dist/esm/services/LinearSdkClient.js +140 -0
  363. package/dist/esm/services/LinearSdkClient.js.map +1 -0
  364. package/dist/esm/services/LinearTracker.js +82 -0
  365. package/dist/esm/services/LinearTracker.js.map +1 -0
  366. package/dist/esm/services/MessengerAdapter/MessengerAdapter.js +21 -0
  367. package/dist/esm/services/MessengerAdapter/MessengerAdapter.js.map +1 -0
  368. package/dist/esm/services/MessengerAdapter/TelegramAdapter.js +124 -0
  369. package/dist/esm/services/MessengerAdapter/TelegramAdapter.js.map +1 -0
  370. package/dist/esm/services/MessengerAdapter/TelegramConfig.js +71 -0
  371. package/dist/esm/services/MessengerAdapter/TelegramConfig.js.map +1 -0
  372. package/dist/esm/services/MessengerAdapter.js +21 -0
  373. package/dist/esm/services/MessengerAdapter.js.map +1 -0
  374. package/dist/esm/services/OctokitClient.js +341 -0
  375. package/dist/esm/services/OctokitClient.js.map +1 -0
  376. package/dist/esm/services/PlanOverviewUploader.js +109 -0
  377. package/dist/esm/services/PlanOverviewUploader.js.map +1 -0
  378. package/dist/esm/services/PlanOverviewUploaderMap.js +17 -0
  379. package/dist/esm/services/PlanOverviewUploaderMap.js.map +1 -0
  380. package/dist/esm/services/PlanSession.js +471 -0
  381. package/dist/esm/services/PlanSession.js.map +1 -0
  382. package/dist/esm/services/ProjectStore.js +98 -0
  383. package/dist/esm/services/ProjectStore.js.map +1 -0
  384. package/dist/esm/services/PullRequestTracker.js +177 -0
  385. package/dist/esm/services/PullRequestTracker.js.map +1 -0
  386. package/dist/esm/services/SpecUploader.js +101 -0
  387. package/dist/esm/services/SpecUploader.js.map +1 -0
  388. package/dist/esm/services/SpecUploaderMap.js +17 -0
  389. package/dist/esm/services/SpecUploaderMap.js.map +1 -0
  390. package/dist/esm/services/TaskEventSource.js +50 -0
  391. package/dist/esm/services/TaskEventSource.js.map +1 -0
  392. package/dist/esm/services/TaskTracker/GitHubIssueTracker.js +148 -0
  393. package/dist/esm/services/TaskTracker/GitHubIssueTracker.js.map +1 -0
  394. package/dist/esm/services/TaskTracker/LinearSdkClient.js +140 -0
  395. package/dist/esm/services/TaskTracker/LinearSdkClient.js.map +1 -0
  396. package/dist/esm/services/TaskTracker/LinearTracker.js +119 -0
  397. package/dist/esm/services/TaskTracker/LinearTracker.js.map +1 -0
  398. package/dist/esm/services/TaskTracker/TaskTracker.js +12 -0
  399. package/dist/esm/services/TaskTracker/TaskTracker.js.map +1 -0
  400. package/dist/esm/services/TaskTracker/TrackerLayerMap.js +19 -0
  401. package/dist/esm/services/TaskTracker/TrackerLayerMap.js.map +1 -0
  402. package/dist/esm/services/TaskTracker/buildEventStream.js +47 -0
  403. package/dist/esm/services/TaskTracker/buildEventStream.js.map +1 -0
  404. package/dist/esm/services/TaskTracker.js +12 -0
  405. package/dist/esm/services/TaskTracker.js.map +1 -0
  406. package/dist/esm/services/TelegramAdapter.js +118 -0
  407. package/dist/esm/services/TelegramAdapter.js.map +1 -0
  408. package/dist/esm/services/TelegramConfig.js +71 -0
  409. package/dist/esm/services/TelegramConfig.js.map +1 -0
  410. package/dist/esm/services/TelegramConfigStore.js +71 -0
  411. package/dist/esm/services/TelegramConfigStore.js.map +1 -0
  412. package/dist/esm/services/TelegramNotifier.js +41 -0
  413. package/dist/esm/services/TelegramNotifier.js.map +1 -0
  414. package/dist/esm/services/TrackerLayerMap.js +19 -0
  415. package/dist/esm/services/TrackerLayerMap.js.map +1 -0
  416. package/dist/esm/services/TrackerResolver.js +36 -0
  417. package/dist/esm/services/TrackerResolver.js.map +1 -0
  418. package/dist/esm/services/messenger/MessengerAdapter.js +21 -0
  419. package/dist/esm/services/messenger/MessengerAdapter.js.map +1 -0
  420. package/dist/esm/services/messenger/TelegramAdapter.js +118 -0
  421. package/dist/esm/services/messenger/TelegramAdapter.js.map +1 -0
  422. package/dist/esm/services/task-tracker/GitHubIssueTracker.js +150 -0
  423. package/dist/esm/services/task-tracker/GitHubIssueTracker.js.map +1 -0
  424. package/dist/esm/services/task-tracker/LinearTracker.js +120 -0
  425. package/dist/esm/services/task-tracker/LinearTracker.js.map +1 -0
  426. package/dist/esm/services/task-tracker/TaskTracker.js +12 -0
  427. package/dist/esm/services/task-tracker/TaskTracker.js.map +1 -0
  428. package/dist/esm/services/task-tracker/TrackerLayerMap.js +19 -0
  429. package/dist/esm/services/task-tracker/TrackerLayerMap.js.map +1 -0
  430. package/dist/esm/shim/bin.js +28 -0
  431. package/dist/esm/shim/bin.js.map +1 -0
  432. package/dist/esm/shim/main.js +196 -0
  433. package/dist/esm/shim/main.js.map +1 -0
  434. package/dist/esm/shim/parseArgs.js +39 -0
  435. package/dist/esm/shim/parseArgs.js.map +1 -0
  436. package/dist/esm/shim/schemas.js +28 -0
  437. package/dist/esm/shim/schemas.js.map +1 -0
  438. package/lib/AnalysisPrompts/package.json +6 -0
  439. package/lib/BranchParser/package.json +6 -0
  440. package/lib/MermaidToPlantUml/package.json +6 -0
  441. package/lib/SpecHtmlGenerator/package.json +6 -0
  442. package/lib/StreamJsonParser/package.json +6 -0
  443. package/lib/TelegramFormatter/package.json +6 -0
  444. package/lib/TelegraphMarkdown/package.json +6 -0
  445. package/package.json +360 -0
  446. package/schemas/CredentialSchemas/package.json +6 -0
  447. package/schemas/GitHubSchemas/package.json +6 -0
  448. package/schemas/LinearSchemas/package.json +6 -0
  449. package/schemas/ProjectSchemas/package.json +6 -0
  450. package/schemas/TrackerSchemas/package.json +6 -0
  451. package/services/AppContext/package.json +6 -0
  452. package/services/AppRuntimeConfig/package.json +6 -0
  453. package/services/AutoMerge/package.json +6 -0
  454. package/services/ChatMachine/package.json +6 -0
  455. package/services/CommentTimer/package.json +6 -0
  456. package/services/EventLoop/package.json +6 -0
  457. package/services/GitHubClient/package.json +6 -0
  458. package/services/LalphConfig/package.json +6 -0
  459. package/services/LinearSdkClient/package.json +6 -0
  460. package/services/MessengerAdapter/MessengerAdapter/package.json +6 -0
  461. package/services/MessengerAdapter/TelegramAdapter/package.json +6 -0
  462. package/services/OctokitClient/package.json +6 -0
  463. package/services/PlanOverviewUploader/package.json +6 -0
  464. package/services/PlanOverviewUploaderMap/package.json +6 -0
  465. package/services/PlanSession/package.json +6 -0
  466. package/services/ProjectStore/package.json +6 -0
  467. package/services/PullRequestTracker/package.json +6 -0
  468. package/services/TaskTracker/GitHubIssueTracker/package.json +6 -0
  469. package/services/TaskTracker/LinearTracker/package.json +6 -0
  470. package/services/TaskTracker/TaskTracker/package.json +6 -0
  471. package/services/TelegramConfig/package.json +6 -0
  472. package/services/TrackerLayerMap/package.json +6 -0
  473. package/shim/bin/package.json +6 -0
  474. package/shim/main/package.json +6 -0
  475. package/shim/parseArgs/package.json +6 -0
  476. package/shim/schemas/package.json +6 -0
  477. package/src/Events.ts +98 -0
  478. package/src/Main.ts +177 -0
  479. package/src/index.ts +124 -0
  480. package/src/lib/AnalysisPrompts.ts +54 -0
  481. package/src/lib/BranchParser.ts +58 -0
  482. package/src/lib/MermaidToPlantUml.ts +103 -0
  483. package/src/lib/SpecHtmlGenerator.ts +199 -0
  484. package/src/lib/StreamJsonParser.ts +99 -0
  485. package/src/lib/TelegramFormatter.ts +151 -0
  486. package/src/lib/TelegraphMarkdown.ts +305 -0
  487. package/src/schemas/CredentialSchemas.ts +23 -0
  488. package/src/schemas/GitHubSchemas.ts +50 -0
  489. package/src/schemas/LinearSchemas.ts +57 -0
  490. package/src/schemas/ProjectSchemas.ts +18 -0
  491. package/src/schemas/TrackerSchemas.ts +27 -0
  492. package/src/services/AppContext.ts +72 -0
  493. package/src/services/AppRuntimeConfig.ts +23 -0
  494. package/src/services/AutoMerge.ts +198 -0
  495. package/src/services/ChatMachine.ts +911 -0
  496. package/src/services/CommentTimer.ts +133 -0
  497. package/src/services/EventLoop.ts +321 -0
  498. package/src/services/GitHubClient.ts +282 -0
  499. package/src/services/LalphConfig.ts +218 -0
  500. package/src/services/LinearSdkClient.ts +181 -0
  501. package/src/services/MessengerAdapter/MessengerAdapter.ts +53 -0
  502. package/src/services/MessengerAdapter/TelegramAdapter.ts +145 -0
  503. package/src/services/OctokitClient.ts +628 -0
  504. package/src/services/PlanOverviewUploader.ts +160 -0
  505. package/src/services/PlanOverviewUploaderMap.ts +17 -0
  506. package/src/services/PlanSession.ts +589 -0
  507. package/src/services/ProjectStore.ts +140 -0
  508. package/src/services/PullRequestTracker.ts +253 -0
  509. package/src/services/TaskTracker/GitHubIssueTracker.ts +162 -0
  510. package/src/services/TaskTracker/LinearTracker.ts +141 -0
  511. package/src/services/TaskTracker/TaskTracker.ts +34 -0
  512. package/src/services/TelegramConfig.ts +120 -0
  513. package/src/services/TrackerLayerMap.ts +19 -0
  514. package/src/shim/bin.ts +36 -0
  515. package/src/shim/main.ts +255 -0
  516. package/src/shim/parseArgs.ts +43 -0
  517. package/src/shim/schemas.ts +38 -0
@@ -0,0 +1,140 @@
1
+ /**
2
+ * Project store — reads/writes lalph project configuration
3
+ * @since 1.0.0
4
+ */
5
+ import { FileSystem, Path } from "@effect/platform"
6
+ import type { Option } from "effect"
7
+ import { Context, Data, Effect, Layer, Schema } from "effect"
8
+ import { LalphProject } from "../schemas/ProjectSchemas.js"
9
+ import { AppContext } from "./AppContext.js"
10
+
11
+ /**
12
+ * @since 1.0.0
13
+ * @category errors
14
+ */
15
+ export class ProjectStoreError extends Data.TaggedError("ProjectStoreError")<{
16
+ message: string
17
+ cause: unknown
18
+ }> {}
19
+
20
+ /**
21
+ * @since 1.0.0
22
+ * @category services
23
+ */
24
+ export interface ProjectStoreService {
25
+ readonly listProjects: Effect.Effect<ReadonlyArray<LalphProject>, ProjectStoreError>
26
+ readonly getProject: (id: string) => Effect.Effect<LalphProject, ProjectStoreError>
27
+ readonly createProject: (data: {
28
+ readonly id: string
29
+ readonly targetBranch: Option.Option<string>
30
+ readonly concurrency: number
31
+ readonly gitFlow: "pr" | "commit"
32
+ readonly reviewAgent: boolean
33
+ }) => Effect.Effect<LalphProject, ProjectStoreError>
34
+ }
35
+
36
+ /**
37
+ * @since 1.0.0
38
+ * @category context
39
+ */
40
+ export class ProjectStore extends Context.Tag("ProjectStore")<
41
+ ProjectStore,
42
+ ProjectStoreService
43
+ >() {}
44
+
45
+ const ProjectsArray = Schema.Array(LalphProject)
46
+
47
+ /**
48
+ * @since 1.0.0
49
+ * @category layers
50
+ */
51
+ export const ProjectStoreLive = Layer.effect(
52
+ ProjectStore,
53
+ Effect.gen(function*() {
54
+ const fs = yield* FileSystem.FileSystem
55
+ const pathService = yield* Path.Path
56
+ const appContext = yield* AppContext
57
+
58
+ const filePath = pathService.join(appContext.configDir, "settings.projects")
59
+
60
+ const readProjects = Effect.gen(function*() {
61
+ const exists = yield* fs.exists(filePath).pipe(
62
+ Effect.mapError((err) =>
63
+ new ProjectStoreError({ message: `Failed to check projects file: ${String(err)}`, cause: err })
64
+ )
65
+ )
66
+ if (!exists) {
67
+ const empty: ReadonlyArray<typeof LalphProject.Type> = []
68
+ return empty
69
+ }
70
+
71
+ const content = yield* fs.readFileString(filePath).pipe(
72
+ Effect.mapError((err) =>
73
+ new ProjectStoreError({ message: `Failed to read projects file: ${String(err)}`, cause: err })
74
+ )
75
+ )
76
+ const json = yield* Effect.try({
77
+ try: () => JSON.parse(content),
78
+ catch: (err) => new ProjectStoreError({ message: `Failed to parse projects JSON: ${String(err)}`, cause: err })
79
+ })
80
+ return yield* Schema.decodeUnknown(ProjectsArray)(json).pipe(
81
+ Effect.mapError((err) =>
82
+ new ProjectStoreError({ message: `Failed to decode projects: ${String(err)}`, cause: err })
83
+ )
84
+ )
85
+ })
86
+
87
+ const listProjects = readProjects.pipe(
88
+ Effect.map((projects) => projects.filter((p) => p.enabled))
89
+ )
90
+
91
+ const getProject = (id: string) =>
92
+ readProjects.pipe(
93
+ Effect.flatMap((projects) => {
94
+ const project = projects.find((p) => p.id === id)
95
+ if (project == null) {
96
+ return Effect.fail(new ProjectStoreError({ message: `Project not found: ${id}`, cause: null }))
97
+ }
98
+ return Effect.succeed(project)
99
+ })
100
+ )
101
+
102
+ const createProject = (data: {
103
+ readonly id: string
104
+ readonly targetBranch: Option.Option<string>
105
+ readonly concurrency: number
106
+ readonly gitFlow: "pr" | "commit"
107
+ readonly reviewAgent: boolean
108
+ }) =>
109
+ Effect.gen(function*() {
110
+ const allProjects = yield* readProjects
111
+ const newProject = new LalphProject({
112
+ id: data.id,
113
+ enabled: true,
114
+ targetBranch: data.targetBranch,
115
+ concurrency: data.concurrency,
116
+ gitFlow: data.gitFlow,
117
+ reviewAgent: data.reviewAgent
118
+ })
119
+ const updated = [...allProjects, newProject]
120
+ const encoded = yield* Schema.encode(ProjectsArray)(updated).pipe(
121
+ Effect.mapError((err) =>
122
+ new ProjectStoreError({ message: `Failed to encode projects: ${String(err)}`, cause: err })
123
+ )
124
+ )
125
+ yield* fs.makeDirectory(pathService.dirname(filePath), { recursive: true }).pipe(
126
+ Effect.mapError((err) =>
127
+ new ProjectStoreError({ message: `Failed to create config dir: ${String(err)}`, cause: err })
128
+ )
129
+ )
130
+ yield* fs.writeFileString(filePath, JSON.stringify(encoded, null, 2)).pipe(
131
+ Effect.mapError((err) =>
132
+ new ProjectStoreError({ message: `Failed to write projects file: ${String(err)}`, cause: err })
133
+ )
134
+ )
135
+ return newProject
136
+ })
137
+
138
+ return ProjectStore.of({ listProjects, getProject, createProject })
139
+ })
140
+ )
@@ -0,0 +1,253 @@
1
+ /**
2
+ * GitHub event source polling service
3
+ * @since 1.0.0
4
+ */
5
+ import { Array, Context, Data, Duration, Effect, HashMap, HashSet, Layer, Option, Ref, Schedule, Stream } from "effect"
6
+ import { PRCIFailed, PRCommentAdded, PRConflictDetected, PROpened } from "../Events.js"
7
+ import type { PullRequestEvent } from "../Events.js"
8
+ import type { GitHubPullRequest, GitHubRepo } from "../schemas/GitHubSchemas.js"
9
+ import { GitHubRepo as GitHubRepoClass } from "../schemas/GitHubSchemas.js"
10
+ import { AppRuntimeConfig } from "./AppRuntimeConfig.js"
11
+ import { GitHubClient } from "./GitHubClient.js"
12
+ import { LalphConfig } from "./LalphConfig.js"
13
+
14
+ /**
15
+ * @since 1.0.0
16
+ * @category errors
17
+ */
18
+ export class PullRequestTrackerError extends Data.TaggedError("PullRequestTrackerError")<{
19
+ message: string
20
+ cause: unknown
21
+ }> {}
22
+
23
+ /**
24
+ * @since 1.0.0
25
+ * @category services
26
+ */
27
+ export interface PullRequestTrackerService {
28
+ readonly eventStream: Stream.Stream<PullRequestEvent, PullRequestTrackerError>
29
+ }
30
+
31
+ /**
32
+ * @since 1.0.0
33
+ * @category context
34
+ */
35
+ export class PullRequestTracker extends Context.Tag("PullRequestTracker")<
36
+ PullRequestTracker,
37
+ PullRequestTrackerService
38
+ >() {}
39
+
40
+ interface PRWithRepo {
41
+ readonly pr: GitHubPullRequest
42
+ readonly repo: GitHubRepo
43
+ }
44
+
45
+ const makeRepoFromFullName = (fullName: string) =>
46
+ new GitHubRepoClass({
47
+ id: 0,
48
+ name: "",
49
+ full_name: fullName,
50
+ owner: { login: "" },
51
+ html_url: ""
52
+ })
53
+
54
+ const isCIFailed = (state: string, checkRuns: ReadonlyArray<{ readonly conclusion: string | null }>) => {
55
+ const anyCheckFailed = Array.some(
56
+ checkRuns,
57
+ (cr) => cr.conclusion !== null && cr.conclusion !== "success" && cr.conclusion !== "skipped"
58
+ )
59
+ return state === "failure" || anyCheckFailed
60
+ }
61
+
62
+ /**
63
+ * @since 1.0.0
64
+ * @category layers
65
+ */
66
+ export const PullRequestTrackerLive = Layer.effect(
67
+ PullRequestTracker,
68
+ Effect.gen(function*() {
69
+ const config = yield* AppRuntimeConfig
70
+ const lalphConfig = yield* LalphConfig
71
+ const github = yield* GitHubClient
72
+ const interval = Duration.seconds(config.pollIntervalSeconds)
73
+
74
+ const authenticatedUser = yield* github.getAuthenticatedUser().pipe(
75
+ Effect.mapError((err) =>
76
+ new PullRequestTrackerError({ message: `Failed to get authenticated user: ${String(err)}`, cause: err })
77
+ )
78
+ )
79
+
80
+ const knownPRsRef = yield* Ref.make(HashSet.empty<number>())
81
+ const conflictNotifiedRef = yield* Ref.make(HashSet.empty<number>())
82
+ const lastCommentIdsRef = yield* Ref.make(HashMap.empty<number, number>())
83
+ const failureNotifiedRef = yield* Ref.make(HashMap.empty<number, string>())
84
+ const isFirstCycleRef = yield* Ref.make(true)
85
+
86
+ const pollCycle = Effect.gen(function*() {
87
+ const isFirstCycle = yield* Ref.get(isFirstCycleRef)
88
+ const knownPRs = yield* Ref.get(knownPRsRef)
89
+ const conflictNotified = yield* Ref.get(conflictNotifiedRef)
90
+ const lastCommentIds = yield* Ref.get(lastCommentIdsRef)
91
+
92
+ const allRepos = yield* github.listUserRepos().pipe(
93
+ Effect.mapError((err) =>
94
+ new PullRequestTrackerError({ message: `Failed to list repos: ${String(err)}`, cause: err })
95
+ )
96
+ )
97
+
98
+ const repos = allRepos.filter((repo) => repo.full_name === lalphConfig.repoFullName)
99
+
100
+ const allPRsWithRepos = yield* Effect.forEach(repos, (repo) =>
101
+ github.listOpenPRs(repo).pipe(
102
+ Effect.map(Array.map((pr): PRWithRepo => ({ pr, repo }))),
103
+ Effect.mapError((err) =>
104
+ new PullRequestTrackerError({
105
+ message: `Failed to list PRs for ${repo.full_name}: ${String(err)}`,
106
+ cause: err
107
+ })
108
+ )
109
+ )).pipe(Effect.map(Array.flatten))
110
+
111
+ const events: Array<PullRequestEvent> = []
112
+ const currentPRIds = HashSet.fromIterable(allPRsWithRepos.map(({ pr }) => pr.id))
113
+
114
+ // Detect new PRs (only emit PROpened after first cycle)
115
+ for (const { pr } of allPRsWithRepos) {
116
+ if (!HashSet.has(knownPRs, pr.id) && !isFirstCycle) {
117
+ events.push(new PROpened({ pr }))
118
+ }
119
+ }
120
+
121
+ // Detect conflicts (emit even on first cycle)
122
+ for (const { pr } of allPRsWithRepos) {
123
+ if (pr.hasConflicts && !HashSet.has(conflictNotified, pr.id)) {
124
+ events.push(new PRConflictDetected({ pr }))
125
+ }
126
+ }
127
+
128
+ // Detect new comments
129
+ for (const { pr, repo } of allPRsWithRepos) {
130
+ const issueComments = yield* github.listComments(repo, pr.number).pipe(
131
+ Effect.mapError((err) =>
132
+ new PullRequestTrackerError({
133
+ message: `Failed to list comments for PR #${pr.number}: ${String(err)}`,
134
+ cause: err
135
+ })
136
+ )
137
+ )
138
+ const reviewComments = yield* github.listReviewComments(repo, pr.number).pipe(
139
+ Effect.mapError((err) =>
140
+ new PullRequestTrackerError({
141
+ message: `Failed to list review comments for PR #${pr.number}: ${String(err)}`,
142
+ cause: err
143
+ })
144
+ )
145
+ )
146
+ const comments = [...issueComments, ...reviewComments]
147
+
148
+ const filteredComments = comments.filter((c) => c.user.login === authenticatedUser.login)
149
+
150
+ const lastId = Option.getOrElse(HashMap.get(lastCommentIds, pr.id), () => 0)
151
+ const newComments = filteredComments.filter((c) => c.id > lastId)
152
+
153
+ if (!isFirstCycle) {
154
+ for (const comment of newComments) {
155
+ events.push(new PRCommentAdded({ pr, comment }))
156
+ }
157
+ }
158
+
159
+ if (filteredComments.length > 0) {
160
+ const maxId = Math.max(...filteredComments.map((c) => c.id))
161
+ yield* Ref.update(lastCommentIdsRef, (m) => HashMap.set(m, pr.id, maxId))
162
+ }
163
+ }
164
+
165
+ // Detect CI failures
166
+ for (const { pr } of allPRsWithRepos) {
167
+ const repo = makeRepoFromFullName(pr.repo)
168
+ const ciStatus = yield* github.getCIStatus(repo, pr.headSha).pipe(
169
+ Effect.mapError((err) =>
170
+ new PullRequestTrackerError({
171
+ message: `Failed to get CI status for PR #${pr.number}: ${String(err)}`,
172
+ cause: err
173
+ })
174
+ )
175
+ )
176
+
177
+ if (isCIFailed(ciStatus.state, ciStatus.checkRuns)) {
178
+ const failureNotified = yield* Ref.get(failureNotifiedRef)
179
+ const notifiedSha = HashMap.get(failureNotified, pr.number)
180
+ const alreadyNotified = Option.isSome(notifiedSha) && notifiedSha.value === pr.headSha
181
+
182
+ if (!alreadyNotified) {
183
+ const failedChecks = Array.filter(
184
+ ciStatus.checkRuns,
185
+ (cr) => cr.conclusion !== null && cr.conclusion !== "success" && cr.conclusion !== "skipped"
186
+ )
187
+
188
+ const failedCheckNames = Array.map(failedChecks, (cr) => `- ${cr.name}: ${cr.conclusion}`).join("\n")
189
+ yield* github.postComment(
190
+ repo,
191
+ pr.number,
192
+ `CI checks failed for this PR:\n${failedCheckNames}`
193
+ ).pipe(
194
+ Effect.mapError((err) =>
195
+ new PullRequestTrackerError({
196
+ message: `Failed to post CI failure comment for PR #${pr.number}: ${String(err)}`,
197
+ cause: err
198
+ })
199
+ )
200
+ )
201
+
202
+ yield* Ref.update(failureNotifiedRef, (m) => HashMap.set(m, pr.number, pr.headSha))
203
+
204
+ events.push(
205
+ new PRCIFailed({
206
+ pr,
207
+ failedChecks: Array.map(failedChecks, (cr) => ({
208
+ name: cr.name,
209
+ html_url: cr.html_url,
210
+ conclusion: cr.conclusion ?? "unknown"
211
+ }))
212
+ })
213
+ )
214
+ }
215
+ }
216
+ }
217
+
218
+ // Update state
219
+ yield* Ref.set(knownPRsRef, currentPRIds)
220
+
221
+ const conflictedIds = HashSet.fromIterable(
222
+ allPRsWithRepos.filter(({ pr }) => pr.hasConflicts).map(({ pr }) => pr.id)
223
+ )
224
+ yield* Ref.set(conflictNotifiedRef, conflictedIds)
225
+
226
+ const currentPRNumbers = HashSet.fromIterable(allPRsWithRepos.map(({ pr }) => pr.number))
227
+ yield* Ref.update(
228
+ failureNotifiedRef,
229
+ (m) => HashMap.filter(m, (_, prNumber) => HashSet.has(currentPRNumbers, prNumber))
230
+ )
231
+
232
+ yield* Ref.set(isFirstCycleRef, false)
233
+
234
+ return events
235
+ })
236
+
237
+ const emptyBatch: Array<PullRequestEvent> = []
238
+
239
+ const safePollCycle = pollCycle.pipe(
240
+ Effect.tapError((err) => Effect.logError(`PullRequestTracker poll cycle failed: ${err.message}`)),
241
+ Effect.orElseSucceed(() => emptyBatch)
242
+ )
243
+
244
+ const eventStream = Stream.repeatEffectWithSchedule(
245
+ safePollCycle,
246
+ Schedule.spaced(interval)
247
+ ).pipe(
248
+ Stream.flatMap((batch) => Stream.fromIterable(batch))
249
+ )
250
+
251
+ return PullRequestTracker.of({ eventStream })
252
+ })
253
+ )
@@ -0,0 +1,162 @@
1
+ /**
2
+ * GitHub Issues implementation of TaskTracker
3
+ * @since 1.0.0
4
+ */
5
+ import { Array, DateTime, Duration, Effect, HashMap, Layer, Option, Ref, Schedule, Stream } from "effect"
6
+ import { TaskCreated, TaskUpdated } from "../../Events.js"
7
+ import type { TaskTrackerEvent } from "../../Events.js"
8
+ import { TrackerIssue, TrackerIssueEvent } from "../../schemas/TrackerSchemas.js"
9
+ import { AppRuntimeConfig } from "../AppRuntimeConfig.js"
10
+ import { OctokitClient } from "../OctokitClient.js"
11
+ import { TaskTracker, TaskTrackerError } from "./TaskTracker.js"
12
+
13
+ const extractRepoFullName = (repositoryUrl: string): string => {
14
+ const parts = repositoryUrl.split("/repos/")
15
+ return parts[1] ?? repositoryUrl
16
+ }
17
+
18
+ const parseIssueId = (issueId: string) => {
19
+ const slashIdx = issueId.indexOf("/")
20
+ const hashIdx = issueId.indexOf("#")
21
+ const owner = issueId.substring(0, slashIdx)
22
+ const repo = issueId.substring(slashIdx + 1, hashIdx)
23
+ const issueNumber = issueId.substring(hashIdx + 1)
24
+ return { owner, repo, issueNumber }
25
+ }
26
+
27
+ export const GitHubIssueTrackerLive = Layer.effect(
28
+ TaskTracker,
29
+ Effect.gen(function*() {
30
+ const octokit = yield* OctokitClient
31
+ const config = yield* AppRuntimeConfig
32
+ const interval = Duration.seconds(config.pollIntervalSeconds)
33
+
34
+ const fetchRecentEvents = (since: string) =>
35
+ Effect.gen(function*() {
36
+ const issues = yield* octokit.listUserIssues({
37
+ state: "all",
38
+ sort: "updated",
39
+ since
40
+ }).pipe(
41
+ Effect.mapError((err) =>
42
+ new TaskTrackerError({ message: `GitHub API request failed: ${String(err)}`, cause: err })
43
+ )
44
+ )
45
+ return Array.map(issues, (issue) => {
46
+ const repoFullName = extractRepoFullName(issue.repositoryUrl)
47
+ const trackerIssue = new TrackerIssue({
48
+ id: `${repoFullName}#${issue.number}`,
49
+ title: issue.title,
50
+ state: issue.state,
51
+ url: issue.htmlUrl,
52
+ createdAt: issue.createdAt,
53
+ updatedAt: issue.updatedAt
54
+ })
55
+ const action = issue.createdAt === issue.updatedAt ? "created" : "updated"
56
+ return new TrackerIssueEvent({ action, issue: trackerIssue })
57
+ })
58
+ })
59
+
60
+ const lastPollRef = yield* Ref.make(DateTime.unsafeNow())
61
+ const knownStatesRef = yield* Ref.make(HashMap.empty<string, string>())
62
+
63
+ const pollCycle = Effect.gen(function*() {
64
+ const lastPoll = yield* Ref.get(lastPollRef)
65
+ const since = DateTime.formatIso(lastPoll)
66
+ const knownStates = yield* Ref.get(knownStatesRef)
67
+ yield* Ref.set(lastPollRef, DateTime.unsafeNow())
68
+
69
+ const issueEvents = yield* fetchRecentEvents(since)
70
+
71
+ const events: Array<TaskTrackerEvent> = []
72
+ for (const issueEvent of issueEvents) {
73
+ if (issueEvent.action === "created") {
74
+ events.push(new TaskCreated({ issue: issueEvent.issue }))
75
+ yield* Ref.update(knownStatesRef, HashMap.set(issueEvent.issue.id, issueEvent.issue.state))
76
+ } else {
77
+ const previousState = HashMap.get(knownStates, issueEvent.issue.id)
78
+ const stateChanged = Option.isNone(previousState) || previousState.value !== issueEvent.issue.state
79
+ if (stateChanged) {
80
+ events.push(
81
+ new TaskUpdated({
82
+ issue: issueEvent.issue,
83
+ previousState: Option.getOrElse(previousState, () => "Unknown")
84
+ })
85
+ )
86
+ }
87
+ yield* Ref.update(knownStatesRef, HashMap.set(issueEvent.issue.id, issueEvent.issue.state))
88
+ }
89
+ }
90
+ return events
91
+ })
92
+
93
+ const emptyBatch: Array<TaskTrackerEvent> = []
94
+ const safePollCycle = pollCycle.pipe(
95
+ Effect.tapError((err) => Effect.logError(`GitHubIssueTracker poll cycle failed: ${err.message}`)),
96
+ Effect.orElseSucceed(() => emptyBatch)
97
+ )
98
+
99
+ const eventStream: Stream.Stream<TaskTrackerEvent, TaskTrackerError> = Stream.repeatEffectWithSchedule(
100
+ safePollCycle,
101
+ Schedule.spaced(interval)
102
+ ).pipe(
103
+ Stream.flatMap((batch) => Stream.fromIterable(batch))
104
+ )
105
+
106
+ return TaskTracker.of({
107
+ eventStream,
108
+
109
+ moveToTodo: (issueId) =>
110
+ Effect.gen(function*() {
111
+ const { issueNumber, owner, repo } = parseIssueId(issueId)
112
+ yield* octokit.addIssueLabels({
113
+ owner,
114
+ repo,
115
+ issueNumber: Number(issueNumber),
116
+ labels: ["todo"]
117
+ }).pipe(
118
+ Effect.mapError((err) =>
119
+ new TaskTrackerError({ message: `GitHub API request failed: ${String(err)}`, cause: err })
120
+ )
121
+ )
122
+ }),
123
+
124
+ setPriorityUrgent: (issueId) =>
125
+ Effect.gen(function*() {
126
+ const { issueNumber, owner, repo } = parseIssueId(issueId)
127
+ yield* octokit.addIssueLabels({
128
+ owner,
129
+ repo,
130
+ issueNumber: Number(issueNumber),
131
+ labels: ["urgent"]
132
+ }).pipe(
133
+ Effect.mapError((err) =>
134
+ new TaskTrackerError({ message: `GitHub API request failed: ${String(err)}`, cause: err })
135
+ )
136
+ )
137
+ }),
138
+
139
+ getIssue: (issueId) =>
140
+ Effect.gen(function*() {
141
+ const { issueNumber, owner, repo } = parseIssueId(issueId)
142
+ const issue = yield* octokit.getIssue({
143
+ owner,
144
+ repo,
145
+ issueNumber: Number(issueNumber)
146
+ }).pipe(
147
+ Effect.mapError((err) =>
148
+ new TaskTrackerError({ message: `GitHub API request failed: ${String(err)}`, cause: err })
149
+ )
150
+ )
151
+ return new TrackerIssue({
152
+ id: `${owner}/${repo}#${issue.number}`,
153
+ title: issue.title,
154
+ state: issue.state,
155
+ url: issue.htmlUrl,
156
+ createdAt: issue.createdAt,
157
+ updatedAt: issue.updatedAt
158
+ })
159
+ })
160
+ })
161
+ })
162
+ )
@@ -0,0 +1,141 @@
1
+ /**
2
+ * Linear SDK implementation of TaskTracker
3
+ * @since 1.0.0
4
+ */
5
+ import { DateTime, Duration, Effect, HashMap, Layer, Option, Ref, Schedule, Stream } from "effect"
6
+ import { TaskCreated, TaskUpdated } from "../../Events.js"
7
+ import type { TaskTrackerEvent } from "../../Events.js"
8
+ import { TrackerIssue, TrackerIssueEvent } from "../../schemas/TrackerSchemas.js"
9
+ import { AppRuntimeConfig } from "../AppRuntimeConfig.js"
10
+ import { LinearSdkClient } from "../LinearSdkClient.js"
11
+ import { TaskTracker, TaskTrackerError } from "./TaskTracker.js"
12
+
13
+ export const LinearTrackerLive = Layer.effect(
14
+ TaskTracker,
15
+ Effect.gen(function*() {
16
+ const linearClient = yield* LinearSdkClient
17
+ const config = yield* AppRuntimeConfig
18
+ const interval = Duration.seconds(config.pollIntervalSeconds)
19
+ const todoStateIdRef = yield* Ref.make<string | null>(null)
20
+
21
+ const resolveTodoStateId = Effect.gen(function*() {
22
+ const cached = yield* Ref.get(todoStateIdRef)
23
+ if (cached !== null) return cached
24
+
25
+ const states = yield* linearClient.listWorkflowStates().pipe(
26
+ Effect.mapError((err) =>
27
+ new TaskTrackerError({ message: `Failed to fetch workflow states: ${err.message}`, cause: err })
28
+ )
29
+ )
30
+ const todoState = states.find((s) => s.name === "Todo")
31
+ if (!todoState) {
32
+ return yield* new TaskTrackerError({ message: "No 'Todo' workflow state found", cause: null })
33
+ }
34
+ yield* Ref.set(todoStateIdRef, todoState.id)
35
+ return todoState.id
36
+ })
37
+
38
+ const fetchRecentEvents = (since: string) =>
39
+ linearClient.listIssues({ since }).pipe(
40
+ Effect.map((issues) =>
41
+ issues.map((node) => {
42
+ const issue = new TrackerIssue({
43
+ id: node.identifier,
44
+ title: node.title,
45
+ state: node.stateName,
46
+ url: node.url,
47
+ createdAt: node.createdAt,
48
+ updatedAt: node.updatedAt
49
+ })
50
+ const action = node.createdAt === node.updatedAt ? "created" : "updated"
51
+ return new TrackerIssueEvent({ action, issue })
52
+ })
53
+ ),
54
+ Effect.mapError((err) =>
55
+ new TaskTrackerError({ message: `Failed to get recent events: ${err.message}`, cause: err })
56
+ )
57
+ )
58
+
59
+ const lastPollRef = yield* Ref.make(DateTime.unsafeNow())
60
+ const knownStatesRef = yield* Ref.make(HashMap.empty<string, string>())
61
+
62
+ const pollCycle = Effect.gen(function*() {
63
+ const lastPoll = yield* Ref.get(lastPollRef)
64
+ const since = DateTime.formatIso(lastPoll)
65
+ const knownStates = yield* Ref.get(knownStatesRef)
66
+ yield* Ref.set(lastPollRef, DateTime.unsafeNow())
67
+
68
+ const issueEvents = yield* fetchRecentEvents(since)
69
+
70
+ const events: Array<TaskTrackerEvent> = []
71
+ for (const issueEvent of issueEvents) {
72
+ if (issueEvent.action === "created") {
73
+ events.push(new TaskCreated({ issue: issueEvent.issue }))
74
+ yield* Ref.update(knownStatesRef, HashMap.set(issueEvent.issue.id, issueEvent.issue.state))
75
+ } else {
76
+ const previousState = HashMap.get(knownStates, issueEvent.issue.id)
77
+ const stateChanged = Option.isNone(previousState) || previousState.value !== issueEvent.issue.state
78
+ if (stateChanged) {
79
+ events.push(
80
+ new TaskUpdated({
81
+ issue: issueEvent.issue,
82
+ previousState: Option.getOrElse(previousState, () => "Unknown")
83
+ })
84
+ )
85
+ }
86
+ yield* Ref.update(knownStatesRef, HashMap.set(issueEvent.issue.id, issueEvent.issue.state))
87
+ }
88
+ }
89
+ return events
90
+ })
91
+
92
+ const emptyBatch: Array<TaskTrackerEvent> = []
93
+ const safePollCycle = pollCycle.pipe(
94
+ Effect.tapError((err) => Effect.logError(`LinearTracker poll cycle failed: ${err.message}`)),
95
+ Effect.orElseSucceed(() => emptyBatch)
96
+ )
97
+
98
+ const eventStream: Stream.Stream<TaskTrackerEvent, TaskTrackerError> = Stream.repeatEffectWithSchedule(
99
+ safePollCycle,
100
+ Schedule.spaced(interval)
101
+ ).pipe(
102
+ Stream.flatMap((batch) => Stream.fromIterable(batch))
103
+ )
104
+
105
+ return TaskTracker.of({
106
+ eventStream,
107
+
108
+ moveToTodo: (issueId) =>
109
+ Effect.gen(function*() {
110
+ const stateId = yield* resolveTodoStateId
111
+ yield* linearClient.updateIssue({ id: issueId, stateId }).pipe(
112
+ Effect.mapError((err) =>
113
+ new TaskTrackerError({ message: `Failed to update issue state: ${err.message}`, cause: err })
114
+ )
115
+ )
116
+ }),
117
+
118
+ setPriorityUrgent: (issueId) =>
119
+ linearClient.updateIssuePriority({ id: issueId, priority: 1 }).pipe(
120
+ Effect.mapError((err) =>
121
+ new TaskTrackerError({ message: `Failed to set priority urgent: ${err.message}`, cause: err })
122
+ )
123
+ ),
124
+
125
+ getIssue: (issueId) =>
126
+ linearClient.getIssue({ id: issueId }).pipe(
127
+ Effect.map((node) =>
128
+ new TrackerIssue({
129
+ id: node.identifier,
130
+ title: node.title,
131
+ state: node.stateName,
132
+ url: node.url,
133
+ createdAt: node.createdAt,
134
+ updatedAt: node.updatedAt
135
+ })
136
+ ),
137
+ Effect.mapError((err) => new TaskTrackerError({ message: `Failed to get issue: ${err.message}`, cause: err }))
138
+ )
139
+ })
140
+ })
141
+ )