Forum Discussion
ddickinsonBHCET
May 21, 2025Copper Contributor
User Profile Deletion
Hi,
I just wanted to pick anyone's brains, in case they have also encountered this or would have any idea why this is the case. I am fairly new to Intune and script writing, to clarify.
Basically, we have been working on a Detect and Remediation script that is deployed via Intune (Devices >Ssni Script and Remediations) to Windows 10 (Ent 22H2) and Windows 11 (Ent 24H2) devices. On any fresh enrolled devices, it detects and deletes user profiles completely fine, but fails to even detect profiles on devices that were enrolled a while ago. However, if we run an Autopilot reset on those devices, the script works again. What difference would a freshly built/enrolled device have to an older one, when they also run other scripts fine.
The script targets profiles that are older than 1 hour as we want to keep on top of removing profiles consistently to keep disk space low, especially on lower spec laptops. It will exclude SYSTEM profiles and also any *Admin* user folders - as that has a separate script to only delete LAPSAdmin on an evening, when the workplace is closed (8pm UK). This LAPSAdmin script worked fine on the older enrolled devices. Some of the profiles on the machines go back to 2023, is the '1 hour' target not effective against that old of a profile - has it become stale?SS
Like I said, I am fairly new to this and have used bits and pieces from different locations to help muster up a script. I thought I had it nailed as it was working on test devices that were just enrolled purely for testing, until I was asked to put it onto another group.
Intune doesn't say the script fails - indicating there are no errors. However, I am not saying there isn't.
Detect:
Remediate:
Thanks for your time,
Dean
3 Replies
Sort By
- Luca_Scarano_TheItalianWayIron Contributor
You can try this in detection and check if it detects correctly the profiles.
$cutoff = (Get-Date).AddMinutes(-60) Write-Output "`n---- Profile Diagnostic Report ----" Write-Output "Cutoff time: $cutoff" # Get tasklist output once $tasklistOutput = tasklist /v Get-ChildItem "C:\Users" -Directory -ErrorAction SilentlyContinue | ForEach-Object { $folder = $_ $folderPath = $folder.FullName $ntName = $folder.Name $lastWrite = $folder.LastWriteTime $idleMinutes = [math]::Round(((Get-Date) - $lastWrite).TotalMinutes) $profile = Get-CimInstance -Class Win32_UserProfile -ErrorAction SilentlyContinue | Where-Object { $_.LocalPath -eq $folderPath } $status = "Unknown" $isSpecial = $false $canBeDeleted = $false if ($profile) { $isSpecial = $profile.Special if (-not $profile.Loaded) { $status = "Unloaded" if (-not $isSpecial -and $ntName -notlike "*Windows*" -and $ntName -notlike "*default*" -and $ntName -notlike "*Public*" -and $ntName -notlike "*Admin*" -and $lastWrite -lt $cutoff) { $canBeDeleted = $true } } else { # Loaded profile — check process activity $tasklistName = "$env:COMPUTERNAME\$ntName" $hasProcess = $tasklistOutput | Where-Object { $_ -match "\b$([regex]::Escape($tasklistName))\b" } $status = $hasProcess ? "Loaded Active" : "Loaded Idle" } } [PSCustomObject]@{ FolderName = $ntName LastWriteTime = $lastWrite IdleMinutes = $idleMinutes Status = $status IsSpecial = $isSpecial Deletable = $canBeDeleted ProfileFound = [bool]$profile } } | Sort-Object LastWriteTime | Format-Table -AutoSize
- ddickinsonBHCETCopper Contributor
Hey, Luca_Scarano_TheItalianWay
Thanks for your reply. I will get round to testing this.
Could you kindly explain what you have changed and why you think it would make a difference when deleting profiles on older enrolled devices. This is also a learning process for me, so would be glad to take any advice or methodology on board.
- Luca_Scarano_TheItalianWayIron Contributor
Hi,
use it just as a diagnostic. Profiles can result loaded also if they are not, and folders can be accessed also by background process, giving you false information on last activity.
I would better go with a simple task list.
In this case I kept Deletable false for loaded idle profiles (without processes). From this script you can already understand if this kind of detection works better for you, and after fix in the general script.