Files
Deploymentcenter/scripts/installer/install.ps1
T
Deploymentcenter Bot 087f4392a9 feat: UpdateAgent Selbstaktualisierung & kopflose Installation, .NET 10 Migration, Backend- & SDK-Fixes
- .NET 10 Migration: Alle .NET-Projekte auf net10.0 umgestellt (#459)
- Client-SDK: ResolveAgentPath bereinigt und DLL-Pruefung ergaenzt (#458)
- Packager: Commit-Ermittlung aus publishDir / Assembly InformationalVersion (#456)
- BuildInfo.targets: ExitCode-Abfang und Regex-Validierung gegen Git-Fehlertexte (#363)
- UpdateService: Re-Publish erhaelt bestehende Manifeste und Werte (#457)
- Bugtracker API: on_roadmap-Filter in manage?action=list durchgereicht (#349)
- Watchdog API: project_slug-Filter in GET /status ergaenzt (#420)
- UpdateService API: no_release_for_platform mit verfuegbaren Plattformen (#421)
- Bugtracker Core: Fehler-Normalisierung gegen zersplitterte error_hashes (#419)
- UpdateAgent: Kopfloser Installationsmodus via --answers (#89)
- Installer & Agent: Automatische Selbstaktualisierung beim Start
- Tooling: AGENTS.md, CLAUDE.md und Standalone-CLI scripts/dc.py hinzugefuegt
2026-09-02 23:43:37 +02:00

136 lines
5.0 KiB
PowerShell

<#
Holt den Deploymentcenter Update-Agent und legt ihn ausfuehrbar ab.
irm https://dc.mhdf.de/installer/install.ps1 | iex
Das Skript fuehrt die Installation NICHT selbst aus. Es laedt das Binary,
prueft die Pruefsumme und sagt, wie es weitergeht - was danach passiert,
entscheidet der Mensch davor. Ein Skript aus dem Netz, das ungefragt eine
Anwendung einrichtet und dabei nach Zugangsdaten fragt, waere genau das
Muster, vor dem man Nutzer sonst warnt.
#>
param(
[switch] $Check,
[switch] $Force
)
$ErrorActionPreference = 'Stop'
$baseUrl = if ($env:DC_BASE_URL) { $env:DC_BASE_URL.TrimEnd('/') } else { 'https://dc.mhdf.de' }
$targetDir = if ($env:DC_INSTALL_DIR) { $env:DC_INSTALL_DIR } else { $PWD.Path }
function Get-WebContentString([string] $uri, [int] $timeoutSec = 10) {
$resp = Invoke-WebRequest -Uri $uri -UseBasicParsing -TimeoutSec $timeoutSec
if ($resp.Content -is [byte[]]) {
return [System.Text.Encoding]::UTF8.GetString($resp.Content)
}
return [string]$resp.Content
}
# --------------------------------------------------- Selbstaktualisierung Skript
# Falls das Skript als Datei von der Festplatte ausgefuehrt wird, prueft es
# sich selbst gegen die Server-Fassung und aktualisiert sich.
$scriptPath = $MyInvocation.MyCommand.Path
if ($scriptPath -and (Test-Path $scriptPath)) {
try {
$remoteScript = Get-WebContentString "$baseUrl/installer/install.ps1" 5
if ($remoteScript) {
$currentScript = Get-Content -Path $scriptPath -Raw
if ($remoteScript.Trim() -ne $currentScript.Trim()) {
Set-Content -Path $scriptPath -Value $remoteScript -Force
Write-Host "Installer-Skript ($scriptPath) wurde selbststaendig aktualisiert." -ForegroundColor Cyan
}
}
} catch { }
}
# ------------------------------------------------------------------ Plattform
$arch = [System.Runtime.InteropServices.RuntimeInformation]::ProcessArchitecture
switch ($arch) {
'X64' { $rid = 'win-x64' }
default {
Write-Error "Nicht unterstuetzte Architektur: $arch. Verfuegbar ist derzeit win-x64."
return
}
}
$binary = "update-agent-$rid.exe"
$target = Join-Path $targetDir 'update-agent.exe'
# --------------------------------------------------------- Versionsabgleich
try {
$rawExpected = Get-WebContentString "$baseUrl/installer/$binary.sha256" 10
$expected = $rawExpected.Trim().ToLower()
} catch {
Write-Error "Konnte Pruefsumme von $baseUrl/installer/$binary.sha256 nicht abrufen: $_"
return
}
if ((Test-Path $target) -and -not $Force) {
$currentHash = (Get-FileHash $target -Algorithm SHA256).Hash.ToLower()
if ($currentHash -eq $expected) {
Write-Host "Update-Agent ist bereits auf dem neuesten Stand ($target)." -ForegroundColor Green
if ($Check) { return }
Write-Host ''
Write-Host 'Weiter mit:'
Write-Host " & '$target' --action install"
Write-Host ''
Write-Host 'Nur diese Maschine ueberwachen, ohne etwas zu installieren:'
Write-Host " & '$target' --action monitor"
return
} else {
Write-Host "Aktualisierung fuer Update-Agent verfuegbar. Lade neue Fassung..." -ForegroundColor Cyan
}
}
if ($Check) {
Write-Host "Neue Version von $binary ist verfuegbar (SHA256: $expected)."
return
}
$temp = Join-Path ([System.IO.Path]::GetTempPath()) ("dc-installer-" + [guid]::NewGuid().ToString('N'))
New-Item -ItemType Directory -Path $temp -Force | Out-Null
try {
Write-Host "Lade $binary von $baseUrl ..."
$tempBinary = Join-Path $temp 'agent.exe'
Invoke-WebRequest -Uri "$baseUrl/installer/$binary" -OutFile $tempBinary -UseBasicParsing
# --------------------------------------------------------- Pruefsumme
$actual = (Get-FileHash $tempBinary -Algorithm SHA256).Hash.ToLower()
if ($actual -ne $expected) {
Write-Error "ABBRUCH: Pruefsumme stimmt nicht ueberein.`n erwartet: $expected`n erhalten: $actual"
return
}
Write-Host 'Pruefsumme in Ordnung.'
# ------------------------------------------------------------ Ablegen
Move-Item -Path $tempBinary -Destination $target -Force
# Von Windows als "aus dem Internet" markierte Dateien loesen beim Start
# eine Sicherheitswarnung aus. Die Herkunft ist hier durch die gepruefte
# Pruefsumme belegt.
try { Unblock-File -Path $target -ErrorAction SilentlyContinue } catch { }
Write-Host ''
Write-Host "Abgelegt: $target"
Write-Host ''
Write-Host 'Weiter mit:'
Write-Host " & '$target' --action install"
Write-Host ''
Write-Host 'Nur diese Maschine ueberwachen, ohne etwas zu installieren:'
Write-Host " & '$target' --action monitor"
Write-Host ''
Write-Host "Dafuer werden Benutzername und Passwort eines Kontos der Rolle 'installer'"
Write-Host 'gebraucht. Ein Administratorkonto tut es auch, gehoert aber nicht auf ein'
Write-Host 'Zielsystem.'
}
finally {
Remove-Item -Recurse -Force $temp -ErrorAction SilentlyContinue
}