You're right to be wary of transmitting the password with every request. Fortunately there's a fairly straightforward answer: implement sessions, and have your cookies contain a session ID instead of a password. In a nutshell, do this every time someone tries to access a secured resource:
in reply to Secure passwords
Some finer points:
- If a cookie was sent with the request, check for a session ID in the cookie.
- If the session is invalid or expired, or no cookie was sent, send the user to a login page. Otherwise, serve the resource.
- On the login page, ask for the password. You may want this transmission to be secure.
- Once the user is validated, generate an unguessable session ID (see this node for tips on that).
- Set the cookie's expire time to a reasonable amount (or blank if you want it to expire when the browser closes). I've found five to fifteen minutes to be good numbers depending on the application. Longer is riskier, but shorter annoys your users.
- On the server, save the session ID and the login time. The sophistication should depend on the application and anticipated hit rate. A flat file may work if you have very few users, or you may need a full blown database if you have hundreds of logins per minutes. More database-like solutions are more attractive if there's additional info you want to store with the session (e.g. a shopping cart).
- Send the cookie with the login result page. You could help your user out by redirecting to whatever page they originally wanted to go to.
- When checking for valid sessions, don't trust the browser to expire when you told it to; always use your local knowledge of login time to determine expiry.
- Include an option to log out explicitly. When this is chosen, mark or delete the session locally and send a cookie with an invalid (e.g. empty) session ID and a negative expiry. This will delete the cookie from the browser.
- Update the expiry every time the user requests a page; otherwise they'll be logged out after a constant time following login.
- Every once in a while (minutes to days depending on usage), clear expired sessions from the server.