Skip to content

Commit a87b09a

Browse files
authored
Paginated methods returning publisher or iterable implement logic in … (#4046)
* Paginated methods returning publisher or iterable implement logic in interface instead of throwing unsupported exception * Added internal annotation to class
1 parent 2a15452 commit a87b09a

30 files changed

+346
-1366
lines changed

codegen/src/main/java/software/amazon/awssdk/codegen/emitters/tasks/CommonGeneratorTasks.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,6 @@ class CommonGeneratorTasks extends CompositeGeneratorTask {
2828
new ModelClassGeneratorTasks(params),
2929
new PackageInfoGeneratorTasks(params),
3030
new BaseExceptionClassGeneratorTasks(params),
31-
new ClientOptionsClassGeneratorTasks(params));
31+
new CommonInternalGeneratorTasks(params));
3232
}
3333
}
Lines changed: 15 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -15,26 +15,35 @@
1515

1616
package software.amazon.awssdk.codegen.emitters.tasks;
1717

18-
import java.util.Collections;
18+
import java.util.Arrays;
1919
import java.util.List;
2020
import software.amazon.awssdk.codegen.emitters.GeneratorTask;
2121
import software.amazon.awssdk.codegen.emitters.GeneratorTaskParams;
2222
import software.amazon.awssdk.codegen.emitters.PoetGeneratorTask;
2323
import software.amazon.awssdk.codegen.poet.client.SdkClientOptions;
24+
import software.amazon.awssdk.codegen.poet.common.UserAgentUtilsSpec;
2425

25-
public class ClientOptionsClassGeneratorTasks extends BaseGeneratorTasks {
26+
public class CommonInternalGeneratorTasks extends BaseGeneratorTasks {
2627
private final GeneratorTaskParams params;
2728

28-
public ClientOptionsClassGeneratorTasks(GeneratorTaskParams params) {
29+
public CommonInternalGeneratorTasks(GeneratorTaskParams params) {
2930
super(params);
3031
this.params = params;
3132
}
3233

3334
@Override
3435
protected List<GeneratorTask> createTasks() throws Exception {
35-
return Collections.singletonList(
36-
new PoetGeneratorTask(clientOptionsDir(), params.getModel().getFileHeader(), new SdkClientOptions(params.getModel()))
37-
);
36+
return Arrays.asList(createClientOptionTask(), createUserAgentTask());
37+
}
38+
39+
private PoetGeneratorTask createClientOptionTask() {
40+
return new PoetGeneratorTask(clientOptionsDir(), params.getModel().getFileHeader(),
41+
new SdkClientOptions(params.getModel()));
42+
}
43+
44+
private PoetGeneratorTask createUserAgentTask() {
45+
return new PoetGeneratorTask(clientOptionsDir(), params.getModel().getFileHeader(),
46+
new UserAgentUtilsSpec(params.getModel()));
3847
}
3948

4049
private String clientOptionsDir() {

codegen/src/main/java/software/amazon/awssdk/codegen/poet/PoetExtension.java

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -73,6 +73,10 @@ public ClassName getServiceConfigClass() {
7373
+ model.getMetadata().getServiceName() + "ServiceClientConfiguration");
7474
}
7575

76+
public ClassName getUserAgentClass() {
77+
return ClassName.get(model.getMetadata().getFullClientInternalPackageName(), "UserAgentUtils");
78+
}
79+
7680
/**
7781
* @param operationName Name of the operation
7882
* @return A Poet {@link ClassName} for the response type of a paginated operation in the base service package.

codegen/src/main/java/software/amazon/awssdk/codegen/poet/client/AsyncClientClass.java

Lines changed: 0 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,6 @@
2424
import static javax.lang.model.element.Modifier.STATIC;
2525
import static software.amazon.awssdk.codegen.internal.Constant.EVENT_PUBLISHER_PARAM_NAME;
2626
import static software.amazon.awssdk.codegen.poet.client.ClientClassUtils.addS3ArnableFieldCode;
27-
import static software.amazon.awssdk.codegen.poet.client.ClientClassUtils.applyPaginatorUserAgentMethod;
2827
import static software.amazon.awssdk.codegen.poet.client.ClientClassUtils.applySignerOverrideMethod;
2928
import static software.amazon.awssdk.codegen.poet.client.SyncClientClass.getProtocolSpecs;
3029

@@ -155,10 +154,6 @@ protected void addAdditionalMethods(TypeSpec.Builder type) {
155154
.addMethod(protocolSpec.initProtocolFactory(model))
156155
.addMethod(resolveMetricPublishersMethod());
157156

158-
if (model.hasPaginators()) {
159-
type.addMethod(applyPaginatorUserAgentMethod(poetExtensions, model));
160-
}
161-
162157
if (model.containsRequestSigners() || model.containsRequestEventStreams() || hasStreamingV4AuthOperations()) {
163158
type.addMethod(applySignerOverrideMethod(poetExtensions, model));
164159
type.addMethod(isSignerOverriddenOnClientMethod());
@@ -196,9 +191,6 @@ protected List<MethodSpec> operations() {
196191
private Stream<MethodSpec> operations(OperationModel opModel) {
197192
List<MethodSpec> methods = new ArrayList<>();
198193
methods.add(traditionalMethod(opModel));
199-
if (opModel.isPaginated()) {
200-
methods.add(paginatedTraditionalMethod(opModel));
201-
}
202194
return methods.stream();
203195
}
204196

@@ -420,14 +412,6 @@ protected MethodSpec.Builder operationBody(MethodSpec.Builder builder, Operation
420412
return builder;
421413
}
422414

423-
@Override
424-
protected MethodSpec.Builder paginatedMethodBody(MethodSpec.Builder builder, OperationModel opModel) {
425-
return builder.addModifiers(PUBLIC)
426-
.addStatement("return new $T(this, applyPaginatorUserAgent($L))",
427-
poetExtensions.getResponseClassForPaginatedAsyncOperation(opModel.getOperationName()),
428-
opModel.getInput().getVariableName());
429-
}
430-
431415
@Override
432416
public ClassName className() {
433417
return className;

codegen/src/main/java/software/amazon/awssdk/codegen/poet/client/AsyncClientInterface.java

Lines changed: 21 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -201,21 +201,34 @@ private MethodSpec builder() {
201201
*/
202202
protected Iterable<MethodSpec> operations() {
203203
return model.getOperations().values().stream()
204-
.flatMap(this::operationsAndSimpleMethods)
204+
.flatMap(this::operationsWithVariants)
205205
.sorted(Comparator.comparing(m -> m.name))
206206
.collect(toList());
207207
}
208208

209-
private Stream<MethodSpec> operationsAndSimpleMethods(OperationModel operationModel) {
209+
private Stream<MethodSpec> operationsWithVariants(OperationModel operationModel) {
210210
List<MethodSpec> methods = new ArrayList<>();
211-
methods.addAll(traditionalMethods(operationModel));
212-
methods.addAll(overloadMethods(operationModel));
211+
methods.addAll(traditionalMethodWithConsumerVariant(operationModel));
212+
methods.addAll(overloadedMethods(operationModel));
213213
methods.addAll(paginatedMethods(operationModel));
214214
return methods.stream()
215215
// Add Deprecated annotation if needed to all overloads
216216
.map(m -> DeprecationUtils.checkDeprecated(operationModel, m));
217217
}
218218

219+
/**
220+
* Generates the traditional method for an operation (i.e. one that takes a request and returns a response).
221+
*/
222+
private List<MethodSpec> traditionalMethodWithConsumerVariant(OperationModel opModel) {
223+
List<MethodSpec> methods = new ArrayList<>();
224+
String consumerBuilderJavadoc = consumerBuilderJavadoc(opModel, SimpleMethodOverload.NORMAL);
225+
226+
methods.add(traditionalMethod(opModel));
227+
methods.add(ClientClassUtils.consumerBuilderVariant(methods.get(0), consumerBuilderJavadoc));
228+
229+
return methods;
230+
}
231+
219232
private List<MethodSpec> paginatedMethods(OperationModel opModel) {
220233
List<MethodSpec> methods = new ArrayList<>();
221234

@@ -251,7 +264,9 @@ protected MethodSpec paginatedTraditionalMethod(OperationModel opModel) {
251264

252265
protected MethodSpec.Builder paginatedMethodBody(MethodSpec.Builder builder, OperationModel operationModel) {
253266
return builder.addModifiers(DEFAULT, PUBLIC)
254-
.addStatement("throw new $T()", UnsupportedOperationException.class);
267+
.addStatement("return new $T(this, $L)",
268+
poetExtensions.getResponseClassForPaginatedAsyncOperation(operationModel.getOperationName()),
269+
operationModel.getInput().getVariableName());
255270
}
256271

257272
private MethodSpec paginatedSimpleMethod(OperationModel opModel) {
@@ -274,7 +289,7 @@ private MethodSpec paginatedSimpleMethod(OperationModel opModel) {
274289
* @param opModel Operation to generate simple methods for.
275290
* @return All simple method overloads for a given operation.
276291
*/
277-
private List<MethodSpec> overloadMethods(OperationModel opModel) {
292+
private List<MethodSpec> overloadedMethods(OperationModel opModel) {
278293
String consumerBuilderFileJavadoc = consumerBuilderJavadoc(opModel, SimpleMethodOverload.FILE);
279294

280295
List<MethodSpec> methodOverloads = new ArrayList<>();
@@ -312,20 +327,6 @@ protected MethodSpec.Builder operationBody(MethodSpec.Builder builder, Operation
312327
.addStatement("throw new $T()", UnsupportedOperationException.class);
313328
}
314329

315-
/**
316-
* Generates the traditional method for an operation (i.e. one that takes a request and returns a response).
317-
*/
318-
private List<MethodSpec> traditionalMethods(OperationModel opModel) {
319-
List<MethodSpec> methods = new ArrayList<>();
320-
321-
methods.add(traditionalMethod(opModel));
322-
323-
String consumerBuilderJavadoc = consumerBuilderJavadoc(opModel, SimpleMethodOverload.NORMAL);
324-
methods.add(ClientClassUtils.consumerBuilderVariant(methods.get(0), consumerBuilderJavadoc));
325-
326-
return methods;
327-
}
328-
329330
protected MethodSpec traditionalMethod(OperationModel opModel) {
330331
ClassName responsePojoType = getPojoResponseType(opModel);
331332
ClassName requestType = ClassName.get(modelPackage, opModel.getInput().getVariableType());

codegen/src/main/java/software/amazon/awssdk/codegen/poet/client/ClientClassUtils.java

Lines changed: 0 additions & 37 deletions
Original file line numberDiff line numberDiff line change
@@ -40,15 +40,12 @@
4040
import software.amazon.awssdk.codegen.model.service.HostPrefixProcessor;
4141
import software.amazon.awssdk.codegen.poet.PoetExtension;
4242
import software.amazon.awssdk.codegen.poet.PoetUtils;
43-
import software.amazon.awssdk.core.ApiName;
4443
import software.amazon.awssdk.core.signer.Signer;
45-
import software.amazon.awssdk.core.util.VersionInfo;
4644
import software.amazon.awssdk.utils.HostnameValidator;
4745
import software.amazon.awssdk.utils.StringUtils;
4846
import software.amazon.awssdk.utils.Validate;
4947

5048
final class ClientClassUtils {
51-
private static final String PAGINATOR_USER_AGENT = "PAGINATED";
5249

5350
private ClientClassUtils() {
5451
}
@@ -85,40 +82,6 @@ static MethodSpec consumerBuilderVariant(MethodSpec spec, String javadoc) {
8582
return result.build();
8683
}
8784

88-
static MethodSpec applyPaginatorUserAgentMethod(PoetExtension poetExtensions, IntermediateModel model) {
89-
90-
TypeVariableName typeVariableName =
91-
TypeVariableName.get("T", poetExtensions.getModelClass(model.getSdkRequestBaseClassName()));
92-
93-
ParameterizedTypeName parameterizedTypeName = ParameterizedTypeName
94-
.get(ClassName.get(Consumer.class), ClassName.get(AwsRequestOverrideConfiguration.Builder.class));
95-
96-
CodeBlock codeBlock = CodeBlock.builder()
97-
.addStatement("$T userAgentApplier = b -> b.addApiName($T.builder().version"
98-
+ "($T.SDK_VERSION).name($S).build())",
99-
parameterizedTypeName, ApiName.class,
100-
VersionInfo.class,
101-
PAGINATOR_USER_AGENT)
102-
.addStatement("$T overrideConfiguration =\n"
103-
+ " request.overrideConfiguration().map(c -> c.toBuilder()"
104-
+ ".applyMutation"
105-
+ "(userAgentApplier).build())\n"
106-
+ " .orElse((AwsRequestOverrideConfiguration.builder()"
107-
+ ".applyMutation"
108-
+ "(userAgentApplier).build()))", AwsRequestOverrideConfiguration.class)
109-
.addStatement("return (T) request.toBuilder().overrideConfiguration"
110-
+ "(overrideConfiguration).build()")
111-
.build();
112-
113-
return MethodSpec.methodBuilder("applyPaginatorUserAgent")
114-
.addModifiers(Modifier.PRIVATE)
115-
.addParameter(typeVariableName, "request")
116-
.addTypeVariable(typeVariableName)
117-
.addCode(codeBlock)
118-
.returns(typeVariableName)
119-
.build();
120-
}
121-
12285
static MethodSpec applySignerOverrideMethod(PoetExtension poetExtensions, IntermediateModel model) {
12386
String signerOverrideVariable = "signerOverride";
12487

codegen/src/main/java/software/amazon/awssdk/codegen/poet/client/DelegatingAsyncClientClass.java

Lines changed: 0 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -42,7 +42,6 @@
4242
import software.amazon.awssdk.codegen.model.intermediate.OperationModel;
4343
import software.amazon.awssdk.codegen.poet.PoetExtension;
4444
import software.amazon.awssdk.codegen.poet.PoetUtils;
45-
import software.amazon.awssdk.codegen.utils.PaginatorUtils;
4645
import software.amazon.awssdk.core.SdkClient;
4746
import software.amazon.awssdk.utils.Validate;
4847

@@ -171,9 +170,6 @@ protected List<MethodSpec> operations() {
171170
private Stream<MethodSpec> operations(OperationModel opModel) {
172171
List<MethodSpec> methods = new ArrayList<>();
173172
methods.add(traditionalMethod(opModel));
174-
if (opModel.isPaginated()) {
175-
methods.add(paginatedTraditionalMethod(opModel));
176-
}
177173
return methods.stream();
178174
}
179175

@@ -212,14 +208,6 @@ protected MethodSpec.Builder operationBody(MethodSpec.Builder builder, Operation
212208
return builder;
213209
}
214210

215-
@Override
216-
protected MethodSpec.Builder paginatedMethodBody(MethodSpec.Builder builder, OperationModel opModel) {
217-
String methodName = PaginatorUtils.getPaginatedMethodName(opModel.getMethodName());
218-
return builder.addModifiers(PUBLIC)
219-
.addAnnotation(Override.class)
220-
.addStatement("return delegate.$N($N)", methodName, opModel.getInput().getVariableName());
221-
}
222-
223211
@Override
224212
protected MethodSpec.Builder utilitiesOperationBody(MethodSpec.Builder builder) {
225213
return builder.addAnnotation(Override.class).addStatement("return delegate.$N()", UtilitiesMethod.METHOD_NAME);

codegen/src/main/java/software/amazon/awssdk/codegen/poet/client/DelegatingSyncClientClass.java

Lines changed: 25 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@
1616
package software.amazon.awssdk.codegen.poet.client;
1717

1818
import static java.util.stream.Collectors.joining;
19+
import static java.util.stream.Collectors.toList;
1920
import static javax.lang.model.element.Modifier.ABSTRACT;
2021
import static javax.lang.model.element.Modifier.FINAL;
2122
import static javax.lang.model.element.Modifier.PRIVATE;
@@ -31,16 +32,17 @@
3132
import com.squareup.javapoet.TypeSpec;
3233
import com.squareup.javapoet.TypeVariableName;
3334
import java.util.ArrayList;
35+
import java.util.Comparator;
3436
import java.util.List;
3537
import java.util.function.Function;
38+
import java.util.stream.Stream;
3639
import software.amazon.awssdk.annotations.SdkPublicApi;
3740
import software.amazon.awssdk.codegen.docs.SimpleMethodOverload;
3841
import software.amazon.awssdk.codegen.model.config.customization.UtilitiesMethod;
3942
import software.amazon.awssdk.codegen.model.intermediate.IntermediateModel;
4043
import software.amazon.awssdk.codegen.model.intermediate.OperationModel;
4144
import software.amazon.awssdk.codegen.poet.PoetExtension;
4245
import software.amazon.awssdk.codegen.poet.PoetUtils;
43-
import software.amazon.awssdk.codegen.utils.PaginatorUtils;
4446
import software.amazon.awssdk.core.SdkClient;
4547
import software.amazon.awssdk.utils.Validate;
4648

@@ -112,6 +114,23 @@ protected void addCloseMethod(TypeSpec.Builder type) {
112114
type.addMethod(method);
113115
}
114116

117+
@Override
118+
protected List<MethodSpec> operations() {
119+
return model.getOperations().values().stream()
120+
// TODO Sync not supported for event streaming yet. Revisit after sync/async merge
121+
.filter(o -> !o.hasEventStreamInput())
122+
.filter(o -> !o.hasEventStreamOutput())
123+
.flatMap(this::operations)
124+
.sorted(Comparator.comparing(m -> m.name))
125+
.collect(toList());
126+
}
127+
128+
private Stream<MethodSpec> operations(OperationModel opModel) {
129+
List<MethodSpec> methods = new ArrayList<>();
130+
methods.add(traditionalMethod(opModel));
131+
return methods.stream();
132+
}
133+
115134
@Override
116135
public ClassName className() {
117136
return className;
@@ -122,6 +141,11 @@ protected MethodSpec.Builder simpleMethodModifier(MethodSpec.Builder builder) {
122141
return builder.addAnnotation(Override.class);
123142
}
124143

144+
protected MethodSpec traditionalMethod(OperationModel opModel) {
145+
MethodSpec.Builder builder = operationMethodSignature(model, opModel);
146+
return operationBody(builder, opModel).build();
147+
}
148+
125149
@Override
126150
protected MethodSpec.Builder operationBody(MethodSpec.Builder builder, OperationModel opModel) {
127151
builder.addModifiers(PUBLIC)
@@ -143,14 +167,6 @@ protected MethodSpec.Builder operationBody(MethodSpec.Builder builder, Operation
143167
return builder;
144168
}
145169

146-
@Override
147-
protected MethodSpec.Builder paginatedMethodBody(MethodSpec.Builder builder, OperationModel opModel) {
148-
String methodName = PaginatorUtils.getPaginatedMethodName(opModel.getMethodName());
149-
return builder.addModifiers(PUBLIC)
150-
.addAnnotation(Override.class)
151-
.addStatement("return delegate.$N($N)", methodName, opModel.getInput().getVariableName());
152-
}
153-
154170
@Override
155171
protected MethodSpec.Builder utilitiesOperationBody(MethodSpec.Builder builder) {
156172
return builder.addAnnotation(Override.class).addStatement("return delegate.$N()", UtilitiesMethod.METHOD_NAME);

0 commit comments

Comments
 (0)