Skip to content

Export and import settings and layout as a file #1238

Description

@sumeet-bansal

Problem

There is no supported way to save an OpenUsage configuration to a file, carry it to a second
Mac, or keep it under version control. Every setting and the whole Customize layout live only in
the app's UserDefaults domain, com.robinebers.openusage, alongside runtime state: provider
snapshots that are rewritten on every refresh, the account registry, the iCloud device id, the
shell-environment snapshot, and Sparkle's update state. The existing mechanisms do not cover it:

  • iCloud sync covers history only, by design (docs/icloud-sync.md).
  • The plist is binary, and about 80% of it is the snapshot cache, so it changes every five
    minutes.
  • Symlinking the plist into a dotfiles repo does not work: cfprefsd refuses to write a domain
    whose plist is a symlink ("Could not write domain"), so the app can no longer save settings.

"Reset All Settings" (#602) exists, but there is no counterpart that saves a configuration and
restores it.

Proposed Solution

A JSON export and import of user-chosen configuration only, reachable from the openusage CLI
(openusage settings export writing to stdout, openusage settings import <file>) and, if it
fits the Settings screen, as buttons beside Reset All Settings.

In scope:

  • Customize layout and metric order
  • Menu-bar pins and style
  • Expanded metrics
  • Enabled providers
  • Appearance, density, and meter style
  • Pacing
  • Notification toggles
  • Total-spend settings
  • Update preferences

Out of scope, as refetchable or machine-specific:

  • Provider snapshots
  • The account registry
  • The iCloud device id
  • The shell-environment snapshot
  • Sparkle timestamps

Import merges over the current domain and reloads the layout, the way defaults import merges
keys, so a partial file only touches the keys it names.

Alternatives Considered

  • iCloud sync: history only, and I would want the layout in git rather than in iCloud anyway.
  • Symlinking the preferences plist: cfprefsd rejects writes through a symlink (tested on
    macOS 26.6).
  • defaults export filtered to an allowlist, then defaults import: this is what I do today.
    It works (21 keys; the three Data-typed layout keys hold JSON and decode cleanly), but it
    depends on internal key names that carry schema versions (openusage.layout.v1,
    openusage.providerSnapshots.v9), so it breaks silently whenever those names change. A
    first-party export is the stable version of the same allowlist.

Additional Context

OpenUsage 0.7.x on macOS 26.6, Apple Silicon. The allowlist above is the set of keys that
survived a capture, import, restart, and recapture round trip byte-for-byte; I can share it
if it helps scope the export.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions