If I understand correctly, each API request comes with a user ID and a client. Each client can have several user identifiers. You want to evaluate the limit both at the client level and at the user level.
You will need to use several keys ABC_day, ABC_hour, ABC_userID1_hour, ABC_userID2_hour, etc. to count the number of times these actions have occurred. The problem with this approach is when reset these counters. Since memcached only supports the increment operator by numerical values, we need to encode this information in the key itself. We can use ABC_2012_02_28 as a key to limit the daily rate. In your code, just create them using the current date and increment it. When the day changes, your code will look for ABC_2012_02_29, which does not exist, and gives you the opportunity to create a new key.
An alternative is cacheismo. It is a cache, like memcached, and supports the memcached protocol, and it provides in-cache scripts. Instead of creating so many keys, you can implement your own ratelimiting object, which will do all this bookkeeping for you. See http://chakpak.blogspot.in/2011/09/rate-limitingquota-with-cacheismo.html for a selective implementation of speed limits. You can get it from here. https://github.com/iamrohit/cacheismo .
source share