8 Replies Latest reply on Feb 24, 2010 2:33 AM by joannecorless

    Creating a complex webservice as a listener

    joannecorless Level 1

      I've an external supplier who hosts a number of webservices to which we are currently sending requests and then polling a webservice until a result is returned - this is fine at the moment with only development traffic going back and forth but as soon as we go live - We are going to need to retrieve the results back asynchronously via our own webservice acting as a listener

       

      I've created a webservice that works fine when I pass it the expected xml in my test harness - However when the supplier tries to send the xml - it gets very upset - It appears that the object that is being created from by the underlying system is an org.apache.xerces.dom.DeferredDocumentImpl - I don't know how I can get at the methods on this object - I can't cast it nor can I call them directly

       

      The remote system is sending me the xml from a C# service - Although the XML is a complex type - I don't really care - I just want to get at the raw xml

       

      In the generated wsdl - the object is being defined as SOL_Acknowledgement

       
      <element name="SOL_Result" type="apachesoap:Document"/>

      whereas in the suppliers original wsdl - it is defined as

      <xs:element name="SOL_Result" type="tns:TSOL_Result" nillable="true" minOccurs="1" maxOccurs="1" />

      I'm not sure - do I need to create a complex type to match this up? and how do I define it in the cffunction header ? Do I still put 'type="xml"' or do I put type="<packageName>.TSOL_Result
      TSOL_Result" ?
        • 1. Re: Creating a complex webservice as a listener
          joannecorless Level 1

          Just to add - I've tried

           

          <cfset soapResponse = xmlParse( "#SOL_Result#" ) />  

           

          I've also tried

           

          <cfset soapResponse = xmlParse( "#SOL_Result.toString()#" ) />  

           

          Neither of them work unfortunately - Obviously the easiest way would be to get at the Java methods underneath - The one I want is
          getElementsByTagName() as this returns a node list - which I can then use the standard Coldfusion dot notation to get at the values I need - but how do I do this when I can't cast the result to a org.apache.xerces.dom.DeferredDocumentImpl object ? because if I do that I get the following error

           

          coldfusion.xml.rpc.CFCInvocationException: [coldfusion.runtime.JavaCastException :
          JavaCast type org.apache.xerces.dom.DeferredDocumentImpl must be one of the following
          types: byte, char, short, int, long, float, double, boolean, string, bigdecimal,  their corresponding array representation (eg : int[]) or null.];detail=*coldfusion.xml.rpc.CFCInvocationException:
          [coldfusion.runtime.JavaCastException : JavaCast type org.apache.xerces.dom.DeferredDocumentImpl must be one of the following types: byte, char, short, int, long, float, double, boolean, string, bigdecimal,  their corresponding array representation (eg : int[]) or null.]

          • 2. Re: Creating a complex webservice as a listener
            BKBK Adobe Community Professional & MVP

            The trouble is, an XML document object in Coldfusion wont be recognised by C# or even Java. The lingua franca for XML in web services is SOAP.

             

            In fact, your question is similar to the one in thread, Capturing XML to be sent to a Web Service. There, you will find a fully worked out example of sending XML in a web service by means of SOAP.

            • 3. Re: Creating a complex webservice as a listener
              joannecorless Level 1

              No - It's not the answer I'm afraid - I think you've got the wrong end of what I'm asking - I know

              that SOAP is the lingua franca of webservices - It's receiving stuff back that is the problem - Our webservice is basically a listener there to receive results back  from a 3rd Party supplier

               

              I've quite successfully created the calls &  dealt with the responses to create the order but the response is just an acknowledgement that the order has been  received - The actual results come back asynch - Hence the listener

               

              If I send the asynch response XML from my test harness - the code works  exactly as I'm expecting - It falls over when it hits a db call but  thats fine as it's only test data - It does however read and parse the  XML correctly however when it's sent directly from the supplier using  their C# setup it falls over at the point where I'm trying to do a read  (to dump out a copy of the response to the local file system before  processing) on the XML document that's been sent

               

              We don't receive  any errors in our exception log but the calling service gets an error

              ErrorMessage=Unable  to send API Result to EPSL:

               

              faultstring=coldfusion.xml.rpc.CFCInvocationException:

               

              [coldfusion.runtime.CfJspPage$ArrayBoundException : The element at  position 1 cannot be

               

              found.];detail=*coldfusion.xml.rpc.CFCInvocationException:

               

              [coldfusion.runtime.CfJspPage$ArrayBoundException : The element at  position 1 cannot be found.]

               

              at

               

              coldfusion.xml.rpc.CFComponentSkeleton.__createCFCInvocationExceptio

               

              n(CFComponentSkeleton.java:723)

               

              at

               

              coldfusion.xml.rpc.CFComponentSkeleton.__invoke(CFComponentSkeleto

               

              n.java:670)

               

              at

               

              sol.SolServiceListener.SolReceiveResult(........

               

              What I'm asking - Is how do I get hold of the XML that has been returned because it's not getting parsed correctly by the underlying Axis framework - Do I need to make the java classes generated from running WSDL2Java available on the classpath and how do I reference them in the code to ensure that the SOL_Result object that is sent is interpreted correctly

              • 4. Re: Creating a complex webservice as a listener
                joannecorless Level 1

                The calling server is a C# one sending the XML in a SOAP envelope -  My webservice at the other end working as the listener is Coldfusion  -  We've done a bit more investigation and found that the underlying object  that Coldfusion uses for the XML is an org.apache.xerces.dom.DeferredDocumentImpl - This works fine when I  use my test harness (which is my local dev Coldfusion server) but when  the remote system sends the SOAP envelope - Coldfusion doesn't seem to  be able to read it correctly and returns a seemingly null object

                I've  tried making use of the underlying java methods but they return null  and I've tried getting the toString() of the object and parsing that but  that is empty as well

                 

                As I mentioned before the only real clue I have that might help  is the WSDL supplied to us by the supplier

                In my Coldfusion  generated wsdl - the object is being defined as

                <element  name="SOL_Result" type="apachesoap:Document"/>

                 

                whereas in the  suppliers original wsdl - it is defined as

                 

                <xs:element  name="SOL_Result" type="tns:TSOL_Result" nillable="true" minOccurs="1"  maxOccurs="1" />

                 

                I don't know how to deal with this object  difference - It's obviously significant

                 

                I've actually now managed to get something working with the supplier  WSDL - the webservice accepts calls to it - However the object created from  the SOAP envelope sent in is still empty - I'm not sure Coldfusion  actually likes the suppliers WSDL as it has alot of complex type  definitions in it

                 

                I'm completely at a standstill as how to  progress with this - It is usually just so easy with Coldfusion but when  it doesn't work boy doesn't it work big time!

                • 5. Re: Creating a complex webservice as a listener
                  BKBK Adobe Community Professional & MVP
                  It's receiving stuff back that is the problem

                   

                  Sorry about that. Could we see the code you use for receiving stuff back?

                  • 6. Re: Creating a complex webservice as a listener
                    Jochem van Dieten Level 4

                    Does the supplier have a reference implementation?

                    • 7. Re: Creating a complex webservice as a listener
                      joannecorless Level 1

                      They do but it's in C# which isn't really any help

                      • 8. Re: Creating a complex webservice as a listener
                        joannecorless Level 1

                        We've had a bit of a breakthrough this morning - It appears that the WSDL is incorrect and there are namespace declarations missing which means that Coldfusion can't de-serialize properly - I don't think that there is actually anything wrong with the code at this point - I think it's the WSDL - I'm now writing the service by hand in Java to try and get around the problems