-
Notifications
You must be signed in to change notification settings - Fork 1.2k
Description
Capacitor Version
💊 Capacitor Doctor 💊
Latest Dependencies:
@capacitor/cli: 8.2.0
@capacitor/core: 8.2.0
@capacitor/android: unknown
@capacitor/ios: 8.2.0
Installed Dependencies:
@capacitor/android: not installed
@capacitor/cli: 7.6.0
@capacitor/ios: 7.0.0
@capacitor/core: 7.0.0
[error] Xcode is not installed
Other API Details
npm --version output:
10.9.4
node --version output:
v22.22.1Platforms Affected
- iOS
- Android
- Web
Current Behavior
We upgraded @capacitor/cli from 7.4.4 to 7.6.0 to resolve the tar dependency security vulnerability. After the upgrade, all Ionic Appflow CI builds running on Linux 2025.01 build stack started failing.
✔ copy ios in 136.39ms
✔ Updating iOS plugins in 22.76ms
[info] Found 1 Cordova plugin for ios:
cordova-plugin-ionic@5.5.3
✖ Updating iOS native dependencies with pod install - failed!
✖ update ios - failed!
[error] bundler: command not found: pod
Install missing gem executables with `bundle install`
Running after_script
Running after script...
$ run "clean-up"
Cleaning up project directory and file based variables
ERROR: Job failed: command terminated with exit code 1
We tried setting packageManager in the iOS config of capacitor.config.ts to attempt to skip the iOS native dependency install on Linux but it has no effect:
export default {
ios: {
packageManager: 'Cocoapods',
},
};loadIOSConfig in cli/src/config.ts unconditionally calls determinePackageManager() and ignores the user-provided value:
const packageManager = lazy(() => determinePackageManager(rootDir, platformDirAbs, nativeProjectDirAbs));This causes cap sync to fail on Linux CI environments when a Gemfile containing gem 'cocoapods' exists in the project and bundler is installed on the system. determinePackageManager() resolves to 'bundler' and unconditionally runs bundle exec pod install, which fails because CocoaPods cannot run on Linux.
PR #8344 fixed the non-bundler code path by adding an isInstalled('pod') check, but the bundler path has no equivalent guard — if packageManager resolves to 'bundler', it runs bundle exec pod install unconditionally.
Expected Behavior
Appflow Web build should succeed, skipping the pod install step on Web builds on Linux:
[03:20:31]: ▸ ✔ copy ios in 131.09ms
[03:20:31]: ▸ ✔ Updating iOS plugins in 23.35ms
[03:20:31]: ▸ [info] Found 1 Cordova plugin for ios:
[03:20:31]: ▸ cordova-plugin-ionic@5.5.3
[03:20:31]: ▸ [warn] Skipping pod install because CocoaPods is not installed
[03:20:31]: ▸ [warn] Unable to find "xcodebuild". Skipping xcodebuild clean step...
[03:20:31]: ▸ ✔ Updating iOS native dependencies with pod install in 7.68ms
[03:20:31]: ▸ [info] Found 18 Capacitor plugins for ios:
...
[03:20:31]: ▸ ✔ update ios in 109.06ms
Potentially if ios.packageManager is explicitly set in the Capacitor config, it should be respected and determinePackageManager() should not be called.
Project Reproduction
https://github.com/philyy/my-app
Additional Information
Run npx cap sync ios in the reproduction repo on Linux (tested on Ubuntu 22 LTS) and you should see the error.
We temporarily patched this with a yarn patch so if ios.packageManager is explicitly set in the Capacitor config, it should be respected and determinePackageManager() should not be called.