Tuesday, July 28, 2009

WCF Authorization with WindowsIdentity.GetCurrent()

Well, in a nutshell this doesn’t work. Our application has some role based security that depends on a AD role to run certain methods. One of the users was having no problems with the security model on the client side, but couldn’t access certain methods behind the WCF service. We wasted a few hours trying to figure out why our WCF service was not correctly recognizing this user’s role. With the help of some added logging we finally figured out that it wasn’t recognizing the user or the role.

Even though our web server is an internal server in the same domain as the client app, the Name property on our windows identity kept returning “NT AUTHORITY\NETWORK SERVICE”, regardless of the fact that we had set up the WCF binding to use Windows authentication. There are so many configuration options for WCF most of the debugging time was wasted trying to figure out what we had configured improperly, or what we needed to do to get the impersonation to work. I finally realized that configuration wasn’t the issue.

To correctly get the windows identity, or the user name and role, you need to either use the ServiceSecurityContext class or pull the name directly from the thread. This is somewhat obvious if you think about the whole security model and how WCF is doing the impersonation, but still it could throw you for a loop if you’re not used to using user security with WCF. It definately caused us a mile headache for a few hours. Solution below.

Web service bindings configuration:


<bindings>


  <wsHttpBinding>


    <binding name="secureBinding">


      <security mode="Message">


        <message clientCredentialType="Windows" />


      </security>


    </binding>


  </wsHttpBinding>


</bindings>





C# code:


WindowsIdentity sscIdentity= ServiceSecurityContext.Current.WindowsIdentity;


//OR


WindowsIdentity threadIdentity = (WindowsIdentity)Thread.CurrentPrincipal.Identity;


No comments: