Now your talking!! Go for it! Perhaps you can copy and alter the metadata before passing it into the utilities class to generate the functions. I can talk to you offlist about the best ways to do this 

C


On Jul 11, 2007, at 11:09 PM, Barney Boisvert wrote:

On the other hand, if you were to subclass RemoteFactoryBean with
CF8AjaxRemoteFactoryBean and have it take care of the extra crap
(which is specific to CF8's Ajax stuff, not general purpose like the
XML metadata), I'd say it's a sound solution.

That's the kind of extension that more closely follows the Spring
paradigm: something generally useful that is BUILT UPON core
functionality, as opposed to TWEAKS to core functionality.

cheers,
barneyb

On 7/11/07, Chris Scott <[EMAIL PROTECTED]> wrote:

Hmm, I like the idea, but am not 100% sure this is a good thing to add to the RemoteFactoryBean. It is a big departure from what Spring offers on one hand, but more importantly, the code example looks to me like fully metaprogramming your cfcs in xml. All you are missing is your actual method call. Being able to fully transform one method into basically a totally different one is really not what AOP is about, it is about introducing a little code seamlessly across your application logic, maximizing code reuse, while simplifying your core business logic. This seems too much of major magical code transformation to me


C





Chris Scott













On Jul 11, 2007, at 8:32 PM, Brian Kotek wrote:

I wanted to get some input about a hack that I just created in ColdSpring. First, some background:

I was playing with the new AJAX features in CF8. In particular, I was messing with the AJAX grid. I created a simple service component that returns a query, and wanted to use ColdSpring to generate a remote proxy bean that the grid can call. So far so good.

The first issue I ran into was that the AJAX grid requires a query to be reformatted using QueryConvertForGrid(). So I created a simple AOP advice that runs the target method and then returns the result wrapped with QueryConvertForGrid(). I could also imagine doing this to format data for use in the AJAX tree component.

Anyway, when I bound my grid to the CFC method, ColdFusion complained loudly. I seems any method used to update a grid requires several arguments, such as cfgridpage, cfgridsize, cfgridpagesortcolumn, and cfgridpagesortdirection. So I specified these arguments in my CFC call from the grid. CF still complained. It seems that the AJAX to CFC binding uses CFC metadata and REQUIRES that cfargument tags exist in the target CFC that match these arguments.

Now you can probably see the problem. My base service component has no such arguments. It has no idea I'm eventually using the data it returns in an AJAX grid. And since ColdSpring uses the base CFC metadata when generating the remote proxy bean, it won't generate any arguments at all for that remote method. So it looked like I was out of luck on using ColdSpring for this sort of thing. Which would suck for an app that sent a lot of data to AJAX grids...I'd have to manually create remote facades for every method.

Unless....

The wheels began turning...

What if I could somehow inject artificial metadata into the system, so that even though my base service component didn't have these grid-specific cfargument tags, the generated remote proxy would? Then ColdFusion's AJAX to CFC binding would be happy, and the AOP advice would have these arguments available for use in the QueryConvertForGrid() function call that it does.

 Well, I did it. The result is that a bean definition like this will have extra metadata defined, that will be used the the RemoteFactoryBean to generate the remote proxy bean:

    <!-- Generate remote facade for Product Service -->
    <bean id="artServiceAJAX" class="coldspring.aop.framework.RemoteFactoryBean" lazy-init="false">
        <property name="target">
            <ref bean="artService" />
        </property>
        <property name="serviceName">
            <value>ArtServiceAJAX</value>
        </property>
        <property name="relativePath">
            <value>/artstore/components/</value>
        </property>
        <property name="remoteMethodNames">
            <value>get*</value>
        </property>
        <property name="beanFactoryName">
               <value>BeanFactory</value>
        </property>
        <property name="interceptorNames">
            <list>
                <value>AJAXGridAdvisor</value>
            </list>
        </property>
        <metadata>
            <methods>
                <method name="getArtists" returnType="query">
                    <parameter name="cfgridpage" required="yes" type="numeric" />
                    <parameter name="cfgridpageSize" required="yes" type="numeric" />
                    <parameter name="cfgridpagesortcolumn" required="no" type="string" default="" />
                    <parameter name="cfgridpagesortdirection" required="no" type="string" default="" />
                </method>
            </methods>
        </metadata>
    </bean>

And the resulting ArtServiceAJAX.cfc has this method defined:


    <cffunction name="getArtists" access="remote" returntype="any" output="false" >
        <cfargument name="cfgridpage" type="numeric" required="yes" />
        <cfargument name="cfgridpageSize" type="numeric" required="yes" />
        <cfargument name="cfgridpagesortcolumn" type="string" required="no" default="" />
        <cfargument name="cfgridpagesortdirection" type="string" required="no" default="" />
        <cfset var rtn = callMethod('getArtists', arguments) />
        <cfif isDefined('rtn')><cfreturn rtn /></cfif>
    </cffunction>

It seems to me this could be very useful in any remote proxy bean that also uses AOP to do something beyond what the base component it is proxying does. In theory it would work for web service calls too, which are also obviously highly dependent on the metadata of the proxy to generate WSDL, etc. Flex apps might benefit less since I don't believe they depend on the actual metadata/arguments/types of the methods being called, but someone who knows more might correct me. This proof of concept requires you to spell out the full method names, but I could easily see changing it to support wildcards like get*.

 I set it up so that you can alter the return type of the method itself, alter the type, required, and default attributes of existing arguments, and add completely artificial arguments as well.

I'm interested to hear what people think. One downside is that it seems to definitely alter the ColdSpring XML DTD to differ from the Java Spring DTD, though I know there is already at least one other difference between the two (in the constructor arg I think).

Is this madness?

Thanks,

Brian





-- 
Barney Boisvert

Got Gmail? I have 100 invites.


Reply via email to