diff --git a/dev/bots/firebase_testlab.sh b/dev/bots/firebase_testlab.sh index 14be500e618..41e29f088e2 100755 --- a/dev/bots/firebase_testlab.sh +++ b/dev/bots/firebase_testlab.sh @@ -1,13 +1,17 @@ #!/bin/bash +# The tests to run on Firebase Test Lab. +# Currently, the test consists on building an Android App Bundle and ensuring +# that the app doesn't crash upon startup. +tests=( + "dev/integration_tests/release_smoke_test" + "dev/integration_tests/abstract_method_smoke_test" +) + set -e GIT_REVISION=$(git rev-parse HEAD) -pushd dev/integration_tests/release_smoke_test - -../../../bin/flutter build appbundle --target-platform android-arm,android-arm64 - # New contributors will not have permissions to run this test - they won't be # able to access the service account information. We should just mark the test # as passed - it will run fine on post submit, where it will still catch @@ -22,21 +26,29 @@ echo $GCLOUD_FIREBASE_TESTLAB_KEY > ${HOME}/gcloud-service-key.json gcloud auth activate-service-account --key-file=${HOME}/gcloud-service-key.json gcloud --quiet config set project flutter-infra -# Firebase Test Lab tests are currently known to be failing with -# "Firebase Test Lab infrastructure failure: Error during preprocessing" -# Remove "|| exit 0" once the failures are resolved -# https://github.com/flutter/flutter/issues/36501 +function test_app_bundle() { + pushd "$@" + ../../../bin/flutter build appbundle --target-platform android-arm,android-arm64 -# Run the test. -gcloud firebase test android run --type robo \ - --app build/app/outputs/bundle/release/app.aab \ - --timeout 2m \ - --results-bucket=gs://flutter_firebase_testlab \ - --results-dir=release_smoke_test/$GIT_REVISION/$CIRRUS_BUILD_ID || exit 0 + # Firebase Test Lab tests are currently known to be failing with + # "Firebase Test Lab infrastructure failure: Error during preprocessing" + # Remove "|| exit 0" once the failures are resolved + # https://github.com/flutter/flutter/issues/36501 -# Check logcat for "E/flutter" - if it's there, something's wrong. -gsutil cp gs://flutter_firebase_testlab/release_smoke_test/$GIT_REVISION/$CIRRUS_BUILD_ID/walleye-26-en-portrait/logcat /tmp/logcat -! grep "E/flutter" /tmp/logcat || false -grep "I/flutter" /tmp/logcat + # Run the test. + gcloud firebase test android run --type robo \ + --app build/app/outputs/bundle/release/app.aab \ + --timeout 2m \ + --results-bucket=gs://flutter_firebase_testlab \ + --results-dir="$@"/"$GIT_REVISION"/"$CIRRUS_BUILD_ID" || exit 0 -popd + # Check logcat for "E/flutter" - if it's there, something's wrong. + gsutil cp gs://flutter_firebase_testlab/"$@"/"$GIT_REVISION"/"$CIRRUS_BUILD_ID"/walleye-26-en-portrait/logcat /tmp/logcat + ! grep "E/flutter" /tmp/logcat || false + grep "I/flutter" /tmp/logcat + popd +} + +for test in ${tests[*]}; do + test_app_bundle $test +done diff --git a/dev/integration_tests/abstract_method_smoke_test/android/app/build.gradle b/dev/integration_tests/abstract_method_smoke_test/android/app/build.gradle new file mode 100644 index 00000000000..ed57ad71f0a --- /dev/null +++ b/dev/integration_tests/abstract_method_smoke_test/android/app/build.gradle @@ -0,0 +1,71 @@ +def localProperties = new Properties() +def localPropertiesFile = rootProject.file('local.properties') +if (localPropertiesFile.exists()) { + localPropertiesFile.withReader('UTF-8') { reader -> + localProperties.load(reader) + } +} + +def flutterRoot = localProperties.getProperty('flutter.sdk') +if (flutterRoot == null) { + throw new GradleException("Flutter SDK not found. Define location with flutter.sdk in the local.properties file.") +} + +def flutterVersionCode = localProperties.getProperty('flutter.versionCode') +if (flutterVersionCode == null) { + flutterVersionCode = '1' +} + +def flutterVersionName = localProperties.getProperty('flutter.versionName') +if (flutterVersionName == null) { + flutterVersionName = '1.0' +} + +apply plugin: 'com.android.application' +apply plugin: 'kotlin-android' +apply from: "$flutterRoot/packages/flutter_tools/gradle/flutter.gradle" + +android { + compileSdkVersion 29 + + sourceSets { + main.java.srcDirs += 'src/main/kotlin' + } + + lintOptions { + disable 'InvalidPackage' + } + + compileOptions { + sourceCompatibility JavaVersion.VERSION_1_8 + targetCompatibility JavaVersion.VERSION_1_8 + } + + defaultConfig { + // TODO: Specify your own unique Application ID (https://developer.android.com/studio/build/application-id.html). + applicationId "com.example.abstract_method_smoke_test" + minSdkVersion 21 + targetSdkVersion 29 + versionCode flutterVersionCode.toInteger() + versionName flutterVersionName + testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner" + } + + buildTypes { + release { + signingConfig signingConfigs.debug + } + } + + kotlinOptions { + jvmTarget = "1.8" + } +} + +flutter { + source '../..' +} + +dependencies { + implementation "org.jetbrains.kotlin:kotlin-stdlib-jdk7:$kotlin_version" +} diff --git a/dev/integration_tests/abstract_method_smoke_test/android/app/src/debug/AndroidManifest.xml b/dev/integration_tests/abstract_method_smoke_test/android/app/src/debug/AndroidManifest.xml new file mode 100644 index 00000000000..122c170ab62 --- /dev/null +++ b/dev/integration_tests/abstract_method_smoke_test/android/app/src/debug/AndroidManifest.xml @@ -0,0 +1,7 @@ + + + + diff --git a/dev/integration_tests/abstract_method_smoke_test/android/app/src/main/AndroidManifest.xml b/dev/integration_tests/abstract_method_smoke_test/android/app/src/main/AndroidManifest.xml new file mode 100644 index 00000000000..87652c589d6 --- /dev/null +++ b/dev/integration_tests/abstract_method_smoke_test/android/app/src/main/AndroidManifest.xml @@ -0,0 +1,35 @@ + + + + + + + + + + + + + + + diff --git a/dev/integration_tests/abstract_method_smoke_test/android/app/src/main/kotlin/com/example/abstract_method_smoke_test/MainActivity.kt b/dev/integration_tests/abstract_method_smoke_test/android/app/src/main/kotlin/com/example/abstract_method_smoke_test/MainActivity.kt new file mode 100644 index 00000000000..4b7eeb7b1fc --- /dev/null +++ b/dev/integration_tests/abstract_method_smoke_test/android/app/src/main/kotlin/com/example/abstract_method_smoke_test/MainActivity.kt @@ -0,0 +1,19 @@ +package com.example.abstract_method_smoke_test + +import android.content.Context +import android.os.Bundle +import android.view.inputmethod.InputMethodManager +import io.flutter.app.FlutterActivity +import io.flutter.plugins.GeneratedPluginRegistrant + +class MainActivity: FlutterActivity() { + override fun onCreate(savedInstanceState: Bundle?) { + super.onCreate(savedInstanceState) + GeneratedPluginRegistrant.registerWith(this) + + // Triggers the Android keyboard, which causes the resize of the Flutter view. + // https://github.com/flutter/flutter/issues/40126 + val imm = getSystemService(Context.INPUT_METHOD_SERVICE) as InputMethodManager + imm.toggleSoftInput(InputMethodManager.SHOW_FORCED, 0) + } +} diff --git a/dev/integration_tests/abstract_method_smoke_test/android/app/src/main/res/drawable/launch_background.xml b/dev/integration_tests/abstract_method_smoke_test/android/app/src/main/res/drawable/launch_background.xml new file mode 100644 index 00000000000..304732f8842 --- /dev/null +++ b/dev/integration_tests/abstract_method_smoke_test/android/app/src/main/res/drawable/launch_background.xml @@ -0,0 +1,12 @@ + + + + + + + + diff --git a/dev/integration_tests/abstract_method_smoke_test/android/app/src/main/res/values/styles.xml b/dev/integration_tests/abstract_method_smoke_test/android/app/src/main/res/values/styles.xml new file mode 100644 index 00000000000..00fa4417cfb --- /dev/null +++ b/dev/integration_tests/abstract_method_smoke_test/android/app/src/main/res/values/styles.xml @@ -0,0 +1,8 @@ + + + + diff --git a/dev/integration_tests/abstract_method_smoke_test/android/app/src/profile/AndroidManifest.xml b/dev/integration_tests/abstract_method_smoke_test/android/app/src/profile/AndroidManifest.xml new file mode 100644 index 00000000000..122c170ab62 --- /dev/null +++ b/dev/integration_tests/abstract_method_smoke_test/android/app/src/profile/AndroidManifest.xml @@ -0,0 +1,7 @@ + + + + diff --git a/dev/integration_tests/abstract_method_smoke_test/android/build.gradle b/dev/integration_tests/abstract_method_smoke_test/android/build.gradle new file mode 100644 index 00000000000..3100ad2d555 --- /dev/null +++ b/dev/integration_tests/abstract_method_smoke_test/android/build.gradle @@ -0,0 +1,31 @@ +buildscript { + ext.kotlin_version = '1.3.50' + repositories { + google() + jcenter() + } + + dependencies { + classpath 'com.android.tools.build:gradle:3.5.0' + classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version" + } +} + +allprojects { + repositories { + google() + jcenter() + } +} + +rootProject.buildDir = '../build' +subprojects { + project.buildDir = "${rootProject.buildDir}/${project.name}" +} +subprojects { + project.evaluationDependsOn(':app') +} + +task clean(type: Delete) { + delete rootProject.buildDir +} diff --git a/dev/integration_tests/abstract_method_smoke_test/android/gradle.properties b/dev/integration_tests/abstract_method_smoke_test/android/gradle.properties new file mode 100644 index 00000000000..d2032bce8be --- /dev/null +++ b/dev/integration_tests/abstract_method_smoke_test/android/gradle.properties @@ -0,0 +1,4 @@ +org.gradle.jvmargs=-Xmx1536M +android.enableJetifier=true +android.useAndroidX=true +android.enableR8=true diff --git a/dev/integration_tests/abstract_method_smoke_test/android/gradle/wrapper/gradle-wrapper.properties b/dev/integration_tests/abstract_method_smoke_test/android/gradle/wrapper/gradle-wrapper.properties new file mode 100644 index 00000000000..9ec7236c631 --- /dev/null +++ b/dev/integration_tests/abstract_method_smoke_test/android/gradle/wrapper/gradle-wrapper.properties @@ -0,0 +1,6 @@ +#Fri Jun 23 08:50:38 CEST 2017 +distributionBase=GRADLE_USER_HOME +distributionPath=wrapper/dists +zipStoreBase=GRADLE_USER_HOME +zipStorePath=wrapper/dists +distributionUrl=https\://services.gradle.org/distributions/gradle-5.6.1-all.zip diff --git a/dev/integration_tests/abstract_method_smoke_test/android/settings.gradle b/dev/integration_tests/abstract_method_smoke_test/android/settings.gradle new file mode 100644 index 00000000000..5a2f14fb18f --- /dev/null +++ b/dev/integration_tests/abstract_method_smoke_test/android/settings.gradle @@ -0,0 +1,15 @@ +include ':app' + +def flutterProjectRoot = rootProject.projectDir.parentFile.toPath() + +def plugins = new Properties() +def pluginsFile = new File(flutterProjectRoot.toFile(), '.flutter-plugins') +if (pluginsFile.exists()) { + pluginsFile.withReader('UTF-8') { reader -> plugins.load(reader) } +} + +plugins.each { name, path -> + def pluginDirectory = flutterProjectRoot.resolve(path).resolve('android').toFile() + include ":$name" + project(":$name").projectDir = pluginDirectory +} diff --git a/dev/integration_tests/abstract_method_smoke_test/lib/main.dart b/dev/integration_tests/abstract_method_smoke_test/lib/main.dart new file mode 100644 index 00000000000..9720d8fe737 --- /dev/null +++ b/dev/integration_tests/abstract_method_smoke_test/lib/main.dart @@ -0,0 +1,61 @@ +import 'package:flutter/material.dart'; +import 'package:google_maps_flutter/google_maps_flutter.dart'; + +void main() => runApp(MyApp()); + +class MyApp extends StatelessWidget { + @override + Widget build(BuildContext context) { + return MaterialApp( + title: 'Flutter Demo', + theme: ThemeData( + primarySwatch: Colors.blue, + ), + home: HomePage(), + ); + } +} + +class HomePage extends StatefulWidget { + @override + _HomePage createState() => _HomePage(); +} + +class _HomePage extends State { + @override + void initState() { + super.initState(); + + // Trigger the second route. + // https://github.com/flutter/flutter/issues/40126 + WidgetsBinding.instance.addPostFrameCallback((_) async { + Navigator.of(context).push( + MaterialPageRoute(builder: (_) => SecondPage())); + }); + } + + @override + Widget build(BuildContext context) { + return const Scaffold(); + } +} + +class SecondPage extends StatelessWidget { + @override + Widget build(BuildContext context) { + return Scaffold( + body: Column( + children: [ + TextFormField(), + const Expanded( + child: GoogleMap( + initialCameraPosition: CameraPosition( + target: LatLng(0, 0) + ), + ), + ), + ], + ), + ); + } +} \ No newline at end of file diff --git a/dev/integration_tests/abstract_method_smoke_test/pubspec.yaml b/dev/integration_tests/abstract_method_smoke_test/pubspec.yaml new file mode 100644 index 00000000000..cc95e731a19 --- /dev/null +++ b/dev/integration_tests/abstract_method_smoke_test/pubspec.yaml @@ -0,0 +1,47 @@ +name: abstract_method_smoke_test +description: A new Flutter project. + +version: 1.0.0+1 + +environment: + sdk: ">=2.1.0 <3.0.0" + +dependencies: + flutter: + sdk: flutter + google_maps_flutter: 0.5.21+4 + + collection: 1.14.11 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade" + meta: 1.1.7 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade" + typed_data: 1.1.6 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade" + vector_math: 2.0.8 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade" + +dev_dependencies: + flutter_test: + sdk: flutter + + archive: 2.0.10 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade" + args: 1.5.2 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade" + async: 2.3.0 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade" + boolean_selector: 1.0.5 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade" + charcode: 1.1.2 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade" + convert: 2.1.1 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade" + crypto: 2.1.3 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade" + image: 2.1.4 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade" + matcher: 0.12.5 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade" + path: 1.6.4 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade" + pedantic: 1.8.0+1 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade" + petitparser: 2.4.0 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade" + quiver: 2.0.5 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade" + source_span: 1.5.5 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade" + stack_trace: 1.9.3 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade" + stream_channel: 2.0.0 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade" + string_scanner: 1.0.5 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade" + term_glyph: 1.1.0 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade" + test_api: 0.2.5 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade" + xml: 3.5.0 # THIS LINE IS AUTOGENERATED - TO UPDATE USE "flutter update-packages --force-upgrade" + +flutter: + uses-material-design: true + +# PUBSPEC CHECKSUM: 3231 diff --git a/packages/flutter_tools/gradle/flutter.gradle b/packages/flutter_tools/gradle/flutter.gradle index 606d3a3bd2c..bbc1c8e2933 100644 --- a/packages/flutter_tools/gradle/flutter.gradle +++ b/packages/flutter_tools/gradle/flutter.gradle @@ -332,9 +332,11 @@ class FlutterPlugin implements Plugin { } Closure addEmbeddingCompileOnlyDependency = { buildType -> String flutterBuildMode = buildModeFor(buildType) - // Add the embedding as a compile only dependency to the plugin. + // In AGP 3.5, the embedding must be added as an API implementation, + // so java8 features are desugared against the runtime classpath. + // For more, see https://github.com/flutter/flutter/issues/40126 if (flutterJar) { - addCompileOnlyDependency( + addApiDependencies( pluginProject, buildType.name, project.files { @@ -343,7 +345,7 @@ class FlutterPlugin implements Plugin { ) return } - addCompileOnlyDependency( + addApiDependencies( pluginProject, buildType.name, "io.flutter:flutter_embedding_$flutterBuildMode:1.0.0-$engineVersion",