Skip to content

Commit

Permalink
[ggj][codegen] feat: add protobuf comments to ServiceClient (#310)
Browse files Browse the repository at this point in the history
* feat: add protobuf comment parser util

* fix: add basic proto build rules

* feat: add header comments to ServiceClient

* fix: build protoc at test time

* fix!: wrap protobuf location and process comments

* feat: add comment parsing to methods and fields

* fix: test

* feat: add protobuf comments to ServiceClient

* fix: solidify codegen method order with TypeNode/MethodArg and Comparable

* fix: clean up tests

* fix: merge
  • Loading branch information
miraleung authored Sep 19, 2020
1 parent 95ca83e commit 5e0fa91
Show file tree
Hide file tree
Showing 3 changed files with 168 additions and 1 deletion.
Original file line number Diff line number Diff line change
Expand Up @@ -587,6 +587,8 @@ private static List<MethodDefinition> createMethodVariants(

javaMethods.add(
MethodDefinition.builder()
.setHeaderCommentStatements(
ServiceClientCommentComposer.createRpcMethodHeaderComment(method, signature))
.setScope(ScopeNode.PUBLIC)
.setIsFinal(true)
.setReturnType(methodOutputType)
Expand Down Expand Up @@ -618,6 +620,8 @@ private static List<MethodDefinition> createMethodVariants(
.build();
javaMethods.add(
MethodDefinition.builder()
.setHeaderCommentStatements(
ServiceClientCommentComposer.createRpcMethodHeaderComment(method))
.setScope(ScopeNode.PUBLIC)
.setIsFinal(true)
.setReturnType(methodOutputType)
Expand All @@ -631,6 +635,7 @@ private static List<MethodDefinition> createMethodVariants(

private static MethodDefinition createLroAsyncMethod(
String serviceName, Method method, Map<String, TypeNode> types) {
// TODO(miraleung): Create variants as well.
Preconditions.checkState(
method.hasLro(), String.format("Method %s does not have an LRO", method.name()));
String methodName = JavaStyle.toLowerCamelCase(method.name());
Expand Down Expand Up @@ -665,6 +670,8 @@ private static MethodDefinition createLroAsyncMethod(
.build();

return MethodDefinition.builder()
.setHeaderCommentStatements(
ServiceClientCommentComposer.createRpcMethodHeaderComment(method))
.setScope(ScopeNode.PUBLIC)
.setIsFinal(true)
.setReturnType(returnType)
Expand Down Expand Up @@ -736,6 +743,8 @@ private static MethodDefinition createCallableMethod(
.build();

return MethodDefinition.builder()
.setHeaderCommentStatements(
ServiceClientCommentComposer.createRpcCallableMethodHeaderComment(method))
.setScope(ScopeNode.PUBLIC)
.setIsFinal(true)
.setName(methodName)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,14 +17,20 @@
import com.google.api.generator.engine.ast.CommentStatement;
import com.google.api.generator.engine.ast.JavaDocComment;
import com.google.api.generator.engine.ast.TypeNode;
import com.google.api.generator.gapic.model.Method;
import com.google.api.generator.gapic.model.MethodArgument;
import com.google.api.generator.gapic.model.Service;
import com.google.api.generator.gapic.utils.JavaStyle;
import java.util.Arrays;
import java.util.Collections;
import java.util.List;

class ServiceClientCommentComposer {
// Tokens.
private static final String COLON = ":";
private static final String EMPTY_STRING = "";
private static final String API_EXCEPTION_TYPE_NAME = "com.google.api.gax.rpc.ApiException";
private static final String EXCEPTION_CONDITION = "if the remote call fails";

// Constants.
private static final String SERVICE_DESCRIPTION_INTRO_STRING =
Expand All @@ -49,6 +55,8 @@ class ServiceClientCommentComposer {
private static final String SERVICE_DESCRIPTION_ENDPOINT_SUMMARY_STRING =
"To customize the endpoint:";

private static final String METHOD_DESCRIPTION_SAMPLE_CODE_SUMMARY_STRING = "Sample code:";

private static final List<String> SERVICE_DESCRIPTION_SURFACE_DESCRIPTION =
Arrays.asList(
"A \"flattened\" method. With this type of method, the fields of the request type have"
Expand Down Expand Up @@ -133,6 +141,53 @@ static CommentStatement createCreateMethodStubArgComment(TypeNode settingsType)
String.format(CREATE_METHOD_STUB_ARG_PATTERN, settingsType.reference().name()));
}

static List<CommentStatement> createRpcMethodHeaderComment(
Method method, List<MethodArgument> methodArguments) {
JavaDocComment.Builder methodJavadocBuilder = JavaDocComment.builder();

if (method.hasDescription()) {
methodJavadocBuilder.addComment(method.description());
}

methodJavadocBuilder.addParagraph(METHOD_DESCRIPTION_SAMPLE_CODE_SUMMARY_STRING);
// TODO(summerji): Add sample code here.

if (methodArguments.isEmpty()) {
methodJavadocBuilder.addParam(
"request", "The request object containing all of the parameters for the API call.");
} else {
for (MethodArgument argument : methodArguments) {
methodJavadocBuilder.addParam(
argument.name(), argument.hasDescription() ? argument.description() : EMPTY_STRING);
}
}

methodJavadocBuilder.setThrows(API_EXCEPTION_TYPE_NAME, EXCEPTION_CONDITION);

return Arrays.asList(
CommentComposer.AUTO_GENERATED_METHOD_COMMENT,
CommentStatement.withComment(methodJavadocBuilder.build()));
}

static List<CommentStatement> createRpcMethodHeaderComment(Method method) {
return createRpcMethodHeaderComment(method, Collections.emptyList());
}

static List<CommentStatement> createRpcCallableMethodHeaderComment(Method method) {
JavaDocComment.Builder methodJavadocBuilder = JavaDocComment.builder();

if (method.hasDescription()) {
methodJavadocBuilder.addComment(method.description());
}

methodJavadocBuilder.addParagraph(METHOD_DESCRIPTION_SAMPLE_CODE_SUMMARY_STRING);
// TODO(summerji): Add sample code here.

return Arrays.asList(
CommentComposer.AUTO_GENERATED_METHOD_COMMENT,
CommentStatement.withComment(methodJavadocBuilder.build()));
}

private static CommentStatement toSimpleComment(String comment) {
return CommentStatement.withComment(JavaDocComment.withComment(comment));
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -203,6 +203,13 @@ public void generateServiceClasses() {
+ " return operationsClient;\n"
+ " }\n"
+ "\n"
+ " // AUTO-GENERATED DOCUMENTATION AND METHOD.\n"
+ " /**\n"
+ " * Sample code:\n"
+ " *\n"
+ " * @param parent\n"
+ " * @throws com.google.api.gax.rpc.ApiException if the remote call fails\n"
+ " */\n"
+ " public final EchoResponse echo(ResourceName parent) {\n"
+ " EchoRequest request =\n"
+ " EchoRequest.newBuilder()\n"
Expand All @@ -211,11 +218,25 @@ public void generateServiceClasses() {
+ " return echo(request);\n"
+ " }\n"
+ "\n"
+ " // AUTO-GENERATED DOCUMENTATION AND METHOD.\n"
+ " /**\n"
+ " * Sample code:\n"
+ " *\n"
+ " * @param error\n"
+ " * @throws com.google.api.gax.rpc.ApiException if the remote call fails\n"
+ " */\n"
+ " public final EchoResponse echo(Status error) {\n"
+ " EchoRequest request = EchoRequest.newBuilder().setError(error).build();\n"
+ " return echo(request);\n"
+ " }\n"
+ "\n"
+ " // AUTO-GENERATED DOCUMENTATION AND METHOD.\n"
+ " /**\n"
+ " * Sample code:\n"
+ " *\n"
+ " * @param name\n"
+ " * @throws com.google.api.gax.rpc.ApiException if the remote call fails\n"
+ " */\n"
+ " public final EchoResponse echo(FoobarName name) {\n"
+ " EchoRequest request =\n"
+ " EchoRequest.newBuilder()\n"
Expand All @@ -224,85 +245,167 @@ public void generateServiceClasses() {
+ " return echo(request);\n"
+ " }\n"
+ "\n"
+ " // AUTO-GENERATED DOCUMENTATION AND METHOD.\n"
+ " /**\n"
+ " * Sample code:\n"
+ " *\n"
+ " * @param content\n"
+ " * @throws com.google.api.gax.rpc.ApiException if the remote call fails\n"
+ " */\n"
+ " public final EchoResponse echo(String content) {\n"
+ " EchoRequest request = EchoRequest.newBuilder().setContent(content).build();\n"
+ " return echo(request);\n"
+ " }\n"
+ "\n"
+ " // AUTO-GENERATED DOCUMENTATION AND METHOD.\n"
+ " /**\n"
+ " * Sample code:\n"
+ " *\n"
+ " * @param name\n"
+ " * @throws com.google.api.gax.rpc.ApiException if the remote call fails\n"
+ " */\n"
+ " public final EchoResponse echo(String name) {\n"
+ " EchoRequest request = EchoRequest.newBuilder().setName(name).build();\n"
+ " return echo(request);\n"
+ " }\n"
+ "\n"
+ " // AUTO-GENERATED DOCUMENTATION AND METHOD.\n"
+ " /**\n"
+ " * Sample code:\n"
+ " *\n"
+ " * @param parent\n"
+ " * @throws com.google.api.gax.rpc.ApiException if the remote call fails\n"
+ " */\n"
+ " public final EchoResponse echo(String parent) {\n"
+ " EchoRequest request = EchoRequest.newBuilder().setParent(parent).build();\n"
+ " return echo(request);\n"
+ " }\n"
+ "\n"
+ " // AUTO-GENERATED DOCUMENTATION AND METHOD.\n"
+ " /**\n"
+ " * Sample code:\n"
+ " *\n"
+ " * @param content\n"
+ " * @param severity\n"
+ " * @throws com.google.api.gax.rpc.ApiException if the remote call fails\n"
+ " */\n"
+ " public final EchoResponse echo(String content, Severity severity) {\n"
+ " EchoRequest request =\n"
+ " EchoRequest.newBuilder().setContent(content).setSeverity(severity).build();\n"
+ " return echo(request);\n"
+ " }\n"
+ "\n"
+ " // AUTO-GENERATED DOCUMENTATION AND METHOD.\n"
+ " /**\n"
+ " * Sample code:\n"
+ " *\n"
+ " * @param request The request object containing all of the parameters for the API"
+ " call.\n"
+ " * @throws com.google.api.gax.rpc.ApiException if the remote call fails\n"
+ " */\n"
+ " public final EchoResponse echo(EchoRequest request) {\n"
+ " return echoCallable().call(request);\n"
+ " }\n"
+ "\n"
+ " // AUTO-GENERATED DOCUMENTATION AND METHOD.\n"
+ " /** Sample code: */\n"
+ " public final UnaryCallable<EchoRequest, EchoResponse> echoCallable() {\n"
+ " return stub.echoCallable();\n"
+ " }\n"
+ "\n"
+ " // AUTO-GENERATED DOCUMENTATION AND METHOD.\n"
+ " /** Sample code: */\n"
+ " public final ServerStreamingCallable<ExpandRequest, EchoResponse> expandCallable()"
+ " {\n"
+ " return stub.expandCallable();\n"
+ " }\n"
+ "\n"
+ " // AUTO-GENERATED DOCUMENTATION AND METHOD.\n"
+ " /** Sample code: */\n"
+ " public final ClientStreamingCallable<EchoRequest, EchoResponse> collectCallable()"
+ " {\n"
+ " return stub.collectCallable();\n"
+ " }\n"
+ "\n"
+ " // AUTO-GENERATED DOCUMENTATION AND METHOD.\n"
+ " /** Sample code: */\n"
+ " public final BidiStreamingCallable<EchoRequest, EchoResponse> chatCallable() {\n"
+ " return stub.chatCallable();\n"
+ " }\n"
+ "\n"
+ " // AUTO-GENERATED DOCUMENTATION AND METHOD.\n"
+ " /** Sample code: */\n"
+ " public final BidiStreamingCallable<EchoRequest, EchoResponse> chatAgainCallable()"
+ " {\n"
+ " return stub.chatAgainCallable();\n"
+ " }\n"
+ "\n"
+ " // AUTO-GENERATED DOCUMENTATION AND METHOD.\n"
+ " /**\n"
+ " * Sample code:\n"
+ " *\n"
+ " * @param request The request object containing all of the parameters for the API"
+ " call.\n"
+ " * @throws com.google.api.gax.rpc.ApiException if the remote call fails\n"
+ " */\n"
+ " public final PagedExpandPagedResponse pagedExpand(PagedExpandRequest request) {\n"
+ " return pagedExpandPagedCallable().call(request);\n"
+ " }\n"
+ "\n"
+ " // AUTO-GENERATED DOCUMENTATION AND METHOD.\n"
+ " /** Sample code: */\n"
+ " public final UnaryCallable<PagedExpandRequest, PagedExpandPagedResponse>\n"
+ " pagedExpandPagedCallable() {\n"
+ " return stub.pagedExpandPagedCallable();\n"
+ " }\n"
+ "\n"
+ " public final UnaryCallable<PagedExpandRequest, PagedExpandResponse> pagedExpandCallable() {\n"
+ " // AUTO-GENERATED DOCUMENTATION AND METHOD.\n"
+ " /** Sample code: */\n"
+ " public final UnaryCallable<PagedExpandRequest, PagedExpandResponse>"
+ " pagedExpandCallable() {\n"
+ " return stub.pagedExpandCallable();\n"
+ " }\n"
+ "\n"
+ " // AUTO-GENERATED DOCUMENTATION AND METHOD.\n"
+ " /**\n"
+ " * Sample code:\n"
+ " *\n"
+ " * @param request The request object containing all of the parameters for the API"
+ " call.\n"
+ " * @throws com.google.api.gax.rpc.ApiException if the remote call fails\n"
+ " */\n"
+ " public final OperationFuture<WaitResponse, WaitMetadata> waitAsync(WaitRequest"
+ " request) {\n"
+ " return waitOperationCallable().futureCall(request);\n"
+ " }\n"
+ "\n"
+ " // AUTO-GENERATED DOCUMENTATION AND METHOD.\n"
+ " /** Sample code: */\n"
+ " public final OperationCallable<WaitRequest, WaitResponse, WaitMetadata>"
+ " waitOperationCallable() {\n"
+ " return stub.waitOperationCallable();\n"
+ " }\n"
+ "\n"
+ " // AUTO-GENERATED DOCUMENTATION AND METHOD.\n"
+ " /** Sample code: */\n"
+ " public final UnaryCallable<WaitRequest, Operation> waitCallable() {\n"
+ " return stub.waitCallable();\n"
+ " }\n"
+ "\n"
+ " // AUTO-GENERATED DOCUMENTATION AND METHOD.\n"
+ " /**\n"
+ " * Sample code:\n"
+ " *\n"
+ " * @param request The request object containing all of the parameters for the API"
+ " call.\n"
+ " * @throws com.google.api.gax.rpc.ApiException if the remote call fails\n"
+ " */\n"
+ " public final BlockResponse block(BlockRequest request) {\n"
+ " return blockCallable().call(request);\n"
+ " }\n"
+ "\n"
+ " // AUTO-GENERATED DOCUMENTATION AND METHOD.\n"
+ " /** Sample code: */\n"
+ " public final UnaryCallable<BlockRequest, BlockResponse> blockCallable() {\n"
+ " return stub.blockCallable();\n"
+ " }\n"
Expand Down

0 comments on commit 5e0fa91

Please sign in to comment.