0 votes

Not sure if this is possible but is there a mechanism to query AD to get the latest "serialised" username.
We don't use proper names for usernames we use a logon name based on employee numbers for employees but we use a serialised number for contractors.
The employee side is fine but for contractors I want to be able to query AD live for the "highest" existing contractor logon name and create the next one in sequence.

A bridge too far maybe?

by (840 points)
0

Hello,

A bridge too far maybe?

Not at all, actually, however querying your AD for the highest existing logon name, sorting etc can take up much time, so we can suggest a solution that's a bit different, but will allow you to achieve your goal:

  1. When a new contractor is created, a Business Rule will be triggered before the user account creation. It will run a script that assigns the username.
  2. On the 1st launch, the script will query your AD for all contractor usernames and find the highest one in the sequence. Then, the script will increase the username by 1 and assign the thus generated username to the new user.
  3. What is important here is that the script will also save the generated username in Adaxes configuration.
  4. When a contractor is created next time, the script will simply read the last generated username from Adaxes configuration and add a +1 to that. Then, the script will check whether the new username is unique (in case someone creates a contractor is created outside of Adaxes). This will work much faster than searching for the highest username each time.
  5. Each time the script generates and assigns a username, it will store it in Adaxes configuration so that next time increasing the stored username by 1 generates a new username in the sequence.

If you are OK with such a solution, we will help you implementing it. To better understand the task, can you answer the following questions:

  • What is the format for contractor usernames? Simply a number or a combination of numbers and letters? Any limitation by length?
  • What is the difference between an employee and a contractor username? How can we distinguish between a contractor and a regular employee?
0

That sounds like a solution I'd already put to one side because of the potential issues with users created outside of the system but the post allocation check would fix that. (I just knew I couldn't code that myself)
I think the allocation of the number and commital to the Adaxes configuration would need to happen after my approvals are successful just in case we allocate and the request is rejected or the approval process is delayed.

The contractor format is Annnnnn always an A and then 6 figures. Employees start with an M or L but the contractors are only Annnnnn.
Would also like to exclude anything over A900000 as they are reserved for test accounts.
Also, instead of the first run trying to determine the latest number can we just set that manually? Easy enough to determine manually first time and the ability to control manually might be useful after an audit, might need to reconcile maybe.
Last thing I can think of is a limit on the number of times the allocation will increment based on the post allocation test, 5 increments might be an upper limit before it fails and says something is wrong!

Look forward to looking at the solution. Thanks.

1 Answer

0 votes
by (216k points)
selected by
Best answer

Hello,

To implement what you want, first of all, you need to somehow specify that a new user is a contractor. For this purpose you can, for example, add a boolean (True/False) attribute to the form for creating new users. It will serve as a flag to distinguish new contractors from other users. Setting the attribute to True will mean that a new contractor is created. This can be one of Adaxes custom attributes, for example, CustomAttributeBoolean1. Such attributes are not stored in AD, but can be used the same as any other attributes of AD objects.

Also, you'll need to create a Business Rule triggered before creating a new user that will generate and assign the next username in the sequence.

Finally, to give your users an idea about what the custom attribute is used for, you can change the name under which it appears in Adaxes.

To implement such a solution:

i. Add custom attribute to the form for creating users

For information on how to add an attribute to the form for creating users, see the following tutorial (starting from step 6): http://www.adaxes.com/tutorials_WebInte ... tomization.

ii. Create Business Rule to assign username

For information on how to create such a Business Rule, see the following tutorial: http://www.adaxes.com/tutorials_Simplif ... Script.htm. Use it as a guide.

  1. On step 5 of the tutorial, add the following script:

     $usernameFomrat = "A{0:000000}" # TODO: modify me
     $initialNumber = 1 # TODO: modify me
     $maxNumber = 900000 # TODO: modify me
    
     $settingsPath = $Context.GetWellKnownContainerPath("ConfigurationSetSettings")
     $settings = $Context.BindToObject($settingsPath)
    
     # Get the next contractor number from global configuration
     try
     {
         $number = [int]($settings.Get("adm-CustomAttributeInt1"))
         $number++
     }
     catch
     {
         # If no number is set in the global configuration, use the initial number
         $number = $initialNumber
     }
    
     $uniqueUsername = [System.String]::Format($usernameFomrat, $number)
     do
     {
         if ($number -gt [int]$maxNumber)
         {
             $Context.Cancel("Cannot generate a username for the contractor because the maximum allowed contractor number has been reached. Please contact your system administrator.")
             return
         }
    
         # Check whether the username is unique
         $searcher = $Context.BindToObject("Adaxes://rootDse")
         $searcher.PageSize = 500
         $searcher.SearchScope = "ADS_SCOPE_SUBTREE"
         $searcher.SearchFilter = "(&(sAMAccountType=805306368)(sAMAccountName=$uniqueUsername))"
         $searcher.ReferralChasing = "ADS_CHASE_REFERRALS_NEVER"
         $searcher.VirtualRoot = $True
    
         try
         {
             $searchResult = $searcher.ExecuteSearch()
             $result = $searchResult.FetchAll()
    
             # If the username is not unique, find a unique one
             if ($result.Count -ne 0)
             {
                 $number++
                 $uniqueUsername = [System.String]::Format($usernameFomrat, $number)
             }
         }
         finally
         {
             $searchResult.Dispose()
         }
    
     }
     while ($result.Count -ne 0)
    
     # Save the new number in the gloabal settings
     $settings.Put("adm-CustomAttributeInt1", $number)
     $settings.SetInfo()
    
     # Update the User Logon Name
     $Context.SetModifiedPropertyValue("sAMAccountName", "$uniqueUsername") # User Logon Name (Pre-Windows 2000)
     $upnSuffix = $Context.GetObjectDomain("%distinguishedName%")
     $userLogonName = $uniqueUsername + "@" + $upnSuffix
     $Context.SetModifiedPropertyValue("userPrincipalName", $userLogonName) # User Logon Name
     $Context.LogMessage("Contractor username: $userLogonName", "Information")
    
  2. In the script, modify the following to meet your requirements:

    • $usernameFomrat - specifies the contractor username format. Currently, it is set to the format you described, however, if you need to change it in the future, see the following MSDN article for instructions: https://msdn.microsoft.com/en-us/librar ... 10%29.aspx.
    • $initialNumber - specifies the initial number that will be used on the first run.
    • $maxNumber - specifies the maximum number; numbers higher than this won't be used.
  3. Also, you'll need to run the Business Rule only when the custom attribute is set to True. For this purpose, you need to add a condition. You will find information on how to do this on step 6 of the tutorial. You'll need to specify the following condition: If CustomAttributeBoolean1 equals True.

    where CustomAttributeBoolean1 is the name of the custom attribute you want to use.

iii. Change display name for the property

For information on how to change the name under which the property appears in Adaxes, see the following help article: http://www.adaxes.com/help/?HowDoI.Mana ... Names.html.

0

Hi,

I've implemented and tested that and it works beautifully!

Thanks.

I think the only thing I need now is a way to set the number in the global settings manually. Ideally I'd like a menu option in the Admin interface that displays the current setting and allows me to set a new setting but I don't know the "context". What object am I modifying (user, group, other).
Can you help with that please?

0

Hello support,

Is there a way I can set/reset the global setting holding the contractor number please? as below.

"I think the only thing I need now is a way to set the number in the global settings manually. Ideally I'd like a menu option in the Admin interface that displays the current setting and allows me to set a new setting but I don't know the "context". What object am I modifying (user, group, other).
Can you help with that please?"

Related questions

0 votes
1 answer

Hi I've added values to two attributes of an Oraganization Unit: adm-CustomAttributeText1 adm-CustomAttributeText2 I'm trying to extract these properties with a powershell ... But this does not provide the value set in adm-CustomAttributeText1. Any ideas?

asked Jan 28, 2013 by kjesoo (960 points)
0 votes
1 answer

I'm working on user deprovision and need to re-assign a user's home directory to the manager's home directory after disabling. I found a PowerShell script on this site to ... retrieve the same for the Manager? I'm a PowerShell novice, so excuse my ignorance.

asked Feb 26, 2021 by mkvidera (60 points)
0 votes
0 answers

Trying to configure a custom launcher in Thycotic Secret Server that will launch Adaxes on the user's local machine with the username and password passed as parameters. Has anyone made this work?

asked May 20, 2022 by amillard (20 points)
0 votes
1 answer

Hello, We have multiple Domain Controllers in single domain. let saya DC1.domain.com, DC2.domain.com, DC3.domain.com When we want to get LastLogon value, how can we get the latest LastLogon value among the three DCs?

asked Dec 19, 2021 by fachmi (170 points)
0 votes
1 answer

For creating a computer object, we want to check if the entered CN is already used in our AD. And for that we want to use a powershell script. An other dot ... powershell script should be start before creating the computer object, right? Thanks for your help.

asked Jun 4 by KEME (80 points)
3,588 questions
3,277 answers
8,303 comments
548,092 users