Board index » delphi » bds 2006 against Visual Studio 2005 webservice

bds 2006 against Visual Studio 2005 webservice


2006-04-22 11:28:58 PM
delphi242
I've got a relatively simple Webservice that is written in C# and .net
2.0 (VS2005). One of the methods is a method that returns an object
based on a unique identifier. That method is called "GetContactById",
and takes a single long parameter. The webservice is responsible for
populating that structure by making the required database calls.
I have run the WSDL compiler in both Delphi and C++ Builder 2006, and
have breakpoints set in both development environments. The problem is,
VS2005 is not correctly receiving the parameter to the GetContactById()
call. I am passing a long value of 5, and inside the de{*word*81} on the VS
side, it thinks it is getting a 0.
If I use another .net client to access the same webservice, the value
comes over fine. Since these are all just XML messages being passed
back and forth, I ran MS Soap toolkit 3.0 to track the messages and
compared the differences between the Borland generated requests and the
Microsoft generated requests, and there are some that I am investigating.
I was hoping however that someone else had run across what would seem
like a basic problem and have a potential suggestion for a solution.
Here is the XML that the Borland client is generating for the
GetContactById call:
<?xml version="1.0" ?>
<SOAP-ENV:Envelope
xmlns:SOAP-ENV="schemas.xmlsoap.org/soap/envelope/"
xmlns:xsd="www.w3.org/2001/XMLSchema"
xmlns:xsi="www.w3.org/2001/XMLSchema-instance"
xmlns:SOAP-ENC="schemas.xmlsoap.org/soap/encoding/">
<SOAP-ENV:Body
SOAP-ENV:encodingStyle="schemas.xmlsoap.org/soap/encoding/">
<NS1:GetContactById xmlns:NS1="tempuri.org/">
<Id xsi:type="xsd:long">5</Id>
</NS1:GetContactById>
</SOAP-ENV:Body>
</SOAP-ENV:Envelope>
Here is the XML that the Microsoft C# 2.0 client is generating for the
GetContactById call:
<?xml version="1.0" encoding="utf-8" ?>
<soap:Envelope xmlns:soap="schemas.xmlsoap.org/soap/envelope/"
xmlns:xsi="www.w3.org/2001/XMLSchema-instance"
xmlns:xsd="www.w3.org/2001/XMLSchema">
<soap:Body>
<GetContactById xmlns="tempuri.org/">
<id>5</id>
</GetContactById>
</soap:Body>
</soap:Envelope>
The first difference I noticed is that the Borland generated client is
including type information in the data element for 'id', but that can be
turned on or off by toggling the
THTTPRIO.Converter.Options.soSendUntyped option. I have tried toggling
this flag and it changes the XML message that is sent, but that doesn't
seem to affect the behavior.
Another difference I noticed is that Microsoft uses simpler soap tags
<soap>vs. <SOAP-ENV>.
Yet another difference I noticed is that the Borland version includes
the namespace as part of the method name. I wouldn't think this to be a
problem because inside the Microsoft IDE, I have a breakpoint set in the
method I am calling, and when the borland client executes, I am hitting
that breakpoint in the Microsoft IDE, so the Microsoft environment is
correctly mapping the method to its response. that is all I can see
different, and I am while I am new at this, I am admittedly stumped.
 
 

Re:bds 2006 against Visual Studio 2005 webservice

sean hoffman writes:
[Borland]
<Id xsi:type="xsd:long">5</Id>
[.NET]
<id>5</id>
XML is case sensitive. Could that be the problem? (Id vs id)
Quote
Another difference I noticed is that Microsoft uses simpler soap tags
<soap>vs. <SOAP-ENV>.
This is no issue because the "SOAP-ENV:" and "soap:" are aliases, you
could use something like
<sean:Envelop xmlns:sean="schemas.xmlsoap.org/soap/envelope/" ...
and it would be exactly the seme.
Quote
Yet another difference I noticed is that the Borland version includes
the namespace as part of the method name.
Typically this should not be a problem but it is, here.
<GetContactById xmlns="tempuri.org/">
<id>5</id>
</GetContactById>
as generated by .NET puts the element "id" in the namespace
"tempuri.org". that is because the parent element
"GetContactById" is rooted to that namespace by the "xmlns=" attribute
(children inherit that)
In the Borland generated code:
<NS1:GetContactById xmlns:NS1="tempuri.org/">
<Id xsi:type="xsd:long">5</Id>
</NS1:GetContactById>
the "Id" node is in no specific namespace (it should have the NS1: tag
to be in the parent namespace) I think that is the problem.
There should be a way to set the namespace of a specific node - You
might be able to figure that out from the source. Otherwise, post a
demo project and I will try and work it out.
--
Deepak Shenoy (TeamB)
shenoyatwork.blogspot.com
 

Re:bds 2006 against Visual Studio 2005 webservice

Sean,
I have something similar, passing a string parameter to a simple
webservice ( return an other string ). When I pass "1" as string value
the vs2005 webservice doesn't receive this as a "1"
I do not have a solution.
But I think it is the responsibility for Borland to provide working
tools. I spend my money on BDS2006 ( update from my favourite delphi 5 )
because I needed the added webservice-functionality. But right now I
wonder if it would be a better idea to switch to VS2005 for the client
part of my application also. I mean.... this is the most simple
webservice on the planet and I am not able to use it "out of the box". My
time is precious Borland. How's yours ?
Leon
 

Re:bds 2006 against Visual Studio 2005 webservice

Leon, I can completely understand how you feel. My problem is I don't
know enough about SOAP to know if it is Borland's issue or Microsoft's
problem. I know from experience that Microsoft doesn't always follow
standardization rules; I remember when SET (secure electronic
transactions) was a hot item having to work around the fact that their
HTTP messages always had extra data larger than what their
content-length indicator suggested. I got my knuckles wrapped at the
time for insisting that our development partner adhere to the standard
because it was a security risk.
In any case, even if it is Microsoft's problem, with Borland being the
paddleboat and Microsoft being the oceanliner, it unfortunately is in
Borland's best interest to make it as easy as possible to interact with
an industry leader. SOAP just represents too big an opportunity to
allow x-platform development. The API I am working on will be accessible
from both fat-clients and thin clients UIs. that is a big win. I opened
a bug report on it:
qc.borland.com/wc/qcmain.aspx
leon writes:
Quote
Sean,

I have something similar, passing a string parameter to a simple
webservice ( return an other string ). When I pass "1" as string value
the vs2005 webservice doesn't receive this as a "1"

I do not have a solution.
But I think it is the responsibility for Borland to provide working
tools. I spend my money on BDS2006 ( update from my favourite delphi 5 )
because I needed the added webservice-functionality. But right now I
wonder if it would be a better idea to switch to VS2005 for the client
part of my application also. I mean.... this is the most simple
webservice on the planet and I am not able to use it "out of the box". My
time is precious Borland. How's yours ?

Leon
 

Re:bds 2006 against Visual Studio 2005 webservice

Sean,
thanks for your clear reply.8 years ago when I "discovered" delphi I
promised never to go back to an MS environment again. And look at me now
( haha ).
Leon
 

Re:bds 2006 against Visual Studio 2005 webservice

Hi,
We are experiencing the same problems, and I might have found the
underlying issue. If you look at the soap message, you will see that
Delphi is specifying encoding. It looks like Delphi is trying to use
the (old) rpc/encoding message style, rather than the document/literal
message style. Do any of you know how to specifiy the request encoding
style from Delphi? As best as I can tell, I can only specify to use
rpc/encoding in the Microsoft environment, since document/literal is
the default.
-- Sancerre
leon writes:
Quote
Sean,

thanks for your clear reply.8 years ago when I "discovered" delphi I
promised never to go back to an MS environment again. And look at me now
( haha ).

Leon
 

Re:bds 2006 against Visual Studio 2005 webservice

Sean,
As per my post below, we detected an encoding issue that explains your
data going from 5 to 0 (0 is the default for ints). We had the same
problem, basically all data was getting nulled out or set to default
values. I build a dead simple web service that accepted a string and
sent it right back. The string value kept on getting received as null,
even though the Delphi client was sending text. The Soap message from
Delphi declared the same encodingStyle as your message above. My
colleague (the Delphi guy) made a change in serialization settings, and
all worked as it should. The new Soap message didn't specify encoding,
so the default took over (the default is document/literal). In short,
using rpc/encoding when call a .NET web service is problematic. For
that matter, it sounds like rpc/encoding is basically getting
deprecated in all new WS standards,
Hope this helps,
Sancerre
 

Re:bds 2006 against Visual Studio 2005 webservice

"sance" writes:
Quote
The string value kept on getting received as null, even though the Delphi
client was sending text. The Soap message from Delphi declared the same
encodingStyle as your message above. My
colleague (the Delphi guy) made a change in serialization settings, and
all worked as it should.
Would you mind sharing how you set the style to literal in Delphi? I'm
having the exact same problem with nulls.
BTW, I believe messages posted on google groups don't show up on the borland
servers.
 

Re:bds 2006 against Visual Studio 2005 webservice

As I understand if, there is an option to set the serialization. I
don't know how, since I work on the .NET side of things. However, I do
know that the file generated by Delphi includes the following snippets
after setting the serialization - everywhere where you see
..ToSoapDomConvert is the new code.
1. interface declaration
interface
uses InvokeRegistry, SOAPHTTPClient, Types,
XSBuiltIns,OPToSOAPDomConv,OpConvert;
type
2. variable declaration
var
RIO: THTTPRIO;
DCT:TOPToSoapDomConvert; // To expose the data converter
begin
3. in the middle of the procedure
DCT:=RIO.Converter;
DCT.Options:=[
soDocument,soTryAllSchema,soUTF8InHeader,soUTF8EncodeXML,soSendMultiRefObj
]; // To set the convertion options
Hope that this helps,
Sancerre
 

Re:bds 2006 against Visual Studio 2005 webservice

sean & others,
I have posted the following via Google Groups, but it looks like the message never got here, so... By the way, we have solved the problem!
Post 1:
Hi,
We are experiencing the same problems, and I might have found the underlying issue. If you look at the soap message, you will see that Delphi is specifying encoding. It looks like Delphi is trying to use the (old) rpc/encoding message style, rather than the document/literal message style. Do any of you know how to specifiy the request encoding style from Delphi? As best as I can tell, I can only specify to use rpc/encoding in the Microsoft environment, since document/literal is the default.
-- Sancerre
Post 2:
Sean,
As per my post below, we detected an encoding issue that explains your data going from 5 to 0 (0 is the default for ints). We had the same problem, basically all data was getting nulled out or set to default values. I build a dead simple web service that accepted a string and sent it right back. The string value kept on getting received as null, even though the Delphi client was sending text. The Soap message from Delphi declared the same encodingStyle as your message above. My
colleague (the Delphi guy) made a change in serialization settings, and all worked as it should. The new Soap message didn't specify encoding, so the default took over (the default is document/literal). In short, using rpc/encoding when call a .NET web service is problematic. For that matter, it sounds like rpc/encoding is basically getting deprecated in all new WS standards,
Hope this helps,
Sancerre
Post 3:
As I understand if, there is an option to set the serialization. I don't know how, since I work on the .NET side of things. However, I do know that the file generated by Delphi includes the following snippets after setting the serialization - everywhere where you see ..ToSoapDomConvert is the new code.
1. interface declaration
interface
uses InvokeRegistry, SOAPHTTPClient, Types,
XSBuiltIns,OPToSOAPDomConv,OpConvert;
type
2. variable declaration
var
RIO: THTTPRIO;
DCT:TOPToSoapDomConvert; // To expose the data converter
begin
3. in the middle of the procedure
DCT:=RIO.Converter;
DCT.Options:=[
soDocument,soTryAllSchema,soUTF8InHeader,soUTF8EncodeXML,soSendMultiRefObj
]; // To set the convertion options
Hope that this helps,
Sancerre
sean hoffman <XXXX@XXXXX.COM>writes:
Quote
I've got a relatively simple Webservice that is written in C# and .net
2.0 (VS2005). One of the methods is a method that returns an object
based on a unique identifier. That method is called "GetContactById",
and takes a single long parameter. The webservice is responsible for
populating that structure by making the required database calls.

I have run the WSDL compiler in both Delphi and C++ Builder 2006, and
have breakpoints set in both development environments. The problem is,
VS2005 is not correctly receiving the parameter to the GetContactById()
call. I am passing a long value of 5, and inside the de{*word*81} on the VS
side, it thinks it is getting a 0.

If I use another .net client to access the same webservice, the value
comes over fine. Since these are all just XML messages being passed
back and forth, I ran MS Soap toolkit 3.0 to track the messages and
compared the differences between the Borland generated requests and the
Microsoft generated requests, and there are some that I am investigating.
I was hoping however that someone else had run across what would seem
like a basic problem and have a potential suggestion for a solution.

Here is the XML that the Borland client is generating for the
GetContactById call:

<?xml version="1.0" ?>
<SOAP-ENV:Envelope
xmlns:SOAP-ENV="schemas.xmlsoap.org/soap/envelope/"
xmlns:xsd="www.w3.org/2001/XMLSchema"
xmlns:xsi="www.w3.org/2001/XMLSchema-instance"
xmlns:SOAP-ENC="schemas.xmlsoap.org/soap/encoding/">
<SOAP-ENV:Body
SOAP-ENV:encodingStyle="schemas.xmlsoap.org/soap/encoding/">
<NS1:GetContactById xmlns:NS1="tempuri.org/">
<Id xsi:type="xsd:long">5</Id>
</NS1:GetContactById>
</SOAP-ENV:Body>
</SOAP-ENV:Envelope>


Here is the XML that the Microsoft C# 2.0 client is generating for the
GetContactById call:
<?xml version="1.0" encoding="utf-8" ?>
<soap:Envelope xmlns:soap="schemas.xmlsoap.org/soap/envelope/"
xmlns:xsi="www.w3.org/2001/XMLSchema-instance"
xmlns:xsd="www.w3.org/2001/XMLSchema">
<soap:Body>
<GetContactById xmlns="tempuri.org/">
<id>5</id>
</GetContactById>
</soap:Body>
</soap:Envelope>

The first difference I noticed is that the Borland generated client is
including type information in the data element for 'id', but that can be
turned on or off by toggling the
THTTPRIO.Converter.Options.soSendUntyped option. I have tried toggling
this flag and it changes the XML message that is sent, but that doesn't
seem to affect the behavior.

Another difference I noticed is that Microsoft uses simpler soap tags
<soap>vs. <SOAP-ENV>.

Yet another difference I noticed is that the Borland version includes
the namespace as part of the method name. I wouldn't think this to be a
problem because inside the Microsoft IDE, I have a breakpoint set in the
method I am calling, and when the borland client executes, I am hitting
that breakpoint in the Microsoft IDE, so the Microsoft environment is
correctly mapping the method to its response. that is all I can see
different, and I am while I am new at this, I am admittedly stumped.
 

Re:bds 2006 against Visual Studio 2005 webservice

Make sure you have
InvRegistry.RegisterInvokeOptions(TypeInfo(YourInterface), ioDocument);
in your WSDL import file - down in the innitialization part.
Neil
sean hoffman <XXXX@XXXXX.COM>wrote in
Quote
I've got a relatively simple Webservice that is written in C# and .net
2.0 (VS2005). One of the methods is a method that returns an object
based on a unique identifier.
 

Re:bds 2006 against Visual Studio 2005 webservice

"Neil McEntaggart" <XXXX@XXXXX.COM>writes
Quote
Make sure you have

InvRegistry.RegisterInvokeOptions(TypeInfo(YourInterface), ioDocument);
in your WSDL import file - down in the innitialization part.

Neil


Are you saying you can pass paramters to a VS2005 .net web service with this
change?
It doesn't work for me. The problem is that the parameters are not passed in
proper namespace.
 

Re:bds 2006 against Visual Studio 2005 webservice

For sure I have a number of instances where I am calling VS2005 webservices
from win32 delphi code. usualy I have to hack a bit at the imported WSDL,
but I can get it to work. I have passed simple and complex objects back and
forth too and have had this work for me in D6, Delphi 7 and D2006.
Did you try adding the RegisterInvokeOptions line to your innitialization ?
Try that and also make sure that you have soDocument in your converter
options.
The ioDocument will take the explicit typing out of parameters. If you are
passing a complex type as a parameter there is an option on the TRemotable
to stop it from namespacing node names for complex subtypes.
If you send me a stripped down code example I should be able to send you
back working calling code.
Neil
Quote

Are you saying you can pass paramters to a VS2005 .net web service
with this change?

It doesn't work for me. The problem is that the parameters are not
passed in proper namespace.


 

Re:bds 2006 against Visual Studio 2005 webservice

Ok.. I found my mistake. I thought you meant I had to replace the call
passing ioLiteral using ioDocument. But both are needed. Which makes sense
since literal should only be replaced by encoded now that I think about it.
Thanks for you help Neil.
I still don't understand why the WSDL importer doesn't do this for you.
Other people are bound to go through the same confusion.
"Neil McEntaggart" <XXXX@XXXXX.COM>writes
Quote
Did you try adding the RegisterInvokeOptions line to your innitialization
?
Try that and also make sure that you have soDocument in your converter
options.

The ioDocument will take the explicit typing out of parameters. If you are
passing a complex type as a parameter there is an option on the TRemotable
to stop it from namespacing node names for complex subtypes.

 

Re:bds 2006 against Visual Studio 2005 webservice

Quote
I still don't understand why the WSDL importer doesn't do this for
you. Other people are bound to go through the same confusion.

It does do it sometimes. I am not sure why it dosen't do it all the time.
From what I have seen of the win32 soap code - it is all rather poorly
written, so it is not a supprise.
Glag that I could help.
Neil