From fb32ca29de961cc91f04a67a79589333b71e0f74 Mon Sep 17 00:00:00 2001 From: ospab Date: Fri, 15 May 2026 00:55:51 +0300 Subject: [PATCH] DevOps: Overhaul Windows install.ps1 to support dynamic location preservation and smart permission-agnostic deployment mapping. --- scripts/install.ps1 | 92 +++++++++++++++++++++++++++------------------ 1 file changed, 55 insertions(+), 37 deletions(-) diff --git a/scripts/install.ps1 b/scripts/install.ps1 index f120150..737bf94 100644 --- a/scripts/install.ps1 +++ b/scripts/install.ps1 @@ -1,40 +1,61 @@ $ErrorActionPreference = "Stop" - $repo = "ospab/ostp" -$InstallDir = "C:\opt\ostp" + +# 1. Smart Installation Path Resolution +$InstallDir = "C:\opt\ostp" # Standard default fallback + +if (Test-Path "config.json") { + # If current directory already has a configuration, keep it here + $InstallDir = (Get-Item .).FullName +} elseif (Test-Path "ostp.exe") { + # If binary already exists in current working directory, use it + $InstallDir = (Get-Item .).FullName +} elseif ($cmd = Get-Command "ostp" -ErrorAction SilentlyContinue) { + # If binary is already in the system PATH, find where it lives and update it there + $InstallDir = Split-Path $cmd.Path +} Write-Host "========================================================" Write-Host " Installing Ospab Stealth Transport Protocol (OSTP)" Write-Host "========================================================" +Write-Host "Target deployment location: $InstallDir" -# 1. Verify Administrator Privileges +# 2. Check Write Access & Verify Elevation $isAdmin = ([Security.Principal.WindowsPrincipal] [Security.Principal.WindowsIdentity]::GetCurrent()).IsInRole([Security.Principal.WindowsBuiltInRole]::Administrator) -if (-not $isAdmin) { - Write-Error "This script must be run as Administrator (Run Windows PowerShell as Administrator)." - exit 1 -} -# 2. Setup Target Directory if (-not (Test-Path $InstallDir)) { - New-Item -ItemType Directory -Path $InstallDir | Out-Null + try { + New-Item -ItemType Directory -Path $InstallDir -ErrorAction Stop | Out-Null + } catch { + Write-Error "Access Denied: Cannot create target directory '$InstallDir'. Run as Administrator to proceed." + exit 1 + } +} else { + try { + $testFile = Join-Path $InstallDir "ostp_write_test_$($PID).tmp" + "test" | Set-Content $testFile -ErrorAction Stop + Remove-Item $testFile -Force + } catch { + Write-Error "Access Denied: Target directory '$InstallDir' is write-protected. Run as Administrator to proceed." + exit 1 + } } -# 3. Detect Operating System Architecture +# 3. Detect System Architecture $arch = "amd64" if ([System.Environment]::Is64BitOperatingSystem -and ($Env:PROCESSOR_ARCHITECTURE -eq "ARM64" -or $Env:PROCESSOR_ARCHITEW6432 -eq "ARM64")) { $arch = "arm64" } -# 4. Fetch Latest Asset via GitHub API +# 4. Fetch Stable Version Asset Write-Host "Fetching the latest stable version from the repository..." try { - # We set SecurityProtocol to TLS 1.2 just in case [Net.ServicePointManager]::SecurityProtocol = [Net.SecurityProtocolType]::Tls12 $api = Invoke-RestMethod -Uri "https://api.github.com/repos/$repo/releases/latest" $tag = $api.tag_name } catch { - Write-Host "[Notice] Failed to automatically retrieve the latest release tag." - $tag = Read-Host "Enter release tag version manually (e.g., v0.1.22)" + Write-Host "[Notice] Failed to automatically retrieve latest version tag." + $tag = Read-Host "Enter release version tag manually (e.g., v0.1.23)" if (-not $tag) { exit 1 } } @@ -47,7 +68,7 @@ Write-Host "Downloading asset windows-${arch}: $url ..." Invoke-WebRequest -Uri $url -OutFile $zipPath if (-not (Test-Path $zipPath)) { - Write-Error "Failed to download zip payload." + Write-Error "Failed to download zip archive." exit 1 } @@ -57,24 +78,22 @@ Expand-Archive -Path $zipPath -DestinationPath $extractPath -Force $exeFile = Get-ChildItem -Path $extractPath -Filter "*.exe" -Recurse | Select-Object -First 1 if ($exeFile) { - Write-Host "Stopping any running instances of ostp..." + Write-Host "Stopping any running instances of ostp to unlock binary..." Stop-Process -Name "ostp" -ErrorAction SilentlyContinue - - # Brief pause to let process handle unlock Start-Sleep -Seconds 1 Copy-Item -Path $exeFile.FullName -Destination (Join-Path $InstallDir "ostp.exe") -Force Write-Host "Executable successfully deployed to $(Join-Path $InstallDir 'ostp.exe')." } else { - Write-Error "Executable ostp.exe not found in extracted archive package." + Write-Error "Executable ostp.exe not found in package." exit 1 } -# Cleanup cache +# Cleanup temp cache Remove-Item $zipPath -Force Remove-Item $extractPath -Recurse -Force -# 5. Smart Auto-Updater Mode +# 5. Zero-Interactive Smart Updater $configPath = Join-Path $InstallDir "config.json" if (Test-Path $configPath) { Write-Host "--------------------------------------------------------" @@ -107,27 +126,26 @@ if ($mode -eq "1") { if (-not $keyCount) { $keyCount = 1 } if ([int]$keyCount -gt 1) { - Write-Host "Generating additional telemetry registration keys..." + Write-Host "Generating additional telemetry keys..." $keys = & .\ostp.exe -g -c $keyCount - # Split output to string array $config.access_keys = $keys -split "`r`n" | Where-Object { $_ -ne "" } } $config | ConvertTo-Json -Depth 10 | Set-Content "config.json" - Write-Host "Server deployment complete. Config file written to $(Join-Path $InstallDir 'config.json')" + Write-Host "Server deployment completed. Config file: $(Join-Path $InstallDir 'config.json')" } elseif ($mode -eq "2") { Write-Host "Initializing client configuration..." & .\ostp.exe --init client --config config.json $config = Get-Content "config.json" -Raw | ConvertFrom-Json - $server = Read-Host "Enter remote server collector address (IP:PORT)" + $server = Read-Host "Enter remote server address (IP:PORT)" if ($server) { $config.server = $server } $key = Read-Host "Enter access key (leave blank to generate automatically)" if (-not $key) { $key = & .\ostp.exe -g - Write-Host "Successfully auto-generated client access key: $key" + Write-Host "Automatically generated client access key: $key" } $config.access_key = $key.Trim() @@ -135,7 +153,7 @@ if ($mode -eq "1") { if ($socks) { $config.socks5_bind = $socks } $config | ConvertTo-Json -Depth 10 | Set-Content "config.json" - Write-Host "Client deployment complete. Config file written to $(Join-Path $InstallDir 'config.json')" + Write-Host "Client deployment completed. Config file: $(Join-Path $InstallDir 'config.json')" } else { Write-Error "Invalid configuration selection." Pop-Location @@ -144,21 +162,21 @@ if ($mode -eq "1") { Pop-Location -# 7. Inject into System PATH variables +# 7. Adaptive Environment PATH Injection Write-Host "--------------------------------------------------------" -Write-Host "Injecting deployment route into System PATH..." -$sysPath = [Environment]::GetEnvironmentVariable("Path", [EnvironmentVariableTarget]::Machine) +Write-Host "Registering binary route in Environment PATH..." +$targetScope = if ($isAdmin) { [EnvironmentVariableTarget]::Machine } else { [EnvironmentVariableTarget]::User } +$sysPath = [Environment]::GetEnvironmentVariable("Path", $targetScope) if ($sysPath -notlike "*$InstallDir*") { $newPath = "$sysPath;$InstallDir" - [Environment]::SetEnvironmentVariable("Path", $newPath, [EnvironmentVariableTarget]::Machine) - Write-Host "System PATH updated successfully." + [Environment]::SetEnvironmentVariable("Path", $newPath, $targetScope) + Write-Host "Environment PATH updated successfully ($($targetScope.ToString()) scope)." } else { - Write-Host "$InstallDir route already present in System PATH." + Write-Host "$InstallDir is already mapped in PATH." } Write-Host "--------------------------------------------------------" -Write-Host "Deployment completed successfully." -Write-Host "Deployment file cataloged at $(Join-Path $InstallDir 'config.json')" -Write-Host "OSTP binary added to global terminal paths. To test, open a new terminal and type: ostp" -Write-Host "To start active routing run: ostp --config $(Join-Path $InstallDir 'config.json')" +Write-Host "Deployment completed successfully!" +Write-Host "OSTP binary can now be run globally by typing: ostp" +Write-Host "Configuration location: $(Join-Path $InstallDir 'config.json')" Write-Host "--------------------------------------------------------"