taskchef 8.6.2 → 8.7.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (630) hide show
  1. package/.codex-plugin/plugin.json +1 -1
  2. package/README.md +8 -4
  3. package/assets/README.md +19 -0
  4. package/assets/taskchef-app-rounded.png +0 -0
  5. package/assets/taskchef-avatar-square.png +0 -0
  6. package/assets/taskchef-avatar-square.svg +8 -0
  7. package/assets/taskchef-sidebar-dark.svg +6 -0
  8. package/assets/taskchef-sidebar-light.svg +6 -0
  9. package/assets/taskchef-sidebar.svg +6 -0
  10. package/docs/advanced-guide.md +20 -29
  11. package/docs/dashboard-ui.md +15 -0
  12. package/docs/diagrams/taskchef-next-reply-lookup.drawio +38 -0
  13. package/docs/diagrams/taskchef-next-reply-lookup.drawio.png +0 -0
  14. package/docs/diagrams/taskchef-next-storage.drawio +41 -0
  15. package/docs/diagrams/taskchef-next-storage.drawio.png +0 -0
  16. package/docs/images/taskchef-pr-icon-comparison.jpg +0 -0
  17. package/docs/images/taskchef-unified-status-popup.jpg +0 -0
  18. package/docs/mcp-app.md +261 -6
  19. package/docs/spec.md +24 -69
  20. package/docs/taskchef-next-github.md +206 -0
  21. package/docs/taskchef-next-status-research.md +102 -0
  22. package/docs/taskchef-next-storage.md +167 -0
  23. package/docs/workflows.md +4 -2
  24. package/node_modules/@napi-rs/keyring/LICENSE +21 -0
  25. package/node_modules/@napi-rs/keyring/README.md +45 -0
  26. package/node_modules/@napi-rs/keyring/index.d.ts +232 -0
  27. package/node_modules/@napi-rs/keyring/index.js +706 -0
  28. package/node_modules/@napi-rs/keyring/keytar.d.ts +53 -0
  29. package/node_modules/@napi-rs/keyring/keytar.js +26 -0
  30. package/node_modules/@napi-rs/keyring/package.json +126 -0
  31. package/node_modules/@napi-rs/keyring-darwin-arm64/README.md +3 -0
  32. package/node_modules/@napi-rs/keyring-darwin-arm64/keyring.darwin-arm64.node +0 -0
  33. package/node_modules/@napi-rs/keyring-darwin-arm64/package.json +32 -0
  34. package/node_modules/@napi-rs/keyring-darwin-x64/README.md +3 -0
  35. package/node_modules/@napi-rs/keyring-darwin-x64/keyring.darwin-x64.node +0 -0
  36. package/node_modules/@napi-rs/keyring-darwin-x64/package.json +32 -0
  37. package/node_modules/@napi-rs/keyring-linux-arm64-gnu/README.md +3 -0
  38. package/node_modules/@napi-rs/keyring-linux-arm64-gnu/keyring.linux-arm64-gnu.node +0 -0
  39. package/node_modules/@napi-rs/keyring-linux-arm64-gnu/package.json +35 -0
  40. package/node_modules/@napi-rs/keyring-linux-arm64-musl/README.md +3 -0
  41. package/node_modules/@napi-rs/keyring-linux-arm64-musl/keyring.linux-arm64-musl.node +0 -0
  42. package/node_modules/@napi-rs/keyring-linux-arm64-musl/package.json +35 -0
  43. package/node_modules/@napi-rs/keyring-linux-x64-gnu/README.md +3 -0
  44. package/node_modules/@napi-rs/keyring-linux-x64-gnu/keyring.linux-x64-gnu.node +0 -0
  45. package/node_modules/@napi-rs/keyring-linux-x64-gnu/package.json +35 -0
  46. package/node_modules/@napi-rs/keyring-linux-x64-musl/README.md +3 -0
  47. package/node_modules/@napi-rs/keyring-linux-x64-musl/keyring.linux-x64-musl.node +0 -0
  48. package/node_modules/@napi-rs/keyring-linux-x64-musl/package.json +35 -0
  49. package/node_modules/@napi-rs/keyring-win32-arm64-msvc/README.md +3 -0
  50. package/node_modules/@napi-rs/keyring-win32-arm64-msvc/keyring.win32-arm64-msvc.node +0 -0
  51. package/node_modules/@napi-rs/keyring-win32-arm64-msvc/package.json +32 -0
  52. package/node_modules/@napi-rs/keyring-win32-x64-msvc/README.md +3 -0
  53. package/node_modules/@napi-rs/keyring-win32-x64-msvc/keyring.win32-x64-msvc.node +0 -0
  54. package/node_modules/@napi-rs/keyring-win32-x64-msvc/package.json +32 -0
  55. package/node_modules/@types/debug/LICENSE +21 -0
  56. package/node_modules/@types/debug/README.md +69 -0
  57. package/node_modules/@types/debug/index.d.ts +50 -0
  58. package/node_modules/@types/debug/package.json +58 -0
  59. package/node_modules/@types/mdast/LICENSE +21 -0
  60. package/node_modules/@types/mdast/README.md +15 -0
  61. package/node_modules/@types/mdast/index.d.ts +1123 -0
  62. package/node_modules/@types/mdast/package.json +47 -0
  63. package/node_modules/@types/ms/LICENSE +21 -0
  64. package/node_modules/@types/ms/README.md +82 -0
  65. package/node_modules/@types/ms/index.d.ts +63 -0
  66. package/node_modules/@types/ms/package.json +26 -0
  67. package/node_modules/@types/unist/LICENSE +21 -0
  68. package/node_modules/@types/unist/README.md +15 -0
  69. package/node_modules/@types/unist/index.d.ts +119 -0
  70. package/node_modules/@types/unist/package.json +60 -0
  71. package/node_modules/character-entities/index.d.ts +6 -0
  72. package/node_modules/character-entities/index.js +2132 -0
  73. package/node_modules/character-entities/license +22 -0
  74. package/node_modules/character-entities/package.json +78 -0
  75. package/node_modules/character-entities/readme.md +152 -0
  76. package/node_modules/decode-named-character-reference/index.d.ts +13 -0
  77. package/node_modules/decode-named-character-reference/index.d.ts.map +1 -0
  78. package/node_modules/decode-named-character-reference/index.dom.d.ts +6 -0
  79. package/node_modules/decode-named-character-reference/index.dom.d.ts.map +1 -0
  80. package/node_modules/decode-named-character-reference/index.dom.js +32 -0
  81. package/node_modules/decode-named-character-reference/index.js +19 -0
  82. package/node_modules/decode-named-character-reference/license +22 -0
  83. package/node_modules/decode-named-character-reference/package.json +90 -0
  84. package/node_modules/decode-named-character-reference/readme.md +136 -0
  85. package/node_modules/dequal/dist/index.js +86 -0
  86. package/node_modules/dequal/dist/index.min.js +1 -0
  87. package/node_modules/dequal/dist/index.mjs +84 -0
  88. package/node_modules/dequal/index.d.ts +1 -0
  89. package/node_modules/dequal/license +21 -0
  90. package/node_modules/dequal/lite/index.d.ts +1 -0
  91. package/node_modules/dequal/lite/index.js +31 -0
  92. package/node_modules/dequal/lite/index.min.js +1 -0
  93. package/node_modules/dequal/lite/index.mjs +29 -0
  94. package/node_modules/dequal/package.json +57 -0
  95. package/node_modules/dequal/readme.md +112 -0
  96. package/node_modules/devlop/lib/default.js +9 -0
  97. package/node_modules/devlop/lib/development.d.ts +84 -0
  98. package/node_modules/devlop/lib/development.js +238 -0
  99. package/node_modules/devlop/license +22 -0
  100. package/node_modules/devlop/package.json +80 -0
  101. package/node_modules/devlop/readme.md +360 -0
  102. package/node_modules/mdast-util-from-markdown/dev/index.d.ts +23 -0
  103. package/node_modules/mdast-util-from-markdown/dev/index.js +2 -0
  104. package/node_modules/mdast-util-from-markdown/dev/lib/index.d.ts +53 -0
  105. package/node_modules/mdast-util-from-markdown/dev/lib/index.d.ts.map +1 -0
  106. package/node_modules/mdast-util-from-markdown/dev/lib/index.js +1348 -0
  107. package/node_modules/mdast-util-from-markdown/dev/lib/types.d.ts +295 -0
  108. package/node_modules/mdast-util-from-markdown/dev/lib/types.js +2 -0
  109. package/node_modules/mdast-util-from-markdown/index.d.ts +23 -0
  110. package/node_modules/mdast-util-from-markdown/index.js +2 -0
  111. package/node_modules/mdast-util-from-markdown/lib/index.d.ts +53 -0
  112. package/node_modules/mdast-util-from-markdown/lib/index.js +1177 -0
  113. package/node_modules/mdast-util-from-markdown/lib/types.d.ts +295 -0
  114. package/node_modules/mdast-util-from-markdown/lib/types.js +2 -0
  115. package/node_modules/mdast-util-from-markdown/license +22 -0
  116. package/node_modules/mdast-util-from-markdown/package.json +139 -0
  117. package/node_modules/mdast-util-from-markdown/readme.md +537 -0
  118. package/node_modules/mdast-util-to-string/index.d.ts +2 -0
  119. package/node_modules/mdast-util-to-string/index.js +5 -0
  120. package/node_modules/mdast-util-to-string/lib/index.d.ts +31 -0
  121. package/node_modules/mdast-util-to-string/lib/index.js +108 -0
  122. package/node_modules/mdast-util-to-string/license +22 -0
  123. package/node_modules/mdast-util-to-string/package.json +78 -0
  124. package/node_modules/mdast-util-to-string/readme.md +218 -0
  125. package/node_modules/micromark/dev/index.d.ts +82 -0
  126. package/node_modules/micromark/dev/index.d.ts.map +1 -0
  127. package/node_modules/micromark/dev/index.js +68 -0
  128. package/node_modules/micromark/dev/lib/compile.d.ts +16 -0
  129. package/node_modules/micromark/dev/lib/compile.d.ts.map +1 -0
  130. package/node_modules/micromark/dev/lib/compile.js +1162 -0
  131. package/node_modules/micromark/dev/lib/constructs.d.ts +73 -0
  132. package/node_modules/micromark/dev/lib/constructs.d.ts.map +1 -0
  133. package/node_modules/micromark/dev/lib/constructs.js +101 -0
  134. package/node_modules/micromark/dev/lib/create-tokenizer.d.ts +46 -0
  135. package/node_modules/micromark/dev/lib/create-tokenizer.d.ts.map +1 -0
  136. package/node_modules/micromark/dev/lib/create-tokenizer.js +718 -0
  137. package/node_modules/micromark/dev/lib/initialize/content.d.ts +4 -0
  138. package/node_modules/micromark/dev/lib/initialize/content.d.ts.map +1 -0
  139. package/node_modules/micromark/dev/lib/initialize/content.js +99 -0
  140. package/node_modules/micromark/dev/lib/initialize/document.d.ts +10 -0
  141. package/node_modules/micromark/dev/lib/initialize/document.d.ts.map +1 -0
  142. package/node_modules/micromark/dev/lib/initialize/document.js +449 -0
  143. package/node_modules/micromark/dev/lib/initialize/flow.d.ts +4 -0
  144. package/node_modules/micromark/dev/lib/initialize/flow.d.ts.map +1 -0
  145. package/node_modules/micromark/dev/lib/initialize/flow.js +86 -0
  146. package/node_modules/micromark/dev/lib/initialize/text.d.ts +8 -0
  147. package/node_modules/micromark/dev/lib/initialize/text.d.ts.map +1 -0
  148. package/node_modules/micromark/dev/lib/initialize/text.js +248 -0
  149. package/node_modules/micromark/dev/lib/parse.d.ts +10 -0
  150. package/node_modules/micromark/dev/lib/parse.d.ts.map +1 -0
  151. package/node_modules/micromark/dev/lib/parse.js +58 -0
  152. package/node_modules/micromark/dev/lib/postprocess.d.ts +9 -0
  153. package/node_modules/micromark/dev/lib/postprocess.d.ts.map +1 -0
  154. package/node_modules/micromark/dev/lib/postprocess.js +19 -0
  155. package/node_modules/micromark/dev/lib/preprocess.d.ts +13 -0
  156. package/node_modules/micromark/dev/lib/preprocess.d.ts.map +1 -0
  157. package/node_modules/micromark/dev/lib/preprocess.js +139 -0
  158. package/node_modules/micromark/dev/stream.d.ts +35 -0
  159. package/node_modules/micromark/dev/stream.d.ts.map +1 -0
  160. package/node_modules/micromark/dev/stream.js +270 -0
  161. package/node_modules/micromark/index.d.ts +82 -0
  162. package/node_modules/micromark/index.d.ts.map +1 -0
  163. package/node_modules/micromark/index.js +60 -0
  164. package/node_modules/micromark/lib/compile.d.ts +16 -0
  165. package/node_modules/micromark/lib/compile.d.ts.map +1 -0
  166. package/node_modules/micromark/lib/compile.js +1068 -0
  167. package/node_modules/micromark/lib/constructs.d.ts +73 -0
  168. package/node_modules/micromark/lib/constructs.d.ts.map +1 -0
  169. package/node_modules/micromark/lib/constructs.js +85 -0
  170. package/node_modules/micromark/lib/create-tokenizer.d.ts +46 -0
  171. package/node_modules/micromark/lib/create-tokenizer.d.ts.map +1 -0
  172. package/node_modules/micromark/lib/create-tokenizer.js +613 -0
  173. package/node_modules/micromark/lib/initialize/content.d.ts +4 -0
  174. package/node_modules/micromark/lib/initialize/content.d.ts.map +1 -0
  175. package/node_modules/micromark/lib/initialize/content.js +79 -0
  176. package/node_modules/micromark/lib/initialize/document.d.ts +10 -0
  177. package/node_modules/micromark/lib/initialize/document.d.ts.map +1 -0
  178. package/node_modules/micromark/lib/initialize/document.js +370 -0
  179. package/node_modules/micromark/lib/initialize/flow.d.ts +4 -0
  180. package/node_modules/micromark/lib/initialize/flow.d.ts.map +1 -0
  181. package/node_modules/micromark/lib/initialize/flow.js +58 -0
  182. package/node_modules/micromark/lib/initialize/text.d.ts +8 -0
  183. package/node_modules/micromark/lib/initialize/text.d.ts.map +1 -0
  184. package/node_modules/micromark/lib/initialize/text.js +216 -0
  185. package/node_modules/micromark/lib/parse.d.ts +10 -0
  186. package/node_modules/micromark/lib/parse.d.ts.map +1 -0
  187. package/node_modules/micromark/lib/parse.js +56 -0
  188. package/node_modules/micromark/lib/postprocess.d.ts +9 -0
  189. package/node_modules/micromark/lib/postprocess.d.ts.map +1 -0
  190. package/node_modules/micromark/lib/postprocess.js +18 -0
  191. package/node_modules/micromark/lib/preprocess.d.ts +13 -0
  192. package/node_modules/micromark/lib/preprocess.d.ts.map +1 -0
  193. package/node_modules/micromark/lib/preprocess.js +112 -0
  194. package/node_modules/micromark/license +22 -0
  195. package/node_modules/micromark/package.json +87 -0
  196. package/node_modules/micromark/readme.md +488 -0
  197. package/node_modules/micromark/stream.d.ts +35 -0
  198. package/node_modules/micromark/stream.d.ts.map +1 -0
  199. package/node_modules/micromark/stream.js +256 -0
  200. package/node_modules/micromark-core-commonmark/dev/index.d.ts +23 -0
  201. package/node_modules/micromark-core-commonmark/dev/index.d.ts.map +1 -0
  202. package/node_modules/micromark-core-commonmark/dev/index.js +22 -0
  203. package/node_modules/micromark-core-commonmark/dev/lib/attention.d.ts +4 -0
  204. package/node_modules/micromark-core-commonmark/dev/lib/attention.d.ts.map +1 -0
  205. package/node_modules/micromark-core-commonmark/dev/lib/attention.js +294 -0
  206. package/node_modules/micromark-core-commonmark/dev/lib/autolink.d.ts +4 -0
  207. package/node_modules/micromark-core-commonmark/dev/lib/autolink.d.ts.map +1 -0
  208. package/node_modules/micromark-core-commonmark/dev/lib/autolink.js +269 -0
  209. package/node_modules/micromark-core-commonmark/dev/lib/blank-line.d.ts +4 -0
  210. package/node_modules/micromark-core-commonmark/dev/lib/blank-line.d.ts.map +1 -0
  211. package/node_modules/micromark-core-commonmark/dev/lib/blank-line.js +62 -0
  212. package/node_modules/micromark-core-commonmark/dev/lib/block-quote.d.ts +4 -0
  213. package/node_modules/micromark-core-commonmark/dev/lib/block-quote.d.ts.map +1 -0
  214. package/node_modules/micromark-core-commonmark/dev/lib/block-quote.js +162 -0
  215. package/node_modules/micromark-core-commonmark/dev/lib/character-escape.d.ts +4 -0
  216. package/node_modules/micromark-core-commonmark/dev/lib/character-escape.d.ts.map +1 -0
  217. package/node_modules/micromark-core-commonmark/dev/lib/character-escape.js +69 -0
  218. package/node_modules/micromark-core-commonmark/dev/lib/character-reference.d.ts +4 -0
  219. package/node_modules/micromark-core-commonmark/dev/lib/character-reference.d.ts.map +1 -0
  220. package/node_modules/micromark-core-commonmark/dev/lib/character-reference.js +166 -0
  221. package/node_modules/micromark-core-commonmark/dev/lib/code-fenced.d.ts +4 -0
  222. package/node_modules/micromark-core-commonmark/dev/lib/code-fenced.d.ts.map +1 -0
  223. package/node_modules/micromark-core-commonmark/dev/lib/code-fenced.js +472 -0
  224. package/node_modules/micromark-core-commonmark/dev/lib/code-indented.d.ts +4 -0
  225. package/node_modules/micromark-core-commonmark/dev/lib/code-indented.d.ts.map +1 -0
  226. package/node_modules/micromark-core-commonmark/dev/lib/code-indented.js +178 -0
  227. package/node_modules/micromark-core-commonmark/dev/lib/code-text.d.ts +4 -0
  228. package/node_modules/micromark-core-commonmark/dev/lib/code-text.d.ts.map +1 -0
  229. package/node_modules/micromark-core-commonmark/dev/lib/code-text.js +257 -0
  230. package/node_modules/micromark-core-commonmark/dev/lib/content.d.ts +7 -0
  231. package/node_modules/micromark-core-commonmark/dev/lib/content.d.ts.map +1 -0
  232. package/node_modules/micromark-core-commonmark/dev/lib/content.js +185 -0
  233. package/node_modules/micromark-core-commonmark/dev/lib/definition.d.ts +4 -0
  234. package/node_modules/micromark-core-commonmark/dev/lib/definition.d.ts.map +1 -0
  235. package/node_modules/micromark-core-commonmark/dev/lib/definition.js +295 -0
  236. package/node_modules/micromark-core-commonmark/dev/lib/hard-break-escape.d.ts +4 -0
  237. package/node_modules/micromark-core-commonmark/dev/lib/hard-break-escape.d.ts.map +1 -0
  238. package/node_modules/micromark-core-commonmark/dev/lib/hard-break-escape.js +65 -0
  239. package/node_modules/micromark-core-commonmark/dev/lib/heading-atx.d.ts +4 -0
  240. package/node_modules/micromark-core-commonmark/dev/lib/heading-atx.d.ts.map +1 -0
  241. package/node_modules/micromark-core-commonmark/dev/lib/heading-atx.js +229 -0
  242. package/node_modules/micromark-core-commonmark/dev/lib/html-flow.d.ts +4 -0
  243. package/node_modules/micromark-core-commonmark/dev/lib/html-flow.d.ts.map +1 -0
  244. package/node_modules/micromark-core-commonmark/dev/lib/html-flow.js +938 -0
  245. package/node_modules/micromark-core-commonmark/dev/lib/html-text.d.ts +4 -0
  246. package/node_modules/micromark-core-commonmark/dev/lib/html-text.d.ts.map +1 -0
  247. package/node_modules/micromark-core-commonmark/dev/lib/html-text.js +783 -0
  248. package/node_modules/micromark-core-commonmark/dev/lib/label-end.d.ts +4 -0
  249. package/node_modules/micromark-core-commonmark/dev/lib/label-end.d.ts.map +1 -0
  250. package/node_modules/micromark-core-commonmark/dev/lib/label-end.js +658 -0
  251. package/node_modules/micromark-core-commonmark/dev/lib/label-start-image.d.ts +4 -0
  252. package/node_modules/micromark-core-commonmark/dev/lib/label-start-image.d.ts.map +1 -0
  253. package/node_modules/micromark-core-commonmark/dev/lib/label-start-image.js +119 -0
  254. package/node_modules/micromark-core-commonmark/dev/lib/label-start-link.d.ts +4 -0
  255. package/node_modules/micromark-core-commonmark/dev/lib/label-start-link.d.ts.map +1 -0
  256. package/node_modules/micromark-core-commonmark/dev/lib/label-start-link.js +71 -0
  257. package/node_modules/micromark-core-commonmark/dev/lib/line-ending.d.ts +4 -0
  258. package/node_modules/micromark-core-commonmark/dev/lib/line-ending.d.ts.map +1 -0
  259. package/node_modules/micromark-core-commonmark/dev/lib/line-ending.js +34 -0
  260. package/node_modules/micromark-core-commonmark/dev/lib/list.d.ts +4 -0
  261. package/node_modules/micromark-core-commonmark/dev/lib/list.d.ts.map +1 -0
  262. package/node_modules/micromark-core-commonmark/dev/lib/list.js +306 -0
  263. package/node_modules/micromark-core-commonmark/dev/lib/partial-non-lazy-continuation.d.ts +4 -0
  264. package/node_modules/micromark-core-commonmark/dev/lib/partial-non-lazy-continuation.d.ts.map +1 -0
  265. package/node_modules/micromark-core-commonmark/dev/lib/partial-non-lazy-continuation.js +67 -0
  266. package/node_modules/micromark-core-commonmark/dev/lib/setext-underline.d.ts +4 -0
  267. package/node_modules/micromark-core-commonmark/dev/lib/setext-underline.d.ts.map +1 -0
  268. package/node_modules/micromark-core-commonmark/dev/lib/setext-underline.js +213 -0
  269. package/node_modules/micromark-core-commonmark/dev/lib/thematic-break.d.ts +4 -0
  270. package/node_modules/micromark-core-commonmark/dev/lib/thematic-break.d.ts.map +1 -0
  271. package/node_modules/micromark-core-commonmark/dev/lib/thematic-break.js +120 -0
  272. package/node_modules/micromark-core-commonmark/index.d.ts +23 -0
  273. package/node_modules/micromark-core-commonmark/index.d.ts.map +1 -0
  274. package/node_modules/micromark-core-commonmark/index.js +22 -0
  275. package/node_modules/micromark-core-commonmark/lib/attention.d.ts +4 -0
  276. package/node_modules/micromark-core-commonmark/lib/attention.d.ts.map +1 -0
  277. package/node_modules/micromark-core-commonmark/lib/attention.js +231 -0
  278. package/node_modules/micromark-core-commonmark/lib/autolink.d.ts +4 -0
  279. package/node_modules/micromark-core-commonmark/lib/autolink.d.ts.map +1 -0
  280. package/node_modules/micromark-core-commonmark/lib/autolink.js +233 -0
  281. package/node_modules/micromark-core-commonmark/lib/blank-line.d.ts +4 -0
  282. package/node_modules/micromark-core-commonmark/lib/blank-line.d.ts.map +1 -0
  283. package/node_modules/micromark-core-commonmark/lib/blank-line.js +61 -0
  284. package/node_modules/micromark-core-commonmark/lib/block-quote.d.ts +4 -0
  285. package/node_modules/micromark-core-commonmark/lib/block-quote.d.ts.map +1 -0
  286. package/node_modules/micromark-core-commonmark/lib/block-quote.js +143 -0
  287. package/node_modules/micromark-core-commonmark/lib/character-escape.d.ts +4 -0
  288. package/node_modules/micromark-core-commonmark/lib/character-escape.d.ts.map +1 -0
  289. package/node_modules/micromark-core-commonmark/lib/character-escape.js +64 -0
  290. package/node_modules/micromark-core-commonmark/lib/character-reference.d.ts +4 -0
  291. package/node_modules/micromark-core-commonmark/lib/character-reference.d.ts.map +1 -0
  292. package/node_modules/micromark-core-commonmark/lib/character-reference.js +149 -0
  293. package/node_modules/micromark-core-commonmark/lib/code-fenced.d.ts +4 -0
  294. package/node_modules/micromark-core-commonmark/lib/code-fenced.d.ts.map +1 -0
  295. package/node_modules/micromark-core-commonmark/lib/code-fenced.js +422 -0
  296. package/node_modules/micromark-core-commonmark/lib/code-indented.d.ts +4 -0
  297. package/node_modules/micromark-core-commonmark/lib/code-indented.d.ts.map +1 -0
  298. package/node_modules/micromark-core-commonmark/lib/code-indented.js +159 -0
  299. package/node_modules/micromark-core-commonmark/lib/code-text.d.ts +4 -0
  300. package/node_modules/micromark-core-commonmark/lib/code-text.d.ts.map +1 -0
  301. package/node_modules/micromark-core-commonmark/lib/code-text.js +225 -0
  302. package/node_modules/micromark-core-commonmark/lib/content.d.ts +7 -0
  303. package/node_modules/micromark-core-commonmark/lib/content.d.ts.map +1 -0
  304. package/node_modules/micromark-core-commonmark/lib/content.js +163 -0
  305. package/node_modules/micromark-core-commonmark/lib/definition.d.ts +4 -0
  306. package/node_modules/micromark-core-commonmark/lib/definition.d.ts.map +1 -0
  307. package/node_modules/micromark-core-commonmark/lib/definition.js +254 -0
  308. package/node_modules/micromark-core-commonmark/lib/hard-break-escape.d.ts +4 -0
  309. package/node_modules/micromark-core-commonmark/lib/hard-break-escape.d.ts.map +1 -0
  310. package/node_modules/micromark-core-commonmark/lib/hard-break-escape.js +60 -0
  311. package/node_modules/micromark-core-commonmark/lib/heading-atx.d.ts +4 -0
  312. package/node_modules/micromark-core-commonmark/lib/heading-atx.d.ts.map +1 -0
  313. package/node_modules/micromark-core-commonmark/lib/heading-atx.js +191 -0
  314. package/node_modules/micromark-core-commonmark/lib/html-flow.d.ts +4 -0
  315. package/node_modules/micromark-core-commonmark/lib/html-flow.d.ts.map +1 -0
  316. package/node_modules/micromark-core-commonmark/lib/html-flow.js +827 -0
  317. package/node_modules/micromark-core-commonmark/lib/html-text.d.ts +4 -0
  318. package/node_modules/micromark-core-commonmark/lib/html-text.d.ts.map +1 -0
  319. package/node_modules/micromark-core-commonmark/lib/html-text.js +678 -0
  320. package/node_modules/micromark-core-commonmark/lib/label-end.d.ts +4 -0
  321. package/node_modules/micromark-core-commonmark/lib/label-end.d.ts.map +1 -0
  322. package/node_modules/micromark-core-commonmark/lib/label-end.js +561 -0
  323. package/node_modules/micromark-core-commonmark/lib/label-start-image.d.ts +4 -0
  324. package/node_modules/micromark-core-commonmark/lib/label-start-image.d.ts.map +1 -0
  325. package/node_modules/micromark-core-commonmark/lib/label-start-image.js +110 -0
  326. package/node_modules/micromark-core-commonmark/lib/label-start-link.d.ts +4 -0
  327. package/node_modules/micromark-core-commonmark/lib/label-start-link.d.ts.map +1 -0
  328. package/node_modules/micromark-core-commonmark/lib/label-start-link.js +63 -0
  329. package/node_modules/micromark-core-commonmark/lib/line-ending.d.ts +4 -0
  330. package/node_modules/micromark-core-commonmark/lib/line-ending.d.ts.map +1 -0
  331. package/node_modules/micromark-core-commonmark/lib/line-ending.js +33 -0
  332. package/node_modules/micromark-core-commonmark/lib/list.d.ts +4 -0
  333. package/node_modules/micromark-core-commonmark/lib/list.d.ts.map +1 -0
  334. package/node_modules/micromark-core-commonmark/lib/list.js +213 -0
  335. package/node_modules/micromark-core-commonmark/lib/partial-non-lazy-continuation.d.ts +4 -0
  336. package/node_modules/micromark-core-commonmark/lib/partial-non-lazy-continuation.d.ts.map +1 -0
  337. package/node_modules/micromark-core-commonmark/lib/partial-non-lazy-continuation.js +61 -0
  338. package/node_modules/micromark-core-commonmark/lib/setext-underline.d.ts +4 -0
  339. package/node_modules/micromark-core-commonmark/lib/setext-underline.d.ts.map +1 -0
  340. package/node_modules/micromark-core-commonmark/lib/setext-underline.js +187 -0
  341. package/node_modules/micromark-core-commonmark/lib/thematic-break.d.ts +4 -0
  342. package/node_modules/micromark-core-commonmark/lib/thematic-break.d.ts.map +1 -0
  343. package/node_modules/micromark-core-commonmark/lib/thematic-break.js +102 -0
  344. package/node_modules/micromark-core-commonmark/license +22 -0
  345. package/node_modules/micromark-core-commonmark/package.json +62 -0
  346. package/node_modules/micromark-core-commonmark/readme.md +171 -0
  347. package/node_modules/micromark-factory-destination/dev/index.d.ts +42 -0
  348. package/node_modules/micromark-factory-destination/dev/index.d.ts.map +1 -0
  349. package/node_modules/micromark-factory-destination/dev/index.js +255 -0
  350. package/node_modules/micromark-factory-destination/index.d.ts +42 -0
  351. package/node_modules/micromark-factory-destination/index.d.ts.map +1 -0
  352. package/node_modules/micromark-factory-destination/index.js +206 -0
  353. package/node_modules/micromark-factory-destination/license +22 -0
  354. package/node_modules/micromark-factory-destination/package.json +57 -0
  355. package/node_modules/micromark-factory-destination/readme.md +234 -0
  356. package/node_modules/micromark-factory-label/dev/index.d.ts +37 -0
  357. package/node_modules/micromark-factory-label/dev/index.d.ts.map +1 -0
  358. package/node_modules/micromark-factory-label/dev/index.js +172 -0
  359. package/node_modules/micromark-factory-label/index.d.ts +37 -0
  360. package/node_modules/micromark-factory-label/index.d.ts.map +1 -0
  361. package/node_modules/micromark-factory-label/index.js +148 -0
  362. package/node_modules/micromark-factory-label/license +22 -0
  363. package/node_modules/micromark-factory-label/package.json +60 -0
  364. package/node_modules/micromark-factory-label/readme.md +224 -0
  365. package/node_modules/micromark-factory-space/dev/index.d.ts +60 -0
  366. package/node_modules/micromark-factory-space/dev/index.d.ts.map +1 -0
  367. package/node_modules/micromark-factory-space/dev/index.js +122 -0
  368. package/node_modules/micromark-factory-space/index.d.ts +60 -0
  369. package/node_modules/micromark-factory-space/index.d.ts.map +1 -0
  370. package/node_modules/micromark-factory-space/index.js +116 -0
  371. package/node_modules/micromark-factory-space/license +22 -0
  372. package/node_modules/micromark-factory-space/package.json +46 -0
  373. package/node_modules/micromark-factory-space/readme.md +225 -0
  374. package/node_modules/micromark-factory-title/dev/index.d.ts +36 -0
  375. package/node_modules/micromark-factory-title/dev/index.d.ts.map +1 -0
  376. package/node_modules/micromark-factory-title/dev/index.js +169 -0
  377. package/node_modules/micromark-factory-title/index.d.ts +36 -0
  378. package/node_modules/micromark-factory-title/index.d.ts.map +1 -0
  379. package/node_modules/micromark-factory-title/index.js +158 -0
  380. package/node_modules/micromark-factory-title/license +22 -0
  381. package/node_modules/micromark-factory-title/package.json +58 -0
  382. package/node_modules/micromark-factory-title/readme.md +229 -0
  383. package/node_modules/micromark-factory-whitespace/dev/index.d.ts +22 -0
  384. package/node_modules/micromark-factory-whitespace/dev/index.d.ts.map +1 -0
  385. package/node_modules/micromark-factory-whitespace/dev/index.js +53 -0
  386. package/node_modules/micromark-factory-whitespace/index.d.ts +22 -0
  387. package/node_modules/micromark-factory-whitespace/index.d.ts.map +1 -0
  388. package/node_modules/micromark-factory-whitespace/index.js +44 -0
  389. package/node_modules/micromark-factory-whitespace/license +22 -0
  390. package/node_modules/micromark-factory-whitespace/package.json +57 -0
  391. package/node_modules/micromark-factory-whitespace/readme.md +205 -0
  392. package/node_modules/micromark-util-character/dev/index.d.ts +195 -0
  393. package/node_modules/micromark-util-character/dev/index.d.ts.map +1 -0
  394. package/node_modules/micromark-util-character/dev/index.js +252 -0
  395. package/node_modules/micromark-util-character/index.d.ts +195 -0
  396. package/node_modules/micromark-util-character/index.d.ts.map +1 -0
  397. package/node_modules/micromark-util-character/index.js +246 -0
  398. package/node_modules/micromark-util-character/license +22 -0
  399. package/node_modules/micromark-util-character/package.json +57 -0
  400. package/node_modules/micromark-util-character/readme.md +446 -0
  401. package/node_modules/micromark-util-chunked/dev/index.d.ts +41 -0
  402. package/node_modules/micromark-util-chunked/dev/index.d.ts.map +1 -0
  403. package/node_modules/micromark-util-chunked/dev/index.js +89 -0
  404. package/node_modules/micromark-util-chunked/index.d.ts +41 -0
  405. package/node_modules/micromark-util-chunked/index.d.ts.map +1 -0
  406. package/node_modules/micromark-util-chunked/index.js +81 -0
  407. package/node_modules/micromark-util-chunked/license +22 -0
  408. package/node_modules/micromark-util-chunked/package.json +57 -0
  409. package/node_modules/micromark-util-chunked/readme.md +219 -0
  410. package/node_modules/micromark-util-classify-character/dev/index.d.ts +18 -0
  411. package/node_modules/micromark-util-classify-character/dev/index.d.ts.map +1 -0
  412. package/node_modules/micromark-util-classify-character/dev/index.js +38 -0
  413. package/node_modules/micromark-util-classify-character/index.d.ts +18 -0
  414. package/node_modules/micromark-util-classify-character/index.d.ts.map +1 -0
  415. package/node_modules/micromark-util-classify-character/index.js +27 -0
  416. package/node_modules/micromark-util-classify-character/license +22 -0
  417. package/node_modules/micromark-util-classify-character/package.json +59 -0
  418. package/node_modules/micromark-util-classify-character/readme.md +205 -0
  419. package/node_modules/micromark-util-combine-extensions/index.d.ts +22 -0
  420. package/node_modules/micromark-util-combine-extensions/index.d.ts.map +1 -0
  421. package/node_modules/micromark-util-combine-extensions/index.js +143 -0
  422. package/node_modules/micromark-util-combine-extensions/license +22 -0
  423. package/node_modules/micromark-util-combine-extensions/package.json +52 -0
  424. package/node_modules/micromark-util-combine-extensions/readme.md +201 -0
  425. package/node_modules/micromark-util-decode-numeric-character-reference/dev/index.d.ts +16 -0
  426. package/node_modules/micromark-util-decode-numeric-character-reference/dev/index.d.ts.map +1 -0
  427. package/node_modules/micromark-util-decode-numeric-character-reference/dev/index.js +42 -0
  428. package/node_modules/micromark-util-decode-numeric-character-reference/index.d.ts +16 -0
  429. package/node_modules/micromark-util-decode-numeric-character-reference/index.d.ts.map +1 -0
  430. package/node_modules/micromark-util-decode-numeric-character-reference/index.js +32 -0
  431. package/node_modules/micromark-util-decode-numeric-character-reference/license +22 -0
  432. package/node_modules/micromark-util-decode-numeric-character-reference/package.json +59 -0
  433. package/node_modules/micromark-util-decode-numeric-character-reference/readme.md +184 -0
  434. package/node_modules/micromark-util-decode-string/dev/index.d.ts +14 -0
  435. package/node_modules/micromark-util-decode-string/dev/index.d.ts.map +1 -0
  436. package/node_modules/micromark-util-decode-string/dev/index.js +53 -0
  437. package/node_modules/micromark-util-decode-string/index.d.ts +14 -0
  438. package/node_modules/micromark-util-decode-string/index.d.ts.map +1 -0
  439. package/node_modules/micromark-util-decode-string/index.js +45 -0
  440. package/node_modules/micromark-util-decode-string/license +22 -0
  441. package/node_modules/micromark-util-decode-string/package.json +63 -0
  442. package/node_modules/micromark-util-decode-string/readme.md +179 -0
  443. package/node_modules/micromark-util-edit-map/dev/index.d.ts +78 -0
  444. package/node_modules/micromark-util-edit-map/dev/index.d.ts.map +1 -0
  445. package/node_modules/micromark-util-edit-map/dev/index.js +237 -0
  446. package/node_modules/micromark-util-edit-map/index.d.ts +78 -0
  447. package/node_modules/micromark-util-edit-map/index.d.ts.map +1 -0
  448. package/node_modules/micromark-util-edit-map/index.js +225 -0
  449. package/node_modules/micromark-util-edit-map/license +22 -0
  450. package/node_modules/micromark-util-edit-map/package.json +48 -0
  451. package/node_modules/micromark-util-edit-map/readme.md +234 -0
  452. package/node_modules/micromark-util-encode/index.d.ts +14 -0
  453. package/node_modules/micromark-util-encode/index.d.ts.map +1 -0
  454. package/node_modules/micromark-util-encode/index.js +33 -0
  455. package/node_modules/micromark-util-encode/license +22 -0
  456. package/node_modules/micromark-util-encode/package.json +47 -0
  457. package/node_modules/micromark-util-encode/readme.md +176 -0
  458. package/node_modules/micromark-util-html-tag-name/index.d.ts +30 -0
  459. package/node_modules/micromark-util-html-tag-name/index.d.ts.map +1 -0
  460. package/node_modules/micromark-util-html-tag-name/index.js +93 -0
  461. package/node_modules/micromark-util-html-tag-name/license +22 -0
  462. package/node_modules/micromark-util-html-tag-name/package.json +47 -0
  463. package/node_modules/micromark-util-html-tag-name/readme.md +193 -0
  464. package/node_modules/micromark-util-normalize-identifier/dev/index.d.ts +21 -0
  465. package/node_modules/micromark-util-normalize-identifier/dev/index.d.ts.map +1 -0
  466. package/node_modules/micromark-util-normalize-identifier/dev/index.js +38 -0
  467. package/node_modules/micromark-util-normalize-identifier/index.d.ts +21 -0
  468. package/node_modules/micromark-util-normalize-identifier/index.d.ts.map +1 -0
  469. package/node_modules/micromark-util-normalize-identifier/index.js +33 -0
  470. package/node_modules/micromark-util-normalize-identifier/license +22 -0
  471. package/node_modules/micromark-util-normalize-identifier/package.json +58 -0
  472. package/node_modules/micromark-util-normalize-identifier/readme.md +187 -0
  473. package/node_modules/micromark-util-resolve-all/index.d.ts +22 -0
  474. package/node_modules/micromark-util-resolve-all/index.d.ts.map +1 -0
  475. package/node_modules/micromark-util-resolve-all/index.js +32 -0
  476. package/node_modules/micromark-util-resolve-all/license +22 -0
  477. package/node_modules/micromark-util-resolve-all/package.json +48 -0
  478. package/node_modules/micromark-util-resolve-all/readme.md +238 -0
  479. package/node_modules/micromark-util-sanitize-uri/dev/index.d.ts +36 -0
  480. package/node_modules/micromark-util-sanitize-uri/dev/index.d.ts.map +1 -0
  481. package/node_modules/micromark-util-sanitize-uri/dev/index.js +124 -0
  482. package/node_modules/micromark-util-sanitize-uri/index.d.ts +36 -0
  483. package/node_modules/micromark-util-sanitize-uri/index.d.ts.map +1 -0
  484. package/node_modules/micromark-util-sanitize-uri/index.js +107 -0
  485. package/node_modules/micromark-util-sanitize-uri/license +22 -0
  486. package/node_modules/micromark-util-sanitize-uri/package.json +59 -0
  487. package/node_modules/micromark-util-sanitize-uri/readme.md +214 -0
  488. package/node_modules/micromark-util-subtokenize/dev/index.d.ts +12 -0
  489. package/node_modules/micromark-util-subtokenize/dev/index.d.ts.map +1 -0
  490. package/node_modules/micromark-util-subtokenize/dev/index.js +284 -0
  491. package/node_modules/micromark-util-subtokenize/dev/lib/splice-buffer.d.ts +161 -0
  492. package/node_modules/micromark-util-subtokenize/dev/lib/splice-buffer.d.ts.map +1 -0
  493. package/node_modules/micromark-util-subtokenize/dev/lib/splice-buffer.js +288 -0
  494. package/node_modules/micromark-util-subtokenize/index.d.ts +12 -0
  495. package/node_modules/micromark-util-subtokenize/index.d.ts.map +1 -0
  496. package/node_modules/micromark-util-subtokenize/index.js +228 -0
  497. package/node_modules/micromark-util-subtokenize/lib/splice-buffer.d.ts +161 -0
  498. package/node_modules/micromark-util-subtokenize/lib/splice-buffer.d.ts.map +1 -0
  499. package/node_modules/micromark-util-subtokenize/lib/splice-buffer.js +251 -0
  500. package/node_modules/micromark-util-subtokenize/license +22 -0
  501. package/node_modules/micromark-util-subtokenize/package.json +60 -0
  502. package/node_modules/micromark-util-subtokenize/readme.md +181 -0
  503. package/node_modules/micromark-util-symbol/lib/codes.d.ts +139 -0
  504. package/node_modules/micromark-util-symbol/lib/codes.d.ts.map +1 -0
  505. package/node_modules/micromark-util-symbol/lib/codes.js +158 -0
  506. package/node_modules/micromark-util-symbol/lib/constants.d.ts +37 -0
  507. package/node_modules/micromark-util-symbol/lib/constants.d.ts.map +1 -0
  508. package/node_modules/micromark-util-symbol/lib/constants.js +44 -0
  509. package/node_modules/micromark-util-symbol/lib/default.d.ts +5 -0
  510. package/node_modules/micromark-util-symbol/lib/default.d.ts.map +1 -0
  511. package/node_modules/micromark-util-symbol/lib/default.js +4 -0
  512. package/node_modules/micromark-util-symbol/lib/types.d.ts +106 -0
  513. package/node_modules/micromark-util-symbol/lib/types.d.ts.map +1 -0
  514. package/node_modules/micromark-util-symbol/lib/types.js +453 -0
  515. package/node_modules/micromark-util-symbol/lib/values.d.ts +102 -0
  516. package/node_modules/micromark-util-symbol/lib/values.d.ts.map +1 -0
  517. package/node_modules/micromark-util-symbol/lib/values.js +109 -0
  518. package/node_modules/micromark-util-symbol/license +22 -0
  519. package/node_modules/micromark-util-symbol/package.json +43 -0
  520. package/node_modules/micromark-util-symbol/readme.md +168 -0
  521. package/node_modules/micromark-util-types/index.d.ts +1315 -0
  522. package/node_modules/micromark-util-types/index.js +2 -0
  523. package/node_modules/micromark-util-types/license +22 -0
  524. package/node_modules/micromark-util-types/package.json +37 -0
  525. package/node_modules/micromark-util-types/readme.md +151 -0
  526. package/node_modules/smol-toml/LICENSE +24 -0
  527. package/node_modules/smol-toml/README.md +605 -0
  528. package/node_modules/smol-toml/dist/date.d.ts +41 -0
  529. package/node_modules/smol-toml/dist/date.js +156 -0
  530. package/node_modules/smol-toml/dist/error.d.ts +37 -0
  531. package/node_modules/smol-toml/dist/error.js +67 -0
  532. package/node_modules/smol-toml/dist/extract.js +289 -0
  533. package/node_modules/smol-toml/dist/index.cjs +770 -0
  534. package/node_modules/smol-toml/dist/index.d.ts +44 -0
  535. package/node_modules/smol-toml/dist/index.js +34 -0
  536. package/node_modules/smol-toml/dist/parse.d.ts +73 -0
  537. package/node_modules/smol-toml/dist/parse.js +164 -0
  538. package/node_modules/smol-toml/dist/primitive.js +151 -0
  539. package/node_modules/smol-toml/dist/stringify.d.ts +32 -0
  540. package/node_modules/smol-toml/dist/stringify.js +219 -0
  541. package/node_modules/smol-toml/dist/struct.js +156 -0
  542. package/node_modules/smol-toml/dist/util.d.ts +43 -0
  543. package/node_modules/smol-toml/dist/util.js +57 -0
  544. package/node_modules/smol-toml/package.json +68 -0
  545. package/node_modules/unist-util-stringify-position/index.d.ts +1 -0
  546. package/node_modules/unist-util-stringify-position/index.js +1 -0
  547. package/node_modules/unist-util-stringify-position/lib/index.d.ts +61 -0
  548. package/node_modules/unist-util-stringify-position/lib/index.js +84 -0
  549. package/node_modules/unist-util-stringify-position/license +22 -0
  550. package/node_modules/unist-util-stringify-position/package.json +80 -0
  551. package/node_modules/unist-util-stringify-position/readme.md +206 -0
  552. package/package.json +27 -8
  553. package/scripts/prepare-github-keyring.js +29 -0
  554. package/src/codex-app.js +20 -2
  555. package/src/codex-pricing.js +79 -0
  556. package/src/codex-projects.js +90 -0
  557. package/src/codex-session-scanner.js +748 -0
  558. package/src/codex-session-usage.js +332 -0
  559. package/src/dashboard/app.js +2 -2
  560. package/src/dashboard/dist/app.js +135 -60
  561. package/src/dashboard/dist/app.js.map +1 -1
  562. package/src/dashboard/dist/styles.css +1 -1
  563. package/src/dashboard/react/components/AnimatedUsage.test.tsx +78 -0
  564. package/src/dashboard/react/components/CardStatusIcons.test.tsx +146 -0
  565. package/src/dashboard/react/components/CardStatusIcons.tsx +138 -0
  566. package/src/dashboard/react/components/ImageGallery.tsx +22 -0
  567. package/src/dashboard/react/components/ModelSettings.test.tsx +4 -4
  568. package/src/dashboard/react/components/ModelSettings.tsx +1 -1
  569. package/src/dashboard/react/components/OpenChatButton.test.tsx +19 -0
  570. package/src/dashboard/react/components/OpenChatButton.tsx +2 -1
  571. package/src/dashboard/react/components/PrGlyph.tsx +35 -0
  572. package/src/dashboard/react/components/PullRequestBadges.tsx +18 -0
  573. package/src/dashboard/react/components/QueuedPrompts.test.tsx +42 -0
  574. package/src/dashboard/react/components/QueuedPrompts.tsx +34 -0
  575. package/src/dashboard/react/components/RelativeTime.test.tsx +100 -0
  576. package/src/dashboard/react/components/RelativeTime.tsx +46 -11
  577. package/src/dashboard/react/components/ReplyCover.test.tsx +30 -0
  578. package/src/dashboard/react/components/ReplyCover.tsx +33 -0
  579. package/src/dashboard/react/components/ReplyImagePreview.test.tsx +90 -0
  580. package/src/dashboard/react/components/ReplyImagePreview.tsx +34 -0
  581. package/src/dashboard/react/components/ReplyMarkdown.test.tsx +108 -0
  582. package/src/dashboard/react/components/ReplyMarkdown.tsx +112 -0
  583. package/src/dashboard/react/components/SavedUsageFormat.test.tsx +11 -0
  584. package/src/dashboard/react/components/SavedUsageFormat.tsx +68 -0
  585. package/src/dashboard/react/components/StatusBadge.tsx +2 -2
  586. package/src/dashboard/react/components/TaskBoard.test.tsx +256 -1
  587. package/src/dashboard/react/components/TaskBoard.tsx +136 -28
  588. package/src/dashboard/react/components/TaskCard.tsx +7 -4
  589. package/src/dashboard/react/components/TaskDetail.test.tsx +92 -1
  590. package/src/dashboard/react/components/TaskDetail.tsx +37 -10
  591. package/src/dashboard/react/components/TurnContent.test.tsx +44 -0
  592. package/src/dashboard/react/components/TurnContent.tsx +53 -0
  593. package/src/dashboard/react/components/UsagePanel.tsx +2 -2
  594. package/src/dashboard/react/image-cache.test.ts +23 -0
  595. package/src/dashboard/react/image-cache.ts +33 -0
  596. package/src/dashboard/react/presentation.test.tsx +31 -0
  597. package/src/dashboard/react/styles.css +126 -2
  598. package/src/dashboard/react/types.ts +55 -1
  599. package/src/dashboard/time.js +39 -0
  600. package/src/dashboard.js +4 -3
  601. package/src/data/codex-pricing.json +537 -0
  602. package/src/mcp-app/dist/index.html +216 -112
  603. package/src/mcp-app/react/AppearancePicker.test.tsx +50 -0
  604. package/src/mcp-app/react/AppearancePicker.tsx +56 -0
  605. package/src/mcp-app/react/GitHubConnection.test.tsx +78 -0
  606. package/src/mcp-app/react/GitHubConnection.tsx +78 -0
  607. package/src/mcp-app/react/NextNotificationCenter.test.tsx +121 -0
  608. package/src/mcp-app/react/NextNotificationCenter.tsx +94 -0
  609. package/src/mcp-app/react/NextTaskDetail.test.tsx +124 -0
  610. package/src/mcp-app/react/NextTaskDetail.tsx +147 -0
  611. package/src/mcp-app/react/ProjectPicker.tsx +49 -0
  612. package/src/mcp-app/react/main.test.tsx +499 -49
  613. package/src/mcp-app/react/main.tsx +359 -86
  614. package/src/mcp-app/react/styles.css +186 -9
  615. package/src/mcp-app/react/themes.test.ts +34 -0
  616. package/src/mcp-app/react/themes.ts +112 -0
  617. package/src/mcp-app.js +238 -120
  618. package/src/mcp.js +8 -1
  619. package/src/next-cache.js +16 -0
  620. package/src/next-github.js +273 -0
  621. package/src/next-notifications.js +90 -0
  622. package/src/recorded-usage-tracker.js +92 -0
  623. package/src/reply-image.js +65 -0
  624. package/src/usage-tracker.js +7 -6
  625. package/src/usage.js +7 -355
  626. package/src/user-prompt.js +55 -0
  627. package/src/version.js +0 -1
  628. package/node_modules/proper-lockfile/CHANGELOG.md +0 -108
  629. package/node_modules/which/CHANGELOG.md +0 -166
  630. package/src/resolve-ccusage.js +0 -17
@@ -1,22 +1,38 @@
1
+ import { cachedImageLoader } from "../../dashboard/react/image-cache";
1
2
  import { App } from "@modelcontextprotocol/ext-apps";
2
- import { ActionIcon, Alert, Box, Button, Group, MantineProvider, Paper, SegmentedControl, Select, Stack, Text, Title } from "@mantine/core";
3
- import { IconRefresh } from "@tabler/icons-react";
3
+ import { ActionIcon, Alert, Box, Button, Group, MantineProvider, Modal, createTheme, Paper, SegmentedControl, Select, Stack, Text, TextInput, Title } from "@mantine/core";
4
+ import { IconRefresh, IconSearch, IconSettings } from "@tabler/icons-react";
4
5
  import { createRoot } from "react-dom/client";
5
6
  import { useCallback, useEffect, useMemo, useRef, useState } from "react";
6
- import type { DashboardSnapshot, Task } from "../../dashboard/react/types";
7
- import { filterTasks, manualTransitionExpectedState, statusFilterCounts, STATUS_FILTERS, taskMatchesManualTransitionExpected } from "../../dashboard/state.js";
7
+ import type { DashboardSnapshot, Task, Project } from "../../dashboard/react/types";
8
+ import { filterTasks } from "../../dashboard/state.js";
8
9
  import { TaskBoard } from "../../dashboard/react/components/TaskBoard";
9
10
  import { TaskCard } from "../../dashboard/react/components/TaskCard";
10
- import { TaskDetail } from "../../dashboard/react/components/TaskDetail";
11
+ import { NextTaskDetail } from "./NextTaskDetail";
11
12
  import { RelativeTimeProvider } from "../../dashboard/react/components/RelativeTime";
13
+ import { NextNotificationCenter, type NextNotification, type NextNotificationState } from "./NextNotificationCenter";
14
+ import { GitHubConnection, type GitHubAuth } from "./GitHubConnection";
15
+ import { AppearancePicker } from "./AppearancePicker";
16
+ import { savedVisualTheme, themeVariables, visualTheme, VISUAL_THEME_KEY } from "./themes";
17
+ import { ProjectPicker } from "./ProjectPicker";
12
18
  import brandIcon from "../../../assets/taskchef-dark.svg";
13
19
  import "@mantine/core/styles.css";
14
20
  import "../../dashboard/react/styles.css";
15
21
  import "./styles.css";
16
22
 
17
- const bridge = new App({ name: "TaskChef board", version: "1.0.0" });
23
+ const theme = createTheme({
24
+ fontFamily: '-apple-system, BlinkMacSystemFont, "Segoe UI", sans-serif',
25
+ headings: { fontFamily: "inherit" },
26
+ colors: { dark: ["#dcdcdc", "#cdcdcd", "#afafaf", "#808080", "#414141", "#353535", "#282828", "#212121", "#181818", "#131313"] },
27
+ });
28
+
29
+ const bridge = new App({ name: "TaskChef", version: "1.0.0" });
18
30
  const connected = bridge.connect();
19
31
 
32
+ function logLifecycle(event: string, displayMode = bridge.getHostContext?.()?.displayMode ?? "unknown") {
33
+ console.warn(`[TaskChef] TaskChef lifecycle: ${event} ${JSON.stringify({ visibility: document.visibilityState, displayMode })}`);
34
+ }
35
+
20
36
  async function call<T>(name: string, args: Record<string, unknown> = {}): Promise<T> {
21
37
  await connected;
22
38
  const result = await bridge.callServerTool({ name, arguments: args });
@@ -24,43 +40,171 @@ async function call<T>(name: string, args: Record<string, unknown> = {}): Promis
24
40
  return result.structuredContent as T;
25
41
  }
26
42
 
43
+ const THEME_KEY = "taskchef.app.theme";
44
+ type ThemeChoice = "dark" | "light" | "system";
45
+ function initialTheme(): ThemeChoice {
46
+ try { const saved = window.localStorage.getItem(THEME_KEY); return saved === "light" || saved === "system" ? saved : "dark"; }
47
+ catch { return "dark"; }
48
+ }
49
+
27
50
  const VIEW_KEY = "taskchef.app.view";
28
51
  function initialView(): "board" | "list" {
29
52
  try { return window.localStorage.getItem(VIEW_KEY) === "board" ? "board" : "list"; }
30
53
  catch { return "list"; }
31
54
  }
32
55
 
56
+ interface VisibilitySettings { showExec: boolean; showCli: boolean; showArchived: boolean; showCalendarDates?: boolean; showCardUsage?: boolean; }
57
+ function eligibleForView(task: Task, showCli: boolean, showArchived: boolean, showExec: boolean) {
58
+ return (showExec || task.observed?.source !== "exec") && (showCli || task.observed?.source !== "cli") && (showArchived || !task.observed?.archive);
59
+ }
60
+
61
+ const loadReplyImage = cachedImageLoader(async (task: Task, url = task.replyImage?.url): Promise<string | null> => {
62
+ const result = await call<{ dataUrl: string | null }>("taskchef_app_image", { taskId: task.id, expectedTurnId: task.turnId, expectedUrl: url });
63
+ return result.dataUrl;
64
+ });
65
+
66
+ const NEXT_LANES = [{ status: "scheduled", label: "Scheduled", emptyMessage: "No scheduled chats" }, { status: "working", label: "Running", emptyMessage: "No chats running" }, { status: "needs_input", label: "Waiting for review", emptyMessage: "No chats waiting for review" }, { status: "completed", label: "Done", emptyMessage: "No completed chats" }, { status: "archived", label: "Archived", emptyMessage: "No archived chats" }, { status: null, label: "Unverified", emptyMessage: "No unverified chats" }] as const;
67
+
68
+ interface ScanStats { cacheHit?: boolean; scheduleErrors?: number; source?: "database"; mode: string; checkedAt: string; error?: string; intervalSeconds?: number; fullIntervalSeconds?: number; indexedFiles?: number; activeFiles?: number | null; archivedFiles?: number | null; parsedFiles?: number | null; visibleFiles?: number; unreadFiles?: number; errors?: number; }
69
+
33
70
  export function TaskChefApp() {
71
+ const [themeChoice, setThemeChoice] = useState<ThemeChoice>(initialTheme);
72
+ const [systemDark, setSystemDark] = useState(() => window.matchMedia?.("(prefers-color-scheme: dark)").matches ?? true);
73
+ const colorScheme = themeChoice === "system" ? (systemDark ? "dark" : "light") : themeChoice;
74
+ useEffect(() => {
75
+ const media = window.matchMedia?.("(prefers-color-scheme: dark)");
76
+ if (!media) return;
77
+ const update = () => setSystemDark(media.matches);
78
+ update();
79
+ media.addEventListener("change", update);
80
+ return () => media.removeEventListener("change", update);
81
+ }, []);
82
+ const [visualThemes, setVisualThemes] = useState(() => ({ light: savedVisualTheme("light"), dark: savedVisualTheme("dark") }));
83
+ const selectedTheme = visualTheme(visualThemes[colorScheme], colorScheme);
84
+ const variables = useMemo(() => themeVariables(selectedTheme, colorScheme), [selectedTheme, colorScheme]);
85
+ function chooseVisualTheme(id: string) {
86
+ setVisualThemes(current => ({ ...current, [colorScheme]: id }));
87
+ try { window.localStorage.setItem(`${VISUAL_THEME_KEY}.${colorScheme}`, id); } catch { /* Keep selection in memory. */ }
88
+ }
89
+ useEffect(() => {
90
+ document.documentElement.dataset.taskchefPalette = selectedTheme.id;
91
+ for (const [key, value] of Object.entries(variables)) document.documentElement.style.setProperty(key, value);
92
+ document.documentElement.dataset.taskchefTheme = colorScheme;
93
+ return () => {
94
+ delete document.documentElement.dataset.taskchefTheme;
95
+ delete document.documentElement.dataset.taskchefPalette;
96
+ for (const key of Object.keys(variables)) document.documentElement.style.removeProperty(key);
97
+ };
98
+ }, [colorScheme, selectedTheme, variables]);
99
+ function chooseTheme(value: string | null) {
100
+ const choice: ThemeChoice = value === "light" || value === "system" ? value : "dark";
101
+ setThemeChoice(choice);
102
+ try { window.localStorage.setItem(THEME_KEY, choice); } catch { /* Keep the choice for this view if storage is unavailable. */ }
103
+ }
104
+
105
+ const [displayMode, setDisplayMode] = useState(bridge.getHostContext?.()?.displayMode ?? "unknown");
106
+ const [githubOpenSignal, setGitHubOpenSignal] = useState(0);
107
+ const [githubAuth, setGitHubAuth] = useState<GitHubAuth>({ configured: false, connected: false, login: null });
34
108
  const [tasks, setTasks] = useState<Task[]>([]);
109
+ const [loading, setLoading] = useState(true);
110
+ const [taskchefVersion, setTaskchefVersion] = useState<string | null>(null);
111
+ const [registeredProjects, setRegisteredProjects] = useState<Project[]>([]);
112
+ const [{ showExec, showCli, showArchived, showCalendarDates = false, showCardUsage = true }, setVisibility] = useState<VisibilitySettings>({ showExec: false, showCli: false, showArchived: false });
113
+ const [scan, setScan] = useState<ScanStats | null>(null);
35
114
  const [selected, setSelected] = useState<Task | null>(null);
36
115
  const [opened, setOpened] = useState(false);
37
116
  const [busy, setBusy] = useState(false);
38
117
  const [error, setError] = useState<string | null>(null);
118
+
119
+ const [detailLoading, setDetailLoading] = useState(false);
39
120
  const [detailError, setDetailError] = useState<string | null>(null);
40
- const [notice, setNotice] = useState<string | null>(null);
121
+ const [archiveHelp, setArchiveHelp] = useState<Task | null>(null);
122
+ const [notifications, setNotifications] = useState<NextNotificationState>({ revision: 0, items: [] });
123
+ const [toasts, setToasts] = useState<NextNotification[]>([]);
124
+ const notificationRevision = useRef(-1);
125
+ const seenNotifications = useRef<Set<string> | null>(null);
126
+ const toastTimers = useRef(new Map<string, number>());
127
+ const dismissToast = useCallback((id: string) => {
128
+ window.clearTimeout(toastTimers.current.get(id));
129
+ toastTimers.current.delete(id);
130
+ setToasts((items) => items.filter((item) => item.id !== id));
131
+ }, []);
132
+ const receiveNotifications = useCallback((next?: NextNotificationState) => {
133
+ if (!next || next.revision < notificationRevision.current) return;
134
+ notificationRevision.current = next.revision;
135
+ setNotifications(next);
136
+ const added = seenNotifications.current ? next.items.filter((item) => !seenNotifications.current!.has(item.id)) : [];
137
+ seenNotifications.current = new Set(next.items.map((item) => item.id));
138
+ if (added.length) {
139
+ setToasts((items) => [...added, ...items].slice(0, 3));
140
+ for (const item of added) toastTimers.current.set(item.id, window.setTimeout(() => dismissToast(item.id), 5000));
141
+ }
142
+ }, [dismissToast]);
143
+ useEffect(() => () => { for (const timer of toastTimers.current.values()) window.clearTimeout(timer); }, []);
144
+ async function notificationAction(action: "read" | "read_all" | "clear", id?: string) {
145
+ try {
146
+ const result = await call<{ notifications: NextNotificationState }>("taskchef_app_notifications", { action, ...(id ? { id } : {}) });
147
+ receiveNotifications(result.notifications);
148
+ if (action === "clear") { for (const item of toasts) dismissToast(item.id); }
149
+ } catch (cause) { setError(String(cause)); throw cause; }
150
+ }
151
+ async function actionError(operation: "open" | "done" | "move" | "copy" | "settings", cause: unknown, task?: Task) {
152
+ try {
153
+ const result = await call<{ notifications: NextNotificationState }>("taskchef_app_notifications", { action: "error", operation, error: String(cause).slice(0, 1000), ...(task ? { taskId: task.id } : {}) });
154
+ receiveNotifications(result.notifications);
155
+ } catch (notificationError) { setError(`${String(cause)}. ${String(notificationError)}`); }
156
+ }
41
157
  const [project, setProject] = useState("");
158
+ const [search, setSearch] = useState("");
42
159
  const [date, setDate] = useState("all");
43
160
  const [status, setStatus] = useState("");
44
- const [view, setView] = useState(initialView);
161
+ // Keep the list implementation for later, but expose only Board. Ignore old saved List choices.
162
+ const [view, setView] = useState<"board" | "list">("board");
45
163
  const [completedLimit, setCompletedLimit] = useState(5);
164
+ const [archivedLimit, setArchivedLimit] = useState(5);
46
165
  const [now, setNow] = useState(() => Date.now());
47
166
  const selectedRef = useRef<Task | null>(null);
167
+ const detailPending = useRef(false);
168
+ function setDetailPending(value: boolean) { detailPending.current = value; setDetailLoading(value); }
48
169
  const selectionVersion = useRef(0);
170
+ const notificationSelection = useRef(false);
49
171
  const detailRequestVersion = useRef(0);
50
172
  const refreshVersion = useRef(0);
51
173
  const revisionRef = useRef<number | null>(null);
52
- const refresh = useCallback(async () => {
174
+ const displayModeRef = useRef(displayMode);
175
+ const previousDisplayMode = useRef(displayMode);
176
+ displayModeRef.current = displayMode;
177
+ const visibleTaskIds = useRef<string[]>([]);
178
+ const visibilityRefreshTimer = useRef<number | null>(null);
179
+ const refresh = useCallback(async (force = false) => {
53
180
  const version = ++refreshVersion.current;
54
181
  const initialSelection = selectionVersion.current;
55
- const data = await call<{ snapshot: DashboardSnapshot & { revision: number }; unchanged?: never } | { unchanged: true; revision: number; snapshot?: never }>(
56
- "taskchef_app_snapshot", revisionRef.current === null ? {} : { revision: revisionRef.current },
182
+ const data = await call<({ snapshot: DashboardSnapshot & { revision: number; scan: ScanStats; projects?: Project[] }; unchanged?: never; scan?: never; settings: VisibilitySettings; settingsUrl?: string | null; notifications?: NextNotificationState; github?: GitHubAuth } | { unchanged: true; revision: number; scan: ScanStats; snapshot?: never; settings: VisibilitySettings; settingsUrl?: string | null; notifications?: NextNotificationState; github?: GitHubAuth }) & { version?: string }>(
183
+ "taskchef_app_snapshot", { project, date, visibleTaskIds: visibleTaskIds.current, ...(revisionRef.current === null ? {} : { revision: revisionRef.current }), ...(force ? { force: true } : {}) },
57
184
  );
58
185
  if (version !== refreshVersion.current) return;
186
+ if (data.version) setTaskchefVersion(data.version);
187
+ setLoading(false);
188
+ receiveNotifications(data.notifications);
189
+ if (data.github) setGitHubAuth(data.github);
190
+ setVisibility(data.settings);
59
191
  if (data.snapshot) {
60
192
  revisionRef.current = data.snapshot.revision;
61
- setTasks(data.snapshot.tasks);
62
- setError(data.snapshot.healthy === false ? "Task log is temporarily unavailable. Showing the last valid snapshot." : null);
63
- } else setError(null);
193
+ setTasks(data.snapshot.healthy === false ? [] : data.snapshot.tasks);
194
+ setRegisteredProjects(data.snapshot.healthy === false ? [] : data.snapshot.projects ?? []);
195
+ setScan(data.snapshot.scan);
196
+ setError(data.snapshot.healthy === false ? data.snapshot.scan.error?.startsWith("TaskChef")
197
+ ? data.snapshot.scan.error
198
+ : "TaskChef cannot read the Codex databases. Check that state_5.sqlite and thread_history_1.sqlite are available and compatible, then refresh." : null);
199
+ if (data.snapshot.healthy === false) {
200
+ selectedRef.current = null;
201
+ selectionVersion.current += 1;
202
+ setSelected(null);
203
+ setOpened(false);
204
+ setDetailError(null);
205
+ return;
206
+ }
207
+ } else { setScan(data.scan); setError(null); }
64
208
  setNow(Date.now());
65
209
  const selectedTask = selectedRef.current;
66
210
  if (!selectedTask || initialSelection !== selectionVersion.current) return;
@@ -76,49 +220,143 @@ export function TaskChefApp() {
76
220
  clearRemovedTask();
77
221
  return;
78
222
  }
223
+ if (detailPending.current && !force) return;
79
224
  const detailRequest = ++detailRequestVersion.current;
225
+ setDetailPending(true);
80
226
  try {
81
- const detail = await call<{ task: Task }>("taskchef_app_task", { taskId: selectedTask.id });
82
- if (version !== refreshVersion.current || selection !== selectionVersion.current || detailRequest !== detailRequestVersion.current || selectedRef.current?.id !== detail.task.id) return;
227
+ const detail = await call<{ task: Task }>("taskchef_app_task", { taskId: selectedTask.id, ...(force ? { refreshGithub: true } : {}) });
228
+ if (selection !== selectionVersion.current || detailRequest !== detailRequestVersion.current || selectedRef.current?.id !== detail.task.id) return;
83
229
  selectedRef.current = detail.task;
84
230
  setSelected(detail.task);
85
231
  setDetailError(null);
86
232
  } catch (cause) {
87
- if (version !== refreshVersion.current || selection !== selectionVersion.current || detailRequest !== detailRequestVersion.current) return;
233
+ if (selection !== selectionVersion.current || detailRequest !== detailRequestVersion.current) return;
88
234
  if (cause instanceof Error && cause.message === "Task not found.") clearRemovedTask();
89
235
  else setDetailError(String(cause));
236
+ } finally {
237
+ if (selection === selectionVersion.current && detailRequest === detailRequestVersion.current) setDetailPending(false);
90
238
  }
91
- }, []);
239
+ }, [receiveNotifications, project, date]);
240
+ const onVisibleTasksChange = useCallback((ids: string[]) => {
241
+ if (JSON.stringify(ids) === JSON.stringify(visibleTaskIds.current)) return;
242
+ visibleTaskIds.current = ids;
243
+ if (visibilityRefreshTimer.current !== null) window.clearTimeout(visibilityRefreshTimer.current);
244
+ visibilityRefreshTimer.current = null;
245
+ if (ids.length === 0) return;
246
+ visibilityRefreshTimer.current = window.setTimeout(() => {
247
+ if (document.visibilityState === "visible") void refresh().catch(cause => setError(String(cause)));
248
+ }, 250);
249
+ }, [refresh]);
250
+ useEffect(() => () => { if (visibilityRefreshTimer.current !== null) window.clearTimeout(visibilityRefreshTimer.current); }, []);
251
+ const githubRequest = useCallback(async (action: "status" | "start" | "poll" | "disconnect") => (await call<{ github: GitHubAuth }>("taskchef_app_github", { action })).github, []);
252
+ const githubOpenLink = useCallback((url: string) => bridge.openLink({ url }), []);
253
+ const githubRefresh = useCallback(() => refresh(true), [refresh]);
254
+ const githubOpenSettings = useCallback(() => call("taskchef_app_open_settings"), []);
92
255
  useEffect(() => {
93
- void refresh().catch((cause) => setError(String(cause)));
94
- const timer = window.setInterval(() => { void refresh().catch((cause) => setError(String(cause))); }, 5000);
95
- return () => window.clearInterval(timer);
256
+ logLifecycle("mounted");
257
+ const onVisibility = () => {
258
+ const next = document.visibilityState;
259
+ logLifecycle("visibilitychange");
260
+ if (next === "visible" && displayModeRef.current !== "inline") void refresh().catch((cause) => { setTasks([]); setError(String(cause)); });
261
+ };
262
+ const onPageHide = () => {
263
+ logLifecycle("pagehide");
264
+ };
265
+ document.addEventListener("visibilitychange", onVisibility);
266
+ window.addEventListener("pagehide", onPageHide);
267
+ bridge.onhostcontextchanged = (context) => {
268
+ const next = context.displayMode ?? bridge.getHostContext?.()?.displayMode ?? "unknown";
269
+ logLifecycle("host context changed", next);
270
+ setDisplayMode(next);
271
+ };
272
+ bridge.onteardown = () => {
273
+ logLifecycle("host teardown");
274
+ return {};
275
+ };
276
+ void connected.then(() => setDisplayMode(bridge.getHostContext?.()?.displayMode ?? "unknown"));
277
+ void refresh().catch((cause) => { setTasks([]); setError(String(cause)); });
278
+ return () => {
279
+ logLifecycle("unmounted");
280
+ document.removeEventListener("visibilitychange", onVisibility);
281
+ window.removeEventListener("pagehide", onPageHide);
282
+ };
96
283
  }, [refresh]);
97
- const projects = useMemo(() => [
98
- { label: "All projects", value: "" },
99
- ...[...new Set(tasks.map((task) => task.project.name))].sort().map((value) => ({ label: value, value })),
100
- ], [tasks]);
101
- const visible: Task[] = useMemo(() => filterTasks(tasks, { project, date, status, now }), [tasks, project, date, status, now]);
102
- const boardTasks: Task[] = useMemo(() => filterTasks(tasks, { project, date, now }), [tasks, project, date, now]);
103
- const counts = useMemo(() => statusFilterCounts(tasks, { project, date, now }), [tasks, project, date, now]);
104
- const statusOptions = STATUS_FILTERS.map(({ label, value }: { label: string; value: string }) => ({
105
- label: counts[value] > 0 ? `${label} ${counts[value]}` : label,
106
- value,
107
- }));
284
+ useEffect(() => {
285
+ if (previousDisplayMode.current === "inline" && displayMode !== "inline" && document.visibilityState === "visible") {
286
+ void refresh().catch((cause) => { setTasks([]); setError(String(cause)); });
287
+ }
288
+ previousDisplayMode.current = displayMode;
289
+ if (displayMode === "inline") return;
290
+ const timer = window.setInterval(() => {
291
+ if (document.visibilityState === "visible") void refresh().catch((cause) => { setTasks([]); setError(String(cause)); });
292
+ }, 5000);
293
+ return () => window.clearInterval(timer);
294
+ }, [displayMode, refresh]);
295
+ const eligibleTasks = useMemo(() => tasks.filter((task) => eligibleForView(task, showCli, showArchived, showExec)), [tasks, showCli, showArchived, showExec]);
296
+ useEffect(() => {
297
+ setProject("");
298
+ setCompletedLimit(5);
299
+ setArchivedLimit(5);
300
+ if (!showArchived) setStatus((current) => current === "archived" ? "" : current);
301
+ }, [showExec, showCli, showArchived]);
302
+ const lanes = NEXT_LANES.filter((lane) => lane.status !== "archived" || showArchived);
303
+ useEffect(() => {
304
+ if (!selected || notificationSelection.current || eligibleForView(selected, showCli, showArchived, showExec)) return;
305
+ selectionVersion.current += 1;
306
+ selectedRef.current = null;
307
+ setSelected(null);
308
+ setOpened(false);
309
+ setDetailError(null);
310
+ }, [selected, showCli, showArchived, showExec]);
311
+ const projects = useMemo(() => {
312
+ const items = registeredProjects.length ? registeredProjects : [...new Map(eligibleTasks
313
+ .filter((task) => task.project.id !== "projectless")
314
+ .map((task) => [task.project.id || task.project.path || task.project.name, task.project])).values()];
315
+ const recent = new Map<string, number>();
316
+ for (const task of eligibleTasks) {
317
+ const key = task.project.id || task.project.path || task.project.name;
318
+ const timestamp = Date.parse(task.updatedAt);
319
+ if (Number.isFinite(timestamp)) recent.set(key, Math.max(recent.get(key) ?? 0, timestamp));
320
+ }
321
+ return [
322
+ { label: "All projects", value: "" },
323
+ ...items.map((item) => ({ label: items.some((other) => other !== item && other.name === item.name)
324
+ ? `${item.name} (${item.path})` : item.name, value: item.id || item.path || item.name, path: item.path, updatedAt: recent.get(item.id || item.path || item.name) })),
325
+ { label: "No project", value: "projectless" },
326
+ ];
327
+ }, [eligibleTasks, registeredProjects]);
328
+ useEffect(() => { if (project && !projects.some((item) => item.value === project)) setProject(""); }, [project, projects]);
329
+ const projectTasks = useMemo(() => eligibleTasks.filter((task) => !project || (task.project.id || task.project.path || task.project.name) === project), [eligibleTasks, project]);
330
+ const boardTasks: Task[] = useMemo(() => {
331
+ const terms = search.trim().toLocaleLowerCase().split(/\s+/).filter(Boolean);
332
+ return filterTasks(projectTasks, { date, now }).filter((task: Task) => {
333
+ const content = [
334
+ task.title, task.promptExcerpt ?? "", task.replyExcerpt ?? "", task.project.name,
335
+ ...(task.project.githubRepos ?? []),
336
+ ...(task.pullRequests ?? []).flatMap((pr) => [pr.title ?? "", pr.url.match(/^https:\/\/github\.com\/([^/]+\/[^/]+)/)?.[1] ?? ""]),
337
+ ].join("\n").toLocaleLowerCase();
338
+ return terms.every((term) => content.includes(term));
339
+ });
340
+ }, [projectTasks, date, now, search]);
341
+ const visible = useMemo(() => boardTasks.filter((task) => !status || (task.status ?? "unverified") === status), [boardTasks, status]);
342
+ const statusOptions = [{ label: `All ${boardTasks.length}`, value: "" }, ...lanes.map(({ label, status: value }) => ({
343
+ label: `${label} ${boardTasks.filter((task) => task.status === value).length}`, value: value ?? "unverified",
344
+ }))];
108
345
 
109
346
  function changeView(value: string) {
110
347
  if (value !== "board" && value !== "list") return;
111
348
  setView(value);
112
349
  try { window.localStorage.setItem(VIEW_KEY, value); } catch { /* Keep the selection in memory. */ }
113
350
  }
114
- async function select(task: Task) {
351
+ async function select(task: Task, fromNotification = false) {
352
+ notificationSelection.current = fromNotification;
115
353
  const selection = ++selectionVersion.current;
116
354
  const detailRequest = ++detailRequestVersion.current;
117
355
  selectedRef.current = task;
118
356
  setSelected(task);
119
357
  setOpened(true);
358
+ setDetailPending(true);
120
359
  setDetailError(null);
121
- setNotice(null);
122
360
  try {
123
361
  const result = await call<{ task: Task }>("taskchef_app_task", { taskId: task.id });
124
362
  if (selection !== selectionVersion.current || detailRequest !== detailRequestVersion.current) return;
@@ -126,44 +364,46 @@ export function TaskChefApp() {
126
364
  setSelected(result.task);
127
365
  } catch (cause) {
128
366
  if (selection === selectionVersion.current && detailRequest === detailRequestVersion.current) setDetailError(String(cause));
367
+ } finally {
368
+ if (selection === selectionVersion.current && detailRequest === detailRequestVersion.current) setDetailPending(false);
129
369
  }
130
370
  }
131
371
  async function openChat(task: Task) {
132
372
  setBusy(true);
133
373
  try {
134
- const result = await call<{ message: string }>("taskchef_app_open_chat", { taskId: task.id });
135
- setNotice(result.message);
374
+ await call("taskchef_app_open_chat", { taskId: task.id });
136
375
  } catch (cause) {
137
- if (selectedRef.current?.id === task.id) setDetailError(String(cause));
138
- else setError(String(cause));
376
+ await actionError("open", cause, task);
139
377
  }
140
378
  finally { setBusy(false); }
141
379
  }
142
- async function transition(targetStatus: "completed" | "failed", actionId: string) {
143
- const requestTask = selectedRef.current;
144
- if (!requestTask) return { ok: false };
145
- const selection = selectionVersion.current;
146
- const expected = manualTransitionExpectedState(requestTask);
380
+ async function markDone(task: Task) {
381
+ if (!task.turnId) return;
147
382
  setBusy(true);
148
- setDetailError(null);
149
383
  try {
150
- const result = await call<{ task: Task }>("taskchef_app_transition", {
151
- taskId: requestTask.id, actionId,
152
- expected, targetStatus,
153
- });
154
- if (selection === selectionVersion.current && taskMatchesManualTransitionExpected(selectedRef.current, expected)) {
155
- selectedRef.current = result.task;
156
- setSelected(result.task);
157
- }
158
- setTasks((current) => current.map((task) => task.id === result.task.id && taskMatchesManualTransitionExpected(task, expected) ? { ...task, ...result.task } : task));
159
- setNotice(`Marked ${result.task.status?.replace("_", " ")}.`);
160
- void refresh().catch((cause) => setError(String(cause)));
161
- return { ok: true };
162
- } catch (cause) {
163
- await refresh().catch(() => {});
164
- setDetailError(`${String(cause)} The task has been refreshed; review its current state before trying again.`);
165
- return { ok: false, rotateActionId: true };
166
- } finally { setBusy(false); }
384
+ const result = await call<{ task: Task; notifications?: NextNotificationState; github?: GitHubAuth }>("taskchef_app_set_done", { taskId: task.id, expectedTurnId: task.turnId, done: true });
385
+ if (selectedRef.current?.id === task.id) { selectedRef.current = result.task; setSelected(result.task); }
386
+ receiveNotifications(result.notifications);
387
+ await refresh().catch((cause) => { setTasks([]); setError(String(cause)); });
388
+ } catch (cause) { await actionError("done", cause, task); }
389
+ finally { setBusy(false); }
390
+ }
391
+ async function moveTask(task: Task, destination: Task["status"]) {
392
+ if (busy) return;
393
+ if (destination === "archived") { setArchiveHelp(task); return; }
394
+ if (!["needs_input", "interrupted"].includes(task.status ?? "")) return;
395
+ if (destination === "completed") {
396
+ if (task.scheduled) { await actionError("move", new Error("This chat has an active schedule. Move it to Scheduled instead of Done."), task); return; }
397
+ if (task.pullRequests?.some(pr => pr.state !== "merged")) { await actionError("move", new Error("Chats with an unmerged or unconfirmed PR cannot move to Done. Merge the PR first."), task); return; }
398
+ await markDone(task); return;
399
+ }
400
+ if (destination !== "scheduled" || !task.turnId) return;
401
+ setBusy(true);
402
+ try {
403
+ await call("taskchef_app_set_scheduled", { taskId: task.id, expectedTurnId: task.turnId });
404
+ await refresh();
405
+ } catch (cause) { await actionError("move", cause, task); }
406
+ finally { setBusy(false); }
167
407
  }
168
408
  function closeDetail() {
169
409
  if (busy) return;
@@ -173,41 +413,74 @@ export function TaskChefApp() {
173
413
  setSelected(null);
174
414
  setDetailError(null);
175
415
  }
176
- return <MantineProvider forceColorScheme="dark">
177
- <RelativeTimeProvider now={now}>
178
- <Box className="taskchef-app-shell">
416
+ return <MantineProvider theme={theme} forceColorScheme={colorScheme}>
417
+ <RelativeTimeProvider now={now} showCalendarDates={showCalendarDates}>
418
+ <Box className={`taskchef-app-shell${displayMode === "inline" ? " taskchef-app-inline" : ""}`}>
179
419
  <header className="taskchef-app-header">
180
- <Group gap="xs" wrap="nowrap"><img alt="" aria-hidden className="taskchef-app-mark" src={brandIcon} /><Title order={1}>TaskChef <span>Dashboard</span></Title></Group>
181
- <ActionIcon aria-label="Refresh" onClick={() => void refresh().catch((cause) => setError(String(cause)))} variant="subtle"><IconRefresh size={17} /></ActionIcon>
420
+ <Group className="taskchef-app-brand" gap="xs" wrap="nowrap"><img alt="" aria-hidden className="taskchef-app-mark" src={brandIcon} /><Title order={1}>TaskChef</Title></Group>
421
+ {displayMode !== "inline" && <Group className="taskchef-app-filters" gap="xs" wrap="nowrap">
422
+ <ProjectPicker data={projects} onChange={(value) => { setProject(value); setCompletedLimit(5); }} value={project} />
423
+ <Select className="taskchef-app-date" aria-label="Updated" data={[{ label: "Latest 24 hours", value: "24h" }, { label: "Latest 7 days", value: "7d" }, { label: "All time", value: "all" }]} onChange={(value) => { setDate(value ?? "all"); setCompletedLimit(5); }} value={date} size="xs" />
424
+ <TextInput className="taskchef-app-search" aria-label="Search Chats" placeholder="Search Chats" type="search" leftSection={<IconSearch size={14} aria-hidden />} value={search} onChange={(event) => { setSearch(event.currentTarget.value); setCompletedLimit(5); setArchivedLimit(5); }} size="xs" />
425
+ </Group>}
426
+ <Group className="taskchef-app-actions" gap="xs" wrap="nowrap">
427
+ <GitHubConnection hideTrigger openSignal={githubOpenSignal} auth={githubAuth} request={githubRequest} openLink={githubOpenLink} refresh={githubRefresh} openSettings={githubOpenSettings} />
428
+ <NextNotificationCenter state={notifications} toasts={toasts} onAction={notificationAction} onDismiss={dismissToast} onOpen={(item) => { const task = tasks.find((task) => task.id === item.taskId); if (task) void select(task, true); else void actionError("open", new Error("This chat is no longer available.")); }} />
429
+ <ActionIcon aria-label="Settings" title="Plugin settings" onClick={() => void (async () => {
430
+ try { await call("taskchef_app_open_settings", {}); }
431
+ catch (cause) { await actionError("settings", cause); }
432
+ })()} variant="subtle"><IconSettings size={17} /></ActionIcon>
433
+ <ActionIcon aria-label="Refresh" onClick={() => void refresh(true).catch((cause) => setError(String(cause)))} variant="subtle"><IconRefresh size={17} /></ActionIcon>
434
+ <AppearancePicker value={themeChoice} onChange={chooseTheme} visualThemeId={selectedTheme.id} appearance={colorScheme} onVisualThemeChange={chooseVisualTheme} />
435
+ </Group>
182
436
  </header>
183
- <main className={`taskchef-app-main${view === "list" ? " taskchef-app-main-list" : ""}`}>
184
- <Paper className="taskchef-toolbar" radius={0}>
185
- <Stack gap="sm">
186
- <SegmentedControl aria-label="View" className="taskchef-app-view" data={[{ label: "Board", value: "board" }, { label: "List", value: "list" }]} onChange={changeView} size="xs" value={view} withItemsBorders={false} />
187
- <Group className="taskchef-app-filters" gap="xs" wrap="nowrap">
188
- <Select aria-label="Project" data={projects} onChange={(value) => { setProject(value ?? ""); setCompletedLimit(5); }} value={project} size="xs" />
189
- <Select aria-label="Updated" data={[{ label: "Latest 24 hours", value: "24h" }, { label: "Latest 7 days", value: "7d" }, { label: "All time", value: "all" }]} onChange={(value) => { setDate(value ?? "all"); setCompletedLimit(5); }} value={date} size="xs" />
190
- </Group>
191
- {view === "list" && <Box className="taskchef-app-status"><SegmentedControl aria-label="Status" data={statusOptions} onChange={setStatus} size="xs" value={status} withItemsBorders={false} /></Box>}
437
+ {displayMode === "inline" ? <main className="taskchef-inline-main">
438
+ {error ? <Alert color="red" role="alert">{error}</Alert> : <>
439
+ <Text size="sm">{eligibleTasks.length} eligible top-level chats</Text>
440
+ <Stack gap="xs" mt="xs">
441
+ {eligibleTasks.slice(0, 3).map((task) => <Button key={task.id} onClick={() => void openChat(task)} variant="subtle">{task.title}</Button>)}
192
442
  </Stack>
193
- </Paper>
194
- {view === "list" && <Text aria-live="polite" className="taskchef-results-summary" id="task-results-summary">Tasks: {visible.length} of {tasks.length}</Text>}
195
- {error && <Alert color="yellow" role="alert" mt="sm">{error}</Alert>}
196
- {notice && !opened && <Alert color="teal" role="status" mt="sm">{notice}</Alert>}
197
- {view === "board" ? <TaskBoard completedLimit={completedLimit} onMoreCompleted={() => setCompletedLimit((limit) => limit + 5)} onOpenCodex={(task) => void openChat(task)} onOpenDetail={(task) => void select(task)} tasks={boardTasks} />
443
+ </>}
444
+ </main> : <>
445
+ <main className={`taskchef-app-main${view === "list" ? " taskchef-app-main-list" : ""}`}>
446
+ {view === "list" && <Paper className="taskchef-toolbar" radius={0}>
447
+ <Box className="taskchef-app-status"><SegmentedControl aria-label="Status" data={statusOptions} onChange={setStatus} size="xs" value={status} withItemsBorders={false} /></Box>
448
+ </Paper>}
449
+ {!!scan?.scheduleErrors && <Alert color="yellow" role="alert">{scan.scheduleErrors} schedule files could not be read; schedule placement may be incomplete.</Alert>}
450
+ {view === "list" && <Text aria-live="polite" className="taskchef-results-summary" id="task-results-summary">Tasks: {visible.length} of {eligibleTasks.length}</Text>}
451
+ {error && <Alert color="red" role="alert" mt="sm">{error}</Alert>}
452
+ {!error && (view === "board" ? <TaskBoard showCardUsage={showCardUsage} loading={loading} onMoveTask={(task, destination) => void moveTask(task, destination)} onVisibleTasksChange={onVisibleTasksChange} doneNotice={!githubAuth.connected ? <Text size="sm" c="dimmed">Connect GitHub to move merged PR chats here. <Button variant="subtle" size="compact-xs" onClick={() => setGitHubOpenSignal((value) => value + 1)}>Connect GitHub</Button></Text> : undefined} loadImage={loadReplyImage} groupInterruptedWithWaiting lanes={[...lanes]} completedLimit={completedLimit} archivedLimit={archivedLimit} onMoreArchived={() => setArchivedLimit((limit) => limit + 5)} onMoreCompleted={() => setCompletedLimit((limit) => limit + 5)} onOpenCodex={(task) => void openChat(task)} onOpenDetail={(task) => void select(task)} tasks={boardTasks} />
198
453
  : <Stack aria-describedby="task-results-summary" aria-label="Tasks" className="taskchef-list" component="section" gap="sm" mt="xs">
199
454
  {visible.map((task) => <TaskCard key={task.id} onOpenCodex={(item) => void openChat(item)} onOpenDetail={(item) => void select(item)} task={task} />)}
200
455
  {visible.length === 0 && <Paper className="taskchef-empty" p="lg" ta="center" withBorder><Title order={2} size="h5">No tasks match these filters</Title><Text c="dimmed" size="sm">Choose a different project, update window, or status.</Text></Paper>}
201
- </Stack>}
456
+ </Stack>)}
202
457
  </main>
458
+ </>}
459
+ {taskchefVersion && displayMode !== "inline" && <footer className="taskchef-app-version" aria-label="TaskChef version">v{taskchefVersion}</footer>}
203
460
  </Box>
204
- <TaskDetail busy={busy} error={detailError} highlightTurnRef={null} onClose={closeDetail} onCopy={() => {
205
- if (!selected) return;
206
- void navigator.clipboard.writeText(selected.id).then(() => setNotice("Task ID copied."), () => setNotice("Clipboard unavailable. Copy the ID from metadata."));
207
- }} onOpenCodex={() => selected && void openChat(selected)} onTransition={transition} opened={opened} task={selected} notice={notice} />
461
+ <Modal opened={!!archiveHelp} onClose={() => setArchiveHelp(null)} title="Archive in Codex" centered>
462
+ <Text size="sm">Open this chat in Codex. Use the top-right … menu and choose Archive.</Text>
463
+ <Button mt="md" disabled={busy} onClick={() => { if (archiveHelp) void openChat(archiveHelp); }}>Open chat</Button>
464
+ </Modal>
465
+ <NextTaskDetail loadImage={loadReplyImage} extraActions={selected && !selected.scheduled && !selected.manualDone && !selected.pullRequests?.length && !selected.observed?.archive && selected.observed?.lastTurnEvent !== "inProgress" ? <Button variant="default" size="compact-sm" disabled={busy} onClick={() => void markDone(selected)}>Mark Done</Button> : undefined} busy={busy} usageLoading={detailLoading} error={detailError} onClose={closeDetail} onOpenCodex={() => selected && void openChat(selected)} opened={opened} task={selected} />
208
466
  </RelativeTimeProvider>
209
467
  </MantineProvider>;
210
468
  }
211
469
 
212
470
  const root = document.getElementById("root");
213
- if (root) createRoot(root).render(<TaskChefApp />);
471
+ function GitHubSettingsApp() {
472
+ const [auth, setAuth] = useState<GitHubAuth>({ configured: false, connected: false, login: null });
473
+ const [error, setError] = useState<string | null>(null);
474
+ const request = useCallback(async (action: "status" | "start" | "poll" | "disconnect") => {
475
+ const result = await call<{ github: GitHubAuth }>("taskchef_github_settings_auth", { action });
476
+ setAuth(result.github);
477
+ return result.github;
478
+ }, []);
479
+ useEffect(() => { void request("status").catch((cause) => setError(String(cause))); }, [request]);
480
+ return <MantineProvider theme={theme} forceColorScheme="dark"><Box p="md">
481
+ <Title order={1} size="h4" mb="md">GitHub PR status</Title>
482
+ {error && <Alert color="red" role="alert" mb="sm">{error}</Alert>}
483
+ <GitHubConnection inline auth={auth} request={request} openLink={(url) => bridge.openLink({ url })} refresh={async () => { await request("status"); }} openSettings={() => call("taskchef_github_settings_open_plugin")} />
484
+ </Box></MantineProvider>;
485
+ }
486
+ if (root) createRoot(root).render(root.dataset.taskchefPage === "github" ? <GitHubSettingsApp /> : <TaskChefApp />);