Search code examples
wcfauthorizationweb-configwindows-authenticationiis-10

Why won't Authorization Rules in IIS restrict access to my WCF service?


I have a standalone WCF service hosted in IIS 10. I would like to restrict access to the web service to a select group of users. I was able to do this for a web application by doing the following in IIS:

  • Authentication: Windows Authentication only (disabled Anonymous Authentication)
  • Authorization Rules: Allow a predefined group (i.e., Roles)

However, when I do the above steps for the web service, and changed clientCredentialType="Windows" in its web.config, it still allows any user from the domain to talk to it. Am I missing something obvious? Do web services function differently than web applications in terms of configuring authorization? Given my setup I would expect only users in the MyTestGroup to be able to talk with the web service, and all others getting 401 - Unauthorized.

As an aside, I tried setting up "Deny Everyone" rules but domain users could still talk to the web service, so I feel like the Authorization settings aren't being effectuated somehow. Looking for any insight on this.

Here are the relevant web.config contents:

  <system.serviceModel>
    <services>
      <service name="StudyManagement.StudyManagement">
        <endpoint address="" binding="basicHttpBinding" bindingConfiguration="secureHttpBinding" name="StudyManagement" contract="StudyManagement.IStudyManagement" />
      </service>
    </services>
    <behaviors>
      <serviceBehaviors>
        <behavior>
          <serviceMetadata httpGetEnabled="false" httpsGetEnabled="true" />
          <serviceDebug includeExceptionDetailInFaults="true" />
        </behavior>
      </serviceBehaviors>
    </behaviors>
    <protocolMapping>
      <add binding="basicHttpsBinding" scheme="https" />
    </protocolMapping>
    <bindings>
      <basicHttpBinding>
        <binding maxReceivedMessageSize="1048576" />
        <binding name="secureHttpBinding">
          <security mode="Transport">
            <transport clientCredentialType="Windows" />
          </security>
        </binding>
      </basicHttpBinding>
    </bindings>
    <serviceHostingEnvironment aspNetCompatibilityEnabled="false" minFreeMemoryPercentageToActivateService="0" />
  </system.serviceModel>
  <system.webServer>
    <modules runAllManagedModulesForAllRequests="true" />
    <directoryBrowse enabled="false" />
        <security>
            <authorization>
                <remove users="*" roles="" verbs="" />
                <add accessType="Allow" users="" roles="MyAllowGroup" />
            </authorization>
        </security>
  </system.webServer>

Solution

  • The following Microsoft documentation helped to answer my question:

    WCF services and ASP.NET

    Important takeaways:

    The ASP.NET HTTP runtime handles ASP.NET requests but does not participate in the processing of requests destined for WCF services, even though these services are hosted in the same AppDomain as is the ASP.NET content. Instead, the WCF Service Model intercepts messages addressed to WCF services and routes them through the WCF transport/channel stack.

    Within an AppDomain, features implemented by the HTTP runtime apply to ASP.NET content but not to WCF. Many HTTP-specific features of the ASP.NET application platform do not apply to WCF Services hosted inside of an AppDomain that contains ASP.NET content. Examples of these features include the following:

    • File-based authorization: The WCF security model does not allow for the access control list (ACL) applied to the .svc file of the service when deciding if a service request is authorized.

    • Configuration-based URL Authorization: Similarly, the WCF security model does not adhere to any URL-based authorization rules specified in System.Web’s configuration element. These settings are ignored for WCF requests if a service resides in a URL space secured by ASP.NET’s URL authorization rules.

    Solution:

    Use ASP.NET Compatibility Mode by configuring web.config:

    <system.serviceModel>
        <serviceHostingEnvironment aspNetCompatibilityEnabled="true" />
    </system.serviceModel>
    

    Unlike the default side-by-side configuration, where the WCF hosting infrastructure intercepts WCF messages and routes them out of the HTTP pipeline, WCF services running in ASP.NET Compatibility Mode participate fully in the ASP.NET HTTP request lifecycle. In compatibility mode, WCF services use the HTTP pipeline through an IHttpHandler implementation, similar to the way requests for ASPX pages and ASMX Web services are handled. As a result, WCF behaves identically to ASMX with respect to the following ASP.NET features:

    • File-based authorization: WCF services running in ASP.NET compatibility mode can be secure by attaching file system access control lists (ACLs) to the service’s .svc file.
    • Configurable URL authorization: ASP.NET’s URL authorization rules are enforced for WCF requests when the WCF service is running in ASP.NET Compatibility Mode.

    I recommend reading the entire article for additional information. It's a short and helpful read.


    Thanks to @Shiraz Bhaiji for the article reference on WCF Authorization using IIS and ACLs.