docs: add Capacitor 9 app upgrade guide - #589
Conversation
Covers app-level changes only (Cordova-optional, CLI, Android/iOS breaking changes, upgrade steps, plugin summary). Deprecated-API removal tables and the plugin-author guide are tracked separately (RMET-4728, RMET-5321). RMET-5320
|
The latest updates on your projects. Learn more about Vercel for GitHub.
|
OS-pedrogustavobilro
left a comment
There was a problem hiding this comment.
Left a few comments. If some of them are better to address offline, let me know!
| - On Android, the generated `settings.gradle` and app `build.gradle` no longer include the `capacitor-cordova-android` / `capacitor-cordova-android-plugins` modules. | ||
| - On iOS, `CapacitorCordova` is no longer added to your `Podfile` or `Package.swift`. | ||
|
|
||
| There is currently no configuration option to force-include the Cordova runtime when no Cordova plugin is present. If your app's native code (or a plugin you maintain) directly references symbols from Capacitor's Cordova compatibility layer — for example `com.getcapacitor.cordova.CordovaPlugin` on Android, or anything from the `CapacitorCordova` pod/product on iOS — without having an actual Cordova plugin installed, those references will fail to resolve after upgrading. Add a Cordova plugin dependency (even a trivial one) if you need the layer present, or remove the direct reference. |
There was a problem hiding this comment.
This paragraph may change soon with this task but I suppose for now it's true. Just something to keep in mind, we may want to revire this doc in the near future after this PR is merged.
| AGP 9 no longer ships `proguard-android.txt` — any `build.gradle` that still references it fails at Gradle configuration time, even with `minifyEnabled false`: | ||
|
|
||
| ```groovy | ||
| // Before — hard build error on AGP 9 | ||
| proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' | ||
| // After | ||
| proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro' | ||
| ``` | ||
|
|
||
| `androidx.core:core` 1.19.0 merges every extension function previously shipped in `core-ktx` into `core` itself, turning `core-ktx` into an empty compatibility artifact. If your app (or an old/community plugin it depends on) still explicitly pins `core-ktx` to a version older than `1.19.0`, you may hit a duplicate class error at build time; remove the explicit `core-ktx` version override. | ||
|
|
||
| AGP 9 also bundles the Kotlin Gradle Plugin natively and removes the `jcenter()` repository helper entirely. These are unlikely to affect your app directly, but can break the build if you (or a legacy/community plugin) still apply Kotlin standalone or reference `jcenter()` — see [Update Kotlin and remove jcenter()](#update-kotlin-and-remove-jcenter) below. |
There was a problem hiding this comment.
Trying to think if these changes would go on @capacitor/android or in separate sections. You mention the proguard and Kotlin / jcenter in their own sections, so this feels like duplicated information here.
The core isn't mentioned below I guess, but could be moved below to its own subsection perhaps?
And here at most we would like to those sections?
Let me know if that makes sense.
|
|
||
| ## NodeJS 24+ | ||
|
|
||
| Capacitor 9 requires NodeJS 24 or greater. (Latest LTS version is recommended.) |
There was a problem hiding this comment.
Minor: Could also mention that Node 24 also uses npm 11 as default (as opposed to npm 10 with Node 22)
|
|
||
| Capacitor 9 requires NodeJS 24 or greater. (Latest LTS version is recommended.) | ||
|
|
||
| ## Using the CLI to Migrate |
There was a problem hiding this comment.
When I compare this page to 8.0 and 7.0, I notice some differences in section structure. Particularly, the "Using the CLI to Migrate" section is usually more above, or rather, the breaking changes that can be migrated automatically (like iOS deployment target and Android minSDK) using the CLI show up below the section on using the CLI
Logically that makes more sense to me than this structure, because if we're reading this top-to-bottom, we'd want developers to first try to use the CLI to migrate and save time, and then only go through the manual sections that the CLI usually migrates if they have issues.
Let me know if this makes sense, and/or if you have a differing opinion.
PS: I think the 8.5 guide "suffers" from this as well, which we can look into, but not in this PR.
| ``` | ||
|
|
||
| :::note | ||
| CocoaPods Trunk is expected to become read-only later in 2026. If you haven't already, consider migrating your app to SPM, which is the default for new Capacitor projects. |
There was a problem hiding this comment.
Per https://blog.cocoapods.org/CocoaPods-Specs-Repo/ it's december 2nd 2026, don't know if we want to be more specific.
Capacitor 9 is currently in alpha, but when it reaches GA, the "later in 2026" might not be so "later" 😅
- We can link to the spm guide, which I think the link would be
../ios/spm.md#using-spm-in-an-existing-capacitor-project(but do double check that)
|
|
||
|  | ||
|
|
||
| ### Update Android Project Variables |
There was a problem hiding this comment.
One thing that we do in the template is remove the targetSDK declaration from the app's build.gradle, as by default it matches compileSDK in AGP 9 (the variable in variables.gradle still remains). Perhaps we want to place a ### section somewhere in this doc for that? It's not a "mandatory change", but the cap migrate does it, and Capacitor apps should try to match the templates as much as possible.
| Once it's updated, Android Studio can assist with some of the updates related to gradle. To start, run `Tools -> AGP Upgrade Assistant` and choose `9.2.1` as the version to update on dropdown. Then click `Run selected steps`. | ||
|
|
||
|  |
There was a problem hiding this comment.
This migration from Android Studio adds several properties to gradle.properties, that should not exist for Capacitor 9 (some will even break cap 9 apps).
However, it was not covered in the task, so we may cover this in a separate PR for this task? That one doesn't cover capacitor-docs updates, but can be changed to cover it.
What do you think?
|
|
||
| ### InAppBrowser | ||
|
|
||
| - Native Android dependencies have been updated to their latest versions. |
There was a problem hiding this comment.
To match what other sections have, I think it should be something along the lines of (even if other dependency versions are updated, what this doc covers is dependency versions that should use a variable from variables.gradle, and if that variable changes, the app developers should update their variables.gradle to match, assuming they have added that variable to the gradle file)
Also I re-ordered browser and barcode scanner to be alphabetically ordered.
| - Native Android dependencies have been updated to their latest versions. | |
| ### Barcode Scanner | |
| - `kotlinxCoroutinesVersion` variable has been updated to `1.11.0`. | |
| ### Browser | |
| - `androidxBrowserVersion` variable has been updated to `1.10.0`. | |
| ### Camera | |
| - `androidxExifInterfaceVersion` variable has been updated to `1.4.2`. | |
| - `androidxMaterialVersion` variable has been updated to `1.14.0`. | |
| ### Geolocation | |
| - `playServicesLocationVersion` variable has been updated to `21.4.0`. | |
| - `kotlinxCoroutinesVersion` variable has been updated to `1.11.0`. | |
| ### Google Maps | |
| - `kotlinxCoroutinesVersion` variable has been updated to `1.11.0`. | |
| - `googleMapsPlayServicesVersion` variable has been updated to `20.0.0`. | |
| - `googleMapsUtilsVersion` variable has been updated to `5.0.0`. | |
| - `googleMapsKtxVersion` and `googleMapsUtilsKtxVersion` variables have been updated to `6.0.1`. | |
| ### InAppBrowser | |
| - `androidxBrowserVersion` variable has been updated to `1.10.0`. |
| - classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:1.9.10" | ||
| } | ||
| } | ||
| -apply plugin: 'kotlin-android' | ||
|
|
||
| dependencies { | ||
| - implementation "org.jetbrains.kotlin:kotlin-stdlib:1.9.10" |
There was a problem hiding this comment.
Minor: Something else I noticed Well since Cap 8 apps are meant to be using kotlin 2.2.20, it should be
| - classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:1.9.10" | |
| } | |
| } | |
| -apply plugin: 'kotlin-android' | |
| dependencies { | |
| - implementation "org.jetbrains.kotlin:kotlin-stdlib:1.9.10" | |
| - classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:2.2.20" | |
| } | |
| } | |
| -apply plugin: 'kotlin-android' | |
| dependencies { | |
| - implementation "org.jetbrains.kotlin:kotlin-stdlib:2.2.20" |
Description
Adds
docs/main/updating/9-0.md, the "Updating to 9.0" app upgrade guide, and registers it in the Upgrade Guides sidebar (sidebars.js).Covers app-level changes only:
@capacitor/cli(--urlreplacing the separate live-reload flags)@capacitor/android(minSdk 26, compileSdk/targetSdk 37, AGP 9.2.1 / Gradle 9.5.1, theproguard-android.txtrename,androidx.core1.19 /core-ktx, removing standalone Kotlin plugin references,jcenter()removal)@capacitor/ios(deployment target 16.0,@mainreplacing@UIApplicationMain, a pointer to the 8.5 guide for UIScene if updating from 8.4 or earlier)Using the CLI to Migrate, and the manual iOS/Android upgrade steps (Xcode, Android Studio,variables.gradle, Gradle wrapper, google-services)Change Type
Rationale / Problems Fixed
Capacitor 9 needs an "Updating to 9.0" guide before GA so app developers upgrading from 8.x have a single place documenting breaking changes and migration steps, and so Capacitor CLI and other components can link to it.
Internal Jira reference: https://outsystemsrd.atlassian.net/browse/RMET-5320
Tests or Reproductions
Content was cross-checked against the actual merged PRs in
ionic-team/capacitorandionic-team/capacitor-plugins(and sibling plugin repos) that introduce each breaking change, plus the currentnextbranch state of the Android/iOS templates (variables.gradle,app/build.gradle,Podfile, etc.) to confirm the exact version numbers. Verifiednpm run build(Docusaurus) succeeds and the new page renders at/next/updating/9-0/with no broken links.Note: Capacitor 9 hasn't reached GA yet, so the guide's install instructions point at the
nextdist-tag (@capacitor/cli@next) rather than@latest.Screenshots / Media
N/A
Platforms Affected