Wednesday, December 3, 2014 =========================== makecitizen ----------- {sysops, scripting, adduser, chfn} Paul Ford sent out an e-mail to the tilde.club waitlist pointing at ~pfhawkins's list of other tildes, so I'm getting signup requests. There are enough that I want to write a script for adding a new squiggle.city user. I'm not determined to be very fancy about this right now; I just want to save some keystrokes. The first thing I do is google "adduser". `adduser(1)` is basically just a front end to `useradd(1)`. (This distinction will never stop being confusing, and should probably be a lesson to anyone considering that naming pattern.) I learn via Wikipedia that the metadata (name, room number, phone, etc.) which adduser prompts for is called the [GECOS field](http://en.wikipedia.org/wiki/Gecos_field), and is a relic of something called the General Electric Comprehensive Operating System, which ran on some machines at Bell Labs. You can change that info with `chfn(1)`. What my script needs to do is: 1. create a user with a given `$USERNAME` 2. generate a random password for the user and tell me 3. do `chage -d0 $USERNAME` 4. put a given public key in `~$USERNAME/.ssh/authorized_keys` You can't log in to squiggle.city with a password, so why go to the trouble of setting a random one and forcing users to change it at their first login? Mostly because users are going to need to know a password for things like changing their shell or in the case that they get operator privileges one day. This is what I come up with, after a couple of even dumber iterations: #!/bin/bash CITIZEN=$1 KEYSTRING=$2 # Complain and exit if we weren't given a path and a property: if [[ ! $CITIZEN || ! $KEYSTRING ]]; then echo "usage: makecitizen " exit 64 fi # this should actually check if a _user_ exists, # not just the homedir if [ -d /home/$CITIZEN ]; then echo "$CITIZEN already exists - giving up" exit 68 fi PASSWORD=`apg -d -n2` adduser --disabled-login $CITIZEN echo "$CITIZEN:$PASSWORD" | chpasswd chage -d 0 $CITIZEN echo "$KEYSTRING" >> /home/$CITIZEN/.ssh/authorized_keys echo "passwd: $PASSWORD" exit 0 This is used like so: root@squiggle:~# ./makecitizen jrandomuser "ssh-rsa ..." It'll still do `adduser` interactively, which is fine for my purposes. I think this would be improved if it took a fullname and e-mail as input, and then sent that person a message, or at least output the text of one, telling them their password. It'd probably be improved even more than that if it operated in batch mode, was totally idempotent, and could be driven off some separate file or output containing the set of users. (Thoughts like this are how systems like Puppet and Chef are born.)