I could have sworn I saw this done somewhere, but I guess maybe it was a DLL, not a web service. I was originally doing this as a DLL, but now need to use a web service.
I have a service file (DataService.svc). I have class Foo and class Bar. Both have the same methods (Load, LoadAll, Insert, Update). I know that a web service doesn't support overloading, but I thought that since these were in separate classes it might be possible. Is there a way to configure this so that in my client, I could do this:
DataService.Foo.Load();
or
DataService.Bar.Load();
Thanks,
Andrew
Related
I have two projects in the same solution, a service and a consumer app. In the service I have many classes that can be instantiated by the consumer app but some classes are not accessible. There's no difference apart from name. All classes are all Public so they should all be seen. Is there any buffering problems or anything else that could cause the problem to behave like this?
Consumer does not get access to Server classes when you use WCF or any other Web Services/Removing technology. Proxy classes are created instead. Think about them as set of Interfaces that are able to call method over app boundaries. You can instantiate proxy classes but when you call method proxy class will go to Service and call corresponding method of class hosted by service.
You need to use Class Library and move move your shared classes there (and deploy dll with Service and Consumer) if both parties use them.
Update (thanks razlebe):
Business logic should not be shared in DLLs. It should be hosted by server. But it will make sense to share supporting classes (for example class that do data formatting) to avoid code duplication.
When you update service class and change interface by:
Adding a method (Your case)
Removing a method
Changing signature
Your consumer needs to learn about the change. You have to update service reference (http://msdn.microsoft.com/en-us/library/bb628652.aspx) to rebuild proxy.
How to update it?
Check here to see how: http://msdn.microsoft.com/en-us/library/bb628652.aspx)
But one image is better than thousand words:
My guess is that the classes that "are not accessible" were created after the last generation of the proxy (classes of the service, client-side). Check if REgenerating the proxy helps.
Ok so I have built my WCF service and its functioning great! However, I am starting to implement it into our pre-existing piece of software now and I am instantly running into the question, do I only use the proxy generated code and get rid of the dll that I used initially? Or do I keep both, and make distinctions between the two very obvious?
What I mean by keeping distinctions is, having a ServerUser and a LocalUser property that represent the same user object. However, my LocalUser property would be filled via the dll that the app initally ran with, if the application service is unavailable.
My main reasoning for this thought pattern is that if I remove my dll, I have a single point of failure. If for some reason my ServiceHost is just not up and running, but the DB server is, I would want my users to still be able to do their job. The features that the new WCF implementation utilize are not dependant for employees to do their job. It is more of a convenience in what the WCF service provides. Also, building in this kind of logic to the Service would allow service modifications more readily available in a non IIS hosted environment.
Also, is there a way to build in logic on the service so that when I pull down the proxy code for the client that it just knows to access the DB manually if the ServiceHost is unavailable? If this was a possibility, I think about 90% of all my problems would disappear.
Thank you in advance!
From what you describe it sounds like keeping your existing DLL, i.e. direct access to the DB, would best suit your needs. Having a WCF service adds nothing if, when it fails, you'll just use the DLL anyway.
Ideally you would go with the WCF service completly and offer some kind of redundency to deal with any potenial service issues. Plus, using a service will mean you won't have to deal with any DLL upgrades/deployments.
But, from your question, it sounds like there would be some real issues to deal with should the service not be available, so just do with the DLL.
EDIT: Just read the last part of your question and I don't think that is possible. The proxy code for accessing services is generated when you add the reference to your project. The kind of "dynamic" information you're after would actually require a service.
EDIT: As a follow up to my comment below you could test this by creating a DLL and class, lets call it Class1. Then create a WCF service with a method that will return Class1. Create a client application and add a reference to the service. If you look at the proxy-generated code you should see (hopefully...I'm thinking of this as I type :)) that the method returns Class1, but when you compile it won't be able to find Class1. This is because Class1 does not have the DataContractAttribute which would auto-generate Class1 on the client. So, you have to distribute the shared DLL to the client. Now when the method returns and WCF tries to re-create Class1 it will use the local version in the shared DLL. Your other DLL, which will already be on the client, would use the same shared DLL.
I have a Silverlight Class Library that I want to use in both my Silverlight and my WebService project.
I am able to create and reference the Library in both projects without any problems, but when I try to use any of the classes in the Library on the Silerlight project, I get an ambiguous reference error between my Library and the Asmx Webservice (apparently, the silverlight project believes that the classes in the class library exist in the webservice).
How can I correct this issue? I have tried rebuilding and cleaning, but it does not seem to work. Can anyone help?
Sounds like the objects you are passing to Silverlight, via the WCF service, are the same objects in your class library. In that case the generated web-reference objects will be given the same names. Linking with the library will then give you 2 sets of objects with the same names.
If you install RIA services, once feature is the ability to share code between client and server by simply adding ".shared" in the class filenames before the extensions. ASMX services are so last century :)
if you don't want to learn the RIA services way of sharing objects across the great-web-divide (which I would recommend), you need to separate the data objects from the functionality you actually want to share client and server side.
To give more specific advice on your current set-up I would need to see more about how it is structured.
A technique you can use is aliasing your using statements:
using MyNameSpace = My.Name.Space;
using MyWebService = My.Web.Service;
Then access all of your objects with these aliases to remove the ambiguities.
I have a webservice with a function that returns a type (foo). If I consume this webservice in .NET through the 2.0 generated proxies, it creates a class called foo in the generated proxy. If I have the DLL that contains that class (foo) that is the DLL being used by the webservice, is there any way to have it use that class instead of creating a custom proxy class? I'm looking for something similar to what remoting does... but not remoting.
I've seen 3 ways of doing this:
Let Visual Studio generate the proxy and then change the classes in the proxy to the full class names of the dll, by hand. Works, but you would have to do this again everytime you update your proxy. Plus it's really dirty, isn't it?
Use a generic class/method that
creates deep copies of your proxy
objects into the "real" objects by
reflection. Works, but of course
with a little performance offtrade
Use WCF, where you can reference the
dll with the data contracts (your
data classes) and use them instead
of creating any proxy by code
generation.
I think the key issue here is in generating the proxies. I've generally used two different approaches to web services:
1) Traditional services, where you expose methods and a client generates the proxy in Visual Studio to consume the methods.
2) Request/Response services, where the exposed "service" is more of a pass-through and the "actions" being performed are encapsulated in the objects being sent to and received from the service. These actions would be in that shared library that both the server and the client have.
In the former I often run into this same problem and I don't really think there's a solution, at least not one that Visual Studio is going to like at all. You could perhaps manually modify the generated proxies to use the other classes, but then you'll have to repeat that step any time you re-generate. Conversely, you can generate outside of Visual Studio in something like CodeSmith (the older version is free, but depends on .NET 1.1), which will require some work to create a template for the proxies and to step outside the IDE to re-generate any time you need to update them.
I can recommend a good tool for the latter, however, and that would be the Agatha project. It takes the approach of separating the "service" from the "actions" that are being performed, and makes the approach of the shared library very easy. Such a re-architecture may very well be out of the question for the project you're working on depending on your schedule, but it's definitely something to explore for future projects.
You could write your own proxy class, or you could implement a constructor on your Foo class that takes an instance of the generated Foo class and copies over the data as appropriate.
I have to call a webservice published in the same website the caller aspx is.
When I try to "Add a Web Reference" the editor does not show the webservice methods from the generated namespace.
Do I have to use the "Add Web Reference" or is there another way because the webservice is in the same website?
Visual Studio 2005, C#
Thanks,
Eduardo
I used the way that Andy Rose wrote in comments:
Instantiate the webservice class and call the methods directly because it is accessible inside the project (no need to add web reference).
There are ways to trick it... You can deploy the app with the web service, then add reference to the deployed location.
Another idea is to just start it using ctrl-f5 so as to not start the debugger as well, then add a reference to your localhost:/.asmx
This will get all of the configuration information created in your web.config which, of course, you can modify later as necessary.
The Webreference itself is just a proxy implementation so that VS can pretend it knows how your webservice will react to calls to it (so you can compile), you can actually code without them (though it is much harder :)).
You have a few of options, that I can think of, if you want to do this:
Create your webservice as a separate project, but deploy it to the same location. You will get mixed binaries in the bin directory, but otherwise it should work fine. In this way you can deploy each separately as needed.
Consider pulling them apart into two separate applications. This might not be available for whatever reason.
Create a stub webservice in your main project, which only has the function definitions (return type and parameters) and deploy that, then generate your webservice against that. You can then begin your development against the prototype and fill it in as necessary
Do the two-step shuffle as Chris suggested. First create a approximate representation of your webservice, deploy it. Second create your proxy against it, create your web app, deploy it and test. Repeat as necessary.
Once your proxy is created you can change the URL it points to in the proxy bindings.