I get bit by the multithreading bug on a regular basis. This site has had it's fair share (and I think I've managed to remove them all out by now).
Generally I find that multithreading bugs mostly occur when you store CFCs in shared persistant scopes, such as
So as a rule of thumb to make sure you don't get bit by the dreaded multithreaded bug, here are my tips and tricks:
- Use CFMX 6.1. It is possible to do persitatant CFCs with 6.0, but it's really not consistant in it's applications.
varall your local variables within CFC methods. This is my NUMBER 1 cause of multithreading issues, I forget this all the time.
- Use the
arguments scope when referring to arguments passed through in the CFC method. (This would be my number 2).
varall your local variables within CFC methods. This is SO important, I'm going to write it twice.
- Refer to instance variables by some sort of scope, beit directly through the
variablesscope, or if you use an instance struct of some kind, use that.
Use appropriate locking to ensure that data corruption doesn't occur. As far as I am aware, CF arrays are not thread safe, so write appropriate locking when dealing with them. I find named locks do the job nicely.
EDIT :::: Actually, I retract this statement. I did some investigating, and the Java array extends java.util.Vector, which IS thread safe. To quote from the relevent javadocs "As of the Java 2 platform v1.2, this class has been retrofitted to implement List, so that it becomes a part of Java's collection framework. Unlike the new collection implementations, Vector is synchronized.". I had originally thought that the ColdFusion array extended java.util.ArrayList, which is NOT thread safe, and requires itself to be constructed through java.utils.Collections.synchronizedList() to be thread safe. My bad.
- Write an error handler that sends you emails when an error occurs. Just because you don't see it, doesn't mean it doesn't exist, and multithreaded errors tend to be a sneaky little bunch. I have a tendency to use a modified version of the DumpVar udf from Cflib that outputs strings with a
XMLFormat()on them, and then dump out the
Formstructs to the email.
- Use some sort of stress tool (I've been using the MS Web Application Stress tool) and catch any and all the emails that come out of your above error handler. Fix these bugs. Rinse and Repeat.
That's pretty much it. That should make your CFCs thread safe.
It seems really simple, but I get caught with it so often (damn being used to declarative programming languages!) I figured I would write up a post.
Let me know if you have any other tips and tricks that help you stave off the dreaded multithreading demon.