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

Swift调用GIPHY API加载动图到UITableView报NSUnknownKeyException

崩溃根因
  • 核心崩溃触发点:你已经通过Codable完成了JSON到模型的转换,却错误地使用Objective-C时代的KVC(value(forKey:))方式取值,且取值的目标对象完全错误。
  • 你在fetchGiphyData中写的let gifImages = [gifs],是把整个接口返回的根模型GiphyResponseData(这个结构体只有data一个属性,根本没有url字段)包成了数组,遍历的时候对这个根对象取url字段,直接触发KVC不兼容的崩溃。另外Swift原生结构体本身就不支持这种KVC取值方式,完全没必要这么写。
  • 日志里的boringssl_metrics_log_metric_block_invoke是iOS系统底层的调试日志,和本次崩溃无关,直接忽略即可。
  • 额外隐患:你当前的cell图片加载逻辑没有处理UITableView复用,滑动的时候会出现图片错位、重复加载的问题。
修复方案

1. 修正数据解析逻辑

你自己定义的模型层级是清晰的:GiphyResponseData.data是图片信息数组,每个元素下的images.original就是存了动图url的GiphyData对象,直接用点语法访问属性即可,完全不需要KVC。
替换原有fetchGiphyData方法代码:

func fetchGiphyData() {
    let request = AF.request("https://api.giphy.com/v1/gifs/trending?api_key=zONZGFIbbvYDBjLEBlgKxLjbsClfmptw&limit=25&rating=pg-13")
    
    request.responseDecodable(of: GiphyResponseData.self) { (response) in
        // 先处理请求错误,方便排查问题
        if let error = response.error {
            print("GIPHY接口请求失败: \(error.localizedDescription)")
            return
        }
        guard let responseModel = response.value else { return }
        
        // 直接映射提取所有动图的original地址
        self.giphyImage = responseModel.data.map { $0.images.original }
        
        // UI刷新必须放在主线程
        DispatchQueue.main.async {
            self.giphyTableView.reloadData()
        }
    }
}

2. 修复UITableView复用导致的图片错位问题

首先在GiphyTableViewCell类中添加请求持有属性和复用重置逻辑:

class GiphyTableViewCell: UITableViewCell {
    @IBOutlet weak var giphyImage: UIImageView!
    // 持有图片加载请求,方便复用的时候取消
    var imageLoadRequest: DataRequest?
    
    override func prepareForReuse() {
        super.prepareForReuse()
        // 复用时取消上一个未完成的请求,清空图片
        imageLoadRequest?.cancel()
        giphyImage.image = nil
    }
}

再替换原有cellForRowAt方法代码:

func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
    let cell = tableView.dequeueReusableCell(withIdentifier: "cell", for: indexPath) as! GiphyTableViewCell
    let gifModel = giphyImage[indexPath.row]
    
    // 发起图片请求并持有
    cell.imageLoadRequest = AF.request(gifModel.url).responseImage { response in
        // 校验当前cell是否还对应当前indexPath,避免复用时错图
        guard let currentIndexPath = tableView.indexPath(for: cell),
              currentIndexPath == indexPath,
              case .success(let image) = response.result else { return }
        cell.giphyImage.image = image
    }
    
    return cell
}

改完之后崩溃问题会直接解决,滑动列表也不会出现图片错位的情况。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.30 10:06:20