[转贴][WCF Security] 4. 用户名/密码身份验证

原文:http://www.rainsts.net/article.asp?id=475

 

X.509 比较适合验证 "客户机" 的身份,而另外一方面,我们可能需要针对具体的 "用户" 进行验证。本文将记述基于 "用户名/密码" 方式的身份验证开发步骤。

1. 服务器数字证书

我们同样需要为服务器准备一个数字证书。

D:\>makecert -r -pe -n "CN=MyServer" -ss My -sky exchange

2. 创建服务
[ServiceContract]
public interface IService
{
  [OperationContract]
  string Test();
}

public class MyService : IService
{
  public string Test()
  {
    return "Server:" + DateTime.Now.ToString();
  }
}

public class WcfTest
{
  public static void Test()
  {
    ServiceHost host = new ServiceHost(typeof(MyService));
    host.Open();
  }
}


我们通过继承 UserNamePasswordValidator 来创建一个自定义验证器。
public class MyUserNamePasswordValidator : UserNamePasswordValidator
{
  public override void Validate(string userName, string password)
  {
    if (userName != "user" || password != "pwd")
    {
      throw new SecurityTokenException("Unknown Username or Password");
    }
  }
}

接下来创建服务器配置文件,我们使用 WsHttpBinding,采取 Message 安全模式。其他的设置还包括 certificateValidationMode、userNamePasswordValidationMode、customUserNamePasswordValidatorType 等。
<?xml version="1.0" encoding="utf-8"?>
<configuration>
  <system.serviceModel>
    <behaviors>
      <serviceBehaviors>
        <behavior name="NewBehavior">
          <serviceMetadata httpGetEnabled="true" />
          <serviceDebug includeExceptionDetailInFaults="true" />
          <serviceCredentials>
            <clientCertificate>
              <authentication certificateValidationMode="None" />
            </clientCertificate>
            <serviceCertificate findValue="MyServer" storeLocation="CurrentUser"
              x509FindType="FindBySubjectName" />
            <userNameAuthentication userNamePasswordValidationMode="Custom"
              customUserNamePasswordValidatorType=
                "Learn.Library.WCF.MyUserNamePasswordValidator, Learn.Library.WCF" />
          </serviceCredentials>
        </behavior>
      </serviceBehaviors>
    </behaviors>
    <bindings>
      <wsHttpBinding>
        <binding name="Binding1">
          <security mode="Message">
            <message clientCredentialType="UserName" />
          </security>
        </binding>
      </wsHttpBinding>
    </bindings>
    <services>
      <service behaviorConfiguration="NewBehavior" name="Learn.Library.WCF.MyService">
        <endpoint address="service" binding="wsHttpBinding" bindingConfiguration="Binding1"
          name="username" contract="Learn.Library.WCF.IService" />
        <host>
          <baseAddresses>
            <add baseAddress="http://localhost:8080" />
          </baseAddresses>
        </host>
      </service>
    </services>
  </system.serviceModel>
</configuration>


3. 创建客户端

启动服务器后,创建客户端代理文件。注意自动生成的客户端配置文件中包含了服务器数字证书的相关信息。
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
  <system.serviceModel>
    <bindings>
      <wsHttpBinding>
        <binding name="username">
          <security mode="Message">
            <message clientCredentialType="UserName" negotiateServiceCredential="true"
              algorithmSuite="Default" establishSecurityContext="true" />
          </security>
        </binding>
      </wsHttpBinding>
    </bindings>
    <client>
      <endpoint address="http://localhost:8080/service" binding="wsHttpBinding"
        bindingConfiguration="username" contract="ConsoleApplication1.localhost.IService"
        name="username">
        <identity>
          <certificate encodedValue="AwAA...IgFHqYA==" />
        </identity>
      </endpoint>
    </client>
  </system.serviceModel>
</configuration>

开始调用服务,注意将 CertificateValidationMode 设置为 None,当然也可以写到配置文件中。
using (ServiceClient client = new ServiceClient())
{
  client.ClientCredentials.ServiceCertificate.Authentication.CertificateValidationMode =
    X509CertificateValidationMode.None;

  client.ClientCredentials.UserName.UserName = "user";
  client.ClientCredentials.UserName.Password = "pwd";

  Console.WriteLine(client.Test());
}

OK! 测试通过! [lol]
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
WCF 中接收 `uni.uploadFile` 文件,你可以按照以下步骤进行操作: 1. 首先,在 WCF 服务的契约中定义一个操作合同,用于接收文件。例如: ```csharp [ServiceContract] public interface IFileService { [OperationContract] void UploadFile(Stream fileData); } ``` 2. 在服务实现类中,实现该操作合同。在方法中,你可以使用 `Stream` 类型的参数接收文件数据。例如: ```csharp public class FileService : IFileService { public void UploadFile(Stream fileData) { // 处理文件数据 // 可以使用流操作、保存到磁盘、或者进行其他自定义操作 } } ``` 3. 在服务的配置文件中,配置绑定和终结点。你可以使用基于 HTTP 的绑定,如 `basicHttpBinding` 或 `webHttpBinding`。例如: ```xml <system.serviceModel> <bindings> <basicHttpBinding> <binding name="BasicHttpBinding_IFileService" /> </basicHttpBinding> </bindings> <services> <service name="YourNamespace.FileService"> <endpoint address="" binding="basicHttpBinding" bindingConfiguration="BasicHttpBinding_IFileService" contract="YourNamespace.IFileService" /> </service> </services> </system.serviceModel> ``` 4. 在客户端调用代码中,引用服务契约并创建代理对象。然后,可以使用代理对象调用 `UploadFile` 方法并传递文件数据。例如: ```csharp using (var client = new FileServiceClient()) { using (var fileStream = File.OpenRead("path/to/file")) { client.UploadFile(fileStream); } } ``` 这样,你就可以在 WCF 中成功接收 `uni.uploadFile` 的文件数据。记得根据实际需求进行适当的异常处理和文件操作。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值