I have a web service that I'm trying to call using VS2005. I'm not understanding how to pass a collection as a parameter into my web service. (This does work in VS2003 by modifying the Reference.vb file, which does not exist in VS2005.)
Here is a simple web service:
<WebMethod()> _
Public Sub TestMethod(ByRef oTestItems As GlobalAccountsClasses.TestItems)
End Sub
Here is the TestItems collection along with the TestItem class:
Public Class TestItems
Inherits CollectionBase
'Retrieves an item from the collection by index
Default Public Property Item(ByVal Index As Integer) As TestItem
Get
Return CType(List.Item(Index), TestItem)
End Get
Set(ByVal Value As TestItem)
List.Item(Index) = Value
End Set
End Property
'Adds an item to the collection
Public Function Add(ByVal Item As TestItem) As Integer
Return List.Add(Item)
End Function
Public Sub Remove(ByVal Item As TestItem)
List.Remove(Item)
End Sub
End Class
Public Class TestItem
Private _FirstName As String
Private _LastName As String
Public Property FirstName() As String
Get
Return _FirstName
End Get
Set(ByVal Value As String)
_FirstName = Value
End Set
End Property
Public Property LastName() As String
Get
Return _LastName
End Get
Set(ByVal Value As String)
_LastName = Value
End Set
End Property
End Class
Here is the VS2005 generated wsdl definition of what we have so far:
<s:element name="TestMethod">
<s:complexType>
<s:sequence>
<s:element minOccurs="0" maxOccurs="1" name="oTestItems" type="tns:ArrayOfTestItem" />
</s:sequence>
</s:complexType>
</s:element>
<s:complexType name="ArrayOfTestItem">
<s:sequence>
<s:element minOccurs="0" maxOccurs="unbounded" name="TestItem" nillable="true" type="tns:TestItem" />
</s:sequence>
</s:complexType>
<s:complexType name="TestItem">
<s:sequence>
<s:element minOccurs="0" maxOccurs="1" name="FirstName" type="s:string" />
<s:element minOccurs="0" maxOccurs="1" name="LastName" type="s:string" />
</s:sequence>
</s:complexType>
<s:element name="TestMethodResponse">
<s:complexType>
<s:sequence>
<s:element minOccurs="0" maxOccurs="1" name="oTestItems" type="tns:ArrayOfTestItem" />
</s:sequence>
</s:complexType>
</s:element>
Here is what I'm expecting to be able to do in my aspx.vb but I can't:
Dim oTestWebService As New GlobalAccountsWebService_Test.Test
Dim oTestItems As New GlobalAccountsWebService_Test.TestItems
Dim oTestItem As New GlobalAccountsWebService_Test.TestItem
oTestItem.FirstName = "FN"
oTestItem.LastName = "LN"
oTestItems.Add(oTestItem)
oTestWebService.TestMethod(oTestItems)
Any help would be greatly appreciated.

VS2005 - Passing Collection/Array as a Parameter to a Web Service
ManjuVijay
dophine
Rodrigo,
Thanks for the reply. I've looked everywhere for a reference.vb file but I can't find one anywhere in my project. Under each web service I have a .disco, .discomap, and .wsdll; no Reference.vb file anywhere. Where are your Reference.vb files in a VS2005 project
I'll look into the SchemaImporterExtensions.
FireFreak
Hello Rodrigo,
You have mentioned in your previous reply something about “SchemaImporterExtensions”, and have said that it can modify the way the proxy class is generated.
I currently need that ability of modifying the proxy class generation.
My case is the following:
1- I am using the same ClassLibrary on the server and client side.
2- Web Methods are returning objects of types that exist in the ClassLibrary (example: ClassA).
3- When I “Update Web Reference” in Visual Studio 2005 it creates a Reference.cs file. It implements a new dynamically generated version of ClassA, which only contains private fields and public properties with the same names as the alternate properties in the original ClassA of the ClassLibrary.
4- Each time their would be changes in the web service, I need to:
a. “Update Web Reference
b. Open the Reference.cs file and add a “using” statement to include the ClassLibrary.
c. And remove all the dynamically generated versions of the original ClassLibrary.ClassA class.
d. And modify the types that are generated in the return values of the web methods (in case I was using a CollectionBase derived class), example: ClassA[] to ClassACollection class.
If the use of “SchemaImporterExtensions” helps me avoid this annoying modification each time I need to update the web reference, please reply with whatever deficient information or code examples I should know.
Thanks in advance,
Fadi
Ultrawhack
jason,
Reference.vb is still there and you can modify it as you used to do it with VS2003.
However modifying it each time you update the web references is quite annoying. For that a new feature is included with .NET Framework 2.0 that is called "SchemaImporterExtensions"
Schema importer extensions can modify the way the proxy class is generated for example adding "using" statements and avoiding the type convertion the wsdl tool implements.... I found it very useful with generic types for example (List<T> is converted to T[] by wsdl.exe)
Please let me know whether you need more info. on the SIE implementation.
Rgds
Rodrigo
Namrata Prashar
Hello Rodrigo,
You have mentioned in your previous reply something about “SchemaImporterExtensions”, and have said that it can modify the way the proxy class is generated.
I currently need that ability of modifying the proxy class generation.
My case is the following:
1- I am using the same ClassLibrary on the server and client side.
2- Web Methods are returning objects of types that exist in the ClassLibrary (example: ClassA).
3- When I “Update Web Reference” in Visual Studio 2005 it creates a Reference.cs file. It implements a new dynamically generated version of ClassA, which only contains private fields and public properties with the same names as the alternate properties in the original ClassA of the ClassLibrary.
4- Each time their would be changes in the web service, I need to:
a. “Update Web Reference
b. Open the Reference.cs file and add a “using” statement to include the ClassLibrary.
c. And remove all the dynamically generated versions of the original ClassLibrary.ClassA class.
d. And modify the types that are generated in the return values of the web methods (in case I was using a CollectionBase derived class), example: ClassA[] to ClassACollection class.
If the use of “SchemaImporterExtensions” helps me avoid this annoying modification each time I need to update the web reference, please reply with whatever deficient information or code examples I should know.
Thanks in advance,
Fadi
AAKurtz
You have to select the web reference in your client project. Then click on "Show all files".... you should see Reference.map, Service.disco and Service.wsdl
Under Reference.map you should have the Reference.vb proxy class.
http200
Hello Rodrigo,
You have mentioned in your previous reply something about “SchemaImporterExtensions”, and have said that it can modify the way the proxy class is generated.
I currently need that ability of modifying the proxy class generation.
My case is the following:
1- I am using the same ClassLibrary on the server and client side.
2- Web Methods are returning objects of types that exist in the ClassLibrary (example: ClassA).
3- When I “Update Web Reference” in Visual Studio 2005 it creates a Reference.cs file. It implements a new dynamically generated version of ClassA, which only contains private fields and public properties with the same names as the alternate properties in the original ClassA of the ClassLibrary.
4- Each time their would be changes in the web service, I need to:
a. “Update Web Reference
b. Open the Reference.cs file and add a “using” statement to include the ClassLibrary.
c. And remove all the dynamically generated versions of the original ClassLibrary.ClassA class.
d. And modify the types that are generated in the return values of the web methods (in case I was using a CollectionBase derived class), example: ClassA[] to ClassACollection class.
If the use of “SchemaImporterExtensions” helps me avoid this annoying modification each time I need to update the web reference, please reply with whatever deficient information or code examples I should know.
Thanks in advance,
Fadi
Dennis Mark Thorsen
Hello Rodrigo,
You have mentioned in your previous reply something about “SchemaImporterExtensions”, and have said that it can modify the way the proxy class is generated.
I currently need that ability of modifying the proxy class generation.
My case is the following:
1- I am using the same ClassLibrary on the server and client side.
2- Web Methods are returning objects of types that exist in the ClassLibrary (example: ClassA).
3- When I “Update Web Reference” in Visual Studio 2005 it creates a Reference.cs file. It implements a new dynamically generated version of ClassA, which only contains private fields and public properties with the same names as the alternate properties in the original ClassA of the ClassLibrary.
4- Each time their would be changes in the web service, I need to:
a. “Update Web Reference
b. Open the Reference.cs file and add a “using” statement to include the ClassLibrary.
c. And remove all the dynamically generated versions of the original ClassLibrary.ClassA class.
d. And modify the types that are generated in the return values of the web methods (in case I was using a CollectionBase derived class), example: ClassA[] to ClassACollection class.
If the use of “SchemaImporterExtensions” helps me avoid this annoying modification each time I need to update the web reference, please reply with whatever deficient information or code examples I should know.
Thanks in advance,
Fadi
Tryst
Fadi,
here you have an example of a SIE....
1. First create a class library for the SIE
2. Create a new class that inherits from System.Xml.Serialization.Advanced.SchemaImporterExtension
3. Override the ImportSchemaType method..... here you have an example of that in where I change the proxy generation so you have List<T> in the proxy instead of T[]
public
override string ImportSchemaType(string name, string ns, XmlSchemaObject context, System.Xml.Serialization.XmlSchemas schemas, System.Xml.Serialization.XmlSchemaImporter importer, CodeCompileUnit compileUnit, CodeNamespace mainNamespace, System.Xml.Serialization.CodeGenerationOptions options, System.CodeDom.Compiler.CodeDomProvider codeProvider){
try{
// use the SIE only for my types if (!ns.Contains("mynamespace.com")) return null; string typeName = name; if (!string.IsNullOrEmpty(name)){
// When returning List<T> it is serialized as ArrayOfT .... so I check for that to change it back to List<T> if (name.StartsWith("ArrayOf")){
// Using CodeDOM I add the using statement to System.Collection.Generic in the generated proxymainNamespace.Imports.Add(
new CodeNamespaceImport("System.Collections.Generic")); // I get the actual generic type (T) string nType = name.Substring(7);typeName =
string.Format("List<{0}>", nType);}
}
// I return List<T> instead of ArrayOfT return typeName;}
catch{
// returning null will do the usual stuff. return null;}
}
4. Sign the assembly and put it in the GAC
5. Register the SIE in the machine.config....
<
system.xml.serialization><
schemaImporterExtensions><
add name="someName" type="full type name here" /></
schemaImporterExtensions></
system.xml.serialization>6. Restart Visual Studio to see the changes.
Hope it helps
Rgsd
Rodrigo