Thank you for your interest in contributing to ImmiBridge! This document provides guidelines and instructions for contributing.
- macOS 12.0 or later
- Xcode 15.0 or later
- Apple Developer account (free account works for local development)
-
Fork and clone the repository
git clone https://github.com/YOUR_USERNAME/ImmiBridge.git cd ImmiBridge -
Open in Xcode
open ImmiBridge/ImmiBridge.xcodeproj
-
Configure code signing
- Select the
ImmiBridgeproject in the navigator - Select the
ImmiBridgetarget - Go to Signing & Capabilities
- Change Team to your Apple Developer team
- Xcode will automatically manage signing
- Select the
-
Build and run
- Select the
ImmiBridgescheme - Press ⌘R to build and run
- Select the
ImmiBridge/
├── ImmiBridge/
│ ├── ImmiBridge/
│ │ ├── Core/ # Backup logic
│ │ │ ├── PhotoBackupCore.swift
│ │ │ ├── FileBackupCore.swift
│ │ │ ├── BackupTypes.swift
│ │ │ └── ...
│ │ ├── UI/ # SwiftUI interface
│ │ │ ├── ContentView.swift
│ │ │ ├── PhotoBackupViewModel.swift
│ │ │ ├── MenuBarView.swift
│ │ │ └── ...
│ │ └── Assets.xcassets
│ └── ImmiBridge.xcodeproj
├── scripts/
│ ├── build_ui_app_bundle.sh # Build via command line
│ └── release.sh # Create notarized release
├── assets/ # App icons
├── LICENSE
├── README.md
└── CONTRIBUTING.md
In Xcode:
- Press ⌘B to build
- Press ⌘R to build and run
Via command line:
./scripts/build_ui_app_bundle.shThe built app will be at build/ImmiBridge.app.
- Follow Swift standard naming conventions
- Use meaningful variable and function names
- Keep functions focused and reasonably sized
- Add comments for complex logic
Core Module (Core/):
PhotoBackupCore.swift- Main export engine using PhotoKitFileBackupCore.swift- File/folder backup logicBackupTypes.swift- Shared data typesManifestStore.swift- Tracks completed backups for incremental mode
UI Module (UI/):
PhotoBackupViewModel.swift- Main state management (MVVM)ContentView.swift- Primary interfaceMenuBarView.swift- Menu bar extra
Patterns:
- MVVM: Views observe
PhotoBackupViewModelvia@EnvironmentObject - Async/await: Network and file operations use Swift concurrency
- Progress callbacks: Core module reports progress via closures
-
Test common workflows:
- Configure a backup destination
- Run a backup (use dry-run or limit for quick tests)
- Test pause/resume functionality
- Verify Immich connection (if applicable)
-
Test permissions:
- Test on a fresh install if possible
- Verify Photos and Local Network permission prompts appear correctly
-
Create a feature branch
git checkout -b feature/your-feature-name
-
Make your changes and commit with clear messages
git commit -m "Add feature: description of what you added" -
Push to your fork
git push origin feature/your-feature-name
-
Open a Pull Request with:
- Clear description of the changes
- Any relevant issue numbers
- Screenshots for UI changes
To distribute ImmiBridge outside the App Store, the app must be signed with a Developer ID certificate and notarized by Apple. This prevents Gatekeeper warnings for users.
-
Apple Developer Program membership ($99/year) - developer.apple.com/programs
-
Developer ID Application certificate
- Go to developer.apple.com/account/resources/certificates
- Click + → Select Developer ID Application
- Follow the prompts to create and download the certificate
- Double-click to install in Keychain
-
Verify your certificate is installed:
security find-identity -v -p codesigning | grep "Developer ID"
-
Create an app-specific password for notarization:
- Go to appleid.apple.com → Sign-In and Security → App-Specific Passwords
- Generate a new password and save it
Copy the example environment file and fill in your values:
cp .env.example .envEdit .env with your credentials:
CODESIGN_IDENTITY="Developer ID Application: Your Name (TEAMID)"
APPLE_ID="your@email.com"
APPLE_TEAM_ID="XXXXXXXXXX"
APPLE_APP_PASSWORD="xxxx-xxxx-xxxx-xxxx"
VERSION="1.0.0"Note:
.envis git-ignored and will not be committed.
./scripts/release.shThis will:
- Build the app in Release configuration
- Sign it with your Developer ID certificate
- Submit to Apple for notarization (takes 1-5 minutes)
- Staple the notarization ticket to the app
- Create a signed DMG at
build/ImmiBridge-{VERSION}.dmg
gh release create v1.0.0 build/ImmiBridge-1.0.0.dmg --title "v1.0.0" --generate-notesWhen reporting bugs, please include:
- macOS version
- App version (or commit hash if building from source)
- Steps to reproduce
- Expected vs actual behavior
- Any error messages or logs
Feel free to open an issue for questions or discussion about potential changes.