Web Authentication
Sun, 05 Jan 2014 17:56:30 -0000
Dynamic content has become widely spread throughout the web, it has become quite common to use the web page front itself to edit the content of the web page. It is a good idea indeed to secure access to the editing facilities through user authendtication. Being a total newby to web development I never really thought about how this is actually done. Now for naga, I have to think about ways of implementing user authentication. This is my (current) thoughts about it. I dont think this is the final version, though...
Update: Added hints to secure cookies.
Update: Corrected spelling error.
Currently I am working on editing facilities of my naga CMS. Of course, it is highly desireable to implement some form of authentication to prevent having your content modified by anybody that passes by your web page[br] This must be some kind of standard problem regarding web page development, but I am still a total newby in this field and here I summarize my thoughts on this issue. If you want to just add a new article on your web page, it suffices to just send the text along with your user name and password. In HTTP terms, this could be done by an HTTP GET request like this:
http://www.example.com/post.cgi?user=me&password=secret&new_text=MyNewText
The server then is able to check whether the password authenticates the user name and whether the user name is authorized to add a new text. Of course, this should not be done just in plain text, but this problem I will address later on. What if you want to add several texts? Right now, for me it looks as if there were two possible principal ways of implementing some sort of session management to retrieve this functionality.
  1. Just send along the user name and password on every http request
  2. Use some sort of session management on the server side

Login on every request

The first point would mean in principle that one has to log in for every single action - quite clumsy. Eventually, every user will uprise if he has to log in before every single action hes wants to do. Of course, this incommodity can be avoided by proper programming. In principle, the software would have to take care to turn every link inside of an html document from something like http://www.example.com/news.cgi to http://www.example.com/news.cgi?user=me&password=secret However, this would be clumsy, still, and the clumsiness would not even be hidden from the user: When following one of these links, what appears in the address line of his browser would be exactly this URL including his user name and password! A better solution would be to transmit the credentials with every request, but have it transmitted not as part of the URL but within a cookie . This bears two benefits:
  1. The address line would not uncover the user's credentials
  2. Programming would be much easier, as the server would just have to set the cookie once and not to adapt every single link that it delivers.
This could be done by having the user log in once by sending his credentials by HTTP GET/POST to one special page: code http://www.example.com/set_cookie.cgi?user=me&password=secret This page does nothing but setting the cookie by delivering an additional HTTP header Set-Cookie :

Content-type: text/html
Set-Cookie: user=me; password=secret Cookie set


Afterwards, the user can do whatever he wishes, the cookie containing his credentials will be sent along by every request he issues, no need to explicilty transmitting the credentials on every request.

Server Side Sessions

The other way of dealing with authentication is having the server maintain some kind of session state for every login done. I will not say too much about this possibility, though. The big problem herein is for the server to decide whether one particular request stems from a client that has authenticated already or not. This could be possible by looking at the IP address one request stems from or, again, by setting a cookie with a session id. However, using IPs to identify clients is unhandy, as CGI scripts will in general not be able to determine the IP a request originated from (to my knowledge at least), so your web daemon would have to support it. Setting a cookie with a session id turns out to be just a variant of transmitting user name and password. It would be more complicated, though as by transmitting the user name and password directly would not require any kind of session management on the server side. So, to sum it up, currently it looks to me that sending the credentials within a cookie with every single request is the best solution.

Security

At the first glance, it looks like using server side sessions bears the advantage of avoiding the transmission of the credentials: While when using login on every request the credentials have to be transmitted with every single request sent to the server, when using server side sessions you only need to send them once when opening the session. It turns out that this is not the entire truth. There is not a big difference in whether you just transmit the user name and password, or transmit a session id instead of it. What happens if you decided to use server side sessions is to just switch from the credentials to the session id to authenticate. Everyone knowing the session id would be able to authenticate just as if he knew the credentials. The only difference is that a session id will deprecate after some time. The security gain in using server side sessions is therefore not as big as one could guess at the first glance. For the same reason, it does not really make sense to do something like hashing the credentials on the client and then transmitting the hash instead of the plain text credentials. Hashing is a proper way when storing passwords for later verification. When authenticating, the password will be read in, then hashed and the hash will be compared with the hash stored. This makes sense, as noone can restore the password from the stored hash. This is, however, only feasible if you can ensure that the hashing process cannot be bypassed. If one manages to bypass the hashing step and just send an already hashed password to the verification, he does not need to know the password anymore, and the entire situation turns out to be just as if there was no hashing in place and the hash itself was the password. This is exactly the situation when hashing the credentials on the client side and then transmitting the hash to the server. Think about it! The only way to implement proper security is to encrypt the transmitted credentials, and the best way to ensure this is to just encrypt the entire transmission. Instead of making the mistake of trying to implement own encryption just switch to HTTPS. HTTPS might be flawed in some way, but do-it-yourself encyption will be worse! Moreover, HTTPS cookies provide a convenient way to ensure using HTTPS. Just make your cookies secure cookies, this ensures that the cookies will be sent only if HTTPS is used. In addition to this, it will add some additional security as the browser will confine itself to the same site policy .