1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
|
# Stop every MeshBay node on this machine before setup touches its files, or
# before the uninstaller removes them. Embedded in the installer and run from
# its plugins directory: the installed copy of anything may be the one being
# replaced.
#
# 1. Ask the node through its own control API (/api/shutdown, loopback, per-run
# token): the only stop that reaches a node in any session with no
# elevation, and the one that lets it shut down properly -- WebRTC sessions
# closed, transcodes stopped.
# 2. Task Scheduler for a background-service node (the owner may end the task;
# taskkill from here gets "Access is denied" in its session).
# 3. taskkill for anything left in this session.
#
# Before all that, the command-line client (-InstallDir, setup's $INSTDIR): it
# runs from the same node-runtime folder and holds its Python DLLs, so one left
# open -- a `chat --follow`, a `stream` -- made the previous version's
# uninstaller fail ("Failed to uninstall old application files"), silent
# updates included. It is ended like the app is; only copies of this install.
# Exit 0 once neither is left, 1 otherwise.
param([string]$InstallDir = "")
$ErrorActionPreference = "SilentlyContinue"
if ($InstallDir) {
$runtime = Join-Path $InstallDir "resources\node-runtime\"
# Through CIM, not Get-Process: setup runs the 32-bit PowerShell ($SYSDIR is
# SysWOW64 there), which reads no path for a 64-bit process -- the filter
# matched nothing and the update failed as before.
function CliLeft {
@(Get-CimInstance Win32_Process -Filter "Name='meshbay-cli.exe'" `
-ErrorAction SilentlyContinue | Where-Object {
$_.ExecutablePath -and
$_.ExecutablePath.StartsWith($runtime, [StringComparison]::OrdinalIgnoreCase)
})
}
CliLeft | ForEach-Object { Stop-Process -Id $_.ProcessId -Force -ErrorAction SilentlyContinue }
$deadline = (Get-Date).AddSeconds(10)
while ((CliLeft).Count -and (Get-Date) -lt $deadline) { Start-Sleep -Milliseconds 250 }
if ((CliLeft).Count) { exit 1 }
}
function NodeLeft { [bool](Get-Process -Name meshbay-node -ErrorAction SilentlyContinue) }
function WaitGone([int]$Seconds) {
$deadline = (Get-Date).AddSeconds($Seconds)
while ((NodeLeft) -and (Get-Date) -lt $deadline) { Start-Sleep -Milliseconds 250 }
-not (NodeLeft)
}
if (-not (NodeLeft)) { exit 0 }
$cfg = Join-Path $env:LOCALAPPDATA "meshbay"
$port = 18000
$toml = Join-Path $cfg "node.toml"
if (Test-Path $toml) {
$m = Select-String -Path $toml -Pattern '^\s*ui_port\s*=\s*(\d+)' | Select-Object -First 1
if ($m) { $port = [int]$m.Matches[0].Groups[1].Value }
}
$tokenFile = Join-Path $cfg "data\ui-token"
if (Test-Path $tokenFile) {
$token = (Get-Content $tokenFile -Raw).Trim()
try {
Invoke-WebRequest -UseBasicParsing -Method Post -TimeoutSec 5 `
-Uri "http://127.0.0.1:$port/api/shutdown?t=$token" | Out-Null
if (WaitGone 20) { exit 0 }
} catch { }
}
& schtasks /end /tn "MeshBay Node" 2>&1 | Out-Null
Get-Process -Name meshbay-node -ErrorAction SilentlyContinue | Stop-Process -Force -ErrorAction SilentlyContinue
if (WaitGone 20) { exit 0 }
exit 1
|