You can't do exactly what you're trying to in your example code. You have a few options, though.
Method 1: Remotely accessible object
Move your function(s) into a CFC, and access them via the URL of the CFC. This access method requires that the function use the permission attribute access='remote'
-- if set to public (the default) or private, (or package, or any role levels, etc) then you'll get a method not found error when attempting to access it remotely.
Doing this, you're creating a SOAP webservice and consuming it via AJAX. You do this by using the following format in your jQuery request:
http://domain.com/path/to/your.cfc?method=functionName&argument1=arg1Val&foo=bar&...
If you have ColdFusion 8, you can also specify the returnFormat='format'
url argument, which will convert whatever native ColdFusion data objects you return to the requested format on the fly. It supports JSON, XML, and WDDX.
foo.cfc
<cfcomponent output="false">
<cffunction name="foobar" output="false" access="remote" hint="...">
<cfargument name="arg1" type="string" required="true" />
...
<cfreturn someVar />
</cffunction>
</cfcomponent>
Access by URL:
http://domain.com/path/to/foo.cfc?method=foobar&arg1=some%20value&returnFormat=JSON
Method 2: Remote proxy object
The negative side of approach #1 is that there is a slight efficiency hit on instantiating CFCs, so if this particular AJAX method will be run very frequently, and/or your CFC contains more than a few methods or is longer than a couple hundred lines, you don't want to instantiate it over and over for every request. Instead, you would want to look into the remote proxy pattern, where you cache the CFC that implements the functionality in Application scope, and have a separate 'remote proxy' CFC that is much lighter-weight, and simply acts as a proxy (hence the name) between the http request and the cached CFC.
In this pattern, your business object (the one that has the function that does the real work) can have access=public
(or package, etc), as long as the proxy has access to it. The proxy itself must have access=remote
, though.
proxy.cfc
<cfcomponent output="false">
<cffunction name="foobar" output="false" access="remote" hint="...">
<cfargument name="arg1" type="string" required="true" />
<!--- Application.foo is an instantiated object of foo.cfc --->
<cfreturn Application.foo.foobar(argumentCollection=arguments) />
</cffunction>
</cfcomponent>
Access by URL:
http://domain.com/path/to/proxy.cfc?method=foobar&arg1=some%20value&returnFormat=JSON
Method 3: Do It Yourself
Lastly, you could manually implement the function invocation and return in a CFM template. This method doesn't involve the (slight) performance hit of writing a CFC, but will be more typing for you, and additional potential points of failure. To do this, include your functions in the CFM template, and treat the output stream as just that: a stream of text that will be returned to the browser.
You should be careful to manage whitespace in the return value (use output=false
on function definitions, consider using <cfsetting enableCFOutputOnly='true'
, and just be careful about your spacing overall). If your jQuery request expects JSON back, you need to serialize it. (If you need to serialize data to JSON on ColdFusion 6 or 7, I recommend JSONUtil)
With this approach, you point your AJAX request to the .cfm file with URL parameters, and then you need to write code that takes those url parameters and passes them into the function, and then displays (essentially, returns to the AJAX request) the result of the function.
foo.cfm
<cfsetting enableCFOutputOnly="true">
<cfparam name="arg1" default="defaultVal"/>
<cffunction name="foobar" output="false" access="remote" hint="...">
<cfargument name="arg1" type="string" required="true" />
...
<cfreturn someVar />
</cffunction>
<cfset variables.result = foobar(url.arg1) />
<cfoutput>#serializeJSON(variables.result)#</cfoutput>