且构网

分享程序员开发的那些事...
且构网 - 分享程序员编程开发的那些事

在 xml 请求中将用户名和密码传递给 wcf 服务进行身份验证?

更新时间:2021-12-30 21:35:08

我将很快尝试描述我在自己的 WCF 服务中使用的身份验证方法.使用 WS-Security 规范(即您正在使用的 wsHttpBinding)对 WCF SOAP 端点进行内置身份验证处理.您可以像这样在 web.config 中使用设置来实现:

I will shortly try to describe the method I use in my own WCF Service for authentication. There is built-in authentication handling with WCF SOAP endpoints using WS-Security specification (i.e., wsHttpBinding, as you are using). You can implement using settings in web.config like this:

<bindings>
  <wsHttpBinding>
    <binding name="myBindingName">
      <security mode="Message">
        <transport clientCredentialType="None" />
        <message clientCredentialType="UserName" />
      </security>

然后您可以指定一个自定义类型来处理身份验证逻辑:

Then you can specify a custom type to handle authentication logic:

<behaviors>
  <serviceBehaviors>
    <behavior name="myBehaviorName">
      <serviceCredentials>
        <userNameAuthentication userNamePasswordValidationMode="Custom" customUserNamePasswordValidatorType="NameSpaceName.Class,AssemblyName" />
      </serviceCredentials>

这个处理认证逻辑的类应该扩展UserNamePasswordValidator(需要引用System.IdentityModel.dll并导入System.IdentityModel.Selectors为此)并覆盖Validate:

This class that handles authentication logic should extend UserNamePasswordValidator (will need to reference System.IdentityModel.dll and import System.IdentityModel.Selectors for this) and override Validate:

public class MyValidator : UserNamePasswordValidator {
    public override void Validate(string userName, string password) {
        // check password. if success, do nothing
        // if fail, throw a FaultException
    }
}

使用 ASP.Net WCF 客户端调用此代码需要使用 ClientCredential 来传递用户名和密码,如下所示:

Calling this code using an ASP.Net WCF client needs to use ClientCredential to pass the username and password, like this:

// This pattern needs to be repeated and username / password set with every creation
// of a client object.  This can be refactored to a separate method to simplify.
MyAPIClient client = new MyAPIClient();

// yes UserName is there twice on purpose, that's the proper structure
client.ClientCredentials.UserName.UserName = theUsername;
client.ClientCredentials.UserName.Password = thePassword;

try {
    client.Open();
    client.DoSomething();
    client.Close();
} catch (Exception ex) {
    // handle exception, which should contain a FaultException;
    // could be failed login, or problem in DoSomething
}

显然,上面定义的绑定和行为必须使用 behaviorConfigurationbindingConfiguration 属性分配给服务本身.

Obviously the binding and behavior defined above have to be assigned to the service itself using the behaviorConfiguration and bindingConfiguration properties.