1
00:00:03,410 --> 00:00:06,170
Welcome to the exercise walk through.

2
00:00:06,260 --> 00:00:11,690
Now the goal of this particular exercise is to create a shell script that adds users to the same Linux

3
00:00:11,690 --> 00:00:14,760
system as that shellscript was executed on.

4
00:00:14,900 --> 00:00:17,930
This exercise actually builds upon the previous exercise.

5
00:00:17,930 --> 00:00:19,220
It's going to be very similar.

6
00:00:19,220 --> 00:00:22,160
We're just going to really make a few improvements.

7
00:00:22,430 --> 00:00:28,280
And by the way that first script you created in our scenario has been used by the helpdesk team to create

8
00:00:28,280 --> 00:00:30,100
accounts and they are really happy about it.

9
00:00:30,230 --> 00:00:35,300
But after using it for a little while they have some requests they would like you to make some changes

10
00:00:35,300 --> 00:00:35,780
to it.

11
00:00:35,900 --> 00:00:41,000
When you get a chance and of course you're so nice that you're going to oblige one of the requests they

12
00:00:41,000 --> 00:00:46,220
have is that they're kind of tired of coming up with passwords every time they create account and they

13
00:00:46,220 --> 00:00:51,200
think you could automate that for them just generate a password for the account so that they don't have

14
00:00:51,200 --> 00:00:52,630
to do that.

15
00:00:52,640 --> 00:00:58,700
Another thing that they found when using that particular script was that they already knew all the information

16
00:00:59,000 --> 00:01:00,880
that they were going to provide the scrip.

17
00:01:00,890 --> 00:01:05,000
However they would have to wait to be prompted in order to type in that information.

18
00:01:05,000 --> 00:01:10,430
They thought it would be just a little bit more efficient if they could just type everything right in

19
00:01:10,520 --> 00:01:15,100
at the command line all at once and not wait to be prompted.

20
00:01:15,110 --> 00:01:18,650
So again you go back to thinking about the requirements what the script should do.

21
00:01:18,770 --> 00:01:24,280
And a lot of these requirements are going to be exactly the same as you had in the first exercise.

22
00:01:24,290 --> 00:01:28,340
The first thing that's a little bit different is that you're going to name the script something else

23
00:01:28,340 --> 00:01:33,050
just to distinguish it from the previous script so that they know they're running the new script and

24
00:01:33,050 --> 00:01:39,390
not the old script so you decide to call this script add dash new dash local dash user data.

25
00:01:39,410 --> 00:01:46,280
Sh like your previous script it's going to enforce that it be executed with super user or root privileges.

26
00:01:46,460 --> 00:01:51,740
And if the script is not executed with super user privileges it will not attempt to create a user and

27
00:01:51,740 --> 00:01:54,350
simply return an exit status of one.

28
00:01:54,710 --> 00:01:59,000
Here's something you decide to add to the script that wasn't requested by the helpdesk team but you

29
00:01:59,000 --> 00:02:00,660
can see how this would be helpful.

30
00:02:00,740 --> 00:02:06,500
And that thing is to provide a usage statement much like you would find in a man page if the user executing

31
00:02:06,500 --> 00:02:10,140
the script does not supply an account name on the command line.

32
00:02:10,220 --> 00:02:12,890
And if they do that you teach them how to use the script.

33
00:02:12,880 --> 00:02:15,560
This script again is a little different than the last one.

34
00:02:15,680 --> 00:02:20,610
So maybe they're used to getting prompted But this script requires them to have a user name.

35
00:02:20,810 --> 00:02:22,780
So you're going to tell them about that.

36
00:02:22,940 --> 00:02:27,740
And when you tell them about that you're also going to exit your script with a status of one.

37
00:02:27,740 --> 00:02:32,390
Now speaking of supplying things on the command line you decide that the first argument provided on

38
00:02:32,390 --> 00:02:38,090
the command line should be the username for the account and any additional remaining arguments on the

39
00:02:38,090 --> 00:02:42,200
command line will be treated as the comment for the account.

40
00:02:42,200 --> 00:02:47,660
And that's pretty smart because the account is always going to be one word or one item and the description

41
00:02:47,660 --> 00:02:48,610
could be nothing.

42
00:02:48,650 --> 00:02:54,770
Or it could be a name like Jane Smith or it could be a description of an application for which the account

43
00:02:54,770 --> 00:02:56,210
is being created.

44
00:02:56,270 --> 00:03:01,390
The next requirement you've listed is to generate a password for that new account.

45
00:03:01,490 --> 00:03:05,930
And again you're not going to proffer this password you're just going to create it inside the script

46
00:03:06,650 --> 00:03:11,720
just like in your previous script you're going to inform the user if the account you're trying to create

47
00:03:11,720 --> 00:03:14,620
was not able to be created for some reason.

48
00:03:14,660 --> 00:03:19,880
And in that particular case you're going to exit the script with an exit status of one family you're

49
00:03:19,880 --> 00:03:24,500
going to display the user name the password and the host where the account was created.

50
00:03:24,500 --> 00:03:27,710
This is just like in your previous script.

51
00:03:27,740 --> 00:03:33,160
So at this point let's go ahead and use the existing virtual machine we used in the first exercise.

52
00:03:33,200 --> 00:03:39,810
So we'll move into that vagrant project folder.

53
00:03:39,820 --> 00:03:46,770
Now we just run vagrant up to start the virtual machine.

54
00:03:46,830 --> 00:03:53,300
Now connect to it with vagrant S-sh once you're connected you can move into the shared folder of four

55
00:03:53,380 --> 00:03:55,140
slash vagrant.

56
00:03:55,270 --> 00:03:59,710
At this point you can either create the script inside the virtual machine using your favorite editor

57
00:03:59,830 --> 00:04:06,520
beat them nano or I-Max or you can create this script on your local machine using your favorite editor

58
00:04:06,520 --> 00:04:07,170
there.

59
00:04:07,300 --> 00:04:12,550
But if you do that just remember to place your script in the shared folder which you'll be able to access

60
00:04:12,550 --> 00:04:16,670
here on the virtual machine and the forward slash vagrant folder.

61
00:04:17,050 --> 00:04:21,490
I'm going to use the vim editor and just create that here on the local machine so I'm going to type

62
00:04:21,490 --> 00:04:25,830
them add new local user dot sh.

63
00:04:26,020 --> 00:04:32,090
Of course it goes without saying that every script starts with a Shabak and then we're just going to

64
00:04:32,090 --> 00:04:36,060
provide some information a header if you will for this script.

65
00:04:48,540 --> 00:04:52,710
So here we're just saying that the script creates a new user on a local machine and that the first thing

66
00:04:52,710 --> 00:04:58,110
on the command line after the script has to be a user name and anything that comes after the user name

67
00:04:58,110 --> 00:05:11,410
will be considered a comment for the account.

68
00:05:11,420 --> 00:05:21,200
Next we're going to automatically generate a password.

69
00:05:21,350 --> 00:05:24,070
And finally we're going to display that information.

70
00:05:32,000 --> 00:05:38,000
Perhaps that's a bit verbose for a header but you can use this or your own language or even use the

71
00:05:38,000 --> 00:05:41,390
usage statement that we're going to come up with here in just a minute.

72
00:05:41,630 --> 00:05:47,390
So of course we really don't want to do anything unless the user that's executing the script is doing

73
00:05:47,390 --> 00:05:48,680
it with proper permissions.

74
00:05:48,680 --> 00:05:53,060
There's no reason to try to add a user account when you don't have root permissions.

75
00:05:53,060 --> 00:05:55,130
So let's check for that first.

76
00:05:55,130 --> 00:06:11,250
And again this is exactly the same thing you did in your first script.

77
00:06:11,280 --> 00:06:13,900
So if a user ID is not equal to zero.

78
00:06:13,920 --> 00:06:16,250
And that means the user is not root.

79
00:06:21,270 --> 00:06:26,950
And then we'll exit with an exit status of one and close out or if statement here.

80
00:06:27,010 --> 00:06:31,810
Now the next thing we want to do is make sure that they supply at least one argument.

81
00:06:31,810 --> 00:06:46,620
It's required that they give us a username so we'll go ahead and check for that next.

82
00:06:46,630 --> 00:06:53,980
So if the number of arguments is less than one then you can do this you can give them a usage statement

83
00:06:56,420 --> 00:07:00,080
and just echo back to them the command that they just executed.

84
00:07:01,050 --> 00:07:03,540
Tell them that the user name is required.

85
00:07:04,050 --> 00:07:09,720
And you're going to put a comment in brackets here because that's optional and there could be more than

86
00:07:09,720 --> 00:07:11,860
one comment or more than one word.

87
00:07:12,030 --> 00:07:19,410
And so to repeat that you just signify that with three dots here and then close the echo command.

88
00:07:19,440 --> 00:07:22,570
Now you don't have to use this exact statement.

89
00:07:22,590 --> 00:07:26,730
You could have come up with something on your own and you could have written this in paragraph form.

90
00:07:26,940 --> 00:07:33,780
But if you are used to reading man pages and built in help with bash you'll see this very same thing

91
00:07:33,780 --> 00:07:35,200
this very same format.

92
00:07:35,340 --> 00:07:37,770
So there's no use in reinventing the wheel here.

93
00:07:37,800 --> 00:07:41,670
We'll just go ahead and use the same thing that we see everywhere else.

94
00:07:41,670 --> 00:07:43,860
Again if you come up with something different that's totally fine.

95
00:07:43,860 --> 00:07:45,180
Obviously it works.

96
00:07:45,180 --> 00:07:49,140
You know this is not going to affect the execution of the program.

97
00:07:50,550 --> 00:07:52,600
We'll give them some more information here.

98
00:08:04,780 --> 00:08:08,920
And then we'll exit with one because the script didn't complete.

99
00:08:09,130 --> 00:08:14,800
And now that we're sure that they have provided a user name we can go ahead and assign that user name

100
00:08:14,800 --> 00:08:22,280
to a variable.

101
00:08:22,370 --> 00:08:29,330
So I'll just use upper case user underscore name and assign the value of whatever is in the first positional

102
00:08:29,330 --> 00:08:31,210
parameter to that variable.

103
00:08:33,060 --> 00:08:37,860
Now as you already know our requirements in the Help statement that we just wrote here that everything

104
00:08:37,860 --> 00:08:40,580
else on the line are considered comments

105
00:08:48,230 --> 00:08:53,660
since we've already assigned a user name to the value that was stored in the first positional parameter

106
00:08:53,660 --> 00:08:55,190
dollar on one there.

107
00:08:55,190 --> 00:08:57,680
We no longer need dollar sign one.

108
00:08:57,680 --> 00:09:04,730
So what we can do is use the shift command to shift everything down one more or less making dollar sign

109
00:09:04,730 --> 00:09:06,990
1 drop off or get chopped off.

110
00:09:07,130 --> 00:09:10,260
And then what is left obviously are the comments.

111
00:09:10,280 --> 00:09:20,110
So that means we can do this we can assign the variable comment to every thing else now remember dollar

112
00:09:20,110 --> 00:09:24,960
sign at sign is every positional parameter starting at 1 and beyond.

113
00:09:24,970 --> 00:09:27,820
So this captures everything that's left on the command line.

114
00:09:27,830 --> 00:09:34,030
Again running shift took the user name out of the positional parameters and then again what's left is

115
00:09:34,030 --> 00:09:36,030
going to be the comments.

116
00:09:36,070 --> 00:09:38,500
Now what you want to do is generate a password

117
00:09:42,560 --> 00:09:45,830
will assign this to the password variable.

118
00:09:45,850 --> 00:09:48,100
Again you could use any variable name that you would like.

119
00:09:48,100 --> 00:09:49,680
That's a valid variable name.

120
00:09:49,690 --> 00:09:51,970
This is just what I happened to come up with.

121
00:09:51,970 --> 00:09:58,720
Now we're going to use command substitution starting that with a dollar sign and then an open parentheses.

122
00:09:59,170 --> 00:10:04,180
And then here is where you'll put the command that will generate a password and previous lessons.

123
00:10:04,180 --> 00:10:09,610
We went over a few different methods and you just simply can pick one your favorite one or the one you

124
00:10:09,610 --> 00:10:11,480
think makes most sense and use it here.

125
00:10:11,500 --> 00:10:15,330
So you don't have to use this exact method to generate this password either.

126
00:10:24,560 --> 00:10:28,770
I'm going to create a forty eight character password so this is how I'll do it here.

127
00:10:29,210 --> 00:10:31,130
Now we have all the information we need.

128
00:10:31,130 --> 00:10:33,170
We got the username from the command line.

129
00:10:33,200 --> 00:10:35,310
We also got the comments from the command line.

130
00:10:35,390 --> 00:10:36,670
We didn't ask for a password.

131
00:10:36,670 --> 00:10:38,750
We went ahead and generated on our own.

132
00:10:38,870 --> 00:10:48,270
And so now we're ready to create the account.

133
00:10:48,440 --> 00:10:55,850
The dash C stands for comment and so will supply the comments to the dash see argument here.

134
00:10:56,670 --> 00:11:04,080
And we're going to put those comments in quotation marks so that they are treated as one thing one argument

135
00:11:04,080 --> 00:11:06,420
to the dash see option.

136
00:11:06,440 --> 00:11:10,390
Now we can use dash them to force the creation of a home directory.

137
00:11:10,490 --> 00:11:15,450
And now the only thing we have left is supply is the user name.

138
00:11:15,600 --> 00:11:19,860
At this point what we want to do is check to see if the user and command succeeded.

139
00:11:19,860 --> 00:11:24,480
Of course if it didn't succeed for some reason we don't want to tell the user that hey we created an

140
00:11:24,480 --> 00:11:26,710
account when we actually didn't.

141
00:11:26,790 --> 00:11:29,690
So we'll want to exit out of our script as well.

142
00:11:29,850 --> 00:11:32,900
So what we can do here is check for the return status

143
00:11:52,160 --> 00:11:59,140
so of dollar sign questionmark which contains the exit status or return status of the most recently

144
00:11:59,140 --> 00:12:00,560
executed command.

145
00:12:00,580 --> 00:12:03,810
If that does not equal zero then something went wrong.

146
00:12:04,000 --> 00:12:05,650
So then what we'll say is

147
00:12:09,470 --> 00:12:15,110
the account cannot be created and we are going to exit with a non-zero exit status as well.

148
00:12:16,370 --> 00:12:18,670
Now we need to set the password on the account

149
00:12:21,900 --> 00:12:31,460
and we'll just echo the password into the password command with the standard in option and then we'll

150
00:12:31,460 --> 00:12:34,530
supply the user name that that password is for.

151
00:12:34,850 --> 00:12:40,190
So again the output of the command that precedes the pipe that comes before the pipe is used as the

152
00:12:40,190 --> 00:12:45,020
standard input of the command that comes after the pipe which in this case is password.

153
00:12:45,140 --> 00:12:56,130
And we're telling it to read standard and with dash dash SDD i n.

154
00:12:56,350 --> 00:12:59,380
Let's check to see if the password command succeeded as well.

155
00:13:12,400 --> 00:13:17,410
Well just tell the user that the password couldn't be set and then exit with one.

156
00:13:17,410 --> 00:13:22,550
The last thing we need to do is to force a password change on first log in for the account.

157
00:13:22,600 --> 00:13:32,010
So we'll do this force password change in.

158
00:13:32,100 --> 00:13:42,150
Now we're just going to display the information.

159
00:13:42,190 --> 00:13:47,140
Print out a blank line because we know those password commands generate some output so we just separate

160
00:13:47,140 --> 00:13:50,760
them with a blank line and then we'll display the username

161
00:13:57,340 --> 00:13:58,510
another blank line.

162
00:14:13,240 --> 00:14:17,140
And will display the hostname name which is a built in variable in bash.

163
00:14:18,070 --> 00:14:20,980
We've made it to the end here obviously the script succeeded.

164
00:14:21,100 --> 00:14:25,300
So we're going to exit with an exit status of zero.

165
00:14:25,300 --> 00:14:27,850
Now it's time to save our changes.

166
00:14:27,880 --> 00:14:31,300
Now remember to set the permissions on the script before you try to execute it.

167
00:14:31,300 --> 00:14:38,070
So we'll do that now with chmod 755 add new local user data sh.

168
00:14:38,320 --> 00:14:41,080
Now let's go ahead and test the script.

169
00:14:41,080 --> 00:14:43,470
Of course we're creating accounts so we need root privileges.

170
00:14:43,480 --> 00:14:48,250
And one way to do that is to use the sudo command so will you Sea-Doo and then will you stop forward

171
00:14:48,250 --> 00:14:50,380
slash and the name of the script.

172
00:14:50,530 --> 00:14:56,500
By the way I'm using tab completion here I just typed in the first few letters of the command name there

173
00:14:56,500 --> 00:15:01,900
and then hit tab and I let bash complete that for me so I don't think I'm a super fast typer.

174
00:15:01,900 --> 00:15:05,310
I'm just using some shortcuts and that's when you probably already know.

175
00:15:05,320 --> 00:15:07,790
But just to be clear here that's what I'm doing.

176
00:15:08,020 --> 00:15:11,050
So now what we need to do is supply a user name.

177
00:15:11,230 --> 00:15:15,750
So we'll create the account name of J L O C K E.

178
00:15:16,150 --> 00:15:23,260
And then what we can do here is provide some comments and one common comment for a user account is obviously

179
00:15:23,260 --> 00:15:26,230
the user name that we'll be using it the person's name.

180
00:15:26,440 --> 00:15:28,540
So we'll use John Locke.

181
00:15:28,540 --> 00:15:32,950
That's the person that's going to be using this account and we'll hit enter to go ahead and create this

182
00:15:32,950 --> 00:15:33,560
account.

183
00:15:34,360 --> 00:15:36,190
Hey that appears to have worked.

184
00:15:36,210 --> 00:15:40,290
Let's go ahead and create a couple of other accounts and then check out those accounts.

185
00:15:40,290 --> 00:15:42,750
So let's do this.

186
00:15:42,750 --> 00:15:45,990
It's too soon to add local users.

187
00:15:46,230 --> 00:15:47,880
Let's use the Russell

188
00:15:53,590 --> 00:15:54,140
it ener.

189
00:15:54,150 --> 00:15:54,440
Great.

190
00:15:54,450 --> 00:15:57,800
We get a new password for this account doesn't match the other password.

191
00:15:57,870 --> 00:16:02,910
As a matter of fact the password that you're going to see will not match either because it's being generated

192
00:16:02,910 --> 00:16:04,160
on the fly.

193
00:16:04,160 --> 00:16:06,180
It will do one more account here.

194
00:16:08,110 --> 00:16:14,350
We'll make this say an application account so those two people are philosopher names all pretend that

195
00:16:14,590 --> 00:16:18,140
this is going to be a philosophy application of some sort.

196
00:16:18,280 --> 00:16:23,160
And so we'll just call this Phil app and then we'll just use philosophy.

197
00:16:25,430 --> 00:16:30,670
Application user as the account description or the comment.

198
00:16:30,810 --> 00:16:35,850
Now we've created three accounts so there should be three new entries in the ETSI password file.

199
00:16:35,970 --> 00:16:42,300
So one way to view the bottom portion of a file is with the tail command the tail command is just more

200
00:16:42,300 --> 00:16:45,770
or less the opposite of the head command which you're already familiar with.

201
00:16:45,780 --> 00:16:49,180
So I'm just going to use tail Desch 3 at CPA.

202
00:16:49,180 --> 00:16:54,660
SS WD sure enough the first account we created has the proper username.

203
00:16:54,720 --> 00:17:00,960
John Locke as the comment the same with the second one and the third account we created the application

204
00:17:00,960 --> 00:17:08,700
account add three words as the comment and all three of those words have ended up in the password file.

205
00:17:08,700 --> 00:17:14,160
So it appears that our script is working as planned by the way you may see different account numbers

206
00:17:14,160 --> 00:17:16,480
depending on what accounts are on your system.

207
00:17:16,530 --> 00:17:24,750
For example your jay like user may have an idea of 1004 or 2000 or some other account depending on what

208
00:17:24,750 --> 00:17:28,720
you've previously done on the system and what other accounts exist and so on.

209
00:17:28,860 --> 00:17:34,440
So don't be alarmed if it's not 100 percent exactly the same on your system as what is being displayed

210
00:17:34,440 --> 00:17:35,500
here.

211
00:17:35,610 --> 00:17:41,710
Let's go ahead and switch to an account and make sure that it's forcing a password change on log in.

212
00:17:41,730 --> 00:17:47,920
So I'm actually going to scroll up to find the password for the Jay lock account.

213
00:17:49,540 --> 00:17:52,730
So the user name Jay lock and here's this big long password.

214
00:17:52,840 --> 00:18:00,850
I'm going to copy it and then I'm going to go down here and switch user to the Jay lock account.

215
00:18:00,850 --> 00:18:02,200
Now it asked me for the password.

216
00:18:02,200 --> 00:18:05,970
I'm going to paste it in and ask me for the current password.

217
00:18:06,520 --> 00:18:12,660
And now it's asking me for a new password so what it indeed is changing the password on first log.

218
00:18:12,670 --> 00:18:14,500
So let's use something here.

219
00:18:27,750 --> 00:18:28,110
OK.

220
00:18:28,160 --> 00:18:30,680
I'm successfully switched to the J lock account.

221
00:18:30,790 --> 00:18:35,380
You can see it's A-J lock at local users so that looks right for a password change.

222
00:18:35,380 --> 00:18:40,570
When we first use the account so everything is looking good so I'm just going to type and exit to get

223
00:18:40,570 --> 00:18:43,040
back to the vagrant user.

224
00:18:43,080 --> 00:18:47,940
Now we want to make sure that the script exits with a non-zero exit status if the user does not use

225
00:18:47,940 --> 00:18:49,450
super user privileges.

226
00:18:49,560 --> 00:18:55,800
So let's just execute this command with out using SU to hit enter.

227
00:18:55,800 --> 00:19:01,560
And it says Please run with suruh or as root and then so we can check the exit status with dollar sign

228
00:19:01,570 --> 00:19:02,330
questionmark.

229
00:19:02,430 --> 00:19:07,530
Obviously you can enclose that questionmark in curly braces but I'll just show you that you also don't

230
00:19:07,530 --> 00:19:09,930
have to do that so I'll just give you some variety here.

231
00:19:09,960 --> 00:19:11,970
So sure enough one is not zero.

232
00:19:11,970 --> 00:19:14,630
So that is exactly what we're looking for.

233
00:19:14,670 --> 00:19:20,940
And as a matter of fact one is what we supplied as the exit code for the exit statement.

234
00:19:20,940 --> 00:19:26,010
Now let's check for the other error condition which is where executing the script as true but we didn't

235
00:19:26,010 --> 00:19:27,370
give a user name.

236
00:19:27,420 --> 00:19:28,290
So let's try that.

237
00:19:28,290 --> 00:19:32,910
What do you say to add new local users data SH and hit enter.

238
00:19:33,300 --> 00:19:37,590
And sure enough it spits out our information here to teach the user how to use it.

239
00:19:37,590 --> 00:19:42,710
It tells them that they have to supply a username or otherwise this script is not going to work.

240
00:19:42,870 --> 00:19:49,860
And again we'll look at the exit status and sure enough it's one so everything is working as planned.

241
00:19:50,580 --> 00:19:50,890
All right.

242
00:19:50,910 --> 00:19:57,300
I'm done with this script and I'm actually done for the day so I'm going to log out of the vagrant virtual

243
00:19:57,300 --> 00:19:59,940
machine and I'm actually going to hold it.
