Вот пример реализации в Swift, надеюсь, это покажет вам, как можно использовать ожидания KVO.
Обработчик, который передается в ожидание, принимает в качестве входных данных два объекта (объект, который вы наблюдаете, и словарь изменений). Он должен вернуть true
, если вы уверены, что значение изменилось, как вы ожидали, и false
, если ожидание не было выполнено.
class Person: NSObject {
@objc dynamic var name: String
init(name: String) {
self.name = name
}
func changeName(to newName: String) {
name = newName
}
}
class Tests: XCTestCase {
func testNameValueChangedWhenChangeNameCalled() {
let person = Person(name: "Alice")
let newName = "Bob"
keyValueObservingExpectation(for: person, keyPath: "name", handler: { (observedObject, change) in
// `observedObject` is of type `Any` so it needs to be cast as the correct type before proceeding
guard let observedObject = observedObject as? Person else {
// Don't fulfill the expectation
return false
}
// Check the current name is the name we expect
return observedObject.name == newName
})
person.changeName(to: newName)
waitForExpectations(timeout: 1, handler: nil)
}
}
Вы также можете инициализировать XCTKVOExpectation
напрямую и использовать XCTWaiter
для обработки результатов с большей детализацией.
let person = Person(name: "Alice")
let newName = "Bob"
let expectation = XCTKVOExpectation(keyPath: "name", object: person)
expectation.handler = { (observedObject, change) in
guard let observedObject = observedObject as? Person else {
return false
}
return observedObject.name == newName
}
person.changeName(to: newName)
let result = XCTWaiter().wait(for: [expectation], timeout: 1)
XCTAssertEqual(result, .completed)