【问题标题】:WCF Basic Authentication not using on IISWCF 基本身份验证未在 IIS 上使用
【发布时间】:2016-04-28 06:03:58
【问题描述】:

我有一个使用以下配置的 Rest WCF 服务

<service behaviorConfiguration="webBehaviour" name="AOS.BrokerAPI.WCFService.BrokerAPIService">
    <endpoint address="mex" binding="mexHttpBinding" name="mex" contract="IMetadataExchange" />
    <endpoint address="brokerapi" binding="webHttpBinding" bindingConfiguration="webHttpBinding"
      name="web" contract="AOS.BrokerAPI.WCFService.IBrokerAPIService" behaviorConfiguration="EndPointBehaviour"/>
    <host>
      <baseAddresses>
        <add baseAddress="http://localhost:8733/Design_Time_Addresses/AOS.BrokerAPI.WCFService/BrokerAPIService/" />
        <add baseAddress="https://localhost:8732/Design_Time_Addresses/AOS.BrokerAPI.WCFService/BrokerAPIService/" />
      </baseAddresses>
    </host>
  </service>
</services>


<behavior name="webBehaviour">
      <serviceMetadata httpGetEnabled="true" httpsGetEnabled="true"
        httpGetBinding="" />
      <serviceDiscovery />
      <!--<serviceAuthenticationManager serviceAuthenticationManagerType=""/>-->
      <serviceCredentials>
        <userNameAuthentication userNamePasswordValidationMode="Custom" customUserNamePasswordValidatorType="AOS.BrokerAPI.WCFService.Security.Account,AOS.BrokerAPI.WCFService" />
        <!--<serviceCertificate findValue="CN=Dev Certification Authority" x509FindType="FindBySubjectDistinguishedName" storeLocation="LocalMachine"/>-->
      </serviceCredentials>
    </behavior>

当我从本地主机运行应用程序时,它使用我的自定义用户名和密码验证类,但是当我将它移动到 IIS 时,它无法登录。

我启用了基本身份验证并禁用了匿名身份验证。还有什么我可能会遗漏的吗?

这是 Authentication 类的代码,当使用 Visual Studio 时,它在我的本地主机上完美运行

public class Account : UserNamePasswordValidator
{
    public override void Validate(string userName, string password)
    {
        //log the user in or return a webexception
        if (null == userName || null == password)
        {
            throw new ArgumentNullException();
        }

        var user = DB.GetUser(userName);
        //usernme  = test, password = Password1

        if (!AOS.BrokerAPI.Domain.Security.PasswordStorage.VerifyPassword(password, user.Password))
            throw new SecurityTokenException("Unknown Username or Incorrect Password");
    }
}

我已经为 Authentication 类启用了 Logging,但是代码从来没有命中它。

花了几个小时谷歌后,我找到了一个解决方案,虽然我不能使用它,想法是为 IIS 创建一个授权扩展并将其设置为您的 webconfig 并启用它,这样 IIS 将使用它而不是基本身份验证。

【问题讨论】:

  • 您使用的用户在应用程序的文件夹中有权限吗?
  • 我正在使用数据库进行用户名和密码验证,。他们还需要许可吗?
  • 向我们展示您的代码,但 iis 基本身份验证使用 Windows 帐户。如果您有自己的身份验证类,我认为您应该使用匿名。
  • 好的,看到您的编辑,我们有 2 个选项。最简单的方法是使用日志记录 (log4net) 方法来查看那里发生了什么。另一种方法是在本地 IIS 中调试它,而不是 IIS Express,看看那里发生了什么。
  • 让我试试,我会尽快更新。

标签: c# wcf iis


【解决方案1】:

对于可能正在寻找解决此问题的任何人,我的解决方案是将应用程序托管为 Web 应用程序(在我的情况下为 asp.net MVC),并使用 HttpModule 来处理身份验证和授权

使用

public class CustomAuthenticationModule : IHttpModule
{
    public void Init(HttpApplication context)
    {
        context.AuthenticateRequest += new EventHandler(context_AuthenticateRequest);
    }

    public void context_AuthenticateRequest(object sender, EventArgs e)
    {
        HttpApplication application = (HttpApplication)sender;
        if (!SecuirtyHelper.Authenticate(application.Context))
        {
            application.Context.Response.Status = "01 Unauthorized";
            application.Context.Response.StatusCode = 401;
            application.Context.Response.AddHeader("WWW-Authenticate", "Basic realm=localhost");
           // application.Context.Response.ContentType = "application/json";
            application.CompleteRequest();
        }
    }

    public void Dispose()
    {

    }
}

这将允许使用自定义身份验证进行身份验证。在 Authenticate 方法中,您必须检查您的请求是否安全,是否有授权标头并尝试验证用户的凭据

public static bool Authenticate(HttpContext context)
    {
        if (!HttpContext.Current.Request.IsSecureConnection)
            return false;

        if (!HttpContext.Current.Request.Headers.AllKeys.Contains("Authorization"))
            return false;

        string authHeader = HttpContext.Current.Request.Headers["Authorization"];

        IPrincipal principal;
        if (TryGetPrincipal(authHeader, out principal))
        {
            HttpContext.Current.User = principal;
            return true;
        }
        return false;
    }

private static bool TryGetPrincipal(string authHeader, out IPrincipal principal)
    {
        var creds = ParseAuthHeader(authHeader);
        if (creds != null && TryGetPrincipal(creds, out principal))
            return true;

        principal = null;
        return false;
    }

这应该是使用基本身份验证在 WCF 上进行自定义身份验证所需的全部内容。

【讨论】:

    猜你喜欢
    • 2010-12-02
    • 1970-01-01
    • 2014-09-15
    • 2011-10-11
    • 2012-01-03
    • 1970-01-01
    • 2019-01-28
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多