Reading, Rotating, and Reporting on LAPS and BitLocker in Intune and Entra with PowerShell

After the recent Crowdstrike Incident I've been thinking a lot about how to quickly perform LAPS and BitLocker actions against remote devices, and report on their use primarily via Microsoft Graph and Intune. I work and talk with a lot of folks in highly distributed environments (thinking of you, all of my EDU friends!) and one thing I've begun to recommend is simple, consistent documentation and configuration of these two items – even in that type of environment. While this post assumes you already have LAPS and BitLocker configured for Entra/Intune, I hope the following can be added to your documentation for easy ad-hoc management and reporting of these 2 very important features.

Note that many of these actions can, and often will, be performed directly from the Intune admin center. For example, rotation of both LAPS passwords and BitLocker recovery keys can be triggered via remote tasks found on a device object in Intune:

Retrieve LAPS password via Graph

$DeviceName = "NewPC-001"

Connect-MGGraph -Scopes DeviceLocalCredential.Read.All

Get-LapsAADPassword -DeviceIds $DeviceName -IncludePasswords -AsPlainText

Rotate LAPS password via Graph

$DeviceName = "NewPC-001"

Connect-MgGraph -Scopes DeviceManagementManagedDevices.Read.All -NoWelcome

$DeviceId = (Get-MgBetaDeviceManagementManagedDevice -Filter "DeviceName eq '$($DeviceName)'").Id

Invoke-MgBetaRotateDeviceManagementManagedDeviceLocalAdminPassword -ManagedDeviceId $DeviceId

Note: The LAPS password will still rotate based on your assigned LAPS policy. This allows you to do it faster, but it is not recommended to do this repeatedly.

Retrieve BitLocker recovery key via Graph

$DeviceName = "NewPC-001"

Connect-MgGraph -Scopes "BitLockerKey.Read.All","DeviceManagementManagedDevices.Read.All"

$DeviceId = (Get-MgBetaDeviceManagementManagedDevice -Filter "DeviceName eq '$($DeviceName)'").AzureAdDeviceId

Get-MgInformationProtectionBitlockerRecoveryKey -Filter "deviceId eq '$($DeviceId)'" | Select-Object Id,CreatedDateTime,DeviceId,@{n="Key";e={(Get-MgInformationProtectionBitlockerRecoveryKey -BitlockerRecoveryKeyId $_.Id -Property key).key}},VolumeType

Rotate BitLocker recovery key via Graph

$DeviceName = "NewPC-001"

Connect-MgGraph -Scopes "DeviceManagementManagedDevices.Read.All" -NoWelcome

$DeviceId = (Get-MgBetaDeviceManagementManagedDevice -Filter "DeviceName eq '$($DeviceName)'").Id

Invoke-MgBetaRotateDeviceManagementManagedDeviceBitLockerKey -ManagedDeviceId $DeviceId

Note: If you're using the "Configure Recovery Password Rotation" policy with one of the "Refresh on" settings, key rotation for OS drives and fixed drives will happen automatically upon use. Please review the setting for more information.

Reporting on successful LAPS/BitLocker audit events over the last 24 hours

#Get Intune LAPS and BitLocker Rotate Audit Events from the last 24 hours
[dateTime]$date = (get-date).addDays(-1)

$dateFormatted = Get-Date $date -Format yyyy-MM-dd

Connect-MgGraph -Scopes "DeviceManagementApps.Read.All" -NoWelcome
Get-MgBetaDeviceManagementAuditEvent -Filter "activityDateTime gt $dateFormatted and startswith(ActivityType,'rotate')" | Select-Object ActivityDateTime,ActivityType,@{Name='InitiatedBy';Expression={$_.actor.userprincipalname}},@{Name='TargetDevice';Expression={(Get-MgDeviceManagementManagedDevice -ManagedDeviceId $_.resources.ResourceId).DeviceName}}| Sort-Object ActivityDateTime

#Get Entra BitLocker Recovery Key read events from the last 24 hours
[dateTime]$date = (get-date).addDays(-1)

$dateFormatted = Get-Date $date -Format yyyy-MM-dd

Connect-MgGraph -Scopes "AuditLog.Read.All" -NoWelcome

Get-MgAuditLogDirectoryAudit -Filter "activityDateTime gt $dateFormatted and startswith(ActivityDisplayName,'Read')" | Select-Object ActivityDateTime,ActivityDisplayName,@{Name='InitiatedBy';Expression={$_.InitiatedBy.User.UserPrincipalName}},@{Name='TargetDevice';Expression={(Get-MgBetaDeviceManagementManagedDevice -Filter "AzureAdDeviceId eq '$([regex]::Match($_.AdditionalDetails.Value, "'[0-9a-fA-F-]{36}'[^']+'([0-9a-fA-F-]{36})'").Groups[1].Value)'").DeviceName }}

The amount of time it took to get the output of the BitLocker Recovery Key read events the way I wanted was far too long. 🙂 It turns out that the "Read BitLocker key" Audit Log Event in Entra only has one reference to the target device as of the writing of this post. That reference is in the "AdditionalInfo" field, in the form of a string like this:

Successfully retrieved BitLocker recovery key associated with key ID: '{BitLockerKeyID}'. Backed up from device: '{AzureAdDeviceId}'

To make myself feel better, I'm telling myself "if it's stupid and it works, it's not stupid." 🙂 I like having the UserPrincipalName of the person that initiated the action and the device name of the target device in these simple reports as device naming – even in a cloud native world – has continued to be important for many processes and organizations.

Additional resources:

While I wanted to record some ad-hoc actions we can take with BitLocker and LAPS, I also want to call out some other fantastic resources that I've come across or used over the last couple of weeks:

Get Rubix – How to automatically rotate your BitLocker recovery keys every 30 days
https://www.youtube.com/watch?v=l0AK3TPVU7w
Get Rubix – Updated BitLocker Key rotation
https://www.youtube.com/watch?v=vr08g2L86p8
Ugur Koc – Rotate All BitLocker Keys
https://github.com/ugurkocde/Intune/blob/main/Windows/rotate_all_bitlocker_keys.ps1
Petri Paavola – IntuneDeviceDetailsGUI
Note: This is a very useful tool that can be used to retrieve LAPS passwords and BitLocker recovery keys for individual devices but goes beyond that to also gather a lot of information about a specific device.
https://github.com/petripaavola/IntuneDeviceDetailsGUI

About the author

Andrew Johnson

5 1 vote
Article Rating
Subscribe
Notify of
guest
0 Comments
Newest
Oldest Most Voted

>