@shepai/cli 1.76.0-pr240.447630e → 1.76.0-pr241.9ff2c05

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 (247) hide show
  1. package/dist/src/presentation/web/app/actions/get-feature-messages.d.ts +15 -0
  2. package/dist/src/presentation/web/app/actions/get-feature-messages.d.ts.map +1 -0
  3. package/dist/src/presentation/web/app/actions/get-feature-messages.js +26 -0
  4. package/dist/src/presentation/web/app/actions/get-feature-phase-timings.d.ts +17 -0
  5. package/dist/src/presentation/web/app/actions/get-feature-phase-timings.d.ts.map +1 -0
  6. package/dist/src/presentation/web/app/actions/get-feature-phase-timings.js +25 -0
  7. package/dist/src/presentation/web/app/actions/get-feature-plan.d.ts +18 -0
  8. package/dist/src/presentation/web/app/actions/get-feature-plan.d.ts.map +1 -0
  9. package/dist/src/presentation/web/app/actions/get-feature-plan.js +31 -0
  10. package/dist/src/presentation/web/components/common/feature-drawer-tabs/activity-tab.d.ts +8 -0
  11. package/dist/src/presentation/web/components/common/feature-drawer-tabs/activity-tab.d.ts.map +1 -0
  12. package/dist/src/presentation/web/components/common/feature-drawer-tabs/activity-tab.js +90 -0
  13. package/dist/src/presentation/web/components/common/feature-drawer-tabs/activity-tab.stories.d.ts +20 -0
  14. package/dist/src/presentation/web/components/common/feature-drawer-tabs/activity-tab.stories.d.ts.map +1 -0
  15. package/dist/src/presentation/web/components/common/feature-drawer-tabs/activity-tab.stories.js +252 -0
  16. package/dist/src/presentation/web/components/common/feature-drawer-tabs/feature-drawer-tabs.d.ts +7 -0
  17. package/dist/src/presentation/web/components/common/feature-drawer-tabs/feature-drawer-tabs.d.ts.map +1 -0
  18. package/dist/src/presentation/web/components/common/feature-drawer-tabs/feature-drawer-tabs.js +68 -0
  19. package/dist/src/presentation/web/components/common/feature-drawer-tabs/feature-drawer-tabs.stories.d.ts +14 -0
  20. package/dist/src/presentation/web/components/common/feature-drawer-tabs/feature-drawer-tabs.stories.d.ts.map +1 -0
  21. package/dist/src/presentation/web/components/common/feature-drawer-tabs/feature-drawer-tabs.stories.js +112 -0
  22. package/dist/src/presentation/web/components/common/feature-drawer-tabs/index.d.ts +3 -0
  23. package/dist/src/presentation/web/components/common/feature-drawer-tabs/index.d.ts.map +1 -0
  24. package/dist/src/presentation/web/components/common/feature-drawer-tabs/index.js +1 -0
  25. package/dist/src/presentation/web/components/common/feature-drawer-tabs/messages-tab.d.ts +8 -0
  26. package/dist/src/presentation/web/components/common/feature-drawer-tabs/messages-tab.d.ts.map +1 -0
  27. package/dist/src/presentation/web/components/common/feature-drawer-tabs/messages-tab.js +24 -0
  28. package/dist/src/presentation/web/components/common/feature-drawer-tabs/messages-tab.stories.d.ts +18 -0
  29. package/dist/src/presentation/web/components/common/feature-drawer-tabs/messages-tab.stories.d.ts.map +1 -0
  30. package/dist/src/presentation/web/components/common/feature-drawer-tabs/messages-tab.stories.js +125 -0
  31. package/dist/src/presentation/web/components/common/feature-drawer-tabs/overview-tab.d.ts +6 -0
  32. package/dist/src/presentation/web/components/common/feature-drawer-tabs/overview-tab.d.ts.map +1 -0
  33. package/dist/src/presentation/web/components/common/feature-drawer-tabs/overview-tab.js +35 -0
  34. package/dist/src/presentation/web/components/common/feature-drawer-tabs/overview-tab.stories.d.ts +28 -0
  35. package/dist/src/presentation/web/components/common/feature-drawer-tabs/overview-tab.stories.d.ts.map +1 -0
  36. package/dist/src/presentation/web/components/common/feature-drawer-tabs/overview-tab.stories.js +157 -0
  37. package/dist/src/presentation/web/components/common/feature-drawer-tabs/plan-tab.d.ts +8 -0
  38. package/dist/src/presentation/web/components/common/feature-drawer-tabs/plan-tab.d.ts.map +1 -0
  39. package/dist/src/presentation/web/components/common/feature-drawer-tabs/plan-tab.js +40 -0
  40. package/dist/src/presentation/web/components/common/feature-drawer-tabs/plan-tab.stories.d.ts +22 -0
  41. package/dist/src/presentation/web/components/common/feature-drawer-tabs/plan-tab.stories.d.ts.map +1 -0
  42. package/dist/src/presentation/web/components/common/feature-drawer-tabs/plan-tab.stories.js +188 -0
  43. package/dist/src/presentation/web/components/common/feature-drawer-tabs/use-tab-data-fetch.d.ts +30 -0
  44. package/dist/src/presentation/web/components/common/feature-drawer-tabs/use-tab-data-fetch.d.ts.map +1 -0
  45. package/dist/src/presentation/web/components/common/feature-drawer-tabs/use-tab-data-fetch.js +100 -0
  46. package/dist/src/presentation/web/components/common/feature-node/derive-feature-state.d.ts.map +1 -1
  47. package/dist/src/presentation/web/components/common/feature-node/derive-feature-state.js +1 -2
  48. package/dist/src/presentation/web/components/common/feature-node/feature-node-state-config.d.ts +1 -1
  49. package/dist/src/presentation/web/components/common/feature-node/feature-node-state-config.d.ts.map +1 -1
  50. package/dist/src/presentation/web/components/common/feature-node/feature-node-state-config.js +0 -2
  51. package/dist/tsconfig.build.tsbuildinfo +1 -1
  52. package/package.json +1 -1
  53. package/web/.next/BUILD_ID +1 -1
  54. package/web/.next/build-manifest.json +2 -2
  55. package/web/.next/cache/.previewinfo +1 -1
  56. package/web/.next/cache/.rscinfo +1 -1
  57. package/web/.next/cache/.tsbuildinfo +1 -1
  58. package/web/.next/cache/config.json +3 -3
  59. package/web/.next/fallback-build-manifest.json +2 -2
  60. package/web/.next/prerender-manifest.json +3 -3
  61. package/web/.next/server/app/(dashboard)/@drawer/create/page/server-reference-manifest.json +16 -16
  62. package/web/.next/server/app/(dashboard)/@drawer/create/page.js.nft.json +1 -1
  63. package/web/.next/server/app/(dashboard)/@drawer/create/page_client-reference-manifest.js +1 -1
  64. package/web/.next/server/app/(dashboard)/@drawer/feature/[featureId]/page/server-reference-manifest.json +19 -19
  65. package/web/.next/server/app/(dashboard)/@drawer/feature/[featureId]/page.js.nft.json +1 -1
  66. package/web/.next/server/app/(dashboard)/@drawer/feature/[featureId]/page_client-reference-manifest.js +1 -1
  67. package/web/.next/server/app/(dashboard)/@drawer/repository/[repositoryId]/page/server-reference-manifest.json +14 -14
  68. package/web/.next/server/app/(dashboard)/@drawer/repository/[repositoryId]/page.js.nft.json +1 -1
  69. package/web/.next/server/app/(dashboard)/@drawer/repository/[repositoryId]/page_client-reference-manifest.js +1 -1
  70. package/web/.next/server/app/(dashboard)/create/page/server-reference-manifest.json +16 -16
  71. package/web/.next/server/app/(dashboard)/create/page.js.nft.json +1 -1
  72. package/web/.next/server/app/(dashboard)/create/page_client-reference-manifest.js +1 -1
  73. package/web/.next/server/app/(dashboard)/feature/[featureId]/page/server-reference-manifest.json +19 -19
  74. package/web/.next/server/app/(dashboard)/feature/[featureId]/page.js.nft.json +1 -1
  75. package/web/.next/server/app/(dashboard)/feature/[featureId]/page_client-reference-manifest.js +1 -1
  76. package/web/.next/server/app/(dashboard)/page/server-reference-manifest.json +14 -14
  77. package/web/.next/server/app/(dashboard)/page.js.nft.json +1 -1
  78. package/web/.next/server/app/(dashboard)/page_client-reference-manifest.js +1 -1
  79. package/web/.next/server/app/(dashboard)/repository/[repositoryId]/page/server-reference-manifest.json +14 -14
  80. package/web/.next/server/app/(dashboard)/repository/[repositoryId]/page.js.nft.json +1 -1
  81. package/web/.next/server/app/(dashboard)/repository/[repositoryId]/page_client-reference-manifest.js +1 -1
  82. package/web/.next/server/app/_global-error.html +2 -2
  83. package/web/.next/server/app/_global-error.rsc +1 -1
  84. package/web/.next/server/app/_global-error.segments/__PAGE__.segment.rsc +1 -1
  85. package/web/.next/server/app/_global-error.segments/_full.segment.rsc +1 -1
  86. package/web/.next/server/app/_global-error.segments/_head.segment.rsc +1 -1
  87. package/web/.next/server/app/_global-error.segments/_index.segment.rsc +1 -1
  88. package/web/.next/server/app/_global-error.segments/_tree.segment.rsc +1 -1
  89. package/web/.next/server/app/_not-found/page/server-reference-manifest.json +1 -1
  90. package/web/.next/server/app/_not-found/page_client-reference-manifest.js +1 -1
  91. package/web/.next/server/app/skills/page/server-reference-manifest.json +6 -6
  92. package/web/.next/server/app/skills/page.js.nft.json +1 -1
  93. package/web/.next/server/app/skills/page_client-reference-manifest.js +1 -1
  94. package/web/.next/server/app/tools/page/server-reference-manifest.json +6 -6
  95. package/web/.next/server/app/tools/page.js.nft.json +1 -1
  96. package/web/.next/server/app/tools/page_client-reference-manifest.js +1 -1
  97. package/web/.next/server/app/version/page/server-reference-manifest.json +1 -1
  98. package/web/.next/server/app/version/page_client-reference-manifest.js +1 -1
  99. package/web/.next/server/chunks/ssr/744ca_web_components_common_control-center-drawer_create-drawer-client_tsx_5e26fc0a._.js +1 -1
  100. package/web/.next/server/chunks/ssr/744ca_web_components_common_control-center-drawer_create-drawer-client_tsx_5e26fc0a._.js.map +1 -1
  101. package/web/.next/server/chunks/ssr/8ba4b_server_app_(dashboard)_@drawer_repository_[repositoryId]_page_actions_da7eef33.js +1 -1
  102. package/web/.next/server/chunks/ssr/8ba4b_server_app_(dashboard)_@drawer_repository_[repositoryId]_page_actions_da7eef33.js.map +1 -1
  103. package/web/.next/server/chunks/ssr/8ba4b_server_app_(dashboard)_repository_[repositoryId]_page_actions_0a9251aa.js +1 -1
  104. package/web/.next/server/chunks/ssr/8ba4b_server_app_(dashboard)_repository_[repositoryId]_page_actions_0a9251aa.js.map +1 -1
  105. package/web/.next/server/chunks/ssr/[root-of-the-server]__17a611f0._.js +2 -2
  106. package/web/.next/server/chunks/ssr/[root-of-the-server]__17a611f0._.js.map +1 -1
  107. package/web/.next/server/chunks/ssr/[root-of-the-server]__45dbf93d._.js +2 -2
  108. package/web/.next/server/chunks/ssr/[root-of-the-server]__45dbf93d._.js.map +1 -1
  109. package/web/.next/server/chunks/ssr/[root-of-the-server]__6258349c._.js +1 -1
  110. package/web/.next/server/chunks/ssr/[root-of-the-server]__6258349c._.js.map +1 -1
  111. package/web/.next/server/chunks/ssr/[root-of-the-server]__6b17a22d._.js +1 -1
  112. package/web/.next/server/chunks/ssr/[root-of-the-server]__6b17a22d._.js.map +1 -1
  113. package/web/.next/server/chunks/ssr/[root-of-the-server]__6cbc1149._.js +2 -2
  114. package/web/.next/server/chunks/ssr/[root-of-the-server]__804c006d._.js +1 -1
  115. package/web/.next/server/chunks/ssr/[root-of-the-server]__804c006d._.js.map +1 -1
  116. package/web/.next/server/chunks/ssr/[root-of-the-server]__94a6d275._.js +1 -1
  117. package/web/.next/server/chunks/ssr/[root-of-the-server]__94a6d275._.js.map +1 -1
  118. package/web/.next/server/chunks/ssr/[root-of-the-server]__aad040c0._.js +1 -1
  119. package/web/.next/server/chunks/ssr/[root-of-the-server]__aad040c0._.js.map +1 -1
  120. package/web/.next/server/chunks/ssr/_0e9d6bf7._.js +1 -1
  121. package/web/.next/server/chunks/ssr/_0e9d6bf7._.js.map +1 -1
  122. package/web/.next/server/chunks/ssr/{_d8868bc0._.js → _30fd6f01._.js} +2 -2
  123. package/web/.next/server/chunks/ssr/{_d8868bc0._.js.map → _30fd6f01._.js.map} +1 -1
  124. package/web/.next/server/chunks/ssr/_61351ed3._.js +1 -1
  125. package/web/.next/server/chunks/ssr/_61351ed3._.js.map +1 -1
  126. package/web/.next/server/chunks/ssr/_6e08ce21._.js +1 -1
  127. package/web/.next/server/chunks/ssr/_6e08ce21._.js.map +1 -1
  128. package/web/.next/server/chunks/ssr/_8400c8bb._.js +1 -1
  129. package/web/.next/server/chunks/ssr/_8400c8bb._.js.map +1 -1
  130. package/web/.next/server/chunks/ssr/_9f940437._.js +1 -1
  131. package/web/.next/server/chunks/ssr/_9f940437._.js.map +1 -1
  132. package/web/.next/server/chunks/ssr/src_presentation_web_163038ba._.js +2 -2
  133. package/web/.next/server/chunks/ssr/src_presentation_web_163038ba._.js.map +1 -1
  134. package/web/.next/server/chunks/ssr/src_presentation_web_30d7eeda._.js +1 -1
  135. package/web/.next/server/chunks/ssr/src_presentation_web_30d7eeda._.js.map +1 -1
  136. package/web/.next/server/chunks/ssr/src_presentation_web_459cb687._.js +2 -2
  137. package/web/.next/server/chunks/ssr/src_presentation_web_459cb687._.js.map +1 -1
  138. package/web/.next/server/chunks/ssr/src_presentation_web_565a14f8._.js +1 -1
  139. package/web/.next/server/chunks/ssr/src_presentation_web_565a14f8._.js.map +1 -1
  140. package/web/.next/server/chunks/ssr/src_presentation_web__next-internal_server_app_(dashboard)_page_actions_021a05f2.js +1 -1
  141. package/web/.next/server/chunks/ssr/src_presentation_web__next-internal_server_app_(dashboard)_page_actions_021a05f2.js.map +1 -1
  142. package/web/.next/server/chunks/ssr/src_presentation_web_components_features_control-center_7ac3562e._.js +1 -1
  143. package/web/.next/server/chunks/ssr/src_presentation_web_components_features_control-center_7ac3562e._.js.map +1 -1
  144. package/web/.next/server/pages/500.html +2 -2
  145. package/web/.next/server/server-reference-manifest.js +1 -1
  146. package/web/.next/server/server-reference-manifest.json +22 -22
  147. package/web/.next/standalone/src/presentation/web/.next/BUILD_ID +1 -1
  148. package/web/.next/standalone/src/presentation/web/.next/build-manifest.json +2 -2
  149. package/web/.next/standalone/src/presentation/web/.next/prerender-manifest.json +3 -3
  150. package/web/.next/standalone/src/presentation/web/.next/server/app/(dashboard)/@drawer/create/page/server-reference-manifest.json +16 -16
  151. package/web/.next/standalone/src/presentation/web/.next/server/app/(dashboard)/@drawer/create/page.js.nft.json +1 -1
  152. package/web/.next/standalone/src/presentation/web/.next/server/app/(dashboard)/@drawer/create/page_client-reference-manifest.js +1 -1
  153. package/web/.next/standalone/src/presentation/web/.next/server/app/(dashboard)/@drawer/feature/[featureId]/page/server-reference-manifest.json +19 -19
  154. package/web/.next/standalone/src/presentation/web/.next/server/app/(dashboard)/@drawer/feature/[featureId]/page.js.nft.json +1 -1
  155. package/web/.next/standalone/src/presentation/web/.next/server/app/(dashboard)/@drawer/feature/[featureId]/page_client-reference-manifest.js +1 -1
  156. package/web/.next/standalone/src/presentation/web/.next/server/app/(dashboard)/@drawer/repository/[repositoryId]/page/server-reference-manifest.json +14 -14
  157. package/web/.next/standalone/src/presentation/web/.next/server/app/(dashboard)/@drawer/repository/[repositoryId]/page.js.nft.json +1 -1
  158. package/web/.next/standalone/src/presentation/web/.next/server/app/(dashboard)/@drawer/repository/[repositoryId]/page_client-reference-manifest.js +1 -1
  159. package/web/.next/standalone/src/presentation/web/.next/server/app/(dashboard)/create/page/server-reference-manifest.json +16 -16
  160. package/web/.next/standalone/src/presentation/web/.next/server/app/(dashboard)/create/page.js.nft.json +1 -1
  161. package/web/.next/standalone/src/presentation/web/.next/server/app/(dashboard)/create/page_client-reference-manifest.js +1 -1
  162. package/web/.next/standalone/src/presentation/web/.next/server/app/(dashboard)/feature/[featureId]/page/server-reference-manifest.json +19 -19
  163. package/web/.next/standalone/src/presentation/web/.next/server/app/(dashboard)/feature/[featureId]/page.js.nft.json +1 -1
  164. package/web/.next/standalone/src/presentation/web/.next/server/app/(dashboard)/feature/[featureId]/page_client-reference-manifest.js +1 -1
  165. package/web/.next/standalone/src/presentation/web/.next/server/app/(dashboard)/page/server-reference-manifest.json +14 -14
  166. package/web/.next/standalone/src/presentation/web/.next/server/app/(dashboard)/page.js.nft.json +1 -1
  167. package/web/.next/standalone/src/presentation/web/.next/server/app/(dashboard)/page_client-reference-manifest.js +1 -1
  168. package/web/.next/standalone/src/presentation/web/.next/server/app/(dashboard)/repository/[repositoryId]/page/server-reference-manifest.json +14 -14
  169. package/web/.next/standalone/src/presentation/web/.next/server/app/(dashboard)/repository/[repositoryId]/page.js.nft.json +1 -1
  170. package/web/.next/standalone/src/presentation/web/.next/server/app/(dashboard)/repository/[repositoryId]/page_client-reference-manifest.js +1 -1
  171. package/web/.next/standalone/src/presentation/web/.next/server/app/_global-error.html +2 -2
  172. package/web/.next/standalone/src/presentation/web/.next/server/app/_global-error.rsc +1 -1
  173. package/web/.next/standalone/src/presentation/web/.next/server/app/_global-error.segments/__PAGE__.segment.rsc +1 -1
  174. package/web/.next/standalone/src/presentation/web/.next/server/app/_global-error.segments/_full.segment.rsc +1 -1
  175. package/web/.next/standalone/src/presentation/web/.next/server/app/_global-error.segments/_head.segment.rsc +1 -1
  176. package/web/.next/standalone/src/presentation/web/.next/server/app/_global-error.segments/_index.segment.rsc +1 -1
  177. package/web/.next/standalone/src/presentation/web/.next/server/app/_global-error.segments/_tree.segment.rsc +1 -1
  178. package/web/.next/standalone/src/presentation/web/.next/server/app/_not-found/page/server-reference-manifest.json +1 -1
  179. package/web/.next/standalone/src/presentation/web/.next/server/app/_not-found/page_client-reference-manifest.js +1 -1
  180. package/web/.next/standalone/src/presentation/web/.next/server/app/skills/page/server-reference-manifest.json +6 -6
  181. package/web/.next/standalone/src/presentation/web/.next/server/app/skills/page.js.nft.json +1 -1
  182. package/web/.next/standalone/src/presentation/web/.next/server/app/skills/page_client-reference-manifest.js +1 -1
  183. package/web/.next/standalone/src/presentation/web/.next/server/app/tools/page/server-reference-manifest.json +6 -6
  184. package/web/.next/standalone/src/presentation/web/.next/server/app/tools/page.js.nft.json +1 -1
  185. package/web/.next/standalone/src/presentation/web/.next/server/app/tools/page_client-reference-manifest.js +1 -1
  186. package/web/.next/standalone/src/presentation/web/.next/server/app/version/page/server-reference-manifest.json +1 -1
  187. package/web/.next/standalone/src/presentation/web/.next/server/app/version/page_client-reference-manifest.js +1 -1
  188. package/web/.next/standalone/src/presentation/web/.next/server/chunks/ssr/744ca_web_components_common_control-center-drawer_create-drawer-client_tsx_5e26fc0a._.js +1 -1
  189. package/web/.next/standalone/src/presentation/web/.next/server/chunks/ssr/8ba4b_server_app_(dashboard)_@drawer_repository_[repositoryId]_page_actions_da7eef33.js +1 -1
  190. package/web/.next/standalone/src/presentation/web/.next/server/chunks/ssr/8ba4b_server_app_(dashboard)_repository_[repositoryId]_page_actions_0a9251aa.js +1 -1
  191. package/web/.next/standalone/src/presentation/web/.next/server/chunks/ssr/[root-of-the-server]__17a611f0._.js +2 -2
  192. package/web/.next/standalone/src/presentation/web/.next/server/chunks/ssr/[root-of-the-server]__45dbf93d._.js +2 -2
  193. package/web/.next/standalone/src/presentation/web/.next/server/chunks/ssr/[root-of-the-server]__6258349c._.js +1 -1
  194. package/web/.next/standalone/src/presentation/web/.next/server/chunks/ssr/[root-of-the-server]__6b17a22d._.js +1 -1
  195. package/web/.next/standalone/src/presentation/web/.next/server/chunks/ssr/[root-of-the-server]__6cbc1149._.js +2 -2
  196. package/web/.next/standalone/src/presentation/web/.next/server/chunks/ssr/[root-of-the-server]__804c006d._.js +1 -1
  197. package/web/.next/standalone/src/presentation/web/.next/server/chunks/ssr/[root-of-the-server]__94a6d275._.js +1 -1
  198. package/web/.next/standalone/src/presentation/web/.next/server/chunks/ssr/[root-of-the-server]__aad040c0._.js +1 -1
  199. package/web/.next/standalone/src/presentation/web/.next/server/chunks/ssr/_0e9d6bf7._.js +1 -1
  200. package/web/.next/standalone/src/presentation/web/.next/server/chunks/ssr/{_d8868bc0._.js → _30fd6f01._.js} +2 -2
  201. package/web/.next/standalone/src/presentation/web/.next/server/chunks/ssr/_61351ed3._.js +1 -1
  202. package/web/.next/standalone/src/presentation/web/.next/server/chunks/ssr/_6e08ce21._.js +1 -1
  203. package/web/.next/standalone/src/presentation/web/.next/server/chunks/ssr/_8400c8bb._.js +1 -1
  204. package/web/.next/standalone/src/presentation/web/.next/server/chunks/ssr/_9f940437._.js +1 -1
  205. package/web/.next/standalone/src/presentation/web/.next/server/chunks/ssr/src_presentation_web_163038ba._.js +2 -2
  206. package/web/.next/standalone/src/presentation/web/.next/server/chunks/ssr/src_presentation_web_30d7eeda._.js +1 -1
  207. package/web/.next/standalone/src/presentation/web/.next/server/chunks/ssr/src_presentation_web_459cb687._.js +2 -2
  208. package/web/.next/standalone/src/presentation/web/.next/server/chunks/ssr/src_presentation_web_565a14f8._.js +1 -1
  209. package/web/.next/standalone/src/presentation/web/.next/server/chunks/ssr/src_presentation_web__next-internal_server_app_(dashboard)_page_actions_021a05f2.js +1 -1
  210. package/web/.next/standalone/src/presentation/web/.next/server/chunks/ssr/src_presentation_web_components_features_control-center_7ac3562e._.js +1 -1
  211. package/web/.next/standalone/src/presentation/web/.next/server/pages/500.html +2 -2
  212. package/web/.next/standalone/src/presentation/web/.next/server/server-reference-manifest.js +1 -1
  213. package/web/.next/standalone/src/presentation/web/.next/server/server-reference-manifest.json +22 -22
  214. package/web/.next/standalone/src/presentation/web/app/actions/get-feature-messages.ts +42 -0
  215. package/web/.next/standalone/src/presentation/web/app/actions/get-feature-phase-timings.ts +42 -0
  216. package/web/.next/standalone/src/presentation/web/app/actions/get-feature-plan.ts +52 -0
  217. package/web/.next/standalone/src/presentation/web/components/common/feature-drawer-tabs/activity-tab.stories.tsx +272 -0
  218. package/web/.next/standalone/src/presentation/web/components/common/feature-drawer-tabs/activity-tab.tsx +245 -0
  219. package/web/.next/standalone/src/presentation/web/components/common/feature-drawer-tabs/feature-drawer-tabs.stories.tsx +130 -0
  220. package/web/.next/standalone/src/presentation/web/components/common/feature-drawer-tabs/feature-drawer-tabs.tsx +136 -0
  221. package/web/.next/standalone/src/presentation/web/components/common/feature-drawer-tabs/index.ts +2 -0
  222. package/web/.next/standalone/src/presentation/web/components/common/feature-drawer-tabs/messages-tab.stories.tsx +149 -0
  223. package/web/.next/standalone/src/presentation/web/components/common/feature-drawer-tabs/messages-tab.tsx +92 -0
  224. package/web/.next/standalone/src/presentation/web/components/common/feature-drawer-tabs/overview-tab.stories.tsx +186 -0
  225. package/web/.next/standalone/src/presentation/web/components/common/feature-drawer-tabs/overview-tab.tsx +142 -0
  226. package/web/.next/standalone/src/presentation/web/components/common/feature-drawer-tabs/plan-tab.stories.tsx +214 -0
  227. package/web/.next/standalone/src/presentation/web/components/common/feature-drawer-tabs/plan-tab.tsx +121 -0
  228. package/web/.next/standalone/src/presentation/web/components/common/feature-drawer-tabs/use-tab-data-fetch.ts +143 -0
  229. package/web/.next/standalone/src/presentation/web/components/common/feature-node/derive-feature-state.ts +1 -2
  230. package/web/.next/standalone/src/presentation/web/components/common/feature-node/feature-node-state-config.ts +0 -3
  231. package/web/.next/static/chunks/{eba61cbc1ad20c1d.js → 2e2355741bd6a9a7.js} +1 -1
  232. package/web/.next/static/chunks/{ff6489e28cbf0b7b.js → 437a925303b28b53.js} +1 -1
  233. package/web/.next/static/chunks/{ba17181b8e8a3593.js → 45b6a69a50b9d9e8.js} +1 -1
  234. package/web/.next/static/chunks/{4484a8fa29865af9.js → 47b5d582b373816d.js} +3 -3
  235. package/web/.next/static/chunks/{90f17af918bf9d84.js → 4e6ecfe539924a71.js} +1 -1
  236. package/web/.next/static/chunks/84d2f2d55e5cf753.css +2 -0
  237. package/web/.next/static/chunks/90f36476e66cbace.js +1 -0
  238. package/web/.next/static/chunks/{1f91036a11c9dc01.js → b5078ac043e7335a.js} +1 -1
  239. package/web/.next/static/chunks/{2b2d40707c3526be.js → dcb8f73fb28b2a26.js} +1 -1
  240. package/web/.next/static/chunks/{ff708b9a4954c701.js → e37d7d4d215db8f5.js} +1 -1
  241. package/web/.next/trace +1 -1
  242. package/web/.next/trace-build +1 -1
  243. package/web/.next/static/chunks/23c4643c3c3d429c.js +0 -1
  244. package/web/.next/static/chunks/e12fff3b57456bc2.css +0 -2
  245. /package/web/.next/static/{8IW4pcSs1YMI4I3CN6S8X → TuKZpCcwG7RLlpnyasgpZ}/_buildManifest.js +0 -0
  246. /package/web/.next/static/{8IW4pcSs1YMI4I3CN6S8X → TuKZpCcwG7RLlpnyasgpZ}/_clientMiddlewareManifest.json +0 -0
  247. /package/web/.next/static/{8IW4pcSs1YMI4I3CN6S8X → TuKZpCcwG7RLlpnyasgpZ}/_ssgManifest.js +0 -0
@@ -0,0 +1,52 @@
1
+ 'use server';
2
+
3
+ import { resolve } from '@/lib/server-container';
4
+ import type { IFeatureRepository } from '@shepai/core/application/ports/output/repositories/feature-repository.interface';
5
+
6
+ export interface PlanTaskData {
7
+ title: string;
8
+ description: string;
9
+ state: string;
10
+ }
11
+
12
+ export interface PlanData {
13
+ state: string;
14
+ overview: string;
15
+ tasks: PlanTaskData[];
16
+ }
17
+
18
+ type GetPlanResult = { plan: PlanData | undefined } | { error: string };
19
+
20
+ export async function getFeaturePlan(featureId: string): Promise<GetPlanResult> {
21
+ if (!featureId.trim()) {
22
+ return { error: 'Feature id is required' };
23
+ }
24
+
25
+ try {
26
+ const repo = resolve<IFeatureRepository>('IFeatureRepository');
27
+ const feature = await repo.findById(featureId);
28
+
29
+ if (!feature) {
30
+ return { error: 'Feature not found' };
31
+ }
32
+
33
+ if (!feature.plan) {
34
+ return { plan: undefined };
35
+ }
36
+
37
+ const plan: PlanData = {
38
+ state: feature.plan.state,
39
+ overview: feature.plan.overview,
40
+ tasks: feature.plan.tasks.map((t) => ({
41
+ title: t.title ?? '',
42
+ description: t.description ?? '',
43
+ state: t.state,
44
+ })),
45
+ };
46
+
47
+ return { plan };
48
+ } catch (error: unknown) {
49
+ const message = error instanceof Error ? error.message : 'Failed to load feature plan';
50
+ return { error: message };
51
+ }
52
+ }
@@ -0,0 +1,272 @@
1
+ import type { Meta, StoryObj } from '@storybook/react';
2
+ import { ActivityTab } from './activity-tab';
3
+ import type { PhaseTimingData } from '@/app/actions/get-feature-phase-timings';
4
+
5
+ const meta: Meta<typeof ActivityTab> = {
6
+ title: 'Drawers/Feature/Tabs/ActivityTab',
7
+ component: ActivityTab,
8
+ tags: ['autodocs'],
9
+ parameters: {
10
+ layout: 'fullscreen',
11
+ },
12
+ decorators: [
13
+ (Story) => (
14
+ <div style={{ height: '600px', width: '400px', border: '1px solid var(--color-border)' }}>
15
+ <Story />
16
+ </div>
17
+ ),
18
+ ],
19
+ };
20
+
21
+ export default meta;
22
+ type Story = StoryObj<typeof ActivityTab>;
23
+
24
+ /* ---------------------------------------------------------------------------
25
+ * Data fixtures
26
+ * ------------------------------------------------------------------------- */
27
+
28
+ const singleRunTimings: PhaseTimingData[] = [
29
+ {
30
+ agentRunId: 'run-1',
31
+ phase: 'run:started',
32
+ startedAt: '2025-01-15T10:00:00Z',
33
+ completedAt: '2025-01-15T10:00:00Z',
34
+ durationMs: 0,
35
+ },
36
+ {
37
+ agentRunId: 'run-1',
38
+ phase: 'analyze',
39
+ startedAt: '2025-01-15T10:00:01Z',
40
+ completedAt: '2025-01-15T10:00:15Z',
41
+ durationMs: 14000,
42
+ },
43
+ {
44
+ agentRunId: 'run-1',
45
+ phase: 'requirements',
46
+ startedAt: '2025-01-15T10:00:15Z',
47
+ completedAt: '2025-01-15T10:01:45Z',
48
+ durationMs: 90000,
49
+ waitingApprovalAt: '2025-01-15T10:01:00Z',
50
+ approvalWaitMs: 30000,
51
+ },
52
+ {
53
+ agentRunId: 'run-1',
54
+ phase: 'research',
55
+ startedAt: '2025-01-15T10:01:45Z',
56
+ completedAt: '2025-01-15T10:03:30Z',
57
+ durationMs: 105000,
58
+ },
59
+ {
60
+ agentRunId: 'run-1',
61
+ phase: 'plan',
62
+ startedAt: '2025-01-15T10:03:30Z',
63
+ completedAt: '2025-01-15T10:05:00Z',
64
+ durationMs: 90000,
65
+ waitingApprovalAt: '2025-01-15T10:04:30Z',
66
+ approvalWaitMs: 15000,
67
+ },
68
+ {
69
+ agentRunId: 'run-1',
70
+ phase: 'implement',
71
+ startedAt: '2025-01-15T10:05:00Z',
72
+ completedAt: '2025-01-15T10:15:00Z',
73
+ durationMs: 600000,
74
+ },
75
+ {
76
+ agentRunId: 'run-1',
77
+ phase: 'run:completed',
78
+ startedAt: '2025-01-15T10:15:00Z',
79
+ completedAt: '2025-01-15T10:15:00Z',
80
+ durationMs: 0,
81
+ },
82
+ ];
83
+
84
+ const multiRunTimings: PhaseTimingData[] = [
85
+ // Run 1
86
+ {
87
+ agentRunId: 'run-1',
88
+ phase: 'run:started',
89
+ startedAt: '2025-01-15T10:00:00Z',
90
+ durationMs: 0,
91
+ },
92
+ {
93
+ agentRunId: 'run-1',
94
+ phase: 'analyze',
95
+ startedAt: '2025-01-15T10:00:01Z',
96
+ completedAt: '2025-01-15T10:00:20Z',
97
+ durationMs: 19000,
98
+ },
99
+ {
100
+ agentRunId: 'run-1',
101
+ phase: 'requirements',
102
+ startedAt: '2025-01-15T10:00:20Z',
103
+ completedAt: '2025-01-15T10:02:00Z',
104
+ durationMs: 100000,
105
+ waitingApprovalAt: '2025-01-15T10:01:20Z',
106
+ approvalWaitMs: 40000,
107
+ },
108
+ {
109
+ agentRunId: 'run-1',
110
+ phase: 'run:completed',
111
+ startedAt: '2025-01-15T10:02:00Z',
112
+ durationMs: 0,
113
+ },
114
+ // Run 2
115
+ {
116
+ agentRunId: 'run-2',
117
+ phase: 'run:resumed',
118
+ startedAt: '2025-01-15T11:00:00Z',
119
+ durationMs: 0,
120
+ },
121
+ {
122
+ agentRunId: 'run-2',
123
+ phase: 'research',
124
+ startedAt: '2025-01-15T11:00:01Z',
125
+ completedAt: '2025-01-15T11:02:30Z',
126
+ durationMs: 149000,
127
+ },
128
+ {
129
+ agentRunId: 'run-2',
130
+ phase: 'plan',
131
+ startedAt: '2025-01-15T11:02:30Z',
132
+ completedAt: '2025-01-15T11:04:00Z',
133
+ durationMs: 90000,
134
+ waitingApprovalAt: '2025-01-15T11:03:30Z',
135
+ approvalWaitMs: 20000,
136
+ },
137
+ {
138
+ agentRunId: 'run-2',
139
+ phase: 'implement',
140
+ startedAt: '2025-01-15T11:04:00Z',
141
+ completedAt: '2025-01-15T11:12:00Z',
142
+ durationMs: 480000,
143
+ },
144
+ {
145
+ agentRunId: 'run-2',
146
+ phase: 'merge',
147
+ startedAt: '2025-01-15T11:12:00Z',
148
+ completedAt: '2025-01-15T11:13:30Z',
149
+ durationMs: 90000,
150
+ },
151
+ {
152
+ agentRunId: 'run-2',
153
+ phase: 'run:completed',
154
+ startedAt: '2025-01-15T11:13:30Z',
155
+ durationMs: 0,
156
+ },
157
+ ];
158
+
159
+ const runningTimings: PhaseTimingData[] = [
160
+ {
161
+ agentRunId: 'run-1',
162
+ phase: 'run:started',
163
+ startedAt: '2025-01-15T10:00:00Z',
164
+ durationMs: 0,
165
+ },
166
+ {
167
+ agentRunId: 'run-1',
168
+ phase: 'analyze',
169
+ startedAt: '2025-01-15T10:00:01Z',
170
+ completedAt: '2025-01-15T10:00:15Z',
171
+ durationMs: 14000,
172
+ },
173
+ {
174
+ agentRunId: 'run-1',
175
+ phase: 'implement',
176
+ startedAt: '2025-01-15T10:00:15Z',
177
+ durationMs: 45000,
178
+ },
179
+ ];
180
+
181
+ /* ---------------------------------------------------------------------------
182
+ * Stories
183
+ * ------------------------------------------------------------------------- */
184
+
185
+ /** Default — single run with complete phase timings and approval waits. */
186
+ export const Default: Story = {
187
+ args: {
188
+ timings: singleRunTimings,
189
+ loading: false,
190
+ error: null,
191
+ },
192
+ };
193
+
194
+ /** Multiple runs with run headers showing grouping. */
195
+ export const MultipleRuns: Story = {
196
+ args: {
197
+ timings: multiRunTimings,
198
+ loading: false,
199
+ error: null,
200
+ },
201
+ };
202
+
203
+ /** Running phase — a phase without completedAt shows blue bar. */
204
+ export const RunningPhase: Story = {
205
+ args: {
206
+ timings: runningTimings,
207
+ loading: false,
208
+ error: null,
209
+ },
210
+ };
211
+
212
+ /** Loading state — spinner displayed while data is being fetched. */
213
+ export const Loading: Story = {
214
+ args: {
215
+ timings: null,
216
+ loading: true,
217
+ error: null,
218
+ },
219
+ };
220
+
221
+ /** Empty state — no activity recorded yet. */
222
+ export const Empty: Story = {
223
+ args: {
224
+ timings: [],
225
+ loading: false,
226
+ error: null,
227
+ },
228
+ };
229
+
230
+ /** Error state — inline error message. */
231
+ export const Error: Story = {
232
+ args: {
233
+ timings: null,
234
+ loading: false,
235
+ error: 'Failed to load phase timings. Please try again.',
236
+ },
237
+ };
238
+
239
+ /** Approval wait indicators — phases with approval wait sub-rows. */
240
+ export const WithApprovalWaits: Story = {
241
+ args: {
242
+ timings: [
243
+ {
244
+ agentRunId: 'run-1',
245
+ phase: 'requirements',
246
+ startedAt: '2025-01-15T10:00:00Z',
247
+ completedAt: '2025-01-15T10:03:00Z',
248
+ durationMs: 180000,
249
+ waitingApprovalAt: '2025-01-15T10:01:00Z',
250
+ approvalWaitMs: 120000,
251
+ },
252
+ {
253
+ agentRunId: 'run-1',
254
+ phase: 'plan',
255
+ startedAt: '2025-01-15T10:03:00Z',
256
+ completedAt: '2025-01-15T10:06:00Z',
257
+ durationMs: 180000,
258
+ waitingApprovalAt: '2025-01-15T10:04:00Z',
259
+ approvalWaitMs: 90000,
260
+ },
261
+ {
262
+ agentRunId: 'run-1',
263
+ phase: 'implement',
264
+ startedAt: '2025-01-15T10:06:00Z',
265
+ completedAt: '2025-01-15T10:16:00Z',
266
+ durationMs: 600000,
267
+ },
268
+ ],
269
+ loading: false,
270
+ error: null,
271
+ },
272
+ };
@@ -0,0 +1,245 @@
1
+ 'use client';
2
+
3
+ import { Loader2, AlertCircle, Clock } from 'lucide-react';
4
+ import type { PhaseTimingData } from '@/app/actions/get-feature-phase-timings';
5
+
6
+ export interface ActivityTabProps {
7
+ timings: PhaseTimingData[] | null;
8
+ loading: boolean;
9
+ error: string | null;
10
+ }
11
+
12
+ const NODE_TO_PHASE: Record<string, string> = {
13
+ analyze: 'Analyzing',
14
+ requirements: 'Requirements',
15
+ research: 'Researching',
16
+ plan: 'Planning',
17
+ implement: 'Implementing',
18
+ merge: 'Merging',
19
+ };
20
+
21
+ const LIFECYCLE_EVENTS: Record<string, { label: string; colorClass: string }> = {
22
+ 'run:started': { label: 'started', colorClass: 'text-blue-600' },
23
+ 'run:resumed': { label: 'resumed', colorClass: 'text-blue-600' },
24
+ 'run:completed': { label: 'completed', colorClass: 'text-emerald-600' },
25
+ 'run:failed': { label: 'failed', colorClass: 'text-red-600' },
26
+ 'run:stopped': { label: 'stopped', colorClass: 'text-amber-600' },
27
+ 'run:crashed': { label: 'crashed', colorClass: 'text-red-600' },
28
+ };
29
+
30
+ function isLifecycleEvent(phase: string): boolean {
31
+ return phase.startsWith('run:');
32
+ }
33
+
34
+ function formatDuration(ms: number): string {
35
+ return `${(ms / 1000).toFixed(1)}s`;
36
+ }
37
+
38
+ interface TimingRunGroup {
39
+ runId: string;
40
+ timings: PhaseTimingData[];
41
+ }
42
+
43
+ function groupTimingsByRun(timings: PhaseTimingData[]): TimingRunGroup[] {
44
+ const groups: TimingRunGroup[] = [];
45
+
46
+ for (const t of timings) {
47
+ const last = groups[groups.length - 1];
48
+ if (last?.runId === t.agentRunId) {
49
+ last.timings.push(t);
50
+ } else {
51
+ groups.push({ runId: t.agentRunId, timings: [t] });
52
+ }
53
+ }
54
+ return groups;
55
+ }
56
+
57
+ export function ActivityTab({ timings, loading, error }: ActivityTabProps) {
58
+ if (loading) {
59
+ return (
60
+ <div data-testid="activity-tab-loading" className="flex items-center justify-center p-8">
61
+ <Loader2 className="text-muted-foreground h-6 w-6 animate-spin" />
62
+ </div>
63
+ );
64
+ }
65
+
66
+ if (error) {
67
+ return (
68
+ <div className="flex items-center gap-2 p-4 text-sm text-red-600">
69
+ <AlertCircle className="h-4 w-4 shrink-0" />
70
+ <span>{error}</span>
71
+ </div>
72
+ );
73
+ }
74
+
75
+ if (!timings || timings.length === 0) {
76
+ return (
77
+ <div className="flex flex-col items-center justify-center gap-2 p-8">
78
+ <Clock className="text-muted-foreground h-8 w-8" />
79
+ <p className="text-muted-foreground text-sm">No activity recorded yet</p>
80
+ </div>
81
+ );
82
+ }
83
+
84
+ const nodeTimings = timings.filter((t) => !isLifecycleEvent(t.phase));
85
+ const maxDurationMs = Math.max(
86
+ ...nodeTimings.map((t) => t.durationMs ?? 0),
87
+ ...nodeTimings.map((t) => t.approvalWaitMs ?? 0),
88
+ 0
89
+ );
90
+
91
+ const groups = groupTimingsByRun(timings);
92
+ const multiRun = groups.length > 1;
93
+
94
+ const totalExecMs = nodeTimings.reduce((sum, t) => sum + (t.durationMs ?? 0), 0);
95
+ const totalWaitMs = nodeTimings.reduce((sum, t) => sum + (t.approvalWaitMs ?? 0), 0);
96
+
97
+ return (
98
+ <div className="flex flex-col gap-4 p-4">
99
+ <div data-testid="activity-timings" className="flex flex-col gap-3">
100
+ {groups.map((group, groupIdx) => (
101
+ <RunGroup
102
+ key={group.runId}
103
+ group={group}
104
+ groupIdx={groupIdx}
105
+ multiRun={multiRun}
106
+ maxDurationMs={maxDurationMs}
107
+ />
108
+ ))}
109
+ </div>
110
+ {totalExecMs > 0 ? (
111
+ <SummaryTotals totalExecMs={totalExecMs} totalWaitMs={totalWaitMs} />
112
+ ) : null}
113
+ </div>
114
+ );
115
+ }
116
+
117
+ function RunGroup({
118
+ group,
119
+ groupIdx,
120
+ multiRun,
121
+ maxDurationMs,
122
+ }: {
123
+ group: { runId: string; timings: PhaseTimingData[] };
124
+ groupIdx: number;
125
+ multiRun: boolean;
126
+ maxDurationMs: number;
127
+ }) {
128
+ return (
129
+ <div className="flex flex-col gap-1.5">
130
+ {multiRun ? (
131
+ <div className="text-muted-foreground text-xs font-medium">Run #{groupIdx + 1}</div>
132
+ ) : null}
133
+ {group.timings.map((t) => {
134
+ if (isLifecycleEvent(t.phase)) {
135
+ return <LifecycleEventRow key={`${t.agentRunId}-${t.phase}-${t.startedAt}`} timing={t} />;
136
+ }
137
+ return (
138
+ <NodeTimingRow
139
+ key={`${t.agentRunId}-${t.phase}-${t.startedAt}`}
140
+ timing={t}
141
+ maxDurationMs={maxDurationMs}
142
+ />
143
+ );
144
+ })}
145
+ </div>
146
+ );
147
+ }
148
+
149
+ function LifecycleEventRow({ timing }: { timing: PhaseTimingData }) {
150
+ const event = LIFECYCLE_EVENTS[timing.phase];
151
+ if (!event) return null;
152
+ return (
153
+ <div className={`text-xs ${event.colorClass}`}>
154
+ <span>{event.label}</span>
155
+ </div>
156
+ );
157
+ }
158
+
159
+ function NodeTimingRow({
160
+ timing,
161
+ maxDurationMs,
162
+ }: {
163
+ timing: PhaseTimingData;
164
+ maxDurationMs: number;
165
+ }) {
166
+ const label = timing.phase.includes(':')
167
+ ? `rev ${timing.phase.split(':')[1]}`
168
+ : (NODE_TO_PHASE[timing.phase] ?? timing.phase);
169
+
170
+ const durationMs = timing.durationMs ?? 0;
171
+ const barPercent = maxDurationMs > 0 ? Math.max(2, (durationMs / maxDurationMs) * 100) : 2;
172
+ const barColorClass = timing.completedAt ? 'bg-emerald-500' : 'bg-blue-500';
173
+
174
+ return (
175
+ <div className="flex flex-col gap-1">
176
+ <div data-testid={`timing-bar-${timing.phase}`} className="flex items-center gap-3">
177
+ <span className="text-muted-foreground w-24 shrink-0 text-xs">{label}</span>
178
+ <div className="bg-muted h-3 flex-1 overflow-hidden rounded-full">
179
+ <div
180
+ className={`h-full rounded-full ${barColorClass}`}
181
+ style={{ width: `${Math.min(barPercent, 100)}%` }}
182
+ />
183
+ </div>
184
+ <span className="text-muted-foreground w-14 shrink-0 text-right text-xs">
185
+ {formatDuration(durationMs)}
186
+ </span>
187
+ </div>
188
+ {timing.approvalWaitMs != null && timing.approvalWaitMs > 0 ? (
189
+ <ApprovalWaitRow timing={timing} maxDurationMs={maxDurationMs} />
190
+ ) : null}
191
+ </div>
192
+ );
193
+ }
194
+
195
+ function ApprovalWaitRow({
196
+ timing,
197
+ maxDurationMs,
198
+ }: {
199
+ timing: PhaseTimingData;
200
+ maxDurationMs: number;
201
+ }) {
202
+ const waitMs = timing.approvalWaitMs ?? 0;
203
+ const barPercent = maxDurationMs > 0 ? Math.max(2, (waitMs / maxDurationMs) * 100) : 2;
204
+
205
+ return (
206
+ <div data-testid={`approval-wait-${timing.phase}`} className="flex items-center gap-3 pl-4">
207
+ <span className="text-muted-foreground w-20 shrink-0 text-xs">approval</span>
208
+ <div className="bg-muted h-2.5 flex-1 overflow-hidden rounded-full">
209
+ <div
210
+ className="h-full rounded-full bg-amber-500"
211
+ style={{ width: `${Math.min(barPercent, 100)}%` }}
212
+ />
213
+ </div>
214
+ <span className="text-muted-foreground w-14 shrink-0 text-right text-xs">
215
+ {formatDuration(waitMs)}
216
+ </span>
217
+ </div>
218
+ );
219
+ }
220
+
221
+ function SummaryTotals({ totalExecMs, totalWaitMs }: { totalExecMs: number; totalWaitMs: number }) {
222
+ return (
223
+ <div
224
+ data-testid="activity-summary"
225
+ className="border-border flex flex-col gap-1.5 border-t pt-3"
226
+ >
227
+ <SummaryRow label="Total execution" value={formatDuration(totalExecMs)} />
228
+ {totalWaitMs > 0 ? (
229
+ <>
230
+ <SummaryRow label="Total wait" value={formatDuration(totalWaitMs)} />
231
+ <SummaryRow label="Total wall-clock" value={formatDuration(totalExecMs + totalWaitMs)} />
232
+ </>
233
+ ) : null}
234
+ </div>
235
+ );
236
+ }
237
+
238
+ function SummaryRow({ label, value }: { label: string; value: string }) {
239
+ return (
240
+ <div className="flex items-center justify-between">
241
+ <span className="text-muted-foreground text-xs font-medium">{label}</span>
242
+ <span className="text-xs font-medium">{value}</span>
243
+ </div>
244
+ );
245
+ }
@@ -0,0 +1,130 @@
1
+ import type { Meta, StoryObj } from '@storybook/react';
2
+ import { PrStatus, CiStatus } from '@shepai/core/domain/generated/output';
3
+ import { FeatureDrawerTabs } from './feature-drawer-tabs';
4
+ import type { FeatureNodeData } from '@/components/common/feature-node';
5
+
6
+ const meta: Meta<typeof FeatureDrawerTabs> = {
7
+ title: 'Drawers/Feature/Tabs/FeatureDrawerTabs',
8
+ component: FeatureDrawerTabs,
9
+ tags: ['autodocs'],
10
+ parameters: {
11
+ layout: 'fullscreen',
12
+ },
13
+ decorators: [
14
+ (Story) => (
15
+ <div style={{ height: '600px', width: '400px', border: '1px solid var(--color-border)' }}>
16
+ <Story />
17
+ </div>
18
+ ),
19
+ ],
20
+ };
21
+
22
+ export default meta;
23
+ type Story = StoryObj<typeof FeatureDrawerTabs>;
24
+
25
+ /* ---------------------------------------------------------------------------
26
+ * Data fixtures
27
+ * ------------------------------------------------------------------------- */
28
+
29
+ const runningFeature: FeatureNodeData = {
30
+ name: 'Auth Module',
31
+ description: 'Implement OAuth2 authentication flow with multiple providers',
32
+ featureId: '#f1',
33
+ lifecycle: 'implementation',
34
+ state: 'running',
35
+ progress: 65,
36
+ agentType: 'claude-code',
37
+ runtime: '2h 15m',
38
+ repositoryPath: '/home/user/my-repo',
39
+ branch: 'feat/auth-module',
40
+ pr: {
41
+ url: 'https://github.com/org/repo/pull/42',
42
+ number: 42,
43
+ status: PrStatus.Open,
44
+ ciStatus: CiStatus.Pending,
45
+ commitHash: 'abc1234567890def',
46
+ },
47
+ };
48
+
49
+ const doneFeature: FeatureNodeData = {
50
+ name: 'Payment Gateway',
51
+ description: 'Stripe integration for subscriptions',
52
+ featureId: '#f3',
53
+ lifecycle: 'deploy',
54
+ state: 'done',
55
+ progress: 100,
56
+ runtime: '1h 42m',
57
+ repositoryPath: '/home/user/my-repo',
58
+ branch: 'feat/payment-gateway',
59
+ pr: {
60
+ url: 'https://github.com/org/repo/pull/55',
61
+ number: 55,
62
+ status: PrStatus.Merged,
63
+ ciStatus: CiStatus.Success,
64
+ commitHash: 'def4567890abc123',
65
+ },
66
+ };
67
+
68
+ const requirementsFeature: FeatureNodeData = {
69
+ name: 'API Rate Limiting',
70
+ description: 'Implement sliding window rate limiting for public endpoints',
71
+ featureId: '#bi1',
72
+ lifecycle: 'requirements',
73
+ state: 'action-required',
74
+ progress: 0,
75
+ repositoryPath: '/home/user/my-repo',
76
+ branch: 'feat/api-rate-limiting',
77
+ };
78
+
79
+ const errorFeature: FeatureNodeData = {
80
+ name: 'Email Service',
81
+ description: 'Transactional email with SendGrid',
82
+ featureId: '#f5',
83
+ lifecycle: 'review',
84
+ state: 'error',
85
+ progress: 30,
86
+ errorMessage: 'Build failed: type mismatch in EmailHandler',
87
+ repositoryPath: '/home/user/my-repo',
88
+ branch: 'feat/email-service',
89
+ };
90
+
91
+ /* ---------------------------------------------------------------------------
92
+ * Stories
93
+ *
94
+ * Note: In Storybook, server actions are mocked and return error states.
95
+ * The Overview tab renders fully since it uses FeatureNodeData (no server action).
96
+ * Activity, Messages, and Plan tabs show error states from the mocked actions.
97
+ * See individual tab stories (ActivityTab, MessagesTab, PlanTab) for populated states.
98
+ * ------------------------------------------------------------------------- */
99
+
100
+ /** Default — running feature with full data. Overview tab active. */
101
+ export const Default: Story = {
102
+ args: {
103
+ featureNode: runningFeature,
104
+ featureId: '#f1',
105
+ },
106
+ };
107
+
108
+ /** Completed feature in deploy phase with merged PR. */
109
+ export const CompletedFeature: Story = {
110
+ args: {
111
+ featureNode: doneFeature,
112
+ featureId: '#f3',
113
+ },
114
+ };
115
+
116
+ /** Early-stage feature in requirements phase, no progress. */
117
+ export const RequirementsPhase: Story = {
118
+ args: {
119
+ featureNode: requirementsFeature,
120
+ featureId: '#bi1',
121
+ },
122
+ };
123
+
124
+ /** Feature in error state. */
125
+ export const ErrorState: Story = {
126
+ args: {
127
+ featureNode: errorFeature,
128
+ featureId: '#f5',
129
+ },
130
+ };