# Create realistic lab users

•
•
•
•
•
•

In testing out some of my other tools over the last few weeks, I’ve found it necessary to create a some test users.  A lot of test users.  Not a normal “a lot,” either.  I needed hundreds of thousands at a minimum, a million if possible, as fully fleshed-out can be.  I needed some with Exchange mailboxes, some without.  I wanted locations, departments, job roles, and org charts.

I’ve found several scripts around the internet that purport to do parts of this, and can (to some extent), but nothing that gets close to the level of complexity that I wanted to entertain. And, you frequently had to supply your own names, addresses, and so forth.  Too much stuff to keep track of and copy around as I needed.

So, I wrote a tool.

It’s got enough possible combinations to get you to nearly 1 billion user accounts.  Yes, that’s billion with a b. I’ve got some plans to features to add to it, but for now, this should meet all most of your lab mailbox needs.  Over the course of 2 days, I used this to create 1.2 million users.  At that point, I figured it wasn’t going to break.

Oh, and it also can create and populate nested groups.

# Parameters

This is where all of the magic happens.  I’ll go over the parameters and what they do here.

Add the UPN suffix specified in UpnSuffix to Active Directory if it does not exist.  Yeah, I know. Now I’m just showing off.

## Company

Specify value for company.  By default, it will use Contoso, Ltd.

## Count

Integer to specify number of users. Minimum 1, maximum 965,000,000 and change.

## CreateGroups

Yes, I had to come back and add this feature, since it seemed like a glaring omission.  Using the Locations and Roles, the CreateGroups parameter will create groups containing both users and roll-up nested groups.  It further adds realism to the environment.

## CreateMailboxes

Use this switch parameter to create mailboxes (as opposed to only creating AD users).  It will bark at you if you specify this without specifying an Exchange server.

## Domain

Specify domain suffix to use for UPN and PrimarySmtpAddress.  The domain doesn’t have to be part of the forest UPN suffixes or an Exchange accepted domain.  However, if it’s not an Exchange Accepted domain and you create mailboxes, at some point, when the address book is updated, the default address policy may interfere with it (unless you flag the mailboxes to not inherit the email address policy).

## ExchangeServer

Specify Exchange Server hostname.  The script will attempt to connect via Kerberos authentication; please use the NetBIOS name or a registered SPN.

## OUPath

Specify OU path under which to create users. If it does not exist, the path will be created. The syntax will be checked for validity; if the path specified
cannot be created (such as incorrect forest), the script will exit.  By default, the script will create a test OU at OU=”Test Accounts,DC=<domain>,DC=com,” and then a series of OUs underneath it that map to the state and department variables.

## UpnSuffix

Value for UPN suffix. Default value is forest DnsDomainName. If this value is specified, it will be used in place of the current DomainName value.

# Examples

Now, on to some examples.

.\Create-LabUsers.ps1 -CreateMailboxes -ExchangeServer Exchange1 -AddUpnSuffix -UpnSuffix contoso.com -Count 5000

Create 5,000 mailboxes using Exchange server Exchange1. Add the UPN Suffix contoso.com to the forest.

.\Create-LabUsers.ps1 -UpnSuffix fabrikam.com -Count 5000 -Company "Fabrikam, Inc." -OUPath "OU=Fabrikam Users,DC=domain,DC=com"

Create 5,000 AD user accounts in a structure starting at OU=Fabrikam Users,DC=domain,DC=com.”

One of the fun aspects was figuring out how to provision groups in a way that would make sense.  As I mentioned in the parameter description, I ended up using the user job titles in conjunction with their state location to create groups.  In this example, you can see that the script has created a number of groups and relationships.  The “Consulting Manager – New York” group was created because there are users in the OU=Consulting,OU=New York,OU=Test Accounts container that have the job title “Manager.”  The group “Consulting Manager” was created to hold all of the “Consulting Manager – <state>” groups.  And, as you can also see, users with the title “Manager” are eligible to have direct reports.

If a user is created in an OU that already has someone with a Manager title, they will get assigned that user as a manager.

As always, let me know what works and what doesn’t for you guys.  Until then, bulk up in a steroid-free way using this script over at https://gallery.technet.microsoft.com/Create-Realistic-Lab-Users-b756fedf.

Helping companies conquer inferior technology since 1997. I spend my time developing and implementing technology solutions so people can spend less time with technology. Specialties: Active Directory and Exchange consulting and deployment, Virtualization, Disaster Recovery, Office 365, datacenter migration/consolidation, cheese.

1. NS says:

Nice practical script.

Just wondering how can I add parameters to enable users for Lync/Skype aswell ?

1. I was actually going to add that in. 🙂 There are a handful of additional attributes to populate to make users show up like Skype/Lync on-premises.

1. Jonathan Christie says:

Did I ever sent you my updated script with the lync/skype enablement?
Let me know if I didn’t!

2. Anonymous says:

(The content was deleted per user request)

3. Jonathan Christie says:

cool script. I’ve had to make a couple of changes. One was to avoid an ambiguous parameter.
line 536 – Ambiguous argument ‘-Member’. Changed -Member to -Members

The other was to fix the same issue TBEB had – and to cater for a longer domain name (ie homelab.domain.com, not just domain.com)

4. Jonathan says:

Excellent tool for the homelab.
Had to change line 536 – Ambiguous argument ‘-Member’. Changed -Member to -Members

1. Aaron Guilmette says:

Interesting. Looks like a typo on my end. It didn’t return ambiguous when I’ve tested, which is probably how I missed it. What version(s) of Windows are you running? I’ll update the posted version. Thanks!

5. Jonathan says:

Cool script – really useful.
Changed line 536 to -Members as -Member is ambiguous?
Had the same issue with a subdomain (my lab is homelab.domain.com, not domain.com) so altered the CreateOU procedure to cater for it.

Write-Log -LogFile $Logfile -LogLevel INFO -ConsoleOutput -Message “Organizational unit$($Path) does not exist. Creating.” [array]$OuFullPath = $Path.Split(“,”) [array]::Reverse($OuFullPath)
$OuDepthCount = 0 foreach ($obj in $OuFullPath) { If ($OuFullPath[$OuDepthCount] -like ‘DC=*’) { if ($ou -like ”)
{
#top level, do not insert ‘,’
$Ou =$obj
}
else
{
$Ou =$obj + “,” + $Ou } # Do nothing else, since Test-Path will return a referral error when querying the very top levels } Else { #Write-Host Current item is$obj
$Ou =$obj + “,” + $Ou When reporting on the number of users created, it always seems to be one short (ie does [1/10] to [9/10]) I havent dug into that yet 1. Aaron Guilmette says: As previously noted, I’ll update the -Member(s) parameter. It didn’t return ambiguous for me, which is probably how I missed it. As to the OU depth modification, I’ll dig into that as well. I built this function for another tool (and just re-used it here). My lab doesn’t have multiple subdomains, so I want to go through and try it in your configuration and some additional configurations with domain structures before I commit the change. Thanks for putting some sample code around it; if you could share the error that you are receiving, I’d be very interested in that, too. I think I found the counting error. I used “for ($i = 1; $i -lt$Count; $i++)”; I updated it to$i -le $Count, and that seems to have resolved that error. Thanks for the feedback! 6. TBEB says: this is great…. Can’t seem to get it to work with corp.domain.com though. It keeps trying to use domain.com only. 1. Aaron Guilmette says: Where are you seeing the domain.com instead of corp.domain.com? I just ran it in my lab (Windows 2012R2) for 500 users, and it seemed to work fine. I ran: .\Create-LabUsers.ps1 -Count 500 -Domain corp.domain.com -OUPath “OU=subdomaintest,dc=forest,dc=com” and both the mail and UPN attributes were populated correctly. 2. Jonathan Christie says: around line 270, I changed the CreateOU procedure, to cope with this (I just know this formatting is going to get messed up!) [array]::Reverse($OuFullPath)
$OuDepthCount = 0 foreach ($obj in $OuFullPath) { If ($OuFullPath[$OuDepthCount] -like ‘DC=*’) { if ($ou -like ”)
{
#top level, do not insert ‘,’
$Ou =$obj
}
else
{
$Ou =$obj + “,” + $Ou } # Do nothing else, since Test-Path will return a referral error when querying the very top levels } Else { #Write-Host Current item is$obj
$Ou =$obj + “,” + \$Ou

This site uses Akismet to reduce spam. Learn how your comment data is processed.