Reputation:
I want to store in a NSMutableDictionary
some null values using NSNull
and then serialize this data using a property list. Problem is NSNull
is not allowed and I get "Property list is in invalid format" error. Is there a workaround for this? Seems very surprising they didn't put NSNull
on the list of valid plist objects.
Upvotes: 12
Views: 7224
Reputation: 1173
I convert NSArray or NSDictionary to NSData before serializing. Following is a category on nsarray for serializing and deserializing. This comfortableby handles some data being nsnull
@implementation NSArray(Plist)
-(BOOL)writeToPlistFile:(NSString*)filename{
NSData * data = [NSKeyedArchiver archivedDataWithRootObject:self];
NSArray * paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString * documentsDirectory = [paths objectAtIndex:0];
NSString * path = [documentsDirectory stringByAppendingPathComponent:filename];
BOOL didWriteSuccessfull = [data writeToFile:path atomically:YES];
return didWriteSuccessfull;
}
+(NSArray*)readFromPlistFile:(NSString*)filename{
NSArray * paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString * documentsDirectory = [paths objectAtIndex:0];
NSString * path = [documentsDirectory stringByAppendingPathComponent:filename];
NSData * data = [NSData dataWithContentsOfFile:path];
return [NSKeyedUnarchiver unarchiveObjectWithData:data];
}
Upvotes: 14
Reputation: 14247
Instead of using a property list, consider using an NSKeyedArchiver and NSKeyedUnarchiver. Properties lists have a fixed set of types, and that doesn't include NSNull, and it isn't meant to be extended.
Here are links to the relevant documentation: NSCoding, NSKeyedArchiver and NSKeyedUnarchiver.
Upvotes: 9
Reputation: 24040
From the documentation of NSPropertyListSerializationClass:
A property list object. plist must be a kind of NSData, NSString, NSNumber, NSDate, NSArray, or NSDictionary object. Container objects must also contain only these kinds of objects.
So you need to have one of those. Depending on the type of data, you could put in a placeholder instead of NSNull and then do a process before/after loading the .plist (like, for example, using a zero-length NSData object to represent your NSNull in the plist). Exactly what kind of placeholder would be dependent on what kind of data you are storing, and choosing something to avoid. Then, after loading, translate the empty NSData back to NSNull.
Upvotes: 3
Reputation: 14558
No, there is no way to put NSNull
in a property list. (Trivia: the binary property list format actually supports nulls, but the writer doesn’t implement support.)
For a dictionary, the easiest workaround is to simply filter out the null values, so { foo = "bar"; baz = null; } becomes { foo = "bar"; }.
Upvotes: 6