December 21, 2012

WCF credentials

This time it is not a sitecore post but I had to search a long time to find how to put my WCF service authentication in the web.config file.
To pass the service credentials in the code it is easy:
myServiceClient.ClientCredentials.Windows.ClientCredential = new System.Net.NetworkCredential("myUsername", "myPassword", "myDomain");
But to put those credentials into the web.config it is a bit more complex.
  1. Create this class:
    using System;
    using System.Collections.Generic;
    using System.Configuration;
    using System.Linq;
    using System.ServiceModel.Configuration;
    using System.ServiceModel.Description;
    using System.Text;
    
    namespace MyNamespace
    {
        public class UserNameClientCredentialsElement : ClientCredentialsElement
        {
            private ConfigurationPropertyCollection properties;
    
            public override Type BehaviorType
            {
                get { return typeof(ClientCredentials); }
            }
    
            /// <summary>
            /// Username (required)
            /// </summary>
            public string UserName
            {
                get { return (string)base["userName"]; }
                set { base["userName"] = value; }
            }
    
            /// <summary>
            /// Password (optional)
            /// </summary>
            public string Password
            {
                get { return (string)base["password"]; }
                set { base["password"] = value; }
            }
    
            protected override ConfigurationPropertyCollection Properties
            {
                get
                {
                    if (properties == null)
                    {
                        ConfigurationPropertyCollection baseProps = base.Properties;
                        baseProps.Add(new ConfigurationProperty(
                                          "userName",
                                          typeof(String),
                                          null,
                                          null,
                                          new StringValidator(1),
                                          ConfigurationPropertyOptions.IsRequired));
                        baseProps.Add(new ConfigurationProperty(
                                          "password",
                                          typeof(String),
                                          ""));
                        properties = baseProps;
                    }
                    return properties;
                }
            }
    
            protected override object CreateBehavior()
            {
                var creds = (ClientCredentials)base.CreateBehavior();
                if(creds != null)
                    creds.Windows.ClientCredential = new NetworkCredential(UserName, Password);            
                return creds;
            }
        }
    }
  2. Register the behaviorExtension
  3. Use your new extension
Now your web.config should look like:
<system.serviceModel>
  <client><!--(3)-->
    <endpoint ...YourEndpointConfig... behaviorConfiguration="UserNamePasswordBehavior" />
  </client>
  <behaviors><!--(2)-->
    <endpointBehaviors>
      <behavior name="UserNamePasswordBehavior">
        <userNameClientCredentials userName="skroob" password="12345" />
        <!--Visual Studio will give you warning squiggly on <userNameClientCredentials>
            saying that "The element 'behavior' has invalid child element" 
            but will work at runtime.-->
      </behavior>
    </endpointBehaviors>
  </behaviors>
  <extensions><!--(1)-->
    <behaviorExtensions>
      <add name="userNameClientCredentials" type="MyNamespace.UserNameClientCredentialsElement, MyAssembly, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null" />
    </behaviorExtensions>
  </extensions>
  ...
</system.serviceModel>
Thanks a lot to Patrick Paquet to post this answer on this topic

No comments:

Post a Comment