Pick the closest match to your repo; the MCP backend refines it.
@@ -296,54 +333,99 @@ export default function ConfigurePage() {
- {/* Node version + commands */}
+ {/* Runtime version + commands */}
-
+ {/* Node.js version: only show for node_app AND build stage enabled */}
+ {template === "node_app" && stages.includes("build") && (
+
+ )}
-
+ {/* Install command: only show if build stage enabled */}
+ {stages.includes("build") && (
+
+ )}
-
+ {/* Test command: only show if test stage enabled */}
+ {stages.includes("test") && (
+
+ )}
-
+ {/* Build command: only show if build stage enabled */}
+ {stages.includes("build") && (
+
+ )}
- {provider === "aws" && (
+ {provider === "aws" && stages.includes("deploy") && (
+ <>
+
+
+
+ >
)}
{provider === "gcp" && (
diff --git a/client/src/pages/DashboardPage.tsx b/client/src/pages/DashboardPage.tsx
index 317539e..9995e98 100644
--- a/client/src/pages/DashboardPage.tsx
+++ b/client/src/pages/DashboardPage.tsx
@@ -38,6 +38,12 @@ export default function DashboardPage() {
const repoFullName = result?.repo || repo || "";
const branchName =
(result as any)?.branch || selectedBranch || "main";
+ const environment = cfg.env || "dev";
+ const workflowFile =
+ (result as any)?.pipeline_name || `${environment}-deploy.yml`;
+ const workflowPath = workflowFile.startsWith(".github/workflows/")
+ ? workflowFile
+ : `.github/workflows/${workflowFile}`;
const [versions, setVersions] = useState([]);
const [loadingHistory, setLoadingHistory] = useState(false);
@@ -48,6 +54,12 @@ export default function DashboardPage() {
const [editingYaml, setEditingYaml] = useState(false);
const [draftYaml, setDraftYaml] = useState(result?.generated_yaml ?? "");
+ const currentYaml = (result?.generated_yaml ?? draftYaml ?? "").trim();
+ const canCommitYaml = currentYaml.length > 0;
+ // 🔑 Single source of truth for the currently active YAML
+
+// const canCommitYaml =
+// (editingYaml ? draftYaml : (result?.generated_yaml ?? draftYaml))?.trim();
useEffect(() => {
if (!editingYaml) {
@@ -67,6 +79,7 @@ export default function DashboardPage() {
const rows = await api.getPipelineHistory({
repoFullName,
branch: branchName,
+ path: workflowPath,
limit: 20,
});
if (!cancelled) {
@@ -88,57 +101,79 @@ export default function DashboardPage() {
cancelled = true;
};
// eslint-disable-next-line react-hooks/exhaustive-deps
- }, [repoFullName, branchName]);
-
- async function handleRollback(version: PipelineVersion) {
- if (!version?.id) return;
- const confirmMsg = `Rollback ${repoFullName}@${branchName} to version created at ${formatDate(
- version.created_at
- )}?`;
- if (!window.confirm(confirmMsg)) return;
-
- setRollbackBusy(true);
- try {
- const data = await api.rollbackPipeline(version.id);
- console.log("[Dashboard] Rollback response:", data);
- alert("Rollback queued successfully.");
-
- const rows = await api.getPipelineHistory({
- repoFullName,
- branch,
- limit: 20,
- });
- setVersions(rows);
- } catch (err: any) {
- console.error("[Dashboard] rollbackPipeline failed:", err);
- alert(err.message || "Rollback failed");
- } finally {
- setRollbackBusy(false);
- }
- }
+ }, [repoFullName, branchName, workflowPath]);
- function handleCommitClick() {
- const repoFullNameLocal = result?.repo || repo;
- const yaml = result?.generated_yaml;
- const branchLocal = (result as any)?.branch || branchName || "main";
- const environment = cfg.env || "dev";
- const provider = "aws";
- const path = `.github/workflows/${environment}-deploy.yml`;
-
- if (!repoFullNameLocal || !yaml) {
- alert("Missing repo or YAML — generate a pipeline first.");
- return;
- }
+async function handleRollback(version: PipelineVersion) {
+ if (!version?.id) return;
+
+ const confirmMsg = `Rollback ${repoFullName}@${branchName} to version created at ${formatDate(
+ version.created_at
+ )}?`;
+ if (!window.confirm(confirmMsg)) return;
+
+ setRollbackBusy(true);
+ try {
+ // 👇 THIS is where the rollback happens
+ const data = await api.rollbackPipeline(version.id);
- startDeploy({
- repoFullName: repoFullNameLocal,
- branch: branchLocal,
- env: environment,
- yaml,
- provider,
- path,
+ // 👇 SHOW REAL OUTPUT (GitHub commit URL)
+ alert(
+ `Rollback committed ✅\n${
+ data?.github?.commit?.html_url ?? "OK"
+ }`
+ );
+
+ // 👇 Update Current Pipeline YAML in UI
+ setResultYaml(version.yaml);
+ setEditingYaml(false);
+
+ // 👇 Refresh history list
+ const rows = await api.getPipelineHistory({
+ repoFullName,
+ branch: branchName,
+ path: workflowPath,
+ limit: 20,
});
+ setVersions(rows);
+ setSelectedVersion(rows[0] ?? null);
+
+ } catch (err: any) {
+ console.error("[Dashboard] rollbackPipeline failed:", err);
+ alert(err.message || "Rollback failed");
+ } finally {
+ setRollbackBusy(false);
}
+}
+
+
+
+async function handleCommitClick() {
+ const repoFullNameLocal = result?.repo || repo;
+ const yaml = currentYaml;
+
+ const branchLocal = (result as any)?.branch || branchName || "main";
+ const provider = "aws";
+ const path = workflowPath;
+
+ if (!repoFullNameLocal || !yaml) {
+ alert("Missing repo or YAML — generate a pipeline first.");
+ return;
+ }
+
+ const res = await startDeploy({
+ repoFullName: repoFullNameLocal,
+ branch: branchLocal,
+ env: environment,
+ yaml,
+ provider,
+ path,
+ });
+
+ // backend response you showed: res.data.commit.html_url
+ const url = res?.data?.commit?.html_url;
+ alert(url ? `Committed ✅\n${url}` : "Committed ✅");
+}
+
return (
@@ -183,26 +218,28 @@ export default function DashboardPage() {
- {result?.generated_yaml ?? "No pipeline generated yet."}
+ {currentYaml || "No pipeline generated yet."}
+
)}
-
+
+ size="sm"
+ disabled={running || !repoFullName || !canCommitYaml}
+ onClick={handleCommitClick}
+>
+ {running ? "Committing…" : "Commit to GitHub"}
+
+
{running && (
)}
- {result?.generated_yaml && (
+ {currentYaml && (
<>