#requires -Version 5.1 #requires -RunAsAdministrator [CmdletBinding()] param( [string]$InstallRoot='C:\Existco\Setup', [string]$LogPath='C:\Existco\Setup\Existco.ExPCS.Online.Installer.log' ) Set-StrictMode -Version Latest $ErrorActionPreference='Stop'; $ProgressPreference='SilentlyContinue' [Net.ServicePointManager]::SecurityProtocol=[Net.SecurityProtocolType]::Tls12 # Id|Name|Relative folder|File|URL path below updates.existco.com.au|Type|Silent arguments $data=@' PCS|Existco Plant Control System|PCS SMS V2|PlantControlSystemSetup.exe|AdvanceInstaller/PCS%20SMS/PlantControlSystemSetup.exe|Exe|/qn /norestart SMS|Existco Sales Management System|PCS SMS V2|SalesManagementSystemSetup.exe|AdvanceInstaller/PCS%20SMS/SalesManagementSystemSetup.exe|Exe|/qn /norestart PCSManager|Existco Plant Control System Manager|PCS Manager|PlantControlSystemManager.msi|AdvanceInstaller/PCS%20Manager/PlantControlSystemManager.msi|Msi|/QB ExLabel|Existco ExLabel|ExLabel|Existco.ExLabel.Setup.exe|AdvanceInstaller/ExLabel/Existco.ExLabel.Setup.exe|Exe|/qn /norestart VC2010x86|Microsoft Visual C++ 2010 32 Bit|Microsoft Visual C++ Runtime\2010|vcredist_x86.exe|Microsoft%20Visual%20C%20Runtime/2010/vcredist_x86.exe|Exe|/q /norestart VC2010x64|Microsoft Visual C++ 2010 64 Bit|Microsoft Visual C++ Runtime\2010|vcredist_x64.exe|Microsoft%20Visual%20C%20Runtime/2010/vcredist_x64.exe|Exe|/q /norestart VC2012x86|Microsoft Visual C++ 2012 32 Bit|Microsoft Visual C++ Runtime\2012|vcredist_x86.exe|Microsoft%20Visual%20C%20Runtime/2012/vcredist_x86.exe|Exe|/q /norestart VC2012x64|Microsoft Visual C++ 2012 64 Bit|Microsoft Visual C++ Runtime\2012|vcredist_x64.exe|Microsoft%20Visual%20C%20Runtime/2012/vcredist_x64.exe|Exe|/q /norestart VC2015to2022x86|Microsoft Visual C++ 2015-2022 32 Bit|Microsoft Visual C++ Runtime\2015-2022|VC_redist.x86.exe|Microsoft%20Visual%20C%20Runtime/2015-2022/VC_redist.x86.exe|Exe|/q /norestart VC2015to2022x64|Microsoft Visual C++ 2015-2022 64 Bit|Microsoft Visual C++ Runtime\2015-2022|VC_redist.x64.exe|Microsoft%20Visual%20C%20Runtime/2015-2022/VC_redist.x64.exe|Exe|/q /norestart Crystal13x86|SAP Crystal Reports V13 32 Bit|CrystalReports\V13|CRRuntime_32bit_13_0_24.msi|CrystalReports/V13/CRRuntime_32bit_13_0_24.msi|Msi|/QB Crystal13x64|SAP Crystal Reports V13 64 Bit|CrystalReports\V13|CRRuntime_64bit_13_0_24.msi|CrystalReports/V13/CRRuntime_64bit_13_0_24.msi|Msi|/QB TreeSize|TreeSize Free|TreeSize|TreeSizeFreeSetup.exe|TreeSize/TreeSizeFreeSetup.exe|Exe|/VERYSILENT NotepadPlusPlus|Notepad++|Editors\Notepad++|npp.Installer.x64.exe|Editors/NotepadPlusPlus/npp.Installer.x64.exe|Exe|/S WinRAR|WinRAR|WinRAR|winrar-x64.exe|WinRAR/winrar-x64.exe|Exe|/S OnlineSupport|Existco Online Support|Existco Online Support|Existco.Online.Support.msi|Existco.Online.Support/Existco.Online.Support.msi|Msi|/QB '@ $catalog=@($data.Trim() -split "`r?`n" | ForEach-Object { $p=$_ -split '\|',7 [pscustomobject]@{Id=$p[0];Name=$p[1];Folder=$p[2];File=$p[3];Url='https://updates.existco.com.au/'+$p[4];Type=$p[5];Args=$p[6]} }) function Write-Log([string]$Message,[ValidateSet('INFO','WARN','ERROR','SUCCESS')][string]$Level='INFO'){ $line='{0:yyyy-MM-dd HH:mm:ss} [{1}] {2}' -f (Get-Date),$Level,$Message Write-Host $line -ForegroundColor (@{INFO='Cyan';WARN='Yellow';ERROR='Red';SUCCESS='Green'}[$Level]) $d=Split-Path -Parent $LogPath; if($d -and !(Test-Path -LiteralPath $d)){New-Item -ItemType Directory -Path $d -Force|Out-Null}; Add-Content -LiteralPath $LogPath -Value $line } function Save-RemoteFile([string]$Uri,[string]$Destination){ $d=Split-Path -Parent $Destination; if(!(Test-Path -LiteralPath $d)){New-Item -ItemType Directory -Path $d -Force|Out-Null} if(Test-Path -LiteralPath $Destination){Remove-Item -LiteralPath $Destination -Force} Write-Log "Downloading $Uri"; Invoke-WebRequest -Uri $Uri -OutFile $Destination -UseBasicParsing if(!(Test-Path -LiteralPath $Destination) -or (Get-Item -LiteralPath $Destination).Length -eq 0){throw "Empty or missing download: $Destination"} Write-Log "Downloaded: $Destination" SUCCESS } function Install-Component($Item){ $folder=Join-Path $InstallRoot $Item.Folder; $file=Join-Path $folder $Item.File Write-Log "Processing: $($Item.Name)"; Save-RemoteFile $Item.Url $file if($Item.Id -eq 'WinRAR'){Save-RemoteFile 'https://updates.existco.com.au/WinRAR/rarkey.rar' (Join-Path $folder 'rarkey.rar')} if($Item.Type -eq 'Download'){Write-Log "Downloaded reference file: $($Item.Name)" SUCCESS;return} if($Item.Type -eq 'Msi'){$p=Start-Process msiexec.exe -ArgumentList "/i `"$file`" $($Item.Args) /norestart" -Wait -PassThru} else{$p=Start-Process -FilePath $file -ArgumentList $Item.Args -Wait -PassThru} if($p.ExitCode -notin 0,1641,3010){throw "Installer failed for $($Item.Name). Exit code: $($p.ExitCode)"} Write-Log "Installed: $($Item.Name). Exit code: $($p.ExitCode)" SUCCESS } try{ if(!(Test-Path -LiteralPath $InstallRoot)){New-Item -ItemType Directory -Path $InstallRoot -Force|Out-Null} $selected=$catalog Write-Log 'Existco ExPCS fully unattended installation started.' Write-Log "Installing all $($selected.Count) catalog components and downloading all reference files." $failed=@() foreach($item in $selected){try{Install-Component $item}catch{$failed+=$item.Id;Write-Log $_.Exception.Message ERROR}} if($failed){throw "Completed with failures: $($failed -join ', '). See $LogPath"};Write-Log 'All components completed successfully.' SUCCESS;exit 0 }catch{Write-Log $_.Exception.Message ERROR;exit 1}