Job history is empty, max history is default (100)
Alternatively a way to delete specific jobs from the history instead of archive would work too I guess :)
Job history is empty, max history is default (100)
We do see more logs now, about 11 yesterday but it's down to 6 today - jobs we would expect to retain are still being removed.
Job history is empty, max history is default (100)
We're running 2026.1.3
on SQL Server,
for one affected script that runs every 15 minutes I would expect to see 100 jobs in the history, currently only seeing 9, another is running every minute and I only see one job in the history (should be 100)
Data Retention is set to 180 days
I have changed the script with 1 job to 500 max history, will let you know the result :)
Job history is empty, max history is default (100)
We're having an issue with empty or near empty job histories on some of our more aggresive scripts that run multiple times every hour even though we have the default setting of 100 max history on every job.
This issue seems to be on scripts that run many times every day and have a lot of jobs being archived by a custom trigger based on the amount of work done in the script.
My best guess is that PSU is including archived jobs in the calculation when deciding how many jobs to archive since scripts that don't run as often and don't have a lot jobs archived by our custom trigger don't seem to be affected.
This is our custom archive trigger script:
param ($Job)
#$DebugPreference = "Continue"
$jobId = $Job.Id
if ([string]::IsNullOrEmpty($jobId))
{
Write-Error "No job id supplied."
}
Write-Information "$jobId - $($Job.Script.Name) ran by $($Job.Identity.Name) @ $($Job.StartTime) for $(($Job.EndTime - $Job.StartTime).TotalSeconds) seconds."
if (!$Job.Schedule)
{
Write-Information "Job is not scheduled - aborting."
return
}
$output = Get-PSUJobPipelineOutput -JobId $jobId -Integrated #-AppToken $apiToken.Token
$HostOutput = Get-PSUJobOutput -JobId $jobId -Integrated
if ($HostOutput)
{
Write-Information "[Job Output]"
Write-Information ($HostOutput -join [Environment]::NewLine)
Write-Information "[/Job Output]"
}
if ($output.Archive -eq $true)
{
# Archieve job
$apiToken = Get-PSUAppToken -Identity "JobArchiver" -Integrated | Where-Object -Property Revoked -Eq $false | Select-Object -ExpandProperty Token -First 1
if (!$apiToken)
{
Write-Error "Failed to retrieve api token!"
return
}
Write-Host "Archiving job.. " -NoNewLine
$response = Invoke-RestMethod -Uri "https://localhost/api/v1/job/archive/$jobId" -Method "DELETE" -SkipCertificateCheck -Headers @{
Authorization="Bearer $apiToken"
}
if($response.Archived)
{
Write-Host "✅ OK" -ForegroundColor Green
}
else {
Write-Host "Not archived?" -BackgroundColor Red
}
}
Write-Debug "Triggered by job:"
Write-Debug ($Job | ConvertTo-Json -WarningAction Ignore)Integrated mode intermittently fails with "You must be running this command in PowerShell Universal to use the integrated mode" after upgrading to 2026.3.0
Got the same issue with a dashboard that calls Get-PSUDashboard -Integrated to enumerate all dashboards, fails with error: "You must be running this command in PowerShell Universal to use the integrated mode." - worked before upgrading to 2026.3 from 2026.1.3 - fails consistently.
New-UDDashboard -Title "Test" -Content {
New-UDLayout -Columns 4 -Content {
Get-PSUDashboard -Integrated | Sort-Object Name | ForEach-Object { Write-Host "test $_.Name"}
}
}
Suggestion for a cleaner job-log
This would be a nice feature, I have the same problem in our environment.. until an official solution arrives I’ve slapped together something custom to solve it. For anyone interested.
A trigger script that runs on ANY job completion:
param ($Job)
$jobId = $Job.Id
Write-Information "$jobId - $($Job.Script.Name) ran by $($Job.Identity.Name) @ $($Job.StartTime) for $(($Job.EndTime - $Job.StartTime).TotalSeconds) seconds."
if (!$Job.Schedule)
{
Write-Information "Job is not scheduled - aborting."
return
}
$output = Get-PSUJobPipelineOutput -JobId $jobId -Integrated #-AppToken $apiToken.Token
$HostOutput = Get-PSUJobOutput -JobId $jobId -Integrated
if ($HostOutput)
{
Write-Information "[Job Output]"
Write-Information ($HostOutput -join [Environment]::NewLine)
Write-Information "[/Job Output]"
}
if ($output.Archive -eq $true)
{
# Archieve job
$apiToken = Get-PSUAppToken -Identity "JobArchiver" -Integrated | Where-Object -Property Revoked -Eq $false | Select-Object -ExpandProperty Token -First 1
if (!$apiToken)
{
Write-Error "Failed to retrieve api token!"
return
}
Write-Host "Archiving job.. " -NoNewLine
$response = Invoke-RestMethod -Uri "https://localhost/api/v1/job/archive/$jobId" -Method "DELETE" -SkipCertificateCheck -Headers @{
Authorization="Bearer $apiToken"
}
if($response.Archived)
{
Write-Host "✅ OK" -ForegroundColor Green
}
else {
Write-Host "Not archived?" -BackgroundColor Red
}
}
Write-Debug "Triggered by job:"
Write-Debug ($Job | ConvertTo-Json -WarningAction Ignore)and then I return an object with Archive = $true at the end of every job that I want to discard. Example:
return @{
Archive = ($actionCount -eq 0)
}PowerShell Universal - 5.6.4
Settings > Files, hover Reload Configuration Files and choose Reload Apps
PowerShell Universal - 5.6.4
I had a similar experience but they returned after reloading configuration
PowerShell Universal - 5.6.3
Additionally I cannot view any jobs, I get the following error:
An error was unhandled and caused this component to fail to render. Please report this to Ironman Software using the tracker link below.
An error occured. Could not find 'ansiToHtml' ('ansiToHtml' was undefined). findFunction/<@https://psutst.rn.dk/_framework/blazor.server.js?v=5.6.3:1:374 findFunction@https://psutst.rn.dk/_framework/blazor.server.js?v=5.6.3:1:342 b@https://psutst.rn.dk/_framework/blazor.server.js?v=5.6.3:1:5091 beginInvokeJSFromDotNet/i<@https://psutst.rn.dk/_framework/blazor.server.js?v=5.6.3:1:2884 beginInvokeJSFromDotNet@https://psutst.rn.dk/_framework/blazor.server.js?v=5.6.3:1:2847 _invokeClientMethod@https://psutst.rn.dk/_framework/blazor.server.js?v=5.6.3:1:63689 _processIncomingData@https://psutst.rn.dk/_framework/blazor.server.js?v=5.6.3:1:61078 Jt/this.connection.onreceive@https://psutst.rn.dk/_framework/blazor.server.js?v=5.6.3:1:54719 connect/</i.onmessage@https://psutst.rn.dk/_framework/blazor.server.js?v=5.6.3:1:78667
at Microsoft.JSInterop.JSRuntime.InvokeAsync[TValue](Int64 targetInstanceId, String identifier, Object[] args) at PowerShellUniversal.ScriptOutputLine.OnParametersSetAsync() in D:\a\universal\universal\src\Universal.Server\Shared\Automation\ScriptOutputLine.razor:line 61 at Microsoft.AspNetCore.Components.ComponentBase.CallStateHasChangedOnAsyncCompletion(Task task) at Microsoft.AspNetCore.Components.RenderTree.Renderer.GetErrorHandledTask(Task taskToHandle, ComponentState owningComponentState) PowerShell Universal - 5.6.3
Hi @Adam Driscoll - after installing 5.6.3 in our test environment New-UDButton is broken.

If I look at the built-in doc, it seems that New-UDButton only works if -Size is specified.
Automatic Archiving
If there is no better solution I’m considering putting my cleaning logic into a trigger, then at least I don’t have to include the logic in every script, just have to make sure they output something I can check in the trigger.
Automatic Archiving
Thank you for your reply! It’s not exactly what I’m looking for, I only want to cleanup the jobs that I consider spam, as an example say I have a script that monitors an object for changes, if there are no changes the jobs aren’t interesting and I would like to remove them so it’s easier to find the jobs where something actually happened.
Automatic Archiving
Product: PowerShell Universal
Version: 5.3.2I’m in the process of moving some scripts from Jenkins into PSU that run on a schedule, some of them run very often but don’t necessarily do anything so to avoid flooding the job list I want to prune those that aren’t actually performing any actions… in Jenkins I used a plugin that would delete runs based on a regex in the script output. In PSU I’ve implemented the following snippet in the bottom of my script:
if ($actionCount -eq 0 -and $UAJob.Schedule)
{
# Archieve job
$jobId = $UAJob.Id
$apiToken = Get-PSUAppToken -Identity "JobArchiver" -Integrated
Write-Host "Archiving job: $jobId .."
$response = Invoke-RestMethod -Uri "https://psu/api/v1/job/archive/$jobId" -Method "DELETE" -Headers @{
Authorization="Bearer $($apiToken.Token)"
}
}It works but it’s a bit much to have to put in every script, so I have a couple of questions.
Is there a better way of achieving what I want or would it be possible to add something to PSU so a script can mark its own job to be archived on completion?
How do I limit the permissions of the app token identity, currently I have it set to Operator but I’m unsure how to only give access to archive jobs. The documentation mentions permissions like “automation/*” but I’ve only been able to find a couple of spefic “sub permissions” like read and execute.
PowerShell Universal - 5.1.0
Seems unrelated to the App itself, happens on all Apps for us, small or big. No pages.
PowerShell Universal - 5.1.0
Works fine on Scripts and under Settings > Files
PowerShell Universal - 5.1.0
After upgrading from 5.0.16 to 5.1.0 we can no longer edit any Apps.
The editor loads but instantly gets replaced by the following error:
An error occured. Cannot access a disposed object. Object name: ‘Microsoft.JSInterop.DotNetObjectReference`1[[BlazorMonaco.Editor.Editor, BlazorMonaco, Version=3.3.0.0, Culture=neutral, PublicKeyToken=null]]’.
at Microsoft.JSInterop.DotNetObjectReference
1.get_Value() at BlazorMonaco.Editor.Global.Create(IJSRuntime jsRuntime, String domElementId, StandaloneEditorConstructionOptions options, EditorOverrideServices overrideServices, DotNetObjectReference1 dotnetObjectRef) at BlazorMonaco.Editor.StandaloneCodeEditor.OnAfterRenderAsync(Boolean firstRender) at Microsoft.AspNetCore.Components.RenderTree.Renderer.GetErrorHandledTask(Task taskToHandle, ComponentState owningComponentState)
PSU v4 to v5 issues
We recently updated from v4 to v5 and I’m having an issue with getting the identity of the caller in a script started by an Invoke-PSUScript call in a dashboard.
Currently have the following code to invoke the script which works.
Invoke-PSUScript -Script (Get-PSUScript -Name "Script.ps1") -UserName $SomeInput (and some other script parameters) | Tee-Object -Variable job | Wait-PSUJobThe problem is when trying to get the identity of the caller in “Script.ps1” by calling
$UAJob.Identity.Nameit just returns “System” whereas in v4 I would get the user that triggered the invoke in the dashboard.
Currently have TrustCertificate: true and SecurityModel: Permissive in appsettings.json
I would really prefer to have this information available so I don’t have to pass it to the script manually and this worked in v4.
Synchronous Triggers or another way to run code before every job?
Right now I have a solution where I’ve defined a startup script for the environment, unfortunately I guess there is no way to find the job information at this point?
It would also be nice if this could be done with triggers in a way so we can define this to run globally no matter the environment.
Synchronous Triggers or another way to run code before every job?
Product: PowerShell Universal
Version: 4.3.0Hi there,
I was wondering if there is any way to make triggers run synchronously, aka. blocking a started job until the trigger script is done.
I’m looking for a way to run some code before every job without having to write it into every script, is this possible?