diff --git a/src/ClaudeDo.Installer/Pages/InstallPage/InstallPageViewModel.cs b/src/ClaudeDo.Installer/Pages/InstallPage/InstallPageViewModel.cs index 9f46f68..3d6edad 100644 --- a/src/ClaudeDo.Installer/Pages/InstallPage/InstallPageViewModel.cs +++ b/src/ClaudeDo.Installer/Pages/InstallPage/InstallPageViewModel.cs @@ -84,6 +84,15 @@ public partial class InstallPageViewModel : ObservableObject, IInstallerPage { if (IsInstalling) return; + // Reset per-step state so a re-run starts clean instead of appending + // output to the previous run's messages. + foreach (var s in Steps) + { + s.Messages.Clear(); + s.Status = StepStatus.Pending; + s.IsExpanded = false; + } + IsInstalling = true; IsComplete = false; HasErrors = false; @@ -96,7 +105,11 @@ public partial class InstallPageViewModel : ObservableObject, IInstallerPage var step = Steps.FirstOrDefault(s => s.Name == p.StepName); if (step is null) return; - step.Status = p.Status; + // Status and output lines arrive on two separate Progress channels, so a + // trailing "Running" line-message can be delivered after the step's terminal + // Done/Failed. Never let that downgrade a completed step back to Running. + if (!(step.Status is StepStatus.Done or StepStatus.Failed && p.Status is StepStatus.Running)) + step.Status = p.Status; if (p.Message is not null) { // Messages starting with "\r" overwrite the previous line (live progress).