2009-06-15 9 views
9

Core Data le permite agregar múltiples almacenes persistentes a un solo nombre NSPersistentStoreCoordinator (cada uno con una configuración diferente), reuniéndolos en un solo NSManagedObjectContext. Lo que no he podido averiguar es cómo Core Data maneja la atomicidad de una operación de guardado para múltiples tiendas.atomicidad del almacén de datos centrales con múltiples almacenes

Digamos que tengo dos tiendas:

NSPersistentStoreCoordinator *coordinator = [[NSPersistentStoreCoordinator alloc] init]; 
[coordinator addPersistentStoreWithType:type configuration:@"A" URL:aURL options:nil error:NULL]; 
[coordinator addPersistentStoreWithType:type configuration:@"B" URL:bURL options:nil error:NULL]; 

NSManagedObjectContext *context = [[NSManageObjectContext alloc] init]; 
[context setPersistentStoreCoordinator:coordinator]; 

Y entonces es el momento para salvar a hacer eso:

NSError *error = nil; 
BOOL result = [context save:&error]; 

La documentación indica que la secuencia de los eventos será:

  1. Guardar tienda A
  2. Guardar tienda B

¿Qué sucede si la tienda A guarda correctamente, pero la tienda B no se puede guardar por algún motivo? (por ejemplo, se eliminó el archivo en el disco o los permisos lo hicieron de solo lectura, ese tipo de cosas). No puedo encontrar ninguna documentación que detalle si Core Data revertirá los cambios en la tienda A.

Me parece extraño que el gráfico objeto se deje en un estado inconsistente (es decir, una tienda actualizada, otra no), pero un tanto complicado y con muchos recursos para realizar un ahorro totalmente atómico en múltiples tiendas. Realmente me gustaría alguna aclaración aquí, ¡tal vez de alguien con más experiencia en el sistema!

Respuesta

5

Finalmente me encontré con la respuesta hoy en CoreDataErrors.h. Hay un código de error:

NSPersistentStoreIncompleteSaveError    = 134040, // one or more of the stores returned an error during save (stores/objects that failed will be in userInfo) 

por lo que parece que Core datos no intentará revertir salva de las tiendas que tuvo éxito. Y de hecho no puede proporcionar atomicidad en múltiples tiendas. ¡Lo suficientemente justo!

1

Esto suena como algo a lo que no sería difícil obtener una respuesta experimental al recrear sus condiciones. ¿Ha tenido tiempo de recrear el escenario que describe?

Me gustaría hacer esto por:

  1. creación de dos tiendas SqlLite y escribiendo un conjunto de datos para cada uno de los archivos.
  2. apagado las tiendas
  3. eliminar el segundo archivo SQLLite
  4. escribir a cabo una operación fácil ver en el primer almacén (que podría ser la mejor manera de hacer una inserción en una tabla y eliminar de la otra). Combine esto con otra operación en la segunda tienda y que debería fallar debido al archivo que falta 5. Compruebe el estado de la primera tienda.

Tengo la sensación de que los cambios en la tienda A no se revertirán, pero quedaré impresionado por cualquier otra respuesta.

+0

No he intentado esto todavía. Soy un poco cauteloso de considerar el resultado experimental como el comportamiento documentado, ya que cualquier cambio en el comportamiento sería bastante catastrófico para lo que estoy planeando. Tenía la esperanza de que alguien pudiera señalarme un trozo de documentación sobre el tema que no había podido encontrar en mis búsquedas. –

+1

Bueno, no puedo encontrar ninguna documentación. Luego planificaría para el peor de los casos y asumir que la reversión no funcionará en dos almacenes de datos y me aseguraré de que el código pueda manejar esto de alguna manera. Siempre puedes intentar hacer inserciones en tablas ficticias antes de comenzar tu gran transacción para asegurarte de que el estado de las tiendas sea correcto. – Grouchal

+0

@Grouchal - No estoy seguro de que la prueba que está proponiendo funcionaría. De manera predeterminada, CoreData creará la segunda tienda según sea necesario (si el archivo se cerró como usted sugiere). Si el archivo estuviera abierto, el sistema de archivos Unix desvincularía el archivo del sistema de archivos, pero la pila CoreData aún tendría acceso al archivo no enlazado hasta que se cerrara. – xyzzycoder

0

Una opción para lograr transacciones entre varias fuentes de datos se conoce como "confirmación de dos fases"." http://en.wikipedia.org/wiki/Two-phase_commit_protocol

confirmación en dos fases sistemas se encuentran comúnmente en desarrollo de la empresa, a veces incrustado dentro de los sistemas de procesamiento de transacciones http://en.wikipedia.org/wiki/Transaction_processing_monitor

tales como Tuxedo http://en.wikipedia.org/wiki/Tuxedo_(software)

CoreData no es realmente un objeto-relacional empresa herramienta de mapeo, y no creo que sea capaz de confirmaciones en dos fases. Algunos de los tipos de tienda compatibles con CoreData y no transaccionales o atómicos. Para admitir una confirmación en dos fases, se necesitaría que cada tienda persistente sea ambas transactio nal y atómico.

Cuestiones relacionadas