diff --git a/android/build.gradle b/android/build.gradle index 3c2c918446f..83dfc39fb80 100644 --- a/android/build.gradle +++ b/android/build.gradle @@ -1,27 +1,11 @@ -apply plugin: 'com.android.library' +plugins { + id "maven-publish" -group = "io.grpc" -version = "1.29.0-SNAPSHOT" // CURRENT_GRPC_VERSION -description = 'gRPC: Android' - -buildscript { - repositories { - google() - jcenter() - mavenCentral() - maven { url "https://plugins.gradle.org/m2/" } - } - dependencies { - classpath 'com.android.tools.build:gradle:3.3.0' - classpath "net.ltgt.gradle:gradle-errorprone-plugin:0.8.1" - classpath "digital.wup:android-maven-publish:3.6.2" - } + id "com.android.library" + id "digital.wup.android-maven-publish" } -apply plugin: "maven-publish" -apply plugin: "net.ltgt.errorprone" -apply plugin: "digital.wup.android-maven-publish" -apply plugin: "signing" +description = 'gRPC: Android' android { compileSdkVersion 28 @@ -39,20 +23,16 @@ android { repositories { google() jcenter() - mavenCentral() - mavenLocal() } dependencies { - errorprone 'com.google.errorprone:error_prone_core:2.3.4' - errorproneJavac 'com.google.errorprone:javac:9+181-r4173-1' + implementation project(':grpc-core') - implementation 'io.grpc:grpc-core:1.29.0-SNAPSHOT' // CURRENT_GRPC_VERSION - - testImplementation 'io.grpc:grpc-okhttp:1.29.0-SNAPSHOT' // CURRENT_GRPC_VERSION - testImplementation 'junit:junit:4.12' - testImplementation 'org.robolectric:robolectric:4.3.1' - testImplementation 'com.google.truth:truth:1.0.1' + testImplementation project('::grpc-okhttp') + testImplementation libraries.androidx_test + testImplementation libraries.junit + testImplementation libraries.robolectric + testImplementation libraries.truth } task javadocs(type: Javadoc) { @@ -83,81 +63,11 @@ task sourcesJar(type: Jar) { publishing { publications { - maven(MavenPublication) { + maven { from components.android artifact javadocJar artifact sourcesJar - - pom { - name = project.group + ":" + project.name - url = 'https://github.com/grpc/grpc-java' - afterEvaluate { - // description is not available until evaluated. - description = project.description - } - - scm { - connection = 'scm:git:https://github.com/grpc/grpc-java.git' - developerConnection = 'scm:git:git@github.com:grpc/grpc-java.git' - url = 'https://github.com/grpc/grpc-java' - } - - licenses { - license { - name = 'Apache 2.0' - url = 'https://opensource.org/licenses/Apache-2.0' - } - } - - developers { - developer { - id = "grpc.io" - name = "gRPC Contributors" - email = "grpc-io@googlegroups.com" - url = "https://grpc.io/" - organization = "gRPC Authors" - organizationUrl = "https://www.google.com" - } - } - - withXml { - asNode().dependencies.'*'.findAll() { dep -> - dep.artifactId.text() in ['grpc-api', 'grpc-core'] - }.each() { core -> - core.version*.value = "[" + core.version.text() + "]" - } - } - } - } - } - repositories { - maven { - if (rootProject.hasProperty('repositoryDir')) { - url = new File(rootProject.repositoryDir).toURI() - } else { - String stagingUrl - if (rootProject.hasProperty('repositoryId')) { - stagingUrl = 'https://oss.sonatype.org/service/local/staging/deployByRepositoryId/' + - rootProject.repositoryId - } else { - stagingUrl = 'https://oss.sonatype.org/service/local/staging/deploy/maven2/' - } - credentials { - if (rootProject.hasProperty('ossrhUsername') && rootProject.hasProperty('ossrhPassword')) { - username = rootProject.ossrhUsername - password = rootProject.ossrhPassword - } - } - def releaseUrl = stagingUrl - def snapshotUrl = 'https://oss.sonatype.org/content/repositories/snapshots/' - url = version.endsWith('SNAPSHOT') ? snapshotUrl : releaseUrl - } } } } - -signing { - required false - sign publishing.publications.maven -} diff --git a/android/settings.gradle b/android/settings.gradle deleted file mode 100644 index 9b09956c740..00000000000 --- a/android/settings.gradle +++ /dev/null @@ -1 +0,0 @@ -rootProject.name = 'grpc-android' diff --git a/android/src/test/java/io/grpc/android/AndroidChannelBuilderTest.java b/android/src/test/java/io/grpc/android/AndroidChannelBuilderTest.java index bb8e31712ca..391134a9d1d 100644 --- a/android/src/test/java/io/grpc/android/AndroidChannelBuilderTest.java +++ b/android/src/test/java/io/grpc/android/AndroidChannelBuilderTest.java @@ -28,6 +28,7 @@ import android.net.ConnectivityManager; import android.net.Network; import android.net.NetworkInfo; +import androidx.test.core.app.ApplicationProvider; import io.grpc.CallOptions; import io.grpc.ClientCall; import io.grpc.ManagedChannel; @@ -39,7 +40,6 @@ import org.junit.Test; import org.junit.runner.RunWith; import org.robolectric.RobolectricTestRunner; -import org.robolectric.RuntimeEnvironment; import org.robolectric.annotation.Config; import org.robolectric.annotation.Implementation; import org.robolectric.annotation.Implements; @@ -54,24 +54,32 @@ public final class AndroidChannelBuilderTest { private final NetworkInfo WIFI_CONNECTED = ShadowNetworkInfo.newInstance( - NetworkInfo.DetailedState.CONNECTED, ConnectivityManager.TYPE_WIFI, 0, true, true); + NetworkInfo.DetailedState.CONNECTED, + ConnectivityManager.TYPE_WIFI, + 0, + true, + NetworkInfo.State.CONNECTED); private final NetworkInfo WIFI_DISCONNECTED = ShadowNetworkInfo.newInstance( - NetworkInfo.DetailedState.DISCONNECTED, ConnectivityManager.TYPE_WIFI, 0, true, false); + NetworkInfo.DetailedState.DISCONNECTED, + ConnectivityManager.TYPE_WIFI, + 0, + true, + NetworkInfo.State.DISCONNECTED); private final NetworkInfo MOBILE_CONNECTED = ShadowNetworkInfo.newInstance( NetworkInfo.DetailedState.CONNECTED, ConnectivityManager.TYPE_MOBILE, ConnectivityManager.TYPE_MOBILE_MMS, true, - true); + NetworkInfo.State.CONNECTED); private final NetworkInfo MOBILE_DISCONNECTED = ShadowNetworkInfo.newInstance( NetworkInfo.DetailedState.DISCONNECTED, ConnectivityManager.TYPE_MOBILE, ConnectivityManager.TYPE_MOBILE_MMS, true, - false); + NetworkInfo.State.DISCONNECTED); private ConnectivityManager connectivityManager; @@ -79,7 +87,9 @@ public final class AndroidChannelBuilderTest { public void setUp() { connectivityManager = (ConnectivityManager) - RuntimeEnvironment.application.getSystemService(Context.CONNECTIVITY_SERVICE); + ApplicationProvider + .getApplicationContext() + .getSystemService(Context.CONNECTIVITY_SERVICE); } @Test @@ -103,8 +113,9 @@ public void nullContextDoesNotThrow_api23() { // Network change and shutdown should be no-op for the channel without an Android Context shadowOf(connectivityManager).setActiveNetworkInfo(WIFI_CONNECTED); - RuntimeEnvironment.application.sendBroadcast( - new Intent(ConnectivityManager.CONNECTIVITY_ACTION)); + ApplicationProvider + .getApplicationContext() + .sendBroadcast(new Intent(ConnectivityManager.CONNECTIVITY_ACTION)); androidChannel.shutdown(); assertThat(delegateChannel.resetCount).isEqualTo(0); @@ -131,48 +142,55 @@ public void resetConnectBackoff_api23() { TestChannel delegateChannel = new TestChannel(); ManagedChannel androidChannel = new AndroidChannelBuilder.AndroidChannel( - delegateChannel, RuntimeEnvironment.application.getApplicationContext()); + delegateChannel, ApplicationProvider.getApplicationContext()); assertThat(delegateChannel.resetCount).isEqualTo(0); // On API levels < 24, the broadcast receiver will invoke resetConnectBackoff() on the first // connectivity action broadcast regardless of previous connection status shadowOf(connectivityManager).setActiveNetworkInfo(WIFI_CONNECTED); - RuntimeEnvironment.application.sendBroadcast( - new Intent(ConnectivityManager.CONNECTIVITY_ACTION)); + ApplicationProvider + .getApplicationContext() + .sendBroadcast(new Intent(ConnectivityManager.CONNECTIVITY_ACTION)); assertThat(delegateChannel.resetCount).isEqualTo(1); // The broadcast receiver may fire when the active network status has not actually changed - RuntimeEnvironment.application.sendBroadcast( - new Intent(ConnectivityManager.CONNECTIVITY_ACTION)); + ApplicationProvider + .getApplicationContext() + .sendBroadcast(new Intent(ConnectivityManager.CONNECTIVITY_ACTION)); assertThat(delegateChannel.resetCount).isEqualTo(1); // Drop the connection shadowOf(connectivityManager).setActiveNetworkInfo(null); - RuntimeEnvironment.application.sendBroadcast( - new Intent(ConnectivityManager.CONNECTIVITY_ACTION)); + ApplicationProvider + .getApplicationContext() + .sendBroadcast(new Intent(ConnectivityManager.CONNECTIVITY_ACTION)); assertThat(delegateChannel.resetCount).isEqualTo(1); // Notify that a new but not connected network is available shadowOf(connectivityManager).setActiveNetworkInfo(MOBILE_DISCONNECTED); - RuntimeEnvironment.application.sendBroadcast( - new Intent(ConnectivityManager.CONNECTIVITY_ACTION)); + ApplicationProvider + .getApplicationContext() + .sendBroadcast(new Intent(ConnectivityManager.CONNECTIVITY_ACTION)); assertThat(delegateChannel.resetCount).isEqualTo(1); // Establish a connection shadowOf(connectivityManager).setActiveNetworkInfo(MOBILE_CONNECTED); - RuntimeEnvironment.application.sendBroadcast( - new Intent(ConnectivityManager.CONNECTIVITY_ACTION)); + ApplicationProvider + .getApplicationContext() + .sendBroadcast(new Intent(ConnectivityManager.CONNECTIVITY_ACTION)); assertThat(delegateChannel.resetCount).isEqualTo(2); // Disconnect, then shutdown the channel and verify that the broadcast receiver has been // unregistered shadowOf(connectivityManager).setActiveNetworkInfo(null); - RuntimeEnvironment.application.sendBroadcast( - new Intent(ConnectivityManager.CONNECTIVITY_ACTION)); + ApplicationProvider + .getApplicationContext() + .sendBroadcast(new Intent(ConnectivityManager.CONNECTIVITY_ACTION)); androidChannel.shutdown(); shadowOf(connectivityManager).setActiveNetworkInfo(MOBILE_CONNECTED); - RuntimeEnvironment.application.sendBroadcast( - new Intent(ConnectivityManager.CONNECTIVITY_ACTION)); + ApplicationProvider + .getApplicationContext() + .sendBroadcast(new Intent(ConnectivityManager.CONNECTIVITY_ACTION)); assertThat(delegateChannel.resetCount).isEqualTo(2); // enterIdle is not called on API levels < 24 @@ -186,7 +204,7 @@ public void resetConnectBackoffAndEnterIdle_api24() { TestChannel delegateChannel = new TestChannel(); ManagedChannel androidChannel = new AndroidChannelBuilder.AndroidChannel( - delegateChannel, RuntimeEnvironment.application.getApplicationContext()); + delegateChannel, ApplicationProvider.getApplicationContext()); assertThat(delegateChannel.resetCount).isEqualTo(0); assertThat(delegateChannel.enterIdleCount).isEqualTo(0); @@ -227,7 +245,7 @@ public void newChannelWithConnection_entersIdleOnSecondConnectionChange_api24() TestChannel delegateChannel = new TestChannel(); ManagedChannel androidChannel = new AndroidChannelBuilder.AndroidChannel( - delegateChannel, RuntimeEnvironment.application.getApplicationContext()); + delegateChannel, ApplicationProvider.getApplicationContext()); // The first onAvailable() may just signal that the device was connected when the callback is // registered, rather than indicating a changed network, so we do not enter idle. @@ -248,15 +266,17 @@ public void shutdownNowUnregistersBroadcastReceiver_api23() { TestChannel delegateChannel = new TestChannel(); ManagedChannel androidChannel = new AndroidChannelBuilder.AndroidChannel( - delegateChannel, RuntimeEnvironment.application.getApplicationContext()); + delegateChannel, ApplicationProvider.getApplicationContext()); shadowOf(connectivityManager).setActiveNetworkInfo(null); - RuntimeEnvironment.application.sendBroadcast( - new Intent(ConnectivityManager.CONNECTIVITY_ACTION)); + ApplicationProvider + .getApplicationContext() + .sendBroadcast(new Intent(ConnectivityManager.CONNECTIVITY_ACTION)); androidChannel.shutdownNow(); shadowOf(connectivityManager).setActiveNetworkInfo(WIFI_CONNECTED); - RuntimeEnvironment.application.sendBroadcast( - new Intent(ConnectivityManager.CONNECTIVITY_ACTION)); + ApplicationProvider + .getApplicationContext() + .sendBroadcast(new Intent(ConnectivityManager.CONNECTIVITY_ACTION)); assertThat(delegateChannel.resetCount).isEqualTo(0); } @@ -268,7 +288,7 @@ public void shutdownNowUnregistersNetworkCallback_api24() { TestChannel delegateChannel = new TestChannel(); ManagedChannel androidChannel = new AndroidChannelBuilder.AndroidChannel( - delegateChannel, RuntimeEnvironment.application.getApplicationContext()); + delegateChannel, ApplicationProvider.getApplicationContext()); androidChannel.shutdownNow(); shadowOf(connectivityManager).setActiveNetworkInfo(WIFI_CONNECTED); @@ -318,6 +338,7 @@ private void notifyDefaultNetworkCallbacksOnLost(Network network) { } @Implementation(minSdk = N) + @Override protected void registerDefaultNetworkCallback( ConnectivityManager.NetworkCallback networkCallback) { defaultNetworkCallbacks.add(networkCallback); diff --git a/build.gradle b/build.gradle index e66203b6373..ecb5c7e011e 100644 --- a/build.gradle +++ b/build.gradle @@ -157,6 +157,7 @@ subprojects { mockito: 'org.mockito:mockito-core:2.28.2', truth: 'com.google.truth:truth:1.0.1', guava_testlib: "com.google.guava:guava-testlib:${guavaVersion}", + androidx_test: "androidx.test:core:1.2.0", robolectric: "org.robolectric:robolectric:4.3.1", // Benchmark dependencies diff --git a/buildscripts/kokoro/linux_artifacts.sh b/buildscripts/kokoro/linux_artifacts.sh index ed448ffa8c8..17402fe89b3 100755 --- a/buildscripts/kokoro/linux_artifacts.sh +++ b/buildscripts/kokoro/linux_artifacts.sh @@ -16,7 +16,6 @@ echo y | ${ANDROID_HOME}/tools/bin/sdkmanager "build-tools;28.0.3" LOCAL_MVN_TEMP=$(mktemp -d) pushd "$GRPC_JAVA_DIR/android" ../gradlew publish \ - --include-build "$GRPC_JAVA_DIR" \ -Dorg.gradle.parallel=false \ -PskipCodegen=true \ -PrepositoryDir="$LOCAL_MVN_TEMP" diff --git a/settings.gradle b/settings.gradle index 05a6da12d36..9d2517fcd18 100644 --- a/settings.gradle +++ b/settings.gradle @@ -86,4 +86,6 @@ if (settings.hasProperty('skipAndroid') && skipAndroid.toBoolean()) { println '*** Android SDK is required. To avoid building Android projects, set -PskipAndroid=true' include ":grpc-cronet" project(':grpc-cronet').projectDir = "$rootDir/cronet" as File + include ":grpc-android" + project(':grpc-android').projectDir = "$rootDir/android" as File }