How to set accountexpires value on Active Directory
Symptoms
Many times IIQ developer facing an issue to set accountexpires active directory application attribute value via beanshell code.
Please find below solution for setting accountexpires, pwdLastSet,accountExpires, LastLogon, LastLogonTimestamp, and LastPwdSet value using beanshell code.
Diagnosis
The expected timestamp required for the accountexpires AD attribute is the 18-digit Active Directory timestamps, also named 'Windows NT time format', 'Win32 FILETIME or SYSTEMTIME' or NTFS file time. These are used in Microsoft Active Directory for pwdLastSet, accountExpires, LastLogon, LastLogonTimestamp, and LastPwdSet. The timestamp is the number of 100-nanosecond intervals (1 nanosecond = one billionth of a second) since Jan 1, 1601 UTC.
Solution
Please find below solution to calculate pwdLastSet, accountExpires, LastLogon, LastLogonTimestamp, and LastPwdSet from String value.
import java.time.LocalDate;
import java.time.Month;
import java.util.Calendar;
import java.util.TimeZone;
/**
* This method will convert date into the 18-digit Active Directory timestamps,
* also named 'Windows NT time format', 'Win32 FILETIME or SYSTEMTIME' or NTFS file time
* @param terminationDate
* @return ldapTimeStamp
*/
public String getAcccountExpiresValue(String terminationDate) {
// "2020-07-18" - example date
String ldapTimeStamp = "never";
if (null != terminationDate && !"never".equalsIgnoreCase(terminationDate)) {
LocalDate currentDate = LocalDate.parse(terminationDate);
// Get day from date
int day = currentDate.getDayOfMonth();
// Get month from date
Month month = currentDate.getMonth();
// Get year from date
int year = currentDate.getYear();
// Print the day, month, and year
System.out.println("Day: " + day);
System.out.println("Month: " + month.getValue());
System.out.println("Year: " + year);
Calendar c = Calendar.getInstance(TimeZone.getTimeZone("UTC"));
c.clear();
c.set(year, month.getValue(), day); // your date
long time1 = c.getTimeInMillis();
c.set(1601, 1, 1);
long time2 = c.getTimeInMillis();
long ldap = (time1 - time2) * 10000;
System.out.println(ldap);
ldapTimeStamp = Long.toString(ldap);
}
return ldapTimeStamp;
}
You can validate the ldaptimestamp or the return String is correct or not follow below steps -
- Run the code.
- Get the string value.
- Open the link in browser - https://www.epochconverter.com/ldap
- Copy the output of string & paste it on converter.
- And press the button to convert.
- You will see the output as Date format on webpage.
- Please check the below image.
Please let me know if any one have any questions!!
Thanks,
IAM PDU
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Content to Moderator
This is very helpful. Thank you for posting it.
Current code assumes 12:00:00AM as time when converting the input date. If we have specific need to use certain time 06:00:00PM (for example), how could we do it? Any suggestions
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Content to Moderator
Hello @A_Desai ,
Try to add 6 hours in ldaptime(in form of millsec - which is equal to 21600000 ).
long ldap = (time1 - time2) * 10000 + 21600000;
Please let me know if you have question.
Thanks,
IAMPDU
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Content to Moderator
Hello @A_Desai ,
Ignore the above reply.
You just need to add below line of code
c.add(Calendar.HOUR_OF_DAY, <int hour>);
//Eg
c.add(Calendar.HOUR_OF_DAY, 6);
before below line
long time1 = c.getTimeInMillis();
Thanks,
IAM-PDU
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Content to Moderator
This is helpful. Thanks for posting!
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Content to Moderator
If just setting the initial accountExpires attribute when creating the account, a simple Date Format transform does the trick. Add the attribute to your source's AD create account XML. Map it to the end date attribute in the identity profile with the transform below. Change the input format to your needs.
"name": "AB_EPOCH_TIME_WIN32_Convert",
"type": "dateFormat",
"attributes": {
"inputFormat": "MM/dd/yyyy",
"outputFormat": "EPOCH_TIME_WIN32"
},
"internal": false
To update the attribute later, just sync it on the source.
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Content to Moderator
Hi @pholdridge ,
I have used above code to update accountExpires in AD , Some how it is showing one day before date
Example : i have given in CSV 12/30/2024,Im getting in AD 12/29/2024 07:00:00 PM
I wanted to populate same date with 12:00:00 PM .
Can you let me know if you have idea on this ?
Thank you,
Saikumar
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Content to Moderator
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Content to Moderator
Yes, this is normal. I believe it translates to "11:59:59 PM" the day before which is practically the next day.