@shepai/cli 1.125.0 → 1.126.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.
- package/dist/packages/core/src/application/ports/output/services/deployment-service.interface.d.ts +13 -2
- package/dist/packages/core/src/application/ports/output/services/deployment-service.interface.d.ts.map +1 -1
- package/dist/packages/core/src/infrastructure/di/container.d.ts.map +1 -1
- package/dist/packages/core/src/infrastructure/di/container.js +2 -0
- package/dist/packages/core/src/infrastructure/persistence/sqlite/migrations/040-create-dev-servers-table.d.ts +21 -0
- package/dist/packages/core/src/infrastructure/persistence/sqlite/migrations/040-create-dev-servers-table.d.ts.map +1 -0
- package/dist/packages/core/src/infrastructure/persistence/sqlite/migrations/040-create-dev-servers-table.js +32 -0
- package/dist/packages/core/src/infrastructure/services/agents/feature-agent/nodes/merge/ci-watch-fix-loop.d.ts.map +1 -1
- package/dist/packages/core/src/infrastructure/services/agents/feature-agent/nodes/merge/ci-watch-fix-loop.js +9 -0
- package/dist/packages/core/src/infrastructure/services/deployment/deployment.service.d.ts +24 -14
- package/dist/packages/core/src/infrastructure/services/deployment/deployment.service.d.ts.map +1 -1
- package/dist/packages/core/src/infrastructure/services/deployment/deployment.service.js +203 -31
- package/dist/packages/core/src/infrastructure/services/deployment/parse-port.d.ts +0 -6
- package/dist/packages/core/src/infrastructure/services/deployment/parse-port.d.ts.map +1 -1
- package/dist/packages/core/src/infrastructure/services/deployment/parse-port.js +6 -1
- package/dist/packages/core/src/infrastructure/services/git/git-pr.service.d.ts.map +1 -1
- package/dist/packages/core/src/infrastructure/services/git/git-pr.service.js +7 -2
- package/dist/src/presentation/web/app/actions/deploy-feature.js +1 -1
- package/dist/src/presentation/web/app/actions/deploy-repository.js +1 -1
- package/dist/src/presentation/web/components/common/repository-node/repository-node.d.ts.map +1 -1
- package/dist/src/presentation/web/components/common/repository-node/repository-node.js +7 -4
- package/dist/src/presentation/web/components/features/control-center/use-control-center-state.d.ts.map +1 -1
- package/dist/src/presentation/web/components/features/control-center/use-control-center-state.js +12 -3
- package/dist/src/presentation/web/hooks/use-deploy-action.d.ts.map +1 -1
- package/dist/src/presentation/web/hooks/use-deploy-action.js +69 -10
- package/dist/src/presentation/web/lib/layout-with-dagre.js +3 -3
- package/dist/tsconfig.build.tsbuildinfo +1 -1
- package/package.json +1 -1
- package/web/.next/BUILD_ID +1 -1
- package/web/.next/build-manifest.json +2 -2
- package/web/.next/fallback-build-manifest.json +2 -2
- package/web/.next/prerender-manifest.json +3 -3
- package/web/.next/required-server-files.js +2 -2
- package/web/.next/required-server-files.json +2 -2
- package/web/.next/server/app/(dashboard)/@drawer/create/page/server-reference-manifest.json +57 -57
- package/web/.next/server/app/(dashboard)/@drawer/create/page.js +2 -2
- package/web/.next/server/app/(dashboard)/@drawer/create/page.js.nft.json +1 -1
- package/web/.next/server/app/(dashboard)/@drawer/create/page_client-reference-manifest.js +1 -1
- package/web/.next/server/app/(dashboard)/@drawer/feature/[featureId]/[tab]/page/server-reference-manifest.json +69 -69
- package/web/.next/server/app/(dashboard)/@drawer/feature/[featureId]/[tab]/page.js +2 -2
- package/web/.next/server/app/(dashboard)/@drawer/feature/[featureId]/[tab]/page.js.nft.json +1 -1
- package/web/.next/server/app/(dashboard)/@drawer/feature/[featureId]/[tab]/page_client-reference-manifest.js +1 -1
- package/web/.next/server/app/(dashboard)/@drawer/feature/[featureId]/page/server-reference-manifest.json +69 -69
- package/web/.next/server/app/(dashboard)/@drawer/feature/[featureId]/page.js +2 -2
- package/web/.next/server/app/(dashboard)/@drawer/feature/[featureId]/page.js.nft.json +1 -1
- package/web/.next/server/app/(dashboard)/@drawer/feature/[featureId]/page_client-reference-manifest.js +1 -1
- package/web/.next/server/app/(dashboard)/@drawer/repository/[repositoryId]/page/server-reference-manifest.json +53 -53
- package/web/.next/server/app/(dashboard)/@drawer/repository/[repositoryId]/page.js +2 -2
- package/web/.next/server/app/(dashboard)/@drawer/repository/[repositoryId]/page.js.nft.json +1 -1
- package/web/.next/server/app/(dashboard)/@drawer/repository/[repositoryId]/page_client-reference-manifest.js +1 -1
- package/web/.next/server/app/(dashboard)/create/page/server-reference-manifest.json +57 -57
- package/web/.next/server/app/(dashboard)/create/page.js +2 -2
- package/web/.next/server/app/(dashboard)/create/page.js.nft.json +1 -1
- package/web/.next/server/app/(dashboard)/create/page_client-reference-manifest.js +1 -1
- package/web/.next/server/app/(dashboard)/feature/[featureId]/[tab]/page/server-reference-manifest.json +69 -69
- package/web/.next/server/app/(dashboard)/feature/[featureId]/[tab]/page.js +2 -2
- package/web/.next/server/app/(dashboard)/feature/[featureId]/[tab]/page.js.nft.json +1 -1
- package/web/.next/server/app/(dashboard)/feature/[featureId]/[tab]/page_client-reference-manifest.js +1 -1
- package/web/.next/server/app/(dashboard)/feature/[featureId]/page/server-reference-manifest.json +69 -69
- package/web/.next/server/app/(dashboard)/feature/[featureId]/page.js +2 -2
- package/web/.next/server/app/(dashboard)/feature/[featureId]/page.js.nft.json +1 -1
- package/web/.next/server/app/(dashboard)/feature/[featureId]/page_client-reference-manifest.js +1 -1
- package/web/.next/server/app/(dashboard)/page/server-reference-manifest.json +53 -53
- package/web/.next/server/app/(dashboard)/page.js +2 -2
- package/web/.next/server/app/(dashboard)/page.js.nft.json +1 -1
- package/web/.next/server/app/(dashboard)/page_client-reference-manifest.js +1 -1
- package/web/.next/server/app/(dashboard)/repository/[repositoryId]/page/server-reference-manifest.json +53 -53
- package/web/.next/server/app/(dashboard)/repository/[repositoryId]/page.js +2 -2
- package/web/.next/server/app/(dashboard)/repository/[repositoryId]/page.js.nft.json +1 -1
- package/web/.next/server/app/(dashboard)/repository/[repositoryId]/page_client-reference-manifest.js +1 -1
- package/web/.next/server/app/_global-error.html +2 -2
- package/web/.next/server/app/_global-error.rsc +1 -1
- package/web/.next/server/app/_global-error.segments/__PAGE__.segment.rsc +1 -1
- package/web/.next/server/app/_global-error.segments/_full.segment.rsc +1 -1
- package/web/.next/server/app/_global-error.segments/_head.segment.rsc +1 -1
- package/web/.next/server/app/_global-error.segments/_index.segment.rsc +1 -1
- package/web/.next/server/app/_global-error.segments/_tree.segment.rsc +1 -1
- package/web/.next/server/app/_not-found/page/server-reference-manifest.json +1 -1
- package/web/.next/server/app/_not-found/page_client-reference-manifest.js +1 -1
- package/web/.next/server/app/settings/page/server-reference-manifest.json +6 -6
- package/web/.next/server/app/settings/page.js.nft.json +1 -1
- package/web/.next/server/app/settings/page_client-reference-manifest.js +1 -1
- package/web/.next/server/app/skills/page/server-reference-manifest.json +6 -6
- package/web/.next/server/app/skills/page.js +1 -2
- package/web/.next/server/app/skills/page.js.nft.json +1 -1
- package/web/.next/server/app/skills/page_client-reference-manifest.js +1 -1
- package/web/.next/server/app/tools/page/server-reference-manifest.json +6 -6
- package/web/.next/server/app/tools/page.js +1 -2
- package/web/.next/server/app/tools/page.js.nft.json +1 -1
- package/web/.next/server/app/tools/page_client-reference-manifest.js +1 -1
- package/web/.next/server/app/version/page/server-reference-manifest.json +1 -1
- package/web/.next/server/app/version/page_client-reference-manifest.js +1 -1
- package/web/.next/server/chunks/403f9_next_dist_esm_build_templates_app-route_370c43b1.js +1 -1
- package/web/.next/server/chunks/403f9_next_dist_esm_build_templates_app-route_370c43b1.js.map +1 -1
- package/web/.next/server/chunks/[root-of-the-server]__a402b567._.js +1 -1
- package/web/.next/server/chunks/ssr/744ca_web_components_common_control-center-drawer_create-drawer-client_tsx_5e26fc0a._.js +1 -1
- package/web/.next/server/chunks/ssr/744ca_web_components_common_control-center-drawer_create-drawer-client_tsx_5e26fc0a._.js.map +1 -1
- package/web/.next/server/chunks/ssr/8ba4b_server_app_(dashboard)_@drawer_repository_[repositoryId]_page_actions_fdfbf5cc.js +3 -0
- package/web/.next/server/chunks/ssr/8ba4b_server_app_(dashboard)_@drawer_repository_[repositoryId]_page_actions_fdfbf5cc.js.map +1 -0
- package/web/.next/server/chunks/ssr/8ba4b_server_app_(dashboard)_repository_[repositoryId]_page_actions_d8fa0b5f.js +3 -0
- package/web/.next/server/chunks/ssr/8ba4b_server_app_(dashboard)_repository_[repositoryId]_page_actions_d8fa0b5f.js.map +1 -0
- package/web/.next/server/chunks/ssr/[root-of-the-server]__06fef644._.js +1 -1
- package/web/.next/server/chunks/ssr/{[root-of-the-server]__7cbda1ea._.js → [root-of-the-server]__248b9fc3._.js} +2 -2
- package/web/.next/server/chunks/ssr/{[root-of-the-server]__9e8b25ad._.js.map → [root-of-the-server]__248b9fc3._.js.map} +1 -1
- package/web/.next/server/chunks/ssr/[root-of-the-server]__357de47c._.js +4 -0
- package/web/.next/server/chunks/ssr/[root-of-the-server]__357de47c._.js.map +1 -0
- package/web/.next/server/chunks/ssr/[root-of-the-server]__56ecbe40._.js +1 -1
- package/web/.next/server/chunks/ssr/[root-of-the-server]__56ecbe40._.js.map +1 -1
- package/web/.next/server/chunks/ssr/[root-of-the-server]__67fe07fe._.js +4 -0
- package/web/.next/server/chunks/ssr/[root-of-the-server]__67fe07fe._.js.map +1 -0
- package/web/.next/server/chunks/ssr/[root-of-the-server]__6b17a22d._.js +1 -1
- package/web/.next/server/chunks/ssr/[root-of-the-server]__6b17a22d._.js.map +1 -1
- package/web/.next/server/chunks/ssr/[root-of-the-server]__6bb00d90._.js +2 -2
- package/web/.next/server/chunks/ssr/[root-of-the-server]__6bb00d90._.js.map +1 -1
- package/web/.next/server/chunks/ssr/[root-of-the-server]__804c006d._.js +1 -1
- package/web/.next/server/chunks/ssr/[root-of-the-server]__804c006d._.js.map +1 -1
- package/web/.next/server/chunks/ssr/[root-of-the-server]__8c553503._.js +2 -2
- package/web/.next/server/chunks/ssr/[root-of-the-server]__a50a7e39._.js +4 -0
- package/web/.next/server/chunks/ssr/[root-of-the-server]__a50a7e39._.js.map +1 -0
- package/web/.next/server/chunks/ssr/{[root-of-the-server]__9e8b25ad._.js → [root-of-the-server]__dfc367f2._.js} +2 -2
- package/web/.next/server/chunks/ssr/{[root-of-the-server]__ce6057f6._.js.map → [root-of-the-server]__dfc367f2._.js.map} +1 -1
- package/web/.next/server/chunks/ssr/{[root-of-the-server]__ce6057f6._.js → [root-of-the-server]__e7f61cc6._.js} +2 -2
- package/web/.next/server/chunks/ssr/{[root-of-the-server]__7cbda1ea._.js.map → [root-of-the-server]__e7f61cc6._.js.map} +1 -1
- package/web/.next/server/chunks/ssr/{[root-of-the-server]__aed1d6f8._.js → [root-of-the-server]__fe48d2dc._.js} +2 -2
- package/web/.next/server/chunks/ssr/{[root-of-the-server]__aed1d6f8._.js.map → [root-of-the-server]__fe48d2dc._.js.map} +1 -1
- package/web/.next/server/chunks/ssr/{_d8b3f91f._.js → _243e3685._.js} +2 -2
- package/web/.next/server/chunks/ssr/{_d8b3f91f._.js.map → _243e3685._.js.map} +1 -1
- package/web/.next/server/chunks/ssr/_2f6f48b8._.js +1 -1
- package/web/.next/server/chunks/ssr/_2f6f48b8._.js.map +1 -1
- package/web/.next/server/chunks/ssr/_7dca1882._.js +3 -0
- package/web/.next/server/chunks/ssr/_7dca1882._.js.map +1 -0
- package/web/.next/server/chunks/ssr/{_772be40b._.js → _821bbcc5._.js} +2 -2
- package/web/.next/server/chunks/ssr/{_772be40b._.js.map → _821bbcc5._.js.map} +1 -1
- package/web/.next/server/chunks/ssr/_e9703421._.js +1 -1
- package/web/.next/server/chunks/ssr/_e9703421._.js.map +1 -1
- package/web/.next/server/chunks/ssr/_f39a1adb._.js +3 -0
- package/web/.next/server/chunks/ssr/{_135edb9c._.js.map → _f39a1adb._.js.map} +1 -1
- package/web/.next/server/chunks/ssr/b1a17_presentation_web_components_features_settings_settings-page-client_tsx_6ed9d5f8._.js +1 -1
- package/web/.next/server/chunks/ssr/b1a17_presentation_web_components_features_settings_settings-page-client_tsx_6ed9d5f8._.js.map +1 -1
- package/web/.next/server/chunks/ssr/src_presentation_web_9db47db7._.js +5 -0
- package/web/.next/server/chunks/ssr/{src_presentation_web_5f039db1._.js.map → src_presentation_web_9db47db7._.js.map} +1 -1
- package/web/.next/server/chunks/ssr/src_presentation_web__next-internal_server_app_(dashboard)_page_actions_f66cd328.js +3 -0
- package/web/.next/server/chunks/ssr/src_presentation_web__next-internal_server_app_(dashboard)_page_actions_f66cd328.js.map +1 -0
- package/web/.next/server/chunks/ssr/src_presentation_web_aeddd007._.js +3 -0
- package/web/.next/server/chunks/ssr/{src_presentation_web_d2912c21._.js.map → src_presentation_web_aeddd007._.js.map} +1 -1
- package/web/.next/server/chunks/ssr/src_presentation_web_ca99d62d._.js +1 -1
- package/web/.next/server/chunks/ssr/src_presentation_web_ca99d62d._.js.map +1 -1
- package/web/.next/server/chunks/ssr/src_presentation_web_components_bf50c527._.js +1 -1
- package/web/.next/server/chunks/ssr/src_presentation_web_components_de814675._.js +1 -1
- package/web/.next/server/chunks/ssr/src_presentation_web_components_features_control-center_7ac3562e._.js +1 -1
- package/web/.next/server/chunks/ssr/src_presentation_web_components_features_control-center_7ac3562e._.js.map +1 -1
- package/web/.next/server/chunks/ssr/src_presentation_web_ede4a227._.js +5 -0
- package/web/.next/server/chunks/ssr/{src_presentation_web_c4337169._.js.map → src_presentation_web_ede4a227._.js.map} +1 -1
- package/web/.next/server/pages/500.html +2 -2
- package/web/.next/server/server-reference-manifest.js +1 -1
- package/web/.next/server/server-reference-manifest.json +325 -325
- package/web/.next/static/chunks/{88639a2a92364951.js → 044f4665499a9656.js} +1 -1
- package/web/.next/static/chunks/{ab42606b8d9a837b.js → 112cf5891d1ca558.js} +1 -1
- package/web/.next/static/chunks/1be7ac7a24009333.css +1 -0
- package/web/.next/static/chunks/{cab346230cafc536.js → 303a1217006489b9.js} +1 -1
- package/web/.next/static/chunks/4ac11847f73b50d6.js +1 -0
- package/web/.next/static/chunks/{ee1b7156e3985766.js → 4ac4a43b7eb441e1.js} +1 -1
- package/web/.next/static/chunks/{609a74a7c7084d18.js → 5fb66ee5a353a6c6.js} +1 -1
- package/web/.next/static/chunks/{225092aaa7291166.js → 6cfc75060a243290.js} +1 -1
- package/web/.next/static/chunks/{0eb9cffdddfd0bb6.js → d60f93a1a25ab09d.js} +1 -1
- package/web/.next/static/chunks/dcfed2c9b7cd1cb4.js +1 -0
- package/web/.next/static/chunks/{3b6956717a7c4e16.js → de66f8d6a67c2361.js} +1 -1
- package/web/.next/static/chunks/{03efd55a6de64460.js → de8b0265f780e212.js} +2 -2
- package/web/.next/server/chunks/ssr/8ba4b_server_app_(dashboard)_@drawer_repository_[repositoryId]_page_actions_f30d0343.js +0 -3
- package/web/.next/server/chunks/ssr/8ba4b_server_app_(dashboard)_@drawer_repository_[repositoryId]_page_actions_f30d0343.js.map +0 -1
- package/web/.next/server/chunks/ssr/8ba4b_server_app_(dashboard)_repository_[repositoryId]_page_actions_9f1775bb.js +0 -3
- package/web/.next/server/chunks/ssr/8ba4b_server_app_(dashboard)_repository_[repositoryId]_page_actions_9f1775bb.js.map +0 -1
- package/web/.next/server/chunks/ssr/[root-of-the-server]__14664e9b._.js +0 -4
- package/web/.next/server/chunks/ssr/[root-of-the-server]__14664e9b._.js.map +0 -1
- package/web/.next/server/chunks/ssr/[root-of-the-server]__a7de2711._.js +0 -4
- package/web/.next/server/chunks/ssr/[root-of-the-server]__a7de2711._.js.map +0 -1
- package/web/.next/server/chunks/ssr/_135edb9c._.js +0 -3
- package/web/.next/server/chunks/ssr/_cc77a143._.js +0 -3
- package/web/.next/server/chunks/ssr/_cc77a143._.js.map +0 -1
- package/web/.next/server/chunks/ssr/src_presentation_web_5f039db1._.js +0 -5
- package/web/.next/server/chunks/ssr/src_presentation_web__next-internal_server_app_(dashboard)_page_actions_2a52b697.js +0 -3
- package/web/.next/server/chunks/ssr/src_presentation_web__next-internal_server_app_(dashboard)_page_actions_2a52b697.js.map +0 -1
- package/web/.next/server/chunks/ssr/src_presentation_web__next-internal_server_app_skills_page_actions_1fa8042e.js +0 -3
- package/web/.next/server/chunks/ssr/src_presentation_web__next-internal_server_app_skills_page_actions_1fa8042e.js.map +0 -1
- package/web/.next/server/chunks/ssr/src_presentation_web__next-internal_server_app_tools_page_actions_24684200.js +0 -3
- package/web/.next/server/chunks/ssr/src_presentation_web__next-internal_server_app_tools_page_actions_24684200.js.map +0 -1
- package/web/.next/server/chunks/ssr/src_presentation_web_c4337169._.js +0 -5
- package/web/.next/server/chunks/ssr/src_presentation_web_d2912c21._.js +0 -3
- package/web/.next/static/chunks/0158bd913a9f8332.css +0 -1
- package/web/.next/static/chunks/93e492830319fe32.js +0 -1
- package/web/.next/static/chunks/9ff2ffa85c1a522d.js +0 -1
- /package/web/.next/static/{kV-WQWxVkAheI2w3nsEIN → 4hN7Gtw--ruMbDn0FRI2-}/_buildManifest.js +0 -0
- /package/web/.next/static/{kV-WQWxVkAheI2w3nsEIN → 4hN7Gtw--ruMbDn0FRI2-}/_clientMiddlewareManifest.json +0 -0
- /package/web/.next/static/{kV-WQWxVkAheI2w3nsEIN → 4hN7Gtw--ruMbDn0FRI2-}/_ssgManifest.js +0 -0
|
@@ -38,12 +38,17 @@ const PORT_PATTERNS = [
|
|
|
38
38
|
* @param line - A single line of process output
|
|
39
39
|
* @returns The detected URL string, or null if no URL/port was found
|
|
40
40
|
*/
|
|
41
|
+
// Strip ANSI escape codes (colors, cursor movement, etc.)
|
|
42
|
+
// eslint-disable-next-line no-control-regex
|
|
43
|
+
const ANSI_REGEX = /\x1b\[[0-9;]*[a-zA-Z]/g;
|
|
41
44
|
export function parsePort(line) {
|
|
42
45
|
if (!line?.trim()) {
|
|
43
46
|
return null;
|
|
44
47
|
}
|
|
48
|
+
// Strip ANSI escape codes before matching — dev servers often emit colored output
|
|
49
|
+
const clean = line.replace(ANSI_REGEX, '');
|
|
45
50
|
for (const { regex, extract } of PORT_PATTERNS) {
|
|
46
|
-
const match =
|
|
51
|
+
const match = clean.match(regex);
|
|
47
52
|
if (match) {
|
|
48
53
|
return extract(match);
|
|
49
54
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"git-pr.service.d.ts","sourceRoot":"","sources":["../../../../../../../packages/core/src/infrastructure/services/git/git-pr.service.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAGH,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,wEAAwE,CAAC;AAC5G,OAAO,KAAK,EACV,cAAc,EAGd,WAAW,EACX,QAAQ,EACR,aAAa,EACb,cAAc,EACd,YAAY,EACb,MAAM,wEAAwE,CAAC;AAUhF,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,uBAAuB,CAAC;AAE1D,qBACa,YAAa,YAAW,aAAa;IACZ,OAAO,CAAC,QAAQ,CAAC,QAAQ;gBAAR,QAAQ,EAAE,YAAY;IAErE,SAAS,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC;IAKxC,YAAY,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,GAAG,IAAI,CAAC;IAgBjD,gBAAgB,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC;IAgF9C,QAAQ,CAAC,GAAG,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC;IAKnD,qBAAqB,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC;IAKpD,SAAS,CAAC,GAAG,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC;IAWxD,IAAI,CAAC,GAAG,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,WAAW,CAAC,EAAE,OAAO,GAAG,OAAO,CAAC,IAAI,CAAC;IAYvE,QAAQ,CAAC,GAAG,EAAE,MAAM,EAAE,UAAU,EAAE,MAAM,GAAG,OAAO,CAAC,cAAc,CAAC;IAuClE,OAAO,CAAC,GAAG,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,EAAE,QAAQ,GAAE,aAAwB,GAAG,OAAO,CAAC,IAAI,CAAC;YA6BjF,eAAe;IASvB,gBAAgB,CACpB,GAAG,EAAE,MAAM,EACX,aAAa,EAAE,MAAM,EACrB,UAAU,EAAE,MAAM,EAClB,aAAa,EAAE,MAAM,EACrB,SAAS,UAAQ,GAChB,OAAO,CAAC,IAAI,CAAC;IA4EV,WAAW,CAAC,GAAG,EAAE,MAAM,EAAE,YAAY,EAAE,MAAM,EAAE,YAAY,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAUnF,WAAW,CAAC,GAAG,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,cAAc,CAAC;IAsBjE,OAAO,CACX,GAAG,EAAE,MAAM,EACX,MAAM,EAAE,MAAM,EACd,SAAS,CAAC,EAAE,MAAM,EAClB,eAAe,CAAC,EAAE,MAAM,GACvB,OAAO,CAAC,cAAc,CAAC;
|
|
1
|
+
{"version":3,"file":"git-pr.service.d.ts","sourceRoot":"","sources":["../../../../../../../packages/core/src/infrastructure/services/git/git-pr.service.ts"],"names":[],"mappings":"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"}
|
|
@@ -308,15 +308,19 @@ let GitPrService = class GitPrService {
|
|
|
308
308
|
}
|
|
309
309
|
}
|
|
310
310
|
async watchCi(cwd, branch, timeoutMs, intervalSeconds) {
|
|
311
|
+
// Resolve the latest run for the branch BEFORE the try/catch so the
|
|
312
|
+
// runUrl is available in both success and failure return paths.
|
|
313
|
+
let runUrl;
|
|
311
314
|
try {
|
|
312
315
|
// gh run watch requires a run ID — it does not support --branch.
|
|
313
316
|
// First, resolve the latest run ID for the branch via gh run list.
|
|
314
|
-
const { stdout: listOut } = await this.execFile('gh', ['run', 'list', '--branch', branch, '--json', 'databaseId', '--limit', '1'], { cwd });
|
|
317
|
+
const { stdout: listOut } = await this.execFile('gh', ['run', 'list', '--branch', branch, '--json', 'databaseId,url', '--limit', '1'], { cwd });
|
|
315
318
|
const runs = JSON.parse(listOut);
|
|
316
319
|
if (runs.length === 0 || !runs[0].databaseId) {
|
|
317
320
|
return { status: 'pending' };
|
|
318
321
|
}
|
|
319
322
|
const runId = String(runs[0].databaseId);
|
|
323
|
+
runUrl = runs[0].url;
|
|
320
324
|
const interval = intervalSeconds ?? 30;
|
|
321
325
|
const args = [
|
|
322
326
|
'run',
|
|
@@ -335,6 +339,7 @@ let GitPrService = class GitPrService {
|
|
|
335
339
|
// If we reach here (no exception), CI passed — no need for fragile stdout parsing.
|
|
336
340
|
return {
|
|
337
341
|
status: 'success',
|
|
342
|
+
runUrl,
|
|
338
343
|
logExcerpt: stdout.trim(),
|
|
339
344
|
};
|
|
340
345
|
}
|
|
@@ -356,7 +361,7 @@ let GitPrService = class GitPrService {
|
|
|
356
361
|
// Build a useful log excerpt from stdout/stderr if available
|
|
357
362
|
const errObj = error;
|
|
358
363
|
const parts = [errObj.stdout, errObj.stderr, message].filter(Boolean);
|
|
359
|
-
return { status: 'failure', logExcerpt: parts.join('\n').trim() };
|
|
364
|
+
return { status: 'failure', runUrl, logExcerpt: parts.join('\n').trim() };
|
|
360
365
|
}
|
|
361
366
|
throw new GitPrError(message, GitPrErrorCode.GIT_ERROR, cause);
|
|
362
367
|
}
|
|
@@ -27,7 +27,7 @@ export async function deployFeature(featureId) {
|
|
|
27
27
|
}
|
|
28
28
|
log.info('worktree path exists, calling deploymentService.start()');
|
|
29
29
|
const deploymentService = resolve('IDeploymentService');
|
|
30
|
-
deploymentService.start(featureId, worktreePath);
|
|
30
|
+
deploymentService.start(featureId, worktreePath, 'feature');
|
|
31
31
|
log.info('start() returned successfully — state=Booting');
|
|
32
32
|
return { success: true, state: DeploymentState.Booting };
|
|
33
33
|
}
|
|
@@ -18,7 +18,7 @@ export async function deployRepository(repositoryPath) {
|
|
|
18
18
|
}
|
|
19
19
|
log.info('directory exists, calling deploymentService.start()');
|
|
20
20
|
const deploymentService = resolve('IDeploymentService');
|
|
21
|
-
deploymentService.start(repositoryPath, repositoryPath);
|
|
21
|
+
deploymentService.start(repositoryPath, repositoryPath, 'repository');
|
|
22
22
|
log.info('start() returned successfully — state=Booting');
|
|
23
23
|
return { success: true, state: DeploymentState.Booting };
|
|
24
24
|
}
|
package/dist/src/presentation/web/components/common/repository-node/repository-node.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"repository-node.d.ts","sourceRoot":"","sources":["../../../../../../../src/presentation/web/components/common/repository-node/repository-node.tsx"],"names":[],"mappings":"AAmCA,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,0BAA0B,CAAC;AAOnE,wBAAgB,cAAc,CAAC,EAAE,IAAI,EAAE,EAAE;IAAE,IAAI,EAAE,kBAAkB,CAAC;IAAC,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAA;CAAE,
|
|
1
|
+
{"version":3,"file":"repository-node.d.ts","sourceRoot":"","sources":["../../../../../../../src/presentation/web/components/common/repository-node/repository-node.tsx"],"names":[],"mappings":"AAmCA,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,0BAA0B,CAAC;AAOnE,wBAAgB,cAAc,CAAC,EAAE,IAAI,EAAE,EAAE;IAAE,IAAI,EAAE,kBAAkB,CAAC;IAAC,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAA;CAAE,2CAkX5F"}
|
|
@@ -3,13 +3,12 @@ import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-run
|
|
|
3
3
|
import { useState, useCallback } from 'react';
|
|
4
4
|
import { Handle, Position } from '@xyflow/react';
|
|
5
5
|
import { useRouter } from 'next/navigation';
|
|
6
|
-
import { Github, Plus, Code2, Terminal, FolderOpen, Trash2, Play, Square, GitBranch, GitCommitHorizontal, ArrowDown, User, } from 'lucide-react';
|
|
6
|
+
import { Github, Plus, Code2, Terminal, FolderOpen, Trash2, Play, Square, GitBranch, GitCommitHorizontal, ArrowDown, User, RotateCcw, } from 'lucide-react';
|
|
7
7
|
import { cn } from '../../../lib/utils.js';
|
|
8
8
|
import { ActionButton } from '../../common/action-button/index.js';
|
|
9
9
|
import { Dialog, DialogClose, DialogContent, DialogDescription, DialogFooter, DialogHeader, DialogTitle, } from '../../ui/dialog.js';
|
|
10
10
|
import { Button } from '../../ui/button.js';
|
|
11
11
|
import { Tooltip, TooltipContent, TooltipProvider, TooltipTrigger } from '../../ui/tooltip.js';
|
|
12
|
-
import { DeploymentStatusBadge } from '../../common/deployment-status-badge/index.js';
|
|
13
12
|
import { useDeployAction } from '../../../hooks/use-deploy-action.js';
|
|
14
13
|
import { useFeatureFlags } from '../../../hooks/feature-flags-context.js';
|
|
15
14
|
import { useRepositoryActions } from './use-repository-actions.js';
|
|
@@ -72,9 +71,13 @@ export function RepositoryNode({ data }) {
|
|
|
72
71
|
e.stopPropagation();
|
|
73
72
|
data.onClick?.();
|
|
74
73
|
}
|
|
75
|
-
}, className: "nodrag bg-card flex w-[26rem] cursor-pointer flex-col overflow-hidden rounded-xl border shadow-sm", children: [_jsxs("div", { className: "flex items-center gap-3 px-4 py-3", children: [_jsx(Github, { className: "text-muted-foreground h-5 w-5 shrink-0" }), _jsx("span", { "data-testid": "repository-node-name", className: "min-w-0 truncate text-sm font-medium", children: data.name }), _jsxs("div", { className: cn('flex shrink-0 items-center gap-2', (data.repositoryPath ?? data.onAdd) && 'ml-auto'), onClick: (e) => e.stopPropagation(), children: [data.repositoryPath ? (_jsxs(_Fragment, { children: [_jsx(TooltipProvider, { children: _jsxs(Tooltip, { children: [_jsx(TooltipTrigger, { asChild: true, children: _jsx("span", { className: "flex items-center", children: _jsx(ActionButton, { label: "Open in IDE", onClick: actions.openInIde, loading: actions.ideLoading, error: !!actions.ideError, icon: Code2, iconOnly: true, variant: "ghost", size: "icon-xs" }) }) }), _jsx(TooltipContent, { children: "Open in IDE" })] }) }), _jsx(TooltipProvider, { children: _jsxs(Tooltip, { children: [_jsx(TooltipTrigger, { asChild: true, children: _jsx("span", { className: "flex items-center", children: _jsx(ActionButton, { label: "Open in Shell", onClick: actions.openInShell, loading: actions.shellLoading, error: !!actions.shellError, icon: Terminal, iconOnly: true, variant: "ghost", size: "icon-xs" }) }) }), _jsx(TooltipContent, { children: "Open in Shell" })] }) }), _jsx(TooltipProvider, { children: _jsxs(Tooltip, { children: [_jsx(TooltipTrigger, { asChild: true, children: _jsx("span", { className: "flex items-center", children: _jsx(ActionButton, { label: "Open Folder", onClick: actions.openFolder, loading: actions.folderLoading, error: !!actions.folderError, icon: FolderOpen, iconOnly: true, variant: "ghost", size: "icon-xs" }) }) }), _jsx(TooltipContent, { children: "Open Folder" })] }) }), _jsx(FeatureSessionsDropdown, { repositoryPath: data.repositoryPath, onCreateFromSession: handleCreateFromSession })
|
|
74
|
+
}, className: "nodrag bg-card flex w-[26rem] cursor-pointer flex-col overflow-hidden rounded-xl border shadow-sm", children: [_jsxs("div", { className: "flex items-center gap-3 px-4 py-3", children: [_jsx(Github, { className: "text-muted-foreground h-5 w-5 shrink-0" }), _jsx("span", { "data-testid": "repository-node-name", className: "min-w-0 truncate text-sm font-medium", children: data.name }), _jsxs("div", { className: cn('flex shrink-0 items-center gap-2', (data.repositoryPath ?? data.onAdd) && 'ml-auto'), onClick: (e) => e.stopPropagation(), children: [data.repositoryPath ? (_jsxs(_Fragment, { children: [_jsx(TooltipProvider, { children: _jsxs(Tooltip, { children: [_jsx(TooltipTrigger, { asChild: true, children: _jsx("span", { className: "flex items-center", children: _jsx(ActionButton, { label: "Open in IDE", onClick: actions.openInIde, loading: actions.ideLoading, error: !!actions.ideError, icon: Code2, iconOnly: true, variant: "ghost", size: "icon-xs" }) }) }), _jsx(TooltipContent, { children: "Open in IDE" })] }) }), _jsx(TooltipProvider, { children: _jsxs(Tooltip, { children: [_jsx(TooltipTrigger, { asChild: true, children: _jsx("span", { className: "flex items-center", children: _jsx(ActionButton, { label: "Open in Shell", onClick: actions.openInShell, loading: actions.shellLoading, error: !!actions.shellError, icon: Terminal, iconOnly: true, variant: "ghost", size: "icon-xs" }) }) }), _jsx(TooltipContent, { children: "Open in Shell" })] }) }), _jsx(TooltipProvider, { children: _jsxs(Tooltip, { children: [_jsx(TooltipTrigger, { asChild: true, children: _jsx("span", { className: "flex items-center", children: _jsx(ActionButton, { label: "Open Folder", onClick: actions.openFolder, loading: actions.folderLoading, error: !!actions.folderError, icon: FolderOpen, iconOnly: true, variant: "ghost", size: "icon-xs" }) }) }), _jsx(TooltipContent, { children: "Open Folder" })] }) }), _jsx(FeatureSessionsDropdown, { repositoryPath: data.repositoryPath, onCreateFromSession: handleCreateFromSession })] })) : null, data.onAdd ? (_jsx(TooltipProvider, { children: _jsxs(Tooltip, { children: [_jsx(TooltipTrigger, { asChild: true, children: _jsx("button", { "aria-label": "Add feature", "data-testid": "repository-node-add-button", onClick: (e) => {
|
|
76
75
|
e.stopPropagation();
|
|
77
76
|
data.onAdd?.();
|
|
78
77
|
}, className: cn('text-muted-foreground hover:bg-accent dark:hover:bg-accent/50 flex h-6 w-6 shrink-0 cursor-pointer items-center justify-center rounded-full transition-colors hover:text-blue-500', data.pulseAdd &&
|
|
79
|
-
'animate-pulse-cta bg-blue-100 text-blue-500 dark:bg-blue-900/40'), children: _jsx(Plus, { className: "h-3.5 w-3.5" }) }) }), _jsx(TooltipContent, { children: "Add feature" })] }) })) : null] })] }), data.branch ? (_jsx("div", { "data-testid": "repository-node-git-info", className: "text-muted-foreground border-t px-4 py-2", children: _jsxs("div", { className: "flex items-center gap-3 text-xs", children: [_jsxs("span", { className: "flex items-center gap-1 truncate", "data-testid": "repository-node-branch", children: [_jsx(GitBranch, { className: "h-3 w-3 shrink-0" }), _jsx("span", { className: "truncate", children: data.branch })] }), data.behindCount != null && data.behindCount > 0 ? (_jsxs("span", { className: "flex shrink-0 items-center gap-1 whitespace-nowrap text-amber-500", "data-testid": "repository-node-behind", children: [_jsx(ArrowDown, { className: "h-3 w-3 shrink-0" }), data.behindCount, " behind"] })) : null] }) })) : null, data.commitMessage ? (_jsx("div", { "data-testid": "repository-node-commit-info", className: "text-muted-foreground border-t px-4 py-2", children: _jsxs("div", { className: "flex items-center gap-2 text-xs", children: [_jsx(GitCommitHorizontal, { className: "h-3 w-3 shrink-0" }), _jsx("span", { className: "min-w-0 truncate", "data-testid": "repository-node-commit-message", children: data.commitMessage }), data.committer ? (_jsxs("span", { className: "text-muted-foreground/70 ml-auto flex shrink-0 items-center gap-1", "data-testid": "repository-node-committer", children: [_jsx(User, { className: "h-3 w-3 shrink-0" }), _jsx("span", { children: data.committer })] })) : null] }) })) : null
|
|
78
|
+
'animate-pulse-cta bg-blue-100 text-blue-500 dark:bg-blue-900/40'), children: _jsx(Plus, { className: "h-3.5 w-3.5" }) }) }), _jsx(TooltipContent, { children: "Add feature" })] }) })) : null] })] }), data.branch ? (_jsx("div", { "data-testid": "repository-node-git-info", className: "text-muted-foreground border-t px-4 py-2", children: _jsxs("div", { className: "flex items-center gap-3 text-xs", children: [_jsxs("span", { className: "flex items-center gap-1 truncate", "data-testid": "repository-node-branch", children: [_jsx(GitBranch, { className: "h-3 w-3 shrink-0" }), _jsx("span", { className: "truncate", children: data.branch })] }), data.behindCount != null && data.behindCount > 0 ? (_jsxs("span", { className: "flex shrink-0 items-center gap-1 whitespace-nowrap text-amber-500", "data-testid": "repository-node-behind", children: [_jsx(ArrowDown, { className: "h-3 w-3 shrink-0" }), data.behindCount, " behind"] })) : null] }) })) : null, data.commitMessage ? (_jsx("div", { "data-testid": "repository-node-commit-info", className: "text-muted-foreground border-t px-4 py-2", children: _jsxs("div", { className: "flex items-center gap-2 text-xs", children: [_jsx(GitCommitHorizontal, { className: "h-3 w-3 shrink-0" }), _jsx("span", { className: "min-w-0 truncate", "data-testid": "repository-node-commit-message", children: data.commitMessage }), data.committer ? (_jsxs("span", { className: "text-muted-foreground/70 ml-auto flex shrink-0 items-center gap-1", "data-testid": "repository-node-committer", children: [_jsx(User, { className: "h-3 w-3 shrink-0" }), _jsx("span", { children: data.committer })] })) : null] }) })) : null, featureFlags.envDeploy && data.repositoryPath ? (_jsx("div", { "data-testid": "repository-node-dev-preview", className: "border-t px-4 py-2", onClick: (e) => e.stopPropagation(), children: _jsxs("div", { className: "flex items-center gap-2 text-xs", children: [deployAction.deployError ? (_jsx("span", { className: "truncate text-xs text-red-500", children: deployAction.deployError })) : isDeploymentActive ? (_jsxs(_Fragment, { children: [_jsx("span", { className: "mr-0.5 inline-block h-2 w-2 shrink-0 rounded-full bg-green-500" }), deployAction.url ? (_jsx("a", { href: deployAction.url, target: "_blank", rel: "noopener noreferrer", className: "truncate text-green-700 hover:underline dark:text-green-400", children: deployAction.url })) : (_jsx("span", { className: "text-muted-foreground", children: "Starting..." }))] })) : (_jsxs("span", { className: "text-muted-foreground", children: ["Run", _jsx("span", { className: "text-muted-foreground/50 ml-2 text-[10px]", children: "start local environment" })] })), _jsx(TooltipProvider, { children: _jsxs(Tooltip, { children: [_jsx(TooltipTrigger, { asChild: true, children: _jsx("span", { className: "ml-auto flex items-center", children: _jsx(ActionButton, { label: deployAction.deployError
|
|
79
|
+
? 'Retry'
|
|
80
|
+
: isDeploymentActive
|
|
81
|
+
? 'Stop Dev Server'
|
|
82
|
+
: 'Start Dev Server', onClick: isDeploymentActive ? deployAction.stop : deployAction.deploy, loading: deployAction.deployLoading || deployAction.stopLoading, error: false, icon: deployAction.deployError ? RotateCcw : isDeploymentActive ? Square : Play, iconOnly: true, variant: "ghost", size: "icon-xs" }) }) }), _jsx(TooltipContent, { children: isDeploymentActive ? 'Stop Dev Server' : 'Start Dev Server' })] }) })] }) })) : null] }), data.onAdd || data.showHandles ? (_jsx(Handle, { type: "source", position: Position.Right, isConnectable: !data.showHandles, className: "opacity-0!" })) : null] }));
|
|
80
83
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"use-control-center-state.d.ts","sourceRoot":"","sources":["../../../../../../../src/presentation/web/components/features/control-center/use-control-center-state.ts"],"names":[],"mappings":"AAKA,OAAO,KAAK,EAAE,UAAU,EAAE,IAAI,EAAE,UAAU,EAAE,MAAM,eAAe,CAAC;AAClE,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,kCAAkC,CAAC;AACxE,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,qCAAqC,CAAC;AAC9E,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,uCAAuC,CAAC;AAC5E,OAAO,EAGL,KAAK,eAAe,EACrB,MAAM,yBAAyB,CAAC;AAgBjC,OAAO,EAAiB,KAAK,cAAc,EAAE,MAAM,yBAAyB,CAAC;AAM7E,MAAM,WAAW,kBAAkB;IACjC,KAAK,EAAE,cAAc,EAAE,CAAC;IACxB,KAAK,EAAE,IAAI,EAAE,CAAC;IACd,aAAa,EAAE,CAAC,OAAO,EAAE,UAAU,CAAC,cAAc,CAAC,EAAE,KAAK,IAAI,CAAC;IAC/D,aAAa,EAAE,CAAC,UAAU,EAAE,UAAU,KAAK,IAAI,CAAC;IAChD,mBAAmB,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK;QAAE,QAAQ,EAAE,OAAO,CAAC;QAAC,QAAQ,EAAE,MAAM,CAAA;KAAE,CAAC;IAC/E,YAAY,EAAE,CAAC,SAAS,EAAE,eAAe,KAAK,IAAI,CAAC;IACnD,mBAAmB,EAAE,CAAC,SAAS,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE,OAAO,EAAE,aAAa,CAAC,EAAE,OAAO,KAAK,IAAI,CAAC;IAC7F,kBAAkB,EAAE,CAAC,SAAS,EAAE,MAAM,KAAK,IAAI,CAAC;IAChD,kBAAkB,EAAE,CAAC,SAAS,EAAE,MAAM,KAAK,IAAI,CAAC;IAChD,iBAAiB,EAAE,CAAC,SAAS,EAAE,MAAM,KAAK,IAAI,CAAC;IAC/C,sBAAsB,EAAE,CAAC,YAAY,EAAE,MAAM,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;IAChE,iBAAiB,EAAE,CACjB,YAAY,EAAE,MAAM,GAAG,IAAI,EAC3B,YAAY,CAAC,EAAE,OAAO,CAAC,eAAe,CAAC,EACvC,QAAQ,CAAC,EAAE,MAAM,KACd,MAAM,CAAC;IACZ,wDAAwD;IACxD,wBAAwB,EAAE,CAAC,aAAa,EAAE,MAAM,KAAK,MAAM,GAAG,SAAS,CAAC;IACxE,gDAAgD;IAChD,iBAAiB,EAAE,CAAC,MAAM,EAAE,MAAM,KAAK,kBAAkB,GAAG,SAAS,CAAC;IACtE,0EAA0E;IAC1E,YAAY,EAAE,CAAC,SAAS,EAAE,cAAc,KAAK,IAAI,CAAC;CACnD;AAQD,wBAAgB,qBAAqB,CACnC,YAAY,EAAE,cAAc,EAAE,EAC9B,YAAY,EAAE,IAAI,EAAE,GACnB,kBAAkB,
|
|
1
|
+
{"version":3,"file":"use-control-center-state.d.ts","sourceRoot":"","sources":["../../../../../../../src/presentation/web/components/features/control-center/use-control-center-state.ts"],"names":[],"mappings":"AAKA,OAAO,KAAK,EAAE,UAAU,EAAE,IAAI,EAAE,UAAU,EAAE,MAAM,eAAe,CAAC;AAClE,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,kCAAkC,CAAC;AACxE,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,qCAAqC,CAAC;AAC9E,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,uCAAuC,CAAC;AAC5E,OAAO,EAGL,KAAK,eAAe,EACrB,MAAM,yBAAyB,CAAC;AAgBjC,OAAO,EAAiB,KAAK,cAAc,EAAE,MAAM,yBAAyB,CAAC;AAM7E,MAAM,WAAW,kBAAkB;IACjC,KAAK,EAAE,cAAc,EAAE,CAAC;IACxB,KAAK,EAAE,IAAI,EAAE,CAAC;IACd,aAAa,EAAE,CAAC,OAAO,EAAE,UAAU,CAAC,cAAc,CAAC,EAAE,KAAK,IAAI,CAAC;IAC/D,aAAa,EAAE,CAAC,UAAU,EAAE,UAAU,KAAK,IAAI,CAAC;IAChD,mBAAmB,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK;QAAE,QAAQ,EAAE,OAAO,CAAC;QAAC,QAAQ,EAAE,MAAM,CAAA;KAAE,CAAC;IAC/E,YAAY,EAAE,CAAC,SAAS,EAAE,eAAe,KAAK,IAAI,CAAC;IACnD,mBAAmB,EAAE,CAAC,SAAS,EAAE,MAAM,EAAE,OAAO,CAAC,EAAE,OAAO,EAAE,aAAa,CAAC,EAAE,OAAO,KAAK,IAAI,CAAC;IAC7F,kBAAkB,EAAE,CAAC,SAAS,EAAE,MAAM,KAAK,IAAI,CAAC;IAChD,kBAAkB,EAAE,CAAC,SAAS,EAAE,MAAM,KAAK,IAAI,CAAC;IAChD,iBAAiB,EAAE,CAAC,SAAS,EAAE,MAAM,KAAK,IAAI,CAAC;IAC/C,sBAAsB,EAAE,CAAC,YAAY,EAAE,MAAM,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;IAChE,iBAAiB,EAAE,CACjB,YAAY,EAAE,MAAM,GAAG,IAAI,EAC3B,YAAY,CAAC,EAAE,OAAO,CAAC,eAAe,CAAC,EACvC,QAAQ,CAAC,EAAE,MAAM,KACd,MAAM,CAAC;IACZ,wDAAwD;IACxD,wBAAwB,EAAE,CAAC,aAAa,EAAE,MAAM,KAAK,MAAM,GAAG,SAAS,CAAC;IACxE,gDAAgD;IAChD,iBAAiB,EAAE,CAAC,MAAM,EAAE,MAAM,KAAK,kBAAkB,GAAG,SAAS,CAAC;IACtE,0EAA0E;IAC1E,YAAY,EAAE,CAAC,SAAS,EAAE,cAAc,KAAK,IAAI,CAAC;CACnD;AAQD,wBAAgB,qBAAqB,CACnC,YAAY,EAAE,cAAc,EAAE,EAC9B,YAAY,EAAE,IAAI,EAAE,GACnB,kBAAkB,CAuhBpB"}
|
package/dist/src/presentation/web/components/features/control-center/use-control-center-state.js
CHANGED
|
@@ -102,11 +102,20 @@ export function useControlCenterState(initialNodes, initialEdges) {
|
|
|
102
102
|
for (const { featureId, state, lifecycle } of resolveSseEventUpdates(newEvents)) {
|
|
103
103
|
if (state !== undefined || lifecycle !== undefined) {
|
|
104
104
|
const nodeId = `feat-${featureId}`;
|
|
105
|
+
const existingNode = nodesRef.current.find((n) => n.id === nodeId);
|
|
106
|
+
const existingState = existingNode
|
|
107
|
+
? existingNode.data.state
|
|
108
|
+
: undefined;
|
|
105
109
|
// Skip SSE updates for features in 'deleting' state — the optimistic
|
|
106
110
|
// delete state must not be overwritten by stale SSE events (e.g. agent
|
|
107
111
|
// cancellation emitting AgentFailed during the soft-delete window).
|
|
108
|
-
|
|
109
|
-
|
|
112
|
+
if (existingState === 'deleting')
|
|
113
|
+
continue;
|
|
114
|
+
// Skip SSE error events during mutation cooldown — after approve/reject
|
|
115
|
+
// the agent may still report AgentFailed from the previous run before
|
|
116
|
+
// the resume kicks in. The optimistic 'running' state must not be
|
|
117
|
+
// overwritten by stale error events during this transition window.
|
|
118
|
+
if (state === 'error' && isMutating() && existingState === 'running')
|
|
110
119
|
continue;
|
|
111
120
|
updateFeature(nodeId, {
|
|
112
121
|
...(state !== undefined && { state }),
|
|
@@ -114,7 +123,7 @@ export function useControlCenterState(initialNodes, initialEdges) {
|
|
|
114
123
|
});
|
|
115
124
|
}
|
|
116
125
|
}
|
|
117
|
-
}, [events, updateFeature]);
|
|
126
|
+
}, [events, updateFeature, isMutating]);
|
|
118
127
|
// Listen for optimistic approval/rejection events from the drawer (fires before SSE arrives).
|
|
119
128
|
// Uses beginMutation + endMutation to prevent stale poll/reconcile data from overwriting
|
|
120
129
|
// the optimistic 'running' state during the transition window (avoids brief "Something went wrong" flash).
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"use-deploy-action.d.ts","sourceRoot":"","sources":["../../../../../src/presentation/web/hooks/use-deploy-action.ts"],"names":[],"mappings":"AAIA,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,sCAAsC,CAAC;AAM5E,MAAM,WAAW,iBAAiB;IAChC,QAAQ,EAAE,MAAM,CAAC;IACjB,UAAU,EAAE,SAAS,GAAG,YAAY,CAAC;IACrC,cAAc,EAAE,MAAM,CAAC;IACvB,MAAM,CAAC,EAAE,MAAM,CAAC;CACjB;AAED,MAAM,WAAW,iBAAiB;IAChC,MAAM,EAAE,MAAM,OAAO,CAAC,IAAI,CAAC,CAAC;IAC5B,IAAI,EAAE,MAAM,OAAO,CAAC,IAAI,CAAC,CAAC;IAC1B,aAAa,EAAE,OAAO,CAAC;IACvB,WAAW,EAAE,OAAO,CAAC;IACrB,WAAW,EAAE,MAAM,GAAG,IAAI,CAAC;IAC3B,MAAM,EAAE,eAAe,GAAG,IAAI,CAAC;IAC/B,GAAG,EAAE,MAAM,GAAG,IAAI,CAAC;CACpB;
|
|
1
|
+
{"version":3,"file":"use-deploy-action.d.ts","sourceRoot":"","sources":["../../../../../src/presentation/web/hooks/use-deploy-action.ts"],"names":[],"mappings":"AAIA,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,sCAAsC,CAAC;AAM5E,MAAM,WAAW,iBAAiB;IAChC,QAAQ,EAAE,MAAM,CAAC;IACjB,UAAU,EAAE,SAAS,GAAG,YAAY,CAAC;IACrC,cAAc,EAAE,MAAM,CAAC;IACvB,MAAM,CAAC,EAAE,MAAM,CAAC;CACjB;AAED,MAAM,WAAW,iBAAiB;IAChC,MAAM,EAAE,MAAM,OAAO,CAAC,IAAI,CAAC,CAAC;IAC5B,IAAI,EAAE,MAAM,OAAO,CAAC,IAAI,CAAC,CAAC;IAC1B,aAAa,EAAE,OAAO,CAAC;IACvB,WAAW,EAAE,OAAO,CAAC;IACrB,WAAW,EAAE,MAAM,GAAG,IAAI,CAAC;IAC3B,MAAM,EAAE,eAAe,GAAG,IAAI,CAAC;IAC/B,GAAG,EAAE,MAAM,GAAG,IAAI,CAAC;CACpB;AAMD,wBAAgB,eAAe,CAAC,KAAK,EAAE,iBAAiB,GAAG,IAAI,GAAG,iBAAiB,CAmOlF"}
|
|
@@ -6,7 +6,6 @@ import { deployRepository } from '../app/actions/deploy-repository.js';
|
|
|
6
6
|
import { stopDeployment } from '../app/actions/stop-deployment.js';
|
|
7
7
|
import { getDeploymentStatus } from '../app/actions/get-deployment-status.js';
|
|
8
8
|
const log = createLogger('[useDeployAction]');
|
|
9
|
-
const ERROR_CLEAR_DELAY = 5000;
|
|
10
9
|
const POLL_INTERVAL = 3000;
|
|
11
10
|
export function useDeployAction(input) {
|
|
12
11
|
const [deployLoading, setDeployLoading] = useState(false);
|
|
@@ -14,7 +13,6 @@ export function useDeployAction(input) {
|
|
|
14
13
|
const [deployError, setDeployError] = useState(null);
|
|
15
14
|
const [status, setStatus] = useState(null);
|
|
16
15
|
const [url, setUrl] = useState(null);
|
|
17
|
-
const errorTimerRef = useRef(null);
|
|
18
16
|
const pollIntervalRef = useRef(null);
|
|
19
17
|
const mountedRef = useRef(true);
|
|
20
18
|
const statusRef = useRef(status);
|
|
@@ -29,11 +27,37 @@ export function useDeployAction(input) {
|
|
|
29
27
|
mountedRef.current = false;
|
|
30
28
|
};
|
|
31
29
|
}, []);
|
|
30
|
+
// Fetch status on mount — recover running dev servers after page reload
|
|
31
|
+
useEffect(() => {
|
|
32
|
+
if (!input)
|
|
33
|
+
return;
|
|
34
|
+
let cancelled = false;
|
|
35
|
+
(async () => {
|
|
36
|
+
try {
|
|
37
|
+
const result = await getDeploymentStatus(input.targetId);
|
|
38
|
+
if (cancelled || !mountedRef.current)
|
|
39
|
+
return;
|
|
40
|
+
if (result && result.state !== 'Stopped') {
|
|
41
|
+
log.info(`mount recovery: "${input.targetId}" state=${result.state}, url=${result.url}`);
|
|
42
|
+
setStatus(result.state);
|
|
43
|
+
setUrl(result.url);
|
|
44
|
+
startPolling(input.targetId);
|
|
45
|
+
}
|
|
46
|
+
}
|
|
47
|
+
catch {
|
|
48
|
+
// Server container may not be available (e.g., in tests)
|
|
49
|
+
log.debug(`mount recovery failed for "${input.targetId}" — ignoring`);
|
|
50
|
+
}
|
|
51
|
+
})();
|
|
52
|
+
return () => {
|
|
53
|
+
cancelled = true;
|
|
54
|
+
};
|
|
55
|
+
// Only run on mount (input identity is stable from the caller)
|
|
56
|
+
// eslint-disable-next-line react-hooks/exhaustive-deps
|
|
57
|
+
}, [input?.targetId]);
|
|
32
58
|
// Cleanup on unmount
|
|
33
59
|
useEffect(() => {
|
|
34
60
|
return () => {
|
|
35
|
-
if (errorTimerRef.current)
|
|
36
|
-
clearTimeout(errorTimerRef.current);
|
|
37
61
|
if (pollIntervalRef.current)
|
|
38
62
|
clearInterval(pollIntervalRef.current);
|
|
39
63
|
};
|
|
@@ -53,7 +77,20 @@ export function useDeployAction(input) {
|
|
|
53
77
|
stopPolling();
|
|
54
78
|
return;
|
|
55
79
|
}
|
|
56
|
-
|
|
80
|
+
let result;
|
|
81
|
+
try {
|
|
82
|
+
result = await getDeploymentStatus(targetId);
|
|
83
|
+
}
|
|
84
|
+
catch (err) {
|
|
85
|
+
log.warn(`poll fetch failed for "${targetId}":`, err);
|
|
86
|
+
// Treat fetch failure as deployment gone — clear UI
|
|
87
|
+
if (mountedRef.current) {
|
|
88
|
+
setStatus(null);
|
|
89
|
+
setUrl(null);
|
|
90
|
+
stopPolling();
|
|
91
|
+
}
|
|
92
|
+
return;
|
|
93
|
+
}
|
|
57
94
|
if (!mountedRef.current)
|
|
58
95
|
return;
|
|
59
96
|
if (!result || result.state === 'Stopped') {
|
|
@@ -71,6 +108,32 @@ export function useDeployAction(input) {
|
|
|
71
108
|
}
|
|
72
109
|
}, POLL_INTERVAL);
|
|
73
110
|
}, [stopPolling]);
|
|
111
|
+
// Idle poll — when no deployment is known, periodically check if one was
|
|
112
|
+
// started externally (e.g., from the drawer while the repo node is mounted).
|
|
113
|
+
const IDLE_POLL_INTERVAL = 5000;
|
|
114
|
+
useEffect(() => {
|
|
115
|
+
if (!input || status !== null)
|
|
116
|
+
return;
|
|
117
|
+
const timer = setInterval(async () => {
|
|
118
|
+
if (!mountedRef.current)
|
|
119
|
+
return;
|
|
120
|
+
try {
|
|
121
|
+
const result = await getDeploymentStatus(input.targetId);
|
|
122
|
+
if (!mountedRef.current)
|
|
123
|
+
return;
|
|
124
|
+
if (result && result.state !== 'Stopped') {
|
|
125
|
+
log.info(`idle poll: "${input.targetId}" state=${result.state}, url=${result.url}`);
|
|
126
|
+
setStatus(result.state);
|
|
127
|
+
setUrl(result.url);
|
|
128
|
+
startPolling(input.targetId);
|
|
129
|
+
}
|
|
130
|
+
}
|
|
131
|
+
catch {
|
|
132
|
+
// ignore
|
|
133
|
+
}
|
|
134
|
+
}, IDLE_POLL_INTERVAL);
|
|
135
|
+
return () => clearInterval(timer);
|
|
136
|
+
}, [input, status, startPolling]);
|
|
74
137
|
const handleDeploy = useCallback(async () => {
|
|
75
138
|
if (!input) {
|
|
76
139
|
log.warn('deploy() called but input is null — no-op');
|
|
@@ -81,8 +144,6 @@ export function useDeployAction(input) {
|
|
|
81
144
|
return;
|
|
82
145
|
}
|
|
83
146
|
log.info(`deploy() — targetType="${input.targetType}", targetId="${input.targetId}", repositoryPath="${input.repositoryPath}"`);
|
|
84
|
-
if (errorTimerRef.current)
|
|
85
|
-
clearTimeout(errorTimerRef.current);
|
|
86
147
|
setDeployLoading(true);
|
|
87
148
|
setDeployError(null);
|
|
88
149
|
try {
|
|
@@ -96,9 +157,8 @@ export function useDeployAction(input) {
|
|
|
96
157
|
}
|
|
97
158
|
if (!result.success) {
|
|
98
159
|
const errorMessage = result.error ?? 'An unexpected error occurred';
|
|
99
|
-
log.
|
|
160
|
+
log.warn(`deploy failed: ${errorMessage}`);
|
|
100
161
|
setDeployError(errorMessage);
|
|
101
|
-
errorTimerRef.current = setTimeout(() => setDeployError(null), ERROR_CLEAR_DELAY);
|
|
102
162
|
}
|
|
103
163
|
else {
|
|
104
164
|
log.info(`deploy succeeded — initial state=${result.state}, starting polling`);
|
|
@@ -113,7 +173,6 @@ export function useDeployAction(input) {
|
|
|
113
173
|
const errorMessage = err instanceof Error ? err.message : 'An unexpected error occurred';
|
|
114
174
|
log.error(`deploy threw exception: ${errorMessage}`, err);
|
|
115
175
|
setDeployError(errorMessage);
|
|
116
|
-
errorTimerRef.current = setTimeout(() => setDeployError(null), ERROR_CLEAR_DELAY);
|
|
117
176
|
}
|
|
118
177
|
finally {
|
|
119
178
|
if (mountedRef.current) {
|
|
@@ -3,12 +3,12 @@ import dagre from '@dagrejs/dagre';
|
|
|
3
3
|
export const CANVAS_LAYOUT_DEFAULTS = {
|
|
4
4
|
direction: 'LR',
|
|
5
5
|
ranksep: 200,
|
|
6
|
-
nodesep:
|
|
6
|
+
nodesep: 30,
|
|
7
7
|
};
|
|
8
8
|
/** Known node-type dimensions for the canvas node types */
|
|
9
9
|
const NODE_DIMENSIONS = {
|
|
10
|
-
featureNode: { width: 288, height:
|
|
11
|
-
repositoryNode: { width: 400, height:
|
|
10
|
+
featureNode: { width: 288, height: 160 },
|
|
11
|
+
repositoryNode: { width: 400, height: 160 },
|
|
12
12
|
};
|
|
13
13
|
function getNodeSize(node, defaultSize) {
|
|
14
14
|
// Prefer per-node size from data, then type-based lookup, then default
|