Skip to content

Darwin: stop bundling Flutter framework; delegate to host Xcode project#24

Merged
lhoward merged 1 commit into
mainfrom
darwin-flutter-via-xcode-host
May 15, 2026
Merged

Darwin: stop bundling Flutter framework; delegate to host Xcode project#24
lhoward merged 1 commit into
mainfrom
darwin-flutter-via-xcode-host

Conversation

@lhoward

@lhoward lhoward commented May 15, 2026

Copy link
Copy Markdown
Contributor

Summary

Removes two Darwin-specific assumptions baked into `Package.swift` that broke under common configurations:

  1. `/opt/flutter` was hardcoded as the macOS Flutter SDK root — broke any developer whose SDK lived elsewhere, and was useless on Apple Silicon (`darwin-x64` artifact name only).
  2. `Flutter.xcframework.zip` (~63 MB) was committed in the repo and wired in as a `.binaryTarget` for iOS — pinned to whatever engine revision the zip was built against, bloated git history, and risked conflicting with the `Flutter.framework` the host Xcode project already provides.

Both are removed. On Darwin, `Flutter.framework` / `FlutterMacOS.framework` is now sourced from the host Xcode project's `$(FRAMEWORK_SEARCH_PATHS)`, populated by Flutter's standard `xcode_backend.sh` / `macos_assemble.sh` build phases — the same mechanism Flutter's SwiftPM-aware plugins (e.g. `url_launcher_macos`) rely on. SPM targets compiled within an Xcode build inherit those search paths, so `import FlutterMacOS` / `import Flutter` continues to resolve in `FlutterPlatformMessenger.swift`.

Linux and Android (cross-compiled on macOS) code paths are untouched: the Linux branch still emits its own engine linker flags, and the Android branch still overwrites `FlutterPlatform` / `FlutterUnsafeLinkerFlags` downstream of the Darwin block.

Tradeoff

Standalone `swift build` on Darwin no longer pulls in the Flutter framework — `FlutterPlatformMessenger` is hidden by `#if canImport(...)`. This is acceptable because the example apps (and intended downstream consumers) reference FlutterSwift via `XCLocalSwiftPackageReference` (path-based), and Xcode always supplies the framework. README updated to call this out.

Test plan

  • macOS: `swift test` — 28/28 pass
  • macOS counter: `flutter build macos --debug` — built
  • iOS counter (simulator): `flutter build ios --debug --no-codesign --simulator` — built
  • Android counter: `JAVA_HOME=… ./gradlew :app:assembleDebug` — `BUILD SUCCESSFUL`
  • `swift package describe` with `FLUTTER_SWIFT_JVM=true` (Android-on-macOS resolve path)
  • eLinux GBM: `./build-elinux.sh` (untouched code, untested locally)
  • eLinux Wayland: `FLUTTER_SWIFT_BACKEND=wayland ./build-elinux.sh` (untouched code, untested locally)

🤖 Generated with Claude Code

Removes two Darwin-specific assumptions baked into Package.swift:

1. /opt/flutter was hardcoded as the macOS Flutter SDK root — broke any
   developer whose SDK lived elsewhere, and was useless on Apple Silicon
   (darwin-x64 artifact name only).
2. Flutter.xcframework.zip (~63 MB) was committed in the repo and wired in as
   a .binaryTarget for iOS — pinned to whatever engine revision the zip was
   built against, bloated git history, and risked conflicting with the
   Flutter.framework the host Xcode project already provides.

Both are removed. On Darwin, Flutter.framework / FlutterMacOS.framework is
now sourced from the host Xcode project's $(FRAMEWORK_SEARCH_PATHS),
populated by Flutter's standard xcode_backend.sh / macos_assemble.sh build
phases — the same mechanism Flutter's SwiftPM-aware plugins (e.g.
url_launcher_macos) rely on. SPM targets compiled within an Xcode build
inherit those search paths, so `import FlutterMacOS` / `import Flutter`
continues to resolve in FlutterPlatformMessenger.swift.

Linux and Android (cross-compiled on macOS) code paths are untouched: the
Linux branch still emits its own engine linker flags, and the Android branch
still overwrites FlutterPlatform / FlutterUnsafeLinkerFlags downstream of
the Darwin block.

Tradeoff: standalone `swift build` on Darwin no longer pulls in the Flutter
framework — FlutterPlatformMessenger is hidden by `#if canImport(...)`.
This is acceptable because the example apps (and intended downstream
consumers) reference FlutterSwift via XCLocalSwiftPackageReference, and
Xcode always supplies the framework. README updated to call this out.

Verified by:
- swift test (28/28 pass)
- flutter build macos --debug
- flutter build ios --debug --no-codesign --simulator
- gradlew :app:assembleDebug (Android arm64)
- swift package describe (macOS, FLUTTER_SWIFT_JVM=true)

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
@lhoward lhoward force-pushed the darwin-flutter-via-xcode-host branch from 1a0e92a to 9d9859c Compare May 15, 2026 02:56
@lhoward lhoward merged commit 8982c10 into main May 15, 2026
6 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant