2012-08-14 17 views
14

Buduję model odwzorowania dla mojej migracji za pomocą niestandardowej polityki migracji jednostek i chciałbym zbudować kilka testów jednostkowych dla tej migracji. Migracja wydaje się działać poprawnie po uruchomieniu aplikacji, ale moja metoda podklasy NSEntityMigrationPolicy nie jest wywoływana w ogóle po uruchomieniu migracji za pomocą testu jednostki.Jak mogę przetestować jednostkę migracji danych podstawowych?

Używam wbudowanej struktury OCUnit Xcode.

Mój kod testowy:

- (void)test1to2Migration_appIdentifierMoved { 
    [self createVersion1Store]; 

    // TODO Perform migration 
    NSManagedObjectModel *version1Model = [self version1Model]; 
    NSManagedObjectModel *version2Model = [self version2Model]; 

    NSError *error = nil; 
    NSMappingModel *mappingModel = [NSMappingModel 
     inferredMappingModelForSourceModel:version1Model 
     destinationModel:version2Model error:&error]; 
    STAssertNotNil(mappingModel, @"Error finding mapping model: %@", error); 

    NSMigrationManager *migrationManager = 
     [[[NSMigrationManager alloc] 
     initWithSourceModel:version1Model 
     destinationModel:version2Model] 
     autorelease]; 

    BOOL migrationSucceeded = 
     [migrationManager migrateStoreFromURL:self.version1StoreURL 
      type:NSSQLiteStoreType 
      options:nil 
      withMappingModel:mappingModel 
      toDestinationURL:self.version2StoreURL 
      destinationType:NSSQLiteStoreType 
      destinationOptions:nil 
      error:&error]; 
    STAssertTrue(migrationSucceeded, @"Error migrating store: %@", error); 

    // TODO Verify appIdentifier is moved from Project to its Tests 

    [self deleteTempStores]; 
} 

Mój model odwzorowania określa niestandardową NSEntityMigrationPolicy definiujący metody -createRelationshipsForDestinationInstance:entityMapping:manager:error:, ale moja polityka nigdy nie jest wywoływana z testów jednostkowych. Po uruchomieniu migracji model jest modyfikowany do nowej wersji - oczekiwane atrybuty pojawiają się w odpowiednich miejscach.

Jakieś pomysły, w jaki sposób mogę sprawić, aby moja polityka migracyjna działała w teście jednostkowym?

Odpowiedz

4

Problemem okazała się w linii

NSMappingModel *mappingModel = [NSMappingModel 
    inferredMappingModelForSourceModel:version1Model 
    destinationModel:version2Model error:&error]; 

Gdybym go zmienić na

NSMappingModel *mappingModel = [NSMappingModel 
    mappingModelFromBundles:@[[NSBundle bundleForClass:[MyTestClass class]]] 
    forSourceModel:version1Model destinationModel:version2Model]; 

wówczas funkcje testowe poprawnie.

2

Swift 3

Wymień zmienne MODELNAME i modelNameVersionFormatString dla modeli nazwy plików

import XCTest 
import CoreData 

class RCCoreDataMigrationTests: XCTestCase { 

    private let storeType = NSSQLiteStoreType 
    private let modelName = "Model" 
    private let modelNameVersionFormatString = "Model-%@" 

    private func storeURL(_ version: String) -> URL? { 
     let storeURL = URL(fileURLWithPath: "\(NSTemporaryDirectory())\(version).sqlite") 
     return storeURL 
    } 

    private func createObjectModel(_ version: String) -> NSManagedObjectModel? { 
     let bundle = Bundle.main 
     let managedObjectModelURL = bundle.url(forResource: modelName, withExtension: "momd") 
     let managedObjectModelURLBundle = Bundle(url: managedObjectModelURL!) 
     let modelVersionName = String(format: modelNameVersionFormatString, version) 
     let managedObjectModelVersionURL = managedObjectModelURLBundle!.url(forResource: modelVersionName, withExtension: "mom") 
     return NSManagedObjectModel(contentsOf: managedObjectModelVersionURL!) 
    } 

    private func createStore(_ version: String) -> NSPersistentStoreCoordinator { 
     let model = createObjectModel(version) 
     let storeCoordinator = NSPersistentStoreCoordinator(managedObjectModel: model!) 
     try! storeCoordinator.addPersistentStore(ofType: storeType, 
               configurationName: nil, 
               at: storeURL(version), 
               options: nil) 
     return storeCoordinator 
    } 

    private func migrateStore(fromVersionMOM: String, toVersionMOM: String) { 
     let store = createStore(fromVersionMOM) 
     let nextVersionObjectModel = createObjectModel(toVersionMOM)! 
     let mappingModel = NSMappingModel(from: [Bundle.main], forSourceModel: store.managedObjectModel, destinationModel: nextVersionObjectModel)! 
     let migrationManager = NSMigrationManager(sourceModel: store.managedObjectModel, destinationModel: nextVersionObjectModel) 
     do { 
      try migrationManager.migrateStore(from: store.persistentStores.first!.url!, 
               sourceType: storeType, 
               options: nil, 
               with: mappingModel, 
               toDestinationURL: storeURL(toVersionMOM)!, 
               destinationType: NSSQLiteStoreType, 
               destinationOptions: nil) 
     } catch { 
      print("Error: \(error)") 
      XCTAssertNil(error) 
     } 
     try! FileManager.default.removeItem(at: storeURL(toVersionMOM)!) 
     try! FileManager.default.removeItem(at: storeURL(fromVersionMOM)!) 
    } 

    func testMigratingStores() { 
     migrateStore(fromVersionMOM: "1486", toVersionMOM: "1487") 
    } 
} 
Powiązane problemy