1fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville// Protocol Buffers - Google's data interchange format
2fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville// Copyright 2008 Google Inc.  All rights reserved.
3fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville// http://code.google.com/p/protobuf/
4fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville//
5fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville// Redistribution and use in source and binary forms, with or without
6fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville// modification, are permitted provided that the following conditions are
7fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville// met:
8fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville//
9fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville//     * Redistributions of source code must retain the above copyright
10fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville// notice, this list of conditions and the following disclaimer.
11fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville//     * Redistributions in binary form must reproduce the above
12fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville// copyright notice, this list of conditions and the following disclaimer
13fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville// in the documentation and/or other materials provided with the
14fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville// distribution.
15fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville//     * Neither the name of Google Inc. nor the names of its
16fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville// contributors may be used to endorse or promote products derived from
17fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville// this software without specific prior written permission.
18fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville//
19fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
20fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
21fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
22fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
23fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
24fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
25fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
26fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
27fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
28fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
29fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
31fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville// Author: kenton@google.com (Kenton Varda)
32fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville//  Based on original Protocol Buffers design by
33fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville//  Sanjay Ghemawat, Jeff Dean, and others.
34fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
35fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville#include <google/protobuf/compiler/java/java_service.h>
36fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville#include <google/protobuf/compiler/java/java_helpers.h>
37fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville#include <google/protobuf/io/printer.h>
38fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville#include <google/protobuf/descriptor.pb.h>
39fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville#include <google/protobuf/stubs/strutil.h>
40fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
41fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Savillenamespace google {
42fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Savillenamespace protobuf {
43fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Savillenamespace compiler {
44fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Savillenamespace java {
45fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
46fbaaef999ba563838ebd00874ed8a1c01fbf286dWink SavilleServiceGenerator::ServiceGenerator(const ServiceDescriptor* descriptor)
47fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  : descriptor_(descriptor) {}
48fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
49fbaaef999ba563838ebd00874ed8a1c01fbf286dWink SavilleServiceGenerator::~ServiceGenerator() {}
50fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
51fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Savillevoid ServiceGenerator::Generate(io::Printer* printer) {
52fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  bool is_own_file = descriptor_->file()->options().java_multiple_files();
53fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print(
54fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "public $static$ abstract class $classname$\n"
55fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "    implements com.google.protobuf.Service {\n",
56fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "static", is_own_file ? "" : "static",
57fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "classname", descriptor_->name());
58fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Indent();
59fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
60fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print(
61fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "protected $classname$() {}\n\n",
62fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "classname", descriptor_->name());
63fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
64fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  GenerateInterface(printer);
65fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
66fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  GenerateNewReflectiveServiceMethod(printer);
67fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  GenerateNewReflectiveBlockingServiceMethod(printer);
68fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
69fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  GenerateAbstractMethods(printer);
70fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
71fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  // Generate getDescriptor() and getDescriptorForType().
72fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print(
73fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "public static final\n"
74fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "    com.google.protobuf.Descriptors.ServiceDescriptor\n"
75fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "    getDescriptor() {\n"
76fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "  return $file$.getDescriptor().getServices().get($index$);\n"
77fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "}\n",
78fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "file", ClassName(descriptor_->file()),
79fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "index", SimpleItoa(descriptor_->index()));
80fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  GenerateGetDescriptorForType(printer);
81fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
82fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  // Generate more stuff.
83fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  GenerateCallMethod(printer);
84fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  GenerateGetPrototype(REQUEST, printer);
85fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  GenerateGetPrototype(RESPONSE, printer);
86fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  GenerateStub(printer);
87fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  GenerateBlockingStub(printer);
88fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
89fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Outdent();
90fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print("}\n\n");
91fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville}
92fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
93fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Savillevoid ServiceGenerator::GenerateGetDescriptorForType(io::Printer* printer) {
94fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print(
95fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "public final com.google.protobuf.Descriptors.ServiceDescriptor\n"
96fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "    getDescriptorForType() {\n"
97fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "  return getDescriptor();\n"
98fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "}\n");
99fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville}
100fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
101fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Savillevoid ServiceGenerator::GenerateInterface(io::Printer* printer) {
102fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print("public interface Interface {\n");
103fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Indent();
104fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  GenerateAbstractMethods(printer);
105fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Outdent();
106fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print("}\n\n");
107fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville}
108fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
109fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Savillevoid ServiceGenerator::GenerateNewReflectiveServiceMethod(
110fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    io::Printer* printer) {
111fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print(
112fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "public static com.google.protobuf.Service newReflectiveService(\n"
113fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "    final Interface impl) {\n"
114fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "  return new $classname$() {\n",
115fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "classname", descriptor_->name());
116fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Indent();
117fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Indent();
118fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
119fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  for (int i = 0; i < descriptor_->method_count(); i++) {
120fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    const MethodDescriptor* method = descriptor_->method(i);
121fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    printer->Print("@Override\n");
122fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    GenerateMethodSignature(printer, method, IS_CONCRETE);
123fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    printer->Print(
124fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      " {\n"
125fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      "  impl.$method$(controller, request, done);\n"
126fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      "}\n\n",
127fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      "method", UnderscoresToCamelCase(method));
128fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  }
129fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
130fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Outdent();
131fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print("};\n");
132fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Outdent();
133fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print("}\n\n");
134fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville}
135fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
136fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Savillevoid ServiceGenerator::GenerateNewReflectiveBlockingServiceMethod(
137fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    io::Printer* printer) {
138fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print(
139fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "public static com.google.protobuf.BlockingService\n"
140fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "    newReflectiveBlockingService(final BlockingInterface impl) {\n"
141fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "  return new com.google.protobuf.BlockingService() {\n");
142fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Indent();
143fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Indent();
144fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
145fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  GenerateGetDescriptorForType(printer);
146fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
147fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  GenerateCallBlockingMethod(printer);
148fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  GenerateGetPrototype(REQUEST, printer);
149fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  GenerateGetPrototype(RESPONSE, printer);
150fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
151fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Outdent();
152fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print("};\n");
153fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Outdent();
154fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print("}\n\n");
155fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville}
156fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
157fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Savillevoid ServiceGenerator::GenerateAbstractMethods(io::Printer* printer) {
158fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  for (int i = 0; i < descriptor_->method_count(); i++) {
159fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    const MethodDescriptor* method = descriptor_->method(i);
160fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    GenerateMethodSignature(printer, method, IS_ABSTRACT);
161fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    printer->Print(";\n\n");
162fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  }
163fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville}
164fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
165fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Savillevoid ServiceGenerator::GenerateCallMethod(io::Printer* printer) {
166fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print(
167fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "\n"
168fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "public final void callMethod(\n"
169fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "    com.google.protobuf.Descriptors.MethodDescriptor method,\n"
170fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "    com.google.protobuf.RpcController controller,\n"
171fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "    com.google.protobuf.Message request,\n"
172fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "    com.google.protobuf.RpcCallback<\n"
173fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "      com.google.protobuf.Message> done) {\n"
174fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "  if (method.getService() != getDescriptor()) {\n"
175fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "    throw new java.lang.IllegalArgumentException(\n"
176fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "      \"Service.callMethod() given method descriptor for wrong \" +\n"
177fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "      \"service type.\");\n"
178fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "  }\n"
179fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "  switch(method.getIndex()) {\n");
180fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Indent();
181fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Indent();
182fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
183fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  for (int i = 0; i < descriptor_->method_count(); i++) {
184fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    const MethodDescriptor* method = descriptor_->method(i);
185fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    map<string, string> vars;
186fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    vars["index"] = SimpleItoa(i);
187fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    vars["method"] = UnderscoresToCamelCase(method);
188fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    vars["input"] = ClassName(method->input_type());
189fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    vars["output"] = ClassName(method->output_type());
190fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    printer->Print(vars,
191fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      "case $index$:\n"
192fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      "  this.$method$(controller, ($input$)request,\n"
193fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      "    com.google.protobuf.RpcUtil.<$output$>specializeCallback(\n"
194fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      "      done));\n"
195fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      "  return;\n");
196fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  }
197fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
198fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print(
199fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "default:\n"
200fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "  throw new java.lang.AssertionError(\"Can't get here.\");\n");
201fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
202fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Outdent();
203fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Outdent();
204fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
205fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print(
206fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "  }\n"
207fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "}\n"
208fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "\n");
209fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville}
210fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
211fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Savillevoid ServiceGenerator::GenerateCallBlockingMethod(io::Printer* printer) {
212fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print(
213fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "\n"
214fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "public final com.google.protobuf.Message callBlockingMethod(\n"
215fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "    com.google.protobuf.Descriptors.MethodDescriptor method,\n"
216fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "    com.google.protobuf.RpcController controller,\n"
217fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "    com.google.protobuf.Message request)\n"
218fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "    throws com.google.protobuf.ServiceException {\n"
219fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "  if (method.getService() != getDescriptor()) {\n"
220fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "    throw new java.lang.IllegalArgumentException(\n"
221fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "      \"Service.callBlockingMethod() given method descriptor for \" +\n"
222fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "      \"wrong service type.\");\n"
223fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "  }\n"
224fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "  switch(method.getIndex()) {\n");
225fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Indent();
226fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Indent();
227fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
228fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  for (int i = 0; i < descriptor_->method_count(); i++) {
229fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    const MethodDescriptor* method = descriptor_->method(i);
230fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    map<string, string> vars;
231fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    vars["index"] = SimpleItoa(i);
232fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    vars["method"] = UnderscoresToCamelCase(method);
233fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    vars["input"] = ClassName(method->input_type());
234fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    vars["output"] = ClassName(method->output_type());
235fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    printer->Print(vars,
236fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      "case $index$:\n"
237fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      "  return impl.$method$(controller, ($input$)request);\n");
238fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  }
239fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
240fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print(
241fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "default:\n"
242fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "  throw new java.lang.AssertionError(\"Can't get here.\");\n");
243fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
244fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Outdent();
245fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Outdent();
246fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
247fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print(
248fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "  }\n"
249fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "}\n"
250fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "\n");
251fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville}
252fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
253fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Savillevoid ServiceGenerator::GenerateGetPrototype(RequestOrResponse which,
254fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville                                            io::Printer* printer) {
255fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  /*
256fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville   * TODO(cpovirk): The exception message says "Service.foo" when it may be
257fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville   * "BlockingService.foo."  Consider fixing.
258fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville   */
259fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print(
260fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "public final com.google.protobuf.Message\n"
261fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "    get$request_or_response$Prototype(\n"
262fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "    com.google.protobuf.Descriptors.MethodDescriptor method) {\n"
263fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "  if (method.getService() != getDescriptor()) {\n"
264fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "    throw new java.lang.IllegalArgumentException(\n"
265fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "      \"Service.get$request_or_response$Prototype() given method \" +\n"
266fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "      \"descriptor for wrong service type.\");\n"
267fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "  }\n"
268fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "  switch(method.getIndex()) {\n",
269fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "request_or_response", (which == REQUEST) ? "Request" : "Response");
270fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Indent();
271fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Indent();
272fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
273fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  for (int i = 0; i < descriptor_->method_count(); i++) {
274fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    const MethodDescriptor* method = descriptor_->method(i);
275fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    map<string, string> vars;
276fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    vars["index"] = SimpleItoa(i);
277fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    vars["type"] = ClassName(
278fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      (which == REQUEST) ? method->input_type() : method->output_type());
279fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    printer->Print(vars,
280fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      "case $index$:\n"
281fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      "  return $type$.getDefaultInstance();\n");
282fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  }
283fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
284fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print(
285fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "default:\n"
286fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "  throw new java.lang.AssertionError(\"Can't get here.\");\n");
287fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
288fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Outdent();
289fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Outdent();
290fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
291fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print(
292fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "  }\n"
293fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "}\n"
294fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "\n");
295fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville}
296fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
297fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Savillevoid ServiceGenerator::GenerateStub(io::Printer* printer) {
298fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print(
299fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "public static Stub newStub(\n"
300fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "    com.google.protobuf.RpcChannel channel) {\n"
301fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "  return new Stub(channel);\n"
302fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "}\n"
303fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "\n"
304fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "public static final class Stub extends $classname$ implements Interface {"
305fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "\n",
306fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "classname", ClassName(descriptor_));
307fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Indent();
308fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
309fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print(
310fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "private Stub(com.google.protobuf.RpcChannel channel) {\n"
311fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "  this.channel = channel;\n"
312fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "}\n"
313fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "\n"
314fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "private final com.google.protobuf.RpcChannel channel;\n"
315fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "\n"
316fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "public com.google.protobuf.RpcChannel getChannel() {\n"
317fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "  return channel;\n"
318fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "}\n");
319fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
320fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  for (int i = 0; i < descriptor_->method_count(); i++) {
321fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    const MethodDescriptor* method = descriptor_->method(i);
322fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    printer->Print("\n");
323fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    GenerateMethodSignature(printer, method, IS_CONCRETE);
324fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    printer->Print(" {\n");
325fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    printer->Indent();
326fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
327fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    map<string, string> vars;
328fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    vars["index"] = SimpleItoa(i);
329fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    vars["output"] = ClassName(method->output_type());
330fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    printer->Print(vars,
331fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      "channel.callMethod(\n"
332fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      "  getDescriptor().getMethods().get($index$),\n"
333fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      "  controller,\n"
334fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      "  request,\n"
335fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      "  $output$.getDefaultInstance(),\n"
336fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      "  com.google.protobuf.RpcUtil.generalizeCallback(\n"
337fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      "    done,\n"
338fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      "    $output$.class,\n"
339fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      "    $output$.getDefaultInstance()));\n");
340fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
341fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    printer->Outdent();
342fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    printer->Print("}\n");
343fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  }
344fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
345fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Outdent();
346fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print(
347fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "}\n"
348fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "\n");
349fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville}
350fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
351fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Savillevoid ServiceGenerator::GenerateBlockingStub(io::Printer* printer) {
352fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print(
353fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "public static BlockingInterface newBlockingStub(\n"
354fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "    com.google.protobuf.BlockingRpcChannel channel) {\n"
355fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "  return new BlockingStub(channel);\n"
356fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "}\n"
357fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "\n");
358fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
359fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print(
360fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "public interface BlockingInterface {");
361fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Indent();
362fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
363fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  for (int i = 0; i < descriptor_->method_count(); i++) {
364fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    const MethodDescriptor* method = descriptor_->method(i);
365fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    GenerateBlockingMethodSignature(printer, method);
366fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    printer->Print(";\n");
367fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  }
368fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
369fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Outdent();
370fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print(
371fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "}\n"
372fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "\n");
373fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
374fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print(
375fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "private static final class BlockingStub implements BlockingInterface {\n");
376fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Indent();
377fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
378fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print(
379fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "private BlockingStub(com.google.protobuf.BlockingRpcChannel channel) {\n"
380fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "  this.channel = channel;\n"
381fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "}\n"
382fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "\n"
383fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "private final com.google.protobuf.BlockingRpcChannel channel;\n");
384fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
385fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  for (int i = 0; i < descriptor_->method_count(); i++) {
386fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    const MethodDescriptor* method = descriptor_->method(i);
387fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    GenerateBlockingMethodSignature(printer, method);
388fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    printer->Print(" {\n");
389fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    printer->Indent();
390fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
391fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    map<string, string> vars;
392fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    vars["index"] = SimpleItoa(i);
393fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    vars["output"] = ClassName(method->output_type());
394fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    printer->Print(vars,
395fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      "return ($output$) channel.callBlockingMethod(\n"
396fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      "  getDescriptor().getMethods().get($index$),\n"
397fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      "  controller,\n"
398fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      "  request,\n"
399fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      "  $output$.getDefaultInstance());\n");
400fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
401fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    printer->Outdent();
402fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    printer->Print(
403fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      "}\n"
404fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville      "\n");
405fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  }
406fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
407fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Outdent();
408fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print("}\n");
409fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville}
410fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
411fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Savillevoid ServiceGenerator::GenerateMethodSignature(io::Printer* printer,
412fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville                                               const MethodDescriptor* method,
413fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville                                               IsAbstract is_abstract) {
414fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  map<string, string> vars;
415fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  vars["name"] = UnderscoresToCamelCase(method);
416fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  vars["input"] = ClassName(method->input_type());
417fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  vars["output"] = ClassName(method->output_type());
418fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  vars["abstract"] = (is_abstract == IS_ABSTRACT) ? "abstract" : "";
419fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print(vars,
420fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "public $abstract$ void $name$(\n"
421fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "    com.google.protobuf.RpcController controller,\n"
422fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "    $input$ request,\n"
423fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "    com.google.protobuf.RpcCallback<$output$> done)");
424fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville}
425fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
426fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Savillevoid ServiceGenerator::GenerateBlockingMethodSignature(
427fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    io::Printer* printer,
428fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    const MethodDescriptor* method) {
429fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  map<string, string> vars;
430fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  vars["method"] = UnderscoresToCamelCase(method);
431fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  vars["input"] = ClassName(method->input_type());
432fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  vars["output"] = ClassName(method->output_type());
433fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville  printer->Print(vars,
434fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "\n"
435fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "public $output$ $method$(\n"
436fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "    com.google.protobuf.RpcController controller,\n"
437fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "    $input$ request)\n"
438fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville    "    throws com.google.protobuf.ServiceException");
439fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville}
440fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville
441fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville}  // namespace java
442fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville}  // namespace compiler
443fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville}  // namespace protobuf
444fbaaef999ba563838ebd00874ed8a1c01fbf286dWink Saville}  // namespace google
445