You need to enable JavaScript to run this app. Xamarin.Forms经Android模拟器连本地CosmosDB遇SSL验证失败咨询
优惠活动
大模型
产品
解决方案
定价
更多

Xamarin.Forms经Android模拟器连本地CosmosDB遇SSL验证失败咨询

根因定位
  • 10.0.2.2的地址配置完全正确,这是Android模拟器内置的、专门映射到宿主机127.0.0.1回环地址的专用地址,不需要在本地网络列表中显示存在。
  • 同配置下Azure存储模拟器能连通,是因为当前Azurite存储模拟器默认提供无HTTPS的HTTP端点,整个连接流程不会触发TLS证书校验。
  • CosmosDB本地模拟器连接失败抛SSL证书错误,核心原因是:该模拟器默认启动时使用自签名SSL证书提供HTTPS服务,而Android模拟器内置的BoringSSL信任链未内置这份本地自签证书的根信任,TLS握手阶段直接校验失败,抛出你看到的CERTIFICATE_VERIFY_FAILED异常。
方案一:应用内导入自定义信任证书(适配长期本地开发场景)

准备工作

  • 从CosmosDB本地模拟器的安装目录找到自带的DefaultDocumentDBEmulatorCertificate.pfx证书文件,导出其中的根证书,保存为DER编码格式的cosmos-emulator.cer文件。

项目配置步骤

  • 将导出的cosmos-emulator.cer文件放入Xamarin Android项目的Assets目录,将文件的生成操作设置为AndroidAsset。
  • 在Android应用启动阶段加载这份证书,构建应用专属的信任链:
    // 在MainActivity的OnCreate方法中初始化
    var certificate = CertificateFactory.Instance.CreateCertificate(Assets.Open("cosmos-emulator.cer"));
    var trustStore = KeyStore.GetInstance(KeyStore.DefaultType);
    trustStore.Load(null, null);
    trustStore.SetCertificateEntry("cosmos-local-emulator", certificate);
    
    // 基于自定义信任栈初始化SSL上下文
    var trustManagerFactory = TrustManagerFactory.GetInstance(TrustManagerFactory.DefaultAlgorithm);
    trustManagerFactory.Init(trustStore, null);
    var sslContext = SSLContext.GetInstance("TLS");
    sslContext.Init(null, trustManagerFactory.GetTrustManagers(), null);
    
  • 初始化CosmosDB客户端时,将自定义的SSL校验逻辑传入客户端配置,校验时仅放行和导入证书指纹匹配的本地服务:
    // 提前记录导出的cosmos-emulator.cer的SHA1指纹
    var emulatorCertSha1 = "你导出的证书对应的SHA1哈希值";
    var cosmosOptions = new CosmosClientOptions
    {
        HttpClientFactory = () => new HttpClient(new HttpClientHandler
        {
            ServerCertificateCustomValidationCallback = (request, cert, chain, errors) =>
            {
                // 仅当目标地址是本地模拟器、证书指纹匹配时才放行
                return request.RequestUri.Host == "10.0.2.2" 
                    && cert.GetCertHashString() == emulatorCertSha1;
            }
        })
    };
    // 用配置好的选项初始化CosmosClient连接本地模拟器
    var cosmosClient = new CosmosClient("https://10.0.2.2:8081/", "你的CosmosDB模拟器主连接字符串密钥", cosmosOptions);
    
  • 注意:Android 7.0及以上版本默认不识别用户手动安装到系统目录的证书,直接在应用内做信任映射的方式不受系统版本限制,配置稳定性最高。
方案二:本地开发临时跳过SSL校验(仅适用于非公网的本地测试场景)
  • 因为你的测试链路是Android模拟器 -> 宿主机本地服务,全程无公网传输风险,可以直接跳过本地CosmosDB模拟器的SSL证书校验,不需要额外导入证书,配置成本更低。
  • 具体配置逻辑就是在CosmosDB客户端初始化时,只对10.0.2.2的本地地址放行所有证书校验,避免影响生产环境的正常证书校验:
    var cosmosOptions = new CosmosClientOptions
    {
        HttpClientFactory = () => new HttpClient(new HttpClientHandler
        {
            ServerCertificateCustomValidationCallback = (request, cert, chain, errors) =>
            {
                // 仅本地模拟器地址跳过校验,其他地址保持默认严格校验
                return request.RequestUri.Host == "10.0.2.2";
            }
        })
    };
    
  • 该方式配置完成后即可直接连通本地CosmosDB模拟器,和你目前连接存储模拟器的配置流程完全一致,没有额外环境依赖。

内容的提问来源于stack exchange,提问作者Bisjob

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.24 22:15:10