<# Deploy-RustDesk-TSK.ps1 Installs the official RustDesk client and preconfigures it for TSK Invent's self-hosted server (rustdesk.tskinvent.com), with an unattended password. Run from an ELEVATED PowerShell. .\Deploy-RustDesk-TSK.ps1 # generates + prints a random unattended password .\Deploy-RustDesk-TSK.ps1 -Password 'xxx' # sets a specific unattended password #> param([string]$Password) $ErrorActionPreference = 'Stop' $Server = 'rustdesk.tskinvent.com' $Relay = 'rustdesk.tskinvent.com' $Api = 'https://rustdesk.tskinvent.com' $Key = 'NGUXLfha0FWVGH79qWE2itTsifuyjC0MwKtFNvPtYJo=' function Get-RustDeskId([string]$Rd) { # RustDesk.exe is a GUI app — capture --get-id via a redirected process (with timeout). $out = Join-Path $env:TEMP ("rdid_{0}.txt" -f ([guid]::NewGuid().ToString('N'))) $id = '' try { $p = Start-Process -FilePath $Rd -ArgumentList '--get-id' -RedirectStandardOutput $out -WindowStyle Hidden -PassThru if (-not $p.WaitForExit(8000)) { try { $p.Kill() } catch {} } Start-Sleep -Milliseconds 250 if (Test-Path $out) { $m = [regex]::Match(((Get-Content $out -Raw) -as [string]), '\d{6,}') if ($m.Success) { $id = $m.Value } } } catch {} finally { Remove-Item $out -Force -ErrorAction SilentlyContinue } return $id } if (-not ([Security.Principal.WindowsPrincipal] [Security.Principal.WindowsIdentity]::GetCurrent() ).IsInRole([Security.Principal.WindowsBuiltInRole]::Administrator)) { Write-Warning 'Please run this script from an elevated (Run as administrator) PowerShell.' return } if (-not $Password) { $Password = -join ((48..57) + (65..90) + (97..122) | Get-Random -Count 14 | ForEach-Object { [char]$_ }) Write-Host "==> Generated unattended password: $Password" -ForegroundColor Yellow } $toml = @" [options] custom-rendezvous-server = '$Server' relay-server = '$Relay' api-server = '$Api' key = '$Key' "@ # 1) Download the latest official RustDesk (x86_64) Write-Host '==> Locating latest RustDesk release...' $rel = Invoke-RestMethod 'https://api.github.com/repos/rustdesk/rustdesk/releases/latest' -Headers @{ 'User-Agent' = 'tsk-deploy' } $asset = $rel.assets | Where-Object { $_.name -match 'x86_64\.exe$' -and $_.name -notmatch 'aarch64' } | Select-Object -First 1 if (-not $asset) { throw 'Could not find a Windows x86_64 RustDesk asset.' } $exe = Join-Path $env:TEMP $asset.name Write-Host "==> Downloading $($asset.name)..." Invoke-WebRequest $asset.browser_download_url -OutFile $exe # 2) Silent install Write-Host '==> Installing (silent)...' Start-Process -FilePath $exe -ArgumentList '--silent-install' -Wait Start-Sleep -Seconds 5 $rd = Join-Path $env:ProgramFiles 'RustDesk\RustDesk.exe' # 3) Pre-seed config into the admin-only service profile + current user $paths = @( (Join-Path $env:WINDIR 'ServiceProfiles\LocalService\AppData\Roaming\RustDesk\config\RustDesk2.toml'), (Join-Path $env:APPDATA 'RustDesk\config\RustDesk2.toml') ) foreach ($p in $paths) { New-Item -ItemType Directory -Force -Path (Split-Path $p) | Out-Null $toml | Set-Content -Path $p -Encoding UTF8 Write-Host "==> Wrote $p" } Restart-Service -Name RustDesk -ErrorAction SilentlyContinue Start-Sleep -Seconds 3 # 4) Set the unattended (permanent) password if (Test-Path $rd) { Start-Process -FilePath $rd -ArgumentList "--password `"$Password`"" -Wait Write-Host '==> Unattended password set.' } # 5) Report this device's RustDesk ID $id = '' if (Test-Path $rd) { $id = Get-RustDeskId $rd } # 5b) Self-enroll computer name / OS / user with the console (matched by MachineGuid) try { $os = (Get-CimInstance Win32_OperatingSystem -ErrorAction SilentlyContinue).Caption if (-not $os) { $os = [System.Environment]::OSVersion.VersionString } $uuid = '' try { $uuid = (Get-ItemProperty 'HKLM:\SOFTWARE\Microsoft\Cryptography' -Name MachineGuid -ErrorAction Stop).MachineGuid } catch {} $body = @{ id = $id; uuid = $uuid; hostname = $env:COMPUTERNAME; user = $env:USERNAME; os = "$os".Trim() } | ConvertTo-Json -Compress $r = Invoke-RestMethod -Uri "https://$Server/api/enroll" -Method Post -ContentType 'application/json' -Body $body -TimeoutSec 15 Write-Host "==> Enrolled '$env:COMPUTERNAME' (ID $($r.id)) with the console." } catch { Write-Host "==> Enrollment skipped: $($_.Exception.Message)" -ForegroundColor DarkYellow } Write-Host '' Write-Host '==================== TSK Invent RustDesk ====================' -ForegroundColor Green Write-Host " Device ID : $id" Write-Host " Password : $Password" Write-Host " Server : $Server" Write-Host ' Record the ID + password for unattended access.' Write-Host '============================================================='