68458

iOS - NSUserDefaults value returns null for 'valueForKey' but isn't null

Question:

I am trying to see if a user has made a purchase by retrieving the NSUserDefaults value for each product identifier. I save the value when a product is purchased and it is getting set correctly.

<strong>The key-value pair show up correctly when calling this:</strong>

NSLog(@"%@", [[NSUserDefaults standardUserDefaults] dictionaryRepresentation]);

<strong>As this:</strong>

"com.COMPANY.PRODUCTIDENTIFIER" = 1;

<strong>But when I try to actually validate that specific key-value it always returns null:</strong>

for (NSString * productIdentifier in _productIdentifiers) { NSLog(@"ProductIdentifier: %@",productIdentifier); NSLog(@"Defaults Value: %@",[[NSUserDefaults standardUserDefaults] valueForKey:productIdentifier]); NSLog(@"Defaults Bool: %d",[[NSUserDefaults standardUserDefaults] boolForKey:productIdentifier]); NSLog(@"Defaults Object: %@",[[NSUserDefaults standardUserDefaults] objectForKey:productIdentifier]); BOOL productPurchased = [[NSUserDefaults standardUserDefaults] boolForKey:productIdentifier]; if (productPurchased) { [_purchasedProductIdentifiers addObject:productIdentifier]; NSLog(@"Previously purchased: %@", productIdentifier); } else { NSLog(@"Not purchased: %@", productIdentifier); } }

<strong>Results in this:</strong>

2013-03-10 17:45:13.609 COMPANY[1140:907] ProductIdentifier: com.COMPANY.PRODUCTIDENTIFIER 2013-03-10 17:45:13.611 COMPANY[1140:907] Defaults Value: (null) 2013-03-10 17:45:13.612 COMPANY[1140:907] Defaults Bool: 0 2013-03-10 17:45:13.611 COMPANY[1140:907] Defaults Object: (null)

<em>NOTE - The above methods are both called in the same method in this order, so it isn't a problem with the app not loading the defaults yet or anything like that since the value is correctly shown through the 'dictionaryRepresentation' method. Also, Company and Product Identifiers have been replaced for privacy. There are no typos in the real app so that is not the issue.</em>

<strong>UPDATE</strong>

Ok so this is interesting. If I use a static string as the key, it returns the correct value. But using the 'productIdentifier' (which is NSString) does not, even though logging the 'productIdentifier' it is the exact same string... Any Ideas???

<strong>Code:</strong>

for (NSString *productIdentifier in _productIdentifiers) { NSLog(@"ProductIdentifier: %@",productIdentifier); NSLog(@"Defaults Value: %@",[[NSUserDefaults standardUserDefaults] valueForKey:productIdentifier]); NSLog(@"Defaults Bool: %d",[[NSUserDefaults standardUserDefaults] boolForKey:productIdentifier]); NSLog(@"Defaults Object: %@",[[NSUserDefaults standardUserDefaults] objectForKey:productIdentifier]); NSLog(@"Static Key: %d",[[NSUserDefaults standardUserDefaults] boolForKey:@"com.COMPANY.PRODUCTIDENTIFIER"]); BOOL productPurchased = [[NSUserDefaults standardUserDefaults] boolForKey:productIdentifier]; if (productPurchased) { [_purchasedProductIdentifiers addObject:productIdentifier]; NSLog(@"Previously purchased: %@", productIdentifier); } else { NSLog(@"Not purchased: %@", productIdentifier); } }

<strong>Result:</strong>

2013-03-10 17:45:13.609 COMPANY[1140:907] ProductIdentifier: com.COMPANY.PRODUCTIDENTIFIER 2013-03-10 17:45:13.611 COMPANY[1140:907] Defaults Value: (null) 2013-03-10 17:45:13.612 COMPANY[1140:907] Defaults Bool: 0 2013-03-10 17:45:13.611 COMPANY[1140:907] Defaults Object: (null) 2013-03-10 17:45:13.611 COMPANY[1140:907] Static Key: 1

Answer1:

The problem is your use of valueForKey: instead of objectForKey:. valueForKey has different semantics (key-value coding), especially when used with a key that has dots in it.

Change this:

[[NSUserDefaults standardUserDefaults] valueForKey:productIdentifier]

to this:

[[NSUserDefaults standardUserDefaults] objectForKey:productIdentifier]

and it should work.

Answer2:

Problem was the product identifier in the NSSet being used had a leading whitespace so it was never a direct match.

Recommend

  • Obj-C, Storekit restoreCompletedTransactions returns zero transactions?
  • NSMutableArray to NSData Conversion using NSUserDefaults [closed]
  • Best practice to add a transaction queue observer at application launch for Storekit
  • Core Data validation: from Objective-C to Swift
  • Core Data validation: from Objective-C to Swift
  • How do I know if user didn't allow push notifications
  • Image Being Saved is Not Appearing
  • Google Analytics SDK iOS10
  • Resizing UITableViewCells in iOS4 versus iOS3
  • adding zeros in objective-c string formats
  • Customizing NSLog Function on iPhone
  • using AVSystemController in iPhone App
  • Unable to add the file iOS application bundle
  • Display a .pdf in an iOS app without downloading it from the internet
  • How to make a post call to a Web Api Action?
  • Detecting both left and right mouse movement and no movement
  • How do I include superscripts in NSString?
  • bundle sqlite database with app and stringByAppendingPathComponent error
  • Objective-C – access extern const with a string containing its name? [duplicate]
  • How can I allow tags through rails 4 sanitize?
  • Post comment to WordPress Blog from iPhone programmatically
  • iOS Date formatting
  • Does argparse support multiple exclusive arguments?
  • Deleting a widget from QTableView
  • What is this iOS exception with NSCFType?
  • multidatatrigger with multibinding in ControlTemplate.Triggers
  • Is there a parser equivalent of 'fragment' marking in ANTLR4?
  • how to solve invalid conversion specifier warning in iphone app
  • didUpdatePushCredentials not get called
  • Build Successful but not running on simulator
  • The plugin 'org.apache.maven.plugins:maven-jboss-as-plugin' does not exist or no valid ver
  • Regex thinks I'm nesting, but I'm not
  • Fill an image in a square container while keeping aspect ratio
  • Rearranging Cells in UITableView Bug & Saving Changes
  • Compare two NSDates in iPhone
  • Linker errors when using intrinsic function via function pointer
  • Windows forms listbox.selecteditem displaying “System.Data.DataRowView” instead of actual value
  • LevelDB C iterator
  • Reading document lines to the user (python)
  • How can i traverse a binary tree from right to left in java?