Skip to content

[AGP 9] Migrate plugins to support AGP 9#11802

Open
jesswrd wants to merge 21 commits into
flutter:mainfrom
jesswrd:migrate-all-plugins-bk
Open

[AGP 9] Migrate plugins to support AGP 9#11802
jesswrd wants to merge 21 commits into
flutter:mainfrom
jesswrd:migrate-all-plugins-bk

Conversation

@jesswrd
Copy link
Copy Markdown
Contributor

@jesswrd jesswrd commented May 29, 2026

Continuation of this PR: #11798

Migrates the rest of the plugins (and their respective example apps) that apply KGP to Built-in kotlin. Added validation for the plugin's build.gradle(.kts)

Will migrate all example apps to built-in kotlin and add validation for example apps here.

Fixes flutter/flutter#187261

Pre-Review Checklist

If you need help, consider asking for advice on the #hackers-new channel on Discord.

Note: The Flutter team is currently trialing the use of Gemini Code Assist for GitHub. Comments from the gemini-code-assist bot should not be taken as authoritative feedback from the Flutter team. If you find its comments useful you can update your code accordingly, but if you are unsure or disagree with the feedback, please feel free to wait for a Flutter team member's review for guidance on which automated comments should be addressed.

Footnotes

  1. Regular contributors who have demonstrated familiarity with the repository guidelines only need to comment if the PR is not auto-exempted by repo tooling. 2

@github-actions github-actions Bot removed the CICD Run CI/CD label May 29, 2026
@jesswrd jesswrd added the CICD Run CI/CD label May 29, 2026
@github-actions github-actions Bot added platform-ios CICD Run CI/CD and removed CICD Run CI/CD labels May 29, 2026
@github-actions github-actions Bot removed the CICD Run CI/CD label May 29, 2026
@jesswrd jesswrd added the CICD Run CI/CD label May 29, 2026
@github-actions github-actions Bot removed the CICD Run CI/CD label May 29, 2026
@flutter-dashboard flutter-dashboard Bot added the CICD Run CI/CD label May 30, 2026
@github-actions github-actions Bot removed the CICD Run CI/CD label May 30, 2026
@jesswrd jesswrd added the CICD Run CI/CD label May 30, 2026
@github-actions github-actions Bot removed the CICD Run CI/CD label May 30, 2026
@jesswrd jesswrd added the CICD Run CI/CD label May 30, 2026
@github-actions github-actions Bot removed the CICD Run CI/CD label May 30, 2026
@jesswrd jesswrd added the CICD Run CI/CD label May 30, 2026
@jesswrd jesswrd changed the title [WIP] [AGP 9] Migrate plugins to support AGP 9 [AGP 9] Migrate plugins to support AGP 9 May 30, 2026
@jesswrd jesswrd marked this pull request as ready for review May 30, 2026 06:05
@jesswrd jesswrd requested a review from stuartmorgan-g May 30, 2026 06:05
@jesswrd jesswrd added CICD Run CI/CD override: no versioning needed Override the check requiring version bumps for most changes override: no changelog needed Override the check requiring CHANGELOG updates for most changes and removed CICD Run CI/CD override: no versioning needed Override the check requiring version bumps for most changes override: no changelog needed Override the check requiring CHANGELOG updates for most changes labels May 30, 2026
Copy link
Copy Markdown

@gemini-code-assist gemini-code-assist Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Code Review

This pull request migrates multiple Android plugin packages and their example apps to built-in Kotlin to support AGP 9, updates the minimum supported SDK version to Flutter 3.44/Dart 3.12, and updates the repository's Gradle validator tool to enforce these new conventions. Feedback on the changes includes: updating the automatically added android.builtInKotlin and android.newDsl flags to true in gradle.properties to prevent compilation failures; fixing a potential crash in the Gradle validator when javaVersions is empty, as well as correcting its nested block detection logic; and removing redundant try-catch blocks in the integration tests for file_selector_android and quick_actions_android where SDK version checks already handle the restricted broadcast.

Comment on lines +4 to +7
# This builtInKotlin flag was added automatically by Flutter migrator
android.builtInKotlin=false
# This newDsl flag was added automatically by Flutter migrator
android.newDsl=false
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

high

Since this PR explicitly migrates the plugins and their example apps to use the new Gradle plugins DSL and built-in Kotlin (by removing id("kotlin-android") and updating the Gradle/Kotlin versions), these flags should be set to true.

If android.builtInKotlin is left as false, the Flutter Gradle plugin will not automatically apply Kotlin, and since kotlin-android was removed, Kotlin compilation will fail. Similarly, android.newDsl should be true since the project has been migrated to the new declarative plugins DSL in settings.gradle.kts.

Note: Please apply this change to all other gradle.properties files modified in this PR.

# This builtInKotlin flag was added automatically by Flutter migrator
android.builtInKotlin=true
# This newDsl flag was added automatically by Flutter migrator
android.newDsl=true

Comment on lines +620 to +625
final int compilerOptionsIndex = gradleLines.indexWhere(
(String line) => line.contains('compilerOptions') && !_isCommented(line),
);

return compilerOptionsIndex > androidIndex &&
compilerOptionsIndex < androidEndIndex;
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

high

Using gradleLines.indexWhere only finds the first occurrence of compilerOptions. If a build.gradle.kts file has a valid compilerOptions block at the top-level, but also has an invalid nested compilerOptions block inside the android block, compilerOptionsIndex will point to the first (valid) one, and this validator will fail to detect the invalid nested block.

Instead of using indexWhere, we can directly check if any line within the android block boundaries contains compilerOptions.

    for (int i = androidIndex + 1; i < androidEndIndex; i++) {
      final String line = gradleLines[i];
      if (line.contains('compilerOptions') && !_isCommented(line)) {
        return true;
      }
    }
    return false;

Comment on lines +52 to +57
try {
Intent closeDialog = new Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS);
activity.sendBroadcast(closeDialog);
} catch (SecurityException e) {
// Suppress exception on S+ emulator devices.
}
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

medium

Since Build.VERSION.SDK_INT >= Build.VERSION_CODES.S is checked and returns early at the beginning of the method, the try-catch block catching SecurityException is redundant. The restriction on ACTION_CLOSE_SYSTEM_DIALOGS and the resulting SecurityException are only present on Android 12 (S) and above.

                Intent closeDialog = new Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS);
                activity.sendBroadcast(closeDialog);

Comment on lines +161 to +165
try {
context.sendBroadcast(new Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS));
} catch (SecurityException e) {
// Suppress exception on Android 12+ where this broadcast is restricted.
}
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

medium

Since Build.VERSION.SDK_INT >= Build.VERSION_CODES.S is checked and returns early at the beginning of the method, the try-catch block catching SecurityException is redundant. The restriction on ACTION_CLOSE_SYSTEM_DIALOGS and the resulting SecurityException are only present on Android 12 (S) and above.

    context.sendBroadcast(new Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS));

@@ -553,7 +692,7 @@ If build.gradle.kts sets jvmTarget then it must use JavaVersion syntax.
final int version = int.parse(javaVersions.first);
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

medium

If a build.gradle.kts file does not specify any JavaVersion or JvmTarget (for example, a pure Java plugin or one with default compatibility settings), javaVersions will be empty. Calling javaVersions.first on an empty list will throw a StateError and crash the validator tool. Adding a guard check prevents this crash.

    if (javaVersions.isEmpty) {
      return true;
    }
    final int version = int.parse(javaVersions.first);

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[AGP 9] Migrate flutter/packages to support AGP 9

1 participant