From 336e8f36a90a55a50d2da0a7f5ad3d9bb3a87187 Mon Sep 17 00:00:00 2001 From: Joe Wang <106995533+JoeWang1127@users.noreply.github.com> Date: Tue, 12 Sep 2023 15:13:27 +0000 Subject: [PATCH] chore: add unit tests for `generate_library.sh` (#1964) * chore: add unit tests for `generate_library.sh` * add os types in unit tests * add more tests * fix broken test * use `uname` to get os info * split generate library golden tests * change library * add script level comments * remove golden tests * remove golden test in ci * change proto path * remove unused parameter * set x separately --- .../workflows/verify_library_generation.yaml | 6 +- library_generation/README.md | 1 - .../test/generate_library_unit_tests.sh | 221 +++++++++--------- library_generation/test/test_utilities.sh | 79 +++++++ library_generation/utilities.sh | 33 ++- 5 files changed, 213 insertions(+), 127 deletions(-) create mode 100755 library_generation/test/test_utilities.sh diff --git a/.github/workflows/verify_library_generation.yaml b/.github/workflows/verify_library_generation.yaml index f993116524..dabf01a458 100644 --- a/.github/workflows/verify_library_generation.yaml +++ b/.github/workflows/verify_library_generation.yaml @@ -31,7 +31,11 @@ jobs: --googleapis_gen_url https://cloud-java-bot:${{ secrets.CLOUD_JAVA_BOT_GITHUB_TOKEN }}@github.com/googleapis/googleapis-gen.git \ --os_type ${{ matrix.os }} unit_tests: - runs-on: ubuntu-22.04 + strategy: + matrix: + java: [ 8 ] + os: [ ubuntu-22.04, macos-12 ] + runs-on: ${{ matrix.os }} steps: - uses: actions/checkout@v3 - name: Run unit tests diff --git a/library_generation/README.md b/library_generation/README.md index 8279b32282..c16d92de0a 100644 --- a/library_generation/README.md +++ b/library_generation/README.md @@ -124,4 +124,3 @@ library_generation/generate_library.sh \ --rest_numeric_enums true \ --include_samples true ``` - diff --git a/library_generation/test/generate_library_unit_tests.sh b/library_generation/test/generate_library_unit_tests.sh index 84e3f11fd0..285f6dbe11 100755 --- a/library_generation/test/generate_library_unit_tests.sh +++ b/library_generation/test/generate_library_unit_tests.sh @@ -2,97 +2,57 @@ set -xeo pipefail -# Variables used to generate final result. -total_num=0 -succeed_num=0 -failed_num=0 -failed_tests="" -# Unit tests against ./utilities.sh +# Unit tests against ../utilities.sh script_dir=$(dirname "$(readlink -f "$0")") +source "${script_dir}"/test_utilities.sh source "${script_dir}"/../utilities.sh -# Helper functions, they shouldn't be called outside this file. -__assertEquals() { - local expected=$1 - local actual=$2 - if [[ "${expected}" == "${actual}" ]]; then - return 0 - fi - - echo "Error: expected ${expected}, got ${actual} instead." - return 1 -} - -__assertFileDoesNotExist() { - local expected_file=$1 - if [ ! -f "${expected_file}" ]; then - return 0 - fi - - echo "Error: ${expected_file} exists." - return 1 -} - -__test_executed() { - total_num=$((1 + total_num)) -} - -__test_succeed() { - succeed_num=$((1 + succeed_num)) -} - -__test_failed() { - failed_test=$1 - failed_num=$((1 + failed_num)) - failed_tests="${failed_tests} ${failed_test}" -} - # Unit tests extract_folder_name_test() { local path="google/cloud/aiplatform/v1/google-cloud-aiplatform-v1-java" local folder_name folder_name=$(extract_folder_name "${path}") - __assertEquals "google-cloud-aiplatform-v1-java" "${folder_name}" + assertEquals "google-cloud-aiplatform-v1-java" "${folder_name}" } get_grpc_version_succeed_with_valid_generator_version_test() { local actual_version actual_version=$(get_grpc_version "2.24.0") - __assertEquals "1.56.1" "${actual_version}" rm "gapic-generator-java-pom-parent-2.24.0.pom" + assertEquals "1.56.1" "${actual_version}" } get_grpc_version_failed_with_invalid_generator_version_test() { - local actual_version - actual_version=$(get_grpc_version "1.99.0") - __assertEquals "" "${actual_version}" + local res=0 + $(get_grpc_version "1.99.0") || res=$? + assertEquals 1 $((res)) } get_protobuf_version_succeed_with_valid_generator_version_test() { local actual_version actual_version=$(get_protobuf_version "2.24.0") - __assertEquals "23.2" "${actual_version}" + assertEquals "23.2" "${actual_version}" rm "gapic-generator-java-pom-parent-2.24.0.pom" } get_protobuf_version_failed_with_invalid_generator_version_test() { - local actual_version - actual_version=$(get_protobuf_version "1.99.0") - __assertEquals "" "${actual_version}" + local res=0 + $(get_protobuf_version "1.99.0") || res=$? + assertEquals 1 $((res)) } search_additional_protos_common_resources_test() { local proto_path="${script_dir}/resources/search_additional_proto/common_resources" local addition_protos addition_protos=$(search_additional_protos) - __assertEquals "google/cloud/common_resources.proto" "${addition_protos}" + assertEquals "google/cloud/common_resources.proto" "${addition_protos}" } search_additional_protos_iam_test() { local proto_path="${script_dir}/resources/search_additional_protos/iam" local addition_protos addition_protos=$(search_additional_protos) - __assertEquals \ + assertEquals \ "google/cloud/common_resources.proto google/iam/v1/iam_policy.proto" \ "${addition_protos}" } @@ -101,7 +61,7 @@ search_additional_protos_location_test() { local proto_path="${script_dir}/resources/search_additional_protos/location" local addition_protos addition_protos=$(search_additional_protos) - __assertEquals \ + assertEquals \ "google/cloud/common_resources.proto google/cloud/location/locations.proto" \ "${addition_protos}" } @@ -110,7 +70,7 @@ search_additional_protos_iam_location_test() { local proto_path="${script_dir}/resources/search_additional_protos/iam_location" local addition_protos addition_protos=$(search_additional_protos) - __assertEquals \ + assertEquals \ "google/cloud/common_resources.proto google/iam/v1/iam_policy.proto google/cloud/location/locations.proto" \ "${addition_protos}" } @@ -121,7 +81,7 @@ get_gapic_opts_with_rest_test() { local rest_numeric_enums="true" local gapic_opts gapic_opts="$(get_gapic_opts)" - __assertEquals \ + assertEquals \ "transport=grpc,rest-numeric-enums,grpc-service-config=${proto_path}/example_grpc_service_config.json,gapic-config=${proto_path}/example_gapic.yaml,api-service-config=${proto_path}/example.yaml" \ "${gapic_opts}" } @@ -132,7 +92,7 @@ get_gapic_opts_without_rest_test() { local rest_numeric_enums="false" local gapic_opts gapic_opts="$(get_gapic_opts)" - __assertEquals \ + assertEquals \ "transport=grpc,grpc-service-config=${proto_path}/example_grpc_service_config.json,gapic-config=${proto_path}/example_gapic.yaml,api-service-config=${proto_path}/example.yaml" \ "$gapic_opts" } @@ -141,21 +101,19 @@ remove_grpc_version_test() { local destination_path="${script_dir}/resources/gapic_options" cp "${destination_path}/QueryServiceGrpc_copy.java" "${destination_path}/QueryServiceGrpc.java" remove_grpc_version - local return_code=0 - if grep -q 'value = "by gRPC proto compiler",' "${destination_path}/QueryServiceGrpc.java"; then - echo "grpc version is removed." - else + local res=0 + if ! grep -q 'value = "by gRPC proto compiler",' "${destination_path}/QueryServiceGrpc.java"; then echo "Error: grpc version is not removed." - return_code=1 + res=1 fi + assertEquals 0 $((res)) rm "${destination_path}/QueryServiceGrpc.java" - return "${return_code}" } download_generator_success_with_valid_version_test() { download_generator "2.24.0" - __assertFileExists "gapic-generator-java-2.24.0.jar" + assertFileOrDirectoryExists "gapic-generator-java-2.24.0.jar" rm "gapic-generator-java-2.24.0.jar" } @@ -168,64 +126,115 @@ download_generator_failed_with_invalid_version_test() { # shell. local res=0 $(download_generator "1.99.0") || res=$? - __assertEquals 1 $((res)) + assertEquals 1 $((res)) } download_protobuf_succeed_with_valid_version_linux_test() { download_protobuf "23.2" "linux-x86_64" - __assertFileExists "protobuf-23.2" + assertFileOrDirectoryExists "protobuf-23.2" rm -rf "protobuf-23.2" } download_protobuf_succeed_with_valid_version_macos_test() { download_protobuf "23.2" "osx-x86_64" - __assertFileExists "protobuf-23.2" + assertFileOrDirectoryExists "protobuf-23.2" rm -rf "protobuf-23.2" "google" } download_protobuf_failed_with_invalid_version_linux_test() { local res=0 $(download_protobuf "22.99" "linux-x86_64") || res=$? - __assertEquals 1 $((res)) + assertEquals 1 $((res)) } download_protobuf_failed_with_invalid_arch_test() { local res=0 $(download_protobuf "23.2" "customized-x86_64") || res=$? - __assertEquals 1 $((res)) + assertEquals 1 $((res)) } download_grpc_plugin_succeed_with_valid_version_linux_test() { download_grpc_plugin "1.55.1" "linux-x86_64" - __assertFileExists "protoc-gen-grpc-java-1.55.1-linux-x86_64.exe" + assertFileOrDirectoryExists "protoc-gen-grpc-java-1.55.1-linux-x86_64.exe" rm "protoc-gen-grpc-java-1.55.1-linux-x86_64.exe" } download_grpc_plugin_succeed_with_valid_version_macos_test() { download_grpc_plugin "1.55.1" "osx-x86_64" - __assertFileExists "protoc-gen-grpc-java-1.55.1-osx-x86_64.exe" + assertFileOrDirectoryExists "protoc-gen-grpc-java-1.55.1-osx-x86_64.exe" rm "protoc-gen-grpc-java-1.55.1-osx-x86_64.exe" } download_grpc_plugin_failed_with_invalid_version_linux_test() { local res=0 $(download_grpc_plugin "0.99.0" "linux-x86_64") || res=$? - __assertEquals 1 $((res)) + assertEquals 1 $((res)) } download_grpc_plugin_failed_with_invalid_arch_test() { local res=0 $(download_grpc_plugin "1.55.1" "customized-x86_64") || res=$? - __assertEquals 1 $((res)) + assertEquals 1 $((res)) +} + +generate_library_failed_with_invalid_generator_version() { + local destination="google-cloud-alloydb-v1-java" + local res=0 + cd "${script_dir}/resources" + $("${script_dir}"/../generate_library.sh \ + -p google/cloud/alloydb/v1 \ + -d ../"${destination}" \ + --gapic_generator_version 1.99.0 \ + --protobuf_version 23.2 \ + --grpc_version 1.55.1 \ + --transport grpc+rest \ + --rest_numeric_enums true \ + --os_architecture "$(__get_os_architecture)") || res=$? + assertEquals 1 $((res)) + # still need to clean up potential downloaded tooling. + cleanup "${destination}" } -get_config_from_valid_BUILD_test() { +generate_library_failed_with_invalid_protobuf_version() { + local destination="google-cloud-alloydb-v1-java" + local res=0 + cd "${script_dir}/resources" + $("${script_dir}"/../generate_library.sh \ + -p google/cloud/alloydb/v1 \ + -d ../"${destination}" \ + --gapic_generator_version 2.24.0 \ + --protobuf_version 22.99 \ + --grpc_version 1.55.1 \ + --transport grpc+rest \ + --rest_numeric_enums true \ + --os_architecture "$(__get_os_architecture)") || res=$? + assertEquals 1 $((res)) + # still need to clean up potential downloaded tooling. + cleanup "${destination}" +} + +generate_library_failed_with_invalid_grpc_version() { + local destination="google-cloud-alloydb-v1-java" + local res=0 + cd "${script_dir}/resources" + $("${script_dir}"/../generate_library.sh \ + -p google/cloud/alloydb/v1 \ + -d ../"${destination}" \ + --gapic_generator_version 2.24.0 \ + --grpc_version 0.99.0 \ + --transport grpc+rest \ + --rest_numeric_enums true \ + --os_architecture "$(__get_os_architecture)") || res=$? + assertEquals 1 $((res)) + # still need to clean up potential downloaded tooling. + cleanup "${destination}" +} + +get_config_from_valid_BUILD_matched_test() { build_file="${script_dir}/resources/misc/TESTBUILD.bazel" rule="java_gapic_library(" # the pattern we expect to find in the BUILD file pattern_should_match="name" - # the pattern that we should not find in the BUILD file - pattern_should_not_match="should-not-match" # default value if the pattern was not found if_matched_return="got-a-match" if_not_matched_return="no-match" @@ -236,7 +245,17 @@ get_config_from_valid_BUILD_test() { "${if_not_matched_return}" \ "${if_matched_return}" ) - __assertEquals "${pattern_matched_result}" "${if_matched_return}" + assertEquals "${if_matched_return}" "${pattern_matched_result}" +} + +get_config_from_valid_BUILD_not_match_test() { + build_file="${script_dir}/resources/misc/TESTBUILD.bazel" + rule="java_gapic_library(" + # the pattern that we should not find in the BUILD file + pattern_should_not_match="should-not-match" + # default value if the pattern was not found + if_matched_return="got-a-match" + if_not_matched_return="no-match" pattern_not_matched_result=$(get_config_from_BUILD \ "${build_file}" \ "${rule}" \ @@ -244,21 +263,25 @@ get_config_from_valid_BUILD_test() { "${if_not_matched_return}" \ "${if_matched_return}" ) - __assertEquals "${pattern_not_matched_result}" "${if_not_matched_return}" + assertEquals "${if_not_matched_return}" "${pattern_not_matched_result}" } get_version_from_valid_WORKSPACE_test() { workspace_file="${script_dir}/resources/misc/TESTWORKSPACE" obtained_ggj_version=$(get_version_from_WORKSPACE "_gapic_generator_java_version" "${workspace_file}") - __assertEquals '2.25.1-SNAPSHOT' "${obtained_ggj_version}" + assertEquals '2.25.1-SNAPSHOT' "${obtained_ggj_version}" } -get_version_from_valid_versions_txt_test() { +get_generator_version_from_valid_versions_txt_test() { versions_file="${script_dir}/resources/misc/testversions.txt" obtained_ggj_version=$(get_version_from_versions_txt "${versions_file}" "gapic-generator-java") - __assertEquals '2.25.1-SNAPSHOT' "${obtained_ggj_version}" + assertEquals '2.25.1-SNAPSHOT' "${obtained_ggj_version}" +} + +get_gax_version_from_valid_versions_txt_test() { + versions_file="${script_dir}/resources/misc/testversions.txt" obtained_gax_version=$(get_version_from_versions_txt "${versions_file}" "gax") - __assertEquals '2.33.1-SNAPSHOT' "${obtained_gax_version}" + assertEquals '2.33.1-SNAPSHOT' "${obtained_gax_version}" } # Execute tests. @@ -286,30 +309,16 @@ test_list=( download_grpc_plugin_succeed_with_valid_version_macos_test download_grpc_plugin_failed_with_invalid_version_linux_test download_grpc_plugin_failed_with_invalid_arch_test - get_config_from_valid_BUILD_test + generate_library_failed_with_invalid_generator_version + generate_library_failed_with_invalid_protobuf_version + generate_library_failed_with_invalid_grpc_version + get_config_from_valid_BUILD_matched_test + get_config_from_valid_BUILD_not_match_test get_version_from_valid_WORKSPACE_test - get_version_from_valid_versions_txt_test + get_generator_version_from_valid_versions_txt_test + get_gax_version_from_valid_versions_txt_test ) -for ut in "${test_list[@]}"; do - pushd "${script_dir}" - __test_executed - result=0 - "${ut}" || result=$? - if [[ "${result}" == 0 ]]; then - __test_succeed - else - __test_failed "${ut}" - fi - popd -done - -echo "Test result: ${total_num} tests executed, ${succeed_num} succeed, ${failed_num} failed." -if [[ "${total_num}" == "${succeed_num}" ]]; then - echo "All tests passed." - exit -fi - -echo "Test failed." -echo "Failed test(s): ${failed_tests}." -exit 1 +pushd "${script_dir}" +execute_tests "${test_list[@]}" +popd diff --git a/library_generation/test/test_utilities.sh b/library_generation/test/test_utilities.sh new file mode 100755 index 0000000000..1f3f022a1b --- /dev/null +++ b/library_generation/test/test_utilities.sh @@ -0,0 +1,79 @@ +#!/usr/bin/env bash + +set -xeo pipefail + +# Utility functions commonly used in test cases. + +# Variables used to generate final result +total_num=0 +succeed_num=0 +failed_num=0 +failed_tests="" + +# Helper functions, they shouldn't be called outside this file. +__test_executed() { + total_num=$((1 + total_num)) +} + +__test_succeed() { + succeed_num=$((1 + succeed_num)) +} + +__test_failed() { + failed_test=$1 + failed_num=$((1 + failed_num)) + failed_tests="${failed_tests} ${failed_test}" +} + +assertEquals() { + local expected=$1 + local actual=$2 + if [[ "${expected}" == "${actual}" ]]; then + __test_succeed + return + fi + + echo "Error: expected ${expected}, got ${actual} instead." + __test_failed "${ut}" +} + +assertFileOrDirectoryExists() { + local expected_file=$1 + if [ -d "${expected_file}" ]|| [ -f "${expected_file}" ]; then + __test_succeed + return + fi + + echo "Error: ${expected_file} does not exist." + __test_failed "${ut}" +} + +# Clean up generated files, tooling when testing `generate_library.sh`. +cleanup() { + local library_directory=$1 + rm -rf ../"${library_directory}" \ + google/protobuf \ + protobuf-* \ + gapic-generator-java-*.jar \ + gapic-generator-java-pom-parent-*.pom \ + protoc-gen-grpc-*.exe +} + +execute_tests() { + local test_list=("$@") + for ut in "${test_list[@]}"; do + echo "========== Execute ${ut} ==========" + __test_executed + "${ut}" + done + + echo "Test result: ${total_num} tests executed, ${succeed_num} succeed, ${failed_num} failed." + if [[ "${total_num}" == "${succeed_num}" ]]; then + echo "All tests passed." + exit + fi + + echo "Test failed." + echo "Failed test(s): ${failed_tests}." + exit 1 +} diff --git a/library_generation/utilities.sh b/library_generation/utilities.sh index d45af802c4..70dccc6c6c 100755 --- a/library_generation/utilities.sh +++ b/library_generation/utilities.sh @@ -178,7 +178,6 @@ download_protobuf() { fi protoc_path=protobuf-${protobuf_version}/bin - echo "protoc version: $("$protoc_path"/protoc --version)" } download_grpc_plugin() { @@ -223,13 +222,12 @@ get_version_from_WORKSPACE() { version_key_word=$1 workspace=$2 version=$(\ - cat "$workspace" |\ - grep "$version_key_word" |\ + grep "${version_key_word}" "${workspace}" |\ head -n 1 |\ sed 's/\(.*\) = "\(.*\)"\(.*\)/\2/' |\ sed 's/[a-zA-Z-]*//' ) - echo "$version" + echo "${version}" } # Used to obtain configuration values from a bazel BUILD file @@ -244,12 +242,11 @@ get_config_from_BUILD() { default=$4 if_match=$5 - result="$default" - if grep -A 15 "$rule" "$build_file" | grep -q "$pattern"; then - result="$if_match" + result="${default}" + if grep -A 15 "${rule}" "${build_file}" | grep -q "${pattern}"; then + result="${if_match}" fi - echo "$result" - + echo "${result}" } # Convenience function to clone only the necessary folders from a git repository @@ -258,13 +255,13 @@ sparse_clone() { paths=$2 commitish=$3 clone_dir=$(basename "${repo_url%.*}") - rm -rf "$clone_dir" - git clone -n --depth=1 --no-single-branch --filter=tree:0 "$repo_url" - cd "$clone_dir" - if [ ! -z $commitish ]; then - git checkout $commitish + rm -rf "${clone_dir}" + git clone -n --depth=1 --no-single-branch --filter=tree:0 "${repo_url}" + cd "${clone_dir}" + if [ -n "${commitish}" ]; then + git checkout "${commitish}" fi - git sparse-checkout set --no-cone $paths + git sparse-checkout set --no-cone ${paths} git checkout cd .. } @@ -273,8 +270,6 @@ sparse_clone() { get_version_from_versions_txt() { versions=$1 key=$2 - version=$(cat "$versions" | grep "$key:" | cut -d: -f3) # 3rd field is snapshot - echo $version + version=$(grep "$key:" "${versions}" | cut -d: -f3) # 3rd field is snapshot + echo "${version}" } - -