Skip to content

Latest commit

 

History

History
352 lines (252 loc) · 6.92 KB

File metadata and controls

352 lines (252 loc) · 6.92 KB

Build Guide

Complete guide for building, testing, and distributing Pindrop.

Prerequisites

Required

  • Xcode 15+ with Command Line Tools
  • macOS 14+ (Sonoma or later)
  • just - Command runner (brew install just)

The development pipeline is native macOS only: Xcode builds the app, SwiftPM resolves dependencies, and just wraps the common workflows.

Optional (for distribution)

  • create-dmg - DMG creation (brew install create-dmg)
  • Apple Developer Account - Required for the default signed release/export workflow and notarization
  • swiftlint - Code linting (brew install swiftlint)
  • swiftformat - Code formatting (brew install swiftformat)

Check installed tools:

just check-tools

Quick Start

just build
just test
just run

just build uses Xcode-managed signing. If you do not have a signing certificate configured, use just build-unsigned instead.

Build Commands

Development

just build              # Debug build with signing
just build-unsigned     # Debug build without signing
just test               # Run test suite
just test-coverage      # Run tests with coverage
just dev                # Clean + build + test
just build-unsigned     # Debug build without signing (CI/fallback)

Release

just build-release      # Release build
just export-app         # Archive + export Developer ID-signed app
just dmg                # Export signed app + create DMG
just dmg-self-signed    # Fallback self-signed DMG (only if Apple signing is unavailable)
just appcast dist/Pindrop.dmg   # Generate appcast.xml for DMG
just release-notes 1.9.0        # Create draft release notes file
just release 1.9.0      # Manual GitHub release workflow (local)

Maintenance

just clean              # Remove build artifacts
just lint               # Lint Swift code
just format             # Format Swift code

Build Workflows

1. Development Build

For local testing and development:

just dev

This runs:

  1. clean - Remove old artifacts
  2. build - Debug build
  3. test - Run test suite

2. Release Build

For creating a local Release build with Xcode-managed signing:

just build-release

Output: DerivedData/Build/Products/Release/Pindrop.app

3. Export Signed App

For a public Developer ID-signed app bundle:

just export-app

This runs:

  1. archive - Create an Xcode archive
  2. xcodebuild -exportArchive - Export a Developer ID-signed app with automatic signing

Output: DerivedData/Build/Products/Release/Pindrop.app

4. DMG Creation

For distribution to users:

just dmg

This runs:

  1. export-app - Export Developer ID-signed app
  2. create-dmg.sh - Package into DMG

Output: dist/Pindrop.dmg

5. Manual GitHub Release

For maintainer releases (local machine, not CI):

just release 1.9.0

This runs:

  1. Ensure contextual release notes exist (release-notes/vX.Y.Z.md)
  2. Bump version/build in project.pbxproj (if needed)
  3. Commit version bump (if needed)
  4. just test
  5. just dmg
  6. just appcast dist/Pindrop.dmg
  7. Create and push tag (vX.Y.Z)
  8. Create GitHub release with notes + DMG + appcast.xml via gh

Optional notarization/stapling for signed distribution:

just notarize dist/Pindrop.dmg
just staple dist/Pindrop.dmg

Code Signing

Setup

  1. Sign into Xcode with your Apple Developer account and enable automatic signing for the Pindrop target.

  2. Verify signing identities:

security find-identity -v -p codesigning

just export-app uses scripts/ExportOptions.plist with method=developer-id and automatic signing, so it defaults to the team used for the archive.

Sign App Bundle

just sign

Use this only for manual re-signing; the default release flow goes through just export-app / just dmg.

Verify Signature

just verify-signature

Notarization

Setup

  1. Create app-specific password at appleid.apple.com

  2. Store credentials:

xcrun notarytool store-credentials "notarytool-password" \
  --apple-id "your@email.com" \
  --team-id "YOUR_TEAM_ID" \
  --password "app-specific-password"

Notarize DMG

just notarize dist/Pindrop.dmg

Staple Ticket

just staple dist/Pindrop.dmg

Version Management

Show Current Version

just version

Bump Version

just bump-patch        # 1.0.0 → 1.0.1
just bump-minor        # Manual: 1.0.0 → 1.1.0

Testing

Run All Tests

just test

Run with Coverage

just test-coverage

Manual Testing

xcodebuild test \
  -project Pindrop.xcodeproj \
  -scheme Pindrop \
  -destination 'platform=macOS'

CI/CD

GitHub Actions Example

name: Build and Test

on: [push, pull_request]

jobs:
  build:
    runs-on: macos-14
    steps:
      - uses: actions/checkout@v4
      - name: Install just
        run: brew install just
      - name: Run CI workflow
        run: just ci

The just ci command runs:

  1. clean
  2. build-unsigned (Debug)
  3. test-unsigned
  4. build-release-unsigned

Troubleshooting

Build Fails

just clean
just build

Tests Fail

just clean
just test

DMG Creation Fails

Check requirements:

brew install create-dmg
just export-app
just dmg-quick

Code Signing Fails

Verify certificate:

security find-identity -v -p codesigning

Notarization Fails

Check credentials:

xcrun notarytool history --keychain-profile "notarytool-password"

Directory Structure

pindrop/
├── DerivedData/            # Local build + export output
│   └── Build/Products/Release/Pindrop.app
├── dist/                   # Distribution files
│   └── Pindrop.dmg
├── scripts/                # Build scripts
│   ├── create-dmg.sh
│   ├── create-dmg-self-signed.sh
│   ├── sign-app-bundle.sh
│   └── ExportOptions.plist
├── justfile                # Build commands
└── Pindrop.xcodeproj       # Xcode project

Advanced Usage

Custom Build Settings

just show-settings

Archive for App Store

just archive
just export-app

Open in Xcode

just xcode

Tips

  1. Use just for everything - Consistent, documented commands
  2. Run tests before committing - just test
  3. Clean before release builds - just clean build-release
  4. Verify signatures - just verify-signature
  5. Test DMG on clean Mac - Before distribution

Resources