Security is one of the most important topics in the IT field. Without some degree of security, we wouldn't have the Internet, e-Commerse, ATM machines, emails, etc. A lot of the seemingly unrelated topics base their existance on security.
There are two primary forms of security that system designers have to care about, authentication, and authorization.
Authentication refers to the idea of ensuring you are who you say you are. This usually takes the form of username/passwords. If you know the password, you are authenticated, and the system trusts you. If you don't know the password, the system doesn't trust you. Simple as that.
Authentication can happen in many different ways; not nessasarily via passwords. It usually boils down to three basic principles:
Something You Know: This would be the password. It could also be something more obscure, like mother's maiden name, or your social security number, etc.
Something You Have: This is usually some sort of a token. This can take the form of a bank card, a credit card, or for more secure situations a cryptographic token (ie: a keychain like thing that generates `random' keys; which you combine with a password to login).
Something You Are: This takes the form of fingerprints, iris scans, DNA fingerprinting, weight, height, pictures, etc.
By itself, these methods can be easily defeated (you can guess/intercept/buy someone's password, take away their tokens/keys, or somehow criple the person not to have fingerprints). When combined in several combinations, they present quite robust security. ie: A credit card with a picture prevents someone else from making in-store purchases. It is also pointless to steal cryptographic key chains, since you don't know the password, etc.
Now that the system knows who you are, another issue in security comes into play... What are you as a user of the system allowed to do?
This concept usually boils down to what priviledges you have in using the system. Can you update certain records?, etc.
This idea is usually implemented via `user roles'. When someone logs into the system, their account contains a list of roles that the user may take. If the user's role includes being a `user administrator', then the user is allowed to create/ remove/ update users, and so on and so on. Each `role' may have various priviledges associated with it. So for example, you might discover that your `account manager' person also needs `access_old_records' permission, then you add that permission to that role, and anyone who is of that role will automatically get that permission. This can also work both ways; if you're a `developer' role, you have access to certain resources. But if at the same time you're of the `consultant' role, some priviledges might be revoked (even if they were granted by the `developer' role).
Web Site Security
Most websites concentrate their security handling on authentication, and less so on authorization. Most users of the website are untrusted, so there is no point in distinguishing among several hundred thousands of equally untrusted users.
Here's how the security works: The client (web-browser) connects to the server. The server generates a unique key, also knows as `session id'. This session is saved on the server (somewhere - usually in memory, but sometimes in simple databases). The key is returned to the client as a cookie. (usually).
[Note: While most websites today maintain the session using cookies, you can also maintain session without cookies - by using URL rewriting. Basically the `session id' becomes part of the URL, and every single page the server returns is modified to have every URL maintain that `session id'. As you can imagine, it is quite cumbersome.]
The client is responsible for presenting the cookie to the server everytime it reconnects. If it doesn't, the server simply issues a new cookie (starting a new session).
Login happens simply: The client sends the server the username/password pair. The server looks these up in a database, and if found, puts a little checkmark next to the `session id' in the database. From now on, the client with that cookie is trusted as a user of the system.
Logouts happen similarly. The cookie can expire (usually when you close the browser). The session (on the server) can expire (if you don't contact the server within say 30 minutes, the session is erased - and your cookie is no longer recognized as valid; you need to relogin. Or, the user presses the logout button, at which point the session is invalidated, and the cookie is discarded.
Distributed Systems Security
With distributed system, the idea of security is very similar to the one described for web sites. There is quite a bit more complexity though.
With websites, there is a notion of a unique `id' for the session. Most distributed systems (if they have to deal with such security) also manage a form of `session id'.
You connect to a component, you give it a username/password. The component generates the `id', stores some session information in a database (or memory cache) and returns you the id.
The client is now responsible for presenting this `id' to the server every time it invokes a method or does any operation.
There are several ways of passing around this token; and some are just as convinient as passing around cookies. In most distributed system architectures, there is usually a notion of a connection channel. All communication is happening via this channel. So instead of logging in and tracking the authorization of the user - you can in effect track the channel. The channel usually has some back-door mechanism, a context of sorts, that you can use to send information to the server that's not part of the actual request. In CORBA this is called piggy-back approach.
Anyway, from the client side, the whole thing boils down to: sending username/ password, the recieved `id' is added to the communication channel context (under some nice name like `ticket'), and from then on, the client doesn't have to care about security - just invoke methods on the server, and the communication context will ensure that the ticket is sent with every request.
From the server's perspective, after the user loggs in, you need to generate the ticket, save it, and send it to the user. On every request that the user performs, you need to extract the ticket, find the user, determine if that user has the priviledges to execute that method, and then continue on with the method.
Several things should be mentioned: Often the security/ priviledges of methods can be setup externally. For example, with EJBs, the container manages security and access to the beans. So you never have to code up security access in actual processing code.
The user `id' lookup usually happens in a memory database; so handling security doesn't involve an extra database hit; for some systems this may be unscalable, but even for those, combined with a memory caching scheme, most user based security is not hitting the database every single time.
Encryption is well beyond the scope of this discussion, but here are a few pointers:
If the connection ever goes through an untrusted network (wireless, Internet, etc.) and the data shouldn't be seen by anyone, then it should be encrypted. Usually the form that takes is via SSL (Secure Socket Layer).
For websites, (for properly setup websites), that usually means just connecting to https://something instead of http://something. A good rule of thumb is never to send a password to an http connection, but use https.
For distributed systems, that usually means using an SSL interface, or some other custom encryption scheme. (heh, Note that custom encryption has a very high chance of not working right).
In the real world, most data is not encrypted, and nobody seems to care. Most e-mail you send out is unencrypted. In fact, very often people are checking their e-mail via an unsecured wireless connection (like in the park). So while security is a good idea, is it important not to go overboard and make it intrusive enough for people stop using the system in the first place.