.NET Forum / ASP.NET / Web Services / March 2005
Need help on passing custom objects (classes) to web service
|
|
Thread rating:  |
Noel - 05 Mar 2005 16:15 GMT Hello,
I'm currently developing a web service that retrieves data from an employee table. I would like to send and retrieve a custom employee class to/from the webservice. I have currently coded the custom employee class and have built it as a separate library (employee.dll). This employee.dll is being referenced by both the web service and the windows application.
I face the following problem when I send this class to the webservice.
1. The procedures and functions are not getting serialized. i.e. when the webservice returns this class, I'm unable to access the procedures and functions for manipulating the data in the class.
Could someone let me know how I could solve this issue? I'm in trouble and am badly in need of help. Please advise.
Thanks, Noel
Manohar Kamath - 05 Mar 2005 16:35 GMT The methods are never serialized in web services, only data (state) is. You could serialize and de-serialize into the same type, but it will require some manual changes to your proxy classes (you need to reference the employee assembly, instead of proxy-generated types).
 Signature Manohar Kamath Editor, .netWire www.dotnetwire.com
> Hello, > [quoted text clipped - 15 lines] > Thanks, > Noel Noel - 07 Mar 2005 05:14 GMT Thanks for the reply Manohar.
When I try to reference the employee assembly instead of proxy-generated types, I get an invalid type-cast error. BTW, I'm trying to pass the employee object to the web-service as a reference. Is there a way to get around the invalid type cast error?
Thanks in advance.
> The methods are never serialized in web services, only data (state) is. You > could serialize and de-serialize into the same type, but it will require [quoted text clipped - 23 lines] > > Thanks, > > Noel Manohar Kamath - 07 Mar 2005 14:57 GMT Could you please post the code snippets? Thanks!
 Signature Manohar Kamath Editor, .netWire www.dotnetwire.com
> Thanks for the reply Manohar. > [quoted text clipped - 35 lines] > > > Thanks, > > > Noel Noel - 07 Mar 2005 17:30 GMT There is so little code, that I thought I'd explain a bit more. Please do not mistake me, just let me know if you still need the code and I'll send it across.
This is what I have in the project:
1. Employee project (stand alone executable - windows application) 2. Employee Class Built as a library. This has been compiled as a library just to allow me to use in both the web services as well as the Employee Project. 3. Web service that interfaces with the database.
The web service and the employee project reference the employee library.
In the windows application, I create an instance of webservice and pass the employee object as reference, like:
Dim wsEmp as New EmployeeWebService Dim obj As EmployeeObject ' obj is sent across by reference - Error occurs here ' (like Employee Object cannot be ' typecast to ' EmployeeWebService.EmployeeObject) wsEmp.GetData(obj)
In the web service, I create an instance of the employee object and fill it with data from the webservice, like:
Sub GetData(ByRef obj As EmployeeObject) obj = New EmployeeObject ' Access database and fill Employee object with data FillData(obj) End Sub
I get an error "Invalid Typecast" in wsEmp.GetData(obj).
Both the objects (Windows and Web Service) are the same and refer to Common.EmployeeObject. I'm wondering if I need to mark the Common.EmployeeObject as serializable (Not sure though).
Thanks in advance.
> Could you please post the code snippets? Thanks! > [quoted text clipped - 38 lines] > > > > Thanks, > > > > Noel Manohar Kamath - 07 Mar 2005 18:54 GMT Noel,
Here's the problem:
You are sending in obj, which is of different type than the proxy type:
wsEmp.GetData(obj)
It is expecting: EmployeeWebService.EmployeeObject -- this is a proxy type, whereas your EmployeeObject is in a different namespace.
To remedy this, you need to manually change your proxy class, remove the type EmployeeWebService.EmployeeObject from the class, and add a reference to your Employee library in the proxy class (using Imports). This tricks the compiler into thinking that you are using the proxy type, while it is actually using your custom type.
Hope that helps.
 Signature Manohar Kamath Editor, .netWire www.dotnetwire.com
> There is so little code, that I thought I'd explain a bit more. Please do > not mistake me, just let me know if you still need the code and I'll send it [quoted text clipped - 86 lines] > > > > > Thanks, > > > > > Noel Glenn - 07 Mar 2005 17:19 GMT Noel
What about creating serialisable types from schema definitions and then passing the xml as a XmlNode or XmlDocument and then deserialising and reserialising inside the web service. That way if anyone else needs to use your web service, you only need publish the schema and wsdl and anyone could bind to it.
As for the employee.dll, could you expose the functionality as a web service? It may make your application a bit chatty on the wire depending on how you use it, but a least you won't have as many deployment headaches (albeit reduced with .net).
Apologies if I've misunderstood Manohar's comment, but manual changes to the web service proxy would be lost if you made a change to the web service and refreshed the reference at the client end.
HTH
Glenn
> Thanks for the reply Manohar. > [quoted text clipped - 40 lines] > > > Thanks, > > > Noel Noel - 07 Mar 2005 17:33 GMT Glenn, I like your idea. Could you please point me to some source code or website where I could learn how to do this? I'll be glad if you could help.
Thanks in advance.
> Noel > [quoted text clipped - 62 lines] > > > > Thanks, > > > > Noel Glenn - 07 Mar 2005 17:42 GMT Noel
Not a problem, but can't do it this evening, Man City vs Bolton and I've got a date with the pub, I'll post some more detail tommorrow morning (GMT ).
Cheers
Glenn
> Glenn, I like your idea. Could you please point me to some source code or > website where I could learn how to do this? I'll be glad if you could help. [quoted text clipped - 79 lines] > > > > > Thanks, > > > > > Noel Glenn - 08 Mar 2005 10:50 GMT Noel
The XML part or exposing the employee.dll functionality as a web service?
With regards to XML serialization
http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dnexxml/htm l/xml01202003.asp
http://msdn.microsoft.com/library/default.asp?url=/library/en-us/cpref/html/ frlrfsystemxmlserialization.asp
If your using VS.NET you could use the rather good XML Designer to build your schema definitions.
As for exposing functionality on the web for an existing DLL, a personal preference is to create a thin web service wrapper type around the existing class. Any overloaded methods can be handled using the MessageName property of the WebMethod attribute.
I've have to say that most of the work I've been doing with XML and web services in general has been processing data in a single hit. Dealing with rich client applications may not lend itself to using a serialisation mechanism.
Thinking about it a bit more, DataSets may be a better solution than having to worry so much about the serialisation mechanism. I've not personally used them in web services having been told by a supposedly more learned colleague not to, but it may be perfect for what you want to do.
I'd check out these articles before attempting to use DataSets with web services
http://www.oreillynet.com/pub/wlg/2142
http://weblogs.asp.net/aaguiar/archive/2004/06/03/147208.aspx
Sorry if I've not been much help, I'm extremely hungover.
Glenn
> Glenn, I like your idea. Could you please point me to some source code or > website where I could learn how to do this? I'll be glad if you could help. [quoted text clipped - 79 lines] > > > > > Thanks, > > > > > Noel Manohar Kamath - 07 Mar 2005 18:55 GMT Yes, you will lose the changes to the proxy classes if you re-generated the proxy class. However, this is one of those "to-do" if this ever happened. And also, once you have the web service solidified, the proxy class should never change -- as a change would mean a change in the version.
 Signature Manohar Kamath Editor, .netWire www.dotnetwire.com
> Noel > [quoted text clipped - 62 lines] > > > > Thanks, > > > > Noel Noel - 08 Mar 2005 05:09 GMT Could you please throw some light on how the versioning needs to be done for the proxy class?
One more question regarding the custom class:
I'm not sure what's the preferred/best method to retrieve the records from the webservice. Which one is better when deciding to retrieve data from web service?
1. Using Datasets (Multiple datatables can be returned. But could this make the web service slower than when using custom objects) 2. Custom objects
BTW, when deciding to use custom objects. How should the records be stored inside the object (I mean what's the industry standard or preferred method of storing multiple records in a custom object?) Should a dataset/datatable be used inside the custom object to store data or is there another better method?
Another question/topic:
The architecture that I want to follow is GUI -> Web service -> Business Objects -> database.
I would like the application to be highly scalable and load balanced. Therefore I would like to scale it at the business objects level. If I have multiple servers with the Business Objects installed/running. How could I let the web service know
1. Which server to use (depending on load balancing.) BTW to load balance should I incorporate any logic to the application/webservice? 2. How to supply/notify my web service at run-time the servers that have the Business Objects running?
Thanks in advance for your valuable inputs.
> Yes, you will lose the changes to the proxy classes if you re-generated the > proxy class. However, this is one of those "to-do" if this ever happened. [quoted text clipped - 79 lines] > > > > > Thanks, > > > > > Noel Raj Tripathi - 08 Mar 2005 12:43 GMT If you want to return binary objects from the webservice the only way is to mark your object as [Serializable] then:
On Server: [WebMethod] [SoapDocumentMethod(ParameterStyle=SoapParameterStyle.Bare)] byte[] GetEmployee() { Employee employee = new Employee("Eric Cartmen"); MemoryStream memoryStream = new MemoryStream(); BinaryFormatter formater = new BinaryFormatter(); formater.Serialize(memoryStream, employee); return memoryStream.ToByteArray(); }
On Client: Employee GetEmployee() { byte[] rawEmployee = Service.GetEmployee(); BinaryFormatter formater = new BinaryFormatter(); return (Employee) formater.Deserialize(rawemployee);
---------------------------------------------------------------------------------------------- Lookup MSDN for [SoapDocumentMethod(ParameterStyle=SoapParameterStyle.Bare)]
!!! BEWARE Binary formating is not version safe. i.e. If you change the version of your Employee class make shure that Server and Client use the same version.
If this is not accepteble to you use XML Serialization.
> Hello, > [quoted text clipped - 15 lines] > Thanks, > Noel
Free MagazinesGet these publications absolutely FREE for up to 12 months. There are no hidden fees and no obligation. Simply choose a title, complete the application form and submit it. Read more ...
|
|
|