A really interesting thread on CFGURU today discussing how to minimize the impact of clients that don’t accept cookies from rapidly creating “phantom” sessions that eat up memory. Because the client doesn’t accept a cookie, each request will appear to be a new client and ColdFusion will generate a new session along with any objects you create in onSessionStart() or Application.cfc. Bots from most search engines behave exactly like this and while most of them have some throttling on their request rate, there are many that will canvas your site quickly generating hundreds of empty sessions. If your session timeout is not very short, this could lead to out of memory errors.
There have been some discussions about this previous on Ben Nadels blog as well as Mark Kruger. Ben’s solution is reported as effective but it is a moving target in that it tests the User-Agent. But Cameron Childress posited testing for the existence of cookies as a check for, well, a client that accepts cookie. If sessions are enabled in an application, ColdFusion will automatically set CFID and CFTOKEN for every page request which seems to be the perfect test! Johan Steenkamp put it to the test and reported back with a working code snippet (that I’ve slightly modified to make simple here):
< !-- this code goes in the Application.cfc in the psuedo-constructor outside of any function declaration --->
<cfif structKeyExists(cookie, "CFID")>
<cfset this.sessionTimeout = createTimeSpan(0,0,5,0) />< !--- 5 minutes --->
<cfelse>
<cfset this.sessionTimeout = createTimeSpan(0,0,0,5) />< !--- 5 sec short session for agents like bots that do not accept cookies --->
</cfif>
Brilliant – good on you mate! Now the bots will be a very short 5 second session that will quickly time out and return memory to ColdFusion while real users will get a 5-minute session. Obviously you can set those values, particularly the real-user version, to be whatever is appropriate for your application. Personally I use 1 hour for my session timeouts to afford a good user experience and avoid the “oops, you were logged out…” disappointment.
I can’t take any credit for the solution – I just thought this was a very clever mod to make your public ColdFusion app more resistant to dodgy clients. I use J2EE sessions so I modified it to check for jsessionid instead but otherwise it seems to be working properly in my testing with and without cookies enabled.
Geoff said:
on March 27, 2008 at 3:04 pm
I think this solution assumes a ‘real’ visitor will click another page within 5 seconds – otherwise how will you know the difference between a user’s first visit and a spider?
Along with the first page request, cookie information is sent to the browser – at this point, CF doesn’t know you’re not a real person, so gives you a 5 second session…
Yes, your cookie still exists, but if you’ve not clicked a second page within 5 seconds, your initial session will have expired and CF will create a second 5-minute long session along with your next page view.
brian said:
on March 27, 2008 at 5:29 pm
@Geoff, good question. It will treat the second request from a legitimate client as a new session, but in my opinion that is OK. Since 99% of the time the user needs to enter a username or password or something, it doesn’t matter much that the session is reset after the first page view. Another option would be to set the “short” session to something like 2 minutes; a reasonable enough time frame for a legitimate user to click again and maintain their initial request but short enough to let ColdFusion clear out the related memory variables. Charlie Arehart has some related content on his site about client variables and bots as well that’s worth checking out too.
In writing this response, I can think of two places in my app where the ultra short timeout might be a problem: URL variables can trigger a non-default theme which is stored in the session and when users forget their passwords, we send them a temporary reset token via email. That token logs them in automatically so losing their session could be a problem. Although in the latter case at least, we redirect them to the password page after authentication so I think they would get both requests in in quick succession.
I will probably revisit my setting to be a little more lenient. Since my real sessions last for as long as an hour, this will still provide lots of protection against spiraling memory use.
Great comment!
SitePoint Blogs » The Week in ColdFusion: 26 March-1st April: No fooling here said:
on April 3, 2008 at 6:18 am
[...] Brian Ghidinelli shares a technique to minimize memory usage by bots in applications using session management [...]