• Open Menu Close Menu
  • Apple
  • Shopping Bag
  • Apple
  • Mac
  • iPad
  • iPhone
  • Watch
  • TV
  • Music
  • Support
  • Search apple.com
  • Shopping Bag

Lists

Open Menu Close Menu
  • Terms and Conditions
  • Lists hosted on this site
  • Email the Postmaster
  • Tips for posting to public mailing lists
Re: CFPreferences vs. NSUserDefaults
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: CFPreferences vs. NSUserDefaults


  • Subject: Re: CFPreferences vs. NSUserDefaults
  • From: Chris Parker <email@hidden>
  • Date: Tue, 26 Mar 2002 15:13:14 -0800

Hi Evan,

On Tuesday, March 26, 2002, at 11:36 AM, Evan Coyne Maloney wrote:

[some text deleted]

All of this experiementation led me to the following questions. Any help/advice/flames would be welcome!

1. What do the CFPreferences calls expect the "appName" parameter to be? "appName" implies name (as in "Dock" or "Finder"), but the documentation says "the ID of the application", which implies bundle identifier (as in "com.apple.dock" or "com.apple.finder").

Applications aren't necessarily restricted to bundle IDs. Non-bundled applications using the CFPreferences API wind up having their application name chosen as the identifier if they use kCFPreferencesCurrentApplication as the appName parameter. If you wish to synchronize against a specific domain, you have to discover that domain somehow.

2. Is NSUserDefaults built on top of CFPreferences? I would assume so, but if that's the case, then why can't I retrieve the keys for the Dock's preferences using CFPreferences? It seems that I can only interact with the Dock's preferences though NSUserDefaults. For example, both of the following calls return nil:

CFPreferencesCopyKeyList((CFStringRef) @"com.apple.dock",
kCFPreferencesCurrentUser, kCFPreferencesCurrentHost);

This is returning nil probably because the Dock doesn't store a ByHost preference domain. This is asking for a specific domain triplet (in terms of {app, user, host}): {com.apple.dock, this user, this host} which would be the plist stored in ~/Library/Preferences/ByHost/com.apple.dock.<ethernet address>.plist.

If that plist isn't there, there's nothing to get.

What you probably are looking for is

CFPreferencesCopyKeyList((CFStringRef)@"com.apple.dock", kCFPreferencesCurrentUser, kCFPreferencesAnyHost);

which is in ~/Library/Preferences/com.apple.dock.plist

CFPreferencesCopyKeyList((CFStringRef) @"Dock",
kCFPreferencesCurrentUser, kCFPreferencesCurrentHost);

Again, this is looking for something similar: {Dock.<ethernet address>.plist, this user, this host} which is most likely non-existant.

3. Do the CFPreferences calls simply not work for Cocoa apps? Is the Dock a Carbon app or Cocoa app? (I'd assume Cocoa, since the Dock wasn't ported from OS 9.)

They work fine in Cocoa apps, and in fact some features available to CFPreferences (like by-host preferences) are only available through the CF API (this is being worked on).

[4. is slightly edited by me]

4. Can NSUserDefaults' synchronize method be used to interact with other apps? Can the equivalent CFPreferences calls?

Yes.

Even while running?

Sure, but see my notes at the bottom of this email.

Or does synchronization only work with the app the calls it? If the latter, then WHY does CFPreferences allow me to specify the application?

You're specifying the domain you want =your= application to synchronize against. You're not really specifying the application who owns those preferences.

5. Lastly, what does preference synchronization do, precisely? The documentation implies that it can be used to (1) reload the ".plist" file from disk AND (2) write the preferences BACK to the ".plist" file. What happens if there's a conflict? The app's preferences change internally AND the file changes THEN a synchronize is performed. What happens? Who gets priority? Is there a merge, a la CVS? Or does everything get hosed?

There -is- a lightweight merge, but any values for keys that the application has made itself will win out over anything you may have set in the file.

NOTE:

The warning that was referenced earlier by Jonathan Feinberg from the defaults(1) man page can basically be restated as follows:

The application itself is the final arbiter of its preferences. Changes made to preferences from outside the application's context cannot be expected to persist since the application itself decides to sync what it's got out to disk.

I can't jump up and down about this enough. If the application itself wants to provide a mechanism for preferences to be modified externally in a consistent manner, the application will have to provide that through some form of interprocess communication - whether that's a distributed notification, or an Apple Event, or something else. Applications can agree on using a specific (external) domain (i.e. suite preferences) but should agree amongst themselves how to handle access to that domain.

It is expected that applications may wish to read values for keys in other preference domains, but the application owning that domain is the definitive source for when that domain is synchronized, etc.

.chris

--
Chris Parker <email@hidden>
Cocoa Frameworks Engineer
Apple Computer, Inc.
_______________________________________________
cocoa-dev mailing list | email@hidden
Help/Unsubscribe/Archives: http://www.lists.apple.com/mailman/listinfo/cocoa-dev
Do not post admin requests to the list. They will be ignored.

References: 
 >CFPreferences vs. NSUserDefaults (From: Evan Coyne Maloney <email@hidden>)

  • Prev by Date: Re: JavaOne: OS X is Java dream
  • Next by Date: Re: OT: What would it take to make AOL impressive to Mac users?
  • Previous by thread: Re: CFPreferences vs. NSUserDefaults
  • Next by thread: Displaying a license agreement when mounting a disk image
  • Index(es):
    • Date
    • Thread