2018-12-07
Why we like HTTP Basic Authentication in Apache so much
Our web server of choice here is Apache, and when we need some sort of access control for it for people, our usual choice of method is HTTP Basic Authentication (also MDN). This is an unusual choice these days; most people use much more sophisticated and user-friendlier schemes, usually based on cookies and login forms and so on. We persist with HTTP Basic Authentication in Apache despite this because, from our perspective, it has three great advantages.
The first advantage is that it uses a username and a password that people already have, because we invariably reuse our existing Unix logins and passwords. This gets us out of more than making people remember (or note down) another login and password; it also means that we don't have to build and operate another account system (with creation, management, removal, tracking which Unix login has which web account, and so on). The follow on benefit from this is that it is very easy to put authentication restrictions on something, because we need basically no new infrastructure.
The second advantage is that because we use HTTP Basic Authentication in Apache itself, we can use it to protect anything. Apache is perfectly happy to impose authentication in front of static files, entire directory hierarchies, CGIs, or full scale web applications, whatever you want. For CGIs and full scale web applications, you can generally pass on the authenticated user name, which comes in handy for things that want that sort of information. This makes it quite easy to build a new service that needs authentication, since all of the work is done for you.
The third advantage is that when we put HTTP Basic Authentication in front of something, we don't have to trust that thing as much. This isn't just an issue of whether we trust its own authentication system (when it has one); it's also how much we want to have to trust the attack surface it exposes to unauthenticated people. When Apache requires HTTP Basic Authentication up front, there is no attack surface exposed to unauthenticated people; to even start talking to the real web app, you have to have valid login credentials. We have to trust Apache, but we were doing that already.
(Of course this does nothing to protect us from someone who can get the login credentials of a user who has access to whatever it is, but that exposure is always there.)
In an environment of sophisticated web services and web setups, there are probably ways to get all of this with something other than HTTP Basic Authentication. However, we don't have such an environment. We do not do a lot with web servers and web services, and our need for authentication is confined to things like our account request handling system, our self-serve DHCP registration portals, small CGI frontends to let people avoid the Unix command line, and various internal sysadmin services. At this modest level, the ease of Apache's Basic HTTP Authentication is very much appreciated.
Modern Bourne shell arithmetic is pretty pleasant
I started writing shell scripts sufficiently long ago that the only
way you had to do arithmetic was to use expr
. So that settled in
my mind as how you had to do arithmetic in shell scripts, and since
using expr
is kind of painful (and it has an annoying, obscure
misfeature), mostly I didn't. If I
actually had to do arithmetic in a shell script I might reach for
relatively heroic measures to avoid expr
, like running numbers
through awk
. In one relatively recent occasion, I had enough
calculations to do that I resorted to dc
(in retrospect this was
probably a mistake). However, lately I've been using shellcheck, and it's been nagging at me about
my occasional use of expr
, which had the effect of raising my
awareness of the modern alternatives.
Today I needed to write a script that involved a decent amount of
math, so I decided to finally actually use modern built-in Bourne
shell arithmetic expressions for all of my calculations. The whole
experience was pretty pleasant, everything worked, and the
$((...))
syntax is a lot nicer and more readable than any of
the other alternatives (including expr
). Since $((...))
is
part of the POSIX shell standard and so supported by basically
anything I want to use, I'm going to both switch my habits to it
and try to remember that I can use arithmetic in shell scripts now
if I want to.
Since some of what I was doing in my shell script was division and percentages, I found it a little bit irksome that Bourne shell arithmetic is entirely integer arithmetic; it got in the way of writing some expressions in the natural way. For example, if you want N% of a number (where both the number and the percent are variables), you'd better not write it as:
$(( avar * (npercent/100) ))
That only works in floating point. Instead you need to restructure the expression to:
$(( (avar * npercent) / 100 ))
It's a little thing, but it was there. And since at least some Bourne shells truncate instead of round in this situation, I found myself carefully looking at every division I was doing to see how it was going to come out.
One thing I found both pleasant and interesting is how you don't
write '$avar
' in arithmetic expansion context, just 'avar
'.
Unlike almost everywhere else in Bourne shell syntax, here the
Bourne shell treats a bare word as a variable instead of straight
text. This is a completely sensible decision, because arithmetic
expansion is a context where you're not going to use bare words.
This context dependent shift is a pretty clever way to partially
bridge the gulf between shells and scripting languages.
(For an example of how annoying it is to make the decision the other way, see my view of where TCL went wrong.)
PS: You might ask why it took me so long to switch. Partly it's
habit, partly it's that I spent a long time writing shell scripts
that sometimes had to run on Solaris machines (where /bin/sh
is not a POSIX shell), and partly
it's that I spent a long time thinking of arithmetic in the shell
as a Bash-specific feature. It was only within the past few years
that it sunk in that arithmetic expressions are actually a POSIX
shell feature and so it's portable and widely supported, not a
Bash-ism.
(It took me a similarly long amount of time to switch to $(...)
instead of `...`
for command substitution, even though the
former is much superior to the latter.)