You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Flutter加载图片报handshake.cc:359自签名证书验证失败如何解决

问题原因

你单独定义的IOClient没有被CachedNetworkImage使用,该库默认使用内部自带的默认HttpClient加载图片,默认的HttpClient会严格校验SSL证书,当你请求的图片服务用了自签名证书时,就会抛出证书验证失败的错误。

解决方案

有两种常用的解决方式,可根据场景选择:

方案1:自定义CacheManager指定HttpClient(推荐)

CachedNetworkImage依赖flutter_cache_manager实现缓存逻辑,你可以自定义CacheManager,传入你配置好的IOClient,所有通过该CacheManager加载的图片都会使用你指定的客户端。

  1. 首先实现自定义CacheManager:
import 'package:flutter_cache_manager/flutter_cache_manager.dart';
import 'package:http/io_client.dart';
import 'dart:io';

class CustomCacheManager extends CacheManager {
  static const String _cacheKey = 'customImageCache';
  static CustomCacheManager? _instance;

  factory CustomCacheManager() {
    _instance ??= CustomCacheManager._internal();
    return _instance!;
  }

  CustomCacheManager._internal() : super(
    Config(
      _cacheKey,
      fileService: HttpFileService(
        httpClient: IOClient(
          HttpClient()
            ..connectionTimeout = const Duration(seconds: 30)
            ..idleTimeout = const Duration(seconds: 30)
            ..badCertificateCallback = (X509Certificate cert, String host, int port) => true,
        ),
      ),
    ),
  );
}
  1. 在使用CachedNetworkImage时指定自定义的cacheManager:
CachedNetworkImage(
  imageUrl: item.thumbnail,
  fit: BoxFit.cover,
  cacheManager: CustomCacheManager(), // 加上这一行
  httpHeaders: {
    'Authorization': 'Bearer ${authProvider.token}',
  },
  errorWidget: (context, _, __) => const Center(
    child: Icon(
      Icons.broken_image_rounded,
      size: 28.0,
      color: Colors.black54,
    ),
  ),
)

方案2:全局重写HttpOverrides(适合开发调试用)

如果不需要单独管控图片请求的客户端,也可以全局重写Dart的HttpClient创建逻辑,所有Http请求都会默认跳过证书校验:

import 'dart:io';
import 'package:flutter/material.dart';

void main() {
  HttpOverrides.global = _DevHttpOverrides();
  runApp(const MyApp());
}

class _DevHttpOverrides extends HttpOverrides {
  @override
  HttpClient createHttpClient(SecurityContext? context) {
    return super.createHttpClient(context)
      ..connectionTimeout = const Duration(seconds: 30)
      ..idleTimeout = const Duration(seconds: 30)
      ..badCertificateCallback = (X509Certificate cert, String host, int port) => true;
  }
}
注意事项
  • 生产环境不要直接设置badCertificateCallback固定返回true,会导致所有SSL校验失效,存在严重的安全风险。正式上线时建议将服务端的自签名证书加入客户端的可信证书列表,仅对可信域名的证书放行校验。
  • 如果你需要全局携带Authorization等请求头,也可以直接加到自定义HttpClient的defaultHeaders属性中,无需每个CachedNetworkImage都单独传httpHeaders。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.09.24 14:45:04