Saturday, February 16, 2008

Perl Script For User Account Addition - C/Shell/Perl Porting Part II

Hey there,

NOTE: Code revision 2/16/08 --
$home = "$ARGV[0]/$ARGV[0]";
should be
$home = "$ARGV[0]/$ARGV[1]";
Code below updated - thanks to the folks who caught that :)

A brief note before we lay bare today's script. This script, and all the scripts we use here to demonstrate how to port between C, Perl and shell code are all just examples. It is not advised that you actually use these scripts to directly manipulate your system passwd and shadow files. It shouldn't cause a problem, but facilities exist to do this already (If you do use these, run "pwconv" afterward, just in case). This working code/script is merely meant to demonstrate principles of porting between languages.

Now that we have gloom and doom out of the way, let's check out today's version of the C code to add user accounts that we introduced yesterday. This should run equally well on both Linux and Unix - Pick a flavor.

The most obvious thing you'll notice with today's Perl code is that it's a lot easier to read and understand. Porting from C to Perl has demystified a lot of what we're actually doing. And the shell script to come tomorrow will make the process (and actions involved) even more accessible :)

If you find that you have any issues with the code (anything seems presumptuous or convoluted), please refer back to yesterdays post on the original C code, as a lot of those issues were addressed up front.

Hope you enjoy this, and best wishes :)

Creative Commons License

This work is licensed under a
Creative Commons Attribution-Noncommercial-Share Alike 3.0 United States License


# Add Users, Set Up Profiles,
# Set The Password And Email
# An Admin
# 2008 - Mike Golvach -
# Creative Commons Attribution-Noncommercial-Share Alike 3.0 United States License

if ( $#ARGV != 2 ) {
print "Usage: $0 [dirname - no slashes ] [ logname ] [ comment - in quotes ]\n";

$userdir = $ARGV[0];
$username = $ARGV[1];
$commentfield = $ARGV[2];
$home = "$ARGV[0]/$ARGV[1]";
@argument2 = split(//,$ARGV[1]);
$argument2 = @argument2;

if ( $argument2 > 8 || $argument2 < 5 ) {
print "Please choose a logname between 5 and 8 characters!\n";


$count = `awk -F":" '{print \$3}' /etc/passwd|sort -n|tail -1`;
$usernumber = $count++;

print "\n";
print "Check this out before proceeding!!!\n";
print "-----------------------------------\n";
printf("Logname:\t%s\n", $username);
printf("Homedir:\t/%s/%s\n", $userdir, $username);
printf("Comment:\t%s\n", $commentfield);
print "-----------------------------------\n";
print "\n";
print "\n";
print "All of this ok?\n";
print "\n";
print "y or n\n";
print "\n";

$reply = <STDIN>;

if ( $reply =~ /n/i ) {
print "\n";
print "All right, give it another shot if you want!\n";
} elsif ( $reply =~ /y/i ) {
} else {
print "Only y or n - case insenstive allowed\n";
print "Try Again\n";

open(A, ">>/etc/passwd");
print A "$username:x:$usernumber:1:$commentfield:/${userdir}/$username:/bin/ksh\n";

open(A, ">>/etc/shadow");
print A "$username:*LK*:::::::\n";

mkdir($home, 0755);
chdir "$home";

open(A, ">>.profile");
print A "stty istrip\n";
print A "PATH=/bin:/usr/bin:/usr/local/bin:/usr/share/bin:.\n";
print A "export PATH\n";
print A "\n";
print A "\n";

chown($home, 1, $username);
system("chown ${usernumber}:1 .profile");
system("chmod 0644 .profile");

open(MAILER, "|/usr/lib/sendmail -t") or die "Cannot Open Sendmail!\n";
print MAILER "To: devnull\\n";
print MAILER "Subject: New User Added!!!\n";
print MAILER "\n";
print MAILER "$commentfield\n";
print MAILER "has a new account set up!\n";
print MAILER "The email address is $username\!\n";
print MAILER "\n";
print MAILER "Thank you,\n";
print MAILER "\t Mike Golvach\n";

print "\n";
print "All Done!!!\n";
print "\n";
print "Now set the Password!\n";
print "\n";
system("/usr/bin/passwd $username");
print "\n";
print "Password set!!! Take a break...\n";

, Mike