tags:

views:

839

answers:

6

Hi everybody,

we have windows app. which expected to connect different soap web services. Service urls are added dynamically to database.I tried "Add Web Reference" feather but problem is it accepts only one url.

Can any one suggest different approach?or link to source

Thanks

+1  A: 

You have to add a web reference to each service you want to connect to. The reference generates proxy classes used to connect to that service. So, each distinct service you are wanting to use needs its own references.

yodaj007
-1: Read the question, please.
John Saunders
I did read the question. He's connecting to multiple web services and each one accepts only one url. Which part, exactly, did I overlook?
yodaj007
It's multiple instances of the same service, located at different URLs.
John Saunders
Reading the code he posted, maybe I was mistaken about what he wanted. I've removed the -1.
John Saunders
+3  A: 

Just set the Url property of the proxy. See Ways to Customize your ASMX Client Proxy.

John Saunders
+2  A: 

I would suggest using Add Service Reference instead.

However, you will still only be able to set one address at design time.

You therefore need to read the url's from the database and set the address of the proxy whenever you use it.

Shiraz Bhaiji
+1  A: 

I have found such piece of code at "Dynamically Invoking a Web Service" on Kirk Evans Blog. Hope will help someone...


(the original code needed some work. This should be equivalent)

using System;
using System.CodeDom;
using System.CodeDom.Compiler;
using System.Diagnostics;
using System.Net;
using System.Security.Permissions;
using System.Web.Services.Description;
using System.Xml.Serialization;

namespace ConnectionLib
{
    internal class WsProxy
    {
        [SecurityPermission(SecurityAction.Demand, Unrestricted = true)]
        internal static object CallWebService(
            string webServiceAsmxUrl,
            string serviceName,
            string methodName,
            object[] args)
        {
            var description = ReadServiceDescription(webServiceAsmxUrl);

            var compileUnit = CreateProxyCodeDom(description);
            if (compileUnit == null)
            {
                return null;
            }

            var results = CompileProxyCode(compileUnit);

            // Finally, Invoke the web service method
            var wsvcClass = results.CompiledAssembly.CreateInstance(serviceName);
            var mi = wsvcClass.GetType().GetMethod(methodName);
            return mi.Invoke(wsvcClass, args);
        }

        private static ServiceDescription ReadServiceDescription(string webServiceAsmxUrl)
        {
            using (var client = new WebClient())
            {
                using (var stream = client.OpenRead(webServiceAsmxUrl + "?wsdl"))
                {
                    return ServiceDescription.Read(stream);
                }
            }
        }

        private static CodeCompileUnit CreateProxyCodeDom(ServiceDescription description)
        {
            var importer = new ServiceDescriptionImporter
                           {
                               ProtocolName = "Soap12",
                               Style = ServiceDescriptionImportStyle.Client,
                               CodeGenerationOptions =
                                   CodeGenerationOptions.GenerateProperties
                           };
            importer.AddServiceDescription(description, null, null);

            // Initialize a Code-DOM tree into which we will import the service.
            var nmspace = new CodeNamespace();
            var compileUnit = new CodeCompileUnit();
            compileUnit.Namespaces.Add(nmspace);

            // Import the service into the Code-DOM tree. This creates proxy code
            // that uses the service.
            var warning = importer.Import(nmspace, compileUnit);
            return warning != 0 ? null : compileUnit;
        }

        private static CompilerResults CompileProxyCode(CodeCompileUnit compileUnit)
        {
            CompilerResults results;
            using (var provider = CodeDomProvider.CreateProvider("CSharp"))
            {
                var assemblyReferences = new[]
                                         {
                                             "System.dll",
                                             "System.Web.Services.dll",
                                             "System.Web.dll", "System.Xml.dll",
                                             "System.Data.dll"
                                         };
                var parms = new CompilerParameters(assemblyReferences);
                results = provider.CompileAssemblyFromDom(parms, compileUnit);
            }

            // Check For Errors
            if (results.Errors.Count == 0)
            {
                return results;
            }

            foreach (CompilerError oops in results.Errors)
            {
                Debug.WriteLine("========Compiler error============");
                Debug.WriteLine(oops.ErrorText);
            }

            throw new Exception(
                "Compile Error Occurred calling webservice. Check Debug output window.");
        }
    }
}
qasanov
When you say "some work", do you mean that there is a bug, or simply that you have organized the code in a better way? (Sorry for annoying you with this 1 year old topic xD)Cheers.
vtortola
A: 

The source of qasanov's finding: http://blogs.msdn.com/kaevans/archive/2006/04/27/585013.aspx

Viktor Jevdokimov
yeah good point :)
qasanov
A: 

How would you go about passing a username and password to a web service using this code. The web service I have in mind has the following Authentication Class:

Public Class AuthHeader : Inherits SoapHeader
    Public SalonID As String
    Public SalonPassword As String
End Class

Then within it's web service class it has the following:

    Public Credentials As AuthHeader 'Part of the general declarations of the class - not within any particular method



    Private Function AuthenticateUser(ByVal ID As String, ByVal PassWord As String, ByVal theHeader As AuthHeader) As Boolean
        If (Not (ID Is Nothing) And Not (PassWord Is Nothing)) Then
            If ((ID = "1")) And (PassWord = "PWD")) Then
                Return True
            Else
                Return False
            End If
        Else
            Return False
        End If
    End Function



    <WebMethod(Description:="Authenticat User."), SoapHeader("Credentials")> _
    Public Function AreYouAlive() As Boolean
        Dim SalonID As String = Credentials.SalonID
        Dim SalonPassword As String = Credentials.SalonPassword
        If (AuthenticateUser(ID, Password, Credentials)) Then
            Return True
        Else
            Return False
        End If
    End Function

I am finding that I cannot get the proxy class you mentioned above to pass the username and password to this

Michael