Bug: PowerShell Core Suggestion Messages
What Happened?
When running tenant investigation functions in PowerShell Core (but not PowerShell Desktop), several functions generate unwanted Suggestion [4,General]: The most similar commands are... messages after completing their operations. This affects 12 specific tenant investigation functions that interact with Exchange Online.
Steps to Reproduce
- Install Hawk module version 4.0
- Open PowerShell Core (not PowerShell Desktop)
- Run
Start-HawkTenantInvestigation - At the end of the of tenant investigation notice the message
Suggestion [4,General]: The most similar commands are...:
Technical Analysis
- Issue only occurs in PowerShell Core
- Only affects functions that use Exchange Online cmdlets through
Get-AllUnifiedAuditLogEntry - Does not affect functionality or data collection
- User investigation functions using the same cmdlets do not exhibit this behavior due to different scoping
- ** The only functions that this occurs on when running a tenant investigation are:
Get-HawkTenantConfigurationGet-HawkTenantEDiscoveryConfigurationGet-HawkTenantAdminInboxRuleCreationGet-HawkTenantAdminInboxRuleModificationGet-HawkTenantAdminInboxRuleRemovalGet-HawkTenantAdminMailboxPermissionChangeGet-HawkTenantAdminEmailForwardingChangeGet-HawkTenantEDiscoveryLogGet-HawkTenantDomainActivityGet-HawkTenantRBACChangeGet-HawkTenantAzureAppAuditLogGet-HawkTenantEXOAdmin
- Pattern suggests PowerShell Core handles Exchange Online session cleanup differently than Desktop
Previously attempted fixes:
1. Using Global Parameter Defaults in preimport.ps1
$session = Test-EXOConnection
if ($PSVersionTable.PSEdition -eq 'Core') {
$PSDefaultParameterValues['*:InformationAction'] = 'SilentlyContinue'
}
2. Attempted global parameter values in preimport.ps1:
if ($PSVersionTable.PSEdition -eq 'Core') {
$PSDefaultParameterValues['*:InformationAction'] = 'SilentlyContinue'
}
3. Adding Explicit return or break to end Block in Start-HawkTenantInvestigation:
end {
try {
# Calculate end time
$investigationEndTime = Get-Date
Write-HawkInvestigationSummary -StartTime $investigationStartTime -EndTime $investigationEndTime -InvestigationType 'Tenant' | Out-Null
Out-LogFile "Tenant Investigation completed" -Information
return
}
catch {
Out-LogFile "Error in investigation summary: $($_.Exception.Message)" -isError
Write-Error -ErrorRecord $_ -ErrorAction Continue
return
}
}
4. Mirroring Start-HawkTenantInvestigation to Match Start-HawkUserInvestigation Structure:
process {
if ($PSCmdlet.ShouldProcess("Investigating Tenant")) {
Get-HawkTenantConfiguration
Get-HawkTenantEDiscoveryConfiguration
Get-HawkTenantAdminInboxRuleCreation
Get-HawkTenantAdminInboxRuleModification
Get-HawkTenantAdminInboxRuleRemoval
Get-HawkTenantAdminMailboxPermissionChange
Get-HawkTenantAdminEmailForwardingChange
Get-HawkTenantEDiscoveryLog
Get-HawkTenantDomainActivity
Get-HawkTenantRBACChange
Get-HawkTenantEntraIDAuditLog
Get-HawkTenantAzureAppAuditLog
Get-HawkTenantEXOAdmin
Get-HawkTenantConsentGrant
Get-HawkTenantRiskyUsers
Get-HawkTenantRiskDetections
Get-HawkTenantEntraIDAdmin
Get-HawkTenantAppAndSPNCredentialDetail
Get-HawkTenantEntraIDUser
}
}
5. Investigating Folder Creation Differences Between Tenant and User Investigations:
- Found that Out-MultipleFileType handles folder creation differently for user vs tenant investigations.
- User investigations create user-specific folders, while tenant investigations create a Tenant folder.
if ([string]::IsNullOrEmpty($User)) {
$path = Join-Path $Hawk.FilePath "\Tenant"
} else {
$path = Join-Path $Hawk.FilePath $User
}
6. Ensuring Write-HawkInvestigationSummary Does Not Return Output:
end {
try {
$investigationEndTime = Get-Date
$null = Write-HawkInvestigationSummary -StartTime $investigationStartTime -EndTime $investigationEndTime -InvestigationType 'Tenant'
$null = Out-LogFile "Tenant Investigation completed" -Information
}
catch {
$null = Out-LogFile "Error in investigation summary: $($_.Exception.Message)" -isError
Write-Error -ErrorRecord $_ -ErrorAction Continue
}
}
Acceptance Criteria
- Root cause determined
- Suggestion prompt no longer displayed after a Tenant Investigation
- User Guide->Troubleshooting section of Hawk website is updated
This behavior appears to be related to PowerShell's command suggestion feature, which became a mainstream (non-experimental) feature in PowerShell 7.5. We are actively investigating this issue. Our current understanding is that this behavior is tied to PowerShell's new FeedbackProvider system, which replaced the previous experimental PSCommandNotFoundSuggestion feature. Since this is now a core PowerShell feature, it can no longer be disabled through experimental feature flags. See more at:
https://learn.microsoft.com/en-us/powershell/scripting/learn/experimental-features?view=powershell-7.5
https://github.com/PowerShell/PowerShell/issues/10213