-
Notifications
You must be signed in to change notification settings - Fork 4.8k
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
NET9 HttpClient isn't following the OTel spec for some attributes #109847
Comments
Re: AppContext.SetSwitch("System.Net.Http.DisableUriRedaction", true);
Environment.SetEnvironmentVariable("DOTNET_SYSTEM_NET_HTTP_DISABLEURIREDACTION", "1"); Re: method, we'll currently populate runtime/src/libraries/System.Net.Http/src/System/Net/Http/DiagnosticsHandler.cs Lines 121 to 126 in 1e98c05
|
Oh no.... now there is another flag for this that we need to be aware too besides the OTEL redaction one? This is really suboptimal to say the least. I still don't understand why the team decided to do this redaction by default 😞 |
Thanks for the reply @MihaZupan! Re: Follow up question; is this the correct behavior?I understand why query strings are redacted, and it's obvious when it happens because this is recorded with the asterisk The PR that made this change seems to suggest that only query string would be affected: #103769 and the doc page for "DisableUriRedaction" only mentions query strings: https://learn.microsoft.com/en-us/dotnet/core/compatibility/networking/9.0/query-redaction-events Additionally, from a casual search multiple specifications define the fragment as separate and distinct from the query. |
(Edit: Originally copied the wrong text into the quote) IIRC we did it to keep the implementation simple and fast. We may consider to change it in .NET 10.
We need defaults which are "safe enough" for most users. Accidentally emitting unredacted query values may lead to serious privacy incidents, we have customer evidence on this.
I wonder which specific flags do you mean? Assuming the HttpClient built-in OTel would be feature-complete (meaning that eg. enrichment is implemented) do you still need to worry about the OTEL configuration? @julealgon @TimothyMothra if there was an option to customize Uri redaction via a callback or by setting |
I can totally accept that you have evidence of people doing this, but even then I don't think it should be up to the framework to "protect" those people. People do all sorts of terrible things, like exposing credentials in source code, in logs, etc, but we don't suddenly start enforcing redaction by default in all logs and start throwing errors when the word "password" exists somewhere. In this case, IMHO, devs should just know what the best practices are and follow them. If they expose something in a querystring, that's on them to suffer the consequences.
I'm talking about these:
Which we already maintain on our side. Now we have to also add this new Additionally, keep in mind that companies sometimes have complex setups. We have a very large solution right now that is still targeting NET472. Some of the projects in that solution are actually stuck on .NET Framework land, as they are WebForms projects. This means we'll have a mix of framework targets for the foreseeable future as we start to migrate the rest of that solution to .NET8 and .NET9 soon. Thus, we'll have to live with all of these settings at the same time, since some projects cannot take advantage of the built-in HTTP tracing and have to keep using the OTEL instrumentation. And even outside of this solution, we have many other smaller solutions already targeting NET8, so in effect we already have a mix of frameworks even before a migration of the legacy projects start to happen.
That's what I proposed when I first saw the redaction changes in the OTEL libraries. Instead of forcing redaction like what you are doing now, you could just expose a simple redaction mechanism: I even suggested using the And let consumers do what they want: if they want the redaction, they apply it. Making it the other way around is super intrusive, opinionated (in a bad way IMHO) and handholdy. To make things even worse, all the OTEL packages at the time were marked as "vulnerable", which increased NuGet warning noise on our side. If writing a querystring is considered a "vulnerability", perhaps the I strongly dislike this direction, as you can probably tell by the above. |
Do you know of a real-world example where you might care about the casing of the HTTP method specified, or is this just for the sake of following the spec to the letter even if there's no practical use to it? |
Happy Friday and thanks everyone for sharing information! Regarding HTTP Methods
That's a good question, no I don't know of any real-world examples. I can ping some people in OTel who might know the reasoning behind this specific rule. I absolutely have my OTel-goggles on and trying to follow the spec to the letter. I'm also thinking about OTel users who would be upgrading to NET9 and then their exported attributes have changed. Regarding Redaction
Thanks for the reply. Please consider updating your docs to mention that the fragment is included in the redaction.
I expect some users would be very interested in a callback and I think this would be worth exploring. Can you share a conversational example of how setting the Redaction in general has been a divisive subject, and I think all parties involved are still trying to find the right balance. FYI the OpenTelemetry Spec recently merged a new rule naming specific query string keys that MUST be redacted by default (open-telemetry/semantic-conventions#971). NET 9 and OTel-dotnet are technically compliant because we both redact everything by default. |
HI @julealgon, I really appreciate all your input. I don't expect any major changes in the near future. But I'm committed to having this clearly and completely documented so users don't need to search for this information.
My understanding is that it's not only devs that suffer but also customers and/or end-users. The trend that I'm seeing is that technologies are moving to be secure by default to protect the entire industry/ecosystem. Please continue sharing your insights and holding us accountable to do this in a way that's transparent and configurable!!! |
Triage: |
Beyond documentation, it might worth to review the discussions that resulted in open-telemetry/semantic-conventions#971. However, working with an ever-changing deny list is very impractical from the instrumented library's perspective IMHO.
Exactly. There is an inherent tradeoff between observability and security. Our current guidelines require us to prioritize security.
When implemented, it would the equivalent of the server-side |
Removing the |
@antonfirsov can you elaborate what extra allocation(s) are needed here? Doesn't the original |
The string behind |
Opened #110018 to track the customizable uri redaction feature request. |
Description
This is a follow up to #104251.
I'm working on the OpenTelemetry.Instrumentation.Http library, which should not overwrite attributes set by NET9's runtime: open-telemetry/opentelemetry-dotnet-contrib#2314
I found two examples where runtime isn't following the OTel spec:
URL Fragement Identifier
OTel Spec (link): "[4]: For network calls, URL usually has scheme://host[:port][path][?query][#fragment] format, where the fragment is not transmitted over HTTP, but if it is known, it SHOULD be included nevertheless."
Runtime is NOT recording the Fragment in
url.full
.HTTP Method
OTel Spec (link): "[1]: HTTP method names are case-sensitive and http.request.method attribute value MUST match a known HTTP method name exactly. Instrumentations for specific web frameworks that consider HTTP methods to be case insensitive, SHOULD populate a canonical equivalent. Tracing instrumentations that do so, MUST also set http.request.method_original to the original value."
Runtime is treating the HTTP Method as case-insensitive and not setting
http.request.method_original
(ie: "Get" vs "GET")Reproduction Steps
CSPROJ
PROGRAM.CS
Expected behavior
Using the OpenTelemetry.Instrumentation.Http instrumentation:
Actual behavior
Using the NET9 native instrumentation:
Note that "http.request.method_original: Get" is missing.
Regression?
No response
Known Workarounds
No response
Configuration
No response
Other information
No response
The text was updated successfully, but these errors were encountered: