# macOS - Managing Preferences with defaults and PlistBuddy
Programmatic preference changes on macOS fail in three silent ways: `defaults write` guesses the value type, `defaults write -dict-add` breaks on nested structures, and the preference cache in `cfprefsd` keeps the old value after the write. Reliable changes need three pieces: explicit type flags for `defaults`, PlistBuddy for nested keys, and a `cfprefsd` restart to flush the cache.
## Key points
- `defaults write` parses value types by heuristic. A string value that looks like JSON is parsed as a dictionary, and the write fails. Pass an explicit type flag, such as `-string` or `-int`, instead.
- `defaults write -dict-add` is unreliable for nested plist structures. `/usr/libexec/PlistBuddy` addresses deeply nested keys directly. Use PlistBuddy for edits inside `com.apple.symbolichotkeys`.
- macOS 15+ caches preferences in `cfprefsd`. Killing only the target app, such as `SystemUIServer`, does not flush that cache. Kill `cfprefsd` after the write to force the flush.
- The correct sequence to disable a macOS symbolic hotkey:
```
/usr/libexec/PlistBuddy -c "Set :AppleSymbolicHotKeys:60:enabled false" \
~/Library/Preferences/com.apple.symbolichotkeys.plist && killall cfprefsd
```
## How to apply
1. Write flat preference keys with `defaults write` and an explicit type flag. Use `-string` for text and `-int` for numbers.
2. Write nested keys with `/usr/libexec/PlistBuddy`. Address each nesting level in the `-c` command.
3. Run `killall cfprefsd` after every write. On macOS 15+, the preference cache holds the old value until this restart.
4. Chain the write and the flush with `&&`.
## Observations
- [macos] `defaults write` parses value types by heuristic. JSON-looking strings become dictionaries and the write fails. Use `-string` or `-int`. #macos #cli (source: agent sessions, 2026-02)
- [macos] `defaults write -dict-add` is unreliable for nested plists. `/usr/libexec/PlistBuddy` sets deeply nested keys correctly. #macos #cli (source: agent sessions, 2026-02)
- [macos] On macOS 15+, kill `cfprefsd` to flush the preference cache after a write. Killing only `SystemUIServer` does not flush it. #macos #cli (source: agent sessions, 2026-02)
## Relations
- relates_to [[resources/documentation/macOS - Developer Environment Pitfalls]] (same platform, other silent failure modes of the macOS command line)
- relates_to [[resources/documentation/Karabiner Configuration]] (keyboard-level configuration, the other main route to custom hotkeys on macOS)
## Sources
- Personal agent-session notes, February 2026