Both of them can take (owing to using params) variable quantity of income
parameters.
Then I use these methods inside other methods of that web service, they
successfully work. For example, I can invoke method as
MethodName1("StringHere") and as MethodName1("StringHere",25).
Now I need to invoke methods on client side. And unfortunately with
MethodName1("StringHere") I receive the error:
No overload for method 'MethodName1' takes '1' arguments
What is my mistake?
And how can I use methods with params on clien side? What should I do?
I expect your help impatiently.
For example:
[webmethod] MyMethod (IncomingMessage m) {
...
}
where IncomingMessage is defined in a W3C XML Schema to include numerous
fields, all of which are optional. In C# or VB, it would be a struct or
class with numerous properties, not all of which need to be set (or passed).
Variable param lists is a function-call concept. For web services, you have
to think "message passing", not "remote function call". You don't pass
"variable parameter lists" to a webmethod, you pass a message, with varying
content within it.
-D
"Evgenia" <Evg...@discussions.microsoft.com> wrote in message
news:FA50226F-CF39-43FD...@microsoft.com...
I nearly understand your idea. But, please, may I ask you for a simple
example of IncomingMessage class?
And one more question - what will be the invoke of such method? How will it
look like? For me it's very important to use invokes like:
MyMethod(param1)
MyMethod(param1,param2)
MyMethod(param1,param2,param3)
Is it possible?
here is a great article covering the topic:
http://www.webservices.org/index.php/ws/content/view/full/39565
> please, may I ask you for a simple example of IncomingMessage class?
The way I do it: construct a W3C XML Schema describing the datatype, then
generate types for that Schema, specific to each platform. Let's suppose
you have a .NET and a Java system inter-connecting via webservices. A
request message gets passed from requester to receiver - it does not matter
which one is which. The message might include an order ID, a priority, some
authentication information, and a conversation ID. In response, optionally
a Response Message gets passed back. [in one-way web service requests,
there is no response message]. In C# code you might code something like
this series of classes:
public enum PriorityLevel {
Normal=0,
High=1,
Urgent=2,
Lazy=3
}
// this is the request message
public class RequestMessage1 {
public int orderID;
public PriorityLevel priority;
public string OnBehalfOf;
public int conversationID;
}
public class Order {
public int ID;
public int customerID;
// public OrderItems[] i;
// etc
}
public enum Confidence {
High,
Normal,
Low
}
// this is the response message
public class ResponseMessage {
public Order o;
public Confidence c;
// etc
}
By compiling this C# code into a DLL, then running xsd.exe on the resulting
DLL, you can develop an XSD that describes these types. It looks like
this:
<xs:schema elementFormDefault="qualified"
xmlns:xs="http://www.w3.org/2001/XMLSchema">
<xs:element name="PriorityLevel" type="PriorityLevel" />
<xs:simpleType name="PriorityLevel">
<xs:restriction base="xs:string">
<xs:enumeration value="Normal" />
<xs:enumeration value="High" />
<xs:enumeration value="Urgent" />
<xs:enumeration value="Lazy" />
</xs:restriction>
</xs:simpleType>
<xs:element name="RequestMessage1" nillable="true" type="RequestMessage1"
/>
<xs:complexType name="RequestMessage1">
<xs:sequence>
<xs:element minOccurs="1" maxOccurs="1" name="orderID" type="xs:int"
/>
<xs:element minOccurs="1" maxOccurs="1" name="priority"
type="PriorityLevel" />
<xs:element minOccurs="0" maxOccurs="1" name="OnBehalfOf"
type="xs:string" />
<xs:element minOccurs="1" maxOccurs="1" name="conversationID"
type="xs:int" />
</xs:sequence>
</xs:complexType>
<xs:element name="Order" nillable="true" type="Order" />
<xs:complexType name="Order">
<xs:sequence>
<xs:element minOccurs="1" maxOccurs="1" name="ID" type="xs:int" />
<xs:element minOccurs="1" maxOccurs="1" name="customerID"
type="xs:int" />
</xs:sequence>
</xs:complexType>
<xs:element name="Confidence" type="Confidence" />
<xs:simpleType name="Confidence">
<xs:restriction base="xs:string">
<xs:enumeration value="High" />
<xs:enumeration value="Normal" />
<xs:enumeration value="Low" />
</xs:restriction>
</xs:simpleType>
<xs:element name="ResponseMessage" nillable="true" type="ResponseMessage"
/>
<xs:complexType name="ResponseMessage">
<xs:sequence>
<xs:element minOccurs="0" maxOccurs="1" name="o" type="Order" />
<xs:element minOccurs="1" maxOccurs="1" name="c" type="Confidence" />
</xs:sequence>
</xs:complexType>
</xs:schema>
You can now modify, adjust, tweak, or extend this XSD. [The alternative is
to simply write XSD from the beginning, without prototyping the messages in
C#. If you are fluent in XSD or have tools like XmlSpy, then go for it!
But not all people "think in XSD". ]
At some point you will be happy with your schema definition. Take this
schema and then generate platform-specific types with it. Also, import
this XSD into the web service interface definition (WSDL).
http://devresource.hp.com/drc/slide_presentations/schemaWSDL/index.jsp
Then generate proxy classes (stubs) for the client from this WSDL. Also
generate server-side skeleton classes for the server from the same WSDL.
This approach of designing the datatypes and interface and deriving or
generating the implementation skeleton from those definitions is called
"WSDL first" or sometimes "contract first" design.
http://www.google.com/search?hl=en&num=30&q="contract+first"+"web+services"
In your case you have fields like param1, param2, param3, etc. It will look
like this in (generated) C# code:
public class RequestMessage1 {
public int param1;
public string param2,
public MyCustomDataType param3;
// etc
}
(NB: the actual code will be attributed with XmlSerialization attributes).
The requester application can then instantiate the RequestMessage1,
optionally fill or set the fields as necessary, and then invoke the service.
Like so:
// get a proxy to the remote webservice
MyNamespace.MyWebService svc= new MyNamespace.MyWebService () ;
// instantiate and fill the request
MyNamespace.RequestMessage1 m = MyNamespace.RequestMessage1 () ;
m.param1= 42;
if (some condition) m.param2= "Contract First";
if (I feel like it) m.param3= new MyCustomDataType(....) ;
// invoke (implicitly passing the request message)
MyNamespace.ResponseMessage1 r = svc.MyMethod(m);
The request and response messages are always the same type, but the fields
within them may be optionally set, or not. On the server side, the code
can behave differently depending on the content of the incoming request
message.
-Dino
--
Dino Chiesa
Microsoft Developer Division
d i n o c h @ OmitThis . m i c r o s o f t . c o m
"Evgenia" <Evg...@discussions.microsoft.com> wrote in message
news:16F5645F-8B6F-452E...@microsoft.com...
No. Well, it is possible, but it goes counter to my advice of using a
message-passing model.