Problema con el almacenamiento de NSDate para el context CoreData

Estoy intentando save el object gestionado con uno de los attributes de tipo Date en managedObjectContext .

El código es como:

 reminder.eventDate = selectedDate; NSLog(@"Date: %@", selectedDate); NSError *error = nil; if (![reminder.managedObjectContext save:&error]) { NSLog(@"Unresolved error %@, %@", error, [error userInfo]); abort(); } 

durante el progtwig de ahorro de context se bloquea con SIGABRT. Aquí hay un logging de la console:

 2011-02-28 00: 50: 18.817 MyApp [9021: 207] *** Terminación de la aplicación debido a uncaught 
 exception 'NSInvalidArgumentException', motivo: '- [__ NSDate isEqualToString:]: 
 el selector no reconocido enviado a la instancia 0x4e73490 '
 *** Pila de llamadas en el primer tiro:
 (
     0 CoreFoundation 0x01057be9 __exceptionPreprocess + 185
     1 libobjc.A.dylib 0x011ac5c2 objc_exception_throw + 47
     2 CoreFoundation 0x010596fb - [NSObject (NSObject) doesNotRecognizeSelector:] + 187
     3 CoreFoundation 0x00fc9366 ___forwarding___ + 966
     4 CoreFoundation 0x00fc8f22 _CF_forwarding_prep_0 + 50

¿Alguien sabe por qué tengo eso? La segunda pregunta es por qué cuando hago el check in en el modo depurador selectedDate no es un tipo de date NSDate pero __NSDate (doble subrayado en el frente).

¡Gracias!

ACTUALIZAR:

Hice algunos cambios para captar más fácilmente el error. entonces el código ahora es como:

 reminder.eventDate = [NSDate date]; NSLog(@"Date: %@", selectedDate); NSError *error = nil; if (![reminder.managedObjectContext save:&error]) { NSLog(@"Unresolved error %@, %@", error, [error userInfo]); abort(); } 

Entonces, aquí guardamos definitivamente NSDate. recorder.eventDate es NSDate también. Pero todavía tengo este error. Si comento reminder.eventDate = [NSDate date]; saving arroja otro error (la date es el campo obligatorio en NSData, por lo que save: devuelve el error "La operación no pudo completarse" con eventDate = nil; La estructura CoreData se verifica varias veces: eventDate tiene el tipo Date.

ACTUALIZACIÓN (Problema resuelto): Finalmente encontré el problema. eventDate se configuró como key para detailTextLabel.text en mis celdas de tableview (usé KVO para eso). Entonces, si no hubo una llamada directa y no pude encontrar ninguna invocación de método para eventDate . Lo extraño es que el locking estaba en el método save , no más tarde. Y en la stack de llamadas no hay tableView:cellForRowAtIndexPath: método en absoluto …

Solo para agregar a lo que ya se ha dicho:

No tiene que ser un problema con el model o la subclass NSManagedObject. Podría ser solo un código casi en cualquier parte que llame isEqualToString: En algún lugar tienes un object que el código asume que debe ser un NSString pero es un object NSDate. Miraría cualquier código que pudiera convertir dates a cadenas.

Sin embargo, dado que ocurre al save, observaría las personalizaciones que podría haber hecho en la subclass.

El lugar para comenzar es search en el proyecto isEqualToString:

Actualizar:

Dado que isEqualToString es un método de testing, se puede activar en cualquier momento que realice una comparación para una cadena, como en una especie. No pude reproducir su error exacto, pero el siguiente código hace algo similar:

 id idDate=[NSDate date]; NSString *bob=[NSString stringWithString:@"bob"]; NSString *steve=@"test this"; steve=idDate; NSLog(@"test=%@",([steve compare:bob]) ?@"YES":@"NO"); 

… cumple pero arroja una exception:

 -[NSCFString timeIntervalSinceReferenceDate]: unrecognized selector sent to instance 0x4040 

Entonces, puedes ver cómo pueden deslizarse estos types de errores. También es una demostración de por qué debes tener cuidado con el uso de id .

Por más tonto que parezca, le sugiero que compruebe que tanto su object recordatorio como el object managedObjectContext asociado son válidos.

Está seguro de que su model modela correctamente eventDate como un atributo de date, y también está seguro de que el object que pasa al atributo eventDate es un object NSDate. Por lo tanto, intente verificar que el recordatorio y its managedObjectContext no sean nulos.

Finalmente, verifique si todos los demás attributes y relaciones están correctamente configurados (verifique si realmente inserta todos los attributes y relaciones requeridos, verifique si los objects que usa son del tipo correcto, etc.).

Esto también ayudará a networkingucir las posibilidades.

EDITAR : puede verificar lo que realmente está sucediendo dentro de su database sqlite. Simplemente agregue lo siguiente como argumento antes de comenzar su aplicación:

-com.apple.CoreData.SQLDebug 1

mira la documentation

Cómo hacer esto depende de su set de herramientas instalado (Xcode 3 o 4). Estoy usando el último Xcode 4 y para agregar un argumento, simplemente selecciona tu esquema actual, luego selecciona Ejecutar "nombre de tu aplicación" y haz clic en la pestaña Argumentos para agregar el argumento.

Parece que tiene su model de datos configurado para esperar una cadena en la propiedad eventDate, en lugar de una date.

NSDate es un "clúster de class", lo que significa que las instancias con las que realmente manejas serán instancias de alguna subclass privada de NSDate (en este caso, __NSDate).

En cuanto al error, estoy de acuerdo con Simon Goldeen en que la razón más probable es que el model de datos o la subclass NSManagedObject esté esperando una cadena en lugar de una date.

También perseguí esto. Dado que su model y las definiciones de class son buenas, y asumiendo que su valor es bueno, hay un lugar less obvio que lo solucionó para mí … Elimine la aplicación del dispositivo y limpie su compilation, y asegúrese de que cualquier file sqlite sembrado sea nuevo también. Mi dispositivo o carpeta de construcción tenía una vieja tienda o model persistente que causó esto. ¿Qué otros frameworks estás usando? RestKit, JSON, etc. Cualquier cosa que sobrecargue un método de class también podría ser un sospechoso. … Es difícil saber qué se compara en ese ahorro … Mi conjetura es una tienda vieja