Recently I had someone contact me because they were looking for a script that would pull users from a CSV, and then import them into Open Directory on OS X Mavericks Server. Always up for a challenge I wrote a bash script to grab the users then send them to the Open Directory domain.
This script brings in the first name, surname, student ID and password from a CSV (the path can be specified in the only argument the script requires, which is the path to the CSV). The shortname is derived from the first name, surname and student ID. For example, Steve Miller with the Student ID of 654321 becomes sm654321.
To run the script, you would enter something like this:
And, using the example Users.csv provided in the Gist (please bear in mind that the Gist automatically removes the trailing blank line, please add it before running the script), you would expect something like below:
2013-12-11 21:49:03: Added Joe Smith (js123456) to /LDAPv3/127.0.0.1.
2013-12-11 21:49:06: Added Bill Jones (bj987654) to /LDAPv3/127.0.0.1.
2013-12-11 21:49:09: Added Steve Miller (sm654321) to /LDAPv3/127.0.0.1.
For each user, the commands take between 3 to 4 seconds. That includes creating the user along with adding them to the groups. As noted in the bash script, you must ensure your CSV has Unix (CRLF) line endings, and a blank line at the end of the script. If it doesn’t have the correct line endings, it’ll fail completely. If you don’t have a blank line at the end, the last person in the list won’t be added.
Thankfully, adding this user through dscl creates the proper AuthenticationAuthority so the user is set up with Kerberos v5 and Apple Password Server. By default, the user will be added to the local groups com.apple.access_radius, com.apple.access_afp and com.apple.access_addressbook, and the network group workgroup.
Here’s a dump of a user created through this script:
dsAttrTypeNative:objectClass: person inetOrgPerson organizationalPerson posixAccount shadowAccount top extensibleObject apple-user
;ApplePasswordServer;0xdb945916625111e39e62000c2928b48d,1024 65537 128972542829193592982355741981221062100920762016712038819623846465209128342622049783124389838185059988320142773235291480753225648977678597461748953848863734839600213928074142175413820927534135441280785829108224574601521657224863604777924988844508041132576614047193318182335513084715122081757952216834576233343 email@example.com:10.1.125.120
Student ID: 654321
Note: I’ve tested this script a fair bit, but don’t blame me if your Open Directory screws up! Always ensure you have a known-good backup before running a script you got off the internet. I’ve tried to get this script as perfect as possible, but there’s always bugs because not every environment is the same.
Along with adding users to your OS X Mavericks Server’s Open Directory you can also add groups to contain specific users to specific groups. For example, your sales team might have their own group called sales that provides them specific file sharepoints, jabber group and even add a special group mailing list for all users in that group. The group also allows you to specify different ACLs for each group.
First, I recommend following my guide adding users to add users to your Open Directory domain because groups are pretty useless without users! Anyway, onwards and upwards.
Okay, jump over to the Server app and load up the Groups section. If this is a base installation with Open Directory, you should only see one group in the Local Network Groups and it’s called Workgroup. By default, any user you add to the Open Directory domain will be added to this group. Given that I’m still rolling with characters from The Office, I’ll add some groups that relate to the users we added earlier. Click the plus in the bottom-left corner to add a new group.
First off, I’m going to make a group called Accounting. For the Full Name, enter Accounting and the Group Name will be accounting. Once you’ve entered those details, go ahead and click the Create button to add the group. Initially when you add the group there’s hardly any configuration aside from the name. Believe me, there’s more configuration to be done once you’ve added the group!
You’ll now be taken back to the list of groups, but now the group you just added will be in that list. Hooray! But we can’t celebrate yet because our group has no one in it! Let’s change that. Double click on your group to modify the settings and add/remove users.
Alrighty then, we can now modify some settings. First thing you’ll notice is that you can rename the “nice” name of the group, but you can’t change the shortname. Basically, if you didn’t name your group correctly the first time and you want to change its name, just delete the damn thing and create a new one. This may be more tedious if you’ve been using the group for a while, so make sure you do it right the first time. Next thing is giving the group a special shared folder on the Server, which is located at /Groups/<groupshortname> on the server. Enable this if you want that folder to be enabled, otherwise if you have your own folder structure you’re following, you can just add this group to the folder’s ACL.
Next is making the group members all buddies in Messages (or jabber). Enable it if you want the members to automatically be friends if they have the Messages app set up. If you’re not using the inbuilt Messages server, this option won’t need to be enabled. For the curious, if you enter the following command into Terminal, you’ll be shown all the groups and their Messages autobuddy status.
sudo serveradmin settings accounts
For example, if I were to enable or disable autobuddy via Terminal for the group accounting, I would enter the commands below:
The next easy option is setting up a mailing list which, when email is sent to that address, will be sent to all the members of the group. This email address is the group’s short name. For example, firstname.lastname@example.org or email@example.com. By default, only members of the group can send emails to that mailing list, otherwise, enable the “Allow mail from non-group members” to enable emails from anyone (yes, it’s literally everyone – not just people in the Open Directory domain).
It’s now time to add members to the group! Not only can you add users to a group, but you can also add groups to other groups! There’s a very cool hierarchy that you can configure with users and groups, but don’t over-complicate it otherwise your ACL precedence and inheritance are going to be very, very confusing. When you click the plus you can either start typing in a user name or group name (and it will auto suggest then click on the user to add it), otherwise, start typing browse then select Browse to bring up a list of all applicable users and groups that can be added to the group.
As per usual, you can add keywords and notes for the group. Once you’re done editing the group, click OK to save your changes.
As with every other OS X Server release there has been a program called Workgroup Manager (internally I’ve heard the nickname Workgroup Mangler) which shows you all the users, groups, machines and machine groups for Open Directory domains. First off, Workgroup Manager isn’t distributed with Server so we need to download it seperately off Apple’s website so click here to download. Once you’ve downloaded and installed Workgroup Manager, open it up and connect to your server! Go to Server then click Connect…
Enter details for your local server to connect. For example, the address will be the FQDN (remember what that stands for?) so my server will be mavericks.pretendco.com. If you want to make any edits you’ll need to be logged in as the Master Directory Administrator (or any other user you’ve given Server administration rights to). If you’re just connecting to browse the Open Directory domain, log in as any admin user (for example, my Server Administrator login for the Server machine gives me read-only access to the Open Directory domain). Next, enter the applicable password. Hit Connect to… you know… connect.
If all goes well and you’ve entered the correct details you should now be shown a list of all the users in your Open Directory domain! Hooray!
You’ll notice that in the list of users, any user that has a pencil in their icon means that they have administration rights for the Open Directory domain you’ve connected to. Anyway, just above the list of users are four icons, the second one from the left is Groups – click it.
Excellent, we can now see all the groups in the Open Directory domain. Clicking on any group will show you the basic settings for the group, you can also change memberships for the group and even the Group Folder. Have a look around in Workgroup Manager, but make sure you know what changes you’re making, you could permanently damage a user or group by making the wrong change (word of advice, don’t change short names or IDs).
Command Line Goodness
Accessible via Terminal is the very powerful command dseditgroup which as you might guess, allow you to edit directory service groups. The name of the command however is a bit of a misnomer given that you can do more than just edit the group. I personally think the command should be called dsgroup but that’s just me. Anyway, now onto the usefulness of this command. Given that we’ve been playing with the group accounting, let’s use this command to show us details about the group!
dseditgroup -o list accounting
Essentially what we’re doing here is using the -o flag (otherwise known as operation), we specify that we’re requesting a list of the accounting group. Here’s the output of dseditgroup for the group accounting on my system:
Or if if the user isn’t a member of the group, you’ll get the following response:
no jhalpert is NOT a member of accounting
Finally, another way of looking up groups via the command line is by using dscl, or the Directory Service command line utility. To get a list of all the groups in the local Open Directory domain, you would use the command below:
If you prefer to get a little bit more information, you can also request a specific value like GeneratedUID, RealName, AppleMetaRecordName or Member. If I wanted to get a list of the shortnames of members for each group I could enter something like below:
dscl /LDAPv3/127.0.0.1 -list /Groups Member
Which will in turn show me all the groups and their members (as requested):
Adding users to your server is probably going to be something you will end up doing the most once the server has been configured, so it’s important that you’re doing right. Personally I’ve found to be the most valuable tip when creating users is to… keep it consistent! I’ve been brought into far too many environments when the shortnames, email addresses and even names are inconsistent. Personally, it drives me nuts and can cause confusion between staff about what their username is.
You’d think it’s pretty basic and obvious, but you’d be surprised how many people forgo style and consistency. Now, how about we get to creating users.
Open the Server app and go to the “Users” tab. If you’re using Open Directory (which you should be!), ensure you’re looking at “Local Network Users”. You’d hate to add users to the server, only to find that you’ve added them to the local domain, rather than the Local Network Domain (Your Open Directory domain). So far, you should only see the Directory Administrator user. Let’s change that. Click the + (plus) in the bottom-left corner to add a user!
Full Name: — the full name of the user you’re adding. This is required, but does not have to be unique. While your Mac will require unique Full Names, Open Directory will allow you to have multiple users with the same Full Name.
Short Name: — the shortname of the user you’re adding. This is also required, and must be unique. You will not be able to add more than one user with the same shortname, so if you have two people with the shortname jhalpert, consider having a counter at the end of the shortname, e.g. jhalpert, jhalpert2, jhalpert3 and so on. I opt to have the first user with no number because you may not always know if someone with the same shortname will be added the server, so it just looks neater to have no numbers on the end of the first shortname.
Email: — the email for the user. This field isn’t required, and you can use it even if your server isn’t running Mail services. It’s purely cosmetic, and is used for the global address list in the Open Directory domain. Note: if you do use this field, but enter a different username and are running Mail on the server you must add an alias for that shortname, if you have jhalpert as the user shortname, but jim as the email username, Jim won’t receive email to jim until that name has been entered as an alias (coming up soon).
Password & Verify: — enter the users password twice. Best to generate a password, save it to a Numbers document then distribute the password to each user. Otherwise, set a generic one then require them to change password on next login.
Allow user to administer this server: — having this checked enables the user to successfully authenticate and have full authorisation for the Server app. Use it wisely.
Home Folder: — I absolutely despise networked home folders, they screw up so often and are very hard to fix (sometimes impossible to fix). I will always change this to None - Services Only. Takes up less space on the server too, as it doesn’t generate a home folder in /Users.
Keywords: — Add keywords for your user. This field is not required, and acts as a tag field for the user. It’s new to the GUI for Mavericks Server. I have yet to see a solid use case for this field, but I’m sure someone is using it to the full effect.
Notes: — Add notes for the user. Like keywords, this field is optional, and again, I’ve yet to see a good use for this field.
Given that I love the hit TV show The Office (US) (P.S. I really love the UK original too), I’m going to use fake users that are named after main characters from the show. My first user will be Jim Halpert. Following the style guide as above, you’ll be entering something like this:
Full Name: Jim Halpert
Account Name: jhalpert
Password:a random password of your choice (for this example, I just did pam)
Home Folder: None – Services Only
Notes: Often plays pranks on Dwight.
Note:In reality, keywords and notes aren’t important to the functionality of OS X Server and Open Directory, it can help with usability, however. Note that adding the keyword sales won’t add them to a group called sales. Keywords are purely for easy searching.
I’ve also added a picture for Jim, I suspect most people don’t realise you can drag and drop and image file onto the generic user picture to add a picture for that person.
Once you’ve added those details, click “Create” to add the user! If there’s any errors, you’ll be notified and the window won’t change, otherwise, you should be redirected back to the Users list (with your new user in the list!)
A handy feature in the Server app is the ability to restrict specific users to specific services. For example, you might say that newer employees are not allowed access to the VPN service, or maybe you want a shared account that only has access to File Sharing or collaboration services.
First off, what is a SACL? SACL stands for Service Access Control List, which, as the name would suggest, are lists that define user and group access to each service in OS X Mavericks Server. The lists themselves aren’t necessarily files in OS X, they’re memberships to specific groups in the local directory. For example, the service Contacts is actually a membership to the group com.apple.access_addressbook.
By default, all users are allowed access to all services. To change a specific users access to a group, you can do one of two things. The first option is to right click on the user (in the Users list) and then click “Edit Access to Services…”. You’ll be shown a list of the most common services (note: not all the services), where you can uncheck each box you don’t want the user to have access too.
Alternatively, you can go to the Groups section of the Server app and change the membership there. First off, you’ll have to enable to option to see system accounts, as they are hidden by default. Go up to View, then click on “Show System Accounts”. Now you’ll see a huge list of accounts, lots with interesting names. Scroll down until you get to the groups starting with com.apple.access_. If you open up those groups, you can add and remove members from there. Otherwise, you can go to the user in the Users section of the Server app and add or remove group memberships from there.
New in OS X Mavericks Server is the ability to add users that conform to a specified template. You might decide that most users only need access to AFP, Contacts, Calendars, and Mail. You also decide that they won’t have a home folder (services only) on the server and cannot administer the server. To make a template, go to the Users section in Server app, then click the gear in the bottom-left corner and click on the “Edit Templates…” button.
Hit the plus to create a new template! I’m going to call mine Standard Sales User as I want to use it for all standard sales people.
Next, I’m going to ensure that “administer this server” is unticked, because standard sales users shouldn’t be allowed to modify the server in any way! Next, change home folder to “None – Services Only”. Then, change Login shell to “/bin/bash/false” (the default for OS X Mavericks Server).
Leave the Primary Group as staff, you don’t want to mess with that as the user may never be able to log in. Next up, with groups we can utilise what we learnt with SACLs to restrict what groups (and services) they have access too. As with all users, I’ll put them in the default “Workgroup” group, but we’ll also add them to a few other groups. As I mentioned, I want to restrict these users to only having access to several services. These services are AFP, Contacts, Calendars and Mail. Click the + (plus) for adding groups, and enter the following groups: com.apple.access_afp, com.apple.access_addressbook, com.apple.access_calendar and com.apple.access_mail.
If you want to add or remove any other services, refer to the list below which has the service name and group name for the Services in OS X Mavericks Server.
Finally, you can add keywords and notes for the user template. I’m just going to add sales for a keyword, and that’s it. Finally, click “Done” to add the template. Now to test out the template!
You’ll now notice that when you go to add a new user, at the top of the form you’ll have a new field called “Template” that has a drop-down menu of all your templates! I’m going to enter a fake account for a user called John Citizen. Check the image below for my configuration:
Now, click “Create” to create the user from the specified “Standard Sales User” template. Once the user has been created, right-click on the user then click “Edit Access to Services…”. This will bring a window that shows you all the services John Citizen is a member for. As you’ll see, all the services we entered above are ticked (with exception for File Sharing, as that combines AFP and SMB).
Excellent, John has the right privileges and is associated with the right groups, all thanks to our user template! I believe at this stage the User Template system is still in its infancy, but could grow to become a really powerful tool. I’d love to see the ability to customise the way it grabs the full name and brings that across to short name and email address.
In most cases I set up Open Directory after doing the initial server and DNS configuration. Most of the services that OS X Server have hooks into the Open Directory database, so why not configure it now then do the other services after.
If you intend on using Open Directory properly (this includes LDAP and Kerberos), then you must ensure your DNS is healthy before continuing. One wrong character can screw up your entire Kerberos realm and trust me, you don’t want to have to go back and fix that mess (I’d rather punch myself in the face). To check the status of DNS on your server, enter the following command:
sudo changeip -checkhostname
If your result is not “The names match. There is nothing to change.” then you’ve got unhealthy (and sad) DNS. Fix it.
So your DNS is all healthy? Great, let’s continue. Open the Server app, but wait! Open Directory isn’t listed there?! Did Apple kill Open Directory?! Nope, see that Advanced section in the list on your sidebar? Mouse over it and click “Show”. You may now breathe normally. Click on the Open Directory button to view its section in the Server app. Even at the best of times the Open Directory tab in Server is pretty boring, but it’s especially boring when the service isn’t even running. Let’s change that and set up an Open Directory Master! Start by clicking that nice On button in the top-right corner.
This initial setup wizard hasn’t changed visually since Mountain Lion, but it’s worth going through if you never used Mountain Lion Server! Given that we don’t have an existing Open Directory domain, but we want to make one, we’ll go with the first option, “Create a new Open Directory domain”. Click Next.
By default, OS X Server suggests Directory Administrator and diradmin as the name for the Directory Administrator. My preference is to use Master Directory Administrator, and masterdiradmin respectively, as the server is the Open Directory Master. It’s purely a stylistic choice, just make sure you have the details saved somewhere (in 1Password I should hope). For this example, I’m using a very basic password, in the real world I would use a randomly generated one, maybe something like this: e9uZxrcsY6vwJe3y6CvK. Click Next
Next up is your organisation name and contact email address. Given that these details are used in your SSL certificate or CSR, you must ensure these details are correct. Click Next.
In your setup, confirm that your details are all correct before clicking the Set Up button. You don’t want to find down the track you entered wrong details. For the curious, before you click Set Up, open a Terminal window and enter:
tail -f /Library/Logs/slapconfig.log
When you click Set Up you’ll see lots of info fly by as it creates the Open Directory domain.
We can now do a quick test using the dscl command to ensure Open Directory is happy. Using those Directory Administrator credentials we used in set up, we can use a feature of dscl called authonly which, as you would expect, tests for authentication only. See the example below:
This says that datasource we’re using is LDAPv3, and the location of that is 127.0.0.1. We then add the flag -authonly to tell dscl we’re just testing for authentication. Finally, we send over the username and password. Given that the password is being sent as cleartext, only do this when you’re physically at the server during set up (or if you do it remotely, do it with a standard user account, not an administrator account). When you press Return (or Enter) to send the command, you won’t get anything returned if it’s correct. Here’s two examples of authentication failure:
See the difference? You get an eDSInvalidSession with a bad password, and an eDSAuthFailed with a bad username. It’s handy to know the difference between the two errors, it may come in use one day when testing.
If you’re really anal about testing, you can also test authentication with Kerberos. Here’s the structure of the command:
First off, we’re using the kinit command, which acquires the initial Kerberos ticket (but can also renew old tickets). Our first flag is -V, which gives us some verbosity when testing kinit – I like verbosity when testing, so we’ll use it in our command. Next up is -S host/server_hostname@KERBEROS_REALM, let’s break this down a little more. the -S means we’re using a realm other than krbtgt/LOCAL.REALM, which is appropriate when testing Kerberos on any other system other than the Kerberos server itself. Technically, we can simplify the kinit command, so that will be reflected below. Finally, is od_user@KERBEROS_REALM. At this stage, the only user in the Open Directory domain is masterdiradmin (or the username for your Directory Administrator). Given that we’re currently only using the one Open Directory server, we know that our KERBEROS_REALM will be MAVERICKS.PRETENDCO.COM (all caps your host name).
kinit -V od_user@KERBEROS_REALM
Now that we’ve got our simplified command structure, use the command below in Terminal:
kinit -V masterdiradmin@MAVERICKS.PRETENDCO.COM
You’ll be prompted to enter in the password for the user (you could use -stdinpass and echo the password, but that’s for another day). If all is successful, you should see something similar to below:
Placing tickets for 'masterdiradmin@MAVERICKS.PRETENDCO.COM' in cache 'API:C7F85975-55A4-4930-8DC3-6D668D209087'
The long UUID you see in the cache string is the unique identifier for that ticket session. To check out the details for your ticket, enter:
klist will give you minor details about your ticket, but adding the -v flag will increase the verbosity of output, which you could use for troubleshooting (or just general information gathering or learning). Here’s an example of the output you might expect from klist with the verbosity flag:
Alrighty then, everything appears to be in order! We now have a happy Open Directory Master than is running and accepting connections. Going back to the Server app, you can see a gear in the bottom-left corner of the window where you can change the Global Password Policy, archive the Open Directory Master, or promote a Replica to Master.
We can also get more information regarding Open Directory using serveradmin and the command line. See below for the status:
sudo serveradmin status dirserv
And your output should be as follows:
dirserv:state = "RUNNING"
If you want to get more information regarding the status of Directory Services, do this command:
There’s a lot to see there, and most of it’s not worth going through if you’re going to be running a small network with 1 server. Nonetheless, it’s still interesting to see all the configuration details for Directory Services.