From 4f5e160679bf1ac37c7d3094a65690ce59986fc3 Mon Sep 17 00:00:00 2001 From: Max Bruce Date: Fri, 12 Feb 2021 07:59:44 -0800 Subject: [PATCH] feat(build): Add disable_package_emission option to tonic-build (#556) --- tonic-build/src/client.rs | 15 ++++++--------- tonic-build/src/prost.rs | 22 ++++++++++++++++++++-- tonic-build/src/server.rs | 12 ++++-------- 3 files changed, 30 insertions(+), 19 deletions(-) diff --git a/tonic-build/src/client.rs b/tonic-build/src/client.rs index db8eaa32c..cb0f728c7 100644 --- a/tonic-build/src/client.rs +++ b/tonic-build/src/client.rs @@ -7,10 +7,10 @@ use quote::{format_ident, quote}; /// /// This takes some `Service` and will generate a `TokenStream` that contains /// a public module with the generated client. -pub fn generate(service: &T, proto_path: &str) -> TokenStream { +pub fn generate(service: &T, emit_package: bool, proto_path: &str) -> TokenStream { let service_ident = quote::format_ident!("{}Client", service.name()); let client_mod = quote::format_ident!("{}_client", naive_snake_case(&service.name())); - let methods = generate_methods(service, proto_path); + let methods = generate_methods(service, emit_package, proto_path); let connect = generate_connect(&service_ident); let service_doc = generate_doc_comments(service.comment()); @@ -87,18 +87,15 @@ fn generate_connect(_service_ident: &syn::Ident) -> TokenStream { TokenStream::new() } -fn generate_methods(service: &T, proto_path: &str) -> TokenStream { +fn generate_methods(service: &T, emit_package: bool, proto_path: &str) -> TokenStream { let mut stream = TokenStream::new(); + let package = if emit_package { service.package() } else { "" }; for method in service.methods() { let path = format!( "/{}{}{}/{}", - service.package(), - if service.package().is_empty() { - "" - } else { - "." - }, + package, + if package.is_empty() { "" } else { "." }, service.identifier(), method.identifier() ); diff --git a/tonic-build/src/prost.rs b/tonic-build/src/prost.rs index f8284d4f0..cdc2e4a9b 100644 --- a/tonic-build/src/prost.rs +++ b/tonic-build/src/prost.rs @@ -19,6 +19,7 @@ pub fn configure() -> Builder { proto_path: "super".to_string(), #[cfg(feature = "rustfmt")] format: true, + emit_package: true, } } @@ -136,12 +137,20 @@ impl ServiceGenerator { impl prost_build::ServiceGenerator for ServiceGenerator { fn generate(&mut self, service: prost_build::Service, _buf: &mut String) { if self.builder.build_server { - let server = server::generate(&service, &self.builder.proto_path); + let server = server::generate( + &service, + self.builder.emit_package, + &self.builder.proto_path, + ); self.servers.extend(server); } if self.builder.build_client { - let client = client::generate(&service, &self.builder.proto_path); + let client = client::generate( + &service, + self.builder.emit_package, + &self.builder.proto_path, + ); self.clients.extend(client); } } @@ -184,6 +193,7 @@ pub struct Builder { pub(crate) field_attributes: Vec<(String, String)>, pub(crate) type_attributes: Vec<(String, String)>, pub(crate) proto_path: String, + pub(crate) emit_package: bool, out_dir: Option, #[cfg(feature = "rustfmt")] @@ -258,6 +268,14 @@ impl Builder { self } + /// Emits GRPC endpoints with no attached package. Effectively ignores protofile package declaration from grpc context. + /// + /// This effectively sets prost's exported package to an empty string. + pub fn disable_package_emission(mut self) -> Self { + self.emit_package = false; + self + } + /// Compile the .proto files and execute code generation. pub fn compile

(self, protos: &[P], includes: &[P]) -> io::Result<()> where diff --git a/tonic-build/src/server.rs b/tonic-build/src/server.rs index 0d0b00617..c64baedb6 100644 --- a/tonic-build/src/server.rs +++ b/tonic-build/src/server.rs @@ -8,7 +8,7 @@ use syn::{Ident, Lit, LitStr}; /// /// This takes some `Service` and will generate a `TokenStream` that contains /// a public module containing the server service and handler trait. -pub fn generate(service: &T, proto_path: &str) -> TokenStream { +pub fn generate(service: &T, emit_package: bool, proto_path: &str) -> TokenStream { let methods = generate_methods(service, proto_path); let server_service = quote::format_ident!("{}Server", service.name()); @@ -16,16 +16,12 @@ pub fn generate(service: &T, proto_path: &str) -> TokenStream { let server_mod = quote::format_ident!("{}_server", naive_snake_case(&service.name())); let generated_trait = generate_trait(service, proto_path, server_trait.clone()); let service_doc = generate_doc_comments(service.comment()); - + let package = if emit_package { service.package() } else { "" }; // Transport based implementations let path = format!( "{}{}{}", - service.package(), - if service.package().is_empty() { - "" - } else { - "." - }, + package, + if package.is_empty() { "" } else { "." }, service.identifier() ); let transport = generate_transport(&server_service, &server_trait, &path);