Files
lexware-db-mirror/push-dump.ps1
T

151 lines
5.4 KiB
PowerShell

# Lexware PostgreSQL Dump -> Push nach Linux
# Laeuft als Windows Scheduled Task alle 2 Minuten
$pgDump = "C:\Program Files\Lexware\PostgreSql\17\Bin\pg_dump.exe"
$pgCtl = "C:\Program Files\Lexware\PostgreSql\17\Bin\pg_ctl.exe"
$dataDir = "C:\ProgramData\Lexware\LexwarePG\Data\current"
$hbaFile = "$dataDir\pg_hba.conf"
$dumpDir = "C:\lexware-db-connect\dumps"
$linuxHost = "root@192.168.115.113"
$linuxDir = "/opt/lexware-dumps"
$sshKey = "C:\lexware-db-connect\ssh\id_rsa"
$logFile = "C:\Users\Administrator\Desktop\LexWare-DB-Mirror.log"
$lockFile = "C:\lexware-db-connect\push-dump.lock"
$maxLines = 500
# Datenbanken die gedumpt werden sollen
$databases = @("f1", "f2", "f3", "lexkonto", "lexkk", "rk", "lxoffice", "lx", "lxcatalog")
$utf8NoBom = [System.Text.UTF8Encoding]::new($false)
function Write-Log {
param([string]$Message, [string]$Level = "INFO")
$ts = Get-Date -Format "yyyy-MM-dd HH:mm:ss"
$entry = "[$ts] [$Level] $Message`n"
[System.IO.File]::AppendAllText($logFile, $entry, $utf8NoBom)
# Log auf 500 Zeilen begrenzen
$content = [System.IO.File]::ReadAllLines($logFile)
if ($content.Count -gt $maxLines) {
$trimmed = $content | Select-Object -Last $maxLines
[System.IO.File]::WriteAllLines($logFile, $trimmed, $utf8NoBom)
}
}
# --- 0. Doppelausfuehrung verhindern ---
if (Test-Path $lockFile) {
$lockAge = (Get-Date) - (Get-Item $lockFile).LastWriteTime
if ($lockAge.TotalMinutes -lt 10) {
exit 0
}
Remove-Item $lockFile -Force
}
New-Item -ItemType File -Path $lockFile -Force | Out-Null
try {
# --- 1. Dumpverzeichnis anlegen ---
New-Item -ItemType Directory -Force -Path $dumpDir | Out-Null
$timestamp = Get-Date -Format "yyyy-MM-dd_HH-mm"
$stopwatch = [System.Diagnostics.Stopwatch]::StartNew()
Write-Log "===== Sync-Lauf gestartet ($timestamp) =====" "INFO"
# --- 2. Trust-Regel fuer lxdump hinzufuegen (wird am Ende wieder entfernt) ---
$trustRule = "host all lxdump 127.0.0.1/32 trust"
$lines = Get-Content $hbaFile
if ($lines -notmatch "lxdump") {
$newLines = [System.Collections.Generic.List[string]]::new()
$inserted = $false
foreach ($line in $lines) {
if (-not $inserted -and $line -match "127\.0\.0\.1/32") {
$newLines.Add($trustRule)
$inserted = $true
}
$newLines.Add($line)
}
[System.IO.File]::WriteAllLines($hbaFile, $newLines, [System.Text.Encoding]::ASCII)
& $pgCtl reload -D $dataDir 2>&1 | Out-Null
Start-Sleep -Seconds 2
}
# --- 3. lxdump User anlegen falls nicht vorhanden ---
$env:PGSSLMODE = "disable"
$env:PGPASSWORD = ""
$env:PGCLIENTENCODING = "LATIN1"
$sql = @'
DO $$
BEGIN
IF NOT EXISTS (SELECT 1 FROM pg_roles WHERE rolname = 'lxdump') THEN
CREATE USER lxdump WITH SUPERUSER LOGIN;
END IF;
END
$$;
'@
& "C:\Program Files\Lexware\PostgreSql\17\Bin\psql.exe" -h 127.0.0.1 -p 15432 -U altertillattbruker -d postgres -c $sql 2>&1 | Out-Null
# --- 4. Dumps erstellen und nach Linux pushen ---
$errors = @()
$okCount = 0
foreach ($db in $databases) {
$dumpFile = "$dumpDir\${db}_${timestamp}.dump"
& $pgDump -h 127.0.0.1 -p 15432 -U lxdump -d $db -Fc -f $dumpFile 2>&1 | Out-Null
if ($LASTEXITCODE -ne 0) {
Write-Log " $db -> DUMP FEHLGESCHLAGEN" "ERROR"
$errors += $db
continue
}
$dumpSize = if (Test-Path $dumpFile) { "{0:N1} MB" -f ((Get-Item $dumpFile).Length / 1MB) } else { "?" }
& scp -i $sshKey -o StrictHostKeyChecking=no $dumpFile "${linuxHost}:${linuxDir}/${db}_${timestamp}.dump" 2>&1 | Out-Null
if ($LASTEXITCODE -eq 0) {
try {
Invoke-WebRequest -Uri "http://192.168.115.113:9055/restore?db=$db" -Method POST -UseBasicParsing -TimeoutSec 5 | Out-Null
} catch {}
Write-Log " $db -> OK ($dumpSize)" "INFO"
$okCount++
} else {
Write-Log " $db -> SCP FEHLGESCHLAGEN ($dumpSize)" "ERROR"
$errors += $db
}
Remove-Item $dumpFile -Force
}
# --- 5. Trust-Regel wieder entfernen ---
$lines = Get-Content $hbaFile | Where-Object { $_ -notmatch "lxdump" }
[System.IO.File]::WriteAllLines($hbaFile, $lines, [System.Text.Encoding]::ASCII)
& $pgCtl reload -D $dataDir 2>&1 | Out-Null
# --- 6. Alte Dumps auf Linux aufraemen (nur letzte 5 pro DB behalten) ---
& ssh -i $sshKey -o StrictHostKeyChecking=no root@192.168.115.113 @"
for db in f1 f2 f3 lexkonto lexkk rk lxoffice lx lxcatalog; do
ls -t /opt/lexware-dumps/\${db}_*.dump 2>/dev/null | tail -n +6 | xargs -r rm -f
done
"@ 2>&1 | Out-Null
# --- 7. Zusammenfassung loggen ---
$stopwatch.Stop()
$elapsed = "{0:mm\:ss}" -f $stopwatch.Elapsed
if ($errors.Count -gt 0) {
Write-Log " Ergebnis: $okCount/$($databases.Count) OK | Fehler: $($errors -join ', ') | Dauer: $elapsed" "WARN"
Write-Log "===== Sync-Lauf beendet =====" "INFO"
} else {
Write-Log " Ergebnis: $okCount/$($databases.Count) OK | Alle synchronisiert | Dauer: $elapsed" "INFO"
Write-Log "===== Sync-Lauf beendet =====" "INFO"
}
} finally {
# Trust-Regel sicher entfernen (auch bei Absturz)
$lines = Get-Content $hbaFile -ErrorAction SilentlyContinue | Where-Object { $_ -notmatch "lxdump" }
if ($lines) {
[System.IO.File]::WriteAllLines($hbaFile, $lines, [System.Text.Encoding]::ASCII)
& $pgCtl reload -D $dataDir 2>&1 | Out-Null
}
Remove-Item $lockFile -Force -ErrorAction SilentlyContinue
}