Wax/Trace triad: harden against empty $PSScriptRoot
Tech ran Export-FormtracepakInventory.ps1 from S:\DT\shopfloor\scripts\ waxandtrace\ and the picker fired correctly but Export-Csv failed with 'Cannot bind argument to parameter Path because it is an empty string'. Root cause: $OutputPath defaulted to $PSScriptRoot and $PSScriptRoot came through empty in that invocation path (suspected ISE / IEX-style host or remote wrapper). On a [string] param, $null/empty default coerces to '' and Join-Path then errors. Fix in all three triad scripts: resolve a local $scriptDir via a fallback chain ($PSScriptRoot -> $PSCommandPath -> Get-Location), and use that instead of $PSScriptRoot for sibling lookups (Select-WaxtraceAsset.ps1, bay-config.csv). Export additionally: - Drops the $OutputPath = $PSScriptRoot param default in favor of the same fallback chain. - Tests / creates $OutputPath BEFORE the 90k-item registry scan so a bad output dir surfaces immediately instead of after a long scan. Smoke tested on win11 VM: explicit -OutputPath '' now resolves to a writable directory and the CSV writes successfully.
This commit is contained in:
@@ -47,6 +47,13 @@ param(
|
|||||||
|
|
||||||
$SharedRoot = 'S:\2 WJ Scans Record Retention\backup\waxtrace'
|
$SharedRoot = 'S:\2 WJ Scans Record Retention\backup\waxtrace'
|
||||||
|
|
||||||
|
# Resolve the script's own directory robustly. $PSScriptRoot can come through
|
||||||
|
# empty in some hosts (IEX / dot-source / certain remote wrappers), which
|
||||||
|
# would silently skip the picker invocation below.
|
||||||
|
$scriptDir = if ($PSScriptRoot) { $PSScriptRoot } `
|
||||||
|
elseif ($PSCommandPath) { Split-Path -Parent $PSCommandPath } `
|
||||||
|
else { (Get-Location).Path }
|
||||||
|
|
||||||
if (-not $Destination) {
|
if (-not $Destination) {
|
||||||
if (-not $AssetNumber) {
|
if (-not $AssetNumber) {
|
||||||
$defaultAsset = $env:COMPUTERNAME
|
$defaultAsset = $env:COMPUTERNAME
|
||||||
@@ -54,8 +61,8 @@ if (-not $Destination) {
|
|||||||
# Prefer arrow-key picker against bay-config.csv if it is sitting
|
# Prefer arrow-key picker against bay-config.csv if it is sitting
|
||||||
# next to this script. Falls through to a plain Read-Host prompt
|
# next to this script. Falls through to a plain Read-Host prompt
|
||||||
# if no picker / no CSV available.
|
# if no picker / no CSV available.
|
||||||
$picker = Join-Path $PSScriptRoot 'Select-WaxtraceAsset.ps1'
|
$picker = Join-Path $scriptDir 'Select-WaxtraceAsset.ps1'
|
||||||
$cfg = Join-Path $PSScriptRoot 'bay-config.csv'
|
$cfg = Join-Path $scriptDir 'bay-config.csv'
|
||||||
if ((Test-Path -LiteralPath $picker) -and (Test-Path -LiteralPath $cfg)) {
|
if ((Test-Path -LiteralPath $picker) -and (Test-Path -LiteralPath $cfg)) {
|
||||||
$picked = & $picker -ConfigCsv $cfg -Title 'Backup FormTracePak - pick the bay being captured'
|
$picked = & $picker -ConfigCsv $cfg -Title 'Backup FormTracePak - pick the bay being captured'
|
||||||
if ($picked) {
|
if ($picked) {
|
||||||
|
|||||||
@@ -27,15 +27,35 @@
|
|||||||
#>
|
#>
|
||||||
[CmdletBinding()]
|
[CmdletBinding()]
|
||||||
param(
|
param(
|
||||||
[string]$OutputPath = $PSScriptRoot,
|
[string]$OutputPath,
|
||||||
[string]$ComputerName = $env:COMPUTERNAME,
|
[string]$ComputerName = $env:COMPUTERNAME,
|
||||||
[string]$AssetNumber
|
[string]$AssetNumber
|
||||||
)
|
)
|
||||||
|
|
||||||
|
# $PSScriptRoot can come through empty in some PowerShell hosts (e.g. when
|
||||||
|
# the script is invoked via IEX, dot-sourced, or run through certain remote
|
||||||
|
# wrappers). The param default = $PSScriptRoot then coerces to '' on a [string]
|
||||||
|
# parameter and Join-Path later fails with "Cannot bind argument to parameter
|
||||||
|
# 'Path' because it is an empty string". Resolve $OutputPath lazily with a
|
||||||
|
# fallback chain so the script always lands on a writable directory.
|
||||||
|
if (-not $OutputPath) {
|
||||||
|
if ($PSScriptRoot) {
|
||||||
|
$OutputPath = $PSScriptRoot
|
||||||
|
} elseif ($PSCommandPath) {
|
||||||
|
$OutputPath = Split-Path -Parent $PSCommandPath
|
||||||
|
} else {
|
||||||
|
$OutputPath = (Get-Location).Path
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
$scriptDir = if ($PSScriptRoot) { $PSScriptRoot } `
|
||||||
|
elseif ($PSCommandPath) { Split-Path -Parent $PSCommandPath } `
|
||||||
|
else { (Get-Location).Path }
|
||||||
|
|
||||||
if (-not $AssetNumber) {
|
if (-not $AssetNumber) {
|
||||||
if ([Environment]::UserInteractive -and -not [Console]::IsInputRedirected) {
|
if ([Environment]::UserInteractive -and -not [Console]::IsInputRedirected) {
|
||||||
$picker = Join-Path $PSScriptRoot 'Select-WaxtraceAsset.ps1'
|
$picker = Join-Path $scriptDir 'Select-WaxtraceAsset.ps1'
|
||||||
$cfg = Join-Path $PSScriptRoot 'bay-config.csv'
|
$cfg = Join-Path $scriptDir 'bay-config.csv'
|
||||||
if ((Test-Path -LiteralPath $picker) -and (Test-Path -LiteralPath $cfg)) {
|
if ((Test-Path -LiteralPath $picker) -and (Test-Path -LiteralPath $cfg)) {
|
||||||
$picked = & $picker -ConfigCsv $cfg -Title 'Inventory FormTracePak - pick the bay being audited'
|
$picked = & $picker -ConfigCsv $cfg -Title 'Inventory FormTracePak - pick the bay being audited'
|
||||||
if ($picked) {
|
if ($picked) {
|
||||||
@@ -128,7 +148,19 @@ $MitutoyoFileExtensions = @(
|
|||||||
# ----------------------------------------------------------------------
|
# ----------------------------------------------------------------------
|
||||||
|
|
||||||
$timestamp = Get-Date -Format 'yyyyMMdd_HHmmss'
|
$timestamp = Get-Date -Format 'yyyyMMdd_HHmmss'
|
||||||
$csvFile = Join-Path $OutputPath "formtracepak_inventory_${AssetNumber}_${ComputerName}_${timestamp}.csv"
|
|
||||||
|
# Ensure $OutputPath exists / is creatable BEFORE doing the slow scan, so
|
||||||
|
# the operator does not sit through a 90k-item registry walk only to have
|
||||||
|
# the final Export-Csv fail.
|
||||||
|
if (-not (Test-Path -LiteralPath $OutputPath)) {
|
||||||
|
try {
|
||||||
|
New-Item -ItemType Directory -Path $OutputPath -Force -ErrorAction Stop | Out-Null
|
||||||
|
} catch {
|
||||||
|
Write-Error "OutputPath '$OutputPath' does not exist and cannot be created: $_"
|
||||||
|
exit 1
|
||||||
|
}
|
||||||
|
}
|
||||||
|
$csvFile = Join-Path $OutputPath "formtracepak_inventory_${AssetNumber}_${ComputerName}_${timestamp}.csv"
|
||||||
$inventory = [System.Collections.Generic.List[PSObject]]::new()
|
$inventory = [System.Collections.Generic.List[PSObject]]::new()
|
||||||
|
|
||||||
function Add-Item {
|
function Add-Item {
|
||||||
|
|||||||
@@ -62,13 +62,20 @@ param(
|
|||||||
|
|
||||||
$SharedRoot = 'S:\2 WJ Scans Record Retention\backup\waxtrace'
|
$SharedRoot = 'S:\2 WJ Scans Record Retention\backup\waxtrace'
|
||||||
|
|
||||||
|
# Resolve the script's own directory robustly. $PSScriptRoot can come through
|
||||||
|
# empty in some hosts (IEX / dot-source / certain remote wrappers), which
|
||||||
|
# would silently skip the picker invocation below.
|
||||||
|
$scriptDir = if ($PSScriptRoot) { $PSScriptRoot } `
|
||||||
|
elseif ($PSCommandPath) { Split-Path -Parent $PSCommandPath } `
|
||||||
|
else { (Get-Location).Path }
|
||||||
|
|
||||||
if (-not $BackupPath) {
|
if (-not $BackupPath) {
|
||||||
if (-not $AssetNumber) {
|
if (-not $AssetNumber) {
|
||||||
$defaultAsset = $env:COMPUTERNAME
|
$defaultAsset = $env:COMPUTERNAME
|
||||||
if ([Environment]::UserInteractive -and -not [Console]::IsInputRedirected) {
|
if ([Environment]::UserInteractive -and -not [Console]::IsInputRedirected) {
|
||||||
# Prefer arrow-key picker against bay-config.csv if available.
|
# Prefer arrow-key picker against bay-config.csv if available.
|
||||||
$picker = Join-Path $PSScriptRoot 'Select-WaxtraceAsset.ps1'
|
$picker = Join-Path $scriptDir 'Select-WaxtraceAsset.ps1'
|
||||||
$cfg = Join-Path $PSScriptRoot 'bay-config.csv'
|
$cfg = Join-Path $scriptDir 'bay-config.csv'
|
||||||
if ((Test-Path -LiteralPath $picker) -and (Test-Path -LiteralPath $cfg)) {
|
if ((Test-Path -LiteralPath $picker) -and (Test-Path -LiteralPath $cfg)) {
|
||||||
$picked = & $picker -ConfigCsv $cfg -Title 'Restore FormTracePak - pick the bay being restored'
|
$picked = & $picker -ConfigCsv $cfg -Title 'Restore FormTracePak - pick the bay being restored'
|
||||||
if ($picked) {
|
if ($picked) {
|
||||||
|
|||||||
Reference in New Issue
Block a user