Skip to content

Ship code-signed (Developer ID) macOS binaries #2661

Description

@fnando

Feature request

Ship the macOS stellar binary code-signed with a stable Developer ID identity (and ideally notarized) in our official release artifacts (GitHub releases, Homebrew, installers).

Today's release binaries appear to be ad-hoc/linker-signed, which gives them no stable code-signing identity. That directly degrades the secure-store (OS keychain) experience on macOS — see background below.

Why

  • Secure-store keys are stored in the macOS keychain. A keychain item's ACL is pinned to the code-signing designated requirement (DR) of the binary that created it.
  • With a stable Developer ID DR, a signed binary that created a key reads it silently. Keys created and read by the same signed release binary → zero prompts.
  • Without a stable DR, macOS treats the binary as untrusted for the item and shows a two-dialog authorization prompt on every read, and grants never persist.

Acceptance criteria

  • Release macOS binaries are signed with a stable Developer ID Application identity (pinned --identifier, e.g. org.stellar.cli) so the DR is identical across builds.
  • Signing (and notarization/stapling) is wired into the release pipeline.
  • Verified: a secure-store key created and used with a release binary produces no repeated keychain prompts.

Background — why secure-store signing can prompt for keychain access twice

TL;DR: it's macOS keychain behavior tied to code signing, not a bug in the CLI. The CLI reads the keychain exactly once per sign (verified with a backtrace on the single read path); macOS shows two dialogs for that one read.

On macOS, a keychain item's ACL is pinned to the code-signing designated requirement (DR) of whatever binary created it (stellar keys add/generate). When a binary whose DR isn't on that ACL reads the item, macOS shows the two-dialog pair ("wants to use your confidential information…" + "wants to access key…").

  • A signed binary (stable Developer ID DR) that also created the item reads it silently — zero prompts.
  • An unsigned / ad-hoc binary (e.g. a local cargo build, whose DR changes every build) is never on the ACL, so it gets prompted on every read.

Confirmed empirically: after signing the binary with a stable Developer ID, a newly created key → 0 prompts, but a pre-existing key → still 2 prompts.

We can't easily fix this for existing items. A keychain item's ACL can only be modified by an app already trusted for it, so we can't retroactively correct the DR on keys users already created. The reliable fix is to re-add the key with the signed binary, so its ACL is pinned to the correct DR.

See Apple TN3137: On Mac keychain APIs and implementations.

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    Status
    Backlog (Not Ready)

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions