How to configure TAP (Temporary Access Pass) in Entra ID for multiple users using Powershell

TAP is a great feature to use for recovering accounts that have lost access to their MFA token, for onboarding new users to Autopilot or enrolling devices in Intune or perhaps to setup strong authentication like Yubikeys. However in Azure when assigning TAP you can only do it for one user at a time which can sometimes be frustrating and time consuming when you need to assign TAP to a lot of users. Below I present my solution to this problem. This what we will be going over in today’s post:

DISCLAIMER ⚠️

TAP is considered a really strong authentication method so when assigning it to multiple users and especially storing it in a CSV-file it can be considered kind of a risky move if the wrong person reaches that information (when doing it in the Azure portal you can only see the TAP password once for a reason). So treat that CSV-file like the biggest and baddest master key to the final castle in a Zelda game, okay? We will go over on how to properly remove everything once we are done and I will also point out how to do this in a secure way.

What is TAP?

This is how Microsoft in short describes TAP:

“A Temporary Access Pass (TAP) is a time-limited passcode that can be configured for single use or multiple sign-ins. Users can sign in with a TAP to onboard other passwordless authentication methods. A TAP also makes recovery easier when a user loses or forgets a strong authentication method.”

Is this really possible?

From what I can find there is no “official” way from Microsoft to assign TAP for multiple users (for obvious reasons maybe as mentioned in the disclaimer). However, there are multiple scenarios where this can be very useful hence this workaround.

There is no direct way of assigning TAP to multiple users using Microsoft Graph which is the tool we will be using. However, you can initialize an array and then loop through the CSV-file with a foreach-loop and assign TAP to all users individually and then store the output of that array in a CSV-file.

Prerequisites

  • Access to a Global administrator account in the tenant
  • Latest version of Microsoft Graph module installed in Powershell
  • A CSV-file with all users you want to assign TAP to.

Making the CSV-file

Prepare the CSV with one column called userPrincipalName and add all your users in there:

The script

Below is the full script followed by a breakdown explaining what we are actually doing. Please read the full post before using it to understand what is actually happening and what to think of in terms of security.

# Connect Mg-Graph
Connect-MgGraph -Scopes "UserAuthenticationMethod.ReadWrite.All", "Directory.AccessAsUser.All", "Policy.Read.All" -NoWelcome

# Check if TAP is enabled
$tapPolicy = Get-MgPolicyAuthenticationMethodPolicyAuthenticationMethodConfiguration -AuthenticationMethodConfigurationId "TemporaryAccessPass"

if ($tapPolicy.state -ne "enabled") {
    Write-Host "❌ Please enable TAP in Microsoft Entra Authentication Methods before running this script." -ForegroundColor Red
    exit
}

Write-Host "✅ TAP is enabled. Continuing script execution..." -ForegroundColor Green


# Import user list from CSV
$users = Import-Csv -Path ".\users.csv"

# Initialize an array to store TAP details
$tapList = @()

foreach ($user in $users) {
    # Generate TAP for each user
    $tap = @{
        isUsable = $true
        lifetimeInMinutes = 480  # TAP valid for 8 hours, Change this if you want a shorter timespan.
    }

    $result = New-MgUserAuthenticationTemporaryAccessPassMethod -UserId $user.UserPrincipalName -BodyParameter $tap

    # Store TAP details in an array
    $tapDetails = [PSCustomObject]@{
        Email        = $user.UserPrincipalName
        TAP_Password = $result.TemporaryAccessPass  # Retrieve TAP password
    }

    $tapList += $tapDetails
    Write-Host "Created TAP for: $($user.UserPrincipalName) - Password: $($result.TemporaryAccessPass)" -ForegroundColor Cyan
}

# Export TAPs to CSV
$tapList | Export-Csv -Path ".\TAP_Users.csv" -NoTypeInformation -Force

Write-Host "TAP creation complete. Check TAP_Users.csv for details." -ForegroundColor Green

Breaking down the script pt.1

# Connect Mg-Graph
Connect-MgGraph -Scopes "UserAuthenticationMethod.ReadWrite.All", "Directory.AccessAsUser.All", "Policy.Read.All" -NoWelcome

# Check if TAP is enabled
$tapPolicy = Get-MgPolicyAuthenticationMethodPolicyAuthenticationMethodConfiguration -AuthenticationMethodConfigurationId "TemporaryAccessPass"

if ($tapPolicy.state -ne "enabled") {
    Write-Host "❌ Please enable TAP in Microsoft Entra Authentication Methods before running this script." -ForegroundColor Red
    exit
} else {
    Write-Host "✅ TAP is enabled. Continuing script execution..." -ForegroundColor Green
}

The first part of the script consists of connecting to Microsoft Graph and checking if TAP is enabled in your tenant. If not you will get the message below.

If not enabled: Enable TAP in Entra Authentication methods

I tried to do this part using Powershell but couldn’t get it to work, so I did it the hard way via the GUI instead. Navigate to the Azure portal and search for Microsoft Entra authentication methods and then go to “Policies” to enable Temporary Access Pass (TAP).

I recommend making a group for all users that you want to enable TAP for instead of enabling it for All users. Make sure the members of the group match the content of your CSV-file.

When TAP is enabled you should get a green message in your Powershell prompt when running the first part again and then you’re ready to move on!

Breaking down the script pt.2

In the next part of the script, we import a CSV file containing our users. Make sure the file path is correct — if you’re using .\ ensure you’re in the same directory as the script is running from in Powershell.

We then initialize an array called $tapList, which we’ll use to store the TAP details for each user.

Then we trigger a foreach loop to look through all users in the CSV-file.

After that, we create a hashtable called $tap where we define the TAP settings:

isUsable is set to $true, allowing the TAP to be used.

lifetimeInMinutes is set to 480 (8 hours), but can be adjusted to your needs. Here is the values we have to work with from Microsofts documentation:

“The lifetime of the Temporary Access Pass in minutes starting at startDateTime. Must be between 10 and 43200 inclusive (equivalent to 30 days).”

Finally, we call the Microsoft Graph command New-MgUserAuthenticationTemporaryAccessPassMethod using the user’s UPN from the CSV and our $tap settings. This creates the TAP and returns the result, including the actual TAP password. This is what is included in the variable $result. Below is what we covered in this part:

# Import user list from CSV
$users = Import-Csv -Path ".\users.csv"

# Initialize an array to store TAP details
$tapList = @()

foreach ($user in $users) {
    # Generate TAP for each user
    $tap = @{
        isUsable = $true
        lifetimeInMinutes = 480  # TAP valid for 8 hours, Change this if you want a shorter timespan.
    }

    $result = New-MgUserAuthenticationTemporaryAccessPassMethod -UserId $user.UserPrincipalName -BodyParameter $tap

We now have generated the TAP so to display it along with the UPN later we can store them in a PSCustomObject that we call $tapDetails where we include the UPN and the result from our variable $result, which is the acutal TAP password. Then we add it to the $tapList array. This is what we will use to actually display the UPN and TAP.

    $tapDetails = [PSCustomObject]@{
        Email        = $user.UserPrincipalName
        TAP_Password = $result.TemporaryAccessPass
    }

    $tapList += $tapDetails

To be able to follow along we log each creation in the Powershell console using Write-Host and also add some nice Cyan color to it. If you feel like you want to display the TAP on as few places as possible (only in the CSV) you can always comment this section with a # in the beginning to not use it.

Write-Host "Created TAP for: $($user.UserPrincipalName) - Password: $($result.TemporaryAccessPass)" -ForegroundColor Cyan

Finally we use our mighty $tapList variable to export everything into a new CSV-file called TAP_users.csv and also display it in the console.

$tapList | Export-Csv -Path ".\TAP_Users.csv" -NoTypeInformation -Force

Write-Host "TAP creation complete. Check TAP_Users.csv for details." -ForegroundColor Green

Final result

The output from Powershell:

Our CSV-File:

And just to verify it works we test it out with Mr. Jim Hawkins (anyone who knows that name had an awesome childhood).

IT WORKS!!

Last IMPORTANT step: Cleaning up

This is a really important part since we don’t want anyone using our exported TAP to access peoples data or to bypass MFA. When done with using the TAPs, I strongly recommend to permanently delete the CSV-file with shift + delete!!! and only share one TAP at a time with each user if needed and keep the file to yourself if possible or only share it with people you trust. I can’t say that enough!

Run this removal script which is basically the same as before except we changed New-MgUserAuthenticationTemporaryAccessPassMethod to Remove-MgUserAuthenticationTemporaryAccessPassMethod.

# Load users from CSV
$csvPath = ".\users.csv"
$users = Import-Csv -Path $csvPath

foreach ($user in $users) {
    $upn = $user.userPrincipalName
    try {
        # Get TAP methods for the user
        $taps = Get-MgUserAuthenticationTemporaryAccessPassMethod -UserId $upn

        if ($taps.Count -eq 0) {
            Write-Host "ℹ️ No TAPs found for $upn" -ForegroundColor Yellow
            continue
        }

        foreach ($tap in $taps) {
            # Remove TAP
            Remove-MgUserAuthenticationTemporaryAccessPassMethod -UserId $upn -TemporaryAccessPassAuthenticationMethodId $tap.Id -Confirm:$false
            Write-Host "✅ Removed TAP for $upn" -ForegroundColor Green
        }
    }
    catch {
        Write-Host "❌ Failed to process '$upn': $_" -ForegroundColor Red
    }
}

Output in Powershell:

Verify by trying to sign in again, you should now get to the regular sign-in screen with password:

OPTIONAL: Also remove the group from Entra authentication methods and de-activate TAP completely (if no other groups are using it!)

Bonus tip if using TAP to enroll devices

When enrolling devices in Intune (with or without Autopilot) you can’t use TAP after you get past the OOBE when enrolling a new device. What you have to do is assign the settings catalog below to enable Web Sign In for your device. If using Autopilot I highly recommend assigning this to the dynamic user group with your target Autopilot devices so your devices can get it as soon as possible.

That’s it! We now know how to assign TAP in bulk to make enrolling in Autopilot or Intune a lot easier. No need to collect passwords anymore! This can also be used to recover lost MFA tokens or setup strong authentication methods like Yubikeys like mentioned at the start of this post. If you read this far, thank you so much! Until next time 😀🤛

Leave a Reply

Your email address will not be published. Required fields are marked *