Skip to content
The Lazy Administrator
  • Home
  • Disclaimer
  • Contact
  • About Me
  • Search Icon

The Lazy Administrator

Finding ways to do the most work with the least effort possible

Microsoft Graph API Endpoint Adds Last Successful Sign-In Date Time

Microsoft Graph API Endpoint Adds Last Successful Sign-In Date Time

December 9, 2023 Brad Wyatt Comments 4 comments

Table of Contents

  • LastSignInDateTime vs LastSuccessfulSignInDateTime
  • Other Properties Available Under the Resource Type
  • Conditions and Limitations
  • Converting the DateTime Object to Local Time
  • Getting All Users Last Successful Sign-In Date Time

Previously, if you wanted to find a user’s last successful sign-in to your Microsoft 365 tenant using the Microsoft Graph REST API, you would have to iterate through Entra ID sign-in logs. With new recent additions to the Microsoft Graph API Beta Endpoint, you can now return the UTC value just by parsing the user details and properties. The Microsoft documentation regarding the signInActivity resource type can be found here.

LastSignInDateTime vs LastSuccessfulSignInDateTime

The difference between lastSignInDateTime and lastSuccessfulSignInDateTime property is:

  • lastSignInDateTime: The last interactive sign-in date and time for a specific user. You can use this field to calculate the last time a user attempted to sign into the directory the directory with an interactive authentication method. This field can be used to build reports, such as inactive users. The timestamp represents date and time information using ISO 8601 format and is always in UTC time. For example, midnight UTC on Jan 1, 2014 is: '2014-01-01T00:00:00Z'. Microsoft Entra ID maintains interactive sign-ins going back to April 2020.
  • lastSuccessfulSignInDateTime: The datetime of the user’s most recent successful sign in activity.

Other Properties Available Under the Resource Type

The other properties are also currently available under the resource type:

  • lastSignInDateTime
  • lastSignInRequestID
  • lastNonInteractiveSignInDateTime
  • lastNonInteractiveSignInRequestId
  • lastSuccessfulSignInDateTime
  • lastSuccessfulSignInRequestID

Conditions and Limitations

  • Details for this property require a Microsoft Entra ID P1 or P2 license and the AuditLog.Read.All permission.
  • This property is not returned for a user who has never signed in or last signed in before April 2020.
  • Returned only on $select. Supports $filter (eq, ne, not, ge, le) but not with any other filterable properties.
  • LastSuccessfulSignInDateTime is currently only available in the beta endpoint at the time of writing.

In regard to the $select statement, if you were to query your user in the API using the following code, you will see that it does not return any signInActivity data.

$apiUrl = 'https://graph.microsoft.com/beta/users/5bcffade-2afd-48a2-8096-390a9090555c'
$Data = Invoke-RestMethod -Headers @{Authorization = "Bearer $($Tokenresponse.access_token)"} -Uri $apiUrl -Method Get
$data

## Results 
<#
@odata.context                  : https://graph.microsoft.com/beta/$metadata#users/$entity
id                              : 5bcffade-2afd-48a2-8096-390a9090555c
deletedDateTime                 : 
accountEnabled                  : True
ageGroup                        : 
businessPhones                  : {6305556528}
city                            : Geneva
createdDateTime                 : 9/20/2017 4:21:43AM
creationType                    : 
companyName                     : The Lazy Administrator
consentProvidedForMinor         : 
country                         : United States
department                      : IT
displayName                     : Bradley Wyatt
employeeId                      : 
employeeHireDate                : 
employeeLeaveDateTime           : 
employeeType                    : 
faxNumber                       : 
givenName                       : Bradley
imAddresses                     : {[email protected]}
infoCatalogs                    : {}
isLicenseReconciliationNeeded   : False
isManagementRestricted          : 
isResourceAccount               : 
jobTitle                        : Manager of the Cool Kids
legalAgeGroupClassification     : 
mail                            : [email protected]
mailNickname                    : brad
mobilePhone                     : 
onPremisesDistinguishedName     : 
officeLocation                  : Corner Office Duh
onPremisesDomainName            : 
onPremisesImmutableId           : 
onPremisesLastSyncDateTime      : 
onPremisesObjectIdentifier      : 
onPremisesSecurityIdentifier    : 
onPremisesSamAccountName        : 
onPremisesSyncEnabled           : 
onPremisesUserPrincipalName     : 
otherMails                      : {}
passwordPolicies                : DisablePasswordExpiration
postalCode                      : 60134
preferredDataLocation           : 
preferredLanguage               : en-US
proxyAddresses                  : {SMTP:[email protected], smtp:[email protected]}
refreshTokensValidFromDateTime  : 8/26/2020 2:14:57PM
securityIdentifier              : S-1-12-1-1540356830-1218587389-171546240-1549111440
showInAddressList               : 
signInSessionsValidFromDateTime : 8/26/2020 2:14:57PM
state                           : Illinois
streetAddress                   : 123 Fake Street
surname                         : Wyatt
usageLocation                   : US
userPrincipalName               : [email protected]
externalUserConvertedOn         : 
externalUserState               : 
externalUserStateChangeDateTime : 
userType                        : Member
employeeOrgData                 : 
passwordProfile                 : 
assignedLicenses                : {@{disabledPlans=System.Object[]; skuId=cbdc14ab-d96c-4c30-b9f4-6ada7cdc1d46}}
authorizationInfo               : @{certificateUserIds=System.Object[]}
cloudRealtimeCommunicationInfo  : @{isSipEnabled=True}
deviceKeys                      : {@{deviceId=8cd46cd2-3123-4bb1-a262-c75fce0ea538; keyMaterial=UlNBMQAIAAADAAAAAAEAAAAAAAAAAAAAAQABwiWermA4yh+cd4Qyq3N133M9+fsbCZ
identities                      : {@{signInType=userPrincipalName; issuer=bwya77.onmicrosoft.com; [email protected]}}
onPremisesProvisioningErrors    : {}
serviceProvisioningErrors       : {}
#>

However, when using the following code with the $select statement, we are returned the proper data.

$apiUrl = 'https://graph.microsoft.com/beta/users/5bcffade-2afd-48a2-8096-390a9090555c?$select=signInActivity'
$Data = Invoke-RestMethod -Headers @{Authorization = "Bearer $($Tokenresponse.access_token)"} -Uri $apiUrl -Method Get

$data.signInActivity

## Results 
<#
lastSignInDateTime                : 12/9/2023 4:34:35AM
lastSignInRequestId               : edb253e1-bd6b-4396-bda4-0295e3044900
lastNonInteractiveSignInDateTime  : 12/9/2023 10:56:08AM
lastNonInteractiveSignInRequestId : dabfdf4c-b63c-421f-b9b5-33b7907f1a00
lastSuccessfulSignInDateTime      : 12/9/2023 10:56:08AM
lastSuccessfulSignInRequestId     : dabfdf4c-b63c-421f-b9b5-33b7907f1a00
#>

Converting the DateTime Object to Local Time

As mentioned earlier, the datetime objects are always returned using UTC time. We can convert that to our local time zone. Below, I am converting the returned datetime object to Central Standard Time (the time zone I am located in)

$apiUrl = 'https://graph.microsoft.com/beta/users/5bcffade-2afd-48a2-8096-390a9090555c?$select=signInActivity'
$Data = Invoke-RestMethod -Headers @{Authorization = "Bearer $($Tokenresponse.access_token)"} -Uri $apiUrl -Method Get
$lastSignInDateTimeCST = [TimeZoneInfo]::ConvertTimeBySystemTimeZoneId($data.signInActivity.lastSignInDateTime, 'Central Standard Time')
$data.signInActivity | Select-Object -Property lastSuccessfulSignInDateTime, @{Name = 'Last Sign In (CST)'; Expression = {$lastSignInDateTimeCST}}

Then using Select-Object, I can select my new property and value.

$apiUrl = 'https://graph.microsoft.com/beta/users/5bcffade-2afd-48a2-8096-390a9090555c?$select=signInActivity'
$Data = Invoke-RestMethod -Headers @{Authorization = "Bearer $($Tokenresponse.access_token)"} -Uri $apiUrl -Method Get
$lastSignInDateTimeCST = [TimeZoneInfo]::ConvertTimeBySystemTimeZoneId($data.signInActivity.lastSignInDateTime, 'Central Standard Time')
$data.signInActivity | Select-Object -Property lastSuccessfulSignInDateTime, @{Name = 'Last Sign In (CST)'; Expression = {$lastSignInDateTimeCST}}

The returned object is shown below:

lastSuccessfulSignInDateTime Last Sign In (CST)
---------------------------- ------------------
12/9/2023 2:48:58PM          12/8/2023 10:34:35PM

Getting All Users Last Successful Sign-In Date Time

O365 IT Pro’s have posted on GitHub a great script that will iterate through all of your users and not only return their LastSuccessfulSignInDateTime and LastSignIn, but also the days since the last successful sign in and last sign in.

Brad Wyatt
Brad Wyatt

My name is Bradley Wyatt; I am a 5x Microsoft Most Valuable Professional (MVP) in Microsoft Azure and Microsoft 365. I have given talks at many different conferences, user groups, and companies throughout the United States, ranging from PowerShell to DevOps Security best practices, and I am the 2022 North American Outstanding Contribution to the Microsoft Community winner.


Graph
API, Azure, Graph, Office 365, PowerShell

Post navigation

PREVIOUS
Getting Started with the IntuneCLI, an Automated Intune Management Solution
NEXT
The Microsoft Graph Command-Line Interface (CLI)

4 thoughts on “Microsoft Graph API Endpoint Adds Last Successful Sign-In Date Time”

  1. David says:
    December 10, 2023 at 1:22 am

    Thanks for the hint!
    Is there also the possibility so filter the Sign-In‘s by application, so you can see a user never logged in to Exchange but to SPO?

    Reply
  2. Pingback: Intune Newsletter - 15th December 2023 - Andrew Taylor
  3. Lucas says:
    January 30, 2024 at 12:32 pm

    Thank you. I have been digging through documentation trying to get last sign in date, but couldn’t find a straight forward way to get at it. I was requesting auditlog directly. While it has much more granularity, it isn’t very efficient. Thanks for the article, you saved my bacon!

    Reply
  4. Gary Herbstman says:
    January 12, 2025 at 5:04 pm

    Per the MS docs and my experience, the lastSuccessfulSignInDateTime is not updated if the user last logged in prior to December 1, 2023. The field returns no data.

    Effective December 1, 2023, the lastSuccessfulSignInDateTime property is available to provide the last successful sign-in time for a specific user, regardless of whether the sign-in was interactive or non-interactive. The data isn’t backfilled for this property.

    Reply

Leave a Reply Cancel reply

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

Subscribe

Email


Categories

  • Active Directory (8)
  • AI (3)
  • API (1)
  • AutoPilot (2)
  • Azure (15)
  • Bicep (4)
  • Connectwise (1)
  • Defender for Cloud Apps (1)
  • Delegated Admin (1)
  • DevOps (6)
  • Graph (6)
  • Intune (15)
  • LabTech (1)
  • Microsoft Teams (6)
  • Office 365 (19)
  • Permissions (2)
  • PowerShell (50)
  • Security (1)
  • SharePoint (3)
  • Skype for Business (1)
  • Terraform (1)
  • Uncategorized (2)
  • Yammer (1)

Recent Comments

  • Mike D on Upload a file to Connectwise and Attach it to a Service Ticket with PowerShell
  • Side Eye on Homeland Security’s Trusted Travelers API and PowerShell – Getting a Better Global Entry Interview Using PowerShell
  • Lisa on Allow Non-Admin Users to Manage Their Desktop Icons Using Intune
  • A1 Lottery LOGIN on Get a New Computer’s Auto Pilot Hash Without Going Through the Out of Box Experience (OOBE)
  • Kristopher Gates on Getting Started with GitHub Copilot in the CLI

1,752,882 People Reached

© 2025   All Rights Reserved.