通过Golang SDK上传至Cloudinary偶现DNS解析失败问题求助
问题分析与解决方案
报错dial tcp: lookup api.cloudinary.com: no such host本质是DNS解析偶发失败,结合你本地Windows无VPN的环境,大概率是本地DNS服务不稳定,或者默认HTTP客户端的DNS缓存策略导致的。以下是针对性的解决办法:
一、代码层面优化(推荐)
给Cloudinary客户端配置自定义HTTP客户端,指定可靠的DNS服务器,同时优化连接池和超时设置,避免解析异常:
import ( "context" "net" "net/http" "time" "github.com/cloudinary/cloudinary-go/v2" "github.com/cloudinary/cloudinary-go/v2/api/uploader" ) type cloudinaryStorageRepository struct { cld *cloudinary.Cloudinary } func NewCloudinaryStorageRepository(cloudName string, apiKey string, apiSecret string) domain.StorageRepository { // 自定义DNS解析器,使用Google公共DNS服务 dnsResolver := &net.Resolver{ PreferGo: true, // 启用Go内置DNS解析器,不依赖系统解析 Dial: func(ctx context.Context, network, address string) (net.Conn, error) { d := net.Dialer{ Timeout: time.Second * 5, } return d.DialContext(ctx, network, "8.8.8.8:53") }, } // 自定义HTTP Transport,配置连接池与解析逻辑 transport := &http.Transport{ DialContext: func(ctx context.Context, network, addr string) (net.Conn, error) { host, port, err := net.SplitHostPort(addr) if err != nil { return nil, err } // 通过自定义解析器获取IP列表 ips, err := dnsResolver.LookupHost(ctx, host) if err != nil { return nil, err } // 遍历IP尝试连接,提升成功率 for _, ip := range ips { conn, err := net.DialTimeout(network, net.JoinHostPort(ip, port), 5*time.Second) if err == nil { return conn, nil } } return nil, err }, MaxIdleConns: 100, MaxIdleConnsPerHost: 10, IdleConnTimeout: 90 * time.Second, } // 配置全局请求超时的HTTP客户端 httpClient := &http.Client{ Transport: transport, Timeout: 30 * time.Second, } // 初始化Cloudinary并绑定自定义客户端 cld, err := cloudinary.NewFromParams(cloudName, apiKey, apiSecret) if err != nil { panic(err) } cld.Config.Client = httpClient return &cloudinaryStorageRepository{cld} } // Upload方法保持原有逻辑不变 func (c *cloudinaryStorageRepository) Upload(ctx context.Context, storage *domain.Storage) (string, error) { file, err := storage.File.Open() defer func(file multipart.File) { err := file.Close() if err != nil { logrus.Error(err) } }(file) if err != nil { logrus.Error(err) return "", err } uploaded, err := c.cld.Upload.Upload(ctx, file, uploader.UploadParams{ Folder: storage.Folder, PublicID: storage.Name, }) if err != nil { logrus.Error(err) return "", err } return uploaded.SecureURL, nil }
二、本地环境排查
- 刷新DNS缓存:打开命令提示符,执行
ipconfig /flushdns,清除本地DNS缓存 - 测试解析稳定性:多次执行
nslookup api.cloudinary.com,观察是否有解析失败的情况,如果频繁失败,建议在网络设置里手动更换DNS服务器(比如8.8.8.8或1.1.1.1) - 检查拦截规则:确认Windows防火墙或第三方安全软件没有拦截对
api.cloudinary.com的DNS请求
内容的提问来源于stack exchange,提问作者Tubagus Saifulloh
相关产品推荐
相关产品推荐

