Я пишу юнит-тесты для методов класса в swift. Эти методы вызывают методы класса, которые макетируются для модульного теста. Методы возвращают обещания с ответом, полученным из макетированных статических / классовых методов.
NetworkAuthProtocol: -
protocol NetworkAuthProtocol {
static func httpGet(_ url: String, completionHandler complete: @escaping(Any?, Error?) -> Void)
static func httpDelete(_ url: String, completionHandler complete: @escaping (Any?, Error?) -> Void)
}
Ниже приведен макет класса для модульного теста с методами класса: -
class NetworkAuthMock: NetworkAuthProtocol {
class func httpGet(_ url: String, completionHandler complete: @escaping(Any?, Error?) -> Void) {
complete(nil, Error)
}
class func httpDelete(_ url: String, completionHandler complete: @escaping (Any?, Error?) -> Void) {
complete(nil, Error)
}
}
Ниже приведен класс, для которого я пишу юнит-тесты: -
class FetchDataAPIService {
var networkAuthDelegate: NetworkAuthProtocol.Type = NetworkAuth.self
func fetchUserData(userUrl: String) -> Promise<Any> {
return Promise<Any> { seal in
networkAuthDelegate.httpGet(userUrl) { (result, error) in
if error == nil {
seal.fulfill(result!)
} else {
seal.reject(error!)
}
}
}
}
func deleteUserData(userUrl: String) -> Promise<Any> {
return Promise<Any> { seal in
networkAuthDelegate.httpDelete(userUrl) { (_, error) in
if error == nil {
seal.fulfill(())
} else {
seal.reject(error!)
}
}
}
}
}
Юнит-тесты, которые я написал, добавив их ниже: -
class FetchDataAPIServiceTests: XCTestCase {
var fetchDataAPIService: FetchDataAPIService!
var result: String?
var error: Error?
override func setUp() {
super.setUp()
self.fetchDataAPIService = FetchDataAPIService()
self.fetchDataAPIService.networkAuthDelegate = NetworkAuthMock.self
self.error = nil
}
override func tearDown() {
super.tearDown()
}
func testFetchUserData() {
let expectation = XCTestExpectation(description: "test fetchUserData")
firstly {
self.fetchDataAPIService.fetchUserData(userUrl: "url")
}.done { (_) in
XCTFail("test failed")
}.catch { (error) in
XCTAssertNotNil(error)
expectation.fulfill()
}
wait(for: [expectation], timeout: 10.0)
}
func testDeleteUserData() {
let expectation = XCTestExpectation(description: "test deleteUserData")
firstly {
self.fetchDataAPIService.deleteUserData(userUrl: "url")
}.done { (_) in
XCTFail("test failed")
}.catch { (error) in
XCTAssertNotNil(error)
expectation.fulfill()
}
wait(for: [expectation], timeout: 10.0)
}
}
С ожиданиями, пройти тест в изоляции, но вместе он не проходит. Я пробовал другие методы, такие как добавление DispatchQueue.main.asyncAfter вне оператора XCTAssert. Также я добавил точки останова в метод httpGet и httpDelete класса Mock, контроль там никогда не достигается. Ничто не похоже на работу. Покрытие кода работает только тогда, когда тесты выполняются изолированно, но иногда это тоже, а также происходит сбой сборки теста в файле main.m. Как я могу сделать все тесты успешными, а также покрыть тестовое покрытие для всех методов?