iOS - Safari Content Blocker can't read data from NSUserDefaults - nsuserdefaults

I've been working on a Content Blocking application for some time now. I have a switch in the main app that should turn of the blocking filter. The value of this switch is saved in an NSUserDefaults property that's enabled with App Groups so the blocking extension can read whether it's enabled or not (if blocking is enabled it returns a full json list and if not it returns an empty one).
On Simulator this works just fine, but when I start running it on a device (tested on 5s and 5c) the extension can't read the properties from the UserDefaults anymore (it always returns nil) and the application can't read the properties from the extension anymore.
I think it has something to do with the App Groups, but I can't seem to find any problems with that (it's enabled in Capibilities etc.) so I'm a bit lost. Has anyone ever had this problem? If so, were you able to fix it?
I'm using Xcode 7 beta, iOS 9 beta2 and Mac OS X Yosemite.

Related

NSUbiquitousKeyValueStore.didChangeExternallyNotification fires also when change is done on device itself

My app worked fine until iOS 16.0.
When I write to iCloud: NSUbiquitousKeyValueStore then the didChangeExternallyNotification notification is triggered also on the device I wrote to iCloud. So it did not change externally but internally. Therefore my app runs into a loop ;-(
Does anyone have the same issue?
I had contact with Apple and found at the you need to use 1 var:
let defaultsAppGroup = UserDefaults(suiteName:"xxx")
When using:
UserDefaults(suiteName:"xxx").set()
Multiple instances of UserDefault are made and therefore a didChangeExternallyNotification will be triggered to the other instances.

WKExtension.sharedExtension().openSystemURL() prompting when it shouldn't

I am developing an extension of an iPhone App for Apple Watch (written in Swift running WatchOS2.2, Xcode 7.3, testing on a physical device)
I am running into an issue where I expect no prompt/confirmation on the Apple Watch when calling the tel schema for the following function:
WKExtension.sharedExtension().openSystemURL(NSURL(string:"tel:1231231234"))
I am not calling the telprompt function as my understanding is that this is not supported directly by Apple however it seems to be behaving as if it is telprompt. Interestingly enough, telprompt doesn't work.
I am expecting this to directly call the phone number without the prompt on the Apple Watch, however it is first prompting the user displaying a Cancel button on the top left, the number in the middle of the screen, and a Call button at the bottom. This also doesn't appear to be picking up the localization on the system (french for example) so it is always displaying Cancel and Call in English.
Image of Cancel, Number, and Call being prompted when French in the system language
Has anyone else encountered this issue? I haven't found much talk about it on the web. Or is this a known issues? Again, I don't see any bugs reported for it.
Fix Found for the Localization - See Below
Interestingly enough I was able to get the localization working.
The fix for it was that my Target for my Watch and WatchExtension needed to be checked off for my Launch Images (or splash screen images, or commonly left as "default.png"). Previously my Launch Images were for the app Target only.
I have no idea why the localization seemed to be require my launch images be added to the Watch and WatchExtension targets.
This did not resolve the prompting as it still took place - however since it was at least presenting the correct language this was good for us.

Application doesn't launch with location key after a significant location change

My application uses the core location also after the application terminates with the method startMonitoringSignificantLocationChanges in CLLocationManager class.
My application launches with a location key in iOS 5 and 6 in the method:
- (BOOL) application:application didFinishLaunchingWithOptions:launchOptions;
in AppDelegate class and everything works well.
But in iOS-7 betas the application doesn't launch with a location key after a significant location change.
Has anybody encountered this problem?
I tried it on a simulator and in the device.
Thanks for the help.
I have the same problem in my app, when the app was terminated by user from app switcher.
But it does launch with location key if it was terminated by OS for low memory or other reason.
It is the expected result from iOS7 unfortunately. An official apple response I got from one of their evangelists:
If a user swipes up in the app switcher then the OS will not launch
the app unless explicitly told to do so by the user. So no, SLC will
not be launching the app, nor will silent notifications. The only
thing that will launch the app at that point is the user tapping the
icon. The intention here is that the user has expressed their choice
of not having that app running any more for any reason, so we honor
that. In this situation, there's really nothing that you can do. The
next time the user launches the app you can let them know that some of
the data may be missing, although you really cannot tell whether
there's missing data or not (i.e. you might have been killed by the OS
in the background and the user may not have moved thereby not
triggering any SLC notifications). My suggestion would be to gather
the data you can within the policies of the OS and if the user has
manually killed the app then respect that wish and don't do anything.
By all means, feel free to file a bug report if this change in
behavior winds up causing problems for you or (especially) confusion
for your users.
Attach link to Apple DEV forums:
https://devforums.apple.com/message/882691#882691

Do NSUserDefaults persist through an Update to an app in the Appstore?

Is this the case? Do NSUserDefaults get reset when you submit an update to an app on the App Store, or are they reset?
My app is crashing when updated but not crashing when downloaded fully - so I'm trying to determine what could possibly be different in the updated session to the freshly downloaded session.
Cheers,
Nick.
They are usually not reset unless the user deletes the app. For basic data, NSUserDefaults is the best way to save data such as preferences, dates, strings etc. If you are looking to save images and files, the file system is a better bet.
I beleive the answer is YES, it will persist. This also fully documented under the Application Directory chapter in the Apple iPhone OS Programming Guide.
Direct answer to the posted question: YES.
Your problem:
Your app gets crashed due to logic issues. Suppose you store an object in defaults and the app checks it's value on launch (or elsewhere). In you update you could change the way it is checked or used, e.g. you expect a value, but the object is nil, or vice versa. This may cause a SIGABRT or EXC_BAD_ACCESS.
If you had CoreData model and you changed something in your model and update, without managing migration, thats probably reason why your app crashes on update...
I have a similar experience. Our app stores a version number in Settings.Bundle/Root.Plist. This gets displayed through the iPhone Settings app. What we find is that on an Install the version number gets loaded from the app bundle - therefore the version number is correct. On an update however the version number doesn't change. This gives the impression the user is running a previous version of the app. We don't have any logic linked to the version number, it's just for display (it could be used by contact centre staff when diagnosing faults).
Our experience is NSUserDefaults doesn't get cleared when a user updates our app, but the Settings display doesn't get updated either.
Be aware of this case, when your app is running in background and you cannot access your stored values in NSUserDefaults:
Eric:
There have been many threads and bugs about this, but it's happening to me again in ios 9. I have an app that launches in the background in response to NSURLSession tasks and content-available pushes. Reproducibly, if I reboot my phone and wait for a background launch of my app to happen, then when I open the app I find that [[NSUserDefaults standardUserDefaults] dictionaryRepresentation] contains all the system values, e.g. AppleITunesStoreItemKinds, etc. but does not contain any of the values I have set. If I force-quit and relaunch the app all of my values come back. Is there any way to avoid it caching the "empty" standardUserDefaults from before the phone is unlocked, or at least to determine when they are messed up and fix them without having to force-quit the app?
Eskimo (eskimo1#apple.com):
The problem here is that NSUserDefaults is ultimately backed by a file in your app’s container and your app’s container is subject to data protection. If you do nothing special then, on iOS 7 and later, your container uses NSFileProtectionCompleteUntilFirstUserAuthentication, a value that’s inherited by the NSUserDefaults backing store, and so you can’t access it prior to first unlock.
IMO the best way around this is to avoid NSUserDefaults for stuff that you rely on in code paths that can execute in the background. Instead store those settings in your own preferences file, one whose data protection you can explicitly manage (in this case that means ‘set to NSFileProtectionNone’).
There are two problems with NSUserDefaults in a data protection context:
Its a fully abstract API: the presence and location of its backing store is not considered part of that API, so you can’t explicitly manage its data protection.
Note On recent versions of OS X NSUserDefaults is managed by a daemon and folks who try to manipulate its backing store directly have run into problems. It’s easy to imagine the same sort of thing coming to iOS at some point.
Even if changing the data protection were possible, NSUserDefaults has no mechanism to classify data based on the context in which you’re using it; it’s an ‘all or nothing’ API. In your case you don’t want to remove protection from all of your user defaults, just those that you need to access in the background before first unlock.
Finally, if any of this data is truly sensitive, you should put it in the keychain. Notably, the keychain does have the ability to set data protection on an item-by-item basis.
Source:
https://webcache.googleusercontent.com/search?q=cache:sR9eZNHpZtwJ:https://forums.developer.apple.com/thread/15685

iPhone - crash logs not generated on Windows

I have some users testing my app on Windows and Mac platforms. The app crashes at some points but the Windows users cannot get any crash logs. Here's what they do
Run the app and play around till it crashes
Sync their device with iTunes
Look for logs here (on a Vista) C:\Users\\AppData\Roaming\Apple computer\Logs\CrashReporter\MobileDevice\
But there is nothing inside the Apple Computer folder.
Any ideas? Thanks.
Aside from you omitting parts of the path in that it should correctly be containing the login username - ow, now noticed you possibly did try to embed it, hence the double backspace after Users....
Ask your user if he possibly is using multiple computers for syncing his device. In case he does, he should check the machine he used first as those Logs are only synced with the "main"-machine, I believe. Bit of a shot in the dark but worth the attempt, I think.
Ow, and there may be another possible reason I just saw within another thread - credits to Kendall:
If there is not crash log, it could mean the app was shut down for using too much memory - in that case you should see a message come up in the device console indicating your application is being shut down.