Swift CoreData UnitTest:如何避免EXC_BREAKPOINT [英] Swift CoreData UnitTest: How to avoid EXC_BREAKPOINT
问题描述
这将是CoreData单元测试中使用swift的常见问题。 EXC_BREAKPOINT异常发生,因为swift的名称空间在正常模块和测试模块之间的差异。我仍然在努力反对这个问题,即使有些解决方案被介绍。
我做了什么,我的问题在这里。
- 使用具有核心数据的单一应用程序模板创建新项目,使用检查选项。
- 运行单元测试。未发生错误。
- 将CoreDataSampleTest目标添加到Appdelegate.swift。
- 在CoreDataSampleTests.swift中更改testExample(),如下所示。
func testExample(){
let appDel:AppDelegate = UIApplication.sharedApplication()。作为AppDelegate委托
}
- 运行单元测试。发生了EXC_BREAKPOINT。
- 在AppDelegate.swift中更改managedObjectModel(),如下所示 Swift无法在Xcode测试中测试核心数据。
pre>lazy var managedObjectModel:NSManagedObjectModel = {
//应用程序的管理对象模型。这个属性不是可选的...
let modelURL = NSBundle.mainBundle()。URLForResource(CoreDataSample,withExtension:momd)!
let managedObjectModel = NSManagedObjectModel(contentsOfURL:modelURL)!
//检查我们是否作为测试运行
let environment = NSProcessInfo.processInfo()。environment as [String:AnyObject]
let isTest =(environment [ XCInjectBundle] as?String)?。pathExtension ==xctest
//创建模块名称
let moduleName =(isTest)? CoreDataSampleTests:CoreDataSample
//使用更新的实体类名创建一个新的托管对象模型
var newEntities = [] as [NSEntityDescription]
for )in enumerate(managedObjectModel.entities){
let newEntity = entity.copy()as NSEntityDescription
newEntity.managedObjectClassName =\(moduleName).\(entity.name)
newEntities.append(newEntity)
}
let newManagedObjectModel = NSManagedObjectModel()
newManagedObjectModel.entities = newEntities
return newManagedObjectModel
} b
- 运行单元测试。再次出现EXC_BREAKPOINT。
我想知道的是两件事。
-
如何避免EXC_BREAKPOINT异常。测试方法似乎正常工作,但EXC_BREAKPOINT异常暂时停止每个测试方法的过程。我必须每次都恢复。
-
如果我无法避免EXC_BREAKPOINT,我想在执行单元测试时忽略EXC_BREAKPOINT异常。
/ li>
任何帮助或建议对我都有帮助。
/ p>
FYI:
编辑: XCode版本是6.2 Wolfgang说我认为Jesse Squires解决方案(它为我),但有几个步骤: (这不是必须的,但会帮助保持整洁,因为以下步骤涉及使很多事情公开,并且如果你不分离它,它将传播整个项目。) 你最终应该看起来像这样的实体: 在SO回答中的另一种方法此处也有效。 编辑1:添加了关于替代方案的注释。 编辑2:通过提示将Core Data移动到单独的模块中。 This would be common problem in CoreData unit testing using swift. EXC_BREAKPOINT exception happens due to swift's namespace differences between normal module and test module. I'm still struggling against this issue even though some solutions are introduced. What I did and my problem is here.
import Foundation
import CoreData
@objc(ClassName)
public class ClassName:NSManagedObject {
@NSManaged public var property:Type
}
func testExample() {
let appDel: AppDelegate = UIApplication.sharedApplication().delegate as AppDelegate
}
- Run unit tests. EXC_BREAKPOINT occurred.
- Change managedObjectModel() in AppDelegate.swift as following Swift cannot test core data in Xcode tests?.
lazy var managedObjectModel: NSManagedObjectModel = { // The managed object model for the application. This property is not optional... let modelURL = NSBundle.mainBundle().URLForResource("CoreDataSample", withExtension: "momd")! let managedObjectModel = NSManagedObjectModel(contentsOfURL: modelURL)! // Check if we are running as test or not let environment = NSProcessInfo.processInfo().environment as [String : AnyObject] let isTest = (environment["XCInjectBundle"] as? String)?.pathExtension == "xctest" // Create the module name let moduleName = (isTest) ? "CoreDataSampleTests" : "CoreDataSample" // Create a new managed object model with updated entity class names var newEntities = [] as [NSEntityDescription] for (_, entity) in enumerate(managedObjectModel.entities) { let newEntity = entity.copy() as NSEntityDescription newEntity.managedObjectClassName = "\(moduleName).\(entity.name)" newEntities.append(newEntity) } let newManagedObjectModel = NSManagedObjectModel() newManagedObjectModel.entities = newEntities return newManagedObjectModel }()
- Run unit tests. EXC_BREAKPOINT occurred again.
What I want to know are two things.
How to avoid EXC_BREAKPOINT exception. Test methods seem to work normally but EXC_BREAKPOINT exception temporary stop the process at every test methods. I have to resume it every time. It very hard to run the test methods.
If I cannot avoid EXC_BREAKPOINT, I want to ignore the EXC_BREAKPOINT exception when executing unit tests.
Any help or suggestion would be helpful for me.
Thanks,
FYI:
Swift cannot test core data in Xcode tests?.
Edit:
XCode Version is 6.2
As Wolfgang said I think the Jesse Squires solution works (it does for me) but there are several steps:
- Optional: Move your Core Data into a separate module (I used a Framework as Xcode 6.2 still seems not to like Swift static libraries) - this tip curtesy of Jessie Squires,
(This is not necessary but will help keep things tidy as the following steps involve making a lot of things public and that will spread through your whole project if you do not separate it out.)
- add @objc(ClassName) to all your NSManagedObject classes,
- make all your NSManagedObject classes and all their contained properties public,
You should end up with entities that look like this:
import Foundation
import CoreData
@objc(ClassName)
public class ClassName: NSManagedObject {
@NSManaged public var property: Type
}
- make the Entity Class name for all your entities in your model a simple reference to the class (e.g. ClassName not a AppName.ClassName).
- make public all classes, methods, properties etc. that are in the same module as Core Data and that you want to unit test,
- remove all your classes from the test target (i.e. untick the test target in 'Target Membership' for each of them), but leave the data model in the test target,
- import your app into your test class(es) (e.g. add import AppName to the test class source).
There is an alternative approach in the SO answer here that also works.
Edit 1: Added note about alternative.
Edit 2: Passed on tip to move Core Data into a separate module.
这篇关于Swift CoreData UnitTest:如何避免EXC_BREAKPOINT的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!