views:

86

answers:

2

I have a table that stores songs and plays counter.
Here's the code:

//Increse plays counter
string ip = Request.UserHostAddress;
if (!string.IsNullOrEmpty(ip))
{
    if (Cache["plays:" + trackID + ":" + ip] == null)
    {
        tracks.IncreasePlaysCounter(trackID);
        Cache["plays:" + trackID + ":" + ip] = true;
    }
}

I wonder what would be a better practice, store many cache items(like this) or store one item like a ArrayList that would contain the users who already heard that song. Is there any difference?

+1  A: 

Neither. If your system is in any way successful it will have far too many individual entries being written for this to be able to scale to cope, especially when you add the locking code to deal with the number of simultaneous writes and reads this will have to cope with.

Store this information in a database. Or don't store it at all, but obtain it by parsing the webserver logs (if the trackID is a query parameter, this information will already be in those logs without any work from you).

Jon Hanna
I agree with Jon Hanna, you're going to quickly run out of memory and with any significant number of users you're likely to have these cache entries kicking each other out of the cache due to memory limits. A database seems like the better solution here. I'd also add, just as a side note, don't use the host ip address, but instead use the session id. Otherwise you're likely to run into problems with me and my wife listening at the same time, as we would both appear to you to be the same IP address (being behind a NAT firewall).
Coding Gorilla
While potentially sound advice, it doesn't answer the question. Perhaps @Adir is writing a simple app for small distribution.
ddc0660
@ddc0660 actually I still don't know how big my web application is going to be, I need to use a solution that will scale.Storing this in a DB will fill up the DB really quickly, perhaps I need to empty that table each X days? Is that a good solution?
Adir
@dcc0660 if it's already big enough to have problems not doing this, it's too big to do this. This is less scalable than the normal approach.
Jon Hanna
@Jon so the best solution here is to store this using a DB and empty that table periodically?
Adir
I'd really need to know why this was being done. All I can see here is logging, which I would do offline based on IIS logs, but a different purpose may not be served by that.
Jon Hanna
A: 

I'm going to approach this question from the angle purely of caching rather than the context of plays and tracks.

When deciding to cache data, it's important to consider what the dependencies are and how the cache expires.

If the cache of each user can be expired individually than how you have it is fine. If it turns out that one record becoming expired should invalidate the entire set of records, then put it into an ArrayList and dump the whole object.

ddc0660