src/Private/Get-SkuReclaimInventory.ps1
|
function Get-SkuReclaimInventory { <# .SYNOPSIS Builds the "owned vs reclaimable" view by joining the reclaimable by-SKU rollup to the tenant's subscribedSkus inventory (prepaid/consumed counts). .DESCRIPTION For each reclaimable SKU it adds how many seats the tenant owns (PrepaidEnabled) and has assigned (ConsumedUnits), so the report can say "you own N, assigned M, and L of those are on dead/stale accounts." Aggregate counts only - no per-account data - so it is safe to show in the Free report. Returns an empty array when no inventory is available (e.g. the subscribedSkus call was not made or the scope was not consented), which makes the renderers fall back to the plain by-type rollup. .OUTPUTS PSCustomObject[]: SkuId, PartNumber, Name, PrepaidUnits, ConsumedUnits, ReclaimableUnits, MonthlyEachUsd, ReclaimableMonthlyUsd, InInventory - sorted by wasted spend descending. #> [CmdletBinding()] param( [Parameter(Mandatory)] [AllowEmptyCollection()] [object[]] $BySku, [Parameter(Mandatory)] [AllowEmptyCollection()] [object[]] $SubscribedSkus ) if (-not $SubscribedSkus -or $SubscribedSkus.Count -eq 0) { return @() } # Index the tenant inventory by SKU id (authoritative) and by part number (fallback). $byId = @{} $byPart = @{} foreach ($s in $SubscribedSkus) { if ($s.SkuId) { $byId[([string]$s.SkuId).ToLowerInvariant()] = $s } if ($s.SkuPartNumber) { $byPart[([string]$s.SkuPartNumber).ToLowerInvariant()] = $s } } $rows = New-Object System.Collections.Generic.List[object] foreach ($sku in $BySku) { $match = $null $idKey = ([string]$sku.SkuId).ToLowerInvariant() if ($byId.ContainsKey($idKey)) { $match = $byId[$idKey] } elseif ($sku.PartNumber -and $byPart.ContainsKey(([string]$sku.PartNumber).ToLowerInvariant())) { $match = $byPart[([string]$sku.PartNumber).ToLowerInvariant()] } $prepaid = if ($match) { [int]$match.PrepaidEnabled } else { $null } $consumed = if ($match) { [int]$match.ConsumedUnits } else { $null } $rows.Add([pscustomobject]@{ SkuId = $sku.SkuId PartNumber = $sku.PartNumber Name = $sku.Name PrepaidUnits = $prepaid ConsumedUnits = $consumed ReclaimableUnits = $sku.Count MonthlyEachUsd = $sku.MonthlyEachUsd ReclaimableMonthlyUsd = $sku.MonthlyTotalUsd InInventory = [bool]$match }) } return @($rows | Sort-Object -Property ReclaimableMonthlyUsd -Descending) } |