diff --git a/rules_java_gapic/java_gapic.bzl b/rules_java_gapic/java_gapic.bzl index 76c238f593..183eaef6ca 100644 --- a/rules_java_gapic/java_gapic.bzl +++ b/rules_java_gapic/java_gapic.bzl @@ -121,6 +121,9 @@ def java_gapic_library( if gapic_yaml: file_args_dict[gapic_yaml] = "gapic-config" + if gapic_yaml: + file_args_dict[gapic_yaml] = "gapic-config" + # Check the allow-list. if service_yaml: service_yaml_in_allowlist = False diff --git a/src/main/java/com/google/api/generator/gapic/model/GapicServiceConfig.java b/src/main/java/com/google/api/generator/gapic/model/GapicServiceConfig.java index d161f44861..4e814b9508 100644 --- a/src/main/java/com/google/api/generator/gapic/model/GapicServiceConfig.java +++ b/src/main/java/com/google/api/generator/gapic/model/GapicServiceConfig.java @@ -42,19 +42,24 @@ public class GapicServiceConfig { private final List methodConfigs; private final Map methodConfigTable; + private final Map lroRetrySettingsTable; private final Map batchingSettingsTable; private GapicServiceConfig( List methodConfigs, Map methodConfigTable, + Map lroRetrySettingsTable, Map batchingSettingsTable) { this.methodConfigs = methodConfigs; this.methodConfigTable = methodConfigTable; + this.lroRetrySettingsTable = lroRetrySettingsTable; this.batchingSettingsTable = batchingSettingsTable; } public static GapicServiceConfig create( - ServiceConfig serviceConfig, Optional> batchingSettingsOpt) { + ServiceConfig serviceConfig, + Optional> lroRetrySettingsOpt, + Optional> batchingSettingsOpt) { // Keep this processing logic out of the constructor. Map methodConfigTable = new HashMap<>(); List methodConfigs = serviceConfig.getMethodConfigList(); @@ -65,6 +70,20 @@ public static GapicServiceConfig create( } } + Map lroRetrySettingsTable = new HashMap<>(); + if (lroRetrySettingsOpt.isPresent()) { + for (GapicLroRetrySettings lroRetrySetting : lroRetrySettingsOpt.get()) { + lroRetrySettingsTable.put( + MethodConfig.Name.newBuilder() + .setService( + String.format( + "%s.%s", lroRetrySetting.protoPakkage(), lroRetrySetting.serviceName())) + .setMethod(lroRetrySetting.methodName()) + .build(), + lroRetrySetting); + } + } + Map batchingSettingsTable = new HashMap<>(); if (batchingSettingsOpt.isPresent()) { for (GapicBatchingSettings batchingSetting : batchingSettingsOpt.get()) { @@ -79,7 +98,8 @@ public static GapicServiceConfig create( } } - return new GapicServiceConfig(methodConfigs, methodConfigTable, batchingSettingsTable); + return new GapicServiceConfig( + methodConfigs, methodConfigTable, lroRetrySettingsTable, batchingSettingsTable); } public Map getAllGapicRetrySettings(Service service) { @@ -118,10 +138,20 @@ public String getRetryParamsName(Service service, Method method) { return NO_RETRY_PARAMS_NAME; } + public boolean hasLroRetrySetting(Service service, Method method) { + return lroRetrySettingsTable.containsKey(toName(service, method)); + } + public boolean hasBatchingSetting(Service service, Method method) { return batchingSettingsTable.containsKey(toName(service, method)); } + public Optional getLroRetrySetting(Service service, Method method) { + return hasLroRetrySetting(service, method) + ? Optional.of(lroRetrySettingsTable.get(toName(service, method))) + : Optional.empty(); + } + public Optional getBatchingSetting(Service service, Method method) { return hasBatchingSetting(service, method) ? Optional.of(batchingSettingsTable.get(toName(service, method))) diff --git a/src/main/java/com/google/api/generator/gapic/protoparser/Parser.java b/src/main/java/com/google/api/generator/gapic/protoparser/Parser.java index 81da3803fc..1295906b61 100644 --- a/src/main/java/com/google/api/generator/gapic/protoparser/Parser.java +++ b/src/main/java/com/google/api/generator/gapic/protoparser/Parser.java @@ -21,6 +21,7 @@ import com.google.api.generator.gapic.model.Field; import com.google.api.generator.gapic.model.GapicBatchingSettings; import com.google.api.generator.gapic.model.GapicContext; +import com.google.api.generator.gapic.model.GapicLroRetrySettings; import com.google.api.generator.gapic.model.GapicServiceConfig; import com.google.api.generator.gapic.model.LongrunningOperation; import com.google.api.generator.gapic.model.Message; @@ -84,11 +85,13 @@ public static GapicContext parse(CodeGeneratorRequest request) { PluginArgumentParser.parseGapicYamlConfigPath(request); Optional> batchingSettingsOpt = BatchingSettingsConfigParser.parse(gapicYamlConfigPathOpt); + Optional> lroRetrySettingsOpt = + GapicLroRetrySettingsParser.parse(gapicYamlConfigPathOpt); Optional serviceConfigPathOpt = PluginArgumentParser.parseJsonConfigPath(request); String serviceConfigPath = serviceConfigPathOpt.isPresent() ? serviceConfigPathOpt.get() : null; Optional serviceConfigOpt = - ServiceConfigParser.parse(serviceConfigPath, batchingSettingsOpt); + ServiceConfigParser.parse(serviceConfigPath, lroRetrySettingsOpt, batchingSettingsOpt); Optional serviceYamlConfigPathOpt = PluginArgumentParser.parseServiceYamlConfigPath(request); diff --git a/src/main/java/com/google/api/generator/gapic/protoparser/ServiceConfigParser.java b/src/main/java/com/google/api/generator/gapic/protoparser/ServiceConfigParser.java index dcab2c4ec3..de36581176 100644 --- a/src/main/java/com/google/api/generator/gapic/protoparser/ServiceConfigParser.java +++ b/src/main/java/com/google/api/generator/gapic/protoparser/ServiceConfigParser.java @@ -15,6 +15,7 @@ package com.google.api.generator.gapic.protoparser; import com.google.api.generator.gapic.model.GapicBatchingSettings; +import com.google.api.generator.gapic.model.GapicLroRetrySettings; import com.google.api.generator.gapic.model.GapicServiceConfig; import com.google.common.annotations.VisibleForTesting; import com.google.common.base.Strings; @@ -28,12 +29,15 @@ public class ServiceConfigParser { public static Optional parse( - String serviceConfigFilePath, Optional> batchingSettingsOpt) { + String serviceConfigFilePath, + Optional> lroRetrySettingsOpt, + Optional> batchingSettingsOpt) { Optional rawConfigOpt = parseFile(serviceConfigFilePath); if (!rawConfigOpt.isPresent()) { return Optional.empty(); } - return Optional.of(GapicServiceConfig.create(rawConfigOpt.get(), batchingSettingsOpt)); + return Optional.of( + GapicServiceConfig.create(rawConfigOpt.get(), lroRetrySettingsOpt, batchingSettingsOpt)); } @VisibleForTesting diff --git a/src/test/java/com/google/api/generator/gapic/composer/BatchingDescriptorComposerTest.java b/src/test/java/com/google/api/generator/gapic/composer/BatchingDescriptorComposerTest.java index 258f9e7f61..4dd2d16b4d 100644 --- a/src/test/java/com/google/api/generator/gapic/composer/BatchingDescriptorComposerTest.java +++ b/src/test/java/com/google/api/generator/gapic/composer/BatchingDescriptorComposerTest.java @@ -89,7 +89,7 @@ public void batchingDescriptor_hasSubresponseField() { String jsonFilename = "pubsub_grpc_service_config.json"; Path jsonPath = Paths.get(ComposerConstants.TESTFILES_DIRECTORY, jsonFilename); Optional configOpt = - ServiceConfigParser.parse(jsonPath.toString(), batchingSettingsOpt); + ServiceConfigParser.parse(jsonPath.toString(), Optional.empty(), batchingSettingsOpt); assertTrue(configOpt.isPresent()); GapicServiceConfig config = configOpt.get(); @@ -151,7 +151,7 @@ public void batchingDescriptor_noSubresponseField() { String jsonFilename = "logging_grpc_service_config.json"; Path jsonPath = Paths.get(ComposerConstants.TESTFILES_DIRECTORY, jsonFilename); Optional configOpt = - ServiceConfigParser.parse(jsonPath.toString(), batchingSettingsOpt); + ServiceConfigParser.parse(jsonPath.toString(), Optional.empty(), batchingSettingsOpt); assertTrue(configOpt.isPresent()); GapicServiceConfig config = configOpt.get(); diff --git a/src/test/java/com/google/api/generator/gapic/composer/RetrySettingsComposerTest.java b/src/test/java/com/google/api/generator/gapic/composer/RetrySettingsComposerTest.java index b451dd2579..a93bce5c94 100644 --- a/src/test/java/com/google/api/generator/gapic/composer/RetrySettingsComposerTest.java +++ b/src/test/java/com/google/api/generator/gapic/composer/RetrySettingsComposerTest.java @@ -91,7 +91,7 @@ public void paramDefinitionsBlock_noConfigsFound() { String jsonFilename = "retrying_grpc_service_config.json"; Path jsonPath = Paths.get(ComposerConstants.TESTFILES_DIRECTORY, jsonFilename); Optional serviceConfigOpt = - ServiceConfigParser.parse(jsonPath.toString(), Optional.empty()); + ServiceConfigParser.parse(jsonPath.toString(), Optional.empty(), Optional.empty()); assertTrue(serviceConfigOpt.isPresent()); GapicServiceConfig serviceConfig = serviceConfigOpt.get(); @@ -129,7 +129,7 @@ public void paramDefinitionsBlock_basic() { String jsonFilename = "showcase_grpc_service_config.json"; Path jsonPath = Paths.get(ComposerConstants.TESTFILES_DIRECTORY, jsonFilename); Optional serviceConfigOpt = - ServiceConfigParser.parse(jsonPath.toString(), Optional.empty()); + ServiceConfigParser.parse(jsonPath.toString(), Optional.empty(), Optional.empty()); assertTrue(serviceConfigOpt.isPresent()); GapicServiceConfig serviceConfig = serviceConfigOpt.get(); @@ -181,7 +181,7 @@ public void codesDefinitionsBlock_noConfigsFound() { String jsonFilename = "retrying_grpc_service_config.json"; Path jsonPath = Paths.get(ComposerConstants.TESTFILES_DIRECTORY, jsonFilename); Optional serviceConfigOpt = - ServiceConfigParser.parse(jsonPath.toString(), Optional.empty()); + ServiceConfigParser.parse(jsonPath.toString(), Optional.empty(), Optional.empty()); assertTrue(serviceConfigOpt.isPresent()); GapicServiceConfig serviceConfig = serviceConfigOpt.get(); @@ -219,7 +219,7 @@ public void codesDefinitionsBlock_basic() { String jsonFilename = "showcase_grpc_service_config.json"; Path jsonPath = Paths.get(ComposerConstants.TESTFILES_DIRECTORY, jsonFilename); Optional serviceConfigOpt = - ServiceConfigParser.parse(jsonPath.toString(), Optional.empty()); + ServiceConfigParser.parse(jsonPath.toString(), Optional.empty(), Optional.empty()); assertTrue(serviceConfigOpt.isPresent()); GapicServiceConfig serviceConfig = serviceConfigOpt.get(); @@ -260,7 +260,7 @@ public void simpleBuilderExpr_basic() { String jsonFilename = "showcase_grpc_service_config.json"; Path jsonPath = Paths.get(ComposerConstants.TESTFILES_DIRECTORY, jsonFilename); Optional serviceConfigOpt = - ServiceConfigParser.parse(jsonPath.toString(), Optional.empty()); + ServiceConfigParser.parse(jsonPath.toString(), Optional.empty(), Optional.empty()); assertTrue(serviceConfigOpt.isPresent()); GapicServiceConfig serviceConfig = serviceConfigOpt.get(); @@ -343,7 +343,7 @@ public void lroBuilderExpr() { String jsonFilename = "showcase_grpc_service_config.json"; Path jsonPath = Paths.get(ComposerConstants.TESTFILES_DIRECTORY, jsonFilename); Optional serviceConfigOpt = - ServiceConfigParser.parse(jsonPath.toString(), Optional.empty()); + ServiceConfigParser.parse(jsonPath.toString(), Optional.empty(), Optional.empty()); assertTrue(serviceConfigOpt.isPresent()); GapicServiceConfig serviceConfig = serviceConfigOpt.get(); @@ -411,7 +411,7 @@ public void batchingSettings_minimalFlowControlSettings() { String jsonFilename = "pubsub_grpc_service_config.json"; Path jsonPath = Paths.get(ComposerConstants.TESTFILES_DIRECTORY, jsonFilename); Optional configOpt = - ServiceConfigParser.parse(jsonPath.toString(), batchingSettingsOpt); + ServiceConfigParser.parse(jsonPath.toString(), Optional.empty(), batchingSettingsOpt); assertTrue(configOpt.isPresent()); GapicServiceConfig config = configOpt.get(); @@ -491,7 +491,7 @@ public void batchingSettings_fullFlowControlSettings() { String jsonFilename = "logging_grpc_service_config.json"; Path jsonPath = Paths.get(ComposerConstants.TESTFILES_DIRECTORY, jsonFilename); Optional configOpt = - ServiceConfigParser.parse(jsonPath.toString(), batchingSettingsOpt); + ServiceConfigParser.parse(jsonPath.toString(), Optional.empty(), batchingSettingsOpt); assertTrue(configOpt.isPresent()); GapicServiceConfig config = configOpt.get(); diff --git a/src/test/java/com/google/api/generator/gapic/composer/ServiceStubSettingsClassComposerTest.java b/src/test/java/com/google/api/generator/gapic/composer/ServiceStubSettingsClassComposerTest.java index 527e513101..ea120724be 100644 --- a/src/test/java/com/google/api/generator/gapic/composer/ServiceStubSettingsClassComposerTest.java +++ b/src/test/java/com/google/api/generator/gapic/composer/ServiceStubSettingsClassComposerTest.java @@ -84,7 +84,7 @@ public void generateServiceStubSettingsClasses_batchingWithEmptyResponses() thro String jsonFilename = "logging_grpc_service_config.json"; Path jsonPath = Paths.get(ComposerConstants.TESTFILES_DIRECTORY, jsonFilename); Optional configOpt = - ServiceConfigParser.parse(jsonPath.toString(), batchingSettingsOpt); + ServiceConfigParser.parse(jsonPath.toString(), Optional.empty(), batchingSettingsOpt); assertTrue(configOpt.isPresent()); GapicServiceConfig config = configOpt.get(); @@ -127,7 +127,7 @@ public void generateServiceStubSettingsClasses_batchingWithNonemptyResponses() String jsonFilename = "pubsub_grpc_service_config.json"; Path jsonPath = Paths.get(ComposerConstants.TESTFILES_DIRECTORY, jsonFilename); Optional configOpt = - ServiceConfigParser.parse(jsonPath.toString(), batchingSettingsOpt); + ServiceConfigParser.parse(jsonPath.toString(), Optional.empty(), batchingSettingsOpt); assertTrue(configOpt.isPresent()); GapicServiceConfig config = configOpt.get(); @@ -158,7 +158,7 @@ public void generateServiceStubSettingsClasses_basic() throws IOException { String jsonFilename = "showcase_grpc_service_config.json"; Path jsonPath = Paths.get(ComposerConstants.TESTFILES_DIRECTORY, jsonFilename); Optional configOpt = - ServiceConfigParser.parse(jsonPath.toString(), Optional.empty()); + ServiceConfigParser.parse(jsonPath.toString(), Optional.empty(), Optional.empty()); assertTrue(configOpt.isPresent()); GapicServiceConfig config = configOpt.get(); diff --git a/src/test/java/com/google/api/generator/gapic/model/GapicServiceConfigTest.java b/src/test/java/com/google/api/generator/gapic/model/GapicServiceConfigTest.java index 43564350d5..30d5234a8d 100644 --- a/src/test/java/com/google/api/generator/gapic/model/GapicServiceConfigTest.java +++ b/src/test/java/com/google/api/generator/gapic/model/GapicServiceConfigTest.java @@ -39,7 +39,7 @@ public class GapicServiceConfigTest { private static final double EPSILON = 1e-4; - private static final String JSON_DIRECTORY = + private static final String TESTDATA_DIRECTORY = "src/test/java/com/google/api/generator/gapic/testdata/"; @Test @@ -49,10 +49,11 @@ public void serviceConfig_noConfigsFound() { Service service = parseService(echoFileDescriptor); String jsonFilename = "retrying_grpc_service_config.json"; - Path jsonPath = Paths.get(JSON_DIRECTORY, jsonFilename); + Path jsonPath = Paths.get(TESTDATA_DIRECTORY, jsonFilename); + Optional> lroRetrySettingsOpt = Optional.empty(); Optional> batchingSettingsOpt = Optional.empty(); Optional serviceConfigOpt = - ServiceConfigParser.parse(jsonPath.toString(), batchingSettingsOpt); + ServiceConfigParser.parse(jsonPath.toString(), lroRetrySettingsOpt, batchingSettingsOpt); assertTrue(serviceConfigOpt.isPresent()); GapicServiceConfig serviceConfig = serviceConfigOpt.get(); @@ -80,10 +81,11 @@ public void serviceConfig_basic() { Service service = parseService(echoFileDescriptor); String jsonFilename = "showcase_grpc_service_config.json"; - Path jsonPath = Paths.get(JSON_DIRECTORY, jsonFilename); + Path jsonPath = Paths.get(TESTDATA_DIRECTORY, jsonFilename); + Optional> lroRetrySettingsOpt = Optional.empty(); Optional> batchingSettingsOpt = Optional.empty(); Optional serviceConfigOpt = - ServiceConfigParser.parse(jsonPath.toString(), batchingSettingsOpt); + ServiceConfigParser.parse(jsonPath.toString(), lroRetrySettingsOpt, batchingSettingsOpt); assertTrue(serviceConfigOpt.isPresent()); GapicServiceConfig serviceConfig = serviceConfigOpt.get(); @@ -137,7 +139,7 @@ public void serviceConfig_withBatchingSettings() { Service service = parseService(echoFileDescriptor); String jsonFilename = "showcase_grpc_service_config.json"; - Path jsonPath = Paths.get(JSON_DIRECTORY, jsonFilename); + Path jsonPath = Paths.get(TESTDATA_DIRECTORY, jsonFilename); GapicBatchingSettings origBatchingSetting = GapicBatchingSettings.builder() @@ -152,9 +154,10 @@ public void serviceConfig_withBatchingSettings() { .build(); Optional> batchingSettingsOpt = Optional.of(Arrays.asList(origBatchingSetting)); + Optional> lroRetrySettingsOpt = Optional.empty(); Optional serviceConfigOpt = - ServiceConfigParser.parse(jsonPath.toString(), batchingSettingsOpt); + ServiceConfigParser.parse(jsonPath.toString(), lroRetrySettingsOpt, batchingSettingsOpt); assertTrue(serviceConfigOpt.isPresent()); GapicServiceConfig serviceConfig = serviceConfigOpt.get(); @@ -204,6 +207,49 @@ public void serviceConfig_withBatchingSettings() { assertFalse(serviceConfig.hasBatchingSetting(service, method)); } + @Test + public void serviceConfig_withLroRetrySettings() { + FileDescriptor echoFileDescriptor = EchoOuterClass.getDescriptor(); + ServiceDescriptor echoServiceDescriptor = echoFileDescriptor.getServices().get(0); + Service service = parseService(echoFileDescriptor); + + String jsonFilename = "showcase_grpc_service_config.json"; + Path jsonPath = Paths.get(TESTDATA_DIRECTORY, jsonFilename); + Optional> batchingSettingsOpt = Optional.empty(); + + // Construct LRO retry settings. + GapicLroRetrySettings origLroRetrySetting = + GapicLroRetrySettings.builder() + .setProtoPakkage("google.showcase.v1beta1") + .setServiceName("Echo") + .setMethodName("Echo") + .setInitialPollDelayMillis(100) + .setPollDelayMultiplier(1.5) + .setMaxPollDelayMillis(200) + .setTotalPollTimeoutMillis(300) + .build(); + Optional> lroRetrySettingsOpt = + Optional.of(Arrays.asList(origLroRetrySetting)); + + Optional serviceConfigOpt = + ServiceConfigParser.parse(jsonPath.toString(), lroRetrySettingsOpt, batchingSettingsOpt); + assertTrue(serviceConfigOpt.isPresent()); + GapicServiceConfig serviceConfig = serviceConfigOpt.get(); + + // Check LRO retry settings. + Method method = findMethod(service, "Echo"); + assertTrue(serviceConfig.hasLroRetrySetting(service, method)); + Optional retrievedSettingsOpt = + serviceConfig.getLroRetrySetting(service, method); + assertTrue(retrievedSettingsOpt.isPresent()); + GapicLroRetrySettings retrievedSettings = retrievedSettingsOpt.get(); + assertEquals( + origLroRetrySetting.initialPollDelayMillis(), retrievedSettings.initialPollDelayMillis()); + assertEquals(origLroRetrySetting.maxPollDelayMillis(), retrievedSettings.maxPollDelayMillis()); + assertEquals( + origLroRetrySetting.totalPollTimeoutMillis(), retrievedSettings.totalPollTimeoutMillis()); + } + private static Service parseService(FileDescriptor fileDescriptor) { Map messageTypes = Parser.parseMessages(fileDescriptor); Map resourceNames = Parser.parseResourceNames(fileDescriptor); diff --git a/test/integration/BUILD.bazel b/test/integration/BUILD.bazel index 162b68f2aa..072af0f3e5 100644 --- a/test/integration/BUILD.bazel +++ b/test/integration/BUILD.bazel @@ -83,6 +83,7 @@ java_gapic_assembly_gradle_pkg( java_gapic_library( name = "redis_java_gapic", srcs = ["@com_google_googleapis//google/cloud/redis/v1:redis_proto_with_info"], + gapic_yaml = "@com_google_googleapis//google/cloud/redis/v1:redis_gapic.yaml", grpc_service_config = "@com_google_googleapis//google/cloud/redis/v1:redis_grpc_service_config.json", package = "google.cloud.redis.v1", test_deps = [