perl-modperl mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From Michael Peters <mpet...@plusthree.com>
Subject Re: Ways to scale a mod_perl site
Date Wed, 16 Sep 2009 17:11:41 GMT
On 09/16/2009 12:13 PM, Brad Van Sickle wrote:

> Can I get you to explain this a little more? I don't see how this could
> be used for truly secure sites because I don't quite understand how
> storing a hash in a plain text cookie would be secure.

If you need to store per-session data about a client that the client 
shouldn't be able to see, then you just encrypt that data, base-64 
encode it and then put it into a cookie.

If you don't care if the user sees that information you just want to 
make sure that they don't change it then add an extra secure hash of 
that information to the cookie itself and then verify it when you 
receive it.

I like to use JSON for my cookie data because it's simple and fast, but 
any serializer should work. Something like this:

use JSON qw(to_json from_json);
use Digest::MD5 qw(md5_hex);
use MIME::Base64::URLSafe qw(urlsafe_b64encode urlsafe_b64decode);

# to generate the cookie
my %data = ( foo => 1, bar => 2, baz => 'frob' );
$data{secure} = generate_data_hash(\%data);
my $cookie = urlsafe_b64encode(to_json(\%data));
print "Cookie: $cookie\n";

# to process/validate the cookie
my $new_data = from_json(urlsafe_b64decode($cookie));
my $new_hash = delete $new_data->{secure};
if( $new_hash eq generate_data_hash($new_data) ) {
     print "Cookie is ok!\n";
} else {
     print "Cookie has been tampered with! Ignore.\n";
}

# very simple hash generation function
sub generate_data_hash {
     my $data = shift;
     my $secret = 'some configured secret';
     return md5_hex($secret . join('|', map { "$_ - $data->{$_}" } keys 
%$data));
}

Doing encryption and encoding on small bits of data (like cookies) in 
memory will almost always be faster than having to hit the database 
(especially if it's on another machine). But the biggest reason is that 
it takes the load off the DB and puts it on the web machines which are 
much easier to scale linearly.

 > I know a lot of true app servers (Websphere, etc..) store
> this data in cached memory,

You could do the same with your session data, or even store it in a 
shared resource like a BDB file. But unless it's available to all of 
your web servers you're stuck with "sticky" sessions and that's a real 
killer for performance/scalability.

-- 
Michael Peters
Plus Three, LP

Mime
View raw message