fusiongrokker

Scope Priority Changes in ColdFusion 9

According to the documentation regarding the order in which unscoped variables are evaluated for ColdFusion 8 vs. the documentation for ColdFusion 9, there have been some not insignificant changes in scope priority. Are these typos in the documentation, or have things really been changed?

The first thing I noticed about these two lists was that version 9 lists one more scope than version 8: Query. It does caveat that by saying that Query is not a true scope, but it's good to know that it is specially checked and where in the priority it falls. (In fact, that's why I was checking this in the first place.)

Let's look at the lists side-by-side for comparison purposes. CF8 is on the left, and CF9 is on the right.

CF8 Scope PriorityCF9 Scope Priority

1) We can see that function local variables -- including the new "local" named scope in CF9 -- get top billing in both CF8 and CF9. No change here.

2-3) It looks as if Arguments and Thread Local (not the named "thread" scope) have been swapped. No big deal here, because you can't define a UDF inside a thread, and although you can run a thread inside a function, when you do the thread has a private namespace and doesn't have access to it's parent's (the function's) arguments scope.

So essentially Arguments and Thread Local variables are equals, being interchanged in the priority list where applicable, and ignored where not applicable; and never the twain shall meet.

4) Query was injected into the list here

5-6) Variables and Thread (the named "thread" scope) have been swapped. This is where there might be a problem!

From here on out, the lists are identical; so we'll ignore the rest and assume they're correct. Of course, this 5/6 swap could have been a human error in transposition, so let's write a test to find out if the documentation is correct or if it needs to be addressed.

Unfortunately, this code sample was lost due to technical difficulties. :(

The first time I ran this test, I got these results:

Inside thread:
local
*thread local has been found - can't be deleted.

Outside thread:
variables
Could not find any more instances.

ref thread externally by thread name: thread

This test confirmed that the thread-local scope is first priority among the 4 being tested (thread-local, thread-named, attributes, variables), as the documentation says it should be. Great! Unfortunately, I can't delete that variable once it's been set (even doing structDelete(local, 'foo') in CF9 didn't work -- the thread local scope is NOT the same as the function local scope!) So to get around this limitation, I comment out my local variable and hard-code in the result where it would fall based on the results of test #1.

With that done, here are the results of re-running the page:

Inside thread:
local
attributes
variables
Could not find any more instances.

Outside thread:
variables
Could not find any more instances.

ref thread externally by thread name: thread

What do these results mean, as far as the exact order that ColdFusion uses for our 4 scopes in question (again: thread-local, thread-named, attributes, variables)? I ran my test on both ColdFusion 8 and 9 and the results were the same.

  1. Function Local (if inside a function) or Thread Local (if inside a thread)
  2. Attributes (if inside a thread)
  3. Variables

Wait, what?!

So thread-named doesn't make the list at all. The documentation says both on the general scope priority page and the thread scopes page (and this is carried over to the CF9 documentation as well) that thread scope should be available to the creating page; but in my testing, it isn't available to the creating page at all (trying to dump #thread# throws an exception) and it is not checked when evaluating unscoped variables. It is shared between running threads, that much is true; but it doesn't seem possible to use thread.someVar to access data that was set inside the thread. That said, you can use [threadName].someVar as I do in my test above, so it's not a total loss. But I'd call it a bug. Would you agree?

In addition, and although documented on the Using Thread Data pages in the CF8 and CF9 documentation, Attributes is not mentioned on the general scope priority documentation (for either version). Attributes is also a scope available in custom tags, but (and I tested this!) it is not checked when evaluating unscoped variables inside a custom tag.

So I think that leaves the final tally for scope priority as such:

  1. Function Local (if inside a function) or Thread Local (if inside a thread)
  2. Attributes (if inside a thread)
  3. Query
  4. Variables
  5. CGI
  6. Cffile (if an applicable CFFile tag was used)
  7. Url
  8. Form
  9. Cookie
  10. Client (if client variables are enabled)

Wow, that turned out to be much deeper of a rabbit hole than I was expecting when I started out. Glad to have it sorted out, though.

in ColdFusion | 7 Responses 2009-12-07 07:00

7 responses:





Leave this field empty: