From d562b93ff4e7928b6e882bd4c96734377f56ee02 Mon Sep 17 00:00:00 2001 From: jon Date: Wed, 22 Jul 2026 16:00:09 -0500 Subject: [PATCH] fix(install-windows): ask before downloading models instead of offering Ctrl+C Ctrl+C in PS 5.1 kills the whole script, so the advertised way to skip the download was also the way to abort the install before its final steps. Now a 'Download them now? [Y/n]' prompt, so declining continues to the end. The default-model seed moves above the pull - it only writes a settings row and was being lost along with the download. A test forbids offering Ctrl+C again. Co-Authored-By: Claude Opus 4.8 --- install-windows.ps1 | 45 ++++++++++++++++++++++++++++----------------- tests/test_smoke.py | 6 ++++++ 2 files changed, 34 insertions(+), 17 deletions(-) diff --git a/install-windows.ps1 b/install-windows.ps1 index ac5a418..18c0e8a 100644 --- a/install-windows.ps1 +++ b/install-windows.ps1 @@ -243,22 +243,9 @@ if ((Test-Path (Join-Path $LegacyStore "blobs")) -and $env:OLLAMA_MODELS = $ModelStore Write-OK "Model store: $ModelStore" -Write-Step "Pulling models ($ChatModel for chat, $MemModel for memory)" -Write-Host " Downloads a few GB; press Ctrl+C to skip and pull them later from the Models tab." -ForegroundColor DarkGray -# No pipe: 'ollama pull' draws a progress bar with cursor control, and piping it -# (to Out-Host or anything else) buffers the redraws - the download then shows no -# output for minutes and reads as a hang. Let it own the console. -# No try/catch either: a native command that exits non-zero does not throw, so -# the catch never fired and a failed pull was reported as success. -ollama pull $ChatModel -if ($LASTEXITCODE -eq 0) { Write-OK "$ChatModel ready (default chat model)" } -else { Write-Warn "$ChatModel pull skipped/failed - pull it from the Models tab later." } - -ollama pull $MemModel -if ($LASTEXITCODE -eq 0) { Write-OK "$MemModel ready (memory curator)" } -else { Write-Warn "$MemModel pull skipped/failed - the memory service will fall back to the chat model." } - -# Pin it as the default chat model. Runs from the repo root so the synapse +# Pin it as the default chat model. Runs BEFORE the download because it only +# writes a settings row - nothing here needs the model to be present on disk, +# and putting it after the pull meant declining the download also lost it. Runs from the repo root so the synapse # package imports; only writes the 'model' setting in the shared DB. Write-Step "Setting $ChatModel as the default model" Push-Location $RepoRoot @@ -268,6 +255,30 @@ Pop-Location if ($seedOk) { Write-OK "Default model set to $ChatModel" } else { Write-Warn "Could not persist default model - pick it at the top of the chat instead." } +Write-Step "Pulling models ($ChatModel for chat, $MemModel for memory)" +# A prompt, not "press Ctrl+C to skip": Ctrl+C in PowerShell 5.1 terminates the +# whole script, so the escape hatch the installer advertised was also the one +# thing that stopped it finishing - no Ollama cleanup, no summary, no window +# close. Answering "n" declines the download and the installer carries on. +Write-Host " These are several GB. You can skip and pull them later from the Models tab." -ForegroundColor DarkGray +$pullAnswer = Read-Host " Download them now? [Y/n]" +if ($pullAnswer -match '^\s*(n|no)\s*$') { + Write-Warn "Model download skipped - get them from the Models tab when you are ready." +} else { +# No pipe: 'ollama pull' draws a progress bar with cursor control, and piping it +# (to Out-Host or anything else) buffers the redraws - the download then shows no +# output for minutes and reads as a hang. Let it own the console. +# No try/catch either: a native command that exits non-zero does not throw, so +# the catch never fired and a failed pull was reported as success. + ollama pull $ChatModel + if ($LASTEXITCODE -eq 0) { Write-OK "$ChatModel ready (default chat model)" } + else { Write-Warn "$ChatModel pull skipped/failed - pull it from the Models tab later." } + + ollama pull $MemModel + if ($LASTEXITCODE -eq 0) { Write-OK "$MemModel ready (memory curator)" } + else { Write-Warn "$MemModel pull skipped/failed - the memory service will fall back to the chat model." } +} + # -- Make Ollama manual-start (NexusOS owns the lifecycle) ---------------------- Write-Step "Setting Ollama to manual start" # The Ollama desktop app autostarts a server at every login, and the elevated @@ -315,7 +326,7 @@ Write-Host " A process reads PATH once, when it starts. This shell started befo Write-Host " the installer put management\ on PATH, so it will never see ncp no" -ForegroundColor DarkGray Write-Host " matter what you run here. The next terminal you open will." -ForegroundColor DarkGray Write-Host "" -Read-Host " Press Enter to close this window (Ctrl+C works too)" +Read-Host " Press Enter to close this window" # Stop-Process on our own PID, not `exit`: `exit` only ends the window when the # host was started with -File. Run interactively - `& .\install-windows.ps1` from diff --git a/tests/test_smoke.py b/tests/test_smoke.py index cda97b9..7cf0e8d 100644 --- a/tests/test_smoke.py +++ b/tests/test_smoke.py @@ -95,6 +95,12 @@ def test_ncp_is_registered_on_path_not_in_a_shell_profile(): assert ps1.index("ollama pull") > ps1.index("Creating desktop shortcut"), \ "model pull must come after the desktop shortcut" + # And it must not TELL anyone to press Ctrl+C: in PS 5.1 that kills the + # script, so the advertised way to skip the download was also the way to + # abort the install. Skipping is a prompt now. Comments stripped so the + # comment explaining this does not trip the check. + assert "Ctrl+C" not in code, "installer must not offer Ctrl+C as a skip" + def test_no_ps1_shadows_the_ncp_path_shim(): """PowerShell resolves ExternalScript (.ps1) ahead of Application (.cmd), so