How Do I Call Methods On ColdFusion Components In Java

Posted October 9, 2006 at 6:16 PM

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:

 Launch code in new window » Download code as text file »

  • 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?

Download Code Snippet ZIP File

Post Comment  |  Ask Ben  |  Other Searches  |  Print Page




Learning ColdFusion 9 - ColdFusion 9 tutorials, samples, examples, demos

Reader Comments

Oct 9, 2006 at 10:41 PM // reply »
2 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.


Oct 10, 2006 at 8:01 AM // reply »
7,572 Comments

Doug,

Awesome information... and horrible information :) Ok, so no worries. I just need to change the way I handle this stuff. The learning will continue.

I like that reflector object, it looks like it is doing a MUCH better job of something I wrote a while back:

http://www.bennadel.com/index.cfm?dax=blog:206.view

I will keep you updated.


Jul 3, 2007 at 6:59 AM // reply »
2 Comments

You can actually do this using the cfcproxy...

http://www.forta.com/misc/cfcproxy.htm


Jul 3, 2007 at 7:06 AM // reply »
2 Comments

You can actually do this using the cfcproxy...

http://www.forta.com/misc/cfcproxy.htm


Jul 3, 2007 at 7:12 AM // reply »
7,572 Comments

@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?


Mar 5, 2009 at 2:11 PM // reply »
28 Comments

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.


Mar 5, 2009 at 2:36 PM // reply »
7,572 Comments

@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?


Mar 9, 2009 at 7:03 AM // reply »
28 Comments

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.


Mar 9, 2009 at 7:06 AM // reply »
28 Comments

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.


Mar 10, 2009 at 8:50 AM // reply »
7,572 Comments

@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.


Mar 13, 2009 at 2:48 PM // reply »
1 Comments

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?


Mar 15, 2009 at 8:37 AM // reply »
28 Comments

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.


Apr 15, 2009 at 12:04 PM // reply »
1 Comments

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


Dec 2, 2009 at 9:57 AM // reply »
7,572 Comments

I know this post is over THREE years cold, but if anyone cares, I figured out how to do this in Groovy:

http://www.bennadel.com/blog/1769-Calling-ColdFusion-Components-And-Methods-From-Groovy.htm


Post Comment  |  Ask Ben

Recent Blog Comments
Mar 20, 2010 at 12:07 PM
Drawing On The iPhone Canvas With jQuery And ColdFusion
Simply awesome. Saved my day. ... read »
Mar 20, 2010 at 9:00 AM
Building A Fixed-Position Bottom Menu Bar (ala FaceBook)
I would like to say thx for an easy way to create a bottom bar. I do have a ?. Is it possible to center the bar if i want to resize it to ex 85%. Regards Offenbach ... read »
Mar 19, 2010 at 7:26 PM
MySQL 3/4 - com.mysql.jdbc.Driver And allowMultiQueries=true
Thank you very much for this post. Adding allowMultiQueries="true" in context.xml didn't help until I added it to url as allowMultiQueries=true Good idea is to use prepared statements and it will he ... read »
Jim
Mar 19, 2010 at 4:49 PM
Nobody Puts Baby In The Corner!
Wow. This is like suddenly finding a support group for your secret shame. I'm not alone! I always liked this movie, even though it is extremely cheesy. I just wish Jennifer Grey hadn't gotten the ... read »
Mar 19, 2010 at 4:47 PM
Application.cfc OnRequest() Method Affects OnError() Arguments
@Jason and @Ben, I've been doing some CF9 refactoring on our systems and noticed an odd occurrence with onError as well. Found a way to work around my problem, but what I saw was... Background: Our ... read »
Jim
Mar 19, 2010 at 4:44 PM
Shoot 'Em Up Starring Clive Owen And Paul Giamatti
I actually enjoyed this movie quite a lot. It was different, certainly, but I think they were going for more of a Quentin Tarentino-"wow, that was weird"-vibe than an actual spoof. Once I realize ... read »
Mar 19, 2010 at 4:34 PM
An Intensive Exploration Of jQuery With Ben Nadel (Video Presentation)
Hey I guess the video is down. Is there anyway you can upload to youtube or vimeo or some other service? Greatly appreciated. ... read »
Mar 19, 2010 at 4:24 PM
ColdFusion CFPOP - My First Look
@Ben Thanks for the follow up! The root of the problem had to do with being able to trace bounced emails to specific records in a DB table. Let's say you run an email campaign and you get 1,000 bou ... read »