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

XCTest中URLSession发起GET请求无法获取API响应问题

问题解决:XCTest中异步API请求无法获取响应

核心原因

XCTest测试方法默认是同步执行的,当你调用异步的requestAPIInfo方法后,测试方法会直接执行完毕并结束,此时网络请求的异步闭包还没来得及执行,所以看不到任何打印或响应结果。

解决方案

1. 给测试添加异步等待机制

在UI测试代码中,通过XCTestExpectation让测试等待异步任务完成:

func testAPIRequest() {
    let temp = APIHelpers()
    // 创建期望对象,标记需要等待的任务
    let apiExpectation = XCTestExpectation(description: "等待API请求返回结果")
    
    temp.requestAPIInfo { apiResult in
        print(apiResult)
        // 任务完成后标记期望达成
        apiExpectation.fulfill()
    }
    
    // 设置超时时间,等待期望完成
    wait(for: [apiExpectation], timeout: 10.0)
}

2. 修复APIHelpers中的潜在问题

你的API工具类里有几个隐藏风险,优化后能避免静默失败:

  • 不再强制解包URL,处理初始化失败的场景
  • 增加响应数据的空值判断,避免崩溃
  • 解码失败时调用completion,让测试能捕获错误
  • 实际使用创建好的URLRequest(之前代码中创建了但没用到)

优化后的APIHelpers代码:

import Foundation

struct Example: Decodable {
    let userId: Int
    let id: Int
    let title: String
    let completed: Bool
}
 
struct APIHelpers {
    
    let resourceURL: URL?
    let urlString = "https://jsonplaceholder.typicode.com/todos/1"
   
    init() {
        resourceURL = URL(string: urlString)
    }
    
    func requestAPIInfo(completion: @escaping(Result<Example, Error>) -> Void) {
        guard let url = resourceURL else {
            completion(.failure(NSError(domain: "APIHelpers", code: -1, userInfo: [NSLocalizedDescriptionKey: "URL初始化失败"])))
            return
        }
        
        var request = URLRequest(url: url)
        request.httpMethod = "GET"
        
        let dataTask = URLSession.shared.dataTask(with: request) { data, response, error in
            if let error = error {
                print(error.localizedDescription)
                completion(.failure(error))
                return
            }
            
            guard let responseData = data else {
                let emptyDataError = NSError(domain: "APIHelpers", code: -2, userInfo: [NSLocalizedDescriptionKey: "未获取到响应数据"])
                print(emptyDataError.localizedDescription)
                completion(.failure(emptyDataError))
                return
            }

            let decoder = JSONDecoder()
            do {
                let jsonData = try decoder.decode(Example.self, from: responseData)
                completion(.success(jsonData))
            } catch {
                print("JSON解码错误: \(error)")
                completion(.failure(error))
            }
        }
        dataTask.resume()
    }
}

验证方式

  1. 把UI测试代码替换为带XCTestExpectation的版本
  2. 替换优化后的APIHelpers代码
  3. 重新运行测试,此时测试会等待API请求完成,控制台就能打印出响应结果

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.11 10:40:29