From 348009463e95b67586832668521597d17bf8cf5f Mon Sep 17 00:00:00 2001 From: Nicklas Lundin Date: Tue, 9 Jun 2026 14:18:06 +0200 Subject: [PATCH] feat: add Swift Package Manager support for iOS Add Package.swift manifest so the iOS plugin resolves via SPM (Flutter 3.44+ default) while keeping CocoaPods backward compat. - Move plugin source to SPM-expected layout - Add FlutterFramework dependency required by Flutter 3.41+ - Vendor Confidence sources via CI (same as CocoaPods path) - Add SPM build check to CI matrix Workaround: Flutter bug #186881 causes SPM identity mismatch when repo name differs from plugin name. CI copies the plugin to /tmp without git context to simulate the pub.dev install path. Co-Authored-By: Claude Opus 4.6 (1M context) --- .github/workflows/ci.yaml | 63 ++++++++++++++----- ios/confidence_flutter_sdk.podspec | 13 ++-- ios/confidence_flutter_sdk/.gitignore | 2 + ios/confidence_flutter_sdk/Package.swift | 24 +++++++ .../ConfidenceFlutterSdkPlugin.swift | 0 5 files changed, 80 insertions(+), 22 deletions(-) create mode 100644 ios/confidence_flutter_sdk/.gitignore create mode 100644 ios/confidence_flutter_sdk/Package.swift rename ios/{Classes => confidence_flutter_sdk/Sources/confidence_flutter_sdk}/ConfidenceFlutterSdkPlugin.swift (100%) diff --git a/.github/workflows/ci.yaml b/.github/workflows/ci.yaml index 82a7ebc..8b3060c 100644 --- a/.github/workflows/ci.yaml +++ b/.github/workflows/ci.yaml @@ -10,18 +10,28 @@ jobs: build: runs-on: macos-latest + strategy: + matrix: + include: + - flutter-version: '3.27.3' + build: cocoapods + - flutter-version: '3.44.0' + build: android + - flutter-version: '3.44.0' + build: spm + env: FLUTTER_CHANNEL: stable - FLUTTER_VERSION: 3.27.3 steps: - name: Checkout code uses: actions/checkout@v2 - - name: fetch submodules + - name: Fetch submodules run: git submodule update --init --recursive - name: Set up JDK 17 + if: matrix.build != 'spm' uses: actions/setup-java@v3 with: java-version: 17 @@ -30,30 +40,55 @@ jobs: - name: Set up Flutter uses: subosito/flutter-action@v2 with: - flutter-version: ${{ env.FLUTTER_VERSION }} + flutter-version: ${{ matrix.flutter-version }} channel: ${{ env.FLUTTER_CHANNEL }} - - name: Install dependencies - working-directory: example - run: flutter pub get - - - run: echo API_KEY=${{ secrets.TEST_API_KEY }} > example/.env - - name: Build Android - working-directory: example - run: flutter build apk --release - - - name: Copy iOS + - name: Copy Confidence sources for CocoaPods + if: matrix.build == 'cocoapods' working-directory: ios/Classes run: cp -r confidence-sdk/Sources/Confidence . - name: Remove the submodule + if: matrix.build == 'cocoapods' working-directory: ios/Classes run: rm -rf confidence-sdk - name: Remove git submodule + if: matrix.build == 'cocoapods' working-directory: ios/Classes run: git rm confidence-sdk - - name: Build iOS + - name: Install dependencies + if: matrix.build != 'spm' + working-directory: example + run: flutter pub get + + - run: echo API_KEY=${{ secrets.TEST_API_KEY }} > example/.env + if: matrix.build != 'spm' + + - name: Build Android + if: matrix.build != 'spm' + working-directory: example + run: flutter build apk --release + + - name: Build iOS (CocoaPods) + if: matrix.build == 'cocoapods' working-directory: example run: flutter build ios --release --no-codesign + + - name: Copy Confidence sources for SPM + if: matrix.build == 'spm' + run: cp -r ios/Classes/confidence-sdk/Sources/Confidence ios/confidence_flutter_sdk/Sources/confidence_flutter_sdk/ + + - name: Prepare plugin without git context + if: matrix.build == 'spm' + run: | + mkdir -p /tmp/confidence_flutter_sdk + rsync -a --exclude='.git' --exclude='ios/Classes/confidence-sdk' . /tmp/confidence_flutter_sdk/ + + - run: echo API_KEY=dummy > /tmp/confidence_flutter_sdk/example/.env + if: matrix.build == 'spm' + - name: Build iOS (SPM) + if: matrix.build == 'spm' + working-directory: /tmp/confidence_flutter_sdk/example + run: flutter build ios --no-codesign diff --git a/ios/confidence_flutter_sdk.podspec b/ios/confidence_flutter_sdk.podspec index 9d53bd4..29a9190 100644 --- a/ios/confidence_flutter_sdk.podspec +++ b/ios/confidence_flutter_sdk.podspec @@ -5,19 +5,16 @@ Pod::Spec.new do |s| s.name = 'confidence_flutter_sdk' s.version = '0.0.1' - s.summary = 'A new Flutter plugin project.' - s.description = <<-DESC -A new Flutter plugin project. - DESC - s.homepage = 'http://example.com' + s.summary = 'Flutter plugin for the Confidence SDK.' + s.description = 'Flutter plugin for the Confidence SDK.' + s.homepage = 'https://confidence.spotify.com' s.license = { :file => '../LICENSE' } - s.author = { 'Your Company' => 'email@example.com' } + s.author = { 'Confidence' => 'confidence@spotify.com' } s.source = { :path => '.' } - s.source_files = 'Classes/**/*' + s.source_files = 'confidence_flutter_sdk/Sources/confidence_flutter_sdk/**/*.swift', 'Classes/Confidence/**/*.swift' s.dependency 'Flutter' s.platform = :ios, '14.0' - # Flutter.framework does not contain a i386 slice. s.pod_target_xcconfig = { 'DEFINES_MODULE' => 'YES', 'EXCLUDED_ARCHS[sdk=iphonesimulator*]' => 'i386' } s.swift_version = '5.0' end diff --git a/ios/confidence_flutter_sdk/.gitignore b/ios/confidence_flutter_sdk/.gitignore new file mode 100644 index 0000000..bb39a0b --- /dev/null +++ b/ios/confidence_flutter_sdk/.gitignore @@ -0,0 +1,2 @@ +.build/ +Package.resolved diff --git a/ios/confidence_flutter_sdk/Package.swift b/ios/confidence_flutter_sdk/Package.swift new file mode 100644 index 0000000..d9a6526 --- /dev/null +++ b/ios/confidence_flutter_sdk/Package.swift @@ -0,0 +1,24 @@ +// swift-tools-version: 5.9 + +import PackageDescription + +let package = Package( + name: "confidence_flutter_sdk", + platforms: [ + .iOS("14.0"), + ], + products: [ + .library(name: "confidence-flutter-sdk", targets: ["confidence_flutter_sdk"]), + ], + dependencies: [ + .package(name: "FlutterFramework", path: "../FlutterFramework"), + ], + targets: [ + .target( + name: "confidence_flutter_sdk", + dependencies: [ + .product(name: "FlutterFramework", package: "FlutterFramework"), + ] + ), + ] +) diff --git a/ios/Classes/ConfidenceFlutterSdkPlugin.swift b/ios/confidence_flutter_sdk/Sources/confidence_flutter_sdk/ConfidenceFlutterSdkPlugin.swift similarity index 100% rename from ios/Classes/ConfidenceFlutterSdkPlugin.swift rename to ios/confidence_flutter_sdk/Sources/confidence_flutter_sdk/ConfidenceFlutterSdkPlugin.swift