From 69926430994a0bd0e7f6360630ce82e925c8817d Mon Sep 17 00:00:00 2001 From: Chengyuan Zhang Date: Tue, 3 Nov 2020 02:19:49 -0800 Subject: [PATCH 01/10] Create an Android library project and an application project base depending on it. --- .../androidTest/proto/sample.proto | 18 ++ .../build_base.gradle | 274 ++++++++++++++++++ .../main/AndroidManifest.xml | 22 ++ .../main/proto/helloworld.proto | 55 ++++ .../main/res/layout/activity_helloworld.xml | 54 ++++ .../main/res/mipmap-hdpi/ic_launcher.png | Bin 0 -> 3418 bytes .../main/res/mipmap-mdpi/ic_launcher.png | Bin 0 -> 2206 bytes .../main/res/mipmap-xhdpi/ic_launcher.png | Bin 0 -> 4842 bytes .../main/res/mipmap-xxhdpi/ic_launcher.png | Bin 0 -> 7718 bytes .../main/res/values/strings.xml | 3 + .../proguard-rules.pro | 17 ++ .../test/proto/unittest.proto | 18 ++ testProjectAndroidLibrary/build.gradle | 91 ++++++ testProjectAndroidLibrary/settings.gradle | 1 + .../src/main/AndroidManifest.xml | 5 + .../src/main/proto/messages.proto | 138 +++++++++ 16 files changed, 696 insertions(+) create mode 100644 testProjectAndroidDependentBase/androidTest/proto/sample.proto create mode 100644 testProjectAndroidDependentBase/build_base.gradle create mode 100644 testProjectAndroidDependentBase/main/AndroidManifest.xml create mode 100644 testProjectAndroidDependentBase/main/proto/helloworld.proto create mode 100644 testProjectAndroidDependentBase/main/res/layout/activity_helloworld.xml create mode 100644 testProjectAndroidDependentBase/main/res/mipmap-hdpi/ic_launcher.png create mode 100644 testProjectAndroidDependentBase/main/res/mipmap-mdpi/ic_launcher.png create mode 100644 testProjectAndroidDependentBase/main/res/mipmap-xhdpi/ic_launcher.png create mode 100644 testProjectAndroidDependentBase/main/res/mipmap-xxhdpi/ic_launcher.png create mode 100644 testProjectAndroidDependentBase/main/res/values/strings.xml create mode 100644 testProjectAndroidDependentBase/proguard-rules.pro create mode 100644 testProjectAndroidDependentBase/test/proto/unittest.proto create mode 100644 testProjectAndroidLibrary/build.gradle create mode 100644 testProjectAndroidLibrary/settings.gradle create mode 100644 testProjectAndroidLibrary/src/main/AndroidManifest.xml create mode 100644 testProjectAndroidLibrary/src/main/proto/messages.proto diff --git a/testProjectAndroidDependentBase/androidTest/proto/sample.proto b/testProjectAndroidDependentBase/androidTest/proto/sample.proto new file mode 100644 index 00000000..70d912cb --- /dev/null +++ b/testProjectAndroidDependentBase/androidTest/proto/sample.proto @@ -0,0 +1,18 @@ +syntax = "proto3"; + +option java_package = "com.example.tutorial"; +option java_outer_classname = "OuterSample"; +option java_multiple_files = true; + +// From the main sourceSet +import "helloworld.proto"; + +message Msg { + string foo = 1; + SecondMsg blah = 2; +} + +message SecondMsg { + int32 blah = 1; + helloworld.HelloReply reply = 2; +} diff --git a/testProjectAndroidDependentBase/build_base.gradle b/testProjectAndroidDependentBase/build_base.gradle new file mode 100644 index 00000000..fd327a65 --- /dev/null +++ b/testProjectAndroidDependentBase/build_base.gradle @@ -0,0 +1,274 @@ +repositories { + maven { url 'https://maven.google.com' } + maven { url "https://plugins.gradle.org/m2/" } +} + +buildscript { + repositories { + maven { url 'https://maven.google.com' } + maven { url "https://plugins.gradle.org/m2/" } + } +} + +android { + compileSdkVersion 26 + buildToolsVersion "26.0.1" + + defaultConfig { + applicationId "io.grpc.helloworldexample" + minSdkVersion 7 + targetSdkVersion 23 + versionCode 1 + versionName "1.0" + } + + flavorDimensions 'abi', 'version' + + productFlavors { + freeapp { + dimension 'version' + } + retailapp { + dimension 'version' + } + x86 { + dimension 'abi' + } + arm { + dimension 'abi' + } + } + + buildTypes { + release { + minifyEnabled false + proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' + } + } + + compileOptions { + sourceCompatibility = JavaVersion.VERSION_1_7 + targetCompatibility = JavaVersion.VERSION_1_7 + } + + packagingOptions { + exclude 'io/grpc/testing/integration/empty.proto' + exclude 'io/grpc/testing/integration/test.proto' + exclude 'io/grpc/testing/integration/messages.proto' + exclude 'tmp/stuff.proto' + } + + // https://github.com/square/okio/issues/58 + lintOptions { + warning 'InvalidPackage' + abortOnError false + } + + dexOptions { + javaMaxHeapSize "1g" + threadCount 1 // reduce predex thread count to limit memory usage + } +} + +protobuf { + protoc { + artifact = 'com.google.protobuf:protoc:3.0.0' + } + plugins { + grpc { + artifact = 'io.grpc:protoc-gen-grpc-java:1.0.0-pre2' + } + javalite { + artifact = 'com.google.protobuf:protoc-gen-javalite:3.0.0' + } + } + generateProtoTasks { + all()*.plugins { + javalite { } + } + ofNonTest()*.plugins { + grpc { + // Options added to --grpc_out + option 'lite' + } + } + } +} + +dependencies { + compile 'com.android.support:appcompat-v7:23.4.0' + compile 'com.squareup.okhttp:okhttp:2.7.5' + compile 'javax.annotation:javax.annotation-api:1.2' + compile 'com.google.protobuf:protobuf-lite:3.0.0' + compile 'io.grpc:grpc-core:1.0.0-pre2' + compile 'io.grpc:grpc-stub:1.0.0-pre2' + compile 'io.grpc:grpc-okhttp:1.0.0-pre2' + compile('io.grpc:grpc-protobuf-lite:1.0.0-pre2') { + // Otherwise Android compile will complain "Multiple dex files define ..." + exclude module: "protobuf-lite" + } + compile(project(':testProjectAndroidLibrary')) { + exclude module: "protobuf-lite" + } + protobuf files('lib/protos.jar') + testCompile 'junit:junit:4.12' +} + +def assertJavaCompileHasProtoGeneratedDir(Object variant, Collection codegenPlugins) { + rootProject.assertJavaCompileHasProtoGeneratedDir(project, variant.name, variant.javaCompileProvider.get(), codegenPlugins) +} + +afterEvaluate { + // 'gradle test' will run the unit tests, which is still experimental in + // Android plugin, and would do nothing with our setup. We make 'test' to + // trigger the "androidTest" Java compile tasks. + android.testVariants.each { testVariant -> + test.dependsOn testVariant.javaCompileProvider + } + + test.doLast { + assert [ + 'generateArmFreeappDebugAndroidTestProto', + 'generateArmFreeappDebugUnitTestProto', + 'generateArmFreeappReleaseUnitTestProto', + 'generateArmFreeappDebugProto', + 'generateArmFreeappReleaseProto', + 'generateArmRetailappDebugAndroidTestProto', + 'generateArmRetailappDebugUnitTestProto', + 'generateArmRetailappReleaseUnitTestProto', + 'generateArmRetailappDebugProto', + 'generateArmRetailappReleaseProto', + 'generateX86FreeappDebugAndroidTestProto', + 'generateX86FreeappDebugUnitTestProto', + 'generateX86FreeappReleaseUnitTestProto', + 'generateX86FreeappDebugProto', + 'generateX86FreeappReleaseProto', + 'generateX86RetailappDebugAndroidTestProto', + 'generateX86RetailappDebugUnitTestProto', + 'generateX86RetailappReleaseUnitTestProto', + 'generateX86RetailappDebugProto', + 'generateX86RetailappReleaseProto', + ] as Set == protobuf.generateProtoTasks.all().collect({ it.name }) as Set + + assert [ + 'generateArmFreeappDebugAndroidTestProto', + 'generateArmFreeappDebugUnitTestProto', + 'generateArmFreeappReleaseUnitTestProto', + 'generateArmRetailappDebugAndroidTestProto', + 'generateArmRetailappDebugUnitTestProto', + 'generateArmRetailappReleaseUnitTestProto', + 'generateX86FreeappDebugAndroidTestProto', + 'generateX86FreeappDebugUnitTestProto', + 'generateX86FreeappReleaseUnitTestProto', + 'generateX86RetailappDebugAndroidTestProto', + 'generateX86RetailappDebugUnitTestProto', + 'generateX86RetailappReleaseUnitTestProto', + ] as Set == protobuf.generateProtoTasks.ofTest().collect({ it.name }) as Set + + assert [ + 'generateArmFreeappDebugProto', + 'generateArmFreeappReleaseProto', + 'generateArmRetailappDebugProto', + 'generateArmRetailappReleaseProto', + 'generateX86FreeappDebugProto', + 'generateX86FreeappReleaseProto', + 'generateX86RetailappDebugProto', + 'generateX86RetailappReleaseProto', + ] as Set == protobuf.generateProtoTasks.ofNonTest().collect({ it.name }) as Set + + assert [ + 'generateArmFreeappDebugAndroidTestProto', + 'generateArmFreeappDebugUnitTestProto', + 'generateArmFreeappReleaseUnitTestProto', + 'generateArmFreeappDebugProto', + 'generateArmFreeappReleaseProto', + 'generateX86FreeappDebugAndroidTestProto', + 'generateX86FreeappDebugUnitTestProto', + 'generateX86FreeappReleaseUnitTestProto', + 'generateX86FreeappDebugProto', + 'generateX86FreeappReleaseProto', + ] as Set == protobuf.generateProtoTasks.ofFlavor('freeapp').collect({ it.name }) as Set + + assert [ + 'generateArmRetailappDebugAndroidTestProto', + 'generateArmRetailappDebugUnitTestProto', + 'generateArmRetailappReleaseUnitTestProto', + 'generateArmRetailappDebugProto', + 'generateArmRetailappReleaseProto', + 'generateX86RetailappDebugAndroidTestProto', + 'generateX86RetailappDebugUnitTestProto', + 'generateX86RetailappReleaseUnitTestProto', + 'generateX86RetailappDebugProto', + 'generateX86RetailappReleaseProto', + ] as Set == protobuf.generateProtoTasks.ofFlavor('retailapp').collect({ it.name }) as Set + + assert [ + 'generateX86FreeappDebugAndroidTestProto', + 'generateX86FreeappDebugUnitTestProto', + 'generateX86FreeappReleaseUnitTestProto', + 'generateX86FreeappDebugProto', + 'generateX86FreeappReleaseProto', + 'generateX86RetailappDebugAndroidTestProto', + 'generateX86RetailappDebugUnitTestProto', + 'generateX86RetailappReleaseUnitTestProto', + 'generateX86RetailappDebugProto', + 'generateX86RetailappReleaseProto', + ] as Set == protobuf.generateProtoTasks.ofFlavor('x86').collect({ it.name }) as Set + + assert [ + 'generateArmFreeappDebugAndroidTestProto', + 'generateArmFreeappDebugUnitTestProto', + 'generateArmFreeappReleaseUnitTestProto', + 'generateArmFreeappDebugProto', + 'generateArmFreeappReleaseProto', + 'generateArmRetailappDebugAndroidTestProto', + 'generateArmRetailappDebugUnitTestProto', + 'generateArmRetailappReleaseUnitTestProto', + 'generateArmRetailappDebugProto', + 'generateArmRetailappReleaseProto', + ] as Set == protobuf.generateProtoTasks.ofFlavor('arm').collect({ it.name }) as Set + + assert [ + 'generateArmFreeappDebugAndroidTestProto', + 'generateArmFreeappDebugUnitTestProto', + 'generateArmFreeappDebugProto', + 'generateArmRetailappDebugAndroidTestProto', + 'generateArmRetailappDebugUnitTestProto', + 'generateArmRetailappDebugProto', + 'generateX86FreeappDebugAndroidTestProto', + 'generateX86FreeappDebugUnitTestProto', + 'generateX86FreeappDebugProto', + 'generateX86RetailappDebugAndroidTestProto', + 'generateX86RetailappDebugUnitTestProto', + 'generateX86RetailappDebugProto' + ] as Set == protobuf.generateProtoTasks.ofBuildType('debug').collect({ it.name }) as Set + + assert [ + 'generateArmFreeappReleaseProto', + 'generateArmFreeappReleaseUnitTestProto', + 'generateArmRetailappReleaseProto', + 'generateArmRetailappReleaseUnitTestProto', + 'generateX86FreeappReleaseProto', + 'generateX86FreeappReleaseUnitTestProto', + 'generateX86RetailappReleaseProto', + 'generateX86RetailappReleaseUnitTestProto', + ] as Set == protobuf.generateProtoTasks.ofBuildType('release').collect({ it.name }) as Set + + assert ['generateX86FreeappDebugAndroidTestProto'] as Set == + protobuf.generateProtoTasks.ofVariant('x86FreeappDebugAndroidTest').collect({ it.name }) as Set + + // "androidTest" sourceSet is not a flavor + assert [] as Set == protobuf.generateProtoTasks.ofFlavor('androidTest').collect({ it.name }) as Set + + // "unitTest" sourceset is not a flavor + assert [] as Set == protobuf.generateProtoTasks.ofFlavor('unitTest').collect({ it.name }) as Set + + android.applicationVariants.each { variant -> + assertJavaCompileHasProtoGeneratedDir(variant, ['javalite', 'grpc']) + } + + android.testVariants.each { variant -> + assertJavaCompileHasProtoGeneratedDir(variant, ['javalite']) + } + } +} diff --git a/testProjectAndroidDependentBase/main/AndroidManifest.xml b/testProjectAndroidDependentBase/main/AndroidManifest.xml new file mode 100644 index 00000000..8c40f116 --- /dev/null +++ b/testProjectAndroidDependentBase/main/AndroidManifest.xml @@ -0,0 +1,22 @@ + + + + + + + + + + + + + + + diff --git a/testProjectAndroidDependentBase/main/proto/helloworld.proto b/testProjectAndroidDependentBase/main/proto/helloworld.proto new file mode 100644 index 00000000..8de3aa8e --- /dev/null +++ b/testProjectAndroidDependentBase/main/proto/helloworld.proto @@ -0,0 +1,55 @@ +// Copyright 2015, Google Inc. +// All rights reserved. +// +// Redistribution and use in source and binary forms, with or without +// modification, are permitted provided that the following conditions are +// met: +// +// * Redistributions of source code must retain the above copyright +// notice, this list of conditions and the following disclaimer. +// * Redistributions in binary form must reproduce the above +// copyright notice, this list of conditions and the following disclaimer +// in the documentation and/or other materials provided with the +// distribution. +// * Neither the name of Google Inc. nor the names of its +// contributors may be used to endorse or promote products derived from +// this software without specific prior written permission. +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +syntax = "proto3"; + +// From testProject: src/nano/proto +import "messages.proto"; + +option java_package = "io.grpc.helloworldexample"; + +package helloworld; + +// The greeting service definition. +service Greeter { + // Sends a greeting + rpc SayHello (HelloRequest) returns (HelloReply) {} +} + +// The request message containing the user's name. +message HelloRequest { + string name = 1; + // Uses message type from messages.proto + grpc.testing.SimpleContext context = 2; +} + +// The response message containing the greetings +message HelloReply { + string message = 1; +} diff --git a/testProjectAndroidDependentBase/main/res/layout/activity_helloworld.xml b/testProjectAndroidDependentBase/main/res/layout/activity_helloworld.xml new file mode 100644 index 00000000..00ca04ce --- /dev/null +++ b/testProjectAndroidDependentBase/main/res/layout/activity_helloworld.xml @@ -0,0 +1,54 @@ + + + + + + + + + + +