Elasticsearch.Nest 教程系列 2-4 连接:Working with certificates | 使用凭证连接


使用证书

如果你已经通过 Elastic Stack Security 功能在 Elasticsearch 上启用了SSL,或者在 ES 服务上层的代理上启用了SSL,并且生成证书的证书颁发机构(CA)受运行客户端代码的计算机信任,那么你不需要进行任何操作。

如果你使用不受信任的 CA 证书(如你自己生成的CA 证书),默认情况下, .NET 不允许你使用 https 请求终结点,不过你可以使用 ServicePointManager.ServerCertificateValidationCallback 来解决这个问题。大部分的示例可能会让你直接返回一个 true,但并不建议你这样做,因为这么设置会允许所有到你应用程序域的 HTTPS 的流量,且无需验证:

//不建议这么干:
ServicePointManager.ServerCertificateValidationCallback +=
(sender, cert, chain, errors) => true
  • 这么设置不会对 HTTPS 连接请求jinxing yanzheng

配置验证

可以使用 Elasticsearch.Net 的 ConnectionConfiguration 和使用 NEST 的ConnectionSettings 公开该回调。你也可以在这处理程序中进行自己的验证,也可以使用静态类 CertificateValidations 提供的一些处理器。

最常用的是 AllowAll 和 DenyAll,它们分别允许或拒绝到节点的所有 SSL 流量:

拒绝所有证书验证

eg:在 ConnectionSettings 上设置回调来拒绝所有证书验证:

[IntegrationOnly]
public class DenyAllCertificatesCluster : SslAndKpiXPackCluster
{
    protected override ConnectionSettings ConnectionSettings(ConnectionSettings s) => s
        .ServerCertificateValidationCallback((o, certificate, chain, errors) => false)
        .ServerCertificateValidationCallback(CertificateValidations.DenyAll); 
}
  • 使用 lambda 表达式:CertificateValidations.DenyAll 来拒绝所有验证。

允许所有证书验证

同样通过 ConnectionSettings 来设置回调

public class AllowAllCertificatesCluster : SslAndKpiXPackCluster
{
    protected override ConnectionSettings ConnectionSettings(ConnectionSettings s) => s
        .ServerCertificateValidationCallback((o, certificate, chain, errors) => true) 
        .ServerCertificateValidationCallback(CertificateValidations.AllowAll); 
}
  • 使用 lambda 表达式:CertificateValidations.AllowAll 来拒绝所有验证。

允许来自证书颁发机构的证书

如果你的客户端应用程序可以在本地访问公共 CA 证书,则 Elasticsearch.NET 和 NEST 附带了一些方便的帮助程序,可以用来判断服务器提供的证书是否来自本地CA的证书。

如果你使用 elasticsearch-certutil工具 来生成SSL证书,则为了减少 SSL 握手数据尺寸,生成的节点证书并不包含在 CA 的证书链中。在这种情况下,你可以使用 CertificateValidations.AuthorityIsRoot 来验证证书。

[IntegrationOnly]
public class CertgenCaCluster : SslAndKpiXPackCluster
{
    public CertgenCaCluster() : base() { }
    public CertgenCaCluster(SslAndKpiClusterConfiguration configuration) : base(configuration) { }
    protected override ConnectionSettings ConnectionSettings(ConnectionSettings s) => s
        .ServerCertificateValidationCallback(
            CertificateValidations.AuthorityIsRoot(new X509Certificate(this.ClusterConfiguration.FileSystem.CaCertificate))
        );
}

如果证书不匹配,客户端会连接失败:

[IntegrationOnly]
public class BadCertgenCaCluster : SslAndKpiXPackCluster
{
    protected override ConnectionSettings ConnectionSettings(ConnectionSettings s) => s
        .ServerCertificateValidationCallback(
            CertificateValidations.AuthorityPartOfChain(new X509Certificate(this.ClusterConfiguration.FileSystem.UnusedCaCertificate))
        );
}

如果你需要使用供应商生成的 SSL 证书,则通常做法是在证书链中包含 CA 和所有中间 CA。使用此类证书时可以通过 CertificateValidations.AuthorityPartOfChain 来验证本地 CA 证书是否存在于证书链中。