When importing a prebuilt Swift framework or XCFramework in Xcode, you may encounter an error such as:
Module compiled with Swift 5.x cannot be imported by the Swift 6.x compiler
A related message may be:
Compiled module was created by a different version of the compiler
This error means that the Swift compiler used by the application cannot understand the compiled Swift module provided by the binary framework.
Swift ABI stability and module stability are separate concepts. Swift 5.0 introduced ABI stability on Apple platforms, while Swift 5.1 introduced module stability for distributing Swift binaries across compiler versions. :contentReference[oaicite:11]{index=11}
This problem is especially common with prebuilt frameworks, vendor SDKs, binary CocoaPods, and binary Swift Package targets.
- What does “Module compiled with Swift cannot be imported” mean?
- ABI stability versus module stability
- Common causes
- 1. The framework and app were built with different Xcode versions
- 2. BUILD_LIBRARY_FOR_DISTRIBUTION is disabled
- 3. The binary framework is outdated
- 4. The XCFramework does not contain .swiftinterface files
- 5. The dependency is distributed only as a binary
- 6. A Debug framework was distributed
- 7. Swift compiler build versions differ
- 8. DerivedData contains an older framework
- 9. CocoaPods is using a cached binary
- 10. A Swift Package binary artifact is stale
- Typical situations where this error appears
- What to check first
- Solution 1: Rebuild the framework with the current Xcode
- Solution 2: Enable Build Libraries for Distribution
- Solution 3: Rebuild the XCFramework
- Solution 4: Verify that .swiftinterface files exist
- Solution 5: Update the vendor SDK
- Solution 6: Temporarily use the framework’s original Xcode version
- Solution 7: Prefer a source package when appropriate
- Solution 8: Update a binary CocoaPod
- Solution 9: Clear an obsolete CocoaPods cache
- Solution 10: Update a Swift Package binary target
- Solution 11: Reset package caches
- Solution 12: Remove DerivedData
- Solution 13: Inspect the actual module files
- Solution 14: Verify distribution settings in Debug and Release
- Solution 15: Check public dependencies of distributable frameworks
- Solution 16: Avoid exposing private implementation dependencies in public API
- Solution 17: Build distributable frameworks from archives
- Solution 18: Pin the Xcode version in CI
- If the message says “compiled with Swift X cannot be imported by Swift Y”
- If the dependency is already an XCFramework
- Checklist for framework authors
- Checklist for framework consumers
- Why ABI stability alone does not fix this
- What you should avoid
- Fast troubleshooting checklist
- Summary
What does “Module compiled with Swift cannot be imported” mean?
A Swift framework contains metadata describing the public API that another module can import.
A traditional compiled module may contain:
MyFramework.swiftmodule
The binary .swiftmodule format contains compiler-specific internal information.
Because that internal format can change between Swift compiler versions, a module created by one compiler may not be readable by another.
Apple’s Binary Frameworks in Swift session explains that the compiled Swift module format contains compiler implementation details and is therefore tied to the compiler version that created it. :contentReference[oaicite:12]{index=12}
ABI stability versus module stability
ABI stability
ABI stability allows Swift binaries and the Swift runtime to remain compatible at runtime across Swift releases on Apple platforms.
Swift 5.0 introduced this ABI stability on Apple platforms. :contentReference[oaicite:13]{index=13}
Module stability
Module stability addresses compile-time compatibility between Swift compiler versions.
Swift 5.1 introduced textual module interfaces such as:
.swiftinterface
which can be consumed by compatible future Swift compilers. :contentReference[oaicite:14]{index=14}
Important: ABI stability alone does not mean every precompiled Swift framework can be imported by every newer Swift compiler. Binary distribution also requires module stability.
Common causes
1. The framework and app were built with different Xcode versions
This is the most common cause.
Framework: Xcode A / Swift Compiler A
Application:
Xcode B / Swift Compiler B
If the framework does not contain a stable module interface, the newer compiler may reject it.
2. BUILD_LIBRARY_FOR_DISTRIBUTION is disabled
For prebuilt frameworks intended for distribution, inspect:
BUILD_LIBRARY_FOR_DISTRIBUTION
Swift’s Library Evolution documentation states that setting this to YES enables the features required for module stability and library evolution in Xcode. :contentReference[oaicite:15]{index=15}
3. The binary framework is outdated
A vendor may have built the SDK with an older Xcode release and not published an updated binary.
4. The XCFramework does not contain .swiftinterface files
An XCFramework can still contain compiler-version-specific Swift modules if its frameworks were not built for distribution.
5. The dependency is distributed only as a binary
Source packages can be recompiled with the consuming application’s compiler. Prebuilt binary dependencies cannot.
6. A Debug framework was distributed
The framework may have been built without the distribution settings needed for reusable binary delivery.
7. Swift compiler build versions differ
Even small Xcode version changes can include different Swift compiler builds.
8. DerivedData contains an older framework
The project may continue using a stale binary even after the framework was replaced.
9. CocoaPods is using a cached binary
A binary Pod may still resolve to an older cached artifact.
10. A Swift Package binary artifact is stale
The URL or checksum in a binary target may still point to an older XCFramework.
Typical situations where this error appears
- After upgrading Xcode
- After changing Swift toolchains
- After adding a binary framework
- When using an outdated vendor SDK
- When distributing your own XCFramework
- When CI upgrades to a newer Xcode release
- When the framework alone is built with an older Xcode
- When using a binary CocoaPod
- When using a Swift Package binary target
- When sharing a prebuilt Swift framework with another developer
What to check first
1. Check Xcode and Swift versions
xcodebuild -version swift --version
Compare these with the environment used to build the framework.
2. Inspect the framework’s Modules directory
MyFramework.framework/ └── Modules/ └── MyFramework.swiftmodule/
A distributable framework may contain files such as:
arm64-apple-ios.swiftinterface arm64-apple-ios.private.swiftinterface
Solution 1: Rebuild the framework with the current Xcode
If you have the framework source, this is the most reliable fix.
Build the framework and application with the same current Xcode toolchain.
Framework source ↓ Rebuild using current Xcode ↓ Replace old framework in application
Solution 2: Enable Build Libraries for Distribution
For a framework that will be distributed as a binary:
Target → Build Settings → Build Libraries for Distribution → Yes
Equivalent build setting:
BUILD_LIBRARY_FOR_DISTRIBUTION = YES
This generates stable module interfaces that make the framework usable across compatible Swift compiler versions. :contentReference[oaicite:16]{index=16}
Important: Swift’s Library Evolution documentation recommends enabling this setting consistently for both Debug and Release when building a framework intended for binary distribution. :contentReference[oaicite:17]{index=17}
Solution 3: Rebuild the XCFramework
Archive the device framework:
xcodebuild archive \ -scheme MyFramework \ -destination "generic/platform=iOS" \ -archivePath "./build/ios_devices" \ -SKIP_INSTALL=NO \ -BUILD_LIBRARY_FOR_DISTRIBUTION=YES
Archive the Simulator framework:
xcodebuild archive \ -scheme MyFramework \ -destination "generic/platform=iOS Simulator" \ -archivePath "./build/ios_simulator" \ -SKIP_INSTALL=NO \ -BUILD_LIBRARY_FOR_DISTRIBUTION=YES
Create the XCFramework:
xcodebuild -create-xcframework \ -framework "./build/ios_devices.xcarchive/Products/Library/Frameworks/MyFramework.framework" \ -framework "./build/ios_simulator.xcarchive/Products/Library/Frameworks/MyFramework.framework" \ -output "./build/MyFramework.xcframework"
Solution 4: Verify that .swiftinterface files exist
find MyFramework.xcframework -name "*.swiftinterface"
If no files are found, the framework may not have been built with a stable module interface.
Solution 5: Update the vendor SDK
If the framework is closed-source, you cannot rebuild it yourself.
Install a newer SDK version that explicitly supports your current Xcode and Swift compiler.
Prefer:
- A current XCFramework release
- A module-stable binary
- A version documented as compatible with your Xcode release
Solution 6: Temporarily use the framework’s original Xcode version
If no updated binary exists, using the same Xcode version that produced the framework may temporarily restore compatibility.
Note: This is a compatibility workaround, not the best long-term distribution strategy.
Solution 7: Prefer a source package when appropriate
If you control the dependency, distributing Swift source through Swift Package Manager can avoid many compiler-version binary module problems because the dependency is rebuilt by the consuming toolchain.
Swift’s Library Evolution documentation notes that libraries built and distributed together with their clients, including typical source Swift packages, do not generally need library evolution enabled. :contentReference[oaicite:18]{index=18}
Solution 8: Update a binary CocoaPod
Check the installed version:
grep -n "SomeSDK" Podfile.lock
Update when appropriate:
pod update SomeSDK
Solution 9: Clear an obsolete CocoaPods cache
Inspect cached Pods:
pod cache list
Remove an outdated SDK cache:
pod cache clean SomeSDK --all
Then reinstall:
pod install
Solution 10: Update a Swift Package binary target
A binary target may look like:
.binaryTarget( name: "SomeSDK", url: "https://example.com/SomeSDK.xcframework.zip", checksum: "..." )
If the vendor publishes an updated XCFramework, update both the URL and checksum.
Solution 11: Reset package caches
If the package should contain a newer binary but Xcode continues using an older artifact, reset and resolve the package dependencies.
For a command-line Swift package:
swift package reset swift package resolve
Solution 12: Remove DerivedData
After replacing the framework:
Product → Clean Build Folder
If necessary:
rm -rf ~/Library/Developer/Xcode/DerivedData/*
Important: DerivedData cleanup cannot make an incompatible binary framework compatible with a different Swift compiler.
Solution 13: Inspect the actual module files
find MyFramework.xcframework \ \( -name "*.swiftmodule" -o -name "*.swiftinterface" \)
If the framework contains only compiler-specific .swiftmodule files and no stable interface, it may be tied to the compiler version that created it.
Solution 14: Verify distribution settings in Debug and Release
xcodebuild -showBuildSettings \ -scheme MyFramework \ -configuration Debug | grep BUILD_LIBRARY_FOR_DISTRIBUTION
xcodebuild -showBuildSettings
-scheme MyFramework
-configuration Release | grep BUILD_LIBRARY_FOR_DISTRIBUTION
Make sure the configuration used to create the distributed artifact actually has the setting enabled.
Solution 15: Check public dependencies of distributable frameworks
A library built with library evolution support may expose types from another module in its public API.
In that case, the compatibility characteristics of the public dependency also matter. Swift compiler guidance notes that public dependencies of library-evolution-enabled modules must themselves preserve the required compatibility guarantees. :contentReference[oaicite:19]{index=19}
Solution 16: Avoid exposing private implementation dependencies in public API
If an external module is only an implementation detail, avoid unnecessarily exposing its types through the public API of your binary framework.
This reduces compatibility requirements for consumers of the framework.
Solution 17: Build distributable frameworks from archives
For production binary distribution, archive the framework rather than simply copying an arbitrary framework from DerivedData.
xcodebuild archive \ -scheme MyFramework \ -configuration Release \ -destination "generic/platform=iOS" \ -SKIP_INSTALL=NO \ -BUILD_LIBRARY_FOR_DISTRIBUTION=YES
Solution 18: Pin the Xcode version in CI
If local builds work but CI fails, compare:
xcodebuild -version swift --version
If CI uses a different compiler and the framework is not module-stable, that difference can trigger the import error.
If the message says “compiled with Swift X cannot be imported by Swift Y”
Use this order:
- Rebuild the framework with the current Xcode if source is available.
- For binary distribution, enable BUILD_LIBRARY_FOR_DISTRIBUTION.
- Verify that .swiftinterface files are included.
- Update vendor SDKs.
- As a temporary workaround, use the Xcode version compatible with the framework.
If the dependency is already an XCFramework
XCFramework packaging alone does not guarantee Swift module stability.
XCFramework primarily packages binaries for multiple platforms and architectures.
The contained Swift frameworks must still be built with stable module interfaces when compiler-version-independent binary distribution is required.
BUILD_LIBRARY_FOR_DISTRIBUTION = YES
Checklist for framework authors
- Enable BUILD_LIBRARY_FOR_DISTRIBUTION.
- Archive both device and Simulator variants.
- Verify .swiftinterface files.
- Create a valid XCFramework.
- Review public dependency compatibility.
- Test the binary in a clean consumer project.
Checklist for framework consumers
- Check the current Xcode version.
- Check the Swift compiler version.
- Check the SDK version.
- Check for stale binary caches.
- Inspect the XCFramework for .swiftinterface files.
- Verify the vendor’s supported Xcode versions.
Why ABI stability alone does not fix this
Swift 5.0 ABI stability primarily addresses runtime binary compatibility.
This error occurs at compile time while the compiler is trying to read another Swift module’s interface.
An Apple DTS engineer explicitly explained that Swift 5.0 ABI stability alone was not sufficient for importing precompiled libraries across compiler versions; module stability is also required. :contentReference[oaicite:20]{index=20}
What you should avoid
Do not assume that deleting DerivedData fixes a genuine Swift compiler compatibility problem.
Cache cleanup helps only when Xcode is using an obsolete artifact.
If the framework itself contains only compiler-specific Swift modules, you need a rebuilt framework, a compatible SDK version, or a module-stable binary.
Also avoid treating the Swift Language Version build setting as a guaranteed fix. The actual Swift compiler toolchain used by Xcode is what reads the module.
Fast troubleshooting checklist
- Check Xcode and Swift compiler versions.
- Determine which compiler built the framework.
- Inspect the framework for .swiftinterface files.
- Rebuild from source with the current Xcode when possible.
- Enable BUILD_LIBRARY_FOR_DISTRIBUTION for binary distribution.
- Recreate the XCFramework.
- Update third-party vendor SDKs.
- Check CocoaPods and Swift Package caches.
- Compare local and CI Xcode versions.
- Clean DerivedData last.
Summary
“Module compiled with Swift cannot be imported” means that the current Swift compiler cannot understand the compiled module metadata contained in a prebuilt Swift framework.
The most common cause is a framework built with a different Swift compiler without module stability support.
If you have source access, rebuild the framework using the same current Xcode toolchain as the application.
For binary frameworks and XCFrameworks intended for distribution, enable BUILD_LIBRARY_FOR_DISTRIBUTION = YES and verify that stable .swiftinterface files are included.
For third-party binary SDKs, install a release that explicitly supports your current Xcode version. Cache cleanup can help with stale artifacts, but it does not solve genuine compiler-version incompatibility.
