Skip to content
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
57 changes: 39 additions & 18 deletions src/cli/tui/screens/deploy/useDeployFlow.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ import {
parsePolicyEngineOutputs,
parsePolicyOutputs,
} from '../../../cloudformation';
import { checkStackStatus } from '../../../cloudformation/stack-status';
import { DEFAULT_DEPLOY_ATTRS, computeDeployAttrs } from '../../../commands/deploy/utils.js';
import { getErrorMessage, isChangesetInProgressError, isExpiredTokenError } from '../../../errors';
import { ExecLogger } from '../../../logging';
Expand Down Expand Up @@ -612,27 +613,47 @@ export function useDeployFlow(options: DeployFlowOptions = {}): DeployFlowState
setIsDiffLoading(true);
setPreDeployDiffStep(prev => ({ ...prev, status: 'running' }));
logger.startStep('Computing diff changes...');
switchableIoHost?.setOnRawMessage((code, _level, message, data) => {
logger.logDiff(code, message);
if (code === 'CDK_TOOLKIT_I4002') {
setDiffSummaries(prev => [...prev, parseStackDiff(data, message)]);
} else if (code === 'CDK_TOOLKIT_I4001') {
setNumStacksWithChanges(parseDiffResult(data).numStacksWithChanges);
}
});
switchableIoHost?.setVerbose(true);

// Skip diff for new stacks — there's nothing to compare against, and CDK's diff
// creates a temporary changeset that leaves a ghost stack which races with deploy.
let skipDiff = false;
try {
await cdkToolkitWrapper.diff();
const target = context?.awsTargets[0];
const currentStackName = stackNames?.[0];
if (target && currentStackName) {
const status = await checkStackStatus(target.region, currentStackName);
skipDiff = !status.exists;
}
} catch {
// Diff failure is non-fatal — deploy will proceed
} finally {
switchableIoHost?.setVerbose(false);
switchableIoHost?.setOnRawMessage(null);
isDiffRunningRef.current = false;
setIsDiffLoading(false);
logger.endStep('success');
setPreDeployDiffStep(prev => ({ ...prev, status: 'success' }));
// Status check failed — fall through to diff (tolerate old race)
}

if (skipDiff) {
logger.log('New stack — skipping diff (nothing to compare against)');
} else {
switchableIoHost?.setOnRawMessage((code, _level, message, data) => {
logger.logDiff(code, message);
if (code === 'CDK_TOOLKIT_I4002') {
setDiffSummaries(prev => [...prev, parseStackDiff(data, message)]);
} else if (code === 'CDK_TOOLKIT_I4001') {
setNumStacksWithChanges(parseDiffResult(data).numStacksWithChanges);
}
});
switchableIoHost?.setVerbose(true);
try {
await cdkToolkitWrapper.diff();
} catch {
// Diff failure is non-fatal — deploy will proceed
} finally {
switchableIoHost?.setVerbose(false);
switchableIoHost?.setOnRawMessage(null);
}
}

isDiffRunningRef.current = false;
setIsDiffLoading(false);
logger.endStep('success');
setPreDeployDiffStep(prev => ({ ...prev, status: 'success' }));
}

setPublishAssetsStep(prev => ({ ...prev, status: 'running' }));
Expand Down
Loading