diff --git a/Makefile b/Makefile index e6b29750570f82649a13dda82319da4bd190708c..d9e1f35cba79f64e01bfc73139dd5055bc69f3da 100644 --- a/Makefile +++ b/Makefile @@ -159,9 +159,14 @@ ifndef VALID_CONFIG_$(CONFIG) $(error Invalid CONFIG value '$(CONFIG)') endif +ifeq ($(SYSTEM),Linux) +TMPOUT = /dev/null +else +TMPOUT = `mktemp /tmp/test-out-XXXXXX` +endif # Detect if we can use C++11 -CXX11_CHECK_CMD = $(CXX) -std=c++11 -o /dev/null -c test/build/c++11.cc +CXX11_CHECK_CMD = $(CXX) -std=c++11 -o $(TMPOUT) -c test/build/c++11.cc HAS_CXX11 = $(shell $(CXX11_CHECK_CMD) 2> /dev/null && echo true || echo false) # The HOST compiler settings are used to compile the protoc plugins. @@ -194,9 +199,25 @@ LDFLAGS += -g -fPIC INCLUDES = . include $(GENDIR) ifeq ($(SYSTEM),Darwin) -INCLUDES += /usr/local/ssl/include /opt/local/include +ifneq ($(wildcard /usr/local/ssl/include),) +INCLUDES += /usr/local/ssl/include +endif +ifneq ($(wildcard /opt/local/include),) +INCLUDES += /opt/local/include +endif +ifneq ($(wildcard /usr/local/include),) +INCLUDES += /usr/local/include +endif LIBS = m z -LDFLAGS += -L/usr/local/ssl/lib -L/opt/local/lib +ifneq ($(wildcard /usr/local/ssl/lib),) +LDFLAGS += -L/usr/local/ssl/lib +endif +ifneq ($(wildcard /opt/local/lib),) +LDFLAGS += -L/opt/local/lib +endif +ifneq ($(wildcard /usr/local/lib),) +LDFLAGS += -L/usr/local/lib +endif else LIBS = rt m z pthread LDFLAGS += -pthread @@ -251,10 +272,10 @@ else IS_GIT_FOLDER = true endif -OPENSSL_ALPN_CHECK_CMD = $(CC) $(CFLAGS) $(CPPFLAGS) -o /dev/null test/build/openssl-alpn.c -lssl -lcrypto -ldl $(LDFLAGS) -ZLIB_CHECK_CMD = $(CC) $(CFLAGS) $(CPPFLAGS) -o /dev/null test/build/zlib.c -lz $(LDFLAGS) -PERFTOOLS_CHECK_CMD = $(CC) $(CFLAGS) $(CPPFLAGS) -o /dev/null test/build/perftools.c -lprofiler $(LDFLAGS) -PROTOBUF_CHECK_CMD = $(CXX) $(CXXFLAGS) $(CPPFLAGS) -o /dev/null test/build/protobuf.cc -lprotobuf $(LDFLAGS) +OPENSSL_ALPN_CHECK_CMD = $(CC) $(CFLAGS) $(CPPFLAGS) -o $(TMPOUT) test/build/openssl-alpn.c -lssl -lcrypto -ldl $(LDFLAGS) +ZLIB_CHECK_CMD = $(CC) $(CFLAGS) $(CPPFLAGS) -o $(TMPOUT) test/build/zlib.c -lz $(LDFLAGS) +PERFTOOLS_CHECK_CMD = $(CC) $(CFLAGS) $(CPPFLAGS) -o $(TMPOUT) test/build/perftools.c -lprofiler $(LDFLAGS) +PROTOBUF_CHECK_CMD = $(CXX) $(CXXFLAGS) $(CPPFLAGS) -o $(TMPOUT) test/build/protobuf.cc -lprotobuf $(LDFLAGS) PROTOC_CMD = which protoc PROTOC_CHECK_CMD = protoc --version | grep -q libprotoc.3 @@ -2039,10 +2060,10 @@ ifeq ($(SYSTEM),MINGW32) $(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/gpr.$(SHARED_EXT) $(prefix)/lib/gpr.$(SHARED_EXT) $(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/libgpr-imp.a $(prefix)/lib/libgpr-imp.a else +ifneq ($(SYSTEM),Darwin) $(E) "[INSTALL] Installing libgpr.$(SHARED_EXT)" $(Q) $(INSTALL) -d $(prefix)/lib $(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/libgpr.$(SHARED_EXT) $(prefix)/lib/libgpr.$(SHARED_EXT) -ifneq ($(SYSTEM),Darwin) $(Q) ln -sf libgpr.$(SHARED_EXT) $(prefix)/lib/libgpr.so endif endif @@ -2052,10 +2073,10 @@ ifeq ($(SYSTEM),MINGW32) $(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/grpc.$(SHARED_EXT) $(prefix)/lib/grpc.$(SHARED_EXT) $(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/libgrpc-imp.a $(prefix)/lib/libgrpc-imp.a else +ifneq ($(SYSTEM),Darwin) $(E) "[INSTALL] Installing libgrpc.$(SHARED_EXT)" $(Q) $(INSTALL) -d $(prefix)/lib $(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/libgrpc.$(SHARED_EXT) $(prefix)/lib/libgrpc.$(SHARED_EXT) -ifneq ($(SYSTEM),Darwin) $(Q) ln -sf libgrpc.$(SHARED_EXT) $(prefix)/lib/libgrpc.so endif endif @@ -2065,10 +2086,10 @@ ifeq ($(SYSTEM),MINGW32) $(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/grpc_unsecure.$(SHARED_EXT) $(prefix)/lib/grpc_unsecure.$(SHARED_EXT) $(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/libgrpc_unsecure-imp.a $(prefix)/lib/libgrpc_unsecure-imp.a else +ifneq ($(SYSTEM),Darwin) $(E) "[INSTALL] Installing libgrpc_unsecure.$(SHARED_EXT)" $(Q) $(INSTALL) -d $(prefix)/lib $(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/libgrpc_unsecure.$(SHARED_EXT) $(prefix)/lib/libgrpc_unsecure.$(SHARED_EXT) -ifneq ($(SYSTEM),Darwin) $(Q) ln -sf libgrpc_unsecure.$(SHARED_EXT) $(prefix)/lib/libgrpc_unsecure.so endif endif @@ -2086,10 +2107,10 @@ ifeq ($(SYSTEM),MINGW32) $(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/grpc++.$(SHARED_EXT) $(prefix)/lib/grpc++.$(SHARED_EXT) $(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/libgrpc++-imp.a $(prefix)/lib/libgrpc++-imp.a else +ifneq ($(SYSTEM),Darwin) $(E) "[INSTALL] Installing libgrpc++.$(SHARED_EXT)" $(Q) $(INSTALL) -d $(prefix)/lib $(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/libgrpc++.$(SHARED_EXT) $(prefix)/lib/libgrpc++.$(SHARED_EXT) -ifneq ($(SYSTEM),Darwin) $(Q) ln -sf libgrpc++.$(SHARED_EXT) $(prefix)/lib/libgrpc++.so endif endif @@ -2099,10 +2120,10 @@ ifeq ($(SYSTEM),MINGW32) $(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/grpc++_unsecure.$(SHARED_EXT) $(prefix)/lib/grpc++_unsecure.$(SHARED_EXT) $(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/libgrpc++_unsecure-imp.a $(prefix)/lib/libgrpc++_unsecure-imp.a else +ifneq ($(SYSTEM),Darwin) $(E) "[INSTALL] Installing libgrpc++_unsecure.$(SHARED_EXT)" $(Q) $(INSTALL) -d $(prefix)/lib $(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/libgrpc++_unsecure.$(SHARED_EXT) $(prefix)/lib/libgrpc++_unsecure.$(SHARED_EXT) -ifneq ($(SYSTEM),Darwin) $(Q) ln -sf libgrpc++_unsecure.$(SHARED_EXT) $(prefix)/lib/libgrpc++_unsecure.so endif endif @@ -2120,10 +2141,10 @@ ifeq ($(SYSTEM),MINGW32) $(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/grpc_csharp_ext.$(SHARED_EXT) $(prefix)/lib/grpc_csharp_ext.$(SHARED_EXT) $(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/libgrpc_csharp_ext-imp.a $(prefix)/lib/libgrpc_csharp_ext-imp.a else +ifneq ($(SYSTEM),Darwin) $(E) "[INSTALL] Installing libgrpc_csharp_ext.$(SHARED_EXT)" $(Q) $(INSTALL) -d $(prefix)/lib $(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/libgrpc_csharp_ext.$(SHARED_EXT) $(prefix)/lib/libgrpc_csharp_ext.$(SHARED_EXT) -ifneq ($(SYSTEM),Darwin) $(Q) ln -sf libgrpc_csharp_ext.$(SHARED_EXT) $(prefix)/lib/libgrpc_csharp_ext.so endif endif diff --git a/include/grpc++/config.h b/include/grpc++/config.h index 327ed7a549a4dbf1c1d988a62fe015c5a4f21e1c..0267b8521599237db822d785ae243f33cbdf3fa9 100644 --- a/include/grpc++/config.h +++ b/include/grpc++/config.h @@ -42,9 +42,9 @@ #define GRPC_OVERRIDE override #endif -#ifndef GRPC_CUSTOM_STRING -#include <string> -#define GRPC_CUSTOM_STRING std::string +#ifndef GRPC_CUSTOM_PROTOBUF_INT64 +#include <google/protobuf/stubs/common.h> +#define GRPC_CUSTOM_PROTOBUF_INT64 ::google::protobuf::int64 #endif #ifndef GRPC_CUSTOM_MESSAGE @@ -52,12 +52,32 @@ #define GRPC_CUSTOM_MESSAGE ::google::protobuf::Message #endif +#ifndef GRPC_CUSTOM_STRING +#include <string> +#define GRPC_CUSTOM_STRING std::string +#endif + +#ifndef GRPC_CUSTOM_ZEROCOPYOUTPUTSTREAM +#include <google/protobuf/io/zero_copy_stream.h> +#define GRPC_CUSTOM_ZEROCOPYOUTPUTSTREAM ::google::protobuf::io::ZeroCopyOutputStream +#define GRPC_CUSTOM_ZEROCOPYINPUTSTREAM ::google::protobuf::io::ZeroCopyInputStream +#endif + + namespace grpc { typedef GRPC_CUSTOM_STRING string; namespace protobuf { + typedef GRPC_CUSTOM_MESSAGE Message; +typedef GRPC_CUSTOM_PROTOBUF_INT64 int64; + +namespace io { +typedef GRPC_CUSTOM_ZEROCOPYOUTPUTSTREAM ZeroCopyOutputStream; +typedef GRPC_CUSTOM_ZEROCOPYINPUTSTREAM ZeroCopyInputStream; +} // namespace io + } // namespace protobuf } // namespace grpc diff --git a/include/grpc++/credentials.h b/include/grpc++/credentials.h index c677cc3e0a3edd8bc01f3d0805ece638e5213760..59ad638f47dbd0c3341f7046cb687f57a8d6cc2c 100644 --- a/include/grpc++/credentials.h +++ b/include/grpc++/credentials.h @@ -105,6 +105,14 @@ std::unique_ptr<Credentials> ServiceAccountCredentials( const grpc::string& json_key, const grpc::string& scope, std::chrono::seconds token_lifetime); +// Builds JWT credentials. +// json_key is the JSON key string containing the client's private key. +// token_lifetime is the lifetime of each Json Web Token (JWT) created with +// this credentials. It should not exceed grpc_max_auth_token_lifetime or +// will be cropped to this value. +std::unique_ptr<Credentials> JWTCredentials( + const grpc::string& json_key, std::chrono::seconds token_lifetime); + // Builds IAM credentials. std::unique_ptr<Credentials> IAMCredentials( const grpc::string& authorization_token, diff --git a/include/grpc/grpc_security.h b/include/grpc/grpc_security.h index c297622a512bf32891b871a77502c2471a3284ba..586cfcffe7f105e30e2e0a6159091903eb837e4e 100644 --- a/include/grpc/grpc_security.h +++ b/include/grpc/grpc_security.h @@ -117,6 +117,15 @@ grpc_credentials *grpc_service_account_credentials_create( grpc_credentials *grpc_jwt_credentials_create(const char *json_key, gpr_timespec token_lifetime); +/* Creates an Oauth2 Refresh Token crednetials object. May return NULL if the + input is invalid. + WARNING: Do NOT use this credentials to connect to a non-google service as + this could result in an oauth2 token leak. + - json_refresh_token is the JSON string containing the refresh token itself + along with a client_id and client_secret. */ +grpc_credentials *grpc_refresh_token_credentials_create( + const char *json_refresh_token); + /* Creates a fake transport security credentials object for testing. */ grpc_credentials *grpc_fake_transport_security_credentials_create(void); diff --git a/include/grpc/support/atm_gcc_atomic.h b/include/grpc/support/atm_gcc_atomic.h index 11d78b40973549342a4ffce91522785629b8238b..65d3d0c60f82a9aa10e7f85288bf3599d92dad1f 100644 --- a/include/grpc/support/atm_gcc_atomic.h +++ b/include/grpc/support/atm_gcc_atomic.h @@ -43,6 +43,7 @@ typedef gpr_intptr gpr_atm; #define gpr_atm_full_barrier() (__atomic_thread_fence(__ATOMIC_SEQ_CST)) #define gpr_atm_acq_load(p) (__atomic_load_n((p), __ATOMIC_ACQUIRE)) +#define gpr_atm_no_barrier_load(p) (__atomic_load_n((p), __ATOMIC_RELAXED)) #define gpr_atm_rel_store(p, value) \ (__atomic_store_n((p), (gpr_intptr)(value), __ATOMIC_RELEASE)) diff --git a/include/grpc/support/atm_gcc_sync.h b/include/grpc/support/atm_gcc_sync.h index e863bfd4c1e56492370d4c62de7c52af6e18fc2a..4955e4436f4485df2cd0f600f0aa20556a05df41 100644 --- a/include/grpc/support/atm_gcc_sync.h +++ b/include/grpc/support/atm_gcc_sync.h @@ -40,9 +40,11 @@ typedef gpr_intptr gpr_atm; +#define GPR_ATM_COMPILE_BARRIER_() __asm__ __volatile__("" : : : "memory") + #if defined(__i386) || defined(__x86_64__) /* All loads are acquire loads and all stores are release stores. */ -#define GPR_ATM_LS_BARRIER_() __asm__ __volatile__("" : : : "memory") +#define GPR_ATM_LS_BARRIER_() GPR_ATM_COMPILE_BARRIER_() #else #define GPR_ATM_LS_BARRIER_() gpr_atm_full_barrier() #endif @@ -55,12 +57,19 @@ static __inline gpr_atm gpr_atm_acq_load(const gpr_atm *p) { return value; } +static __inline gpr_atm gpr_atm_no_barrier_load(const gpr_atm *p) { + gpr_atm value = *p; + GPR_ATM_COMPILE_BARRIER_(); + return value; +} + static __inline void gpr_atm_rel_store(gpr_atm *p, gpr_atm value) { GPR_ATM_LS_BARRIER_(); *p = value; } #undef GPR_ATM_LS_BARRIER_ +#undef GPR_ATM_COMPILE_BARRIER_ #define gpr_atm_no_barrier_fetch_add(p, delta) \ gpr_atm_full_fetch_add((p), (delta)) diff --git a/include/grpc/support/atm_win32.h b/include/grpc/support/atm_win32.h index 3b9113c28b0fb617fd6a47c93cebe27b9be04cf3..18bf372004bbc878e97fb690b83f13bbc7eef8af 100644 --- a/include/grpc/support/atm_win32.h +++ b/include/grpc/support/atm_win32.h @@ -49,6 +49,11 @@ static __inline gpr_atm gpr_atm_acq_load(const gpr_atm *p) { return result; } +static __inline gpr_atm gpr_atm_no_barrier_load(const gpr_atm *p) { + /* TODO(dklempner): Can we implement something better here? */ + gpr_atm_acq_load(p); +} + static __inline void gpr_atm_rel_store(gpr_atm *p, gpr_atm value) { gpr_atm_full_barrier(); *p = value; diff --git a/src/compiler/config.h b/src/compiler/config.h new file mode 100644 index 0000000000000000000000000000000000000000..e81de8d6c8f43aab15850b770a416a882a0c49dc --- /dev/null +++ b/src/compiler/config.h @@ -0,0 +1,90 @@ +/* + * + * Copyright 2015, Google Inc. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are + * met: + * + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above + * copyright notice, this list of conditions and the following disclaimer + * in the documentation and/or other materials provided with the + * distribution. + * * Neither the name of Google Inc. nor the names of its + * contributors may be used to endorse or promote products derived from + * this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR + * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT + * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, + * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT + * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE + * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#ifndef SRC_COMPILER_CONFIG_H +#define SRC_COMPILER_CONFIG_H + +#include <grpc++/config.h> + +#ifndef GRPC_CUSTOM_DESCRIPTOR +#include <google/protobuf/descriptor.h> +#include <google/protobuf/descriptor.pb.h> +#define GRPC_CUSTOM_DESCRIPTOR ::google::protobuf::Descriptor +#define GRPC_CUSTOM_FILEDESCRIPTOR ::google::protobuf::FileDescriptor +#define GRPC_CUSTOM_METHODDESCRIPTOR ::google::protobuf::MethodDescriptor +#define GRPC_CUSTOM_SERVICEDESCRIPTOR ::google::protobuf::ServiceDescriptor +#endif + +#ifndef GRPC_CUSTOM_CODEGENERATOR +#include <google/protobuf/compiler/code_generator.h> +#define GRPC_CUSTOM_CODEGENERATOR ::google::protobuf::compiler::CodeGenerator +#define GRPC_CUSTOM_GENERATORCONTEXT ::google::protobuf::compiler::GeneratorContext +#endif + +#ifndef GRPC_CUSTOM_PRINTER +#include <google/protobuf/io/coded_stream.h> +#include <google/protobuf/io/printer.h> +#include <google/protobuf/io/zero_copy_stream_impl_lite.h> +#define GRPC_CUSTOM_PRINTER ::google::protobuf::io::Printer +#define GRPC_CUSTOM_CODEDOUTPUTSTREAM ::google::protobuf::io::CodedOutputStream +#define GRPC_CUSTOM_STRINGOUTPUTSTREAM ::google::protobuf::io::StringOutputStream +#endif + +#ifndef GRPC_CUSTOM_PLUGINMAIN +#include <google/protobuf/compiler/plugin.h> +#define GRPC_CUSTOM_PLUGINMAIN ::google::protobuf::compiler::PluginMain +#endif + +namespace grpc { +namespace protobuf { +typedef GRPC_CUSTOM_DESCRIPTOR Descriptor; +typedef GRPC_CUSTOM_FILEDESCRIPTOR FileDescriptor; +typedef GRPC_CUSTOM_METHODDESCRIPTOR MethodDescriptor; +typedef GRPC_CUSTOM_SERVICEDESCRIPTOR ServiceDescriptor; +namespace compiler { +typedef GRPC_CUSTOM_CODEGENERATOR CodeGenerator; +typedef GRPC_CUSTOM_GENERATORCONTEXT GeneratorContext; +static inline int PluginMain(int argc, char* argv[], + const CodeGenerator* generator) { + return GRPC_CUSTOM_PLUGINMAIN(argc, argv, generator); +} +} // namespace compiler +namespace io { +typedef GRPC_CUSTOM_PRINTER Printer; +typedef GRPC_CUSTOM_CODEDOUTPUTSTREAM CodedOutputStream; +typedef GRPC_CUSTOM_STRINGOUTPUTSTREAM StringOutputStream; +} // namespace io +} // namespace protobuf +} // namespace grpc + +#endif // SRC_COMPILER_CONFIG_H diff --git a/src/compiler/cpp_generator.cc b/src/compiler/cpp_generator.cc index eade70d5332289ff83675fe32f15e2c7d82c5192..d5004624d42df69d17562840723e366c26ec0cbf 100644 --- a/src/compiler/cpp_generator.cc +++ b/src/compiler/cpp_generator.cc @@ -31,45 +31,42 @@ * */ -#include <string> #include <map> #include "src/compiler/cpp_generator.h" - #include "src/compiler/cpp_generator_helpers.h" -#include <google/protobuf/descriptor.h> -#include <google/protobuf/descriptor.pb.h> -#include <google/protobuf/io/printer.h> -#include <google/protobuf/io/zero_copy_stream_impl_lite.h> + +#include "src/compiler/config.h" + #include <sstream> namespace grpc_cpp_generator { namespace { template <class T> -std::string as_string(T x) { +grpc::string as_string(T x) { std::ostringstream out; out << x; return out.str(); } -bool NoStreaming(const google::protobuf::MethodDescriptor *method) { +bool NoStreaming(const grpc::protobuf::MethodDescriptor *method) { return !method->client_streaming() && !method->server_streaming(); } -bool ClientOnlyStreaming(const google::protobuf::MethodDescriptor *method) { +bool ClientOnlyStreaming(const grpc::protobuf::MethodDescriptor *method) { return method->client_streaming() && !method->server_streaming(); } -bool ServerOnlyStreaming(const google::protobuf::MethodDescriptor *method) { +bool ServerOnlyStreaming(const grpc::protobuf::MethodDescriptor *method) { return !method->client_streaming() && method->server_streaming(); } -bool BidiStreaming(const google::protobuf::MethodDescriptor *method) { +bool BidiStreaming(const grpc::protobuf::MethodDescriptor *method) { return method->client_streaming() && method->server_streaming(); } -bool HasUnaryCalls(const google::protobuf::FileDescriptor *file) { +bool HasUnaryCalls(const grpc::protobuf::FileDescriptor *file) { for (int i = 0; i < file->service_count(); i++) { for (int j = 0; j < file->service(i)->method_count(); j++) { if (NoStreaming(file->service(i)->method(j))) { @@ -80,7 +77,7 @@ bool HasUnaryCalls(const google::protobuf::FileDescriptor *file) { return false; } -bool HasClientOnlyStreaming(const google::protobuf::FileDescriptor *file) { +bool HasClientOnlyStreaming(const grpc::protobuf::FileDescriptor *file) { for (int i = 0; i < file->service_count(); i++) { for (int j = 0; j < file->service(i)->method_count(); j++) { if (ClientOnlyStreaming(file->service(i)->method(j))) { @@ -91,7 +88,7 @@ bool HasClientOnlyStreaming(const google::protobuf::FileDescriptor *file) { return false; } -bool HasServerOnlyStreaming(const google::protobuf::FileDescriptor *file) { +bool HasServerOnlyStreaming(const grpc::protobuf::FileDescriptor *file) { for (int i = 0; i < file->service_count(); i++) { for (int j = 0; j < file->service(i)->method_count(); j++) { if (ServerOnlyStreaming(file->service(i)->method(j))) { @@ -102,7 +99,7 @@ bool HasServerOnlyStreaming(const google::protobuf::FileDescriptor *file) { return false; } -bool HasBidiStreaming(const google::protobuf::FileDescriptor *file) { +bool HasBidiStreaming(const grpc::protobuf::FileDescriptor *file) { for (int i = 0; i < file->service_count(); i++) { for (int j = 0; j < file->service(i)->method_count(); j++) { if (BidiStreaming(file->service(i)->method(j))) { @@ -114,8 +111,8 @@ bool HasBidiStreaming(const google::protobuf::FileDescriptor *file) { } } // namespace -std::string GetHeaderIncludes(const google::protobuf::FileDescriptor *file) { - std::string temp = +grpc::string GetHeaderIncludes(const grpc::protobuf::FileDescriptor *file) { + grpc::string temp = "#include <grpc++/impl/internal_stub.h>\n" "#include <grpc++/impl/service_type.h>\n" "#include <grpc++/status.h>\n" @@ -161,7 +158,7 @@ std::string GetHeaderIncludes(const google::protobuf::FileDescriptor *file) { return temp; } -std::string GetSourceIncludes() { +grpc::string GetSourceIncludes() { return "#include <grpc++/async_unary_call.h>\n" "#include <grpc++/channel_interface.h>\n" "#include <grpc++/impl/client_unary_call.h>\n" @@ -171,9 +168,9 @@ std::string GetSourceIncludes() { "#include <grpc++/stream.h>\n"; } -void PrintHeaderClientMethod(google::protobuf::io::Printer *printer, - const google::protobuf::MethodDescriptor *method, - std::map<std::string, std::string> *vars) { +void PrintHeaderClientMethod(grpc::protobuf::io::Printer *printer, + const grpc::protobuf::MethodDescriptor *method, + std::map<grpc::string, grpc::string> *vars) { (*vars)["Method"] = method->name(); (*vars)["Request"] = grpc_cpp_generator::ClassName(method->input_type(), true); @@ -223,9 +220,9 @@ void PrintHeaderClientMethod(google::protobuf::io::Printer *printer, } void PrintHeaderServerMethodSync( - google::protobuf::io::Printer *printer, - const google::protobuf::MethodDescriptor *method, - std::map<std::string, std::string> *vars) { + grpc::protobuf::io::Printer *printer, + const grpc::protobuf::MethodDescriptor *method, + std::map<grpc::string, grpc::string> *vars) { (*vars)["Method"] = method->name(); (*vars)["Request"] = grpc_cpp_generator::ClassName(method->input_type(), true); @@ -258,9 +255,9 @@ void PrintHeaderServerMethodSync( } void PrintHeaderServerMethodAsync( - google::protobuf::io::Printer *printer, - const google::protobuf::MethodDescriptor *method, - std::map<std::string, std::string> *vars) { + grpc::protobuf::io::Printer *printer, + const grpc::protobuf::MethodDescriptor *method, + std::map<grpc::string, grpc::string> *vars) { (*vars)["Method"] = method->name(); (*vars)["Request"] = grpc_cpp_generator::ClassName(method->input_type(), true); @@ -294,9 +291,9 @@ void PrintHeaderServerMethodAsync( } } -void PrintHeaderService(google::protobuf::io::Printer *printer, - const google::protobuf::ServiceDescriptor *service, - std::map<std::string, std::string> *vars) { +void PrintHeaderService(grpc::protobuf::io::Printer *printer, + const grpc::protobuf::ServiceDescriptor *service, + std::map<grpc::string, grpc::string> *vars) { (*vars)["Service"] = service->name(); printer->Print(*vars, @@ -356,11 +353,11 @@ void PrintHeaderService(google::protobuf::io::Printer *printer, printer->Print("};\n"); } -std::string GetHeaderServices(const google::protobuf::FileDescriptor *file) { - std::string output; - google::protobuf::io::StringOutputStream output_stream(&output); - google::protobuf::io::Printer printer(&output_stream, '$'); - std::map<std::string, std::string> vars; +grpc::string GetHeaderServices(const grpc::protobuf::FileDescriptor *file) { + grpc::string output; + grpc::protobuf::io::StringOutputStream output_stream(&output); + grpc::protobuf::io::Printer printer(&output_stream, '$'); + std::map<grpc::string, grpc::string> vars; for (int i = 0; i < file->service_count(); ++i) { PrintHeaderService(&printer, file->service(i), &vars); @@ -369,9 +366,9 @@ std::string GetHeaderServices(const google::protobuf::FileDescriptor *file) { return output; } -void PrintSourceClientMethod(google::protobuf::io::Printer *printer, - const google::protobuf::MethodDescriptor *method, - std::map<std::string, std::string> *vars) { +void PrintSourceClientMethod(grpc::protobuf::io::Printer *printer, + const grpc::protobuf::MethodDescriptor *method, + std::map<grpc::string, grpc::string> *vars) { (*vars)["Method"] = method->name(); (*vars)["Request"] = grpc_cpp_generator::ClassName(method->input_type(), true); @@ -485,9 +482,9 @@ void PrintSourceClientMethod(google::protobuf::io::Printer *printer, } } -void PrintSourceServerMethod(google::protobuf::io::Printer *printer, - const google::protobuf::MethodDescriptor *method, - std::map<std::string, std::string> *vars) { +void PrintSourceServerMethod(grpc::protobuf::io::Printer *printer, + const grpc::protobuf::MethodDescriptor *method, + std::map<grpc::string, grpc::string> *vars) { (*vars)["Method"] = method->name(); (*vars)["Request"] = grpc_cpp_generator::ClassName(method->input_type(), true); @@ -536,9 +533,9 @@ void PrintSourceServerMethod(google::protobuf::io::Printer *printer, } void PrintSourceServerAsyncMethod( - google::protobuf::io::Printer *printer, - const google::protobuf::MethodDescriptor *method, - std::map<std::string, std::string> *vars) { + grpc::protobuf::io::Printer *printer, + const grpc::protobuf::MethodDescriptor *method, + std::map<grpc::string, grpc::string> *vars) { (*vars)["Method"] = method->name(); (*vars)["Request"] = grpc_cpp_generator::ClassName(method->input_type(), true); @@ -590,9 +587,9 @@ void PrintSourceServerAsyncMethod( } } -void PrintSourceService(google::protobuf::io::Printer *printer, - const google::protobuf::ServiceDescriptor *service, - std::map<std::string, std::string> *vars) { +void PrintSourceService(grpc::protobuf::io::Printer *printer, + const grpc::protobuf::ServiceDescriptor *service, + std::map<grpc::string, grpc::string> *vars) { (*vars)["Service"] = service->name(); printer->Print(*vars, "static const char* $Service$_method_names[] = {\n"); @@ -640,7 +637,7 @@ void PrintSourceService(google::protobuf::io::Printer *printer, "}\n"); printer->Print("service_ = new ::grpc::RpcService();\n"); for (int i = 0; i < service->method_count(); ++i) { - const google::protobuf::MethodDescriptor *method = service->method(i); + const grpc::protobuf::MethodDescriptor *method = service->method(i); (*vars)["Idx"] = as_string(i); (*vars)["Method"] = method->name(); (*vars)["Request"] = @@ -705,11 +702,11 @@ void PrintSourceService(google::protobuf::io::Printer *printer, printer->Print("}\n\n"); } -std::string GetSourceServices(const google::protobuf::FileDescriptor *file) { - std::string output; - google::protobuf::io::StringOutputStream output_stream(&output); - google::protobuf::io::Printer printer(&output_stream, '$'); - std::map<std::string, std::string> vars; +grpc::string GetSourceServices(const grpc::protobuf::FileDescriptor *file) { + grpc::string output; + grpc::protobuf::io::StringOutputStream output_stream(&output); + grpc::protobuf::io::Printer printer(&output_stream, '$'); + std::map<grpc::string, grpc::string> vars; // Package string is empty or ends with a dot. It is used to fully qualify // method names. vars["Package"] = file->package(); diff --git a/src/compiler/cpp_generator.h b/src/compiler/cpp_generator.h index 1bfe5a8819be7a11b5218576bb712c7e58ffefa5..2ecdb5c47e27a1ebbaae19328270413d39772f21 100644 --- a/src/compiler/cpp_generator.h +++ b/src/compiler/cpp_generator.h @@ -34,27 +34,21 @@ #ifndef GRPC_INTERNAL_COMPILER_CPP_GENERATOR_H #define GRPC_INTERNAL_COMPILER_CPP_GENERATOR_H -#include <string> - -namespace google { -namespace protobuf { -class FileDescriptor; -} // namespace protobuf -} // namespace google +#include "src/compiler/config.h" namespace grpc_cpp_generator { // Return the includes needed for generated header file. -std::string GetHeaderIncludes(const google::protobuf::FileDescriptor *file); +grpc::string GetHeaderIncludes(const grpc::protobuf::FileDescriptor *file); // Return the includes needed for generated source file. -std::string GetSourceIncludes(); +grpc::string GetSourceIncludes(); // Return the services for generated header file. -std::string GetHeaderServices(const google::protobuf::FileDescriptor *file); +grpc::string GetHeaderServices(const grpc::protobuf::FileDescriptor *file); // Return the services for generated source file. -std::string GetSourceServices(const google::protobuf::FileDescriptor *file); +grpc::string GetSourceServices(const grpc::protobuf::FileDescriptor *file); } // namespace grpc_cpp_generator diff --git a/src/compiler/cpp_generator_helpers.h b/src/compiler/cpp_generator_helpers.h index 16abbde8d47bf4f2ae4a8536598cbdf8fdefd423..be68cbe695aeeba496b04dd182a50b35c5d8055f 100644 --- a/src/compiler/cpp_generator_helpers.h +++ b/src/compiler/cpp_generator_helpers.h @@ -35,30 +35,28 @@ #define GRPC_INTERNAL_COMPILER_CPP_GENERATOR_HELPERS_H #include <map> -#include <string> -#include <google/protobuf/descriptor.h> -#include <google/protobuf/descriptor.pb.h> +#include "src/compiler/config.h" #include "src/compiler/generator_helpers.h" namespace grpc_cpp_generator { -inline std::string DotsToColons(const std::string &name) { +inline grpc::string DotsToColons(const grpc::string &name) { return grpc_generator::StringReplace(name, ".", "::"); } -inline std::string DotsToUnderscores(const std::string &name) { +inline grpc::string DotsToUnderscores(const grpc::string &name) { return grpc_generator::StringReplace(name, ".", "_"); } -inline std::string ClassName(const google::protobuf::Descriptor *descriptor, - bool qualified) { +inline grpc::string ClassName(const grpc::protobuf::Descriptor *descriptor, + bool qualified) { // Find "outer", the descriptor of the top-level message in which // "descriptor" is embedded. - const google::protobuf::Descriptor *outer = descriptor; + const grpc::protobuf::Descriptor *outer = descriptor; while (outer->containing_type() != NULL) outer = outer->containing_type(); - const std::string &outer_name = outer->full_name(); - std::string inner_name = descriptor->full_name().substr(outer_name.size()); + const grpc::string &outer_name = outer->full_name(); + grpc::string inner_name = descriptor->full_name().substr(outer_name.size()); if (qualified) { return "::" + DotsToColons(outer_name) + DotsToUnderscores(inner_name); diff --git a/src/compiler/cpp_plugin.cc b/src/compiler/cpp_plugin.cc index feb158f89e602273a5b4f73ff27c1c896b080926..5b83aa85cf1f34d94a06f3743730c33138be7f27 100644 --- a/src/compiler/cpp_plugin.cc +++ b/src/compiler/cpp_plugin.cc @@ -35,26 +35,21 @@ // #include <memory> -#include <string> + +#include "src/compiler/config.h" #include "src/compiler/cpp_generator.h" #include "src/compiler/cpp_generator_helpers.h" -#include <google/protobuf/descriptor.h> -#include <google/protobuf/descriptor.pb.h> -#include <google/protobuf/compiler/code_generator.h> -#include <google/protobuf/compiler/plugin.h> -#include <google/protobuf/io/coded_stream.h> -#include <google/protobuf/io/zero_copy_stream.h> -class CppGrpcGenerator : public google::protobuf::compiler::CodeGenerator { +class CppGrpcGenerator : public grpc::protobuf::compiler::CodeGenerator { public: CppGrpcGenerator() {} virtual ~CppGrpcGenerator() {} - virtual bool Generate(const google::protobuf::FileDescriptor *file, - const std::string ¶meter, - google::protobuf::compiler::GeneratorContext *context, - std::string *error) const { + virtual bool Generate(const grpc::protobuf::FileDescriptor *file, + const grpc::string ¶meter, + grpc::protobuf::compiler::GeneratorContext *context, + grpc::string *error) const { if (file->options().cc_generic_services()) { *error = "cpp grpc proto compiler plugin does not work with generic " @@ -63,7 +58,7 @@ class CppGrpcGenerator : public google::protobuf::compiler::CodeGenerator { return false; } - std::string file_name = grpc_generator::StripProto(file->name()); + grpc::string file_name = grpc_generator::StripProto(file->name()); // Generate .pb.h Insert(context, file_name + ".pb.h", "includes", @@ -81,17 +76,17 @@ class CppGrpcGenerator : public google::protobuf::compiler::CodeGenerator { private: // Insert the given code into the given file at the given insertion point. - void Insert(google::protobuf::compiler::GeneratorContext *context, - const std::string &filename, const std::string &insertion_point, - const std::string &code) const { - std::unique_ptr<google::protobuf::io::ZeroCopyOutputStream> output( + void Insert(grpc::protobuf::compiler::GeneratorContext *context, + const grpc::string &filename, const grpc::string &insertion_point, + const grpc::string &code) const { + std::unique_ptr<grpc::protobuf::io::ZeroCopyOutputStream> output( context->OpenForInsert(filename, insertion_point)); - google::protobuf::io::CodedOutputStream coded_out(output.get()); + grpc::protobuf::io::CodedOutputStream coded_out(output.get()); coded_out.WriteRaw(code.data(), code.size()); } }; int main(int argc, char *argv[]) { CppGrpcGenerator generator; - return google::protobuf::compiler::PluginMain(argc, argv, &generator); + return grpc::protobuf::compiler::PluginMain(argc, argv, &generator); } diff --git a/src/compiler/generator_helpers.h b/src/compiler/generator_helpers.h index 2035820f0dccf49ee37b0e91f7ca13f4cb14443d..1e6727dd4c0a0337c5ef0534427c12dd0f61548e 100644 --- a/src/compiler/generator_helpers.h +++ b/src/compiler/generator_helpers.h @@ -35,14 +35,15 @@ #define GRPC_INTERNAL_COMPILER_GENERATOR_HELPERS_H #include <map> -#include <string> + +#include "src/compiler/config.h" namespace grpc_generator { -inline bool StripSuffix(std::string *filename, const std::string &suffix) { +inline bool StripSuffix(grpc::string *filename, const grpc::string &suffix) { if (filename->length() >= suffix.length()) { size_t suffix_pos = filename->length() - suffix.length(); - if (filename->compare(suffix_pos, std::string::npos, suffix) == 0) { + if (filename->compare(suffix_pos, grpc::string::npos, suffix) == 0) { filename->resize(filename->size() - suffix.size()); return true; } @@ -51,20 +52,20 @@ inline bool StripSuffix(std::string *filename, const std::string &suffix) { return false; } -inline std::string StripProto(std::string filename) { +inline grpc::string StripProto(grpc::string filename) { if (!StripSuffix(&filename, ".protodevel")) { StripSuffix(&filename, ".proto"); } return filename; } -inline std::string StringReplace(std::string str, const std::string &from, - const std::string &to) { +inline grpc::string StringReplace(grpc::string str, const grpc::string &from, + const grpc::string &to) { size_t pos = 0; for (;;) { pos = str.find(from, pos); - if (pos == std::string::npos) { + if (pos == grpc::string::npos) { break; } str.replace(pos, from.length(), to); diff --git a/src/compiler/python_generator.cc b/src/compiler/python_generator.cc index b217c0d911f25850baf8663ea54404275e47fa9e..b5022d55c4934adbbc2adb5352e3667f2f795876 100644 --- a/src/compiler/python_generator.cc +++ b/src/compiler/python_generator.cc @@ -60,8 +60,6 @@ using std::make_pair; using std::map; using std::pair; using std::replace; -using std::string; -using std::strlen; using std::vector; namespace grpc_python_generator { @@ -72,14 +70,14 @@ namespace { // Converts an initializer list of the form { key0, value0, key1, value1, ... } // into a map of key* to value*. Is merely a readability helper for later code. -map<string, string> ListToDict(const initializer_list<string>& values) { +map<std::string, std::string> ListToDict(const initializer_list<std::string>& values) { assert(values.size() % 2 == 0); - map<string, string> value_map; + map<std::string, std::string> value_map; auto value_iter = values.begin(); for (unsigned i = 0; i < values.size()/2; ++i) { - string key = *value_iter; + std::string key = *value_iter; ++value_iter; - string value = *value_iter; + std::string value = *value_iter; value_map[key] = value; ++value_iter; } @@ -113,8 +111,8 @@ class IndentScope { bool PrintServicer(const ServiceDescriptor* service, Printer* out) { - string doc = "<fill me in later!>"; - map<string, string> dict = ListToDict({ + std::string doc = "<fill me in later!>"; + map<std::string, std::string> dict = ListToDict({ "Service", service->name(), "Documentation", doc, }); @@ -125,7 +123,7 @@ bool PrintServicer(const ServiceDescriptor* service, out->Print("__metaclass__ = abc.ABCMeta\n"); for (int i = 0; i < service->method_count(); ++i) { auto meth = service->method(i); - string arg_name = meth->client_streaming() ? + std::string arg_name = meth->client_streaming() ? "request_iterator" : "request"; out->Print("@abc.abstractmethod\n"); out->Print("def $Method$(self, $ArgName$, context):\n", @@ -140,8 +138,8 @@ bool PrintServicer(const ServiceDescriptor* service, } bool PrintServer(const ServiceDescriptor* service, Printer* out) { - string doc = "<fill me in later!>"; - map<string, string> dict = ListToDict({ + std::string doc = "<fill me in later!>"; + map<std::string, std::string> dict = ListToDict({ "Service", service->name(), "Documentation", doc, }); @@ -169,8 +167,8 @@ bool PrintServer(const ServiceDescriptor* service, Printer* out) { bool PrintStub(const ServiceDescriptor* service, Printer* out) { - string doc = "<fill me in later!>"; - map<string, string> dict = ListToDict({ + std::string doc = "<fill me in later!>"; + map<std::string, std::string> dict = ListToDict({ "Service", service->name(), "Documentation", doc, }); @@ -181,7 +179,7 @@ bool PrintStub(const ServiceDescriptor* service, out->Print("__metaclass__ = abc.ABCMeta\n"); for (int i = 0; i < service->method_count(); ++i) { const MethodDescriptor* meth = service->method(i); - string arg_name = meth->client_streaming() ? + std::string arg_name = meth->client_streaming() ? "request_iterator" : "request"; auto methdict = ListToDict({"Method", meth->name(), "ArgName", arg_name}); out->Print("@abc.abstractmethod\n"); @@ -198,29 +196,29 @@ bool PrintStub(const ServiceDescriptor* service, // TODO(protobuf team): Export `ModuleName` from protobuf's // `src/google/protobuf/compiler/python/python_generator.cc` file. -string ModuleName(const string& filename) { - string basename = StripProto(filename); +std::string ModuleName(const std::string& filename) { + std::string basename = StripProto(filename); basename = StringReplace(basename, "-", "_"); basename = StringReplace(basename, "/", "."); return basename + "_pb2"; } bool GetModuleAndMessagePath(const Descriptor* type, - pair<string, string>* out) { + pair<std::string, std::string>* out) { const Descriptor* path_elem_type = type; vector<const Descriptor*> message_path; do { message_path.push_back(path_elem_type); path_elem_type = path_elem_type->containing_type(); } while (path_elem_type != nullptr); - string file_name = type->file()->name(); + std::string file_name = type->file()->name(); static const int proto_suffix_length = strlen(".proto"); if (!(file_name.size() > static_cast<size_t>(proto_suffix_length) && file_name.find_last_of(".proto") == file_name.size() - 1)) { return false; } - string module = ModuleName(file_name); - string message_type; + std::string module = ModuleName(file_name); + std::string message_type; for (auto path_iter = message_path.rbegin(); path_iter != message_path.rend(); ++path_iter) { message_type += (*path_iter)->name() + "."; @@ -237,21 +235,21 @@ bool PrintServerFactory(const ServiceDescriptor* service, Printer* out) { "Service", service->name()); { IndentScope raii_create_server_indent(out); - map<string, string> method_description_constructors; - map<string, pair<string, string>> input_message_modules_and_classes; - map<string, pair<string, string>> output_message_modules_and_classes; + map<std::string, std::string> method_description_constructors; + map<std::string, pair<std::string, std::string>> input_message_modules_and_classes; + map<std::string, pair<std::string, std::string>> output_message_modules_and_classes; for (int i = 0; i < service->method_count(); ++i) { const MethodDescriptor* method = service->method(i); - const string method_description_constructor = - string(method->client_streaming() ? "stream_" : "unary_") + - string(method->server_streaming() ? "stream_" : "unary_") + + const std::string method_description_constructor = + std::string(method->client_streaming() ? "stream_" : "unary_") + + std::string(method->server_streaming() ? "stream_" : "unary_") + "service_description"; - pair<string, string> input_message_module_and_class; + pair<std::string, std::string> input_message_module_and_class; if (!GetModuleAndMessagePath(method->input_type(), &input_message_module_and_class)) { return false; } - pair<string, string> output_message_module_and_class; + pair<std::string, std::string> output_message_module_and_class; if (!GetModuleAndMessagePath(method->output_type(), &output_message_module_and_class)) { return false; @@ -272,7 +270,7 @@ bool PrintServerFactory(const ServiceDescriptor* service, Printer* out) { for (auto& name_and_description_constructor : method_description_constructors) { IndentScope raii_descriptions_indent(out); - const string method_name = name_and_description_constructor.first; + const std::string method_name = name_and_description_constructor.first; auto input_message_module_and_class = input_message_modules_and_classes.find(method_name); auto output_message_module_and_class = @@ -306,27 +304,27 @@ bool PrintServerFactory(const ServiceDescriptor* service, Printer* out) { } bool PrintStubFactory(const ServiceDescriptor* service, Printer* out) { - map<string, string> dict = ListToDict({ + map<std::string, std::string> dict = ListToDict({ "Service", service->name(), }); out->Print(dict, "def early_adopter_create_$Service$_stub(host, port):\n"); { IndentScope raii_create_server_indent(out); - map<string, string> method_description_constructors; - map<string, pair<string, string>> input_message_modules_and_classes; - map<string, pair<string, string>> output_message_modules_and_classes; + map<std::string, std::string> method_description_constructors; + map<std::string, pair<std::string, std::string>> input_message_modules_and_classes; + map<std::string, pair<std::string, std::string>> output_message_modules_and_classes; for (int i = 0; i < service->method_count(); ++i) { const MethodDescriptor* method = service->method(i); - const string method_description_constructor = - string(method->client_streaming() ? "stream_" : "unary_") + - string(method->server_streaming() ? "stream_" : "unary_") + + const std::string method_description_constructor = + std::string(method->client_streaming() ? "stream_" : "unary_") + + std::string(method->server_streaming() ? "stream_" : "unary_") + "invocation_description"; - pair<string, string> input_message_module_and_class; + pair<std::string, std::string> input_message_module_and_class; if (!GetModuleAndMessagePath(method->input_type(), &input_message_module_and_class)) { return false; } - pair<string, string> output_message_module_and_class; + pair<std::string, std::string> output_message_module_and_class; if (!GetModuleAndMessagePath(method->output_type(), &output_message_module_and_class)) { return false; @@ -347,7 +345,7 @@ bool PrintStubFactory(const ServiceDescriptor* service, Printer* out) { for (auto& name_and_description_constructor : method_description_constructors) { IndentScope raii_descriptions_indent(out); - const string method_name = name_and_description_constructor.first; + const std::string method_name = name_and_description_constructor.first; auto input_message_module_and_class = input_message_modules_and_classes.find(method_name); auto output_message_module_and_class = @@ -385,8 +383,8 @@ bool PrintPreamble(const FileDescriptor* file, Printer* out) { } // namespace -pair<bool, string> GetServices(const FileDescriptor* file) { - string output; +pair<bool, std::string> GetServices(const FileDescriptor* file) { + std::string output; { // Scope the output stream so it closes and finalizes output to the string. StringOutputStream output_stream(&output); diff --git a/src/compiler/python_plugin.cc b/src/compiler/python_plugin.cc index 825f15a5c787ba775d7d36380f914f0aa4564816..e7d172f7bf4f9c66b7c7276b0dfadff145a8ad20 100644 --- a/src/compiler/python_plugin.cc +++ b/src/compiler/python_plugin.cc @@ -51,18 +51,16 @@ using google::protobuf::compiler::GeneratorContext; using google::protobuf::compiler::PluginMain; using google::protobuf::io::CodedOutputStream; using google::protobuf::io::ZeroCopyOutputStream; -using std::string; -using std::strlen; class PythonGrpcGenerator : public CodeGenerator { public: PythonGrpcGenerator() {} ~PythonGrpcGenerator() {} - bool Generate(const FileDescriptor* file, const string& parameter, - GeneratorContext* context, string* error) const { + bool Generate(const FileDescriptor* file, const std::string& parameter, + GeneratorContext* context, std::string* error) const { // Get output file name. - string file_name; + std::string file_name; static const int proto_suffix_length = strlen(".proto"); if (file->name().size() > static_cast<size_t>(proto_suffix_length) && file->name().find_last_of(".proto") == file->name().size() - 1) { @@ -77,7 +75,7 @@ class PythonGrpcGenerator : public CodeGenerator { context->OpenForInsert(file_name, "module_scope")); CodedOutputStream coded_out(output.get()); bool success = false; - string code = ""; + std::string code = ""; tie(success, code) = grpc_python_generator::GetServices(file); if (success) { coded_out.WriteRaw(code.data(), code.size()); diff --git a/src/core/channel/metadata_buffer.c b/src/core/channel/metadata_buffer.c index da66a028c4d972802587efa3568a065e88b513fd..eac852e4a4ab1234fe2ae3ae47c0f74fa94d13c9 100644 --- a/src/core/channel/metadata_buffer.c +++ b/src/core/channel/metadata_buffer.c @@ -147,54 +147,3 @@ void grpc_metadata_buffer_flush(grpc_metadata_buffer *buffer, gpr_free(impl); *buffer = NULL; } - -size_t grpc_metadata_buffer_count(const grpc_metadata_buffer *buffer) { - return *buffer ? (*buffer)->elems : 0; -} - -typedef struct { - grpc_metadata_buffer_impl *impl; -} elems_hdr; - -grpc_metadata *grpc_metadata_buffer_extract_elements( - grpc_metadata_buffer *buffer) { - grpc_metadata_buffer_impl *impl; - elems_hdr *hdr; - qelem *src; - grpc_metadata *out; - size_t i; - - impl = *buffer; - - if (!impl) { - return NULL; - } - - hdr = gpr_malloc(sizeof(elems_hdr) + impl->elems * sizeof(grpc_metadata)); - src = ELEMS(impl); - out = (grpc_metadata *)(hdr + 1); - - hdr->impl = impl; - for (i = 0; i < impl->elems; i++) { - out[i].key = (char *)grpc_mdstr_as_c_string(src[i].md->key); - out[i].value = (char *)grpc_mdstr_as_c_string(src[i].md->value); - out[i].value_length = GPR_SLICE_LENGTH(src[i].md->value->slice); - } - - /* clear out buffer (it's not possible to extract elements twice */ - *buffer = NULL; - - return out; -} - -void grpc_metadata_buffer_cleanup_elements(void *elements, - grpc_op_error error) { - elems_hdr *hdr = ((elems_hdr *)elements) - 1; - - if (!elements) { - return; - } - - grpc_metadata_buffer_destroy(&hdr->impl, error); - gpr_free(hdr); -} diff --git a/src/core/iomgr/fd_posix.c b/src/core/iomgr/fd_posix.c index abdd49bbda36b960fe1206a0e1a6095493eb08d7..9c8133d2d4c3b59cf319fbc75e76799cc00bc3c7 100644 --- a/src/core/iomgr/fd_posix.c +++ b/src/core/iomgr/fd_posix.c @@ -210,7 +210,7 @@ static void notify_on(grpc_fd *fd, gpr_atm *st, grpc_iomgr_closure *closure, /* swap was unsuccessful due to an intervening set_ready call. Fall through to the READY code below */ case READY: - assert(gpr_atm_acq_load(st) == READY); + assert(gpr_atm_no_barrier_load(st) == READY); gpr_atm_rel_store(st, NOT_READY); make_callback(closure->cb, closure->cb_arg, !gpr_atm_acq_load(&fd->shutdown), @@ -245,8 +245,8 @@ static void set_ready_locked(gpr_atm *st, grpc_iomgr_closure *callbacks, Fall through to the WAITING code below */ state = gpr_atm_acq_load(st); default: /* waiting */ - assert(gpr_atm_acq_load(st) != READY && - gpr_atm_acq_load(st) != NOT_READY); + assert(gpr_atm_no_barrier_load(st) != READY && + gpr_atm_no_barrier_load(st) != NOT_READY); callbacks[(*ncallbacks)++] = *(grpc_iomgr_closure *)state; gpr_atm_rel_store(st, NOT_READY); return; @@ -271,7 +271,7 @@ void grpc_fd_shutdown(grpc_fd *fd) { grpc_iomgr_closure cb[2]; size_t ncb = 0; gpr_mu_lock(&fd->set_state_mu); - GPR_ASSERT(!gpr_atm_acq_load(&fd->shutdown)); + GPR_ASSERT(!gpr_atm_no_barrier_load(&fd->shutdown)); gpr_atm_rel_store(&fd->shutdown, 1); set_ready_locked(&fd->readst, cb, &ncb); set_ready_locked(&fd->writest, cb, &ncb); diff --git a/src/core/security/credentials.c b/src/core/security/credentials.c index 3ad1e7edd7617b7274ac19041ac694b64e704547..698e0991349822ee50d9b261054472e66ffe9ed9 100644 --- a/src/core/security/credentials.c +++ b/src/core/security/credentials.c @@ -46,20 +46,6 @@ #include <grpc/support/sync.h> #include <grpc/support/time.h> -/* -- Constants. -- */ - -#define GRPC_SECURE_TOKEN_REFRESH_THRESHOLD_SECS 60 - -#define GRPC_COMPUTE_ENGINE_METADATA_HOST "metadata" -#define GRPC_COMPUTE_ENGINE_METADATA_TOKEN_PATH \ - "/computeMetadata/v1/instance/service-accounts/default/token" - -#define GRPC_SERVICE_ACCOUNT_HOST "www.googleapis.com" -#define GRPC_SERVICE_ACCOUNT_TOKEN_PATH "/oauth2/v3/token" -#define GRPC_SERVICE_ACCOUNT_POST_BODY_PREFIX \ - "grant_type=urn%3Aietf%3Aparams%3Aoauth%3Agrant-type%3Ajwt-bearer&" \ - "assertion=" - /* -- Common. -- */ typedef struct { @@ -671,8 +657,8 @@ static void service_account_fetch_oauth2( } gpr_asprintf(&body, "%s%s", GRPC_SERVICE_ACCOUNT_POST_BODY_PREFIX, jwt); memset(&request, 0, sizeof(grpc_httpcli_request)); - request.host = GRPC_SERVICE_ACCOUNT_HOST; - request.path = GRPC_SERVICE_ACCOUNT_TOKEN_PATH; + request.host = GRPC_GOOGLE_OAUTH2_SERVICE_HOST; + request.path = GRPC_GOOGLE_OAUTH2_SERVICE_TOKEN_PATH; request.hdr_count = 1; request.hdrs = &header; request.use_ssl = 1; @@ -703,6 +689,67 @@ grpc_credentials *grpc_service_account_credentials_create( return &c->base.base; } +/* -- RefreshToken credentials. -- */ + +typedef struct { + grpc_oauth2_token_fetcher_credentials base; + grpc_auth_refresh_token refresh_token; +} grpc_refresh_token_credentials; + +static void refresh_token_destroy(grpc_credentials *creds) { + grpc_refresh_token_credentials *c = + (grpc_refresh_token_credentials *)creds; + grpc_auth_refresh_token_destruct(&c->refresh_token); + oauth2_token_fetcher_destroy(&c->base.base); +} + +static grpc_credentials_vtable refresh_token_vtable = { + refresh_token_destroy, oauth2_token_fetcher_has_request_metadata, + oauth2_token_fetcher_has_request_metadata_only, + oauth2_token_fetcher_get_request_metadata}; + +static void refresh_token_fetch_oauth2( + grpc_credentials_metadata_request *metadata_req, + grpc_httpcli_response_cb response_cb, gpr_timespec deadline) { + grpc_refresh_token_credentials *c = + (grpc_refresh_token_credentials *)metadata_req->creds; + grpc_httpcli_header header = {"Content-Type", + "application/x-www-form-urlencoded"}; + grpc_httpcli_request request; + char *body = NULL; + gpr_asprintf(&body, GRPC_REFRESH_TOKEN_POST_BODY_FORMAT_STRING, + c->refresh_token.client_id, c->refresh_token.client_secret, + c->refresh_token.refresh_token); + memset(&request, 0, sizeof(grpc_httpcli_request)); + request.host = GRPC_GOOGLE_OAUTH2_SERVICE_HOST; + request.path = GRPC_GOOGLE_OAUTH2_SERVICE_TOKEN_PATH; + request.hdr_count = 1; + request.hdrs = &header; + request.use_ssl = 1; + grpc_httpcli_post(&request, body, strlen(body), deadline, response_cb, + metadata_req); + gpr_free(body); +} + +grpc_credentials *grpc_refresh_token_credentials_create( + const char *json_refresh_token) { + grpc_refresh_token_credentials *c; + grpc_auth_refresh_token refresh_token = + grpc_auth_refresh_token_create_from_string(json_refresh_token); + + if (!grpc_auth_refresh_token_is_valid(&refresh_token)) { + gpr_log(GPR_ERROR, + "Invalid input for refresh token credentials creation"); + return NULL; + } + c = gpr_malloc(sizeof(grpc_refresh_token_credentials)); + memset(c, 0, sizeof(grpc_refresh_token_credentials)); + init_oauth2_token_fetcher(&c->base, refresh_token_fetch_oauth2); + c->base.base.vtable = &refresh_token_vtable; + c->refresh_token = refresh_token; + return &c->base.base; +} + /* -- Fake Oauth2 credentials. -- */ typedef struct { diff --git a/src/core/security/credentials.h b/src/core/security/credentials.h index 454e66845d169e022751e671bf73e919caaedf99..0f70670ced4c15ff191cb0f4525831bfa1af5f9c 100644 --- a/src/core/security/credentials.h +++ b/src/core/security/credentials.h @@ -64,6 +64,22 @@ typedef enum { #define GRPC_GOOGLE_WELL_KNOWN_CREDENTIALS_FILE \ "application_default_credentials.json" +#define GRPC_SECURE_TOKEN_REFRESH_THRESHOLD_SECS 60 + +#define GRPC_COMPUTE_ENGINE_METADATA_HOST "metadata" +#define GRPC_COMPUTE_ENGINE_METADATA_TOKEN_PATH \ + "/computeMetadata/v1/instance/service-accounts/default/token" + +#define GRPC_GOOGLE_OAUTH2_SERVICE_HOST "www.googleapis.com" +#define GRPC_GOOGLE_OAUTH2_SERVICE_TOKEN_PATH "/oauth2/v3/token" + +#define GRPC_SERVICE_ACCOUNT_POST_BODY_PREFIX \ + "grant_type=urn%3Aietf%3Aparams%3Aoauth%3Agrant-type%3Ajwt-bearer&" \ + "assertion=" + +#define GRPC_REFRESH_TOKEN_POST_BODY_FORMAT_STRING \ + "client_id=%s&client_secret=%s&refresh_token=%s&grant_type=refresh_token" + /* --- grpc_credentials. --- */ /* It is the caller's responsibility to gpr_free the result if not NULL. */ diff --git a/src/core/security/google_default_credentials.c b/src/core/security/google_default_credentials.c index bdc907e7b33ada137d4af315799ac63db8f669ac..ebea70dad26a107b66fa98a12c34dfb8a4048384 100644 --- a/src/core/security/google_default_credentials.c +++ b/src/core/security/google_default_credentials.c @@ -138,6 +138,23 @@ static grpc_credentials *create_jwt_creds_from_path(char *creds_path) { return result; } +/* Takes ownership of creds_path if not NULL. */ +static grpc_credentials *create_refresh_token_creds_from_path( + char *creds_path) { + grpc_credentials *result = NULL; + gpr_slice creds_data; + int file_ok = 0; + if (creds_path == NULL) return NULL; + creds_data = gpr_load_file(creds_path, &file_ok); + gpr_free(creds_path); + if (file_ok) { + result = grpc_refresh_token_credentials_create( + (const char *)GPR_SLICE_START_PTR(creds_data)); + gpr_slice_unref(creds_data); + } + return result; +} + grpc_credentials *grpc_google_default_credentials_create(void) { grpc_credentials *result = NULL; int serving_cached_credentials = 0; @@ -157,7 +174,7 @@ grpc_credentials *grpc_google_default_credentials_create(void) { if (result != NULL) goto end; /* Then the well-known file. */ - result = create_jwt_creds_from_path( + result = create_refresh_token_creds_from_path( grpc_get_well_known_google_credentials_file_path()); if (result != NULL) goto end; diff --git a/src/core/security/json_token.c b/src/core/security/json_token.c index 40b612b2065e11213f82a33834407a6a452376b9..eadae336099ae6f48f33fa636823adcf9d906ab3 100644 --- a/src/core/security/json_token.c +++ b/src/core/security/json_token.c @@ -52,8 +52,9 @@ /* 1 hour max. */ const gpr_timespec grpc_max_auth_token_lifetime = {3600, 0}; -#define GRPC_AUTH_JSON_KEY_TYPE_INVALID "invalid" -#define GRPC_AUTH_JSON_KEY_TYPE_SERVICE_ACCOUNT "service_account" +#define GRPC_AUTH_JSON_TYPE_INVALID "invalid" +#define GRPC_AUTH_JSON_TYPE_SERVICE_ACCOUNT "service_account" +#define GRPC_AUTH_JSON_TYPE_AUTHORIZED_USER "authorized_user" #define GRPC_JWT_RSA_SHA256_ALGORITHM "RS256" #define GRPC_JWT_TYPE "JWT" @@ -87,7 +88,7 @@ static int set_json_key_string_property(grpc_json *json, const char *prop_name, int grpc_auth_json_key_is_valid(const grpc_auth_json_key *json_key) { return (json_key != NULL) && - strcmp(json_key->type, GRPC_AUTH_JSON_KEY_TYPE_INVALID); + strcmp(json_key->type, GRPC_AUTH_JSON_TYPE_INVALID); } grpc_auth_json_key grpc_auth_json_key_create_from_string( @@ -100,7 +101,7 @@ grpc_auth_json_key grpc_auth_json_key_create_from_string( int success = 0; memset(&result, 0, sizeof(grpc_auth_json_key)); - result.type = GRPC_AUTH_JSON_KEY_TYPE_INVALID; + result.type = GRPC_AUTH_JSON_TYPE_INVALID; if (json == NULL) { gpr_log(GPR_ERROR, "Invalid json string %s", json_string); goto end; @@ -108,10 +109,10 @@ grpc_auth_json_key grpc_auth_json_key_create_from_string( prop_value = json_get_string_property(json, "type"); if (prop_value == NULL || - strcmp(prop_value, GRPC_AUTH_JSON_KEY_TYPE_SERVICE_ACCOUNT)) { + strcmp(prop_value, GRPC_AUTH_JSON_TYPE_SERVICE_ACCOUNT)) { goto end; } - result.type = GRPC_AUTH_JSON_KEY_TYPE_SERVICE_ACCOUNT; + result.type = GRPC_AUTH_JSON_TYPE_SERVICE_ACCOUNT; if (!set_json_key_string_property(json, "private_key_id", &result.private_key_id) || @@ -148,7 +149,7 @@ end: void grpc_auth_json_key_destruct(grpc_auth_json_key *json_key) { if (json_key == NULL) return; - json_key->type = GRPC_AUTH_JSON_KEY_TYPE_INVALID; + json_key->type = GRPC_AUTH_JSON_TYPE_INVALID; if (json_key->client_id != NULL) { gpr_free(json_key->client_id); json_key->client_id = NULL; @@ -331,3 +332,67 @@ void grpc_jwt_encode_and_sign_set_override( grpc_jwt_encode_and_sign_override func) { g_jwt_encode_and_sign_override = func; } + +/* --- grpc_auth_refresh_token --- */ + +int grpc_auth_refresh_token_is_valid( + const grpc_auth_refresh_token *refresh_token) { + return (refresh_token != NULL) && + strcmp(refresh_token->type, GRPC_AUTH_JSON_TYPE_INVALID); +} + +grpc_auth_refresh_token grpc_auth_refresh_token_create_from_string( + const char *json_string) { + grpc_auth_refresh_token result; + char *scratchpad = gpr_strdup(json_string); + grpc_json *json = grpc_json_parse_string(scratchpad); + const char *prop_value; + int success = 0; + + memset(&result, 0, sizeof(grpc_auth_refresh_token)); + result.type = GRPC_AUTH_JSON_TYPE_INVALID; + if (json == NULL) { + gpr_log(GPR_ERROR, "Invalid json string %s", json_string); + goto end; + } + + prop_value = json_get_string_property(json, "type"); + if (prop_value == NULL || + strcmp(prop_value, GRPC_AUTH_JSON_TYPE_AUTHORIZED_USER)) { + goto end; + } + result.type = GRPC_AUTH_JSON_TYPE_AUTHORIZED_USER; + + if (!set_json_key_string_property(json, "client_secret", + &result.client_secret) || + !set_json_key_string_property(json, "client_id", &result.client_id) || + !set_json_key_string_property(json, "refresh_token", + &result.refresh_token)) { + goto end; + } + success = 1; + +end: + if (json != NULL) grpc_json_destroy(json); + if (!success) grpc_auth_refresh_token_destruct(&result); + gpr_free(scratchpad); + return result; +} + +void grpc_auth_refresh_token_destruct(grpc_auth_refresh_token *refresh_token) { + if (refresh_token == NULL) return; + refresh_token->type = GRPC_AUTH_JSON_TYPE_INVALID; + if (refresh_token->client_id != NULL) { + gpr_free(refresh_token->client_id); + refresh_token->client_id = NULL; + } + if (refresh_token->client_secret != NULL) { + gpr_free(refresh_token->client_secret); + refresh_token->client_secret = NULL; + } + if (refresh_token->refresh_token != NULL) { + gpr_free(refresh_token->refresh_token); + refresh_token->refresh_token = NULL; + } +} + diff --git a/src/core/security/json_token.h b/src/core/security/json_token.h index 029ede3955846412a1d86abc6c38ab2efae92673..197796ab4cd2f6f3d1f5553e0798a08fb6035f24 100644 --- a/src/core/security/json_token.h +++ b/src/core/security/json_token.h @@ -44,7 +44,7 @@ /* --- auth_json_key parsing. --- */ typedef struct { - char *type; + const char *type; char *private_key_id; char *client_id; char *client_email; @@ -79,4 +79,25 @@ typedef char *(*grpc_jwt_encode_and_sign_override)( void grpc_jwt_encode_and_sign_set_override( grpc_jwt_encode_and_sign_override func); +/* --- auth_refresh_token parsing. --- */ + +typedef struct { + const char *type; + char *client_id; + char *client_secret; + char *refresh_token; +} grpc_auth_refresh_token; + +/* Returns 1 if the object is valid, 0 otherwise. */ +int grpc_auth_refresh_token_is_valid( + const grpc_auth_refresh_token *refresh_token); + +/* Creates a refresh token object from string. Returns an invalid object if a + parsing error has been encountered. */ +grpc_auth_refresh_token grpc_auth_refresh_token_create_from_string( + const char *json_string); + +/* Destructs the object. */ +void grpc_auth_refresh_token_destruct(grpc_auth_refresh_token *refresh_token); + #endif /* GRPC_INTERNAL_CORE_SECURITY_JSON_TOKEN_H */ diff --git a/src/core/transport/chttp2_transport.c b/src/core/transport/chttp2_transport.c index 0d01a371128b0762baabfd535299a63604b7a37d..2b15b2a8128cb75d55d7a6c68337617fba7a1ae9 100644 --- a/src/core/transport/chttp2_transport.c +++ b/src/core/transport/chttp2_transport.c @@ -1655,7 +1655,15 @@ static int process_read(transport *t, gpr_slice slice) { if (!init_frame_parser(t)) { return 0; } - t->last_incoming_stream_id = t->incoming_stream_id; + /* t->last_incoming_stream_id is used as last-stream-id when + sending GOAWAY frame. + https://tools.ietf.org/html/draft-ietf-httpbis-http2-17#section-6.8 + says that last-stream-id is peer-initiated stream ID. So, + since we don't have server pushed streams, client should send + GOAWAY last-stream-id=0 in this case. */ + if (!t->is_client) { + t->last_incoming_stream_id = t->incoming_stream_id; + } if (t->incoming_frame_size == 0) { if (!parse_frame_slice(t, gpr_empty_slice(), 1)) { return 0; diff --git a/src/cpp/client/insecure_credentials.cc b/src/cpp/client/insecure_credentials.cc index 2dcfe69591aef588056d20a5e172210bed97d808..f3ca430bd4c56348fa9a093478c45158c1b8158f 100644 --- a/src/cpp/client/insecure_credentials.cc +++ b/src/cpp/client/insecure_credentials.cc @@ -54,7 +54,7 @@ class InsecureCredentialsImpl GRPC_FINAL : public Credentials { target, grpc_channel_create(target.c_str(), &channel_args))); } - SecureCredentials* AsSecureCredentials() { return nullptr; } + SecureCredentials* AsSecureCredentials() GRPC_OVERRIDE { return nullptr; } }; } // namespace diff --git a/src/cpp/client/secure_credentials.cc b/src/cpp/client/secure_credentials.cc index 47f645c1b6366d9698470a5f79ce974df588648a..a2f6a698583e9c746130eb35ca78e1a08ac150f3 100644 --- a/src/cpp/client/secure_credentials.cc +++ b/src/cpp/client/secure_credentials.cc @@ -59,7 +59,7 @@ class SecureCredentials GRPC_FINAL : public Credentials { grpc_secure_channel_create(c_creds_, target.c_str(), &channel_args))); } - SecureCredentials* AsSecureCredentials() { return this; } + SecureCredentials* AsSecureCredentials() GRPC_OVERRIDE { return this; } private: grpc_credentials* const c_creds_; @@ -98,12 +98,30 @@ std::unique_ptr<Credentials> ComputeEngineCredentials() { std::unique_ptr<Credentials> ServiceAccountCredentials( const grpc::string& json_key, const grpc::string& scope, std::chrono::seconds token_lifetime) { - gpr_timespec lifetime = gpr_time_from_seconds( - token_lifetime.count() > 0 ? token_lifetime.count() : 0); + if (token_lifetime.count() <= 0) { + gpr_log(GPR_ERROR, + "Trying to create ServiceAccountCredentials " + "with non-positive lifetime"); + return WrapCredentials(nullptr); + } + gpr_timespec lifetime = gpr_time_from_seconds(token_lifetime.count()); return WrapCredentials(grpc_service_account_credentials_create( json_key.c_str(), scope.c_str(), lifetime)); } +// Builds JWT credentials. +std::unique_ptr<Credentials> JWTCredentials( + const grpc::string &json_key, std::chrono::seconds token_lifetime) { + if (token_lifetime.count() <= 0) { + gpr_log(GPR_ERROR, + "Trying to create JWTCredentials with non-positive lifetime"); + return WrapCredentials(nullptr); + } + gpr_timespec lifetime = gpr_time_from_seconds(token_lifetime.count()); + return WrapCredentials( + grpc_jwt_credentials_create(json_key.c_str(), lifetime)); +} + // Builds IAM credentials. std::unique_ptr<Credentials> IAMCredentials( const grpc::string& authorization_token, diff --git a/src/cpp/proto/proto_utils.cc b/src/cpp/proto/proto_utils.cc index e4e51bfebf5e78d048cf6ce447b105307dbc48b1..9254e5879f238a2a28b1f7ecd36670d2c9e3fcbf 100644 --- a/src/cpp/proto/proto_utils.cc +++ b/src/cpp/proto/proto_utils.cc @@ -39,12 +39,11 @@ #include <grpc/support/slice.h> #include <grpc/support/slice_buffer.h> #include <grpc/support/port_platform.h> -#include <google/protobuf/io/zero_copy_stream.h> const int kMaxBufferLength = 8192; class GrpcBufferWriter GRPC_FINAL - : public ::google::protobuf::io::ZeroCopyOutputStream { + : public ::grpc::protobuf::io::ZeroCopyOutputStream { public: explicit GrpcBufferWriter(grpc_byte_buffer **bp, int block_size = kMaxBufferLength) @@ -85,7 +84,7 @@ class GrpcBufferWriter GRPC_FINAL byte_count_ -= count; } - gpr_int64 ByteCount() const GRPC_OVERRIDE { return byte_count_; } + grpc::protobuf::int64 ByteCount() const GRPC_OVERRIDE { return byte_count_; } private: const int block_size_; @@ -97,7 +96,7 @@ class GrpcBufferWriter GRPC_FINAL }; class GrpcBufferReader GRPC_FINAL - : public ::google::protobuf::io::ZeroCopyInputStream { + : public ::grpc::protobuf::io::ZeroCopyInputStream { public: explicit GrpcBufferReader(grpc_byte_buffer *buffer) : byte_count_(0), backup_count_(0) { @@ -143,7 +142,7 @@ class GrpcBufferReader GRPC_FINAL return false; } - gpr_int64 ByteCount() const GRPC_OVERRIDE { + grpc::protobuf::int64 ByteCount() const GRPC_OVERRIDE { return byte_count_ - backup_count_; } diff --git a/src/cpp/server/server.cc b/src/cpp/server/server.cc index cd6b8a554be04464068c9c2f851b86628a2f6937..ac350df62db3ae314fd0795ba7a9a77e6ef3af06 100644 --- a/src/cpp/server/server.cc +++ b/src/cpp/server/server.cc @@ -181,12 +181,12 @@ Server::Server(ThreadPoolInterface* thread_pool, bool thread_pool_owned) thread_pool_owned_(thread_pool_owned) {} Server::~Server() { - std::unique_lock<std::mutex> lock(mu_); - if (started_ && !shutdown_) { - lock.unlock(); - Shutdown(); - } else { - lock.unlock(); + { + std::unique_lock<std::mutex> lock(mu_); + if (started_ && !shutdown_) { + lock.unlock(); + Shutdown(); + } } grpc_server_destroy(server_); if (thread_pool_owned_) { diff --git a/src/csharp/Grpc.Core.Tests/ClientServerTest.cs b/src/csharp/Grpc.Core.Tests/ClientServerTest.cs index 39be35c21906ec582e10f533101fc36a89515a94..e73159b35073ca4eaefc519c613a8bf92adb525a 100644 --- a/src/csharp/Grpc.Core.Tests/ClientServerTest.cs +++ b/src/csharp/Grpc.Core.Tests/ClientServerTest.cs @@ -122,10 +122,13 @@ namespace Grpc.Core.Tests { var call = new Call<string, string>(unaryEchoStringMethod, channel); - try { + try + { Calls.BlockingUnaryCall(call, "ABC", default(CancellationToken)); Assert.Fail(); - } catch(RpcException e) { + } + catch (RpcException e) + { Assert.AreEqual(StatusCode.Unimplemented, e.Status.StatusCode); } } @@ -140,4 +143,3 @@ namespace Grpc.Core.Tests } } } - diff --git a/src/csharp/Grpc.Core.Tests/GrpcEnvironmentTest.cs b/src/csharp/Grpc.Core.Tests/GrpcEnvironmentTest.cs index 596918c231c0115164a0e95ae25fb4bfa706aabd..6a132a5b224c1b9948eb4e42a8f95742e5da6a92 100644 --- a/src/csharp/Grpc.Core.Tests/GrpcEnvironmentTest.cs +++ b/src/csharp/Grpc.Core.Tests/GrpcEnvironmentTest.cs @@ -68,7 +68,7 @@ namespace Grpc.Core.Tests var tp2 = GrpcEnvironment.ThreadPool; GrpcEnvironment.Shutdown(); - Assert.IsFalse(Object.ReferenceEquals(tp1, tp2)); + Assert.IsFalse(object.ReferenceEquals(tp1, tp2)); } } } diff --git a/src/csharp/Grpc.Core.Tests/PInvokeTest.cs b/src/csharp/Grpc.Core.Tests/PInvokeTest.cs index 9db08d2f02f7ba5042a694cdd30ef065eedf1c9a..3beffc39559a86021e2d211da54c987c8a1d1ae2 100644 --- a/src/csharp/Grpc.Core.Tests/PInvokeTest.cs +++ b/src/csharp/Grpc.Core.Tests/PInvokeTest.cs @@ -33,13 +33,13 @@ using System; using System.Diagnostics; +using System.Runtime.InteropServices; using System.Threading; using System.Threading.Tasks; using Grpc.Core; using Grpc.Core.Internal; using Grpc.Core.Utils; using NUnit.Framework; -using System.Runtime.InteropServices; namespace Grpc.Core.Tests { @@ -73,14 +73,13 @@ namespace Grpc.Core.Tests { BenchmarkUtil.RunBenchmark( 100000, 1000000, - () => { + () => + { CompletionQueueSafeHandle cq = CompletionQueueSafeHandle.Create(); cq.Dispose(); - } - ); + }); } - /// <summary> /// Approximate results: /// (~80ns Mono Linux) @@ -94,10 +93,10 @@ namespace Grpc.Core.Tests counter = 0; BenchmarkUtil.RunBenchmark( 1000000, 10000000, - () => { + () => + { grpcsharp_test_callback(handler); - } - ); + }); Assert.AreNotEqual(0, counter); } @@ -113,10 +112,10 @@ namespace Grpc.Core.Tests counter = 0; BenchmarkUtil.RunBenchmark( 10000, 10000, - () => { - grpcsharp_test_callback(new CompletionCallbackDelegate(Handler)); - } - ); + () => + { + grpcsharp_test_callback(new CompletionCallbackDelegate(Handler)); + }); Assert.AreNotEqual(0, counter); } @@ -129,15 +128,15 @@ namespace Grpc.Core.Tests { BenchmarkUtil.RunBenchmark( 1000000, 100000000, - () => { + () => + { grpcsharp_test_nop(IntPtr.Zero); - } - ); + }); } - private void Handler(GRPCOpError op, IntPtr ptr) { - counter ++; + private void Handler(GRPCOpError op, IntPtr ptr) + { + counter++; } } } - diff --git a/src/csharp/Grpc.Core.Tests/Properties/AssemblyInfo.cs b/src/csharp/Grpc.Core.Tests/Properties/AssemblyInfo.cs index 499d931d2acf15cc93ef0d4c6534ad0982fa80c3..e4328806ad4c67c0f2c868afa0969c09b0608d4d 100644 --- a/src/csharp/Grpc.Core.Tests/Properties/AssemblyInfo.cs +++ b/src/csharp/Grpc.Core.Tests/Properties/AssemblyInfo.cs @@ -1,8 +1,6 @@ using System.Reflection; using System.Runtime.CompilerServices; -// Information about this assembly is defined by the following attributes. -// Change them to the values specific to your project. [assembly: AssemblyTitle("Grpc.Core.Tests")] [assembly: AssemblyDescription("")] [assembly: AssemblyConfiguration("")] @@ -11,12 +9,4 @@ using System.Runtime.CompilerServices; [assembly: AssemblyCopyright("Google Inc. All rights reserved.")] [assembly: AssemblyTrademark("")] [assembly: AssemblyCulture("")] -// The assembly version has the format "{Major}.{Minor}.{Build}.{Revision}". -// The form "{Major}.{Minor}.*" will automatically update the build and revision, -// and "{Major}.{Minor}.{Build}.*" will update just the revision. [assembly: AssemblyVersion("0.1.*")] -// The following attributes are used to specify the signing key for the assembly, -// if desired. See the Mono documentation for more information about signing. -//[assembly: AssemblyDelaySign(false)] -//[assembly: AssemblyKeyFile("")] - diff --git a/src/csharp/Grpc.Core.Tests/ServerTest.cs b/src/csharp/Grpc.Core.Tests/ServerTest.cs index dd30366f6a1286684783b72848121238739f8d45..12f914bfad1bfcb77e5bfb3332eaba773a0f0fcb 100644 --- a/src/csharp/Grpc.Core.Tests/ServerTest.cs +++ b/src/csharp/Grpc.Core.Tests/ServerTest.cs @@ -53,6 +53,5 @@ namespace Grpc.Core.Tests GrpcEnvironment.Shutdown(); } - } } diff --git a/src/csharp/Grpc.Core.Tests/TimespecTest.cs b/src/csharp/Grpc.Core.Tests/TimespecTest.cs index 0ca84ec44bfcdf38dec68e4c5dc360997fc96c06..f5bae6d93552c670bf4f919dd654d2c2eecd480d 100644 --- a/src/csharp/Grpc.Core.Tests/TimespecTest.cs +++ b/src/csharp/Grpc.Core.Tests/TimespecTest.cs @@ -86,4 +86,3 @@ namespace Grpc.Core.Internal.Tests } } } - diff --git a/src/csharp/Grpc.Core/Call.cs b/src/csharp/Grpc.Core/Call.cs index 72dca688952ccd78fd87ae329c3c5dbc43808bda..d84d5940c288c552b1201361084c71f846bead79 100644 --- a/src/csharp/Grpc.Core/Call.cs +++ b/src/csharp/Grpc.Core/Call.cs @@ -47,7 +47,8 @@ namespace Grpc.Core Func<TRequest, byte[]> requestSerializer, Func<byte[], TResponse> responseDeserializer, TimeSpan timeout, - Channel channel) { + Channel channel) + { this.methodName = methodName; this.requestSerializer = requestSerializer; this.responseDeserializer = responseDeserializer; @@ -95,4 +96,3 @@ namespace Grpc.Core } } } - diff --git a/src/csharp/Grpc.Core/Calls.cs b/src/csharp/Grpc.Core/Calls.cs index ee2208e5c255768715cca2f2045f17d37a060bcc..cc1d67afcaeed8d1c0766e8845771bd952d4567a 100644 --- a/src/csharp/Grpc.Core/Calls.cs +++ b/src/csharp/Grpc.Core/Calls.cs @@ -38,8 +38,6 @@ using Grpc.Core.Internal; namespace Grpc.Core { - // NOTE: this class is work-in-progress - /// <summary> /// Helper methods for generated stubs to make RPC calls. /// </summary> @@ -89,9 +87,9 @@ namespace Grpc.Core return new ClientStreamingInputObserver<TRequest, TResponse>(asyncCall); } - private static CompletionQueueSafeHandle GetCompletionQueue() { + private static CompletionQueueSafeHandle GetCompletionQueue() + { return GrpcEnvironment.ThreadPool.CompletionQueue; } } } - diff --git a/src/csharp/Grpc.Core/Channel.cs b/src/csharp/Grpc.Core/Channel.cs index 83d965debf12a097874e97f026195f91e5605a01..3a42dac1d7a54fe8610b5153f69faec12785bbe3 100644 --- a/src/csharp/Grpc.Core/Channel.cs +++ b/src/csharp/Grpc.Core/Channel.cs @@ -36,10 +36,13 @@ using Grpc.Core.Internal; namespace Grpc.Core { + /// <summary> + /// gRPC Channel + /// </summary> public class Channel : IDisposable { readonly ChannelSafeHandle handle; - readonly String target; + readonly string target; /// <summary> /// Creates a channel. diff --git a/src/csharp/Grpc.Core/ChannelArgs.cs b/src/csharp/Grpc.Core/ChannelArgs.cs index 298b6edf2066f78e031ea6ca990a10bd47961364..74ab310e44e64800d097e3f9afc1fac3c549730f 100644 --- a/src/csharp/Grpc.Core/ChannelArgs.cs +++ b/src/csharp/Grpc.Core/ChannelArgs.cs @@ -30,6 +30,7 @@ #endregion using System; using System.Collections.Generic; +using System.Collections.Immutable; using System.Runtime.InteropServices; using System.Threading; using System.Threading.Tasks; @@ -37,33 +38,18 @@ using Grpc.Core.Internal; namespace Grpc.Core { - // TODO: should we be using the builder pattern? + /// <summary> + /// gRPC channel options. + /// </summary> public class ChannelArgs { public const string SslTargetNameOverrideKey = "grpc.ssl_target_name_override"; - public class Builder - { - Dictionary<string,string> stringArgs = new Dictionary<string,string>(); - // TODO: AddInteger not supported yet. - public Builder AddString(string key, string value) - { - stringArgs.Add(key, value); - return this; - } + readonly ImmutableDictionary<string, string> stringArgs; - public ChannelArgs Build() - { - return new ChannelArgs(stringArgs); - } - } - - Dictionary<string,string> stringArgs; - - private ChannelArgs(Dictionary<string, string> stringArgs) + private ChannelArgs(ImmutableDictionary<string, string> stringArgs) { - // TODO: use immutable dict? - this.stringArgs = new Dictionary<string, string>(stringArgs); + this.stringArgs = stringArgs; } public string GetSslTargetNameOverride() @@ -76,11 +62,28 @@ namespace Grpc.Core return null; } - public static Builder NewBuilder() + public static Builder CreateBuilder() { return new Builder(); } + public class Builder + { + readonly Dictionary<string, string> stringArgs = new Dictionary<string, string>(); + + // TODO: AddInteger not supported yet. + public Builder AddString(string key, string value) + { + stringArgs.Add(key, value); + return this; + } + + public ChannelArgs Build() + { + return new ChannelArgs(stringArgs.ToImmutableDictionary()); + } + } + /// <summary> /// Creates native object for the channel arguments. /// </summary> diff --git a/src/csharp/Grpc.Core/ClientStreamingAsyncResult.cs b/src/csharp/Grpc.Core/ClientStreamingAsyncResult.cs index 44580a115424110c78adc13ca11618b54320727c..65bedb0a33f6a96234acf8d0aa6600caae5cd1bd 100644 --- a/src/csharp/Grpc.Core/ClientStreamingAsyncResult.cs +++ b/src/csharp/Grpc.Core/ClientStreamingAsyncResult.cs @@ -67,4 +67,3 @@ namespace Grpc.Core } } } - diff --git a/src/csharp/Grpc.Core/Credentials.cs b/src/csharp/Grpc.Core/Credentials.cs index 5116c277f72a6880abb56a142b5876c1e16c9914..15dd3ef3216e2a14c6b2cb79a11ed7763bc97533 100644 --- a/src/csharp/Grpc.Core/Credentials.cs +++ b/src/csharp/Grpc.Core/Credentials.cs @@ -36,6 +36,9 @@ using Grpc.Core.Internal; namespace Grpc.Core { + /// <summary> + /// Client-side credentials. + /// </summary> public abstract class Credentials { /// <summary> @@ -74,4 +77,3 @@ namespace Grpc.Core } } } - diff --git a/src/csharp/Grpc.Core/Grpc.Core.csproj b/src/csharp/Grpc.Core/Grpc.Core.csproj index c4b12b1cab03545697417a7b7275d5e4abf8628b..29f1a0604a20eb7be0a865312eff97780d54b20d 100644 --- a/src/csharp/Grpc.Core/Grpc.Core.csproj +++ b/src/csharp/Grpc.Core/Grpc.Core.csproj @@ -31,6 +31,9 @@ </PropertyGroup> <ItemGroup> <Reference Include="System" /> + <Reference Include="System.Collections.Immutable"> + <HintPath>..\packages\System.Collections.Immutable.1.1.34-rc\lib\portable-net45+win8+wp8+wpa81\System.Collections.Immutable.dll</HintPath> + </Reference> </ItemGroup> <ItemGroup> <Compile Include="Internal\GrpcLog.cs" /> @@ -54,7 +57,7 @@ <Compile Include="Internal\ServerSafeHandle.cs" /> <Compile Include="Method.cs" /> <Compile Include="ServerCalls.cs" /> - <Compile Include="ServerCallHandler.cs" /> + <Compile Include="Internal\ServerCallHandler.cs" /> <Compile Include="Marshaller.cs" /> <Compile Include="ServerServiceDefinition.cs" /> <Compile Include="Utils\RecordingObserver.cs" /> @@ -77,6 +80,9 @@ <Compile Include="Internal\ServerCredentialsSafeHandle.cs" /> <Compile Include="ServerCredentials.cs" /> </ItemGroup> + <ItemGroup> + <None Include="packages.config" /> + </ItemGroup> <Choose> <!-- Under older versions of Monodevelop, Choose is not supported and is just ignored, which gives us the desired effect. --> diff --git a/src/csharp/Grpc.Core/GrpcEnvironment.cs b/src/csharp/Grpc.Core/GrpcEnvironment.cs index d3a8da4729e3ff3f69c29d03b9d068828d4cf466..9c10a42e23509012574f9fa9815b1b68a1d22bb6 100644 --- a/src/csharp/Grpc.Core/GrpcEnvironment.cs +++ b/src/csharp/Grpc.Core/GrpcEnvironment.cs @@ -63,8 +63,9 @@ namespace Grpc.Core /// lifetime (and call Shutdown once you're done), for the sake of easier testing it's /// allowed to initialize the environment again after it has been successfully shutdown. /// </summary> - public static void Initialize() { - lock(staticLock) + public static void Initialize() + { + lock (staticLock) { if (instance == null) { @@ -79,7 +80,7 @@ namespace Grpc.Core /// </summary> public static void Shutdown() { - lock(staticLock) + lock (staticLock) { if (instance != null) { @@ -133,4 +134,3 @@ namespace Grpc.Core } } } - diff --git a/src/csharp/Grpc.Core/Internal/AsyncCall.cs b/src/csharp/Grpc.Core/Internal/AsyncCall.cs index 5ae036298b00c16f032dc6832f1ba7bf91b76d7f..04fc28d988a669d4f847c0ae08b1adb564df92a2 100644 --- a/src/csharp/Grpc.Core/Internal/AsyncCall.cs +++ b/src/csharp/Grpc.Core/Internal/AsyncCall.cs @@ -54,7 +54,7 @@ namespace Grpc.Core.Internal TaskCompletionSource<TResponse> unaryResponseTcs; // Set after status is received. Only used for streaming response calls. - Nullable<Status> finishedStatus; + Status? finishedStatus; bool readObserverCompleted; // True if readObserver has already been completed. @@ -64,7 +64,7 @@ namespace Grpc.Core.Internal this.finishedHandler = CreateBatchCompletionCallback(HandleFinished); } - public void Initialize(Channel channel, CompletionQueueSafeHandle cq, String methodName) + public void Initialize(Channel channel, CompletionQueueSafeHandle cq, string methodName) { var call = CallSafeHandle.Create(channel.Handle, cq, methodName, channel.Target, Timespec.InfFuture); InitializeInternal(call); @@ -77,9 +77,9 @@ namespace Grpc.Core.Internal /// <summary> /// Blocking unary request - unary response call. /// </summary> - public TResponse UnaryCall(Channel channel, String methodName, TRequest msg) + public TResponse UnaryCall(Channel channel, string methodName, TRequest msg) { - using(CompletionQueueSafeHandle cq = CompletionQueueSafeHandle.Create()) + using (CompletionQueueSafeHandle cq = CompletionQueueSafeHandle.Create()) { byte[] payload = UnsafeSerialize(msg); @@ -254,7 +254,7 @@ namespace Grpc.Core.Internal /// </summary> private void HandleUnaryResponse(bool wasError, BatchContextSafeHandleNotOwned ctx) { - lock(myLock) + lock (myLock) { finished = true; halfclosed = true; @@ -264,9 +264,7 @@ namespace Grpc.Core.Internal if (wasError) { - unaryResponseTcs.SetException(new RpcException( - new Status(StatusCode.Internal, "Internal error occured.") - )); + unaryResponseTcs.SetException(new RpcException(new Status(StatusCode.Internal, "Internal error occured."))); return; } diff --git a/src/csharp/Grpc.Core/Internal/AsyncCallBase.cs b/src/csharp/Grpc.Core/Internal/AsyncCallBase.cs index 44d66b394ca6929bc1fea07c0bf85e0de5e0fcf7..15b0cfe2495705346a8ec4cfacc651ae3d5aab7b 100644 --- a/src/csharp/Grpc.Core/Internal/AsyncCallBase.cs +++ b/src/csharp/Grpc.Core/Internal/AsyncCallBase.cs @@ -225,7 +225,7 @@ namespace Grpc.Core.Internal payload = serializer(msg); return true; } - catch(Exception) + catch (Exception) { Console.WriteLine("Exception occured while trying to serialize message"); payload = null; @@ -240,7 +240,7 @@ namespace Grpc.Core.Internal msg = deserializer(payload); return true; } - catch(Exception) + catch (Exception) { Console.WriteLine("Exception occured while trying to deserialize message"); msg = default(TRead); @@ -254,7 +254,7 @@ namespace Grpc.Core.Internal { readObserver.OnNext(value); } - catch(Exception e) + catch (Exception e) { Console.WriteLine("Exception occured while invoking readObserver.OnNext: " + e); } @@ -266,7 +266,7 @@ namespace Grpc.Core.Internal { readObserver.OnCompleted(); } - catch(Exception e) + catch (Exception e) { Console.WriteLine("Exception occured while invoking readObserver.OnCompleted: " + e); } @@ -278,7 +278,7 @@ namespace Grpc.Core.Internal { readObserver.OnError(error); } - catch(Exception e) + catch (Exception e) { Console.WriteLine("Exception occured while invoking readObserver.OnError: " + e); } @@ -290,7 +290,7 @@ namespace Grpc.Core.Internal { completionDelegate(error); } - catch(Exception e) + catch (Exception e) { Console.WriteLine("Exception occured while invoking completion delegate: " + e); } @@ -302,14 +302,15 @@ namespace Grpc.Core.Internal /// </summary> protected CompletionCallbackDelegate CreateBatchCompletionCallback(Action<bool, BatchContextSafeHandleNotOwned> handler) { - return new CompletionCallbackDelegate( (error, batchContextPtr) => { + return new CompletionCallbackDelegate((error, batchContextPtr) => + { try { var ctx = new BatchContextSafeHandleNotOwned(batchContextPtr); bool wasError = (error != GRPCOpError.GRPC_OP_OK); handler(wasError, ctx); } - catch(Exception e) + catch (Exception e) { Console.WriteLine("Caught exception in a native handler: " + e); } @@ -363,7 +364,6 @@ namespace Grpc.Core.Internal { FireCompletion(origCompletionDelegate, null); } - } /// <summary> diff --git a/src/csharp/Grpc.Core/Internal/AsyncCompletion.cs b/src/csharp/Grpc.Core/Internal/AsyncCompletion.cs index b78bb497fa71efdc0a01340f50bc990a8c454ecd..673b527fb20267fb910b322615fabfb368c977e6 100644 --- a/src/csharp/Grpc.Core/Internal/AsyncCompletion.cs +++ b/src/csharp/Grpc.Core/Internal/AsyncCompletion.cs @@ -91,5 +91,4 @@ namespace Grpc.Core.Internal tcs.SetException(error); } } - } \ No newline at end of file diff --git a/src/csharp/Grpc.Core/Internal/BatchContextSafeHandleNotOwned.cs b/src/csharp/Grpc.Core/Internal/BatchContextSafeHandleNotOwned.cs index 75cd30e1a2d5f463c1d0e3f4d47091815e142db5..3c54753756edbfae2b8a27319ea93b65d4dc2b0c 100644 --- a/src/csharp/Grpc.Core/Internal/BatchContextSafeHandleNotOwned.cs +++ b/src/csharp/Grpc.Core/Internal/BatchContextSafeHandleNotOwned.cs @@ -80,16 +80,18 @@ namespace Grpc.Core.Internal { return null; } - byte[] data = new byte[(int) len]; + byte[] data = new byte[(int)len]; grpcsharp_batch_context_recv_message_to_buffer(this, data, new UIntPtr((ulong)data.Length)); return data; } - public CallSafeHandle GetServerRpcNewCall() { + public CallSafeHandle GetServerRpcNewCall() + { return grpcsharp_batch_context_server_rpc_new_call(this); } - public string GetServerRpcNewMethod() { + public string GetServerRpcNewMethod() + { return Marshal.PtrToStringAnsi(grpcsharp_batch_context_server_rpc_new_method(this)); } } diff --git a/src/csharp/Grpc.Core/Internal/CallSafeHandle.cs b/src/csharp/Grpc.Core/Internal/CallSafeHandle.cs index 61566b54072bbb8ab11f9bde2240d4b3760bd0a9..a8cef4a68b1f154a8ff050ea9cbdc4c05d631109 100644 --- a/src/csharp/Grpc.Core/Internal/CallSafeHandle.cs +++ b/src/csharp/Grpc.Core/Internal/CallSafeHandle.cs @@ -36,13 +36,14 @@ using Grpc.Core; namespace Grpc.Core.Internal { - internal delegate void CompletionCallbackDelegate(GRPCOpError error,IntPtr batchContextPtr); + internal delegate void CompletionCallbackDelegate(GRPCOpError error, IntPtr batchContextPtr); + /// <summary> /// grpc_call from <grpc/grpc.h> /// </summary> internal class CallSafeHandle : SafeHandleZeroIsInvalid { - const UInt32 GRPC_WRITE_BUFFER_HINT = 1; + const uint GRPC_WRITE_BUFFER_HINT = 1; [DllImport("grpc_csharp_ext.dll")] static extern CallSafeHandle grpcsharp_channel_create_call(ChannelSafeHandle channel, CompletionQueueSafeHandle cq, string method, string host, Timespec deadline); @@ -179,7 +180,7 @@ namespace Grpc.Core.Internal Trace.Assert(callError == GRPCCallError.GRPC_CALL_OK, "Status not GRPC_CALL_OK"); } - private static UInt32 GetFlags(bool buffered) + private static uint GetFlags(bool buffered) { return buffered ? 0 : GRPC_WRITE_BUFFER_HINT; } diff --git a/src/csharp/Grpc.Core/Internal/ChannelArgsSafeHandle.cs b/src/csharp/Grpc.Core/Internal/ChannelArgsSafeHandle.cs index ca3c21d84ce83261ca76f8cc941d5d5c05730e71..c69f1a0d0255b5a449ab9f8e2edff29f9c2206c4 100644 --- a/src/csharp/Grpc.Core/Internal/ChannelArgsSafeHandle.cs +++ b/src/csharp/Grpc.Core/Internal/ChannelArgsSafeHandle.cs @@ -74,4 +74,3 @@ namespace Grpc.Core.Internal } } } - diff --git a/src/csharp/Grpc.Core/Internal/CompletionQueueSafeHandle.cs b/src/csharp/Grpc.Core/Internal/CompletionQueueSafeHandle.cs index 6bff923c55229166189b497d666b797436dc5d3b..600d1fc87c00bb455b1020d52794d3d26fc93bdf 100644 --- a/src/csharp/Grpc.Core/Internal/CompletionQueueSafeHandle.cs +++ b/src/csharp/Grpc.Core/Internal/CompletionQueueSafeHandle.cs @@ -77,4 +77,3 @@ namespace Grpc.Core.Internal } } } - diff --git a/src/csharp/Grpc.Core/Internal/Enums.cs b/src/csharp/Grpc.Core/Internal/Enums.cs index f363050b07e592583d0e34e681e367c54c4feb25..94a2fd1784f97b30345a4f3f780428e6de2a178a 100644 --- a/src/csharp/Grpc.Core/Internal/Enums.cs +++ b/src/csharp/Grpc.Core/Internal/Enums.cs @@ -112,4 +112,3 @@ namespace Grpc.Core.Internal GRPC_OP_ERROR } } - diff --git a/src/csharp/Grpc.Core/Internal/GrpcLog.cs b/src/csharp/Grpc.Core/Internal/GrpcLog.cs index 98768d05c6db83f9fda9f23d61624adc35bfaa00..2f3c8ad71c1f850c24f1b2b9ec416dda408378d7 100644 --- a/src/csharp/Grpc.Core/Internal/GrpcLog.cs +++ b/src/csharp/Grpc.Core/Internal/GrpcLog.cs @@ -40,7 +40,7 @@ using System.Threading; namespace Grpc.Core.Internal { - internal delegate void GprLogDelegate(IntPtr fileStringPtr, Int32 line, UInt64 threadId, IntPtr severityStringPtr, IntPtr msgPtr); + internal delegate void GprLogDelegate(IntPtr fileStringPtr, int line, ulong threadId, IntPtr severityStringPtr, IntPtr msgPtr); /// <summary> /// Logs from gRPC C core library can get lost if your application is not a console app. @@ -73,7 +73,7 @@ namespace Grpc.Core.Internal } } - private static void HandleWrite(IntPtr fileStringPtr, Int32 line, UInt64 threadId, IntPtr severityStringPtr, IntPtr msgPtr) + private static void HandleWrite(IntPtr fileStringPtr, int line, ulong threadId, IntPtr severityStringPtr, IntPtr msgPtr) { try { diff --git a/src/csharp/Grpc.Core/Internal/GrpcThreadPool.cs b/src/csharp/Grpc.Core/Internal/GrpcThreadPool.cs index 9e69fe2f43090a51c4ef1f1b430f2c56050cd27e..f4224668f1eaa3550b7799a04b1cc47f1f668dc2 100644 --- a/src/csharp/Grpc.Core/Internal/GrpcThreadPool.cs +++ b/src/csharp/Grpc.Core/Internal/GrpcThreadPool.cs @@ -51,12 +51,13 @@ namespace Grpc.Core.Internal CompletionQueueSafeHandle cq; - public GrpcThreadPool(int poolSize) { + public GrpcThreadPool(int poolSize) + { this.poolSize = poolSize; } - public void Start() { - + public void Start() + { lock (myLock) { if (cq != null) @@ -73,8 +74,8 @@ namespace Grpc.Core.Internal } } - public void Stop() { - + public void Stop() + { lock (myLock) { cq.Shutdown(); @@ -86,7 +87,6 @@ namespace Grpc.Core.Internal } cq.Dispose(); - } } @@ -116,10 +116,9 @@ namespace Grpc.Core.Internal do { completionType = cq.NextWithCallback(); - } while(completionType != GRPCCompletionType.GRPC_QUEUE_SHUTDOWN); + } + while (completionType != GRPCCompletionType.GRPC_QUEUE_SHUTDOWN); Console.WriteLine("Completion queue has shutdown successfully, thread " + Thread.CurrentThread.Name + " exiting."); } } - } - diff --git a/src/csharp/Grpc.Core/Internal/SafeHandleZeroIsInvalid.cs b/src/csharp/Grpc.Core/Internal/SafeHandleZeroIsInvalid.cs index aa6fce2e969ec4dc097fc07d0e6dc5c5491a9e4d..702aea2883ad828c6f0b8e6675bb2b0c56522f92 100644 --- a/src/csharp/Grpc.Core/Internal/SafeHandleZeroIsInvalid.cs +++ b/src/csharp/Grpc.Core/Internal/SafeHandleZeroIsInvalid.cs @@ -64,4 +64,3 @@ namespace Grpc.Core.Internal } } } - diff --git a/src/csharp/Grpc.Core/ServerCallHandler.cs b/src/csharp/Grpc.Core/Internal/ServerCallHandler.cs similarity index 98% rename from src/csharp/Grpc.Core/ServerCallHandler.cs rename to src/csharp/Grpc.Core/Internal/ServerCallHandler.cs index 3eb8422f575e3b4f745e03f13856c254d76de10b..25fd4fab8f7f9ec23396bc434b16c4487b0231de 100644 --- a/src/csharp/Grpc.Core/ServerCallHandler.cs +++ b/src/csharp/Grpc.Core/Internal/ServerCallHandler.cs @@ -36,7 +36,7 @@ using System.Linq; using Grpc.Core.Internal; using Grpc.Core.Utils; -namespace Grpc.Core +namespace Grpc.Core.Internal { internal interface IServerCallHandler { @@ -70,7 +70,6 @@ namespace Grpc.Core handler(request, responseObserver); finishedTask.Wait(); - } } @@ -93,7 +92,7 @@ namespace Grpc.Core asyncCall.Initialize(call); - var responseObserver = new ServerStreamingOutputObserver<TRequest,TResponse>(asyncCall); + var responseObserver = new ServerStreamingOutputObserver<TRequest, TResponse>(asyncCall); var requestObserver = handler(responseObserver); var finishedTask = asyncCall.ServerSideCallAsync(requestObserver); finishedTask.Wait(); @@ -113,7 +112,7 @@ namespace Grpc.Core var finishedTask = asyncCall.ServerSideCallAsync(new NullObserver<byte[]>()); // TODO: check result of the completion status. - asyncCall.StartSendStatusFromServer(new Status(StatusCode.Unimplemented, "No such method."), new AsyncCompletionDelegate((error) => {})); + asyncCall.StartSendStatusFromServer(new Status(StatusCode.Unimplemented, "No such method."), new AsyncCompletionDelegate((error) => { })); finishedTask.Wait(); } @@ -132,7 +131,5 @@ namespace Grpc.Core public void OnNext(T value) { } - } } - diff --git a/src/csharp/Grpc.Core/Internal/ServerSafeHandle.cs b/src/csharp/Grpc.Core/Internal/ServerSafeHandle.cs index b5a5ae4976275f427599b64af39a5229deae381a..dc4781e7966b86ecf6e1d7fa29dc72c7b156a27b 100644 --- a/src/csharp/Grpc.Core/Internal/ServerSafeHandle.cs +++ b/src/csharp/Grpc.Core/Internal/ServerSafeHandle.cs @@ -53,10 +53,10 @@ namespace Grpc.Core.Internal static extern ServerSafeHandle grpcsharp_server_create(CompletionQueueSafeHandle cq, IntPtr args); [DllImport("grpc_csharp_ext.dll")] - static extern Int32 grpcsharp_server_add_http2_port(ServerSafeHandle server, string addr); + static extern int grpcsharp_server_add_http2_port(ServerSafeHandle server, string addr); [DllImport("grpc_csharp_ext.dll")] - static extern Int32 grpcsharp_server_add_secure_http2_port(ServerSafeHandle server, string addr, ServerCredentialsSafeHandle creds); + static extern int grpcsharp_server_add_secure_http2_port(ServerSafeHandle server, string addr, ServerCredentialsSafeHandle creds); [DllImport("grpc_csharp_ext.dll")] static extern void grpcsharp_server_start(ServerSafeHandle server); diff --git a/src/csharp/Grpc.Core/Internal/ServerStreamingOutputObserver.cs b/src/csharp/Grpc.Core/Internal/ServerStreamingOutputObserver.cs index 9873dc9c71077b0d8650199e288e743f8f348896..97b62d05692046bc826cfbda7a21a8c9bb436e52 100644 --- a/src/csharp/Grpc.Core/Internal/ServerStreamingOutputObserver.cs +++ b/src/csharp/Grpc.Core/Internal/ServerStreamingOutputObserver.cs @@ -69,4 +69,3 @@ namespace Grpc.Core.Internal } } } - diff --git a/src/csharp/Grpc.Core/Internal/Timespec.cs b/src/csharp/Grpc.Core/Internal/Timespec.cs index e6efd66f13b9eb717d573f4469927d56c749d9f7..94d48c2c49ca6d55186fd7a405c8ca65fc95718f 100644 --- a/src/csharp/Grpc.Core/Internal/Timespec.cs +++ b/src/csharp/Grpc.Core/Internal/Timespec.cs @@ -40,8 +40,8 @@ namespace Grpc.Core.Internal [StructLayout(LayoutKind.Sequential)] internal struct Timespec { - const int nanosPerSecond = 1000 * 1000 * 1000; - const int nanosPerTick = 100; + const int NanosPerSecond = 1000 * 1000 * 1000; + const int NanosPerTick = 100; [DllImport("grpc_csharp_ext.dll")] static extern Timespec gprsharp_now(); @@ -99,14 +99,13 @@ namespace Grpc.Core.Internal public Timespec Add(TimeSpan timeSpan) { - long nanos = tv_nsec.ToInt64() + (timeSpan.Ticks % TimeSpan.TicksPerSecond) * nanosPerTick; - long overflow_sec = (nanos > nanosPerSecond) ? 1 : 0; + long nanos = tv_nsec.ToInt64() + (timeSpan.Ticks % TimeSpan.TicksPerSecond) * NanosPerTick; + long overflow_sec = (nanos > NanosPerSecond) ? 1 : 0; Timespec result; - result.tv_nsec = new IntPtr(nanos % nanosPerSecond); + result.tv_nsec = new IntPtr(nanos % NanosPerSecond); result.tv_sec = new IntPtr(tv_sec.ToInt64() + (timeSpan.Ticks / TimeSpan.TicksPerSecond) + overflow_sec); return result; } } } - diff --git a/src/csharp/Grpc.Core/Marshaller.cs b/src/csharp/Grpc.Core/Marshaller.cs index 602e0eb8240f4e3e7b258d3f1e370fe35ee437bc..e73e7b762ef27a1798d2f0446d7ce886627783ce 100644 --- a/src/csharp/Grpc.Core/Marshaller.cs +++ b/src/csharp/Grpc.Core/Marshaller.cs @@ -40,8 +40,8 @@ namespace Grpc.Core /// </summary> public struct Marshaller<T> { - readonly Func<T,byte[]> serializer; - readonly Func<byte[],T> deserializer; + readonly Func<T, byte[]> serializer; + readonly Func<byte[], T> deserializer; public Marshaller(Func<T, byte[]> serializer, Func<byte[], T> deserializer) { @@ -66,9 +66,12 @@ namespace Grpc.Core } } - public static class Marshallers { - - public static Marshaller<T> Create<T>(Func<T,byte[]> serializer, Func<byte[],T> deserializer) + /// <summary> + /// Utilities for creating marshallers. + /// </summary> + public static class Marshallers + { + public static Marshaller<T> Create<T>(Func<T, byte[]> serializer, Func<byte[], T> deserializer) { return new Marshaller<T>(serializer, deserializer); } @@ -81,7 +84,5 @@ namespace Grpc.Core System.Text.Encoding.UTF8.GetString); } } - } } - diff --git a/src/csharp/Grpc.Core/Method.cs b/src/csharp/Grpc.Core/Method.cs index c94aa8161fe7fb7aa2deb488ce003c88ce937d1c..4f97eeef37f1fb77b7fcb5bff71bebdce779faf0 100644 --- a/src/csharp/Grpc.Core/Method.cs +++ b/src/csharp/Grpc.Core/Method.cs @@ -94,4 +94,3 @@ namespace Grpc.Core } } } - diff --git a/src/csharp/Grpc.Core/OperationFailedException.cs b/src/csharp/Grpc.Core/OperationFailedException.cs index 34a8c95a85c3790f49582bdcd0e1d627e837a4c7..9b1c24d0c1646caa9e8a01b83d10daadeff5813b 100644 --- a/src/csharp/Grpc.Core/OperationFailedException.cs +++ b/src/csharp/Grpc.Core/OperationFailedException.cs @@ -45,4 +45,3 @@ namespace Grpc.Core } } } - diff --git a/src/csharp/Grpc.Core/Properties/AssemblyInfo.cs b/src/csharp/Grpc.Core/Properties/AssemblyInfo.cs index 37ba1e2263c3f09c378262ab4b6a45c3f36baad3..168939cf8c5c54ea07e6a7e702ed8ac9684210d1 100644 --- a/src/csharp/Grpc.Core/Properties/AssemblyInfo.cs +++ b/src/csharp/Grpc.Core/Properties/AssemblyInfo.cs @@ -1,24 +1,14 @@ using System.Reflection; using System.Runtime.CompilerServices; -// Information about this assembly is defined by the following attributes. -// Change them to the values specific to your project. -[assembly: AssemblyTitle ("Grpc.Core")] -[assembly: AssemblyDescription ("")] -[assembly: AssemblyConfiguration ("")] -[assembly: AssemblyCompany ("")] -[assembly: AssemblyProduct ("")] -[assembly: AssemblyCopyright ("Google Inc. All rights reserved.")] -[assembly: AssemblyTrademark ("")] -[assembly: AssemblyCulture ("")] -// The assembly version has the format "{Major}.{Minor}.{Build}.{Revision}". -// The form "{Major}.{Minor}.*" will automatically update the build and revision, -// and "{Major}.{Minor}.{Build}.*" will update just the revision. -[assembly: AssemblyVersion ("0.1.*")] -// The following attributes are used to specify the signing key for the assembly, -// if desired. See the Mono documentation for more information about signing. -//[assembly: AssemblyDelaySign(false)] -//[assembly: AssemblyKeyFile("")] +[assembly: AssemblyTitle("Grpc.Core")] +[assembly: AssemblyDescription("")] +[assembly: AssemblyConfiguration("")] +[assembly: AssemblyCompany("")] +[assembly: AssemblyProduct("")] +[assembly: AssemblyCopyright("Google Inc. All rights reserved.")] +[assembly: AssemblyTrademark("")] +[assembly: AssemblyCulture("")] +[assembly: AssemblyVersion("0.1.*")] [assembly: InternalsVisibleTo("Grpc.Core.Tests")] - diff --git a/src/csharp/Grpc.Core/RpcException.cs b/src/csharp/Grpc.Core/RpcException.cs index e1cf64ca56af8a50a2bf6fbe0d2825bc654f9a4e..433d87215ee3f4b6151ce020ff8c7f4ed5840508 100644 --- a/src/csharp/Grpc.Core/RpcException.cs +++ b/src/csharp/Grpc.Core/RpcException.cs @@ -35,6 +35,9 @@ using System; namespace Grpc.Core { + /// <summary> + /// Thrown when remote procedure call fails. + /// </summary> public class RpcException : Exception { private readonly Status status; @@ -58,4 +61,3 @@ namespace Grpc.Core } } } - diff --git a/src/csharp/Grpc.Core/Server.cs b/src/csharp/Grpc.Core/Server.cs index cafdb3b6637bb2614c5a401ad8731e6bd1d830fa..2439cdb6dc3c9d4752530fbfa66dda779ad6a080 100644 --- a/src/csharp/Grpc.Core/Server.cs +++ b/src/csharp/Grpc.Core/Server.cs @@ -67,8 +67,9 @@ namespace Grpc.Core } // only call this before Start() - public void AddServiceDefinition(ServerServiceDefinition serviceDefinition) { - foreach(var entry in serviceDefinition.CallHandlers) + public void AddServiceDefinition(ServerServiceDefinition serviceDefinition) + { + foreach (var entry in serviceDefinition.CallHandlers) { callHandlers.Add(entry.Key, entry.Value); } @@ -108,7 +109,7 @@ namespace Grpc.Core { var rpcInfo = newRpcQueue.Take(); - //Console.WriteLine("Server received RPC " + rpcInfo.Method); + // Console.WriteLine("Server received RPC " + rpcInfo.Method); IServerCallHandler callHandler; if (!callHandlers.TryGetValue(rpcInfo.Method, out callHandler)) @@ -117,7 +118,7 @@ namespace Grpc.Core } callHandler.StartCall(rpcInfo.Method, rpcInfo.Call, GetCompletionQueue()); } - catch(Exception e) + catch (Exception e) { Console.WriteLine("Exception while handling RPC: " + e); } @@ -128,7 +129,8 @@ namespace Grpc.Core /// cleans up used resources. /// </summary> /// <returns>The async.</returns> - public async Task ShutdownAsync() { + public async Task ShutdownAsync() + { handle.ShutdownAndNotify(serverShutdownHandler); await shutdownTcs.Task; handle.Dispose(); @@ -145,11 +147,13 @@ namespace Grpc.Core } } - public void Kill() { + public void Kill() + { handle.Dispose(); } - private async Task StartHandlingRpcs() { + private async Task StartHandlingRpcs() + { while (true) { await Task.Factory.StartNew(RunRpc); @@ -161,22 +165,27 @@ namespace Grpc.Core AssertCallOk(handle.RequestCall(GetCompletionQueue(), newServerRpcHandler)); } - private void HandleNewServerRpc(GRPCOpError error, IntPtr batchContextPtr) { - try { + private void HandleNewServerRpc(GRPCOpError error, IntPtr batchContextPtr) + { + try + { var ctx = new BatchContextSafeHandleNotOwned(batchContextPtr); - if (error != GRPCOpError.GRPC_OP_OK) { + if (error != GRPCOpError.GRPC_OP_OK) + { // TODO: handle error } var rpcInfo = new NewRpcInfo(ctx.GetServerRpcNewCall(), ctx.GetServerRpcNewMethod()); // after server shutdown, the callback returns with null call - if (!rpcInfo.Call.IsInvalid) { + if (!rpcInfo.Call.IsInvalid) + { newRpcQueue.Add(rpcInfo); } - - } catch(Exception e) { + } + catch (Exception e) + { Console.WriteLine("Caught exception in a native handler: " + e); } } diff --git a/src/csharp/Grpc.Core/ServerCalls.cs b/src/csharp/Grpc.Core/ServerCalls.cs index bed77796de10e7bedc3962326660d0eabd45afcf..dcae99446fe3e1474843f56a40119110bf18b151 100644 --- a/src/csharp/Grpc.Core/ServerCalls.cs +++ b/src/csharp/Grpc.Core/ServerCalls.cs @@ -32,17 +32,18 @@ #endregion using System; +using Grpc.Core.Internal; namespace Grpc.Core { // TODO: perhaps add also serverSideStreaming and clientSideStreaming - public delegate void UnaryRequestServerMethod<TRequest, TResponse> (TRequest request, IObserver<TResponse> responseObserver); + public delegate void UnaryRequestServerMethod<TRequest, TResponse>(TRequest request, IObserver<TResponse> responseObserver); - public delegate IObserver<TRequest> StreamingRequestServerMethod<TRequest, TResponse> (IObserver<TResponse> responseObserver); - - internal static class ServerCalls { + public delegate IObserver<TRequest> StreamingRequestServerMethod<TRequest, TResponse>(IObserver<TResponse> responseObserver); + internal static class ServerCalls + { public static IServerCallHandler UnaryRequestCall<TRequest, TResponse>(Method<TRequest, TResponse> method, UnaryRequestServerMethod<TRequest, TResponse> handler) { return new UnaryRequestServerCallHandler<TRequest, TResponse>(method, handler); @@ -52,7 +53,5 @@ namespace Grpc.Core { return new StreamingRequestServerCallHandler<TRequest, TResponse>(method, handler); } - } } - diff --git a/src/csharp/Grpc.Core/ServerCredentials.cs b/src/csharp/Grpc.Core/ServerCredentials.cs index 1372e61fa71990bb7f1160831877001ec621743c..ab7d0b49143ed74b72ca021239171ea1aa05ba24 100644 --- a/src/csharp/Grpc.Core/ServerCredentials.cs +++ b/src/csharp/Grpc.Core/ServerCredentials.cs @@ -33,10 +33,14 @@ using System; using System.Collections.Generic; +using System.Collections.Immutable; using Grpc.Core.Internal; namespace Grpc.Core { + /// <summary> + /// Server side credentials. + /// </summary> public abstract class ServerCredentials { /// <summary> @@ -51,8 +55,8 @@ namespace Grpc.Core /// </summary> public class KeyCertificatePair { - string certChain; - string privateKey; + readonly string certChain; + readonly string privateKey; public KeyCertificatePair(string certChain, string privateKey) { @@ -82,10 +86,9 @@ namespace Grpc.Core /// </summary> public class SslServerCredentials : ServerCredentials { - // TODO: immutable list... - List<KeyCertificatePair> keyCertPairs; + ImmutableList<KeyCertificatePair> keyCertPairs; - public SslServerCredentials(List<KeyCertificatePair> keyCertPairs) + public SslServerCredentials(ImmutableList<KeyCertificatePair> keyCertPairs) { this.keyCertPairs = keyCertPairs; } @@ -104,4 +107,3 @@ namespace Grpc.Core } } } - diff --git a/src/csharp/Grpc.Core/ServerServiceDefinition.cs b/src/csharp/Grpc.Core/ServerServiceDefinition.cs index 231c37606205fca9aa2fa700c40422bb90bd0dc4..004415477ca6c79606f1e31d78b006b47d028aea 100644 --- a/src/csharp/Grpc.Core/ServerServiceDefinition.cs +++ b/src/csharp/Grpc.Core/ServerServiceDefinition.cs @@ -33,22 +33,26 @@ using System; using System.Collections.Generic; +using System.Collections.Immutable; +using Grpc.Core.Internal; namespace Grpc.Core { + /// <summary> + /// Mapping of method names to server call handlers. + /// </summary> public class ServerServiceDefinition { readonly string serviceName; - // TODO: we would need an immutable dictionary here... - readonly Dictionary<string, IServerCallHandler> callHandlers; + readonly ImmutableDictionary<string, IServerCallHandler> callHandlers; - private ServerServiceDefinition(string serviceName, Dictionary<string, IServerCallHandler> callHandlers) + private ServerServiceDefinition(string serviceName, ImmutableDictionary<string, IServerCallHandler> callHandlers) { this.serviceName = serviceName; - this.callHandlers = new Dictionary<string, IServerCallHandler>(callHandlers); + this.callHandlers = callHandlers; } - internal Dictionary<string, IServerCallHandler> CallHandlers + internal ImmutableDictionary<string, IServerCallHandler> CallHandlers { get { @@ -56,8 +60,7 @@ namespace Grpc.Core } } - - public static Builder CreateBuilder(String serviceName) + public static Builder CreateBuilder(string serviceName) { return new Builder(serviceName); } @@ -65,7 +68,7 @@ namespace Grpc.Core public class Builder { readonly string serviceName; - readonly Dictionary<string, IServerCallHandler> callHandlers = new Dictionary<String, IServerCallHandler>(); + readonly Dictionary<string, IServerCallHandler> callHandlers = new Dictionary<string, IServerCallHandler>(); public Builder(string serviceName) { @@ -90,9 +93,8 @@ namespace Grpc.Core public ServerServiceDefinition Build() { - return new ServerServiceDefinition(serviceName, callHandlers); + return new ServerServiceDefinition(serviceName, callHandlers.ToImmutableDictionary()); } } } } - diff --git a/src/csharp/Grpc.Core/StatusCode.cs b/src/csharp/Grpc.Core/StatusCode.cs index 1987e52789a01e181bcb434c9373ba9b5c98ec11..a9696fa46904174f8d590e524776d9c6ec48ee15 100644 --- a/src/csharp/Grpc.Core/StatusCode.cs +++ b/src/csharp/Grpc.Core/StatusCode.cs @@ -35,9 +35,9 @@ using System; namespace Grpc.Core { - // TODO: element names should changed to comply with C# naming conventions. /// <summary> - /// based on grpc_status_code from grpc/status.h + /// Result of a remote procedure call. + /// Based on grpc_status_code from grpc/status.h /// </summary> public enum StatusCode { @@ -139,4 +139,3 @@ namespace Grpc.Core DataLoss = 15 } } - diff --git a/src/csharp/Grpc.Core/Utils/BenchmarkUtil.cs b/src/csharp/Grpc.Core/Utils/BenchmarkUtil.cs index 3f0dae84cf87eb26b6608b558c5c3b3d3af589e1..4180d989385ca2069d4cb72ed0d7acadcb54de01 100644 --- a/src/csharp/Grpc.Core/Utils/BenchmarkUtil.cs +++ b/src/csharp/Grpc.Core/Utils/BenchmarkUtil.cs @@ -32,10 +32,10 @@ #endregion using System; -using System.Threading.Tasks; -using System.Collections.Generic; using System.Collections.Concurrent; +using System.Collections.Generic; using System.Diagnostics; +using System.Threading.Tasks; namespace Grpc.Core.Utils { @@ -61,8 +61,7 @@ namespace Grpc.Core.Utils } stopwatch.Stop(); Console.WriteLine("Elapsed time: " + stopwatch.ElapsedMilliseconds + "ms"); - Console.WriteLine("Ops per second: " + (int) ((double) benchmarkIterations * 1000 / stopwatch.ElapsedMilliseconds)); + Console.WriteLine("Ops per second: " + (int)((double)benchmarkIterations * 1000 / stopwatch.ElapsedMilliseconds)); } } } - diff --git a/src/csharp/Grpc.Core/Utils/ExceptionHelper.cs b/src/csharp/Grpc.Core/Utils/ExceptionHelper.cs index 18702e1cc4257c75703de7b85b9cd3aa8b5f6025..c4d6bee05807437d2905804fbc793121119028c4 100644 --- a/src/csharp/Grpc.Core/Utils/ExceptionHelper.cs +++ b/src/csharp/Grpc.Core/Utils/ExceptionHelper.cs @@ -42,7 +42,8 @@ namespace Grpc.Core.Utils /// Otherwise, rethrows the original aggregate exception. /// Always throws, the exception return type is here only to make the. /// </summary> - public static Exception UnwrapRpcException(AggregateException ae) { + public static Exception UnwrapRpcException(AggregateException ae) + { foreach (var e in ae.InnerExceptions) { if (e is RpcException) @@ -54,4 +55,3 @@ namespace Grpc.Core.Utils } } } - diff --git a/src/csharp/Grpc.Core/Utils/Preconditions.cs b/src/csharp/Grpc.Core/Utils/Preconditions.cs index b17ce4211783701b6b4ab8d6e9fb84057fe0fc75..aeb5d210a79f286fa754b4e898df4e9a96cc62bf 100644 --- a/src/csharp/Grpc.Core/Utils/Preconditions.cs +++ b/src/csharp/Grpc.Core/Utils/Preconditions.cs @@ -32,10 +32,10 @@ #endregion using System; -using System.Threading.Tasks; -using System.Collections.Generic; using System.Collections.Concurrent; +using System.Collections.Generic; using System.Diagnostics; +using System.Threading.Tasks; namespace Grpc.Core.Utils { @@ -66,7 +66,7 @@ namespace Grpc.Core.Utils /// <summary> /// Throws NullReferenceException if reference is null. /// </summary> - public static T CheckNotNull<T> (T reference) + public static T CheckNotNull<T>(T reference) { if (reference == null) { @@ -78,7 +78,7 @@ namespace Grpc.Core.Utils /// <summary> /// Throws NullReferenceException with given message if reference is null. /// </summary> - public static T CheckNotNull<T> (T reference, string errorMessage) + public static T CheckNotNull<T>(T reference, string errorMessage) { if (reference == null) { @@ -110,4 +110,3 @@ namespace Grpc.Core.Utils } } } - diff --git a/src/csharp/Grpc.Core/Utils/RecordingObserver.cs b/src/csharp/Grpc.Core/Utils/RecordingObserver.cs index 99d2725b70eda679b4c0679eb5d40365c67279a2..7b43ab8ad5f20b9fedbd926187e49bfc9ecc1f52 100644 --- a/src/csharp/Grpc.Core/Utils/RecordingObserver.cs +++ b/src/csharp/Grpc.Core/Utils/RecordingObserver.cs @@ -57,9 +57,9 @@ namespace Grpc.Core.Utils data.Add(value); } - public Task<List<T>> ToList() { + public Task<List<T>> ToList() + { return tcs.Task; } } } - diff --git a/src/csharp/Grpc.Core/Utils/RecordingQueue.cs b/src/csharp/Grpc.Core/Utils/RecordingQueue.cs index 63992da6a95d8aa24ca72f5cf951ef7a87fe90ee..9749168af02731f0e02f1a497ece3371080eb4a6 100644 --- a/src/csharp/Grpc.Core/Utils/RecordingQueue.cs +++ b/src/csharp/Grpc.Core/Utils/RecordingQueue.cs @@ -32,9 +32,9 @@ #endregion using System; -using System.Threading.Tasks; -using System.Collections.Generic; using System.Collections.Concurrent; +using System.Collections.Generic; +using System.Threading.Tasks; namespace Grpc.Core.Utils { @@ -81,4 +81,3 @@ namespace Grpc.Core.Utils } } } - diff --git a/src/csharp/Grpc.Core/packages.config b/src/csharp/Grpc.Core/packages.config new file mode 100644 index 0000000000000000000000000000000000000000..cf711ac3622cb22cdce4ef12b733f14abaf635f3 --- /dev/null +++ b/src/csharp/Grpc.Core/packages.config @@ -0,0 +1,4 @@ +<?xml version="1.0" encoding="utf-8"?> +<packages> + <package id="System.Collections.Immutable" version="1.1.34-rc" targetFramework="net45" /> +</packages> \ No newline at end of file diff --git a/src/csharp/Grpc.Examples.MathClient/Properties/AssemblyInfo.cs b/src/csharp/Grpc.Examples.MathClient/Properties/AssemblyInfo.cs index bdd7189db2f43ee1d04fbf153460ecc31b9d568f..11fc099a954c4b3054a327a9f2d78d85de381340 100644 --- a/src/csharp/Grpc.Examples.MathClient/Properties/AssemblyInfo.cs +++ b/src/csharp/Grpc.Examples.MathClient/Properties/AssemblyInfo.cs @@ -1,22 +1,12 @@ using System.Reflection; using System.Runtime.CompilerServices; -// Information about this assembly is defined by the following attributes. -// Change them to the values specific to your project. -[assembly: AssemblyTitle ("Grpc.Examples.MathClient")] -[assembly: AssemblyDescription ("")] -[assembly: AssemblyConfiguration ("")] -[assembly: AssemblyCompany ("")] -[assembly: AssemblyProduct ("")] -[assembly: AssemblyCopyright ("Google Inc. All rights reserved.")] -[assembly: AssemblyTrademark ("")] -[assembly: AssemblyCulture ("")] -// The assembly version has the format "{Major}.{Minor}.{Build}.{Revision}". -// The form "{Major}.{Minor}.*" will automatically update the build and revision, -// and "{Major}.{Minor}.{Build}.*" will update just the revision. -[assembly: AssemblyVersion ("0.1.*")] -// The following attributes are used to specify the signing key for the assembly, -// if desired. See the Mono documentation for more information about signing. -//[assembly: AssemblyDelaySign(false)] -//[assembly: AssemblyKeyFile("")] - +[assembly: AssemblyTitle("Grpc.Examples.MathClient")] +[assembly: AssemblyDescription("")] +[assembly: AssemblyConfiguration("")] +[assembly: AssemblyCompany("")] +[assembly: AssemblyProduct("")] +[assembly: AssemblyCopyright("Google Inc. All rights reserved.")] +[assembly: AssemblyTrademark("")] +[assembly: AssemblyCulture("")] +[assembly: AssemblyVersion("0.1.*")] diff --git a/src/csharp/Grpc.Examples.Tests/MathClientServerTests.cs b/src/csharp/Grpc.Examples.Tests/MathClientServerTests.cs index 767340d6f2b287a8af169eb07e6c7ce0c7c0aa50..c86da65af47bd23d2048d9e2ad82d32b63d90465 100644 --- a/src/csharp/Grpc.Examples.Tests/MathClientServerTests.cs +++ b/src/csharp/Grpc.Examples.Tests/MathClientServerTests.cs @@ -105,7 +105,7 @@ namespace math.Tests var recorder = new RecordingObserver<Num>(); client.Fib(new FibArgs.Builder { Limit = 6 }.Build(), recorder); - CollectionAssert.AreEqual(new List<long>{1, 1, 2, 3, 5, 8}, + CollectionAssert.AreEqual(new List<long> { 1, 1, 2, 3, 5, 8 }, recorder.ToList().Result.ConvertAll((n) => n.Num_)); } @@ -114,7 +114,8 @@ namespace math.Tests public void Sum() { var res = client.Sum(); - foreach (var num in new long[] { 10, 20, 30 }) { + foreach (var num in new long[] { 10, 20, 30 }) + { res.Inputs.OnNext(Num.CreateBuilder().SetNum_(num).Build()); } res.Inputs.OnCompleted(); @@ -125,7 +126,8 @@ namespace math.Tests [Test] public void DivMany() { - List<DivArgs> divArgsList = new List<DivArgs>{ + List<DivArgs> divArgsList = new List<DivArgs> + { new DivArgs.Builder { Dividend = 10, Divisor = 3 }.Build(), new DivArgs.Builder { Dividend = 100, Divisor = 21 }.Build(), new DivArgs.Builder { Dividend = 7, Divisor = 2 }.Build() @@ -142,9 +144,8 @@ namespace math.Tests var result = recorder.ToList().Result; - CollectionAssert.AreEqual(new long[] {3, 4, 3}, result.ConvertAll((divReply) => divReply.Quotient)); - CollectionAssert.AreEqual(new long[] {1, 16, 1}, result.ConvertAll((divReply) => divReply.Remainder)); + CollectionAssert.AreEqual(new long[] { 3, 4, 3 }, result.ConvertAll((divReply) => divReply.Quotient)); + CollectionAssert.AreEqual(new long[] { 1, 16, 1 }, result.ConvertAll((divReply) => divReply.Remainder)); } } } - diff --git a/src/csharp/Grpc.Examples.Tests/Properties/AssemblyInfo.cs b/src/csharp/Grpc.Examples.Tests/Properties/AssemblyInfo.cs index 44b075ac0a805161e1bd7c8138a7ae218dcfbbc7..43c7616ac3afc047aa92279b228e64487254cca9 100644 --- a/src/csharp/Grpc.Examples.Tests/Properties/AssemblyInfo.cs +++ b/src/csharp/Grpc.Examples.Tests/Properties/AssemblyInfo.cs @@ -1,8 +1,6 @@ using System.Reflection; using System.Runtime.CompilerServices; -// Information about this assembly is defined by the following attributes. -// Change them to the values specific to your project. [assembly: AssemblyTitle("Grpc.Examples.Tests")] [assembly: AssemblyDescription("")] [assembly: AssemblyConfiguration("")] @@ -11,12 +9,4 @@ using System.Runtime.CompilerServices; [assembly: AssemblyCopyright("Google Inc. All rights reserved.")] [assembly: AssemblyTrademark("")] [assembly: AssemblyCulture("")] -// The assembly version has the format "{Major}.{Minor}.{Build}.{Revision}". -// The form "{Major}.{Minor}.*" will automatically update the build and revision, -// and "{Major}.{Minor}.{Build}.*" will update just the revision. [assembly: AssemblyVersion("0.1.*")] -// The following attributes are used to specify the signing key for the assembly, -// if desired. See the Mono documentation for more information about signing. -//[assembly: AssemblyDelaySign(false)] -//[assembly: AssemblyKeyFile("")] - diff --git a/src/csharp/Grpc.Examples/MathExamples.cs b/src/csharp/Grpc.Examples/MathExamples.cs index 134270f6f76c8e20c367d132c9e5bffe009df3db..b8bb7eacbd0f3572ab9ec3aa5660dd0af6e9a613 100644 --- a/src/csharp/Grpc.Examples/MathExamples.cs +++ b/src/csharp/Grpc.Examples/MathExamples.cs @@ -71,7 +71,8 @@ namespace math public static void SumExample(MathGrpc.IMathServiceClient stub) { List<Num> numbers = new List<Num> - {new Num.Builder { Num_ = 1 }.Build(), + { + new Num.Builder { Num_ = 1 }.Build(), new Num.Builder { Num_ = 2 }.Build(), new Num.Builder { Num_ = 3 }.Build() }; @@ -110,24 +111,12 @@ namespace math public static void DependendRequestsExample(MathGrpc.IMathServiceClient stub) { var numberList = new List<Num> - { new Num.Builder{ Num_ = 1 }.Build(), - new Num.Builder{ Num_ = 2 }.Build(), new Num.Builder{ Num_ = 3 }.Build() + { + new Num.Builder { Num_ = 1 }.Build(), + new Num.Builder { Num_ = 2 }.Build(), new Num.Builder { Num_ = 3 }.Build() }; numberList.ToObservable(); - - //IObserver<Num> numbers; - //Task<Num> call = stub.Sum(out numbers); - //foreach (var num in numberList) - //{ - // numbers.OnNext(num); - //} - //numbers.OnCompleted(); - - //Num sum = call.Result; - - //DivReply result = stub.Div(new DivArgs.Builder { Dividend = sum.Num_, Divisor = numberList.Count }.Build()); } } } - diff --git a/src/csharp/Grpc.Examples/MathGrpc.cs b/src/csharp/Grpc.Examples/MathGrpc.cs index f938a245439b9bb04222c1c86ded99ab0b820d11..33a9ca928764938f1c70d99298f8d93c87717f83 100644 --- a/src/csharp/Grpc.Examples/MathGrpc.cs +++ b/src/csharp/Grpc.Examples/MathGrpc.cs @@ -45,35 +45,34 @@ namespace math /// </summary> public class MathGrpc { - readonly static Marshaller<DivArgs> divArgsMarshaller = Marshallers.Create((arg) => arg.ToByteArray(), DivArgs.ParseFrom); - readonly static Marshaller<DivReply> divReplyMarshaller = Marshallers.Create((arg) => arg.ToByteArray(), DivReply.ParseFrom); - readonly static Marshaller<Num> numMarshaller = Marshallers.Create((arg) => arg.ToByteArray(), Num.ParseFrom); - readonly static Marshaller<FibArgs> fibArgsMarshaller = Marshallers.Create((arg) => arg.ToByteArray(), FibArgs.ParseFrom); + static readonly Marshaller<DivArgs> DivArgsMarshaller = Marshallers.Create((arg) => arg.ToByteArray(), DivArgs.ParseFrom); + static readonly Marshaller<DivReply> DivReplyMarshaller = Marshallers.Create((arg) => arg.ToByteArray(), DivReply.ParseFrom); + static readonly Marshaller<Num> NumMarshaller = Marshallers.Create((arg) => arg.ToByteArray(), Num.ParseFrom); + static readonly Marshaller<FibArgs> FibArgsMarshaller = Marshallers.Create((arg) => arg.ToByteArray(), FibArgs.ParseFrom); - readonly static Method<DivArgs, DivReply> divMethod = new Method<DivArgs, DivReply>( + static readonly Method<DivArgs, DivReply> DivMethod = new Method<DivArgs, DivReply>( MethodType.Unary, "/math.Math/Div", - divArgsMarshaller, - divReplyMarshaller - ); - readonly static Method<FibArgs, Num> fibMethod = new Method<FibArgs, Num>( + DivArgsMarshaller, + DivReplyMarshaller); + + static readonly Method<FibArgs, Num> FibMethod = new Method<FibArgs, Num>( MethodType.ServerStreaming, "/math.Math/Fib", - fibArgsMarshaller, - numMarshaller - ); - readonly static Method<Num, Num> sumMethod = new Method<Num, Num>( + FibArgsMarshaller, + NumMarshaller); + + static readonly Method<Num, Num> SumMethod = new Method<Num, Num>( MethodType.ClientStreaming, "/math.Math/Sum", - numMarshaller, - numMarshaller - ); - readonly static Method<DivArgs, DivReply> divManyMethod = new Method<DivArgs, DivReply>( + NumMarshaller, + NumMarshaller); + + static readonly Method<DivArgs, DivReply> DivManyMethod = new Method<DivArgs, DivReply>( MethodType.DuplexStreaming, "/math.Math/DivMany", - divArgsMarshaller, - divReplyMarshaller - ); + DivArgsMarshaller, + DivReplyMarshaller); public interface IMathServiceClient { @@ -99,31 +98,31 @@ namespace math public DivReply Div(DivArgs request, CancellationToken token = default(CancellationToken)) { - var call = new Grpc.Core.Call<DivArgs, DivReply>(divMethod, channel); + var call = new Grpc.Core.Call<DivArgs, DivReply>(DivMethod, channel); return Calls.BlockingUnaryCall(call, request, token); } public Task<DivReply> DivAsync(DivArgs request, CancellationToken token = default(CancellationToken)) { - var call = new Grpc.Core.Call<DivArgs, DivReply>(divMethod, channel); + var call = new Grpc.Core.Call<DivArgs, DivReply>(DivMethod, channel); return Calls.AsyncUnaryCall(call, request, token); } public void Fib(FibArgs request, IObserver<Num> responseObserver, CancellationToken token = default(CancellationToken)) { - var call = new Grpc.Core.Call<FibArgs, Num>(fibMethod, channel); + var call = new Grpc.Core.Call<FibArgs, Num>(FibMethod, channel); Calls.AsyncServerStreamingCall(call, request, responseObserver, token); } public ClientStreamingAsyncResult<Num, Num> Sum(CancellationToken token = default(CancellationToken)) { - var call = new Grpc.Core.Call<Num, Num>(sumMethod, channel); + var call = new Grpc.Core.Call<Num, Num>(SumMethod, channel); return Calls.AsyncClientStreamingCall(call, token); } public IObserver<DivArgs> DivMany(IObserver<DivReply> responseObserver, CancellationToken token = default(CancellationToken)) { - var call = new Grpc.Core.Call<DivArgs, DivReply>(divManyMethod, channel); + var call = new Grpc.Core.Call<DivArgs, DivReply>(DivManyMethod, channel); return Calls.DuplexStreamingCall(call, responseObserver, token); } } @@ -143,10 +142,10 @@ namespace math public static ServerServiceDefinition BindService(IMathService serviceImpl) { return ServerServiceDefinition.CreateBuilder("/math.Math/") - .AddMethod(divMethod, serviceImpl.Div) - .AddMethod(fibMethod, serviceImpl.Fib) - .AddMethod(sumMethod, serviceImpl.Sum) - .AddMethod(divManyMethod, serviceImpl.DivMany).Build(); + .AddMethod(DivMethod, serviceImpl.Div) + .AddMethod(FibMethod, serviceImpl.Fib) + .AddMethod(SumMethod, serviceImpl.Sum) + .AddMethod(DivManyMethod, serviceImpl.DivMany).Build(); } public static IMathServiceClient NewStub(Channel channel) diff --git a/src/csharp/Grpc.Examples/MathServiceImpl.cs b/src/csharp/Grpc.Examples/MathServiceImpl.cs index 76a08ce51865aba626f85f66a6f91dfc70afdb66..0b2357e0fade71eab84e6e23dede9b24b6e73ef7 100644 --- a/src/csharp/Grpc.Examples/MathServiceImpl.cs +++ b/src/csharp/Grpc.Examples/MathServiceImpl.cs @@ -73,8 +73,8 @@ namespace math public IObserver<Num> Sum(IObserver<Num> responseObserver) { var recorder = new RecordingObserver<Num>(); - Task.Factory.StartNew(() => { - + Task.Factory.StartNew(() => + { List<Num> inputs = recorder.ToList().Result; long sum = 0; @@ -104,7 +104,7 @@ namespace math static IEnumerable<Num> FibInternal(long n) { long a = 1; - yield return new Num.Builder { Num_=a }.Build(); + yield return new Num.Builder { Num_ = a }.Build(); long b = 1; for (long i = 0; i < n - 1; i++) @@ -112,12 +112,12 @@ namespace math long temp = a; a = b; b = temp + b; - yield return new Num.Builder { Num_=a }.Build(); + yield return new Num.Builder { Num_ = a }.Build(); } } - private class DivObserver : IObserver<DivArgs> { - + private class DivObserver : IObserver<DivArgs> + { readonly IObserver<DivReply> responseObserver; public DivObserver(IObserver<DivReply> responseObserver) @@ -142,4 +142,3 @@ namespace math } } } - diff --git a/src/csharp/Grpc.Examples/Properties/AssemblyInfo.cs b/src/csharp/Grpc.Examples/Properties/AssemblyInfo.cs index 7603db7ffd135be4ee2b10adcbf928bc30b8e3b3..b55d24166cc586b02d302e659044f9ef4ee0a2f1 100644 --- a/src/csharp/Grpc.Examples/Properties/AssemblyInfo.cs +++ b/src/csharp/Grpc.Examples/Properties/AssemblyInfo.cs @@ -1,22 +1,12 @@ using System.Reflection; using System.Runtime.CompilerServices; -// Information about this assembly is defined by the following attributes. -// Change them to the values specific to your project. -[assembly: AssemblyTitle ("Grpc.Examples")] -[assembly: AssemblyDescription ("")] -[assembly: AssemblyConfiguration ("")] -[assembly: AssemblyCompany ("")] -[assembly: AssemblyProduct ("")] -[assembly: AssemblyCopyright ("Google Inc. All rights reserved.")] -[assembly: AssemblyTrademark ("")] -[assembly: AssemblyCulture ("")] -// The assembly version has the format "{Major}.{Minor}.{Build}.{Revision}". -// The form "{Major}.{Minor}.*" will automatically update the build and revision, -// and "{Major}.{Minor}.{Build}.*" will update just the revision. -[assembly: AssemblyVersion ("0.1.*")] -// The following attributes are used to specify the signing key for the assembly, -// if desired. See the Mono documentation for more information about signing. -//[assembly: AssemblyDelaySign(false)] -//[assembly: AssemblyKeyFile("")] - +[assembly: AssemblyTitle("Grpc.Examples")] +[assembly: AssemblyDescription("")] +[assembly: AssemblyConfiguration("")] +[assembly: AssemblyCompany("")] +[assembly: AssemblyProduct("")] +[assembly: AssemblyCopyright("Google Inc. All rights reserved.")] +[assembly: AssemblyTrademark("")] +[assembly: AssemblyCulture("")] +[assembly: AssemblyVersion("0.1.*")] diff --git a/src/csharp/Grpc.Examples/Settings.StyleCop b/src/csharp/Grpc.Examples/Settings.StyleCop new file mode 100644 index 0000000000000000000000000000000000000000..e9b6e7172aa37c6bf6801d97d2b694b0a936fc3f --- /dev/null +++ b/src/csharp/Grpc.Examples/Settings.StyleCop @@ -0,0 +1,10 @@ +<StyleCopSettings Version="105"> + <SourceFileList> + <SourceFile>Math.cs</SourceFile> + <Settings> + <GlobalSettings> + <BooleanProperty Name="RulesEnabledByDefault">False</BooleanProperty> + </GlobalSettings> + </Settings> + </SourceFileList> +</StyleCopSettings> \ No newline at end of file diff --git a/src/csharp/Grpc.IntegrationTesting.Client/Properties/AssemblyInfo.cs b/src/csharp/Grpc.IntegrationTesting.Client/Properties/AssemblyInfo.cs index d1f9e8560dc8b99946848be51f7be213c4ce9f7a..c93dd1eb2f318dc8f03b34602c2bbb58a4ac1065 100644 --- a/src/csharp/Grpc.IntegrationTesting.Client/Properties/AssemblyInfo.cs +++ b/src/csharp/Grpc.IntegrationTesting.Client/Properties/AssemblyInfo.cs @@ -1,8 +1,6 @@ using System.Reflection; using System.Runtime.CompilerServices; -// Information about this assembly is defined by the following attributes. -// Change them to the values specific to your project. [assembly: AssemblyTitle("Grpc.IntegrationTesting.Client")] [assembly: AssemblyDescription("")] [assembly: AssemblyConfiguration("")] @@ -11,12 +9,4 @@ using System.Runtime.CompilerServices; [assembly: AssemblyCopyright("Google Inc. All rights reserved.")] [assembly: AssemblyTrademark("")] [assembly: AssemblyCulture("")] -// The assembly version has the format "{Major}.{Minor}.{Build}.{Revision}". -// The form "{Major}.{Minor}.*" will automatically update the build and revision, -// and "{Major}.{Minor}.{Build}.*" will update just the revision. [assembly: AssemblyVersion("0.1.*")] -// The following attributes are used to specify the signing key for the assembly, -// if desired. See the Mono documentation for more information about signing. -//[assembly: AssemblyDelaySign(false)] -//[assembly: AssemblyKeyFile("")] - diff --git a/src/csharp/Grpc.IntegrationTesting.Server/Properties/AssemblyInfo.cs b/src/csharp/Grpc.IntegrationTesting.Server/Properties/AssemblyInfo.cs index 4ef93f328d299796967b51fc0a279eb7e4d28809..f3def1aea4469c4ce6c38d50f3ae7b7de2030ed8 100644 --- a/src/csharp/Grpc.IntegrationTesting.Server/Properties/AssemblyInfo.cs +++ b/src/csharp/Grpc.IntegrationTesting.Server/Properties/AssemblyInfo.cs @@ -1,8 +1,6 @@ using System.Reflection; using System.Runtime.CompilerServices; -// Information about this assembly is defined by the following attributes. -// Change them to the values specific to your project. [assembly: AssemblyTitle("Grpc.IntegrationTesting.Server")] [assembly: AssemblyDescription("")] [assembly: AssemblyConfiguration("")] @@ -11,12 +9,4 @@ using System.Runtime.CompilerServices; [assembly: AssemblyCopyright("Google Inc. All rights reserved.")] [assembly: AssemblyTrademark("")] [assembly: AssemblyCulture("")] -// The assembly version has the format "{Major}.{Minor}.{Build}.{Revision}". -// The form "{Major}.{Minor}.*" will automatically update the build and revision, -// and "{Major}.{Minor}.{Build}.*" will update just the revision. [assembly: AssemblyVersion("0.1.*")] -// The following attributes are used to specify the signing key for the assembly, -// if desired. See the Mono documentation for more information about signing. -//[assembly: AssemblyDelaySign(false)] -//[assembly: AssemblyKeyFile("")] - diff --git a/src/csharp/Grpc.IntegrationTesting/Grpc.IntegrationTesting.csproj b/src/csharp/Grpc.IntegrationTesting/Grpc.IntegrationTesting.csproj index 438bf9e95de6ab8715f6d845b3fcf4d2c082faa7..cfb258711ad70af0ba79f93444445c383987b71a 100644 --- a/src/csharp/Grpc.IntegrationTesting/Grpc.IntegrationTesting.csproj +++ b/src/csharp/Grpc.IntegrationTesting/Grpc.IntegrationTesting.csproj @@ -39,6 +39,10 @@ <Reference Include="Google.ProtocolBuffers"> <HintPath>..\packages\Google.ProtocolBuffers.2.4.1.521\lib\net40\Google.ProtocolBuffers.dll</HintPath> </Reference> + <Reference Include="System.Collections.Immutable, Version=1.1.34.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a, processorArchitecture=MSIL"> + <SpecificVersion>False</SpecificVersion> + <HintPath>..\packages\System.Collections.Immutable.1.1.34-rc\lib\portable-net45+win8+wp8+wpa81\System.Collections.Immutable.dll</HintPath> + </Reference> </ItemGroup> <ItemGroup> <Compile Include="Properties\AssemblyInfo.cs" /> @@ -76,8 +80,5 @@ <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory> </None> </ItemGroup> - <ItemGroup> - <Folder Include="proto\" /> - <Folder Include="data\" /> - </ItemGroup> -</Project> + <ItemGroup /> +</Project> \ No newline at end of file diff --git a/src/csharp/Grpc.IntegrationTesting/InteropClient.cs b/src/csharp/Grpc.IntegrationTesting/InteropClient.cs index 2992c42ae95db1710ebc9c5d8b26ca7ec1550213..6b92d3c660fe56737661b551f40527ee32d68949 100644 --- a/src/csharp/Grpc.IntegrationTesting/InteropClient.cs +++ b/src/csharp/Grpc.IntegrationTesting/InteropClient.cs @@ -38,10 +38,10 @@ using System.IO; using System.Text.RegularExpressions; using System.Threading.Tasks; using Google.ProtocolBuffers; +using grpc.testing; using Grpc.Core; using Grpc.Core.Utils; using NUnit.Framework; -using grpc.testing; namespace Grpc.IntegrationTesting { @@ -50,7 +50,7 @@ namespace Grpc.IntegrationTesting private class ClientOptions { public bool help; - public string serverHost= "127.0.0.1"; + public string serverHost = "127.0.0.1"; public string serverHostOverride = TestCredentials.DefaultHostOverride; public int? serverPort; public string testCase = "large_unary"; @@ -109,7 +109,7 @@ namespace Grpc.IntegrationTesting ChannelArgs channelArgs = null; if (!string.IsNullOrEmpty(options.serverHostOverride)) { - channelArgs = ChannelArgs.NewBuilder() + channelArgs = ChannelArgs.CreateBuilder() .AddString(ChannelArgs.SslTargetNameOverrideKey, options.serverHostOverride).Build(); } @@ -180,7 +180,7 @@ namespace Grpc.IntegrationTesting { Console.WriteLine("running client_streaming"); - var bodySizes = new List<int>{27182, 8, 1828, 45904}; + var bodySizes = new List<int> { 27182, 8, 1828, 45904 }; var context = client.StreamingInputCall(); foreach (var size in bodySizes) @@ -199,7 +199,7 @@ namespace Grpc.IntegrationTesting { Console.WriteLine("running server_streaming"); - var bodySizes = new List<int>{31415, 9, 2653, 58979}; + var bodySizes = new List<int> { 31415, 9, 2653, 58979 }; var request = StreamingOutputCallRequest.CreateBuilder() .SetResponseType(PayloadType.COMPRESSABLE) @@ -256,7 +256,6 @@ namespace Grpc.IntegrationTesting Assert.AreEqual(PayloadType.COMPRESSABLE, response.Payload.Type); Assert.AreEqual(2653, response.Payload.Body.Length); - inputs.OnNext(StreamingOutputCallRequest.CreateBuilder() .SetResponseType(PayloadType.COMPRESSABLE) .AddResponseParameters(ResponseParameters.CreateBuilder().SetSize(58979)) @@ -292,17 +291,18 @@ namespace Grpc.IntegrationTesting public static void RunBenchmarkEmptyUnary(TestServiceGrpc.ITestServiceClient client) { BenchmarkUtil.RunBenchmark(10000, 10000, - () => { client.EmptyCall(Empty.DefaultInstance);}); + () => { client.EmptyCall(Empty.DefaultInstance); }); } - private static Payload CreateZerosPayload(int size) { + private static Payload CreateZerosPayload(int size) + { return Payload.CreateBuilder().SetBody(ByteString.CopyFrom(new byte[size])).Build(); } private static ClientOptions ParseArguments(string[] args) { var options = new ClientOptions(); - foreach(string arg in args) + foreach (string arg in args) { ParseArgument(arg, options); if (options.help) diff --git a/src/csharp/Grpc.IntegrationTesting/InteropClientServerTest.cs b/src/csharp/Grpc.IntegrationTesting/InteropClientServerTest.cs index ab2d6f4a6ac1ed31c3e8d2422d8d39ed9d161ba0..814f6311f2321c21ab569789974d241dbed6758c 100644 --- a/src/csharp/Grpc.IntegrationTesting/InteropClientServerTest.cs +++ b/src/csharp/Grpc.IntegrationTesting/InteropClientServerTest.cs @@ -35,10 +35,10 @@ using System; using System.Collections.Generic; using System.Threading; using System.Threading.Tasks; +using grpc.testing; using Grpc.Core; using Grpc.Core.Utils; using NUnit.Framework; -using grpc.testing; namespace Grpc.IntegrationTesting { @@ -62,7 +62,7 @@ namespace Grpc.IntegrationTesting int port = server.AddPort(host + ":0", TestCredentials.CreateTestServerCredentials()); server.Start(); - var channelArgs = ChannelArgs.NewBuilder() + var channelArgs = ChannelArgs.CreateBuilder() .AddString(ChannelArgs.SslTargetNameOverrideKey, TestCredentials.DefaultHostOverride).Build(); channel = new Channel(host + ":" + port, TestCredentials.CreateTestClientCredentials(true), channelArgs); @@ -117,7 +117,5 @@ namespace Grpc.IntegrationTesting // TODO: add cancel_after_begin // TODO: add cancel_after_first_response - } } - diff --git a/src/csharp/Grpc.IntegrationTesting/InteropServer.cs b/src/csharp/Grpc.IntegrationTesting/InteropServer.cs index 24d72da0c3f2b87d3a01d81d974c572314e7e573..5e580280b6119411d015d6dd21007e5905d08607 100644 --- a/src/csharp/Grpc.IntegrationTesting/InteropServer.cs +++ b/src/csharp/Grpc.IntegrationTesting/InteropServer.cs @@ -38,10 +38,10 @@ using System.IO; using System.Text.RegularExpressions; using System.Threading.Tasks; using Google.ProtocolBuffers; +using grpc.testing; using Grpc.Core; using Grpc.Core.Utils; using NUnit.Framework; -using grpc.testing; namespace Grpc.IntegrationTesting { @@ -113,7 +113,7 @@ namespace Grpc.IntegrationTesting private static ServerOptions ParseArguments(string[] args) { var options = new ServerOptions(); - foreach(string arg in args) + foreach (string arg in args) { ParseArgument(arg, options); if (options.help) diff --git a/src/csharp/Grpc.IntegrationTesting/Properties/AssemblyInfo.cs b/src/csharp/Grpc.IntegrationTesting/Properties/AssemblyInfo.cs index f633c19132e2eab39fb8b9cadfc68a41c1477b68..f09a448e9e28bc48f073dfbe18cbbcf336882800 100644 --- a/src/csharp/Grpc.IntegrationTesting/Properties/AssemblyInfo.cs +++ b/src/csharp/Grpc.IntegrationTesting/Properties/AssemblyInfo.cs @@ -1,8 +1,6 @@ using System.Reflection; using System.Runtime.CompilerServices; -// Information about this assembly is defined by the following attributes. -// Change them to the values specific to your project. [assembly: AssemblyTitle("Grpc.IntegrationTesting")] [assembly: AssemblyDescription("")] [assembly: AssemblyConfiguration("")] @@ -11,12 +9,4 @@ using System.Runtime.CompilerServices; [assembly: AssemblyCopyright("Google Inc. All rights reserved.")] [assembly: AssemblyTrademark("")] [assembly: AssemblyCulture("")] -// The assembly version has the format "{Major}.{Minor}.{Build}.{Revision}". -// The form "{Major}.{Minor}.*" will automatically update the build and revision, -// and "{Major}.{Minor}.{Build}.*" will update just the revision. [assembly: AssemblyVersion("0.1.*")] -// The following attributes are used to specify the signing key for the assembly, -// if desired. See the Mono documentation for more information about signing. -//[assembly: AssemblyDelaySign(false)] -//[assembly: AssemblyKeyFile("")] - diff --git a/src/csharp/Grpc.IntegrationTesting/Settings.StyleCop b/src/csharp/Grpc.IntegrationTesting/Settings.StyleCop new file mode 100644 index 0000000000000000000000000000000000000000..fb99cd4af1cd6f61557b16a2cedca158b689b7c3 --- /dev/null +++ b/src/csharp/Grpc.IntegrationTesting/Settings.StyleCop @@ -0,0 +1,11 @@ +<StyleCopSettings Version="105"> + <SourceFileList> + <SourceFile>Messages.cs</SourceFile> + <SourceFile>Empty.cs</SourceFile> + <Settings> + <GlobalSettings> + <BooleanProperty Name="RulesEnabledByDefault">False</BooleanProperty> + </GlobalSettings> + </Settings> + </SourceFileList> +</StyleCopSettings> \ No newline at end of file diff --git a/src/csharp/Grpc.IntegrationTesting/TestCredentials.cs b/src/csharp/Grpc.IntegrationTesting/TestCredentials.cs index b31abf118118fc2e992c32c237e7844da7b5462f..401c50b1aeaf6ee12dcda2940c436364e7f245ba 100644 --- a/src/csharp/Grpc.IntegrationTesting/TestCredentials.cs +++ b/src/csharp/Grpc.IntegrationTesting/TestCredentials.cs @@ -33,15 +33,16 @@ using System; using System.Collections.Generic; +using System.Collections.Immutable; using System.Diagnostics; using System.IO; using System.Text.RegularExpressions; using System.Threading.Tasks; using Google.ProtocolBuffers; +using grpc.testing; using Grpc.Core; using Grpc.Core.Utils; using NUnit.Framework; -using grpc.testing; namespace Grpc.IntegrationTesting { @@ -77,7 +78,7 @@ namespace Grpc.IntegrationTesting var keyCertPair = new KeyCertificatePair( File.ReadAllText(ServerCertChainPath), File.ReadAllText(ServerPrivateKeyPath)); - return new SslServerCredentials(new List<KeyCertificatePair> {keyCertPair}); + return new SslServerCredentials(ImmutableList.Create(keyCertPair)); } } } diff --git a/src/csharp/Grpc.IntegrationTesting/TestServiceGrpc.cs b/src/csharp/Grpc.IntegrationTesting/TestServiceGrpc.cs index b71704bcc7b05e439f778cd771450fa732a2d2b5..9b0251c3ca9d6012f287eb32510a54a5a839531b 100644 --- a/src/csharp/Grpc.IntegrationTesting/TestServiceGrpc.cs +++ b/src/csharp/Grpc.IntegrationTesting/TestServiceGrpc.cs @@ -44,50 +44,49 @@ namespace grpc.testing /// </summary> public class TestServiceGrpc { - readonly static Marshaller<Empty> emptyMarshaller = Marshallers.Create((arg) => arg.ToByteArray(), Empty.ParseFrom); - readonly static Marshaller<SimpleRequest> simpleRequestMarshaller = Marshallers.Create((arg) => arg.ToByteArray(), SimpleRequest.ParseFrom); - readonly static Marshaller<SimpleResponse> simpleResponseMarshaller = Marshallers.Create((arg) => arg.ToByteArray(), SimpleResponse.ParseFrom); - readonly static Marshaller<StreamingOutputCallRequest> streamingOutputCallRequestMarshaller = Marshallers.Create((arg) => arg.ToByteArray(), StreamingOutputCallRequest.ParseFrom); - readonly static Marshaller<StreamingOutputCallResponse> streamingOutputCallResponseMarshaller = Marshallers.Create((arg) => arg.ToByteArray(), StreamingOutputCallResponse.ParseFrom); - readonly static Marshaller<StreamingInputCallRequest> streamingInputCallRequestMarshaller = Marshallers.Create((arg) => arg.ToByteArray(), StreamingInputCallRequest.ParseFrom); - readonly static Marshaller<StreamingInputCallResponse> streamingInputCallResponseMarshaller = Marshallers.Create((arg) => arg.ToByteArray(), StreamingInputCallResponse.ParseFrom); - - readonly static Method<Empty, Empty> emptyCallMethod = new Method<Empty, Empty>( + static readonly Marshaller<Empty> EmptyMarshaller = Marshallers.Create((arg) => arg.ToByteArray(), Empty.ParseFrom); + static readonly Marshaller<SimpleRequest> SimpleRequestMarshaller = Marshallers.Create((arg) => arg.ToByteArray(), SimpleRequest.ParseFrom); + static readonly Marshaller<SimpleResponse> SimpleResponseMarshaller = Marshallers.Create((arg) => arg.ToByteArray(), SimpleResponse.ParseFrom); + static readonly Marshaller<StreamingOutputCallRequest> StreamingOutputCallRequestMarshaller = Marshallers.Create((arg) => arg.ToByteArray(), StreamingOutputCallRequest.ParseFrom); + static readonly Marshaller<StreamingOutputCallResponse> StreamingOutputCallResponseMarshaller = Marshallers.Create((arg) => arg.ToByteArray(), StreamingOutputCallResponse.ParseFrom); + static readonly Marshaller<StreamingInputCallRequest> StreamingInputCallRequestMarshaller = Marshallers.Create((arg) => arg.ToByteArray(), StreamingInputCallRequest.ParseFrom); + static readonly Marshaller<StreamingInputCallResponse> StreamingInputCallResponseMarshaller = Marshallers.Create((arg) => arg.ToByteArray(), StreamingInputCallResponse.ParseFrom); + + static readonly Method<Empty, Empty> EmptyCallMethod = new Method<Empty, Empty>( MethodType.Unary, "/grpc.testing.TestService/EmptyCall", - emptyMarshaller, - emptyMarshaller - ); - readonly static Method<SimpleRequest, SimpleResponse> unaryCallMethod = new Method<SimpleRequest, SimpleResponse>( + EmptyMarshaller, + EmptyMarshaller); + + static readonly Method<SimpleRequest, SimpleResponse> UnaryCallMethod = new Method<SimpleRequest, SimpleResponse>( MethodType.Unary, "/grpc.testing.TestService/UnaryCall", - simpleRequestMarshaller, - simpleResponseMarshaller - ); - readonly static Method<StreamingOutputCallRequest, StreamingOutputCallResponse> streamingOutputCallMethod = new Method<StreamingOutputCallRequest, StreamingOutputCallResponse>( + SimpleRequestMarshaller, + SimpleResponseMarshaller); + + static readonly Method<StreamingOutputCallRequest, StreamingOutputCallResponse> StreamingOutputCallMethod = new Method<StreamingOutputCallRequest, StreamingOutputCallResponse>( MethodType.ServerStreaming, "/grpc.testing.TestService/StreamingOutputCall", - streamingOutputCallRequestMarshaller, - streamingOutputCallResponseMarshaller - ); - readonly static Method<StreamingInputCallRequest, StreamingInputCallResponse> streamingInputCallMethod = new Method<StreamingInputCallRequest, StreamingInputCallResponse>( + StreamingOutputCallRequestMarshaller, + StreamingOutputCallResponseMarshaller); + + static readonly Method<StreamingInputCallRequest, StreamingInputCallResponse> StreamingInputCallMethod = new Method<StreamingInputCallRequest, StreamingInputCallResponse>( MethodType.ClientStreaming, "/grpc.testing.TestService/StreamingInputCall", - streamingInputCallRequestMarshaller, - streamingInputCallResponseMarshaller - ); - readonly static Method<StreamingOutputCallRequest, StreamingOutputCallResponse> fullDuplexCallMethod = new Method<StreamingOutputCallRequest, StreamingOutputCallResponse>( + StreamingInputCallRequestMarshaller, + StreamingInputCallResponseMarshaller); + + static readonly Method<StreamingOutputCallRequest, StreamingOutputCallResponse> FullDuplexCallMethod = new Method<StreamingOutputCallRequest, StreamingOutputCallResponse>( MethodType.DuplexStreaming, "/grpc.testing.TestService/FullDuplexCall", - streamingOutputCallRequestMarshaller, - streamingOutputCallResponseMarshaller - ); - readonly static Method<StreamingOutputCallRequest, StreamingOutputCallResponse> halfDuplexCallMethod = new Method<StreamingOutputCallRequest, StreamingOutputCallResponse>( + StreamingOutputCallRequestMarshaller, + StreamingOutputCallResponseMarshaller); + + static readonly Method<StreamingOutputCallRequest, StreamingOutputCallResponse> HalfDuplexCallMethod = new Method<StreamingOutputCallRequest, StreamingOutputCallResponse>( MethodType.DuplexStreaming, "/grpc.testing.TestService/HalfDuplexCall", - streamingOutputCallRequestMarshaller, - streamingOutputCallResponseMarshaller - ); + StreamingOutputCallRequestMarshaller, + StreamingOutputCallResponseMarshaller); public interface ITestServiceClient { @@ -119,49 +118,49 @@ namespace grpc.testing public Empty EmptyCall(Empty request, CancellationToken token = default(CancellationToken)) { - var call = new Grpc.Core.Call<Empty, Empty>(emptyCallMethod, channel); + var call = new Grpc.Core.Call<Empty, Empty>(EmptyCallMethod, channel); return Calls.BlockingUnaryCall(call, request, token); } public Task<Empty> EmptyCallAsync(Empty request, CancellationToken token = default(CancellationToken)) { - var call = new Grpc.Core.Call<Empty, Empty>(emptyCallMethod, channel); + var call = new Grpc.Core.Call<Empty, Empty>(EmptyCallMethod, channel); return Calls.AsyncUnaryCall(call, request, token); } public SimpleResponse UnaryCall(SimpleRequest request, CancellationToken token = default(CancellationToken)) { - var call = new Grpc.Core.Call<SimpleRequest, SimpleResponse>(unaryCallMethod, channel); + var call = new Grpc.Core.Call<SimpleRequest, SimpleResponse>(UnaryCallMethod, channel); return Calls.BlockingUnaryCall(call, request, token); } public Task<SimpleResponse> UnaryCallAsync(SimpleRequest request, CancellationToken token = default(CancellationToken)) { - var call = new Grpc.Core.Call<SimpleRequest, SimpleResponse>(unaryCallMethod, channel); + var call = new Grpc.Core.Call<SimpleRequest, SimpleResponse>(UnaryCallMethod, channel); return Calls.AsyncUnaryCall(call, request, token); } - public void StreamingOutputCall(StreamingOutputCallRequest request, IObserver<StreamingOutputCallResponse> responseObserver, CancellationToken token = default(CancellationToken)) { - var call = new Grpc.Core.Call<StreamingOutputCallRequest, StreamingOutputCallResponse>(streamingOutputCallMethod, channel); + public void StreamingOutputCall(StreamingOutputCallRequest request, IObserver<StreamingOutputCallResponse> responseObserver, CancellationToken token = default(CancellationToken)) + { + var call = new Grpc.Core.Call<StreamingOutputCallRequest, StreamingOutputCallResponse>(StreamingOutputCallMethod, channel); Calls.AsyncServerStreamingCall(call, request, responseObserver, token); } public ClientStreamingAsyncResult<StreamingInputCallRequest, StreamingInputCallResponse> StreamingInputCall(CancellationToken token = default(CancellationToken)) { - var call = new Grpc.Core.Call<StreamingInputCallRequest, StreamingInputCallResponse>(streamingInputCallMethod, channel); + var call = new Grpc.Core.Call<StreamingInputCallRequest, StreamingInputCallResponse>(StreamingInputCallMethod, channel); return Calls.AsyncClientStreamingCall(call, token); } public IObserver<StreamingOutputCallRequest> FullDuplexCall(IObserver<StreamingOutputCallResponse> responseObserver, CancellationToken token = default(CancellationToken)) { - var call = new Grpc.Core.Call<StreamingOutputCallRequest, StreamingOutputCallResponse>(fullDuplexCallMethod, channel); + var call = new Grpc.Core.Call<StreamingOutputCallRequest, StreamingOutputCallResponse>(FullDuplexCallMethod, channel); return Calls.DuplexStreamingCall(call, responseObserver, token); } - public IObserver<StreamingOutputCallRequest> HalfDuplexCall(IObserver<StreamingOutputCallResponse> responseObserver, CancellationToken token = default(CancellationToken)) { - var call = new Grpc.Core.Call<StreamingOutputCallRequest, StreamingOutputCallResponse>(halfDuplexCallMethod, channel); + var call = new Grpc.Core.Call<StreamingOutputCallRequest, StreamingOutputCallResponse>(HalfDuplexCallMethod, channel); return Calls.DuplexStreamingCall(call, responseObserver, token); } } @@ -185,12 +184,12 @@ namespace grpc.testing public static ServerServiceDefinition BindService(ITestService serviceImpl) { return ServerServiceDefinition.CreateBuilder("/grpc.testing.TestService/") - .AddMethod(emptyCallMethod, serviceImpl.EmptyCall) - .AddMethod(unaryCallMethod, serviceImpl.UnaryCall) - .AddMethod(streamingOutputCallMethod, serviceImpl.StreamingOutputCall) - .AddMethod(streamingInputCallMethod, serviceImpl.StreamingInputCall) - .AddMethod(fullDuplexCallMethod, serviceImpl.FullDuplexCall) - .AddMethod(halfDuplexCallMethod, serviceImpl.HalfDuplexCall) + .AddMethod(EmptyCallMethod, serviceImpl.EmptyCall) + .AddMethod(UnaryCallMethod, serviceImpl.UnaryCall) + .AddMethod(StreamingOutputCallMethod, serviceImpl.StreamingOutputCall) + .AddMethod(StreamingInputCallMethod, serviceImpl.StreamingInputCall) + .AddMethod(FullDuplexCallMethod, serviceImpl.FullDuplexCall) + .AddMethod(HalfDuplexCallMethod, serviceImpl.HalfDuplexCall) .Build(); } diff --git a/src/csharp/Grpc.IntegrationTesting/TestServiceImpl.cs b/src/csharp/Grpc.IntegrationTesting/TestServiceImpl.cs index 176843b1305683db5e14584cc406e05e820c7855..661b31b0ee67f909c95aa9a533b97054c900b760 100644 --- a/src/csharp/Grpc.IntegrationTesting/TestServiceImpl.cs +++ b/src/csharp/Grpc.IntegrationTesting/TestServiceImpl.cs @@ -55,14 +55,14 @@ namespace grpc.testing { var response = SimpleResponse.CreateBuilder() .SetPayload(CreateZerosPayload(request.ResponseSize)).Build(); - //TODO: check we support ReponseType + // TODO: check we support ReponseType responseObserver.OnNext(response); responseObserver.OnCompleted(); } public void StreamingOutputCall(StreamingOutputCallRequest request, IObserver<StreamingOutputCallResponse> responseObserver) { - foreach(var responseParam in request.ResponseParametersList) + foreach (var responseParam in request.ResponseParametersList) { var response = StreamingOutputCallResponse.CreateBuilder() .SetPayload(CreateZerosPayload(responseParam.Size)).Build(); @@ -74,9 +74,10 @@ namespace grpc.testing public IObserver<StreamingInputCallRequest> StreamingInputCall(IObserver<StreamingInputCallResponse> responseObserver) { var recorder = new RecordingObserver<StreamingInputCallRequest>(); - Task.Run(() => { + Task.Run(() => + { int sum = 0; - foreach(var req in recorder.ToList().Result) + foreach (var req in recorder.ToList().Result) { sum += req.Payload.Body.Length; } @@ -98,8 +99,8 @@ namespace grpc.testing throw new NotImplementedException(); } - private class FullDuplexObserver : IObserver<StreamingOutputCallRequest> { - + private class FullDuplexObserver : IObserver<StreamingOutputCallRequest> + { readonly IObserver<StreamingOutputCallResponse> responseObserver; public FullDuplexObserver(IObserver<StreamingOutputCallResponse> responseObserver) @@ -119,22 +120,18 @@ namespace grpc.testing public void OnNext(StreamingOutputCallRequest value) { - // TODO: this is not in order!!! - //Task.Factory.StartNew(() => { - - foreach(var responseParam in value.ResponseParametersList) - { - var response = StreamingOutputCallResponse.CreateBuilder() - .SetPayload(CreateZerosPayload(responseParam.Size)).Build(); - responseObserver.OnNext(response); - } - //}); + foreach (var responseParam in value.ResponseParametersList) + { + var response = StreamingOutputCallResponse.CreateBuilder() + .SetPayload(CreateZerosPayload(responseParam.Size)).Build(); + responseObserver.OnNext(response); + } } } - private static Payload CreateZerosPayload(int size) { + private static Payload CreateZerosPayload(int size) + { return Payload.CreateBuilder().SetBody(ByteString.CopyFrom(new byte[size])).Build(); } } } - diff --git a/src/csharp/Grpc.IntegrationTesting/packages.config b/src/csharp/Grpc.IntegrationTesting/packages.config index 51c17bcd5e74685ab31264eae00dc062b5b9083d..157c264eac0bd9c9f341180bfc099973aa4382f2 100644 --- a/src/csharp/Grpc.IntegrationTesting/packages.config +++ b/src/csharp/Grpc.IntegrationTesting/packages.config @@ -2,4 +2,5 @@ <packages> <package id="Google.ProtocolBuffers" version="2.4.1.521" targetFramework="net45" /> <package id="NUnit" version="2.6.4" targetFramework="net45" /> + <package id="System.Collections.Immutable" version="1.1.34-rc" targetFramework="net45" /> </packages> \ No newline at end of file diff --git a/src/csharp/Settings.StyleCop b/src/csharp/Settings.StyleCop new file mode 100644 index 0000000000000000000000000000000000000000..2ecf22f69e9460fe2db79aae22ef44d2283aaae8 --- /dev/null +++ b/src/csharp/Settings.StyleCop @@ -0,0 +1,509 @@ +<StyleCopSettings Version="105"> + <Analyzers> + <Analyzer AnalyzerId="StyleCop.CSharp.DocumentationRules"> + <Rules> + <Rule Name="ElementsMustBeDocumented"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="PartialElementsMustBeDocumented"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="EnumerationItemsMustBeDocumented"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="DocumentationMustContainValidXml"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="ElementDocumentationMustHaveSummary"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="PartialElementDocumentationMustHaveSummary"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="ElementDocumentationMustHaveSummaryText"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="PartialElementDocumentationMustHaveSummaryText"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="ElementDocumentationMustNotHaveDefaultSummary"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="ElementParametersMustBeDocumented"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="ElementParameterDocumentationMustMatchElementParameters"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="ElementParameterDocumentationMustDeclareParameterName"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="ElementParameterDocumentationMustHaveText"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="ElementReturnValueMustBeDocumented"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="ElementReturnValueDocumentationMustHaveText"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="VoidReturnValueMustNotBeDocumented"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="GenericTypeParametersMustBeDocumented"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="GenericTypeParametersMustBeDocumentedPartialClass"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="GenericTypeParameterDocumentationMustMatchTypeParameters"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="GenericTypeParameterDocumentationMustDeclareParameterName"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="GenericTypeParameterDocumentationMustHaveText"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="PropertySummaryDocumentationMustMatchAccessors"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="PropertySummaryDocumentationMustOmitSetAccessorWithRestrictedAccess"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="ElementDocumentationMustNotBeCopiedAndPasted"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="SingleLineCommentsMustNotUseDocumentationStyleSlashes"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="DocumentationTextMustNotBeEmpty"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="DocumentationTextMustContainWhitespace"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="DocumentationMustMeetCharacterPercentage"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="ConstructorSummaryDocumentationMustBeginWithStandardText"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="DestructorSummaryDocumentationMustBeginWithStandardText"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="DocumentationHeadersMustNotContainBlankLines"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="IncludedDocumentationXPathDoesNotExist"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="IncludeNodeDoesNotContainValidFileAndPath"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="InheritDocMustBeUsedWithInheritingClass"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="ElementDocumentationMustBeSpelledCorrectly"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="FileMustHaveHeader"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="FileHeaderMustShowCopyright"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="FileHeaderMustHaveCopyrightText"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="FileHeaderMustContainFileName"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="FileHeaderFileNameDocumentationMustMatchFileName"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="FileHeaderMustHaveValidCompanyText"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="FileHeaderFileNameDocumentationMustMatchTypeName"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + </Rules> + <AnalyzerSettings /> + </Analyzer> + <Analyzer AnalyzerId="StyleCop.CSharp.MaintainabilityRules"> + <Rules> + <Rule Name="AccessModifierMustBeDeclared"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="FieldsMustBePrivate"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="CodeAnalysisSuppressionMustHaveJustification"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="DebugAssertMustProvideMessageText"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="DebugFailMustProvideMessageText"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="FileMayOnlyContainASingleClass"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="StatementMustNotUseUnnecessaryParenthesis"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="ArithmeticExpressionsMustDeclarePrecedence"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="ConditionalExpressionsMustDeclarePrecedence"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="RemoveDelegateParenthesisWhenPossible"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="AttributeConstructorMustNotUseUnnecessaryParenthesis"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="RemoveUnnecessaryCode"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + </Rules> + <AnalyzerSettings /> + </Analyzer> + <Analyzer AnalyzerId="StyleCop.CSharp.NamingRules"> + <Rules> + <Rule Name="NonPrivateReadonlyFieldsMustBeginWithUpperCaseLetter"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="FieldNamesMustNotUseHungarianNotation"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="FieldNamesMustBeginWithLowerCaseLetter"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="AccessibleFieldsMustBeginWithUpperCaseLetter"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="VariableNamesMustNotBePrefixed"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="FieldNamesMustNotBeginWithUnderscore"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="FieldNamesMustNotContainUnderscore"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="ElementMustBeginWithUpperCaseLetter"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + </Rules> + <AnalyzerSettings /> + </Analyzer> + <Analyzer AnalyzerId="StyleCop.CSharp.OrderingRules"> + <Rules> + <Rule Name="UsingDirectivesMustBePlacedWithinNamespace"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="ElementsMustAppearInTheCorrectOrder"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="ElementsMustBeOrderedByAccess"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="StaticElementsMustAppearBeforeInstanceElements"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="PropertyAccessorsMustFollowOrder"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="EventAccessorsMustFollowOrder"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="UsingAliasDirectivesMustBePlacedAfterOtherUsingDirectives"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="UsingAliasDirectivesMustBeOrderedAlphabeticallyByAliasName"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + </Rules> + <AnalyzerSettings /> + </Analyzer> + <Analyzer AnalyzerId="StyleCop.CSharp.ReadabilityRules"> + <Rules> + <Rule Name="DoNotPrefixCallsWithBaseUnlessLocalImplementationExists"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="PrefixLocalCallsWithThis"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="PrefixCallsCorrectly"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="OpeningParenthesisMustBeOnDeclarationLine"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="ClosingParenthesisMustBeOnLineOfLastParameter"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="ClosingParenthesisMustBeOnLineOfOpeningParenthesis"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="CommaMustBeOnSameLineAsPreviousParameter"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="ParameterListMustFollowDeclaration"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="ParameterMustFollowComma"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="SplitParametersMustStartOnLineAfterDeclaration"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="ParametersMustBeOnSameLineOrSeparateLines"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="ParameterMustNotSpanMultipleLines"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="QueryClauseMustFollowPreviousClause"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="QueryClausesMustBeOnSeparateLinesOrAllOnOneLine"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="QueryClauseMustBeginOnNewLineWhenPreviousClauseSpansMultipleLines"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="QueryClausesSpanningMultipleLinesMustBeginOnOwnLine"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="CodeMustNotContainEmptyStatements"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="CodeMustNotContainMultipleStatementsOnOneLine"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="BlockStatementsMustNotContainEmbeddedComments"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="BlockStatementsMustNotContainEmbeddedRegions"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="UseStringEmptyForEmptyStrings"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + </Rules> + <AnalyzerSettings /> + </Analyzer> + <Analyzer AnalyzerId="StyleCop.CSharp.LayoutRules"> + <Rules> + <Rule Name="SingleLineCommentsMustNotBeFollowedByBlankLine"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="ClosingCurlyBracketMustBeFollowedByBlankLine"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="ElementDocumentationHeaderMustBePrecededByBlankLine"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + <Rule Name="SingleLineCommentMustBePrecededByBlankLine"> + <RuleSettings> + <BooleanProperty Name="Enabled">False</BooleanProperty> + </RuleSettings> + </Rule> + </Rules> + <AnalyzerSettings /> + </Analyzer> + </Analyzers> +</StyleCopSettings> \ No newline at end of file diff --git a/src/node/README.md b/src/node/README.md index 5b3de6b4f6e5075c3dd3d352bb078b1922d318ac..b1d2310ede05f5c5b5c14f1e91713f4629cfebc6 100644 --- a/src/node/README.md +++ b/src/node/README.md @@ -10,9 +10,9 @@ This requires `node` to be installed. If you instead have the `nodejs` executabl ## Installation -First, clone this repository (NPM package coming soon). Then follow the instructions in the `INSTALL` file in the root of the repository to install the C core library that this package depends on. - -Then, simply run `npm install` in or referencing this directory. + 1. Clone [the grpc repository](https://github.com/grpc/grpc). + 2. Follow the instructions in the `INSTALL` file in the root of that repository to install the C core library that this package depends on. + 3. Run `npm install`. ## Tests diff --git a/src/node/package.json b/src/node/package.json index f8c3ab079d9ef599b45c10249a7e7e517ecf28a2..1d0aa0e669d98dd217fbd032b166b046acdc8bd8 100644 --- a/src/node/package.json +++ b/src/node/package.json @@ -1,6 +1,6 @@ { "name": "grpc", - "version": "0.5.3", + "version": "0.5.5", "author": "Google Inc.", "description": "gRPC Library for Node", "homepage": "http://www.grpc.io/", @@ -26,7 +26,7 @@ "dependencies": { "bindings": "^1.2.0", "nan": "^1.5.0", - "protobufjs": "murgatroid99/ProtoBuf.js", + "protobufjs": "^4.0.0-b2", "underscore": "^1.6.0", "underscore.string": "^3.0.0" }, diff --git a/src/php/ext/grpc/call.c b/src/php/ext/grpc/call.c index df0635dc7272561fa6cec0e14c2279cfb0681eb5..798747109a1b21c486a0f374db6e977ae9f22524 100644 --- a/src/php/ext/grpc/call.c +++ b/src/php/ext/grpc/call.c @@ -56,6 +56,8 @@ #include "completion_queue.h" #include "byte_buffer.h" +zend_class_entry *grpc_ce_call; + /* Frees and destroys an instance of wrapped_grpc_call */ void free_wrapped_grpc_call(void *object TSRMLS_DC) { wrapped_grpc_call *call = (wrapped_grpc_call *)object; diff --git a/src/php/ext/grpc/call.h b/src/php/ext/grpc/call.h index 827e9a27a874c9e173d733110718546538634a4b..bce5d82974f37306fd043c6c3304099c5da535e8 100644 --- a/src/php/ext/grpc/call.h +++ b/src/php/ext/grpc/call.h @@ -57,7 +57,7 @@ } while (0) /* Class entry for the Call PHP class */ -zend_class_entry *grpc_ce_call; +extern zend_class_entry *grpc_ce_call; /* Wrapper struct for grpc_call that can be associated with a PHP object */ typedef struct wrapped_grpc_call { diff --git a/src/php/ext/grpc/channel.c b/src/php/ext/grpc/channel.c index d6296f94130ee35bf7274d17557197a025f95260..5e99332fab81a04fe309db1ad395dbd9ba63d3aa 100644 --- a/src/php/ext/grpc/channel.c +++ b/src/php/ext/grpc/channel.c @@ -55,6 +55,8 @@ #include "server.h" #include "credentials.h" +zend_class_entry *grpc_ce_channel; + /* Frees and destroys an instance of wrapped_grpc_channel */ void free_wrapped_grpc_channel(void *object TSRMLS_DC) { wrapped_grpc_channel *channel = (wrapped_grpc_channel *)object; diff --git a/src/php/ext/grpc/channel.h b/src/php/ext/grpc/channel.h index f426a25cafcbfa70ce4f9bb0f479f1e19dbda226..2c79668a4d8599bb43b9a84dafe6d9e684dd9e27 100755 --- a/src/php/ext/grpc/channel.h +++ b/src/php/ext/grpc/channel.h @@ -46,7 +46,7 @@ #include "grpc/grpc.h" /* Class entry for the PHP Channel class */ -zend_class_entry *grpc_ce_channel; +extern zend_class_entry *grpc_ce_channel; /* Wrapper struct for grpc_channel that can be associated with a PHP object */ typedef struct wrapped_grpc_channel { diff --git a/src/php/ext/grpc/completion_queue.c b/src/php/ext/grpc/completion_queue.c index 30c871b078319d68d9e31f9cb96ebff4d86dc62a..93abf5df36bff2b7da199fdc9b964ff5fff27daf 100644 --- a/src/php/ext/grpc/completion_queue.c +++ b/src/php/ext/grpc/completion_queue.c @@ -52,6 +52,8 @@ #include "event.h" #include "timeval.h" +zend_class_entry *grpc_ce_completion_queue; + /* Frees and destroys a wrapped instance of grpc_completion_queue */ void free_wrapped_grpc_completion_queue(void *object TSRMLS_DC) { wrapped_grpc_completion_queue *queue = NULL; diff --git a/src/php/ext/grpc/completion_queue.h b/src/php/ext/grpc/completion_queue.h index 6ce1df7c8cddfc2e309d1e015a0b8a3da81def7f..1d386cc58f4a9fa8356dbe5b270d1718bc8b6da4 100755 --- a/src/php/ext/grpc/completion_queue.h +++ b/src/php/ext/grpc/completion_queue.h @@ -46,7 +46,7 @@ #include "grpc/grpc.h" /* Class entry for the PHP CompletionQueue class */ -zend_class_entry *grpc_ce_completion_queue; +extern zend_class_entry *grpc_ce_completion_queue; /* Wrapper class for grpc_completion_queue that can be associated with a PHP object */ diff --git a/src/php/ext/grpc/credentials.c b/src/php/ext/grpc/credentials.c index 6d8f59fa33dc6435848ecc28906c85aa2fc9a593..a94b0eac2d30d0bdda13d1b7c0e7d54b136d4207 100644 --- a/src/php/ext/grpc/credentials.c +++ b/src/php/ext/grpc/credentials.c @@ -49,6 +49,8 @@ #include "grpc/grpc.h" #include "grpc/grpc_security.h" +zend_class_entry *grpc_ce_credentials; + /* Frees and destroys an instance of wrapped_grpc_credentials */ void free_wrapped_grpc_credentials(void *object TSRMLS_DC) { wrapped_grpc_credentials *creds = (wrapped_grpc_credentials *)object; diff --git a/src/php/ext/grpc/credentials.h b/src/php/ext/grpc/credentials.h index 3ff75af9dbe51caf0981f0e416e20e4492a1260e..86d7ae5b144c983726a861674bbb7a0414f00e31 100755 --- a/src/php/ext/grpc/credentials.h +++ b/src/php/ext/grpc/credentials.h @@ -47,7 +47,7 @@ #include "grpc/grpc_security.h" /* Class entry for the Credentials PHP class */ -zend_class_entry *grpc_ce_credentials; +extern zend_class_entry *grpc_ce_credentials; /* Wrapper struct for grpc_credentials that can be associated with a PHP * object */ diff --git a/src/php/ext/grpc/server.c b/src/php/ext/grpc/server.c index 00d08c6ecf0976d1c336e33bc86145e8a137f1ee..a5cfd952871798c0281f7767d00a624ca10ed6f4 100644 --- a/src/php/ext/grpc/server.c +++ b/src/php/ext/grpc/server.c @@ -56,6 +56,8 @@ #include "channel.h" #include "server_credentials.h" +zend_class_entry *grpc_ce_server; + /* Frees and destroys an instance of wrapped_grpc_server */ void free_wrapped_grpc_server(void *object TSRMLS_DC) { wrapped_grpc_server *server = (wrapped_grpc_server *)object; diff --git a/src/php/ext/grpc/server.h b/src/php/ext/grpc/server.h index ecef4c642998b094a37f86261da7fc8cdcdebac9..b55689c5816b3683cefe715626e614e2b477d08b 100755 --- a/src/php/ext/grpc/server.h +++ b/src/php/ext/grpc/server.h @@ -46,7 +46,7 @@ #include "grpc/grpc.h" /* Class entry for the Server PHP class */ -zend_class_entry *grpc_ce_server; +extern zend_class_entry *grpc_ce_server; /* Wrapper struct for grpc_server that can be associated with a PHP object */ typedef struct wrapped_grpc_server { diff --git a/src/php/ext/grpc/server_credentials.c b/src/php/ext/grpc/server_credentials.c index 8aaa86ce947ed51bcb4b00efb317f4dd69bc076c..df64e6598692d207a5f9e36b344e5d81742b6d71 100644 --- a/src/php/ext/grpc/server_credentials.c +++ b/src/php/ext/grpc/server_credentials.c @@ -49,6 +49,8 @@ #include "grpc/grpc.h" #include "grpc/grpc_security.h" +zend_class_entry *grpc_ce_server_credentials; + /* Frees and destroys an instace of wrapped_grpc_server_credentials */ void free_wrapped_grpc_server_credentials(void *object TSRMLS_DC) { wrapped_grpc_server_credentials *creds = diff --git a/src/php/ext/grpc/server_credentials.h b/src/php/ext/grpc/server_credentials.h index ce2a4da138c73f16447daff48b045b9409bdc8fe..8ed36971506d7fb5a18eeab39213ab506bc35240 100755 --- a/src/php/ext/grpc/server_credentials.h +++ b/src/php/ext/grpc/server_credentials.h @@ -47,7 +47,7 @@ #include "grpc/grpc_security.h" /* Class entry for the Server_Credentials PHP class */ -zend_class_entry *grpc_ce_server_credentials; +extern zend_class_entry *grpc_ce_server_credentials; /* Wrapper struct for grpc_server_credentials that can be associated with a PHP * object */ diff --git a/src/php/ext/grpc/timeval.c b/src/php/ext/grpc/timeval.c index 5b0142cbe47d43218d75ed9292e03e334a0f7c09..f90f0062baba22e7f765d30104928c566beef5cb 100644 --- a/src/php/ext/grpc/timeval.c +++ b/src/php/ext/grpc/timeval.c @@ -50,6 +50,8 @@ #include "grpc/grpc.h" #include "grpc/support/time.h" +zend_class_entry *grpc_ce_timeval; + /* Frees and destroys an instance of wrapped_grpc_call */ void free_wrapped_grpc_timeval(void *object TSRMLS_DC) { efree(object); } diff --git a/src/php/ext/grpc/timeval.h b/src/php/ext/grpc/timeval.h index 0e215fc88480b07c0b3eaf0055712d7cbf47fb8c..e3183f691dbd34c7c587ff439638158842ea129d 100755 --- a/src/php/ext/grpc/timeval.h +++ b/src/php/ext/grpc/timeval.h @@ -47,7 +47,7 @@ #include "grpc/support/time.h" /* Class entry for the Timeval PHP Class */ -zend_class_entry *grpc_ce_timeval; +extern zend_class_entry *grpc_ce_timeval; /* Wrapper struct for timeval that can be associated with a PHP object */ typedef struct wrapped_grpc_timeval { diff --git a/src/python/src/grpc/_adapter/_call.c b/src/python/src/grpc/_adapter/_call.c index dca2e49373b36a4b2c318926100acbf1e14ae017..d8806e568050137081159bdbca87d7b220c2a8f4 100644 --- a/src/python/src/grpc/_adapter/_call.c +++ b/src/python/src/grpc/_adapter/_call.c @@ -45,7 +45,7 @@ static int pygrpc_call_init(Call *self, PyObject *args, PyObject *kwds) { const PyObject *channel; const char *method; const char *host; - const double deadline; + double deadline; static char *kwlist[] = {"channel", "method", "host", "deadline", NULL}; if (!PyArg_ParseTupleAndKeywords(args, kwds, "O!ssd:Call", kwlist, diff --git a/src/python/src/grpc/early_adopter/implementations.py b/src/python/src/grpc/early_adopter/implementations.py index 1c02f9e4d63f510a109f00e4a66f5e98f69ca7a3..6fe90594a746a0b3fcc0dadf4a5c5b4bcd8bf29e 100644 --- a/src/python/src/grpc/early_adopter/implementations.py +++ b/src/python/src/grpc/early_adopter/implementations.py @@ -71,7 +71,8 @@ class _Server(interfaces.Server): _ONE_DAY_IN_SECONDS) self._fore_link = _fore.ForeLink( self._pool, self._breakdown.request_deserializers, - self._breakdown.response_serializers, None, self._key_chain_pairs) + self._breakdown.response_serializers, None, self._key_chain_pairs, + port=self._port) self._back.join_fore_link(self._fore_link) self._fore_link.join_rear_link(self._back) self._fore_link.start() diff --git a/templates/Makefile.template b/templates/Makefile.template index 6573e03f7f55746d73cc48d8fdcd9e1fd4236ada..a69c7a7f2f1cf6689d34665c9a23ac24851af196 100644 --- a/templates/Makefile.template +++ b/templates/Makefile.template @@ -176,9 +176,14 @@ ifndef VALID_CONFIG_$(CONFIG) $(error Invalid CONFIG value '$(CONFIG)') endif +ifeq ($(SYSTEM),Linux) +TMPOUT = /dev/null +else +TMPOUT = `mktemp /tmp/test-out-XXXXXX` +endif # Detect if we can use C++11 -CXX11_CHECK_CMD = $(CXX) -std=c++11 -o /dev/null -c test/build/c++11.cc +CXX11_CHECK_CMD = $(CXX) -std=c++11 -o $(TMPOUT) -c test/build/c++11.cc HAS_CXX11 = $(shell $(CXX11_CHECK_CMD) 2> /dev/null && echo true || echo false) # The HOST compiler settings are used to compile the protoc plugins. @@ -211,9 +216,25 @@ LDFLAGS += -g -fPIC INCLUDES = . include $(GENDIR) ifeq ($(SYSTEM),Darwin) -INCLUDES += /usr/local/ssl/include /opt/local/include +ifneq ($(wildcard /usr/local/ssl/include),) +INCLUDES += /usr/local/ssl/include +endif +ifneq ($(wildcard /opt/local/include),) +INCLUDES += /opt/local/include +endif +ifneq ($(wildcard /usr/local/include),) +INCLUDES += /usr/local/include +endif LIBS = m z -LDFLAGS += -L/usr/local/ssl/lib -L/opt/local/lib +ifneq ($(wildcard /usr/local/ssl/lib),) +LDFLAGS += -L/usr/local/ssl/lib +endif +ifneq ($(wildcard /opt/local/lib),) +LDFLAGS += -L/opt/local/lib +endif +ifneq ($(wildcard /usr/local/lib),) +LDFLAGS += -L/usr/local/lib +endif else LIBS = rt m z pthread LDFLAGS += -pthread @@ -268,10 +289,10 @@ else IS_GIT_FOLDER = true endif -OPENSSL_ALPN_CHECK_CMD = $(CC) $(CFLAGS) $(CPPFLAGS) -o /dev/null test/build/openssl-alpn.c -lssl -lcrypto -ldl $(LDFLAGS) -ZLIB_CHECK_CMD = $(CC) $(CFLAGS) $(CPPFLAGS) -o /dev/null test/build/zlib.c -lz $(LDFLAGS) -PERFTOOLS_CHECK_CMD = $(CC) $(CFLAGS) $(CPPFLAGS) -o /dev/null test/build/perftools.c -lprofiler $(LDFLAGS) -PROTOBUF_CHECK_CMD = $(CXX) $(CXXFLAGS) $(CPPFLAGS) -o /dev/null test/build/protobuf.cc -lprotobuf $(LDFLAGS) +OPENSSL_ALPN_CHECK_CMD = $(CC) $(CFLAGS) $(CPPFLAGS) -o $(TMPOUT) test/build/openssl-alpn.c -lssl -lcrypto -ldl $(LDFLAGS) +ZLIB_CHECK_CMD = $(CC) $(CFLAGS) $(CPPFLAGS) -o $(TMPOUT) test/build/zlib.c -lz $(LDFLAGS) +PERFTOOLS_CHECK_CMD = $(CC) $(CFLAGS) $(CPPFLAGS) -o $(TMPOUT) test/build/perftools.c -lprofiler $(LDFLAGS) +PROTOBUF_CHECK_CMD = $(CXX) $(CXXFLAGS) $(CPPFLAGS) -o $(TMPOUT) test/build/protobuf.cc -lprotobuf $(LDFLAGS) PROTOC_CMD = which protoc PROTOC_CHECK_CMD = protoc --version | grep -q libprotoc.3 @@ -810,10 +831,10 @@ ifeq ($(SYSTEM),MINGW32) $(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/${lib.name}.$(SHARED_EXT) $(prefix)/lib/${lib.name}.$(SHARED_EXT) $(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/lib${lib.name}-imp.a $(prefix)/lib/lib${lib.name}-imp.a else +ifneq ($(SYSTEM),Darwin) $(E) "[INSTALL] Installing lib${lib.name}.$(SHARED_EXT)" $(Q) $(INSTALL) -d $(prefix)/lib $(Q) $(INSTALL) $(LIBDIR)/$(CONFIG)/lib${lib.name}.$(SHARED_EXT) $(prefix)/lib/lib${lib.name}.$(SHARED_EXT) -ifneq ($(SYSTEM),Darwin) $(Q) ln -sf lib${lib.name}.$(SHARED_EXT) $(prefix)/lib/lib${lib.name}.so endif endif diff --git a/test/core/security/credentials_test.c b/test/core/security/credentials_test.c index 078462410ad6df115e3efc064e763561f7c3f818..d1d1ec15623fa58e99be6cefc110d78f4abd328f 100644 --- a/test/core/security/credentials_test.c +++ b/test/core/security/credentials_test.c @@ -84,6 +84,13 @@ static const char test_json_key_str_part3[] = "\"777-abaslkan11hlb6nmim3bpspl31ud.apps.googleusercontent." "com\", \"type\": \"service_account\" }"; +/* Test refresh token. */ +static const char test_refresh_token_str[] = + "{ \"client_id\": \"32555999999.apps.googleusercontent.com\"," + " \"client_secret\": \"EmssLNjJy1332hD4KFsecret\"," + " \"refresh_token\": \"1/Blahblasj424jladJDSGNf-u4Sua3HDA2ngjd42\"," + " \"type\": \"authorized_user\"}"; + static const char valid_oauth2_json_response[] = "{\"access_token\":\"ya29.AHES6ZRN3-HlhAPya30GnW_bHSb_\"," " \"expires_in\":3599, " @@ -97,10 +104,6 @@ static const char test_signed_jwt[] = "eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCIsImtpZCI6ImY0OTRkN2M1YWU2MGRmOTcyNmM4YW" "U0MDcyZTViYTdmZDkwODg2YzcifQ"; -static const char expected_service_account_http_body_prefix[] = - "grant_type=urn%3Aietf%3Aparams%3Aoauth%3Agrant-type%3Ajwt-bearer&" - "assertion="; - static const char test_service_url[] = "https://foo.com/foo.v1"; static const char other_test_service_url[] = "https://bar.com/bar.v1"; @@ -463,6 +466,87 @@ static void test_compute_engine_creds_failure(void) { grpc_httpcli_set_override(NULL, NULL); } +static void validate_refresh_token_http_request( + const grpc_httpcli_request *request, const char *body, size_t body_size) { + /* The content of the assertion is tested extensively in json_token_test. */ + char *expected_body = NULL; + GPR_ASSERT(body != NULL); + GPR_ASSERT(body_size != 0); + gpr_asprintf(&expected_body, GRPC_REFRESH_TOKEN_POST_BODY_FORMAT_STRING, + "32555999999.apps.googleusercontent.com", + "EmssLNjJy1332hD4KFsecret", + "1/Blahblasj424jladJDSGNf-u4Sua3HDA2ngjd42"); + GPR_ASSERT(strlen(expected_body) == body_size); + GPR_ASSERT(memcmp(expected_body, body, body_size) == 0); + gpr_free(expected_body); + GPR_ASSERT(request->use_ssl); + GPR_ASSERT(strcmp(request->host, GRPC_GOOGLE_OAUTH2_SERVICE_HOST) == 0); + GPR_ASSERT(strcmp(request->path, GRPC_GOOGLE_OAUTH2_SERVICE_TOKEN_PATH) == 0); + GPR_ASSERT(request->hdr_count == 1); + GPR_ASSERT(strcmp(request->hdrs[0].key, "Content-Type") == 0); + GPR_ASSERT(strcmp(request->hdrs[0].value, + "application/x-www-form-urlencoded") == 0); +} + +static int refresh_token_httpcli_post_success( + const grpc_httpcli_request *request, const char *body, size_t body_size, + gpr_timespec deadline, grpc_httpcli_response_cb on_response, + void *user_data) { + grpc_httpcli_response response = + http_response(200, valid_oauth2_json_response); + validate_refresh_token_http_request(request, body, body_size); + on_response(user_data, &response); + return 1; +} + +static int refresh_token_httpcli_post_failure( + const grpc_httpcli_request *request, const char *body, size_t body_size, + gpr_timespec deadline, grpc_httpcli_response_cb on_response, + void *user_data) { + grpc_httpcli_response response = http_response(403, "Not Authorized."); + validate_refresh_token_http_request(request, body, body_size); + on_response(user_data, &response); + return 1; +} + +static void test_refresh_token_creds_success(void) { + grpc_credentials *refresh_token_creds = + grpc_refresh_token_credentials_create(test_refresh_token_str); + GPR_ASSERT(grpc_credentials_has_request_metadata(refresh_token_creds)); + GPR_ASSERT(grpc_credentials_has_request_metadata_only(refresh_token_creds)); + + /* First request: http get should be called. */ + grpc_httpcli_set_override(httpcli_get_should_not_be_called, + refresh_token_httpcli_post_success); + grpc_credentials_get_request_metadata(refresh_token_creds, test_service_url, + on_oauth2_creds_get_metadata_success, + (void *)test_user_data); + + /* Second request: the cached token should be served directly. */ + grpc_httpcli_set_override(httpcli_get_should_not_be_called, + httpcli_post_should_not_be_called); + grpc_credentials_get_request_metadata(refresh_token_creds, test_service_url, + on_oauth2_creds_get_metadata_success, + (void *)test_user_data); + + grpc_credentials_unref(refresh_token_creds); + grpc_httpcli_set_override(NULL, NULL); +} + +static void test_refresh_token_creds_failure(void) { + grpc_credentials *refresh_token_creds = + grpc_refresh_token_credentials_create(test_refresh_token_str); + grpc_httpcli_set_override(httpcli_get_should_not_be_called, + refresh_token_httpcli_post_failure); + GPR_ASSERT(grpc_credentials_has_request_metadata(refresh_token_creds)); + GPR_ASSERT(grpc_credentials_has_request_metadata_only(refresh_token_creds)); + grpc_credentials_get_request_metadata(refresh_token_creds, test_service_url, + on_oauth2_creds_get_metadata_failure, + (void *)test_user_data); + grpc_credentials_unref(refresh_token_creds); + grpc_httpcli_set_override(NULL, NULL); +} + static void validate_jwt_encode_and_sign_params( const grpc_auth_json_key *json_key, const char *scope, gpr_timespec token_lifetime) { @@ -515,13 +599,13 @@ static void validate_service_account_http_request( GPR_ASSERT(body != NULL); GPR_ASSERT(body_size != 0); gpr_asprintf(&expected_body, "%s%s", - expected_service_account_http_body_prefix, test_signed_jwt); + GRPC_SERVICE_ACCOUNT_POST_BODY_PREFIX, test_signed_jwt); GPR_ASSERT(strlen(expected_body) == body_size); - GPR_ASSERT(!memcmp(expected_body, body, body_size)); + GPR_ASSERT(memcmp(expected_body, body, body_size) == 0); gpr_free(expected_body); GPR_ASSERT(request->use_ssl); - GPR_ASSERT(strcmp(request->host, "www.googleapis.com") == 0); - GPR_ASSERT(strcmp(request->path, "/oauth2/v3/token") == 0); + GPR_ASSERT(strcmp(request->host, GRPC_GOOGLE_OAUTH2_SERVICE_HOST) == 0); + GPR_ASSERT(strcmp(request->path, GRPC_GOOGLE_OAUTH2_SERVICE_TOKEN_PATH) == 0); GPR_ASSERT(request->hdr_count == 1); GPR_ASSERT(strcmp(request->hdrs[0].key, "Content-Type") == 0); GPR_ASSERT(strcmp(request->hdrs[0].value, @@ -711,6 +795,8 @@ int main(int argc, char **argv) { test_ssl_oauth2_iam_composite_creds(); test_compute_engine_creds_success(); test_compute_engine_creds_failure(); + test_refresh_token_creds_success(); + test_refresh_token_creds_failure(); test_service_account_creds_success(); test_service_account_creds_http_failure(); test_service_account_creds_signing_failure(); diff --git a/test/core/security/fetch_oauth2.c b/test/core/security/fetch_oauth2.c index 748a5982fdeb41343874c06b523c54e96147df37..cc847c82f71c4e5dd5c55d62e5753a3d5792d98d 100644 --- a/test/core/security/fetch_oauth2.c +++ b/test/core/security/fetch_oauth2.c @@ -34,7 +34,6 @@ #include <stdio.h> #include <string.h> -#include "src/core/security/credentials.h" #include <grpc/grpc.h> #include <grpc/grpc_security.h> #include <grpc/support/alloc.h> @@ -43,6 +42,9 @@ #include <grpc/support/slice.h> #include <grpc/support/sync.h> +#include "src/core/security/credentials.h" +#include "src/core/support/file.h" + typedef struct { gpr_cv cv; gpr_mu mu; @@ -74,50 +76,50 @@ static void on_oauth2_response(void *user_data, grpc_mdelem **md_elems, static grpc_credentials *create_service_account_creds( const char *json_key_file_path, const char *scope) { - char json_key[8192]; /* Should be plenty. */ - char *current = json_key; - FILE *json_key_file = fopen(json_key_file_path, "r"); - if (json_key_file == NULL) { - gpr_log(GPR_ERROR, "Invalid path for json key file: %s.", - json_key_file_path); + int success; + gpr_slice json_key = gpr_load_file(json_key_file_path, &success); + if (!success) { + gpr_log(GPR_ERROR, "Could not read file %s.", json_key_file_path); exit(1); } + return grpc_service_account_credentials_create( + (const char *)GPR_SLICE_START_PTR(json_key), scope, + grpc_max_auth_token_lifetime); +} - do { - size_t bytes_read = fread( - current, 1, sizeof(json_key) - (current - json_key), json_key_file); - if (bytes_read == 0) { - if (!feof(json_key_file)) { - gpr_log(GPR_ERROR, "Error occured while reading %s.", - json_key_file_path); - exit(1); - } - break; - } - current += bytes_read; - } while (sizeof(json_key) > (size_t)(current - json_key)); - - if ((current - json_key) == sizeof(json_key)) { - gpr_log(GPR_ERROR, "Json key file %s exceeds size limit (%d bytes).", - json_key_file_path, (int)sizeof(json_key)); +static grpc_credentials *create_refresh_token_creds( + const char *json_refresh_token_file_path) { + int success; + gpr_slice refresh_token = + gpr_load_file(json_refresh_token_file_path, &success); + if (!success) { + gpr_log(GPR_ERROR, "Could not read file %s.", json_refresh_token_file_path); exit(1); } - fclose(json_key_file); - - return grpc_service_account_credentials_create(json_key, scope, - grpc_max_auth_token_lifetime); + return grpc_refresh_token_credentials_create( + (const char *)GPR_SLICE_START_PTR(refresh_token)); } int main(int argc, char **argv) { synchronizer sync; grpc_credentials *creds = NULL; char *json_key_file_path = NULL; + char *json_refresh_token_file_path = NULL; int use_gce = 0; char *scope = NULL; gpr_cmdline *cl = gpr_cmdline_create("fetch_oauth2"); - gpr_cmdline_add_string(cl, "json_key", "File path of the json key.", + gpr_cmdline_add_string(cl, "json_key", + "File path of the json key. Mutually exclusive with " + "--json_refresh_token.", &json_key_file_path); - gpr_cmdline_add_string(cl, "scope", "Space delimited permissions.", &scope); + gpr_cmdline_add_string(cl, "json_refresh_token", + "File path of the json refresh token. Mutually " + "exclusive with --json_key.", + &json_refresh_token_file_path); + gpr_cmdline_add_string(cl, "scope", + "Space delimited permissions. Only used for " + "--json_key, ignored otherwise.", + &scope); gpr_cmdline_add_flag( cl, "gce", "Get a token from the GCE metadata server (only works in GCE).", @@ -126,6 +128,12 @@ int main(int argc, char **argv) { grpc_init(); + if (json_key_file_path != NULL && json_refresh_token_file_path != NULL) { + gpr_log(GPR_ERROR, + "--json_key and --json_refresh_token are mutually exclusive."); + exit(1); + } + if (use_gce) { if (json_key_file_path != NULL || scope != NULL) { gpr_log(GPR_INFO, @@ -137,6 +145,15 @@ int main(int argc, char **argv) { gpr_log(GPR_ERROR, "Could not create gce credentials."); exit(1); } + } else if (json_refresh_token_file_path != NULL) { + creds = create_refresh_token_creds(json_refresh_token_file_path); + if (creds == NULL) { + gpr_log(GPR_ERROR, + "Could not create refresh token creds. %s does probably not " + "contain a valid json refresh token.", + json_refresh_token_file_path); + exit(1); + } } else { if (json_key_file_path == NULL) { gpr_log(GPR_ERROR, "Missing --json_key option."); diff --git a/test/core/security/json_token_test.c b/test/core/security/json_token_test.c index ca5b8891023e7e216e5aea9d5eccbd5ccdb68dda..b43e0425ee2af3e5164243ece5b915f09cd44965 100644 --- a/test/core/security/json_token_test.c +++ b/test/core/security/json_token_test.c @@ -78,6 +78,13 @@ static const char test_json_key_str_part3[] = "\"777-abaslkan11hlb6nmim3bpspl31ud.apps.googleusercontent." "com\", \"type\": \"service_account\" }"; +/* Test refresh token. */ +static const char test_refresh_token_str[] = + "{ \"client_id\": \"32555999999.apps.googleusercontent.com\"," + " \"client_secret\": \"EmssLNjJy1332hD4KFsecret\"," + " \"refresh_token\": \"1/Blahblasj424jladJDSGNf-u4Sua3HDA2ngjd42\"," + " \"type\": \"authorized_user\"}"; + static const char test_scope[] = "myperm1 myperm2"; static const char test_service_url[] = "https://foo.com/foo.v1"; @@ -419,6 +426,64 @@ static void test_jwt_creds_jwt_encode_and_sign(void) { jwt_creds_check_jwt_claim); } +static void test_parse_refresh_token_success(void) { + grpc_auth_refresh_token refresh_token = + grpc_auth_refresh_token_create_from_string(test_refresh_token_str); + GPR_ASSERT(grpc_auth_refresh_token_is_valid(&refresh_token)); + GPR_ASSERT(refresh_token.type != NULL && + (strcmp(refresh_token.type, "authorized_user") == 0)); + GPR_ASSERT(refresh_token.client_id != NULL && + (strcmp(refresh_token.client_id, + "32555999999.apps.googleusercontent.com") == 0)); + GPR_ASSERT( + refresh_token.client_secret != NULL && + (strcmp(refresh_token.client_secret, "EmssLNjJy1332hD4KFsecret") == 0)); + GPR_ASSERT(refresh_token.refresh_token != NULL && + (strcmp(refresh_token.refresh_token, + "1/Blahblasj424jladJDSGNf-u4Sua3HDA2ngjd42") == 0)); + grpc_auth_refresh_token_destruct(&refresh_token); +} + +static void test_parse_refresh_token_failure_no_type(void) { + const char refresh_token_str[] = + "{ \"client_id\": \"32555999999.apps.googleusercontent.com\"," + " \"client_secret\": \"EmssLNjJy1332hD4KFsecret\"," + " \"refresh_token\": \"1/Blahblasj424jladJDSGNf-u4Sua3HDA2ngjd42\"}"; + grpc_auth_refresh_token refresh_token = + grpc_auth_refresh_token_create_from_string(refresh_token_str); + GPR_ASSERT(!grpc_auth_refresh_token_is_valid(&refresh_token)); +} + +static void test_parse_refresh_token_failure_no_client_id(void) { + const char refresh_token_str[] = + "{ \"client_secret\": \"EmssLNjJy1332hD4KFsecret\"," + " \"refresh_token\": \"1/Blahblasj424jladJDSGNf-u4Sua3HDA2ngjd42\"," + " \"type\": \"authorized_user\"}"; + grpc_auth_refresh_token refresh_token = + grpc_auth_refresh_token_create_from_string(refresh_token_str); + GPR_ASSERT(!grpc_auth_refresh_token_is_valid(&refresh_token)); +} + +static void test_parse_refresh_token_failure_no_client_secret(void) { + const char refresh_token_str[] = + "{ \"client_id\": \"32555999999.apps.googleusercontent.com\"," + " \"refresh_token\": \"1/Blahblasj424jladJDSGNf-u4Sua3HDA2ngjd42\"," + " \"type\": \"authorized_user\"}"; + grpc_auth_refresh_token refresh_token = + grpc_auth_refresh_token_create_from_string(refresh_token_str); + GPR_ASSERT(!grpc_auth_refresh_token_is_valid(&refresh_token)); +} + +static void test_parse_refresh_token_failure_no_refresh_token(void) { + const char refresh_token_str[] = + "{ \"client_id\": \"32555999999.apps.googleusercontent.com\"," + " \"client_secret\": \"EmssLNjJy1332hD4KFsecret\"," + " \"type\": \"authorized_user\"}"; + grpc_auth_refresh_token refresh_token = + grpc_auth_refresh_token_create_from_string(refresh_token_str); + GPR_ASSERT(!grpc_auth_refresh_token_is_valid(&refresh_token)); +} + int main(int argc, char **argv) { grpc_test_init(argc, argv); test_parse_json_key_success(); @@ -430,5 +495,10 @@ int main(int argc, char **argv) { test_parse_json_key_failure_no_private_key(); test_service_account_creds_jwt_encode_and_sign(); test_jwt_creds_jwt_encode_and_sign(); + test_parse_refresh_token_success(); + test_parse_refresh_token_failure_no_type(); + test_parse_refresh_token_failure_no_client_id(); + test_parse_refresh_token_failure_no_client_secret(); + test_parse_refresh_token_failure_no_refresh_token(); return 0; } diff --git a/test/cpp/interop/client.cc b/test/cpp/interop/client.cc index ae68f7a55649b79be08f46123f690c0058a98c8e..e5645e568e0871ef3766409c7d716caef5107c8e 100644 --- a/test/cpp/interop/client.cc +++ b/test/cpp/interop/client.cc @@ -73,6 +73,7 @@ DEFINE_string(test_case, "large_unary", "ping_pong : full-duplex streaming; " "service_account_creds : large_unary with service_account auth; " "compute_engine_creds: large_unary with compute engine auth; " + "jwt_token_creds: large_unary with JWT token auth; " "all : all of above."); DEFINE_string(default_service_account, "", "Email of GCE default service account"); @@ -85,6 +86,7 @@ using grpc::ClientContext; using grpc::ComputeEngineCredentials; using grpc::CreateTestChannel; using grpc::Credentials; +using grpc::JWTCredentials; using grpc::ServiceAccountCredentials; using grpc::testing::ResponseParameters; using grpc::testing::SimpleRequest; @@ -146,6 +148,13 @@ std::shared_ptr<ChannelInterface> CreateChannelForTestCase( creds = ComputeEngineCredentials(); return CreateTestChannel(host_port, FLAGS_server_host_override, FLAGS_enable_ssl, FLAGS_use_prod_roots, creds); + } else if (test_case == "jwt_token_creds") { + std::unique_ptr<Credentials> creds; + GPR_ASSERT(FLAGS_enable_ssl); + grpc::string json_key = GetServiceAccountJsonKey(); + creds = JWTCredentials(json_key, std::chrono::hours(1)); + return CreateTestChannel(host_port, FLAGS_server_host_override, + FLAGS_enable_ssl, FLAGS_use_prod_roots, creds); } else { return CreateTestChannel(host_port, FLAGS_server_host_override, FLAGS_enable_ssl, FLAGS_use_prod_roots); @@ -227,6 +236,21 @@ void DoServiceAccountCreds() { gpr_log(GPR_INFO, "Large unary with service account creds done."); } +void DoJwtTokenCreds() { + gpr_log(GPR_INFO, + "Sending a large unary rpc with JWT token credentials ..."); + std::shared_ptr<ChannelInterface> channel = + CreateChannelForTestCase("jwt_token_creds"); + SimpleRequest request; + SimpleResponse response; + request.set_fill_username(true); + PerformLargeUnary(channel, &request, &response); + GPR_ASSERT(!response.username().empty()); + grpc::string json_key = GetServiceAccountJsonKey(); + GPR_ASSERT(json_key.find(response.username()) != grpc::string::npos); + gpr_log(GPR_INFO, "Large unary with JWT token creds done."); +} + void DoLargeUnary() { gpr_log(GPR_INFO, "Sending a large unary rpc..."); std::shared_ptr<ChannelInterface> channel = @@ -415,6 +439,8 @@ int main(int argc, char** argv) { DoServiceAccountCreds(); } else if (FLAGS_test_case == "compute_engine_creds") { DoComputeEngineCreds(); + } else if (FLAGS_test_case == "jwt_token_creds") { + DoJwtTokenCreds(); } else if (FLAGS_test_case == "all") { DoEmpty(); DoLargeUnary(); @@ -422,9 +448,10 @@ int main(int argc, char** argv) { DoResponseStreaming(); DoHalfDuplex(); DoPingPong(); - // service_account_creds can only run with ssl. + // service_account_creds and jwt_token_creds can only run with ssl. if (FLAGS_enable_ssl) { DoServiceAccountCreds(); + DoJwtTokenCreds(); } // compute_engine_creds only runs in GCE. } else { @@ -432,7 +459,7 @@ int main(int argc, char** argv) { GPR_ERROR, "Unsupported test case %s. Valid options are all|empty_unary|" "large_unary|client_streaming|server_streaming|half_duplex|ping_pong|" - "service_account_creds|compute_engine_creds", + "service_account_creds|compute_engine_creds|jwt_token_creds", FLAGS_test_case.c_str()); } diff --git a/tools/dockerfile/grpc_python/Dockerfile b/tools/dockerfile/grpc_python/Dockerfile index 58a3d8c14f1c2aa6c5bdb1d913f750dd361865a4..fd07e9cc6a99ab147ca2a39b91c0a5f224de1c67 100644 --- a/tools/dockerfile/grpc_python/Dockerfile +++ b/tools/dockerfile/grpc_python/Dockerfile @@ -53,13 +53,15 @@ RUN cd /var/local/git/grpc \ && python2.7 -B -m grpc._adapter._links_test \ && python2.7 -B -m grpc._adapter._lonely_rear_link_test \ && python2.7 -B -m grpc._adapter._low_test \ - && python2.7 -B -m grpc.framework.assembly.implementations_test \ + && python2.7 -B -m grpc.early_adopter.implementations_test \ && python2.7 -B -m grpc.framework.base.packets.implementations_test \ && python2.7 -B -m grpc.framework.face.blocking_invocation_inline_service_test \ && python2.7 -B -m grpc.framework.face.event_invocation_synchronous_event_service_test \ && python2.7 -B -m grpc.framework.face.future_invocation_asynchronous_event_service_test \ && python2.7 -B -m grpc.framework.foundation._later_test \ - && python2.7 -B -m grpc.framework.foundation._logging_pool_test + && python2.7 -B -m grpc.framework.foundation._logging_pool_test \ + && python2.7 -B -m interop._insecure_interop_test \ + && python2.7 -B -m interop._secure_interop_test # Add a cacerts directory containing the Google root pem file, allowing the interop client to access the production test instance ADD cacerts cacerts diff --git a/tools/run_tests/run_tests.py b/tools/run_tests/run_tests.py index aee19cdc42d6ec9b106ce39d045dc679922584a7..a132ef4541361618dbf7b1888436e58f01de7f2f 100755 --- a/tools/run_tests/run_tests.py +++ b/tools/run_tests/run_tests.py @@ -240,7 +240,7 @@ _CONFIGS = { } -_DEFAULT = ['dbg', 'opt'] +_DEFAULT = ['opt'] _LANGUAGES = { 'c++': CLanguage('cxx', 'c++'), 'c': CLanguage('c', 'c'),