grpc / grpc-dotnet

gRPC for .NET
Apache License 2.0
4.21k stars 773 forks source link

Documentation for importing proto files #1458

Open JamesNK opened 3 years ago

JamesNK commented 3 years ago

Importing and sharing proto files is a common tripping point. Grpc.Tools doesn't really have docs.

Document this to help people and provide a link that we can point people towards.

andyfurniss4 commented 3 years ago

After watching your .NET 6 video on gRPC (never used it before but I'm interested!), I was wondering what the best approach is for sharing protos between services so I'd be interested to see what the recommendations are here.

We have a bunch of microservices, each of which lives in a separate repository and thus, a separate solution. However, we'd like to centralise the protos/contracts for each service's request/response models. Initially I was thinking NuGet was the answer and I found this old issue: https://github.com/grpc/grpc-dotnet/issues/183 on that subject but it's pretty old and the activity seems to have died a while ago.

Liversage commented 2 years ago

I found this old issue: #183 on that subject but it's pretty old and the activity seems to have died a while ago.

@andyfurniss4 One of the proposed solutions in that issue works well except that it has problems with IntelliSense. To me this must be a problem with the build tools and I was hoping that it would be resolved but unfortunately it doesn't seem so. I have created a demo project that shows both how to share a NuGet package with .proto files and also the IntelliSense problem.

AntoCanza commented 2 years ago

@Liversage do you have some tips on how to split definitions into multiple proto files? for example i want to have one with all messages definition and the other one with service definition. i have tried with import, like google documentation says, but it's not working.

UPDATE: https://github.com/grpc/grpc-dotnet/tree/master/examples#liber this is the example

Liversage commented 2 years ago

@AntoCanza I don't have any advice on why import doesn't work for you. It works for me.

Blackclaws commented 2 years ago

Import is dependent on the path, where the path is relative to where to compiler is being run. Depending on how your directory structure is set up you might need to add/remove relative folders.

runenilsenoe commented 2 years ago

@AntoCanza using the ProtoRoot parameter is nice if you want to share certain commonly used files. Take this file structure as an example:

AntoCanza commented 2 years ago

@AntoCanza using the ProtoRoot parameter is nice if you want to share certain commonly used files. Take this file structure as an example:

* Protos
  -> project1
  ----------> thing1.proto
  -> shared
  ----------> sharedmodels.proto
  Considering this,you can include **thing1** with ProtoRoot set to the **Proto/** folder.
  Then you could reference an import from sharedmodels inside the thing1.proto with respect to that root; example
  `import "shared/sharedmodels.proto";`

yes, works perfectly following this.

pjh1974 commented 2 years ago

Having looked at the Liber example, I can see how you make the import work, as the greet.proto and common.proto files reside in the same folder and are linked into the projects. This seems like a simplification that would only lend itself to scenarios where the client and server reside in the same solution.

The ideal scenario for many would be to make Common.csproj build a Nuget package which contains both the .proto file and the accompanying partial class. I presume I could then do some "Nuget Magic " to present the .proto file to the consuming project, which it could then import into any protos it defines. Would this even be possible?

My goal here would be to create a Nuget package that defines both Decimal and Guid messages; which I could then use in all my microservices. The fact that this (seemingly obvious) library hasn't already been created suggests that it is either not possible, or not desirable and I am missing something. Any advice would be gratefully received.

runenilsenoe commented 2 years ago

Having looked at the Liber example, I can see how you make the import work, as the greet.proto and common.proto files reside in the same folder and are linked into the projects. This seems like a simplification that would only lend itself to scenarios where the client and server reside in the same solution.

The ideal scenario for many would be to make Common.csproj build a Nuget package which contains both the .proto file and the accompanying partial class. I presume I could then do some "Nuget Magic " to present the .proto file to the consuming project, which it could then import into any protos it defines. Would this even be possible?

My goal here would be to create a Nuget package that defines both Decimal and Guid messages; which I could then use in all my microservices. The fact that this (seemingly obvious) library hasn't already been created suggests that it is either not possible, or not desirable and I am missing something. Any advice would be gratefully received.

Ill se if i Get time to setup an example of our implementation. We Are creative a nuget package for each project, and all generic request types Are generated into a shared nuget package. Which The other packages references if need be. I think The obviousness of this might be overthought as The reward of adding an extra external package reference for a couple of generic types might be more work than just writing them

I might have time this evening to provide an example

tonydnewell commented 1 year ago

@JamesNK BUILD-INTEGRATION.md has now been updated with how to share proto files.