#!/bin/bash # Copyright 2021 The gRPC Authors # # Licensed under the Apache License, Version 2.0 (the "License"); # you may not use this file except in compliance with the License. # You may obtain a copy of the License at # # http://www.apache.org/licenses/LICENSE-2.0 # # Unless required by applicable law or agreed to in writing, software # distributed under the License is distributed on an "AS IS" BASIS, # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. # See the License for the specific language governing permissions and # limitations under the License. # This script generates a set of load test examples from templates. LOADTEST_CONFIG=tools/run_tests/performance/loadtest_config.py if (( $# < 1 )); then echo "Usage: ${0} " >&2 exit 1 fi if [[ ! -x "${LOADTEST_CONFIG}" ]]; then echo "${LOADTEST_CONFIG} not found." >&2 exit 1 fi outputbasedir="${1}" mkdir -p "${outputbasedir}/templates" example_file() { local scenario="${1}" local suffix="${2}" if [[ "${scenario#cpp_}" != "${scenario}" ]]; then echo "cxx${suffix}" return fi if [[ "${scenario#python_asyncio_}" != "${scenario}" ]]; then echo "python_asyncio${suffix}" return fi if [[ "${scenario#php7_protobuf_c_}" != "${scenario}" ]]; then echo "php7_protobuf_c${suffix}" return fi echo "${scenario%%_*}${suffix}" } example_language() { local filename="${1}" if [[ "${filename#cxx_}" != "${filename}" ]]; then echo "c++" return fi if [[ "${filename#python_asyncio_}" != "${filename}" ]]; then echo "python_asyncio" return fi if [[ "${filename#php7_protobuf_c_}" != "${filename}" ]]; then echo "php7_protobuf_c" return fi echo "${filename%%_*}" } scenarios=( "cpp_generic_async_streaming_ping_pong_secure" "csharp_protobuf_async_unary_ping_pong" "dotnet_protobuf_async_unary_ping_pong" "go_generic_sync_streaming_ping_pong_secure" "java_generic_async_streaming_ping_pong_secure" "node_to_node_generic_async_streaming_ping_pong_secure" "php7_protobuf_php_extension_to_cpp_protobuf_sync_unary_ping_pong" "php7_protobuf_c_extension_to_cpp_protobuf_sync_unary_ping_pong" "python_generic_sync_streaming_ping_pong" "python_asyncio_generic_async_streaming_ping_pong" "ruby_protobuf_sync_streaming_ping_pong" ) psm_scenarios=( "cpp_protobuf_async_unary_5000rpcs_1KB_psm" "csharp_protobuf_async_unary_5000rpcs_1KB_psm" "go_protobuf_async_unary_5000rpcs_1KB_psm" "java_protobuf_async_unary_5000rpcs_1KB_psm" "node_to_node_protobuf_async_unary_5000rpcs_1KB_psm" "php7_protobuf_php_extension_to_cpp_protobuf_async_unary_5000rpcs_1KB_psm" "php7_protobuf_c_extension_to_cpp_protobuf_async_unary_5000rpcs_1KB_psm" "python_protobuf_async_unary_5000rpcs_1KB_psm" "python_asyncio_protobuf_async_unary_5000rpcs_1KB_psm" "ruby_protobuf_async_unary_5000rpcs_1KB_psm" ) # Basic examples are intended to be runnable _as is_, so substitution keys # are stripped. Fields can be inserted manually following the pattern of the # prebuilt examples. basic_example() { local -r scenario="${1}" local -r outputdir="${2}" local -r outputfile="$(example_file "${scenario}" _example_loadtest.yaml)" local -r language="$(example_language "${outputfile}")" ${LOADTEST_CONFIG} \ -l "${language}" \ -t ./tools/run_tests/performance/templates/loadtest_template_basic_all_languages.yaml \ -s client_pool= -s server_pool= -s big_query_table= \ -s timeout_seconds=900 --prefix=examples -u basic -r "^${scenario}$" \ --allow_client_language=c++ --allow_server_language=c++ \ --allow_server_language=node \ -o "${outputdir}/${outputfile}" echo "Created example: ${outputdir}/${outputfile}" } # Prebuilt examples contain substitution keys, so must be processed before # running. prebuilt_example() { local -r scenario="${1}" local -r outputdir="${2}" local -r outputfile="$(example_file "${scenario}" _example_loadtest_with_prebuilt_workers.yaml)" local -r language="$(example_language "${outputfile}")" ${LOADTEST_CONFIG} \ -l "${language}" \ -t ./tools/run_tests/performance/templates/loadtest_template_prebuilt_all_languages.yaml \ -s driver_pool="\${driver_pool}" -s driver_image="\${driver_image}" \ -s client_pool="\${workers_pool}" -s server_pool="\${workers_pool}" \ -s big_query_table="\${big_query_table}" -s timeout_seconds=900 \ -s prebuilt_image_prefix="\${prebuilt_image_prefix}" \ -s prebuilt_image_tag="\${prebuilt_image_tag}" --prefix=examples -u prebuilt \ -a pool="\${workers_pool}" -r "^${scenario}$" \ --allow_client_language=c++ --allow_server_language=c++ \ --allow_server_language=node \ -o "${outputdir}/${outputfile}" echo "Created example: ${outputdir}/${outputfile}" } # PSM basic examples are intended to be runnable with only subsituding the # xds-server and sidecar images, so substitution keys for xds-server and # sidecar images are kept. psm_basic_example() { local -r scenario="${1}" local -r outputdir="${2}" local -r uniquifier="${3}" local -r outputfile="$(example_file "${scenario}" _example_loadtest_"${uniquifier}".yaml)" local -r language="$(example_language "${outputfile}")" ${LOADTEST_CONFIG} \ -l "${language}" \ -t ./tools/run_tests/performance/templates/loadtest_template_psm_"${uniquifier}"_basic_all_languages.yaml \ -s client_pool= -s server_pool= -s big_query_table= \ -s psm_image_prefix="\${psm_image_prefix}" \ -s psm_image_tag="\${psm_image_tag}" \ -s timeout_seconds=900 --prefix=psm-examples -u "${uniquifier}" -r "^${scenario}$" \ --allow_client_language=c++ --allow_server_language=c++ \ --allow_server_language=node \ --client_channels=8 \ --category=psm \ --server_threads=16 \ --offered_loads 5000 \ -o "${outputdir}/${outputfile}" echo "Created example: ${outputdir}/${outputfile}" } # PSM prebuilt examples contain substitution keys, so must be processed before # running. psm_prebuilt_example() { local -r scenario="${1}" local -r outputdir="${2}" local -r uniquifier="${3}" local -r outputfile="$(example_file "${scenario}" _example_loadtest_"${uniquifier}"_with_prebuilt_workers.yaml)" local -r language="$(example_language "${outputfile}")" ${LOADTEST_CONFIG} \ -l "${language}" \ -t ./tools/run_tests/performance/templates/loadtest_template_psm_"${uniquifier}"_prebuilt_all_languages.yaml \ -s driver_pool="\${driver_pool}" -s driver_image="\${driver_image}" \ -s client_pool="\${workers_pool}" -s server_pool="\${workers_pool}" \ -s big_query_table="\${big_query_table}" -s timeout_seconds=900 \ -s prebuilt_image_prefix="\${prebuilt_image_prefix}" \ -s prebuilt_image_tag="\${prebuilt_image_tag}" \ -s psm_image_prefix="\${psm_image_prefix}" \ -s psm_image_tag="\${psm_image_tag}" \ --prefix=psm-examples -u prebuilt-"${uniquifier}" -r "^${scenario}$" \ -a pool="\${workers_pool}" \ --allow_client_language=c++ --allow_server_language=c++ \ --allow_server_language=node \ --client_channels=8 \ --category=psm \ --server_threads=16 \ --offered_loads 5000 \ -o "${outputdir}/${outputfile}" echo "Created example: ${outputdir}/${outputfile}" } for scenario in "${scenarios[@]}"; do basic_example "${scenario}" "${outputbasedir}" done for scenario in "${scenarios[@]}"; do prebuilt_example "${scenario}" "${outputbasedir}/templates" done for scenario in "${psm_scenarios[@]}"; do psm_basic_example "${scenario}" "${outputbasedir}/templates/psm" "proxied" psm_basic_example "${scenario}" "${outputbasedir}/templates/psm" "proxyless" done for scenario in "${psm_scenarios[@]}"; do psm_prebuilt_example "${scenario}" "${outputbasedir}/templates/psm/prebuilt" "proxied" psm_prebuilt_example "${scenario}" "${outputbasedir}/templates/psm/prebuilt" "proxyless" done