-
Notifications
You must be signed in to change notification settings - Fork 780
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
First pass at Grpc.StatusProto API #2205
Conversation
Is the plan still for a lot of this to be in Google.Api.CommonProtos? If so, it's probably worth indicating which bits would be there in this PR. |
The parts of this that could be moved into
but as I don't have ownership of |
That split sounds reasonable to me. Will review when I get a chance. |
[gRPC richer error model](https://grpc.io/docs/guides/error/#richer-error-model). | ||
|
||
It had dependencies NuGet packages on: | ||
* `Google.Api.CommonProtos` - to provide the proto implementations used by the richer error model |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
as discussed offline, if some of the C# gets added to Google.Api.CommonProtos as extension methods, let's pay close attention to in which namespace these extension methods live, since we don't want to require adding too many "using x.y.z" statements to be able to use the Grpc.StatusProto functionality (in order for the extension methods to become visible).
src/Grpc.StatusProto/README.md
Outdated
Note: the [status.proto](https://github.com/googleapis/googleapis/blob/master/google/rpc/status.proto) | ||
and [error_details.proto](https://github.com/googleapis/googleapis/blob/master/google/rpc/error_details.proto) | ||
files are not currently provided in any NuGet packages. The text for those proto files can be copied from | ||
the given links and included in your project. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
nit: reword "The text for those proto files can be copied from
the given links and included in your project."
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is interesting... do you think it would be beneficial to ship them in Google.Api.CommonProtos? I wouldn't be averse to that, but I'd need to consult the rest of the team.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
At this point, I'd say this wouldn't help much. I'd probably help if we had a general mechanism for shipping .proto file in nuget packages and Grpc.Tools could autogenerate source code for them (see #183), but we currently don't have that.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
As it happens, we had a feature request for that last week: googleapis/gax-dotnet#715
@jtattermusch If you believe it wouldn't actually help much, please could you comment on that issue?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It is on my list to document a standard way/best practices for shipping proto files in NuGet packages so that Grpc.Tools can easily pick them up. Basically what @JamesNK does in the Microsoft.AspNetCore.Grpc.JsonTranscoding package.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I've focused on the API surface rather than the implementation and tests. I suspect we'll have more discussions.
src/Grpc.StatusProto/README.md
Outdated
Message = "Simple error message", | ||
Details = | ||
{ | ||
Any.Pack(new ErrorInfo |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
FYI: There are Google-internal proposals around the use of ErrorInfo; I'm checking on the status of those, but they could affect the preferred layout for the richer error model.
src/Grpc.StatusProto/README.md
Outdated
Note: the [status.proto](https://github.com/googleapis/googleapis/blob/master/google/rpc/status.proto) | ||
and [error_details.proto](https://github.com/googleapis/googleapis/blob/master/google/rpc/error_details.proto) | ||
files are not currently provided in any NuGet packages. The text for those proto files can be copied from | ||
the given links and included in your project. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is interesting... do you think it would be beneficial to ship them in Google.Api.CommonProtos? I wouldn't be averse to that, but I'd need to consult the rest of the team.
@jtattermusch @jskeet @JamesNK There is now less code! In summary:
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Added a bunch of comments, but they are mostly minor.
Overall this is looking good so we are getting closer to being able to merge this soon (ish).
src/Grpc.StatusProto/README.md
Outdated
Note: the [status.proto](https://github.com/googleapis/googleapis/blob/master/google/rpc/status.proto) | ||
and [error_details.proto](https://github.com/googleapis/googleapis/blob/master/google/rpc/error_details.proto) | ||
files are not currently provided in any NuGet packages. The text for those proto files can be copied from | ||
the given links and included in your project. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
At this point, I'd say this wouldn't help much. I'd probably help if we had a general mechanism for shipping .proto file in nuget packages and Grpc.Tools could autogenerate source code for them (see #183), but we currently don't have that.
@JamesNK can you please review? |
Updated from review comments. I've also added extension methods I still need to update the project files to add net8.0 but as I branched before the net8.0 change I didn't want to break anything. The README.md is getting quite long but there isn't really anywhere else to add documentation at the moment. I'm trying to keep a balance between brevity and enough detail to be useful without giving a full tutorial. |
I'm not quite sure what the expectation is for me personally at this point. I suggest that I wait for @JamesNK and @jtattermusch to be happy, then I'll re-review - paying particular attention to the code that would be in Google.Api.CommonProtos. |
That seems fair. I think I'm mostly happy (I'll give this one more final pass once we believe the PR is in its final form). We're waiting for @JamesNK's review currently, since he haven't provided any comments yet. Also, can you remind me what exactly is the plan for "code that should be in Google.Api.CommonProtos"? Is the code going be merged to as part of this PR first (and eventually migrated to Google.Api.CommonProtos) or are we planning to merge this PR once that code is in Google.Api.CommonProtos? |
@JamesNK friendly ping on the review. |
/// The found <see cref="Google.Rpc.Status"/> or null if it was | ||
/// not present or could the data could not be parsed. | ||
/// </returns> | ||
public static Google.Rpc.Status? GetRpcStatus(this Metadata metadata, bool throwOnParseError=false) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
public static Google.Rpc.Status? GetRpcStatus(this Metadata metadata, bool throwOnParseError=false) | |
public static Google.Rpc.Status? GetRpcStatus(this Metadata metadata, bool throwOnParseError = false) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why suppress the parse error by default? That seems like it could lead to errors disappearing.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Copying the behaviour from Google.Api.Gax.Grpc
https://github.com/googleapis/gax-dotnet/blob/897b4bdf84d5b314c424113a8bb633bb703ff1a3/Google.Api.Gax.Grpc/RpcExceptionExtensions.cs#L73-L81
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@jskeet Do you know this code? Why did you choose this behavior by default?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes, I know this code. It feels like if we're already in an error situation (which is where this code would usually be used), failing in a different way due to parse failures in metadata is unhelpful. It's a bit like ending up with an exception caused by disposing of a socket, when the original exception is trying to write to the socket, if you see what I mean.
Happy to discuss alternatives though.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think that not losing the original error (because reporting the error itself has problems) is my preference. But no strong views.
@jskeet @JamesNK @jtattermusch
Also |
Yes - and one thing I hadn't even thought to mention before is that we won't need to use extension methods there. It can just be a partial class. |
Should I/can I do that here too to make the moving easier? |
@jtattermusch @JamesNK Should I create a "proposal" for this feature? I've noticed there is one for python (L44-python-rich-status.md) |
To answer my own question, looks like partial classes can only be used in the same project/assembly. So no here. |
I'll leave this to @apolcyn, @JamesNK and @jskeet to decide. Note that since all the APIs are marked as experimental, we could start with the namespace being |
|
||
The `Google.Rpc.Status` extension method `ToRpcException` creates the appropriate `RpcException` from the status. | ||
|
||
__Example__ - creating and throwing a `RpcException`: |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Will there be a way to use this without requiring the implementation to throw an exception?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You can instead explicitly set the Status
and add to the ResponseTrailers
in the ServerCallContext
before returning from the call (this was documented in previous commit but was removed to keep it simple). However the client will still receive an Exception since any non-OK response status generates an exception on the client.
Co-authored-by: Cody Mullins <[email protected]>
@tonydnewell @JamesNK FYI, I've been using this in our (pre-production) app and it seems to work okay. There's probably some improvements that can eventually be made to make it less verbose (or perhaps extension libraries) but I'd +1 getting this merged in. |
There are things I'd still like changed:
|
FYI Changes to Google.Api.CommonProtos have been merged (moving the TODOs from this code to there). Waiting for Google.Api.CommonProtos 2.13.0 to be released before submitting further changes here. |
Just to set expectations, we're currently in a release freeze. I'd expect to release this around November 30th. I don't think there are any blockers for it other than the freeze - I may update to a newer version of protobuf first though (both in terms of generation and runtime). |
@tonydnewell What's the plan on finishing this? I can take over if you're unavailable. |
It is on my list for this week. I'll let you know if I don't get to it. |
@JamesNK I think I've covered all the review comments. I've also merged master into the branch as there were conflicting changes (package versioning changes). I just need to do some more sanity checks myself with some examples projects, but feel free to review the changes. |
Looks good. There are small things to clean up in XML comments but it doesn't need to be done now and this PR is long enough. |
[![Mend Renovate](https://app.renovatebot.com/images/banner.svg)](https://renovatebot.com) This PR contains the following updates: | Package | Change | Age | Adoption | Passing | Confidence | |---|---|---|---|---|---| | [Google.Protobuf](https://togithub.com/protocolbuffers/protobuf) | `3.25.2` -> `3.25.3` | [![age](https://developer.mend.io/api/mc/badges/age/nuget/Google.Protobuf/3.25.3?slim=true)](https://docs.renovatebot.com/merge-confidence/) | [![adoption](https://developer.mend.io/api/mc/badges/adoption/nuget/Google.Protobuf/3.25.3?slim=true)](https://docs.renovatebot.com/merge-confidence/) | [![passing](https://developer.mend.io/api/mc/badges/compatibility/nuget/Google.Protobuf/3.25.2/3.25.3?slim=true)](https://docs.renovatebot.com/merge-confidence/) | [![confidence](https://developer.mend.io/api/mc/badges/confidence/nuget/Google.Protobuf/3.25.2/3.25.3?slim=true)](https://docs.renovatebot.com/merge-confidence/) | | [Grpc.Net.Client](https://togithub.com/grpc/grpc-dotnet) | `2.60.0` -> `2.61.0` | [![age](https://developer.mend.io/api/mc/badges/age/nuget/Grpc.Net.Client/2.61.0?slim=true)](https://docs.renovatebot.com/merge-confidence/) | [![adoption](https://developer.mend.io/api/mc/badges/adoption/nuget/Grpc.Net.Client/2.61.0?slim=true)](https://docs.renovatebot.com/merge-confidence/) | [![passing](https://developer.mend.io/api/mc/badges/compatibility/nuget/Grpc.Net.Client/2.60.0/2.61.0?slim=true)](https://docs.renovatebot.com/merge-confidence/) | [![confidence](https://developer.mend.io/api/mc/badges/confidence/nuget/Grpc.Net.Client/2.60.0/2.61.0?slim=true)](https://docs.renovatebot.com/merge-confidence/) | | [NUnit](https://nunit.org/) ([source](https://togithub.com/nunit/nunit)) | `4.0.1` -> `4.1.0` | [![age](https://developer.mend.io/api/mc/badges/age/nuget/NUnit/4.1.0?slim=true)](https://docs.renovatebot.com/merge-confidence/) | [![adoption](https://developer.mend.io/api/mc/badges/adoption/nuget/NUnit/4.1.0?slim=true)](https://docs.renovatebot.com/merge-confidence/) | [![passing](https://developer.mend.io/api/mc/badges/compatibility/nuget/NUnit/4.0.1/4.1.0?slim=true)](https://docs.renovatebot.com/merge-confidence/) | [![confidence](https://developer.mend.io/api/mc/badges/confidence/nuget/NUnit/4.0.1/4.1.0?slim=true)](https://docs.renovatebot.com/merge-confidence/) | | [coverlet.collector](https://togithub.com/coverlet-coverage/coverlet) | `6.0.0` -> `6.0.1` | [![age](https://developer.mend.io/api/mc/badges/age/nuget/coverlet.collector/6.0.1?slim=true)](https://docs.renovatebot.com/merge-confidence/) | [![adoption](https://developer.mend.io/api/mc/badges/adoption/nuget/coverlet.collector/6.0.1?slim=true)](https://docs.renovatebot.com/merge-confidence/) | [![passing](https://developer.mend.io/api/mc/badges/compatibility/nuget/coverlet.collector/6.0.0/6.0.1?slim=true)](https://docs.renovatebot.com/merge-confidence/) | [![confidence](https://developer.mend.io/api/mc/badges/confidence/nuget/coverlet.collector/6.0.0/6.0.1?slim=true)](https://docs.renovatebot.com/merge-confidence/) | --- ### Release Notes <details> <summary>protocolbuffers/protobuf (Google.Protobuf)</summary> ### [`v3.25.3`](https://togithub.com/protocolbuffers/protobuf/compare/v3.25.2...v3.25.3) </details> <details> <summary>grpc/grpc-dotnet (Grpc.Net.Client)</summary> ### [`v2.61.0`](https://togithub.com/grpc/grpc-dotnet/releases/tag/v2.61.0) ##### What's Changed - Update Grpc.Tools to 2.60.0 by [@​JamesNK](https://togithub.com/JamesNK) in [https://github.com/grpc/grpc-dotnet/pull/2336](https://togithub.com/grpc/grpc-dotnet/pull/2336) - Bump dev version to 2.61.0-dev on master branch by [@​stanley-cheung](https://togithub.com/stanley-cheung) in [https://github.com/grpc/grpc-dotnet/pull/2337](https://togithub.com/grpc/grpc-dotnet/pull/2337) - Fix cancellation token reported when using retries by [@​JamesNK](https://togithub.com/JamesNK) in [https://github.com/grpc/grpc-dotnet/pull/2345](https://togithub.com/grpc/grpc-dotnet/pull/2345) - First pass at Grpc.StatusProto API by [@​tonydnewell](https://togithub.com/tonydnewell) in [https://github.com/grpc/grpc-dotnet/pull/2205](https://togithub.com/grpc/grpc-dotnet/pull/2205) - Add ProtoStatus example by [@​JamesNK](https://togithub.com/JamesNK) in [https://github.com/grpc/grpc-dotnet/pull/2273](https://togithub.com/grpc/grpc-dotnet/pull/2273) - Grpc.StatusProto clean up by [@​JamesNK](https://togithub.com/JamesNK) in [https://github.com/grpc/grpc-dotnet/pull/2349](https://togithub.com/grpc/grpc-dotnet/pull/2349) - Bump follow-redirects from 1.15.3 to 1.15.4 in /testassets/InteropTestsGrpcWebWebsite/Tests by [@​dependabot](https://togithub.com/dependabot) in [https://github.com/grpc/grpc-dotnet/pull/2352](https://togithub.com/grpc/grpc-dotnet/pull/2352) - Add key services tests for service and interceptor by [@​JamesNK](https://togithub.com/JamesNK) in [https://github.com/grpc/grpc-dotnet/pull/2356](https://togithub.com/grpc/grpc-dotnet/pull/2356) - Allow GrpcChannel to use WinHttpHandler on Windows Server 2019 by [@​JamesNK](https://togithub.com/JamesNK) in [https://github.com/grpc/grpc-dotnet/pull/2362](https://togithub.com/grpc/grpc-dotnet/pull/2362) - Add .NET 9 NuGet feed by [@​JamesNK](https://togithub.com/JamesNK) in [https://github.com/grpc/grpc-dotnet/pull/2365](https://togithub.com/grpc/grpc-dotnet/pull/2365) - Add missing package mapping for net9 feed by [@​JamesNK](https://togithub.com/JamesNK) in [https://github.com/grpc/grpc-dotnet/pull/2366](https://togithub.com/grpc/grpc-dotnet/pull/2366) - proposal: Build changelog based on previous stable version by [@​tomkerkhove](https://togithub.com/tomkerkhove) in [https://github.com/grpc/grpc-dotnet/pull/2269](https://togithub.com/grpc/grpc-dotnet/pull/2269) - Bump Grpc.Tools to 1.61.0 by [@​apolcyn](https://togithub.com/apolcyn) in [https://github.com/grpc/grpc-dotnet/pull/2370](https://togithub.com/grpc/grpc-dotnet/pull/2370) - Bump versions on v2.61.x by [@​apolcyn](https://togithub.com/apolcyn) in [https://github.com/grpc/grpc-dotnet/pull/2371](https://togithub.com/grpc/grpc-dotnet/pull/2371) - Bump to v2.61.0 on v2.61.x branch by [@​apolcyn](https://togithub.com/apolcyn) in [https://github.com/grpc/grpc-dotnet/pull/2374](https://togithub.com/grpc/grpc-dotnet/pull/2374) ##### New Contributors - [@​tonydnewell](https://togithub.com/tonydnewell) made their first contribution in [https://github.com/grpc/grpc-dotnet/pull/2205](https://togithub.com/grpc/grpc-dotnet/pull/2205) - [@​tomkerkhove](https://togithub.com/tomkerkhove) made their first contribution in [https://github.com/grpc/grpc-dotnet/pull/2269](https://togithub.com/grpc/grpc-dotnet/pull/2269) **Full Changelog**: grpc/grpc-dotnet@v2.60.0...v2.61.0 </details> <details> <summary>nunit/nunit (NUnit)</summary> ### [`v4.1.0`](https://togithub.com/nunit/nunit/releases/tag/4.1.0): NUnit 4.1.0 See [release notes](https://docs.nunit.org/articles/nunit/release-notes/framework.html#nunit-41---february-23-2024) </details> <details> <summary>coverlet-coverage/coverlet (coverlet.collector)</summary> ### [`v6.0.1`](https://togithub.com/coverlet-coverage/coverlet/releases/tag/v6.0.1) ##### Fixed - Uncovered lines in .NET 8 for inheriting records [#​1555](https://togithub.com/coverlet-coverage/coverlet/issues/1555) - Fix record constructors not covered when SkipAutoProps is true [#​1561](https://togithub.com/coverlet-coverage/coverlet/issues/1561) - Fix .NET 7 Method Group branch coverage issue [#​1447](https://togithub.com/coverlet-coverage/coverlet/issues/1447) - Fix ExcludeFromCodeCoverage does not exclude method in a partial class [#​1548](https://togithub.com/coverlet-coverage/coverlet/issues/1548) - Fix ExcludeFromCodeCoverage does not exclude F# task [#​1547](https://togithub.com/coverlet-coverage/coverlet/issues/1547) - Fix issues where ExcludeFromCodeCoverage ignored [#​1431](https://togithub.com/coverlet-coverage/coverlet/issues/1431) - Fix issues with ExcludeFromCodeCoverage attribute [#​1484](https://togithub.com/coverlet-coverage/coverlet/issues/1484) - Fix broken links in documentation [#​1514](https://togithub.com/coverlet-coverage/coverlet/issues/1514) - Fix problem with coverage for .net5 WPF application [#​1221](https://togithub.com/coverlet-coverage/coverlet/issues/1221) by https://github.com/lg2de - Fix unable to instrument module for Microsoft.AspNetCore.Mvc.Razor [#​1459](https://togithub.com/coverlet-coverage/coverlet/issues/1459) by https://github.com/lg2de ##### Improvements - Extended exclude by attribute feature to work with fully qualified name [#​1589](https://togithub.com/coverlet-coverage/coverlet/issues/1589) - Use System.CommandLine instead of McMaster.Extensions.CommandLineUtils [#​1474](https://togithub.com/coverlet-coverage/coverlet/issues/1474) by https://github.com/Bertk - Fix deadlog in Coverlet.Integration.Tests.BaseTest [#​1541](https://togithub.com/coverlet-coverage/coverlet/pull/1541) by https://github.com/Bertk - Add coverlet.msbuild.tasks unit tests [#​1534](https://togithub.com/coverlet-coverage/coverlet/pull/1534) by https://github.com/Bertk [Diff between 6.0.0 and 6.0.1](https://togithub.com/coverlet-coverage/coverlet/compare/v6.0.0...v6.0.1) </details> --- ### Configuration 📅 **Schedule**: Branch creation - "before 4am on Monday" (UTC), Automerge - At any time (no schedule defined). 🚦 **Automerge**: Disabled by config. Please merge this manually once you are satisfied. ♻ **Rebasing**: Whenever PR becomes conflicted, or you tick the rebase/retry checkbox. 👻 **Immortal**: This PR will be recreated if closed unmerged. Get [config help](https://togithub.com/renovatebot/renovate/discussions) if that's undesired. --- - [ ] <!-- rebase-check -->If you want to rebase/retry this PR, check this box --- This PR has been generated by [Mend Renovate](https://www.mend.io/free-developer-tools/renovate/). View repository job log [here](https://developer.mend.io/github/cerbos/cerbos-sdk-net). <!--renovate-debug:eyJjcmVhdGVkSW5WZXIiOiIzNy4xOTEuMCIsInVwZGF0ZWRJblZlciI6IjM3LjIxMi4wIiwidGFyZ2V0QnJhbmNoIjoibWFpbiJ9--> Signed-off-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> Signed-off-by: Oğuzhan Durgun <[email protected]> Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com>
Should this change dotnet/aspnetcore#51394 use these APIs as well? |
Maybe. I created an issue: dotnet/aspnetcore#55410 |
Grpc.StatusProto API and NuGet package for implementing the gRPC richer error model.
It is a work in progress. This draft PR is for reviewing the design and to enable discussion. No examples yet included.
@jtattermusch @JamesNK @jskeet