gpt4 book ai didi

ios - 使用 CoreData 进行单元测试 DI 不起作用

转载 作者:行者123 更新时间:2023-11-30 12:08:39 24 4
gpt4 key购买 nike

我正在尝试编写一个测试,以确保我的 View 模型的模型属性在设置时从模型调用我的 fetchPlan 方法,然后在我的 View 模型中设置我的“计划”属性。似乎正在设置属性,但缺少值...

这是我的 View 模型

final class PlanProgressViewModel: PlanProgressViewModelView {

// MARK: - Properties
fileprivate var plan: PlanData?

// MARK: - PlanProgressViewModelView
weak var viewDelegate: PlanProgressViewModelViewDelegate?

var model: PlanModel? {
didSet {
model?.fetchCurrentPlan(completionHandler: { (plan) in
guard let plan = plan else {return}
self.plan = plan
})
}
}
// Testing this fails...
var planName: String! {
guard let plan = plan else {return "No plan"}
return plan.name
}

var planProgressionString: String! {
return "\(Int(round(self.progress * 100)))%"
}

var progress: Double! {
guard let plan = plan, let workouts = plan.workouts, let completedWorkouts = plan.completedWorkouts else {return 0}
return Double(Int(completedWorkouts) / workouts.count)
}
}

这是我的测试套件,我正在使用模拟从模型返回硬编码数据。

var sut: PlanProgressViewModel!
var model: MockPlanModel!
var moc: NSManagedObjectContext!

override func setUp() {
super.setUp()
moc = setupInMemoryMOC()

let mockModel = MockPlanModel(moc: moc)
model = mockModel

let viewModel = PlanProgressViewModel()
viewModel.model = model
sut = viewModel
}

override func tearDown() {
moc = nil
model = nil
sut = nil
super.tearDown()
}
// This passes
func testModelFetchesCurrentPlanOnce() {
XCTAssertEqual(model.fetchPlanWasCalled, 1)
}

// This is failing
func testPlanName() {
XCTAssertEqual(sut.planName, "Test plan")
}

这是我设置内存持久存储的方法...

public func setupInMemoryMOC() -> NSManagedObjectContext {
let mom = NSManagedObjectModel.mergedModel(from: [Bundle.main])
let psc = NSPersistentStoreCoordinator(managedObjectModel: mom!)

do {
try psc.addPersistentStore(ofType: NSInMemoryStoreType, configurationName: nil, at: nil, options: nil)
} catch {
fatalError()
}

let moc = NSManagedObjectContext.init(concurrencyType: .mainQueueConcurrencyType)
moc.persistentStoreCoordinator = psc

return moc }

这是我对返回硬编码数据的模型的模拟...

public class MockPlanModel: MWPlanModel {
var fetchPlanWasCalled = 0

override public func fetchCurrentPlan(completionHandler: @escaping (_ plan: PlanData?) -> ()) {
fetchPlanWasCalled += 1

let moc = setupInMemoryMOC()
let plan = createTestPlan(moc: moc)

completionHandler(plan)
}}

这是我用于创建模型对象的辅助方法(PlanData 是我的“Plan”NSManaged 对象继承的协议(protocol))。

public func createTestPlan(moc: NSManagedObjectContext) -> PlanData {
let plan: Plan = Plan(context: moc)
plan.name = "Test plan"
plan.completedWorkouts = 5
plan.currentPlan = true

for _ in 0..<5 {
plan.mutableOrderedSetValue(forKeyPath: #keyPath(Plan.workouts)).add(createTestCompletedWorkout(moc: moc))
}

return plan }

计划名称应该是“测试计划”,因为这就是我设置的硬编码值,但它失败并返回一个空字符串...... enter image description here

真的坚持这一点,我对测试还很陌生,所以我很感谢这方面的任何帮助。谢谢

最佳答案

@MartinR 评论指出了要点:

The non-optional on the left side "Test plan" gets automatically promoted to an optional. because sut.planName is an optional. more check this Swift comparing Strings optionals vs non-optional

您需要解开sut.planName

if let planName = sut.planName{
XCTAssertEqual(planName, "Test plan")
}

或者尝试这样:

 XCTAssertEqual((sut.planName ?? ""), "Test plan")

注意:如果您仍然遇到同样的问题,请更新您的 Xcode

// Using Apple XCTest (Xcode 7.3.1), this produces the output:
// "XCTAssertEqual failed: ("Optional(1)") is not equal to ("Optional(2)") - "
XCTAssertEqual(1, 2)

更多详细信息:Here Bug reported

关于ios - 使用 CoreData 进行单元测试 DI 不起作用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/46354319/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com