3

我正在与Flurl一起使用需要基于证书的身份验证的 API。我从这篇 SO 帖子中看到,向 a 添加证书WebRequestHandler并指示 aHttpClient使用此处理程序很容易。

但是,对我来说使用 Flurl 并不是很清楚。我已经尝试了以下三件事。

扩展 DefaultHttpFactory

我首先怀疑我需要创建自己的X509HttpFactory : DefaultHttpFactory来创建处理程序并将其分配给HttpClient. 但是,在查看源代码时,我注意到 for 的构造函数CreateClient已经需要一个处理程序。这个处理程序来自哪里?

使用 DefaultHttpFactory 创建客户端

WebRequestHandler handler = new WebRequestHandler();
handler.ClientCertificates.Add(myX509Cert);
var clientFactory = new DefaultHttpClientFactory();
FlurlClient fc = clientFactory.CreateClient(url, handler);

这不能编译,因为HttpClient不能转换为FlurlClient

使用 ConfigureHttpClient

var clientFactory = new DefaultHttpClientFactory();
FlurlClient fc = new Url("foobar.com").ConfigureHttpClient(client => client = clientFactory
  .CreateClient(url, handler));

这似乎是最可行的选择,但我不确定,因为委托是Action没有返回类型的。

问题

使用 Flurl 支持客户端证书身份验证的最佳/正确方法是什么?

4

1 回答 1

9

你很接近 - 定制工厂绝对是要走的路。但是你想覆盖CreateMessageHandler而不是CreateClient

public class X509HttpFactory : DefaultHttpClientFactory
{
    private readonly X509Certificate2 _cert;

    public X509HttpFactory(X509Certificate2 cert) {
        _cert = cert;
    }

    public override HttpMessageHandler CreateMessageHandler() {
        var handler = new WebRequestHandler();
        handler.ClientCertificates.Add(_cert);
        return handler;
    }
}

然后您可以全局注册它(在应用程序启动时):

FlurlHttp.Configure(settings => {
    settings.HttpClientFactory = new X509HttpFactory(myCert);
});

或者对于对特定主机的所有调用:

FlurlHttp.ConfigureClient(ROOT_URL, cli => {
    cli.Settings.HttpClientFactory = new X509HttpFactory(myCert);
});

或者换一个新的FlurlClient

var cli = new FlurlClient(url)
    .Configure(settings => settings.HttpClientFactory = new X509HttpFactory(myCert));

或现有的:

cli.Settings.HttpClientFactory = new X509HttpFactory(myCert);
于 2016-12-08T16:50:19.007 回答