Ben Nadel
On User Experience (UX) Design, JavaScript, ColdFusion, Node.js, Life, and Love.
I am the chief technical officer at InVision App, Inc - a prototyping and collaboration platform for designers, built by designers. I also rock out in JavaScript and ColdFusion 24x7.
Meanwhile on Twitter
Loading latest tweet...
Ben Nadel at cf.Objective() 2014 (Bloomington, MN) with:

How Do I Call Methods On ColdFusion Components In Java

By Ben Nadel on
Tags: ColdFusion

I am experimenting with Java and ColdFusion and I am hitting a brick wall very quickly. As one of my first experiments, I tried to pass a ColdFusion component into a Java wrapper class. The idea was that method calls on the Java object would turn around and call those methods on the ColdFusion component. Now, I can pass in the object no problem. Storing it get's sticky. I am storing it as java.lang.Object since I can't store it as a ColdFusion class (don't have access to those class definitions).

I tried to call Invoke() on the ColdFusion component, but I am not sure how it is called. I tried sending the method name I wanted to call. I tried sending the method pointer that I wanted to call (as returned from the GetMethods() array). Nope, nothing but and ColdFusion errors.

I see that a component is of type coldfusion.runtime.TemplateProxy. Not sure what that is. I have found references to it on other sites, but nothing extensive.

What I want to do is something like this:

  • public java.lang.String GetFirstName(){
  •  
  • // Call this method on the ColdFusion component
  • // object and return that value. This component is
  • // currently stored as java.lang.Object (this.Handler).
  • return(
  • this.Handler.GetFirstName()
  • );
  •  
  • }

As I said, this is not working... Anyone have any ideas?



Looking For A New Job?

100% of job board revenue is donated to Kiva. Loans that change livesFind out more »

Reader Comments

I did a lot of playing around with this some time ago. First off, what you want to do isn't "really" possible. A CFC is not one java class, but a collection of classes. For an example look under your cfclasses directory (under coldfusion). Find a class in there that looks familiar and you'll see a class for the CFC and one for each method. That's right! A CFC method gets compiled down to one java class.

Furthermore, if you reflect the Template Proxy you'll notice that it has methods on named invoke. I assume these are what CF calls to invoke methods. However, I have no idea what arguments they accept (and I've tried quite a range of options!). Furthermore, this is unsupported and I think it would be a mistake to actually implement due to risk of these APIs changing in future versions of ColdFusion.

For assistance reflecting CF classes use this tool: http://doughughes.net/reflection/index.cfm?event=ReflectClass

It can be downloaded here: http://doughughes.net/includes/reflector/reflection.zip (Requires MG 1.1)

Now, if you're using an old version of CF 7 (I forget the exact version, but before the first big update related by Macromeda. 7.0.1?), you can read a blog entry I wrote that shows a method of using an undocumented feature (for that version - which existed at that time in both CF standard and enterprise) called the CFCProxy to execute methods on CFCs from Java. Here's the entry: http://doughughes.net/index.cfm?event=viewEntry&entryId=122. There's a lot of information in there, but if you look past the technique for embedding java classes in a CFC you'll find a Java class that can call methods on a provided CFC.

Now, the problem is that from what I've been told CF removed the CFC proxy in the standard version (a risk with undocumented features) and supposedly enhanced it for enterprise only use in the first major update after the release of MX 7. So, now (for whatever stupid bloody reason) only MX 7 Enterprise users are allowed to use the CFCProxy. This rather ticks me off, personally. I refuse to use any features that aren't stupidly compelling in CF that are enterprise only features.

Anyhow, good luck with your experiments with Java! This is fun stuff with CF/Java.

Reply to this Comment

@Nick,

That looks very cool. But, it looks like the CFCProxy object can only be initialized via a file location. Is there a way to use the CFCProxy to invoke arguments on CFCs that were passed into a Java method?

Or am I totally misunderstanding something?

Reply to this Comment

Ben

Did you figure this out in the end?

I spent a fair bit of time a while ago calling methods on CFCs from Java in order to write a SAX parser I could use in ColdFusion. That was fairly straight-forward as everything was done in the same request to a CFM. I've now hit a dead-end when trying to call CFC methods from Java outside of a ColdFusion request.

If everything's going to be done on the same request, such as a CFM page creating a CFC and a Java object, then having the Java object call CFML methods in the CFC, I can mail you some code to show you how it's done using Java reflection.

I, however, will carry on investigating how to do it outside of a ColdFusion request...

George.

Reply to this Comment

@George,

I never got this working. I can easily call Java methods from within ColdFusion. But, I was never able to figure out how to pass a ColdFusion component to Java and then, within a Java class, call a method on the passed-in ColdFusion component. Have you been able to get that to work?

Reply to this Comment

Sorry for the late reply... didn't get an email when you posted a response and only just came back to check.

Yes, I managed to call functions inside a CFC from Java. That part is (relatively) straight-forward. I did it a different way to how it's described here, but Ben Forta released some documentation on how it's done using CFCProxy. See this page:
http://www.forta.com/blog/index.cfm?mode=entry&entry=A61BD06B-3048-80A9-EF15B0E3B096BFCD

The downside of using CFCProxy is that you'll need the developer or enterprise version of CF for it to work. If you've got the standard edition running on your production systems, you're on your own. I think my implementation will work even if you're using standard edition as the licence checks are done inside CFCProxy, which I don't use.

The whole topic of calling CF from Java is incredibly poorly supported by Adobe. In that article, Ben mentions that they're going to be putting up some proper documentation on the subject but there's still absolutely nothing on the Adobe site besides the patch notes. Poor show, Adobe.

The technique he describes will also create a new instance of the CFC each time. This may be fine under some circumstances but most of the time I've needed to do this, I need to call methods on a CFC I've already initialised, and now I need to do it outside of a page request as well. I spent nearly four days figuring out how to do this and I've now got it working by mimicking the CFCProxy functionality but providing it an instance of the CFC I've created already. Works fine but it's definately not going to be supported by Adobe, that's for sure.

When I get the time, I'd quite like to write a paper on everything I've researched to get this functionality working and all the bits and pieces I've discovered in the process.

Reply to this Comment

Accidentally posted before finishing!

I'll clean the code up a little this week and email it over to you so you can see how to call CFC methods from Java on an existing CFC from inside a request.

Reply to this Comment

@George,

Thanks for pointing me to the CFCProxy API. At least it gives some insight into all the casting that might need to be done. I am looking forward to seeing your work.

Reply to this Comment

I'm a ColdFusion newbie and my Java experience isn't up to Doug's. I need to call a CFC from an applet.

As I understand it, CFCProxy requires that the Java program calling the CFC must be running in the ColdFusion server's JVM? Obviously that wouldn't work for an applet.

If that's the case, perhaps I should fall back to WSDL or even AJAX calls?

Reply to this Comment

Eric,

For the most part, CFCProxy does indeed need to be running in ColdFusion's JVM.

I'd use web services in your case. Very, very easy to set up from your CF code and easy to call, too.

George.

Reply to this Comment

Hello George,

You mention in your post: I'll clean the code up a little this week and email it over to you so you can see how to call CFC methods from Java on an existing CFC from inside a request.

Is it possible to have a copy of the code you mention?
We would like to call CFC methods from external Java files too.

Regards,
Zoltan

Reply to this Comment

It was a awe-inspiring post and it has a significant meaning and thanks for sharing the information.Would love to read your next post too......
Thanks

Reply to this Comment

Good posting...I always waiting snippet code to calling methods on CFCs from Java....:)

Reply to this Comment

Post A Comment

You — Get Out Of My Dreams, Get Into My Comments
Live in the Now
Oops!
Comment Etiquette: Please do not post spam. Please keep the comments on-topic. Please do not post unrelated questions or large chunks of code. And, above all, please be nice to each other - we're trying to have a good conversation here.